clean up memory card logic:

- Don't do the OS mount for cards during the attract screens.  Only do OS mounts in the time between BeginGame and PlayersFinalized.
 - Remove logic for fast load of a Profile from the MemoryCard.  Instead, load the whole profile all at once on PlayersFinalized.
This commit is contained in:
Chris Danford
2004-08-09 05:01:24 +00:00
parent 404ed69faf
commit e435165014
15 changed files with 144 additions and 138 deletions
+4 -2
View File
@@ -95,6 +95,7 @@ void GameState::Reset()
{
EndGame();
MEMCARDMAN->LockCards( true );
ASSERT( THEME );
@@ -191,7 +192,6 @@ void GameState::Reset()
m_iCpuSkill[p] = 5;
}
MEMCARDMAN->LockCards( false );
LIGHTSMAN->SetLightsMode( LIGHTSMODE_ATTRACT );
@@ -218,6 +218,8 @@ void GameState::BeginGame()
// play attract on the ending screen, then in one more whole attract
// sequence after the game is over (even if attract sounds are set to off)
m_iNumTimesThroughAttract = -2;
MEMCARDMAN->LockCards( false );
}
void CheckStageStats( const StageStats &ss, int p )
@@ -247,7 +249,7 @@ void GameState::PlayersFinalized()
// apply saved default modifiers if any
FOREACH_HumanPlayer( pn )
{
PROFILEMAN->LoadFirstAvailableProfile( pn, false ); // load full profile
PROFILEMAN->LoadFirstAvailableProfile( pn ); // load full profile
if( !PROFILEMAN->IsUsingProfile(pn) )
continue; // skip
+16 -18
View File
@@ -29,7 +29,7 @@ MemoryCardManager::MemoryCardManager()
m_soundTooLate.Load( THEME->GetPathToS("MemoryCardManager too late") );
m_soundDisconnect.Load( THEME->GetPathToS("MemoryCardManager disconnect") );
AssignUnassignedCards();
UpdateUnassignedCards();
}
MemoryCardManager::~MemoryCardManager()
@@ -94,18 +94,8 @@ void MemoryCardManager::Update( float fDelta )
}
}
AssignUnassignedCards();
UpdateUnassignedCards();
// Load profiles from cards that were just connected.
if( !m_bCardsLocked )
{
FOREACH_PlayerNumber( pn )
{
bool bPlayersCardWasJustConnected = find(vConnects.begin(),vConnects.end(),m_Device[pn]) != vConnects.end();
if( bPlayersCardWasJustConnected )
PROFILEMAN->LoadFirstAvailableProfile( pn, true ); // fast load
}
}
SCREENMAN->RefreshCreditsMessages();
}
}
@@ -150,14 +140,14 @@ void MemoryCardManager::LockCards( bool bLock )
}
if( m_bCardsLocked )
m_pDriver->DontDoOsMount();
m_pDriver->SetMountThreadState( MemoryCardDriver::detect_and_dont_mount );
else
m_pDriver->DoOsMount();
m_pDriver->SetMountThreadState( MemoryCardDriver::detect_and_mount );
}
void MemoryCardManager::AssignUnassignedCards()
void MemoryCardManager::UpdateUnassignedCards()
{
LOG->Trace( "AssignUnassignedCards" );
LOG->Trace( "UpdateUnassignedCards" );
// make a list of unassigned
vector<UsbStorageDevice> vUnassignedDevices = m_vStorageDevices; // copy
@@ -171,7 +161,12 @@ void MemoryCardManager::AssignUnassignedCards()
vector<UsbStorageDevice>::iterator it = find(vUnassignedDevices.begin(),vUnassignedDevices.end(),m_Device[p]);
if( it != vUnassignedDevices.end() )
{
// TRICKY:
m_Device[p] = *it;
vUnassignedDevices.erase( it );
}
}
}
@@ -289,12 +284,15 @@ CString MemoryCardManager::GetName( PlayerNumber pn ) const
void MemoryCardManager::PauseMountingThread()
{
m_pDriver->PauseMountingThread();
m_pDriver->SetMountThreadState( MemoryCardDriver::paused );
}
void MemoryCardManager::UnPauseMountingThread()
{
m_pDriver->UnPauseMountingThread();
m_pDriver->SetMountThreadState(
m_bCardsLocked ?
MemoryCardDriver::detect_and_dont_mount :
MemoryCardDriver::detect_and_mount );
}
bool IsAnyPlayerUsingMemoryCard()
+1 -1
View File
@@ -38,7 +38,7 @@ public:
CString GetName( PlayerNumber pn ) const;
protected:
void AssignUnassignedCards(); // do our best to assign a Device to each player
void UpdateUnassignedCards(); // do our best to assign a Device to each player
MemoryCardDriver *m_pDriver;
+22 -40
View File
@@ -66,9 +66,9 @@ void ProfileManager::GetLocalProfileNames( vector<CString> &asNamesOut ) const
}
bool ProfileManager::LoadProfile( PlayerNumber pn, CString sProfileDir, bool bIsMemCard, bool bLoadNamesOnly )
bool ProfileManager::LoadProfile( PlayerNumber pn, CString sProfileDir, bool bIsMemCard )
{
LOG->Trace( "LoadingProfile P%d, %s, %d, %d", pn+1, sProfileDir.c_str(), bIsMemCard, bLoadNamesOnly );
LOG->Trace( "LoadingProfile P%d, %s, %d, %d", pn+1, sProfileDir.c_str(), bIsMemCard );
ASSERT( !sProfileDir.empty() );
ASSERT( sProfileDir.Right(1) == "/" );
@@ -79,10 +79,7 @@ bool ProfileManager::LoadProfile( PlayerNumber pn, CString sProfileDir, bool bIs
m_sProfileDir[pn] = sProfileDir;
m_bWasLoadedFromMemoryCard[pn] = bIsMemCard;
if( bLoadNamesOnly )
m_Profile[pn].LoadEditableDataFromDir( m_sProfileDir[pn] );
else
m_Profile[pn].LoadAllFromDir( m_sProfileDir[pn], PREFSMAN->m_bSignProfileData );
m_Profile[pn].LoadAllFromDir( m_sProfileDir[pn], PREFSMAN->m_bSignProfileData );
if( bIsMemCard )
MEMCARDMAN->UnPauseMountingThread();
@@ -106,7 +103,7 @@ bool ProfileManager::CreateProfile( CString sProfileDir, CString sName )
return true;
}
bool ProfileManager::LoadDefaultProfileFromMachine( PlayerNumber pn, bool bLoadNamesOnly )
bool ProfileManager::LoadLocalProfileFromMachine( PlayerNumber pn )
{
CString sProfileID = PREFSMAN->m_sDefaultLocalProfileID[pn];
if( sProfileID.empty() )
@@ -117,48 +114,33 @@ bool ProfileManager::LoadDefaultProfileFromMachine( PlayerNumber pn, bool bLoadN
CString sDir = USER_PROFILES_DIR + sProfileID + "/";
return LoadProfile( pn, sDir, false, bLoadNamesOnly );
return LoadProfile( pn, sDir, false );
}
bool ProfileManager::LoadProfileFromMemoryCard( PlayerNumber pn, bool bLoadNamesOnly )
bool ProfileManager::LoadProfileFromMemoryCard( PlayerNumber pn )
{
UnloadProfile( pn );
#ifndef _XBOX
// mount slot
if( MEMCARDMAN->GetCardState(pn) == MEMORY_CARD_STATE_READY )
{
if( bLoadNamesOnly )
{
CString sMemCardDir = MEM_CARD_MOUNT_POINT[pn];
CString sProfileDir = sMemCardDir + PREFSMAN->m_sMemoryCardProfileSubdir + '/';
CString sDir = MEM_CARD_MOUNT_POINT[pn];
m_sProfileDir[pn] = sProfileDir;
m_bWasLoadedFromMemoryCard[pn] = true;
// tack on a subdirectory so that we don't write everything to the root
sDir += PREFSMAN->m_sMemoryCardProfileSubdir;
sDir += '/';
m_Profile[pn].InitAll();
m_Profile[pn].m_sDisplayName = MEMCARDMAN->GetName(pn);
bool bResult;
bResult = LoadProfile( pn, sDir, true );
if( bResult )
return true;
}
else
{
CString sDir = MEM_CARD_MOUNT_POINT[pn];
// tack on a subdirectory so that we don't write everything to the root
sDir += PREFSMAN->m_sMemoryCardProfileSubdir;
sDir += '/';
bool bResult;
bResult = LoadProfile( pn, sDir, true, bLoadNamesOnly );
if( bResult )
return true;
CreateMemoryCardProfile( pn );
CreateMemoryCardProfile( pn );
bResult = LoadProfile( pn, sDir, true, bLoadNamesOnly );
return bResult;
}
bResult = LoadProfile( pn, sDir, true );
return bResult;
}
#endif
return false;
}
@@ -179,12 +161,12 @@ bool ProfileManager::CreateMemoryCardProfile( PlayerNumber pn )
return CreateProfile( sDir, NEW_MEM_CARD_NAME );
}
bool ProfileManager::LoadFirstAvailableProfile( PlayerNumber pn, bool bLoadNamesOnly )
bool ProfileManager::LoadFirstAvailableProfile( PlayerNumber pn )
{
if( LoadProfileFromMemoryCard(pn,bLoadNamesOnly) )
if( LoadProfileFromMemoryCard(pn) )
return true;
if( LoadDefaultProfileFromMachine(pn,bLoadNamesOnly) )
if( LoadLocalProfileFromMachine(pn) )
return true;
return false;
+4 -4
View File
@@ -25,8 +25,9 @@ public:
void GetLocalProfileIDs( vector<CString> &asProfileIDsOut ) const;
void GetLocalProfileNames( vector<CString> &asNamesOut ) const;
bool LoadFirstAvailableProfile( PlayerNumber pn, bool bLoadNamesOnly ); // memory card or local profile
bool LoadProfileFromMemoryCard( PlayerNumber pn, bool bLoadNamesOnly );
bool LoadFirstAvailableProfile( PlayerNumber pn ); // memory card or local profile
bool LoadLocalProfileFromMachine( PlayerNumber pn );
bool LoadProfileFromMemoryCard( PlayerNumber pn );
void SaveAllProfiles() const;
bool SaveProfile( PlayerNumber pn ) const;
void UnloadProfile( PlayerNumber pn );
@@ -83,9 +84,8 @@ public:
// void ReadSM300NoteScores();
private:
bool LoadDefaultProfileFromMachine( PlayerNumber pn, bool bLoadNamesOnly );
bool CreateMemoryCardProfile( PlayerNumber pn );
bool LoadProfile( PlayerNumber pn, CString sProfileDir, bool bIsMemCard, bool bLoadNamesOnly );
bool LoadProfile( PlayerNumber pn, CString sProfileDir, bool bIsMemCard );
bool CreateProfile( CString sProfileDir, CString sName );
// Directory that contains the profile. Either on local machine or
+2 -1
View File
@@ -204,7 +204,8 @@ bool Screen::JoinInput( const DeviceInput& DeviceI, const InputEventType type, c
SCREENMAN->PlayStartSound();
GAMESTATE->JoinPlayer( MenuI.player );
PROFILEMAN->LoadFirstAvailableProfile( MenuI.player, true ); // fast load
// don't load memory card profiles here. It's slow and can cause a big skip.
PROFILEMAN->LoadLocalProfileFromMachine( MenuI.player );
SCREENMAN->RefreshCreditsMessages();
return true;
+2 -2
View File
@@ -97,8 +97,8 @@ void ScreenEvaluation::Init()
if( PREFSMAN->m_bScreenTestMode )
{
PROFILEMAN->LoadFirstAvailableProfile(PLAYER_1, false);
PROFILEMAN->LoadFirstAvailableProfile(PLAYER_2, false);
PROFILEMAN->LoadFirstAvailableProfile(PLAYER_1);
PROFILEMAN->LoadFirstAvailableProfile(PLAYER_2);
GAMESTATE->m_PlayMode = PLAY_MODE_REGULAR;
GAMESTATE->m_pCurStyle = GAMEMAN->GameAndStringToStyle( GAMEMAN->GetDefaultGame(), "versus" );
+23 -24
View File
@@ -48,6 +48,7 @@ ScreenManager* SCREENMAN = NULL; // global and accessable from anywhere in our p
#define CREDITS_INSERT_CARD THEME->GetMetric ("ScreenSystemLayer","CreditsInsertCard")
#define CREDITS_CARD_ERROR THEME->GetMetric ("ScreenSystemLayer","CreditsCardError")
#define CREDITS_CARD_TOO_LATE THEME->GetMetric ("ScreenSystemLayer","CreditsCardTooLate")
#define CREDITS_CARD_NO_NAME THEME->GetMetric ("ScreenSystemLayer","CreditsCardNoName")
#define CREDITS_FREE_PLAY THEME->GetMetric ("ScreenSystemLayer","CreditsFreePlay")
#define CREDITS_CREDITS THEME->GetMetric ("ScreenSystemLayer","CreditsCredits")
#define CREDITS_NOT_PRESENT THEME->GetMetric ("ScreenSystemLayer","CreditsNotPresent")
@@ -184,32 +185,30 @@ void ScreenSystemLayer::RefreshCreditsMessages()
{
MemoryCardState mcs = MEMCARDMAN->GetCardState( p );
Profile* pProfile = PROFILEMAN->GetProfile( p );
if( pProfile )
switch( mcs )
{
sCredits = pProfile->GetDisplayName();
}
else
{
switch( mcs )
{
case MEMORY_CARD_STATE_NO_CARD:
if( GAMESTATE->PlayersCanJoin() )
sCredits = CREDITS_INSERT_CARD;
else
sCredits = "";
break;
case MEMORY_CARD_STATE_WRITE_ERROR:
sCredits = CREDITS_CARD_ERROR;
break;
case MEMORY_CARD_STATE_TOO_LATE:
sCredits = CREDITS_CARD_TOO_LATE;
break;
case MEMORY_CARD_STATE_READY:
case MEMORY_CARD_STATE_NO_CARD:
if( pProfile ) // this is a local machine profile
sCredits = pProfile->GetDisplayName();
else if( GAMESTATE->PlayersCanJoin() )
sCredits = CREDITS_INSERT_CARD;
else
sCredits = "";
break;
default:
ASSERT(0);
}
break;
case MEMORY_CARD_STATE_WRITE_ERROR:
sCredits = CREDITS_CARD_ERROR;
break;
case MEMORY_CARD_STATE_TOO_LATE:
sCredits = CREDITS_CARD_TOO_LATE;
break;
case MEMORY_CARD_STATE_READY:
if( !MEMCARDMAN->GetName(p).empty() )
sCredits = MEMCARDMAN->GetName(p);
else
sCredits = CREDITS_CARD_NO_NAME;
break;
default:
ASSERT(0);
}
}
else // bShowCreditsMessage
@@ -47,10 +47,13 @@ public:
virtual void Unmount( UsbStorageDevice* pDevice, CString sMountPoint ) = 0;
virtual void Flush( UsbStorageDevice* pDevice ) = 0;
virtual void ResetUsbStorage() = 0;
virtual void PauseMountingThread() = 0;
virtual void UnPauseMountingThread() = 0;
virtual void DoOsMount() = 0;
virtual void DontDoOsMount() = 0;
enum MountThreadState
{
detect_and_mount,
detect_and_dont_mount,
paused
};
virtual void SetMountThreadState( MountThreadState mts ) = 0;
};
MemoryCardDriver *MakeMemoryCardDriver();
@@ -25,8 +25,9 @@ MemoryCardDriverThreaded::MemoryCardDriverThreaded() :
m_mutexStorageDevices("StorageDevices")
{
m_bShutdownNextUpdate = false;
m_bForceRedetectNextUpdate = true;
m_bStorageDevicesChanged = false;
m_bDoOsMount = true;
m_MountThreadState = detect_and_mount;
}
void MemoryCardDriverThreaded::StartThread()
@@ -52,24 +53,26 @@ MemoryCardDriverThreaded::~MemoryCardDriverThreaded()
ASSERT( !m_threadMemoryCardMount.IsCreated() );
}
void MemoryCardDriverThreaded::PauseMountingThread()
void MemoryCardDriverThreaded::SetMountThreadState( MountThreadState mts )
{
m_mutexPause.Lock();
}
CHECKPOINT;
void MemoryCardDriverThreaded::UnPauseMountingThread()
{
m_mutexPause.Unlock();
}
MountThreadState old = m_MountThreadState;
void MemoryCardDriverThreaded::DoOsMount()
{
m_bDoOsMount = true;
}
if( old != paused && mts == paused )
m_mutexPause.Lock();
void MemoryCardDriverThreaded::DontDoOsMount()
{
m_bDoOsMount = false;
if( old == paused && mts != paused )
m_mutexPause.Unlock();
if( old == detect_and_dont_mount && mts == detect_and_mount )
{
m_bForceRedetectNextUpdate = true;
LockMut( m_mutexStorageDevices );
m_vStorageDevices.clear();
}
m_MountThreadState = mts;
}
int MemoryCardDriverThreaded::MountThread_Start( void *p )
@@ -80,6 +83,8 @@ int MemoryCardDriverThreaded::MountThread_Start( void *p )
void MemoryCardDriverThreaded::MountThreadMain()
{
CHECKPOINT;
while( !m_bShutdownNextUpdate )
{
LockMut( m_mutexPause ); // wait until we're unpaused
@@ -89,6 +94,8 @@ void MemoryCardDriverThreaded::MountThreadMain()
bool MemoryCardDriverThreaded::StorageDevicesChanged()
{
CHECKPOINT;
LockMut( m_mutexStorageDevices );
if( m_bStorageDevicesChanged )
{
@@ -103,6 +110,8 @@ bool MemoryCardDriverThreaded::StorageDevicesChanged()
void MemoryCardDriverThreaded::GetStorageDevices( vector<UsbStorageDevice>& vDevicesOut )
{
CHECKPOINT;
LockMut( m_mutexStorageDevices );
vDevicesOut.clear();
for( unsigned i=0; i<m_vStorageDevices.size(); i++ )
@@ -10,6 +10,7 @@ struct UsbStorageDeviceEx : public UsbStorageDevice
void MakeBlank()
{
UsbStorageDevice::MakeBlank();
bWriteTestSucceeded = false;
}
@@ -25,10 +26,7 @@ public:
virtual bool StorageDevicesChanged();
virtual void GetStorageDevices( vector<UsbStorageDevice>& vStorageDevicesOut );
virtual bool MountAndTestWrite( UsbStorageDevice* pDevice, CString sMountPoint );
virtual void PauseMountingThread();
virtual void UnPauseMountingThread();
virtual void DoOsMount();
virtual void DontDoOsMount();
virtual void SetMountThreadState( MountThreadState mts );
private:
static int MountThread_Start( void *p );
@@ -42,20 +40,19 @@ private:
// will temporarily halt.
RageMutex m_mutexPause;
// If true, detect and report changes in connected devices, but don't don't
// do the OS mount or unmount.
bool m_bDoOsMount;
MountThreadState m_MountThreadState;
protected:
void StartThread(); // call this in the derived constructor to start the mounting thread
void StopThread(); // call this in the derived desstructor to stop the mounting thread
virtual void MountThreadDoOneUpdate() = 0; // this will get called as fast as possible
virtual void Mount( UsbStorageDevice* pDevice, CString sMountPoint ) = 0;
bool ShouldDoOsMount() { return m_bDoOsMount; }
bool ShouldDoOsMount() { return m_MountThreadState==detect_and_mount; }
vector<UsbStorageDeviceEx> m_vStorageDevices;
bool m_bStorageDevicesChanged;
RageMutex m_mutexStorageDevices; // protects the above two
bool m_bForceRedetectNextUpdate; // on the next update, redetect from scratch report new devices found
};
#endif
@@ -131,8 +131,6 @@ MemoryCardDriverThreaded_Linux::MemoryCardDriverThreaded_Linux()
if( m_fd == -1 )
LOG->Warn( "Failed to open \"%s\": %s", USB_DEVICE_LIST_FILE, strerror(errno) );
m_bForceRedetect = false;
this->StartThread();
}
@@ -164,8 +162,7 @@ void MemoryCardDriverThreaded_Linux::ResetUsbStorage()
ExecuteCommand( "rmmod usb-storage" );
ExecuteCommand( "modprobe usb-storage" );
m_vDevicesLastSeen.clear();
m_bForceRedetect = true;
m_bForceRedetectNextUpdate = true;
MountThreadDoOneUpdate();
}
@@ -178,9 +175,10 @@ void MemoryCardDriverThreaded_Linux::MountThreadDoOneUpdate()
return;
}
if( m_bForceRedetect )
if( m_bForceRedetectNextUpdate )
{
m_bForceRedetect = false;
m_vDevicesLastSeen.clear();
m_bForceRedetectNextUpdate = false;
// fall through
}
else
@@ -18,7 +18,6 @@ protected:
int m_fd;
vector<UsbStorageDeviceEx> m_vDevicesLastSeen;
bool m_bForceRedetect;
};
#endif
@@ -67,7 +67,17 @@ void MemoryCardDriverThreaded_Windows::ResetUsbStorage()
void MemoryCardDriverThreaded_Windows::MountThreadDoOneUpdate()
{
DWORD dwNewLogicalDrives = ::GetLogicalDrives();
if( dwNewLogicalDrives != m_dwLastLogicalDrives )
if( m_bForceRedetectNextUpdate )
{
m_bForceRedetectNextUpdate = false;
}
else if( dwNewLogicalDrives == m_dwLastLogicalDrives )
{
// no change from last update
return;
}
{
vector<UsbStorageDeviceEx> vNewStorageDevices;
@@ -89,29 +99,36 @@ void MemoryCardDriverThreaded_Windows::MountThreadDoOneUpdate()
UsbStorageDeviceEx usbd;
usbd.sOsMountDir = sDrive;
usbd.bWriteTestSucceeded = TestWrite( sDrive );
// read name
this->Mount( &usbd, TEMP_MOUNT_POINT );
FILEMAN->FlushDirCache( TEMP_MOUNT_POINT );
Profile profile;
CString sProfileDir = TEMP_MOUNT_POINT + PREFSMAN->m_sMemoryCardProfileSubdir + '/';
profile.LoadEditableDataFromDir( sProfileDir );
usbd.sName = profile.GetDisplayName();
if( ShouldDoOsMount() )
{
usbd.bWriteTestSucceeded = TestWrite( sDrive );
// read name
this->Mount( &usbd, TEMP_MOUNT_POINT );
FILEMAN->FlushDirCache( TEMP_MOUNT_POINT );
Profile profile;
CString sProfileDir = TEMP_MOUNT_POINT + PREFSMAN->m_sMemoryCardProfileSubdir + '/';
profile.LoadEditableDataFromDir( sProfileDir );
usbd.sName = profile.GetDisplayName();
}
vNewStorageDevices.push_back( usbd );
}
}
CHECKPOINT;
{
LockMut( m_mutexStorageDevices );
m_bStorageDevicesChanged = true;
m_vStorageDevices = vNewStorageDevices;
}
}
m_dwLastLogicalDrives = dwNewLogicalDrives;
usleep( 100000 );
CHECKPOINT;
m_dwLastLogicalDrives = dwNewLogicalDrives;
}
}
void MemoryCardDriverThreaded_Windows::Mount( UsbStorageDevice* pDevice, CString sMountPoint )
@@ -17,6 +17,7 @@ public:
virtual void UnPauseMountingThread() {}
virtual void DoOsMount() {}
virtual void DontDoOsMount() {}
virtual void SetMountThreadState( MountThreadState mts ) {}
};
#endif