⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ppu.cpp

📁 著名SFC模拟器Snes9x的源代码。
💻 CPP
📖 第 1 页 / 共 5 页
字号:
    case 0x421e:    case 0x421f:	// Joypad values (read-only)	return;    case 0x4300:    case 0x4310:    case 0x4320:    case 0x4330:    case 0x4340:    case 0x4350:    case 0x4360:    case 0x4370:	d = (Address >> 4) & 0x7;	DMA[d].TransferDirection = (byte & 128) != 0 ? 1 : 0;	DMA[d].HDMAIndirectAddressing = (byte & 64) != 0 ? 1 : 0;	DMA[d].AAddressDecrement = (byte & 16) != 0 ? 1 : 0;	DMA[d].AAddressFixed = (byte & 8) != 0 ? 1 : 0;	DMA[d].TransferMode = (byte & 7);	break;    case 0x4301:    case 0x4311:    case 0x4321:    case 0x4331:    case 0x4341:    case 0x4351:    case 0x4361:    case 0x4371:	DMA[((Address >> 4) & 0x7)].BAddress = byte;	break;    case 0x4302:    case 0x4312:    case 0x4322:    case 0x4332:    case 0x4342:    case 0x4352:    case 0x4362:    case 0x4372:	d = (Address >> 4) & 0x7;	DMA[d].AAddress &= 0xFF00;	DMA[d].AAddress |= byte;	break;    case 0x4303:    case 0x4313:    case 0x4323:    case 0x4333:    case 0x4343:    case 0x4353:    case 0x4363:    case 0x4373:	d = (Address >> 4) & 0x7;	DMA[d].AAddress &= 0xFF;	DMA[d].AAddress |= byte << 8;	break;    case 0x4304:    case 0x4314:    case 0x4324:    case 0x4334:    case 0x4344:    case 0x4354:    case 0x4364:    case 0x4374:	DMA[((Address >> 4) & 0x7)].ABank = byte;	break;    case 0x4305:    case 0x4315:    case 0x4325:    case 0x4335:    case 0x4345:    case 0x4355:    case 0x4365:    case 0x4375:	d = (Address >> 4) & 0x7;	DMA[d].TransferBytes &= 0xFF00;	DMA[d].TransferBytes |= byte;	DMA[d].IndirectAddress &= 0xff00;	DMA[d].IndirectAddress |= byte;	break;    case 0x4306:    case 0x4316:    case 0x4326:    case 0x4336:    case 0x4346:    case 0x4356:    case 0x4366:    case 0x4376:	d = (Address >> 4) & 0x7;	DMA[d].TransferBytes &= 0xFF;	DMA[d].TransferBytes |= byte << 8;	DMA[d].IndirectAddress &= 0xff;	DMA[d].IndirectAddress |= byte << 8;	break;    case 0x4307:    case 0x4317:    case 0x4327:    case 0x4337:    case 0x4347:    case 0x4357:    case 0x4367:    case 0x4377:	DMA[d = ((Address >> 4) & 0x7)].IndirectBank = byte;	break;    case 0x4308:    case 0x4318:    case 0x4328:    case 0x4338:    case 0x4348:    case 0x4358:    case 0x4368:    case 0x4378:	d = (Address >> 4) & 7;	DMA[d].Address &= 0xff00;	DMA[d].Address |= byte;	break;    case 0x4309:    case 0x4319:    case 0x4329:    case 0x4339:    case 0x4349:    case 0x4359:    case 0x4369:    case 0x4379:	d = (Address >> 4) & 0x7;	DMA[d].Address &= 0xff;	DMA[d].Address |= byte << 8;	break;    case 0x430A:    case 0x431A:    case 0x432A:    case 0x433A:    case 0x434A:    case 0x435A:    case 0x436A:    case 0x437A:	d = (Address >> 4) & 0x7;	DMA[d].LineCount = byte & 0x7f;	DMA[d].Repeat = !(byte & 0x80);	break;    case 0x4800:    case 0x4801:    case 0x4802:    case 0x4803:	break;    case 0x4804:    case 0x4805:    case 0x4806:    case 0x4807:	S9xSetSDD1MemoryMap (Address - 0x4804, byte & 7);	break;    default:#ifdef DEBUGGER	missing.unknowncpu_write = Address;	if (Settings.TraceUnknownRegisters)	{	    sprintf (String, "Unknown register write: $%02X->$%04X\n",		     byte, Address);	    S9xMessage (S9X_TRACE, S9X_PPU_TRACE, String);	}#endif	break;    }    Memory.FillRAM [Address] = byte;}/**********************************************************************************************//* S9xGetCPU()                                                                                   *//* This function retrieves a CPU/DMA Register                                                 *//**********************************************************************************************/uint8 S9xGetCPU (uint16 Address){    uint8 byte;    if (Address < 0x4200)    {#ifdef VAR_CYCLES	CPU.Cycles += ONE_CYCLE;#endif	switch (Address)	{	// Secret of the Evermore	case 0x4000:	case 0x4001:	    return (0x40);	case 0x4016:	{	    if (Memory.FillRAM [0x4016] & 1)	    {		if ((!Settings.SwapJoypads &&		     IPPU.Controller == SNES_MOUSE_SWAPPED) ||		    (Settings.SwapJoypads &&		     IPPU.Controller == SNES_MOUSE))		{		    if (++PPU.MouseSpeed [0] > 2)			PPU.MouseSpeed [0] = 0;		}		return (0);	    }			    int ind = Settings.SwapJoypads ? 1 : 0;	    byte = IPPU.Joypads[ind] >> (PPU.Joypad1ButtonReadPos ^ 15);	    PPU.Joypad1ButtonReadPos++;	    return (byte & 1);	}	case 0x4017:        {	    if (Memory.FillRAM [0x4016] & 1)	    {		// MultiPlayer5 adaptor is only allowed to be plugged into port 2		switch (IPPU.Controller)		{		case SNES_MULTIPLAYER5:		    return (2);		case SNES_MOUSE_SWAPPED:		    if (Settings.SwapJoypads && ++PPU.MouseSpeed [0] > 2)			PPU.MouseSpeed [0] = 0;		    break;		    		case SNES_MOUSE:		    if (!Settings.SwapJoypads && ++PPU.MouseSpeed [0] > 2)			PPU.MouseSpeed [0] = 0;		    break;		}		return (0x00);	    }	    int ind = Settings.SwapJoypads ? 0 : 1;	    if (IPPU.Controller == SNES_MULTIPLAYER5)	    {		if (Memory.FillRAM [0x4201] & 0x80)		{		    byte = ((IPPU.Joypads[ind] >> (PPU.Joypad2ButtonReadPos ^ 15)) & 1) |			    (((IPPU.Joypads[2] >> (PPU.Joypad2ButtonReadPos ^ 15)) & 1) << 1);		    PPU.Joypad2ButtonReadPos++;		    return (byte);		}		else		{		    byte = ((IPPU.Joypads[3] >> (PPU.Joypad3ButtonReadPos ^ 15)) & 1) |			    (((IPPU.Joypads[4] >> (PPU.Joypad3ButtonReadPos ^ 15)) & 1) << 1);		    PPU.Joypad3ButtonReadPos++;		    return (byte);		}	    }	    return ((IPPU.Joypads[ind] >> (PPU.Joypad2ButtonReadPos++ ^ 15)) & 1);        }	default:#ifdef DEBUGGER	    missing.unknowncpu_read = Address;	    if (Settings.TraceUnknownRegisters)	    {		sprintf (String, "Unknown register read: $%04X\n", Address);		S9xMessage (S9X_TRACE, S9X_PPU_TRACE, String);	    }#endif	    break;	}	return (Memory.FillRAM [Address]);    }    else    switch (Address)    {	// BS Dynami Tracer! needs to be able to check if NMIs are enabled	// already, otherwise the game locks up.    case 0x4200:	// NMI, h & v timers and joypad reading enable    case 0x4201:	// I/O port (output - write only?)    case 0x4202:    case 0x4203:	// Multiplier and multiplicand (write)    case 0x4204:    case 0x4205:    case 0x4206:	// Divisor and dividend (write)	return (Memory.FillRAM[Address]);    case 0x4207:	return (uint8)(PPU.IRQHBeamPos);    case 0x4208:	return (PPU.IRQHBeamPos >> 8);    case 0x4209:	return (uint8)(PPU.IRQVBeamPos);    case 0x420a:	return (PPU.IRQVBeamPos >> 8);    case 0x420b:	// General purpose DMA enable	// Super Formation Soccer 95 della Serie A UCC Xaqua requires this	// register should not always return zero.	// .. But Aero 2 waits until this register goes zero..	// Just keep toggling the value for now in the hope that it breaks	// the game out of its wait loop...	Memory.FillRAM [0x420b] = !Memory.FillRAM [0x420b];	return (Memory.FillRAM [0x420b]);    case 0x420c:	// H-DMA enable	return (IPPU.HDMA);    case 0x420d:	// Cycle speed 0 - 2.68Mhz, 1 - 3.58Mhz (banks 0x80 +)	return (Memory.FillRAM[Address]);    case 0x420e:    case 0x420f:	// --->>> Unknown	return (Memory.FillRAM[Address]);    case 0x4210:#ifdef CPU_SHUTDOWN	CPU.WaitAddress = CPU.PCAtOpcodeStart;#endif		byte = Memory.FillRAM[0x4210];	Memory.FillRAM[0x4210] = 0;	return (byte);    case 0x4211:	byte = (CPU.IRQActive & (PPU_V_BEAM_IRQ_SOURCE | PPU_H_BEAM_IRQ_SOURCE)) ? 0x80 : 0;	// Super Robot Wars Ex ROM bug requires this.	byte |= CPU.Cycles >= Settings.HBlankStart ? 0x40 : 0;	CLEAR_IRQ_SOURCE (PPU_V_BEAM_IRQ_SOURCE | PPU_H_BEAM_IRQ_SOURCE);	return (byte);//    case 0x4200:    case 0x4212:	// V-blank, h-blank and joypads being read flags (read-only)#ifdef CPU_SHUTDOWN	CPU.WaitAddress = CPU.PCAtOpcodeStart;#endif	return (REGISTER_4212());    case 0x4213:	// I/O port input    case 0x4214:    case 0x4215:	// Quotient of divide result    case 0x4216:    case 0x4217:	// Multiplcation result (for multiply) or remainder of	// divison.	return (Memory.FillRAM[Address]);    case 0x4218:    case 0x4219:    case 0x421a:    case 0x421b:    case 0x421c:    case 0x421d:    case 0x421e:    case 0x421f:	// Joypads 1-4 button and direction state.	return (Memory.FillRAM [Address]);    case 0x4300:    case 0x4310:    case 0x4320:    case 0x4330:    case 0x4340:    case 0x4350:    case 0x4360:    case 0x4370:	// DMA direction, address type, fixed flag,	return (Memory.FillRAM[Address]);    case 0x4301:    case 0x4311:    case 0x4321:    case 0x4331:    case 0x4341:    case 0x4351:    case 0x4361:    case 0x4371:	return (Memory.FillRAM[Address]);    case 0x4302:    case 0x4312:    case 0x4322:    case 0x4332:    case 0x4342:    case 0x4352:    case 0x4362:    case 0x4372:	return (Memory.FillRAM[Address]);    case 0x4303:    case 0x4313:    case 0x4323:    case 0x4333:    case 0x4343:    case 0x4353:    case 0x4363:    case 0x4373:	return (Memory.FillRAM[Address]);    case 0x4304:    case 0x4314:    case 0x4324:    case 0x4334:    case 0x4344:    case 0x4354:    case 0x4364:    case 0x4374:	return (Memory.FillRAM[Address]);    case 0x4305:    case 0x4315:    case 0x4325:    case 0x4335:    case 0x4345:    case 0x4355:    case 0x4365:    case 0x4375:	return (Memory.FillRAM[Address]);    case 0x4306:    case 0x4316:    case 0x4326:    case 0x4336:    case 0x4346:    case 0x4356:    case 0x4366:    case 0x4376:	return (Memory.FillRAM[Address]);    case 0x4307:    case 0x4317:    case 0x4327:    case 0x4337:    case 0x4347:    case 0x4357:    case 0x4367:    case 0x4377:	return (DMA[(Address >> 4) & 7].IndirectBank);    case 0x4308:    case 0x4318:    case 0x4328:    case 0x4338:    case 0x4348:    case 0x4358:    case 0x4368:    case 0x4378:	return (Memory.FillRAM[Address]);    case 0x4309:    case 0x4319:    case 0x4329:    case 0x4339:    case 0x4349:    case 0x4359:    case 0x4369:    case 0x4379:	return (Memory.FillRAM[Address]);    case 0x430A:    case 0x431A:    case 0x432A:    case 0x433A:    case 0x434A:    case 0x435A:    case 0x436A:    case 0x437A:    {	int d = (Address & 0x70) >> 4;	if (IPPU.HDMA & (1 << d))	{	    return (DMA[d].LineCount);	}	return (Memory.FillRAM[Address]);    }    default:#ifdef DEBUGGER	missing.unknowncpu_read = Address;	if (Settings.TraceUnknownRegisters)	{	    sprintf (String, "Unknown register read: $%04X\n", Address);	    S9xMessage (S9X_TRACE, S9X_PPU_TRACE, String);	}	    #endif	break;    }    return (Memory.FillRAM[Address]);}void S9xResetPPU (){    PPU.BGMode = 0;    PPU.BG3Priority = 0;    PPU.Brightness = 0;    PPU.VMA.High = 0;    PPU.VMA.Increment = 1;    PPU.VMA.Address = 0;    PPU.VMA.FullGraphicCount = 0;    PPU.VMA.Shift = 0;    for (uint8 B = 0; B != 4; B++)    {	PPU.BG[B].SCBase = 0;	PPU.BG[B].VOffset = 0;	PPU.BG[B].HOffset = 0;	PPU.BG[B].BGSize = 0;	PPU.BG[B].NameBase = 0;	PPU.BG[B].SCSize = 0;	PPU.ClipCounts[B] = 0;	PPU.ClipWindowOverlapLogic [B] = CLIP_OR;	PPU.ClipWindow1Enable[B] = FALSE;	PPU.ClipWindow2Enable[B] = FALSE;	PPU.ClipWindow1Inside[B] = TRUE;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -