Overclocking. Implemented by adding extra scanlines to PPU loop. Disabled (optionally) while 7-bit samples are playing (as they can't be worked around otherwise).

This commit is contained in:
feos-tas 2015-06-16 19:52:49 +00:00
parent e71e32ceb7
commit 72f2d47f3a
16 changed files with 191 additions and 103 deletions

View File

@ -45,7 +45,7 @@ static void COOLBOYCW(uint32 A, uint8 V) {
}
static void COOLBOYPW(uint32 A, uint8 V) {
uint32 mask, shift;
uint32 mask;
uint32 base = ((EXPREGS[0] & 0x07) >> 0) | ((EXPREGS[1] & 0x10) >> 1) | ((EXPREGS[1] & 0x0C) << 2) | ((EXPREGS[0] & 0x30) << 2);
switch(EXPREGS[0] & 0xC0) {
case 0x00:

View File

@ -197,7 +197,7 @@ static void UNROM512LSync() {
}
else if (latche==0x10)
{
for(int i=0;i<(ROM_size*4);i++)
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% :)
}

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"
@ -184,6 +176,9 @@ static CFGSTRUCT fceuconfig[] =
AC(ntsccol),AC(ntsctint),AC(ntschue),
AC(force_grayscale),
AC(dendy),
AC(extrascanlines),
AC(overclocked),
AC(skip_7bit_overclocking),
NAC("palyo",pal_emulation),
NAC("genie",genie),

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

View File

@ -147,6 +147,12 @@ int genie = 0;
int pal_emulation = 0;
int pal_setting_specified = 0;
int dendy = 0;
// overclock the console by adding dummy scanlines to PPU loop
// disables DMC DMA and WaveHi filling for these dummies
// doesn't work with new PPU
bool overclocked = 0;
// 7-bit samples have priority over overclocking
bool skip_7bit_overclocking = 1;
bool swapDuty = 0; // some Famicom and NES clones had duty cycle bits swapped
int ntsccol = 0, ntsctint, ntschue;
std::string BaseDirectory;

View File

@ -57,6 +57,11 @@ extern int EnableBackgroundInput;
extern int AFon;
extern int AFoff;
extern int AutoFireOffset;
extern int normalscanlines;
extern int extrascanlines;
extern int totalscanlines;
extern bool overclocked;
extern bool skip_7bit_overclocking;
extern int vmod;

View File

@ -1,6 +1,5 @@
extern int PPUViewScanline;
extern int PPUViewer;
extern int scanline;
void DoPPUView();
void PPUViewDoBlit();

View File

@ -559,15 +559,19 @@ BEGIN
PUSHBUTTON "Enter",400,444,107,16,28
END
TIMINGCONFIG DIALOGEX 23, 157, 203, 60
TIMINGCONFIG DIALOGEX 23, 157, 203, 83
STYLE DS_SETFONT | DS_MODALFRAME | DS_3DLOOK | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU
CAPTION "Timing Configuration"
FONT 8, "MS Sans Serif", 0, 0, 0x0
BEGIN
DEFPUSHBUTTON "Close",1,137,38,56,14
DEFPUSHBUTTON "Close",1,137,61,56,14
CONTROL "Disable speed throttling used when sound is disabled.",CB_DISABLE_SPEED_THROTTLING,
"Button",BS_AUTOCHECKBOX | WS_TABSTOP,10,8,183,12
CONTROL "Set high-priority thread.",CB_SET_HIGH_PRIORITY,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,10,24,146,12
CONTROL "Set high-priority thread.",CB_SET_HIGH_PRIORITY,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,10,24,102,12
CONTROL "Overclocking (old PPU only).",CB_OVERCLOCKING,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,10,42,101,10
EDITTEXT IDC_EXTRA_SCANLINES,122,38,61,14,ES_AUTOHSCROLL
LTEXT "Extra scanlines:",IDC_STATIC,127,26,51,8
CONTROL "Don't overclock 7-bit samples.",CB_SKIP_7BIT,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,10,58,111,10
END
MOVIEOPTIONS DIALOGEX 65520, 76, 147, 222

View File

@ -577,6 +577,7 @@
#define IDC_SELECTION_MARKER_EDIT 1147
#define IDC_NOTE_TO_FIND 1147
#define IDC_AUTOSAVE_PERIOD 1147
#define IDC_EXTRA_SCANLINES 1147
#define IDC_BUTTON9 1148
#define TASEDITOR_FIND_NEXT_SIMILAR_MARKER 1148
#define IDC_SYMBOLIC_ADDRESS 1148
@ -636,6 +637,7 @@
#define IDC_MASK_UNUSED_GRAPHICS 1203
#define CHECK_SOUND_SWAPDUTY 1203
#define CHECK_PALETTE_MONOCHROME 1203
#define CB_OVERCLOCKING 1203
#define IDC_VOLUMEGROUP 1204
#define IDC_OMITBLANK 1204
#define IDC_CHECK3 1204
@ -762,6 +764,7 @@
#define CTL_PALHUE_TRACKBAR 1291
#define CHECK_PALETTE_HDTV 1292
#define STATIC_HUEVALUE 1293
#define CB_SKIP_7BIT 1294
#define MENU_NETWORK 40040
#define MENU_PALETTE 40041
#define MENU_SOUND 40042

View File

@ -3,6 +3,9 @@
#include "gui.h"
#include "resource.h"
char str[5];
extern int newppu;
/**
* This function is called when the dialog closes.
*
@ -28,7 +31,27 @@ void CloseTimingDialog(HWND hwndDlg)
eoptions &= ~EO_NOTHROTTLE;
}
EndDialog(hwndDlg, 0);
overclocked = (IsDlgButtonChecked(hwndDlg, CB_OVERCLOCKING) == BST_CHECKED);
skip_7bit_overclocking = (IsDlgButtonChecked(hwndDlg, CB_SKIP_7BIT) == BST_CHECKED);
GetDlgItemText(hwndDlg, IDC_EXTRA_SCANLINES, str, 4);
sscanf(str,"%d",&extrascanlines);
if (extrascanlines < 0)
{
extrascanlines = 0;
MessageBox(hwndDlg, "Overclocking is when you speed up your CPU, not slow it down!", "Error", MB_OK);
sprintf(str,"%d",extrascanlines);
SetDlgItemText(hwndDlg,IDC_EXTRA_SCANLINES,str);
}
else if (overclocked && newppu)
{
MessageBox(hwndDlg, "Overclocking doesn't work with new PPU!", "Error", MB_OK);
}
else
EndDialog(hwndDlg, 0);
totalscanlines = normalscanlines + (overclocked ? extrascanlines : 0);
}
/**
@ -51,6 +74,17 @@ BOOL CALLBACK TimingConCallB(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lPar
CheckDlgButton(hwndDlg, CB_DISABLE_SPEED_THROTTLING, BST_CHECKED);
}
if(overclocked)
CheckDlgButton(hwndDlg, CB_OVERCLOCKING, BST_CHECKED);
if(skip_7bit_overclocking)
CheckDlgButton(hwndDlg, CB_SKIP_7BIT, BST_CHECKED);
SendDlgItemMessage(hwndDlg,IDC_EXTRA_SCANLINES,EM_SETLIMITTEXT,3,0);
sprintf(str,"%d",extrascanlines);
SetDlgItemText(hwndDlg,IDC_EXTRA_SCANLINES,str);
CenterWindowOnScreen(hwndDlg);
break;

View File

@ -135,10 +135,12 @@ void FCEU_TogglePPU(void) {
if (newppu) {
FCEU_DispMessage("New PPU loaded", 0);
FCEUI_printf("New PPU loaded");
overclocked = 0;
} else {
FCEU_DispMessage("Old PPU loaded", 0);
FCEUI_printf("Old PPU loaded");
}
normalscanlines = (dendy ? 290 : 240)+newppu; // use flag as number!
#ifdef WIN32
SetMainWindowText();
#endif
@ -856,6 +858,11 @@ void FCEU_ResetVidSys(void) {
PAL = w ? 1 : 0;
if (newppu)
overclocked = 0;
normalscanlines = (dendy ? 290 : 240)+newppu; // use flag as number!
totalscanlines = normalscanlines + (overclocked ? extrascanlines : 0);
FCEUPPU_SetVideoSystem(w || dendy);
SetSoundVariables();
}
@ -921,18 +928,23 @@ int FCEUI_GetCurrentVidSystem(int *slstart, int *slend) {
void FCEUI_SetRegion(int region) {
switch (region) {
case 0: // NTSC
normalscanlines = 240;
pal_emulation = 0;
dendy = 0;
break;
case 1: // PAL
normalscanlines = 240;
pal_emulation = 1;
dendy = 0;
break;
case 2: // Dendy
normalscanlines = 290;
pal_emulation = 0;
dendy = 1;
break;
}
normalscanlines += newppu;
totalscanlines = normalscanlines + (overclocked ? extrascanlines : 0);
FCEUI_SetVidSystem(pal_emulation);
RefreshThrottleFPS();
#ifdef WIN32

View File

@ -19,45 +19,45 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "types.h"
#include "x6502.h"
#include "fceu.h"
#include "ppu.h"
#include "nsf.h"
#include "sound.h"
#include "file.h"
#include "utils/endian.h"
#include "utils/memory.h"
#include "types.h"
#include "x6502.h"
#include "fceu.h"
#include "ppu.h"
#include "nsf.h"
#include "sound.h"
#include "file.h"
#include "utils/endian.h"
#include "utils/memory.h"
#include "cart.h"
#include "palette.h"
#include "state.h"
#include "video.h"
#include "input.h"
#include "driver.h"
#include "debug.h"
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include "cart.h"
#include "palette.h"
#include "state.h"
#include "video.h"
#include "input.h"
#include "driver.h"
#include "debug.h"
#define VBlankON (PPU[0] & 0x80) //Generate VBlank NMI
#define Sprite16 (PPU[0] & 0x20) //Sprites 8x16/8x8
#define BGAdrHI (PPU[0] & 0x10) //BG pattern adr $0000/$1000
#define SpAdrHI (PPU[0] & 0x08) //Sprite pattern adr $0000/$1000
#define INC32 (PPU[0] & 0x04) //auto increment 1/32
#include <cstring>
#include <cstdio>
#include <cstdlib>
#define SpriteON (PPU[1] & 0x10) //Show Sprite
#define ScreenON (PPU[1] & 0x08) //Show screen
#define PPUON (PPU[1] & 0x18) //PPU should operate
#define GRAYSCALE (PPU[1] & 0x01) //Grayscale (AND palette entries with 0x30)
#define VBlankON (PPU[0] & 0x80) //Generate VBlank NMI
#define Sprite16 (PPU[0] & 0x20) //Sprites 8x16/8x8
#define BGAdrHI (PPU[0] & 0x10) //BG pattern adr $0000/$1000
#define SpAdrHI (PPU[0] & 0x08) //Sprite pattern adr $0000/$1000
#define INC32 (PPU[0] & 0x04) //auto increment 1/32
#define SpriteLeft8 (PPU[1] & 0x04)
#define BGLeft8 (PPU[1] & 0x02)
#define SpriteON (PPU[1] & 0x10) //Show Sprite
#define ScreenON (PPU[1] & 0x08) //Show screen
#define PPUON (PPU[1] & 0x18) //PPU should operate
#define GRAYSCALE (PPU[1] & 0x01) //Grayscale (AND palette entries with 0x30)
#define PPU_status (PPU[2])
#define SpriteLeft8 (PPU[1] & 0x04)
#define BGLeft8 (PPU[1] & 0x02)
#define PPU_status (PPU[2])
#define Pal (PALRAM)
#define Pal (PALRAM)
static void FetchSpriteData(void);
static void RefreshLine(int lastpixel);
@ -343,6 +343,9 @@ static int maxsprites = 8;
//scanline is equal to the current visible scanline we're on.
int scanline;
int normalscanlines;
int extrascanlines = 0;
int totalscanlines;
int g_rasterpos;
static uint32 scanlines_per_frame;
@ -1759,7 +1762,7 @@ int FCEUPPU_Loop(int skip) {
kook ^= 1;
}
if (GameInfo->type == GIT_NSF)
X6502_Run((256 + 85) * (dendy ? 290 : 240));
X6502_Run((256 + 85) * normalscanlines);
#ifdef FRAMESKIP
else if (skip) {
int y;
@ -1786,14 +1789,22 @@ int FCEUPPU_Loop(int skip) {
#endif
else {
int x, max, maxref;
deemp = PPU[1] >> 5;
for (scanline = 0; scanline < (dendy ? 290 : 240); ) { //scanline is incremented in DoLine. Evil. :/
// manual samples can't play correctly with overclocking
if (DMC_7bit && skip_7bit_overclocking)
totalscanlines = normalscanlines;
else
totalscanlines = normalscanlines + (overclocked ? extrascanlines : 0);
for (scanline = 0; scanline < totalscanlines; ) { //scanline is incremented in DoLine. Evil. :/
deempcnt[deemp]++;
if (scanline < 240)
if (scanline < normalscanlines)
DEBUG(FCEUD_UpdatePPUView(scanline, 1));
DoLine();
}
DMC_7bit = 0;
if (MMC5Hack) MMC5_hb(scanline);
for (x = 1, max = 0, maxref = 0; x < 7; x++) {
if (deempcnt[x] > max) {
@ -2032,7 +2043,8 @@ int FCEUX_PPU_Loop(int skip) {
//capture the initial xscroll
//int xscroll = ppur.fh;
//render 241/291 scanlines (1 dummy at beginning, dendy's 50 at the end)
for (int sl = 0; sl < (dendy ? 291 : 241); sl++) {
//ignore overclocking!
for (int sl = 0; sl < normalscanlines; sl++) {
spr_read.start_scanline();
g_rasterpos = 0;
@ -2318,6 +2330,8 @@ int FCEUX_PPU_Loop(int skip) {
runppu(1);
} //scanline loop
DMC_7bit = 0;
if (MMC5Hack) MMC5_hb(240);
//idle for one line

View File

@ -34,9 +34,11 @@ extern void (*FFCEUX_PPUWrite)(uint32 A, uint8 V);
extern uint8 FASTCALL FFCEUX_PPURead_Default(uint32 A);
void FFCEUX_PPUWrite_Default(uint32 A, uint8 V);
extern int scanline;
extern int g_rasterpos;
extern uint8 PPU[4];
extern bool overclocked;
extern bool skip_7bit_overclocking;
extern bool DMC_7bit;
enum PPUPHASE {
PPUPHASE_VBL, PPUPHASE_BG, PPUPHASE_OBJ

View File

@ -58,6 +58,7 @@ uint8 EnabledChannels=0; // $4015 / Sound channels enable and status
uint8 IRQFrameMode=0; // $4017 / Frame counter control / xx000000
uint8 InitialRawDALatch=0; // used only for lua
bool DMC_7bit = 0; // used to skip overclocking
ENVUNIT EnvUnits[3];
static const int RectDuties[4]={1,2,4,6};
@ -307,58 +308,69 @@ static DECLFW(Write_PSG)
static DECLFW(Write_DMCRegs)
{
A&=0xF;
switch(A)
{
case 0x00:DoPCM();
LoadDMCPeriod(V&0xF);
if(SIRQStat&0x80)
{
if(!(V&0x80))
{
X6502_IRQEnd(FCEU_IQDPCM);
SIRQStat&=~0x80;
}
else X6502_IRQBegin(FCEU_IQDPCM);
}
DMCFormat=V;
break;
case 0x01:DoPCM();
InitialRawDALatch=V&0x7F;
RawDALatch=InitialRawDALatch;
break;
case 0x02:DMCAddressLatch=V;break;
case 0x03:DMCSizeLatch=V;break;
}
A&=0xF;
switch(A)
{
case 0x00:
DoPCM();
LoadDMCPeriod(V&0xF);
if(SIRQStat&0x80)
{
if(!(V&0x80))
{
X6502_IRQEnd(FCEU_IQDPCM);
SIRQStat&=~0x80;
}
else X6502_IRQBegin(FCEU_IQDPCM);
}
DMCFormat=V;
break;
case 0x01:
DoPCM();
InitialRawDALatch=V&0x7F;
RawDALatch=InitialRawDALatch;
if (RawDALatch)
DMC_7bit = 1;
break;
case 0x02:
DMCAddressLatch=V;
if (V)
DMC_7bit = 0;
break;
case 0x03:
DMCSizeLatch=V;
if (V)
DMC_7bit = 0;
break;
}
}
static DECLFW(StatusWrite)
{
int x;
DoSQ1();
DoSQ2();
DoTriangle();
DoNoise();
DoPCM();
for(x=0;x<4;x++)
if(!(V&(1<<x))) lengthcount[x]=0; /* Force length counters to 0. */
DoSQ1();
DoSQ2();
DoTriangle();
DoNoise();
DoPCM();
if(V&0x10)
{
if(!DMCSize)
PrepDPCM();
}
for(x=0;x<4;x++)
if(!(V&(1<<x))) lengthcount[x]=0; /* Force length counters to 0. */
if(V&0x10)
{
if(!DMCSize)
PrepDPCM();
}
else
{
DMCSize=0;
DMCSize=0;
}
SIRQStat&=~0x80;
X6502_IRQEnd(FCEU_IQDPCM);
X6502_IRQEnd(FCEU_IQDPCM);
EnabledChannels=V&0x1F;
}
@ -548,7 +560,7 @@ static INLINE void DMCDMA(void)
void FCEU_SoundCPUHook(int cycles)
{
fhcnt-=cycles*48;
fhcnt-=cycles*48;
if(fhcnt<=0)
{
FrameSoundUpdate();

View File

@ -35,11 +35,11 @@ uint32 timestamp;
void (*MapIRQHook)(int a);
#define ADDCYC(x) \
{ \
{ \
int __x=x; \
_tcount+=__x; \
_count-=__x*48; \
timestamp+=__x; \
if (scanline < normalscanlines || scanline == totalscanlines) timestamp+=__x; \
}
//normal memory read
@ -493,7 +493,9 @@ extern int test; test++;
temp=_tcount;
_tcount=0;
if(MapIRQHook) MapIRQHook(temp);
FCEU_SoundCPUHook(temp);
if (scanline < normalscanlines || scanline == totalscanlines)
FCEU_SoundCPUHook(temp);
#ifdef _S9XLUA_H
CallRegisteredLuaMemHook(_PC, 1, 0, LUAMEMHOOK_EXEC);
#endif

View File

@ -47,8 +47,9 @@ void X6502_RunDebug(int32 cycles);
//------------
extern uint32 timestamp;
extern int scanline;
extern int normalscanlines;
extern int totalscanlines;
#define N_FLAG 0x80
#define V_FLAG 0x40