mirror of
https://github.com/libretro/mame.git
synced 2024-12-03 07:31:18 +00:00
Merge branch 'master' of https://github.com/mamedev/mame
This commit is contained in:
commit
b868f3115f
@ -1643,7 +1643,7 @@ Screen-Printer (standalone)
|
||||
<info name="usage" value="Type SYSTEM and load with POLEPO, enter / to start" />
|
||||
<part name="cass1" interface="cgenie_cass">
|
||||
<dataarea name="cass" size="14362">
|
||||
<rom name="polepo.cas" size="14362" crc="cfd0d6ce" sha1="35658b20373f4ec0673a6aa81f161101dd916cea" />
|
||||
<rom name="polepo.cas" size="14362" crc="cfd0d6ce" sha1="bfced1e2d8128d38b4657c330ff67037759de832" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
116
hash/compis.xml
116
hash/compis.xml
@ -157,7 +157,7 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
<software name="stvaratt">
|
||||
<description>Stava rätt på nytt sätt (version 8481)</description>
|
||||
<year>19??</year>
|
||||
<publisher>Esselte Stadium</publisher>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-34298-X" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2178838">
|
||||
@ -169,7 +169,7 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
<software name="mattev1">
|
||||
<description>Matematikverkstad I (beta, nät/skollicens)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Esselte Stadium</publisher>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-33777" />
|
||||
<info name="release" value="19870806" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
@ -182,7 +182,7 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
<software name="video">
|
||||
<description>Video-butiken (enanvändare)</description>
|
||||
<year>1986</year>
|
||||
<publisher>Esselte Stadium</publisher>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-33070" />
|
||||
<info name="release" value="19860916" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
@ -202,7 +202,7 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
<software name="statett">
|
||||
<description>StatEtt - Analys</description>
|
||||
<year>1990</year>
|
||||
<publisher>Esselte Stadium</publisher>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-35831" />
|
||||
<info name="release" value="19900101" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
@ -216,7 +216,7 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
<software name="raknrattd" cloneof="raknratt">
|
||||
<description>Räkna lätt, räkna rätt (demo, version 6175)</description>
|
||||
<year>19??</year>
|
||||
<publisher>Esselte Stadium</publisher>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-4408-7" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209405">
|
||||
@ -224,4 +224,110 @@ Systemskiva för hårdskiveenhet [version 7242]
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="stilplus">
|
||||
<description>Stil-Plus (alfa 1.0, nät/skollicens)</description>
|
||||
<year>1989</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-35456" />
|
||||
<info name="release" value="19890530" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2217678">
|
||||
<rom name="StilPlus.mfm" size="2217678" crc="b16bb821" sha1="d965a865e3f97d7d256c89176948ef371d65254b"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="action1">
|
||||
<description>Action1 Glosprogram (nät/skollicens)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Almqvist & Wiksell Läromedel AB</publisher>
|
||||
<info name="serial" value="24-33584" />
|
||||
<info name="release" value="19870114" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209365">
|
||||
<rom name="Action1 Glosprogram.mfm" size="2209365" crc="1e2a96a1" sha1="098842f0571c0b9beb64295bef5ded29e5ce6add"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="coulomb">
|
||||
<description>Coulombs lag (nät/skollicens)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-33772" />
|
||||
<info name="release" value="19870731" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209453">
|
||||
<rom name="Coulombs lag.mfm" size="2209453" crc="16e9749c" sha1="adc4658eaa24cdaf4f261f2a1848b98435155d0a"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="kinetik">
|
||||
<description>Kinetik (nät/skollicens)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-34652" />
|
||||
<info name="release" value="19870823" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209459">
|
||||
<rom name="Kinetik.mfm" size="2209459" crc="c906fa1d" sha1="a6e9411dcc1935cb17a65c7eb162fc127eb1f9a1"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="jordskift">
|
||||
<description>Jorden skiftas, folket skingras (nät/skollicens)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-33799" />
|
||||
<info name="release" value="19871105" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209529">
|
||||
<rom name="Jorden skiftas, folket skingras.mfm" size="2209529" crc="b1df76ea" sha1="6d6e2fd20ccc4cec2999932168f8a82221f16c47"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- Requires a hardware key which isn't dumped -->
|
||||
<software name="skvallra">
|
||||
<description>Får dataregister skvallra? (enanvändare)</description>
|
||||
<year>1985</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-34112" />
|
||||
<info name="release" value="19851029" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209468">
|
||||
<rom name="Far dataregister skvallra.mfm" size="2209468" crc="06fc17bc" sha1="7de8a56025058f2a5298ee0dfa1db32c7f335643"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="skvallrak" cloneof="skvallra">
|
||||
<description>Får dataregister skvallra? (komplement)</description>
|
||||
<year>1986</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-34820" />
|
||||
<info name="release" value="19860904" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2152177">
|
||||
<rom name="Far dataregister skvallra (Komplement).mfm" size="2152177" crc="9fa1f31a" sha1="8e0eb4e26d4167193f2b4504f014cf14a8ab8c65"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- Requires a hardware key which isn't dumped -->
|
||||
<software name="kommunik">
|
||||
<description>Datorn i kommunikation (enanvändare)</description>
|
||||
<year>1986</year>
|
||||
<publisher>Esselte Studium</publisher>
|
||||
<info name="serial" value="24-33828" />
|
||||
<info name="release" value="19861006" />
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="2209396">
|
||||
<rom name="Datorn i kommunikation.mfm" size="2209396" crc="780900ce" sha1="923cbefe3ac449d64f1a5ef50f69f59f3a33e438"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
</softwarelist>
|
||||
|
@ -1366,7 +1366,7 @@ Re-releases (probably the same as the original release, but listed while waiting
|
||||
|
||||
<software name="meikyujd">
|
||||
<description>Meikyuu Jiin Dababa</description>
|
||||
<year>1986</year>
|
||||
<year>1987</year>
|
||||
<publisher>Konami</publisher>
|
||||
<info name="serial" value="KDS-MIK"/>
|
||||
<info name="release" value="19870529"/>
|
||||
|
@ -11042,7 +11042,7 @@ but dumps still have to be confirmed.
|
||||
|
||||
<software name="babyboom">
|
||||
<description>Baby Boom (Prototype, 19940811)</description>
|
||||
<year>199?</year>
|
||||
<year>1994</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="cart" interface="megadriv_cart">
|
||||
<dataarea name="rom" width="16" endianness="big" size="2097152">
|
||||
@ -11053,7 +11053,7 @@ but dumps still have to be confirmed.
|
||||
|
||||
<software name="babyboom1" cloneof="babyboom">
|
||||
<description>Baby Boom (Prototype, 19940603)</description>
|
||||
<year>199?</year>
|
||||
<year>1994</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="cart" interface="megadriv_cart">
|
||||
<dataarea name="rom" width="16" endianness="big" size="2097152">
|
||||
@ -11064,7 +11064,7 @@ but dumps still have to be confirmed.
|
||||
|
||||
<software name="babyboom2" cloneof="babyboom">
|
||||
<description>Baby Boom (Prototype, 19940606)</description>
|
||||
<year>199?</year>
|
||||
<year>1994</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="cart" interface="megadriv_cart">
|
||||
<dataarea name="rom" width="16" endianness="big" size="2097152">
|
||||
|
@ -5312,7 +5312,7 @@ kept for now until finding out what those bytes affect...
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="gw126a">
|
||||
<software name="gw126a" cloneof="gw126">
|
||||
<description>Game World - 126 Games (Kor, Hacked?)</description>
|
||||
<year>19??</year>
|
||||
<publisher>Zemina</publisher>
|
||||
|
10
hash/nes.xml
10
hash/nes.xml
@ -15269,7 +15269,7 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="guardlgnu" cloneof="guardlgn">
|
||||
<software name="guardlgnu" cloneof="guardlgn" supported="no">
|
||||
<description>The Guardian Legend (USA)</description>
|
||||
<year>1989</year>
|
||||
<publisher>Brøderbund</publisher>
|
||||
@ -15288,7 +15288,7 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="guardlgn">
|
||||
<software name="guardlgn" supported="no">
|
||||
<description>The Guardian Legend (Euro)</description>
|
||||
<year>1992</year>
|
||||
<publisher>Nintendo</publisher>
|
||||
@ -15307,7 +15307,7 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="guardic" cloneof="guardlgn">
|
||||
<software name="guardic" cloneof="guardlgn" supported="no">
|
||||
<description>Guardic Gaiden (Jpn)</description>
|
||||
<year>1987</year>
|
||||
<publisher>Irem</publisher>
|
||||
@ -25010,7 +25010,7 @@ license:CC0
|
||||
<publisher>Jaleco</publisher>
|
||||
<info name="serial" value="JF-28"/>
|
||||
<info name="release" value="19900629"/>
|
||||
<info name="alt_title" value="燃えろ!! 柔道うぉり・ーず"/>
|
||||
<info name="alt_title" value="燃えろ!! 柔道うおりあ〜ず"/>
|
||||
<part name="cart" interface="nes_cart">
|
||||
<feature name="slot" value="jf17" />
|
||||
<feature name="pcb" value="JALECO-JF-17" />
|
||||
@ -75764,7 +75764,7 @@ be better to redump them properly. -->
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="sf3_9">
|
||||
<software name="sf3_9" cloneof="sf3">
|
||||
<description>Street Fighter III (Asia, 9 characters)</description>
|
||||
<year>19??</year>
|
||||
<publisher><unknown></publisher>
|
||||
|
@ -7,7 +7,7 @@ license:CC0
|
||||
|
||||
<software name="cpm22">
|
||||
<description>CP/M-80 R2.2 for QX-10 & QX-16</description>
|
||||
<year>198?</year>
|
||||
<year>1984</year>
|
||||
<publisher>Epson</publisher>
|
||||
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
@ -17,6 +17,18 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="cpm22_83">
|
||||
<description>CP/M-80 R2.2 for QX-10 & QX-16 1983</description>
|
||||
<year>1983</year>
|
||||
<publisher>Epson</publisher>
|
||||
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="273195">
|
||||
<rom name="qx10_cpm.imd" size="273195" crc="47d0c8cc" sha1="f6a10a280925d26d4c74cdf17e01ace13ead4773" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="tmp2">
|
||||
<description>TMP-II for QX-10 256K (v2.44)</description>
|
||||
<year>1983</year>
|
||||
|
1891
hash/sgi_mips.xml
1891
hash/sgi_mips.xml
File diff suppressed because it is too large
Load Diff
53
hash/super80_flop.xml
Normal file
53
hash/super80_flop.xml
Normal file
@ -0,0 +1,53 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE softwarelist SYSTEM "softwarelist.dtd">
|
||||
<!--
|
||||
license:CC0
|
||||
|
||||
Procedure: Mount the floppy into the first drive.
|
||||
|
||||
Select the TwinBoot software, and start the emulation.
|
||||
|
||||
When the TwinBoot starts up, it will auto-detect CP/M or DOS, and boot it.
|
||||
|
||||
Super-80 DOS is incredibly primitive. There is no directory as such. DIR lists the contents of each "track".
|
||||
You must load all the tracks needed into memory before running the program.
|
||||
More information will be added when I find it.
|
||||
|
||||
-->
|
||||
<softwarelist name="super80_flop" description="Dick Smith Super-80 floppies">
|
||||
|
||||
<software name="cpm">
|
||||
<description>CP/M boot disk</description>
|
||||
<year>198?</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="470469">
|
||||
<rom name="cpm.imd" size="470469" crc="5f244055" sha1="1fd601efba719d2ee2fb58671f8584aca0e473b0"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="dos">
|
||||
<description>Super-80 DOS disk</description>
|
||||
<year>198?</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="69347">
|
||||
<rom name="s80dos.imd" size="69347" crc="42b3b094" sha1="52ae93b07b9c6a8492bdcf56cbb13685fff47ec5"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="dosgames">
|
||||
<description>Super-80 DOS disk with games</description>
|
||||
<year>198?</year>
|
||||
<publisher><unknown></publisher>
|
||||
<part name="flop1" interface="floppy_5_25">
|
||||
<dataarea name="flop" size="558331">
|
||||
<rom name="s80dosb0.imd" size="558331" crc="2a437bd3" sha1="be2125fee65d4b3f4da59f9ad76598e2bd7d95af"/>
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
|
||||
</softwarelist>
|
437
hash/vgmplay.xml
437
hash/vgmplay.xml
@ -313074,9 +313074,6 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
|
||||
|
||||
|
||||
<!-- Project 2612 VGM Archives located at http://project2612.org/list.php
|
||||
Update April 7, 2020 - 13 new entries -->
|
||||
|
||||
@ -314209,6 +314206,440 @@ license:CC0
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- Project 2612 VGM Archives located at http://project2612.org/list.php
|
||||
Update May 2, 2020 - 5 new entries -->
|
||||
|
||||
<software name="joemont2_md">
|
||||
<description>Joe Montana II - Sports Talk Football (GEN/MD)</description>
|
||||
<year>1991</year>
|
||||
<publisher>Sega</publisher>
|
||||
<info name="cores" value="SN76496, YM2612"/>
|
||||
<part name="001" interface="vgm_quik">
|
||||
<feature name="part_id" value="01 - main theme.vgz" />
|
||||
<dataarea name="quik" size="1572973">
|
||||
<rom name="01 - main theme.vgz" size="1572973" crc="b3572679" sha1="3c63848bc10e1f344d64905f5d14753d6c14b63a" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="lotust_md">
|
||||
<description>Lotus Turbo Challenge (GEN/MD)</description>
|
||||
<year>1992</year>
|
||||
<publisher>Gremlin Graphics Software Ltd.</publisher>
|
||||
<info name="cores" value="SN76496, YM2612"/>
|
||||
<part name="001" interface="vgm_quik">
|
||||
<feature name="part_id" value="01 - title theme.vgz" />
|
||||
<dataarea name="quik" size="719245">
|
||||
<rom name="01 - title theme.vgz" size="719245" crc="c53d07ef" sha1="044371167bd48c5ff94f60848eec7364e28cf890" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="002" interface="vgm_quik">
|
||||
<feature name="part_id" value="02 - forest.vgz" />
|
||||
<dataarea name="quik" size="87473">
|
||||
<rom name="02 - forest.vgz" size="87473" crc="40565839" sha1="ca8e57471b99d0636da1b416efd0bae462800f81" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="003" interface="vgm_quik">
|
||||
<feature name="part_id" value="03 - night.vgz" />
|
||||
<dataarea name="quik" size="127484">
|
||||
<rom name="03 - night.vgz" size="127484" crc="7c07ef2f" sha1="dd9f080f21296bb583e50dfc9702916d1794165a" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="004" interface="vgm_quik">
|
||||
<feature name="part_id" value="04 - fog.vgz" />
|
||||
<dataarea name="quik" size="18374">
|
||||
<rom name="04 - fog.vgz" size="18374" crc="1b11cac4" sha1="9b6d0fa2f0f29d17a1ce798d4fac59fdc38a8fb9" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="005" interface="vgm_quik">
|
||||
<feature name="part_id" value="05 - snow.vgz" />
|
||||
<dataarea name="quik" size="6512">
|
||||
<rom name="05 - snow.vgz" size="6512" crc="851ff91c" sha1="37050143b22ccaa6de9a2963ce59c711cf6ab400" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="006" interface="vgm_quik">
|
||||
<feature name="part_id" value="06 - desert.vgz" />
|
||||
<dataarea name="quik" size="56566">
|
||||
<rom name="06 - desert.vgz" size="56566" crc="090d3910" sha1="614436c539e89922f9276f0ed80e9b961a8e9593" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="007" interface="vgm_quik">
|
||||
<feature name="part_id" value="07 - interstate.vgz" />
|
||||
<dataarea name="quik" size="6490">
|
||||
<rom name="07 - interstate.vgz" size="6490" crc="23bf85b4" sha1="e71dd11b0499d1ceff1eb650b62c738bc6c29501" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="008" interface="vgm_quik">
|
||||
<feature name="part_id" value="08 - marsh.vgz" />
|
||||
<dataarea name="quik" size="69098">
|
||||
<rom name="08 - marsh.vgz" size="69098" crc="54e2e2fb" sha1="222d4567add14996a2fe33ba796cbd5885408d8c" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="009" interface="vgm_quik">
|
||||
<feature name="part_id" value="09 - storm.vgz" />
|
||||
<dataarea name="quik" size="68157">
|
||||
<rom name="09 - storm.vgz" size="68157" crc="3257c4fd" sha1="68e287840435d30a711b7698b1343095b72eaaa2" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="010" interface="vgm_quik">
|
||||
<feature name="part_id" value="10 - ending.vgz" />
|
||||
<dataarea name="quik" size="664924">
|
||||
<rom name="10 - ending.vgz" size="664924" crc="09841b94" sha1="e33b52a3a214972bb216cf768887245dce93a9d8" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="madden95_md">
|
||||
<description>Madden NFL '95 (GEN/MD)</description>
|
||||
<year>1994</year>
|
||||
<publisher>Electronic Arts</publisher>
|
||||
<info name="cores" value="SN76496, YM2612"/>
|
||||
<part name="001" interface="vgm_quik">
|
||||
<feature name="part_id" value="01 - ea sports.vgz" />
|
||||
<dataarea name="quik" size="70299">
|
||||
<rom name="01 - ea sports.vgz" size="70299" crc="5ae906c3" sha1="1a331babeff7fc732a746a884ea649a03577966c" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="002" interface="vgm_quik">
|
||||
<feature name="part_id" value="02 - welcome.vgz" />
|
||||
<dataarea name="quik" size="52680">
|
||||
<rom name="02 - welcome.vgz" size="52680" crc="e267a10f" sha1="25401c69be28a1964b7968140d4cee285172f480" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="003" interface="vgm_quik">
|
||||
<feature name="part_id" value="03 - nfl on fox (game setup).vgz" />
|
||||
<dataarea name="quik" size="1633451">
|
||||
<rom name="03 - nfl on fox (game setup).vgz" size="1633451" crc="e6bb5c3d" sha1="d281f0953956e2a2e5367b1e8e24f9e798f258eb" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="004" interface="vgm_quik">
|
||||
<feature name="part_id" value="04 - game start.vgz" />
|
||||
<dataarea name="quik" size="2285567">
|
||||
<rom name="04 - game start.vgz" size="2285567" crc="74c25daf" sha1="6c40dcf2d5b1b6b82c279d6600775ad5e1a61bd2" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="005" interface="vgm_quik">
|
||||
<feature name="part_id" value="05 - pause menu.vgz" />
|
||||
<dataarea name="quik" size="1128631">
|
||||
<rom name="05 - pause menu.vgz" size="1128631" crc="d74bf85a" sha1="38be59a3c9dc04076474270bacb18cb022c6016a" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="006" interface="vgm_quik">
|
||||
<feature name="part_id" value="06 - playoff tree.vgz" />
|
||||
<dataarea name="quik" size="1599500">
|
||||
<rom name="06 - playoff tree.vgz" size="1599500" crc="0a37d690" sha1="abcad460c51f8f8e6bec8a8fe78b56d224281ddd" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="007" interface="vgm_quik">
|
||||
<feature name="part_id" value="07 - you won.vgz" />
|
||||
<dataarea name="quik" size="588879">
|
||||
<rom name="07 - you won.vgz" size="588879" crc="8f2027d3" sha1="c763a0098b24841d174346b54f07ec02ab63ac63" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="teddyboy_md">
|
||||
<description>Teddy Boy Blues (GEN/MD)</description>
|
||||
<year>1992</year>
|
||||
<publisher>Sega</publisher>
|
||||
<info name="cores" value="SN76496, YM2612"/>
|
||||
<part name="001" interface="vgm_quik">
|
||||
<feature name="part_id" value="01 - title theme.vgz" />
|
||||
<dataarea name="quik" size="7649">
|
||||
<rom name="01 - title theme.vgz" size="7649" crc="fd01f50a" sha1="e77cc1e94a143700af1eee3604d5766501099a26" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="002" interface="vgm_quik">
|
||||
<feature name="part_id" value="02 - bgm 1.vgz" />
|
||||
<dataarea name="quik" size="17868">
|
||||
<rom name="02 - bgm 1.vgz" size="17868" crc="75c872c0" sha1="5950fa5f41ccc78a42e8e53a3232e4580b973b9f" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="003" interface="vgm_quik">
|
||||
<feature name="part_id" value="03 - bgm 2.vgz" />
|
||||
<dataarea name="quik" size="20856">
|
||||
<rom name="03 - bgm 2.vgz" size="20856" crc="a6c24a7d" sha1="1283064246fbad8e1a9c516b66e0b50fed290453" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="004" interface="vgm_quik">
|
||||
<feature name="part_id" value="04 - round clear.vgz" />
|
||||
<dataarea name="quik" size="2953">
|
||||
<rom name="04 - round clear.vgz" size="2953" crc="97d32b54" sha1="ff33193d1f58cdc75b84a51eeec2052950abfe7a" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="005" interface="vgm_quik">
|
||||
<feature name="part_id" value="05 - bonus round.vgz" />
|
||||
<dataarea name="quik" size="10779">
|
||||
<rom name="05 - bonus round.vgz" size="10779" crc="9792d536" sha1="ebec8506f6445d1b042ad6e55f3d260ac1dcfe87" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="006" interface="vgm_quik">
|
||||
<feature name="part_id" value="06 - bonus clear.vgz" />
|
||||
<dataarea name="quik" size="2421">
|
||||
<rom name="06 - bonus clear.vgz" size="2421" crc="2c147774" sha1="60cec9be8ce176b06a368e90b7850c400fb6ab9c" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="007" interface="vgm_quik">
|
||||
<feature name="part_id" value="07 - game over.vgz" />
|
||||
<dataarea name="quik" size="2732">
|
||||
<rom name="07 - game over.vgz" size="2732" crc="e796d745" sha1="5fcd75243bb3c10f7cef4af0f5595e4d89d640c3" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="008" interface="vgm_quik">
|
||||
<feature name="part_id" value="08 - ranking.vgz" />
|
||||
<dataarea name="quik" size="7519">
|
||||
<rom name="08 - ranking.vgz" size="7519" crc="a14bd81e" sha1="2ab52b6e95ad13c1e44ec669f5efa526a0b20d4e" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="uruseiya_md">
|
||||
<description>Urusei Yatsura - Dear My Friends (Sega CD) (GEN/MD)</description>
|
||||
<year>1994</year>
|
||||
<publisher>Game Arts Co., Ltd.</publisher>
|
||||
<info name="cores" value="SN76496, YM2612"/>
|
||||
<part name="001" interface="vgm_quik">
|
||||
<feature name="part_id" value="01 - title.vgz" />
|
||||
<dataarea name="quik" size="69366">
|
||||
<rom name="01 - title.vgz" size="69366" crc="02c5f7f7" sha1="a1a7c4822ba03394e2d6f4d6870c164fc80488ff" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="002" interface="vgm_quik">
|
||||
<feature name="part_id" value="02 - intro 1.vgz" />
|
||||
<dataarea name="quik" size="89092">
|
||||
<rom name="02 - intro 1.vgz" size="89092" crc="89354535" sha1="88d1f733582a80e8bba38d5cd004421abca91bc6" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="003" interface="vgm_quik">
|
||||
<feature name="part_id" value="03 - ataru.vgz" />
|
||||
<dataarea name="quik" size="81237">
|
||||
<rom name="03 - ataru.vgz" size="81237" crc="4c5c16d0" sha1="3f788d9f06bee41fdc666c359dd1921adecc4ed5" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="004" interface="vgm_quik">
|
||||
<feature name="part_id" value="04 - tomobiki.vgz" />
|
||||
<dataarea name="quik" size="116057">
|
||||
<rom name="04 - tomobiki.vgz" size="116057" crc="25328acf" sha1="16a6be97f8f238d9d6ca889ef32858c9810fcd99" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="005" interface="vgm_quik">
|
||||
<feature name="part_id" value="05 - ran.vgz" />
|
||||
<dataarea name="quik" size="111691">
|
||||
<rom name="05 - ran.vgz" size="111691" crc="2cb86244" sha1="526273098e800dc94d8d64c5283776882f037cd2" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="006" interface="vgm_quik">
|
||||
<feature name="part_id" value="06 - school.vgz" />
|
||||
<dataarea name="quik" size="139602">
|
||||
<rom name="06 - school.vgz" size="139602" crc="3e520ebd" sha1="80b6443add96de1a02c05fe89ffa0f027e2fe872" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="007" interface="vgm_quik">
|
||||
<feature name="part_id" value="07 - ryu.vgz" />
|
||||
<dataarea name="quik" size="65098">
|
||||
<rom name="07 - ryu.vgz" size="65098" crc="e31176a9" sha1="ae74f112023af1d9c62a290b13f76645f9d41890" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="008" interface="vgm_quik">
|
||||
<feature name="part_id" value="08 - mendou.vgz" />
|
||||
<dataarea name="quik" size="95557">
|
||||
<rom name="08 - mendou.vgz" size="95557" crc="496eeb61" sha1="bd6809b30e97668406b800e5aa59d3b883bec8b6" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="009" interface="vgm_quik">
|
||||
<feature name="part_id" value="09 - calamity.vgz" />
|
||||
<dataarea name="quik" size="57610">
|
||||
<rom name="09 - calamity.vgz" size="57610" crc="d24d73db" sha1="9f0873345aa5bbbf217a4cbc14ea0e26c4c935f5" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="010" interface="vgm_quik">
|
||||
<feature name="part_id" value="10 - mendou 2.vgz" />
|
||||
<dataarea name="quik" size="80842">
|
||||
<rom name="10 - mendou 2.vgz" size="80842" crc="1cb16579" sha1="9ccd6af831f82e1446d2211d79976c0a07144c3f" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="011" interface="vgm_quik">
|
||||
<feature name="part_id" value="11 - park.vgz" />
|
||||
<dataarea name="quik" size="151110">
|
||||
<rom name="11 - park.vgz" size="151110" crc="230c0595" sha1="8a437a4bd23a30149bbee3fe84e2942b482bc853" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="012" interface="vgm_quik">
|
||||
<feature name="part_id" value="12 - temple.vgz" />
|
||||
<dataarea name="quik" size="138891">
|
||||
<rom name="12 - temple.vgz" size="138891" crc="c6d2e759" sha1="ebbb8adc38ad0a1b233181ec48d91d70461a2676" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="013" interface="vgm_quik">
|
||||
<feature name="part_id" value="13 - funfair.vgz" />
|
||||
<dataarea name="quik" size="83274">
|
||||
<rom name="13 - funfair.vgz" size="83274" crc="1d8ed67c" sha1="75824a39f43e0abc7aed07047a7066fbba136150" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="014" interface="vgm_quik">
|
||||
<feature name="part_id" value="14 - destruction.vgz" />
|
||||
<dataarea name="quik" size="75749">
|
||||
<rom name="14 - destruction.vgz" size="75749" crc="35b68552" sha1="2d98bbcd215ff70fe7b540e90099acea9a0871a4" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="015" interface="vgm_quik">
|
||||
<feature name="part_id" value="15 - mendou slow.vgz" />
|
||||
<dataarea name="quik" size="68245">
|
||||
<rom name="15 - mendou slow.vgz" size="68245" crc="7ad2c10c" sha1="a6512eabfc480ae389c81486dab41096617b7d5b" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="016" interface="vgm_quik">
|
||||
<feature name="part_id" value="16 - subspace2.vgz" />
|
||||
<dataarea name="quik" size="101027">
|
||||
<rom name="16 - subspace2.vgz" size="101027" crc="3cf0f706" sha1="1fcf955102691f4a89b8edbb6b0f5be7d718587f" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="017" interface="vgm_quik">
|
||||
<feature name="part_id" value="17 - subspace4.vgz" />
|
||||
<dataarea name="quik" size="134001">
|
||||
<rom name="17 - subspace4.vgz" size="134001" crc="b2f9343d" sha1="7df9df6f9441f10a2dd560fc7bc570b5df954e45" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="018" interface="vgm_quik">
|
||||
<feature name="part_id" value="18 - danger.vgz" />
|
||||
<dataarea name="quik" size="72784">
|
||||
<rom name="18 - danger.vgz" size="72784" crc="37c39fd9" sha1="11b1d327f39538a9b440caaf977c118d8bd2e941" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="019" interface="vgm_quik">
|
||||
<feature name="part_id" value="19 - cutscene 1a.vgz" />
|
||||
<dataarea name="quik" size="68017">
|
||||
<rom name="19 - cutscene 1a.vgz" size="68017" crc="65640428" sha1="3f7234e2e88c8190b5123741bd81d9ab5a9dc461" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="020" interface="vgm_quik">
|
||||
<feature name="part_id" value="20 - cutscene 4.vgz" />
|
||||
<dataarea name="quik" size="109993">
|
||||
<rom name="20 - cutscene 4.vgz" size="109993" crc="d14ff10b" sha1="ca687de3a0a5bfddc24a1f5cff8d2e3f58450da8" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="021" interface="vgm_quik">
|
||||
<feature name="part_id" value="21 - cutscene 7a.vgz" />
|
||||
<dataarea name="quik" size="54081">
|
||||
<rom name="21 - cutscene 7a.vgz" size="54081" crc="b71f2709" sha1="6b6df178d9730c49bc620ca815c1c13eea428038" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="022" interface="vgm_quik">
|
||||
<feature name="part_id" value="22 - cutscene 7b.vgz" />
|
||||
<dataarea name="quik" size="117350">
|
||||
<rom name="22 - cutscene 7b.vgz" size="117350" crc="14e62acf" sha1="0f733b5604b2001fc7f179a8becb840ade6dd360" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="023" interface="vgm_quik">
|
||||
<feature name="part_id" value="23 - cutscene 7c.vgz" />
|
||||
<dataarea name="quik" size="75096">
|
||||
<rom name="23 - cutscene 7c.vgz" size="75096" crc="f8639ff7" sha1="6692d457107bca6802be5ee4922e2dba54c503ae" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="024" interface="vgm_quik">
|
||||
<feature name="part_id" value="24 - cutscene 8b.vgz" />
|
||||
<dataarea name="quik" size="77382">
|
||||
<rom name="24 - cutscene 8b.vgz" size="77382" crc="73d888de" sha1="78e9dbe51e5088efb932a169788d3abb3deb56c6" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="025" interface="vgm_quik">
|
||||
<feature name="part_id" value="25 - cutscene 8c.vgz" />
|
||||
<dataarea name="quik" size="33654">
|
||||
<rom name="25 - cutscene 8c.vgz" size="33654" crc="ff16102a" sha1="48bfe597b6df4e521f409d17e307d6632cc510d5" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="026" interface="vgm_quik">
|
||||
<feature name="part_id" value="26 - cutscene 11.vgz" />
|
||||
<dataarea name="quik" size="72651">
|
||||
<rom name="26 - cutscene 11.vgz" size="72651" crc="0a09c972" sha1="9c492ac7ee0ab3ca534d83b240bc26e6e14fdfc9" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="027" interface="vgm_quik">
|
||||
<feature name="part_id" value="27 - cutscene 15 (alternate loop).vgz" />
|
||||
<dataarea name="quik" size="174156">
|
||||
<rom name="27 - cutscene 15 (alternate loop).vgz" size="174156" crc="cdaf950e" sha1="16ae31fb1c186cda4e524f07a4b5763cd6185cfd" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="028" interface="vgm_quik">
|
||||
<feature name="part_id" value="27 - cutscene 15.vgz" />
|
||||
<dataarea name="quik" size="68007">
|
||||
<rom name="27 - cutscene 15.vgz" size="68007" crc="226bdaad" sha1="7cbe38c7c413eaa5628a9c507e32629347cbd6fe" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="029" interface="vgm_quik">
|
||||
<feature name="part_id" value="28 - cutscene 16a.vgz" />
|
||||
<dataarea name="quik" size="69652">
|
||||
<rom name="28 - cutscene 16a.vgz" size="69652" crc="1a2034bd" sha1="25140168bb103b77450fb147d794f6dfeab56332" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="030" interface="vgm_quik">
|
||||
<feature name="part_id" value="29 - cutscene 16b.vgz" />
|
||||
<dataarea name="quik" size="100208">
|
||||
<rom name="29 - cutscene 16b.vgz" size="100208" crc="e9614a99" sha1="fd6d09077510ce3de25b7a1442f6793a9b5e1577" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="031" interface="vgm_quik">
|
||||
<feature name="part_id" value="30 - slideshow.vgz" />
|
||||
<dataarea name="quik" size="48301">
|
||||
<rom name="30 - slideshow.vgz" size="48301" crc="adcdaa2a" sha1="8bb6a5e1412574aa123c6c52564c1ef57afeb213" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="032" interface="vgm_quik">
|
||||
<feature name="part_id" value="31 - subspace fighter infinity nitro (menu).vgz" />
|
||||
<dataarea name="quik" size="74709">
|
||||
<rom name="31 - subspace fighter infinity nitro (menu).vgz" size="74709" crc="a4f02550" sha1="3f74fa1123fc8c4fabfe8e90dbade0a08b809203" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="033" interface="vgm_quik">
|
||||
<feature name="part_id" value="32 - subspace fighter infinity nitro (arena).vgz" />
|
||||
<dataarea name="quik" size="89431">
|
||||
<rom name="32 - subspace fighter infinity nitro (arena).vgz" size="89431" crc="c09ec976" sha1="1d2558e207defbbd01947adad23135e8dc8ec020" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="034" interface="vgm_quik">
|
||||
<feature name="part_id" value="33 - subspace fighter infinity nitro (end).vgz" />
|
||||
<dataarea name="quik" size="33473">
|
||||
<rom name="33 - subspace fighter infinity nitro (end).vgz" size="33473" crc="b147fd88" sha1="6d50d69bc22fb326171f8e58e537502e02023f54" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="035" interface="vgm_quik">
|
||||
<feature name="part_id" value="34 - maximum speed (menu).vgz" />
|
||||
<dataarea name="quik" size="86681">
|
||||
<rom name="34 - maximum speed (menu).vgz" size="86681" crc="ab55c3d7" sha1="7a13e8a823cbc82e9a8cfaf6b6c602eef83fa9ed" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="036" interface="vgm_quik">
|
||||
<feature name="part_id" value="35 - maximum speed (level).vgz" />
|
||||
<dataarea name="quik" size="76688">
|
||||
<rom name="35 - maximum speed (level).vgz" size="76688" crc="91bbec09" sha1="5f8b753628523443c157923d0987b4e7d223d43c" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="037" interface="vgm_quik">
|
||||
<feature name="part_id" value="36 - maximum speed (end).vgz" />
|
||||
<dataarea name="quik" size="47101">
|
||||
<rom name="36 - maximum speed (end).vgz" size="47101" crc="842690ea" sha1="0fedeb6f6565b01e84c626c8685fabb13130116e" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="038" interface="vgm_quik">
|
||||
<feature name="part_id" value="37 - happy kotatsuneko episode 2 (menu).vgz" />
|
||||
<dataarea name="quik" size="80263">
|
||||
<rom name="37 - happy kotatsuneko episode 2 (menu).vgz" size="80263" crc="6006f24f" sha1="0dffdfe9b4d4bea1dd1e1739ed03c6a39b2f5abe" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="039" interface="vgm_quik">
|
||||
<feature name="part_id" value="38 - happy kotatsuneko episode 2 (level).vgz" />
|
||||
<dataarea name="quik" size="178449">
|
||||
<rom name="38 - happy kotatsuneko episode 2 (level).vgz" size="178449" crc="2de6c0f7" sha1="b7b82960f631256a9f08a873167f9d121d7f241e" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
<part name="040" interface="vgm_quik">
|
||||
<feature name="part_id" value="39 - happy kotatsuneko episode 2 (end).vgz" />
|
||||
<dataarea name="quik" size="74699">
|
||||
<rom name="39 - happy kotatsuneko episode 2 (end).vgz" size="74699" crc="8d7f2ddf" sha1="b07298ba43b96add6754d239028ac24f1810fb5a" offset="0" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
|
||||
<!-- SMS Power! VGM Archives located at http://www.smspower.org/Music/VGMs
|
||||
Later installments of vgmplay.xml may include other non-game OST content -->
|
||||
|
@ -107,7 +107,7 @@ Regular game cartridges
|
||||
| | 80-090160(US) | <unknown> (Should be Monsters vs. Aliens #80-084440, exists in VTech V.Link database) |
|
||||
| | 80-090163(UK) | Monsters vs. Aliens |
|
||||
| XX | 80-090164(GE) | Monsters vs. Aliens |
|
||||
| | 80-090165(FR) | Monsters Contre Aliens |
|
||||
| XX | 80-090165(FR) | Monsters Contre Aliens |
|
||||
| XX | 80-090167(SP) | Monstruos contra Alienígenas (52-090167(SP) on back label) |
|
||||
+========+===================+================================================================================================+
|
||||
| | 80-090180(US) | <Unknown> |
|
||||
@ -421,7 +421,7 @@ Regular game cartridges
|
||||
| | 80-092503(UK) | Whiz Kid Wheels |
|
||||
| | 80-092504(GE) | Flitzers Schlaue Staedtetour (diff color) |
|
||||
| XX | 80-092504(GE) | Flitzers Schlaue Staedtetour (purple, 52-092504(GER) on back label) |
|
||||
| | 80-092505(FR) | Mission Pilote |
|
||||
| XX | 80-092505(FR) | Mission Pilote |
|
||||
| | 80-092506(PT) | Conducao Diverrido (Cart# 92516) |
|
||||
| XX | 80-092507(SP) | Conducción Divertida (52-92507(SP) on back label) |
|
||||
| | 80-092510(KOR) | Whiz Kid Wheels - 꼬마 자동차 트러클 (50-92510(KOR) on back label) |
|
||||
@ -510,6 +510,7 @@ Regular game cartridges
|
||||
| XX | 80-092854(SE) | Wall-E |
|
||||
| | (NO) | Wall-E |
|
||||
| | (FI) | Wall-E |
|
||||
| | (CN) | 瓦力 |
|
||||
+========+===================+================================================================================================+
|
||||
| XX | 80-092860(US) | Shrek the Third: Arthur's School Day Adventure |
|
||||
| XX | 80-092860(US) | Shrek the Third: Arthur's School Day Adventure (alt) |
|
||||
@ -1998,8 +1999,6 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<dataarea name="rom" size="0x800000">
|
||||
<rom name="52-91327 - V.Smile Gimnasio Interactivo (Spain).bin" size="0x800000" crc="a203eaf7" sha1="bb7c7ecf6b208cd8b81daba58748345d3109268a" />
|
||||
</dataarea>
|
||||
<dataarea name="nvram" size="131072">
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
@ -2512,6 +2511,22 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- No inputs -->
|
||||
<software name="monstalnf" cloneof="monstalng" supported="no">
|
||||
<description>DreamWorks Monstres contre Aliens (France)</description>
|
||||
<year>2009?</year>
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-090165(FR)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="slot" value="vsmile_rom" />
|
||||
<feature name="cart_type" value="lilac" />
|
||||
<feature name="u1" value="" />
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="090165 - MonstresContreAliens (FR).bin" size="8388608" crc="eb7b16b2" sha1="45d32470b2283ea47032e007e4f803f8b5ea6dfa" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- No inputs -->
|
||||
<software name="monstalns" cloneof="monstalng" supported="no">
|
||||
<description>DreamWorks Monstruos contra Alienígenas (Spain)</description>
|
||||
@ -4563,7 +4578,7 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-092504(GER)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="slot" value="vsmile_nvram" />
|
||||
<feature name="slot" value="vsmile_rom" />
|
||||
<feature name="pcb" value="708201" />
|
||||
<feature name="pcb_model" value="708201-4" />
|
||||
<feature name="cart_type" value="lilac" />
|
||||
@ -4571,7 +4586,20 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="80-092504 - Flitzers Schlaue Stadtetour (GER).bin" size="8388608" crc="1bdd6066" sha1="1e2a9090c0bfe08c31e750e263bad4a4a1fb2e73" />
|
||||
</dataarea>
|
||||
<dataarea name="nvram" size="131072">
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="wkwheelf" cloneof="wkwheelg"> <!-- Will be clone of "wkwheel" once found and dumped. -->
|
||||
<description>Mission Pilote (France)</description>
|
||||
<year>200?</year>
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-092505(FR)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="slot" value="vsmile_rom" />
|
||||
<feature name="cart_type" value="lilac" />
|
||||
<feature name="u1" value="" />
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="092505 - MissionPilote (FR).bin" size="8388608" crc="81531074" sha1="11631a6e837d3aa7a7bd6c0bcefa8289440a60b8" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
@ -4582,7 +4610,7 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-092507(SP)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="slot" value="vsmile_nvram" />
|
||||
<feature name="slot" value="vsmile_rom" />
|
||||
<feature name="pcb" value="706714" />
|
||||
<feature name="pcb_model" value="706714-1" />
|
||||
<feature name="cart_type" value="lilac" />
|
||||
@ -4590,8 +4618,6 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="80-092507 - Conduccion Divertida (SP).bin" size="8388608" crc="c52ff5d8" sha1="ce48bb9ea53cbdfa243170217908cc1f4352e4f0" />
|
||||
</dataarea>
|
||||
<dataarea name="nvram" size="131072">
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
@ -4602,7 +4628,7 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-090224(GE)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="slot" value="vsmile_nvram" />
|
||||
<feature name="slot" value="vsmile_rom" />
|
||||
<feature name="pcb" value="708106" />
|
||||
<feature name="pcb_model" value="708106-3" />
|
||||
<feature name="cart_type" value="lilac" />
|
||||
@ -4610,8 +4636,6 @@ V.Smile Smartbook Smartidges (need a Smartbook touch tablet connected to a regul
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="80-090224 - Dolphis Wasserabenteuer (GE).bin" size="8388608" crc="3fd78b1b" sha1="eadbc8b2a9bf09f623f27d3b94a1b19643685629" />
|
||||
</dataarea>
|
||||
<dataarea name="nvram" size="131072">
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
|
@ -141,7 +141,7 @@ Language:
|
||||
| | 80-084362(NL) | Handy Manny |
|
||||
| | 80-084363(UK) | Handy Manny |
|
||||
| | 80-084364(GE) | Meister Manny's Werkzeugkiste |
|
||||
| | 80-084365(FR) | Manny Et Ses Outils |
|
||||
| XX | 80-084365(FR) | Manny et ses outils |
|
||||
| | 80-084366(PT) | Manny Maozinhas (84376 on cart) |
|
||||
| | 80-084367(SP) | Manny Manitas |
|
||||
+========+===================+===========================================================================================+
|
||||
@ -187,20 +187,20 @@ Language:
|
||||
| | 80-084482(NL) | Prinses en de Kikker (label in english) |
|
||||
| XX | 80-084483(UK) | The Princess and the Frog |
|
||||
| XX | 80-084484(GE) | Kuess den Frosch |
|
||||
| | 80-084485(FR) | La Princesse Et La Grenouille |
|
||||
| XX | 80-084485(FR) | La Princesse Et La Grenouille - Le grand rêve de Tiana |
|
||||
| | 80-084487(SP) | Tiana y el Sapo - El gran sueño de Tiana |
|
||||
+========+===================+===========================================================================================+
|
||||
| XX | 80-084500(US) | Shrek Forever After |
|
||||
| | 80-084502(NL) | Sjrek voor eeuwig en altijd |
|
||||
| | 80-084503(UK) | Shrek Forever After |
|
||||
| XX | 80-084504(GE) | Fuer immer Shrek |
|
||||
| | 80-084505(FR) | Shrek 4 - Il Etait une Fin |
|
||||
| XX | 80-084505(FR) | Shrek 4 - Il était une fin |
|
||||
| | 80-084507(SP) | Shrek Felices para siempre |
|
||||
+========+===================+===========================================================================================+
|
||||
| | 80-084520(US) | <Unknown> |
|
||||
+========+===================+===========================================================================================+
|
||||
| | 80-084540(US) | Super Why to the Rescue! The Beach Day Mystery |
|
||||
| | 80-084541(US) | Super Why to the Rescue! The Beach Day Mystery (pocket version) |
|
||||
| | 80-084541(US) | Super Why to the Rescue! The Beach Day Mystery (pocket version) |
|
||||
+========+===================+===========================================================================================+
|
||||
| | 80-084560(US) | <Unknown> |
|
||||
+========+===================+===========================================================================================+
|
||||
@ -473,7 +473,7 @@ Language:
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="hmannym" cloneof="doram" supported="no">
|
||||
<software name="hmannym" supported="no">
|
||||
<description>Disney Handy Manny (USA, Rev. 2?)</description>
|
||||
<year>2009</year>
|
||||
<publisher>VTech</publisher>
|
||||
@ -486,6 +486,19 @@ Language:
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="hmannymf" cloneof="hmannym" supported="no">
|
||||
<description>Disney Manny et ses outils (France)</description>
|
||||
<year>2009</year>
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-084365(FR)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<feature name="u1" value="" />
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="084365 - MannyEtSesOutils (MOTION) (FR).bin" size="8388608" crc="a664071e" sha1="6900419492aa7424290b3db4b37c47b14a17ab61" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="kfpandamg" supported="no">
|
||||
<description>DreamWorks Kung Fu Panda - Der Weg des Panda (Germany)</description>
|
||||
<year>2008?</year>
|
||||
@ -826,6 +839,18 @@ Language:
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="prinfrogmf" cloneof="prinfrogm" supported="no">
|
||||
<description>Disney La Princesse Et La Grenouille - Le grand rêve de Tiana (France)</description>
|
||||
<year>2010</year>
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-084485(FR)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<dataarea name="rom" size="8388608">
|
||||
<rom name="084485 - LaPrincesseEtLaGrenouille (MOTION) (FR).bin" size="8388608" crc="1e1e84a2" sha1="01543d05122809e6bb5e8bdac213eedc22f442bd" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<software name="scoobyffmf" supported="no">
|
||||
<description>Scooby-Doo! - Panique à Funland (France)</description>
|
||||
<year>2008</year> <!-- (s08) -->
|
||||
@ -886,6 +911,20 @@ Language:
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- Does not boot, just loops on the intro -->
|
||||
<software name="shrekfamf" cloneof="shrekfam" supported="no">
|
||||
<description>Shrek 4 - Il était une fin (France)</description>
|
||||
<year>2010?</year>
|
||||
<publisher>VTech</publisher>
|
||||
<info name="serial" value="80-084505(FR)" />
|
||||
<part name="cart" interface="vsmile_cart">
|
||||
<dataarea name="rom" size="0x1000000">
|
||||
<rom name="084505 - Shrek 4 (MOTION) (FR)_blob1.bin" size="0x0800000" crc="bb3d3e09" sha1="539f0948ec1dad3b2465990fcf053f2cacc7e766" offset="0x0000000" />
|
||||
<rom name="084505 - Shrek 4 (MOTION) (FR)_blob2.bin" size="0x0800000" crc="7c633e07" sha1="a07b2439473be97bc1a785ae4050297ae0e5244a" offset="0x0800000" />
|
||||
</dataarea>
|
||||
</part>
|
||||
</software>
|
||||
|
||||
<!-- Soccer Challenge -->
|
||||
<software name="soccerchmg" supported="no">
|
||||
<description>Fussball Meisterschaft (Germany)</description>
|
||||
|
@ -3306,6 +3306,8 @@ if (BUSES["COCO"]~=null) then
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_dcmodem.h",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_orch90.cpp",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_orch90.h",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_ram.cpp",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_ram.h",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_ssc.cpp",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_ssc.h",
|
||||
MAME_DIR .. "src/devices/bus/coco/coco_pak.cpp",
|
||||
|
@ -2781,7 +2781,7 @@ end
|
||||
|
||||
---------------------------------------------------
|
||||
--
|
||||
--@src/devices/machine/scnxx562.h,MACHINES["SCN_PCI"] = true
|
||||
--@src/devices/machine/scn_pci.h,MACHINES["SCN_PCI"] = true
|
||||
---------------------------------------------------
|
||||
|
||||
if (MACHINES["SCN_PCI"]~=null) then
|
||||
|
@ -850,6 +850,17 @@ if (VIDEOS["SED1330"]~=null) then
|
||||
}
|
||||
end
|
||||
|
||||
--------------------------------------------------
|
||||
--
|
||||
--@src/devices/video/sed1500.h,VIDEOS["SED1500"] = true
|
||||
--------------------------------------------------
|
||||
if (VIDEOS["SED1500"]~=null) then
|
||||
files {
|
||||
MAME_DIR .. "src/devices/video/sed1500.cpp",
|
||||
MAME_DIR .. "src/devices/video/sed1500.h",
|
||||
}
|
||||
end
|
||||
|
||||
--------------------------------------------------
|
||||
--
|
||||
--@src/devices/video/sed1520.h,VIDEOS["SED1520"] = true
|
||||
|
@ -354,6 +354,7 @@ VIDEOS["SCN2674"] = true
|
||||
VIDEOS["PWM_DISPLAY"] = true
|
||||
--VIDEOS["SED1200"] = true
|
||||
--VIDEOS["SED1330"] = true
|
||||
--VIDEOS["SED1500"] = true
|
||||
--VIDEOS["SED1520"] = true
|
||||
VIDEOS["SNES_PPU"] = true
|
||||
VIDEOS["STVVDP"] = true
|
||||
@ -1521,8 +1522,6 @@ files {
|
||||
MAME_DIR .. "src/mame/includes/mitchell.h",
|
||||
MAME_DIR .. "src/mame/video/mitchell.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/sf.cpp",
|
||||
MAME_DIR .. "src/mame/includes/sf.h",
|
||||
MAME_DIR .. "src/mame/video/sf.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/sidearms.cpp",
|
||||
MAME_DIR .. "src/mame/includes/sidearms.h",
|
||||
MAME_DIR .. "src/mame/video/sidearms.cpp",
|
||||
|
@ -382,6 +382,7 @@ VIDEOS["PWM_DISPLAY"] = true
|
||||
VIDEOS["SDA5708"] = true
|
||||
VIDEOS["SED1200"] = true
|
||||
VIDEOS["SED1330"] = true
|
||||
VIDEOS["SED1500"] = true
|
||||
VIDEOS["SED1520"] = true
|
||||
VIDEOS["SNES_PPU"] = true
|
||||
VIDEOS["STVVDP"] = true
|
||||
@ -1901,6 +1902,8 @@ files {
|
||||
MAME_DIR .. "src/mame/drivers/fp200.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/fp1100.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/fp6000.cpp",
|
||||
MAME_DIR .. "src/mame/machine/fp6000_kbd.cpp",
|
||||
MAME_DIR .. "src/mame/machine/fp6000_kbd.h",
|
||||
MAME_DIR .. "src/mame/drivers/ht6000.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/pb1000.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/pv1000.cpp",
|
||||
@ -2003,6 +2006,8 @@ files {
|
||||
MAME_DIR .. "src/mame/machine/cit101_kbd.cpp",
|
||||
MAME_DIR .. "src/mame/machine/cit101_kbd.h",
|
||||
MAME_DIR .. "src/mame/drivers/cit220.cpp",
|
||||
MAME_DIR .. "src/mame/machine/cit220_kbd.cpp",
|
||||
MAME_DIR .. "src/mame/machine/cit220_kbd.h",
|
||||
}
|
||||
|
||||
createMESSProjects(_target, _subtarget, "coleco")
|
||||
@ -4279,6 +4284,7 @@ files {
|
||||
MAME_DIR .. "src/mame/drivers/elwro800.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/emate.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/epic14e.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/ergo201.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/esprit.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/eti660.cpp",
|
||||
MAME_DIR .. "src/mame/includes/eti660.h",
|
||||
@ -4460,6 +4466,10 @@ files {
|
||||
MAME_DIR .. "src/mame/drivers/palestra.cpp",
|
||||
MAME_DIR .. "src/mame/machine/nl_palestra.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/mindset.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/gs6502.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/gs6809.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/gscpm.cpp",
|
||||
MAME_DIR .. "src/mame/drivers/gsz80.cpp",
|
||||
}
|
||||
|
||||
end
|
||||
|
@ -661,7 +661,6 @@ INPUT_PORTS_START(matrix_dk)
|
||||
INPUT_PORTS_END
|
||||
|
||||
INPUT_PORTS_START(matrix_ch)
|
||||
// FIXME: natural keyboard doesn't play nicely with PORT_CONDITION, but it's an issue with natural keyboard itself
|
||||
PORT_INCLUDE(matrix_common)
|
||||
|
||||
PORT_START("CFG")
|
||||
|
@ -82,8 +82,7 @@ void bbc_datacentre_device::device_add_mconfig(machine_config &config)
|
||||
ATA_INTERFACE(config, m_ide).options(ata_devices, "hdd", "hdd", false);
|
||||
m_ide->irq_handler().set(FUNC(bbc_datacentre_device::irq_w));
|
||||
|
||||
/* 24LC512 - 512Kb I2C Serial EEPROM */
|
||||
I2CMEM(config, m_nvram).set_page_size(128).set_data_size(0x10000);
|
||||
I2C_24C512(config, m_nvram); // 24LC512
|
||||
|
||||
/* import floppy images - delayed to allow RAMFS to initialise before import */
|
||||
QUICKLOAD(config, "import0", "ssd,dsd,img", attotime::from_seconds(1)).set_load_callback(FUNC(bbc_datacentre_device::quickload_cb<0>));
|
||||
|
@ -40,6 +40,32 @@
|
||||
|
||||
Reading from $FF48-$FF4F clears bit 7 of DSKREG ($FF40)
|
||||
|
||||
---------------------------------------------------------------------------
|
||||
|
||||
Disto No Halt Extension
|
||||
|
||||
The Disto Super Controller II includes "no halt" circuitry. Implemented
|
||||
by using a read and write cache.
|
||||
|
||||
CachDat - Cache Data Register
|
||||
$FF74 & $FF75: Read/Write cache data.
|
||||
|
||||
CachCtrl - Cache Controller
|
||||
$FF76: Read
|
||||
Bit 7 low indicates an interrupt request from the disk controller
|
||||
|
||||
$FF76: Write:
|
||||
00000000 = Caching off
|
||||
00001000 = Tell cache controller to send interrupt when device is
|
||||
ready to send/receive a buffer (seek done, etc.)
|
||||
00000111 = Read cache on - Get next 256 data bytes from controller
|
||||
to cache
|
||||
00000100 = Write cache on - Next 256 bytes stored in cache are
|
||||
sector
|
||||
00000110 = Copy Write cache to controller
|
||||
|
||||
|
||||
|
||||
*********************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
@ -49,18 +75,20 @@
|
||||
#include "machine/msm6242.h"
|
||||
#include "machine/ds1315.h"
|
||||
#include "machine/wd_fdc.h"
|
||||
#include "machine/ram.h"
|
||||
#include "formats/dmk_dsk.h"
|
||||
#include "formats/jvc_dsk.h"
|
||||
#include "formats/vdk_dsk.h"
|
||||
#include "formats/sdf_dsk.h"
|
||||
#include "formats/os9_dsk.h"
|
||||
|
||||
// #define VERBOSE (LOG_GENERAL )
|
||||
#include "logmacro.h"
|
||||
|
||||
/***************************************************************************
|
||||
PARAMETERS
|
||||
***************************************************************************/
|
||||
|
||||
#define LOG_FDC 0
|
||||
#define WD_TAG "wd17xx"
|
||||
#define WD2797_TAG "wd2797"
|
||||
#define DISTO_TAG "disto"
|
||||
@ -88,6 +116,10 @@ protected:
|
||||
NONE = 0xFF
|
||||
};
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
|
||||
// device-level overrides
|
||||
virtual DECLARE_READ8_MEMBER(cts_read) override;
|
||||
virtual DECLARE_READ8_MEMBER(scs_read) override;
|
||||
@ -108,6 +140,16 @@ protected:
|
||||
required_device<msm6242_device> m_disto_msm6242; // 6242 RTC on Disto interface
|
||||
offs_t m_msm6242_rtc_address;
|
||||
optional_ioport m_rtc;
|
||||
|
||||
// Protected
|
||||
virtual DECLARE_READ8_MEMBER(ff74_read);
|
||||
virtual DECLARE_WRITE8_MEMBER(ff74_write);
|
||||
|
||||
private:
|
||||
// registers
|
||||
uint8_t m_cache_controler;
|
||||
uint8_t m_cache_pointer;
|
||||
required_device<ram_device> m_cache_buffer;
|
||||
};
|
||||
|
||||
|
||||
@ -143,6 +185,8 @@ void coco_fdc_device_base::device_add_mconfig(machine_config &config)
|
||||
MSM6242(config, m_disto_msm6242, 32.768_kHz_XTAL);
|
||||
|
||||
DS1315(config, CLOUD9_TAG, 0);
|
||||
|
||||
RAM(config, "cachebuffer").set_default_size("256").set_default_value(0);
|
||||
}
|
||||
|
||||
|
||||
@ -183,6 +227,7 @@ uint8_t* coco_family_fdc_device_base::get_cart_base()
|
||||
return memregion("eprom")->base();
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// coco_family_fdc_device_base::get_cart_memregion
|
||||
//-------------------------------------------------
|
||||
@ -209,9 +254,100 @@ coco_fdc_device_base::coco_fdc_device_base(const machine_config &mconfig, device
|
||||
, m_disto_msm6242(*this, DISTO_TAG)
|
||||
, m_msm6242_rtc_address(0)
|
||||
, m_rtc(*this, ":real_time_clock")
|
||||
, m_cache_buffer(*this, "cachebuffer")
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_start - device-specific start
|
||||
//-------------------------------------------------
|
||||
|
||||
void coco_fdc_device_base::device_start()
|
||||
{
|
||||
install_readwrite_handler(0xFF74, 0xFF76,
|
||||
read8_delegate(*this, FUNC(coco_fdc_device_base::ff74_read)),
|
||||
write8_delegate(*this, FUNC(coco_fdc_device_base::ff74_write)));
|
||||
|
||||
save_item(NAME(m_cache_controler));
|
||||
save_item(NAME(m_cache_pointer));
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_reset - device-specific reset
|
||||
//-------------------------------------------------
|
||||
|
||||
void coco_fdc_device_base::device_reset()
|
||||
{
|
||||
m_cache_controler = 0x80;
|
||||
m_cache_pointer = 0;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// ff74_read - no halt registers
|
||||
//-------------------------------------------------
|
||||
|
||||
READ8_MEMBER(coco_fdc_device_base::ff74_read)
|
||||
{
|
||||
uint8_t data = 0x0;
|
||||
|
||||
switch(offset)
|
||||
{
|
||||
case 0x0:
|
||||
data = m_cache_buffer->read(m_cache_pointer++);
|
||||
LOG( "CachDat_A read: %2.2x\n", data );
|
||||
break;
|
||||
case 0x1:
|
||||
data = m_cache_buffer->read(m_cache_pointer++);
|
||||
LOG( "CachDat_B read: %2.2x\n", data );
|
||||
break;
|
||||
case 0x2:
|
||||
data = m_cache_controler;
|
||||
LOG( "CachCtrl read: %2.2x\n", data );
|
||||
break;
|
||||
}
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// ff74_write - no halt registers
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE8_MEMBER(coco_fdc_device_base::ff74_write)
|
||||
{
|
||||
switch(offset)
|
||||
{
|
||||
case 0x0:
|
||||
LOG( "CachDat_A write: %2.2x\n", data );
|
||||
m_cache_buffer->write(m_cache_pointer++, data);
|
||||
break;
|
||||
case 0x1:
|
||||
LOG( "CachDat_B write: %2.2x\n", data );
|
||||
m_cache_buffer->write(m_cache_pointer++, data);
|
||||
break;
|
||||
case 0x2:
|
||||
LOG( "CachCtrl write: %2.2x\n", data );
|
||||
|
||||
// reset static ram buffer pointer on any write
|
||||
m_cache_pointer = 0;
|
||||
|
||||
if(data == 0)
|
||||
{
|
||||
// Clear interrupt when caching is turned off
|
||||
set_line_value(line::CART, CLEAR_LINE);
|
||||
m_cache_controler |= 0x80;
|
||||
}
|
||||
|
||||
m_cache_controler = (m_cache_controler & 0x80) | (data & 0x7f);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// real_time_clock
|
||||
//-------------------------------------------------
|
||||
@ -238,15 +374,60 @@ coco_fdc_device_base::rtc_type coco_fdc_device_base::real_time_clock()
|
||||
|
||||
void coco_fdc_device_base::update_lines()
|
||||
{
|
||||
// clear HALT enable under certain circumstances
|
||||
if (intrq() && (dskreg() & 0x20))
|
||||
set_dskreg(dskreg() & ~0x80); // clear halt enable
|
||||
if( (m_cache_controler & 0x7f) == 0) /* cache disabled */
|
||||
{
|
||||
// clear HALT enable under certain circumstances
|
||||
if (intrq() && (dskreg() & 0x20))
|
||||
set_dskreg(dskreg() & ~0x80); // clear halt enable
|
||||
|
||||
// set the NMI line
|
||||
set_line_value(line::NMI, intrq() && (dskreg() & 0x20));
|
||||
// set the NMI line
|
||||
set_line_value(line::NMI, intrq() && (dskreg() & 0x20));
|
||||
|
||||
// set the HALT line
|
||||
set_line_value(line::HALT, !drq() && (dskreg() & 0x80));
|
||||
// set the HALT line
|
||||
set_line_value(line::HALT, !drq() && (dskreg() & 0x80));
|
||||
}
|
||||
else
|
||||
{
|
||||
if( drq() == ASSERT_LINE)
|
||||
{
|
||||
if( (m_cache_controler & 0x07) == 0x07) /* Read cache on */
|
||||
{
|
||||
uint8_t data = m_wd17xx->data_r();
|
||||
LOG("Cached drq read: %2.2x\n", data );
|
||||
m_cache_buffer->write(m_cache_pointer++, data);
|
||||
}
|
||||
else if( (m_cache_controler & 0x07) == 0x04 ) /* Write cache on */
|
||||
{
|
||||
uint8_t data = m_cache_buffer->read(m_cache_pointer++);
|
||||
LOG("Cached drq write: %2.2x\n", data );
|
||||
m_wd17xx->data_w(data);
|
||||
}
|
||||
else if( (m_cache_controler & 0x07) == 0x06 ) /* Copy Write cache to controller */
|
||||
{
|
||||
uint8_t data = m_cache_buffer->read(m_cache_pointer++);
|
||||
LOG("Cached drq write: %2.2x\n", data );
|
||||
m_wd17xx->data_w(data);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG("illegal DRQ cached assert mode\n" );
|
||||
}
|
||||
}
|
||||
|
||||
if( (m_cache_controler & 0x08) == 0x08)
|
||||
{
|
||||
set_line_value(line::CART, intrq());
|
||||
}
|
||||
|
||||
if( intrq() == ASSERT_LINE)
|
||||
{
|
||||
m_cache_controler &= 0x7f;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_cache_controler |= 0x80;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -259,19 +440,16 @@ void coco_fdc_device_base::dskreg_w(uint8_t data)
|
||||
uint8_t drive = 0;
|
||||
uint8_t head;
|
||||
|
||||
if (LOG_FDC)
|
||||
{
|
||||
logerror("fdc_coco_dskreg_w(): %c%c%c%c%c%c%c%c ($%02x)\n",
|
||||
data & 0x80 ? 'H' : 'h',
|
||||
data & 0x40 ? '3' : '.',
|
||||
data & 0x20 ? 'D' : 'S',
|
||||
data & 0x10 ? 'P' : 'p',
|
||||
data & 0x08 ? 'M' : 'm',
|
||||
data & 0x04 ? '2' : '.',
|
||||
data & 0x02 ? '1' : '.',
|
||||
data & 0x01 ? '0' : '.',
|
||||
data);
|
||||
}
|
||||
LOG("fdc_coco_dskreg_w(): %c%c%c%c%c%c%c%c ($%02x)\n",
|
||||
data & 0x80 ? 'H' : 'h',
|
||||
data & 0x40 ? '3' : '.',
|
||||
data & 0x20 ? 'D' : 'S',
|
||||
data & 0x10 ? 'P' : 'p',
|
||||
data & 0x08 ? 'M' : 'm',
|
||||
data & 0x04 ? '2' : '.',
|
||||
data & 0x02 ? '1' : '.',
|
||||
data & 0x01 ? '0' : '.',
|
||||
data);
|
||||
|
||||
// An email from John Kowalski informed me that if the DS3 is
|
||||
// high, and one of the other drive bits is selected (DS0-DS2), then the
|
||||
@ -334,41 +512,46 @@ READ8_MEMBER(coco_fdc_device_base::scs_read)
|
||||
{
|
||||
case 8:
|
||||
result = m_wd17xx->status_r();
|
||||
LOG("m_wd17xx->status_r: %2.2x\n", result );
|
||||
break;
|
||||
case 9:
|
||||
result = m_wd17xx->track_r();
|
||||
LOG("m_wd17xx->track_r: %2.2x\n", result );
|
||||
break;
|
||||
case 10:
|
||||
result = m_wd17xx->sector_r();
|
||||
LOG("m_wd17xx->sector_r: %2.2x\n", result );
|
||||
break;
|
||||
case 11:
|
||||
result = m_wd17xx->data_r();
|
||||
LOG("m_wd17xx->data_r: %2.2x\n", result );
|
||||
break;
|
||||
}
|
||||
|
||||
/* other stuff for RTCs */
|
||||
switch (offset)
|
||||
{
|
||||
case 0x10: /* FF50 */
|
||||
if (real_time_clock() == rtc_type::DISTO)
|
||||
result = m_disto_msm6242->read(m_msm6242_rtc_address);
|
||||
break;
|
||||
case 0x10: /* FF50 */
|
||||
if (real_time_clock() == rtc_type::DISTO)
|
||||
result = m_disto_msm6242->read(m_msm6242_rtc_address);
|
||||
break;
|
||||
|
||||
case 0x38: /* FF78 */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
m_ds1315->read_0();
|
||||
break;
|
||||
case 0x38: /* FF78 */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
m_ds1315->read_0();
|
||||
break;
|
||||
|
||||
case 0x39: /* FF79 */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
m_ds1315->read_1();
|
||||
break;
|
||||
case 0x39: /* FF79 */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
m_ds1315->read_1();
|
||||
break;
|
||||
|
||||
case 0x3C: /* FF7C */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
result = m_ds1315->read_data();
|
||||
break;
|
||||
case 0x3C: /* FF7C */
|
||||
if (real_time_clock() == rtc_type::CLOUD9)
|
||||
result = m_ds1315->read_data();
|
||||
break;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -386,15 +569,19 @@ WRITE8_MEMBER(coco_fdc_device_base::scs_write)
|
||||
dskreg_w(data);
|
||||
break;
|
||||
case 8:
|
||||
LOG("m_wd17xx->cmd_w: %2.2x\n", data );
|
||||
m_wd17xx->cmd_w(data);
|
||||
break;
|
||||
case 9:
|
||||
LOG("m_wd17xx->track_w: %2.2x\n", data );
|
||||
m_wd17xx->track_w(data);
|
||||
break;
|
||||
case 10:
|
||||
LOG("m_wd17xx->sector_w: %2.2x\n", data );
|
||||
m_wd17xx->sector_w(data);
|
||||
break;
|
||||
case 11:
|
||||
LOG("m_wd17xx->data_w: %2.2x\n", data );
|
||||
m_wd17xx->data_w(data);
|
||||
break;
|
||||
};
|
||||
|
@ -64,6 +64,7 @@
|
||||
#include "coco_pak.h"
|
||||
#include "coco_rs232.h"
|
||||
#include "coco_ssc.h"
|
||||
#include "coco_ram.h"
|
||||
|
||||
#define SLOT1_TAG "slot1"
|
||||
#define SLOT2_TAG "slot2"
|
||||
@ -164,6 +165,7 @@ static void coco_cart_slot1_3(device_slot_interface &device)
|
||||
device.option_add("dcmodem", COCO_DCMODEM);
|
||||
device.option_add("orch90", COCO_ORCH90);
|
||||
device.option_add("ssc", COCO_SSC);
|
||||
device.option_add("ram", COCO_PAK_RAM);
|
||||
device.option_add("games_master", COCO_PAK_GMC);
|
||||
device.option_add("banked_16k", COCO_PAK_BANKED);
|
||||
device.option_add("pak", COCO_PAK);
|
||||
@ -177,6 +179,7 @@ static void coco_cart_slot4(device_slot_interface &device)
|
||||
device.option_add("dcmodem", COCO_DCMODEM);
|
||||
device.option_add("orch90", COCO_ORCH90);
|
||||
device.option_add("ssc", COCO_SSC);
|
||||
device.option_add("ram", COCO_PAK_RAM);
|
||||
device.option_add("games_master", COCO_PAK_GMC);
|
||||
device.option_add("banked_16k", COCO_PAK_BANKED);
|
||||
device.option_add("pak", COCO_PAK);
|
||||
|
183
src/devices/bus/coco/coco_ram.cpp
Normal file
183
src/devices/bus/coco/coco_ram.cpp
Normal file
@ -0,0 +1,183 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:tim lindner
|
||||
/***************************************************************************
|
||||
|
||||
coco_ram.cpp
|
||||
|
||||
Code for emulating the Disto RAM cartridge
|
||||
|
||||
This cartridge came in several forms: 256K, 512K, 768K, and 1024K.
|
||||
|
||||
***************************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "coco_ram.h"
|
||||
#include "cococart.h"
|
||||
#include "machine/ram.h"
|
||||
|
||||
#define STATICRAM_TAG "static_ram"
|
||||
|
||||
|
||||
// #define VERBOSE (LOG_GENERAL )
|
||||
#include "logmacro.h"
|
||||
|
||||
#define RAM_SIZE_IN_K 1024
|
||||
#define BUFFER_SIZE (RAM_SIZE_IN_K * 1024)
|
||||
|
||||
#define STRINGIZE_HELPER(expr) #expr
|
||||
#define STRINGIZE(expr) STRINGIZE_HELPER(expr)
|
||||
|
||||
//**************************************************************************
|
||||
// TYPE DECLARATIONS
|
||||
//**************************************************************************
|
||||
|
||||
namespace
|
||||
{
|
||||
// ======================> coco_pak_device
|
||||
|
||||
class coco_pak_ram_device :
|
||||
public device_t,
|
||||
public device_cococart_interface
|
||||
{
|
||||
public:
|
||||
// construction/destruction
|
||||
coco_pak_ram_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
virtual void device_add_mconfig(machine_config &config) override;
|
||||
|
||||
protected:
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
virtual DECLARE_WRITE8_MEMBER(scs_write) override;
|
||||
virtual DECLARE_READ8_MEMBER(scs_read) override;
|
||||
|
||||
private:
|
||||
required_device<ram_device> m_staticram;
|
||||
int m_offset;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// GLOBAL VARIABLES
|
||||
//**************************************************************************
|
||||
|
||||
DEFINE_DEVICE_TYPE_PRIVATE(COCO_PAK_RAM, device_cococart_interface, coco_pak_ram_device, "cocopakram", "Disto " STRINGIZE(RAM_SIZE_IN_K) "K RAM Cartridge")
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// coco_pak_device - constructor
|
||||
//-------------------------------------------------
|
||||
|
||||
coco_pak_ram_device::coco_pak_ram_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
|
||||
: device_t(mconfig, COCO_PAK_RAM, tag, owner, clock)
|
||||
, device_cococart_interface(mconfig, *this)
|
||||
, m_staticram(*this, STATICRAM_TAG)
|
||||
, m_offset(0)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// MACHINE FRAGMENTS AND ADDRESS MAPS
|
||||
//**************************************************************************
|
||||
|
||||
void coco_pak_ram_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
RAM(config, STATICRAM_TAG).set_default_size(STRINGIZE(RAM_SIZE_IN_K) "K").set_default_value(0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_start - device-specific startup
|
||||
//-------------------------------------------------
|
||||
|
||||
void coco_pak_ram_device::device_start()
|
||||
{
|
||||
// initial state
|
||||
m_offset = 0;
|
||||
|
||||
// save state
|
||||
save_item(NAME(m_offset));
|
||||
}
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_reset - device-specific reset
|
||||
//-------------------------------------------------
|
||||
|
||||
void coco_pak_ram_device::device_reset()
|
||||
{
|
||||
m_offset = 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// scs_write
|
||||
//-------------------------------------------------
|
||||
|
||||
WRITE8_MEMBER(coco_pak_ram_device::scs_write)
|
||||
{
|
||||
// int idata = data;
|
||||
|
||||
switch(offset)
|
||||
{
|
||||
case 0:
|
||||
m_offset = ((m_offset & 0xffff00) + data);
|
||||
break;
|
||||
case 1:
|
||||
m_offset = ((m_offset & 0xff00ff) + (data << 8));
|
||||
break;
|
||||
case 2:
|
||||
m_offset = ((m_offset & 0x00ffff) + (data << 16));
|
||||
break;
|
||||
case 3:
|
||||
if( m_offset < BUFFER_SIZE )
|
||||
{
|
||||
m_staticram->write(m_offset, data);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
LOG("scs_write: %s: %06x, %02x, %02x\n", machine().describe_context(), m_offset, offset, data);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// scs_read
|
||||
//-------------------------------------------------
|
||||
|
||||
READ8_MEMBER(coco_pak_ram_device::scs_read)
|
||||
{
|
||||
uint8_t data = 0x00;
|
||||
|
||||
switch (offset)
|
||||
{
|
||||
case 0:
|
||||
data = (m_offset) & 0xff;
|
||||
break;
|
||||
case 1:
|
||||
data = (m_offset & 0xff00ff) >> 8;
|
||||
break;
|
||||
case 2:
|
||||
data = (m_offset & 0xff0000) >> 16;
|
||||
break;
|
||||
case 3:
|
||||
if( m_offset < BUFFER_SIZE )
|
||||
{
|
||||
data = m_staticram->read(m_offset);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
LOG("scs_read: %s: %06x, %02x, %02x\n", machine().describe_context(), m_offset, offset, data);
|
||||
return data;
|
||||
}
|
14
src/devices/bus/coco/coco_ram.h
Normal file
14
src/devices/bus/coco/coco_ram.h
Normal file
@ -0,0 +1,14 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:tim lindner
|
||||
#ifndef MAME_BUS_COCO_COCO_RAM_H
|
||||
#define MAME_BUS_COCO_COCO_RAM_H
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "cococart.h"
|
||||
|
||||
// device type definition
|
||||
DECLARE_DEVICE_TYPE(COCO_PAK_RAM, device_cococart_interface)
|
||||
|
||||
#endif // MAME_BUS_COCO_COCO_RAM_H
|
||||
|
@ -148,21 +148,21 @@ bool ekara_rom_i2c_24c08_epitch_device::is_write_access_not_rom(void)
|
||||
|
||||
void ekara_rom_i2c_24c08_epitch_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2CMEM(config, "i2cmem", 0).set_page_size(16).set_data_size(0x400); // 24C08
|
||||
I2C_24C08(config, "i2cmem", 0);
|
||||
}
|
||||
|
||||
// i2c 24lc04
|
||||
|
||||
void ekara_rom_i2c_24lc04_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2CMEM(config, "i2cmem", 0).set_page_size(16).set_data_size(0x200); // 24LC04
|
||||
I2C_24C04(config, "i2cmem", 0); // 24LC04
|
||||
}
|
||||
|
||||
// i2c 24lc02
|
||||
|
||||
void ekara_rom_i2c_24lc02_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2CMEM(config, "i2cmem", 0).set_page_size(16).set_data_size(0x100); // 24LC02
|
||||
I2C_24C02(config, "i2cmem", 0); // 24LC02
|
||||
}
|
||||
|
||||
// i2c 24lc02 with direct IO port access
|
||||
@ -206,7 +206,7 @@ READ_LINE_MEMBER(ekara_rom_i2c_24lc02_gc0010_device::read_sda )
|
||||
|
||||
void ekara_rom_i2c_24lc02_gc0010_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2CMEM(config, "i2cmem", 0)/*.set_page_size(16)*/.set_data_size(0x100); // 24LC02
|
||||
I2C_24C02(config, "i2cmem", 0); // 24LC02
|
||||
}
|
||||
|
||||
|
||||
|
@ -9,6 +9,7 @@
|
||||
|
||||
**********************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
#include "grid2102.h"
|
||||
|
||||
// device type definition
|
||||
|
@ -70,13 +70,30 @@ TIMER_CALLBACK_MEMBER(mc1502_fdc_device::motor_callback)
|
||||
motor_on = 0;
|
||||
}
|
||||
|
||||
void mc1502_fdc_device::motors_onoff()
|
||||
{
|
||||
floppy_image_device *floppy0 = m_fdc->subdevice<floppy_connector>("0")->get_device();
|
||||
floppy_image_device *floppy1 = m_fdc->subdevice<floppy_connector>("1")->get_device();
|
||||
|
||||
if (motor_on)
|
||||
{
|
||||
// bits 2, 3 -- motor on (drive 0, 1)
|
||||
floppy0->mon_w(!(m_control & 4));
|
||||
floppy1->mon_w(!(m_control & 8));
|
||||
}
|
||||
else
|
||||
{
|
||||
floppy0->mon_w(ASSERT_LINE);
|
||||
floppy1->mon_w(ASSERT_LINE);
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t mc1502_fdc_device::mc1502_wd17xx_aux_r()
|
||||
{
|
||||
uint8_t data;
|
||||
|
||||
data = 0;
|
||||
|
||||
return data;
|
||||
motor_timer->adjust(attotime::from_msec(3000));
|
||||
motor_on = 1;
|
||||
motors_onoff();
|
||||
return 0;
|
||||
}
|
||||
|
||||
void mc1502_fdc_device::mc1502_wd17xx_aux_w(uint8_t data)
|
||||
@ -86,24 +103,15 @@ void mc1502_fdc_device::mc1502_wd17xx_aux_w(uint8_t data)
|
||||
floppy_image_device *floppy = ((data & 0x10) ? floppy1 : floppy0);
|
||||
|
||||
// master reset
|
||||
if ((data & 1) == 0)
|
||||
m_fdc->reset();
|
||||
m_fdc->mr_w(data & 1);
|
||||
|
||||
m_fdc->set_floppy(floppy);
|
||||
|
||||
// SIDE ONE
|
||||
floppy->ss_w((data & 2) ? 1 : 0);
|
||||
|
||||
// bits 2, 3 -- motor on (drive 0, 1)
|
||||
// the schematic appears to show the motor lines connected, if they aren't then motor_on doesn't work correctly
|
||||
floppy0->mon_w(!(data & 12));
|
||||
floppy1->mon_w(!(data & 12));
|
||||
|
||||
if (data & 12)
|
||||
{
|
||||
motor_timer->adjust(attotime::from_msec(3000));
|
||||
motor_on = 1;
|
||||
}
|
||||
m_control = data;
|
||||
motors_onoff();
|
||||
}
|
||||
|
||||
/*
|
||||
@ -191,6 +199,7 @@ mc1502_fdc_device::mc1502_fdc_device(const machine_config &mconfig, const char *
|
||||
, device_isa8_card_interface(mconfig, *this)
|
||||
, m_fdc(*this, "fdc")
|
||||
, motor_on(0)
|
||||
, m_control(0)
|
||||
, motor_timer(nullptr)
|
||||
, m_cpu(*this, finder_base::DUMMY_TAG)
|
||||
{
|
||||
@ -214,4 +223,5 @@ void mc1502_fdc_device::device_start()
|
||||
|
||||
motor_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(mc1502_fdc_device::motor_callback),this));
|
||||
motor_on = 0;
|
||||
m_control = 0;
|
||||
}
|
||||
|
@ -51,9 +51,10 @@ private:
|
||||
|
||||
required_device<fd1793_device> m_fdc;
|
||||
int motor_on;
|
||||
u8 m_control;
|
||||
emu_timer *motor_timer;
|
||||
required_device<cpu_device> m_cpu;
|
||||
|
||||
void motors_onoff();
|
||||
public:
|
||||
void mc1502_wd17xx_aux_w(uint8_t data);
|
||||
uint8_t mc1502_wd17xx_aux_r();
|
||||
|
@ -96,7 +96,7 @@ WRITE16_MEMBER(jakks_gamekey_rom_i2c_base_device::write_cart_seeprom)
|
||||
|
||||
void jakks_gamekey_rom_i2c_24lc04_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2CMEM(config, "i2cmem", 0)/*.set_page_size(16)*/.set_data_size(0x200); // 24LC04
|
||||
I2C_24C04(config, "i2cmem", 0); // 24LC04
|
||||
}
|
||||
|
||||
|
||||
|
@ -88,7 +88,7 @@ void md_seprom_codemast_device::device_add_mconfig(machine_config &config)
|
||||
|
||||
void md_seprom_mm96_device::device_add_mconfig(machine_config &config)
|
||||
{
|
||||
I2C_24C16A(config, m_i2cmem);
|
||||
I2C_24C16(config, m_i2cmem); // 24C16A
|
||||
}
|
||||
|
||||
|
||||
|
@ -212,6 +212,7 @@ i8085a_cpu_device::i8085a_cpu_device(const machine_config &mconfig, device_type
|
||||
, m_program_config("program", ENDIANNESS_LITTLE, 8, 16, 0)
|
||||
, m_io_config("io", ENDIANNESS_LITTLE, 8, 8, 0)
|
||||
, m_opcode_config("opcodes", ENDIANNESS_LITTLE, 8, 16, 0)
|
||||
, m_in_inta_func(*this)
|
||||
, m_out_status_func(*this)
|
||||
, m_out_inte_func(*this)
|
||||
, m_in_sid_func(*this)
|
||||
@ -308,6 +309,7 @@ void i8085a_cpu_device::device_start()
|
||||
m_trap_pending = 0;
|
||||
m_trap_im_copy = 0;
|
||||
m_sod_state = 0;
|
||||
m_in_acknowledge = false;
|
||||
m_ietemp = false;
|
||||
|
||||
init_tables();
|
||||
@ -351,6 +353,7 @@ void i8085a_cpu_device::device_start()
|
||||
m_io = &space(AS_IO);
|
||||
|
||||
/* resolve callbacks */
|
||||
m_in_inta_func.resolve();
|
||||
m_out_status_func.resolve_safe();
|
||||
m_out_inte_func.resolve_safe();
|
||||
m_in_sid_func.resolve_safe(0);
|
||||
@ -372,6 +375,7 @@ void i8085a_cpu_device::device_start()
|
||||
save_item(NAME(m_trap_pending));
|
||||
save_item(NAME(m_trap_im_copy));
|
||||
save_item(NAME(m_sod_state));
|
||||
save_item(NAME(m_in_acknowledge));
|
||||
|
||||
set_icountptr(m_icount);
|
||||
}
|
||||
@ -479,11 +483,13 @@ void i8085a_cpu_device::execute_set_input(int irqline, int state)
|
||||
{
|
||||
int newstate = (state != CLEAR_LINE);
|
||||
|
||||
/* NMI is edge-triggered */
|
||||
if (irqline == INPUT_LINE_NMI)
|
||||
/* TRAP is level and edge-triggered NMI */
|
||||
if (irqline == I8085_TRAP_LINE)
|
||||
{
|
||||
if (!m_nmi_state && newstate)
|
||||
m_trap_pending = true;
|
||||
else if (!newstate)
|
||||
m_trap_pending = false;
|
||||
m_nmi_state = newstate;
|
||||
}
|
||||
|
||||
@ -511,6 +517,8 @@ void i8085a_cpu_device::break_halt_for_interrupt()
|
||||
}
|
||||
else
|
||||
set_status(0x23); /* int ack */
|
||||
|
||||
m_in_acknowledge = true;
|
||||
}
|
||||
|
||||
void i8085a_cpu_device::check_for_interrupts()
|
||||
@ -527,7 +535,7 @@ void i8085a_cpu_device::check_for_interrupts()
|
||||
|
||||
/* break out of HALT state and call the IRQ ack callback */
|
||||
break_halt_for_interrupt();
|
||||
standard_irq_callback(INPUT_LINE_NMI);
|
||||
standard_irq_callback(I8085_TRAP_LINE);
|
||||
|
||||
/* push the PC and jump to $0024 */
|
||||
op_push(m_PC);
|
||||
@ -584,29 +592,17 @@ void i8085a_cpu_device::check_for_interrupts()
|
||||
/* followed by classic INTR */
|
||||
else if (m_irq_state[I8085_INTR_LINE] && (m_im & IM_IE))
|
||||
{
|
||||
u32 vector;
|
||||
|
||||
/* break out of HALT state and call the IRQ ack callback */
|
||||
if (!m_in_inta_func.isnull())
|
||||
standard_irq_callback(I8085_INTR_LINE);
|
||||
break_halt_for_interrupt();
|
||||
vector = standard_irq_callback(I8085_INTR_LINE);
|
||||
|
||||
u8 vector = read_inta();
|
||||
|
||||
/* use the resulting vector as an opcode to execute */
|
||||
set_inte(0);
|
||||
switch (vector & 0xff0000)
|
||||
{
|
||||
case 0xcd0000: /* CALL nnnn */
|
||||
m_icount -= 7;
|
||||
op_push(m_PC);
|
||||
case 0xc30000: /* JMP nnnn */
|
||||
m_icount -= 10;
|
||||
m_PC.d = vector & 0xffff;
|
||||
break;
|
||||
|
||||
default:
|
||||
LOG("i8085 take int $%02x\n", vector);
|
||||
execute_one(vector & 0xff);
|
||||
break;
|
||||
}
|
||||
LOG("i8085 take int $%02x\n", vector);
|
||||
execute_one(vector);
|
||||
}
|
||||
}
|
||||
|
||||
@ -670,14 +666,27 @@ u8 i8085a_cpu_device::get_rim_value()
|
||||
// memory access
|
||||
u8 i8085a_cpu_device::read_arg()
|
||||
{
|
||||
return m_cache->read_byte(m_PC.w.l++);
|
||||
set_status(0x82); // memory read
|
||||
if (m_in_acknowledge)
|
||||
return read_inta();
|
||||
else
|
||||
return m_cache->read_byte(m_PC.w.l++);
|
||||
}
|
||||
|
||||
PAIR i8085a_cpu_device::read_arg16()
|
||||
{
|
||||
PAIR p;
|
||||
p.b.l = m_cache->read_byte(m_PC.w.l++);
|
||||
p.b.h = m_cache->read_byte(m_PC.w.l++);
|
||||
set_status(0x82); // memory read
|
||||
if (m_in_acknowledge)
|
||||
{
|
||||
p.b.l = read_inta();
|
||||
p.b.h = read_inta();
|
||||
}
|
||||
else
|
||||
{
|
||||
p.b.l = m_cache->read_byte(m_PC.w.l++);
|
||||
p.b.h = m_cache->read_byte(m_PC.w.l++);
|
||||
}
|
||||
return p;
|
||||
}
|
||||
|
||||
@ -687,6 +696,14 @@ u8 i8085a_cpu_device::read_op()
|
||||
return m_opcode_cache->read_byte(m_PC.w.l++);
|
||||
}
|
||||
|
||||
u8 i8085a_cpu_device::read_inta()
|
||||
{
|
||||
if (m_in_inta_func.isnull())
|
||||
return standard_irq_callback(I8085_INTR_LINE);
|
||||
else
|
||||
return m_in_inta_func(m_PC.w.l);
|
||||
}
|
||||
|
||||
u8 i8085a_cpu_device::read_mem(u32 a)
|
||||
{
|
||||
set_status(0x82); // memory read
|
||||
@ -855,13 +872,15 @@ void i8085a_cpu_device::execute_run()
|
||||
|
||||
do
|
||||
{
|
||||
debugger_instruction_hook(m_PC.d);
|
||||
|
||||
/* the instruction after an EI does not take an interrupt, so
|
||||
we cannot check immediately; handle post-EI behavior here */
|
||||
if (m_after_ei != 0 && --m_after_ei == 0)
|
||||
check_for_interrupts();
|
||||
|
||||
m_in_acknowledge = false;
|
||||
logerror("PC=%04X\n", m_PC.d);
|
||||
debugger_instruction_hook(m_PC.d);
|
||||
|
||||
/* here we go... */
|
||||
execute_one(read_op());
|
||||
|
||||
|
@ -45,6 +45,9 @@ public:
|
||||
// CLK rate callback (8085A only)
|
||||
template <typename... T> void set_clk_out(T &&... args) { m_clk_out_func.set(std::forward<T>(args)...); }
|
||||
|
||||
// INTA vector fetch callback
|
||||
auto in_inta_func() { return m_in_inta_func.bind(); }
|
||||
|
||||
// STATUS changed callback
|
||||
auto out_status_func() { return m_out_status_func.bind(); }
|
||||
|
||||
@ -100,6 +103,7 @@ private:
|
||||
address_space_config m_io_config;
|
||||
address_space_config m_opcode_config;
|
||||
|
||||
devcb_read8 m_in_inta_func;
|
||||
devcb_write8 m_out_status_func;
|
||||
devcb_write_line m_out_inte_func;
|
||||
devcb_read_line m_in_sid_func;
|
||||
@ -121,6 +125,7 @@ private:
|
||||
u8 m_trap_pending; /* TRAP interrupt latched? */
|
||||
u8 m_trap_im_copy; /* copy of IM register when TRAP was taken */
|
||||
u8 m_sod_state; /* state of the SOD line */
|
||||
bool m_in_acknowledge;
|
||||
|
||||
bool m_ietemp; /* import/export temp space */
|
||||
|
||||
@ -144,6 +149,7 @@ private:
|
||||
u8 get_rim_value();
|
||||
void break_halt_for_interrupt();
|
||||
u8 read_op();
|
||||
u8 read_inta();
|
||||
u8 read_arg();
|
||||
PAIR read_arg16();
|
||||
u8 read_mem(u32 a);
|
||||
|
@ -586,7 +586,7 @@ void i80186_cpu_device::device_start()
|
||||
state_add( I8086_VECTOR, "V", m_int_vector).formatstr("%02X");
|
||||
|
||||
state_add( I8086_PC, "PC", m_pc ).callimport().formatstr("%05X");
|
||||
state_add( STATE_GENPCBASE, "CURPC", m_pc ).callimport().formatstr("%05X").noshow();
|
||||
state_add<uint32_t>( STATE_GENPCBASE, "CURPC", [this] { return (m_sregs[CS] << 4) + m_prev_ip; }).mask(0xfffff).noshow();
|
||||
state_add( I8086_HALT, "HALT", m_halt ).mask(1);
|
||||
|
||||
// Most of these mnemonics are borrowed from the Intel 80C186EA/80C188EA User's Manual.
|
||||
|
@ -275,7 +275,7 @@ void i80286_cpu_device::device_start()
|
||||
state_add( I286_VECTOR, "V", m_int_vector).formatstr("%02X");
|
||||
|
||||
state_add( I286_PC, "PC", m_pc).callimport().formatstr("%06X");
|
||||
state_add( STATE_GENPCBASE, "CURPC", m_pc ).callimport().formatstr("%06X").noshow();
|
||||
state_add<uint32_t>( STATE_GENPCBASE, "CURPC", [this] { return m_base[CS] + m_prev_ip; }).mask(0xffffff).noshow();
|
||||
state_add( I8086_HALT, "HALT", m_halt ).mask(1);
|
||||
|
||||
m_out_shutdown_func.resolve_safe();
|
||||
@ -316,7 +316,6 @@ void i80286_cpu_device::state_import(const device_state_entry &entry)
|
||||
break;
|
||||
|
||||
case STATE_GENPC:
|
||||
case STATE_GENPCBASE:
|
||||
if (m_pc - m_base[CS] > m_limit[CS])
|
||||
{
|
||||
// TODO: should this call data_descriptor instead of ignoring jumps outside the current segment?
|
||||
@ -331,6 +330,7 @@ void i80286_cpu_device::state_import(const device_state_entry &entry)
|
||||
}
|
||||
}
|
||||
m_ip = m_pc - m_base[CS];
|
||||
m_prev_ip = m_ip;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -769,7 +769,7 @@ void i80286_cpu_device::code_descriptor(uint16_t selector, uint16_t offset, int
|
||||
m_limit[CS] = LIMIT(desc);
|
||||
m_base[CS] = BASE(desc);
|
||||
m_rights[CS] = RIGHTS(desc);
|
||||
m_ip = offset;
|
||||
m_prev_ip = m_ip = offset;
|
||||
}
|
||||
else
|
||||
{ // systemdescriptor
|
||||
@ -862,7 +862,7 @@ void i80286_cpu_device::code_descriptor(uint16_t selector, uint16_t offset, int
|
||||
}
|
||||
else
|
||||
{
|
||||
m_ip = offset;
|
||||
m_prev_ip = m_ip = offset;
|
||||
m_sregs[CS]=selector;
|
||||
m_base[CS]=selector<<4;
|
||||
m_rights[CS]=0x93;
|
||||
@ -880,11 +880,11 @@ void i80286_cpu_device::interrupt_descriptor(int number, int hwint, int error)
|
||||
{
|
||||
number = standard_irq_callback(0);
|
||||
|
||||
m_irq_state = CLEAR_LINE;
|
||||
m_pending_irq &= ~INT_IRQ;
|
||||
hwint = 1;
|
||||
}
|
||||
|
||||
debugger_exception_hook(number);
|
||||
|
||||
if(!PM)
|
||||
{
|
||||
PUSH(flags & ~0xf000);
|
||||
@ -979,7 +979,7 @@ void i80286_cpu_device::interrupt_descriptor(int number, int hwint, int error)
|
||||
m_limit[CS] = LIMIT(gatedesc);
|
||||
m_base[CS] = BASE(gatedesc);
|
||||
m_rights[CS] = RIGHTS(gatedesc);
|
||||
m_ip = GATEOFF(desc);
|
||||
m_prev_ip = m_ip = GATEOFF(desc);
|
||||
m_TF = 0;
|
||||
m_NT = 0;
|
||||
if(GATE(RIGHTS(desc)) == INTGATE)
|
||||
|
@ -23,6 +23,16 @@ enum
|
||||
I286_BP,
|
||||
I286_SI,
|
||||
I286_DI,
|
||||
|
||||
I286_AL,
|
||||
I286_AH,
|
||||
I286_CL,
|
||||
I286_CH,
|
||||
I286_DL,
|
||||
I286_DH,
|
||||
I286_BL,
|
||||
I286_BH,
|
||||
|
||||
I286_FLAGS,
|
||||
|
||||
I286_ES,
|
||||
|
@ -359,7 +359,7 @@ void i8086_cpu_device::device_start()
|
||||
state_add( I8086_VECTOR, "V", m_int_vector).formatstr("%02X");
|
||||
|
||||
state_add( I8086_PC, "PC", m_pc ).callimport().formatstr("%05X");
|
||||
state_add( STATE_GENPCBASE, "CURPC", m_pc ).callimport().formatstr("%05X").noshow();
|
||||
state_add<uint32_t>( STATE_GENPCBASE, "CURPC", [this] { return (m_sregs[CS] << 4) + m_prev_ip; }).mask(0xfffff).noshow();
|
||||
state_add( I8086_HALT, "HALT", m_halt ).mask(1);
|
||||
}
|
||||
|
||||
@ -421,10 +421,10 @@ void i8086_common_cpu_device::state_import(const device_state_entry &entry)
|
||||
break;
|
||||
|
||||
case STATE_GENPC:
|
||||
case STATE_GENPCBASE:
|
||||
if (m_pc - (m_sregs[CS] << 4) > 0xffff)
|
||||
m_sregs[CS] = m_pc >> 4;
|
||||
m_ip = m_pc - (m_sregs[CS] << 4);
|
||||
m_prev_ip = m_ip;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -506,7 +506,7 @@ void i8086_common_cpu_device::device_start()
|
||||
// Register state for debugger
|
||||
state_add( I8086_IP, "IP", m_ip ).callimport().formatstr("%04X");
|
||||
state_add( I8086_AX, "AX", m_regs.w[AX] ).formatstr("%04X");
|
||||
state_add( I8086_CX, "CX", m_regs.w[CS] ).formatstr("%04X");
|
||||
state_add( I8086_CX, "CX", m_regs.w[CX] ).formatstr("%04X");
|
||||
state_add( I8086_DX, "DX", m_regs.w[DX] ).formatstr("%04X");
|
||||
state_add( I8086_BX, "BX", m_regs.w[BX] ).formatstr("%04X");
|
||||
state_add( I8086_SP, "SP", m_regs.w[SP] ).formatstr("%04X");
|
||||
@ -514,6 +514,15 @@ void i8086_common_cpu_device::device_start()
|
||||
state_add( I8086_SI, "SI", m_regs.w[SI] ).formatstr("%04X");
|
||||
state_add( I8086_DI, "DI", m_regs.w[DI] ).formatstr("%04X");
|
||||
|
||||
state_add( I8086_AL, "AL", m_regs.b[AL] ).noshow();
|
||||
state_add( I8086_AH, "AH", m_regs.b[AH] ).noshow();
|
||||
state_add( I8086_CL, "CL", m_regs.b[CL] ).noshow();
|
||||
state_add( I8086_CH, "CH", m_regs.b[CH] ).noshow();
|
||||
state_add( I8086_DL, "DL", m_regs.b[DL] ).noshow();
|
||||
state_add( I8086_DH, "DH", m_regs.b[DH] ).noshow();
|
||||
state_add( I8086_BL, "BL", m_regs.b[BL] ).noshow();
|
||||
state_add( I8086_BH, "BH", m_regs.b[BH] ).noshow();
|
||||
|
||||
state_add(STATE_GENFLAGS, "GENFLAGS", m_TF).formatstr("%16s").noshow();
|
||||
|
||||
set_icountptr(m_icount);
|
||||
@ -586,7 +595,7 @@ void i8086_common_cpu_device::interrupt(int int_num, int trap)
|
||||
|
||||
PUSH(m_sregs[CS]);
|
||||
PUSH(m_ip);
|
||||
m_ip = dest_off;
|
||||
m_prev_ip = m_ip = dest_off;
|
||||
m_sregs[CS] = dest_seg;
|
||||
}
|
||||
|
||||
|
@ -20,6 +20,7 @@ enum
|
||||
{
|
||||
I8086_PC = STATE_GENPC,
|
||||
I8086_IP = 1, I8086_AX, I8086_CX, I8086_DX, I8086_BX, I8086_SP, I8086_BP, I8086_SI, I8086_DI,
|
||||
I8086_AL, I8086_AH, I8086_CL, I8086_CH, I8086_DL, I8086_DH, I8086_BL, I8086_BH,
|
||||
I8086_FLAGS, I8086_ES, I8086_CS, I8086_SS, I8086_DS,
|
||||
I8086_VECTOR, I8086_HALT
|
||||
};
|
||||
|
@ -91,6 +91,27 @@ void i960_cpu_device::send_iac(uint32_t adr)
|
||||
iac[3] = m_program->read_dword(adr+12);
|
||||
|
||||
switch(iac[0]>>24) {
|
||||
case 0x40: // generate irq
|
||||
break;
|
||||
case 0x41: // test for pending interrupts
|
||||
// check_irqs() seems to take care of this
|
||||
// though it may not be entirely accurate
|
||||
check_irqs();
|
||||
break;
|
||||
case 0x80: // store SAT & PRCB in memory
|
||||
m_program->write_dword(iac[1], m_SAT);
|
||||
m_program->write_dword(iac[1]+4, m_PRCB);
|
||||
break;
|
||||
case 0x89: // invalidate internal instruction cache
|
||||
// we do not emulate the instruction cache, so this is safe to ignore
|
||||
break;
|
||||
case 0x8F: // enable/disable breakpoints
|
||||
// processor breakpoints are not emulated, safe to ignore
|
||||
break;
|
||||
case 0x91: // stop processor
|
||||
break;
|
||||
case 0x92: // continue initialization
|
||||
break;
|
||||
case 0x93: // reinit
|
||||
m_SAT = iac[1];
|
||||
m_PRCB = iac[2];
|
||||
|
@ -9,90 +9,169 @@
|
||||
#include "emu.h"
|
||||
#include "i960dis.h"
|
||||
|
||||
/*
|
||||
Based on documents:
|
||||
270567-001 80960KB Programmer's Reference Manual (March 1988)
|
||||
270710-003 i960 CA/CF Microprocessor User's Manual (March 1994)
|
||||
271081-001 80960MC Programmer's Reference Manual (July 1988)
|
||||
272483-001 i960 Jx Microprocessor User's Manual (September 1994)
|
||||
272484-002 i960 Hx Microprocessor Developer's Manual (September 1998)
|
||||
272736-002 i960 Rx I/O Microprocessor Developer's Manual (April 1997)
|
||||
273353-001 Intel 80303 I/O Processor Developer's Manual (May 2000)
|
||||
*/
|
||||
|
||||
const i960_disassembler::mnemonic_t i960_disassembler::mnemonic[256] = {
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 00
|
||||
{ "b", 8 }, { "call", 8 }, { "ret", 9 }, { "bal", 8 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // 00
|
||||
{ "b", 1, 1 }, { "call", 1, 1 }, { "ret", 1, 0 }, { "bal", 1, 1 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "bno", 8 }, { "bg", 8 }, { "be", 8 }, { "bge", 8 }, { "bl", 8 }, { "bne", 8 }, { "ble", 8 }, { "bo", 8 }, // 10
|
||||
{ "faultno", 0 }, { "faultg", 0 }, { "faulte", 0 }, { "faultge", 0 }, { "faultl", 0 }, { "faultne", 0 }, { "faultle", 0 }, { "faulto", 0 },
|
||||
{ "bno", 1, 1 }, { "bg", 1, 1 }, { "be", 1, 1 }, { "bge", 1, 1 }, { "bl", 1, 1 }, { "bne", 1, 1 }, { "ble", 1, 1 }, { "bo", 1, 1 }, // 10
|
||||
{ "faultno", 1, 0 }, { "faultg", 1, 0 }, { "faulte", 1, 0 }, { "faultge", 1, 0 }, { "faultl", 1, 0 }, { "faultne", 1, 0 }, { "faultle", 1, 0 }, { "faulto", 1, 0 },
|
||||
|
||||
{ "testno", 10 }, { "testg", 10 }, { "teste", 10 }, { "testge", 10 }, { "testl", 10 }, { "testne", 10 }, { "testle", 10 }, { "testo", 10 }, // 20
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "testno", 2, 1 }, { "testg", 2, 1 }, { "teste", 2, 1 }, { "testge", 2, 1 }, { "testl", 2, 1 }, { "testne", 2, 1 }, { "testle", 2, 1 }, { "testo", 2, 1 }, // 20
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "bbc", 6 }, { "cmpobg", 7 }, { "cmpobe", 7 }, { "cmpobge", 7 }, { "cmpobl", 7 }, { "cmpobne", 7 }, { "cmpoble", 7 }, { "bbs", 6 }, // 30
|
||||
{ "cmpibno", 7 }, { "cmpibg", 7 }, { "cmpibe", 7 }, { "cmpibge", 7 }, { "cmpibl", 7 }, { "cmpibne", 7 }, { "cmpible", 7 }, { "cmpibo", 7 },
|
||||
{ "bbc", 2, 3 }, { "cmpobg", 2, 3 }, { "cmpobe", 2, 3 }, { "cmpobge", 2, 3 }, { "cmpobl", 2, 3 }, { "cmpobne", 2, 3 }, { "cmpoble", 2, 3 }, { "bbs", 2, 3 }, // 30
|
||||
{ "cmpibno", 2, 3 }, { "cmpibg", 2, 3 }, { "cmpibe", 2, 3 }, { "cmpibge", 2, 3 }, { "cmpibl", 2, 3 }, { "cmpibne", 2, 3 }, { "cmpible", 2, 3 }, { "cmpibo", 2, 3 },
|
||||
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 40
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // 40
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 50
|
||||
{ "58", 3 }, { "59", 3 }, { "5A", 3 }, { "5B", 3 }, { "5C", 2 }, { "5D", 2 }, { "?", 0 }, { "5F", 2 },
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // 50
|
||||
{ "58", 4, 0 }, { "59", 4, 0 }, { "5A", 4, 0 }, { "5B", 4, 0 }, { "5C", 4, 0 }, { "5D", 4, 0 }, { "?", 0, 0 }, { "5F", 4, 0 },
|
||||
|
||||
{ "60", 3 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "64", 3 }, { "65", 3 }, { "calls", 0 }, { "67", 3 }, // 60
|
||||
{ "68", 3 }, { "69", 3 }, { "?", 0 }, { "?", 0 }, { "6C", 3 }, { "6D", 3 }, { "6E", 3 }, { "?", 0 },
|
||||
{ "60", 4, 0 }, { "61", 4, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "64", 4, 0 }, { "65", 4, 0 }, { "66", 4, 0 }, { "67", 4, 0 }, // 60
|
||||
{ "68", 4, 0 }, { "69", 4, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "6C", 4, 0 }, { "6D", 4, 0 }, { "6E", 4, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "70", 3 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "74", 3 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 70
|
||||
{ "78", 3 }, { "79", 3 }, { "7A", 3 }, { "7B", 3 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "70", 4, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "74", 4, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // 70
|
||||
{ "78", 4, 0 }, { "79", 4, 0 }, { "7A", 4, 0 }, { "7B", 4, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "ldob", 4 }, { "?", 0 }, { "stob", 1 }, { "?", 0 }, { "bx", 11 }, { "balx", 1 }, { "callx", 11 }, { "?", 0 }, // 80
|
||||
{ "ldos", 4 }, { "?", 0 }, { "stos", 1 }, { "?", 0 }, { "lda", 4 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "ldob", 3, 2 }, { "?", 0, 0 }, { "stob", 3, -2 }, { "?", 0, 0 }, { "bx", 3, 1 }, { "balx", 3, 2 }, { "callx", 3, 1 }, { "?", 0, 0 }, // 80
|
||||
{ "ldos", 3, 2 }, { "?", 0, 0 }, { "stos", 3, -2 }, { "?", 0, 0 }, { "lda", 3, 2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "ld", 4 }, { "?", 0 }, { "st", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 90
|
||||
{ "ldl", 4 }, { "?", 0 }, { "stl", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "ld", 3, 2 }, { "?", 0, 0 }, { "st", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // 90
|
||||
{ "ldl", 3, 2 }, { "?", 0, 0 }, { "stl", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "ldt", 4 }, { "?", 0 }, { "stt", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // a0
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "ldt", 3, 2 }, { "?", 0, 0 }, { "stt", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // a0
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "dcinva", 3, 1 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "ldq", 4 }, { "?", 0 }, { "stq", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // b0
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "ldq", 3, 2 }, { "?", 0, 0 }, { "stq", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // b0
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "ldib", 4 }, { "?", 0 }, { "stib", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // c0
|
||||
{ "ldis", 4 }, { "?", 0 }, { "stis", 1 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "ldib", 3, 2 }, { "?", 0, 0 }, { "stib", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // c0
|
||||
{ "ldis", 3, 2 }, { "?", 0, 0 }, { "stis", 3, -2 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // d0
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // d0
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // e0
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 },
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // e0
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 },
|
||||
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // f0
|
||||
{ "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, // f0
|
||||
{ "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }, { "?", 0, 0 }
|
||||
};
|
||||
|
||||
const i960_disassembler::mnemonic_t i960_disassembler::mnem_reg[111] =
|
||||
const i960_disassembler::mnemonic_t i960_disassembler::mnem_reg[197] =
|
||||
{
|
||||
{ "notbit", 0x580 }, { "and", 0x581 }, { "andnot", 0x582 }, { "setbit", 0x583 }, { "notand",0x584 },
|
||||
{ "xor", 0x586 }, { "or", 0x587 }, { "nor", 0x588 }, { "xnor",0x589 }, { "not",0x58a },
|
||||
{ "clrbit", 0x58c }, { "alterbit", 0x58f },
|
||||
{ "addo", 0x590 }, { "addi",0x591 }, { "subo",0x592 }, { "subi",0x593 }, { "cmpob",0x594 }, { "shro",0x598 }, { "shrdi",0x59a }, { "shri",0x59b }, { "shlo",0x59c }, { "rotate",0x59d }, { "shli",0x59e },
|
||||
{ "cmpo",0x5a0 }, { "cmpi",0x5a1 }, { "concmpo",0x5a2 }, { "concmpi",0x5a3 }, { "cmpinco",0x5a4 }, { "cmpinci",0x5a5 }, { "cmpdeco",0x5a6 }, { "cmpdeci",0x5a7 }, { "scanbyte",0x5ac }, { "bswap",0x5ad }, { "chkbit",0x5ae },
|
||||
{ "addc",0x5b0 }, { "subc",0x5b2 },
|
||||
{ "mov", 0x5cc },
|
||||
{ "movl",0x5dc },
|
||||
{ "movq",0x5fc },
|
||||
{ "synmov",0x600 }, { "synmovq",0x602 },
|
||||
{ "scanbit", 0x641 }, { "daddc", 0x642 }, { "dsubc", 0x643 }, { "dmovt", 0x644 }, { "modac",0x645 },
|
||||
{ "modify",0x650 }, { "extract",0x651 }, { "modtc",0x654 }, { "modpc",0x655 },
|
||||
{ "emul",0x670 }, { "ediv",0x671 }, { "cvtir", 0x674 }, { "cvtilr", 0x675 }, { "scalerl", 0x676 }, { "scaler", 0x677 },
|
||||
{ "atanr",0x680 }, { "logepr", 0x681 }, { "logr", 0x682 }, { "remr", 0x683 }, { "cmpor", 0x684 }, { "cmpr", 0x685 }, { "sqrtr", 0x688 },
|
||||
{ "expr", 0x689 }, { "logbnr", 0x68a }, { "roundr", 0x68b }, { "sinr", 0x68c }, { "cosr", 0x68d }, { "tanr", 0x68e }, { "classr", 0x68f },
|
||||
{ "atanrl",0x690 }, { "logeprl", 0x691 }, { "logrl", 0x692 }, { "remrl", 0x693 }, { "cmporl", 0x694 }, { "cmprl", 0x695 }, { "sqrtrl", 0x698 },
|
||||
{ "exprl", 0x699 }, { "logbnrl", 0x69a }, { "roundrl", 0x69b }, { "sinrl", 0x69c }, { "cosrl", 0x69d }, { "tanrl", 0x69e }, { "classrl", 0x69f },
|
||||
{ "cvtri", 0x6c0 }, { "cvtril", 0x6c1 }, { "cvtzri", 0x6c2 }, { "cvtzril", 0x6c3 }, { "movr", 0x6c9 },
|
||||
{ "movrl", 0x6d9 },
|
||||
{ "movre", 0x6e1 }, { "cpysre", 0x6e2 }, { "cpyrsre", 0x6e3 },
|
||||
{ "mulo", 0x701 }, { "remo",0x708 }, { "divo",0x70b },
|
||||
{ "muli",0x741 }, { "remi",0x748 }, { "modi",0x749 }, { "divi",0x74b },
|
||||
{ "divr",0x78b }, { "mulr",0x78c }, { "subr",0x78d }, { "addr",0x78f },
|
||||
{ "divrl",0x79b }, { "mulrl",0x79c }, { "subrl",0x79d }, { "addrl",0x79f },
|
||||
{ "ending_code",0 }
|
||||
};
|
||||
{ "notbit", 0x580, -3 }, { "and", 0x581, -3 }, { "andnot", 0x582, -3 }, { "setbit", 0x583, -3 }, // 58
|
||||
{ "notand", 0x584, -3 }, { "xor", 0x586, -3 }, { "or", 0x587, -3 },
|
||||
{ "nor", 0x588, -3 }, { "xnor", 0x589, -3 }, { "not", 0x58a, -2 }, { "ornot", 0x58b, -3 },
|
||||
{ "clrbit", 0x58c, -3 }, { "notor", 0x58d, -3 }, { "nand", 0x58e, -3 }, { "alterbit", 0x58f, -3 },
|
||||
|
||||
const char *const i960_disassembler::constnames[32] =
|
||||
{
|
||||
"0x0", "0x1", "0x2", "0x3", "0x4", "0x5", "0x6", "0x7", "0x8", "0x9", "0xa", "0xb", "0xc", "0xd", "0xe", "0xf",
|
||||
"0x10", "0x11", "0x12", "0x13", "0x14", "0x15", "0x16", "0x17", "0x18", "0x19", "0x1a", "0x1b", "0x1c", "0x1d", "0x1e", "0x1f"
|
||||
{ "addo", 0x590, -3 }, { "addi", 0x591, -3 }, { "subo", 0x592, -3 }, { "subi", 0x593, -3 }, // 59
|
||||
{ "cmpob", 0x594, 2 }, { "cmpib", 0x595, 2 }, { "cmpos", 0x596, 2 }, { "cmpis", 0x597, 2 },
|
||||
{ "shro", 0x598, -3 }, { "shrdi", 0x59a, -3 }, { "shri", 0x59b, -3 },
|
||||
{ "shlo", 0x59c, -3 }, { "rotate", 0x59d, -3 }, { "shli", 0x59e, -3 },
|
||||
|
||||
{ "cmpo", 0x5a0, 2 }, { "cmpi", 0x5a1, 2 }, { "concmpo", 0x5a2, 2 }, { "concmpi", 0x5a3, 2 }, // 5a
|
||||
{ "cmpinco", 0x5a4, -3 }, { "cmpinci", 0x5a5, -3 }, { "cmpdeco", 0x5a6, -3 }, { "cmpdeci", 0x5a7, -3 },
|
||||
{ "scanbyte", 0x5ac, 2 }, { "bswap", 0x5ad, -2 }, { "chkbit", 0x5ae, 2 },
|
||||
|
||||
{ "addc", 0x5b0, -3 }, { "subc", 0x5b2, -3 }, { "intdis", 0x5b4, 0 }, { "inten", 0x5b5, 0 }, // 5b
|
||||
|
||||
{ "mov", 0x5cc, -2 }, // 5c
|
||||
|
||||
{ "eshro", 0x5d8, -3 }, // 5d
|
||||
{ "movl", 0x5dc, -2 },
|
||||
|
||||
{ "movt", 0x5ec, -2 }, // 5e
|
||||
|
||||
{ "movq", 0x5fc, -2 }, // 5f
|
||||
|
||||
{ "synmov", 0x600, 2 }, { "synmovl", 0x601, 2 }, { "synmovq", 0x602, 2 }, { "cmpstr", 0x603, 3 }, // 60
|
||||
{ "movqstr", 0x604, -3 }, { "movstr", 0x605, -3 },
|
||||
|
||||
{ "atmod", 0x610, 33 }, { "atadd", 0x612, 33 }, { "inspacc", 0x613, -2 }, // 61
|
||||
{ "ldphy", 0x614, -2 }, { "synld", 0x615, -2 }, { "fill", 0x617, 3 },
|
||||
|
||||
{ "sdma", 0x630, 3 }, { "udma", 0x631, 0 }, // 63
|
||||
|
||||
{ "spanbit", 0x640, -2 }, { "scanbit", 0x641, -2 }, { "daddc", 0x642, -3 }, { "dsubc", 0x643, -3 }, // 64
|
||||
{ "dmovt", 0x644, -2 }, { "modac", 0x645, 3 },
|
||||
|
||||
{ "modify", 0x650, 33 }, { "extract", 0x651, 33 }, // 65
|
||||
{ "modtc", 0x654, 33 }, { "modpc", 0x655, 33 }, { "receive", 0x656, -2 },
|
||||
{ "intctl", 0x658, -2 }, { "sysctl", 0x659, 33 }, { "icctl", 0x65b, 33 },
|
||||
{ "dcctl", 0x65c, 33 }, { "halt", 0x65d, 0 },
|
||||
|
||||
{ "calls", 0x660, 1 }, { "send", 0x662, -3 }, { "sendserv", 0x663, 1 }, // 66
|
||||
{ "resumprcs", 0x664, 1 }, { "schedprcs", 0x665, 1 }, { "saveprcs", 0x666, 0 },
|
||||
{ "condwait", 0x668, 1 }, { "wait", 0x669, 1 }, { "signal", 0x66a, 1 }, { "mark", 0x66b, 0 },
|
||||
{ "fmark", 0x66c, 0 }, { "flushreg", 0x66d, 0 }, { "syncf", 0x66f, 0 },
|
||||
|
||||
{ "emul", 0x670, -3 }, { "ediv", 0x671, -3 }, { "ldtime", 0x671, -1 }, // 67
|
||||
{ "cvtir", 0x674, -20 }, { "cvtilr", 0x675, -20 }, { "scalerl", 0x676, -30 }, { "scaler", 0x677, -30 },
|
||||
|
||||
{ "atanr", 0x680, -30 }, { "logepr", 0x681, -30 }, { "logr", 0x682, -30 }, { "remr", 0x683, -30 }, // 68
|
||||
{ "cmpor", 0x684, 20 }, { "cmpr", 0x685, 20 },
|
||||
{ "sqrtr", 0x688, -20 }, { "expr", 0x689, -20 }, { "logbnr", 0x68a, -20 }, { "roundr", 0x68b, -20 },
|
||||
{ "sinr", 0x68c, -20 }, { "cosr", 0x68d, -20 }, { "tanr", 0x68e, -20 }, { "classr", 0x68f, 10 },
|
||||
|
||||
{ "atanrl", 0x690, -30 }, { "logeprl", 0x691, -30 }, { "logrl", 0x692, -30 }, { "remrl", 0x693, -30 }, // 69
|
||||
{ "cmporl", 0x694, 20 }, { "cmprl", 0x695, 20 },
|
||||
{ "sqrtrl", 0x698, -20 }, { "exprl", 0x699, -20 }, { "logbnrl", 0x69a, -20 }, { "roundrl", 0x69b, -20 },
|
||||
{ "sinrl", 0x69c, -20 }, { "cosrl", 0x69d, -20 }, { "tanrl", 0x69e, -20 }, { "classrl", 0x69f, 10 },
|
||||
|
||||
{ "cvtri", 0x6c0, -20 }, { "cvtril", 0x6c1, -20 }, { "cvtzri", 0x6c2, -20 }, { "cvtzril", 0x6c3, -20 }, // 6c
|
||||
{ "movr", 0x6c9, -20 },
|
||||
|
||||
{ "movrl", 0x6d9, -20 }, // 6d
|
||||
|
||||
{ "movre", 0x6e1, -20 }, { "cpysre", 0x6e2, -30 }, { "cpyrsre", 0x6e3, -30 }, // 6e
|
||||
{ "movre", 0x6e9, -20 },
|
||||
|
||||
{ "mulo", 0x701, -3 }, // 70
|
||||
{ "remo", 0x708, -3 }, { "divo", 0x70b, -3 },
|
||||
|
||||
{ "muli", 0x741, -3 }, // 74
|
||||
{ "remi", 0x748, -3 }, { "modi", 0x749, -3 }, { "divi", 0x74b, -3 },
|
||||
|
||||
{ "addono", 0x780, -3 }, { "addino", 0x781, -3 }, { "subono", 0x782, -3 }, { "subino", 0x783, -3 }, // 78
|
||||
{ "selno", 0x784, -3 },
|
||||
{ "divr", 0x78b, -30 }, { "mulr", 0x78c, -30 }, { "subr", 0x78d, -30 }, { "addr", 0x78f, -30 },
|
||||
|
||||
{ "addog", 0x790, -3 }, { "addig", 0x791, -3 }, { "subog", 0x792, -3 }, { "subig", 0x793, -3 }, // 79
|
||||
{ "selg", 0x794, -3 },
|
||||
{ "divrl", 0x79b, -30 }, { "mulrl", 0x79c, -30 }, { "subrl", 0x79d, -30 }, { "addrl", 0x79f, -30 },
|
||||
|
||||
{ "addoe", 0x7a0, -3 }, { "addie", 0x7a1, -3 }, { "suboe", 0x7a2, -3 }, { "subie", 0x7a3, -3 }, // 7a
|
||||
{ "sele", 0x7a4, -3 },
|
||||
|
||||
{ "addoge", 0x7b0, -3 }, { "addige", 0x7b1, -3 }, { "suboge", 0x7b2, -3 }, { "subige", 0x7b3, -3 }, // 7b
|
||||
{ "selge", 0x7b4, -3 },
|
||||
|
||||
{ "addol", 0x7c0, -3 }, { "addil", 0x7c1, -3 }, { "subol", 0x7c2, -3 }, { "subil", 0x7c3, -3 }, // 7c
|
||||
{ "sell", 0x7c4, -3 },
|
||||
|
||||
{ "addone", 0x7d0, -3 }, { "addine", 0x7d1, -3 }, { "subone", 0x7d2, -3 }, { "subine", 0x7d3, -3 }, // 7d
|
||||
{ "selne", 0x7d4, -3 },
|
||||
|
||||
{ "addole", 0x7e0, -3 }, { "addile", 0x7e1, -3 }, { "subole", 0x7e2, -3 }, { "subile", 0x7e3, -3 }, // 7e
|
||||
{ "selle", 0x7e4, -3 },
|
||||
|
||||
{ "addoo", 0x7f0, -3 }, { "addio", 0x7f1, -3 }, { "suboo", 0x7f2, -3 }, { "subio", 0x7f3, -3 }, // 7f
|
||||
{ "selo", 0x7f4, -3 },
|
||||
|
||||
{ "ending_code", 0, 0 }
|
||||
};
|
||||
|
||||
const char *const i960_disassembler::regnames[32] =
|
||||
@ -101,80 +180,355 @@ const char *const i960_disassembler::regnames[32] =
|
||||
"g0","g1","g2","g3", "g4","g5","g6","g7", "g8","g9","g10","g11", "g12","g13","g14","fp",
|
||||
};
|
||||
|
||||
#define REG_DST regnames[dst]
|
||||
#define REG_ABASE regnames[abase]
|
||||
#define REG_REG2 regnames[reg2]
|
||||
#define REG_COBR_SRC1 ((iCode & 0x2000) ? constnames[COBRSRC1] : regnames[COBRSRC1])
|
||||
#define REG_COBR_SRC2 regnames[COBRSRC2]
|
||||
#define NEM mnemonic[op].mnem
|
||||
|
||||
// REG format
|
||||
#define SRC1 (iCode & 0x1f)
|
||||
#define S1 ((iCode >> 5) & 0x1)
|
||||
#define S2 ((iCode >> 6) & 0x1)
|
||||
#define OP2 ((iCode >> 7) & 0xf)
|
||||
#define M1 ((iCode >> 11) & 0x1)
|
||||
#define M2 ((iCode >> 12) & 0x1)
|
||||
#define M3 ((iCode >> 13) & 0x1)
|
||||
#define SRC2 ((iCode >> 14) & 0x1f)
|
||||
#define DST ((iCode >> 19) & 0x1f)
|
||||
#define OP ((iCode >> 24) & 0xff)
|
||||
|
||||
// COBR format
|
||||
#define COBRSRC1 ((iCode >> 19) & 0x1f)
|
||||
#define COBRSRC2 ((iCode >> 14) & 0x1f)
|
||||
|
||||
std::string i960_disassembler::dis_decode_reg(u32 iCode, unsigned char cnt)
|
||||
const char *const i960_disassembler::fprnames[32] =
|
||||
{
|
||||
std::string src1, src2, dst;
|
||||
"fp0","fp1","fp2","fp3", "?","?","?","?", "?","?","?","?", "?","?","?","?",
|
||||
"+0.0","?","?","?", "?","?","+1.0","?", "?","?","?","?", "?","?","?","?",
|
||||
};
|
||||
|
||||
if (S1)
|
||||
src1 = "";
|
||||
else
|
||||
offs_t i960_disassembler::dis_decode_invalid(std::ostream &stream, u32 iCode)
|
||||
{
|
||||
/*
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
u8 op2 = (unsigned char) (iCode >> 7)&0xf;
|
||||
u8 model = (unsigned char) (iCode >> 10) &0x3;
|
||||
u8 modeh = (unsigned char) (iCode >> 12) &0x3;
|
||||
return util::stream_format(stream, "%s %08lx %02x:%01x %1x %1x", mnemonic[op].mnem, iCode, op, op2, modeh, model);
|
||||
*/
|
||||
//util::stream_format(stream, ".word\t0x%08x", iCode);
|
||||
util::stream_format(stream, "? %08x", iCode);
|
||||
|
||||
return 4;
|
||||
}
|
||||
|
||||
offs_t i960_disassembler::dis_decode_ctrl(std::ostream &stream, u32 iCode, u32 ip, signed char cnt)
|
||||
{
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
//u8 t = (unsigned char) (iCode >> 1 & 1); // Cx, Hx, Rx - branch prediction (ignored for now)
|
||||
u32 disp = iCode & 0x00fffffc;
|
||||
|
||||
// check bit 0
|
||||
if ((iCode & 1) != 0x0) return dis_decode_invalid(stream, iCode);
|
||||
|
||||
switch(cnt)
|
||||
{
|
||||
if(M1)
|
||||
src1 = util::string_format("0x%lx", SRC1);
|
||||
else
|
||||
src1 = util::string_format("%s", regnames[SRC1]);
|
||||
case 0: // no operand
|
||||
util::stream_format(stream, "%s", mnemonic[op].mnem);
|
||||
break;
|
||||
case 1: // 1 operand
|
||||
util::stream_format(stream, "%-8s%08lx", mnemonic[op].mnem, ((((s32)disp) << 8) >> 8) + (ip));
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
if (S2)
|
||||
src2 = ",reserved";
|
||||
else
|
||||
return 4;
|
||||
}
|
||||
|
||||
offs_t i960_disassembler::dis_decode_cobr(std::ostream &stream, u32 iCode, u32 ip, signed char cnt)
|
||||
{
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
u8 src1 = (unsigned char) (iCode >> 19) & 0x1f;
|
||||
u8 src2 = (unsigned char) (iCode >> 14) & 0x1f;
|
||||
u8 m1 = (unsigned char) (iCode >> 13 & 1);
|
||||
//u8 t = (unsigned char) (iCode >> 1 & 1); // Cx, Hx, Rx - branch prediction
|
||||
u8 s2 = (unsigned char) iCode & 1; // Cx, Hx, Rx - src2 = special function register
|
||||
u32 disp = iCode & 0x1ffc;
|
||||
|
||||
std::string op1, op2, op3;
|
||||
|
||||
switch(cnt)
|
||||
{
|
||||
if(M2)
|
||||
src2 = util::string_format(",0x%lx", SRC2);
|
||||
else
|
||||
src2 = util::string_format(",%s", regnames[SRC2]);
|
||||
case 1: // 1 operand (test*)
|
||||
// For the test-if instructions, only the srcl field is used. Here, this field specifies a destination global or local register (ml is ignored).
|
||||
util::stream_format(stream, "%-8s%s", mnemonic[op].mnem, regnames[src1]);
|
||||
break;
|
||||
case 3: // 3 operands
|
||||
// TODO m1 set differs on Mx, Kx, Jx, Rx references (literal) and Hx reference (sf-register)
|
||||
if (m1) op1 = util::string_format("%d", src1);
|
||||
else op1 = util::string_format("%s", regnames[src1]);
|
||||
if (s2) op2 = util::string_format("sf%d", src2);
|
||||
else op2 = util::string_format("%s", regnames[src2]);
|
||||
op3 = util::string_format("0x%lx", ((((s32)disp) << 19) >> 19) + (ip));
|
||||
|
||||
util::stream_format(stream, "%-8s%s,%s,%s", mnemonic[op].mnem, op1, op2, op3);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
if(M3)
|
||||
dst = "";
|
||||
else
|
||||
dst = util::string_format(",%s", regnames[DST]);
|
||||
return 4;
|
||||
}
|
||||
|
||||
if (cnt == 1)
|
||||
return util::string_format("%s%s", src1, dst);
|
||||
else
|
||||
return util::string_format("%s%s%s", src1, src2, dst);
|
||||
offs_t i960_disassembler::dis_decode_mema(std::ostream &stream, u32 iCode, signed char cnt)
|
||||
{
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
u8 srcdst = (unsigned char) (iCode >> 19) & 0x1f;
|
||||
u8 abase = (unsigned char) (iCode >> 14) & 0x1f;
|
||||
u8 mode = (unsigned char) (iCode >> 13) & 0x1;
|
||||
u32 offset = iCode & 0xfff;
|
||||
|
||||
switch(mode)
|
||||
{
|
||||
case 0:
|
||||
// offset
|
||||
switch(cnt)
|
||||
{
|
||||
case 1: // bx/callx
|
||||
util::stream_format(stream, "%-8s0x%lx", mnemonic[op].mnem, offset);
|
||||
break;
|
||||
case 2: // load
|
||||
util::stream_format(stream, "%-8s0x%lx,%s", mnemonic[op].mnem, offset, regnames[srcdst]);
|
||||
break;
|
||||
case -2: // store
|
||||
util::stream_format(stream, "%-8s%s,0x%lx", mnemonic[op].mnem, regnames[srcdst], offset);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 1:
|
||||
// (abase) + offset
|
||||
switch(cnt)
|
||||
{
|
||||
case 1: // bx/callx
|
||||
util::stream_format(stream, "%-8s0x%lx(%s)", mnemonic[op].mnem, offset, regnames[abase]);
|
||||
break;
|
||||
case 2: // load
|
||||
util::stream_format(stream, "%-8s0x%lx(%s),%s", mnemonic[op].mnem, offset, regnames[abase], regnames[srcdst]);
|
||||
break;
|
||||
case -2: // store
|
||||
util::stream_format(stream, "%-8s%s,0x%lx(%s)", mnemonic[op].mnem, regnames[srcdst], offset, regnames[abase]);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
return 4;
|
||||
}
|
||||
|
||||
offs_t i960_disassembler::dis_decode_memb(std::ostream &stream, u32 iCode, u32 ip, u32 disp, signed char cnt)
|
||||
{
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
u8 srcdst = (unsigned char) (iCode >> 19) & 0x1f;
|
||||
u8 abase = (unsigned char) (iCode >> 14) & 0x1f;
|
||||
u8 mode = (unsigned char) (iCode >> 10) & 0xf;
|
||||
u8 scale = (unsigned char) (iCode >> 7) & 0x7;
|
||||
u8 index = (unsigned char) iCode & 0x1f;
|
||||
|
||||
offs_t IPinc;
|
||||
std::string efa;
|
||||
|
||||
// check bits 5 and 6
|
||||
if ((iCode & 0x60) != 0x0) return dis_decode_invalid(stream, iCode);
|
||||
|
||||
// check scale
|
||||
if (scale > 4) return dis_decode_invalid(stream, iCode);
|
||||
|
||||
if ((mode == 0x5) || (mode >= 0xc)) IPinc = 8;
|
||||
else IPinc = 4;
|
||||
|
||||
switch(mode)
|
||||
{
|
||||
case 0x4: // (abase)
|
||||
efa = util::string_format("(%s)", regnames[abase]);
|
||||
break;
|
||||
case 0x5: // (IP) + displacement + 8
|
||||
efa = util::string_format("0x%x", ip + disp + 8);
|
||||
break;
|
||||
case 0x6: // reserved
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
case 0x7: // (abase) + (index) * 2^scale
|
||||
if (scale == 0) efa = util::string_format("(%s)[%s]", regnames[abase], regnames[index]);
|
||||
else efa = util::string_format("(%s)[%s*%ld]", regnames[abase], regnames[index], 1 << scale);
|
||||
break;
|
||||
case 0xc: // displacement
|
||||
efa = util::string_format("0x%x", disp);
|
||||
break;
|
||||
case 0xd: // (abase) + displacement
|
||||
efa = util::string_format("0x%x(%s)", disp, regnames[abase]);
|
||||
break;
|
||||
case 0xe: // (index) * 2^scale + displacement
|
||||
if (scale == 0) efa = util::string_format("0x%x[%s]", disp, regnames[index]);
|
||||
else efa = util::string_format("0x%x[%s*%ld]", disp, regnames[index], 1 << scale);
|
||||
break;
|
||||
case 0xf: // (abase) + (index) * 2^scale + displacement
|
||||
if (scale == 0) efa = util::string_format("0x%x(%s)[%s]", disp, regnames[abase], regnames[index]);
|
||||
else efa = util::string_format("0x%x(%s)[%s*%ld]", disp, regnames[abase], regnames[index], 1 << scale);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
switch (cnt)
|
||||
{
|
||||
case 1: // bx/callx
|
||||
util::stream_format(stream, "%-8s%s", mnemonic[op].mnem, efa);
|
||||
break;
|
||||
case 2: // load
|
||||
util::stream_format(stream, "%-8s%s,%s", mnemonic[op].mnem, efa, regnames[srcdst]);
|
||||
break;
|
||||
case -2: // store
|
||||
util::stream_format(stream, "%-8s%s,%s", mnemonic[op].mnem, regnames[srcdst], efa);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
return IPinc;
|
||||
}
|
||||
|
||||
offs_t i960_disassembler::dis_decode_reg(std::ostream &stream, u32 iCode)
|
||||
{
|
||||
u16 op = (unsigned short) ((iCode >> 20) & 0xff0) | ((iCode >> 7) & 0xf);
|
||||
u8 srcdst = (unsigned char) (iCode >> 19) & 0x1f;
|
||||
u8 src2 = (unsigned char) (iCode >> 14) & 0x1f;
|
||||
u8 m3 = (unsigned char) (iCode >> 13) & 1;
|
||||
u8 m2 = (unsigned char) (iCode >> 12) & 1;
|
||||
u8 m1 = (unsigned char) (iCode >> 11) & 1;
|
||||
u8 s2 = (unsigned char) (iCode >> 6) & 1;
|
||||
u8 s1 = (unsigned char) (iCode >> 5) & 1;
|
||||
u8 src1 = (unsigned char) iCode & 0x1f;
|
||||
|
||||
u8 sm1 = ((s1 << 1) | m1);
|
||||
u8 sm2 = ((s2 << 1) | m2);
|
||||
u32 i = 0;
|
||||
std::string op1, op2, op3;
|
||||
|
||||
while(mnem_reg[i].type != 0)
|
||||
{
|
||||
if (mnem_reg[i].type == op) break;
|
||||
i++;
|
||||
}
|
||||
if (mnem_reg[i].type != op) return dis_decode_invalid(stream, iCode);
|
||||
|
||||
switch (sm1)
|
||||
{
|
||||
case 0: // neither set
|
||||
op1 = util::string_format("%s", regnames[src1]);
|
||||
break;
|
||||
case 1: // M1 set
|
||||
op1 = util::string_format("%d", src1);
|
||||
break;
|
||||
case 2: // S1 set
|
||||
op1 = util::string_format("sf%d", src1);
|
||||
break;
|
||||
case 3: // M1 and S1 set
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
switch (sm2)
|
||||
{
|
||||
case 0: // neither set
|
||||
op2 = util::string_format("%s", regnames[src2]);
|
||||
break;
|
||||
case 1: // M2 set
|
||||
op2 = util::string_format("%d", src2);
|
||||
break;
|
||||
case 2: // S2 set
|
||||
op2 = util::string_format("sf%d", src2);
|
||||
break;
|
||||
case 3: // M2 and S2 set
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
switch (mnem_reg[i].flags)
|
||||
{
|
||||
case 0: // no operand
|
||||
util::stream_format(stream, "%-8s", mnem_reg[i].mnem);
|
||||
break;
|
||||
case 1: // single operand, which is NOT a destination.
|
||||
util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem, op1);
|
||||
break;
|
||||
case -1: // single operand, which IS a destination.
|
||||
if (m3) op3 = util::string_format("sf%d", srcdst);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem, op3);
|
||||
break;
|
||||
case 2: // 2 operands, the 2nd of which is NOT a destination.
|
||||
util::stream_format(stream, "%-8s%s,%s", mnem_reg[i].mnem, op1, op2);
|
||||
break;
|
||||
case -2: // 2 operands, the 2nd of which IS a destination.
|
||||
if (m3) op3 = util::string_format("sf%d", srcdst);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s", mnem_reg[i].mnem, op1, op3);
|
||||
break;
|
||||
case 3: // 3 operands, the 3rd of which is NOT a destination.
|
||||
if (m3) op3 = util::string_format("%d", srcdst);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s,%s", mnem_reg[i].mnem, op1, op2, op3);
|
||||
break;
|
||||
case -3: // 3 operands, the 3rd of which IS a destination.
|
||||
if (m3) op3 = util::string_format("sf%d", srcdst);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s,%s", mnem_reg[i].mnem, op1, op2, op3);
|
||||
break;
|
||||
case 33: // 3 operands, the 3rd of which is source and destination.
|
||||
// m3 must NOT be set for src/dst type
|
||||
if (m3) return dis_decode_invalid(stream, iCode);
|
||||
op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s,%s", mnem_reg[i].mnem, op1, op2, op3);
|
||||
break;
|
||||
|
||||
// floating point opcodes
|
||||
case 10: // single operand, which is NOT a destination.
|
||||
if (m1) op1 = util::string_format("%s", fprnames[src1]);
|
||||
else op1 = util::string_format("%s", regnames[src1]);
|
||||
util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem, op1);
|
||||
break;
|
||||
case 20: // 2 operands, the 2nd of which is NOT a destination.
|
||||
if (m1) op1 = util::string_format("%s", fprnames[src1]);
|
||||
else op1 = util::string_format("%s", regnames[src1]);
|
||||
if (m2) op2 = util::string_format("%s", fprnames[src2]);
|
||||
else op2 = util::string_format("%s", regnames[src2]);
|
||||
util::stream_format(stream, "%-8s%s,%s", mnem_reg[i].mnem, op1, op2);
|
||||
break;
|
||||
case -20: // 2 operands, the 2nd of which IS a destination.
|
||||
if (m1) op1 = util::string_format("%s", fprnames[src1]);
|
||||
else op1 = util::string_format("%s", regnames[src1]);
|
||||
if (m3) op3 = util::string_format("%s", fprnames[srcdst]);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s", mnem_reg[i].mnem, op1, op3);
|
||||
break;
|
||||
case -30: // 3 operands, the 3rd of which IS a destination.
|
||||
if (m1) op1 = util::string_format("%s", fprnames[src1]);
|
||||
else op1 = util::string_format("%s", regnames[src1]);
|
||||
if (m2) op2 = util::string_format("%s", fprnames[src2]);
|
||||
else op2 = util::string_format("%s", regnames[src2]);
|
||||
if (m3) op3 = util::string_format("%s", fprnames[srcdst]);
|
||||
else op3 = util::string_format("%s", regnames[srcdst]);
|
||||
util::stream_format(stream, "%-8s%s,%s,%s", mnem_reg[i].mnem, op1, op2, op3);
|
||||
break;
|
||||
default:
|
||||
return dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
}
|
||||
|
||||
return 4;
|
||||
}
|
||||
|
||||
offs_t i960_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms)
|
||||
{
|
||||
u32 IP = pc;
|
||||
|
||||
u32 iCode = opcodes.r32(IP);
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
u8 op2 = (unsigned char) (iCode >> 7)&0xf;
|
||||
u16 opc = 0;
|
||||
u32 i = 0;
|
||||
|
||||
u8 model = (unsigned char) (iCode >> 10) &0x3;
|
||||
u8 modeh = (unsigned char) (iCode >> 12) &0x3;
|
||||
//mode = (unsigned char) (iCode >> 10) &0x7;
|
||||
u8 dst = (unsigned char) (iCode >> 19) &0x1f;
|
||||
u8 abase = (unsigned char) (iCode>>14)&0x1f;
|
||||
u8 reg2 = (unsigned char) (iCode)&0x1f;
|
||||
u8 op = (unsigned char) (iCode >> 24);
|
||||
|
||||
offs_t IPinc = 4;
|
||||
offs_t disflags = 0;
|
||||
@ -186,157 +540,25 @@ offs_t i960_disassembler::disassemble(std::ostream &stream, offs_t pc, const dat
|
||||
|
||||
switch(mnemonic[op].type)
|
||||
{
|
||||
case 0: // not yet implemented
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
case 0: // invalid / not yet implemented
|
||||
IPinc = dis_decode_invalid(stream, iCode);
|
||||
break;
|
||||
case 1: // memory access (write)
|
||||
switch(modeh)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s%s,0x%lx",NEM,REG_DST, iCode&0xfff);
|
||||
break;
|
||||
case 1:
|
||||
switch (model)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s%s,(%s)",NEM,REG_DST, REG_ABASE);
|
||||
break;
|
||||
case 3:
|
||||
util::stream_format(stream, "%-8s%s,(%s)[%s*%ld]",NEM,REG_DST, REG_ABASE,REG_REG2,1<<((iCode>>7)&0x7));
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
util::stream_format(stream, "%-8s%s,0x%lx(%s)",NEM,REG_DST, iCode&0xfff,REG_ABASE);
|
||||
break;
|
||||
case 3:
|
||||
switch (model)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s%s,0x%x",NEM,REG_DST, opcodes.r32(IP + 4));
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 1:
|
||||
util::stream_format(stream, "%-8s%s,0x%x(%s)",NEM,REG_DST, opcodes.r32(IP + 4),REG_ABASE);
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 2:
|
||||
util::stream_format(stream, "%-8s%s,0x%x[%s*%ld]",NEM,REG_DST, opcodes.r32(IP + 4),REG_REG2,1<<((iCode>>7)&0x7));
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 3:
|
||||
util::stream_format(stream, "%-8s%s,0x%x(%s)[%s*%ld]",NEM,REG_DST, opcodes.r32(IP + 4),REG_ABASE,REG_REG2,1<<((iCode>>7)&0x7));
|
||||
IPinc = 8;
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
case 1: // CTRL format
|
||||
IPinc = dis_decode_ctrl(stream, iCode, IP, mnemonic[op].flags);
|
||||
break;
|
||||
case 2:
|
||||
i = 0;
|
||||
opc = op<<4|op2;
|
||||
|
||||
while(mnem_reg[i].type != 0)
|
||||
{
|
||||
if (mnem_reg[i].type == opc) break;
|
||||
i++;
|
||||
}
|
||||
|
||||
if (mnem_reg[i].type == opc) util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,1));
|
||||
else util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
case 2: // COBR compare and branch type
|
||||
IPinc = dis_decode_cobr(stream, iCode, IP, mnemonic[op].flags);
|
||||
break;
|
||||
case 3:
|
||||
i = 0;
|
||||
opc = op<<4|op2;
|
||||
|
||||
while(mnem_reg[i].type != 0)
|
||||
{
|
||||
if (mnem_reg[i].type == opc) break;
|
||||
i++;
|
||||
}
|
||||
|
||||
if (mnem_reg[i].type == opc) util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,0));
|
||||
else util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
case 3: // MEM format
|
||||
if ((iCode >> 12) & 0x1)
|
||||
// MEMB format
|
||||
IPinc = dis_decode_memb(stream, iCode, IP, opcodes.r32(IP + 4), mnemonic[op].flags);
|
||||
else
|
||||
// MEMA format
|
||||
IPinc = dis_decode_mema(stream, iCode, mnemonic[op].flags);
|
||||
break;
|
||||
case 4: // memory access (read)
|
||||
switch(modeh)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s0x%lx,%s",NEM,iCode&0xfff,REG_DST);
|
||||
break;
|
||||
case 1:
|
||||
switch (model)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s(%s),%s",NEM,REG_ABASE,REG_DST);
|
||||
break;
|
||||
case 3:
|
||||
util::stream_format(stream, "%-8s(%s)[%s*%ld],%s",NEM,REG_ABASE,REG_REG2,1<<((iCode>>7)&0x7),REG_DST);
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
util::stream_format(stream, "%-8s0x%lx(%s),%s",NEM,iCode&0xfff,REG_ABASE,REG_DST);
|
||||
break;
|
||||
case 3:
|
||||
switch (model)
|
||||
{
|
||||
case 0:
|
||||
util::stream_format(stream, "%-8s0x%x,%s",NEM,opcodes.r32(IP + 4),REG_DST);
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 1:
|
||||
util::stream_format(stream, "%-8s0x%x(%s),%s",NEM,opcodes.r32(IP + 4),REG_ABASE,REG_DST);
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 2:
|
||||
util::stream_format(stream, "%-8s0x%x[%s*%ld],%s",NEM,opcodes.r32(IP + 4),REG_REG2,1<<((iCode>>7)&0x7),REG_DST);
|
||||
IPinc = 8;
|
||||
break;
|
||||
case 3:
|
||||
util::stream_format(stream, "%-8s0x%x(%s)[%s*%ld],%s",NEM, opcodes.r32(IP + 4),REG_ABASE,REG_REG2,1<<((iCode>>7)&0x7),REG_DST);
|
||||
IPinc = 8;
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case 6: // bitpos and branch type
|
||||
util::stream_format(stream, "%-8s%ld,%s,0x%lx",NEM, COBRSRC1, REG_COBR_SRC2,((((s32)iCode&0x00fffffc)<<19)>>19) + (IP));
|
||||
break;
|
||||
case 7: // compare and branch type
|
||||
util::stream_format(stream, "%-8s%s,%s,0x%lx",NEM,REG_COBR_SRC1,REG_COBR_SRC2,((((s32)iCode&0x00fffffc)<<19)>>19) + (IP));
|
||||
break;
|
||||
case 8: // target type
|
||||
util::stream_format(stream, "%-8s%08lx",NEM,((((s32)iCode&0x00fffffc)<<8)>>8) + (IP));
|
||||
break;
|
||||
case 9: // no operands
|
||||
util::stream_format(stream, "%s",NEM);
|
||||
break;
|
||||
case 10: // TEST type: register only
|
||||
util::stream_format(stream, "%s %s", NEM, REG_DST);
|
||||
break;
|
||||
case 11: // workaround to match users guide
|
||||
util::stream_format(stream, "%-8s(%s)",NEM, REG_ABASE);
|
||||
case 4: // REG format
|
||||
IPinc = dis_decode_reg(stream, iCode);
|
||||
break;
|
||||
default:
|
||||
stream << "???";
|
||||
|
@ -19,14 +19,20 @@ private:
|
||||
{
|
||||
const char *mnem;
|
||||
unsigned short type;
|
||||
signed char flags;
|
||||
};
|
||||
|
||||
static const mnemonic_t mnemonic[256];
|
||||
static const mnemonic_t mnem_reg[111];
|
||||
static const char *const constnames[32];
|
||||
static const mnemonic_t mnem_reg[197];
|
||||
static const char *const regnames[32];
|
||||
static const char *const fprnames[32];
|
||||
|
||||
std::string dis_decode_reg(u32 iCode, unsigned char cnt);
|
||||
offs_t dis_decode_invalid(std::ostream &stream, u32 iCode);
|
||||
offs_t dis_decode_ctrl(std::ostream &stream, u32 iCode, u32 ip, signed char cnt);
|
||||
offs_t dis_decode_cobr(std::ostream &stream, u32 iCode, u32 ip, signed char cnt);
|
||||
offs_t dis_decode_mema(std::ostream &stream, u32 iCode, signed char cnt);
|
||||
offs_t dis_decode_memb(std::ostream &stream, u32 iCode, u32 ip, u32 disp, signed char cnt);
|
||||
offs_t dis_decode_reg(std::ostream &stream, u32 iCode);
|
||||
|
||||
};
|
||||
|
||||
|
@ -37,7 +37,7 @@
|
||||
#define OC2 m_output_compare2.w.l
|
||||
#define OC2H m_output_compare2.w.h
|
||||
#define OC2D m_output_compare2.d
|
||||
#define TOH m_timer_over.w.l
|
||||
#define TOH m_timer_over.w.h
|
||||
#define TOD m_timer_over.d
|
||||
|
||||
// serial I/O
|
||||
@ -1352,10 +1352,10 @@ uint8_t hd6301x_cpu_device::p7_data_r()
|
||||
|
||||
void hd6301x_cpu_device::p7_data_w(uint8_t data)
|
||||
{
|
||||
LOGPORT("Port 7 Data Register: %02x\n", data);
|
||||
|
||||
data &= 0x1f;
|
||||
|
||||
LOGPORT("Port 7 Data Register: %02x\n", data);
|
||||
|
||||
m_portx_data[2] = data;
|
||||
m_out_portx_func[2](0, m_portx_data[2], 0x1f);
|
||||
}
|
||||
@ -1369,9 +1369,11 @@ uint8_t m6801_cpu_device::tcsr_r()
|
||||
|
||||
void m6801_cpu_device::tcsr_w(uint8_t data)
|
||||
{
|
||||
data &= 0x1f;
|
||||
|
||||
LOGTIMER("Timer Control and Status Register: %02x\n", data);
|
||||
|
||||
m_tcsr = data;
|
||||
m_tcsr = data | (m_tcsr & 0xe0);
|
||||
m_pending_tcsr &= m_tcsr;
|
||||
modified_tcsr();
|
||||
if( !(m_cc & 0x10) )
|
||||
@ -1390,11 +1392,7 @@ uint8_t m6801_cpu_device::ch_r()
|
||||
|
||||
uint8_t m6801_cpu_device::cl_r()
|
||||
{
|
||||
uint8_t data = m_counter.b.l;
|
||||
|
||||
// HACK there should be a break here, but Coleco Adam won't boot with it present, proper fix required to the free-running counter
|
||||
(void)data;
|
||||
return ocrh_r();
|
||||
return m_counter.b.l;
|
||||
}
|
||||
|
||||
void m6801_cpu_device::ch_w(uint8_t data)
|
||||
|
@ -91,10 +91,9 @@ protected:
|
||||
uint8_t p4_data_r();
|
||||
void p4_data_w(uint8_t data);
|
||||
|
||||
public: // FIXME: psion.cpp accesses this
|
||||
protected:
|
||||
uint8_t tcsr_r();
|
||||
void tcsr_w(uint8_t data);
|
||||
protected:
|
||||
uint8_t ch_r();
|
||||
uint8_t cl_r();
|
||||
void ch_w(uint8_t data);
|
||||
|
@ -1480,6 +1480,16 @@ void fpgen_rm_reg(u16 w2)
|
||||
m_icount -= 43;
|
||||
break;
|
||||
}
|
||||
case 0x21: // FMOD
|
||||
{
|
||||
s8 const mode = float_rounding_mode;
|
||||
float_rounding_mode = float_round_to_zero;
|
||||
m_fpr[dst] = floatx80_rem(m_fpr[dst], source);
|
||||
SET_CONDITION_CODES(m_fpr[dst]);
|
||||
float_rounding_mode = mode;
|
||||
m_icount -= 43; // guess
|
||||
break;
|
||||
}
|
||||
case 0x22: // FADD
|
||||
{
|
||||
m_fpr[dst] = floatx80_add(m_fpr[dst], source);
|
||||
|
@ -50,7 +50,7 @@ MAIN:
|
||||
case 0x1E: %EXG; return;
|
||||
case 0x1F: %TFR; return;
|
||||
|
||||
case 0x20: set_cond(true); %BRANCH; return;
|
||||
case 0x20: set_cond(true); %BRANCH; return;
|
||||
case 0x21: set_cond(false); %BRANCH; return;
|
||||
case 0x22: set_cond(cond_hi()); %BRANCH; return;
|
||||
case 0x23: set_cond(!cond_hi()); %BRANCH; return;
|
||||
@ -271,7 +271,7 @@ MAIN:
|
||||
case 0xFD: set_regop16(m_q.p.d); %EXTENDED; %ST16; return;
|
||||
case 0xFE: set_regop16(m_u); %EXTENDED; %LD16; return;
|
||||
case 0xFF: set_regop16(m_u); %EXTENDED; %ST16; return;
|
||||
default: %ILLEGAL; return;
|
||||
default: %ILLEGAL; return;
|
||||
}
|
||||
return;
|
||||
|
||||
@ -279,7 +279,6 @@ DISPATCH10:
|
||||
@m_opcode = read_opcode();
|
||||
switch(m_opcode)
|
||||
{
|
||||
case 0x20: set_cond(true); %LBRANCH; return;
|
||||
case 0x21: set_cond(false); %LBRANCH; return;
|
||||
case 0x22: set_cond(cond_hi()); %LBRANCH; return;
|
||||
case 0x23: set_cond(!cond_hi()); %LBRANCH; return;
|
||||
@ -410,7 +409,7 @@ DISPATCH10:
|
||||
case 0xFE: set_regop16(m_s); %EXTENDED; %LD16; return;
|
||||
case 0xFF: set_regop16(m_s); %EXTENDED; %ST16; return;
|
||||
|
||||
default: %ILLEGAL; return;
|
||||
default: %ILLEGAL; return;
|
||||
}
|
||||
return;
|
||||
|
||||
@ -512,7 +511,7 @@ DISPATCH11:
|
||||
case 0xF7: set_regop8(m_q.r.f); %EXTENDED; %ST8; return;
|
||||
case 0xFB: set_regop8(m_q.r.f); %EXTENDED; %ADD8; return;
|
||||
|
||||
default: %ILLEGAL; return;
|
||||
default: %ILLEGAL; return;
|
||||
}
|
||||
return;
|
||||
|
||||
@ -891,7 +890,7 @@ TFM:
|
||||
// operation that executed one transfer, and bumped the program
|
||||
// counter back. However, some documentation suggests that TFM
|
||||
// was abortable, so we now have a get_pending_interrupt() call
|
||||
// here.
|
||||
// here.
|
||||
//
|
||||
// Lastly, I have no information on the precise sub-instruction timing
|
||||
// here; the timings of the reads and writes are really just a guess.
|
||||
|
@ -285,6 +285,7 @@ void nec_common_device::device_reset()
|
||||
memset( &m_regs.w, 0, sizeof(m_regs.w));
|
||||
|
||||
m_ip = 0;
|
||||
m_prev_ip = 0;
|
||||
m_TF = 0;
|
||||
m_IF = 0;
|
||||
m_DF = 0;
|
||||
@ -331,7 +332,7 @@ void nec_common_device::nec_interrupt(unsigned int_num, int/*INTSOURCES*/ source
|
||||
|
||||
PUSH(Sreg(PS));
|
||||
PUSH(m_ip);
|
||||
m_ip = (WORD)dest_off;
|
||||
m_prev_ip = m_ip = (WORD)dest_off;
|
||||
Sreg(PS) = (WORD)dest_seg;
|
||||
CHANGE_PC;
|
||||
}
|
||||
@ -352,7 +353,7 @@ void nec_common_device::nec_brk(unsigned int_num)
|
||||
PUSH(Sreg(PS));
|
||||
PUSH(m_ip);
|
||||
}
|
||||
m_ip = read_mem_word(int_num*4);
|
||||
m_prev_ip = m_ip = read_mem_word(int_num*4);
|
||||
Sreg(PS) = read_mem_word(int_num*4+2);
|
||||
CHANGE_PC;
|
||||
}
|
||||
@ -464,6 +465,7 @@ void nec_common_device::device_start()
|
||||
m_E16 = 0;
|
||||
m_debugger_temp = 0;
|
||||
m_ip = 0;
|
||||
m_prev_ip = 0;
|
||||
|
||||
memset(m_regs.w, 0x00, sizeof(m_regs.w));
|
||||
memset(m_sregs, 0x00, sizeof(m_sregs));
|
||||
@ -472,6 +474,7 @@ void nec_common_device::device_start()
|
||||
save_item(NAME(m_sregs));
|
||||
|
||||
save_item(NAME(m_ip));
|
||||
save_item(NAME(m_prev_ip));
|
||||
save_item(NAME(m_TF));
|
||||
save_item(NAME(m_IF));
|
||||
save_item(NAME(m_DF));
|
||||
@ -511,21 +514,29 @@ void nec_common_device::device_start()
|
||||
|
||||
m_io = &space(AS_IO);
|
||||
|
||||
state_add( NEC_PC, "PC", m_debugger_temp).callimport().callexport().formatstr("%05X");
|
||||
state_add( NEC_IP, "IP", m_ip).formatstr("%04X");
|
||||
state_add( NEC_SP, "SP", Wreg(SP)).formatstr("%04X");
|
||||
state_add( NEC_FLAGS, "F", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( NEC_AW, "AW", Wreg(AW)).formatstr("%04X");
|
||||
state_add( NEC_CW, "CW", Wreg(CW)).formatstr("%04X");
|
||||
state_add( NEC_DW, "DW", Wreg(DW)).formatstr("%04X");
|
||||
state_add( NEC_BW, "BW", Wreg(BW)).formatstr("%04X");
|
||||
state_add( NEC_BP, "BP", Wreg(BP)).formatstr("%04X");
|
||||
state_add( NEC_IX, "IX", Wreg(IX)).formatstr("%04X");
|
||||
state_add( NEC_IY, "IY", Wreg(IY)).formatstr("%04X");
|
||||
state_add( NEC_ES, "DS1", Sreg(DS1)).formatstr("%04X");
|
||||
state_add( NEC_CS, "PS", Sreg(PS)).formatstr("%04X");
|
||||
state_add( NEC_SS, "SS", Sreg(SS)).formatstr("%04X");
|
||||
state_add( NEC_DS, "DS0", Sreg(DS0)).formatstr("%04X");
|
||||
state_add( NEC_PC, "PC", m_ip).formatstr("%04X");
|
||||
state_add( NEC_PSW, "PSW", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( NEC_AW, "AW", Wreg(AW)).formatstr("%04X");
|
||||
state_add( NEC_CW, "CW", Wreg(CW)).formatstr("%04X");
|
||||
state_add( NEC_DW, "DW", Wreg(DW)).formatstr("%04X");
|
||||
state_add( NEC_BW, "BW", Wreg(BW)).formatstr("%04X");
|
||||
state_add( NEC_SP, "SP", Wreg(SP)).formatstr("%04X");
|
||||
state_add( NEC_BP, "BP", Wreg(BP)).formatstr("%04X");
|
||||
state_add( NEC_IX, "IX", Wreg(IX)).formatstr("%04X");
|
||||
state_add( NEC_IY, "IY", Wreg(IY)).formatstr("%04X");
|
||||
state_add( NEC_DS1, "DS1", Sreg(DS1)).formatstr("%04X");
|
||||
state_add( NEC_PS, "PS", Sreg(PS)).formatstr("%04X");
|
||||
state_add( NEC_SS, "SS", Sreg(SS)).formatstr("%04X");
|
||||
state_add( NEC_DS0, "DS0", Sreg(DS0)).formatstr("%04X");
|
||||
|
||||
state_add( NEC_AL, "AL", Breg(AL)).noshow();
|
||||
state_add( NEC_AH, "AH", Breg(AH)).noshow();
|
||||
state_add( NEC_CL, "CL", Breg(CL)).noshow();
|
||||
state_add( NEC_CH, "CH", Breg(CH)).noshow();
|
||||
state_add( NEC_DL, "DL", Breg(DL)).noshow();
|
||||
state_add( NEC_DH, "DH", Breg(DH)).noshow();
|
||||
state_add( NEC_BL, "BL", Breg(BL)).noshow();
|
||||
state_add( NEC_BH, "BH", Breg(BH)).noshow();
|
||||
|
||||
if (m_chip_type == V33_TYPE)
|
||||
state_add(NEC_XA, "XA", m_xa);
|
||||
@ -570,7 +581,7 @@ void nec_common_device::state_import(const device_state_entry &entry)
|
||||
{
|
||||
switch (entry.index())
|
||||
{
|
||||
case NEC_PC:
|
||||
case STATE_GENPC:
|
||||
if (m_debugger_temp - (Sreg(PS)<<4) < 0x10000)
|
||||
{
|
||||
m_ip = m_debugger_temp - (Sreg(PS)<<4);
|
||||
@ -580,9 +591,10 @@ void nec_common_device::state_import(const device_state_entry &entry)
|
||||
Sreg(PS) = m_debugger_temp >> 4;
|
||||
m_ip = m_debugger_temp & 0x0000f;
|
||||
}
|
||||
m_prev_ip = m_ip;
|
||||
break;
|
||||
|
||||
case NEC_FLAGS:
|
||||
case NEC_PSW:
|
||||
ExpandFlags(m_debugger_temp);
|
||||
break;
|
||||
}
|
||||
@ -594,16 +606,18 @@ void nec_common_device::state_export(const device_state_entry &entry)
|
||||
switch (entry.index())
|
||||
{
|
||||
case STATE_GENPC:
|
||||
case STATE_GENPCBASE:
|
||||
case NEC_PC:
|
||||
m_debugger_temp = (Sreg(PS)<<4) + m_ip;
|
||||
break;
|
||||
|
||||
case STATE_GENPCBASE:
|
||||
m_debugger_temp = (Sreg(PS)<<4) + m_prev_ip;
|
||||
break;
|
||||
|
||||
case STATE_GENSP:
|
||||
m_debugger_temp = (Sreg(SS)<<4) + Wreg(SP);
|
||||
break;
|
||||
|
||||
case NEC_FLAGS:
|
||||
case NEC_PSW:
|
||||
m_debugger_temp = CompressFlags();
|
||||
break;
|
||||
}
|
||||
@ -622,6 +636,8 @@ void nec_common_device::execute_run()
|
||||
}
|
||||
|
||||
while(m_icount>0) {
|
||||
m_prev_ip = m_ip;
|
||||
|
||||
/* Dispatch IRQ */
|
||||
if (m_pending_irq && m_no_interrupt==0)
|
||||
{
|
||||
|
@ -13,8 +13,10 @@
|
||||
enum
|
||||
{
|
||||
NEC_PC=0,
|
||||
NEC_IP, NEC_AW, NEC_CW, NEC_DW, NEC_BW, NEC_SP, NEC_BP, NEC_IX, NEC_IY,
|
||||
NEC_FLAGS, NEC_ES, NEC_CS, NEC_SS, NEC_DS,
|
||||
NEC_AW, NEC_CW, NEC_DW, NEC_BW, NEC_SP, NEC_BP, NEC_IX, NEC_IY,
|
||||
NEC_DS1, NEC_PS, NEC_SS, NEC_DS0,
|
||||
NEC_AL, NEC_AH, NEC_CL, NEC_CH, NEC_DL, NEC_DH, NEC_BL, NEC_BH,
|
||||
NEC_PSW,
|
||||
NEC_XA,
|
||||
NEC_PENDING
|
||||
};
|
||||
@ -77,6 +79,7 @@ private:
|
||||
uint16_t m_sregs[4];
|
||||
|
||||
uint16_t m_ip;
|
||||
uint16_t m_prev_ip;
|
||||
|
||||
/* PSW flags */
|
||||
int32_t m_SignVal;
|
||||
|
@ -180,6 +180,7 @@ uint8_t v25_common_device::fetchop()
|
||||
void v25_common_device::device_reset()
|
||||
{
|
||||
m_ip = 0;
|
||||
m_prev_ip = 0;
|
||||
m_IBRK = 1;
|
||||
m_F0 = 0;
|
||||
m_F1 = 0;
|
||||
@ -270,7 +271,7 @@ void v25_common_device::nec_interrupt(unsigned int_num, int /*INTSOURCES*/ sourc
|
||||
|
||||
PUSH(Sreg(PS));
|
||||
PUSH(m_ip);
|
||||
m_ip = (WORD)dest_off;
|
||||
m_prev_ip = m_ip = (WORD)dest_off;
|
||||
Sreg(PS) = (WORD)dest_seg;
|
||||
CHANGE_PC;
|
||||
}
|
||||
@ -286,7 +287,7 @@ void v25_common_device::nec_bankswitch(unsigned bank_num)
|
||||
|
||||
Wreg(PSW_SAVE) = tmp;
|
||||
Wreg(PC_SAVE) = m_ip;
|
||||
m_ip = Wreg(VECTOR_PC);
|
||||
m_prev_ip = m_ip = Wreg(VECTOR_PC);
|
||||
CHANGE_PC;
|
||||
}
|
||||
|
||||
@ -565,6 +566,7 @@ void v25_common_device::device_start()
|
||||
save_item(NAME(m_intp_state));
|
||||
|
||||
save_item(NAME(m_ip));
|
||||
save_item(NAME(m_prev_ip));
|
||||
save_item(NAME(m_IBRK));
|
||||
save_item(NAME(m_F0));
|
||||
save_item(NAME(m_F1));
|
||||
@ -637,23 +639,32 @@ void v25_common_device::device_start()
|
||||
m_p1_out.resolve_safe();
|
||||
m_p2_out.resolve_safe();
|
||||
|
||||
state_add( V25_PC, "PC", m_debugger_temp).callimport().callexport().formatstr("%05X");
|
||||
state_add( V25_IP, "IP", m_ip).formatstr("%04X");
|
||||
state_add( V25_SP, "SP", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_FLAGS, "F", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_AW, "AW", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_CW, "CW", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_DW, "DW", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_BW, "BW", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_BP, "BP", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_IX, "IX", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_IY, "IY", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_ES, "DS1", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_CS, "PS", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_SS, "SS", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_DS, "DS0", m_debugger_temp).callimport().callexport().formatstr("%04X");
|
||||
state_add( V25_PC, "PC", m_ip).formatstr("%04X");
|
||||
state_add<uint16_t>( V25_PSW, "PSW", [this]() { return CompressFlags(); }, [this](uint16_t data) { ExpandFlags(data); });
|
||||
|
||||
state_add( V25_IDB, "IDB", m_IDB).mask(0xffe00).callimport();
|
||||
state_add<uint16_t>( V25_AW, "AW", [this]() { return Wreg(AW); }, [this](uint16_t data) { Wreg(AW) = data; });
|
||||
state_add<uint16_t>( V25_CW, "CW", [this]() { return Wreg(CW); }, [this](uint16_t data) { Wreg(CW) = data; });
|
||||
state_add<uint16_t>( V25_DW, "DW", [this]() { return Wreg(DW); }, [this](uint16_t data) { Wreg(DW) = data; });
|
||||
state_add<uint16_t>( V25_BW, "BW", [this]() { return Wreg(BW); }, [this](uint16_t data) { Wreg(BW) = data; });
|
||||
state_add<uint16_t>( V25_SP, "SP", [this]() { return Wreg(SP); }, [this](uint16_t data) { Wreg(SP) = data; });
|
||||
state_add<uint16_t>( V25_BP, "BP", [this]() { return Wreg(BP); }, [this](uint16_t data) { Wreg(BP) = data; });
|
||||
state_add<uint16_t>( V25_IX, "IX", [this]() { return Wreg(IX); }, [this](uint16_t data) { Wreg(IX) = data; });
|
||||
state_add<uint16_t>( V25_IY, "IY", [this]() { return Wreg(IY); }, [this](uint16_t data) { Wreg(IY) = data; });
|
||||
state_add<uint16_t>( V25_DS1, "DS1", [this]() { return Sreg(DS1); }, [this](uint16_t data) { Sreg(DS1) = data; });
|
||||
state_add<uint16_t>( V25_PS, "PS", [this]() { return Sreg(PS); }, [this](uint16_t data) { Sreg(PS) = data; });
|
||||
state_add<uint16_t>( V25_SS, "SS", [this]() { return Sreg(SS); }, [this](uint16_t data) { Sreg(SS) = data; });
|
||||
state_add<uint16_t>( V25_DS0, "DS0", [this]() { return Sreg(DS0); }, [this](uint16_t data) { Sreg(DS0) = data; });
|
||||
|
||||
state_add<uint8_t>( V25_AL, "AL", [this]() { return Breg(AL); }, [this](uint8_t data) { Breg(AL) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_AH, "AH", [this]() { return Breg(AH); }, [this](uint8_t data) { Breg(AH) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_CL, "CL", [this]() { return Breg(CL); }, [this](uint8_t data) { Breg(CL) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_CH, "CH", [this]() { return Breg(CH); }, [this](uint8_t data) { Breg(CH) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_DL, "DL", [this]() { return Breg(DL); }, [this](uint8_t data) { Breg(DL) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_DH, "DH", [this]() { return Breg(DH); }, [this](uint8_t data) { Breg(DH) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_BL, "BL", [this]() { return Breg(BL); }, [this](uint8_t data) { Breg(BL) = data; }).noshow();
|
||||
state_add<uint8_t>( V25_BH, "BH", [this]() { return Breg(BH); }, [this](uint8_t data) { Breg(BH) = data; }).noshow();
|
||||
|
||||
state_add( V25_IDB, "IDB", m_IDB).mask(0xffe00).callimport();
|
||||
|
||||
state_add( STATE_GENPC, "GENPC", m_debugger_temp).callexport().noshow();
|
||||
state_add( STATE_GENPCBASE, "CURPC", m_debugger_temp).callexport().noshow();
|
||||
@ -694,7 +705,7 @@ void v25_common_device::state_import(const device_state_entry &entry)
|
||||
{
|
||||
switch (entry.index())
|
||||
{
|
||||
case V25_PC:
|
||||
case STATE_GENPC:
|
||||
if( m_debugger_temp - (Sreg(PS)<<4) < 0x10000 )
|
||||
{
|
||||
m_ip = m_debugger_temp - (Sreg(PS)<<4);
|
||||
@ -704,58 +715,7 @@ void v25_common_device::state_import(const device_state_entry &entry)
|
||||
Sreg(PS) = m_debugger_temp >> 4;
|
||||
m_ip = m_debugger_temp & 0x0000f;
|
||||
}
|
||||
break;
|
||||
|
||||
case V25_SP:
|
||||
Wreg(SP) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_FLAGS:
|
||||
ExpandFlags(m_debugger_temp);
|
||||
break;
|
||||
|
||||
case V25_AW:
|
||||
Wreg(AW) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_CW:
|
||||
Wreg(CW) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_DW:
|
||||
Wreg(DW) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_BW:
|
||||
Wreg(BW) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_BP:
|
||||
Wreg(BP) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_IX:
|
||||
Wreg(IX) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_IY:
|
||||
Wreg(IY) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_ES:
|
||||
Sreg(DS1) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_CS:
|
||||
Sreg(PS) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_SS:
|
||||
Sreg(SS) = m_debugger_temp;
|
||||
break;
|
||||
|
||||
case V25_DS:
|
||||
Sreg(DS0) = m_debugger_temp;
|
||||
m_prev_ip = m_ip;
|
||||
break;
|
||||
|
||||
case V25_IDB:
|
||||
@ -770,66 +730,16 @@ void v25_common_device::state_export(const device_state_entry &entry)
|
||||
switch (entry.index())
|
||||
{
|
||||
case STATE_GENPC:
|
||||
case STATE_GENPCBASE:
|
||||
case V25_PC:
|
||||
m_debugger_temp = (Sreg(PS)<<4) + m_ip;
|
||||
break;
|
||||
|
||||
case STATE_GENPCBASE:
|
||||
m_debugger_temp = (Sreg(PS)<<4) + m_prev_ip;
|
||||
break;
|
||||
|
||||
case STATE_GENSP:
|
||||
m_debugger_temp = (Sreg(SS)<<4) + Wreg(SP);
|
||||
break;
|
||||
|
||||
case V25_SP:
|
||||
m_debugger_temp = Wreg(SP);
|
||||
break;
|
||||
|
||||
case V25_FLAGS:
|
||||
m_debugger_temp = CompressFlags();
|
||||
break;
|
||||
|
||||
case V25_AW:
|
||||
m_debugger_temp = Wreg(AW);
|
||||
break;
|
||||
|
||||
case V25_CW:
|
||||
m_debugger_temp = Wreg(CW);
|
||||
break;
|
||||
|
||||
case V25_DW:
|
||||
m_debugger_temp = Wreg(DW);
|
||||
break;
|
||||
|
||||
case V25_BW:
|
||||
m_debugger_temp = Wreg(BW);
|
||||
break;
|
||||
|
||||
case V25_BP:
|
||||
m_debugger_temp = Wreg(BP);
|
||||
break;
|
||||
|
||||
case V25_IX:
|
||||
m_debugger_temp = Wreg(IX);
|
||||
break;
|
||||
|
||||
case V25_IY:
|
||||
m_debugger_temp = Wreg(IY);
|
||||
break;
|
||||
|
||||
case V25_ES:
|
||||
m_debugger_temp = Sreg(DS1);
|
||||
break;
|
||||
|
||||
case V25_CS:
|
||||
m_debugger_temp = Sreg(PS);
|
||||
break;
|
||||
|
||||
case V25_SS:
|
||||
m_debugger_temp = Sreg(SS);
|
||||
break;
|
||||
|
||||
case V25_DS:
|
||||
m_debugger_temp = Sreg(DS0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@ -875,6 +785,7 @@ void v25_common_device::execute_run()
|
||||
|
||||
while(m_icount>0) {
|
||||
/* Dispatch IRQ */
|
||||
m_prev_ip = m_ip;
|
||||
if (m_no_interrupt==0 && (m_pending_irq & m_unmasked_irq))
|
||||
{
|
||||
if (m_pending_irq & NMI_IRQ)
|
||||
|
@ -16,8 +16,10 @@
|
||||
enum
|
||||
{
|
||||
V25_PC=0,
|
||||
V25_IP, V25_AW, V25_CW, V25_DW, V25_BW, V25_SP, V25_BP, V25_IX, V25_IY,
|
||||
V25_FLAGS, V25_ES, V25_CS, V25_SS, V25_DS,
|
||||
V25_AW, V25_CW, V25_DW, V25_BW, V25_SP, V25_BP, V25_IX, V25_IY,
|
||||
V25_DS1, V25_PS, V25_SS, V25_DS0,
|
||||
V25_AL, V25_AH, V25_CL, V25_CH, V25_DL, V25_DH, V25_BL, V25_BH,
|
||||
V25_PSW,
|
||||
V25_IDB,
|
||||
V25_PENDING
|
||||
};
|
||||
@ -80,6 +82,7 @@ private:
|
||||
required_shared_ptr<uint16_t> m_internal_ram;
|
||||
|
||||
uint16_t m_ip;
|
||||
uint16_t m_prev_ip;
|
||||
|
||||
/* PSW flags */
|
||||
int32_t m_SignVal;
|
||||
|
@ -19,7 +19,7 @@
|
||||
|
||||
2017-Feb-15 Edstrom
|
||||
Fixed shift registers to be more accurate, eg 50/50 duty cycle, latching
|
||||
on correct flanks and leading and trailing flanks added + logging.
|
||||
on correct edges and leading and trailing edges added + logging.
|
||||
*/
|
||||
|
||||
#include "emu.h"
|
||||
@ -386,7 +386,7 @@ void via6522_device::clear_int(int data)
|
||||
|
||||
void via6522_device::shift_out()
|
||||
{
|
||||
// Only shift out msb on falling flank
|
||||
// Only shift out msb on falling edge
|
||||
if (m_shift_counter & 1)
|
||||
{
|
||||
LOGSHIFT(" %s shift Out SR: %02x->", tag(), m_sr);
|
||||
@ -399,26 +399,26 @@ void via6522_device::shift_out()
|
||||
if (m_shift_counter == 1 && SO_EXT_CONTROL(m_acr))
|
||||
{
|
||||
LOGINT("SHIFT EXT out INT request ");
|
||||
set_int(INT_SR); // IRQ on last falling flank for external clock (mode 7)
|
||||
set_int(INT_SR); // IRQ on last falling edge for external clock (mode 7)
|
||||
}
|
||||
}
|
||||
else // Check for INT condition, eg the last and raising flank of the 15-0 falling/raising flanks
|
||||
else // Check for INT condition, eg the last and raising edge of the 15-0 falling/raising edges
|
||||
{
|
||||
if (!SO_T2_RATE(m_acr)) // The T2 continous shifter doesn't do interrupts (mode 4)
|
||||
{
|
||||
if (m_shift_counter == 0 && (SO_O2_CONTROL(m_acr) || SO_T2_CONTROL(m_acr)))
|
||||
{
|
||||
LOGINT("SHIFT O2/T2 out INT request ");
|
||||
set_int(INT_SR); // IRQ on last raising flank for internal clock (mode 5-6)
|
||||
set_int(INT_SR); // IRQ on last raising edge for internal clock (mode 5-6)
|
||||
}
|
||||
}
|
||||
}
|
||||
m_shift_counter = (m_shift_counter - 1) & 0x0f; // Count all flanks
|
||||
m_shift_counter = (m_shift_counter - 1) & 0x0f; // Count all edges
|
||||
}
|
||||
|
||||
void via6522_device::shift_in()
|
||||
{
|
||||
// Only shift in data on raising flank
|
||||
// Only shift in data on raising edge
|
||||
if ( !(m_shift_counter & 1) )
|
||||
{
|
||||
LOGSHIFT("%s shift In SR: %02x->", tag(), m_sr);
|
||||
@ -429,10 +429,10 @@ void via6522_device::shift_in()
|
||||
{
|
||||
LOGINT("SHIFT in INT request ");
|
||||
// set_int(INT_SR);// TODO: this interrupt is 1-2 clock cycles too early
|
||||
m_shift_irq_timer->adjust(clocks_to_attotime(2)/2); // Delay IRQ 2 flanks for all shift INs (mode 1-3)
|
||||
m_shift_irq_timer->adjust(clocks_to_attotime(2)/2); // Delay IRQ 2 edges for all shift INs (mode 1-3)
|
||||
}
|
||||
}
|
||||
m_shift_counter = (m_shift_counter - 1) & 0x0f; // Count all flanks
|
||||
m_shift_counter = (m_shift_counter - 1) & 0x0f; // Count all edges
|
||||
}
|
||||
|
||||
void via6522_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
|
||||
@ -440,7 +440,7 @@ void via6522_device::device_timer(emu_timer &timer, device_timer_id id, int para
|
||||
switch (id)
|
||||
{
|
||||
case TIMER_SHIFT_IRQ: // This timer event is a delayed IRQ for improved cycle accuracy
|
||||
set_int(INT_SR); // triggered from shift_in or shift_out on the last rising flank
|
||||
set_int(INT_SR); // triggered from shift_in or shift_out on the last rising edge
|
||||
m_shift_irq_timer->adjust(attotime::never); // Not needed really...
|
||||
break;
|
||||
case TIMER_SHIFT:
|
||||
@ -448,7 +448,7 @@ void via6522_device::device_timer(emu_timer &timer, device_timer_id id, int para
|
||||
m_out_cb1 ^= 1;
|
||||
m_cb1_handler(m_out_cb1);
|
||||
|
||||
// we call shift methods for all flanks
|
||||
// we call shift methods for all edges
|
||||
if (SO_T2_RATE(m_acr) || SO_T2_CONTROL(m_acr) || SO_O2_CONTROL(m_acr))
|
||||
{
|
||||
shift_out();
|
||||
@ -459,7 +459,7 @@ void via6522_device::device_timer(emu_timer &timer, device_timer_id id, int para
|
||||
}
|
||||
|
||||
// If in continous mode or the shifter is still shifting we re-arm the timer
|
||||
if (SO_T2_RATE(m_acr) || (m_shift_counter != 0x0f))
|
||||
if (SO_T2_RATE(m_acr) || (m_shift_counter < 0x0f))
|
||||
{
|
||||
if (SI_O2_CONTROL(m_acr) || SO_O2_CONTROL(m_acr))
|
||||
{
|
||||
@ -703,15 +703,20 @@ u8 via6522_device::read(offs_t offset)
|
||||
val = m_sr;
|
||||
if (!machine().side_effects_disabled())
|
||||
{
|
||||
m_out_cb1 = 1;
|
||||
m_cb1_handler(m_out_cb1);
|
||||
m_shift_counter = 0x0f;
|
||||
if (!(SI_EXT_CONTROL(m_acr) || SO_EXT_CONTROL(m_acr))) {
|
||||
m_out_cb1 = 1;
|
||||
m_cb1_handler(m_out_cb1);
|
||||
m_shift_counter = 0x0f;
|
||||
}
|
||||
else
|
||||
m_shift_counter = m_in_cb1 ? 0x0f : 0x10;
|
||||
|
||||
LOGINT("SR INT ");
|
||||
clear_int(INT_SR);
|
||||
LOGSHIFT(" - ACR: %02x ", m_acr);
|
||||
if (SI_O2_CONTROL(m_acr) || SO_O2_CONTROL(m_acr))
|
||||
{
|
||||
m_shift_timer->adjust(clocks_to_attotime(8) / 2); // 8 flanks to start shifter from a read
|
||||
m_shift_timer->adjust(clocks_to_attotime(8) / 2); // 8 edges to start shifter from a read
|
||||
LOGSHIFT(" - read SR starts O2 timer ");
|
||||
}
|
||||
else if (SI_T2_CONTROL(m_acr) || SO_T2_CONTROL(m_acr))
|
||||
@ -889,21 +894,20 @@ void via6522_device::write(offs_t offset, u8 data)
|
||||
m_sr = data;
|
||||
LOGSHIFT("Write SR: %02x\n", m_sr);
|
||||
|
||||
// make sure CB1 is high - this should not be needed though
|
||||
if (m_out_cb1 != 1)
|
||||
{
|
||||
logerror("VIA: CB1 is low starting shifter\n");
|
||||
if (!(SI_EXT_CONTROL(m_acr) || SO_EXT_CONTROL(m_acr))) {
|
||||
m_out_cb1 = 1;
|
||||
m_cb1_handler(m_out_cb1);
|
||||
m_shift_counter = 0x0f;
|
||||
}
|
||||
else
|
||||
m_shift_counter = m_in_cb1 ? 0x0f : 0x10;
|
||||
|
||||
m_shift_counter = 0x0f;
|
||||
LOGINT("SR INT ");
|
||||
clear_int(INT_SR);
|
||||
LOGSHIFT(" - ACR is: %02x ", m_acr);
|
||||
if (SO_O2_CONTROL(m_acr) || SI_O2_CONTROL(m_acr))
|
||||
{
|
||||
m_shift_timer->adjust(clocks_to_attotime(8) / 2); // 8 flanks to start shifter from a write
|
||||
m_shift_timer->adjust(clocks_to_attotime(8) / 2); // 8 edges to start shifter from a write
|
||||
LOGSHIFT(" - write SR starts O2 timer");
|
||||
}
|
||||
else if (SO_T2_RATE(m_acr) || SO_T2_CONTROL(m_acr) || SI_T2_CONTROL(m_acr))
|
||||
@ -966,6 +970,13 @@ void via6522_device::write(offs_t offset, u8 data)
|
||||
m_t1->adjust(clocks_to_attotime(counter1 + IFR_DELAY));
|
||||
m_t1_active = 1;
|
||||
}
|
||||
|
||||
if (SI_T2_CONTROL(m_acr) || SI_O2_CONTROL(m_acr) || SI_EXT_CONTROL(m_acr))
|
||||
{
|
||||
m_out_cb2 = 1;
|
||||
m_cb2_handler(m_out_cb2);
|
||||
}
|
||||
|
||||
LOGSHIFT("\n");
|
||||
}
|
||||
break;
|
||||
|
@ -4,8 +4,7 @@
|
||||
|
||||
I2C Memory
|
||||
|
||||
Generic ram/rom/eeprom/flash on an i2c bus. Supports specifying the slave address,
|
||||
the data size & the page size for writing.
|
||||
ram/rom/eeprom/flash on an i2c bus.
|
||||
|
||||
inputs:
|
||||
e0,e1,e2 lower 3 bits of the slave address
|
||||
@ -16,9 +15,11 @@ inputs:
|
||||
outputs:
|
||||
sda serial data
|
||||
|
||||
The memory address is only 8 bits, devices larger than this have multiple slave addresses.
|
||||
The top five address bits are set at manufacture time, two values are standard.
|
||||
The memory address is only 8 bits for devices up to 2048 bytes,
|
||||
devices from 512 to 2048 bytes occupy multiple slave addresses.
|
||||
|
||||
The top five address bits are set at manufacture time,
|
||||
there are two standard values.
|
||||
***************************************************************************/
|
||||
|
||||
#include "emu.h"
|
||||
@ -59,15 +60,16 @@ static inline void ATTR_PRINTF( 3, 4 ) verboselog( device_t *device, int n_level
|
||||
//**************************************************************************
|
||||
|
||||
// device type definition
|
||||
DEFINE_DEVICE_TYPE(I2CMEM, i2cmem_device, "i2cmem", "I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_X2404P, i2c_x2404p_device, "x2404p", "X2404P I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C01, i2c_24c01_device, "24c01", "24C01 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_PCD8572, i2c_pcd8572_device, "pcd8572", "PCD8572 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C02, i2c_24c02_device, "24c02", "24C02 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_M24C02, i2c_m24c02_device, "m24c02", "M24C02 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C04, i2c_24c04_device, "24c04", "24C04 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_X2404P, i2c_x2404p_device, "x2404p", "X2404P I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C08, i2c_24c08_device, "24c08", "24C08 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C16, i2c_24c16_device, "24c16", "24C16 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C16A, i2c_24c16a_device, "24c16a", "24C16A I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C64, i2c_24c64_device, "24c64", "24C64 I2C Memory")
|
||||
DEFINE_DEVICE_TYPE(I2C_24C512, i2c_24c512_device, "24c512", "24C512 I2C Memory")
|
||||
|
||||
//**************************************************************************
|
||||
// LIVE DEVICE
|
||||
@ -83,13 +85,15 @@ i2cmem_device::i2cmem_device(
|
||||
const char *tag,
|
||||
device_t *owner,
|
||||
uint32_t clock,
|
||||
int page_size,
|
||||
int read_page_size,
|
||||
int write_page_size,
|
||||
int data_size) :
|
||||
device_t(mconfig, type, tag, owner, clock),
|
||||
device_nvram_interface(mconfig, *this),
|
||||
m_region(*this, DEVICE_SELF),
|
||||
m_slave_address(I2CMEM_SLAVE_ADDRESS),
|
||||
m_page_size(page_size),
|
||||
m_read_page_size(read_page_size),
|
||||
m_write_page_size(write_page_size),
|
||||
m_data_size(data_size),
|
||||
m_scl(0),
|
||||
m_sdaw(0),
|
||||
@ -110,48 +114,53 @@ i2cmem_device::i2cmem_device(
|
||||
assert(!clock);
|
||||
}
|
||||
|
||||
i2cmem_device::i2cmem_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2CMEM, tag, owner, clock, 0, 0)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_x2404p_device::i2c_x2404p_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_X2404P, tag, owner, clock, 8, 0x200)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c01_device::i2c_24c01_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C01, tag, owner, clock, 4, 0x80)
|
||||
i2cmem_device(mconfig, I2C_24C01, tag, owner, clock, 0, 8, 0x80)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_pcd8572_device::i2c_pcd8572_device(const machine_config& mconfig, const char* tag, device_t* owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_PCD8572, tag, owner, clock, 0, 0, 0x80)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c02_device::i2c_24c02_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C02, tag, owner, clock, 4, 0x100)
|
||||
i2cmem_device(mconfig, I2C_24C02, tag, owner, clock, 0, 8, 0x100)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_m24c02_device::i2c_m24c02_device(const machine_config& mconfig, const char* tag, device_t* owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_M24C02, tag, owner, clock, 0, 16, 0x100)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c04_device::i2c_24c04_device(const machine_config& mconfig, const char* tag, device_t* owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C04, tag, owner, clock, 8, 0x200)
|
||||
i2cmem_device(mconfig, I2C_24C04, tag, owner, clock, 0, 16, 0x200)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_x2404p_device::i2c_x2404p_device(const machine_config& mconfig, const char* tag, device_t* owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_X2404P, tag, owner, clock, 0x100, 8, 0x200)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c08_device::i2c_24c08_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C08, tag, owner, clock, 0, 0x400)
|
||||
i2cmem_device(mconfig, I2C_24C08, tag, owner, clock, 0, 16, 0x400)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c16_device::i2c_24c16_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C16, tag, owner, clock, 8, 0x800)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c16a_device::i2c_24c16a_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C16A, tag, owner, clock, 0, 0x800)
|
||||
i2cmem_device(mconfig, I2C_24C16, tag, owner, clock, 0, 16, 0x800)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c64_device::i2c_24c64_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C64, tag, owner, clock, 8, 0x2000)
|
||||
i2cmem_device(mconfig, I2C_24C64, tag, owner, clock, 0, 32, 0x2000)
|
||||
{
|
||||
}
|
||||
|
||||
i2c_24c512_device::i2c_24c512_device(const machine_config& mconfig, const char* tag, device_t* owner, uint32_t clock) :
|
||||
i2cmem_device(mconfig, I2C_24C512, tag, owner, clock, 0, 128, 0x10000)
|
||||
{
|
||||
}
|
||||
|
||||
@ -162,7 +171,7 @@ i2c_24c64_device::i2c_24c64_device(const machine_config &mconfig, const char *ta
|
||||
void i2cmem_device::device_start()
|
||||
{
|
||||
m_data = std::make_unique<uint8_t []>(m_data_size);
|
||||
m_page.resize( m_page_size );
|
||||
m_page.resize( m_write_page_size );
|
||||
|
||||
save_item( NAME(m_scl) );
|
||||
save_item( NAME(m_sdaw) );
|
||||
@ -181,7 +190,7 @@ void i2cmem_device::device_start()
|
||||
save_item( NAME(m_page_offset) );
|
||||
save_item( NAME(m_page_written_size) );
|
||||
save_pointer( &m_data[0], "m_data", m_data_size );
|
||||
if ( m_page_size > 0 )
|
||||
if ( m_write_page_size > 0 )
|
||||
{
|
||||
save_item( NAME(m_page) );
|
||||
}
|
||||
@ -286,13 +295,15 @@ WRITE_LINE_MEMBER( i2cmem_device::write_sda )
|
||||
{
|
||||
if( m_sdaw )
|
||||
{
|
||||
if( m_state == STATE_DATAIN && m_page_size > 0 )
|
||||
if( m_page_written_size > 0 )
|
||||
{
|
||||
int base = data_offset();
|
||||
int root = base & ~( m_page_size - 1);
|
||||
for( int i=0; i < m_page_written_size; i++)
|
||||
m_data[root | ((base + i) & (m_page_size - 1))] = m_page[i];
|
||||
verboselog( this, 1, "data[ %04x to %04x ] = %x bytes\n", base, root | ((base + m_page_written_size - 1) & (m_page_size - 1)), m_page_written_size );
|
||||
int root = base & ~( m_write_page_size - 1 );
|
||||
for( int i = 0; i < m_page_written_size; i++ )
|
||||
m_data[root | ((base + i) & (m_write_page_size - 1))] = m_page[i];
|
||||
verboselog( this, 1, "data[ %04x to %04x ] = %x bytes\n", base, root | ((base + m_page_written_size - 1) & (m_write_page_size - 1)), m_page_written_size );
|
||||
|
||||
m_page_written_size = 0;
|
||||
}
|
||||
verboselog( this, 1, "stop\n" );
|
||||
m_state = STATE_IDLE;
|
||||
@ -373,7 +384,7 @@ WRITE_LINE_MEMBER( i2cmem_device::write_scl )
|
||||
break;
|
||||
|
||||
case STATE_ADDRESSLOW:
|
||||
m_byteaddr = m_shift | (skip_addresshigh() ? (m_devsel & DEVSEL_ADDRESS) << 7 : m_addresshigh << 8);
|
||||
m_byteaddr = m_shift | (skip_addresshigh() ? ((m_devsel & DEVSEL_ADDRESS) << 7) & address_mask() : m_addresshigh << 8);
|
||||
m_page_offset = 0;
|
||||
m_page_written_size = 0;
|
||||
|
||||
@ -388,17 +399,17 @@ WRITE_LINE_MEMBER( i2cmem_device::write_scl )
|
||||
verboselog( this, 0, "write not enabled\n" );
|
||||
m_state = STATE_IDLE;
|
||||
}
|
||||
else if( m_page_size > 0 )
|
||||
else if( m_write_page_size > 0 )
|
||||
{
|
||||
m_page[ m_page_offset ] = m_shift;
|
||||
verboselog( this, 1, "page[ %04x ] <- %02x\n", m_page_offset, m_page[ m_page_offset ] );
|
||||
|
||||
m_page_offset++;
|
||||
if( m_page_offset == m_page_size )
|
||||
if( m_page_offset == m_write_page_size )
|
||||
m_page_offset = 0;
|
||||
m_page_written_size++;
|
||||
if( m_page_written_size > m_page_size)
|
||||
m_page_written_size = m_page_size;
|
||||
if( m_page_written_size > m_write_page_size)
|
||||
m_page_written_size = m_write_page_size;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -440,7 +451,7 @@ WRITE_LINE_MEMBER( i2cmem_device::write_scl )
|
||||
|
||||
m_shift = m_data[offset];
|
||||
verboselog( this, 1, "data[ %04x ] -> %02x\n", offset, m_shift );
|
||||
m_byteaddr++;
|
||||
m_byteaddr = (m_byteaddr & ~(m_read_page_size - 1)) | ((m_byteaddr + 1) & (m_read_page_size - 1));
|
||||
}
|
||||
|
||||
m_sdar = ( m_shift >> 7 ) & 1;
|
||||
|
@ -33,12 +33,7 @@ class i2cmem_device :
|
||||
public device_nvram_interface
|
||||
{
|
||||
public:
|
||||
// construction/destruction
|
||||
i2cmem_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0);
|
||||
|
||||
i2cmem_device & set_address(int address) { m_slave_address = address; return *this; }
|
||||
i2cmem_device & set_page_size(int page_size) { m_page_size = page_size; return *this; }
|
||||
i2cmem_device & set_data_size(int data_size) { m_data_size = data_size; return *this; }
|
||||
i2cmem_device & set_e0(int e0) { m_e0 = e0; return *this; }
|
||||
i2cmem_device & set_e1(int e1) { m_e1 = e1; return *this; }
|
||||
i2cmem_device & set_e2(int e2) { m_e2 = e2; return *this; }
|
||||
@ -55,7 +50,7 @@ public:
|
||||
|
||||
protected:
|
||||
// construction/destruction
|
||||
i2cmem_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int page_size, int data_size);
|
||||
i2cmem_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int read_page_size, int write_page_size, int data_size);
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
@ -76,7 +71,8 @@ protected:
|
||||
// internal state
|
||||
std::unique_ptr<uint8_t[]> m_data;
|
||||
int m_slave_address;
|
||||
int m_page_size;
|
||||
int m_read_page_size;
|
||||
int m_write_page_size;
|
||||
int m_data_size;
|
||||
int m_scl;
|
||||
int m_sdaw;
|
||||
@ -103,24 +99,27 @@ protected:
|
||||
i2c_##name##_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0); \
|
||||
};
|
||||
|
||||
DECLARE_I2C_DEVICE(x2404p)
|
||||
DECLARE_I2C_DEVICE(24c01)
|
||||
DECLARE_I2C_DEVICE(24c02)
|
||||
DECLARE_I2C_DEVICE(24c04)
|
||||
DECLARE_I2C_DEVICE(24c08)
|
||||
DECLARE_I2C_DEVICE(24c01);
|
||||
DECLARE_I2C_DEVICE(pcd8572);
|
||||
DECLARE_I2C_DEVICE(24c02);
|
||||
DECLARE_I2C_DEVICE(m24c02);
|
||||
DECLARE_I2C_DEVICE(24c04);
|
||||
DECLARE_I2C_DEVICE(x2404p);
|
||||
DECLARE_I2C_DEVICE(24c08);
|
||||
DECLARE_I2C_DEVICE(24c16);
|
||||
DECLARE_I2C_DEVICE(24c16a);
|
||||
DECLARE_I2C_DEVICE(24c64);
|
||||
DECLARE_I2C_DEVICE(24c512);
|
||||
|
||||
// device type definition
|
||||
DECLARE_DEVICE_TYPE(I2CMEM, i2cmem_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_X2404P, i2c_x2404p_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C01, i2c_24c01_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_PCD8572, i2c_pcd8572_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C02, i2c_24c02_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_M24C02, i2c_m24c02_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C04, i2c_24c04_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_X2404P, i2c_x2404p_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C08, i2c_24c08_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C16, i2c_24c16_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C16A, i2c_24c16a_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C64, i2c_24c64_device)
|
||||
DECLARE_DEVICE_TYPE(I2C_24C512, i2c_24c512_device)
|
||||
|
||||
#endif // MAME_MACHINE_I2CMEM_H
|
||||
|
@ -46,12 +46,12 @@ void i82357_device::device_add_mconfig(machine_config &config)
|
||||
PIC8259(config, m_pic[0], 0);
|
||||
m_pic[0]->in_sp_callback().set_constant(1);
|
||||
m_pic[0]->read_slave_ack_callback().set(
|
||||
[this](offs_t offset)
|
||||
[this](offs_t offset) -> u8
|
||||
{
|
||||
if (offset == 2)
|
||||
return m_pic[1]->acknowledge();
|
||||
|
||||
return u32(0);
|
||||
return 0;
|
||||
});
|
||||
|
||||
PIC8259(config, m_pic[1], 0);
|
||||
|
@ -158,7 +158,7 @@ INPUT_PORTS_START( generic_keyboard )
|
||||
PORT_BIT( 0x0100U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_8) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x01) PORT_CHAR('8') PORT_CHAR('(')
|
||||
PORT_BIT( 0x0200U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_9) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x00) PORT_CHAR('9') PORT_CHAR('(')
|
||||
PORT_BIT( 0x0200U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_9) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x01) PORT_CHAR('9') PORT_CHAR(')')
|
||||
PORT_BIT( 0x0400U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_0) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x00) PORT_CHAR('0') PORT_CHAR('(')
|
||||
PORT_BIT( 0x0400U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_0) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x00) PORT_CHAR('0') PORT_CHAR(')')
|
||||
PORT_BIT( 0x0400U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_0) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x01) PORT_CHAR('0')
|
||||
PORT_BIT( 0x0800U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_MINUS) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x00) PORT_CHAR('-') PORT_CHAR('_')
|
||||
PORT_BIT( 0x0800U, IP_ACTIVE_HIGH, IPT_KEYBOARD ) PORT_CODE(KEYCODE_MINUS) PORT_CONDITION("GENKBD_CFG", 0x01, EQUALS, 0x01) PORT_CHAR('-') PORT_CHAR('=')
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,12 +1,5 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:R. Belmont, Olivier Galibert
|
||||
/*********************************************************************
|
||||
|
||||
ncr5380n.c
|
||||
|
||||
Implementation of the NCR 5380
|
||||
|
||||
*********************************************************************/
|
||||
// copyright-holders:Patrick Mackinlay
|
||||
|
||||
#ifndef MAME_MACHINE_NCR5380N_H
|
||||
#define MAME_MACHINE_NCR5380N_H
|
||||
@ -15,221 +8,179 @@
|
||||
|
||||
#include "machine/nscsi_bus.h"
|
||||
|
||||
|
||||
class ncr5380n_device : public nscsi_device, public nscsi_slot_card_interface
|
||||
class ncr5380n_device
|
||||
: public nscsi_device
|
||||
, public nscsi_slot_card_interface
|
||||
{
|
||||
public:
|
||||
ncr5380n_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
ncr5380n_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
|
||||
|
||||
// configuration helpers
|
||||
// device configuration
|
||||
auto irq_handler() { return m_irq_handler.bind(); }
|
||||
auto drq_handler() { return m_drq_handler.bind(); }
|
||||
|
||||
uint8_t read(offs_t offset);
|
||||
void write(offs_t offset, uint8_t data);
|
||||
// register access
|
||||
void map(address_map &map);
|
||||
u8 read(offs_t offset);
|
||||
void write(offs_t offset, u8 data);
|
||||
|
||||
uint8_t dma_r();
|
||||
void dma_w(uint8_t val);
|
||||
// dma access
|
||||
void eop_w(int state);
|
||||
u8 dma_r();
|
||||
void dma_w(u8 val);
|
||||
|
||||
protected:
|
||||
ncr5380n_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock);
|
||||
ncr5380n_device(machine_config const &mconfig, device_type type, char const *tag, device_t *owner, u32 clock, bool has_lbs = false);
|
||||
|
||||
// device_t overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_reset() override;
|
||||
virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override;
|
||||
|
||||
// ncsci_device overrides
|
||||
virtual void scsi_ctrl_changed() override;
|
||||
|
||||
// register read handlers
|
||||
u8 csdata_r();
|
||||
u8 icmd_r();
|
||||
u8 mode_r();
|
||||
u8 tcmd_r();
|
||||
u8 csstat_r();
|
||||
u8 bas_r();
|
||||
u8 idata_r();
|
||||
u8 rpi_r();
|
||||
|
||||
// register write handlers
|
||||
void odata_w(u8 data);
|
||||
void icmd_w(u8 data);
|
||||
void mode_w(u8 data);
|
||||
void tcmd_w(u8 data);
|
||||
void selen_w(u8 data);
|
||||
void sds_w(u8 data);
|
||||
void sdtr_w(u8 data);
|
||||
void sdir_w(u8 data);
|
||||
|
||||
// state machine
|
||||
void state_timer(void *ptr, s32 param);
|
||||
int state_step();
|
||||
|
||||
// other helpers
|
||||
void scsi_data_w(u8 data);
|
||||
void set_irq(bool irq_state);
|
||||
void set_drq(bool drq_state);
|
||||
|
||||
private:
|
||||
enum { MODE_D, MODE_T, MODE_I };
|
||||
enum { IDLE };
|
||||
enum icmd_mask : u8
|
||||
{
|
||||
IC_RST = 0x80, // assert R̅S̅T̅
|
||||
IC_TEST = 0x40, // test mode (wo)
|
||||
IC_AIP = 0x40, // arbitration in progress (ro)
|
||||
IC_LA = 0x20, // lost arbitration (ro)
|
||||
IC_ACK = 0x10, // assert A̅C̅K̅
|
||||
IC_BSY = 0x08, // assert B̅S̅Y̅
|
||||
IC_SEL = 0x04, // assert S̅E̅L̅
|
||||
IC_ATN = 0x02, // assert A̅T̅N̅
|
||||
IC_DBUS = 0x01, // assert data bus
|
||||
|
||||
enum {
|
||||
// Bus initiated sequences
|
||||
BUSINIT_SETTLE_DELAY = 1,
|
||||
BUSINIT_ASSERT_BUS_SEL,
|
||||
BUSINIT_MSG_OUT,
|
||||
BUSINIT_RECV_BYTE,
|
||||
BUSINIT_ASSERT_BUS_RESEL,
|
||||
BUSINIT_WAIT_REQ,
|
||||
BUSINIT_RECV_BYTE_NACK,
|
||||
|
||||
// Bus SCSI Reset
|
||||
BUSRESET_WAIT_INT,
|
||||
BUSRESET_RESET_BOARD,
|
||||
|
||||
// Disconnected state commands
|
||||
DISC_SEL_ARBITRATION,
|
||||
DISC_SEL_ATN_WAIT_REQ,
|
||||
DISC_SEL_ATN_SEND_BYTE,
|
||||
DISC_SEL_WAIT_REQ,
|
||||
DISC_SEL_SEND_BYTE,
|
||||
DISC_REC_ARBITRATION,
|
||||
DISC_REC_MSG_IN,
|
||||
DISC_REC_SEND_BYTE,
|
||||
DISC_RESET,
|
||||
|
||||
// Command sequence
|
||||
CMDSEQ_CMD_PHASE,
|
||||
CMDSEQ_RECV_BYTE,
|
||||
|
||||
// Target commands
|
||||
TARGET_SEND_BYTE,
|
||||
TARGET_CMD_RECV_BYTE,
|
||||
TARGET_MSG_RECV_BYTE,
|
||||
TARGET_MSG_RECV_PAD,
|
||||
TARGET_DISC_SEND_BYTE,
|
||||
TARGET_DISC_MSG_IN,
|
||||
TARGET_DISC_SEND_BYTE_2,
|
||||
|
||||
// Initiator commands
|
||||
INIT_MSG_WAIT_REQ,
|
||||
INIT_XFR,
|
||||
INIT_XFR_SEND_BYTE,
|
||||
INIT_XFR_SEND_PAD_WAIT_REQ,
|
||||
INIT_XFR_SEND_PAD,
|
||||
INIT_XFR_RECV_PAD_WAIT_REQ,
|
||||
INIT_XFR_RECV_PAD,
|
||||
INIT_XFR_RECV_BYTE_ACK,
|
||||
INIT_XFR_RECV_BYTE_NACK,
|
||||
INIT_XFR_WAIT_REQ,
|
||||
INIT_CPT_RECV_BYTE_ACK,
|
||||
INIT_CPT_RECV_WAIT_REQ,
|
||||
INIT_CPT_RECV_BYTE_NACK
|
||||
IC_PHASE = 0x9e,
|
||||
IC_WRITE = 0x9f,
|
||||
};
|
||||
|
||||
enum {
|
||||
// Arbitration
|
||||
ARB_WAIT_BUS_FREE = 1,
|
||||
ARB_COMPLETE,
|
||||
ARB_ASSERT_SEL,
|
||||
ARB_SET_DEST,
|
||||
ARB_RELEASE_BUSY,
|
||||
ARB_TIMEOUT_BUSY,
|
||||
ARB_TIMEOUT_ABORT,
|
||||
ARB_DESKEW_WAIT,
|
||||
|
||||
// Send/receive byte
|
||||
SEND_WAIT_SETTLE,
|
||||
SEND_WAIT_REQ_0,
|
||||
RECV_WAIT_REQ_1,
|
||||
RECV_WAIT_SETTLE,
|
||||
RECV_WAIT_REQ_0
|
||||
enum mode_mask : u8
|
||||
{
|
||||
MODE_BLOCKDMA = 0x80,
|
||||
MODE_TARGET = 0x40,
|
||||
MODE_PARITYCHK = 0x20,
|
||||
MODE_PARITYIRQ = 0x10,
|
||||
MODE_EOPIRQ = 0x08,
|
||||
MODE_BSYIRQ = 0x04,
|
||||
MODE_DMA = 0x02,
|
||||
MODE_ARBITRATE = 0x01,
|
||||
};
|
||||
enum tcmd_mask : u8
|
||||
{
|
||||
TC_LBS = 0x80, // last byte sent
|
||||
TC_REQ = 0x08, // assert R̅E̅Q̅
|
||||
TC_MSG = 0x04, // assert M̅S̅G̅
|
||||
TC_CD = 0x02, // assert C̅/D
|
||||
TC_IO = 0x01, // assert I̅/O
|
||||
|
||||
enum {
|
||||
STATE_MASK = 0x00ff,
|
||||
SUB_SHIFT = 8,
|
||||
SUB_MASK = 0xff00
|
||||
TC_PHASE = 0x07,
|
||||
};
|
||||
|
||||
enum { BUS_BUSY, BUS_FREE_WAIT, BUS_FREE };
|
||||
|
||||
enum {
|
||||
ST_RST = 0x80,
|
||||
ST_BSY = 0x40,
|
||||
ST_REQ = 0x20,
|
||||
ST_MSG = 0x10,
|
||||
ST_CD = 0x08,
|
||||
ST_IO = 0x04,
|
||||
ST_SEL = 0x02,
|
||||
ST_DBP = 0x01,
|
||||
|
||||
BAS_ENDOFDMA = 0x80,
|
||||
BAS_DMAREQUEST = 0x40,
|
||||
BAS_PARITYERROR = 0x20,
|
||||
BAS_IRQACTIVE = 0x10,
|
||||
BAS_PHASEMATCH = 0x08,
|
||||
BAS_BUSYERROR = 0x04,
|
||||
BAS_ATN = 0x02,
|
||||
BAS_ACK = 0x01,
|
||||
|
||||
IC_RST = 0x80,
|
||||
IC_ARBITRATION = 0x40,
|
||||
IC_ARBLOST = 0x20,
|
||||
IC_ACK = 0x10,
|
||||
IC_BSY = 0x08,
|
||||
IC_SEL = 0x04,
|
||||
IC_ATN = 0x02,
|
||||
IC_DBUS = 0x01,
|
||||
IC_PHASEMASK = 0x9e,
|
||||
IC_WRITEMASK = 0x9f,
|
||||
|
||||
MODE_BLOCKDMA = 0x80,
|
||||
MODE_TARGET = 0x40,
|
||||
MODE_PARITYCHK = 0x20,
|
||||
MODE_PARITYIRQ = 0x10,
|
||||
MODE_EOPIRQ = 0x08,
|
||||
MODE_BSYIRQ = 0x04,
|
||||
MODE_DMA = 0x02,
|
||||
MODE_ARBITRATE = 0x01
|
||||
enum csstat_mask : u8
|
||||
{
|
||||
ST_RST = 0x80,
|
||||
ST_BSY = 0x40,
|
||||
ST_REQ = 0x20,
|
||||
ST_MSG = 0x10,
|
||||
ST_CD = 0x08,
|
||||
ST_IO = 0x04,
|
||||
ST_SEL = 0x02,
|
||||
ST_DBP = 0x01,
|
||||
};
|
||||
enum bas_mask : u8
|
||||
{
|
||||
BAS_ENDOFDMA = 0x80,
|
||||
BAS_DMAREQUEST = 0x40,
|
||||
BAS_PARITYERROR = 0x20,
|
||||
BAS_IRQACTIVE = 0x10,
|
||||
BAS_PHASEMATCH = 0x08,
|
||||
BAS_BUSYERROR = 0x04,
|
||||
BAS_ATN = 0x02,
|
||||
BAS_ACK = 0x01,
|
||||
};
|
||||
|
||||
enum { DMA_NONE, DMA_IN, DMA_OUT };
|
||||
|
||||
uint32_t m_fake_clock;
|
||||
|
||||
emu_timer *tm;
|
||||
|
||||
uint8_t status, istatus, m_mode, m_outdata, m_busstatus, m_dmalatch;
|
||||
uint8_t m_icommand, m_tcommand;
|
||||
uint8_t clock_conv, sync_offset, sync_period, bus_id, select_timeout, seq;
|
||||
uint16_t tcount;
|
||||
int mode;
|
||||
int state/*, xfr_phase*/;
|
||||
|
||||
bool irq, drq;
|
||||
|
||||
void drq_set();
|
||||
void drq_clear();
|
||||
|
||||
void step(bool timeout);
|
||||
void function_complete();
|
||||
void function_bus_complete();
|
||||
void bus_complete();
|
||||
|
||||
void arbitrate();
|
||||
void check_irq();
|
||||
|
||||
void reset_soft();
|
||||
void reset_disconnect();
|
||||
|
||||
void send_byte();
|
||||
void recv_byte();
|
||||
|
||||
void delay(int cycles);
|
||||
void delay_cycles(int cycles);
|
||||
|
||||
void map(address_map &map);
|
||||
|
||||
uint8_t scsidata_r();
|
||||
void outdata_w(uint8_t data);
|
||||
uint8_t icmd_r();
|
||||
void icmd_w(uint8_t data);
|
||||
uint8_t mode_r();
|
||||
void mode_w(uint8_t data);
|
||||
uint8_t command_r();
|
||||
void command_w(uint8_t data);
|
||||
uint8_t status_r();
|
||||
void selenable_w(uint8_t data);
|
||||
uint8_t busandstatus_r();
|
||||
void startdmasend_w(uint8_t data);
|
||||
uint8_t indata_r();
|
||||
void startdmatargetrx_w(uint8_t data);
|
||||
uint8_t resetparityirq_r();
|
||||
void startdmainitrx_w(uint8_t data);
|
||||
|
||||
devcb_write_line m_irq_handler;
|
||||
devcb_write_line m_drq_handler;
|
||||
|
||||
// state machine
|
||||
emu_timer *m_state_timer;
|
||||
enum state : unsigned
|
||||
{
|
||||
IDLE,
|
||||
|
||||
// arbitration
|
||||
ARB_BUS_FREE,
|
||||
ARB_START,
|
||||
ARB_EVALUATE,
|
||||
|
||||
// dma transfer
|
||||
DMA_IN_REQ,
|
||||
DMA_IN_ACK,
|
||||
DMA_OUT_REQ,
|
||||
DMA_OUT_DRQ,
|
||||
DMA_OUT_ACK,
|
||||
}
|
||||
m_state;
|
||||
|
||||
// registers
|
||||
u8 m_odata;
|
||||
u8 m_icmd;
|
||||
u8 m_mode;
|
||||
u8 m_tcmd;
|
||||
u8 m_bas;
|
||||
u8 m_idata;
|
||||
|
||||
// line state
|
||||
u32 m_scsi_ctrl;
|
||||
bool m_irq_state;
|
||||
bool m_drq_state;
|
||||
|
||||
bool const m_has_lbs;
|
||||
};
|
||||
|
||||
class ncr53c80_device : public ncr5380n_device
|
||||
{
|
||||
public:
|
||||
ncr53c80_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
ncr53c80_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
|
||||
};
|
||||
|
||||
class cxd1180_device : public ncr5380n_device
|
||||
{
|
||||
public:
|
||||
cxd1180_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
|
||||
};
|
||||
|
||||
DECLARE_DEVICE_TYPE(NCR5380N, ncr5380n_device)
|
||||
DECLARE_DEVICE_TYPE(NCR53C80, ncr53c80_device)
|
||||
DECLARE_DEVICE_TYPE(CXD1180, cxd1180_device)
|
||||
|
||||
#endif // MAME_MACHINE_NCR5380N_H
|
||||
|
@ -288,6 +288,11 @@ void nscsi_full_device::step(bool timeout)
|
||||
scsi_bus->ctrl_w(scsi_refid, 0, S_ALL);
|
||||
scsi_state = IDLE;
|
||||
LOG("scsi bus reset\n");
|
||||
scsi_state = scsi_substate = IDLE;
|
||||
buf_control_rpos = buf_control_wpos = 0;
|
||||
scsi_identify = 0;
|
||||
data_buffer_size = 0;
|
||||
data_buffer_pos = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -39,14 +39,15 @@ void pic8259_device::device_timer(emu_timer &timer, device_timer_id id, int para
|
||||
/* is this IRQ in service and not cascading and sfnm? */
|
||||
if ((m_isr & mask) && !(m_master && m_cascade && m_nested && (m_slave & mask)))
|
||||
{
|
||||
LOG("pic8259_timerproc(): PIC IRQ #%d still in service\n", irq);
|
||||
LOG("pic8259_timerproc(): PIC IR%d still in service\n", irq);
|
||||
break;
|
||||
}
|
||||
|
||||
/* is this IRQ pending and enabled? */
|
||||
if ((m_state == state_t::READY) && (m_irr & mask) && !(m_imr & mask))
|
||||
{
|
||||
LOG("pic8259_timerproc(): PIC triggering IRQ #%d\n", irq);
|
||||
LOG("pic8259_timerproc(): PIC triggering IR%d\n", irq);
|
||||
m_current_level = irq;
|
||||
m_out_int_func(1);
|
||||
return;
|
||||
}
|
||||
@ -54,6 +55,7 @@ void pic8259_device::device_timer(emu_timer &timer, device_timer_id id, int para
|
||||
if((m_isr & mask) && m_master && m_cascade && m_nested && (m_slave & mask))
|
||||
break;
|
||||
}
|
||||
m_current_level = -1;
|
||||
m_out_int_func(0);
|
||||
}
|
||||
|
||||
@ -64,7 +66,7 @@ void pic8259_device::set_irq_line(int irq, int state)
|
||||
if (state)
|
||||
{
|
||||
/* setting IRQ line */
|
||||
LOG("set_irq_line(): PIC set IRQ line #%d\n", irq);
|
||||
LOG("set_irq_line(): PIC set IR%d line\n", irq);
|
||||
|
||||
if(m_level_trig_mode || (!m_level_trig_mode && !(m_irq_lines & mask)))
|
||||
{
|
||||
@ -75,26 +77,28 @@ void pic8259_device::set_irq_line(int irq, int state)
|
||||
else
|
||||
{
|
||||
/* clearing IRQ line */
|
||||
LOG("set_irq_line(): PIC cleared IRQ line #%d\n", irq);
|
||||
LOG("set_irq_line(): PIC cleared IR%d line\n", irq);
|
||||
|
||||
m_irq_lines &= ~mask;
|
||||
m_irr &= ~mask;
|
||||
}
|
||||
set_timer();
|
||||
|
||||
if (m_inta_sequence == 0)
|
||||
set_timer();
|
||||
}
|
||||
|
||||
|
||||
uint32_t pic8259_device::acknowledge()
|
||||
uint8_t pic8259_device::acknowledge()
|
||||
{
|
||||
for (int n = 0, irq = m_prio; n < 8; n++, irq = (irq + 1) & 7)
|
||||
if (is_x86())
|
||||
{
|
||||
uint8_t mask = 1 << irq;
|
||||
|
||||
/* is this IRQ pending and enabled? */
|
||||
if ((m_irr & mask) && !(m_imr & mask))
|
||||
if (m_current_level != -1)
|
||||
{
|
||||
if (!machine().side_effects_disabled()) {
|
||||
LOG("pic8259_acknowledge(): PIC acknowledge IRQ #%d\n", irq);
|
||||
uint8_t mask = 1 << m_current_level;
|
||||
if (!machine().side_effects_disabled())
|
||||
{
|
||||
LOG("pic8259_acknowledge(): PIC acknowledge IR%d\n", m_current_level);
|
||||
if (!m_level_trig_mode)
|
||||
m_irr &= ~mask;
|
||||
|
||||
@ -107,29 +111,70 @@ uint32_t pic8259_device::acknowledge()
|
||||
if ((m_cascade!=0) && (m_master!=0) && (mask & m_slave))
|
||||
{
|
||||
// it's from slave device
|
||||
return m_read_slave_ack_func(irq);
|
||||
return m_read_slave_ack_func(m_current_level);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (is_x86())
|
||||
{
|
||||
/* For x86 mode*/
|
||||
return irq + m_base;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* in case of 8080/85) */
|
||||
return 0xcd0000 + (m_vector_addr_high << 8) + m_vector_addr_low + (irq << (3-m_vector_size));
|
||||
}
|
||||
/* For x86 mode*/
|
||||
return m_current_level + m_base;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!machine().side_effects_disabled())
|
||||
logerror("Spurious INTA\n");
|
||||
return m_base + 7;
|
||||
}
|
||||
}
|
||||
if (!machine().side_effects_disabled())
|
||||
logerror("Spurious IRQ\n");
|
||||
if (is_x86())
|
||||
return m_base + 7;
|
||||
else
|
||||
return 0xcd0000 + (m_vector_addr_high << 8) + m_vector_addr_low + (7 << (3-m_vector_size));
|
||||
{
|
||||
/* in case of 8080/85 */
|
||||
if (m_inta_sequence == 0)
|
||||
{
|
||||
if (!machine().side_effects_disabled())
|
||||
{
|
||||
if (m_current_level != -1)
|
||||
{
|
||||
LOG("pic8259_acknowledge(): PIC acknowledge IR%d\n", m_current_level);
|
||||
|
||||
uint8_t mask = 1 << m_current_level;
|
||||
if (!m_level_trig_mode)
|
||||
m_irr &= ~mask;
|
||||
m_isr |= mask;
|
||||
}
|
||||
else
|
||||
logerror("Spurious INTA\n");
|
||||
m_inta_sequence = 1;
|
||||
}
|
||||
if (m_cascade && m_master && m_current_level != -1 && BIT(m_slave, m_current_level))
|
||||
return m_read_slave_ack_func(m_current_level);
|
||||
else
|
||||
return 0xcd;
|
||||
}
|
||||
else if (m_inta_sequence == 1)
|
||||
{
|
||||
if (!machine().side_effects_disabled())
|
||||
m_inta_sequence = 2;
|
||||
if (m_cascade && m_master && m_current_level != -1 && BIT(m_slave, m_current_level))
|
||||
return m_read_slave_ack_func(m_current_level);
|
||||
else
|
||||
return m_vector_addr_low + ((m_current_level & 7) << (3-m_vector_size));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!machine().side_effects_disabled())
|
||||
{
|
||||
m_inta_sequence = 0;
|
||||
if (m_auto_eoi && m_current_level != -1)
|
||||
m_isr &= ~(1 << m_current_level);
|
||||
set_timer();
|
||||
}
|
||||
if (m_cascade && m_master && m_current_level != -1 && BIT(m_slave, m_current_level))
|
||||
return m_read_slave_ack_func(m_current_level);
|
||||
else
|
||||
return m_vector_addr_high;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -150,18 +195,17 @@ uint8_t pic8259_device::read(offs_t offset)
|
||||
if ( m_ocw3 & 0x04 )
|
||||
{
|
||||
/* Polling mode */
|
||||
if ( m_irr & ~m_imr )
|
||||
if (m_current_level != -1)
|
||||
{
|
||||
/* check the various IRQs */
|
||||
for (int n = 0, irq = m_prio; n < 8; n++, irq = (irq + 1) & 7)
|
||||
{
|
||||
if ( ( 1 << irq ) & m_irr & ~m_imr )
|
||||
{
|
||||
data = 0x80 | irq;
|
||||
break;
|
||||
}
|
||||
}
|
||||
acknowledge();
|
||||
data = 0x80 | m_current_level;
|
||||
|
||||
if (!m_level_trig_mode)
|
||||
m_irr &= ~(1 << m_current_level);
|
||||
|
||||
if (!m_auto_eoi)
|
||||
m_isr |= 1 << m_current_level;
|
||||
|
||||
set_timer();
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -207,7 +251,9 @@ void pic8259_device::write(offs_t offset, uint8_t data)
|
||||
m_cascade = (data & 0x02) ? 0 : 1;
|
||||
m_icw4_needed = (data & 0x01) ? 1 : 0;
|
||||
m_vector_addr_low = (data & 0xe0);
|
||||
m_state = state_t::ICW2;
|
||||
m_state = state_t::ICW2;
|
||||
m_current_level = -1;
|
||||
m_inta_sequence = 0;
|
||||
m_out_int_func(0);
|
||||
}
|
||||
else if (m_state == state_t::READY)
|
||||
@ -377,6 +423,8 @@ void pic8259_device::device_start()
|
||||
save_item(NAME(m_mode));
|
||||
save_item(NAME(m_auto_eoi));
|
||||
save_item(NAME(m_is_x86));
|
||||
save_item(NAME(m_current_level));
|
||||
save_item(NAME(m_inta_sequence));
|
||||
}
|
||||
|
||||
|
||||
@ -406,6 +454,8 @@ void pic8259_device::device_reset()
|
||||
m_is_x86 = 0;
|
||||
m_vector_addr_low = 0;
|
||||
m_vector_addr_high = 0;
|
||||
m_current_level = -1;
|
||||
m_inta_sequence = 0;
|
||||
|
||||
m_master = m_in_sp_func();
|
||||
}
|
||||
|
@ -39,7 +39,7 @@ public:
|
||||
|
||||
uint8_t read(offs_t offset);
|
||||
void write(offs_t offset, uint8_t data);
|
||||
uint32_t acknowledge();
|
||||
uint8_t acknowledge();
|
||||
|
||||
DECLARE_WRITE_LINE_MEMBER( ir0_w ) { set_irq_line(0, state); }
|
||||
DECLARE_WRITE_LINE_MEMBER( ir1_w ) { set_irq_line(1, state); }
|
||||
@ -113,6 +113,9 @@ private:
|
||||
uint8_t m_mode;
|
||||
uint8_t m_auto_eoi;
|
||||
uint8_t m_is_x86;
|
||||
|
||||
int8_t m_current_level;
|
||||
uint8_t m_inta_sequence;
|
||||
};
|
||||
|
||||
class v5x_icu_device : public pic8259_device
|
||||
|
@ -3,7 +3,7 @@
|
||||
#ifndef MAME_MACHINE_RESCAP_H
|
||||
#define MAME_MACHINE_RESCAP_H
|
||||
|
||||
/* Little helpers for magnitude conversions */
|
||||
// Little helpers for magnitude conversions
|
||||
#define RES_R(res) ((double)(res))
|
||||
#define RES_K(res) ((double)(res) * 1e3)
|
||||
#define RES_M(res) ((double)(res) * 1e6)
|
||||
@ -15,7 +15,7 @@
|
||||
#define IND_N(ind) ((double)(ind) * 1e-9)
|
||||
#define IND_P(ind) ((double)(ind) * 1e-12)
|
||||
|
||||
/* vin --/\r1/\-- out --/\r2/\-- gnd */
|
||||
// vin --/\r1/\-- out --/\r2/\-- gnd
|
||||
#define RES_VOLTAGE_DIVIDER(r1, r2) ((double)(r2) / ((double)(r1) + (double)(r2)))
|
||||
|
||||
#define RES_2_PARALLEL(r1, r2) (((r1) * (r2)) / ((r1) + (r2)))
|
||||
@ -26,4 +26,15 @@
|
||||
|
||||
#define RES_2_SERIAL(r1,r2) ((r1)+(r2))
|
||||
|
||||
// macro for the RC time constant on a 74LS123 with C > 1000pF
|
||||
// R is in ohms, C is in farads
|
||||
#define TIME_OF_74LS123(r,c) (0.45 * (double)(r) * (double)(c))
|
||||
|
||||
// macros for the RC time constant on a 555 timer IC
|
||||
// R is in ohms, C is in farads
|
||||
#define PERIOD_OF_555_MONOSTABLE_NSEC(r,c) ((attoseconds_t)(1100000000 * (double)(r) * (double)(c)))
|
||||
#define PERIOD_OF_555_ASTABLE_NSEC(r1,r2,c) ((attoseconds_t)( 693000000 * ((double)(r1) + 2.0 * (double)(r2)) * (double)(c)))
|
||||
#define PERIOD_OF_555_MONOSTABLE(r,c) attotime::from_nsec(PERIOD_OF_555_MONOSTABLE_NSEC(r,c))
|
||||
#define PERIOD_OF_555_ASTABLE(r1,r2,c) attotime::from_nsec(PERIOD_OF_555_ASTABLE_NSEC(r1,r2,c))
|
||||
|
||||
#endif // MAME_MACHINE_RESCAP_H
|
||||
|
@ -85,7 +85,7 @@ public:
|
||||
bool enabled() const { return m_timer->enabled(); }
|
||||
|
||||
// property setters
|
||||
void set_param(int param) const { assert(m_type == TIMER_TYPE_GENERIC); m_timer->set_param(param); }
|
||||
void set_param(int param) const { if(m_type != TIMER_TYPE_GENERIC) fatalerror("Cannot change parameter on a non-generic timer.\n"); m_timer->set_param(param); }
|
||||
void set_ptr(void *ptr) { m_ptr = ptr; }
|
||||
void enable(bool enable = true) const { m_timer->enable(enable); }
|
||||
|
||||
@ -93,7 +93,8 @@ public:
|
||||
void reset() { adjust(attotime::never, 0, attotime::never); }
|
||||
void adjust(const attotime &duration, s32 param = 0, const attotime &period = attotime::never) const
|
||||
{
|
||||
assert(m_type == TIMER_TYPE_GENERIC);
|
||||
if(m_type != TIMER_TYPE_GENERIC)
|
||||
fatalerror("Cannot adjust a non-generic timer.\n");
|
||||
m_timer->adjust(duration, param, period);
|
||||
}
|
||||
|
||||
|
@ -68,6 +68,7 @@ public:
|
||||
auto write_port5_callback() { return m_write_port[4].bind(); }
|
||||
auto write_port6_callback() { return m_write_port[5].bind(); }
|
||||
auto write_port7_callback() { return m_write_port[6].bind(); }
|
||||
tms1024_device &set_ms(u8 i) { m_ms = i & 1; return *this; } // if hardwired, can just set MS pin state here
|
||||
|
||||
void write_h(u8 data);
|
||||
u8 read_h();
|
||||
|
@ -1840,8 +1840,8 @@ void z80scc_channel::do_sccreg_wr0(uint8_t data)
|
||||
// loop over all interrupt sources
|
||||
for (auto & elem : m_uart->m_int_state)
|
||||
{
|
||||
// find the first channel with an interrupt requested
|
||||
if (elem & Z80_DAISY_INT)
|
||||
// find the first interrupt under service
|
||||
if (elem & Z80_DAISY_IEO)
|
||||
{
|
||||
LOGCMD("- %c found IUS bit to clear\n", 'A' + m_index);
|
||||
elem = 0; // Clear IUS bit (called IEO in z80 daisy lingo)
|
||||
@ -1858,7 +1858,8 @@ void z80scc_channel::do_sccreg_wr0(uint8_t data)
|
||||
of these modes is selected and this command is issued before the data has been read from the
|
||||
Receive FIFO, the data is lost */
|
||||
LOGCMD("%s: %c : WR0_ERROR_RESET - not implemented\n", owner()->tag(), 'A' + m_index);
|
||||
m_rx_fifo_rp_step(); // Reset error state in fifo and unlock it. unlock == step to next slot in fifo.
|
||||
if (m_rx_fifo_wp != m_rx_fifo_rp)
|
||||
m_rx_fifo_rp_step(); // Reset error state in fifo and unlock it. unlock == step to next slot in fifo.
|
||||
break;
|
||||
case WR0_SEND_ABORT: // Flush transmitter and Send 8-13 bits of '1's, used with SDLC
|
||||
LOGCMD("%s: %c : WR0_SEND_ABORT - not implemented\n", owner()->tag(), 'A' + m_index);
|
||||
|
@ -1,16 +1,21 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:R. Belmont
|
||||
/*
|
||||
C140.c
|
||||
c140.cpp
|
||||
|
||||
Simulator based on AMUSE sources.
|
||||
The C140 sound chip is used by Namco System 2 and System 21
|
||||
The 219 ASIC (which incorporates a modified C140) is used by Namco NA-1 and NA-2
|
||||
This chip controls 24 channels (C140) or 16 (219) of PCM.
|
||||
16 bytes are associated with each channel.
|
||||
Channels can be 8 bit signed PCM, or 12 bit signed PCM.
|
||||
Channels can be 8 bit compressed PCM, or 12 bit signed PCM.
|
||||
|
||||
TODO: What does the INT0 pin do? Normally Namco tied it to VOL0 (with VOL1 = VCC).
|
||||
TODO:
|
||||
- What does the INT0 pin do? Normally Namco tied it to VOL0 (with VOL1 = VCC).
|
||||
- Acknowledge A9 bit (9th address bit) of host interface
|
||||
- Verify data bus bits of C219
|
||||
- Verify C219 LFSR algorithm (same as c352.cpp?)
|
||||
- Verify unknown mode bits (0x40 for C140, 0x02 for C219)
|
||||
|
||||
--------------
|
||||
|
||||
@ -37,43 +42,44 @@ TODO: What does the INT0 pin do? Normally Namco tied it to VOL0 (with VOL1 = VCC
|
||||
2000.06.26 CAB fixed compressed pcm playback
|
||||
2002.07.20 R. Belmont added support for multiple banking types
|
||||
2006.01.08 R. Belmont added support for NA-1/2 "219" derivative
|
||||
2020.05.06 cam900 Implement some features from QuattroPlay sources, by superctr
|
||||
*/
|
||||
|
||||
|
||||
#include "emu.h"
|
||||
#include "c140.h"
|
||||
#include <algorithm>
|
||||
|
||||
struct voice_registers
|
||||
{
|
||||
uint8_t volume_right;
|
||||
uint8_t volume_left;
|
||||
uint8_t frequency_msb;
|
||||
uint8_t frequency_lsb;
|
||||
uint8_t bank;
|
||||
uint8_t mode;
|
||||
uint8_t start_msb;
|
||||
uint8_t start_lsb;
|
||||
uint8_t end_msb;
|
||||
uint8_t end_lsb;
|
||||
uint8_t loop_msb;
|
||||
uint8_t loop_lsb;
|
||||
uint8_t reserved[4];
|
||||
u8 volume_right;
|
||||
u8 volume_left;
|
||||
u8 frequency_msb;
|
||||
u8 frequency_lsb;
|
||||
u8 bank;
|
||||
u8 mode;
|
||||
u8 start_msb;
|
||||
u8 start_lsb;
|
||||
u8 end_msb;
|
||||
u8 end_lsb;
|
||||
u8 loop_msb;
|
||||
u8 loop_lsb;
|
||||
u8 reserved[4];
|
||||
};
|
||||
|
||||
|
||||
// device type definition
|
||||
DEFINE_DEVICE_TYPE(C140, c140_device, "c140", "Namco C140")
|
||||
DEFINE_DEVICE_TYPE(C219, c219_device, "c219", "Namco C219")
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// LIVE DEVICE
|
||||
//**************************************************************************
|
||||
|
||||
static inline int limit(int32_t in)
|
||||
static inline int limit(s32 in)
|
||||
{
|
||||
if(in>0x7fff) return 0x7fff;
|
||||
else if(in<-0x8000) return -0x8000;
|
||||
return in;
|
||||
return std::max(-0x7fff, std::min(0x8000, in));
|
||||
}
|
||||
|
||||
|
||||
@ -82,19 +88,29 @@ static inline int limit(int32_t in)
|
||||
//-------------------------------------------------
|
||||
|
||||
c140_device::c140_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
|
||||
: device_t(mconfig, C140, tag, owner, clock)
|
||||
: c140_device(mconfig, C140, tag, owner, clock)
|
||||
{
|
||||
}
|
||||
|
||||
c140_device::c140_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_sound_interface(mconfig, *this)
|
||||
, device_rom_interface(mconfig, *this, 21)
|
||||
, device_rom_interface(mconfig, *this, 25, ENDIANNESS_BIG, 16) // Verified from schematics (24 bit address, 12(16? for C219) bit data)
|
||||
, m_int1_callback(*this)
|
||||
, m_sample_rate(0)
|
||||
, m_stream(nullptr)
|
||||
, m_banking_type(C140_TYPE::SYSTEM2)
|
||||
, m_mixer_buffer_left(nullptr)
|
||||
, m_mixer_buffer_right(nullptr)
|
||||
, m_baserate(0)
|
||||
{
|
||||
memset(m_REG, 0, sizeof(uint8_t)*0x200);
|
||||
memset(m_pcmtbl, 0, sizeof(int16_t)*8);
|
||||
std::fill(std::begin(m_REG), std::end(m_REG), 0);
|
||||
std::fill(std::begin(m_pcmtbl), std::end(m_pcmtbl), 0);
|
||||
}
|
||||
|
||||
c219_device::c219_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
|
||||
: c140_device(mconfig, C219, tag, owner, clock)
|
||||
{
|
||||
// TODO: unknown address bus bits
|
||||
}
|
||||
|
||||
|
||||
@ -111,46 +127,76 @@ void c140_device::device_start()
|
||||
|
||||
m_stream = stream_alloc(0, 2, m_sample_rate);
|
||||
|
||||
/* make decompress pcm table */ //2000.06.26 CAB
|
||||
int32_t segbase = 0;
|
||||
for(int i = 0; i < 8; i++)
|
||||
// make decompress pcm table (Verified from Wii Virtual Console Arcade Starblade)
|
||||
for (int i = 0; i < 256; i++)
|
||||
{
|
||||
m_pcmtbl[i]=segbase; //segment base value
|
||||
segbase += 16<<i;
|
||||
int j = (s8)i;
|
||||
s8 s1 = j & 7;
|
||||
s8 s2 = abs(j >> 3) & 31;
|
||||
|
||||
m_pcmtbl[i] = 0x80 << s1 & 0xff00;
|
||||
m_pcmtbl[i] += s2 << (s1 ? s1 + 3 : 4);
|
||||
|
||||
if (j < 0)
|
||||
m_pcmtbl[i] = -m_pcmtbl[i];
|
||||
}
|
||||
|
||||
memset(m_REG,0,sizeof(m_REG));
|
||||
std::fill(std::begin(m_REG), std::end(m_REG), 0);
|
||||
|
||||
for(int i = 0; i < MAX_VOICE; i++)
|
||||
for (int i = 0; i < MAX_VOICE; i++)
|
||||
{
|
||||
init_voice(&m_voi[i]);
|
||||
}
|
||||
|
||||
/* allocate a pair of buffers to mix into - 1 second's worth should be more than enough */
|
||||
m_mixer_buffer_left = std::make_unique<int16_t[]>(m_sample_rate);
|
||||
m_mixer_buffer_right = std::make_unique<int16_t[]>(m_sample_rate);
|
||||
m_mixer_buffer_left = std::make_unique<s16[]>(m_sample_rate);
|
||||
m_mixer_buffer_right = std::make_unique<s16[]>(m_sample_rate);
|
||||
|
||||
save_item(NAME(m_REG));
|
||||
|
||||
for (int i = 0; i < MAX_VOICE; i++)
|
||||
{
|
||||
save_item(NAME(m_voi[i].ptoffset), i);
|
||||
save_item(NAME(m_voi[i].pos), i);
|
||||
save_item(NAME(m_voi[i].key), i);
|
||||
save_item(NAME(m_voi[i].lastdt), i);
|
||||
save_item(NAME(m_voi[i].prevdt), i);
|
||||
save_item(NAME(m_voi[i].dltdt), i);
|
||||
save_item(NAME(m_voi[i].rvol), i);
|
||||
save_item(NAME(m_voi[i].lvol), i);
|
||||
save_item(NAME(m_voi[i].frequency), i);
|
||||
save_item(NAME(m_voi[i].bank), i);
|
||||
save_item(NAME(m_voi[i].mode), i);
|
||||
save_item(NAME(m_voi[i].sample_start), i);
|
||||
save_item(NAME(m_voi[i].sample_end), i);
|
||||
save_item(NAME(m_voi[i].sample_loop), i);
|
||||
}
|
||||
save_item(STRUCT_MEMBER(m_voi, ptoffset));
|
||||
save_item(STRUCT_MEMBER(m_voi, pos));
|
||||
save_item(STRUCT_MEMBER(m_voi, key));
|
||||
save_item(STRUCT_MEMBER(m_voi, lastdt));
|
||||
save_item(STRUCT_MEMBER(m_voi, prevdt));
|
||||
save_item(STRUCT_MEMBER(m_voi, dltdt));
|
||||
save_item(STRUCT_MEMBER(m_voi, rvol));
|
||||
save_item(STRUCT_MEMBER(m_voi, lvol));
|
||||
save_item(STRUCT_MEMBER(m_voi, frequency));
|
||||
save_item(STRUCT_MEMBER(m_voi, bank));
|
||||
save_item(STRUCT_MEMBER(m_voi, mode));
|
||||
save_item(STRUCT_MEMBER(m_voi, sample_start));
|
||||
save_item(STRUCT_MEMBER(m_voi, sample_end));
|
||||
save_item(STRUCT_MEMBER(m_voi, sample_loop));
|
||||
}
|
||||
|
||||
void c219_device::device_start()
|
||||
{
|
||||
c140_device::device_start();
|
||||
// generate mulaw table (Verified from Wii Virtual Console Arcade Knuckle Heads)
|
||||
// same as c352.cpp
|
||||
int j = 0;
|
||||
for (int i = 0; i < 128; i++)
|
||||
{
|
||||
m_pcmtbl[i] = j << 5;
|
||||
if (i < 16)
|
||||
j += 1;
|
||||
else if (i < 24)
|
||||
j += 2;
|
||||
else if (i < 48)
|
||||
j += 4;
|
||||
else if (i < 100)
|
||||
j += 8;
|
||||
else
|
||||
j += 16;
|
||||
}
|
||||
for (int i = 0; i < 128; i++)
|
||||
m_pcmtbl[i + 128] = (~m_pcmtbl[i]) & 0xffe0;
|
||||
|
||||
m_lfsr = 0x1234;
|
||||
|
||||
save_item(NAME(m_lfsr));
|
||||
}
|
||||
|
||||
void c140_device::device_clock_changed()
|
||||
{
|
||||
@ -159,8 +205,8 @@ void c140_device::device_clock_changed()
|
||||
m_stream->set_sample_rate(m_sample_rate);
|
||||
|
||||
/* allocate a pair of buffers to mix into - 1 second's worth should be more than enough */
|
||||
m_mixer_buffer_left = std::make_unique<int16_t[]>(m_sample_rate);
|
||||
m_mixer_buffer_right = std::make_unique<int16_t[]>(m_sample_rate);;
|
||||
m_mixer_buffer_left = std::make_unique<s16[]>(m_sample_rate);
|
||||
m_mixer_buffer_right = std::make_unique<s16[]>(m_sample_rate);;
|
||||
}
|
||||
|
||||
|
||||
@ -176,181 +222,100 @@ void c140_device::rom_bank_updated()
|
||||
|
||||
void c140_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
|
||||
{
|
||||
int i,j;
|
||||
s32 dt;
|
||||
|
||||
int32_t rvol,lvol;
|
||||
int32_t dt;
|
||||
int32_t sdt;
|
||||
int32_t st,ed,sz;
|
||||
float pbase = (float)m_baserate * 2.0f / (float)m_sample_rate;
|
||||
|
||||
long sampleData;
|
||||
int32_t frequency,delta,offset,pos;
|
||||
int32_t cnt, voicecnt;
|
||||
int32_t lastdt,prevdt,dltdt;
|
||||
float pbase=(float)m_baserate*2.0f / (float)m_sample_rate;
|
||||
s16 *lmix, *rmix;
|
||||
|
||||
int16_t *lmix, *rmix;
|
||||
|
||||
if(samples>m_sample_rate) samples=m_sample_rate;
|
||||
if (samples > m_sample_rate) samples = m_sample_rate;
|
||||
|
||||
/* zap the contents of the mixer buffer */
|
||||
memset(m_mixer_buffer_left.get(), 0, samples * sizeof(int16_t));
|
||||
memset(m_mixer_buffer_right.get(), 0, samples * sizeof(int16_t));
|
||||
|
||||
/* get the number of voices to update */
|
||||
voicecnt = (m_banking_type == C140_TYPE::ASIC219) ? 16 : 24;
|
||||
std::fill_n(&m_mixer_buffer_left[0], samples, 0);
|
||||
std::fill_n(&m_mixer_buffer_right[0], samples, 0);
|
||||
|
||||
//--- audio update
|
||||
for( i=0;i<voicecnt;i++ )
|
||||
for (int i = 0; i < 24; i++)
|
||||
{
|
||||
C140_VOICE *v = &m_voi[i];
|
||||
const struct voice_registers *vreg = (struct voice_registers *)&m_REG[i*16];
|
||||
const struct voice_registers *vreg = (struct voice_registers *)&m_REG[i * 16];
|
||||
|
||||
if( v->key )
|
||||
if (v->key)
|
||||
{
|
||||
frequency= vreg->frequency_msb*256 + vreg->frequency_lsb;
|
||||
const u16 frequency = (vreg->frequency_msb << 8) | vreg->frequency_lsb;
|
||||
|
||||
/* Abort voice if no frequency value set */
|
||||
if(frequency==0) continue;
|
||||
if (frequency == 0) continue;
|
||||
|
||||
/* Delta = frequency * ((8MHz/374)*2 / sample rate) */
|
||||
delta=(long)((float)frequency * pbase);
|
||||
const int delta = (int)((float)frequency * pbase);
|
||||
|
||||
/* Calculate left/right channel volumes */
|
||||
lvol=(vreg->volume_left*32)/MAX_VOICE; //32ch -> 24ch
|
||||
rvol=(vreg->volume_right*32)/MAX_VOICE;
|
||||
const int lvol = (vreg->volume_left * 32) / MAX_VOICE; //32ch -> 24ch
|
||||
const int rvol = (vreg->volume_right * 32) / MAX_VOICE;
|
||||
|
||||
/* Set mixer outputs base pointers */
|
||||
lmix = m_mixer_buffer_left.get();
|
||||
rmix = m_mixer_buffer_right.get();
|
||||
|
||||
/* Retrieve sample start/end and calculate size */
|
||||
st=v->sample_start;
|
||||
ed=v->sample_end;
|
||||
sz=ed-st;
|
||||
const int st = v->sample_start;
|
||||
const int ed = v->sample_end;
|
||||
const int sz = ed - st;
|
||||
|
||||
/* Retrieve base pointer to the sample data */
|
||||
sampleData = find_sample(st, v->bank, i);
|
||||
const int sampleData = find_sample(st, v->bank, i);
|
||||
|
||||
/* Fetch back previous data pointers */
|
||||
offset=v->ptoffset;
|
||||
pos=v->pos;
|
||||
lastdt=v->lastdt;
|
||||
prevdt=v->prevdt;
|
||||
dltdt=v->dltdt;
|
||||
int offset = v->ptoffset;
|
||||
int pos = v->pos;
|
||||
s32 lastdt = v->lastdt;
|
||||
s32 prevdt = v->prevdt;
|
||||
s32 dltdt = v->dltdt;
|
||||
|
||||
/* Switch on data type - compressed PCM is only for C140 */
|
||||
if ((v->mode&8) && (m_banking_type != C140_TYPE::ASIC219))
|
||||
/* linear or compressed 12bit signed PCM */
|
||||
for (int j = 0; j < samples; j++)
|
||||
{
|
||||
//compressed PCM (maybe correct...)
|
||||
/* Loop for enough to fill sample buffer as requested */
|
||||
for(j=0;j<samples;j++)
|
||||
offset += delta;
|
||||
const int cnt = (offset >> 16) & 0x7fff;
|
||||
offset &= 0xffff;
|
||||
pos += cnt;
|
||||
/* Check for the end of the sample */
|
||||
if (pos >= sz)
|
||||
{
|
||||
offset += delta;
|
||||
cnt = (offset>>16)&0x7fff;
|
||||
offset &= 0xffff;
|
||||
pos+=cnt;
|
||||
//for(;cnt>0;cnt--)
|
||||
/* Check if its a looping sample, either stop or loop */
|
||||
if (ch_looped(v))
|
||||
{
|
||||
/* Check for the end of the sample */
|
||||
if(pos >= sz)
|
||||
{
|
||||
/* Check if its a looping sample, either stop or loop */
|
||||
if(v->mode&0x10)
|
||||
{
|
||||
pos = (v->sample_loop - st);
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key=0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Read the chosen sample byte */
|
||||
dt = (int8_t) read_byte(sampleData + pos);
|
||||
|
||||
/* decompress to 13bit range */ //2000.06.26 CAB
|
||||
sdt=dt>>3; //signed
|
||||
if(sdt<0) sdt = (sdt<<(dt&7)) - m_pcmtbl[dt&7];
|
||||
else sdt = (sdt<<(dt&7)) + m_pcmtbl[dt&7];
|
||||
|
||||
prevdt=lastdt;
|
||||
lastdt=sdt;
|
||||
dltdt=(lastdt - prevdt);
|
||||
pos = (v->sample_loop - st);
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Caclulate the sample value */
|
||||
dt=((dltdt*offset)>>16)+prevdt;
|
||||
|
||||
/* Write the data to the sample buffers */
|
||||
*lmix++ +=(dt*lvol)>>(5+5);
|
||||
*rmix++ +=(dt*rvol)>>(5+5);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* linear 8bit signed PCM */
|
||||
for(j=0;j<samples;j++)
|
||||
|
||||
if (cnt)
|
||||
{
|
||||
offset += delta;
|
||||
cnt = (offset>>16)&0x7fff;
|
||||
offset &= 0xffff;
|
||||
pos += cnt;
|
||||
/* Check for the end of the sample */
|
||||
if(pos >= sz)
|
||||
{
|
||||
/* Check if its a looping sample, either stop or loop */
|
||||
if( v->mode&0x10 )
|
||||
{
|
||||
pos = (v->sample_loop - st);
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key=0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if( cnt )
|
||||
{
|
||||
prevdt=lastdt;
|
||||
|
||||
if (m_banking_type == C140_TYPE::ASIC219)
|
||||
{
|
||||
lastdt = (int8_t) read_byte(sampleData + BYTE_XOR_BE(pos));
|
||||
|
||||
// Sign + magnitude format
|
||||
if ((v->mode & 0x01) && (lastdt & 0x80))
|
||||
lastdt = -(lastdt & 0x7f);
|
||||
|
||||
// Sign flip
|
||||
if (v->mode & 0x40)
|
||||
lastdt = -lastdt;
|
||||
}
|
||||
else
|
||||
{
|
||||
lastdt = (int8_t) read_byte(sampleData + pos);
|
||||
}
|
||||
|
||||
dltdt = (lastdt - prevdt);
|
||||
}
|
||||
|
||||
/* Caclulate the sample value */
|
||||
dt=((dltdt*offset)>>16)+prevdt;
|
||||
|
||||
/* Write the data to the sample buffers */
|
||||
*lmix++ +=(dt*lvol)>>5;
|
||||
*rmix++ +=(dt*rvol)>>5;
|
||||
prevdt = lastdt;
|
||||
lastdt = ((ch_mulaw(v)) ? m_pcmtbl[read_byte((sampleData + pos) << 1)] : s16(read_word((sampleData + pos) << 1) & 0xfff0)) >> 4; // 12bit
|
||||
dltdt = (lastdt - prevdt);
|
||||
}
|
||||
|
||||
/* Caclulate the sample value */
|
||||
dt = ((dltdt * offset) >> 16) + prevdt;
|
||||
|
||||
/* Write the data to the sample buffers */
|
||||
*lmix++ += (dt * lvol) >> (5 + 4);
|
||||
*rmix++ += (dt * rvol) >> (5 + 4);
|
||||
}
|
||||
|
||||
/* Save positional data for next callback */
|
||||
v->ptoffset=offset;
|
||||
v->pos=pos;
|
||||
v->lastdt=lastdt;
|
||||
v->prevdt=prevdt;
|
||||
v->dltdt=dltdt;
|
||||
v->ptoffset = offset;
|
||||
v->pos = pos;
|
||||
v->lastdt = lastdt;
|
||||
v->prevdt = prevdt;
|
||||
v->dltdt = dltdt;
|
||||
}
|
||||
}
|
||||
|
||||
@ -360,9 +325,146 @@ void c140_device::sound_stream_update(sound_stream &stream, stream_sample_t **in
|
||||
{
|
||||
stream_sample_t *dest1 = outputs[0];
|
||||
stream_sample_t *dest2 = outputs[1];
|
||||
for (i = 0; i < samples; i++)
|
||||
for (int i = 0; i < samples; i++)
|
||||
{
|
||||
int32_t val;
|
||||
s32 val;
|
||||
|
||||
val = 8 * (*lmix++);
|
||||
*dest1++ = limit(val);
|
||||
val = 8 * (*rmix++);
|
||||
*dest2++ = limit(val);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void c219_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
|
||||
{
|
||||
s32 dt;
|
||||
|
||||
float pbase = (float)m_baserate * 2.0f / (float)m_sample_rate;
|
||||
|
||||
s16 *lmix, *rmix;
|
||||
|
||||
if (samples > m_sample_rate) samples = m_sample_rate;
|
||||
|
||||
/* zap the contents of the mixer buffer */
|
||||
std::fill_n(&m_mixer_buffer_left[0], samples, 0);
|
||||
std::fill_n(&m_mixer_buffer_right[0], samples, 0);
|
||||
|
||||
//--- audio update
|
||||
for (int i = 0; i < 16; i++)
|
||||
{
|
||||
C140_VOICE *v = &m_voi[i];
|
||||
const struct voice_registers *vreg = (struct voice_registers *)&m_REG[i * 16];
|
||||
|
||||
if (v->key)
|
||||
{
|
||||
const u16 frequency = (vreg->frequency_msb << 8) | vreg->frequency_lsb;
|
||||
|
||||
/* Abort voice if no frequency value set */
|
||||
if (frequency == 0) continue;
|
||||
|
||||
/* Delta = frequency * ((8MHz/374)*2 / sample rate) */
|
||||
const int delta = (int)((float)frequency * pbase);
|
||||
|
||||
/* Calculate left/right channel volumes */
|
||||
const int lvol = (vreg->volume_left * 32) / MAX_VOICE; //32ch -> 24ch
|
||||
const int rvol = (vreg->volume_right * 32) / MAX_VOICE;
|
||||
|
||||
/* Set mixer outputs base pointers */
|
||||
lmix = m_mixer_buffer_left.get();
|
||||
rmix = m_mixer_buffer_right.get();
|
||||
|
||||
/* Retrieve sample start/end and calculate size */
|
||||
const int st = v->sample_start;
|
||||
const int ed = v->sample_end;
|
||||
const int sz = ed - st;
|
||||
|
||||
/* Retrieve base pointer to the sample data */
|
||||
const int sampleData = find_sample(st, v->bank, i);
|
||||
|
||||
/* Fetch back previous data pointers */
|
||||
int offset = v->ptoffset;
|
||||
int pos = v->pos;
|
||||
s32 lastdt = v->lastdt;
|
||||
s32 prevdt = v->prevdt;
|
||||
s32 dltdt = v->dltdt;
|
||||
|
||||
/* linear or compressed 8bit signed PCM */
|
||||
for (int j = 0; j < samples; j++)
|
||||
{
|
||||
offset += delta;
|
||||
const int cnt = (offset >> 16) & 0x7fff;
|
||||
offset &= 0xffff;
|
||||
pos += cnt;
|
||||
/* Check for the end of the sample */
|
||||
if (pos >= sz)
|
||||
{
|
||||
/* Check if its a looping sample, either stop or loop */
|
||||
if (ch_looped(v) || ch_noise(v))
|
||||
{
|
||||
pos = (v->sample_loop - st);
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
const int shift = ch_noise(v) ? 8 : 3;
|
||||
if (cnt)
|
||||
{
|
||||
prevdt = lastdt;
|
||||
|
||||
if (ch_noise(v)) // noise
|
||||
{
|
||||
m_lfsr = (m_lfsr >> 1) ^ ((-(m_lfsr & 1)) & 0xfff6);
|
||||
lastdt = s16(m_lfsr);
|
||||
}
|
||||
else
|
||||
{
|
||||
lastdt = s8(read_byte(sampleData + pos));
|
||||
// 11 bit mulaw
|
||||
if (ch_mulaw(v))
|
||||
lastdt = m_pcmtbl[lastdt & 0xff] >> 5;
|
||||
else
|
||||
lastdt <<= 3; // scale as 11bit
|
||||
}
|
||||
|
||||
// Sign flip
|
||||
if (ch_inv_sign(v))
|
||||
lastdt = -lastdt;
|
||||
|
||||
dltdt = (lastdt - prevdt);
|
||||
}
|
||||
|
||||
/* Caclulate the sample value */
|
||||
dt = ((dltdt * offset) >> 16) + prevdt;
|
||||
|
||||
/* Write the data to the sample buffers */
|
||||
*lmix++ += ((ch_inv_lout(v)) ? -(dt * lvol) : (dt * lvol)) >> (5 + shift);
|
||||
*rmix++ += (dt * rvol) >> (5 + shift);
|
||||
}
|
||||
|
||||
/* Save positional data for next callback */
|
||||
v->ptoffset = offset;
|
||||
v->pos = pos;
|
||||
v->lastdt = lastdt;
|
||||
v->prevdt = prevdt;
|
||||
v->dltdt = dltdt;
|
||||
}
|
||||
}
|
||||
|
||||
/* render to MAME's stream buffer */
|
||||
lmix = m_mixer_buffer_left.get();
|
||||
rmix = m_mixer_buffer_right.get();
|
||||
{
|
||||
stream_sample_t *dest1 = outputs[0];
|
||||
stream_sample_t *dest2 = outputs[1];
|
||||
for (int i = 0; i < samples; i++)
|
||||
{
|
||||
s32 val;
|
||||
|
||||
val = 8 * (*lmix++);
|
||||
*dest1++ = limit(val);
|
||||
@ -375,7 +477,7 @@ void c140_device::sound_stream_update(sound_stream &stream, stream_sample_t **in
|
||||
|
||||
u8 c140_device::c140_r(offs_t offset)
|
||||
{
|
||||
offset&=0x1ff;
|
||||
offset &= 0x1ff;
|
||||
return m_REG[offset];
|
||||
}
|
||||
|
||||
@ -384,58 +486,38 @@ void c140_device::c140_w(offs_t offset, u8 data)
|
||||
{
|
||||
m_stream->update();
|
||||
|
||||
offset&=0x1ff;
|
||||
offset &= 0x1ff;
|
||||
|
||||
// mirror the bank registers on the 219, fixes bkrtmaq (and probably xday2 based on notes in the HLE)
|
||||
if ((offset >= 0x1f8) && BIT(offset, 0) && (m_banking_type == C140_TYPE::ASIC219))
|
||||
m_REG[offset] = data;
|
||||
if (offset < 0x180)
|
||||
{
|
||||
offset -= 8;
|
||||
}
|
||||
const u8 ch = offset >> 4;
|
||||
C140_VOICE *v = &m_voi[ch];
|
||||
|
||||
m_REG[offset]=data;
|
||||
if( offset<0x180 )
|
||||
{
|
||||
C140_VOICE *v = &m_voi[offset>>4];
|
||||
|
||||
if( (offset&0xf)==0x5 )
|
||||
if ((offset & 0xf) == 0x5)
|
||||
{
|
||||
if( data&0x80 )
|
||||
if (data & 0x80)
|
||||
{
|
||||
const struct voice_registers *vreg = (struct voice_registers *) &m_REG[offset&0x1f0];
|
||||
v->key=1;
|
||||
v->ptoffset=0;
|
||||
v->pos=0;
|
||||
v->lastdt=0;
|
||||
v->prevdt=0;
|
||||
v->dltdt=0;
|
||||
const struct voice_registers *vreg = (struct voice_registers *) &m_REG[offset & 0x1f0];
|
||||
v->key = 1;
|
||||
v->ptoffset = 0;
|
||||
v->pos = 0;
|
||||
v->lastdt = 0;
|
||||
v->prevdt = 0;
|
||||
v->dltdt = 0;
|
||||
v->bank = vreg->bank;
|
||||
v->mode = data;
|
||||
|
||||
// on the 219 asic, addresses are in words
|
||||
if (m_banking_type == C140_TYPE::ASIC219)
|
||||
{
|
||||
v->sample_loop = (vreg->loop_msb*256 + vreg->loop_lsb)*2;
|
||||
v->sample_start = (vreg->start_msb*256 + vreg->start_lsb)*2;
|
||||
v->sample_end = (vreg->end_msb*256 + vreg->end_lsb)*2;
|
||||
|
||||
#if 0
|
||||
logerror("219: play v %d mode %02x start %x loop %x end %x\n",
|
||||
offset>>4, v->mode,
|
||||
find_sample(v->sample_start, v->bank, offset>>4),
|
||||
find_sample(v->sample_loop, v->bank, offset>>4),
|
||||
find_sample(v->sample_end, v->bank, offset>>4));
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
v->sample_loop = vreg->loop_msb*256 + vreg->loop_lsb;
|
||||
v->sample_start = vreg->start_msb*256 + vreg->start_lsb;
|
||||
v->sample_end = vreg->end_msb*256 + vreg->end_lsb;
|
||||
}
|
||||
const u32 loop = (vreg->loop_msb << 8) + vreg->loop_lsb;
|
||||
const u32 start = (vreg->start_msb << 8) + vreg->start_lsb;
|
||||
const u32 end = (vreg->end_msb << 8) + vreg->end_lsb;
|
||||
v->sample_loop = loop;
|
||||
v->sample_start = start;
|
||||
v->sample_end = end;
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key=0;
|
||||
v->key = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -466,61 +548,108 @@ void c140_device::c140_w(offs_t offset, u8 data)
|
||||
}
|
||||
|
||||
|
||||
u8 c219_device::c219_r(offs_t offset)
|
||||
{
|
||||
offset &= 0x1ff;
|
||||
return m_REG[offset];
|
||||
}
|
||||
|
||||
|
||||
void c219_device::c219_w(offs_t offset, u8 data)
|
||||
{
|
||||
m_stream->update();
|
||||
|
||||
offset &= 0x1ff;
|
||||
|
||||
// mirror the bank registers on the 219, fixes bkrtmaq (and probably xday2 based on notes in the HLE)
|
||||
if ((offset >= 0x1f8) && BIT(offset, 0))
|
||||
{
|
||||
offset -= 8;
|
||||
}
|
||||
|
||||
m_REG[offset] = data;
|
||||
if (offset < 0x100) // only 16 voices
|
||||
{
|
||||
const u8 ch = offset >> 4;
|
||||
C140_VOICE *v = &m_voi[ch];
|
||||
|
||||
if ((offset & 0xf) == 0x5)
|
||||
{
|
||||
if (data & 0x80)
|
||||
{
|
||||
const struct voice_registers *vreg = (struct voice_registers *) &m_REG[offset & 0x1f0];
|
||||
v->key = 1;
|
||||
v->ptoffset = 0;
|
||||
v->pos = 0;
|
||||
v->lastdt = 0;
|
||||
v->prevdt = 0;
|
||||
v->dltdt = 0;
|
||||
v->bank = vreg->bank;
|
||||
v->mode = data;
|
||||
|
||||
const u32 loop = (vreg->loop_msb << 8) + vreg->loop_lsb;
|
||||
const u32 start = (vreg->start_msb << 8) + vreg->start_lsb;
|
||||
const u32 end = (vreg->end_msb << 8) + vreg->end_lsb;
|
||||
// on the 219 asic, addresses are in words
|
||||
v->sample_loop = loop << 1;
|
||||
v->sample_start = start << 1;
|
||||
v->sample_end = end << 1;
|
||||
|
||||
#if 0
|
||||
logerror("219: play v %d mode %02x start %x loop %x end %x\n",
|
||||
ch, v->mode,
|
||||
find_sample(v->sample_start, v->bank, ch),
|
||||
find_sample(v->sample_loop, v->bank, ch),
|
||||
find_sample(v->sample_end, v->bank, ch));
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
v->key = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
// TODO: No interrupt/timers?
|
||||
}
|
||||
|
||||
TIMER_CALLBACK_MEMBER(c140_device::int1_on)
|
||||
{
|
||||
m_int1_callback(ASSERT_LINE);
|
||||
}
|
||||
|
||||
|
||||
void c140_device::init_voice( C140_VOICE *v )
|
||||
void c140_device::init_voice(C140_VOICE *v)
|
||||
{
|
||||
v->key=0;
|
||||
v->ptoffset=0;
|
||||
v->rvol=0;
|
||||
v->lvol=0;
|
||||
v->frequency=0;
|
||||
v->bank=0;
|
||||
v->mode=0;
|
||||
v->sample_start=0;
|
||||
v->sample_end=0;
|
||||
v->sample_loop=0;
|
||||
v->key = 0;
|
||||
v->ptoffset = 0;
|
||||
v->rvol = 0;
|
||||
v->lvol = 0;
|
||||
v->frequency = 0;
|
||||
v->bank = 0;
|
||||
v->mode = 0;
|
||||
v->sample_start = 0;
|
||||
v->sample_end = 0;
|
||||
v->sample_loop = 0;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
find_sample: compute the actual address of a sample given it's
|
||||
address and banking registers, as well as the board type.
|
||||
|
||||
I suspect in "real life" this works like the Sega MultiPCM where the banking
|
||||
is done by a small PAL or GAL external to the sound chip, which can be switched
|
||||
per-game or at least per-PCB revision as addressing range needs grow.
|
||||
address and banking registers, as well as the chip type.
|
||||
*/
|
||||
long c140_device::find_sample(long adrs, long bank, int voice)
|
||||
int c140_device::find_sample(int adrs, int bank, int voice)
|
||||
{
|
||||
long newadr = 0;
|
||||
adrs = (bank << 16) + adrs;
|
||||
|
||||
static const int16_t asic219banks[4] = { 0x1f7, 0x1f1, 0x1f3, 0x1f5 };
|
||||
|
||||
adrs=(bank<<16)+adrs;
|
||||
|
||||
switch (m_banking_type)
|
||||
{
|
||||
case C140_TYPE::SYSTEM2:
|
||||
// System 2 banking
|
||||
newadr = ((adrs&0x200000)>>2)|(adrs&0x7ffff);
|
||||
break;
|
||||
|
||||
case C140_TYPE::SYSTEM21:
|
||||
// System 21 banking.
|
||||
// similar to System 2's.
|
||||
newadr = ((adrs&0x300000)>>1)+(adrs&0x7ffff);
|
||||
break;
|
||||
|
||||
case C140_TYPE::ASIC219:
|
||||
// ASIC219's banking is fairly simple
|
||||
newadr = ((m_REG[asic219banks[voice/4]]&0x3) * 0x20000) + adrs;
|
||||
break;
|
||||
}
|
||||
|
||||
return (newadr);
|
||||
return adrs;
|
||||
}
|
||||
|
||||
int c219_device::find_sample(int adrs, int bank, int voice)
|
||||
{
|
||||
static const s16 asic219banks[4] = { 0x1f7, 0x1f1, 0x1f3, 0x1f5 };
|
||||
|
||||
adrs = (bank << 16) + adrs;
|
||||
|
||||
// ASIC219's banking is fairly simple
|
||||
return ((m_REG[asic219banks[voice / 4]] & 0x3) * 0x20000) + adrs;
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:R. Belmont
|
||||
/* C140.h */
|
||||
/* c140.h */
|
||||
|
||||
#ifndef MAME_SOUND_C140_H
|
||||
#define MAME_SOUND_C140_H
|
||||
@ -20,23 +20,21 @@ class c140_device : public device_t,
|
||||
public device_rom_interface
|
||||
{
|
||||
public:
|
||||
enum class C140_TYPE
|
||||
{
|
||||
SYSTEM2,
|
||||
SYSTEM21,
|
||||
ASIC219
|
||||
};
|
||||
|
||||
c140_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
|
||||
// configuration
|
||||
void set_bank_type(C140_TYPE bank) { m_banking_type = bank; }
|
||||
auto int1_callback() { return m_int1_callback.bind(); }
|
||||
|
||||
u8 c140_r(offs_t offset);
|
||||
void c140_w(offs_t offset, u8 data);
|
||||
|
||||
// little endian: Swap even and odd word
|
||||
u8 c140_le_r(offs_t offset) { return c140_r(offset ^ 1); }
|
||||
void c140_le_w(offs_t offset, u8 data) { c140_w(offset ^ 1, data);}
|
||||
|
||||
protected:
|
||||
c140_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock);
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_clock_changed() override;
|
||||
@ -46,34 +44,38 @@ protected:
|
||||
// sound stream update overrides
|
||||
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples) override;
|
||||
|
||||
private:
|
||||
virtual int find_sample(int adrs, int bank, int voice);
|
||||
|
||||
static constexpr unsigned MAX_VOICE = 24;
|
||||
|
||||
struct C140_VOICE
|
||||
{
|
||||
C140_VOICE() { }
|
||||
|
||||
int32_t ptoffset = 0;
|
||||
int32_t pos = 0;
|
||||
int32_t key = 0;
|
||||
s32 ptoffset = 0;
|
||||
s32 pos = 0;
|
||||
s32 key = 0;
|
||||
//--work
|
||||
int32_t lastdt = 0;
|
||||
int32_t prevdt = 0;
|
||||
int32_t dltdt = 0;
|
||||
s32 lastdt = 0;
|
||||
s32 prevdt = 0;
|
||||
s32 dltdt = 0;
|
||||
//--reg
|
||||
int32_t rvol = 0;
|
||||
int32_t lvol = 0;
|
||||
int32_t frequency = 0;
|
||||
int32_t bank = 0;
|
||||
int32_t mode = 0;
|
||||
s32 rvol = 0;
|
||||
s32 lvol = 0;
|
||||
s32 frequency = 0;
|
||||
s32 bank = 0;
|
||||
s32 mode = 0;
|
||||
|
||||
int32_t sample_start = 0;
|
||||
int32_t sample_end = 0;
|
||||
int32_t sample_loop = 0;
|
||||
s32 sample_start = 0;
|
||||
s32 sample_end = 0;
|
||||
s32 sample_loop = 0;
|
||||
};
|
||||
|
||||
void init_voice( C140_VOICE *v );
|
||||
long find_sample(long adrs, long bank, int voice);
|
||||
void init_voice(C140_VOICE *v);
|
||||
const inline bool ch_looped(C140_VOICE *v) { return BIT(v->mode, 4); } // shared as c140 and c219
|
||||
|
||||
virtual const inline bool ch_mulaw(C140_VOICE *v) { return BIT(v->mode, 3); }
|
||||
// bit 6 used, unknown
|
||||
|
||||
TIMER_CALLBACK_MEMBER(int1_on);
|
||||
|
||||
@ -81,21 +83,51 @@ private:
|
||||
|
||||
int m_sample_rate;
|
||||
sound_stream *m_stream;
|
||||
C140_TYPE m_banking_type;
|
||||
/* internal buffers */
|
||||
std::unique_ptr<int16_t[]> m_mixer_buffer_left;
|
||||
std::unique_ptr<int16_t[]> m_mixer_buffer_right;
|
||||
std::unique_ptr<s16[]> m_mixer_buffer_left;
|
||||
std::unique_ptr<s16[]> m_mixer_buffer_right;
|
||||
|
||||
int m_baserate;
|
||||
uint8_t m_REG[0x200];
|
||||
u8 m_REG[0x200];
|
||||
|
||||
int16_t m_pcmtbl[8]; //2000.06.26 CAB
|
||||
s16 m_pcmtbl[256]; //2000.06.26 CAB
|
||||
|
||||
C140_VOICE m_voi[MAX_VOICE];
|
||||
|
||||
emu_timer *m_int1_timer;
|
||||
};
|
||||
|
||||
class c219_device : public c140_device
|
||||
{
|
||||
public:
|
||||
c219_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
|
||||
u8 c219_r(offs_t offset);
|
||||
void c219_w(offs_t offset, u8 data);
|
||||
|
||||
// little endian: Swap even and odd word
|
||||
u8 c219_le_r(offs_t offset) { return c219_r(offset ^ 1); }
|
||||
void c219_le_w(offs_t offset, u8 data) { c219_w(offset ^ 1, data);}
|
||||
|
||||
protected:
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
|
||||
// sound stream update overrides
|
||||
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples) override;
|
||||
|
||||
virtual int find_sample(int adrs, int bank, int voice) override;
|
||||
|
||||
virtual const inline bool ch_mulaw(C140_VOICE *v) override { return BIT(v->mode, 0); }
|
||||
private:
|
||||
// bit 1 used, unknown
|
||||
const inline bool ch_noise(C140_VOICE *v) { return BIT(v->mode, 2); }
|
||||
const inline bool ch_inv_lout(C140_VOICE *v) { return BIT(v->mode, 3); }
|
||||
const inline bool ch_inv_sign(C140_VOICE *v) { return BIT(v->mode, 6); }
|
||||
u16 m_lfsr;
|
||||
};
|
||||
|
||||
DECLARE_DEVICE_TYPE(C140, c140_device)
|
||||
DECLARE_DEVICE_TYPE(C219, c219_device)
|
||||
|
||||
#endif // MAME_SOUND_C140_H
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#if C352_LOG_PCM
|
||||
#include <map>
|
||||
static std::map<uint32_t, bool> s_found_pcm;
|
||||
static std::map<u32, bool> s_found_pcm;
|
||||
#endif
|
||||
|
||||
// device type definition
|
||||
@ -41,7 +41,7 @@ DEFINE_DEVICE_TYPE(C352, c352_device, "c352", "Namco C352")
|
||||
// c352_device - constructor
|
||||
//-------------------------------------------------
|
||||
|
||||
c352_device::c352_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
|
||||
c352_device::c352_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock)
|
||||
: device_t(mconfig, C352, tag, owner, clock)
|
||||
, device_sound_interface(mconfig, *this)
|
||||
, device_rom_interface(mconfig, *this, 24)
|
||||
@ -69,14 +69,14 @@ void c352_device::fetch_sample(c352_voice_t& v)
|
||||
}
|
||||
else
|
||||
{
|
||||
int8_t s = (int8_t)read_byte(v.pos);
|
||||
s8 s = (s8)read_byte(v.pos);
|
||||
|
||||
if (v.flags & C352_FLG_MULAW)
|
||||
v.sample = m_mulawtab[s & 0xff];
|
||||
else
|
||||
v.sample = s << 8;
|
||||
|
||||
uint16_t pos = v.pos & 0xffff;
|
||||
u16 pos = v.pos & 0xffff;
|
||||
|
||||
if ((v.flags & C352_FLG_LOOP) && v.flags & C352_FLG_REVERSE)
|
||||
{
|
||||
@ -115,9 +115,9 @@ void c352_device::fetch_sample(c352_voice_t& v)
|
||||
}
|
||||
}
|
||||
|
||||
void c352_device::ramp_volume(c352_voice_t &v, int ch, uint8_t val)
|
||||
void c352_device::ramp_volume(c352_voice_t &v, int ch, u8 val)
|
||||
{
|
||||
int16_t vol_delta = v.curr_vol[ch] - val;
|
||||
s16 vol_delta = v.curr_vol[ch] - val;
|
||||
if (vol_delta != 0)
|
||||
v.curr_vol[ch] += (vol_delta > 0) ? -1 : 1;
|
||||
}
|
||||
@ -131,16 +131,16 @@ void c352_device::sound_stream_update(sound_stream &stream, stream_sample_t **in
|
||||
|
||||
for (int i = 0; i < samples; i++)
|
||||
{
|
||||
long out[4] = { 0, 0, 0, 0 };
|
||||
int out[4] = { 0, 0, 0, 0 };
|
||||
|
||||
for (int j = 0; j < 32; j++)
|
||||
{
|
||||
c352_voice_t &v = m_c352_v[j];
|
||||
int16_t s = 0;
|
||||
s16 s = 0;
|
||||
|
||||
if (v.flags & C352_FLG_BUSY)
|
||||
{
|
||||
int32_t next_counter = v.counter + v.freq;
|
||||
s32 next_counter = v.counter + v.freq;
|
||||
|
||||
if (next_counter & 0x10000)
|
||||
{
|
||||
@ -173,32 +173,32 @@ void c352_device::sound_stream_update(sound_stream &stream, stream_sample_t **in
|
||||
out[3] += (((v.flags & C352_FLG_PHASEFR) ? -s : s) * v.curr_vol[3]) >> 8;
|
||||
}
|
||||
|
||||
*buffer_fl++ = (int16_t)(out[0] >> 3);
|
||||
*buffer_fr++ = (int16_t)(out[1] >> 3);
|
||||
*buffer_rl++ = (int16_t)(out[2] >> 3);
|
||||
*buffer_rr++ = (int16_t)(out[3] >> 3);
|
||||
*buffer_fl++ = (s16)(out[0] >> 3);
|
||||
*buffer_fr++ = (s16)(out[1] >> 3);
|
||||
*buffer_rl++ = (s16)(out[2] >> 3);
|
||||
*buffer_rr++ = (s16)(out[3] >> 3);
|
||||
}
|
||||
}
|
||||
|
||||
uint16_t c352_device::read_reg16(unsigned long address)
|
||||
u16 c352_device::read_reg16(offs_t offset)
|
||||
{
|
||||
m_stream->update();
|
||||
|
||||
const int reg_map[8] =
|
||||
{
|
||||
offsetof(c352_voice_t, vol_f) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, vol_r) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, freq) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, flags) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_bank) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_start) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_end) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_loop) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, vol_f) / sizeof(u16),
|
||||
offsetof(c352_voice_t, vol_r) / sizeof(u16),
|
||||
offsetof(c352_voice_t, freq) / sizeof(u16),
|
||||
offsetof(c352_voice_t, flags) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_bank) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_start) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_end) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_loop) / sizeof(u16),
|
||||
};
|
||||
|
||||
if (address < 0x100)
|
||||
return *((uint16_t*)&m_c352_v[address / 8] + reg_map[address % 8]);
|
||||
else if (address == 0x200)
|
||||
if (offset < 0x100)
|
||||
return *((u16*)&m_c352_v[offset / 8] + reg_map[offset % 8]);
|
||||
else if (offset == 0x200)
|
||||
return m_control;
|
||||
else
|
||||
return 0;
|
||||
@ -206,33 +206,38 @@ uint16_t c352_device::read_reg16(unsigned long address)
|
||||
return 0;
|
||||
}
|
||||
|
||||
void c352_device::write_reg16(unsigned long address, unsigned short val)
|
||||
void c352_device::write_reg16(offs_t offset, u16 data, u16 mem_mask)
|
||||
{
|
||||
m_stream->update();
|
||||
|
||||
const int reg_map[8] =
|
||||
{
|
||||
offsetof(c352_voice_t, vol_f) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, vol_r) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, freq) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, flags) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_bank) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_start) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_end) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, wave_loop) / sizeof(uint16_t),
|
||||
offsetof(c352_voice_t, vol_f) / sizeof(u16),
|
||||
offsetof(c352_voice_t, vol_r) / sizeof(u16),
|
||||
offsetof(c352_voice_t, freq) / sizeof(u16),
|
||||
offsetof(c352_voice_t, flags) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_bank) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_start) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_end) / sizeof(u16),
|
||||
offsetof(c352_voice_t, wave_loop) / sizeof(u16),
|
||||
};
|
||||
|
||||
if (address < 0x100)
|
||||
if (offset < 0x100)
|
||||
{
|
||||
*((uint16_t*)&m_c352_v[address / 8] + reg_map[address % 8]) = val;
|
||||
u16 newval = read_reg16(offset);
|
||||
COMBINE_DATA(&newval);
|
||||
*((u16*)&m_c352_v[offset / 8] + reg_map[offset % 8]) = newval;
|
||||
}
|
||||
else if (address == 0x200)
|
||||
else if (offset == 0x200)
|
||||
{
|
||||
m_control = val;
|
||||
logerror("C352 control register write: %04x\n",val);
|
||||
COMBINE_DATA(&m_control);
|
||||
logerror("C352 control register write: %04x & %04x\n", data, mem_mask);
|
||||
}
|
||||
else if (address == 0x202) // execute keyons/keyoffs
|
||||
else if (offset == 0x202) // execute keyons/keyoffs
|
||||
{
|
||||
if (mem_mask != 0xffff) // 16 bit only?
|
||||
return;
|
||||
|
||||
for (int i = 0; i < 32; i++)
|
||||
{
|
||||
if (m_c352_v[i].flags & C352_FLG_KEYON)
|
||||
@ -252,7 +257,7 @@ void c352_device::write_reg16(unsigned long address, unsigned short val)
|
||||
#if C352_LOG_PCM
|
||||
if (!(m_c352_v[i].flags & C352_FLG_NOISE))
|
||||
{
|
||||
std::map<uint32_t, bool>::iterator iter = s_found_pcm.find(m_c352_v[i].pos);
|
||||
std::map<u32, bool>::iterator iter = s_found_pcm.find(m_c352_v[i].pos);
|
||||
if (iter != s_found_pcm.end())
|
||||
{
|
||||
return;
|
||||
@ -266,27 +271,27 @@ void c352_device::write_reg16(unsigned long address, unsigned short val)
|
||||
if (file != nullptr)
|
||||
{
|
||||
c352_voice_t &v = m_c352_v[i];
|
||||
uint32_t pos = v.pos;
|
||||
uint32_t flags = v.flags;
|
||||
uint32_t counter = v.counter;
|
||||
int16_t sample = 0;
|
||||
u32 pos = v.pos;
|
||||
u32 flags = v.flags;
|
||||
u32 counter = v.counter;
|
||||
s16 sample = 0;
|
||||
|
||||
while (pos != v.wave_end && !(flags & C352_FLG_KEYOFF))
|
||||
{
|
||||
int32_t next_counter = counter + v.freq;
|
||||
s32 next_counter = counter + v.freq;
|
||||
|
||||
if (next_counter & 0x10000)
|
||||
{
|
||||
counter = next_counter & 0xffff;
|
||||
|
||||
int8_t s = (int8_t)read_byte(pos);
|
||||
s8 s = (s8)read_byte(pos);
|
||||
|
||||
if (v.flags & C352_FLG_MULAW)
|
||||
sample = m_mulawtab[s & 0xff];
|
||||
else
|
||||
sample = s << 8;
|
||||
|
||||
uint16_t subpos = pos & 0xffff;
|
||||
u16 subpos = pos & 0xffff;
|
||||
|
||||
if ((flags & C352_FLG_LOOP) && flags & C352_FLG_REVERSE)
|
||||
{
|
||||
@ -382,22 +387,20 @@ void c352_device::device_start()
|
||||
m_mulawtab[i + 128] = (~m_mulawtab[i]) & 0xffe0;
|
||||
|
||||
// register save state info
|
||||
for (int i = 0; i < 32; i++)
|
||||
{
|
||||
save_item(NAME(m_c352_v[i].pos), i);
|
||||
save_item(NAME(m_c352_v[i].counter), i);
|
||||
save_item(NAME(m_c352_v[i].sample), i);
|
||||
save_item(NAME(m_c352_v[i].last_sample), i);
|
||||
save_item(NAME(m_c352_v[i].vol_f), i);
|
||||
save_item(NAME(m_c352_v[i].vol_r), i);
|
||||
save_item(NAME(m_c352_v[i].curr_vol), i);
|
||||
save_item(NAME(m_c352_v[i].freq), i);
|
||||
save_item(NAME(m_c352_v[i].flags), i);
|
||||
save_item(NAME(m_c352_v[i].wave_bank), i);
|
||||
save_item(NAME(m_c352_v[i].wave_start), i);
|
||||
save_item(NAME(m_c352_v[i].wave_end), i);
|
||||
save_item(NAME(m_c352_v[i].wave_loop), i);
|
||||
}
|
||||
save_item(STRUCT_MEMBER(m_c352_v, pos));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, counter));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, sample));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, last_sample));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, vol_f));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, vol_r));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, curr_vol));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, freq));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, flags));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, wave_bank));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, wave_start));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, wave_end));
|
||||
save_item(STRUCT_MEMBER(m_c352_v, wave_loop));
|
||||
|
||||
save_item(NAME(m_random));
|
||||
save_item(NAME(m_control));
|
||||
}
|
||||
@ -419,12 +422,5 @@ READ16_MEMBER( c352_device::read )
|
||||
|
||||
WRITE16_MEMBER( c352_device::write )
|
||||
{
|
||||
if (mem_mask == 0xffff)
|
||||
{
|
||||
write_reg16(offset, data);
|
||||
}
|
||||
else
|
||||
{
|
||||
logerror("C352: byte-wide write unsupported at this time!\n");
|
||||
}
|
||||
write_reg16(offset, data, mem_mask);
|
||||
}
|
||||
|
@ -18,13 +18,13 @@ class c352_device : public device_t,
|
||||
{
|
||||
public:
|
||||
// construction/destruction
|
||||
c352_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock, int divider)
|
||||
c352_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock, int divider)
|
||||
: c352_device(mconfig, tag, owner, clock)
|
||||
{
|
||||
set_divider(divider);
|
||||
}
|
||||
|
||||
c352_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
|
||||
c352_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
|
||||
void set_divider(int divider) { m_divider = divider; }
|
||||
|
||||
@ -67,31 +67,31 @@ private:
|
||||
|
||||
struct c352_voice_t
|
||||
{
|
||||
uint32_t pos;
|
||||
uint32_t counter;
|
||||
u32 pos;
|
||||
u32 counter;
|
||||
|
||||
int16_t sample;
|
||||
int16_t last_sample;
|
||||
s16 sample;
|
||||
s16 last_sample;
|
||||
|
||||
uint16_t vol_f;
|
||||
uint16_t vol_r;
|
||||
uint8_t curr_vol[4];
|
||||
u16 vol_f;
|
||||
u16 vol_r;
|
||||
u8 curr_vol[4];
|
||||
|
||||
uint16_t freq;
|
||||
uint16_t flags;
|
||||
u16 freq;
|
||||
u16 flags;
|
||||
|
||||
uint16_t wave_bank;
|
||||
uint16_t wave_start;
|
||||
uint16_t wave_end;
|
||||
uint16_t wave_loop;
|
||||
u16 wave_bank;
|
||||
u16 wave_start;
|
||||
u16 wave_end;
|
||||
u16 wave_loop;
|
||||
|
||||
};
|
||||
|
||||
void fetch_sample(c352_voice_t &v);
|
||||
void ramp_volume(c352_voice_t &v, int ch, uint8_t val);
|
||||
void ramp_volume(c352_voice_t &v, int ch, u8 val);
|
||||
|
||||
unsigned short read_reg16(unsigned long address);
|
||||
void write_reg16(unsigned long address, unsigned short val);
|
||||
u16 read_reg16(offs_t offset);
|
||||
void write_reg16(offs_t offset, u16 data, u16 mem_mask = 0);
|
||||
|
||||
sound_stream *m_stream;
|
||||
|
||||
@ -100,10 +100,10 @@ private:
|
||||
|
||||
c352_voice_t m_c352_v[32];
|
||||
|
||||
int16_t m_mulawtab[256];
|
||||
s16 m_mulawtab[256];
|
||||
|
||||
uint16_t m_random;
|
||||
uint16_t m_control; // control flags, purpose unknown.
|
||||
u16 m_random;
|
||||
u16 m_control; // control flags, purpose unknown.
|
||||
};
|
||||
|
||||
|
||||
|
@ -16,8 +16,6 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "machine/rescap.h"
|
||||
|
||||
/*
|
||||
* ATARI Pokey (CO12294) pin-out
|
||||
*
|
||||
|
@ -661,17 +661,17 @@ void scn2674_device::write_delayed_command(uint8_t data)
|
||||
{
|
||||
case 0xa4:
|
||||
// read at pointer address
|
||||
m_char_buffer = m_char_space->read_byte(m_screen2_address);
|
||||
m_char_buffer = m_char_space->read_byte(m_display_pointer_address);
|
||||
if (m_attr_space != nullptr)
|
||||
m_attr_buffer = m_attr_space->read_byte(m_screen2_address);
|
||||
m_attr_buffer = m_attr_space->read_byte(m_display_pointer_address);
|
||||
LOGMASKED(LOG_COMMAND, "%s: DELAYED read at pointer address %02x\n", machine().describe_context(), data);
|
||||
break;
|
||||
|
||||
case 0xa2:
|
||||
// write at pointer address
|
||||
m_char_space->write_byte(m_screen2_address, m_char_buffer);
|
||||
m_char_space->write_byte(m_display_pointer_address, m_char_buffer);
|
||||
if (m_attr_space != nullptr)
|
||||
m_attr_space->write_byte(m_screen2_address, m_attr_buffer);
|
||||
m_attr_space->write_byte(m_display_pointer_address, m_attr_buffer);
|
||||
LOGMASKED(LOG_COMMAND, "%s: DELAYED write at pointer address %02x\n", machine().describe_context(), data);
|
||||
break;
|
||||
|
||||
@ -730,7 +730,7 @@ void scn2674_device::write_delayed_command(uint8_t data)
|
||||
m_display_enabled = false;
|
||||
m_display_enabled_field = true;
|
||||
m_display_enabled_scanline = false;
|
||||
for (i = m_cursor_address; i != m_screen2_address; i = ((i + 1) & 0xffff))
|
||||
for (i = m_cursor_address; i != m_display_pointer_address; i = ((i + 1) & 0xffff))
|
||||
{
|
||||
m_char_space->write_byte(i, m_char_buffer);
|
||||
if (m_attr_space != nullptr)
|
||||
@ -739,7 +739,7 @@ void scn2674_device::write_delayed_command(uint8_t data)
|
||||
m_char_space->write_byte(i, m_char_buffer); // get the last
|
||||
if (m_attr_space != nullptr)
|
||||
m_attr_space->write_byte(i, m_attr_buffer);
|
||||
m_cursor_address = m_screen2_address;
|
||||
m_cursor_address = m_display_pointer_address;
|
||||
LOGMASKED(LOG_COMMAND, "%s: DELAYED write from cursor address to pointer address %02x\n", machine().describe_context(), data);
|
||||
break;
|
||||
|
||||
@ -963,15 +963,30 @@ void scn2674_device::write(offs_t offset, uint8_t data)
|
||||
break;
|
||||
|
||||
case 6:
|
||||
m_screen2_address = (m_screen2_address & 0x3f00) | data;
|
||||
break;
|
||||
|
||||
case 7:
|
||||
write_screen2_address(BIT(offset, 0), data);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void scn2674_device::write_screen2_address(bool msb, uint8_t data)
|
||||
{
|
||||
if (msb)
|
||||
{
|
||||
m_screen2_address = (m_screen2_address & 0x00ff) | (data & 0x3f) << 8;
|
||||
m_spl[0] = BIT(data, 6);
|
||||
m_spl[1] = BIT(data, 7);
|
||||
break;
|
||||
}
|
||||
else
|
||||
m_screen2_address = (m_screen2_address & 0x3f00) | data;
|
||||
}
|
||||
|
||||
void scn2672_device::write_screen2_address(bool msb, uint8_t data)
|
||||
{
|
||||
if (msb)
|
||||
m_display_pointer_address = (m_display_pointer_address & 0x00ff) | (data & 0x3f) << 8;
|
||||
else
|
||||
m_display_pointer_address = (m_display_pointer_address & 0x3f00) | data;
|
||||
}
|
||||
|
||||
void scn2674_device::recompute_parameters()
|
||||
|
@ -119,6 +119,7 @@ protected:
|
||||
void write_interrupt_mask(bool enabled, uint8_t bits);
|
||||
void write_delayed_command(uint8_t data);
|
||||
void write_command(uint8_t data);
|
||||
virtual void write_screen2_address(bool msb, uint8_t data);
|
||||
|
||||
void recompute_parameters();
|
||||
|
||||
@ -141,6 +142,7 @@ public:
|
||||
|
||||
protected:
|
||||
virtual void write_init_regs(uint8_t data) override;
|
||||
virtual void write_screen2_address(bool msb, uint8_t data) override;
|
||||
};
|
||||
|
||||
|
||||
|
116
src/devices/video/sed1500.cpp
Normal file
116
src/devices/video/sed1500.cpp
Normal file
@ -0,0 +1,116 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:hap
|
||||
/*
|
||||
|
||||
Epson SED1500 series LCD Driver
|
||||
128 bytes internal RAM.
|
||||
|
||||
SED1500: 8 commons, 42 segments
|
||||
SED1501: 10 commons, 40 segments
|
||||
SED1502: 16 commons, 34 segments
|
||||
SED1503: 8 commons, 42 segments, needs multiple of 2 chips to function
|
||||
|
||||
The default input OSC frequency is 32768Hz, the frame output frequency is
|
||||
divided by 64 and by number of commons, eg. 64Hz on a SED1500.
|
||||
|
||||
TODO:
|
||||
- bus mode (only mode 3 now)
|
||||
- EI pin (master/slave mode)
|
||||
- SYNC pin, used for frame synchronizing if multiple chips are used
|
||||
- SED1503 only has 8 COM pins, the extra 8 outputs are from the slave chip
|
||||
|
||||
*/
|
||||
|
||||
#include "emu.h"
|
||||
#include "video/sed1500.h"
|
||||
|
||||
|
||||
DEFINE_DEVICE_TYPE(SED1500, sed1500_device, "sed1500", "Epson SED1500 LCD Driver")
|
||||
DEFINE_DEVICE_TYPE(SED1501, sed1501_device, "sed1501", "Epson SED1501 LCD Driver")
|
||||
DEFINE_DEVICE_TYPE(SED1502, sed1502_device, "sed1502", "Epson SED1502 LCD Driver")
|
||||
DEFINE_DEVICE_TYPE(SED1503, sed1503_device, "sed1503", "Epson SED1503 LCD Driver")
|
||||
|
||||
//-------------------------------------------------
|
||||
// constructor
|
||||
//-------------------------------------------------
|
||||
|
||||
sed1500_device::sed1500_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u8 cmax, u8 smax) :
|
||||
device_t(mconfig, type, tag, owner, clock),
|
||||
m_cmax(cmax), m_smax(smax),
|
||||
m_write_segs(*this)
|
||||
{ }
|
||||
|
||||
sed1500_device::sed1500_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) :
|
||||
sed1500_device(mconfig, SED1500, tag, owner, clock, 8, 42)
|
||||
{ }
|
||||
|
||||
sed1501_device::sed1501_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) :
|
||||
sed1500_device(mconfig, SED1501, tag, owner, clock, 10, 40)
|
||||
{ }
|
||||
|
||||
sed1502_device::sed1502_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) :
|
||||
sed1500_device(mconfig, SED1502, tag, owner, clock, 16, 34)
|
||||
{ }
|
||||
|
||||
sed1503_device::sed1503_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) :
|
||||
sed1500_device(mconfig, SED1503, tag, owner, clock, 8+8, 42)
|
||||
{ }
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// device_start - device-specific startup
|
||||
//-------------------------------------------------
|
||||
|
||||
void sed1500_device::device_start()
|
||||
{
|
||||
memset(m_ram, 0, sizeof(m_ram));
|
||||
|
||||
// resolve callbacks
|
||||
m_write_segs.resolve_safe();
|
||||
|
||||
// timer
|
||||
m_lcd_timer = timer_alloc();
|
||||
attotime period = attotime::from_hz(clock() / 64);
|
||||
m_lcd_timer->adjust(period, 0, period);
|
||||
|
||||
// register for savestates
|
||||
save_item(NAME(m_mode));
|
||||
save_item(NAME(m_cout));
|
||||
save_item(NAME(m_ram));
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------------------
|
||||
// handlers
|
||||
//-------------------------------------------------
|
||||
|
||||
void sed1500_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
|
||||
{
|
||||
u64 data = 0;
|
||||
|
||||
for (int i = m_smax-1; i >= 0; i--)
|
||||
data = data << 1 | BIT(m_ram[i | 0x40] << 8 | m_ram[i], m_cout);
|
||||
|
||||
// transfer segments to output
|
||||
m_write_segs(m_cout, data);
|
||||
m_cout = (m_cout + 1) % m_cmax;
|
||||
}
|
||||
|
||||
void sed1500_device::write(offs_t offset, u8 data)
|
||||
{
|
||||
offset &= 0x7f;
|
||||
m_ram[offset] = data;
|
||||
|
||||
// bus mode command:
|
||||
// 0 = 4-bit addr, 4-bit data, combined
|
||||
// 1 = 7-bit addr, 4-bit data, separate
|
||||
// 2 = 7-bit addr, 8-bit data, combined
|
||||
// 3 = 7-bit addr, 8-bit data, separate
|
||||
if ((offset & 0x3f) == 0x3f && ~data & 1)
|
||||
m_mode = data >> 1 & 3;
|
||||
}
|
||||
|
||||
u8 sed1500_device::read(offs_t offset)
|
||||
{
|
||||
return m_ram[offset & 0x7f];
|
||||
}
|
85
src/devices/video/sed1500.h
Normal file
85
src/devices/video/sed1500.h
Normal file
@ -0,0 +1,85 @@
|
||||
// license:BSD-3-Clause
|
||||
// copyright-holders:hap
|
||||
/*
|
||||
|
||||
Epson SED1500 series LCD Driver
|
||||
|
||||
*/
|
||||
|
||||
#ifndef MAME_VIDEO_SED1500_H
|
||||
#define MAME_VIDEO_SED1500_H
|
||||
|
||||
#pragma once
|
||||
|
||||
/*
|
||||
|
||||
pinout reference (brief)
|
||||
|
||||
OSC: oscillator (resistors or XTAL)
|
||||
A0-A6: address
|
||||
D0-D7: data (I/O)
|
||||
WR/RD: write/read signal
|
||||
CS: chip select
|
||||
SYNC: frame synchronize (I/O)
|
||||
|
||||
CL: OSC output
|
||||
COM: LCD commons
|
||||
SEG: LCD segments
|
||||
|
||||
*/
|
||||
|
||||
class sed1500_device : public device_t
|
||||
{
|
||||
public:
|
||||
sed1500_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
|
||||
// configuration helpers
|
||||
auto write_segs() { return m_write_segs.bind(); } // common number in offset, segment data in data
|
||||
|
||||
void write(offs_t offset, u8 data);
|
||||
u8 read(offs_t offset);
|
||||
|
||||
protected:
|
||||
sed1500_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u8 cmax, u8 smax);
|
||||
|
||||
// device-level overrides
|
||||
virtual void device_start() override;
|
||||
virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override;
|
||||
|
||||
emu_timer *m_lcd_timer;
|
||||
|
||||
const u8 m_cmax; // number of COL pins
|
||||
const u8 m_smax; // number of SEG pins
|
||||
u8 m_mode = 0;
|
||||
u8 m_cout = 0;
|
||||
u8 m_ram[0x80];
|
||||
|
||||
// callbacks
|
||||
devcb_write64 m_write_segs;
|
||||
};
|
||||
|
||||
class sed1501_device : public sed1500_device
|
||||
{
|
||||
public:
|
||||
sed1501_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
};
|
||||
|
||||
class sed1502_device : public sed1500_device
|
||||
{
|
||||
public:
|
||||
sed1502_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
};
|
||||
|
||||
class sed1503_device : public sed1500_device
|
||||
{
|
||||
public:
|
||||
sed1503_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock);
|
||||
};
|
||||
|
||||
|
||||
DECLARE_DEVICE_TYPE(SED1500, sed1500_device)
|
||||
DECLARE_DEVICE_TYPE(SED1501, sed1501_device)
|
||||
DECLARE_DEVICE_TYPE(SED1502, sed1502_device)
|
||||
DECLARE_DEVICE_TYPE(SED1503, sed1503_device)
|
||||
|
||||
#endif // MAME_VIDEO_SED1500_H
|
@ -153,3 +153,20 @@ const char *attotime::as_string(int precision) const
|
||||
}
|
||||
return buffer;
|
||||
}
|
||||
|
||||
//-------------------------------------------------
|
||||
// to_string - return a human-readable string
|
||||
// describing an attotime for use in logs
|
||||
//-------------------------------------------------
|
||||
|
||||
std::string attotime::to_string() const
|
||||
{
|
||||
attotime t = *this;
|
||||
const char *sign = "";
|
||||
if(t.seconds() < 0) {
|
||||
t = attotime::zero-t;
|
||||
sign = "-";
|
||||
}
|
||||
int nsec = t.attoseconds() / ATTOSECONDS_PER_NANOSECOND;
|
||||
return util::string_format("%s%04d.%03d,%03d,%03d", sign, int(t.seconds()), nsec/1000000, (nsec/1000)%1000, nsec % 1000);
|
||||
}
|
||||
|
@ -122,6 +122,9 @@ public:
|
||||
/** Convert to string using at @p precision */
|
||||
const char *as_string(int precision = 9) const;
|
||||
|
||||
/** Convert to string for human readability in logs */
|
||||
std::string to_string() const;
|
||||
|
||||
/** @return the attoseconds portion. */
|
||||
constexpr attoseconds_t attoseconds() const noexcept { return m_attoseconds; }
|
||||
/** @return the seconds portion. */
|
||||
|
@ -157,8 +157,8 @@ debugger_commands::debugger_commands(running_machine& machine, debugger_cpu& cpu
|
||||
m_console.register_command("gv", CMDFLAG_NONE, 0, 0, 0, std::bind(&debugger_commands::execute_go_vblank, this, _1, _2));
|
||||
m_console.register_command("gint", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_interrupt, this, _1, _2));
|
||||
m_console.register_command("gi", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_interrupt, this, _1, _2));
|
||||
m_console.register_command("gex", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_exception, this, _1, _2));
|
||||
m_console.register_command("ge", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_exception, this, _1, _2));
|
||||
m_console.register_command("gex", CMDFLAG_NONE, 0, 0, 2, std::bind(&debugger_commands::execute_go_exception, this, _1, _2));
|
||||
m_console.register_command("ge", CMDFLAG_NONE, 0, 0, 2, std::bind(&debugger_commands::execute_go_exception, this, _1, _2));
|
||||
m_console.register_command("gtime", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_time, this, _1, _2));
|
||||
m_console.register_command("gt", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_time, this, _1, _2));
|
||||
m_console.register_command("gp", CMDFLAG_NONE, 0, 0, 1, std::bind(&debugger_commands::execute_go_privilege, this, _1, _2));
|
||||
@ -899,7 +899,11 @@ void debugger_commands::execute_go_exception(int ref, const std::vector<std::str
|
||||
if (params.size() > 0 && !validate_number_parameter(params[0], exception))
|
||||
return;
|
||||
|
||||
m_cpu.get_visible_cpu()->debug()->go_exception(exception);
|
||||
parsed_expression condition(m_cpu.get_visible_cpu()->debug()->symtable());
|
||||
if (params.size() > 1 && !debug_command_parameter_expression(params[1], condition))
|
||||
return;
|
||||
|
||||
m_cpu.get_visible_cpu()->debug()->go_exception(exception, (condition.is_empty()) ? "1" : condition.original_string());
|
||||
}
|
||||
|
||||
|
||||
|
@ -1146,8 +1146,15 @@ void debugger_cpu::start_hook(device_t *device, bool stop_on_vblank)
|
||||
assert(m_livecpu == nullptr);
|
||||
m_livecpu = device;
|
||||
|
||||
// can't stop on a device without a state interface
|
||||
if (m_execution_state == exec_state::STOPPED && dynamic_cast<device_state_interface *>(device) == nullptr)
|
||||
{
|
||||
if (m_stop_when_not_device == nullptr)
|
||||
m_stop_when_not_device = device;
|
||||
m_execution_state = exec_state::RUNNING;
|
||||
}
|
||||
// if we're a new device, stop now
|
||||
if (m_stop_when_not_device != nullptr && m_stop_when_not_device != device)
|
||||
else if (m_stop_when_not_device != nullptr && m_stop_when_not_device != device && device->debug()->observing())
|
||||
{
|
||||
m_stop_when_not_device = nullptr;
|
||||
m_execution_state = exec_state::STOPPED;
|
||||
@ -1163,7 +1170,7 @@ void debugger_cpu::start_hook(device_t *device, bool stop_on_vblank)
|
||||
m_machine.debug_view().flush_osd_updates();
|
||||
m_last_periodic_update_time = osd_ticks();
|
||||
}
|
||||
else if (device == m_breakcpu)
|
||||
if (device == m_breakcpu)
|
||||
{ // check for pending breaks
|
||||
m_execution_state = exec_state::STOPPED;
|
||||
m_breakcpu = nullptr;
|
||||
@ -1183,7 +1190,10 @@ void debugger_cpu::start_hook(device_t *device, bool stop_on_vblank)
|
||||
}
|
||||
// check for debug keypresses
|
||||
if (m_machine.ui_input().pressed(IPT_UI_DEBUG_BREAK))
|
||||
{
|
||||
m_visiblecpu->debug()->ignore(false);
|
||||
m_visiblecpu->debug()->halt_on_next_instruction("User-initiated break\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1191,6 +1201,13 @@ void debugger_cpu::stop_hook(device_t *device)
|
||||
{
|
||||
assert(m_livecpu == device);
|
||||
|
||||
// if we are supposed to be stopped at this point (most likely because of a watchpoint), keep going until this CPU is live again
|
||||
if (m_execution_state == exec_state::STOPPED)
|
||||
{
|
||||
m_breakcpu = device;
|
||||
m_execution_state = exec_state::RUNNING;
|
||||
}
|
||||
|
||||
// clear the live CPU
|
||||
m_livecpu = nullptr;
|
||||
}
|
||||
@ -1492,9 +1509,25 @@ void device_debug::exception_hook(int exception)
|
||||
// see if this matches an exception breakpoint
|
||||
if ((m_flags & DEBUG_FLAG_STOP_EXCEPTION) != 0 && (m_stopexception == -1 || m_stopexception == exception))
|
||||
{
|
||||
m_device.machine().debugger().cpu().set_execution_stopped();
|
||||
m_device.machine().debugger().console().printf("Stopped on exception (CPU '%s', exception %d)\n", m_device.tag(), exception);
|
||||
compute_debug_flags();
|
||||
bool matched = true;
|
||||
if (m_exception_condition && !m_exception_condition->is_empty())
|
||||
{
|
||||
try
|
||||
{
|
||||
matched = m_exception_condition->execute();
|
||||
}
|
||||
catch (expression_error &)
|
||||
{
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (matched)
|
||||
{
|
||||
m_device.machine().debugger().cpu().set_execution_stopped();
|
||||
m_device.machine().debugger().console().printf("Stopped on exception (CPU '%s', exception %d, PC=%X)\n", m_device.tag(), exception, m_state->pcbase());
|
||||
compute_debug_flags();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1506,18 +1539,18 @@ void device_debug::exception_hook(int exception)
|
||||
|
||||
void device_debug::privilege_hook()
|
||||
{
|
||||
bool matched = 1;
|
||||
|
||||
if ((m_flags & DEBUG_FLAG_STOP_PRIVILEGE) != 0)
|
||||
{
|
||||
bool matched = true;
|
||||
if (m_privilege_condition && !m_privilege_condition->is_empty())
|
||||
{
|
||||
try
|
||||
{
|
||||
matched = m_privilege_condition->execute();
|
||||
}
|
||||
catch (...)
|
||||
catch (expression_error &)
|
||||
{
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
@ -1840,12 +1873,13 @@ void device_debug::go_next_device()
|
||||
// exception fires on the visible CPU
|
||||
//-------------------------------------------------
|
||||
|
||||
void device_debug::go_exception(int exception)
|
||||
void device_debug::go_exception(int exception, const char *condition)
|
||||
{
|
||||
assert(m_exec != nullptr);
|
||||
|
||||
m_device.machine().rewind_invalidate();
|
||||
m_stopexception = exception;
|
||||
m_exception_condition = std::make_unique<parsed_expression>(m_symtable, condition);
|
||||
m_flags |= DEBUG_FLAG_STOP_EXCEPTION;
|
||||
m_device.machine().debugger().cpu().set_execution_running();
|
||||
}
|
||||
@ -2956,6 +2990,7 @@ void device_debug::watchpoint::triggered(read_or_write type, offs_t address, u64
|
||||
}
|
||||
|
||||
// halt in the debugger by default
|
||||
bool was_stopped = debug.cpu().is_stopped();
|
||||
debug.cpu().set_execution_stopped();
|
||||
|
||||
// evaluate the action
|
||||
@ -2965,19 +3000,28 @@ void device_debug::watchpoint::triggered(read_or_write type, offs_t address, u64
|
||||
// print a notification, unless the action made us go again
|
||||
if (debug.cpu().is_stopped())
|
||||
{
|
||||
offs_t pc = m_space.device().state().pcbase();
|
||||
std::string buffer;
|
||||
|
||||
buffer = string_format(type == read_or_write::READ ?
|
||||
"Stopped at watchpoint %X reading %0*X from %08X (PC=%X)" :
|
||||
"Stopped at watchpoint %X writing %0*X to %08X (PC=%X)",
|
||||
"Stopped at watchpoint %X reading %0*X from %08X" :
|
||||
"Stopped at watchpoint %X writing %0*X to %08X",
|
||||
m_index,
|
||||
size * unit_size / 4,
|
||||
data,
|
||||
address,
|
||||
pc);
|
||||
debug.console().printf("%s\n", buffer);
|
||||
m_debugInterface->compute_debug_flags();
|
||||
address);
|
||||
|
||||
if (debug.cpu().live_cpu() == &m_space.device())
|
||||
{
|
||||
offs_t pc = m_space.device().state().pcbase();
|
||||
debug.console().printf("%s (PC=%X)\n", buffer, pc);
|
||||
m_debugInterface->compute_debug_flags();
|
||||
}
|
||||
else if (!was_stopped)
|
||||
{
|
||||
debug.console().printf("%s\n", buffer);
|
||||
debug.cpu().set_execution_running();
|
||||
debug.cpu().set_break_cpu(&m_space.device());
|
||||
}
|
||||
m_debugInterface->set_triggered_watchpoint(this);
|
||||
}
|
||||
|
||||
|
@ -201,7 +201,7 @@ public:
|
||||
void go(offs_t targetpc = ~0);
|
||||
void go_vblank();
|
||||
void go_interrupt(int irqline = -1);
|
||||
void go_exception(int exception);
|
||||
void go_exception(int exception, const char *condition);
|
||||
void go_milliseconds(u64 milliseconds);
|
||||
void go_privilege(const char *condition);
|
||||
void go_next_device();
|
||||
@ -320,6 +320,7 @@ private:
|
||||
int m_stopirq; // stop IRQ number for DEBUG_FLAG_STOP_INTERRUPT
|
||||
int m_stopexception; // stop exception number for DEBUG_FLAG_STOP_EXCEPTION
|
||||
std::unique_ptr<parsed_expression> m_privilege_condition; // expression to evaluate on privilege change
|
||||
std::unique_ptr<parsed_expression> m_exception_condition; // expression to evaluate on exception hit
|
||||
attotime m_endexectime; // ending time of the current execution
|
||||
u64 m_total_cycles; // current total cycles
|
||||
u64 m_last_total_cycles; // last total cycles
|
||||
|
@ -137,7 +137,7 @@ static const help_item static_help_list[] =
|
||||
" o[ver] [<count>=1] -- single steps over <count> instructions (F10)\n"
|
||||
" out -- single steps until the current subroutine/exception handler is exited (Shift-F11)\n"
|
||||
" g[o] [<address>] -- resumes execution, sets temp breakpoint at <address> (F5)\n"
|
||||
" ge[x] [<exception>] -- resumes execution, setting temp breakpoint if <exception> is raised\n"
|
||||
" ge[x] [<exception>[,<condition>]] -- resumes execution, setting temp breakpoint if <exception> is raised\n"
|
||||
" gi[nt] [<irqline>] -- resumes execution, setting temp breakpoint if <irqline> is taken (F7)\n"
|
||||
" gt[ime] <milliseconds> -- resumes execution until the given delay has elapsed\n"
|
||||
" gv[blank] -- resumes execution, setting temp breakpoint on the next VBLANK (F8)\n"
|
||||
|
@ -195,7 +195,7 @@ void device_image_interface::set_image_filename(const std::string &filename)
|
||||
auto iter = std::find_if(
|
||||
m_image_name.rbegin(),
|
||||
m_image_name.rend(),
|
||||
[](char c) { return (c == '\\') || (c == '/') || (c == ':'); });
|
||||
[](char c) { return (c == '\\') || (c == '/'); });
|
||||
|
||||
if (iter != m_image_name.rend())
|
||||
m_basename.assign(iter.base(), m_image_name.end());
|
||||
|
@ -644,32 +644,33 @@ void natural_keyboard::build_codes(ioport_manager &manager)
|
||||
{
|
||||
if (((code < UCHAR_SHIFT_BEGIN) || (code > UCHAR_SHIFT_END)) && (code != 0))
|
||||
{
|
||||
// prefer lowest shift state
|
||||
keycode_map::iterator const found(m_keycode_map.find(code));
|
||||
if ((m_keycode_map.end() == found) || (found->second.shift > curshift))
|
||||
keycode_map_entry newcode;
|
||||
std::fill(std::begin(newcode.field), std::end(newcode.field), nullptr);
|
||||
newcode.shift = curshift;
|
||||
newcode.condition = field.condition();
|
||||
|
||||
unsigned fieldnum = 0;
|
||||
for (unsigned i = 0, bits = curshift; (i < SHIFT_COUNT) && bits; ++i, bits >>= 1)
|
||||
{
|
||||
keycode_map_entry newcode;
|
||||
std::fill(std::begin(newcode.field), std::end(newcode.field), nullptr);
|
||||
newcode.shift = curshift;
|
||||
if (BIT(bits, 0))
|
||||
newcode.field[fieldnum++] = shift[i];
|
||||
}
|
||||
|
||||
unsigned fieldnum = 0;
|
||||
for (unsigned i = 0, bits = curshift; (i < SHIFT_COUNT) && bits; ++i, bits >>= 1)
|
||||
{
|
||||
if (BIT(bits, 0))
|
||||
newcode.field[fieldnum++] = shift[i];
|
||||
}
|
||||
newcode.field[fieldnum] = &field;
|
||||
if (m_keycode_map.end() == found)
|
||||
{
|
||||
keycode_map_list map_list;
|
||||
map_list.emplace_back(newcode);
|
||||
m_keycode_map.emplace(code, map_list);
|
||||
}
|
||||
else
|
||||
found->second.emplace_back(newcode);
|
||||
|
||||
newcode.field[fieldnum] = &field;
|
||||
if (m_keycode_map.end() == found)
|
||||
m_keycode_map.emplace(code, newcode);
|
||||
else
|
||||
found->second = newcode;
|
||||
|
||||
if (LOG_NATURAL_KEYBOARD)
|
||||
{
|
||||
machine().logerror("natural_keyboard: code=%u (%s) port=%p field.name='%s'\n",
|
||||
code, unicode_to_string(code), (void *)&port, field.name());
|
||||
}
|
||||
if (LOG_NATURAL_KEYBOARD)
|
||||
{
|
||||
machine().logerror("natural_keyboard: code=%u (%s) port=%p field.name='%s'\n",
|
||||
code, unicode_to_string(code), (void *)&port, field.name());
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -879,7 +880,13 @@ std::string natural_keyboard::unicode_to_string(char32_t ch) const
|
||||
const natural_keyboard::keycode_map_entry *natural_keyboard::find_code(char32_t ch) const
|
||||
{
|
||||
keycode_map::const_iterator const found(m_keycode_map.find(ch));
|
||||
return (m_keycode_map.end() != found) ? &found->second : nullptr;
|
||||
if (m_keycode_map.end() == found) return nullptr;
|
||||
for(const keycode_map_entry &entry : found->second)
|
||||
{
|
||||
if (entry.condition.eval())
|
||||
return &entry;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
||||
@ -901,13 +908,16 @@ void natural_keyboard::dump(std::ostream &str) const
|
||||
// pad with spaces
|
||||
util::stream_format(str, "%-*s", left_column_width, description);
|
||||
|
||||
// identify the keys used
|
||||
for (std::size_t field = 0; (code.second.field.size() > field) && code.second.field[field]; ++field)
|
||||
util::stream_format(str, "%s'%s'", first ? "" : ", ", code.second.field[field]->name());
|
||||
for (auto &entry : code.second)
|
||||
{
|
||||
// identify the keys used
|
||||
for (std::size_t field = 0; (entry.field.size() > field) && entry.field[field]; ++field)
|
||||
util::stream_format(str, "%s'%s'", first ? "" : ", ", entry.field[field]->name());
|
||||
|
||||
// carriage return
|
||||
str << '\n';
|
||||
first = false;
|
||||
// carriage return
|
||||
str << '\n';
|
||||
first = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -74,8 +74,10 @@ private:
|
||||
{
|
||||
std::array<ioport_field *, SHIFT_COUNT + 1> field;
|
||||
unsigned shift;
|
||||
ioport_condition condition;
|
||||
};
|
||||
typedef std::unordered_map<char32_t, keycode_map_entry> keycode_map;
|
||||
typedef std::list<keycode_map_entry> keycode_map_list;
|
||||
typedef std::unordered_map<char32_t, keycode_map_list> keycode_map;
|
||||
|
||||
// internal helpers
|
||||
void build_codes(ioport_manager &manager);
|
||||
|
@ -24,17 +24,6 @@
|
||||
|
||||
#define TIMER_CALLBACK_MEMBER(name) void name(void *ptr, s32 param)
|
||||
|
||||
// macro for the RC time constant on a 74LS123 with C > 1000pF
|
||||
// R is in ohms, C is in farads
|
||||
#define TIME_OF_74LS123(r,c) (0.45 * (double)(r) * (double)(c))
|
||||
|
||||
// macros for the RC time constant on a 555 timer IC
|
||||
// R is in ohms, C is in farads
|
||||
#define PERIOD_OF_555_MONOSTABLE_NSEC(r,c) ((attoseconds_t)(1100000000 * (double)(r) * (double)(c)))
|
||||
#define PERIOD_OF_555_ASTABLE_NSEC(r1,r2,c) ((attoseconds_t)( 693000000 * ((double)(r1) + 2.0 * (double)(r2)) * (double)(c)))
|
||||
#define PERIOD_OF_555_MONOSTABLE(r,c) attotime::from_nsec(PERIOD_OF_555_MONOSTABLE_NSEC(r,c))
|
||||
#define PERIOD_OF_555_ASTABLE(r1,r2,c) attotime::from_nsec(PERIOD_OF_555_ASTABLE_NSEC(r1,r2,c))
|
||||
|
||||
|
||||
//**************************************************************************
|
||||
// TYPE DEFINITIONS
|
||||
|
@ -243,6 +243,7 @@ const double XTAL::known_xtals[] = {
|
||||
16'128'000, /* 16.128_MHz_XTAL Fujitsu FM-7 */
|
||||
16'200'000, /* 16.2_MHz_XTAL Debut */
|
||||
16'257'000, /* 16.257_MHz_XTAL IBM PC MDA & EGA */
|
||||
16'313'000, /* 16.313_MHz_XTAL Micro-Term ERGO 201 */
|
||||
16'364'000, /* 16.364_MHz_XTAL Corvus Concept */
|
||||
16'384'000, /* 16.384_MHz_XTAL - */
|
||||
16'400'000, /* 16.4_MHz_XTAL MS 6102 */
|
||||
|
@ -615,7 +615,6 @@ void hfe_format::generate_hfe_bitstream_from_track(int cyl, int head, int& sampl
|
||||
// Start of track? Use next entry.
|
||||
if (edge==0)
|
||||
{
|
||||
cur_pos = 0;
|
||||
edge = tbuf[++cur_entry] & floppy_image::TIME_MASK;
|
||||
}
|
||||
|
||||
@ -671,10 +670,6 @@ void hfe_format::generate_hfe_bitstream_from_track(int cyl, int head, int& sampl
|
||||
}
|
||||
|
||||
cur_pos = next;
|
||||
if(cur_pos >= 200000000) {
|
||||
cur_pos -= 200000000;
|
||||
cur_entry = 0;
|
||||
}
|
||||
|
||||
bit = (bit << 1) & 0xff;
|
||||
if (bit == 0)
|
||||
|
14
src/lib/netlist/.gitignore
vendored
14
src/lib/netlist/.gitignore
vendored
@ -5,8 +5,18 @@ buildVS/x64/*
|
||||
buildVS/.vs/*
|
||||
nltool
|
||||
nlwav
|
||||
nltool.exe
|
||||
nlwav.exe
|
||||
|
||||
# Windows executables
|
||||
*.exe
|
||||
|
||||
# Local doxygen binaries
|
||||
doxygen
|
||||
doxyindexer
|
||||
doxysearch.cgi
|
||||
|
||||
# nltool/nlwav output files
|
||||
*.log
|
||||
*.wav
|
||||
|
||||
# VS 2019
|
||||
*.user
|
@ -97,27 +97,26 @@ namespace analog
|
||||
/// | | FC | coefficient for forward-bias depletion capacitance formula | - | 0.5 | | |
|
||||
/// | | TNOM | Parameter measurement temperature | C | 27 | 50 | |
|
||||
///
|
||||
class bjt_model_t : public param_model_t
|
||||
class bjt_model_t
|
||||
{
|
||||
public:
|
||||
bjt_model_t(device_t &device, const pstring &name, const pstring &val)
|
||||
: param_model_t(device, name, val)
|
||||
, m_IS (*this, "IS")
|
||||
, m_BF (*this, "BF")
|
||||
, m_NF (*this, "NF")
|
||||
, m_BR (*this, "BR")
|
||||
, m_NR (*this, "NR")
|
||||
, m_CJE(*this, "CJE")
|
||||
, m_CJC(*this, "CJC")
|
||||
bjt_model_t(param_model_t &model)
|
||||
: m_IS (model, "IS")
|
||||
, m_BF (model, "BF")
|
||||
, m_NF (model, "NF")
|
||||
, m_BR (model, "BR")
|
||||
, m_NR (model, "NR")
|
||||
, m_CJE(model, "CJE")
|
||||
, m_CJC(model, "CJC")
|
||||
{}
|
||||
|
||||
value_t m_IS; //!< transport saturation current
|
||||
value_t m_BF; //!< ideal maximum forward beta
|
||||
value_t m_NF; //!< forward current emission coefficient
|
||||
value_t m_BR; //!< ideal maximum reverse beta
|
||||
value_t m_NR; //!< reverse current emission coefficient
|
||||
value_t m_CJE; //!< B-E zero-bias depletion capacitance
|
||||
value_t m_CJC; //!< B-C zero-bias depletion capacitance
|
||||
param_model_t::value_t m_IS; //!< transport saturation current
|
||||
param_model_t::value_t m_BF; //!< ideal maximum forward beta
|
||||
param_model_t::value_t m_NF; //!< forward current emission coefficient
|
||||
param_model_t::value_t m_BR; //!< ideal maximum reverse beta
|
||||
param_model_t::value_t m_NR; //!< reverse current emission coefficient
|
||||
param_model_t::value_t m_CJE; //!< B-E zero-bias depletion capacitance
|
||||
param_model_t::value_t m_CJC; //!< B-C zero-bias depletion capacitance
|
||||
|
||||
};
|
||||
|
||||
@ -147,7 +146,7 @@ namespace analog
|
||||
void set_qtype(q_type atype) noexcept { m_qtype = atype; }
|
||||
protected:
|
||||
|
||||
bjt_model_t m_model;
|
||||
param_model_t m_model;
|
||||
private:
|
||||
q_type m_qtype;
|
||||
};
|
||||
@ -179,7 +178,7 @@ namespace analog
|
||||
, m_gB(nlconst::cgmin())
|
||||
, m_gC(nlconst::cgmin())
|
||||
, m_V(nlconst::zero())
|
||||
, m_state_on(*this, "m_state_on", 0)
|
||||
, m_state_on(*this, "m_state_on", 0u)
|
||||
{
|
||||
register_subalias("B", m_RB.P());
|
||||
register_subalias("E", m_RB.N());
|
||||
@ -216,6 +215,7 @@ namespace analog
|
||||
{
|
||||
public:
|
||||
NETLIB_CONSTRUCTOR_DERIVED(QBJT_EB, QBJT)
|
||||
, m_modacc(m_model)
|
||||
, m_gD_BC(*this, "m_D_BC")
|
||||
, m_gD_BE(*this, "m_D_BE")
|
||||
, m_D_CB(*this, "m_D_CB", true)
|
||||
@ -233,13 +233,13 @@ namespace analog
|
||||
connect(m_D_EB.N(), m_D_CB.N());
|
||||
connect(m_D_CB.P(), m_D_EC.N());
|
||||
|
||||
if (m_model.m_CJE > nlconst::zero())
|
||||
if (m_modacc.m_CJE > nlconst::zero())
|
||||
{
|
||||
create_and_register_subdevice("m_CJE", m_CJE);
|
||||
connect("B", "m_CJE.1");
|
||||
connect("E", "m_CJE.2");
|
||||
}
|
||||
if (m_model.m_CJC > nlconst::zero())
|
||||
if (m_modacc.m_CJC > nlconst::zero())
|
||||
{
|
||||
create_and_register_subdevice("m_CJC", m_CJC);
|
||||
connect("B", "m_CJC.1");
|
||||
@ -256,6 +256,7 @@ namespace analog
|
||||
NETLIB_UPDATE_TERMINALSI();
|
||||
|
||||
private:
|
||||
bjt_model_t m_modacc;
|
||||
generic_diode<diode_e::BIPOLAR> m_gD_BC;
|
||||
generic_diode<diode_e::BIPOLAR> m_gD_BE;
|
||||
|
||||
@ -313,11 +314,14 @@ namespace analog
|
||||
|
||||
NETLIB_UPDATE_PARAM(QBJT_switch)
|
||||
{
|
||||
nl_fptype IS = m_model.m_IS;
|
||||
nl_fptype BF = m_model.m_BF;
|
||||
nl_fptype NF = m_model.m_NF;
|
||||
//nl_fptype VJE = m_model.dValue("VJE", 0.75);
|
||||
bjt_model_t model(m_model);
|
||||
|
||||
nl_fptype IS = model.m_IS;
|
||||
nl_fptype BF = model.m_BF;
|
||||
nl_fptype NF = model.m_NF;
|
||||
//nl_fptype VJE = model.dValue("VJE", 0.75);
|
||||
|
||||
// FIXME: check for PNP as well and bail out
|
||||
set_qtype((m_model.type() == "NPN") ? BJT_NPN : BJT_PNP);
|
||||
|
||||
nl_fptype alpha = BF / (nlconst::one() + BF);
|
||||
@ -382,12 +386,12 @@ namespace analog
|
||||
if (m_CJE)
|
||||
{
|
||||
m_CJE->reset();
|
||||
m_CJE->set_cap_embedded(m_model.m_CJE);
|
||||
m_CJE->set_cap_embedded(m_modacc.m_CJE);
|
||||
}
|
||||
if (m_CJC)
|
||||
{
|
||||
m_CJC->reset();
|
||||
m_CJC->set_cap_embedded(m_model.m_CJC);
|
||||
m_CJC->set_cap_embedded(m_modacc.m_CJC);
|
||||
}
|
||||
|
||||
}
|
||||
@ -421,13 +425,14 @@ namespace analog
|
||||
|
||||
NETLIB_UPDATE_PARAM(QBJT_EB)
|
||||
{
|
||||
nl_fptype IS = m_model.m_IS;
|
||||
nl_fptype BF = m_model.m_BF;
|
||||
nl_fptype NF = m_model.m_NF;
|
||||
nl_fptype BR = m_model.m_BR;
|
||||
nl_fptype NR = m_model.m_NR;
|
||||
nl_fptype IS = m_modacc.m_IS;
|
||||
nl_fptype BF = m_modacc.m_BF;
|
||||
nl_fptype NF = m_modacc.m_NF;
|
||||
nl_fptype BR = m_modacc.m_BR;
|
||||
nl_fptype NR = m_modacc.m_NR;
|
||||
//nl_fptype VJE = m_model.dValue("VJE", 0.75);
|
||||
|
||||
// FIXME: check for PNP as well and bail out
|
||||
set_qtype((m_model.type() == "NPN") ? BJT_NPN : BJT_PNP);
|
||||
|
||||
m_alpha_f = BF / (nlconst::one() + BF);
|
||||
|
@ -15,7 +15,7 @@
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
#define VCCS(name, G) \
|
||||
NET_REGISTER_DEVEXT(VCCS, G)
|
||||
NET_REGISTER_DEVEXT(VCCS, name, G)
|
||||
|
||||
#define CCCS(name, G) \
|
||||
NET_REGISTER_DEVEXT(CCCS, name, G)
|
||||
|
@ -95,53 +95,52 @@ namespace analog
|
||||
/// | Y |W | Width scaling |-|100e-6||
|
||||
///
|
||||
|
||||
class fet_model_t : public param_model_t
|
||||
class fet_model_t
|
||||
{
|
||||
public:
|
||||
fet_model_t(device_t &device, const pstring &name, const pstring &val)
|
||||
: param_model_t(device, name, val)
|
||||
, m_VTO(*this, "VTO")
|
||||
, m_N(*this, "N")
|
||||
, m_ISS(*this, "IS") // Haven't seen a model using ISS / ISD
|
||||
, m_ISD(*this, "IS")
|
||||
, m_LD(*this, "LD")
|
||||
, m_L(*this, "L")
|
||||
, m_W(*this, "W")
|
||||
, m_TOX(*this, "TOX")
|
||||
, m_KP(*this, "KP")
|
||||
, m_UO(*this, "UO")
|
||||
, m_PHI(*this, "PHI")
|
||||
, m_NSUB(*this, "NSUB")
|
||||
, m_GAMMA(*this, "GAMMA")
|
||||
, m_LAMBDA(*this, "LAMBDA")
|
||||
, m_RD(*this, "RD")
|
||||
, m_RS(*this, "RS")
|
||||
, m_CGSO(*this, "CGSO")
|
||||
, m_CGDO(*this, "CGDO")
|
||||
, m_CGBO(*this, "CGBO")
|
||||
, m_CAPMOD(*this, "CAPMOD")
|
||||
fet_model_t(param_model_t &model)
|
||||
: m_VTO(model, "VTO")
|
||||
, m_N(model, "N")
|
||||
, m_ISS(model, "IS") // Haven't seen a model using ISS / ISD
|
||||
, m_ISD(model, "IS")
|
||||
, m_LD(model, "LD")
|
||||
, m_L(model, "L")
|
||||
, m_W(model, "W")
|
||||
, m_TOX(model, "TOX")
|
||||
, m_KP(model, "KP")
|
||||
, m_UO(model, "UO")
|
||||
, m_PHI(model, "PHI")
|
||||
, m_NSUB(model, "NSUB")
|
||||
, m_GAMMA(model, "GAMMA")
|
||||
, m_LAMBDA(model, "LAMBDA")
|
||||
, m_RD(model, "RD")
|
||||
, m_RS(model, "RS")
|
||||
, m_CGSO(model, "CGSO")
|
||||
, m_CGDO(model, "CGDO")
|
||||
, m_CGBO(model, "CGBO")
|
||||
, m_CAPMOD(model, "CAPMOD")
|
||||
{}
|
||||
|
||||
value_t m_VTO; //!< Threshold voltage [V]
|
||||
value_t m_N; //!< Bulk diode emission coefficient
|
||||
value_t m_ISS; //!< Body diode saturation current
|
||||
value_t m_ISD; //!< Body diode saturation current
|
||||
value_t m_LD; //!< Lateral diffusion [m]
|
||||
value_t m_L; //!< Length scaling
|
||||
value_t m_W; //!< Width scaling
|
||||
value_t m_TOX; //!< Oxide thickness
|
||||
value_t m_KP; //!< Transconductance parameter [A/V²]
|
||||
value_t m_UO; //!< Surface mobility [cm²/V/s]
|
||||
value_t m_PHI; //!< Surface inversion potential [V]
|
||||
value_t m_NSUB; //!< Substrate doping [1/cm³]
|
||||
value_t m_GAMMA; //!< Bulk threshold parameter [V^½]
|
||||
value_t m_LAMBDA; //!< Channel-length modulation [1/V]
|
||||
value_t m_RD; //!< Drain ohmic resistance
|
||||
value_t m_RS; //!< Source ohmic resistance
|
||||
value_t m_CGSO; //!< Gate-source overlap capacitance per meter channel width
|
||||
value_t m_CGDO; //!< Gate-drain overlap capacitance per meter channel width
|
||||
value_t m_CGBO; //!< Gate-bulk overlap capacitance per meter channel width
|
||||
value_base_t<int> m_CAPMOD; //!< Capacitance model (0=no model 2=Meyer)
|
||||
param_model_t::value_t m_VTO; //!< Threshold voltage [V]
|
||||
param_model_t::value_t m_N; //!< Bulk diode emission coefficient
|
||||
param_model_t::value_t m_ISS; //!< Body diode saturation current
|
||||
param_model_t::value_t m_ISD; //!< Body diode saturation current
|
||||
param_model_t::value_t m_LD; //!< Lateral diffusion [m]
|
||||
param_model_t::value_t m_L; //!< Length scaling
|
||||
param_model_t::value_t m_W; //!< Width scaling
|
||||
param_model_t::value_t m_TOX; //!< Oxide thickness
|
||||
param_model_t::value_t m_KP; //!< Transconductance parameter [A/V²]
|
||||
param_model_t::value_t m_UO; //!< Surface mobility [cm²/V/s]
|
||||
param_model_t::value_t m_PHI; //!< Surface inversion potential [V]
|
||||
param_model_t::value_t m_NSUB; //!< Substrate doping [1/cm³]
|
||||
param_model_t::value_t m_GAMMA; //!< Bulk threshold parameter [V^½]
|
||||
param_model_t::value_t m_LAMBDA; //!< Channel-length modulation [1/V]
|
||||
param_model_t::value_t m_RD; //!< Drain ohmic resistance
|
||||
param_model_t::value_t m_RS; //!< Source ohmic resistance
|
||||
param_model_t::value_t m_CGSO; //!< Gate-source overlap capacitance per meter channel width
|
||||
param_model_t::value_t m_CGDO; //!< Gate-drain overlap capacitance per meter channel width
|
||||
param_model_t::value_t m_CGBO; //!< Gate-bulk overlap capacitance per meter channel width
|
||||
param_model_t::value_base_t<int> m_CAPMOD; //!< Capacitance model (0=no model 2=Meyer)
|
||||
};
|
||||
|
||||
// Have a common start for mosfets
|
||||
@ -170,7 +169,7 @@ namespace analog
|
||||
void set_qtype(q_type atype) noexcept { m_qtype = atype; }
|
||||
protected:
|
||||
|
||||
fet_model_t m_model;
|
||||
param_model_t m_model;
|
||||
private:
|
||||
q_type m_qtype;
|
||||
};
|
||||
@ -207,6 +206,7 @@ namespace analog
|
||||
, m_capmod(2)
|
||||
, m_Vgs(*this, "m_Vgs", nlconst::zero())
|
||||
, m_Vgd(*this, "m_Vgd", nlconst::zero())
|
||||
, m_modacc(m_model)
|
||||
{
|
||||
register_subalias("S", m_SG.P()); // Source
|
||||
register_subalias("G", m_SG.N()); // Gate
|
||||
@ -220,8 +220,8 @@ namespace analog
|
||||
set_qtype((m_model.type() == "NMOS_DEFAULT") ? FET_NMOS : FET_PMOS);
|
||||
m_polarity = (qtype() == FET_NMOS ? nlconst::one() : -nlconst::one());
|
||||
|
||||
m_capmod = m_model.m_CAPMOD;
|
||||
// printf("capmod %d %g %g\n", m_capmod, (nl_fptype)m_model.m_VTO, m_polarity);
|
||||
m_capmod = m_modacc.m_CAPMOD;
|
||||
// printf("capmod %d %g %g\n", m_capmod, (nl_fptype)m_modacc.m_VTO, m_polarity);
|
||||
nl_assert_always(m_capmod == 0 || m_capmod == 2, "Error: CAPMODEL invalid value");
|
||||
|
||||
//
|
||||
@ -234,51 +234,51 @@ namespace analog
|
||||
// But couldn't find a formula for lambda anywhere
|
||||
//
|
||||
|
||||
m_lambda = m_model.m_LAMBDA; // FIXME: m_lambda only set once
|
||||
m_lambda = m_modacc.m_LAMBDA; // FIXME: m_lambda only set once
|
||||
|
||||
// calculate effective channel length
|
||||
m_Leff = m_model.m_L - 2 * m_model.m_LD;
|
||||
m_Leff = m_modacc.m_L - 2 * m_modacc.m_LD;
|
||||
nl_assert_always(m_Leff > nlconst::zero(), "Effective Lateral diffusion would be negative for model");
|
||||
|
||||
nl_fptype Cox = (m_model.m_TOX > nlconst::zero()) ? (constants::eps_SiO2() * constants::eps_0() / m_model.m_TOX) : nlconst::zero();
|
||||
nl_fptype Cox = (m_modacc.m_TOX > nlconst::zero()) ? (constants::eps_SiO2() * constants::eps_0() / m_modacc.m_TOX) : nlconst::zero();
|
||||
|
||||
// calculate DC transconductance coefficient
|
||||
if (m_model.m_KP > nlconst::zero())
|
||||
m_beta = m_model.m_KP * m_model.m_W / m_Leff;
|
||||
else if (Cox > nlconst::zero() && m_model.m_UO > nlconst::zero())
|
||||
m_beta = m_model.m_UO * nlconst::magic(1e-4) * Cox * m_model.m_W / m_Leff;
|
||||
if (m_modacc.m_KP > nlconst::zero())
|
||||
m_beta = m_modacc.m_KP * m_modacc.m_W / m_Leff;
|
||||
else if (Cox > nlconst::zero() && m_modacc.m_UO > nlconst::zero())
|
||||
m_beta = m_modacc.m_UO * nlconst::magic(1e-4) * Cox * m_modacc.m_W / m_Leff;
|
||||
else
|
||||
m_beta = nlconst::magic(2e-5) * m_model.m_W / m_Leff;
|
||||
m_beta = nlconst::magic(2e-5) * m_modacc.m_W / m_Leff;
|
||||
|
||||
//FIXME::UT can disappear
|
||||
const nl_fptype Vt = constants::T0() * constants::k_b() / constants::Q_e();
|
||||
|
||||
// calculate surface potential if not given
|
||||
|
||||
if (m_model.m_PHI > nlconst::zero())
|
||||
m_phi = m_model.m_PHI;
|
||||
else if (m_model.m_NSUB > nlconst::zero())
|
||||
if (m_modacc.m_PHI > nlconst::zero())
|
||||
m_phi = m_modacc.m_PHI;
|
||||
else if (m_modacc.m_NSUB > nlconst::zero())
|
||||
{
|
||||
nl_assert_always(m_model.m_NSUB * nlconst::magic(1e6) >= constants::NiSi(), "Error calculating phi for model");
|
||||
m_phi = nlconst::two() * Vt * plib::log (m_model.m_NSUB * nlconst::magic(1e6) / constants::NiSi());
|
||||
nl_assert_always(m_modacc.m_NSUB * nlconst::magic(1e6) >= constants::NiSi(), "Error calculating phi for model");
|
||||
m_phi = nlconst::two() * Vt * plib::log (m_modacc.m_NSUB * nlconst::magic(1e6) / constants::NiSi());
|
||||
}
|
||||
else
|
||||
m_phi = nlconst::magic(0.6);
|
||||
|
||||
// calculate bulk threshold if not given
|
||||
if (m_model.m_GAMMA > nlconst::zero())
|
||||
m_gamma = m_model.m_GAMMA;
|
||||
if (m_modacc.m_GAMMA > nlconst::zero())
|
||||
m_gamma = m_modacc.m_GAMMA;
|
||||
else
|
||||
{
|
||||
if (Cox > nlconst::zero() && m_model.m_NSUB > nlconst::zero())
|
||||
if (Cox > nlconst::zero() && m_modacc.m_NSUB > nlconst::zero())
|
||||
m_gamma = plib::sqrt (nlconst::two()
|
||||
* constants::Q_e() * constants::eps_Si() * constants::eps_0()
|
||||
* m_model.m_NSUB * nlconst::magic(1e6)) / Cox;
|
||||
* m_modacc.m_NSUB * nlconst::magic(1e6)) / Cox;
|
||||
else
|
||||
m_gamma = nlconst::zero();
|
||||
}
|
||||
|
||||
m_vto = m_model.m_VTO;
|
||||
m_vto = m_modacc.m_VTO;
|
||||
// FIXME zero conversion
|
||||
if(m_vto != nlconst::zero())
|
||||
log().warning(MW_MOSFET_THRESHOLD_VOLTAGE(m_model.name()));
|
||||
@ -286,7 +286,7 @@ namespace analog
|
||||
// FIXME: VTO if missing may be calculated from TPG, NSS and temperature. Usually models
|
||||
// specify VTO so skip this here.
|
||||
|
||||
m_CoxWL = Cox * m_model.m_W * m_Leff;
|
||||
m_CoxWL = Cox * m_modacc.m_W * m_Leff;
|
||||
|
||||
//printf("Cox: %g\n", m_Cox);
|
||||
}
|
||||
@ -317,9 +317,9 @@ namespace analog
|
||||
NETLIB_NAME(FET)::reset();
|
||||
// Bulk diodes
|
||||
|
||||
m_D_BD.set_param(m_model.m_ISD, m_model.m_N, exec().gmin(), constants::T0());
|
||||
m_D_BD.set_param(m_modacc.m_ISD, m_modacc.m_N, exec().gmin(), constants::T0());
|
||||
#if (!BODY_CONNECTED_TO_SOURCE)
|
||||
m_D_BS.set_param(m_model.m_ISS, m_model.m_N, exec().gmin(), constants::T0());
|
||||
m_D_BS.set_param(m_modacc.m_ISS, m_modacc.m_N, exec().gmin(), constants::T0());
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -362,6 +362,7 @@ namespace analog
|
||||
int m_capmod;
|
||||
state_var<nl_fptype> m_Vgs;
|
||||
state_var<nl_fptype> m_Vgd;
|
||||
fet_model_t m_modacc;
|
||||
|
||||
void set_cap(generic_capacitor<capacitor_e::VARIABLE_CAPACITY> cap,
|
||||
nl_fptype capval, nl_fptype V,
|
||||
@ -573,9 +574,9 @@ namespace analog
|
||||
else
|
||||
calculate_caps(Vgd, Vgs, Vth, m_Cgd, m_Cgs, m_Cgb);
|
||||
|
||||
set_cap(m_cap_gb, m_Cgb + m_model.m_CGBO * m_Leff, Vgb, gGG, gGB, gBG, gBB, IG, IB);
|
||||
set_cap(m_cap_gs, m_Cgs + m_model.m_CGSO * m_model.m_W, Vgs, gGG, gGS, gSG, gSS, IG, IS);
|
||||
set_cap(m_cap_gd, m_Cgd + m_model.m_CGDO * m_model.m_W, Vgd, gGG, gGD, gDG, gDD, IG, ID);
|
||||
set_cap(m_cap_gb, m_Cgb + m_modacc.m_CGBO * m_Leff, Vgb, gGG, gGB, gBG, gBB, IG, IB);
|
||||
set_cap(m_cap_gs, m_Cgs + m_modacc.m_CGSO * m_modacc.m_W, Vgs, gGG, gGS, gSG, gSS, IG, IS);
|
||||
set_cap(m_cap_gd, m_Cgd + m_modacc.m_CGDO * m_modacc.m_W, Vgd, gGG, gGD, gDG, gDD, IG, ID);
|
||||
}
|
||||
|
||||
// Source connected to body, Diode S-B shorted!
|
||||
|
@ -75,31 +75,30 @@ namespace netlist
|
||||
/// http://www.ecircuitcenter.com/Circuits/opmodel1/opmodel1.htm
|
||||
///
|
||||
///
|
||||
class opamp_model_t : public param_model_t
|
||||
class opamp_model_t
|
||||
{
|
||||
public:
|
||||
opamp_model_t(device_t &device, const pstring &name, const pstring &val)
|
||||
: param_model_t(device, name, val)
|
||||
, m_TYPE(*this, "TYPE")
|
||||
, m_FPF(*this, "FPF")
|
||||
, m_SLEW(*this, "SLEW")
|
||||
, m_RI(*this, "RI")
|
||||
, m_RO(*this, "RO")
|
||||
, m_UGF(*this, "UGF")
|
||||
, m_VLL(*this, "VLL")
|
||||
, m_VLH(*this, "VLH")
|
||||
, m_DAB(*this, "DAB")
|
||||
opamp_model_t(param_model_t &model)
|
||||
: m_TYPE(model, "TYPE")
|
||||
, m_FPF(model, "FPF")
|
||||
, m_SLEW(model, "SLEW")
|
||||
, m_RI(model, "RI")
|
||||
, m_RO(model, "RO")
|
||||
, m_UGF(model, "UGF")
|
||||
, m_VLL(model, "VLL")
|
||||
, m_VLH(model, "VLH")
|
||||
, m_DAB(model, "DAB")
|
||||
{}
|
||||
|
||||
value_t m_TYPE; //!< Model Type, 1 and 3 are supported
|
||||
value_t m_FPF; //!< frequency of first pole
|
||||
value_t m_SLEW; //!< unity gain slew rate
|
||||
value_t m_RI; //!< input resistance
|
||||
value_t m_RO; //!< output resistance
|
||||
value_t m_UGF; //!< unity gain frequency (transition frequency)
|
||||
value_t m_VLL; //!< low output swing minus low supply rail
|
||||
value_t m_VLH; //!< high supply rail minus high output swing
|
||||
value_t m_DAB; //!< Differential Amp Bias - total quiescent current
|
||||
param_model_t::value_t m_TYPE; //!< Model Type, 1 and 3 are supported
|
||||
param_model_t::value_t m_FPF; //!< frequency of first pole
|
||||
param_model_t::value_t m_SLEW; //!< unity gain slew rate
|
||||
param_model_t::value_t m_RI; //!< input resistance
|
||||
param_model_t::value_t m_RO; //!< output resistance
|
||||
param_model_t::value_t m_UGF; //!< unity gain frequency (transition frequency)
|
||||
param_model_t::value_t m_VLL; //!< low output swing minus low supply rail
|
||||
param_model_t::value_t m_VLH; //!< high supply rail minus high output swing
|
||||
param_model_t::value_t m_DAB; //!< Differential Amp Bias - total quiescent current
|
||||
};
|
||||
|
||||
|
||||
@ -111,11 +110,12 @@ namespace netlist
|
||||
, m_VCC(*this, "VCC")
|
||||
, m_GND(*this, "GND")
|
||||
, m_model(*this, "MODEL", "LM324")
|
||||
, m_modacc(m_model)
|
||||
, m_VH(*this, "VH")
|
||||
, m_VL(*this, "VL")
|
||||
, m_VREF(*this, "VREF")
|
||||
{
|
||||
m_type = static_cast<int>(m_model.m_TYPE);
|
||||
m_type = static_cast<int>(m_modacc.m_TYPE);
|
||||
if (m_type < 1 || m_type > 3)
|
||||
{
|
||||
log().fatal(MF_OPAMP_UNKNOWN_TYPE(m_type));
|
||||
@ -204,7 +204,8 @@ namespace netlist
|
||||
analog_input_t m_VCC;
|
||||
analog_input_t m_GND;
|
||||
|
||||
opamp_model_t m_model;
|
||||
param_model_t m_model;
|
||||
opamp_model_t m_modacc;
|
||||
analog_output_t m_VH;
|
||||
analog_output_t m_VL;
|
||||
analog_output_t m_VREF;
|
||||
@ -216,33 +217,33 @@ namespace netlist
|
||||
NETLIB_UPDATE(opamp)
|
||||
{
|
||||
const nl_fptype cVt = nlconst::np_VT(nlconst::one()); // * m_n;
|
||||
const nl_fptype cId = m_model.m_DAB; // 3 mA
|
||||
const nl_fptype cId = m_modacc.m_DAB; // 3 mA
|
||||
const nl_fptype cVd = cVt * plib::log(cId / nlconst::np_Is() + nlconst::one());
|
||||
|
||||
m_VH.push(m_VCC() - m_model.m_VLH - cVd);
|
||||
m_VL.push(m_GND() + m_model.m_VLL + cVd);
|
||||
m_VH.push(m_VCC() - m_modacc.m_VLH - cVd);
|
||||
m_VL.push(m_GND() + m_modacc.m_VLL + cVd);
|
||||
m_VREF.push((m_VCC() + m_GND()) / nlconst::two());
|
||||
}
|
||||
|
||||
NETLIB_UPDATE_PARAM(opamp)
|
||||
{
|
||||
m_G1.m_RI.set(m_model.m_RI);
|
||||
m_G1.m_RI.set(m_modacc.m_RI);
|
||||
|
||||
if (m_type == 1)
|
||||
{
|
||||
nl_fptype RO = m_model.m_RO;
|
||||
nl_fptype G = m_model.m_UGF / m_model.m_FPF / RO;
|
||||
nl_fptype RO = m_modacc.m_RO;
|
||||
nl_fptype G = m_modacc.m_UGF / m_modacc.m_FPF / RO;
|
||||
m_RP.set_R(RO);
|
||||
m_G1.m_G.set(G);
|
||||
}
|
||||
if (m_type == 3 || m_type == 2)
|
||||
{
|
||||
nl_fptype CP = m_model.m_DAB / m_model.m_SLEW;
|
||||
nl_fptype RP = nlconst::half() / nlconst::pi() / CP / m_model.m_FPF;
|
||||
nl_fptype G = m_model.m_UGF / m_model.m_FPF / RP;
|
||||
nl_fptype CP = m_modacc.m_DAB / m_modacc.m_SLEW;
|
||||
nl_fptype RP = nlconst::half() / nlconst::pi() / CP / m_modacc.m_FPF;
|
||||
nl_fptype G = m_modacc.m_UGF / m_modacc.m_FPF / RP;
|
||||
|
||||
//printf("OPAMP %s: %g %g %g\n", name().c_str(), CP, RP, G);
|
||||
if (m_model.m_SLEW / (nlconst::four() * nlconst::pi() * nlconst::np_VT()) < m_model.m_UGF)
|
||||
if (m_modacc.m_SLEW / (nlconst::four() * nlconst::pi() * nlconst::np_VT()) < m_modacc.m_UGF)
|
||||
log().warning(MW_OPAMP_FAIL_CONVERGENCE(this->name()));
|
||||
|
||||
m_CP->set_cap_embedded(CP);
|
||||
@ -255,9 +256,9 @@ namespace netlist
|
||||
m_EBUF->m_G.set(nlconst::one());
|
||||
#if TEST_ALT_OUTPUT
|
||||
m_EBUF->m_RO.set(0.001);
|
||||
m_RO->set_R(m_model.m_RO);
|
||||
m_RO->set_R(m_modacc.m_RO);
|
||||
#else
|
||||
m_EBUF->m_RO.set(m_model.m_RO);
|
||||
m_EBUF->m_RO.set(m_modacc.m_RO);
|
||||
#endif
|
||||
}
|
||||
if (m_type == 3)
|
||||
@ -265,9 +266,9 @@ namespace netlist
|
||||
m_EBUF->m_G.set(nlconst::one());
|
||||
#if TEST_ALT_OUTPUT
|
||||
m_EBUF->m_RO.set(0.001);
|
||||
m_RO->set_R(m_model.m_RO);
|
||||
m_RO->set_R(m_modacc.m_RO);
|
||||
#else
|
||||
m_EBUF->m_RO.set(m_model.m_RO);
|
||||
m_EBUF->m_RO.set(m_modacc.m_RO);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
@ -145,8 +145,9 @@ namespace analog
|
||||
|
||||
NETLIB_RESET(D)
|
||||
{
|
||||
nl_fptype Is = m_model.m_IS;
|
||||
nl_fptype n = m_model.m_N;
|
||||
diode_model_t modacc(m_model);
|
||||
nl_fptype Is = modacc.m_IS;
|
||||
nl_fptype n = modacc.m_N;
|
||||
|
||||
m_D.set_param(Is, n, exec().gmin(), nlconst::T0());
|
||||
set_G_V_I(m_D.G(), nlconst::zero(), m_D.Ieq());
|
||||
@ -154,8 +155,9 @@ namespace analog
|
||||
|
||||
NETLIB_UPDATE_PARAM(D)
|
||||
{
|
||||
nl_fptype Is = m_model.m_IS;
|
||||
nl_fptype n = m_model.m_N;
|
||||
diode_model_t modacc(m_model);
|
||||
nl_fptype Is = modacc.m_IS;
|
||||
nl_fptype n = modacc.m_N;
|
||||
|
||||
m_D.set_param(Is, n, exec().gmin(), nlconst::T0());
|
||||
}
|
||||
@ -176,19 +178,21 @@ namespace analog
|
||||
|
||||
NETLIB_RESET(Z)
|
||||
{
|
||||
nl_fptype IsBV = m_model.m_IBV / (plib::exp(m_model.m_BV / nlconst::np_VT(m_model.m_NBV)) - nlconst::one());
|
||||
zdiode_model_t modacc(m_model);
|
||||
nl_fptype IsBV = modacc.m_IBV / (plib::exp(modacc.m_BV / nlconst::np_VT(modacc.m_NBV)) - nlconst::one());
|
||||
|
||||
m_D.set_param(m_model.m_IS, m_model.m_N, exec().gmin(), nlconst::T0());
|
||||
m_R.set_param(IsBV, m_model.m_NBV, exec().gmin(), nlconst::T0());
|
||||
m_D.set_param(modacc.m_IS, modacc.m_N, exec().gmin(), nlconst::T0());
|
||||
m_R.set_param(IsBV, modacc.m_NBV, exec().gmin(), nlconst::T0());
|
||||
set_G_V_I(m_D.G(), nlconst::zero(), m_D.Ieq());
|
||||
}
|
||||
|
||||
NETLIB_UPDATE_PARAM(Z)
|
||||
{
|
||||
nl_fptype IsBV = m_model.m_IBV / (plib::exp(m_model.m_BV / nlconst::np_VT(m_model.m_NBV)) - nlconst::one());
|
||||
zdiode_model_t modacc(m_model);
|
||||
nl_fptype IsBV = modacc.m_IBV / (plib::exp(modacc.m_BV / nlconst::np_VT(modacc.m_NBV)) - nlconst::one());
|
||||
|
||||
m_D.set_param(m_model.m_IS, m_model.m_N, exec().gmin(), nlconst::T0());
|
||||
m_R.set_param(IsBV, m_model.m_NBV, exec().gmin(), nlconst::T0());
|
||||
m_D.set_param(modacc.m_IS, modacc.m_N, exec().gmin(), nlconst::T0());
|
||||
m_R.set_param(IsBV, modacc.m_NBV, exec().gmin(), nlconst::T0());
|
||||
set_G_V_I(m_D.G(), nlconst::zero(), m_D.Ieq());
|
||||
}
|
||||
|
||||
|
@ -452,32 +452,31 @@ namespace analog
|
||||
/// | Y |IBV |current at breakdown voltage |A | 0.001| | |
|
||||
/// | |TNOM |parameter measurement temperature|deg C| 27| 50| |
|
||||
///
|
||||
class diode_model_t : public param_model_t
|
||||
class diode_model_t
|
||||
{
|
||||
public:
|
||||
diode_model_t(device_t &device, const pstring &name, const pstring &val)
|
||||
: param_model_t(device, name, val)
|
||||
, m_IS(*this, "IS")
|
||||
, m_N(*this, "N")
|
||||
diode_model_t(param_model_t &model)
|
||||
: m_IS(model, "IS")
|
||||
, m_N(model, "N")
|
||||
{}
|
||||
|
||||
value_t m_IS; //!< saturation current.
|
||||
value_t m_N; //!< emission coefficient.
|
||||
param_model_t::value_t m_IS; //!< saturation current.
|
||||
param_model_t::value_t m_N; //!< emission coefficient.
|
||||
};
|
||||
|
||||
class zdiode_model_t : public diode_model_t
|
||||
{
|
||||
public:
|
||||
zdiode_model_t(device_t &device, const pstring &name, const pstring &val)
|
||||
: diode_model_t(device, name, val)
|
||||
, m_NBV(*this, "NBV")
|
||||
, m_BV(*this, "BV")
|
||||
, m_IBV(*this, "IBV")
|
||||
zdiode_model_t(param_model_t &model)
|
||||
: diode_model_t(model)
|
||||
, m_NBV(model, "NBV")
|
||||
, m_BV(model, "BV")
|
||||
, m_IBV(model, "IBV")
|
||||
{}
|
||||
|
||||
value_t m_NBV; //!< reverse emission coefficient.
|
||||
value_t m_BV; //!< reverse breakdown voltage.
|
||||
value_t m_IBV; //!< current at breakdown voltage.
|
||||
param_model_t::value_t m_NBV; //!< reverse emission coefficient.
|
||||
param_model_t::value_t m_BV; //!< reverse breakdown voltage.
|
||||
param_model_t::value_t m_IBV; //!< current at breakdown voltage.
|
||||
};
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
@ -504,7 +503,7 @@ namespace analog
|
||||
NETLIB_UPDATE_PARAMI();
|
||||
|
||||
private:
|
||||
diode_model_t m_model;
|
||||
param_model_t m_model;
|
||||
generic_diode<diode_e::BIPOLAR> m_D;
|
||||
};
|
||||
|
||||
@ -533,7 +532,7 @@ namespace analog
|
||||
NETLIB_UPDATE_PARAMI();
|
||||
|
||||
private:
|
||||
zdiode_model_t m_model;
|
||||
param_model_t m_model;
|
||||
generic_diode<diode_e::BIPOLAR> m_D;
|
||||
// REVERSE diode
|
||||
generic_diode<diode_e::BIPOLAR> m_R;
|
||||
@ -553,14 +552,13 @@ namespace analog
|
||||
, m_R(*this, "RI", nlconst::magic(0.1))
|
||||
, m_V(*this, "V", nlconst::zero())
|
||||
, m_func(*this,"FUNC", "")
|
||||
, m_compiled()
|
||||
, m_compiled(*this, "m_compiled")
|
||||
, m_funcparam({nlconst::zero()})
|
||||
{
|
||||
m_compiled.save_state(*this, "m_compiled");
|
||||
register_subalias("P", P());
|
||||
register_subalias("N", N());
|
||||
if (m_func() != "")
|
||||
m_compiled.compile(m_func(), std::vector<pstring>({{pstring("T")}}));
|
||||
m_compiled->compile(m_func(), std::vector<pstring>({{pstring("T")}}));
|
||||
}
|
||||
|
||||
NETLIB_IS_TIMESTEP(m_func() != "")
|
||||
@ -570,7 +568,7 @@ namespace analog
|
||||
m_t += step;
|
||||
m_funcparam[0] = m_t;
|
||||
this->set_G_V_I(plib::reciprocal(m_R()),
|
||||
m_compiled.evaluate(m_funcparam),
|
||||
m_compiled->evaluate(m_funcparam),
|
||||
nlconst::zero());
|
||||
}
|
||||
|
||||
@ -587,7 +585,7 @@ namespace analog
|
||||
param_fp_t m_R;
|
||||
param_fp_t m_V;
|
||||
param_str_t m_func;
|
||||
plib::pfunction<nl_fptype> m_compiled;
|
||||
state_var<plib::pfunction<nl_fptype>> m_compiled;
|
||||
std::vector<nl_fptype> m_funcparam;
|
||||
};
|
||||
|
||||
@ -602,14 +600,13 @@ namespace analog
|
||||
, m_t(*this, "m_t", nlconst::zero())
|
||||
, m_I(*this, "I", nlconst::one())
|
||||
, m_func(*this,"FUNC", "")
|
||||
, m_compiled()
|
||||
, m_compiled(*this, "m_compiled")
|
||||
, m_funcparam({nlconst::zero()})
|
||||
{
|
||||
m_compiled.save_state(*this, "m_compiled");
|
||||
register_subalias("P", P());
|
||||
register_subalias("N", N());
|
||||
if (m_func() != "")
|
||||
m_compiled.compile(m_func(), std::vector<pstring>({{pstring("T")}}));
|
||||
m_compiled->compile(m_func(), std::vector<pstring>({{pstring("T")}}));
|
||||
}
|
||||
|
||||
NETLIB_IS_TIMESTEP(m_func() != "")
|
||||
@ -617,7 +614,7 @@ namespace analog
|
||||
{
|
||||
m_t += step;
|
||||
m_funcparam[0] = m_t;
|
||||
const nl_fptype I = m_compiled.evaluate(m_funcparam);
|
||||
const nl_fptype I = m_compiled->evaluate(m_funcparam);
|
||||
const auto zero(nlconst::zero());
|
||||
set_mat(zero, zero, -I,
|
||||
zero, zero, I);
|
||||
@ -649,7 +646,7 @@ namespace analog
|
||||
state_var<nl_fptype> m_t;
|
||||
param_fp_t m_I;
|
||||
param_str_t m_func;
|
||||
plib::pfunction<nl_fptype> m_compiled;
|
||||
state_var<plib::pfunction<nl_fptype>> m_compiled;
|
||||
std::vector<nl_fptype> m_funcparam;
|
||||
};
|
||||
|
||||
|
@ -73,7 +73,10 @@ TIDY_DB = $(OBJ)/compile_commands.json
|
||||
|
||||
# LTO = -flto=4 -fuse-linker-plugin -flto-partition=balanced -Wodr
|
||||
|
||||
CFLAGS = $(LTO) -g -O3 -std=c++14 -I$(CURDIR)/.. -I$(CURDIR)/../.. $(CEXTRAFLAGS)
|
||||
CCOREFLAGS = -g -O3 -std=c++14 -I$(CURDIR)/.. -I$(CURDIR)/../..
|
||||
|
||||
|
||||
CFLAGS = $(LTO) $(CCOREFLAGS) $(CEXTRAFLAGS)
|
||||
LDFLAGS = $(LTO) -g -O3 -std=c++14 $(LDEXTRAFLAGS)
|
||||
LIBS = -lpthread -ldl $(EXTRALIBS)
|
||||
|
||||
@ -82,6 +85,8 @@ LD = @g++
|
||||
MD = @mkdir
|
||||
RM = @rm
|
||||
CLANG_TIDY = clang-tidy-11
|
||||
DEPENDCC=$(CC)
|
||||
|
||||
|
||||
ifndef FAST
|
||||
FAST=1
|
||||
@ -278,17 +283,20 @@ native:
|
||||
$(MAKE) CEXTRAFLAGS="-march=native -msse4.2 -Wall -Wpedantic -Wsign-compare -Wextra "
|
||||
|
||||
gcc9:
|
||||
$(MAKE) CC=g++-9 LD=g++-9 CEXTRAFLAGS="-march=native -fext-numeric-literals -msse4.2 -Wall -pedantic -Wpedantic -Wsign-compare -Wextra" EXTRALIBS="-lquadmath"
|
||||
$(MAKE) CC=g++-9 LD=g++-9 CEXTRAFLAGS="-march=native -fext-numeric-literals -msse4.2 -Wall -pedantic -Wpedantic -Wsign-compare -Wextra " EXTRALIBS="-lquadmath"
|
||||
|
||||
clang:
|
||||
$(MAKE) CC=clang++-11 LD=clang++-11 OBJ=obj/clang CEXTRAFLAGS="-march=native -msse4.2 -Weverything -Wall -pedantic -Wpedantic -Werror -Wno-padded -Wno-weak-vtables -Wno-unused-template -Wno-missing-variable-declarations -Wno-float-equal -Wconversion -Wno-c++98-compat -Wno-c++98-compat-pedantic -Wno-format-nonliteral -Wno-exit-time-destructors"
|
||||
#$(MAKE) CC=clang++-11 LD=clang++-11 OBJ=obj/clang CEXTRAFLAGS="-march=native -msse4.2 -Weverything -Wall -pedantic -Wpedantic -Wunused-private-field -Wno-padded -Wno-unused-template -Wno-missing-variable-declarations -Wno-float-equal -Wconversion -Wno-c++98-compat -Wno-c++98-compat-pedantic -Wno-format-nonliteral -Wno-exit-time-destructors"
|
||||
$(MAKE) CC=clang++-11 LD=clang++-11 OBJ=obj/clang CEXTRAFLAGS="-march=native -msse4.2 -Weverything -Wall -pedantic -Wpedantic -Wunused-private-field -Werror -Wno-padded -Wno-weak-vtables -Wno-unused-template -Wno-missing-variable-declarations -Wno-float-equal -Wconversion -Wno-c++98-compat -Wno-c++98-compat-pedantic -Wno-format-nonliteral -Wno-exit-time-destructors"
|
||||
|
||||
clang-5:
|
||||
$(MAKE) CC=clang++-5.0 LD=clang++-5.0 CEXTRAFLAGS="-march=native -Weverything -Werror -Wno-inconsistent-missing-destructor-override -Wno-unreachable-code -Wno-padded -Wno-weak-vtables -Wno-missing-variable-declarations -Wconversion -Wno-c++98-compat -Wno-float-equal -Wno-global-constructors -Wno-c++98-compat-pedantic -Wno-format-nonliteral -Wno-weak-template-vtables -Wno-exit-time-destructors"
|
||||
|
||||
nvcc:
|
||||
$(MAKE) CC=/usr/local/cuda-9.0/bin/nvcc LD=/usr/local/cuda-9.2/bin/nvcc OBJ=obj/nvcc \
|
||||
CEXTRAFLAGS="-x cu -DNVCCBUILD=1 --expt-extended-lambda --expt-relaxed-constexpr --default-stream per-thread --restrict"
|
||||
$(MAKE) CC=/usr/local/cuda-9.0/bin/nvcc LD=/usr/local/cuda-9.2/bin/nvcc \
|
||||
OBJ=obj/nvcc CEXTRAFLAGS="-x cu -DNVCCBUILD=1 --expt-extended-lambda \
|
||||
--expt-relaxed-constexpr --default-stream per-thread --restrict" \
|
||||
DEPENDCC=g++
|
||||
|
||||
tidy_db: compile_commands_prefix $(ALL_TIDY_FILES) compile_commands_postfix
|
||||
|
||||
@ -327,7 +335,7 @@ $(DEPEND): maketree $(SOURCES)
|
||||
@echo creating $(DEPEND)
|
||||
@rm -f $(DEPEND)
|
||||
@for i in $(SOURCES); do \
|
||||
$(CC) $(CFLAGS) -MM $$i -MT `echo $$i | sed -e 's+$(SRC)+$(OBJ)+' -e 's+.cpp+.o+' ` >> $(DEPEND); \
|
||||
$(DEPENDCC) $(CCOREFLAGS) -MM $$i -MT `echo $$i | sed -e 's+$(SRC)+$(OBJ)+' -e 's+.cpp+.o+' ` >> $(DEPEND); \
|
||||
done
|
||||
|
||||
depend: $(DEPEND)
|
||||
|
@ -1,12 +1,14 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio 14
|
||||
VisualStudioVersion = 14.0.25420.1
|
||||
# Visual Studio Version 16
|
||||
VisualStudioVersion = 16.0.30011.22
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "netlistlib", "netlistlib.vcxproj", "{A374399B-B87F-4E0F-9525-6C099600705F}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nltool", "nltool.vcxproj", "{9204EC28-A29B-4A36-9E47-2C46041D67D3}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nlwav", "nlwav.vcxproj", "{48D0ADAF-62EC-472E-A51B-8D837280649D}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|x64 = Debug|x64
|
||||
@ -31,8 +33,19 @@ Global
|
||||
{9204EC28-A29B-4A36-9E47-2C46041D67D3}.Release|x64.Build.0 = Release|x64
|
||||
{9204EC28-A29B-4A36-9E47-2C46041D67D3}.Release|x86.ActiveCfg = Release|Win32
|
||||
{9204EC28-A29B-4A36-9E47-2C46041D67D3}.Release|x86.Build.0 = Release|Win32
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Debug|x64.Build.0 = Debug|x64
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Debug|x86.Build.0 = Debug|Win32
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Release|x64.ActiveCfg = Release|x64
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Release|x64.Build.0 = Release|x64
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Release|x86.ActiveCfg = Release|Win32
|
||||
{48D0ADAF-62EC-472E-A51B-8D837280649D}.Release|x86.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {992701A0-B9F5-4F7D-BF3F-5B0EBEA51F04}
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
|
@ -1,4 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup />
|
||||
</Project>
|
162
src/lib/netlist/buildVS/nlwav.vcxproj
Executable file
162
src/lib/netlist/buildVS/nlwav.vcxproj
Executable file
@ -0,0 +1,162 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\prg\nlwav.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="netlistlib.vcxproj">
|
||||
<Project>{a374399b-b87f-4e0f-9525-6c099600705f}</Project>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>16.0</VCProjectVersion>
|
||||
<ProjectGuid>{48D0ADAF-62EC-472E-A51B-8D837280649D}</ProjectGuid>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<RootNamespace>nlwav</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<LinkIncremental>true</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>
|
||||
</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)..\..\</AdditionalIncludeDirectories>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Console</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Console</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Console</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Console</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
22
src/lib/netlist/buildVS/nlwav.vcxproj.filters
Executable file
22
src/lib/netlist/buildVS/nlwav.vcxproj.filters
Executable file
@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;c++;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\prg\nlwav.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
@ -7,7 +7,6 @@
|
||||
|
||||
#include "nld_2102A.h"
|
||||
#include "netlist/nl_base.h"
|
||||
#include "nlid_system.h"
|
||||
|
||||
#define ADDR2BYTE(a) ((a) >> 3)
|
||||
#define ADDR2BIT(a) ((a) & 0x7)
|
||||
@ -33,7 +32,8 @@ namespace netlist
|
||||
NETLIB_RESETI();
|
||||
NETLIB_UPDATEI();
|
||||
|
||||
protected:
|
||||
friend class NETLIB_NAME(2102A_dip);
|
||||
private:
|
||||
object_array_t<logic_input_t, 10> m_A;
|
||||
logic_input_t m_CEQ;
|
||||
logic_input_t m_RWQ;
|
||||
@ -46,31 +46,36 @@ namespace netlist
|
||||
nld_power_pins m_power_pins;
|
||||
};
|
||||
|
||||
NETLIB_OBJECT_DERIVED(2102A_dip, 2102A)
|
||||
NETLIB_OBJECT(2102A_dip)
|
||||
{
|
||||
NETLIB_CONSTRUCTOR_DERIVED(2102A_dip, 2102A)
|
||||
NETLIB_CONSTRUCTOR(2102A_dip)
|
||||
, A(*this, "A")
|
||||
{
|
||||
register_subalias("8", m_A[0]);
|
||||
register_subalias("4", m_A[1]);
|
||||
register_subalias("5", m_A[2]);
|
||||
register_subalias("6", m_A[3]);
|
||||
register_subalias("7", m_A[4]);
|
||||
register_subalias("2", m_A[5]);
|
||||
register_subalias("1", m_A[6]);
|
||||
register_subalias("16", m_A[7]);
|
||||
register_subalias("15", m_A[8]);
|
||||
register_subalias("14", m_A[9]);
|
||||
register_subalias("8", A.m_A[0]);
|
||||
register_subalias("4", A.m_A[1]);
|
||||
register_subalias("5", A.m_A[2]);
|
||||
register_subalias("6", A.m_A[3]);
|
||||
register_subalias("7", A.m_A[4]);
|
||||
register_subalias("2", A.m_A[5]);
|
||||
register_subalias("1", A.m_A[6]);
|
||||
register_subalias("16", A.m_A[7]);
|
||||
register_subalias("15", A.m_A[8]);
|
||||
register_subalias("14", A.m_A[9]);
|
||||
|
||||
register_subalias("13", m_CEQ);
|
||||
register_subalias("3", m_RWQ);
|
||||
register_subalias("13", A.m_CEQ);
|
||||
register_subalias("3", A.m_RWQ);
|
||||
|
||||
register_subalias("11", m_DI);
|
||||
register_subalias("12", m_DO);
|
||||
register_subalias("11", A.m_DI);
|
||||
register_subalias("12", A.m_DO);
|
||||
|
||||
register_subalias("10", "VCC");
|
||||
register_subalias("9", "GND");
|
||||
register_subalias("10", "A.VCC");
|
||||
register_subalias("9", "A.GND");
|
||||
|
||||
}
|
||||
NETLIB_RESETI() {}
|
||||
NETLIB_UPDATEI() {}
|
||||
private:
|
||||
NETLIB_SUB(2102A) A;
|
||||
};
|
||||
|
||||
NETLIB_UPDATE(2102A)
|
||||
|
@ -7,7 +7,6 @@
|
||||
|
||||
#include "nld_2716.h"
|
||||
#include "netlist/nl_base.h"
|
||||
#include "nlid_system.h"
|
||||
|
||||
namespace netlist
|
||||
{
|
||||
@ -28,7 +27,8 @@ namespace netlist
|
||||
|
||||
NETLIB_UPDATEI();
|
||||
|
||||
protected:
|
||||
friend class NETLIB_NAME(2716_dip);
|
||||
private:
|
||||
object_array_t<logic_input_t, 11> m_A;
|
||||
logic_input_t m_GQ;
|
||||
logic_input_t m_EPQ;
|
||||
@ -40,37 +40,42 @@ namespace netlist
|
||||
nld_power_pins m_power_pins;
|
||||
};
|
||||
|
||||
NETLIB_OBJECT_DERIVED(2716_dip, 2716)
|
||||
NETLIB_OBJECT(2716_dip)
|
||||
{
|
||||
NETLIB_CONSTRUCTOR_DERIVED(2716_dip, 2716)
|
||||
NETLIB_CONSTRUCTOR(2716_dip)
|
||||
, A(*this, "A")
|
||||
{
|
||||
register_subalias("8", m_A[0]);
|
||||
register_subalias("7", m_A[1]);
|
||||
register_subalias("6", m_A[2]);
|
||||
register_subalias("5", m_A[3]);
|
||||
register_subalias("4", m_A[4]);
|
||||
register_subalias("3", m_A[5]);
|
||||
register_subalias("2", m_A[6]);
|
||||
register_subalias("1", m_A[7]);
|
||||
register_subalias("23", m_A[8]);
|
||||
register_subalias("22", m_A[9]);
|
||||
register_subalias("19", m_A[10]);
|
||||
register_subalias("8", A.m_A[0]);
|
||||
register_subalias("7", A.m_A[1]);
|
||||
register_subalias("6", A.m_A[2]);
|
||||
register_subalias("5", A.m_A[3]);
|
||||
register_subalias("4", A.m_A[4]);
|
||||
register_subalias("3", A.m_A[5]);
|
||||
register_subalias("2", A.m_A[6]);
|
||||
register_subalias("1", A.m_A[7]);
|
||||
register_subalias("23", A.m_A[8]);
|
||||
register_subalias("22", A.m_A[9]);
|
||||
register_subalias("19", A.m_A[10]);
|
||||
|
||||
register_subalias("20", m_GQ);
|
||||
register_subalias("18", m_EPQ);
|
||||
register_subalias("20", A.m_GQ);
|
||||
register_subalias("18", A.m_EPQ);
|
||||
|
||||
register_subalias("9", m_D[0]);
|
||||
register_subalias("10", m_D[1]);
|
||||
register_subalias("11", m_D[2]);
|
||||
register_subalias("13", m_D[3]);
|
||||
register_subalias("14", m_D[4]);
|
||||
register_subalias("15", m_D[5]);
|
||||
register_subalias("16", m_D[6]);
|
||||
register_subalias("17", m_D[7]);
|
||||
register_subalias("9", A.m_D[0]);
|
||||
register_subalias("10", A.m_D[1]);
|
||||
register_subalias("11", A.m_D[2]);
|
||||
register_subalias("13", A.m_D[3]);
|
||||
register_subalias("14", A.m_D[4]);
|
||||
register_subalias("15", A.m_D[5]);
|
||||
register_subalias("16", A.m_D[6]);
|
||||
register_subalias("17", A.m_D[7]);
|
||||
|
||||
register_subalias("12", "GND");
|
||||
register_subalias("24", "VCC");
|
||||
register_subalias("12", "A.GND");
|
||||
register_subalias("24", "A.VCC");
|
||||
}
|
||||
NETLIB_RESETI() {}
|
||||
NETLIB_UPDATEI() {}
|
||||
private:
|
||||
NETLIB_SUB(2716) A;
|
||||
};
|
||||
|
||||
// FIXME: timing!
|
||||
|
@ -6,7 +6,7 @@
|
||||
*/
|
||||
|
||||
#include "nld_4006.h"
|
||||
#include "nlid_system.h"
|
||||
#include "nl_base.h"
|
||||
|
||||
namespace netlist
|
||||
{
|
||||
@ -61,7 +61,8 @@ namespace netlist
|
||||
}
|
||||
}
|
||||
|
||||
protected:
|
||||
friend class NETLIB_NAME(CD4006_dip);
|
||||
private:
|
||||
logic_input_t m_CLOCK;
|
||||
object_array_t<logic_input_t, 4> m_I;
|
||||
object_array_t<logic_output_t, 7> m_Q;
|
||||
@ -70,27 +71,32 @@ namespace netlist
|
||||
nld_power_pins m_supply;
|
||||
};
|
||||
|
||||
NETLIB_OBJECT_DERIVED(CD4006_dip, CD4006)
|
||||
NETLIB_OBJECT(CD4006_dip)
|
||||
{
|
||||
NETLIB_CONSTRUCTOR_DERIVED(CD4006_dip, CD4006)
|
||||
NETLIB_CONSTRUCTOR(CD4006_dip)
|
||||
, A(*this, "A")
|
||||
{
|
||||
register_subalias("1", m_I[0]);
|
||||
register_subalias("2", m_Q[1]);
|
||||
register_subalias("3", m_CLOCK);
|
||||
register_subalias("4", m_I[1]);
|
||||
register_subalias("5", m_I[2]);
|
||||
register_subalias("6", m_I[3]);
|
||||
register_subalias("7", "VSS");
|
||||
register_subalias("1", A.m_I[0]);
|
||||
register_subalias("2", A.m_Q[1]);
|
||||
register_subalias("3", A.m_CLOCK);
|
||||
register_subalias("4", A.m_I[1]);
|
||||
register_subalias("5", A.m_I[2]);
|
||||
register_subalias("6", A.m_I[3]);
|
||||
register_subalias("7", "A.VSS");
|
||||
|
||||
register_subalias("8", m_Q[5]);
|
||||
register_subalias("9", m_Q[6]);
|
||||
register_subalias("10", m_Q[4]);
|
||||
register_subalias("11", m_Q[2]);
|
||||
register_subalias("12", m_Q[3]);
|
||||
register_subalias("13", m_Q[0]);
|
||||
register_subalias("14", "VDD");
|
||||
register_subalias("8", A.m_Q[5]);
|
||||
register_subalias("9", A.m_Q[6]);
|
||||
register_subalias("10", A.m_Q[4]);
|
||||
register_subalias("11", A.m_Q[2]);
|
||||
register_subalias("12", A.m_Q[3]);
|
||||
register_subalias("13", A.m_Q[0]);
|
||||
register_subalias("14", "A.VDD");
|
||||
|
||||
}
|
||||
NETLIB_RESETI() {}
|
||||
NETLIB_UPDATEI() {}
|
||||
private:
|
||||
NETLIB_SUB(CD4006) A;
|
||||
};
|
||||
|
||||
NETLIB_DEVICE_IMPL(CD4006, "CD4006", "+CLOCK,+D1,+D2,+D3,+D4,+D1P4,+D1P4S,+D2P4,+D2P5,+D3P4,+D4P4,+D3P5,@VCC,@GND")
|
||||
|
@ -6,7 +6,8 @@
|
||||
*/
|
||||
|
||||
#include "nld_4020.h"
|
||||
#include "nlid_system.h"
|
||||
#include "nl_base.h"
|
||||
#include "nl_factory.h"
|
||||
|
||||
namespace netlist
|
||||
{
|
||||
|
@ -9,7 +9,6 @@
|
||||
|
||||
#include "netlist/analog/nlid_twoterm.h"
|
||||
#include "netlist/solver/nld_solver.h"
|
||||
#include "nlid_system.h"
|
||||
|
||||
// This is an experimental approach to implement the analog switch.
|
||||
// This will make the switch a 3 terminal element which is completely
|
||||
|
@ -8,7 +8,6 @@
|
||||
#include "nld_4316.h"
|
||||
#include "netlist/analog/nlid_twoterm.h"
|
||||
#include "netlist/solver/nld_solver.h"
|
||||
#include "nlid_system.h"
|
||||
|
||||
namespace netlist { namespace devices {
|
||||
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user