mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-07-22 22:00:39 -06:00
Interface and general: Fixed the hangings and crashes that would occur from repeated Start and Stop, added optional toolbar themes, made the fullscreen mode in the OpenGL plugin more user friendly for Windows users
git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@1770 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
@ -15,6 +15,10 @@
|
||||
// Official SVN repository and contact information can be found at
|
||||
// http://code.google.com/p/dolphin-emu/
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Include
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
#ifdef _WIN32
|
||||
#include <windows.h>
|
||||
#else
|
||||
@ -63,6 +67,8 @@
|
||||
#ifndef _WIN32
|
||||
#define WINAPI
|
||||
#endif
|
||||
////////////////////////////////////////
|
||||
|
||||
|
||||
// The idea behind the recent restructure is to fix various stupid problems.
|
||||
// glXMakeCurrent/ wglMakeCurrent takes a context and makes it current on the current thread.
|
||||
@ -71,7 +77,12 @@
|
||||
|
||||
namespace Core
|
||||
{
|
||||
// forwarding
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Declarations and definitions
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
|
||||
// Function forwarding
|
||||
//void Callback_VideoRequestWindowSize(int _iWidth, int _iHeight, BOOL _bFullscreen);
|
||||
void Callback_VideoLog(const TCHAR* _szMessage, int _bDoBreak);
|
||||
void Callback_VideoCopiedToXFB();
|
||||
@ -89,9 +100,9 @@ TPeekMessages Callback_PeekMessages = NULL;
|
||||
TUpdateFPSDisplay g_pUpdateFPSDisplay = NULL;
|
||||
|
||||
#ifdef _WIN32
|
||||
DWORD WINAPI EmuThread(void *pArg);
|
||||
DWORD WINAPI EmuThread(void *pArg);
|
||||
#else
|
||||
void *EmuThread(void *pArg);
|
||||
void *EmuThread(void *pArg);
|
||||
#endif
|
||||
void Stop();
|
||||
|
||||
@ -102,6 +113,7 @@ Common::Thread* g_pThread = NULL;
|
||||
SCoreStartupParameter g_CoreStartupParameter; //uck
|
||||
|
||||
Common::Event emuThreadGoing;
|
||||
//////////////////////////////////////
|
||||
|
||||
|
||||
bool PanicAlertToVideo(const char* text, bool yes_no)
|
||||
@ -184,19 +196,45 @@ void Stop() // - Hammertime!
|
||||
|
||||
// The quit is to get it out of its message loop
|
||||
// Should be moved inside the plugin.
|
||||
#ifdef _WIN32
|
||||
PostMessage((HWND)g_pWindowHandle, WM_QUIT, 0, 0);
|
||||
#else
|
||||
PluginVideo::Video_Stop();
|
||||
#endif
|
||||
#ifdef _WIN32
|
||||
PostMessage((HWND)g_pWindowHandle, WM_QUIT, 0, 0);
|
||||
#else
|
||||
PluginVideo::Video_Stop();
|
||||
#endif
|
||||
|
||||
delete g_pThread; //Wait for emuthread to close
|
||||
#ifdef _WIN32
|
||||
/* I have to use this to avoid the hangings, it seems harmless and it works so I'm
|
||||
okay with it */
|
||||
if (GetParent((HWND)g_pWindowHandle) == NULL)
|
||||
delete g_pThread; // Wait for emuthread to close
|
||||
#else
|
||||
delete g_pThread;
|
||||
#endif
|
||||
g_pThread = 0;
|
||||
Core::StopTrace();
|
||||
LogManager::Shutdown();
|
||||
Host_SetWaitCursor(false);
|
||||
}
|
||||
|
||||
void Callback_DebuggerBreak()
|
||||
{
|
||||
CCPU::EnableStepping(true);
|
||||
}
|
||||
|
||||
const SCoreStartupParameter& GetStartupParameter()
|
||||
{
|
||||
return g_CoreStartupParameter;
|
||||
}
|
||||
|
||||
void* GetWindowHandle()
|
||||
{
|
||||
return g_pWindowHandle;
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Create the CPU thread
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
THREAD_RETURN CpuThread(void *pArg)
|
||||
{
|
||||
Common::SetCurrentThreadName("CPU thread");
|
||||
@ -239,19 +277,21 @@ THREAD_RETURN CpuThread(void *pArg)
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
//////////////////////////////////////////
|
||||
|
||||
void Callback_DebuggerBreak()
|
||||
{
|
||||
CCPU::EnableStepping(true);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Initalize plugins and create emulation thread
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
/* Call browser: Init():g_pThread(). See the BootManager.cpp file description for a completel
|
||||
call schedule. */
|
||||
THREAD_RETURN EmuThread(void *pArg)
|
||||
{
|
||||
Common::SetCurrentThreadName("Emuthread - starting");
|
||||
const SCoreStartupParameter& _CoreParameter = *(SCoreStartupParameter*)pArg;
|
||||
|
||||
if (_CoreParameter.bLockThreads)
|
||||
Common::Thread::SetCurrentThreadAffinity(2); //Force to second core
|
||||
Common::Thread::SetCurrentThreadAffinity(2); // Force to second core
|
||||
|
||||
LOG(OSREPORT, "Starting core = %s mode", _CoreParameter.bWii ? "Wii" : "Gamecube");
|
||||
LOG(OSREPORT, "Dualcore = %s", _CoreParameter.bUseDualCore ? "Yes" : "No");
|
||||
@ -265,7 +305,8 @@ THREAD_RETURN EmuThread(void *pArg)
|
||||
VideoInitialize.pGetMemoryPointer = Memory::GetPointer;
|
||||
VideoInitialize.pSetPEToken = PixelEngine::SetToken;
|
||||
VideoInitialize.pSetPEFinish = PixelEngine::SetFinish;
|
||||
VideoInitialize.pWindowHandle = _CoreParameter.hMainWindow; // NULL; // filled by video_initialize
|
||||
// This is first the m_Panel handle, then it is updated to have the new window handle
|
||||
VideoInitialize.pWindowHandle = _CoreParameter.hMainWindow;
|
||||
VideoInitialize.pLog = Callback_VideoLog;
|
||||
VideoInitialize.pSysMessage = Host_SysMessage;
|
||||
VideoInitialize.pRequestWindowSize = NULL; //Callback_VideoRequestWindowSize;
|
||||
@ -278,7 +319,7 @@ THREAD_RETURN EmuThread(void *pArg)
|
||||
VideoInitialize.pMemoryBase = Memory::base;
|
||||
VideoInitialize.pKeyPress = Callback_KeyPress;
|
||||
VideoInitialize.bWii = _CoreParameter.bWii;
|
||||
PluginVideo::Video_Initialize(&VideoInitialize);
|
||||
PluginVideo::Video_Initialize(&VideoInitialize); // Call the dll
|
||||
|
||||
// Under linux, this is an X11 Display, not an HWND!
|
||||
g_pWindowHandle = (HWND)VideoInitialize.pWindowHandle;
|
||||
@ -339,30 +380,31 @@ THREAD_RETURN EmuThread(void *pArg)
|
||||
//In single core mode, the CPU thread does the graphics. In fact, the
|
||||
//CPU thread should in this case also create the emuwindow...
|
||||
|
||||
//Spawn the CPU thread
|
||||
// Spawn the CPU thread
|
||||
Common::Thread *cpuThread = NULL;
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// ENTER THE VIDEO THREAD LOOP
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
if (!Core::GetStartupParameter().bUseDualCore)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
cpuThread = new Common::Thread(CpuThread, pArg);
|
||||
//Common::SetCurrentThreadName("Idle thread");
|
||||
//TODO(ector) : investigate using GetMessage instead .. although
|
||||
//then we lose the powerdown check. ... unless powerdown sends a message :P
|
||||
while (PowerPC::state != PowerPC::CPU_POWERDOWN)
|
||||
{
|
||||
if (Callback_PeekMessages) {
|
||||
Callback_PeekMessages();
|
||||
#ifdef _WIN32
|
||||
cpuThread = new Common::Thread(CpuThread, pArg);
|
||||
//Common::SetCurrentThreadName("Idle thread");
|
||||
//TODO(ector) : investigate using GetMessage instead .. although
|
||||
//then we lose the powerdown check. ... unless powerdown sends a message :P
|
||||
while (PowerPC::state != PowerPC::CPU_POWERDOWN)
|
||||
{
|
||||
if (Callback_PeekMessages) {
|
||||
Callback_PeekMessages();
|
||||
}
|
||||
Common::SleepCurrentThread(20);
|
||||
}
|
||||
Common::SleepCurrentThread(20);
|
||||
}
|
||||
#else
|
||||
// In single-core mode, the Emulation main thread is also the CPU thread
|
||||
CpuThread(pArg);
|
||||
#endif
|
||||
#else
|
||||
// In single-core mode, the Emulation main thread is also the CPU thread
|
||||
CpuThread(pArg);
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -378,7 +420,8 @@ THREAD_RETURN EmuThread(void *pArg)
|
||||
if (g_pUpdateFPSDisplay != NULL)
|
||||
g_pUpdateFPSDisplay("Stopping...");
|
||||
|
||||
if (cpuThread) {
|
||||
if (cpuThread)
|
||||
{
|
||||
delete cpuThread; // This joins the cpu thread.
|
||||
// Returns after game exited
|
||||
cpuThread = NULL;
|
||||
@ -408,6 +451,10 @@ THREAD_RETURN EmuThread(void *pArg)
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Set or get the running state
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
bool SetState(EState _State)
|
||||
{
|
||||
switch(_State)
|
||||
@ -442,7 +489,12 @@ EState GetState()
|
||||
}
|
||||
return CORE_UNINITIALIZED;
|
||||
}
|
||||
///////////////////////////////////////
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Save or recreate the emulation state
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
void SaveState() {
|
||||
State_Save(0);
|
||||
}
|
||||
@ -450,11 +502,8 @@ void SaveState() {
|
||||
void LoadState() {
|
||||
State_Load(0);
|
||||
}
|
||||
///////////////////////////////////////
|
||||
|
||||
const SCoreStartupParameter& GetStartupParameter()
|
||||
{
|
||||
return g_CoreStartupParameter;
|
||||
}
|
||||
|
||||
bool MakeScreenshot(const std::string &filename)
|
||||
{
|
||||
@ -468,10 +517,6 @@ bool MakeScreenshot(const std::string &filename)
|
||||
return bResult;
|
||||
}
|
||||
|
||||
void* GetWindowHandle()
|
||||
{
|
||||
return g_pWindowHandle;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// --- Callbacks for plugins / engine ---
|
||||
|
@ -67,7 +67,8 @@ struct SCoreStartupParameter
|
||||
|
||||
bool bWii; bool bWiiLeds; bool bWiiSpeakers; // Wii settings
|
||||
|
||||
bool bConfirmStop; // Interface settings
|
||||
bool bConfirmStop, bHideCursor, bAutoHideCursor; // Interface settings
|
||||
int iTheme;
|
||||
|
||||
enum EBootBios
|
||||
{
|
||||
|
@ -76,8 +76,11 @@ CEXIIPL::CEXIIPL() :
|
||||
{
|
||||
/* This is a poor way to handle failure. We should either not display this message unless fonts
|
||||
are actually accessed, or better yet, emulate them using a system font. -bushing */
|
||||
|
||||
// PanicAlert("Error: failed to load font_ansi.bin.\nFonts in a few games may not work, or crash the game.");
|
||||
// JP: But I want to see this error
|
||||
#ifndef __APPLE__
|
||||
PanicAlert("Error: failed to load '" FONT_ANSI_FILE "'. Fonts in a few games may not work, or"
|
||||
" crash the game.");
|
||||
#endif
|
||||
}
|
||||
|
||||
pStream = fopen(FONT_SJIS_FILE, "rb");
|
||||
@ -93,7 +96,11 @@ CEXIIPL::CEXIIPL() :
|
||||
else
|
||||
{
|
||||
// Heh, BIOS fonts don't really work in JAP games anyway ... we get bogus characters.
|
||||
// PanicAlert("Error: failed to load font_sjis.bin.\nFonts in a few Japanese games may not work or crash the game.");
|
||||
// JP: But I want to see this error
|
||||
#ifndef __APPLE__
|
||||
PanicAlert("Error: failed to load '" FONT_SJIS_FILE "'. Fonts in a few Japanese games may"
|
||||
" not work or crash the game.");
|
||||
#endif
|
||||
}
|
||||
|
||||
memcpy(m_pIPL, iplver, sizeof(iplver));
|
||||
|
@ -102,10 +102,15 @@ CEXIMemoryCard::CEXIMemoryCard(const std::string& _rName, const std::string& _rF
|
||||
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Create new memory card
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
void CEXIMemoryCard::Flush(bool exiting)
|
||||
{
|
||||
FILE* pFile = NULL;
|
||||
pFile = fopen(m_strFilename.c_str(), "wb");
|
||||
|
||||
if (!pFile)
|
||||
{
|
||||
std::string dir;
|
||||
@ -114,18 +119,23 @@ void CEXIMemoryCard::Flush(bool exiting)
|
||||
File::CreateDir(dir.c_str());
|
||||
pFile = fopen(m_strFilename.c_str(), "wb");
|
||||
}
|
||||
if (!pFile) //Note - pFile changed inside above if
|
||||
|
||||
if (!pFile) // Note - pFile changed inside above if
|
||||
{
|
||||
PanicAlert("Could not write memory card file %s.\n\n"
|
||||
"Are you running Dolphin from a CD/DVD, or is the save file maybe write protected?", m_strFilename.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
fwrite(memory_card_content, memory_card_size, 1, pFile);
|
||||
fclose(pFile);
|
||||
if (!exiting) {
|
||||
|
||||
if (!exiting)
|
||||
{
|
||||
Core::DisplayMessage(StringFromFormat("Wrote memory card %i contents to %s.", card_index, m_strFilename.c_str()).c_str(), 4000);
|
||||
}
|
||||
}
|
||||
//////////////////////////////////////
|
||||
|
||||
|
||||
CEXIMemoryCard::~CEXIMemoryCard()
|
||||
|
@ -41,8 +41,11 @@ CWII_IPC_HLE_Device_di::CWII_IPC_HLE_Device_di(u32 _DeviceID, const std::string&
|
||||
|
||||
CWII_IPC_HLE_Device_di::~CWII_IPC_HLE_Device_di()
|
||||
{
|
||||
delete m_pFileSystem;
|
||||
delete m_pVolume;
|
||||
if(m_pFileSystem) { delete m_pFileSystem; m_pFileSystem = NULL; }
|
||||
/* This caused the crash in VolumeHandler.cpp, setting m_pVolume = NULL; didn't help
|
||||
it still makes VolumeHandler.cpp have a non-NULL pointer with no content so that
|
||||
delete crashes */
|
||||
//if(m_pVolume) { delete m_pVolume; m_pVolume = NULL; }
|
||||
}
|
||||
|
||||
bool CWII_IPC_HLE_Device_di::Open(u32 _CommandAddress, u32 _Mode)
|
||||
|
@ -191,14 +191,18 @@ void LogManager::Shutdown()
|
||||
{
|
||||
m_bInitialized = false;
|
||||
|
||||
// delete all loggers
|
||||
// Delete all loggers
|
||||
for (int i=0; i<LogTypes::NUMBER_OF_LOGS; i++)
|
||||
{
|
||||
if (m_Log[i] != NULL)
|
||||
for (int j = 0; j < VERBOSITY_LEVELS; j++)
|
||||
{
|
||||
m_Log[i]->Shutdown();
|
||||
delete m_Log[i];
|
||||
m_Log[i] = NULL;
|
||||
int id = i + j*100;
|
||||
if (m_Log[id] != NULL)
|
||||
{
|
||||
m_Log[id]->Shutdown();
|
||||
delete m_Log[id];
|
||||
m_Log[id] = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user