Bug fix for issue #217. The Qt hex editor memory reads are now synchronized with emulation thread execution. This ensures that calls to GetMem will not improperly interfere with certain memory mapped registers while the emulation thread is executing. Reading at an inappropriate time from controller registers mapped at addresses $4016 and $4017 can cause the emulator to miss button presses. Thread synchronization fixes this.
This commit is contained in:
parent
87b6368956
commit
e72cc4d0d5
|
@ -1427,9 +1427,9 @@ void ConsoleDebugger::reloadSymbolsCB(void)
|
|||
{
|
||||
fceuWrapperLock();
|
||||
debugSymbolTable.loadGameSymbols();
|
||||
fceuWrapperUnLock();
|
||||
|
||||
asmView->updateAssemblyView();
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
void ConsoleDebugger::debugRunCB(void)
|
||||
|
@ -2812,7 +2812,9 @@ void QAsmView::setDisplayROMoffsets( bool value )
|
|||
{
|
||||
displayROMoffsets = value;
|
||||
|
||||
fceuWrapperLock();
|
||||
updateAssemblyView();
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
|
@ -2822,7 +2824,9 @@ void QAsmView::setSymbolDebugEnable( bool value )
|
|||
{
|
||||
symbolicDebugEnable = value;
|
||||
|
||||
fceuWrapperLock();
|
||||
updateAssemblyView();
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
|
@ -2832,7 +2836,9 @@ void QAsmView::setRegisterNameEnable( bool value )
|
|||
{
|
||||
registerNameEnable = value;
|
||||
|
||||
fceuWrapperLock();
|
||||
updateAssemblyView();
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
|
|
|
@ -41,6 +41,7 @@
|
|||
#include "Qt/ConsoleUtilities.h"
|
||||
#include "Qt/ConsoleWindow.h"
|
||||
|
||||
static bool memNeedsCheck = false;
|
||||
static HexBookMarkManager_t hbm;
|
||||
static std::list <HexEditorDialog_t*> winList;
|
||||
static const char *memViewNames[] = { "RAM", "PPU", "OAM", "ROM", NULL };
|
||||
|
@ -724,7 +725,12 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
|||
|
||||
periodicTimer->start( 100 ); // 10hz
|
||||
|
||||
// Lock the mutex before adding a new window to the list,
|
||||
// we want to be sure that the emulator is not iterating the list
|
||||
// when we change it.
|
||||
fceuWrapperLock();
|
||||
winList.push_back(this);
|
||||
fceuWrapperUnLock();
|
||||
|
||||
populateBookmarkMenu();
|
||||
|
||||
|
@ -737,6 +743,11 @@ HexEditorDialog_t::~HexEditorDialog_t(void)
|
|||
printf("Hex Editor Deleted\n");
|
||||
periodicTimer->stop();
|
||||
|
||||
// Lock the emulation thread mutex to ensure
|
||||
// that the emulator is not attempting to update memory values
|
||||
// for window while we are destroying it or editing the window list.
|
||||
fceuWrapperLock();
|
||||
|
||||
for (it = winList.begin(); it != winList.end(); it++)
|
||||
{
|
||||
if ( (*it) == this )
|
||||
|
@ -746,6 +757,7 @@ HexEditorDialog_t::~HexEditorDialog_t(void)
|
|||
break;
|
||||
}
|
||||
}
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
void HexEditorDialog_t::setWindowTitle(void)
|
||||
|
@ -1103,7 +1115,18 @@ void HexEditorDialog_t::updatePeriodic(void)
|
|||
{
|
||||
//printf("Update Periodic\n");
|
||||
|
||||
editor->checkMemActivity();
|
||||
if ( fceuWrapperTryLock(0) )
|
||||
{
|
||||
memNeedsCheck = false;
|
||||
|
||||
editor->checkMemActivity();
|
||||
|
||||
fceuWrapperUnLock();
|
||||
}
|
||||
else
|
||||
{
|
||||
memNeedsCheck = true;
|
||||
}
|
||||
|
||||
editor->memModeUpdate();
|
||||
|
||||
|
@ -2009,6 +2032,9 @@ void QHexEdit::jumpToROM(void)
|
|||
setAddr( jumpToRomValue );
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
// Calling of checkMemActivity must always be synchronized with the emulation
|
||||
// thread as calling GetMem while the emulation is executing can mess up certain
|
||||
// registers (especially controller registers $4016 and $4017)
|
||||
int QHexEdit::checkMemActivity(void)
|
||||
{
|
||||
int c;
|
||||
|
@ -2442,3 +2468,20 @@ int hexEditorOpenFromDebugger( int mode, int addr )
|
|||
return 0;
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
// This function must be called from within the emulation thread
|
||||
void hexEditorUpdateMemoryValues(void)
|
||||
{
|
||||
std::list <HexEditorDialog_t*>::iterator it;
|
||||
|
||||
if ( !memNeedsCheck )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
for (it = winList.begin(); it != winList.end(); it++)
|
||||
{
|
||||
(*it)->editor->checkMemActivity();
|
||||
}
|
||||
memNeedsCheck = false;
|
||||
}
|
||||
//----------------------------------------------------------------------------
|
||||
|
|
|
@ -248,6 +248,7 @@ class HexEditorDialog_t : public QDialog
|
|||
};
|
||||
|
||||
int hexEditorNumWindows(void);
|
||||
void hexEditorUpdateMemoryValues(void);
|
||||
void hexEditorLoadBookmarks(void);
|
||||
void hexEditorSaveBookmarks(void);
|
||||
int hexEditorOpenFromDebugger( int mode, int addr );
|
||||
|
|
|
@ -1043,6 +1043,8 @@ int fceuWrapperUpdate( void )
|
|||
{
|
||||
DoFun(frameskip, periodic_saves);
|
||||
|
||||
hexEditorUpdateMemoryValues();
|
||||
|
||||
fceuWrapperUnLock();
|
||||
|
||||
emulatorHasMutux = 0;
|
||||
|
|
Loading…
Reference in New Issue