Better benchmark calculation:

1) Pure Video Hi Res and Text are the same thing
2) Realistic FPS was actually wrong as it would only CPU update the video for the first 10 frames

Signed-off-by: Andrea Odetti <mariofutire@gmail.com>
This commit is contained in:
Andrea Odetti 2019-11-29 20:19:23 +00:00
parent 19c9193412
commit ee09f828ee

View file

@ -1,14 +1,18 @@
#include "StdAfx.h"
#include "Video.h"
#include "Applewin.h"
#include "Memory.h"
#include "Common.h"
#include "Frame.h"
#include "NTSC.h"
#include "Disk.h"
#include "CPU.h"
#include "linux/benchmark.h"
#include <chrono>
void VideoBenchmark(std::function<void()> redraw, std::function<void()> refresh)
{
// PREPARE TWO DIFFERENT FRAME BUFFERS, EACH OF WHICH HAVE HALF OF THE
@ -22,29 +26,6 @@ void VideoBenchmark(std::function<void()> redraw, std::function<void()> refresh)
*(mem32+loop) = ((loop & 1) ^ ((loop & 0x40) >> 6)) ? 0xAAAAAAAA
: 0x14141414;
// SEE HOW MANY TEXT FRAMES PER SECOND WE CAN PRODUCE WITH NOTHING ELSE
// GOING ON, CHANGING HALF OF THE BYTES IN THE VIDEO BUFFER EACH FRAME TO
// SIMULATE THE ACTIVITY OF AN AVERAGE GAME
DWORD totaltextfps = 0;
g_uVideoMode = VF_TEXT;
FillMemory(mem+0x400,0x400,0x14);
redraw();
DWORD milliseconds = GetTickCount();
while (GetTickCount() == milliseconds) ;
milliseconds = GetTickCount();
DWORD cycle = 0;
do {
if (cycle & 1)
FillMemory(mem+0x400,0x400,0x14);
else
CopyMemory(mem+0x400,mem+((cycle & 2) ? 0x4000 : 0x6000),0x400);
refresh();
if (cycle++ >= 3)
cycle = 0;
totaltextfps++;
} while (GetTickCount() - milliseconds < 1000);
// SEE HOW MANY HIRES FRAMES PER SECOND WE CAN PRODUCE WITH NOTHING ELSE
// GOING ON, CHANGING HALF OF THE BYTES IN THE VIDEO BUFFER EACH FRAME TO
// SIMULATE THE ACTIVITY OF AN AVERAGE GAME
@ -52,34 +33,35 @@ void VideoBenchmark(std::function<void()> redraw, std::function<void()> refresh)
g_uVideoMode = VF_HIRES;
FillMemory(mem+0x2000,0x2000,0x14);
redraw();
milliseconds = GetTickCount();
while (GetTickCount() == milliseconds) ;
milliseconds = GetTickCount();
cycle = 0;
auto start = std::chrono::steady_clock::now();
long elapsed;
do {
if (cycle & 1)
if (totalhiresfps & 1)
FillMemory(mem+0x2000,0x2000,0x14);
else
CopyMemory(mem+0x2000,mem+((cycle & 2) ? 0x4000 : 0x6000),0x2000);
CopyMemory(mem+0x2000,mem+((totalhiresfps & 2) ? 0x4000 : 0x6000),0x2000);
refresh();
if (cycle++ >= 3)
cycle = 0;
totalhiresfps++;
} while (GetTickCount() - milliseconds < 1000);
const auto end = std::chrono::steady_clock::now();
elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count();
} while (elapsed < 1000);
// DETERMINE HOW MANY 65C02 CLOCK CYCLES WE CAN EMULATE PER SECOND WITH
// NOTHING ELSE GOING ON
DWORD totalmhz10[2] = {0,0}; // bVideoUpdate & !bVideoUpdate
for (UINT i=0; i<2; i++)
{
CpuSetupBenchmark();
milliseconds = GetTickCount();
while (GetTickCount() == milliseconds) ;
milliseconds = GetTickCount();
do {
CpuExecute(100000, i==0 ? true : false);
totalmhz10[i]++;
} while (GetTickCount() - milliseconds < 1000);
CpuSetupBenchmark();
start = std::chrono::steady_clock::now();
do {
CpuExecute(100000, i==0 ? true : false);
totalmhz10[i]++;
const auto end = std::chrono::steady_clock::now();
elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count();
} while (elapsed < 1000);
}
// IF THE PROGRAM COUNTER IS NOT IN THE EXPECTED RANGE AT THE END OF THE
@ -136,42 +118,45 @@ void VideoBenchmark(std::function<void()> redraw, std::function<void()> refresh)
DWORD realisticfps = 0;
FillMemory(mem+0x2000,0x2000,0xAA);
redraw();
milliseconds = GetTickCount();
while (GetTickCount() == milliseconds) ;
milliseconds = GetTickCount();
cycle = 0;
start = std::chrono::steady_clock::now();
const UINT dwClksPerFrame = NTSC_GetCyclesPerFrame();
const UINT cyclesPerMs = g_fCurrentCLK6502 / 1000;
int cyclesThisFrame = 0;
do {
if (realisticfps < 10) {
int cycles = 100000;
while (cycles > 0) {
DWORD executedcycles = CpuExecute(103, true);
cycles -= executedcycles;
sg_Disk2Card.UpdateDriveState(executedcycles);
// this is a simplified version of AppleWin.cpp:ContinueExecution()
const DWORD executedcycles = CpuExecute(cyclesPerMs, true);
cyclesThisFrame += executedcycles;
// every ms disk and joystick are updated
sg_Disk2Card.UpdateDriveState(executedcycles);
#if 0
JoyUpdateButtonLatch(executedcycles);
JoyUpdateButtonLatch(executedcycles);
#endif
}
if (cyclesThisFrame >= dwClksPerFrame)
{
cyclesThisFrame -= dwClksPerFrame;
if (realisticfps & 1)
FillMemory(mem+0x2000,0x2000,0xAA);
else
CopyMemory(mem+0x2000,mem+((realisticfps & 2) ? 0x4000 : 0x6000),0x2000);
realisticfps++;
refresh();
}
if (cycle & 1)
FillMemory(mem+0x2000,0x2000,0xAA);
else
CopyMemory(mem+0x2000,mem+((cycle & 2) ? 0x4000 : 0x6000),0x2000);
redraw();
if (cycle++ >= 3)
cycle = 0;
realisticfps++;
} while (GetTickCount() - milliseconds < 1000);
const auto end = std::chrono::steady_clock::now();
elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count();
} while (elapsed < 1000);
// DISPLAY THE RESULTS
TCHAR outstr[256];
wsprintf(outstr,
TEXT("Pure Video FPS:\t%u hires, %u text\n")
TEXT("Pure Video FPS:\t%u\n")
TEXT("Pure CPU MHz:\t%u.%u%s (video update)\n")
TEXT("Pure CPU MHz:\t%u.%u%s (full-speed)\n\n")
TEXT("EXPECTED AVERAGE VIDEO GAME\n")
TEXT("PERFORMANCE: %u FPS"),
(unsigned)totalhiresfps,
(unsigned)totaltextfps,
(unsigned)(totalmhz10[0] / 10), (unsigned)(totalmhz10[0] % 10), (LPCTSTR)(IS_APPLE2 ? TEXT(" (6502)") : TEXT("")),
(unsigned)(totalmhz10[1] / 10), (unsigned)(totalmhz10[1] % 10), (LPCTSTR)(IS_APPLE2 ? TEXT(" (6502)") : TEXT("")),
(unsigned)realisticfps);