10 Commits

Author SHA1 Message Date
clobber cd166c0561 Bump version for sparkle updater. Core is still 2.2.3 2018-11-25 16:15:16 -06:00
clobber dd9e1c3cee Cleanup 2018-11-25 16:14:41 -06:00
clobber 28ae039566 Add display mode change support 2018-11-23 00:54:14 -06:00
clobber 33026a6424 Cleanup 2018-11-22 21:11:38 -06:00
clobber 10e4d8fd38 Build fix for latest Clang.
cheat.cpp:219:30: error: ordered comparison between pointer and zero ('char *' and 'int')
2018-04-05 02:11:16 -05:00
clobber 2758d42404 Use -fileSystemRepresentation instead of -UTF8String for file names 2017-08-16 23:42:32 -05:00
Rudy Richter 0fa341d5c1 these should be uint32_t not uint8_t 2017-07-20 20:54:58 -04:00
Rudy Richter 5bfdfc26d4 Use spaces 2017-07-20 08:50:47 -04:00
mrvacbob 22d81842fa Enable direct-rendering 2017-07-20 01:35:09 -07:00
clobber cf62e4485d Update to FCEUX 2.2.3 2016-07-29 20:19:00 -05:00
171 changed files with 10402 additions and 6665 deletions
+71
View File
@@ -38,6 +38,24 @@
3D46DF571BD23A5F008E84E6 /* input.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 949BB9B61A9EED59007B49CC /* input.cpp */; };
82EC409F0FD9EC420017FC19 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 82EC409E0FD9EC420017FC19 /* libz.dylib */; };
82EC40A30FD9EC5A0017FC19 /* FCEUGameCore.mm in Sources */ = {isa = PBXBuildFile; fileRef = B5008DAE0E8BFB3E005AECAF /* FCEUGameCore.mm */; };
870D6EA21D4C1E0C001E8FC6 /* 158B.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EA11D4C1E0C001E8FC6 /* 158B.cpp */; };
870D6EA41D4C1F49001E8FC6 /* 8in1.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EA31D4C1F49001E8FC6 /* 8in1.cpp */; };
870D6EA61D4C1F82001E8FC6 /* BMW8544.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EA51D4C1F82001E8FC6 /* BMW8544.cpp */; };
870D6EA81D4C1F93001E8FC6 /* coolboy.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EA71D4C1F93001E8FC6 /* coolboy.cpp */; };
870D6EAA1D4C1FCB001E8FC6 /* eh8813a.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EA91D4C1FCB001E8FC6 /* eh8813a.cpp */; };
870D6EAE1D4C1FE7001E8FC6 /* et-100.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EAB1D4C1FE7001E8FC6 /* et-100.cpp */; };
870D6EAF1D4C1FE7001E8FC6 /* et-4320.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EAC1D4C1FE7001E8FC6 /* et-4320.cpp */; };
870D6EB01D4C1FE7001E8FC6 /* F-15.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EAD1D4C1FE7001E8FC6 /* F-15.cpp */; };
870D6EB31D4C20B3001E8FC6 /* hp898f.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EB11D4C20B3001E8FC6 /* hp898f.cpp */; };
870D6EB41D4C20B3001E8FC6 /* inlnsf.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EB21D4C20B3001E8FC6 /* inlnsf.cpp */; };
870D6EB61D4C20F8001E8FC6 /* ks7010.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EB51D4C20F8001E8FC6 /* ks7010.cpp */; };
870D6EB81D4C2106001E8FC6 /* ks7016.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EB71D4C2106001E8FC6 /* ks7016.cpp */; };
870D6EBA1D4C2B01001E8FC6 /* rt-01.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EB91D4C2B01001E8FC6 /* rt-01.cpp */; };
870D6EBC1D4C2B11001E8FC6 /* sb-2000.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EBB1D4C2B11001E8FC6 /* sb-2000.cpp */; };
870D6EBE1D4C2B4B001E8FC6 /* unrom512.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EBD1D4C2B4B001E8FC6 /* unrom512.cpp */; };
870D6EC01D4C2BD9001E8FC6 /* pec586kb.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EBF1D4C2BD9001E8FC6 /* pec586kb.cpp */; };
870D6EC21D4C2BF4001E8FC6 /* snesmouse.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 870D6EC11D4C2BF4001E8FC6 /* snesmouse.cpp */; };
870D6EC31D4C3453001E8FC6 /* vidblit.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 949BB8101A9EED57007B49CC /* vidblit.cpp */; };
8D5B49B0048680CD000E48DA /* InfoPlist.strings in Resources */ = {isa = PBXBuildFile; fileRef = 089C167DFE841241C02AAC07 /* InfoPlist.strings */; };
8D5B49B4048680CD000E48DA /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 1058C7ADFEA557BF11CA2CBB /* Cocoa.framework */; };
945942D014E4F2DC0015D2AA /* FCEUX.icns in Resources */ = {isa = PBXBuildFile; fileRef = 945942CF14E4F2DC0015D2AA /* FCEUX.icns */; };
@@ -279,6 +297,23 @@
089C167FFE841241C02AAC07 /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = /System/Library/Frameworks/AppKit.framework; sourceTree = "<absolute>"; };
1058C7ADFEA557BF11CA2CBB /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = /System/Library/Frameworks/Cocoa.framework; sourceTree = "<absolute>"; };
82EC409E0FD9EC420017FC19 /* libz.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libz.dylib; path = usr/lib/libz.dylib; sourceTree = SDKROOT; };
870D6EA11D4C1E0C001E8FC6 /* 158B.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = 158B.cpp; sourceTree = "<group>"; };
870D6EA31D4C1F49001E8FC6 /* 8in1.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = 8in1.cpp; sourceTree = "<group>"; };
870D6EA51D4C1F82001E8FC6 /* BMW8544.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = BMW8544.cpp; sourceTree = "<group>"; };
870D6EA71D4C1F93001E8FC6 /* coolboy.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = coolboy.cpp; sourceTree = "<group>"; };
870D6EA91D4C1FCB001E8FC6 /* eh8813a.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = eh8813a.cpp; sourceTree = "<group>"; };
870D6EAB1D4C1FE7001E8FC6 /* et-100.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = "et-100.cpp"; sourceTree = "<group>"; };
870D6EAC1D4C1FE7001E8FC6 /* et-4320.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = "et-4320.cpp"; sourceTree = "<group>"; };
870D6EAD1D4C1FE7001E8FC6 /* F-15.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = "F-15.cpp"; sourceTree = "<group>"; };
870D6EB11D4C20B3001E8FC6 /* hp898f.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = hp898f.cpp; sourceTree = "<group>"; };
870D6EB21D4C20B3001E8FC6 /* inlnsf.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = inlnsf.cpp; sourceTree = "<group>"; };
870D6EB51D4C20F8001E8FC6 /* ks7010.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ks7010.cpp; sourceTree = "<group>"; };
870D6EB71D4C2106001E8FC6 /* ks7016.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ks7016.cpp; sourceTree = "<group>"; };
870D6EB91D4C2B01001E8FC6 /* rt-01.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = "rt-01.cpp"; sourceTree = "<group>"; };
870D6EBB1D4C2B11001E8FC6 /* sb-2000.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = "sb-2000.cpp"; sourceTree = "<group>"; };
870D6EBD1D4C2B4B001E8FC6 /* unrom512.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = unrom512.cpp; sourceTree = "<group>"; };
870D6EBF1D4C2BD9001E8FC6 /* pec586kb.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = pec586kb.cpp; sourceTree = "<group>"; };
870D6EC11D4C2BF4001E8FC6 /* snesmouse.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = snesmouse.cpp; sourceTree = "<group>"; };
8D5B49B6048680CD000E48DA /* FCEU.oecoreplugin */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = FCEU.oecoreplugin; sourceTree = BUILT_PRODUCTS_DIR; };
8D5B49B7048680CD000E48DA /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
942597DB151471070074E3A3 /* OpenEmuBase.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = OpenEmuBase.framework; path = ../OpenEmu/build/Release/OpenEmuBase.framework; sourceTree = "<group>"; };
@@ -1096,6 +1131,7 @@
);
name = VisualBoyAdvance;
sourceTree = "<group>";
usesTabs = 0;
};
089C1671FE841209C02AAC07 /* Frameworks and Libraries */ = {
isa = PBXGroup;
@@ -1274,6 +1310,7 @@
949BB75D1A9EED55007B49CC /* 15.cpp */,
949BB75E1A9EED55007B49CC /* 151.cpp */,
949BB75F1A9EED55007B49CC /* 156.cpp */,
870D6EA11D4C1E0C001E8FC6 /* 158B.cpp */,
949BB7601A9EED55007B49CC /* 164.cpp */,
949BB7611A9EED55007B49CC /* 168.cpp */,
949BB7621A9EED55007B49CC /* 170.cpp */,
@@ -1333,6 +1370,7 @@
949BB7981A9EED56007B49CC /* 8237.cpp */,
949BB7991A9EED56007B49CC /* 830118C.cpp */,
949BB79A1A9EED56007B49CC /* 88.cpp */,
870D6EA31D4C1F49001E8FC6 /* 8in1.cpp */,
949BB79B1A9EED56007B49CC /* 90.cpp */,
949BB79C1A9EED56007B49CC /* 91.cpp */,
949BB79D1A9EED56007B49CC /* 96.cpp */,
@@ -1348,15 +1386,21 @@
949BB7A71A9EED56007B49CC /* bmc42in1r.cpp */,
949BB7A81A9EED56007B49CC /* bmc64in1nr.cpp */,
949BB7A91A9EED56007B49CC /* bmc70in1.cpp */,
870D6EA51D4C1F82001E8FC6 /* BMW8544.cpp */,
949BB7AA1A9EED56007B49CC /* bonza.cpp */,
949BB7AB1A9EED56007B49CC /* bs-5.cpp */,
949BB7AC1A9EED56007B49CC /* cityfighter.cpp */,
870D6EA71D4C1F93001E8FC6 /* coolboy.cpp */,
949BB7AD1A9EED56007B49CC /* dance2000.cpp */,
949BB7AE1A9EED56007B49CC /* datalatch.cpp */,
949BB7AF1A9EED56007B49CC /* dream.cpp */,
949BB7B01A9EED56007B49CC /* edu2000.cpp */,
870D6EA91D4C1FCB001E8FC6 /* eh8813a.cpp */,
949BB7B11A9EED56007B49CC /* emu2413.c */,
949BB7B21A9EED56007B49CC /* emu2413.h */,
870D6EAB1D4C1FE7001E8FC6 /* et-100.cpp */,
870D6EAC1D4C1FE7001E8FC6 /* et-4320.cpp */,
870D6EAD1D4C1FE7001E8FC6 /* F-15.cpp */,
949BB7B31A9EED56007B49CC /* famicombox.cpp */,
949BB7B41A9EED56007B49CC /* ffe.cpp */,
949BB7B51A9EED56007B49CC /* fk23c.cpp */,
@@ -1364,10 +1408,14 @@
949BB7B71A9EED56007B49CC /* gs-2004.cpp */,
949BB7B81A9EED56007B49CC /* gs-2013.cpp */,
949BB7B91A9EED56007B49CC /* h2288.cpp */,
870D6EB11D4C20B3001E8FC6 /* hp898f.cpp */,
870D6EB21D4C20B3001E8FC6 /* inlnsf.cpp */,
949BB7BA1A9EED56007B49CC /* karaoke.cpp */,
949BB7BB1A9EED56007B49CC /* kof97.cpp */,
870D6EB51D4C20F8001E8FC6 /* ks7010.cpp */,
949BB7BC1A9EED56007B49CC /* ks7012.cpp */,
949BB7BD1A9EED56007B49CC /* ks7013.cpp */,
870D6EB71D4C2106001E8FC6 /* ks7016.cpp */,
949BB7BE1A9EED56007B49CC /* ks7017.cpp */,
949BB7BF1A9EED56007B49CC /* ks7030.cpp */,
949BB7C01A9EED56007B49CC /* ks7031.cpp */,
@@ -1390,8 +1438,10 @@
949BB7D11A9EED56007B49CC /* novel.cpp */,
949BB7D21A9EED56007B49CC /* onebus.cpp */,
949BB7D31A9EED56007B49CC /* pec-586.cpp */,
870D6EB91D4C2B01001E8FC6 /* rt-01.cpp */,
949BB7D41A9EED56007B49CC /* sa-9602b.cpp */,
949BB7D51A9EED56007B49CC /* sachen.cpp */,
870D6EBB1D4C2B11001E8FC6 /* sb-2000.cpp */,
949BB7D61A9EED56007B49CC /* sc-127.cpp */,
949BB7D71A9EED56007B49CC /* SConscript */,
949BB7D81A9EED56007B49CC /* sheroes.cpp */,
@@ -1404,6 +1454,7 @@
949BB7DF1A9EED56007B49CC /* tengen.cpp */,
949BB7E01A9EED56007B49CC /* tf-1201.cpp */,
949BB7E11A9EED56007B49CC /* transformer.cpp */,
870D6EBD1D4C2B4B001E8FC6 /* unrom512.cpp */,
949BB7E21A9EED56007B49CC /* vrc1.cpp */,
949BB7E31A9EED56007B49CC /* vrc2and4.cpp */,
949BB7E41A9EED56007B49CC /* vrc3.cpp */,
@@ -1940,11 +1991,13 @@
949BB9A91A9EED59007B49CC /* mahjong.cpp */,
949BB9AA1A9EED59007B49CC /* mouse.cpp */,
949BB9AB1A9EED59007B49CC /* oekakids.cpp */,
870D6EBF1D4C2BD9001E8FC6 /* pec586kb.cpp */,
949BB9AC1A9EED59007B49CC /* powerpad.cpp */,
949BB9AD1A9EED59007B49CC /* quiz.cpp */,
949BB9AE1A9EED59007B49CC /* SConscript */,
949BB9AF1A9EED59007B49CC /* shadow.cpp */,
949BB9B01A9EED59007B49CC /* share.h */,
870D6EC11D4C2BF4001E8FC6 /* snesmouse.cpp */,
949BB9B11A9EED59007B49CC /* suborkb.cpp */,
949BB9B21A9EED59007B49CC /* suborkb.h */,
949BB9B31A9EED59007B49CC /* toprider.cpp */,
@@ -2258,6 +2311,7 @@
82EC40A30FD9EC5A0017FC19 /* FCEUGameCore.mm in Sources */,
949BBB381A9EFF4A007B49CC /* asm.cpp in Sources */,
949BBB391A9EFF4A007B49CC /* cart.cpp in Sources */,
870D6EA81D4C1F93001E8FC6 /* coolboy.cpp in Sources */,
949BBB3A1A9EFF4A007B49CC /* cheat.cpp in Sources */,
949BBB3B1A9EFF4A007B49CC /* conddebug.cpp in Sources */,
949BBB3C1A9EFF4A007B49CC /* config.cpp in Sources */,
@@ -2286,6 +2340,7 @@
949BBA751A9EF079007B49CC /* 09-034a.cpp in Sources */,
949BBA761A9EF079007B49CC /* 103.cpp in Sources */,
949BBA771A9EF079007B49CC /* 106.cpp in Sources */,
870D6EBC1D4C2B11001E8FC6 /* sb-2000.cpp in Sources */,
949BBA781A9EF079007B49CC /* 108.cpp in Sources */,
949BBA791A9EF079007B49CC /* 112.cpp in Sources */,
949BBA7A1A9EF079007B49CC /* 116.cpp in Sources */,
@@ -2308,6 +2363,7 @@
949BBA8B1A9EF079007B49CC /* 185.cpp in Sources */,
949BBA8C1A9EF079007B49CC /* 186.cpp in Sources */,
949BBA8D1A9EF079007B49CC /* 187.cpp in Sources */,
870D6EB01D4C1FE7001E8FC6 /* F-15.cpp in Sources */,
949BBA8E1A9EF079007B49CC /* 189.cpp in Sources */,
949BBA8F1A9EF079007B49CC /* 193.cpp in Sources */,
949BBA901A9EF079007B49CC /* 199.cpp in Sources */,
@@ -2328,6 +2384,8 @@
949BBA9F1A9EF079007B49CC /* 32.cpp in Sources */,
949BBAA01A9EF079007B49CC /* 33.cpp in Sources */,
949BBAA11A9EF079007B49CC /* 34.cpp in Sources */,
870D6EA21D4C1E0C001E8FC6 /* 158B.cpp in Sources */,
870D6EBE1D4C2B4B001E8FC6 /* unrom512.cpp in Sources */,
949BBAA21A9EF079007B49CC /* 36.cpp in Sources */,
949BBAA31A9EF079007B49CC /* 3d-block.cpp in Sources */,
949BBAA41A9EF079007B49CC /* 40.cpp in Sources */,
@@ -2341,8 +2399,10 @@
949BBAAC1A9EF079007B49CC /* 57.cpp in Sources */,
949BBAAD1A9EF079007B49CC /* 603-5052.cpp in Sources */,
949BBAAE1A9EF079007B49CC /* 62.cpp in Sources */,
870D6EAA1D4C1FCB001E8FC6 /* eh8813a.cpp in Sources */,
949BBAAF1A9EF079007B49CC /* 65.cpp in Sources */,
949BBAB01A9EF079007B49CC /* 67.cpp in Sources */,
870D6EBA1D4C2B01001E8FC6 /* rt-01.cpp in Sources */,
949BBAB11A9EF079007B49CC /* 68.cpp in Sources */,
949BBAB21A9EF079007B49CC /* 69.cpp in Sources */,
949BBAB31A9EF079007B49CC /* 71.cpp in Sources */,
@@ -2383,7 +2443,9 @@
949BBAD71A9EF07A007B49CC /* fk23c.cpp in Sources */,
949BBAD81A9EF07A007B49CC /* ghostbusters63in1.cpp in Sources */,
949BBAD91A9EF07A007B49CC /* gs-2004.cpp in Sources */,
870D6EA41D4C1F49001E8FC6 /* 8in1.cpp in Sources */,
949BBADA1A9EF07A007B49CC /* gs-2013.cpp in Sources */,
870D6EC01D4C2BD9001E8FC6 /* pec586kb.cpp in Sources */,
949BBADB1A9EF07A007B49CC /* h2288.cpp in Sources */,
949BBADC1A9EF07A007B49CC /* karaoke.cpp in Sources */,
949BBADD1A9EF07A007B49CC /* kof97.cpp in Sources */,
@@ -2395,6 +2457,7 @@
949BBAE31A9EF07A007B49CC /* ks7032.cpp in Sources */,
949BBAE41A9EF07A007B49CC /* ks7037.cpp in Sources */,
949BBAE51A9EF07A007B49CC /* ks7057.cpp in Sources */,
870D6EB81D4C2106001E8FC6 /* ks7016.cpp in Sources */,
949BBAE61A9EF07A007B49CC /* le05.cpp in Sources */,
949BBAE71A9EF07A007B49CC /* lh32.cpp in Sources */,
949BBAE81A9EF07A007B49CC /* lh53.cpp in Sources */,
@@ -2410,12 +2473,18 @@
949BBAF41A9EF07A007B49CC /* onebus.cpp in Sources */,
949BBAF51A9EF07A007B49CC /* pec-586.cpp in Sources */,
949BBAF61A9EF07A007B49CC /* sa-9602b.cpp in Sources */,
870D6EA61D4C1F82001E8FC6 /* BMW8544.cpp in Sources */,
870D6EB41D4C20B3001E8FC6 /* inlnsf.cpp in Sources */,
949BBAF71A9EF07A007B49CC /* sachen.cpp in Sources */,
949BBAF81A9EF07A007B49CC /* sc-127.cpp in Sources */,
870D6EB31D4C20B3001E8FC6 /* hp898f.cpp in Sources */,
870D6EAE1D4C1FE7001E8FC6 /* et-100.cpp in Sources */,
949BBAFA1A9EF07A007B49CC /* sheroes.cpp in Sources */,
870D6EC21D4C2BF4001E8FC6 /* snesmouse.cpp in Sources */,
949BBAFB1A9EF07A007B49CC /* sl1632.cpp in Sources */,
949BBAFC1A9EF07A007B49CC /* subor.cpp in Sources */,
949BBAFD1A9EF07A007B49CC /* super24.cpp in Sources */,
870D6EAF1D4C1FE7001E8FC6 /* et-4320.cpp in Sources */,
949BBAFE1A9EF07A007B49CC /* supervision.cpp in Sources */,
949BBAFF1A9EF07A007B49CC /* t-227-1.cpp in Sources */,
949BBB001A9EF07A007B49CC /* t-262.cpp in Sources */,
@@ -2457,6 +2526,8 @@
949BBB301A9EFE2C007B49CC /* memory.cpp in Sources */,
949BBB331A9EFE2C007B49CC /* unzip.cpp in Sources */,
949BBB361A9EFE2C007B49CC /* xstring.cpp in Sources */,
870D6EB61D4C20F8001E8FC6 /* ks7010.cpp in Sources */,
870D6EC31D4C3453001E8FC6 /* vidblit.cpp in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
+392 -75
View File
@@ -1,5 +1,5 @@
/*
Copyright (c) 2015, OpenEmu Team
Copyright (c) 2018, OpenEmu Team
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
@@ -41,18 +41,37 @@
extern uint8 *XBuf;
static uint32_t palette[256];
#define OVERSCAN_VERTICAL 8
#define OVERSCAN_HORIZONTAL 8
#define OptionDefault(_NAME_, _PREFKEY_) @{ OEGameCoreDisplayModeNameKey : _NAME_, OEGameCoreDisplayModePrefKeyNameKey : _PREFKEY_, OEGameCoreDisplayModeStateKey : @YES, }
#define Option(_NAME_, _PREFKEY_) @{ OEGameCoreDisplayModeNameKey : _NAME_, OEGameCoreDisplayModePrefKeyNameKey : _PREFKEY_, OEGameCoreDisplayModeStateKey : @NO, }
#define OptionIndented(_NAME_, _PREFKEY_) @{ OEGameCoreDisplayModeNameKey : _NAME_, OEGameCoreDisplayModePrefKeyNameKey : _PREFKEY_, OEGameCoreDisplayModeStateKey : @NO, OEGameCoreDisplayModeIndentationLevelKey : @(1), }
#define OptionToggleable(_NAME_, _PREFKEY_) @{ OEGameCoreDisplayModeNameKey : _NAME_, OEGameCoreDisplayModePrefKeyNameKey : _PREFKEY_, OEGameCoreDisplayModeStateKey : @NO, OEGameCoreDisplayModeAllowsToggleKey : @YES, }
#define OptionToggleableNoSave(_NAME_, _PREFKEY_) @{ OEGameCoreDisplayModeNameKey : _NAME_, OEGameCoreDisplayModePrefKeyNameKey : _PREFKEY_, OEGameCoreDisplayModeStateKey : @NO, OEGameCoreDisplayModeAllowsToggleKey : @YES, OEGameCoreDisplayModeDisallowPrefSaveKey : @YES, }
#define Label(_NAME_) @{ OEGameCoreDisplayModeLabelKey : _NAME_, }
#define SeparatorItem() @{ OEGameCoreDisplayModeSeparatorItemKey : @"",}
@interface FCEUGameCore () <OENESSystemResponderClient>
{
uint32_t *videoBuffer;
uint8_t *pXBuf;
int32_t *soundBuffer;
int32_t soundSize;
uint32_t pad;
uint32_t arkanoid[3];
uint32_t zapper[3];
uint32_t hypershot[4];
uint32_t *_videoBuffer;
int32_t *_soundBuffer;
int32_t _soundSize;
uint32_t _pad;
uint32_t _arkanoid[3];
uint32_t _zapper[3];
uint32_t _hypershot[4];
int _videoWidth, _videoHeight;
int _videoOffsetX, _videoOffsetY;
int _aspectWidth, _aspectHeight;
BOOL _isHorzOverscanCropped;
BOOL _isVertOverscanCropped;
NSMutableDictionary<NSString *, NSNumber *> *_cheatList;
NSMutableArray <NSMutableDictionary <NSString *, id> *> *_availableDisplayModes;
}
- (void)loadDisplayModeOptions;
@end
@implementation FCEUGameCore
@@ -63,7 +82,7 @@ static __weak FCEUGameCore *_current;
{
if((self = [super init]))
{
videoBuffer = (uint32_t *)malloc(256 * 240 * 4);
_cheatList = [NSMutableDictionary dictionary];
}
_current = self;
@@ -73,51 +92,51 @@ static __weak FCEUGameCore *_current;
- (void)dealloc
{
free(videoBuffer);
free(_videoBuffer);
}
# pragma mark - Execution
- (BOOL)loadFileAtPath:(NSString *)path error:(NSError **)error
{
pad = 0;
memset(arkanoid, 0, sizeof(arkanoid));
memset(zapper, 0, sizeof(zapper));
memset(hypershot, 0, sizeof(hypershot));
_pad = 0;
memset(_arkanoid, 0, sizeof(_arkanoid));
memset(_zapper, 0, sizeof(_zapper));
memset(_hypershot, 0, sizeof(_hypershot));
//newppu = 0 default off, set 1 to enable
FCEUI_Initialize();
NSURL *batterySavesDirectory = [NSURL fileURLWithPath:[self batterySavesDirectoryPath]];
[[NSFileManager defaultManager] createDirectoryAtURL:batterySavesDirectory withIntermediateDirectories:YES attributes:nil error:nil];
//FCEUI_SetBaseDirectory([[self biosDirectoryPath] UTF8String]); unused for now
FCEUI_SetDirOverride(FCEUIOD_NV, strdup([[batterySavesDirectory path] UTF8String]));
NSURL *batterySavesDirectory = [NSURL fileURLWithPath:self.batterySavesDirectoryPath];
[NSFileManager.defaultManager createDirectoryAtURL:batterySavesDirectory withIntermediateDirectories:YES attributes:nil error:nil];
//FCEUI_SetBaseDirectory([[self biosDirectoryPath] fileSystemRepresentation]); unused for now
FCEUI_SetDirOverride(FCEUIOD_NV, strdup(batterySavesDirectory.fileSystemRepresentation));
FCEUI_SetSoundVolume(256);
FCEUI_Sound(48000);
FCEUGI *FCEUGameInfo;
FCEUGameInfo = FCEUI_LoadGame([path UTF8String], 1, false);
FCEUGameInfo = FCEUI_LoadGame(path.fileSystemRepresentation, 1, false);
if(!FCEUGameInfo)
return NO;
//NSLog(@"FPS: %d", FCEUI_GetDesiredFPS() >> 24); // Hz
FCEUI_SetInput(0, SI_GAMEPAD, &pad, 0); // Controllers 1 and 3
FCEUI_SetInput(0, SI_GAMEPAD, &_pad, 0); // Controllers 1 and 3
if(FCEUGameInfo->input[1] == SI_ZAPPER)
FCEUI_SetInput(1, SI_ZAPPER, &zapper, 0);
FCEUI_SetInput(1, SI_ZAPPER, &_zapper, 0);
else if(FCEUGameInfo->input[1] == SI_ARKANOID)
FCEUI_SetInput(1, SI_ARKANOID, &arkanoid, 0);
FCEUI_SetInput(1, SI_ARKANOID, &_arkanoid, 0);
else
FCEUI_SetInput(1, SI_GAMEPAD, &pad, 0); // Controllers 2 and 4
FCEUI_SetInput(1, SI_GAMEPAD, &_pad, 0); // Controllers 2 and 4
if(FCEUGameInfo->inputfc == SIFC_SHADOW)
FCEUI_SetInputFC(SIFC_SHADOW, &hypershot, 0);
FCEUI_SetInputFC(SIFC_SHADOW, &_hypershot, 0);
else if(FCEUGameInfo->inputfc == SIFC_ARKANOID)
FCEUI_SetInputFC(SIFC_ARKANOID, &arkanoid, 0);
FCEUI_SetInputFC(SIFC_ARKANOID, &_arkanoid, 0);
extern uint32_t iNESGameCRC32;
NSString *cartCRC32 = [NSString stringWithFormat:@"%08x", iNESGameCRC32];
@@ -192,29 +211,29 @@ static __weak FCEUGameCore *_current;
FCEUI_SetInputFourscore(true);
if([famicom4Player containsObject:cartCRC32])
FCEUI_SetInputFC(SIFC_4PLAYER, &pad, 0);
FCEUI_SetInputFC(SIFC_4PLAYER, &_pad, 0);
FCEU_ResetPalette();
// Only temporary, so core doesn't crash on an older OpenEmu version
if ([self respondsToSelector:@selector(displayModeInfo)]) {
[self loadDisplayModeOptions];
}
return YES;
}
- (void)executeFrame
{
pXBuf = 0;
soundSize = 0;
uint8_t *pXBuf;
_soundSize = 0;
FCEUI_Emulate(&pXBuf, &soundBuffer, &soundSize, 0);
FCEUI_Emulate(&pXBuf, &_soundBuffer, &_soundSize, 0);
pXBuf = XBuf;
for (unsigned y = 0; y < 240; y++)
for (unsigned x = 0; x < 256; x++, pXBuf++)
videoBuffer[y * 256 + x] = palette[*pXBuf];
for (int i = 0; i < _soundSize; i++)
_soundBuffer[i] = (_soundBuffer[i] << 16) | (_soundBuffer[i] & 0xffff);
for (int i = 0; i < soundSize; i++)
soundBuffer[i] = (soundBuffer[i] << 16) | (soundBuffer[i] & 0xffff);
[[self ringBufferAtIndex:0] write:soundBuffer maxLength:soundSize << 2];
[[self ringBufferAtIndex:0] write:_soundBuffer maxLength:_soundSize << 2];
}
- (void)resetEmulation
@@ -237,19 +256,39 @@ static __weak FCEUGameCore *_current;
# pragma mark - Video
- (const void *)videoBuffer
- (const void *)getVideoBufferWithHint:(void *)hint
{
return videoBuffer;
if (!hint) {
if (!_videoBuffer) _videoBuffer = (uint32_t *)malloc(256 * 240 * sizeof(uint32_t));
hint = _videoBuffer;
}
// TODO: support paletted video in OE
uint8_t *pXBuf = XBuf;
uint32_t *pOBuf = (uint32_t *)hint;
for (unsigned y = 0; y < 240; y++)
for (unsigned x = 0; x < 256; x++, pXBuf++)
pOBuf[y * 256 + x] = palette[*pXBuf];
return hint;
}
- (OEIntRect)screenRect
{
return OEIntRectMake(0, 0, 256, 240);
_videoOffsetX = _isHorzOverscanCropped ? OVERSCAN_HORIZONTAL : 0;
_videoOffsetY = _isVertOverscanCropped ? OVERSCAN_VERTICAL : 0;
_videoWidth = _isHorzOverscanCropped ? 256 - (OVERSCAN_HORIZONTAL * 2) : 256;
_videoHeight = _isVertOverscanCropped ? 240 - (OVERSCAN_VERTICAL * 2) : 240;
return OEIntRectMake(_videoOffsetX, _videoOffsetY, _videoWidth, _videoHeight);
}
- (OEIntSize)aspectSize
{
return OEIntSizeMake(256 * (8.0/7.0), 240);
_aspectWidth = _isHorzOverscanCropped ? (256 - (OVERSCAN_HORIZONTAL * 2)) * (8.0/7.0) : 256 * (8.0/7.0);
_aspectHeight = _isVertOverscanCropped ? 240 - (OVERSCAN_VERTICAL * 2) : 240;
return OEIntSizeMake(_aspectWidth, _aspectHeight);
}
- (OEIntSize)bufferSize
@@ -267,11 +306,6 @@ static __weak FCEUGameCore *_current;
return GL_UNSIGNED_INT_8_8_8_8_REV;
}
- (GLenum)internalPixelFormat
{
return GL_RGB8;
}
# pragma mark - Audio
- (double)audioSampleRate
@@ -316,8 +350,8 @@ static __weak FCEUGameCore *_current;
- (BOOL)deserializeState:(NSData *)state withError:(NSError **)outError
{
u8 *bytes = (u8 *)[state bytes];
size_t length = [state length];
u8 *bytes = (u8 *)state.bytes;
size_t length = state.length;
std::vector<u8> byteVector(bytes, bytes + length);
EMUFILE *emuFile = new EMUFILE_MEMORY(&byteVector);
@@ -349,7 +383,7 @@ const int NESMap[] = {JOY_UP, JOY_DOWN, JOY_LEFT, JOY_RIGHT, JOY_A, JOY_B, JOY_S
break;
}
pad |= NESMap[button] << playerShift;
_pad |= NESMap[button] << playerShift;
}
- (oneway void)didReleaseNESButton:(OENESButton)button forPlayer:(NSUInteger)player;
@@ -370,76 +404,77 @@ const int NESMap[] = {JOY_UP, JOY_DOWN, JOY_LEFT, JOY_RIGHT, JOY_A, JOY_B, JOY_S
break;
}
pad &= ~(NESMap[button] << playerShift);
_pad &= ~(NESMap[button] << playerShift);
}
- (oneway void)didTriggerGunAtPoint:(OEIntPoint)aPoint
{
[self mouseMovedAtPoint:aPoint];
arkanoid[2] = 1;
int xcoord = _isHorzOverscanCropped ? (aPoint.x + OVERSCAN_HORIZONTAL) * 0.876712 : aPoint.x * 0.876712;
int ycoord = _isVertOverscanCropped ? aPoint.y + OVERSCAN_VERTICAL : aPoint.y;
zapper[0] = aPoint.x * 0.876712;
zapper[1] = aPoint.y;
zapper[2] = 1;
_arkanoid[2] = 1;
hypershot[0] = aPoint.x * 0.876712;
hypershot[1] = aPoint.y;
hypershot[2] = 1;
_zapper[0] = xcoord;
_zapper[1] = ycoord;
_zapper[2] = 1;
_hypershot[0] = xcoord;
_hypershot[1] = ycoord;
_hypershot[2] = 1;
}
- (oneway void)didReleaseTrigger
{
arkanoid[2] = 0;
zapper[2] = 0;
hypershot[2] = 0;
_arkanoid[2] = 0;
_zapper[2] = 0;
_hypershot[2] = 0;
}
- (oneway void)mouseMovedAtPoint:(OEIntPoint)aPoint
{
arkanoid[0] = aPoint.x * 0.876712;
_arkanoid[0] = _isHorzOverscanCropped ? (aPoint.x + OVERSCAN_HORIZONTAL) * 0.876712 : aPoint.x * 0.876712;
}
- (oneway void)rightMouseDownAtPoint:(OEIntPoint)point
{
hypershot[3] = 1; // "move" button
_hypershot[3] = 1; // "move" button
}
- (oneway void)rightMouseUp;
{
hypershot[3] = 0;
_hypershot[3] = 0;
}
#pragma mark - Cheats
NSMutableDictionary *cheatList = [[NSMutableDictionary alloc] init];
- (void)setCheat:(NSString *)code setType:(NSString *)type setEnabled:(BOOL)enabled
{
// Sanitize
code = [code stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
code = [code stringByTrimmingCharactersInSet:NSCharacterSet.whitespaceAndNewlineCharacterSet];
// Remove any spaces
code = [code stringByReplacingOccurrencesOfString:@" " withString:@""];
if (enabled)
[cheatList setValue:@YES forKey:code];
_cheatList[code] = @YES;
else
[cheatList removeObjectForKey:code];
[_cheatList removeObjectForKey:code];
FCEU_FlushGameCheats(0, 1);
NSArray *multipleCodes = [[NSArray alloc] init];
NSArray<NSString *> *multipleCodes = [NSArray array];
// Apply enabled cheats found in dictionary
for (id key in cheatList)
for (NSString *key in _cheatList)
{
if ([[cheatList valueForKey:key] isEqual:@YES])
if ([_cheatList[key] boolValue])
{
// Handle multi-line cheats
multipleCodes = [key componentsSeparatedByString:@"+"];
for (NSString *singleCode in multipleCodes) {
const char *cCode = [singleCode UTF8String];
const char *cCode = singleCode.UTF8String;
int address, value, compare;
int type = 1;
@@ -451,6 +486,285 @@ NSMutableDictionary *cheatList = [[NSMutableDictionary alloc] init];
}
}
# pragma mark - Display Mode
- (NSArray <NSDictionary <NSString *, id> *> *)displayModes
{
if (_availableDisplayModes.count == 0)
{
_availableDisplayModes = [NSMutableArray array];
NSArray <NSDictionary <NSString *, id> *> *availableModesWithDefault =
@[
OptionToggleableNoSave(@"No Sprite Limit", @"noSpriteLimit"),
SeparatorItem(),
Label(@"Overscan"),
OptionToggleable(@"Crop Horizontal", @"cropHorizontalOverscan"),
OptionToggleable(@"Crop Vertical", @"cropVerticalOverscan"),
SeparatorItem(),
Label(@"Palette"),
OptionDefault(@"Default — FCEUX", @"palette"),
Option(@"RGB (PlayChoice-10)", @"palette"),
Option(@"NESCAP", @"palette"),
Option(@"Sony CXA2025AS", @"palette"),
Option(@"Smooth (FBX)", @"palette"),
Option(@"Wavebeam", @"palette"),
];
// Deep mutable copy
_availableDisplayModes = (NSMutableArray *)CFBridgingRelease(CFPropertyListCreateDeepCopy(kCFAllocatorDefault, (CFArrayRef)availableModesWithDefault, kCFPropertyListMutableContainers));
}
return [_availableDisplayModes copy];
}
- (void)changeDisplayWithMode:(NSString *)displayMode
{
if (_availableDisplayModes.count == 0)
[self displayModes];
// First check if 'displayMode' is valid
BOOL isDisplayModeToggleable = NO;
BOOL isValidDisplayMode = NO;
BOOL displayModeState = NO;
NSString *displayModePrefKey;
for (NSDictionary *modeDict in _availableDisplayModes) {
if ([modeDict[OEGameCoreDisplayModeNameKey] isEqualToString:displayMode]) {
displayModeState = [modeDict[OEGameCoreDisplayModeStateKey] boolValue];
displayModePrefKey = modeDict[OEGameCoreDisplayModePrefKeyNameKey];
isDisplayModeToggleable = [modeDict[OEGameCoreDisplayModeAllowsToggleKey] boolValue];
isValidDisplayMode = YES;
break;
}
}
// Disallow a 'displayMode' not found in _availableDisplayModes
if (!isValidDisplayMode)
return;
// Handle option state changes
for (NSMutableDictionary *optionDict in _availableDisplayModes) {
NSString *modeName = optionDict[OEGameCoreDisplayModeNameKey];
NSString *prefKey = optionDict[OEGameCoreDisplayModePrefKeyNameKey];
if (!modeName)
continue;
// Mutually exclusive option state change
else if ([modeName isEqualToString:displayMode] && !isDisplayModeToggleable)
optionDict[OEGameCoreDisplayModeStateKey] = @YES;
// Reset mutually exclusive options that are the same prefs group as 'displayMode'
else if (!isDisplayModeToggleable && [prefKey isEqualToString:displayModePrefKey])
optionDict[OEGameCoreDisplayModeStateKey] = @NO;
// Toggleable option state change
else if ([modeName isEqualToString:displayMode] && isDisplayModeToggleable)
optionDict[OEGameCoreDisplayModeStateKey] = @(!displayModeState);
}
if ([displayMode isEqualToString:@"Crop Horizontal"])
{
_isHorzOverscanCropped = !_isHorzOverscanCropped;
}
else if ([displayMode isEqualToString:@"Crop Vertical"])
{
_isVertOverscanCropped = !_isVertOverscanCropped;
}
else if ([displayMode isEqualToString:@"No Sprite Limit"])
{
FCEUI_DisableSpriteLimitation(!displayModeState);
}
else if ([displayMode isEqualToString:@"Default — FCEUX"])
{
FCEU_ResetPalette();
}
else if ([displayMode isEqualToString:@"RGB (PlayChoice-10)"])
{
unsigned int pc10_palette[64] =
{
0x6D6D6D, 0x002492, 0x0000DB, 0x6D49DB,
0x92006D, 0xB6006D, 0xB62400, 0x924900,
0x6D4900, 0x244900, 0x006D24, 0x009200,
0x004949, 0x000000, 0x000000, 0x000000,
0xB6B6B6, 0x006DDB, 0x0049FF, 0x9200FF,
0xB600FF, 0xFF0092, 0xFF0000, 0xDB6D00,
0x926D00, 0x249200, 0x009200, 0x00B66D,
0x009292, 0x242424, 0x000000, 0x000000,
0xFFFFFF, 0x6DB6FF, 0x9292FF, 0xDB6DFF,
0xFF00FF, 0xFF6DFF, 0xFF9200, 0xFFB600,
0xDBDB00, 0x6DDB00, 0x00FF00, 0x49FFDB,
0x00FFFF, 0x494949, 0x000000, 0x000000,
0xFFFFFF, 0xB6DBFF, 0xDBB6FF, 0xFFB6FF,
0xFF92FF, 0xFFB6B6, 0xFFDB92, 0xFFFF49,
0xFFFF6D, 0xB6FF49, 0x92FF6D, 0x49FFDB,
0x92DBFF, 0x929292, 0x000000, 0x000000
};
for (int i = 0; i < 64; i++)
{
int r = pc10_palette[i] >> 16;
int g = (pc10_palette[i] & 0xff00) >> 8;
int b = pc10_palette[i] & 0xff;
FCEUD_SetPalette(i, r, g, b);
FCEUD_SetPalette(i + 64, r, g, b);
FCEUD_SetPalette(i + 128, r, g, b);
FCEUD_SetPalette(i + 192, r, g, b);
}
}
else if ([displayMode isEqualToString:@"NESCAP"])
{
unsigned int nescap_palette[64] =
{
0x646365, 0x001580, 0x1D0090, 0x380082,
0x56005D, 0x5A001A, 0x4F0900, 0x381B00,
0x1E3100, 0x003D00, 0x004100, 0x003A1B,
0x002F55, 0x000000, 0x000000, 0x000000,
0xAFADAF, 0x164BCA, 0x472AE7, 0x6B1BDB,
0x9617B0, 0x9F185B, 0x963001, 0x7B4800,
0x5A6600, 0x237800, 0x017F00, 0x00783D,
0x006C8C, 0x000000, 0x000000, 0x000000,
0xFFFFFF, 0x60A6FF, 0x8F84FF, 0xB473FF,
0xE26CFF, 0xF268C3, 0xEF7E61, 0xD89527,
0xBAB307, 0x81C807, 0x57D43D, 0x47CF7E,
0x4BC5CD, 0x4C4B4D, 0x000000, 0x000000,
0xFFFFFF, 0xC2E0FF, 0xD5D2FF, 0xE3CBFF,
0xF7C8FF, 0xFEC6EE, 0xFECEC6, 0xF6D7AE,
0xE9E49F, 0xD3ED9D, 0xC0F2B2, 0xB9F1CC,
0xBAEDED, 0xBAB9BB, 0x000000, 0x000000
};
for (int i = 0; i < 64; i++)
{
int r = nescap_palette[i] >> 16;
int g = (nescap_palette[i] & 0xff00) >> 8;
int b = nescap_palette[i] & 0xff;
FCEUD_SetPalette(i, r, g, b);
FCEUD_SetPalette(i + 64, r, g, b);
FCEUD_SetPalette(i + 128, r, g, b);
FCEUD_SetPalette(i + 192, r, g, b);
}
}
else if ([displayMode isEqualToString:@"Sony CXA2025AS"])
{
unsigned int cxa2025as_palette[64] =
{
0x585858, 0x00238C, 0x00139B, 0x2D0585,
0x5D0052, 0x7A0017, 0x7A0800, 0x5F1800,
0x352A00, 0x093900, 0x003F00, 0x003C22,
0x00325D, 0x000000, 0x000000, 0x000000,
0xA1A1A1, 0x0053EE, 0x153CFE, 0x6028E4,
0xA91D98, 0xD41E41, 0xD22C00, 0xAA4400,
0x6C5E00, 0x2D7300, 0x007D06, 0x007852,
0x0069A9, 0x000000, 0x000000, 0x000000,
0xFFFFFF, 0x1FA5FE, 0x5E89FE, 0xB572FE,
0xFE65F6, 0xFE6790, 0xFE773C, 0xFE9308,
0xC4B200, 0x79CA10, 0x3AD54A, 0x11D1A4,
0x06BFFE, 0x424242, 0x000000, 0x000000,
0xFFFFFF, 0xA0D9FE, 0xBDCCFE, 0xE1C2FE,
0xFEBCFB, 0xFEBDD0, 0xFEC5A9, 0xFED18E,
0xE9DE86, 0xC7E992, 0xA8EEB0, 0x95ECD9,
0x91E4FE, 0xACACAC, 0x000000, 0x000000
};
for (int i = 0; i < 64; i++)
{
int r = cxa2025as_palette[i] >> 16;
int g = (cxa2025as_palette[i] & 0xff00) >> 8;
int b = cxa2025as_palette[i] & 0xff;
FCEUD_SetPalette(i, r, g, b);
FCEUD_SetPalette(i + 64, r, g, b);
FCEUD_SetPalette(i + 128, r, g, b);
FCEUD_SetPalette(i + 192, r, g, b);
}
}
else if ([displayMode isEqualToString:@"Smooth (FBX)"])
{
unsigned int smoothfbx_palette[64] =
{
0x6A6D6A, 0x001380, 0x1E008A, 0x39007A,
0x550056, 0x5A0018, 0x4F1000, 0x3D1C00,
0x253200, 0x003D00, 0x004000, 0x003924,
0x002E55, 0x000000, 0x000000, 0x000000,
0xB9BCB9, 0x1850C7, 0x4B30E3, 0x7322D6,
0x951FA9, 0x9D285C, 0x983700, 0x7F4C00,
0x5E6400, 0x227700, 0x027E02, 0x007645,
0x006E8A, 0x000000, 0x000000, 0x000000,
0xFFFFFF, 0x68A6FF, 0x8C9CFF, 0xB586FF,
0xD975FD, 0xE377B9, 0xE58D68, 0xD49D29,
0xB3AF0C, 0x7BC211, 0x55CA47, 0x46CB81,
0x47C1C5, 0x4A4D4A, 0x000000, 0x000000,
0xFFFFFF, 0xCCEAFF, 0xDDDEFF, 0xECDAFF,
0xF8D7FE, 0xFCD6F5, 0xFDDBCF, 0xF9E7B5,
0xF1F0AA, 0xDAFAA9, 0xC9FFBC, 0xC3FBD7,
0xC4F6F6, 0xBEC1BE, 0x000000, 0x000000
};
for (int i = 0; i < 64; i++)
{
int r = smoothfbx_palette[i] >> 16;
int g = (smoothfbx_palette[i] & 0xff00) >> 8;
int b = smoothfbx_palette[i] & 0xff;
FCEUD_SetPalette(i, r, g, b);
FCEUD_SetPalette(i + 64, r, g, b);
FCEUD_SetPalette(i + 128, r, g, b);
FCEUD_SetPalette(i + 192, r, g, b);
}
}
else if ([displayMode isEqualToString:@"Wavebeam"])
{
unsigned int wavebeam_palette[64] =
{
0x6B6B6B, 0x001B88, 0x21009A, 0x40008C,
0x600067, 0x64001E, 0x590800, 0x481600,
0x283600, 0x004500, 0x004908, 0x00421D,
0x003659, 0x000000, 0x000000, 0x000000,
0xB4B4B4, 0x1555D3, 0x4337EF, 0x7425DF,
0x9C19B9, 0xAC0F64, 0xAA2C00, 0x8A4B00,
0x666B00, 0x218300, 0x008A00, 0x008144,
0x007691, 0x000000, 0x000000, 0x000000,
0xFFFFFF, 0x63B2FF, 0x7C9CFF, 0xC07DFE,
0xE977FF, 0xF572CD, 0xF4886B, 0xDDA029,
0xBDBD0A, 0x89D20E, 0x5CDE3E, 0x4BD886,
0x4DCFD2, 0x525252, 0x000000, 0x000000,
0xFFFFFF, 0xBCDFFF, 0xD2D2FF, 0xE1C8FF,
0xEFC7FF, 0xFFC3E1, 0xFFCAC6, 0xF2DAAD,
0xEBE3A0, 0xD2EDA2, 0xBCF4B4, 0xB5F1CE,
0xB6ECF1, 0xBFBFBF, 0x000000, 0x000000
};
for (int i = 0; i < 64; i++)
{
int r = wavebeam_palette[i] >> 16;
int g = (wavebeam_palette[i] & 0xff00) >> 8;
int b = wavebeam_palette[i] & 0xff;
FCEUD_SetPalette(i, r, g, b);
FCEUD_SetPalette(i + 64, r, g, b);
FCEUD_SetPalette(i + 128, r, g, b);
FCEUD_SetPalette(i + 192, r, g, b);
}
}
}
- (void)loadDisplayModeOptions
{
// Restore palette
NSString *lastPalette = self.displayModeInfo[@"palette"];
if (lastPalette && ![lastPalette isEqualToString:@"Default — FCEUX"]) {
[self changeDisplayWithMode:lastPalette];
}
// Crop horizontal overscan
BOOL isHorizontalOverscanCropped = [self.displayModeInfo[@"cropHorizontalOverscan"] boolValue];
if (isHorizontalOverscanCropped) {
[self changeDisplayWithMode:@"Crop Horizontal"];
}
// Crop vertical overscan
BOOL isVerticalOverscanCropped = [self.displayModeInfo[@"cropVerticalOverscan"] boolValue];
if (isVerticalOverscanCropped) {
[self changeDisplayWithMode:@"Crop Vertical"];
}
}
// FCEUX internal functions and stubs
void FCEUD_SetPalette(unsigned char index, unsigned char r, unsigned char g, unsigned char b)
{
@@ -462,6 +776,8 @@ uint64 FCEUD_GetTime(void) {return 0;}
uint64 FCEUD_GetTimeFreq(void) {return 0;}
const char *GetKeyboard(void) {return "";}
bool turbo = false;
bool swapDuty = 0; // some Famicom and NES clones had duty cycle bits swapped
int dendy = 0;
int closeFinishedMovie = 0;
int FCEUD_ShowStatusIcon(void) {return 0;}
int FCEUD_SendData(void *data, uint32 len) {return 1;}
@@ -500,13 +816,14 @@ bool FCEUI_AviDisableMovieMessages() {return true;}
FCEUFILE *FCEUD_OpenArchiveIndex(ArchiveScanRecord &asr, std::string &fname, int innerIndex) {return 0;}
FCEUFILE *FCEUD_OpenArchive(ArchiveScanRecord &asr, std::string &fname, std::string *innerFilename) {return 0;}
ArchiveScanRecord FCEUD_ScanArchive(std::string fname) { return ArchiveScanRecord(); }
void GetMouseData(uint32 (&md)[3]) {}
void FCEUD_PrintError(const char *s)
{
NSLog(@"FCEUX error: %s", s);
NSLog(@"[FCEUX] error: %s", s);
}
void FCEUD_Message(const char *s)
{
NSLog(@"FCEUX message: %s", s);
NSLog(@"[FCEUX] message: %s", s);
}
@end
+3 -1
View File
@@ -17,7 +17,7 @@
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleVersion</key>
<string>2.2.2.1</string>
<string>2.2.3.1</string>
<key>NSPrincipalClass</key>
<string>OEGameCoreController</string>
<key>OEGameCoreClass</key>
@@ -32,6 +32,8 @@
<integer>0</integer>
<key>OEGameCoreSupportsCheatCode</key>
<true/>
<key>OEGameCoreSupportsDisplayModeChange</key>
<true/>
<key>OEGameCoreSupportsRewinding</key>
<true/>
</dict>
+10 -3
View File
@@ -276,16 +276,23 @@ char *Disassemble(int addr, uint8 *opcode) {
}
#define indirectX(a) { \
(a) = (opcode[1]+RX)&0xFF; \
(a) = GetMem((a)) | (GetMem((a)+1))<<8; \
(a) = GetMem((a)) | (GetMem(((a)+1)&0xff))<<8; \
}
#define indirectY(a) { \
(a) = GetMem(opcode[1]) | (GetMem(opcode[1]+1))<<8; \
(a) = GetMem(opcode[1]) | (GetMem((opcode[1]+1)&0xff))<<8; \
(a) += RY; \
}
#ifdef BRK_3BYTE_HACK
case 0x00:
sprintf(str,"BRK %02X %02X", opcode[1], opcode[2]);
break;
#else
case 0x00: strcpy(str,"BRK"); break;
#endif
//odd, 1-byte opcodes
case 0x00: strcpy(str,"BRK"); break;
case 0x08: strcpy(str,"PHP"); break;
case 0x0A: strcpy(str,"ASL"); break;
case 0x18: strcpy(str,"CLC"); break;
+1
View File
@@ -72,6 +72,7 @@ static void M112Power(void) {
SetWriteHandler(0x4020, 0x5FFF, M112Write);
SetReadHandler(0x6000, 0x7FFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(8, 0x6000, WRAM);
}
static void StateRestore(int version) {
+21 -18
View File
@@ -17,43 +17,45 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* 7-in-1 Darkwing Duck, Snake, MagicBlock (PCB marked as "12 in 1")
* 7-in-1 Darkwing Duck, Snake, MagicBlock (PCB marked as "12 in 1")
* 12-in-1 1991 New Star Co. Ltd.
*
*/
#include "mapinc.h"
static uint8 reg[4];
static uint8 prgchr[2], ctrl;
static SFORMAT StateRegs[] =
{
{ reg, 4, "REGS" },
{ prgchr, 2, "REGS" },
{ &ctrl, 1, "CTRL" },
{ 0 }
};
static void Sync(void) {
uint8 bank = (reg[3] & 3) << 3;
setchr4(0x0000, (reg[1] >> 3) | (bank << 2));
setchr4(0x1000, (reg[2] >> 3) | (bank << 2));
if (reg[3] & 8) {
setprg32(0x8000, ((reg[2] & 7) >> 1) | bank);
uint8 bank = (ctrl & 3) << 3;
setchr4(0x0000, (prgchr[0] >> 3) | (bank << 2));
setchr4(0x1000, (prgchr[1] >> 3) | (bank << 2));
if (ctrl & 8) {
setprg16(0x8000, bank | (prgchr[0] & 6) | 0); // actually, both 0 and 1 registers used, but they will switch each PA12 transition
setprg16(0xc000, bank | (prgchr[0] & 6) | 1); // if bits are different for both registers, so they must be programmed strongly the same!
} else {
setprg16(0x8000, (reg[1] & 7) | bank);
setprg16(0xc000, 7 | bank);
setprg16(0x8000, bank | (prgchr[0] & 7));
setprg16(0xc000, bank | 7 );
}
setmirror(((reg[3] & 4) >> 2) ^ 1);
setmirror(((ctrl & 4) >> 2) ^ 1);
}
static DECLFW(BMC12IN1Write) {
switch (A) {
case 0xafff: reg[0] = V; break;
case 0xbfff: reg[1] = V; break;
case 0xdfff: reg[2] = V; break;
case 0xefff: reg[3] = V; break;
switch (A & 0xE000) {
case 0xA000: prgchr[0] = V; Sync(); break;
case 0xC000: prgchr[1] = V; Sync(); break;
case 0xE000: ctrl = V & 0x0F; Sync(); break;
}
Sync();
}
static void BMC12IN1Power(void) {
reg[0] = reg[1] = reg[2] = reg[3] = 0;
prgchr[0] = prgchr[1] = ctrl = 0;
Sync();
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, BMC12IN1Write);
@@ -68,3 +70,4 @@ void BMC12IN1_Init(CartInfo *info) {
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+1
View File
@@ -76,6 +76,7 @@ static void M15Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetWriteHandler(0x8000, 0xFFFF, M15Write);
SetReadHandler(0x8000, 0xFFFF, CartBR);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
Sync();
}
+1
View File
@@ -86,6 +86,7 @@ static void M156Power(void) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetWriteHandler(0xC000, 0xCFFF, M156Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M156Close(void) {
+71
View File
@@ -0,0 +1,71 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* "Blood Of Jurassic" protected MMC3 based board (GD-98 Cart ID, 158B PCB ID)
*
*/
#include "mapinc.h"
#include "mmc3.h"
static uint8 lut[8] = { 0x00, 0x00, 0x00, 0x01, 0x02, 0x04, 0x0F, 0x00 };
static void UNL158BPW(uint32 A, uint8 V) {
if (EXPREGS[0] & 0x80) {
uint32 bank = EXPREGS[0] & 7;
if(EXPREGS[0] & 0x20) { // 32Kb mode
setprg32(0x8000, bank >> 1);
} else { // 16Kb mode
setprg16(0x8000, bank);
setprg16(0xC000, bank);
}
} else {
setprg8(A, V & 0xF);
}
}
static DECLFW(UNL158BProtWrite) {
EXPREGS[A & 7] = V;
switch(A & 7) {
case 0:
FixMMC3PRG(MMC3_cmd);
break;
case 7:
FCEU_printf("UNK PROT WRITE\n");
break;
}
}
static DECLFR(UNL158BProtRead) {
return X.DB | lut[A & 7];
}
static void UNL158BPower(void) {
GenMMC3Power();
SetWriteHandler(0x5000, 0x5FFF, UNL158BProtWrite);
SetReadHandler(0x5000, 0x5FFF, UNL158BProtRead);
}
void UNL158B_Init(CartInfo *info) {
GenMMC3_Init(info, 128, 128, 0, 0);
pwrap = UNL158BPW;
info->Power = UNL158BPower;
AddExState(EXPREGS, 8, 0, "EXPR");
}
+3
View File
@@ -102,6 +102,7 @@ static void Power(void) {
SetWriteHandler(0x5000, 0x5FFF, Write);
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
WSync();
}
@@ -155,6 +156,7 @@ static void Power2(void) {
SetWriteHandler(0x5000, 0x5FFF, Write2);
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
WSync();
}
@@ -206,6 +208,7 @@ static void Power3(void) {
SetWriteHandler(0x5000, 0x5FFF, Write3);
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
WSync();
}
+2 -2
View File
@@ -55,7 +55,7 @@ static void M168Power(void) {
SetReadHandler(0x8000, 0xFFFF, CartBR);
}
static void MNNNClose(void) {
static void M168Close(void) {
if (CHRRAM)
FCEU_gfree(CHRRAM);
CHRRAM = NULL;
@@ -67,7 +67,7 @@ static void StateRestore(int version) {
void Mapper168_Init(CartInfo *info) {
info->Power = M168Power;
info->Close = MNNNClose;
info->Close = M168Close;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
+6 -5
View File
@@ -111,15 +111,16 @@ static DECLFW(M176Write_WriteSRAM)
static void M176Power(void)
{
SetReadHandler(0x6000,0x7fff,CartBR);
SetWriteHandler(0x6000,0x7fff,M176Write_WriteSRAM);
SetReadHandler(0x8000,0xFFFF,CartBR);
SetReadHandler(0x6000,0x7fff,CartBR);
SetWriteHandler(0x6000,0x7fff,M176Write_WriteSRAM);
SetReadHandler(0x8000,0xFFFF,CartBR);
SetWriteHandler(0xA001,0xA001,M176Write_A001);
SetWriteHandler(0x5001,0x5001,M176Write_5001);
SetWriteHandler(0x5010,0x5010,M176Write_5010);
SetWriteHandler(0x5011,0x5011,M176Write_5011);
SetWriteHandler(0x5ff1,0x5ff1,M176Write_5FF1);
SetWriteHandler(0x5ff2,0x5ff2,M176Write_5FF2);
SetWriteHandler(0x5ff1,0x5ff1,M176Write_5FF1);
SetWriteHandler(0x5ff2,0x5ff2,M176Write_5FF2);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
we_sram = 0;
sbw = 0;
+1
View File
@@ -50,6 +50,7 @@ static void M177Power(void) {
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, M177Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M177Close(void) {
+68 -43
View File
@@ -29,6 +29,12 @@ static uint8 reg[4];
static uint8 *WRAM = NULL;
static uint32 WRAMSIZE;
// Tennis with VR sensor, very simple behaviour
extern void GetMouseData(uint32 (&md)[3]);
static uint32 MouseData[3], click, lastclick;
static int32 SensorDelay;
// highly experimental, not actually working, just curious if it hapen to work with some other decoder
// SND Registers
static uint8 pcm_enable = 0;
static int16 pcm_latch = 0x3F6, pcm_clock = 0x3F6;
@@ -40,41 +46,41 @@ static SFORMAT StateRegs[] =
{ 0 }
};
static int16 step_size[49] = {
16, 17, 19, 21, 23, 25, 28, 31, 34, 37,
41, 45, 50, 55, 60, 66, 73, 80, 88, 97,
107, 118, 130, 143, 157, 173, 190, 209, 230, 253,
279, 307, 337, 371, 408, 449, 494, 544, 598, 658,
724, 796, 876, 963, 1060, 1166, 1282, 1411, 1552
}; //49 items
static int32 step_adj[16] = { -1, -1, -1, -1, 2, 5, 7, 9, -1, -1, -1, -1, 2, 5, 7, 9 };
//static int16 step_size[49] = {
// 16, 17, 19, 21, 23, 25, 28, 31, 34, 37,
// 41, 45, 50, 55, 60, 66, 73, 80, 88, 97,
// 107, 118, 130, 143, 157, 173, 190, 209, 230, 253,
// 279, 307, 337, 371, 408, 449, 494, 544, 598, 658,
// 724, 796, 876, 963, 1060, 1166, 1282, 1411, 1552
//}; //49 items
//static int32 step_adj[16] = { -1, -1, -1, -1, 2, 5, 7, 9, -1, -1, -1, -1, 2, 5, 7, 9 };
//decode stuff
static int32 jedi_table[16 * 49];
static int32 acc = 0; //ADPCM accumulator, initial condition must be 0
static int32 decstep = 0; //ADPCM decoding step, initial condition must be 0
//static int32 jedi_table[16 * 49];
//static int32 acc = 0; //ADPCM accumulator, initial condition must be 0
//static int32 decstep = 0; //ADPCM decoding step, initial condition must be 0
static void jedi_table_init() {
int step, nib;
//static void jedi_table_init() {
// int step, nib;
//
// for (step = 0; step < 49; step++) {
// for (nib = 0; nib < 16; nib++) {
// int value = (2 * (nib & 0x07) + 1) * step_size[step] / 8;
// jedi_table[step * 16 + nib] = ((nib & 0x08) != 0) ? -value : value;
// }
// }
//}
for (step = 0; step < 49; step++) {
for (nib = 0; nib < 16; nib++) {
int value = (2 * (nib & 0x07) + 1) * step_size[step] / 8;
jedi_table[step * 16 + nib] = ((nib & 0x08) != 0) ? -value : value;
}
}
}
static uint8 decode(uint8 code) {
acc += jedi_table[decstep + code];
if ((acc & ~0x7ff) != 0) // acc is > 2047
acc |= ~0xfff;
else acc &= 0xfff;
decstep += step_adj[code & 7] * 16;
if (decstep < 0) decstep = 0;
if (decstep > 48 * 16) decstep = 48 * 16;
return (acc >> 8) & 0xff;
}
//static uint8 decode(uint8 code) {
// acc += jedi_table[decstep + code];
// if ((acc & ~0x7ff) != 0) // acc is > 2047
// acc |= ~0xfff;
// else acc &= 0xfff;
// decstep += step_adj[code & 7] * 16;
// if (decstep < 0) decstep = 0;
// if (decstep > 48 * 16) decstep = 48 * 16;
// return (acc >> 8) & 0xff;
//}
static void Sync(void) {
uint32 sbank = reg[1] & 0x7;
@@ -109,11 +115,11 @@ static DECLFW(M178WriteSnd) {
if (V & 0xF0) {
pcm_enable = 1;
// pcmwrite(0x4011, (V & 0xF) << 3);
pcmwrite(0x4011, decode(V & 0xf));
// pcmwrite(0x4011, decode(V & 0xf));
} else
pcm_enable = 0;
} else
FCEU_printf("misc %04x:%02x\n", A, V);
}// else
// FCEU_printf("misc %04x:%02x\n", A, V);
}
static DECLFR(M178ReadSnd) {
@@ -123,26 +129,45 @@ static DECLFR(M178ReadSnd) {
return X.DB;
}
static DECLFR(M178ReadSensor) {
X6502_IRQEnd(FCEU_IQEXT); // hacky-hacky, actual reg is 6000 and it clear IRQ while reading, but then I need another mapper lol
return 0x00;
}
static void M178Power(void) {
reg[0] = reg[1] = reg[2] = reg[3] = 0;
reg[0] = reg[1] = reg[2] = reg[3] = SensorDelay = 0;
Sync();
pcmwrite = GetWriteHandler(0x4011);
// pcmwrite = GetWriteHandler(0x4011);
SetWriteHandler(0x4800, 0x4fff, M178Write);
SetWriteHandler(0x5800, 0x5fff, M178WriteSnd);
SetReadHandler(0x5800, 0x5fff, M178ReadSnd);
SetReadHandler(0x5000, 0x5000, M178ReadSensor);
SetReadHandler(0x6000, 0x7fff, CartBR);
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetReadHandler(0x8000, 0xffff, CartBR);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M178SndClk(int a) {
if (pcm_enable) {
pcm_latch -= a;
if (pcm_latch <= 0) {
pcm_latch += pcm_clock;
pcm_enable = 0;
}
SensorDelay += a;
if(SensorDelay > 0x32768) {
SensorDelay -= 32768;
GetMouseData (MouseData);
lastclick = click;
click = MouseData[2] & 1; // to prevent from continuos IRQ trigger if button is held.
// actual circuit is just a D-C-R edge detector for IR-sensor
// triggered by the active IR bat.
if(lastclick && !click)
X6502_IRQBegin(FCEU_IQEXT);
}
// if (pcm_enable) {
// pcm_latch -= a;
// if (pcm_latch <= 0) {
// pcm_latch += pcm_clock;
// pcm_enable = 0;
// }
// }
}
static void M178Close(void) {
@@ -161,7 +186,7 @@ void Mapper178_Init(CartInfo *info) {
GameStateRestore = StateRestore;
MapIRQHook = M178SndClk;
jedi_table_init();
// jedi_table_init();
WRAMSIZE = 32768;
WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE);
+1
View File
@@ -89,6 +89,7 @@ static void M18Power(void) {
SetWriteHandler(0x8000, 0x9FFF, M18WritePrg);
SetWriteHandler(0xA000, 0xDFFF, M18WriteChr);
SetWriteHandler(0xE000, 0xFFFF, M18WriteIRQ);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M18IRQHook(int a) {
+1
View File
@@ -69,6 +69,7 @@ static void M186Power(void) {
SetWriteHandler(0x4200, 0x43FF, M186Write);
SetReadHandler(0x4400, 0x4FFF, ASWRAM);
SetWriteHandler(0x4400, 0x4FFF, BSWRAM);
FCEU_CheatAddRAM(32, 0x6000, WRAM);
regs[0] = regs[1] = regs[2] = regs[3];
Sync();
}
+1 -1
View File
@@ -39,7 +39,7 @@ static void Sync(void) {
} else
setprg32(0x8000, prg >> 1);
setchr8(chr);
setmirror(mirr);
setmirror(mirr ^ 1);
}
static DECLFW(M225Write) {
+1
View File
@@ -54,6 +54,7 @@ static void M246Power(void) {
SetReadHandler(0x6800, 0x6FFF, CartBR);
SetWriteHandler(0x6800, 0x6FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M246Close(void)
+1
View File
@@ -80,6 +80,7 @@ static void M252Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, M252Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M252IRQ(int a) {
+1
View File
@@ -96,6 +96,7 @@ static void M253Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, M253Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M253Close(void) {
+1
View File
@@ -75,6 +75,7 @@ static void M32Power(void) {
SetWriteHandler(0x9000, 0x9FFF, M32Write1);
SetWriteHandler(0xA000, 0xAFFF, M32Write2);
SetWriteHandler(0xB000, 0xBFFF, M32Write3);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M32Close(void)
+1
View File
@@ -66,6 +66,7 @@ static void M34Power(void) {
SetWriteHandler(0x6000, 0x7ffc, CartBW);
SetReadHandler(0x8000, 0xffff, CartBR);
SetWriteHandler(0x7ffd, 0xffff, M34Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M34Close(void) {
+1
View File
@@ -134,6 +134,7 @@ static void M68Power(void) {
SetWriteHandler(0xF000, 0xFFFF, M68WriteROM);
SetWriteHandler(0x6000, 0x6000, M68WriteLo);
SetWriteHandler(0x6001, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M68Close(void) {
+8 -4
View File
@@ -41,7 +41,7 @@ static SFORMAT StateRegs[] =
static void Sync(void) {
uint8 i;
if ((preg[3] & 0xC0) == 0xC0)
setprg8r(0x10, 0x6000, 0);
setprg8r(0x10, 0x6000, preg[3] & 0x3F);
else
setprg8(0x6000, preg[3] & 0x3F);
setprg8(0x8000, preg[0]);
@@ -90,8 +90,8 @@ static DECLFW(M69Write1) {
case 0xB: preg[2] = V; Sync(); break;
case 0xC: mirr = V & 3; Sync();break;
case 0xD: IRQa = V; X6502_IRQEnd(FCEU_IQEXT); break;
case 0xE: IRQCount &= 0xFF00; IRQCount |= V; X6502_IRQEnd(FCEU_IQEXT); break;
case 0xF: IRQCount &= 0x00FF; IRQCount |= V << 8; X6502_IRQEnd(FCEU_IQEXT); break;
case 0xE: IRQCount &= 0xFF00; IRQCount |= V; break;
case 0xF: IRQCount &= 0x00FF; IRQCount |= V << 8; break;
}
}
@@ -232,6 +232,7 @@ static void M69Power(void) {
SetWriteHandler(0xA000, 0xBFFF, M69Write1);
SetWriteHandler(0xC000, 0xDFFF, M69SWrite0);
SetWriteHandler(0xE000, 0xFFFF, M69SWrite1);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M69Close(void) {
@@ -257,7 +258,10 @@ void Mapper69_Init(CartInfo *info) {
info->Power = M69Power;
info->Close = M69Close;
MapIRQHook = M69IRQHook;
WRAMSIZE = 8192;
if(info->ines2)
WRAMSIZE = info->wram_size + info->battery_wram_size;
else
WRAMSIZE = 8192;
WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE);
SetupCartPRGMapping(0x10, WRAM, WRAMSIZE, 1);
AddExState(WRAM, WRAMSIZE, 0, "WRAM");
+1
View File
@@ -68,6 +68,7 @@ static void M82Power(void) {
SetReadHandler(0x6000, 0xffff, CartBR);
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetWriteHandler(0x7ef0, 0x7efc, M82Write); // external WRAM might end at $73FF
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M82Close(void) {
+67
View File
@@ -0,0 +1,67 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2016 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* 8-in-1 Rockin' Kats, Snake, (PCB marked as "8 in 1"), similar to 12IN1,
* but with MMC3 on board, all games are hacked the same, Snake is buggy too!
*
* no reset-citcuit, so selected game can be reset, but to change it you must use power
*
*/
#include "mapinc.h"
#include "mmc3.h"
static void BMC8IN1CW(uint32 A, uint8 V) {
setchr1(A, ((EXPREGS[0] & 0xC) << 5) | (V & 0x7F));
}
static void BMC8IN1PW(uint32 A, uint8 V) {
if(EXPREGS[0] & 0x10) { // MMC3 mode
setprg8(A, ((EXPREGS[0] & 0xC) << 2) | (V & 0xF));
} else {
setprg32(0x8000, EXPREGS[0] & 0xF);
}
}
static DECLFW(BMC8IN1Write) {
if(A & 0x1000) {
EXPREGS[0] = V;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
} else {
if(A < 0xC000)
MMC3_CMDWrite(A, V);
else
MMC3_IRQWrite(A, V);
}
}
static void BMC8IN1Power(void) {
EXPREGS[0] = 0;
GenMMC3Power();
SetWriteHandler(0x8000, 0xFFFF, BMC8IN1Write);
}
void BMC8IN1_Init(CartInfo *info) {
GenMMC3_Init(info, 128, 128, 0, 0);
cwrap = BMC8IN1CW;
pwrap = BMC8IN1PW;
info->Power = BMC8IN1Power;
AddExState(EXPREGS, 1, 0, "EXPR");
}
+1
View File
@@ -51,6 +51,7 @@ static void M99Power(void) {
SetWriteHandler(0x4016, 0x4016, M99Write);
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M99Close(void)
+79
View File
@@ -0,0 +1,79 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* "Dragon Fighter" protected MMC3 based custom mapper board
* mostly hacky implementation, I can't verify if this mapper can read a RAM of the
* console or watches the bus writes somehow.
*
*/
#include "mapinc.h"
#include "mmc3.h"
static void UNLBMW8544PW(uint32 A, uint8 V) {
if(A == 0x8000)
setprg8(A,EXPREGS[0] & 0x1F); // the real hardware has this bank overrided with it's own register,
else // but MMC3 prg swap still works and you can actually change bank C000 at the same time if use 0x46 cmd
setprg8(A,V);
}
static void UNLBMW8544CW(uint32 A, uint8 V) {
if(A == 0x0000)
setchr2(0x0000,(V >> 1) ^ EXPREGS[1]);
else if (A == 0x0800)
setchr2(0x0800,(V >> 1) | ((EXPREGS[2] & 0x40) << 1));
else if (A == 0x1000)
setchr4(0x1000, EXPREGS[2] & 0x3F);
}
static DECLFW(UNLBMW8544ProtWrite) {
if(!(A & 1)) {
EXPREGS[0] = V;
FixMMC3PRG(MMC3_cmd);
}
}
static DECLFR(UNLBMW8544ProtRead) {
if(!fceuindbg) {
if(!(A & 1)) {
if((EXPREGS[0] & 0xE0) == 0xC0) {
EXPREGS[1] = ARead[0x6a](0x6a); // program can latch some data from the BUS, but I can't say how exactly,
} else { // without more euipment and skills ;) probably here we can try to get any write
EXPREGS[2] = ARead[0xff](0xff); // before the read operation
}
FixMMC3CHR(MMC3_cmd & 0x7F); // there are more different behaviour of the board isn't used by game itself, so unimplemented here and
} // actually will break the current logic ;)
}
return 0;
}
static void UNLBMW8544Power(void) {
GenMMC3Power();
SetWriteHandler(0x6000, 0x6FFF, UNLBMW8544ProtWrite);
SetReadHandler(0x6000, 0x6FFF, UNLBMW8544ProtRead);
}
void UNLBMW8544_Init(CartInfo *info) {
GenMMC3_Init(info, 128, 256, 0, 0);
pwrap = UNLBMW8544PW;
cwrap = UNLBMW8544CW;
info->Power = UNLBMW8544Power;
AddExState(EXPREGS, 3, 0, "EXPR");
}
+62
View File
@@ -0,0 +1,62 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* BMC F-15 PCB (256+266 MMC3 based, with 16/32Kb banking discrete logic)
* 150-in-1 Unchaied Melody FIGHT version with system test (START+SELECT)
*
* CHR - MMC3 stock regs
* PRG - MMC3 regs disabled, area 6000-7FFF used instead
* 011xxxxxxxxxxxxx addr mask,
* ----APPp reg bits mask
* A - higher 128K PRG bank select/32K bank mode override
* PP - bank number in 32K mode
* PPp - bank number in 16K mode
* initial state of extra regs is undefined, A001 enables/disables the 6000 area
*/
#include "mapinc.h"
#include "mmc3.h"
static void BMCF15PW(uint32 A, uint8 V) {
uint32 bank = EXPREGS[0] & 0xF;
uint32 mode = (EXPREGS[0] & 8) >> 3;
uint32 mask = ~(mode);
setprg16(0x8000, (bank & mask));
setprg16(0xC000, (bank & mask) | mode);
}
static DECLFW(BMCF15Write) {
if (A001B & 0x80) {
EXPREGS[0] = V & 0xF;
FixMMC3PRG(MMC3_cmd);
}
}
static void BMCF15Power(void) {
GenMMC3Power();
SetWriteHandler(0x6000, 0x7FFF, BMCF15Write);
SetWriteHandler(0x6000, 0x7FFF, BMCF15Write);
}
void BMCF15_Init(CartInfo *info) {
GenMMC3_Init(info, 256, 256, 0, 0);
pwrap = BMCF15PW;
info->Power = BMCF15Power;
AddExState(EXPREGS, 1, 0, "EXPR");
}
+2 -1
View File
@@ -44,6 +44,7 @@ static void LatchPower(void) {
if (WRAM) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
} else
SetReadHandler(0x6000, 0xFFFF, defread);
SetWriteHandler(addrreg0, addrreg1, LatchWrite);
@@ -302,7 +303,7 @@ static void M212Sync(void) {
}
void Mapper212_Init(CartInfo *info) {
Latch_Init(info, M212Sync, M212Read, 0xFFFF, 0x8000, 0xFFFF, 0);
Latch_Init(info, M212Sync, M212Read, 0x0000, 0x8000, 0xFFFF, 0);
}
//------------------ Map 213 ---------------------------
+1
View File
@@ -270,6 +270,7 @@ static void M153Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, BandaiWrite);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
+146
View File
@@ -0,0 +1,146 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3, ClusteR
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* CoolBoy 400-in-1 FK23C-mimic mapper 16Mb/32Mb PROM + 128K/256K CHR RAM, optional SRAM, optional NTRAM
* only MMC3 mode
*
* 6000 (xx76x210) | 0xC0
* 6001 (xxx354x)
* 6002 = 0
* 6003 = 0
*
* hardware tested logic, don't try to understand lol
*/
#include "mapinc.h"
#include "mmc3.h"
static void COOLBOYCW(uint32 A, uint8 V) {
uint32 mask = 0xFF ^ (EXPREGS[0] & 0x80);
if (EXPREGS[3] & 0x10) {
if (EXPREGS[3] & 0x40) { // Weird mode
int cbase = (MMC3_cmd & 0x80) << 5;
switch (cbase ^ A) { // Don't even try do understand
case 0x0400:
case 0x0C00: V &= 0x7F; break;
}
}
// Highest bit goes from MMC3 registers when EXPREGS[3]&0x80==0 or from EXPREGS[0]&0x08 otherwise
setchr1(A,
(V & 0x80 & mask) | ((((EXPREGS[0] & 0x08) << 4) & ~mask)) // 7th bit
| ((EXPREGS[2] & 0x0F) << 3) // 6-3 bits
| ((A >> 10) & 7) // 2-0 bits
);
} else {
if (EXPREGS[3] & 0x40) { // Weird mode, again
int cbase = (MMC3_cmd & 0x80) << 5;
switch (cbase ^ A) { // Don't even try do understand
case 0x0000: V = DRegBuf[0]; break;
case 0x0800: V = DRegBuf[1]; break;
case 0x0400:
case 0x0C00: V = 0; break;
}
}
// Simple MMC3 mode
// Highest bit goes from MMC3 registers when EXPREGS[3]&0x80==0 or from EXPREGS[0]&0x08 otherwise
setchr1(A, (V & mask) | (((EXPREGS[0] & 0x08) << 4) & ~mask));
}
}
static void COOLBOYPW(uint32 A, uint8 V) {
uint32 mask = ((0x3F | (EXPREGS[1] & 0x40) | ((EXPREGS[1] & 0x20) << 2)) ^ ((EXPREGS[0] & 0x40) >> 2)) ^ ((EXPREGS[1] & 0x80) >> 2);
uint32 base = ((EXPREGS[0] & 0x07) >> 0) | ((EXPREGS[1] & 0x10) >> 1) | ((EXPREGS[1] & 0x0C) << 2) | ((EXPREGS[0] & 0x30) << 2);
// Very weird mode
// Last banks are first in this mode, ignored when MMC3_cmd&0x40
if ((EXPREGS[3] & 0x40) && (V >= 0xFE) && !((MMC3_cmd & 0x40) != 0)) {
switch (A & 0xE000) {
case 0xA000:
if ((MMC3_cmd & 0x40)) V = 0;
break;
case 0xC000:
if (!(MMC3_cmd & 0x40)) V = 0;
break;
case 0xE000:
V = 0;
break;
}
}
// Regular MMC3 mode, internal ROM size can be up to 2048kb!
if (!(EXPREGS[3] & 0x10))
setprg8(A, (((base << 4) & ~mask)) | (V & mask));
else { // NROM mode
mask &= 0xF0;
uint8 emask;
if ((((EXPREGS[1] & 2) != 0))) // 32kb mode
emask = (EXPREGS[3] & 0x0C) | ((A & 0x4000) >> 13);
else // 16kb mode
emask = EXPREGS[3] & 0x0E;
setprg8(A, ((base << 4) & ~mask) // 7-4 bits are from base (see below)
| (V & mask) // ... or from MM3 internal regs, depends on mask
| emask // 3-1 (or 3-2 when (EXPREGS[3]&0x0C is set) from EXPREGS[3]
| ((A & 0x2000) >> 13)); // 0th just as is
}
}
static DECLFW(COOLBOYWrite) {
if(A001B & 0x80)
CartBW(A,V);
// Deny any further writes when 7th bit is 1 AND 4th is 0
if ((EXPREGS[3] & 0x90) != 0x80) {
EXPREGS[A & 3] = V;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
}
}
static void COOLBOYReset(void) {
MMC3RegReset();
EXPREGS[0] = EXPREGS[1] = EXPREGS[2] = EXPREGS[3] = 0;
// EXPREGS[0] = 0;
// EXPREGS[1] = 0x60;
// EXPREGS[2] = 0;
// EXPREGS[3] = 0;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
}
static void COOLBOYPower(void) {
GenMMC3Power();
EXPREGS[0] = EXPREGS[1] = EXPREGS[2] = EXPREGS[3] = 0;
// EXPREGS[0] = 0;
// EXPREGS[1] = 0x60;
// EXPREGS[2] = 0;
// EXPREGS[3] = 0;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
SetWriteHandler(0x5000, 0x5fff, CartBW); // some games access random unmapped areas and crashes because of KT-008 PCB hack in MMC3 source lol
SetWriteHandler(0x6000, 0x7fff, COOLBOYWrite);
}
void COOLBOY_Init(CartInfo *info) {
GenMMC3_Init(info, 512, 256, 8, 0);
pwrap = COOLBOYPW;
cwrap = COOLBOYCW;
info->Power = COOLBOYPower;
info->Reset = COOLBOYReset;
AddExState(EXPREGS, 4, 0, "EXPR");
}
+1
View File
@@ -67,6 +67,7 @@ static void UNLD2000Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, UNLD2000Read);
SetWriteHandler(0x5000, 0x5FFF, UNLD2000Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNL2000Hook(uint32 A) {
+28 -11
View File
@@ -30,7 +30,7 @@ static void (*WSync)(void);
static DECLFW(LatchWrite) {
// FCEU_printf("bs %04x %02x\n",A,V);
if (bus_conflict)
latche = (V == CartBR(A)) ? V : 0;
latche = V & CartBR(A);
else
latche = V;
WSync();
@@ -42,6 +42,7 @@ static void LatchPower(void) {
if (WRAM) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
} else {
SetReadHandler(0x8000, 0xFFFF, CartBR);
}
@@ -92,7 +93,7 @@ static DECLFW(NROMWrite) {
static void NROMPower(void) {
setprg8r(0x10, 0x6000, 0); // Famili BASIC (v3.0) need it (uses only 4KB), FP-BASIC uses 8KB
setprg16(0x8000, 0);
setprg16(0x8000, ~1);
setprg16(0xC000, ~0);
setchr8(0);
@@ -100,7 +101,9 @@ static void NROMPower(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
#ifdef DEBUG_MAPPER
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
#ifdef DEBUG_MAPPER
SetWriteHandler(0x4020, 0xFFFF, NROMWrite);
#endif
}
@@ -122,14 +125,14 @@ void NROM_Init(CartInfo *info) {
//------------------ Map 2 ---------------------------
static void UNROMSync(void) {
static uint32 mirror_in_use = 0;
if (PRGsize[0] <= 128 * 1024) {
setprg16(0x8000, latche & 0x7);
if (latche & 8) mirror_in_use = 1;
if (mirror_in_use)
setmirror(((latche >> 3) & 1) ^ 1); // Higway Star Hacked mapper
} else
setprg16(0x8000, latche & 0xf);
// static uint32 mirror_in_use = 0;
// if (PRGsize[0] <= 128 * 1024) {
// setprg16(0x8000, latche & 0x7);
// if (latche & 8) mirror_in_use = 1;
// if (mirror_in_use)
// setmirror(((latche >> 3) & 1) ^ 1); // Higway Star Hacked mapper, disabled till new mapper defined
// } else
setprg16(0x8000, latche);
setprg16(0xc000, ~0);
setchr8(0);
}
@@ -201,6 +204,20 @@ void CPROM_Init(CartInfo *info) {
Latch_Init(info, CPROMSync, 0, 0x8000, 0xFFFF, 0, 0);
}
//------------------ Map 29 --------------------------- //Used by Glider, http://www.retrousb.com/product_info.php?cPath=30&products_id=58
static void M29Sync() {
setprg16(0x8000, (latche & 0x1C) >> 2);
setprg16(0xc000, ~0);
setchr8r(0, latche & 3);
setprg8r(0x10, 0x6000, 0);
}
void Mapper29_Init(CartInfo *info) {
Latch_Init(info, M29Sync, 0, 0x8000, 0xFFFF, 1, 0);
}
//------------------ Map 38 ---------------------------
static void M38Sync(void) {
+1
View File
@@ -48,6 +48,7 @@ static void UNLEDU2000Power(void) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0xFFFF, CartBW);
SetWriteHandler(0x8000, 0xFFFF, UNLEDU2000HiWrite);
FCEU_CheatAddRAM(32, 0x6000, WRAM);
reg = 0;
Sync();
}
+83
View File
@@ -0,0 +1,83 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "mapinc.h"
static uint16 addrlatch;
static uint8 datalatch, hw_mode;
static SFORMAT StateRegs[] =
{
{ &addrlatch, 2, "ADRL" },
{ &datalatch, 1, "DATL" },
{ &hw_mode, 1, "HWMO" },
{ 0 }
};
static void Sync(void) {
uint8 prg = (addrlatch & 7);
setchr8(datalatch);
if(addrlatch & 0x80) {
setprg16(0x8000,prg);
setprg16(0xC000,prg);
} else {
setprg32(0x8000,prg >> 1);
}
setmirror(MI_V);
}
static DECLFW(EH8813AWrite) {
if((addrlatch & 0x100) == 0) {
addrlatch = A & 0x1FF;
datalatch = V & 0xF;
}
Sync();
}
static DECLFR(EH8813ARead) {
if (addrlatch & 0x40)
A= (A & 0xFFF0) + hw_mode;
return CartBR(A);
}
static void EH8813APower(void) {
addrlatch = datalatch = hw_mode = 0;
Sync();
SetReadHandler(0x8000, 0xFFFF, EH8813ARead);
SetWriteHandler(0x8000, 0xFFFF, EH8813AWrite);
}
static void EH8813AReset(void) {
addrlatch = datalatch = 0;
hw_mode = (hw_mode + 1) & 0xF;
FCEU_printf("Hardware Switch is %01X\n", hw_mode);
Sync();
}
static void StateRestore(int version) {
Sync();
}
void UNLEH8813A_Init(CartInfo *info) {
info->Reset = EH8813AReset;
info->Power = EH8813APower;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+103
View File
@@ -0,0 +1,103 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 Cluster
* http://clusterrr.com
* clusterrr@clusterrr.com
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/*
MMC3-based multicart mapper with CHR RAM, CHR ROM and PRG RAM
$6000-7FFF: A~[011xxxxx xxMRSBBB] Multicart reg
This register can only be written to if PRG-RAM is enabled and writable (see $A001)
and BBB = 000 (power on state)
BBB = CHR+PRG block select bits (A19, A18, A17 for both PRG and CHR)
S = PRG block size (0=256k 1=128k)
R = CHR mode (0=CHR ROM 1=CHR RAM)
M = CHR block size (0=256k 1=128k)
ignored when S is 0 for some reason
Example Game:
--------------------------
6 in 1 multicart (SMB3, TMNT2, Contra, Ninja Cat, Ninja Crusaders, Rainbow Islands 2)
*/
#include "mapinc.h"
#include "mmc3.h"
static uint8 *CHRRAM;
static uint32 CHRRAMSize;
static void BMC1024CA1PW(uint32 A, uint8 V) {
if ((EXPREGS[0]>>3)&1)
setprg8(A, (V&0x1F) | ((EXPREGS[0] & 7) << 4));
else
setprg8(A, (V&0x0F) | ((EXPREGS[0] & 7) << 4));
}
static void BMC1024CA1CW(uint32 A, uint8 V) {
if ((EXPREGS[0]>>4)&1)
setchr1r(0x10, A, V);
else if (((EXPREGS[0]>>5)&1) && ((EXPREGS[0]>>3)&1))
setchr1(A, V | ((EXPREGS[0] & 7) << 7));
else
setchr1(A, (V&0x7F) | ((EXPREGS[0] & 7) << 7));
}
static DECLFW(BMC1024CA1Write) {
if (((A001B & 0xC0) == 0x80) && !(EXPREGS[0] & 7))
{
EXPREGS[0] = A & 0x3F;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
} else {
CartBW(A, V);
}
}
static void BMC1024CA1Reset(void) {
EXPREGS[0] = 0;
MMC3RegReset();
}
static void BMC1024CA1Power(void) {
EXPREGS[0] = 0;
GenMMC3Power();
SetWriteHandler(0x6000, 0x7FFF, BMC1024CA1Write);
}
static void BMC1024CA1Close(void) {
if (CHRRAM)
FCEU_gfree(CHRRAM);
CHRRAM = NULL;
}
void BMC1024CA1_Init(CartInfo *info) {
GenMMC3_Init(info, 256, 256, 8, 0);
CHRRAMSize = 8192;
CHRRAM = (uint8*)FCEU_gmalloc(CHRRAMSize);
SetupCartCHRMapping(0x10, CHRRAM, CHRRAMSize, 1);
AddExState(CHRRAM, CHRRAMSize, 0, "CHRR");
pwrap = BMC1024CA1PW;
cwrap = BMC1024CA1CW;
info->Power = BMC1024CA1Power;
info->Reset = BMC1024CA1Reset;
info->Close = BMC1024CA1Close;
AddExState(EXPREGS, 1, 0, "EXPR");
}
+119
View File
@@ -0,0 +1,119 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2016 Cluster
* http://clusterrr.com
* clusterrr@clusterrr.com
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/*
MMC3-based multicart mapper with CHR RAM, CHR ROM and PRG RAM
$6000-7FFF: A~[011xxxxx xxMRSBBB] Multicart reg
This register can only be written to if PRG-RAM is enabled and writable (see $A001)
and BBB = 000 (power on state)
BBB = CHR+PRG block select bits (A19, A18, A17 for both PRG and CHR)
S = PRG block size & mirroring mode (0=128k with normal MMC3, 1=256k with TxSROM-like single-screen mirroring)
R = CHR mode (0=CHR ROM 1=CHR RAM)
M = CHR block size (0=256k 1=128k)
ignored when S is 0 for some reason
Example Game:
--------------------------
7 in 1 multicart (Amarello, TMNT2, Contra, Ninja Cat, Ninja Crusaders, Rainbow Islands 2)
*/
#include "mapinc.h"
#include "mmc3.h"
static uint8 *CHRRAM;
static uint32 CHRRAMSize;
static uint8 PPUCHRBus;
static uint8 TKSMIR[8];
static void BMC810131C_PW(uint32 A, uint8 V) {
if ((EXPREGS[0] >> 3) & 1)
setprg8(A, (V & 0x1F) | ((EXPREGS[0] & 7) << 4));
else
setprg8(A, (V & 0x0F) | ((EXPREGS[0] & 7) << 4));
}
static void BMC810131C_CW(uint32 A, uint8 V) {
if ((EXPREGS[0] >> 4) & 1)
setchr1r(0x10, A, V);
else if (((EXPREGS[0] >> 5) & 1) && ((EXPREGS[0] >> 3) & 1))
setchr1(A, V | ((EXPREGS[0] & 7) << 7));
else
setchr1(A, (V & 0x7F) | ((EXPREGS[0] & 7) << 7));
TKSMIR[A >> 10] = V >> 7;
if (((EXPREGS[0] >> 3) & 1) && (PPUCHRBus == (A >> 10)))
setmirror(MI_0 + (V >> 7));
}
static DECLFW(BMC810131C_Write) {
if (((A001B & 0xC0) == 0x80) && !(EXPREGS[0] & 7))
{
EXPREGS[0] = A & 0x3F;
FixMMC3PRG(MMC3_cmd);
FixMMC3CHR(MMC3_cmd);
}
else {
CartBW(A, V);
}
}
static void BMC810131C_Reset(void) {
EXPREGS[0] = 0;
MMC3RegReset();
}
static void BMC810131C_Power(void) {
EXPREGS[0] = 0;
GenMMC3Power();
SetWriteHandler(0x6000, 0x7FFF, BMC810131C_Write);
}
static void BMC810131C_Close(void) {
if (CHRRAM)
FCEU_gfree(CHRRAM);
CHRRAM = NULL;
}
static void TKSPPU(uint32 A) {
A &= 0x1FFF;
A >>= 10;
PPUCHRBus = A;
if ((EXPREGS[0] >> 3) & 1)
setmirror(MI_0 + TKSMIR[A]);
}
void BMC810131C_Init(CartInfo *info) {
GenMMC3_Init(info, 256, 256, 8, 0);
CHRRAMSize = 8192;
CHRRAM = (uint8*)FCEU_gmalloc(CHRRAMSize);
SetupCartCHRMapping(0x10, CHRRAM, CHRRAMSize, 1);
AddExState(CHRRAM, CHRRAMSize, 0, "CHRR");
pwrap = BMC810131C_PW;
cwrap = BMC810131C_CW;
PPU_hook = TKSPPU;
info->Power = BMC810131C_Power;
info->Reset = BMC810131C_Reset;
info->Close = BMC810131C_Close;
AddExState(EXPREGS, 1, 0, "EXPR");
}
+1 -1
View File
@@ -79,6 +79,7 @@ static void SSSNROMPower(void) {
SetReadHandler(0x6000, 0x7FFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void SSSNROMReset(void) {
@@ -109,7 +110,6 @@ void SSSNROM_Init(CartInfo *info) {
WRAMSIZE = 16384;
WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE);
SetupCartPRGMapping(0x10, WRAM, WRAMSIZE, 1);
AddExState(WRAM, WRAMSIZE, 0, "WRAM");
AddExState(&StateRegs, ~0, 0, 0);
}
+1
View File
@@ -102,6 +102,7 @@ static void FFEPower(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x6000, 0x7FFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, FFEWriteLatch);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void FFEIRQHook(int a) {
+69
View File
@@ -0,0 +1,69 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2015 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "mapinc.h"
static uint8 regs[2];
static SFORMAT StateRegs[] =
{
{ regs, 2, "REGS" },
{ 0 }
};
static void Sync(void) {
uint8 chr = (regs[0] >> 4) & 7;
uint8 prg = (regs[1] >> 3) & 7;
uint8 dec = (regs[1] >> 4) & 4;
setchr8(chr & (~(((regs[0] & 1) << 2) | (regs[0] & 2))));
setprg16(0x8000,prg & (~dec));
setprg16(0xC000,prg | dec);
setmirror(regs[1] >> 7);
}
static DECLFW(HP898FWrite) {
if((A & 0x6000) == 0x6000) {
regs[(A & 4) >> 2] = V;
Sync();
}
}
static void HP898FPower(void) {
regs[0] = regs[1] = 0;
Sync();
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0xFFFF, HP898FWrite);
}
static void HP898FReset(void) {
regs[0] = regs[1] = 0;
Sync();
}
static void StateRestore(int version) {
Sync();
}
void BMCHP898F_Init(CartInfo *info) {
info->Reset = HP898FReset;
info->Power = HP898FPower;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+62
View File
@@ -0,0 +1,62 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2002 Xodnizel
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "mapinc.h"
static uint8 regs[8];
static SFORMAT StateRegs[] =
{
{ regs, 8, "REGS" },
{ 0 }
};
static void Sync(void) {
for (int i=0; i < 8; ++i)
{
setprg4(0x8000 + (0x1000 * i), regs[i]);
}
}
static DECLFW(M31Write) {
if (A >= 0x5000 && A <= 0x5FFF)
{
regs[A&7] = V;
Sync();
}
}
static void M31Power(void) {
setchr8(0);
regs[7] = 0xFF;
Sync();
SetReadHandler(0x8000, 0xffff, CartBR);
SetWriteHandler(0x5000, 0x5fff, M31Write);
}
static void StateRestore(int version) {
Sync();
}
void Mapper31_Init(CartInfo *info) {
info->Power = M31Power;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+85
View File
@@ -0,0 +1,85 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2007 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "mapinc.h"
static uint8 preg[4], creg, mirr;
static SFORMAT StateRegs[] =
{
{ preg, 4, "PREG" },
{ &creg, 1, "CREG" },
{ &mirr, 1, "MIRR" },
{ 0 }
};
static void Sync(void) {
setprg8(0x6000, preg[0]);
setprg8(0x8000, 0xa);
setprg8(0xa000, 0xb);
setprg8(0xc000, 0x6);
setprg8(0xe000, 0x7);
setchr8(0x0c);
setmirror(mirr);
}
static DECLFW(UNLKS7010Write) {
switch (A) {
case 0x4025: mirr = (((V >> 3) & 1) ^ 1); Sync(); break;
default:
FCEU_printf("bs %04x %02x\n",A,V);
break;
}
}
static void UNLKS7010Reset(void) {
preg[0]++;
if(preg[0] == 0x10) {
preg[0] = 0;
preg[1]++;
if(preg[1] == 0x10) {
preg[1] = 0;
preg[2]++;
}
}
FCEU_printf("preg %02x %02x %02x\n",preg[0], preg[1], preg[2]);
Sync();
}
static void UNLKS7010Power(void) {
preg[0] = preg[1] = preg[2] = 0;
Sync();
SetReadHandler(0x6000, 0x7fff, CartBR);
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetReadHandler(0x8000, 0xffff, CartBR);
SetWriteHandler(0x4020, 0xffff, UNLKS7010Write);
}
static void StateRestore(int version) {
Sync();
}
void UNLKS7010_Init(CartInfo *info) {
info->Power = UNLKS7010Power;
info->Reset = UNLKS7010Reset;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+1
View File
@@ -51,6 +51,7 @@ static void UNLKS7012Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, UNLKS7012Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNLKS7012Reset(void) {
+85
View File
@@ -0,0 +1,85 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2016 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* FDS Conversion (Exciting Basket), weird banking addressing, seems because
* of used addressing scheme, made to disable the lower system banks from 6000
* but the kaiser mapper chip and PCB are the same as usual
* probably need a hard eprom dump to verify actual banks layout
*
*/
#include "mapinc.h"
static uint8 preg;
static SFORMAT StateRegs[] =
{
{ &preg, 1, "PREG" },
{ 0 }
};
static void Sync(void) {
setprg8(0x6000, preg);
setprg8(0x8000, 0xC);
setprg8(0xA000, 0xD);
setprg8(0xC000, 0xE);
setprg8(0xE000, 0xF);
setchr8(0);
}
static DECLFW(UNLKS7016Write) {
u16 mask = (A & 0x30);
switch(A & 0xD943) {
case 0xD943: {
if(mask == 0x30) {
preg = 8 | 3; // or A, or no bus (all FF)
} else {
preg = (A >> 2) & 0xF; // can be anything but C-F
}
Sync();
break;
}
case 0xD903: { // this case isn't usedby the game, but addressing does this as a side effect
if(mask == 0x30) {
preg = 8 | ((A >> 2) & 3); // also masked C-F from output
} else {
preg = 8 | 3;
}
Sync();
break;
}
}
}
static void UNLKS7016Power(void) {
preg = 8;
Sync();
SetReadHandler(0x6000, 0xffff, CartBR);
SetWriteHandler(0x8000, 0xffff, UNLKS7016Write);
}
static void StateRestore(int version) {
Sync();
}
void UNLKS7016_Init(CartInfo *info) {
info->Power = UNLKS7016Power;
GameStateRestore = StateRestore;
AddExState(&StateRegs, ~0, 0, 0);
}
+1
View File
@@ -87,6 +87,7 @@ static void UNLKS7017Power(void) {
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetReadHandler(0x4030, 0x4030, FDSRead4030);
SetWriteHandler(0x4020, 0x5FFF, UNLKS7017Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNLKS7017Close(void) {
+1
View File
@@ -82,6 +82,7 @@ static void LH10Power(void) {
SetWriteHandler(0x8000, 0xBFFF, UNLKS7037Write);
SetWriteHandler(0xC000, 0xDFFF, CartBW);
SetWriteHandler(0xE000, 0xFFFF, UNLKS7037Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void Close(void) {
+1
View File
@@ -52,6 +52,7 @@ static void LH32Power(void) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0xC000, 0xDFFF, CartBW);
SetWriteHandler(0x6000, 0x6000, LH32Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void LH32Close(void) {
+1
View File
@@ -80,6 +80,7 @@ static void LH53Power(void) {
SetWriteHandler(0xB800, 0xD7FF, LH53RamWrite);
SetWriteHandler(0xE000, 0xEFFF, LH53IRQaWrite);
SetWriteHandler(0xF000, 0xFFFF, LH53Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void LH53Close(void) {
+16 -15
View File
@@ -73,37 +73,38 @@ static void MMC1CHR(void) {
}
static void MMC1PRG(void) {
uint8 offs = DRegs[1] & 0x10;
uint8 offs_16banks = DRegs[1] & 0x10;
uint8 prg_reg = DRegs[3] & 0xF; //homebrewers arent allowed to use more banks on MMC1. use another mapper.
if (MMC1PRGHook16) {
switch (DRegs[0] & 0xC) {
case 0xC:
MMC1PRGHook16(0x8000, (DRegs[3] + offs));
MMC1PRGHook16(0xC000, 0xF + offs);
MMC1PRGHook16(0x8000, (prg_reg + offs_16banks));
MMC1PRGHook16(0xC000, 0xF + offs_16banks);
break;
case 0x8:
MMC1PRGHook16(0xC000, (DRegs[3] + offs));
MMC1PRGHook16(0x8000, offs);
MMC1PRGHook16(0xC000, (prg_reg + offs_16banks));
MMC1PRGHook16(0x8000, offs_16banks);
break;
case 0x0:
case 0x4:
MMC1PRGHook16(0x8000, ((DRegs[3] & ~1) + offs));
MMC1PRGHook16(0xc000, ((DRegs[3] & ~1) + offs + 1));
MMC1PRGHook16(0x8000, ((prg_reg & ~1) + offs_16banks));
MMC1PRGHook16(0xc000, ((prg_reg & ~1) + offs_16banks + 1));
break;
}
} else {
switch (DRegs[0] & 0xC) {
case 0xC:
setprg16(0x8000, (DRegs[3] + offs));
setprg16(0xC000, 0xF + offs);
setprg16(0x8000, (prg_reg + offs_16banks));
setprg16(0xC000, 0xF + offs_16banks);
break;
case 0x8:
setprg16(0xC000, (DRegs[3] + offs));
setprg16(0x8000, offs);
setprg16(0xC000, (prg_reg + offs_16banks));
setprg16(0x8000, offs_16banks);
break;
case 0x0:
case 0x4:
setprg16(0x8000, ((DRegs[3] & ~1) + offs));
setprg16(0xc000, ((DRegs[3] & ~1) + offs + 1));
setprg16(0x8000, ((prg_reg & ~1) + offs_16banks));
setprg16(0xc000, ((prg_reg & ~1) + offs_16banks + 1));
break;
}
}
@@ -247,8 +248,8 @@ static void GenMMC1Power(void) {
FCEU_CheatAddRAM(8, 0x6000, WRAM);
if (mmc1opts & 4)
FCEU_dwmemset(WRAM, 0, 8192)
else if (!(mmc1opts & 2))
FCEU_dwmemset(WRAM, 0, 8192);
else if (!(mmc1opts & 2))
FCEU_dwmemset(WRAM, 0, 8192); // wtf?
}
SetWriteHandler(0x8000, 0xFFFF, MMC1_write);
SetReadHandler(0x8000, 0xFFFF, CartBR);
+1
View File
@@ -95,6 +95,7 @@ static void MMC2and4Power(void) {
if (is10) {
SetReadHandler(0x6000, 0x7FFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0xA000, 0xFFFF, MMC2and4Write);
+36 -9
View File
@@ -28,6 +28,7 @@
#include "mmc3.h"
uint8 MMC3_cmd;
uint8 kt_extra;
uint8 *WRAM;
uint32 WRAMSIZE;
uint8 *CHRRAM;
@@ -182,6 +183,17 @@ DECLFW(MMC3_IRQWrite) {
}
}
// KT-008 boards hack 2-in-1, TODO assign to new ines mapper, most dump of KT-boards on the net are mapper 4, so need database or goodnes fix support
DECLFW(KT008HackWrite) {
// FCEU_printf("%04x:%04x\n",A,V);
switch (A & 3) {
case 0: kt_extra = V; FixMMC3PRG(MMC3_cmd); break;
case 1: break; // unk
case 2: break; // unk
case 3: break; // unk
}
}
static void ClockMMC3Counter(void) {
int count = IRQCount;
if (!count || IRQReload) {
@@ -220,7 +232,10 @@ static void GENCWRAP(uint32 A, uint8 V) {
}
static void GENPWRAP(uint32 A, uint8 V) {
setprg8(A, V & 0x7F); // [NJ102] Mo Dao Jie (C) has 1024Mb MMC3 BOARD, maybe something other will be broken
// [NJ102] Mo Dao Jie (C) has 1024Mb MMC3 BOARD, maybe something other will be broken
// also HengGe BBC-2x boards enables this mode as default board mode at boot up
setprg8(A, (V & 0x7F) | ((kt_extra & 4) << 4));
// KT-008 boards hack 2-in-1, TODO assign to new ines mapper, most dump of KT-boards on the net are mapper 4, so need database or goodnes fix support
}
static void GENMWRAP(uint8 V) {
@@ -246,6 +261,10 @@ void GenMMC3Power(void) {
SetWriteHandler(0x8000, 0xBFFF, MMC3_CMDWrite);
SetWriteHandler(0xC000, 0xFFFF, MMC3_IRQWrite);
SetReadHandler(0x8000, 0xFFFF, CartBR);
// KT-008 boards hack 2-in-1, TODO assign to new ines mapper, most dump of KT-boards on the net are mapper 4, so need database or goodnes fix support
SetWriteHandler(0x5000,0x5FFF, KT008HackWrite);
A001B = A000B = 0;
setmirror(1);
if (mmc3opts & 1) {
@@ -254,7 +273,7 @@ void GenMMC3Power(void) {
SetReadHandler(0x7000, 0x7FFF, MAWRAMMMC6);
SetWriteHandler(0x7000, 0x7FFF, MBWRAMMMC6);
} else {
FCEU_CheatAddRAM((WRAMSIZE & 0x1fff) >> 10, 0x6000, WRAM);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
SetWriteHandler(0x6000, 0x6000 + ((WRAMSIZE - 1) & 0x1fff), CartBW);
SetReadHandler(0x6000, 0x6000 + ((WRAMSIZE - 1) & 0x1fff), CartBR);
setprg8r(0x10, 0x6000, 0);
@@ -299,6 +318,8 @@ void GenMMC3_Init(CartInfo *info, int prg, int chr, int wram, int battery) {
info->SaveGameLen[0] = WRAMSIZE;
}
// KT-008 boards hack 2-in-1, TODO assign to new ines mapper, most dump of KT-boards on the net are mapper 4, so need database or goodnes fix support
AddExState(&kt_extra, 1, 0, "KTEX");
AddExState(MMC3_StateRegs, ~0, 0, 0);
info->Power = GenMMC3Power;
@@ -477,13 +498,18 @@ static void M45CW(uint32 A, uint8 V) {
NV &= 0; // hack ;( don't know exactly how it should be
NV |= EXPREGS[0] | ((EXPREGS[2] & 0xF0) << 4);
setchr1(A, NV);
}
} else
// setchr8(0); // i don't know what cart need this, but a new one need other lol
setchr1(A, V);
}
static void M45PW(uint32 A, uint8 V) {
V &= (EXPREGS[3] & 0x3F) ^ 0x3F;
V |= EXPREGS[1];
setprg8(A, V);
uint32 MV = V & ((EXPREGS[3] & 0x3F) ^ 0x3F);
MV |= EXPREGS[1];
if(UNIFchrrama)
MV |= ((EXPREGS[2] & 0x40) << 2);
setprg8(A, MV);
// FCEU_printf("1:%02x 2:%02x 3:%02x A=%04x V=%03x\n",EXPREGS[1],EXPREGS[2],EXPREGS[3],A,MV);
}
static DECLFW(M45Write) {
@@ -513,7 +539,6 @@ static void M45Reset(void) {
}
static void M45Power(void) {
setchr8(0);
GenMMC3Power();
EXPREGS[0] = EXPREGS[1] = EXPREGS[2] = EXPREGS[3] = EXPREGS[4] = EXPREGS[5] = 0;
SetWriteHandler(0x5000, 0x7FFF, M45Write);
@@ -820,6 +845,7 @@ void Mapper119_Init(CartInfo *info) {
CHRRAMSIZE = 8192;
CHRRAM = (uint8*)FCEU_gmalloc(CHRRAMSIZE);
SetupCartCHRMapping(0x10, CHRRAM, CHRRAMSIZE, 1);
AddExState(CHRRAM, CHRRAMSIZE, 0, "CHRR");
}
// ---------------------------- Mapper 134 ------------------------------
@@ -1017,8 +1043,8 @@ static DECLFW(Mapper196Write) {
}
static DECLFW(Mapper196WriteLo) {
EXPREGS[0] = 1;
EXPREGS[1] = (V & 0xf) | (V >> 4);
EXPREGS[0] = 1; // hacky
EXPREGS[1] = (V & 0xf) | (V >> 4); // this is the same as 189 mapper, but with addr permutations
FixMMC3PRG(MMC3_cmd);
}
@@ -1321,6 +1347,7 @@ void TQROM_Init(CartInfo *info) {
CHRRAMSIZE = 8192;
CHRRAM = (uint8*)FCEU_gmalloc(CHRRAMSIZE);
SetupCartCHRMapping(0x10, CHRRAM, CHRRAMSIZE, 1);
AddExState(CHRRAM, CHRRAMSIZE, 0, "CHRR");
}
void HKROM_Init(CartInfo *info) {
+40 -11
View File
@@ -88,6 +88,7 @@ static uint8 MMC5LineCounter;
static uint8 mmc5psize, mmc5vsize;
static uint8 mul[2];
static uint32 WRAMSIZE = 0;
static uint8 *WRAM = NULL;
static uint8 *MMC5fill = NULL;
static uint8 *ExRAM = NULL;
@@ -137,7 +138,11 @@ static void mmc5_PPUWrite(uint32 A, uint8 V) {
uint8 FASTCALL mmc5_PPURead(uint32 A) {
if (A < 0x2000) {
if (ppuphase == PPUPHASE_BG)
if (ppuphase == PPUPHASE_BG
//zero 03-aug-2014 - added this to fix Uchuu Keibitai SDF. The game reads NT entries from CHR rom while PPU is disabled.
//obviously we have enormous numbers of bugs springing from our terrible emulation of ppu-disabled states, but this does the job for fixing this one
&& (PPU[1] & 0x10)
)
return *MMC5BGVRAMADR(A);
else return MMC5SPRVPage[(A) >> 10][(A)];
} else {
@@ -269,6 +274,7 @@ static void MMC5WRAM(uint32 A, uint32 V) {
V = MMC5WRAMIndex[V & 7];
if (V != 255) {
setprg8r(0x10, A, V);
FCEU_CheatAddRAM(8, 0x6000, (WRAM + ((V * 8192) & (WRAMSIZE - 1))));
MMC5MemIn[(A - 0x6000) >> 13] = 1;
} else
MMC5MemIn[(A - 0x6000) >> 13] = 0;
@@ -510,21 +516,40 @@ void MMC5Synco(void) {
}
void MMC5_hb(int scanline) {
if (scanline == 240) {
//zero 24-jul-2014 - revised for newer understanding, to fix metal slader glory credits. see r7371 in bizhawk
int sl = scanline + 1;
int ppuon = (PPU[1] & 0x18);
if (!ppuon || sl >= 241)
{
// whenever rendering is off for any reason (vblank or forced disable
// the irq counter resets, as well as the inframe flag (easily verifiable from software)
MMC5IRQR &= ~0x40;
MMC5IRQR &= ~0x80;
MMC5LineCounter = 0;
MMC5IRQR = 0x40;
X6502_IRQEnd(FCEU_IQEXT);
return;
}
if (MMC5LineCounter < 240) {
if (MMC5LineCounter == IRQScanline) {
if (!(MMC5IRQR&0x40))
{
MMC5IRQR |= 0x40;
MMC5IRQR &= ~0x80;
MMC5LineCounter = 0;
X6502_IRQEnd(FCEU_IQEXT);
}
else
{
MMC5LineCounter++;
if (MMC5LineCounter == IRQScanline)
{
MMC5IRQR |= 0x80;
if (IRQEnable & 0x80)
X6502_IRQBegin(FCEU_IQEXT);
}
MMC5LineCounter++;
}
if (MMC5LineCounter == 240)
MMC5IRQR = 0;
}
void MMC5_StateRestore(int version) {
@@ -727,8 +752,11 @@ void NSFMMC5_Init(void) {
}
void NSFMMC5_Close(void) {
if (WRAM)
FCEU_gfree(WRAM);
WRAM = NULL;
FCEU_gfree(ExRAM);
ExRAM = 0;
ExRAM = NULL;
}
static void GenMMC5Reset(void) {
@@ -760,7 +788,7 @@ static void GenMMC5Reset(void) {
SetReadHandler(0x5205, 0x5206, MMC5_read);
// GameHBIRQHook=MMC5_hb;
FCEU_CheatAddRAM(8, 0x6000, WRAM);
// FCEU_CheatAddRAM(8, 0x6000, WRAM);
FCEU_CheatAddRAM(1, 0x5c00, ExRAM);
}
@@ -849,7 +877,8 @@ static void GenMMC5_Init(CartInfo *info, int wsize, int battery) {
}
void Mapper5_Init(CartInfo *info) {
GenMMC5_Init(info, DetectMMC5WRAMSize(info->CRC32), info->battery);
WRAMSIZE = DetectMMC5WRAMSize(info->CRC32);
GenMMC5_Init(info, WRAMSIZE, info->battery);
}
// ELROM seems to have 0KB of WRAM
+16 -11
View File
@@ -32,17 +32,17 @@ static uint8 cpu410x[16], ppu201x[16], apu40xx[64];
// IRQ Registers
static uint8 IRQCount, IRQa, IRQReload;
#define IRQLatch cpu410x[0x1]
#define IRQLatch cpu410x[0x1] // accc cccc, a = 0, AD12 switching, a = 1, HSYNC switching
// MMC3 Registers
static uint8 inv_hack = 0; // some OneBus Systems have swapped PRG reg commans in MMC3 inplementation,
// trying to autodetect unusual behavior, due not to add a new mapper.
#define mmc3cmd cpu410x[0x5]
#define mirror cpu410x[0x6]
static uint8 inv_hack = 0; // some OneBus Systems have swapped PRG reg commans in MMC3 inplementation,
// trying to autodetect unusual behavior, due not to add a new mapper.
#define mmc3cmd cpu410x[0x5] // pcv- ----, p - program swap, c - video swap, v - internal VRAM enable
#define mirror cpu410x[0x6] // ---- ---m, m = 0 - H, m = 1 - V
// APU Registers
static uint8 pcm_enable = 0, pcm_irq = 0;
static int16 pcm_addr, pcm_size, pcm_latch, pcm_clock = 0xF6;
static int16 pcm_addr, pcm_size, pcm_latch, pcm_clock = 0xE1;
static writefunc defapuwrite[64];
static readfunc defapuread[64];
@@ -113,7 +113,7 @@ static void CSync(void) {
setchr1(0x1800 ^ cswap, block | (bank6 & mask));
setchr1(0x1c00 ^ cswap, block | (bank7 & mask));
setmirror((mirror & 1) ^ 1);
setmirror((mirror ^ 1) & 1);
}
static void Sync(void) {
@@ -124,7 +124,7 @@ static void Sync(void) {
static DECLFW(UNLOneBusWriteCPU410X) {
// FCEU_printf("CPU %04x:%04x\n",A,V);
switch (A & 0xf) {
case 0x1: IRQLatch = V & 0xfe; break;
case 0x1: IRQLatch = V & 0xfe; break; // íå ïî äàòàøèòó
case 0x2: IRQReload = 1; break;
case 0x3: X6502_IRQEnd(FCEU_IQEXT); IRQa = 0; break;
case 0x4: IRQa = 1; break;
@@ -180,17 +180,19 @@ static void UNLOneBusIRQHook(void) {
}
static DECLFW(UNLOneBusWriteAPU40XX) {
// FCEU_printf("APU %04x:%04x\n",A,V);
// if(((A & 0x3f)!=0x16) && ((apu40xx[0x30] & 0x10) || ((A & 0x3f)>0x17)))FCEU_printf("APU %04x:%04x\n",A,V);
apu40xx[A & 0x3f] = V;
switch (A & 0x3f) {
case 0x12:
if (apu40xx[0x30] & 0x10) {
pcm_addr = V << 6;
}
break;
case 0x13:
if (apu40xx[0x30] & 0x10) {
pcm_size = (V << 4) + 1;
}
break;
case 0x15:
if (apu40xx[0x30] & 0x10) {
pcm_enable = V & 0x10;
@@ -202,6 +204,7 @@ static DECLFW(UNLOneBusWriteAPU40XX) {
pcm_latch = pcm_clock;
V &= 0xef;
}
break;
}
defapuwrite[A & 0x3f](A, V);
}
@@ -214,6 +217,7 @@ static DECLFR(UNLOneBusReadAPU40XX) {
if (apu40xx[0x30] & 0x10) {
result = (result & 0x7f) | pcm_irq;
}
break;
}
return result;
}
@@ -229,7 +233,8 @@ static void UNLOneBusCpuHook(int a) {
pcm_enable = 0;
X6502_IRQBegin(FCEU_IQEXT);
} else {
uint8 raw_pcm = ARead[pcm_addr](pcm_addr) >> 1;
uint16 addr = pcm_addr | ((apu40xx[0x30]^3) << 14);
uint8 raw_pcm = ARead[addr](addr) >> 1;
defapuwrite[0x11](0x4011, raw_pcm);
pcm_addr++;
pcm_addr &= 0x7FFF;
@@ -281,7 +286,7 @@ void UNLOneBus_Init(CartInfo *info) {
info->Power = UNLOneBusPower;
info->Reset = UNLOneBusReset;
if (((*(uint32*)&(info->MD5)) == 0x305fcdc3) || // PowerJoy Supermax Carts
if (((*(uint32*)&(info->MD5)) == 0x305fcdc3) || // PowerJoy Supermax Carts
((*(uint32*)&(info->MD5)) == 0x6abfce8e))
inv_hack = 0xf;
+1
View File
@@ -101,6 +101,7 @@ static void UNLPEC586Power(void) {
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x5000, 0x5fff, UNLPEC586Write);
SetReadHandler(0x5000, 0x5fff, UNLPEC586Read);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNLPEC586Close(void) {
+53
View File
@@ -0,0 +1,53 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2016 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Test Ver. 1.01 Dlya Proverki TV Pristavok (RT-01, by SS aka Snake)
* A simple board with 16K PRG ROM + 2K CHR ROM with no mapper, hardwired mirroring
* PRG EPROM has copy protected areas with "weak bits", which is tested at some
* points of the program. Trying to simalate "weak bits" behaviour
*
*/
#include "mapinc.h"
static DECLFR(UNLRT01Read) {
// u16 i, prot_areas[2][2] = {
// { 0x8E80, 0x8EFF },
// { 0xFE80, 0xFEFF },
// };
if(((A >= 0xCE80) && (A < 0xCF00)) ||
((A >= 0xFE80) && (A < 0xFF00))) {
return 0xF2 | (rand() & 0x0D);
} else
return CartBR(A);
}
static void UNLRT01Power(void) {
setprg16(0x8000, 0);
setprg16(0xC000, 0);
setchr2(0x0000,0);
setchr2(0x0800,0);
setchr2(0x1000,0);
setchr2(0x1800,0);
SetReadHandler(0x8000, 0xFFFF, UNLRT01Read);
}
void UNLRT01_Init(CartInfo *info) {
info->Power = UNLRT01Power;
}
+195
View File
@@ -0,0 +1,195 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2014 CaH4e3
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "mapinc.h"
static uint8 preg[8];
static uint8 IRQa;
static int16 IRQCount, IRQLatch;
static uint8 *WRAM = NULL;
static uint32 WRAMSIZE;
/*
static uint8 *CHRRAM = NULL;
static uint32 CHRRAMSIZE;
*/
static SFORMAT StateRegs[] =
{
{ preg, 8, "PREG" },
{ &IRQa, 1, "IRQA" },
{ &IRQCount, 2, "IRQC" },
{ &IRQLatch, 2, "IRQL" },
{ 0 }
};
static void Sync(void) {
setchr8(0);
setprg8r(0x10, 0x6000, 0);
if(preg[0] & 0x80)
setprg4r(0x10,0x8000,preg[0] & 0x7f);
else
setprg4(0x8000,preg[0] & 0x7f);
if(preg[1] & 0x80)
setprg4r(0x10,0x9000,preg[1] & 0x7f);
else
setprg4(0x9000,preg[1] & 0x7f);
if(preg[2] & 0x80)
setprg4r(0x10,0xa000,preg[2] & 0x7f);
else
setprg4(0xa000,preg[2] & 0x7f);
if(preg[3] & 0x80)
setprg4r(0x10,0xb000,preg[3] & 0x7f);
else
setprg4(0xb000,preg[3] & 0x7f);
/*
if(preg[4] & 0x80)
setprg4r(0x10,0xc000,preg[4] & 0x7f);
else
setprg4(0xc000,preg[4] & 0x7f);
if(preg[5] & 0x80)
setprg4r(0x10,0xd000,preg[5] & 0x7f);
else
setprg4(0xd000,preg[5] & 0x7f);
if(preg[6] & 0x80)
setprg4r(0x10,0xe000,preg[6] & 0x7f);
else
setprg4(0xe000,preg[6] & 0x7f);
if(preg[7] & 0x80)
setprg4r(0x10,0xf000,preg[7] & 0x7f);
else
setprg4(0xf000,preg[7] & 0x7f);
*/
setprg16(0xC000,1);
}
static DECLFR(UNLSB2000Read) {
switch(A) {
case 0x4033: // IRQ flags
X6502_IRQEnd(FCEU_IQFCOUNT);
return 0xff;
// case 0x4204: // unk
// return 0xff;
// case 0x4205: // unk
// return 0xff;
default:
FCEU_printf("unk read: %04x\n",A);
// break;
return 0xff; // needed to prevent C4715 warning?
}
}
static DECLFW(UNLSB2000Write) {
switch(A) {
case 0x4027: // PCM output
BWrite[0x4015](0x4015, 0x10);
BWrite[0x4011](0x4011, V >> 1);
break;
case 0x4032: // IRQ mask
IRQa &= ~V;
// X6502_IRQEnd(FCEU_IQEXT);
break;
case 0x4040:
case 0x4041:
case 0x4042:
case 0x4043:
case 0x4044:
case 0x4045:
case 0x4046:
case 0x4047:
// FCEU_printf("bank write: %04x:%02x\n",A,V);
preg[A&7] = V;
Sync();
break;
default:
// FCEU_printf("unk write: %04x:%02x\n",A,V);
break;
}
}
static void UNLSB2000Reset(void) {
preg[0] = 0;
preg[1] = 1;
preg[2] = 2;
preg[3] = 3;
preg[4] = 4;
preg[5] = 5;
preg[6] = 6;
preg[7] = 7;
IRQa = 0;
// BWrite[0x4017](0x4017,0xC0);
// BWrite[0x4015](0x4015,0x1F);
}
static void UNLSB2000Power(void) {
UNLSB2000Reset();
Sync();
SetReadHandler(0x6000, 0x7fff, CartBR);
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetReadHandler(0x8000, 0xffff, CartBR);
SetWriteHandler(0x8000, 0xbfff, CartBW);
SetWriteHandler(0x4020, 0x5fff, UNLSB2000Write);
SetReadHandler(0x4020, 0x5fff, UNLSB2000Read);
}
static void UNLSB2000Close(void)
{
if (WRAM)
FCEU_gfree(WRAM);
/*
if (CHRRAM)
FCEU_gfree(CHRRAM);
*/
WRAM = /*CHRRAM = */NULL;
}
/*
static void UNLSB2000IRQHook() {
X6502_IRQBegin(FCEU_IQEXT);
}
*/
static void StateRestore(int version) {
Sync();
}
void UNLSB2000_Init(CartInfo *info) {
info->Reset = UNLSB2000Reset;
info->Power = UNLSB2000Power;
info->Close = UNLSB2000Close;
// GameHBIRQHook = UNLSB2000IRQHook;
GameStateRestore = StateRestore;
/*
CHRRAMSIZE = 8192;
CHRRAM = (uint8*)FCEU_gmalloc(CHRRAMSIZE);
SetupCartCHRMapping(0x10, CHRRAM, CHRRAMSIZE, 1);
AddExState(CHRRAM, CHRRAMSIZE, 0, "CRAM");
*/
// SetupCartCHRMapping(0, PRGptr[0], PRGsize[0], 0);
WRAMSIZE = 512 * 1024;
WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE);
SetupCartPRGMapping(0x10, WRAM, WRAMSIZE, 1);
AddExState(WRAM, WRAMSIZE, 0, "WRAM");
if (info->battery) {
info->SaveGame[0] = WRAM;
info->SaveGameLen[0] = WRAMSIZE;
}
AddExState(&StateRegs, ~0, 0, 0);
}
+15 -6
View File
@@ -31,16 +31,18 @@ static SFORMAT StateRegs[] =
{
{ reg, 8, "REGS" },
{ chr, 8, "CHRS" },
{ &IRQCount, 16, "IRQc" },
{ &IRQa, 16, "IRQa" },
{ &IRQCount, 2, "IRQc" },
{ &IRQa, 2, "IRQa" },
{ 0 }
};
static void Sync(void) {
int i;
setprg8r(0x10, 0x6000, 0);
setprg8(0x8000, reg[0]);
setprg8(0xA000, reg[1]);
setprg8(0xC000, reg[2]);
setprg8(0xE000, ~0);
for (i = 0; i < 8; i++)
setchr1(i << 10, chr[i]);
setmirror(reg[3] ^ 1);
@@ -67,20 +69,26 @@ static DECLFW(UNLSC127Write) {
Sync();
}
static DECLFR(UNLSC127ProtRead) {
return 0x20;
}
static void UNLSC127Power(void) {
IRQCount = IRQa = 0;
Sync();
setprg8r(0x10, 0x6000, 0);
setprg8(0xE000, ~0);
SetReadHandler(0x5800, 0x5800, UNLSC127ProtRead);
SetReadHandler(0x6000, 0x7fff, CartBR);
SetWriteHandler(0x6000, 0x7fff, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, UNLSC127Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNLSC127IRQ(void) {
if (IRQa) {
IRQCount--;
if (IRQCount == 0) {
if(IRQCount > 0)
IRQCount--;
if (!IRQCount) {
X6502_IRQBegin(FCEU_IQEXT);
IRQa = 0;
}
@@ -88,6 +96,7 @@ static void UNLSC127IRQ(void) {
}
static void UNLSC127Reset(void) {
IRQCount = IRQa = 0;
}
static void UNLSC127Close(void) {
+1
View File
@@ -71,6 +71,7 @@ static void TransformerPower(void) {
SetReadHandler(0x6000, 0x7FFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
MapIRQHook = TransformerIRQHook;
}
+269
View File
@@ -0,0 +1,269 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2014 CaitSith2
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/*
* Roms still using NES 1.0 format should be loaded as 32K CHR RAM.
* Roms defined under NES 2.0 should use the VRAM size field, defining 7, 8 or 9, based on how much VRAM should be present.
* UNIF doesn't have this problem, because unique board names can define this information.
* The UNIF names are UNROM-512-8K, UNROM-512-16K and UNROM-512-32K
*
* The battery flag in the NES header enables flash, Mirrror mode 2 Enables MI_0 and MI_1 mode.
* Known games to use this board are:
* Battle Kid 2: Mountain of Torment (512K PRG, 8K CHR RAM, Horizontal Mirroring, Flash disabled)
* Study Hall (128K PRG (in 512K flash chip), 8K CHR RAM, Horizontal Mirroring, Flash enabled)
* Although Xmas 2013 uses a different board, where LEDs can be controlled (with writes to the $8000-BFFF space),
* it otherwise functions identically.
*/
#include "mapinc.h"
#include "../ines.h"
static uint8 latche, latcheinit, bus_conflict, chrram_mask, software_id=false;
static uint16 latcha;
static uint8 *flashdata;
static uint32 *flash_write_count;
static uint8 *FlashPage[32];
static uint32 *FlashWriteCountPage[32];
static uint8 flashloaded = false;
static uint8 flash_save=0, flash_state=0, flash_mode=0, flash_bank;
static void (*WLSync)(void);
static void (*WHSync)(void);
static INLINE void setfpageptr(int s, uint32 A, uint8 *p) {
uint32 AB = A >> 11;
int x;
if (p)
for (x = (s >> 1) - 1; x >= 0; x--) {
FlashPage[AB + x] = p - A;
}
else
for (x = (s >> 1) - 1; x >= 0; x--) {
FlashPage[AB + x] = 0;
}
}
void setfprg16(uint32 A, uint32 V) {
if (PRGsize[0] >= 16384) {
V &= PRGmask16[0];
setfpageptr(16, A, flashdata ? (&flashdata[V << 14]) : 0);
} else {
uint32 VA = V << 3;
int x;
for (x = 0; x < 8; x++)
setfpageptr(2, A + (x << 11), flashdata ? (&flashdata[((VA + x) & PRGmask2[0]) << 11]) : 0);
}
}
void inc_flash_write_count(uint8 bank, uint32 A)
{
flash_write_count[(bank*4) + ((A&0x3000)>>12)]++;
if(!flash_write_count[(bank*4) + ((A&0x3000)>>12)])
flash_write_count[(bank*4) + ((A&0x3000)>>12)]++;
}
uint32 GetFlashWriteCount(uint8 bank, uint32 A)
{
return flash_write_count[(bank*4) + ((A&0x3000)>>12)];
}
static void StateRestore(int version) {
WHSync();
}
static DECLFW(UNROM512LLatchWrite)
{
latche = V;
latcha = A;
WLSync();
}
static DECLFW(UNROM512HLatchWrite)
{
if (bus_conflict)
latche = (V == CartBR(A)) ? V : 0;
else
latche = V;
latcha = A;
WHSync();
}
static DECLFR(UNROM512LatchRead)
{
uint8 flash_id[3]={0xB5,0xB6,0xB7};
if(software_id)
{
if(A&1)
return flash_id[ROM_size>>4];
else
return 0xBF;
}
if(flash_save)
{
if(A < 0xC000)
{
if(GetFlashWriteCount(flash_bank,A))
return FlashPage[A >> 11][A];
}
else
{
if(GetFlashWriteCount(ROM_size-1,A))
return FlashPage[A >> 11][A];
}
}
return Page[A >> 11][A];
}
static void UNROM512LatchPower(void) {
latche = latcheinit;
WHSync();
SetReadHandler(0x8000, 0xFFFF, UNROM512LatchRead);
if(!flash_save)
SetWriteHandler(0x8000, 0xFFFF, UNROM512HLatchWrite);
else
{
SetWriteHandler(0x8000,0xBFFF,UNROM512LLatchWrite);
SetWriteHandler(0xC000,0xFFFF,UNROM512HLatchWrite);
}
}
static void UNROM512LatchClose(void) {
if(flash_write_count)
FCEU_gfree(flash_write_count);
if(flashdata)
FCEU_gfree(flashdata);
flash_write_count = NULL;
flashdata = NULL;
}
static void UNROM512LSync() {
int erase_a[5]={0x9555,0xAAAA,0x9555,0x9555,0xAAAA};
int erase_d[5]={0xAA,0x55,0x80,0xAA,0x55};
int erase_b[5]={1,0,1,1,0};
if(flash_mode==0)
{
if((latcha == erase_a[flash_state]) && (latche == erase_d[flash_state]) && (flash_bank == erase_b[flash_state]))
{
flash_state++;
if(flash_state == 5)
{
flash_mode=1;
}
}
else if ((flash_state==2)&&(latcha==0x9555)&&(latche==0xA0)&&(flash_bank==1))
{
flash_state++;
flash_mode=2;
}
else if ((flash_state==2)&&(latcha==0x9555)&&(latche==0x90)&&(flash_bank==1))
{
flash_state=0;
software_id=true;
}
else
{
if(latche==0xF0)
software_id=false;
flash_state=0;
}
}
else if(flash_mode==1) //Chip Erase or Sector Erase
{
if(latche==0x30)
{
inc_flash_write_count(flash_bank,latcha);
memset(&FlashPage[(latcha & 0xF000) >> 11][latcha & 0xF000],0xFF,0x1000);
}
else if (latche==0x10)
{
for(uint32 i=0;i<(ROM_size*4);i++)
inc_flash_write_count(i>>2,i<<12);
memset(flashdata,0xFF,ROM_size*0x4000); //Erasing the rom chip as instructed. Crash rate calulated to be 99.9% :)
}
flash_state=0;
flash_mode=0;
}
else if(flash_mode==2) //Byte Program
{
if(!GetFlashWriteCount(flash_bank,latcha))
{
inc_flash_write_count(flash_bank,latcha);
memcpy(&FlashPage[(latcha & 0xF000) >> 11][latcha & 0xF000],&Page[(latcha & 0xF000)>>11][latcha & 0xF000],0x1000);
}
FlashPage[latcha>>11][latcha]&=latche;
flash_state=0;
flash_mode=0;
}
}
static void UNROM512HSync()
{
flash_bank=latche&(ROM_size-1);
setprg16(0x8000, flash_bank);
setprg16(0xc000, ~0);
setfprg16(0x8000, flash_bank);
setfprg16(0xC000, ~0);
setchr8r(0, (latche & chrram_mask) >> 5);
setmirror(MI_0+(latche>>7));
}
void UNROM512_Init(CartInfo *info) {
flash_state=0;
flash_bank=0;
flash_save=info->battery;
if(info->vram_size == 8192)
chrram_mask = 0;
else if (info->vram_size == 16384)
chrram_mask = 0x20;
else
chrram_mask = 0x60;
SetupCartMirroring(info->mirror,(info->mirror>=MI_0)?0:1,0);
bus_conflict = !info->battery;
latcheinit = 0;
WLSync = UNROM512LSync;
WHSync = UNROM512HSync;
info->Power = UNROM512LatchPower;
info->Close = UNROM512LatchClose;
GameStateRestore = StateRestore;
if(flash_save)
{
flashdata = (uint8*)FCEU_gmalloc(ROM_size*0x4000);
flash_write_count = (uint32*)FCEU_gmalloc(ROM_size*4*sizeof(uint32));
info->SaveGame[0] = (uint8*)flash_write_count;
info->SaveGame[1] = flashdata;
info->SaveGameLen[0] = ROM_size*4*sizeof(uint32);
info->SaveGameLen[1] = ROM_size*0x4000;
AddExState(flash_write_count,ROM_size*4*sizeof(uint32),0,"FLASH_WRITE_COUNT");
AddExState(flashdata,ROM_size*0x4000,0,"FLASH_DATA");
AddExState(&flash_state,1,0,"FLASH_STATE");
AddExState(&flash_mode,1,0,"FLASH_MODE");
AddExState(&flash_bank,1,0,"FLASH_BANK");
AddExState(&latcha,2,0,"LATA");
}
AddExState(&latche, 1, 0, "LATC");
AddExState(&bus_conflict, 1, 0, "BUSC");
}
+2
View File
@@ -169,6 +169,7 @@ static void M23Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, M23Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M25Power(void) {
@@ -179,6 +180,7 @@ static void M25Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x8000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, M22Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
void VRC24IRQHook(int a) {
+1
View File
@@ -106,6 +106,7 @@ static void M73Power(void) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetWriteHandler(0x8000, 0xFFFF, M73Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void M73Close(void)
+1
View File
@@ -184,6 +184,7 @@ static void M190Power(void) {
SetWriteHandler(0x8000, 0xFFFF, M190Write);
SetReadHandler(0xDC00, 0xDC00, M190Read);
SetReadHandler(0xDD00, 0xDD00, M190Read);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
Sync();
}
+1
View File
@@ -127,6 +127,7 @@ static void VRC6Power(void) {
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetWriteHandler(0x8000, 0xFFFF, VRC6Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void VRC6IRQHook(int a) {
+9 -6
View File
@@ -26,6 +26,12 @@ static int32 IRQCount, CycleCount;
static uint8 *WRAM = NULL;
static uint32 WRAMSIZE;
#include "emu2413.h"
static int32 dwave = 0;
static OPLL *VRC7Sound = NULL;
static OPLL **VRC7Sound_saveptr = &VRC7Sound;
static SFORMAT StateRegs[] =
{
{ &vrc7idx, 1, "VRCI" },
@@ -37,16 +43,12 @@ static SFORMAT StateRegs[] =
{ &IRQLatch, 1, "IRQL" },
{ &IRQCount, 4, "IRQC" },
{ &CycleCount, 4, "CYCC" },
{ 0 }
{ (void**)VRC7Sound_saveptr, sizeof(*VRC7Sound) | FCEUSTATE_INDIRECT, "VRC7" },
{0}
};
// VRC7 Sound
#include "emu2413.h"
static int32 dwave = 0;
static OPLL *VRC7Sound = NULL;
void DoVRC7Sound(void) {
int32 z, a;
if (FSettings.soundq >= 1)
@@ -151,6 +153,7 @@ static void VRC7Power(void) {
SetWriteHandler(0x6000, 0x7FFF, CartBW);
SetReadHandler(0x6000, 0xFFFF, CartBR);
SetWriteHandler(0x8000, 0xFFFF, VRC7Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void VRC7Close(void)
+1
View File
@@ -174,6 +174,7 @@ static void M83Power(void) {
SetWriteHandler(0x6000, 0x7fff, CartBW); // Pirate Dragon Ball Z Party [p1] used if for saves instead of seraial EEPROM
SetReadHandler(0x8000, 0xffff, CartBR);
SetWriteHandler(0x8000, 0xffff, M83Write);
FCEU_CheatAddRAM(WRAMSIZE >> 10, 0x6000, WRAM);
}
static void UNLYOKOReset(void) {
+6
View File
@@ -13,6 +13,12 @@ typedef struct {
// that are not really MMC3 but are
// set to mapper 4.
int battery; // Presence of an actual battery.
int ines2;
int submapper; // Submappers as defined by NES 2.0
int wram_size;
int battery_wram_size;
int vram_size;
int battery_vram_size;
uint8 MD5[16];
uint32 CRC32; // Should be set by the iNES/UNIF loading
// code, used by mapper/board code, maybe
+9 -7
View File
@@ -216,7 +216,7 @@ void FCEU_LoadGameCheats(FILE *override)
}
FCEU_DispMessage("Cheats file loaded.",0); //Tells user a cheats file was loaded.
while(fgets(linebuf,2048,fp)>0)
while(fgets(linebuf,2048,fp) != nullptr)
{
char *tbuf=linebuf;
int doc=0;
@@ -931,12 +931,14 @@ void FCEUI_CheatSearchEnd(int type, uint8 v1, uint8 v2)
int FCEU_CheatGetByte(uint32 A)
{
// if(CheatRPtrs[A>>10])
// return CheatRPtrs[A>>10][A]; //adelikat-commenting this stuff out so that lua can see frozen addresses, I hope this doesn't bork stuff.
/*else*/ if(A < 0x10000)
return ARead[A](A);
else
return 0;
if(A < 0x10000) {
uint32 ret;
fceuindbg=1;
ret = ARead[A](A);
fceuindbg=0;
return ret;
} else
return 0;
}
void FCEU_CheatSetByte(uint32 A, uint8 V)
+6 -3
View File
@@ -18,10 +18,13 @@ char *FCEUI_GetAboutString() {
const char *aboutTemplate =
FCEU_NAME_AND_VERSION "\n\n"
"Administrators:\n"
"zeromus, adelikat, AnS\n\n"
"zeromus, punkrockguy318 (Lukas Sabota), feos\n"
"\n"
"Current Contributors:\n"
"punkrockguy318 (Lukas Sabota)\n"
"CaH4e3, gocha, xhainingx, feos\n"
"CaH4e3, rainwarrior\n"
"\n"
"Past Contributors:\n"
"xhainingx, gocha, AnS\n"
"\n"
"FCEUX 2.0:\n"
"mz, nitsujrehtona, SP, Ugly Joe,\n"
+40 -16
View File
@@ -14,7 +14,7 @@
#include <cstdlib>
#include <cstring>
unsigned int debuggerPageSize = 14;
int vblankScanLines = 0; //Used to calculate scanlines 240-261 (vblank)
int vblankPixel = 0; //Used to calculate the pixels in vblank
@@ -232,12 +232,12 @@ int getBank(int offs)
if (GameInfo && GameInfo->type==GIT_NSF)
return addr != -1 ? addr / 0x1000 : -1;
return addr != -1 ? addr / 0x4000 : -1;
return addr != -1 ? addr / (1<<debuggerPageSize) : -1; //formerly, dividing by 0x4000
}
int GetNesFileAddress(int A){
int result;
if((A < 0x8000) || (A > 0xFFFF))return -1;
if((A < 0x6000) || (A > 0xFFFF))return -1;
result = &Page[A>>11][A]-PRGptr[0];
if((result > (int)(PRGsize[0])) || (result < 0))return -1;
else return result+16; //16 bytes for the header remember
@@ -263,7 +263,7 @@ uint8 *GetNesCHRPointer(int A){
}
uint8 GetMem(uint16 A) {
if ((A >= 0x2000) && (A < 0x4000)) {
if ((A >= 0x2000) && (A < 0x4000)) // PPU regs and their mirrors
switch (A&7) {
case 0: return PPU[0];
case 1: return PPU[1];
@@ -271,16 +271,36 @@ uint8 GetMem(uint16 A) {
case 3: return PPU[3];
case 4: return SPRAM[PPU[3]];
case 5: return XOffset;
case 6: return RefreshAddr&0xFF;
case 6: return FCEUPPU_PeekAddress() & 0xFF;
case 7: return VRAMBuffer;
}
} else if ((A >= 0x4000) && (A < 0x5000)) return 0xFF; // AnS: changed the range, so MMC5 ExRAM can be watched in the Hexeditor
if (GameInfo) return ARead[A](A); //adelikat: 11/17/09: Prevent crash if this is called with no game loaded.
else return 0;
// feos: added more registers
else if ((A >= 0x4000) && (A < 0x4010))
return PSG[A&15];
else if ((A >= 0x4010) && (A < 0x4018))
switch(A&7) {
case 0: return DMCFormat;
case 1: return RawDALatch;
case 2: return DMCAddressLatch;
case 3: return DMCSizeLatch;
case 4: return SpriteDMA;
case 5: return EnabledChannels;
case 6: return RawReg4016;
case 7: return IRQFrameMode;
}
else if ((A >= 0x4018) && (A < 0x5000)) // AnS: changed the range, so MMC5 ExRAM can be watched in the Hexeditor
return 0xFF;
if (GameInfo) { //adelikat: 11/17/09: Prevent crash if this is called with no game loaded.
uint32 ret;
fceuindbg=1;
ret = ARead[A](A);
fceuindbg=0;
return ret;
} else return 0;
}
uint8 GetPPUMem(uint8 A) {
uint16 tmp=RefreshAddr&0x3FFF;
uint16 tmp = FCEUPPU_PeekAddress() & 0x3FFF;
if (tmp<0x2000) return VPage[tmp>>10][tmp];
if (tmp>=0x3F00) return PALRAM[tmp&0x1F];
@@ -405,7 +425,8 @@ void LogCDData(uint8 *opcode, uint16 A, int size) {
for (i = 0; i < size; i++) {
if(cdloggerdata[j+i] & 1)continue; //this has been logged so skip
cdloggerdata[j+i] |= 1;
cdloggerdata[j+i] |=((_PC+i)>>11)&0x0c;
cdloggerdata[j+i] |= ((_PC + i) >> 11) & 0x0c;
cdloggerdata[j+i] |= ((_PC & 0x8000) >> 8) ^ 0x80; // 19/07/14 used last reserved bit, if bit 7 is 1, then code is running from lowe area (6000)
if(indirectnext)cdloggerdata[j+i] |= 0x10;
codecount++;
if(!(cdloggerdata[j+i] & 2))undefinedcount--;
@@ -607,13 +628,14 @@ static void breakpoint(uint8 *opcode, uint16 A, int size) {
// PPU Mem breaks
if ((watchpoint[i].flags & brk_type) && ((A >= 0x2000) && (A < 0x4000)) && ((A&7) == 7))
{
const uint32 PPUAddr = FCEUPPU_PeekAddress();
if (watchpoint[i].endaddress)
{
if ((watchpoint[i].address <= RefreshAddr) && (watchpoint[i].endaddress >= RefreshAddr))
if ((watchpoint[i].address <= PPUAddr) && (watchpoint[i].endaddress >= PPUAddr))
BreakHit(i);
} else
{
if (watchpoint[i].address == RefreshAddr)
if (watchpoint[i].address == PPUAddr)
BreakHit(i);
}
}
@@ -737,7 +759,7 @@ static void breakpoint(uint8 *opcode, uint16 A, int size) {
void DebugCycle()
{
uint8 opcode[3] = {0};
uint16 A = 0;
uint16 A = 0, tmp;
int size;
if (scanline == 240)
@@ -772,12 +794,14 @@ void DebugCycle()
{
case 0: break;
case 1:
A = (opcode[1] + _X) & 0xFF;
A = GetMem(A) | (GetMem(A + 1) << 8);
tmp = (opcode[1] + _X) & 0xFF;
A = GetMem(tmp);
tmp = (opcode[1] + _X + 1) & 0xFF;
A |= (GetMem(tmp) << 8);
break;
case 2: A = opcode[1]; break;
case 3: A = opcode[1] | (opcode[2] << 8); break;
case 4: A = (GetMem(opcode[1]) | (GetMem(opcode[1]+1) << 8)) + _Y; break;
case 4: A = (GetMem(opcode[1]) | (GetMem((opcode[1] + 1) & 0xFF) << 8)) + _Y; break;
case 5: A = opcode[1] + _X; break;
case 6: A = (opcode[1] | (opcode[2] << 8)) + _Y; break;
case 7: A = (opcode[1] | (opcode[2] << 8)) + _X; break;
+11 -3
View File
@@ -116,9 +116,7 @@ extern void IncrementInstructionsCounters();
//internal variables that debuggers will want access to
extern uint8 *vnapage[4],*VPage[8];
extern uint8 PPU[4],PALRAM[0x20],SPRAM[0x100],VRAMBuffer,PPUGenLatch,XOffset;
extern uint32 RefreshAddr;
extern int debug_loggingCD;
extern uint32 FCEUPPU_PeekAddress();
extern int numWPs;
///encapsulates the operational state of the debugger core
@@ -148,6 +146,16 @@ public:
extern NSF_HEADER NSFHeader;
extern uint8 PSG[0x10];
extern uint8 DMCFormat;
extern uint8 RawDALatch;
extern uint8 DMCAddressLatch;
extern uint8 DMCSizeLatch;
extern uint8 EnabledChannels;
extern uint8 SpriteDMA;
extern uint8 RawReg4016;
extern uint8 IRQFrameMode;
///retrieves the core's DebuggerState
DebuggerState &FCEUI_Debugger();
+6 -4
View File
@@ -68,7 +68,7 @@ void FCEUI_NTSCSELTINT(void);
void FCEUI_NTSCDEC(void);
void FCEUI_NTSCINC(void);
void FCEUI_GetNTSCTH(int *tint, int *hue);
void FCEUI_SetNTSCTH(int n, int tint, int hue);
void FCEUI_SetNTSCTH(bool en, int tint, int hue);
void FCEUI_SetInput(int port, ESI type, void *ptr, int attrib);
void FCEUI_SetInputFC(ESIFC type, void *ptr, int attrib);
@@ -120,6 +120,10 @@ void FCEUI_SetGameGenie(bool a);
//Set video system a=0 NTSC, a=1 PAL
void FCEUI_SetVidSystem(int a);
//Set variables for NTSC(0) / PAL(1) / Dendy(2)
//Dendy has PAL framerate and resolution, but ~NTSC timings, and has 50 dummy scanlines to force 50 fps
void FCEUI_SetRegion(int region);
//Convenience function; returns currently emulated video system(0=NTSC, 1=PAL).
int FCEUI_GetCurrentVidSystem(int *slstart, int *slend);
@@ -137,9 +141,7 @@ void FCEUI_SetRenderedLines(int ntscf, int ntscl, int palf, int pall);
//Sets the base directory(save states, snapshots, etc. are saved in directories below this directory.
void FCEUI_SetBaseDirectory(std::string const & dir);
//Tells FCE Ultra to copy the palette data pointed to by pal and use it.
//Data pointed to by pal needs to be 64*3 bytes in length.
void FCEUI_SetPaletteArray(uint8 *pal);
void FCEUI_SetUserPalette(uint8 *pal, int nEntries);
//Sets up sound code to render sound at the specified rate, in samples
//per second. Only sample rates of 44100, 48000, and 96000 are currently supported.
+3 -11
View File
@@ -24,7 +24,7 @@ nes_ntsc_setup_t const nes_ntsc_rgb = { 0, 0, 0, 0,.2, 0,.7, -1, -1,-1,
#define alignment_count 3
#define burst_count 3
#define rescale_in 8
#define rescale_out 6
#define rescale_out 7
#define artifacts_mid 1.0f
#define fringing_mid 1.0f
@@ -81,14 +81,13 @@ static void correct_errors( nes_ntsc_rgb_t color, nes_ntsc_rgb_t* out )
}
}
void nes_ntsc_init( nes_ntsc_t* ntsc, nes_ntsc_setup_t const* setup, int bpp, int multiplier )
void nes_ntsc_init( nes_ntsc_t* ntsc, nes_ntsc_setup_t const* setup, int bpp )
{
int merge_fields;
int entry;
init_t impl;
float gamma_factor;
OutputMultiplier = multiplier;
OutputDepth = bpp * 8;
if ( !setup )
@@ -244,18 +243,12 @@ void nes_ntsc_init( nes_ntsc_t* ntsc, nes_ntsc_setup_t const* setup, int bpp, in
#ifndef NES_NTSC_NO_BLITTERS
void nes_ntsc_blit( nes_ntsc_t const* ntsc, NES_NTSC_IN_T const* input, long in_row_width,
int burst_phase, int in_width, int in_height, void* rgb_out, long out_pitch )
int burst_phase, int emphasis, int in_width, int in_height, void* rgb_out, long out_pitch )
{
int chunk_count = (in_width - 1) / nes_ntsc_in_chunk;
int TempMultiplier = OutputMultiplier * 3;
if (TempMultiplier > 7)
TempMultiplier = 7;
for ( ; in_height; --in_height )
{
int out;
for ( out = OutputMultiplier; out; --out ) {
NES_NTSC_IN_T const* line_in = input;
NES_NTSC_BEGIN_ROW( ntsc, burst_phase, nes_ntsc_black, nes_ntsc_black, NES_NTSC_ADJ_IN( *line_in ) );
nes_ntsc_out_t* restrict line_out = (nes_ntsc_out_t*) rgb_out;
@@ -297,7 +290,6 @@ void nes_ntsc_blit( nes_ntsc_t const* ntsc, NES_NTSC_IN_T const* input, long in_
NES_NTSC_RGB_OUT( 5, line_out [5], OutputDepth );
NES_NTSC_RGB_OUT( 6, line_out [6], OutputDepth );
rgb_out = (char*) rgb_out + out_pitch;
}
burst_phase = (burst_phase + 1) % nes_ntsc_burst_count;
input += in_row_width;
+5 -4
View File
@@ -54,15 +54,16 @@ extern nes_ntsc_setup_t const nes_ntsc_monochrome;/* desaturated + artifacts */
/* Initializes and adjusts parameters. Can be called multiple times on the same
nes_ntsc_t object. Can pass NULL for either parameter. */
typedef struct nes_ntsc_t nes_ntsc_t;
void nes_ntsc_init( nes_ntsc_t* ntsc, nes_ntsc_setup_t const* setup, int bpp, int multiplier );
void nes_ntsc_init( nes_ntsc_t* ntsc, nes_ntsc_setup_t const* setup, int bpp );
/* Filters one or more rows of pixels. Input pixels are 6/9-bit palette indicies.
In_row_width is the number of pixels to get to the next input row. Out_pitch
In_row_width is the number of pixels to get to the next input row. Emphasis is
the emphasis bits to bitwise-OR with all pixels in the input data. Out_pitch
is the number of *bytes* to get to the next output row. Output pixel format
is set by NES_NTSC_OUT_DEPTH (defaults to 16-bit RGB). */
void nes_ntsc_blit( nes_ntsc_t const* ntsc, NES_NTSC_IN_T const* nes_in,
long in_row_width, int burst_phase, int in_width, int in_height,
void* rgb_out, long out_pitch );
long in_row_width, int burst_phase, int emphasis, int in_width,
int in_height, void* rgb_out, long out_pitch );
/* Number of output pixels written by blitter for given input width. Width might
be rounded down slightly; use NES_NTSC_IN_WIDTH() on result to find rounded
+2 -2
View File
@@ -5,7 +5,7 @@
/* Uncomment to enable emphasis support and use a 512 color palette instead
of the base 64 color palette. */
/*#define NES_NTSC_EMPHASIS 1*/
#define NES_NTSC_EMPHASIS 1
/* The following affect the built-in blitter only; a custom blitter can
handle things however it wants. */
@@ -21,7 +21,7 @@ if you enable emphasis above. */
// CUSTOM: (XBuf uses bit 0x80, and has palettes above 0x3f for LUA)
/* Each raw pixel input value is passed through this. You might want to mask
the pixel index if you use the high bits as flags, etc. */
#define NES_NTSC_ADJ_IN( in ) in & 0x3f
#define NES_NTSC_ADJ_IN( in ) ((in & 0x3f) | emphasis)
/* For each pixel, this is the basic operation:
output_color = color_palette [NES_NTSC_ADJ_IN( NES_NTSC_IN_T )] */
File diff suppressed because it is too large Load Diff
+3
View File
@@ -27,3 +27,6 @@ void Blit8To8(uint8 *src, uint8 *dest, int xr, int yr, int pitch, int xscale, in
void Blit32to24(uint32 *src, uint8 *dest, int xr, int yr, int dpitch);
void Blit32to16(uint32 *src, uint16 *dest, int xr, int yr, int dpitch,
int shiftr[3], int shiftl[3]);
u32 ModernDeemphColorMap(u8* src, u8* srcbuf, int xscale, int yscale);
-2
View File
@@ -2,8 +2,6 @@
# Thanks Antonio Ospite!
Import('env')
config_string = 'pkg-config --cflags --libs x11'
if env['PLATFORM'] == 'darwin':
config_string = 'PKG_CONFIG_PATH=/opt/X11/lib/pkgconfig/ ' + config_string
env.ParseConfig(config_string)
Export('env')
+7 -5
View File
@@ -50,7 +50,7 @@ LoadCPalette(const std::string &file)
FCEUD_PrintError(errorMsg);
return 0;
}
FCEUI_SetPaletteArray(tmpp);
FCEUI_SetUserPalette(tmpp, result/3);
fclose(fp);
return 1;
}
@@ -145,6 +145,7 @@ InitConfig()
config->addOption("frameskip", "SDL.Frameskip", 0);
config->addOption("clipsides", "SDL.ClipSides", 0);
config->addOption("nospritelim", "SDL.DisableSpriteLimit", 1);
config->addOption("swapduty", "SDL.SwapDuty", 0);
// color control
config->addOption('p', "palette", "SDL.Palette", "");
@@ -175,6 +176,7 @@ InitConfig()
config->addOption("noframe", "SDL.NoFrame", 0);
config->addOption("special", "SDL.SpecialFilter", 0);
config->addOption("showfps", "SDL.ShowFPS", 0);
config->addOption("togglemenu", "SDL.ToggleMenu", 0);
// OpenGL options
config->addOption("opengl", "SDL.OpenGL", 0);
@@ -250,7 +252,7 @@ InitConfig()
config->addOption("_laststatefrom", "SDL.LastLoadStateFrom", home_dir);
config->addOption("_lastopennsf", "SDL.LastOpenNSF", home_dir);
config->addOption("_lastsavestateas", "SDL.LastSaveStateAs", home_dir);
config->addOption("_lastloadlua", "SDL.LastLoadLua", home_dir);
config->addOption("_lastloadlua", "SDL.LastLoadLua", "");
#endif
// fcm -> fm2 conversion
@@ -401,7 +403,7 @@ InitConfig()
void
UpdateEMUCore(Config *config)
{
int ntsccol, ntsctint, ntschue, flag, start, end;
int ntsccol, ntsctint, ntschue, flag, region, start, end;
std::string cpalette;
config->getOption("SDL.NTSCpalette", &ntsccol);
@@ -414,8 +416,8 @@ UpdateEMUCore(Config *config)
LoadCPalette(cpalette);
}
config->getOption("SDL.PAL", &flag);
FCEUI_SetVidSystem(flag ? 1 : 0);
config->getOption("SDL.PAL", &region);
FCEUI_SetRegion(region);
config->getOption("SDL.GameGenie", &flag);
FCEUI_SetGameGenie(flag ? 1 : 0);
+4 -2
View File
@@ -19,7 +19,8 @@ enum HOTKEY { HK_CHEAT_MENU=0, HK_BIND_STATE, HK_LOAD_LUA, HK_TOGGLE_BG,
HK_SELECT_STATE_0, HK_SELECT_STATE_1, HK_SELECT_STATE_2, HK_SELECT_STATE_3,
HK_SELECT_STATE_4, HK_SELECT_STATE_5, HK_SELECT_STATE_6, HK_SELECT_STATE_7,
HK_SELECT_STATE_8, HK_SELECT_STATE_9,
HK_SELECT_STATE_NEXT, HK_SELECT_STATE_PREV, HK_MAX};
HK_SELECT_STATE_NEXT, HK_SELECT_STATE_PREV, HK_VOLUME_DOWN, HK_VOLUME_UP,
HK_MAX};
static const char* HotkeyStrings[HK_MAX] = {
@@ -50,6 +51,7 @@ static const char* HotkeyStrings[HK_MAX] = {
"LagCounterDisplay",
"SelectState0", "SelectState1", "SelectState2", "SelectState3",
"SelectState4", "SelectState5", "SelectState6", "SelectState7",
"SelectState8", "SelectState9", "SelectStateNext", "SelectStatePrev" };
"SelectState8", "SelectState9", "SelectStateNext", "SelectStatePrev",
"VolumeDown", "VolumeUp" };
#endif
+201 -181
View File
@@ -20,7 +20,9 @@
#include <gtk/gtk.h>
#include <gdk/gdkkeysyms.h>
#ifdef GDK_WINDOWING_X11
#include <gdk/gdkx.h>
#endif
#ifdef _GTK3
#include <gdk/gdkkeysyms-compat.h>
@@ -48,8 +50,10 @@ GtkWidget* evbox = NULL;
GtkWidget* padNoCombo = NULL;
GtkWidget* configNoCombo = NULL;
GtkWidget* buttonMappings[10];
GtkWidget* Menubar;
GtkRadioAction* stateSlot = NULL;
bool gtkIsStarted = false;
bool menuTogglingEnabled;
// check to see if a particular GTK version is available
// 2.24 is required for most of the dialogs -- ie: checkGTKVersion(2,24);
@@ -77,23 +81,31 @@ bool checkGTKVersion(int major_required, int minor_required)
}
}
void setCheckbox(GtkWidget* w, const char* configName)
{
int buf;
g_config->getOption(configName, &buf);
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(w), buf);
}
// This function configures a single hotkey
int configHotkey(char* hotkeyString)
{
SDL_Surface *screen;
SDL_Event event;
KillVideo();
// This is broken right now
//SDL_Surface *screen;
// SDL_Event event;
// KillVideo();
#if SDL_VERSION_ATLEAST(2, 0, 0)
return 0; // TODO - SDL 2.0
#else
screen = SDL_SetVideoMode(420, 200, 8, 0);
//screen = SDL_SetVideoMode(420, 200, 8, 0);
//SDL_WM_SetCaption("Press a key to bind...", 0);
/*
int newkey = 0;
while(1)
{
SDL_WaitEvent(&event);
switch (event.type)
{
case SDL_KEYDOWN:
@@ -105,7 +117,7 @@ int configHotkey(char* hotkeyString)
}
}
return 0;
return 0;*/
#endif
}
// This function configures a single button on a gamepad
@@ -157,10 +169,13 @@ void resetVideo()
InitVideo(GameInfo);
}
void closeVideoWin(GtkWidget* w, GdkEvent* e, gpointer p)
void closeVideoWin(GtkWidget* w, gint response, gpointer p)
{
resetVideo();
gtk_widget_destroy(w);
if(response != GTK_RESPONSE_APPLY)
{
gtk_widget_destroy(w);
}
}
void closeDialog(GtkWidget* w, GdkEvent* e, gpointer p)
@@ -182,6 +197,21 @@ void toggleLowPass(GtkWidget* w, gpointer p)
g_config->save();
}
void toggleSwapDuty(GtkWidget* w, gpointer p)
{
if(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w)))
{
g_config->setOption("SDL.SwapDuty", 1);
swapDuty = 1;
}
else
{
g_config->setOption("SDL.SwapDuty", 0);
swapDuty = 0;
}
g_config->save();
}
// Wrapper for pushing GTK options into the config file
// p : pointer to the string that names the config option
// w : toggle widget
@@ -303,15 +333,8 @@ void openPaletteConfig()
ntscColorChk = gtk_check_button_new_with_label("Use NTSC palette");
g_signal_connect(ntscColorChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.NTSCpalette");
setCheckbox(ntscColorChk, "SDL.NTSCpalette");
int b;
// sync with config
g_config->getOption("SDL.NTSCpalette", &b);
if(b)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(ntscColorChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(ntscColorChk), 0);
// color / tint / hue sliders
slidersFrame = gtk_frame_new("NTSC palette controls");
slidersVbox = gtk_vbox_new(FALSE, 2);
@@ -498,18 +521,17 @@ void openHotkeyConfig()
GtkTreeStore *hotkey_store = gtk_tree_store_new(N_COLUMNS, G_TYPE_STRING, G_TYPE_STRING);
std::string prefix = "SDL.Hotkeys.";
GtkTreeIter iter; // parent
GtkTreeIter iter2; // child
GtkTreeIter iter;
gtk_tree_store_append(hotkey_store, &iter, NULL); // aquire iter
int keycode;
for(int i=0; i<HK_MAX; i++)
{
const char* optionName = (prefix + HotkeyStrings[i]).c_str();
g_config->getOption(optionName, &keycode);
std::string optionName = prefix + HotkeyStrings[i];
g_config->getOption(optionName.c_str(), &keycode);
gtk_tree_store_set(hotkey_store, &iter,
COMMAND_COLUMN, optionName,
COMMAND_COLUMN, optionName.c_str(),
KEY_COLUMN,
#if SDL_VERSION_ATLEAST(2, 0, 0)
SDL_GetKeyName(keycode),
@@ -631,7 +653,7 @@ void openGamepadConfig()
GtkWidget* vbox;
GtkWidget* hboxPadNo;
GtkWidget* padNoLabel;
GtkWidget* configNoLabel;
//GtkWidget* configNoLabel;
GtkWidget* fourScoreChk;
GtkWidget* oppositeDirChk;
GtkWidget* buttonFrame;
@@ -652,7 +674,7 @@ void openGamepadConfig()
hboxPadNo = gtk_hbox_new(FALSE, 0);
padNoLabel = gtk_label_new("Port:");
configNoLabel = gtk_label_new("Config Number:");
//configNoLabel = gtk_label_new("Config Number:");
fourScoreChk = gtk_check_button_new_with_label("Enable Four Score");
oppositeDirChk = gtk_check_button_new_with_label("Allow Up+Down / Left+Right");
@@ -686,22 +708,12 @@ void openGamepadConfig()
g_signal_connect(typeCombo, "changed", G_CALLBACK(setInputDevice),
gtk_combo_box_text_get_active_text(GTK_COMBO_BOX_TEXT(typeCombo)));
// sync with config
int buf = 0;
g_config->getOption("SDL.FourScore", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(fourScoreChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(fourScoreChk), 0);
g_config->getOption("SDL.Input.EnableOppositeDirectionals", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(oppositeDirChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(oppositeDirChk), 0);
setCheckbox(fourScoreChk, "SDL.FourScore");
g_signal_connect(fourScoreChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.FourScore");
setCheckbox(oppositeDirChk, "SDL.Input.EnableOppositeDirectionals");
g_signal_connect(oppositeDirChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.Input.EnableOppositeDirectionals");
gtk_box_pack_start(GTK_BOX(hboxPadNo), padNoLabel, TRUE, TRUE, 5);
gtk_box_pack_start(GTK_BOX(hboxPadNo), padNoCombo, TRUE, TRUE, 5);
//gtk_box_pack_start(GTK_BOX(hboxPadNo), configNoLabel, TRUE, TRUE, 5);
@@ -812,27 +824,52 @@ void resizeGtkWindow()
void setScaler(GtkWidget* w, gpointer p)
{
int x = gtk_combo_box_get_active(GTK_COMBO_BOX(w));
g_config->setOption("SDL.SpecialFilter", x);
int scaler = gtk_combo_box_get_active(GTK_COMBO_BOX(w));
int opengl;
g_config->getOption("SDL.OpenGL", &opengl);
if(opengl && scaler)
{
FCEUD_PrintError("Scalers not supported in OpenGL mode.");
gtk_combo_box_set_active(GTK_COMBO_BOX(w), 0);
return;
}
g_config->setOption("SDL.SpecialFilter", scaler);
// 1 - hq2x 2 - Scale2x 3 - NTSC2x 4 - hq3x 5 - Scale3x
if (x >= 1 && x <= 3)
// 1=hq2x 2=Scale2x 3=NTSC2x 4=hq3x 5=Scale3x 6=Prescale2x 7=Prescale3x 8=Prescale4x 9=pal
switch(scaler)
{
g_config->setOption("SDL.XScale", 2.0);
g_config->setOption("SDL.YScale", 2.0);
resizeGtkWindow();
}
if (x >= 4 && x < 6)
{
g_config->setOption("SDL.XScale", 3.0);
g_config->setOption("SDL.YScale", 3.0);
resizeGtkWindow();
case 4: // hq3x
case 5: // scale3x
case 7: // prescale3x
g_config->setOption("SDL.XScale", 3.0);
g_config->setOption("SDL.YScale", 3.0);
resizeGtkWindow();
break;
case 8: // prescale4x
g_config->setOption("SDL.XScale", 4.0);
g_config->setOption("SDL.YScale", 4.0);
break;
default:
g_config->setOption("SDL.XScale", 2.0);
g_config->setOption("SDL.YScale", 2.0);
resizeGtkWindow();
break;
}
g_config->save();
}
void setRegion(GtkWidget* w, gpointer p)
{
int region = gtk_combo_box_get_active(GTK_COMBO_BOX(w));
g_config->setOption("SDL.PAL", region);
FCEUI_SetRegion(region);
g_config->save();
}
int setXscale(GtkWidget* w, gpointer p)
{
double v = gtk_spin_button_get_value(GTK_SPIN_BUTTON(w));
@@ -854,6 +891,15 @@ int setYscale(GtkWidget* w, gpointer p)
#ifdef OPENGL
void setGl(GtkWidget* w, gpointer p)
{
int scaler;
int opengl = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w));
g_config->getOption("SDL.SpecialFilter", &scaler);
if(scaler && opengl)
{
FCEUD_PrintError("Scalers not supported in OpenGL mode.");
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(w), 0);
return;
}
if(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w)))
g_config->setOption("SDL.OpenGL", 1);
else
@@ -882,7 +928,9 @@ void openVideoConfig()
GtkWidget* glChk;
GtkWidget* linearChk;
GtkWidget* dbChk;
GtkWidget* palChk;
GtkWidget* palHbox;
GtkWidget* palLbl;
GtkWidget* palCombo;
GtkWidget* ppuChk;
GtkWidget* spriteLimitChk;
GtkWidget* frameskipChk;
@@ -894,11 +942,12 @@ void openVideoConfig()
GtkWidget* xscaleHbox;
GtkWidget* yscaleHbox;
GtkWidget* showFpsChk;
win = gtk_dialog_new_with_buttons("Video Preferences",
GTK_WINDOW(MainWindow),
(GtkDialogFlags)(GTK_DIALOG_DESTROY_WITH_PARENT),
GTK_STOCK_CLOSE, GTK_RESPONSE_OK, NULL);
GTK_STOCK_APPLY, GTK_RESPONSE_APPLY,
GTK_STOCK_CLOSE, GTK_RESPONSE_CLOSE, NULL);
gtk_window_set_icon_name(GTK_WINDOW(win), "video-display");
//gtk_widget_set_size_request(win, 250, 250);
@@ -917,6 +966,10 @@ void openVideoConfig()
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "NTSC 2x");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "hq3x");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "scale3x");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "prescale2x");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "prescale3x");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "prescale4x");
//gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(scalerCombo), "pal");
// sync with cfg
int buf;
@@ -930,102 +983,56 @@ void openVideoConfig()
// openGL check
glChk = gtk_check_button_new_with_label("Enable OpenGL");
g_signal_connect(glChk, "clicked", G_CALLBACK(setGl), NULL);
// sync with config
buf = 0;
g_config->getOption("SDL.OpenGL", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(glChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(glChk), 0);
setCheckbox(glChk, "SDL.OpenGL");
// openGL linear filter check
linearChk = gtk_check_button_new_with_label("Enable OpenGL linear filter");
g_signal_connect(linearChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.OpenGLip");
setCheckbox(linearChk, "SDL.OpenGLip");
// sync with config
buf = 0;
g_config->getOption("SDL.OpenGLip", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(linearChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(linearChk), 0);
// DoubleBuffering check
// DoubleBuffering check
dbChk = gtk_check_button_new_with_label("Enable double buffering");
g_signal_connect(dbChk, "clicked", G_CALLBACK(setDoubleBuffering), NULL);
// sync with config
buf = 0;
g_config->getOption("SDL.DoubleBuffering", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dbChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dbChk), 0);
setCheckbox(dbChk, "SDL.DoubleBuffering");
#endif
// PAL check
palChk = gtk_check_button_new_with_label("Enable PAL mode");
g_signal_connect(palChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.PAL");
// sync with config
buf = 0;
// Region (NTSC/PAL/Dendy)
palHbox = gtk_hbox_new(FALSE, 3);
palLbl = gtk_label_new("Region: ");
palCombo = gtk_combo_box_text_new();
// -Video Modes Tag-
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(palCombo), "NTSC");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(palCombo), "PAL");
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(palCombo), "Dendy");
// sync with cfg
g_config->getOption("SDL.PAL", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(palChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(palChk), 0);
gtk_combo_box_set_active(GTK_COMBO_BOX(palCombo), buf);
g_signal_connect(palCombo, "changed", G_CALLBACK(setRegion), NULL);
gtk_box_pack_start(GTK_BOX(palHbox), palLbl, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(palHbox), palCombo, FALSE, FALSE, 5);
// New PPU check
ppuChk = gtk_check_button_new_with_label("Enable new PPU");
g_signal_connect(ppuChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.NewPPU");
// sync with config
buf = 0;
g_config->getOption("SDL.NewPPU", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(ppuChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(ppuChk), 0);
// "disable 8 sprite limit" check
setCheckbox(ppuChk, "SDL.NewPPU");
// "disable 8 sprite limit" check
spriteLimitChk = gtk_check_button_new_with_label("Disable sprite limit");
g_signal_connect(spriteLimitChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.DisableSpriteLimit");
setCheckbox(spriteLimitChk, "SDL.DisableSpriteLimit");
// sync with config
buf = 0;
g_config->getOption("SDL.DisableSpriteLimit", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(spriteLimitChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(spriteLimitChk), 0);
// frameskip check
frameskipChk = gtk_check_button_new_with_label("Enable frameskip");
g_signal_connect(frameskipChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.Frameskip");
// sync with config
buf = 0;
g_config->getOption("SDL.Frameskip", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(frameskipChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(frameskipChk), 0);
setCheckbox(frameskipChk, "SDL.Frameskip");
// clip sides check
clipSidesChk = gtk_check_button_new_with_label("Clip sides");
g_signal_connect(clipSidesChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.ClipSides");
setCheckbox(clipSidesChk, "SDL.ClipSides");
// sync with config
buf = 0;
g_config->getOption("SDL.ClipSides", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(clipSidesChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(clipSidesChk), 0);
// xscale / yscale
xscaleHbox = gtk_hbox_new(FALSE, 5);
xscaleLbl = gtk_label_new("X scaling factor");
@@ -1052,17 +1059,8 @@ void openVideoConfig()
// show FPS check
showFpsChk = gtk_check_button_new_with_label("Show FPS");
g_signal_connect(showFpsChk, "clicked", G_CALLBACK(toggleOption), (gpointer)"SDL.ShowFPS");
setCheckbox(showFpsChk, "SDL.ShowFPS");
// sync with config
buf = 0;
g_config->getOption("SDL.ShowFPS", &buf);
if(buf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(showFpsChk), 1);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(showFpsChk), 0);
gtk_box_pack_start(GTK_BOX(vbox), lbl, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(vbox), hbox1, FALSE, FALSE, 5);
#ifdef OPENGL
@@ -1070,7 +1068,7 @@ void openVideoConfig()
gtk_box_pack_start(GTK_BOX(vbox), linearChk, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(vbox), dbChk, FALSE, FALSE, 5);
#endif
gtk_box_pack_start(GTK_BOX(vbox), palChk, FALSE, FALSE,5);
gtk_box_pack_start(GTK_BOX(vbox), palHbox, FALSE, FALSE,5);
gtk_box_pack_start(GTK_BOX(vbox), ppuChk, FALSE, FALSE, 5);
#ifdef FRAMESKIP
gtk_box_pack_start(GTK_BOX(vbox), frameskipChk, FALSE, FALSE, 5);
@@ -1142,9 +1140,9 @@ void openSoundConfig()
GtkWidget* hbox2;
GtkWidget* rateCombo;
GtkWidget* rateLbl;
GtkWidget* hbox3;
GtkWidget* bufferLbl;
GtkWidget* bufferHscale;
GtkWidget* swapDutyChk;
GtkWidget* mixerFrame;
GtkWidget* mixerHbox;
GtkWidget* mixers[6];
@@ -1158,32 +1156,17 @@ void openSoundConfig()
NULL);
gtk_window_set_icon_name(GTK_WINDOW(win), "audio-x-generic");
main_hbox = gtk_hbox_new(FALSE, 15);
vbox = gtk_vbox_new(False, 5);
vbox = gtk_vbox_new(FALSE, 5);
// sound enable check
soundChk = gtk_check_button_new_with_label("Enable sound");
// sync with cfg
int cfgBuf;
g_config->getOption("SDL.Sound", &cfgBuf);
if(cfgBuf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(soundChk), TRUE);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(soundChk), FALSE);
g_signal_connect(soundChk, "clicked", G_CALLBACK(toggleSound), NULL);
setCheckbox(soundChk,"SDL.Sound");
// low pass filter check
lowpassChk = gtk_check_button_new_with_label("Enable low pass filter");
// sync with cfg
g_config->getOption("SDL.Sound.LowPass", &cfgBuf);
if(cfgBuf)
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lowpassChk), TRUE);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lowpassChk), FALSE);
g_signal_connect(lowpassChk, "clicked", G_CALLBACK(toggleLowPass), NULL);
setCheckbox(lowpassChk, "SDL.Sound.LowPass");
// sound quality combo box
hbox1 = gtk_hbox_new(FALSE, 3);
@@ -1193,13 +1176,9 @@ void openSoundConfig()
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(qualityCombo), "Very High");
// sync widget with cfg
g_config->getOption("SDL.Sound.Quality", &cfgBuf);
if(cfgBuf == 2)
gtk_combo_box_set_active(GTK_COMBO_BOX(qualityCombo), 2);
else if(cfgBuf == 1)
gtk_combo_box_set_active(GTK_COMBO_BOX(qualityCombo), 1);
else
gtk_combo_box_set_active(GTK_COMBO_BOX(qualityCombo), 0);
int buf;
g_config->getOption("SDL.Sound.Quality", &buf);
gtk_combo_box_set_active(GTK_COMBO_BOX(qualityCombo), buf);
g_signal_connect(qualityCombo, "changed", G_CALLBACK(setQuality), NULL);
@@ -1214,17 +1193,17 @@ void openSoundConfig()
const int rates[5] = {11025, 22050, 44100, 48000, 96000};
char buf[8];
char choices[8];
for(int i=0; i<5;i++)
{
sprintf(buf, "%d", rates[i]);
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(rateCombo), buf);
sprintf(choices, "%d", rates[i]);
gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(rateCombo), choices);
}
// sync widget with cfg
g_config->getOption("SDL.Sound.Rate", &cfgBuf);
g_config->getOption("SDL.Sound.Rate", &buf);
for(int i=0; i<5; i++)
if(cfgBuf == rates[i])
if(buf == rates[i])
gtk_combo_box_set_active(GTK_COMBO_BOX(rateCombo), i);
g_signal_connect(rateCombo, "changed", G_CALLBACK(setRate), NULL);
@@ -1235,16 +1214,20 @@ void openSoundConfig()
gtk_box_pack_start(GTK_BOX(hbox2), rateLbl, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(hbox2), rateCombo, FALSE, FALSE, 5);
hbox3 = gtk_hbox_new(FALSE, 2);
bufferHscale = gtk_hscale_new_with_range(15, 200, 2);
bufferLbl = gtk_label_new("Buffer size (in ms)");
// sync widget with cfg
g_config->getOption("SDL.Sound.BufSize", &cfgBuf);
gtk_range_set_value(GTK_RANGE(bufferHscale), cfgBuf);
g_config->getOption("SDL.Sound.BufSize", &buf);
gtk_range_set_value(GTK_RANGE(bufferHscale), buf);
g_signal_connect(bufferHscale, "button-release-event", G_CALLBACK(setBufSize), NULL);
// Swap duty cycles
swapDutyChk = gtk_check_button_new_with_label("Swap Duty Cycles");
g_signal_connect(swapDutyChk, "clicked", G_CALLBACK(toggleSwapDuty), NULL);
setCheckbox(swapDutyChk, "SDL.SwapDuty");
// mixer
mixerFrame = gtk_frame_new("Mixer:");
mixerHbox = gtk_hbox_new(TRUE, 5);
@@ -1283,6 +1266,7 @@ void openSoundConfig()
gtk_box_pack_start(GTK_BOX(vbox), hbox2, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(vbox), bufferLbl, FALSE, FALSE, 5);
gtk_box_pack_start(GTK_BOX(vbox), bufferHscale, FALSE, TRUE, 5);
gtk_box_pack_start(GTK_BOX(vbox), swapDutyChk, FALSE, TRUE, 5);
gtk_box_pack_start(GTK_BOX(main_hbox), mixerFrame, TRUE, TRUE, 5);
gtk_container_add(GTK_CONTAINER(mixerFrame), mixerHbox);
@@ -1315,14 +1299,16 @@ void quit ()
}
const char* Authors[]= {
"Linux/SDL Developers:",
" Lukas Sabota", " Soules", " Bryan Cain", " radsaq", " Shinydoofy",
" Lukas Sabota //punkrockguy318", " Soules", " Bryan Cain", " radsaq", " Shinydoofy",
"FceuX 2.0 Developers:",
" SP", " zeromus", " adelikat", " caH4e3", " qfox",
" Luke Gustafson", " _mz", " UncombedCoconut", " DwEdit", " AnS",
" Luke Gustafson", " _mz", " UncombedCoconut", " DwEdit", " AnS", "rainwarrior", "feos",
"Pre 2.0 Guys:",
" Bero", " Xodnizel", " Aaron Oneal", " Joe Nahmias",
" Paul Kuliniewicz", " Quietust", " Ben Parnell", " Parasyte & bbitmaster",
" blip & nitsuja",
"Included components:",
" Mitsutaka Okazaki - YM2413 emulator", " Andrea Mazzoleni - Scale2x/Scale3x scalers", " Gilles Vollant - unzip.c PKZIP fileio",
NULL};
void openAbout ()
@@ -1332,7 +1318,7 @@ void openAbout ()
gtk_show_about_dialog(GTK_WINDOW(MainWindow),
"program-name", "fceuX",
"version", FCEU_VERSION_STRING,
"copyright", "© 2012 FceuX development team",
"copyright", "© 2015 FceuX development team",
"license", "GPL-2; See COPYING",
//"license-type", GTK_LICENSE_GPL_2_0,
"website", "http://fceux.com",
@@ -1379,6 +1365,14 @@ void enableFullscreen ()
ToggleFS();
}
void toggleMenuToggling (GtkToggleAction *action)
{
bool toggleMenu = gtk_toggle_action_get_active(action);
g_config->setOption("SDL.ToggleMenu", (int)toggleMenu);
menuTogglingEnabled = toggleMenu;
}
void toggleAutoResume (GtkToggleAction *action)
{
bool autoResume = gtk_toggle_action_get_active(action);
@@ -1391,9 +1385,9 @@ void recordMovie()
{
if(isloaded)
{
char* movie_fname = const_cast<char*>(FCEU_MakeFName(FCEUMKF_MOVIE, 0, 0).c_str());
FCEUI_printf("Recording movie to %s\n", movie_fname);
FCEUI_SaveMovie(movie_fname, MOVIE_FLAG_NONE, L"");
std::string name = FCEU_MakeFName(FCEUMKF_MOVIE, 0, 0);
FCEUI_printf("Recording movie to %s\n", name.c_str());
FCEUI_SaveMovie(name.c_str(), MOVIE_FLAG_NONE, L"");
}
return;
@@ -1432,7 +1426,6 @@ void recordMovieAs ()
fname = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (fileChooser));
if (!fname.size())
return; // no filename selected, quit the whole thing
char* movie_fname = const_cast<char*>(FCEU_MakeFName(FCEUMKF_MOVIE, 0, 0).c_str());
std::string s = GetUserText("Author name");
std::wstring author(s.begin(), s.end());
@@ -2213,6 +2206,7 @@ static char* menuXml =
" <menuitem action='PaletteConfigAction' />"
" <menuitem action='NetworkConfigAction' />"
" <menuitem action='AutoResumeAction' />"
" <menuitem action='ToggleMenuAction' />"
" <separator />"
" <menuitem action='FullscreenAction' />"
" </menu>"
@@ -2299,6 +2293,7 @@ static GtkActionEntry normal_entries[] = {
static GtkToggleActionEntry toggle_entries[] = {
{"GameGenieToggleAction", NULL, "Enable Game _Genie", NULL, NULL, G_CALLBACK(toggleGameGenie), FALSE},
{"AutoResumeAction", NULL, "Auto-Resume Play", NULL, NULL, G_CALLBACK(toggleAutoResume), FALSE},
{"ToggleMenuAction", NULL, "Toggle Menubar (alt)", NULL, NULL, G_CALLBACK(toggleMenuToggling), FALSE},
};
// Menu items for selecting a save state slot using radio buttons
@@ -2373,6 +2368,28 @@ void showGui(bool b)
gtk_widget_hide(MainWindow);
}
gint handleKeyRelease(GtkWidget* w, GdkEvent* event, gpointer cb_data)
{
if(menuTogglingEnabled)
{
static bool menuShown = true;
if(((GdkEventKey*)event)->keyval == GDK_KEY_Alt_L || ((GdkEventKey*)event)->keyval == GDK_KEY_Alt_R)
{
if(menuShown)
{
gtk_widget_hide(Menubar);
menuShown = false;
}
else
{
gtk_widget_show(Menubar);
menuShown = true;
}
}
}
return 0;
};
int GtkMouseData[3] = {0,0,0};
gint handleMouseClick(GtkWidget* widget, GdkEvent *event, gpointer callback_data)
@@ -2448,11 +2465,13 @@ void handle_resize(GtkWindow* win, GdkEvent* event, gpointer data)
InitVideo(GameInfo);
}
gtk_widget_set_size_request(evbox, (int)(NES_WIDTH*xscale), (int)(NES_HEIGHT*yscale));
GdkColor black;
// Currently unused; unsure why
/* GdkColor black;
black.red = 0;
black.green = 0;
black.blue = 0;
// gtk_widget_modify_bg(GTK_WIDGET(win), GTK_STATE_NORMAL, &black);
gtk_widget_modify_bg(GTK_WIDGET(win), GTK_STATE_NORMAL, &black);*/
printf("DEBUG: new xscale: %f yscale: %f\n", xscale, yscale);
@@ -2461,10 +2480,10 @@ void handle_resize(GtkWindow* win, GdkEvent* event, gpointer data)
int InitGTKSubsystem(int argc, char** argv)
{
GtkWidget* Menubar;
GtkWidget* vbox;
MainWindow = gtk_window_new(GTK_WINDOW_TOPLEVEL);
gtk_widget_set_events(GTK_WIDGET(MainWindow), GDK_KEY_RELEASE_MASK);
// gtk_window_set_policy (GTK_WINDOW (MainWindow), FALSE, FALSE, TRUE);
gtk_window_set_resizable(GTK_WINDOW(MainWindow), TRUE);
gtk_window_set_title(GTK_WINDOW(MainWindow), FCEU_NAME_AND_VERSION);
@@ -2516,6 +2535,7 @@ int InitGTKSubsystem(int argc, char** argv)
g_signal_connect(G_OBJECT(evbox), "button-press-event", G_CALLBACK(handleMouseClick), NULL);
g_signal_connect(G_OBJECT(evbox), "button-release-event", G_CALLBACK(handleMouseClick), NULL);
g_signal_connect(G_OBJECT(MainWindow), "key-release-event", G_CALLBACK(handleKeyRelease), NULL);
// signal handlers
g_signal_connect(MainWindow, "delete-event", quit, NULL);
-31
View File
@@ -38,39 +38,17 @@ void showGui(bool b);
bool checkGTKVersion(int major_required, int minor_required);
int configHotkey(char* hotkeyString);
int configGamepadButton(GtkButton* button, gpointer p);
void resetVideo();
void closeVideoWin(GtkWidget* w, GdkEvent* e, gpointer p);
void closeDialog(GtkWidget* w, GdkEvent* e, gpointer p);
void toggleLowPass(GtkWidget* w, gpointer p);
void toggleOption(GtkWidget* w, gpointer p);
int setTint(GtkWidget* w, gpointer p);
int setHue(GtkWidget* w, gpointer p);
void loadPalette (GtkWidget* w, gpointer p);
void clearPalette(GtkWidget* w, gpointer p);
void openPaletteConfig();
void launchNet(GtkWidget* w, gpointer p);
void setUsername(GtkWidget* w, gpointer p);
void netResponse(GtkWidget* w, gint response_id, gpointer p);
void openNetworkConfig();
void flushGtkEvents();
void openHotkeyConfig();
int setInputDevice(GtkWidget* w, gpointer p);
void updateGamepadConfig(GtkWidget* w, gpointer p);
void openGamepadConfig();
int setBufSize(GtkWidget* w, gpointer p);
void setRate(GtkWidget* w, gpointer p);
void setQuality(GtkWidget* w, gpointer p);
void resizeGtkWindow();
void setScaler(GtkWidget* w, gpointer p);
int setXscale(GtkWidget* w, gpointer p);
int setYscale(GtkWidget* w, gpointer p);
#ifdef OPENGL
void setGl(GtkWidget* w, gpointer p);
@@ -78,16 +56,13 @@ void setDoubleBuffering(GtkWidget* w, gpointer p);
#endif
void openVideoConfig();
int mixerChanged(GtkWidget* w, gpointer p);
void openSoundConfig();
void quit ();
void openAbout ();
void toggleSound(GtkWidget* check, gpointer data);
void emuReset ();
void hardReset ();
void enableFullscreen ();
void toggleAutoResume (GtkToggleAction *action);
void recordMovie();
void recordMovieAs ();
@@ -98,8 +73,6 @@ void loadLua ();
void loadFdsBios ();
void enableGameGenie(int enabled);
void toggleGameGenie(GtkToggleAction *action);
void togglePause(GtkAction *action);
void loadGameGenie ();
void loadNSF ();
@@ -109,11 +82,7 @@ void saveStateAs();
void loadStateFrom();
void quickLoad();
void quickSave();
void changeState(GtkAction *action, GtkRadioAction *current, gpointer data);
unsigned short GDKToSDLKeyval(int gdk_key);
gint convertKeypress(GtkWidget *grab, GdkEventKey *event, gpointer user_data);
gint handleMouseClick(GtkWidget* widget, GdkEvent *event, gpointer callback_data);
void handle_resize(GtkWindow* win, GdkEvent* event, gpointer data);
int InitGTKSubsystem(int argc, char** argv);
#endif // ifndef FCEUX_GUI_H
+21
View File
@@ -784,6 +784,16 @@ static void KeyboardCommands ()
movieSubtitles ? "n" : "ff");
}
if (_keyonly (Hotkeys[HK_VOLUME_DOWN]))
{
FCEUD_SoundVolumeAdjust(-1);
}
if (_keyonly (Hotkeys[HK_VOLUME_UP]))
{
FCEUD_SoundVolumeAdjust(1);
}
// VS Unisystem games
if (gametype == GIT_VSUNI)
{
@@ -1268,6 +1278,7 @@ void FCEUD_UpdateInput ()
switch (CurInputType[x])
{
case SI_GAMEPAD:
case SI_SNES:
t |= 1;
break;
case SI_ARKANOID:
@@ -1280,6 +1291,10 @@ void FCEUD_UpdateInput ()
case SI_POWERPADB:
powerpadbuf[x] = UpdatePPadData (x);
break;
case SI_MOUSE:
case SI_SNES_MOUSE:
t |= 2;
break;
}
}
@@ -1376,6 +1391,7 @@ void InitInputInterface ()
InputDPtr = &powerpadbuf[x];
break;
case SI_GAMEPAD:
case SI_SNES:
InputDPtr = &JSreturn;
break;
case SI_ARKANOID:
@@ -1387,6 +1403,11 @@ void InitInputInterface ()
t |= 1;
attrib = 1;
break;
case SI_MOUSE:
case SI_SNES_MOUSE:
InputDPtr = MouseData;
t |= 1;
break;
}
FCEUI_SetInput (x, (ESI) CurInputType[x], InputDPtr, attrib);
}
+2
View File
@@ -40,6 +40,8 @@ extern int _sound;
extern long soundrate;
extern long soundbufsize;
extern int pal_emulation;
int CLImain(int argc, char *argv[]);
// Device management defaults
+2 -2
View File
@@ -224,7 +224,7 @@ void
FCEUD_SoundVolumeAdjust(int n)
{
int soundvolume;
g_config->getOption("SDL.SoundVolume", &soundvolume);
g_config->getOption("SDL.Sound.Volume", &soundvolume);
switch(n) {
case -1:
@@ -246,7 +246,7 @@ FCEUD_SoundVolumeAdjust(int n)
s_mute = 0;
FCEUI_SetSoundVolume(soundvolume);
g_config->setOption("SDL.SoundVolume", soundvolume);
g_config->setOption("SDL.Sound.Volume", soundvolume);
FCEU_DispMessage("Sound volume %d.",0, soundvolume);
}
+44 -24
View File
@@ -42,6 +42,8 @@
#ifdef _GTK
#include "gui.h"
#endif
#ifdef GDK_WINDOWING_X11
#include <gdk/gdkx.h>
#endif
@@ -142,10 +144,10 @@ void FCEUD_VideoChanged()
{
int buf;
g_config->getOption("SDL.PAL", &buf);
if(buf)
if(buf == 1)
PAL = 1;
else
PAL = 0;
PAL = 0; // NTSC and Dendy
}
#if SDL_VERSION_ATLEAST(2, 0, 0)
@@ -305,18 +307,6 @@ InitVideo(FCEUGI *gi)
desbpp = 0;
}
// -Video Modes Tag-
if(s_sponge) {
if(s_sponge == 4 || s_sponge == 5) {
s_exs = s_eys = 3;
} else {
s_exs = s_eys = 2;
}
s_eefx = 0;
if(s_sponge == 1 || s_sponge == 4) {
desbpp = 32;
}
}
if((s_useOpenGL && !xstretch) || !s_useOpenGL)
#endif
@@ -354,15 +344,39 @@ InitVideo(FCEUGI *gi)
g_config->getOption("SDL.XScale", &s_exs);
g_config->getOption("SDL.YScale", &s_eys);
g_config->getOption("SDL.SpecialFX", &s_eefx);
// -Video Modes Tag-
if(s_sponge) {
if(s_sponge >= 4) {
s_exs = s_eys = 3;
} else {
if(s_sponge <= 3 && s_sponge >= 1)
{
s_exs = s_eys = 2;
} else if (s_sponge >=4 && s_sponge <= 5)
{
s_exs = s_eys = 3;
} else if (s_sponge >= 6 && s_sponge <= 8)
{
s_exs = s_eys = s_sponge - 4;
}
else if(s_sponge == 9)
{
s_exs = s_eys = 3;
}
else
{
s_exs = s_eys = 1;
}
if(s_sponge == 3) {
xres = 301 * s_exs;
}
s_eefx = 0;
if(s_sponge == 1 || s_sponge == 4) {
desbpp = 32;
}
}
int scrw = NWIDTH * s_exs;
if(s_sponge == 3) {
scrw = 301 * s_exs;
}
#ifdef OPENGL
@@ -387,7 +401,7 @@ InitVideo(FCEUGI *gi)
}
#endif
#if defined(_GTK) && defined(SDL_VIDEO_DRIVER_X11)
#if defined(_GTK) && defined(SDL_VIDEO_DRIVER_X11) && defined(GDK_WINDOWING_X11)
if(noGui == 0)
{
while (gtk_events_pending())
@@ -408,8 +422,7 @@ InitVideo(FCEUGI *gi)
}
#endif
s_screen = SDL_SetVideoMode((int)(NWIDTH * s_exs),
(int)(s_tlines * s_eys),
s_screen = SDL_SetVideoMode(scrw, (int)(s_tlines * s_eys),
desbpp, flags);
if(!s_screen) {
FCEUD_PrintError(SDL_GetError());
@@ -687,6 +700,13 @@ BlitScreen(uint8 *XBuf)
SDL_UnlockSurface(TmpScreen);
}
int scrw;
if(s_sponge == 3) { // NTSC 2x
scrw = 301;
} else {
scrw = NWIDTH;
}
// if we have a hardware video buffer, do a fast video->video copy
if(s_BlitBuf) {
SDL_Rect srect;
@@ -694,12 +714,12 @@ BlitScreen(uint8 *XBuf)
srect.x = 0;
srect.y = 0;
srect.w = NWIDTH;
srect.w = scrw;
srect.h = s_tlines;
drect.x = 0;
drect.y = 0;
drect.w = (Uint16)(s_exs * NWIDTH);
drect.w = (Uint16)(s_exs * scrw);
drect.h = (Uint16)(s_eys * s_tlines);
SDL_BlitSurface(s_BlitBuf, &srect, s_screen, &drect);
@@ -710,7 +730,7 @@ BlitScreen(uint8 *XBuf)
//TODO - SDL2
#else
SDL_UpdateRect(s_screen, xo, yo,
(Uint32)(NWIDTH * s_exs), (Uint32)(s_tlines * s_eys));
(Uint32)(scrw * s_exs), (Uint32)(s_tlines * s_eys));
#endif
#ifdef CREATE_AVI
+1 -1
View File
@@ -3,7 +3,7 @@
#ifdef _SDL2
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#include <SDL.h>
#endif
uint32 PtoV(uint16 x, uint16 y);
+22 -6
View File
@@ -72,6 +72,10 @@ int mutecapture;
#endif
static int noconfig;
int pal_emulation;
int dendy;
bool swapDuty;
// -Video Modes Tag- : See --special
static const char *DriverUsage=
"Option Value Description\n"
@@ -100,8 +104,8 @@ static const char *DriverUsage=
"--fullscreen {0|1} Enable full screen mode.\n"
"--noframe {0|1} Hide title bar and window decorations.\n"
"--special {1-4} Use special video scaling filters\n"
" (1 = hq2x 2 = Scale2x 3 = NTSC 2x 4 = hq3x\n"
" 5 = Scale3x)\n"
" (1 = hq2x; 2 = Scale2x; 3 = NTSC 2x; 4 = hq3x;\n"
" 5 = Scale3x; 6 = Prescale2x; 7 = Prescale3x; 8=Precale4x; 9=PAL)\n"
"--palette f Load custom global palette from file f.\n"
"--sound {0|1} Enable sound.\n"
"--soundrate x Set sound playback rate to x Hz.\n"
@@ -213,10 +217,10 @@ int LoadGame(const char *path)
// set pal/ntsc
int id;
g_config->getOption("SDL.PAL", &id);
if(id)
FCEUI_SetVidSystem(1);
else
FCEUI_SetVidSystem(0);
FCEUI_SetRegion(id);
g_config->getOption("SDL.SwapDuty", &id);
swapDuty = id;
std::string filename;
g_config->getOption("SDL.Sound.RecordFile", &filename);
@@ -623,6 +627,18 @@ int main(int argc, char *argv[])
// update the input devices
UpdateInput(g_config);
// check if opengl is enabled with a scaler and display an error and bail
int opengl;
int scaler;
g_config->getOption("SDL.OpenGL", &opengl);
g_config->getOption("SDL.SpecialFilter", &scaler);
if(opengl && scaler)
{
printf("Scalers are not supported in OpenGL mode. Terminating.\n");
exit(2);
}
// check for a .fcm file to convert to .fm2
g_config->getOption ("SDL.FCMConvert", &s);
g_config->setOption ("SDL.FCMConvert", "");
+4
View File
@@ -20,6 +20,10 @@ const int INVALID_STATE = 99;
extern int noGui;
extern int isloaded;
extern int dendy;
extern int pal_emulation;
extern bool swapDuty;
int LoadGame(const char *path);
int CloseGame(void);
void FCEUD_Update(uint8 *XBuf, int32 *Buffer, int Count);
+1 -1
View File
@@ -1,2 +1,2 @@
void RefreshThrottleFPS(void);
void RefreshThrottleFPS();
int SpeedThrottle(void);
Regular → Executable
View File
+5
View File
@@ -29,6 +29,8 @@ char* ConfigToLoad = 0; //Loads a specific .cfg file (loads before any other co
char* LuaToLoad = 0; //Loads a specific lua file
char* PaletteToLoad = 0; //Loads a specific palette file
char* AviToLoad = 0; //Starts an avi capture at startup
char* DumpInput = 0; //Dumps all polled input to a binary file. Probably only useful with -playmovie. This is a rickety system, only useful in limited cases.
char* PlayInput = 0; //Replays all polled input from a binary file. Useful without playmovie. This is a rickety system, only useful in limited cases.
extern bool turbo;
@@ -41,6 +43,7 @@ char *ParseArgies(int argc, char *argv[])
{
static ARGPSTRUCT FCEUArgs[]={
{"-pal",&pal_setting_specified,&pal_emulation,0},
{"-dendy",0,&dendy,0},
{"-noicon",0,&status_icon,0},
{"-gg",0,&genie,0},
{"-no8lim",0,&eoptions,0x8000|EO_NOSPRLIM},
@@ -64,6 +67,8 @@ char *ParseArgies(int argc, char *argv[])
{"-cfg",0,&ConfigToLoad,0x4001},
{"-avi",0,&AviToLoad,0x4001},
{"-avicapture",0,&AVICapture,0},
{"-dumpinput",0,&DumpInput,0x4001},
{"-playinput",0,&PlayInput,0x4001},
{0, 0, 0, 0},
};
+13 -11
View File
@@ -1,11 +1,13 @@
extern char* MovieToLoad; //Contains the filename of the savestate specified in the command line arguments
extern char* StateToLoad; //Contains the filename of the movie file specified in the command line arguments
extern char* ConfigToLoad; //Contains the filename of the config file specified in the command line arguments
extern char* LuaToLoad; //Contains the filename of the lua script specified in the command line arguments
extern char* PaletteToLoad; //Contains the filename of the palette file specified in the command line arguments
extern char* AviToLoad; //Contains the filename of the Avi to be captured specified in the command line arguments
extern bool replayReadOnlySetting;
extern int replayStopFrameSetting;
extern int PauseAfterLoad;
extern int AVICapture; //This initiates AVI capture mode with a frame number, on that frame number the AVI will stop, FCEUX will close, and a special return value will be set
char *ParseArgies(int argc, char *argv[]);
extern char* MovieToLoad; //Contains the filename of the savestate specified in the command line arguments
extern char* StateToLoad; //Contains the filename of the movie file specified in the command line arguments
extern char* ConfigToLoad; //Contains the filename of the config file specified in the command line arguments
extern char* LuaToLoad; //Contains the filename of the lua script specified in the command line arguments
extern char* PaletteToLoad; //Contains the filename of the palette file specified in the command line arguments
extern char* AviToLoad; //Contains the filename of the Avi to be captured specified in the command line arguments
extern char* DumpInput;
extern char* PlayInput;
extern bool replayReadOnlySetting;
extern int replayStopFrameSetting;
extern int PauseAfterLoad;
extern int AVICapture; //This initiates AVI capture mode with a frame number, on that frame number the AVI will stop, FCEUX will close, and a special return value will be set
char *ParseArgies(int argc, char *argv[]);
+14 -5
View File
@@ -414,6 +414,11 @@ void SaveStrippedROM(int invert)
if(!GetSaveFileName(&ofn))return;
fp = fopen(sromfilename,"wb");
if(!fp)
{
FCEUD_PrintError("Error opening target stripped rom file!");
return;
}
if(GameInfo->type==GIT_NSF)
{
@@ -549,13 +554,13 @@ void FreeCDLog()
if (cdloggerdata)
{
free(cdloggerdata);
cdloggerdata = 0;
cdloggerdata = NULL;
cdloggerdataSize = 0;
}
if (cdloggervdata)
{
free(cdloggervdata);
cdloggervdata = 0;
cdloggervdata = NULL;
cdloggerVideoDataSize = 0;
}
}
@@ -567,8 +572,10 @@ void InitCDLog()
if(!CHRram[0] || (CHRptr[0] == PRGptr[0])) { // Some kind of workaround for my OneBus VRAM hack, will remove it if I find another solution for that
cdloggerVideoDataSize = CHRsize[0];
cdloggervdata = (unsigned char*)malloc(cdloggerVideoDataSize);
} else
} else {
cdloggerVideoDataSize = 0;
cdloggervdata = (unsigned char*)malloc(8192);
}
}
void ResetCDLog()
@@ -576,10 +583,12 @@ void ResetCDLog()
codecount = datacount = rendercount = vromreadcount = 0;
undefinedcount = cdloggerdataSize;
ZeroMemory(cdloggerdata, cdloggerdataSize);
if(cdloggerVideoDataSize != 0)
{
if(cdloggerVideoDataSize != 0) {
undefinedvromcount = cdloggerVideoDataSize;
ZeroMemory(cdloggervdata, cdloggerVideoDataSize);
} else {
undefinedvromcount = 8192;
ZeroMemory(cdloggervdata, 8192);
}
}
+116 -116
View File
@@ -1,117 +1,117 @@
#include "common.h"
bool directoryExists(const char* dirname)
{
DWORD res = GetFileAttributes(dirname);
return res != 0xFFFFFFFF && res & FILE_ATTRIBUTE_DIRECTORY;
}
void WindowBoundsCheckResize(int &windowPosX, int &windowPosY, int windowSizeX, long windowRight)
{
if (windowRight < 59) {
windowPosX = 59 - windowSizeX;
}
if (windowPosY < -18) {
windowPosY = -18;
}
}
void WindowBoundsCheckNoResize(int &windowPosX, int &windowPosY, long windowRight)
{
if (windowRight < 59) {
windowPosX = 0;
}
if (windowPosY < -18) {
windowPosY = -18;
}
}
int recalculateResizedItemCoordinate(int initialValue, int initialBase, int newBase, unsigned int resizingType)
{
switch (resizingType)
{
default:
case WINDOW_ITEM_RESIZE_TYPE_LEFT_ALIGNED:
{
return initialValue;
}
case WINDOW_ITEM_RESIZE_TYPE_RIGHT_ALIGNED:
{
return newBase - (initialBase - initialValue);
}
case WINDOW_ITEM_RESIZE_TYPE_CENTER_ALIGNED:
{
return initialValue + (newBase - initialBase) / 2;
}
case WINDOW_ITEM_RESIZE_TYPE_MULTIPLY:
{
return (newBase * initialValue) / initialBase;
break;
}
}
}
// Check if a filename/path has the given extension. The extension is expected to be at the very end of the filename
void AddExtensionIfMissing(char * name, unsigned int maxsize, const char * extension)
{
std::string tempName = name;
// Non-null terminated lengths of both strings, +1 for null termination
if ((strlen(name) + strlen(extension) + 1) <= maxsize)
{
unsigned int x = tempName.rfind(extension);
// x == -1 means the extension string wasn't found
// if the extension was found in the middle of the string, this doesn't count as extension
if ((x == -1) || ((x + strlen(extension)) < tempName.size()))
{
tempName.append(extension);
strcpy(name, tempName.c_str());
}
}
}
// Overloaded operator of above, which deals with native std::string variants.
void AddExtensionIfMissing(std::string &name, const char * extension)
{
unsigned int x = name.rfind(extension);
if ((x == -1) || ((x + strlen(extension)) < name.size()))
name.append(extension);
}
std::string GetPath(std::string filename)
{
return filename.substr(0, filename.find_last_of("/\\") + 1);
}
bool IsRelativePath(char* name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
bool IsRelativePath(const char* name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
bool IsRelativePath(std::string name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
//Precondition: IsRelativePath() == true
std::string ConvertRelativePath(std::string name)
{
extern std::string BaseDirectory;
return BaseDirectory + '\\' + name.substr(2, name.length());
#include "common.h"
bool directoryExists(const char* dirname)
{
DWORD res = GetFileAttributes(dirname);
return res != 0xFFFFFFFF && res & FILE_ATTRIBUTE_DIRECTORY;
}
void WindowBoundsCheckResize(int &windowPosX, int &windowPosY, int windowSizeX, long windowRight)
{
if (windowRight < 59) {
windowPosX = 59 - windowSizeX;
}
if (windowPosY < -18) {
windowPosY = -18;
}
}
void WindowBoundsCheckNoResize(int &windowPosX, int &windowPosY, long windowRight)
{
if (windowRight < 59) {
windowPosX = 0;
}
if (windowPosY < -18) {
windowPosY = -18;
}
}
int recalculateResizedItemCoordinate(int initialValue, int initialBase, int newBase, unsigned int resizingType)
{
switch (resizingType)
{
default:
case WINDOW_ITEM_RESIZE_TYPE_LEFT_ALIGNED:
{
return initialValue;
}
case WINDOW_ITEM_RESIZE_TYPE_RIGHT_ALIGNED:
{
return newBase - (initialBase - initialValue);
}
case WINDOW_ITEM_RESIZE_TYPE_CENTER_ALIGNED:
{
return initialValue + (newBase - initialBase) / 2;
}
case WINDOW_ITEM_RESIZE_TYPE_MULTIPLY:
{
return (newBase * initialValue) / initialBase;
break;
}
}
}
// Check if a filename/path has the given extension. The extension is expected to be at the very end of the filename
void AddExtensionIfMissing(char * name, unsigned int maxsize, const char * extension)
{
std::string tempName = name;
// Non-null terminated lengths of both strings, +1 for null termination
if ((strlen(name) + strlen(extension) + 1) <= maxsize)
{
unsigned int x = tempName.rfind(extension);
// x == -1 means the extension string wasn't found
// if the extension was found in the middle of the string, this doesn't count as extension
if ((x == -1) || ((x + strlen(extension)) < tempName.size()))
{
tempName.append(extension);
strcpy(name, tempName.c_str());
}
}
}
// Overloaded operator of above, which deals with native std::string variants.
void AddExtensionIfMissing(std::string &name, const char * extension)
{
unsigned int x = name.rfind(extension);
if ((x == -1) || ((x + strlen(extension)) < name.size()))
name.append(extension);
}
std::string GetPath(std::string filename)
{
return filename.substr(0, filename.find_last_of("/\\") + 1);
}
bool IsRelativePath(char* name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
bool IsRelativePath(const char* name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
bool IsRelativePath(std::string name)
{
if (name[0] == '.')
if (name[1] == '\\') return true;
else if (name[1] == '.' && name[2] == '\\') return true;
return false;
}
//Precondition: IsRelativePath() == true
std::string ConvertRelativePath(std::string name)
{
extern std::string BaseDirectory;
return BaseDirectory + '\\' + name.substr(2, name.length());
}
+1 -1
View File
@@ -35,7 +35,7 @@ extern int eoptions;
#define EO_BGRUN 1
#define EO_CPALETTE 4
#define EO_CPALETTE 4 //this is bad, it is desynchronized from other state management in palette.cpp
#define EO_NOSPRLIM 8
#define EO_FSAFTERLOAD 32
#define EO_FOAFTERSTART 64
+29 -11
View File
@@ -18,14 +18,6 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/****************************************************************/
/* FCE Ultra */
/* */
/* This file contains code to interface to the standard */
/* FCE Ultra configuration file saving/loading code. */
/* */
/****************************************************************/
#include "config.h"
#include "common.h"
#include "main.h"
@@ -74,6 +66,13 @@ extern bool fullSaveStateLoads;
extern int frameSkipAmt;
extern int32 fps_scale_frameadvance;
extern bool symbDebugEnabled;
extern bool symbRegNames;
extern int palnotch;
extern int palsaturation;
extern int palsharpness;
extern int palcontrast;
extern int palbrightness;
extern bool paldeemphswap;
extern TASEDITOR_CONFIG taseditorConfig;
extern char* recentProjectsArray[];
@@ -95,6 +94,7 @@ extern int NTViewPosX,NTViewPosY;
extern int PPUViewPosX, PPUViewPosY;
extern bool PPUView_maskUnusedGraphics;
extern bool PPUView_invertTheMask;
extern int PPUView_sprite16Mode;
extern int MainWindow_wndx, MainWindow_wndy;
extern int MemWatch_wndx, MemWatch_wndy;
extern int Monitor_wndx, Monitor_wndy;
@@ -180,8 +180,19 @@ static CFGSTRUCT fceuconfig[] =
ACS(ResumeROM),
AC(gNoBGFillColor),
AC(ntsccol),AC(ntsctint),AC(ntschue),
AC(ntsccol_enable),AC(ntsctint),AC(ntschue),
AC(force_grayscale),
AC(dendy),
AC(postrenderscanlines),
AC(vblankscanlines),
AC(overclock_enabled),
AC(skip_7bit_overclocking),
AC(palnotch),
AC(palsaturation),
AC(palsharpness),
AC(palcontrast),
AC(palbrightness),
AC(paldeemphswap),
NAC("palyo",pal_emulation),
NAC("genie",genie),
@@ -224,10 +235,12 @@ static CFGSTRUCT fceuconfig[] =
AC(soundNoisevol),
AC(soundPCMvol),
AC(muteTurbo),
AC(swapDuty),
AC(goptions),
NAC("eoptions",eoptions),
NACA("cpalette",cpalette),
NAC("cpalette_count",cpalette_count),
NACA("InputType",InputType),
@@ -276,10 +289,14 @@ static CFGSTRUCT fceuconfig[] =
AC(debuggerAutoload),
AC(allowUDLR),
AC(symbDebugEnabled),
AC(symbRegNames),
AC(debuggerSaveLoadDEBFiles),
AC(debuggerDisplayROMoffsets),
AC(debuggerFontSize),
AC(hexeditorFontSize),
AC(debuggerPageSize),
AC(hexeditorFontWidth),
AC(hexeditorFontHeight),
ACS(hexeditorFontName),
AC(fullSaveStateLoads),
AC(frameSkipAmt),
AC(fps_scale_frameadvance),
@@ -306,6 +323,7 @@ static CFGSTRUCT fceuconfig[] =
AC(PPUViewPosY),
AC(PPUView_maskUnusedGraphics),
AC(PPUView_invertTheMask),
AC(PPUView_sprite16Mode),
AC(MainWindow_wndx),
AC(MainWindow_wndy),
AC(MemWatch_wndx),
@@ -466,7 +484,7 @@ void LoadConfig(const char *filename)
LoadFCEUConfig(filename, fceuconfig);
FCEUI_SetNTSCTH(ntsccol, ntsctint, ntschue);
FCEUI_SetNTSCTH(ntsccol_enable, ntsctint, ntschue);
//adelikat:Hacky fix for Ram Watch recent menu
for (int x = 0; x < 5; x++)
+4 -4
View File
@@ -1,4 +1,4 @@
void SaveConfig(const char *filename);
void LoadConfig(const char *filename);
extern int InputType[3];
void SaveConfig(const char *filename);
void LoadConfig(const char *filename);
extern int InputType[3];
+54 -13
View File
@@ -26,6 +26,7 @@
#include "../../fceu.h"
#include "../../debug.h"
#include "../../nsf.h"
#include "../../ppu.h"
#include "../../cart.h"
#include "../../ines.h"
#include "../../asm.h"
@@ -41,12 +42,10 @@
#include "debuggersp.h"
extern Name* lastBankNames;
extern Name* loadedBankNames;
extern Name* pageNames[32];
extern Name* ramBankNames;
extern bool ramBankNamesLoaded;
extern int lastBank;
extern int loadedBank;
extern int pageNumbersLoaded[32];
extern int myNumWPs;
// ################################## End of SP CODE ###########################
@@ -111,7 +110,7 @@ void RestoreSize(HWND hwndDlg)
{
//If the dialog dimensions are changed those changes need to be reflected here. - adelikat
const int DEFAULT_WIDTH = 820; //Original width
const int DEFAULT_HEIGHT = 560; //Original height
const int DEFAULT_HEIGHT = 570; //Original height
SetWindowPos(hwndDlg,HWND_TOP,DbgPosX,DbgPosY,DEFAULT_WIDTH,DEFAULT_HEIGHT,SWP_SHOWWINDOW);
}
@@ -525,8 +524,9 @@ void Disassemble(HWND hWnd, int id, int scrollid, unsigned int addr)
if (symbDebugEnabled)
{
replaceNames(ramBankNames, a, &disassembly_operands[i]);
replaceNames(loadedBankNames, a, &disassembly_operands[i]);
replaceNames(lastBankNames, a, &disassembly_operands[i]);
for(int p=0;p<ARRAY_SIZE(pageNames);p++)
if(pageNames[p] != NULL)
replaceNames(pageNames[p], a, &disassembly_operands[i]);
}
// special case: an RTS opcode
@@ -856,7 +856,7 @@ void UpdateDebugger(bool jump_to_pc)
sprintf(str, "%04X", (int)X.PC);
SetDlgItemText(hDebug, IDC_DEBUGGER_VAL_PC, str);
sprintf(str, "%04X", (int)RefreshAddr);
sprintf(str, "%04X", (int)FCEUPPU_PeekAddress());
SetDlgItemText(hDebug, IDC_DEBUGGER_VAL_PPU, str);
sprintf(str, "%02X", PPU[3]);
SetDlgItemText(hDebug, IDC_DEBUGGER_VAL_SPR, str);
@@ -892,6 +892,13 @@ void UpdateDebugger(bool jump_to_pc)
sprintf(str, "%d", scanline);
sprintf(str2, "%d", ppupixel);
}
if(newppu)
{
sprintf(str,"%d",newppu_get_scanline());
sprintf(str2,"%d",newppu_get_dot());
}
SetDlgItemText(hDebug, IDC_DEBUGGER_VAL_SLINE, str);
SetDlgItemText(hDebug, IDC_DEBUGGER_VAL_PPUPIXEL, str2);
@@ -1614,6 +1621,7 @@ BOOL CALLBACK DebuggerCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPara
CheckDlgButton(hwndDlg, DEBUGAUTOLOAD, debuggerAutoload ? BST_CHECKED : BST_UNCHECKED);
CheckDlgButton(hwndDlg, IDC_DEBUGGER_ROM_OFFSETS, debuggerDisplayROMoffsets ? BST_CHECKED : BST_UNCHECKED);
CheckDlgButton(hwndDlg, IDC_DEBUGGER_ENABLE_SYMBOLIC, symbDebugEnabled ? BST_CHECKED : BST_UNCHECKED);
CheckDlgButton(hwndDlg, IDC_DEBUGGER_PREDEFINED_REGS, symbRegNames ? BST_CHECKED : BST_UNCHECKED);
if (DbgPosX==-32000) DbgPosX=0; //Just in case
if (DbgPosY==-32000) DbgPosY=0;
@@ -2083,7 +2091,15 @@ BOOL CALLBACK DebuggerCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPara
//mbg merge 7/18/06 changed pausing check and set
if (FCEUI_EmulationPaused()) {
UpdateRegs(hwndDlg);
if (GetMem(tmp=X.PC) == 0x20) {
uint8 opcode = GetMem(tmp=X.PC);
bool jsr = opcode==0x20;
bool call = jsr;
#ifdef BRK_3BYTE_HACK
//with this hack, treat BRK similar to JSR
if(opcode == 0x00)
call = true;
#endif
if (call) {
if ((watchpoint[64].flags) && (MessageBox(hwndDlg,"Step Over is currently in process. Cancel it and setup a new Step Over watch?","Step Over Already Active",MB_YESNO|MB_ICONINFORMATION) != IDYES)) break;
watchpoint[64].address = (tmp+3);
watchpoint[64].flags = WP_E|WP_X;
@@ -2152,7 +2168,8 @@ BOOL CALLBACK DebuggerCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPara
case IDC_DEBUGGER_RELOAD_SYMS:
{
ramBankNamesLoaded = false;
lastBank = loadedBank = -1;
for(int i=0;i<ARRAYSIZE(pageNumbersLoaded);i++)
pageNumbersLoaded[i] = -1;
loadNameFiles();
UpdateDebugger(false);
break;
@@ -2167,6 +2184,13 @@ BOOL CALLBACK DebuggerCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPara
UpdateDebugger(false);
break;
}
case IDC_DEBUGGER_PREDEFINED_REGS:
{
symbRegNames ^= 1;
CheckDlgButton(hwndDlg, IDC_DEBUGGER_PREDEFINED_REGS, symbRegNames ? BST_CHECKED : BST_UNCHECKED);
UpdateDebugger(false);
break;
}
// ################################## End of SP CODE ###########################
@@ -2230,6 +2254,13 @@ BOOL CALLBACK DebuggerCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPara
extern void iNESGI(GI h);
void DoDebuggerStepInto()
{
if (!hDebug)
return;
DebuggerCallB(hDebug, WM_COMMAND, IDC_DEBUGGER_STEP_IN, 0);
}
void DoPatcher(int address, HWND hParent)
{
iapoffset = address;
@@ -2307,7 +2338,9 @@ void DoDebug(uint8 halt)
//-----------------------------------------
DebugSystem* debugSystem;
unsigned int debuggerFontSize = 15;
unsigned int hexeditorFontSize = 15;
unsigned int hexeditorFontHeight = 15;
unsigned int hexeditorFontWidth = 7;
char* hexeditorFontName = 0;
DebugSystem::DebugSystem()
{
@@ -2322,12 +2355,20 @@ void DebugSystem::init()
DEFAULT_QUALITY, DEFAULT_PITCH, /*quality, and pitch*/
"Courier New"); /*font name*/
hHexeditorFont = CreateFont(hexeditorFontSize, hexeditorFontSize / 2, /*Height,Width*/
//if the user provided his own courier font, use that
extern std::string BaseDirectory;
std::string courefon_path = BaseDirectory + "\\coure.fon";
AddFontResourceEx(courefon_path.c_str(), FR_PRIVATE, NULL);
char* hexfn = hexeditorFontName;
if(!hexfn) hexfn = "Courier";
hHexeditorFont = CreateFont(hexeditorFontHeight, hexeditorFontWidth, /*Height,Width*/
0,0, /*escapement,orientation*/
FW_REGULAR,FALSE,FALSE,FALSE, /*weight, italic, underline, strikeout*/
ANSI_CHARSET,OUT_DEVICE_PRECIS,CLIP_MASK, /*charset, precision, clipping*/
DEFAULT_QUALITY, DEFAULT_PITCH, /*quality, and pitch*/
"Courier"); /*font name*/
hexfn); /*font name*/
HDC hdc = GetDC(GetDesktopWindow());
HGDIOBJ old = SelectObject(hdc,hFixedFont);
+4 -2
View File
@@ -14,7 +14,6 @@
#define INVALID_BREAKPOINT_CONDITION 3
//extern volatile int userpause; //mbg merge 7/18/06 removed for merging
extern int scanline; //current scanline! :D
extern HWND hDebug;
extern int childwnd,numWPs; //mbg merge 7/18/06 had to make extern
@@ -22,8 +21,11 @@ extern bool debuggerAutoload;
extern bool debuggerSaveLoadDEBFiles;
extern bool debuggerDisplayROMoffsets;
extern unsigned int debuggerPageSize;
extern unsigned int debuggerFontSize;
extern unsigned int hexeditorFontSize;
extern unsigned int hexeditorFontWidth;
extern unsigned int hexeditorFontHeight;
extern char* hexeditorFontName;
void CenterWindow(HWND hwndDlg);
void DoPatcher(int address,HWND hParent);

Some files were not shown because too many files have changed in this diff Show More