diff --git a/Source/Common/Common.vcxproj b/Source/Common/Common.vcxproj
index 4ce014430..e8ba6cbe8 100644
--- a/Source/Common/Common.vcxproj
+++ b/Source/Common/Common.vcxproj
@@ -43,6 +43,7 @@
+
Create
@@ -64,6 +65,7 @@
+
diff --git a/Source/Common/Common.vcxproj.filters b/Source/Common/Common.vcxproj.filters
index 437d0328f..69caab164 100644
--- a/Source/Common/Common.vcxproj.filters
+++ b/Source/Common/Common.vcxproj.filters
@@ -62,6 +62,9 @@
Source Files
+
+ Source Files
+
@@ -124,5 +127,8 @@
Header Files
+
+ Header Files
+
\ No newline at end of file
diff --git a/Source/Common/Random.cpp b/Source/Common/Random.cpp
new file mode 100644
index 000000000..54bc07126
--- /dev/null
+++ b/Source/Common/Random.cpp
@@ -0,0 +1,54 @@
+/****************************************************************************
+* *
+* Project64 - A Nintendo 64 emulator. *
+* http://www.pj64-emu.com/ *
+* Copyright (C) 2017 Project64. All rights reserved. *
+* *
+* License: *
+* GNU/GPLv2 http://www.gnu.org/licenses/gpl-2.0.html *
+* *
+****************************************************************************/
+/*
+ * Implements the CRandom class.
+ *
+ * This class implements the Lehmer Random Number Generator.
+ *
+ */
+
+#include "stdafx.h"
+#include "Random.h"
+#include
+
+CRandom::CRandom()
+{
+ m_state = (uint32_t)time(NULL);
+}
+
+CRandom::CRandom(uint32_t state_value)
+{
+ m_state = state_value;
+}
+
+uint32_t CRandom::randomizer(uint32_t val)
+{
+ return ((uint64_t)val * 279470273UL) % 4294967291UL;
+}
+
+uint32_t CRandom::next()
+{
+ m_state = randomizer(m_state);
+ return m_state;
+}
+
+void CRandom::set_state(uint32_t state_value)
+{
+ if (state_value == 0)
+ m_state = 1;
+ else
+ m_state = state_value;
+}
+
+uint32_t CRandom::get_state()
+{
+ return m_state;
+}
diff --git a/Source/Common/Random.h b/Source/Common/Random.h
new file mode 100644
index 000000000..aeb33536a
--- /dev/null
+++ b/Source/Common/Random.h
@@ -0,0 +1,32 @@
+/****************************************************************************
+* *
+* Project64 - A Nintendo 64 emulator. *
+* http://www.pj64-emu.com/ *
+* Copyright (C) 2017 Project64. All rights reserved. *
+* *
+* License: *
+* GNU/GPLv2 http://www.gnu.org/licenses/gpl-2.0.html *
+* *
+****************************************************************************/
+/*
+ * Defines the CRandom class.
+ *
+ * This class implements the Lehmer Random Number Generator.
+ *
+ */
+#pragma once
+#include
+
+class CRandom
+{
+public:
+ CRandom();
+ CRandom(uint32_t seed_value);
+ uint32_t next();
+ uint32_t get_state();
+ void set_state(uint32_t state_value);
+
+protected:
+ uint32_t randomizer(uint32_t val);
+ uint32_t m_state;
+};
diff --git a/Source/Project64-core/N64System/Mips/Dma.cpp b/Source/Project64-core/N64System/Mips/Dma.cpp
index abfa03ab3..b5eb0ad54 100644
--- a/Source/Project64-core/N64System/Mips/Dma.cpp
+++ b/Source/Project64-core/N64System/Mips/Dma.cpp
@@ -458,9 +458,11 @@ void CDMA::PI_DMA_WRITE()
{
g_Recompiler->ClearRecompCode_Phys(g_Reg->PI_DRAM_ADDR_REG, g_Reg->PI_WR_LEN_REG, CRecompiler::Remove_DMA);
}
- g_Reg->PI_STATUS_REG &= ~PI_STATUS_DMA_BUSY;
- g_Reg->MI_INTR_REG |= MI_INTR_PI;
- g_Reg->CheckInterrupts();
+ g_SystemTimer->SetTimer(g_SystemTimer->PiTimer, PI_WR_LEN_REG/8 + (g_Random->next() % 0x40), false);
+
+ //g_Reg->PI_STATUS_REG &= ~PI_STATUS_DMA_BUSY;
+ //g_Reg->MI_INTR_REG |= MI_INTR_PI;
+ //g_Reg->CheckInterrupts();
//ChangeTimer(PiTimer,(int32_t)(PI_WR_LEN_REG * 8.9) + 50);
//ChangeTimer(PiTimer,(int32_t)(PI_WR_LEN_REG * 8.9));
return;
diff --git a/Source/Project64-core/N64System/Mips/PifRam.cpp b/Source/Project64-core/N64System/Mips/PifRam.cpp
index 8b4ba49d7..9583070f4 100644
--- a/Source/Project64-core/N64System/Mips/PifRam.cpp
+++ b/Source/Project64-core/N64System/Mips/PifRam.cpp
@@ -358,13 +358,14 @@ void CPifRam::SI_DMA_READ()
if (g_System->bDelaySI())
{
- g_SystemTimer->SetTimer(CSystemTimer::SiTimer, 0x900, false);
+ g_SystemTimer->SetTimer(CSystemTimer::SiTimer, 0x900 + (g_Random->next() % 0x40), false);
}
else
{
- g_Reg->MI_INTR_REG |= MI_INTR_SI;
- g_Reg->SI_STATUS_REG |= SI_STATUS_INTERRUPT;
- g_Reg->CheckInterrupts();
+ g_SystemTimer->SetTimer(CSystemTimer::SiTimer, g_Random->next() % 0x40, false);
+ //g_Reg->MI_INTR_REG |= MI_INTR_SI;
+ //g_Reg->SI_STATUS_REG |= SI_STATUS_INTERRUPT;
+ //g_Reg->CheckInterrupts();
}
}
diff --git a/Source/Project64-core/N64System/N64Class.cpp b/Source/Project64-core/N64System/N64Class.cpp
index 2f56f5221..d3190edfc 100644
--- a/Source/Project64-core/N64System/N64Class.cpp
+++ b/Source/Project64-core/N64System/N64Class.cpp
@@ -30,7 +30,7 @@
#pragma warning(disable:4355) // Disable 'this' : used in base member initializer list
-CN64System::CN64System(CPlugins * Plugins, bool SavesReadOnly, bool SyncSystem) :
+CN64System::CN64System(CPlugins * Plugins, uint32_t randomizer_seed, bool SavesReadOnly, bool SyncSystem) :
CSystemEvents(this, Plugins),
m_EndEmulation(false),
m_SaveUsing((SAVE_CHIP_TYPE)g_Settings->LoadDword(Game_SaveChip)),
@@ -57,7 +57,8 @@ CN64System::CN64System(CPlugins * Plugins, bool SavesReadOnly, bool SyncSystem)
m_thread(NULL),
m_hPauseEvent(true),
m_CheatsSlectionChanged(false),
- m_SyncCpu(SyncSystem)
+ m_SyncCpu(SyncSystem),
+ m_Random(randomizer_seed)
{
WriteTrace(TraceN64System, TraceDebug, "Start");
memset(m_LastSuccessSyncPC, 0, sizeof(m_LastSuccessSyncPC));
@@ -110,7 +111,7 @@ CN64System::CN64System(CPlugins * Plugins, bool SavesReadOnly, bool SyncSystem)
g_Plugins->CopyPlugins(g_Settings->LoadStringVal(Directory_PluginSync));
m_SyncPlugins = new CPlugins(Directory_PluginSync, true);
m_SyncPlugins->SetRenderWindows(g_Plugins->SyncWindow(), NULL);
- m_SyncCPU = new CN64System(m_SyncPlugins, true, true);
+ m_SyncCPU = new CN64System(m_SyncPlugins, randomizer_seed, true, true);
}
Reset(true, true);
@@ -359,7 +360,7 @@ bool CN64System::RunFileImage(const char * FileLoc)
void CN64System::RunLoadedImage(void)
{
WriteTrace(TraceN64System, TraceDebug, "Start");
- g_BaseSystem = new CN64System(g_Plugins, false, false);
+ g_BaseSystem = new CN64System(g_Plugins, (uint32_t)time(NULL), false, false);
if (g_BaseSystem)
{
g_BaseSystem->StartEmulation(true);
@@ -716,6 +717,7 @@ void CN64System::Reset(bool bInitReg, bool ClearMenory)
m_SyncCPU->Reset(bInitReg, ClearMenory);
}
g_Settings->SaveBool(GameRunning_InReset, true);
+
WriteTrace(TraceN64System, TraceDebug, "Done");
}
@@ -763,6 +765,7 @@ bool CN64System::SetActiveSystem(bool bActive)
R4300iOp::m_TestTimer = m_TestTimer;
R4300iOp::m_NextInstruction = m_NextInstruction;
R4300iOp::m_JumpToLocation = m_JumpToLocation;
+ g_Random = &m_Random;
}
else
{
@@ -782,6 +785,7 @@ bool CN64System::SetActiveSystem(bool bActive)
g_Plugins = m_Plugins;
g_TLBLoadAddress = NULL;
g_TLBStoreAddress = NULL;
+ g_Random = NULL;
}
}
diff --git a/Source/Project64-core/N64System/N64Class.h b/Source/Project64-core/N64System/N64Class.h
index 63d04d1b7..909cc0732 100644
--- a/Source/Project64-core/N64System/N64Class.h
+++ b/Source/Project64-core/N64System/N64Class.h
@@ -10,6 +10,7 @@
****************************************************************************/
#pragma once
+#include
#include
#include
#include
@@ -48,7 +49,7 @@ class CN64System :
protected CDebugSettings
{
public:
- CN64System(CPlugins * Plugins, bool SavesReadOnly, bool SyncSystem);
+ CN64System(CPlugins * Plugins, uint32_t randomizer_seed, bool SavesReadOnly, bool SyncSystem);
virtual ~CN64System(void);
CCheats m_Cheats;
@@ -164,6 +165,7 @@ private:
uint32_t m_SyncCount;
bool m_SyncCpu;
bool m_CheatsSlectionChanged;
+ CRandom m_Random;
//When Syncing cores this is the PC where it last Sync'ed correctly
uint32_t m_LastSuccessSyncPC[10];
diff --git a/Source/Project64-core/N64System/SystemGlobals.cpp b/Source/Project64-core/N64System/SystemGlobals.cpp
index d6e058b1c..84552337b 100644
--- a/Source/Project64-core/N64System/SystemGlobals.cpp
+++ b/Source/Project64-core/N64System/SystemGlobals.cpp
@@ -32,5 +32,6 @@ uint32_t * g_TLBStoreAddress = NULL;
CDebugger * g_Debugger = NULL;
uint8_t ** g_RecompPos = NULL;
CMempak * g_Mempak = NULL;
+CRandom * g_Random = NULL;
int * g_NextTimer;
\ No newline at end of file
diff --git a/Source/Project64-core/N64System/SystemGlobals.h b/Source/Project64-core/N64System/SystemGlobals.h
index 3ebbff683..b1bfd0521 100644
--- a/Source/Project64-core/N64System/SystemGlobals.h
+++ b/Source/Project64-core/N64System/SystemGlobals.h
@@ -62,4 +62,7 @@ extern CDebugger * g_Debugger;
extern uint8_t ** g_RecompPos;
class CMempak;
-extern CMempak * g_Mempak;
\ No newline at end of file
+extern CMempak * g_Mempak;
+
+class CRandom;
+extern CRandom * g_Random;