diff --git a/source/fceultra/boards/218.cpp b/source/fceultra/boards/218.cpp new file mode 100644 index 0000000..50b6021 --- /dev/null +++ b/source/fceultra/boards/218.cpp @@ -0,0 +1,38 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * Copyright notice for this file: + * Copyright (C) 2020 + * + * 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" +#include "../ines.h" + +static uint8 mirror; +static uint8 mask; + +static void M218Power(void) { + setchr8(0); + setprg32(0x8000, 0); + SetReadHandler(0x8000, 0xFFFF, CartBR); +} + +void Mapper218_Init(CartInfo* info) { + if (head.ROM_type & 0x08) + SetupCartMirroring(MI_0 + (head.ROM_type & 0x01), 1, NULL); + SetupCartCHRMapping(0, NTARAM, 2048, 1); + info->Power = M218Power; +} diff --git a/source/fceultra/boards/bs4xxxr.cpp b/source/fceultra/boards/bs4xxxr.cpp new file mode 100644 index 0000000..90f6d1a --- /dev/null +++ b/source/fceultra/boards/bs4xxxr.cpp @@ -0,0 +1,164 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * Copyright notice for this file: + * Copyright (C) 2020 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 + * + * Double Dragon 310000-in-1 (4040R) + * 700000-in-1 (BS-400R)(Unl) + */ + +#include "mapinc.h" +#include "mmc3.h" + +static uint8 pointer; +static uint8 offset; +static uint8 *WRAM = NULL; +static uint32 WRAMSIZE; + +static int getPRGBankBS4XXXR(int bank) +{ + if (((~bank) & 1) && (pointer & 0x40)) + bank ^= 2; + return (bank & 2) ? (0xFE | (bank & 1)) : EXPREGS[4 | (bank & 1)]; +} + +static void BS4XXXRPW(uint32 A, uint8 V) { + + if ((EXPREGS[3] >> 4) & 0x01) + { + int AND = ((EXPREGS[0] >> 1) & 1) ? 0x0F : 0x0F; + int OR = (EXPREGS[0] & 7) << 4; + int bank0 = getPRGBankBS4XXXR(0); + int bank1 = getPRGBankBS4XXXR(1); + if (!((EXPREGS[3] >> 1) & 1)) //16K Mode + { + setprg8(0x8000, ((bank0) & AND) | OR); + setprg8(0xA000, ((bank1) & AND) | OR); + setprg8(0xC000, ((bank0) & AND) | OR); + setprg8(0xE000, ((bank1) & AND) | OR); + } + else // 32K Mode + { + setprg8(0x8000, ((bank0) & AND) | OR); + setprg8(0xA000, ((bank1) & AND) | OR); + setprg8(0xC000, ((bank0 | 2) & AND) | OR); + setprg8(0xE000, ((bank1 | 2) & AND) | OR); + } + } + else // MMC3 Mode + { + int prgAND = ((EXPREGS[0] >> offset) & 1) ? 0x0F : 0x1F; + int prgOR = (EXPREGS[0] & 7) << 4; + setprg8(A, (V & prgAND) | (prgOR)); + } + setprg8r(0x10, 0x6000, 0); +} + +static void BS4XXXRCW(uint32 A, uint8 V) { + if ((EXPREGS[3] >> 4) & 1) + { + int AND = ((EXPREGS[0] >> 1) & 1) ? 0x0F : 0x0F; + int bank = EXPREGS[2] & AND; + int chrOR = ((EXPREGS[0] >> 3) & 7) << 4; + setchr8((bank) | (chrOR)); + } + else + { + int chrAND = ((EXPREGS[0] >> 1) & 1) ? 0xFF : 0xFF; + int chrOR = ((EXPREGS[0] >> 3) & 7) << 7; + setchr1(A, (V & chrAND) | (chrOR)); + } +} + +static DECLFW(BS4XXXRHiWrite) { +// FCEU_printf("w: %04x-%02x\n",A,V) + if (A==0x8000) + { + pointer = MMC3_cmd ^ V; + } + else if (A == 0x8001) + { + if((MMC3_cmd & 7) > 5) + EXPREGS[4|(MMC3_cmd & 1)] = V; + } + MMC3_CMDWrite(A, V); +} + +static DECLFW(BS4XXXRLoWrite) { +// FCEU_printf("w: %04x-%02x\n", A, V); + if (A & 0x800) + { + if (!(EXPREGS[3] & 0x80)) { + EXPREGS[A & 0x03] = V; + FixMMC3PRG(MMC3_cmd); + FixMMC3CHR(MMC3_cmd); + } + else if (EXPREGS[3] & 0x10) + { + EXPREGS[A & 0x03] = V; + FixMMC3PRG(MMC3_cmd); + FixMMC3CHR(MMC3_cmd); + } + else + WRAM[A - 0x6000] = V; + } + else + WRAM[A - 0x6000] = V; +} + + +static void BSXXXXRPower(void) { + EXPREGS[0] = EXPREGS[1] = EXPREGS[2] = EXPREGS[3] = EXPREGS[4] = EXPREGS[5] = 0; + GenMMC3Power(); + SetReadHandler(0x6000, 0x7FFF, CartBR); + SetWriteHandler(0x6000, 0x7FFF, BS4XXXRLoWrite); + SetWriteHandler(0x8000, 0x9FFF, BS4XXXRHiWrite); + FixMMC3PRG(MMC3_cmd); + FixMMC3CHR(MMC3_cmd); +} + +static void BS4XXXRClose(void) { + if (WRAM) + FCEU_gfree(WRAM); + WRAM = NULL; +} + +void BSXXXXR_Init(CartInfo *info) { + GenMMC3_Init(info, 512, 256, 8, 0); + cwrap = BS4XXXRCW; + pwrap = BS4XXXRPW; + + info->Power = BSXXXXRPower; + info->Close = BS4XXXRClose; + + WRAMSIZE = 8192; + WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE); + SetupCartPRGMapping(0x10, WRAM, WRAMSIZE, 1); + AddExState(WRAM, WRAMSIZE, 0, "WRAM"); + + AddExState(EXPREGS, 8, 0, "EXPR"); +} + +void BS400R_Init(CartInfo *info) { + offset = 1; + BSXXXXR_Init(info); +} + +void BS4040R_Init(CartInfo *info) { + offset = 6; + BSXXXXR_Init(info); +} diff --git a/source/fceultra/boards/copyfami_mmc3.cpp b/source/fceultra/boards/copyfami_mmc3.cpp deleted file mode 100644 index b123853..0000000 --- a/source/fceultra/boards/copyfami_mmc3.cpp +++ /dev/null @@ -1,148 +0,0 @@ -/* 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - - /* -0000 - 1FFF - RAM -2000 - 23FF - PPU -2400 - 27FF - Write: "PAG" / Read: -- -2800 - 2BFF - Write: "BNK" / Read: "STS" -2C00 - 2FFF - Write: "UWR" / Read: "URD" -3000 - 3FFF - Small Flash Page (в регистре BNK) -4000 - 7FFF - Free -8000 - FFFF - Cart/Big Flash Page (смотри регистр PAG) -Биты: -Регистр [PAG], по сбросу должен быть = $00. -D3-D0 - Big Page High Address (D3,D2,D1,D0,A14,A13,A12,A11,A10,A9,A8,A7,A6,A5,A4,A3,A2,A1,A0) - D4 - VMD бит. Если =0, то к PPU подключено внутренее ОЗу на 8Кб, если =1 - то картридж. - D5 - STR бит. Если =0, то вместо карта по адресам 8000-FFFF внутренняя флэш, =1 - карт. -Регистр [BNK], не предустанавливается -D6-D0 - Small Page High Address (D6,D5,D4,D3,D2,D1,D0,A11,A10,A9,A8,A7,A6,A5,A4,A3,A2,A1,A0) - D7 - S/W бит. Управляет USB мостом, в эмуле реализовывать не надо. -Регистры [UWR]/[URD], не предустанавливаются, в эмуле реализовывать не надо. -[UWR] - Регистр записи данных в USB мост. -[URD] - Регистр чтения из USB моста. - */ - -#include "mapinc.h" -#include "mmc3.h" - -static uint8 reg[3]; - -static uint8 *CHRRAM=NULL; // there is no more extern CHRRAM in mmc3.h - // I need chrram here and local static == local -static uint32 CHRRAMSIZE; - -static SFORMAT StateRegs[]= -{ - {reg, 3, "REGS"}, - {0} -}; - -static void Sync(void) -{ - setprg4r(1,0x3000,reg[1]&0x7F); - FixMMC3PRG(MMC3_cmd); - FixMMC3CHR(MMC3_cmd); -} - -static void MCopyFamiMMC3PW(uint32 A, uint8 V) -{ - if(reg[0]&0x20) - setprg8r(0,A,V); - else - setprg32r(1,0x8000,reg[0]&0x0F); -} - -static void MCopyFamiMMC3CW(uint32 A, uint8 V) -{ - if(reg[0]&0x20) - setchr1r(0,A,V); - else - setchr8r(0x10,0); -} - -static DECLFW(MCopyFamiMMC3WritePAG) -{ - reg[0]=V; - Sync(); -} - -static DECLFW(MCopyFamiMMC3WriteBNK) -{ - reg[1]=V; - Sync(); -} - -static DECLFW(MCopyFamiMMC3WriteUSB) -{ - reg[2]=V; -} - -static void MCopyFamiMMC3Power(void) -{ - reg[0] = 0; - GenMMC3Power(); - Sync(); - SetReadHandler(0x3000,0x3FFF,CartBR); - SetWriteHandler(0x3000,0x3FFF,CartBW); - - SetWriteHandler(0x2400,0x27FF,MCopyFamiMMC3WritePAG); - SetWriteHandler(0x2800,0x2BFF,MCopyFamiMMC3WriteBNK); - SetWriteHandler(0x2C00,0x2FFF,MCopyFamiMMC3WriteUSB); -} - -static void MCopyFamiMMC3Reset(void) -{ - reg[0] = 0; - MMC3RegReset(); - Sync(); -} - -static void MCopyFamiMMC3Close(void) -{ - if(CHRRAM) - FCEU_gfree(CHRRAM); - CHRRAM=NULL; -} - -static void StateRestore(int version) -{ - Sync(); -} - -void MapperCopyFamiMMC3_Init(CartInfo *info) -{ - GenMMC3_Init(info, 512, 512, 0, 0); - - cwrap=MCopyFamiMMC3CW; - pwrap=MCopyFamiMMC3PW; - - info->Reset=MCopyFamiMMC3Reset; - info->Power=MCopyFamiMMC3Power; - info->Close=MCopyFamiMMC3Close; - GameStateRestore=StateRestore; - - CHRRAMSIZE=8192; - CHRRAM=(uint8*)FCEU_gmalloc(CHRRAMSIZE); - SetupCartPRGMapping(0x10,CHRRAM,CHRRAMSIZE,1); - AddExState(CHRRAM, CHRRAMSIZE, 0, "SRAM"); - - AddExState(&StateRegs, ~0, 0, 0); -} diff --git a/source/fceultra/boards/fns.cpp b/source/fceultra/boards/fns.cpp new file mode 100644 index 0000000..08bbe24 --- /dev/null +++ b/source/fceultra/boards/fns.cpp @@ -0,0 +1,264 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * Copyright notice for this file: + * Copyright (C) 1998 BERO + * Copyright (C) 2002 Xodnizel + * Copyright (C) 2020 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 + * + * Famicom Network System Base Unit + MMC1 cartridge board + * + */ + +#include "mapinc.h" + +static uint8 DRegs[4]; +static uint8 Buffer, BufferShift; + +static uint32 WRAMSIZE; +static uint8 *WRAM = NULL; + +static int kanji_pos, kanji_page, r40C0; +static int IRQa, IRQCount; + +static DECLFW(MBWRAM) { + if (!(DRegs[3] & 0x10)) + Page[A >> 11][A] = V; +} + +static DECLFR(MAWRAM) { + if (DRegs[3] & 0x10) + return X.DB; + return(Page[A >> 11][A]); +} + +static void MMC1CHR(void) { + setchr8((r40C0 >> 3) & 1); +} + +static void MMC1PRG(void) { + uint8 offs_16banks = DRegs[1] & 0x10; + uint8 prg_reg = DRegs[3] & 0xF; + + setprg8r(0x10, 0x6000, DRegs[1] & 3); + + switch (DRegs[0] & 0xC) { + case 0xC: + setprg16(0x8000, (prg_reg + offs_16banks)); + setprg16(0xC000, 0xF + offs_16banks); + break; + case 0x8: + setprg16(0xC000, (prg_reg + offs_16banks)); + setprg16(0x8000, offs_16banks); + break; + case 0x0: + case 0x4: + setprg16(0x8000, ((prg_reg & ~1) + offs_16banks)); + setprg16(0xc000, ((prg_reg & ~1) + offs_16banks + 1)); + break; + } +} + +static void MMC1MIRROR(void) { + switch (DRegs[0] & 3) { + case 2: setmirror(MI_V); break; + case 3: setmirror(MI_H); break; + case 0: setmirror(MI_0); break; + case 1: setmirror(MI_1); break; + } +} + +static uint64 lreset; +static DECLFW(MMC1_write) { + int n = (A >> 13) - 4; + if ((timestampbase + timestamp) < (lreset + 2)) + return; + + if (V & 0x80) { + DRegs[0] |= 0xC; + BufferShift = Buffer = 0; + MMC1PRG(); + lreset = timestampbase + timestamp; + return; + } + + Buffer |= (V & 1) << (BufferShift++); + + if (BufferShift == 5) { + FCEU_printf("MMC1 REG%d:%02x (PC %04x)\n", n, Buffer, X.PC); + DRegs[n] = Buffer; + BufferShift = Buffer = 0; + switch (n) { + case 0: MMC1MIRROR(); + case 1: + case 2: + case 3: MMC1PRG(); break; + } + } +} + +static void MMC1_Restore(int version) { + MMC1MIRROR(); + MMC1CHR(); + MMC1PRG(); + lreset = 0; +} + +static void MMC1CMReset(void) { + int i; + + for (i = 0; i < 4; i++) + DRegs[i] = 0; + Buffer = BufferShift = 0; + DRegs[0] = 0x1F; + + DRegs[1] = 0; + DRegs[2] = 0; + DRegs[3] = 0; + + MMC1MIRROR(); + MMC1CHR(); + MMC1PRG(); +} + +static DECLFW(FNC_cmd_write) { + switch (A) { + case 0x40A6: { + IRQCount = (IRQCount & 0xFF00) | V; + break; + } + case 0x40A7: { + IRQCount = (IRQCount & 0x00FF) | (V << 8); + break; + } + case 0x40A8: { + IRQa = V; + break; + } + case 0x40B0: { + kanji_page = V & 1; + break; + } + case 0x40C0: { + FCEU_printf("FNS W %04x:%02x (PC %04x)\n", A, V, X.PC); + r40C0 = V; + MMC1CHR(); + break; + } + default: + FCEU_printf("FNS W %04x:%02x (PC %04x)\n", A, V, X.PC); + } +} + +static DECLFR(FNC_stat_read) { + switch (A) { + case 0x40A2: { + int ret = (IRQa >> 1); + X6502_IRQEnd(FCEU_IQEXT); + IRQa = 0; + return ret; + } + case 0x40AC: { // NMI/IRQ state reset (lookalike) + return 0; + } + case 0x40B0: { + kanji_pos = 0; + return 0; + } + case 0x40C0: { + FCEU_printf("FNS R %04x (PC %04x)\n", A, X.PC); + int ret = r40C0; + r40C0 &= 0; + return ret; + } + default: { + FCEU_printf("FNS R %04x (PC %04x)\n", A, X.PC); + return 0xff; + } + } +} + +static DECLFR(FNC_cart_i2c_read) { + FCEU_printf("I2C R %04x (PC %04x)\n", A, X.PC); + return 0; +} + + +static DECLFR(FNC_kanji_read) { + int32 ofs = ((A & 0xFFF) << 5) + kanji_pos; + kanji_pos++; + kanji_pos &= 0x1F; +// if (PRGptr[1] != NULL) // iNES debug + return PRGptr[1][ofs]; +// else +// return CHRptr[0][ofs]; +} + +void NFC_IRQ(int a) { + if (IRQa) { + IRQCount -= a; + if (IRQCount <= 0) + X6502_IRQBegin(FCEU_IQEXT); + } +} + +static void FNS_Power(void) { + lreset = 0; + SetWriteHandler(0x8000, 0xFFFF, MMC1_write); + SetReadHandler(0x8000, 0xFFFF, CartBR); + + kanji_page = 0; + kanji_pos = 0; + r40C0 = 0xC0; + + SetWriteHandler(0x4080, 0x40FF, FNC_cmd_write); + SetReadHandler(0x4080, 0x40FF, FNC_stat_read); + SetReadHandler(0x5000, 0x5FFF, FNC_kanji_read); + + SetReadHandler(0x6000, 0x6000, FNC_cart_i2c_read); + SetReadHandler(0x6001, 0x7FFF, CartBR); + SetWriteHandler(0x6000, 0x7FFF, CartBW); + + FCEU_CheatAddRAM(8, 0x6000, WRAM); + MMC1CMReset(); +} + +static void FNS_Close(void) { + if (WRAM) + FCEU_gfree(WRAM); + WRAM = NULL; +} + +void FNS_Init(CartInfo *info) { + info->Close = FNS_Close; + info->Power = FNS_Power; + + GameStateRestore = MMC1_Restore; + MapIRQHook = NFC_IRQ; + + WRAMSIZE = (8 + 32) * 1024; + WRAM = (uint8*)FCEU_gmalloc(WRAMSIZE); + SetupCartPRGMapping(0x10, WRAM, WRAMSIZE, 1); + AddExState(WRAM, WRAMSIZE, 0, "WRAM"); + + info->SaveGame[0] = WRAM; + info->SaveGameLen[0] = WRAMSIZE; + + AddExState(DRegs, 4, 0, "DREG"); + AddExState(&lreset, 8, 1, "LRST"); + AddExState(&Buffer, 1, 1, "BFFR"); + AddExState(&BufferShift, 1, 1, "BFRS"); +} diff --git a/source/fceultra/config.h b/source/fceultra/config.h deleted file mode 100644 index e69de29..0000000 diff --git a/source/fceultra/input/faminetsys.cpp b/source/fceultra/input/faminetsys.cpp new file mode 100644 index 0000000..dcca51c --- /dev/null +++ b/source/fceultra/input/faminetsys.cpp @@ -0,0 +1,59 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * Copyright notice for this file: + * Copyright (C) 2019 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 + * + * Family Network System controller + * + */ + +#include +#include "share.h" + +static int readbit; +static int32 readdata; + +static uint8 Read(int w, uint8 ret) +{ + if (!w) + { + if (readbit < 24) { + ret |= ((readdata >> readbit) & 1) << 1; + readbit++; + } else + ret |= 2; // sense! + } + return ret; +} + +static void Strobe(void) +{ + readbit = 0; +} + +static void Update(void *data, int arg) +{ + readdata = *(uint32*)data; +} + +static INPUTCFC FamiNetSys = { Read, 0, Strobe, Update, 0, 0 }; + +INPUTCFC *FCEU_InitFamiNetSys(void) +{ + return(&FamiNetSys); +} + diff --git a/source/fceultra/input/lcdcompzapper.cpp b/source/fceultra/input/lcdcompzapper.cpp new file mode 100644 index 0000000..e3b387c --- /dev/null +++ b/source/fceultra/input/lcdcompzapper.cpp @@ -0,0 +1,49 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * 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 "share.h" + +static uint32 lcdCompZapperStrobe[2]; +static uint32 lcdCompZapperData[2]; + +static uint8 ReadLCDCompZapper(int w) +{ + return lcdCompZapperData[w]; +} + +static void StrobeLCDCompZapper(int w) +{ + lcdCompZapperStrobe[w] = 0; +} + +void UpdateLCDCompZapper(int w, void* data, int arg) +{ + // In the '(*(uint32*)data)' variable, bit 0 holds the trigger value and bit 1 holds the light sense value. + // Ultimately this needs to be converted from 0000 00lt to 000t l000 where l is the light bit and t + // is the trigger bit. + // l must be inverted because 0: detected; 1: not detected + lcdCompZapperData[w] = ((((*(uint32*)data) & 1) << 4) | + (((*(uint32*)data) & 2 ^ 2) << 2)); +} + +static INPUTC LCDCompZapperCtrl = { ReadLCDCompZapper,0,StrobeLCDCompZapper,UpdateLCDCompZapper,0,0 }; + +INPUTC* FCEU_InitLCDCompZapper(int w) +{ + lcdCompZapperStrobe[w] = lcdCompZapperData[w] = 0; + return(&LCDCompZapperCtrl); +} diff --git a/source/fceultra/input/virtualboy.cpp b/source/fceultra/input/virtualboy.cpp new file mode 100644 index 0000000..0998da1 --- /dev/null +++ b/source/fceultra/input/virtualboy.cpp @@ -0,0 +1,58 @@ +/* FCE Ultra - NES/Famicom Emulator + * + * 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 "share.h" + +static uint32 vbrsb[2]; +static uint32 vbrdata[2]; + +static uint8 ReadVB(int w) +{ + uint8 ret=0; + ret |= (vbrdata[w]>>vbrsb[w])&1; + if(vbrsb[w] >= 16) + { + ret|=0x1; + vbrsb[w] = 16; + } + if(!fceuindbg) + vbrsb[w]++; + return ret; +} + +static void StrobeVB(int w) +{ + vbrsb[w]=0; +} + +void UpdateVB(int w, void *data, int arg) +{ + vbrdata[w]=0; + for (int x=0;x<14;x++) + { + vbrdata[w]|=(((*(uint32 *)data)>>x)&1)<