mirror of
https://github.com/libretro/ppsspp.git
synced 2024-11-23 08:09:51 +00:00
Fix nasty race condition with menu background audio. Fixes #12365
This commit is contained in:
parent
701d740207
commit
22ee875ffc
@ -223,7 +223,7 @@ private:
|
||||
SimpleAudio *decoder_ = nullptr;
|
||||
};
|
||||
|
||||
static std::mutex bgMutex;
|
||||
static std::mutex g_bgMutex;
|
||||
static std::string bgGamePath;
|
||||
static int playbackOffset;
|
||||
static AT3PlusReader *at3Reader;
|
||||
@ -251,7 +251,7 @@ static void ClearBackgroundAudio(bool hard) {
|
||||
void SetBackgroundAudioGame(const std::string &path) {
|
||||
time_update();
|
||||
|
||||
std::lock_guard<std::mutex> lock(bgMutex);
|
||||
std::lock_guard<std::mutex> lock(g_bgMutex);
|
||||
if (path == bgGamePath) {
|
||||
// Do nothing
|
||||
return;
|
||||
@ -272,7 +272,7 @@ void SetBackgroundAudioGame(const std::string &path) {
|
||||
int PlayBackgroundAudio() {
|
||||
time_update();
|
||||
|
||||
std::lock_guard<std::mutex> lock(bgMutex);
|
||||
std::lock_guard<std::mutex> lock(g_bgMutex);
|
||||
|
||||
// Immediately stop the sound if it is turned off while playing.
|
||||
if (!g_Config.bEnableSound) {
|
||||
@ -281,30 +281,6 @@ int PlayBackgroundAudio() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// If there's a game, and some time has passed since the selected game
|
||||
// last changed... (to prevent crazy amount of reads when skipping through a list)
|
||||
if (!at3Reader && bgGamePath.size() && (time_now_d() - gameLastChanged > 0.5)) {
|
||||
// Grab some audio from the current game and play it.
|
||||
if (!g_gameInfoCache)
|
||||
return 0; // race condition?
|
||||
|
||||
// This is very unsafe! TODO: Get rid of this somehow or make threadsafe!
|
||||
std::shared_ptr<GameInfo> gameInfo = g_gameInfoCache->GetInfo(NULL, bgGamePath, GAMEINFO_WANTSND);
|
||||
if (!gameInfo)
|
||||
return 0;
|
||||
|
||||
if (gameInfo->pending) {
|
||||
// Should try again shortly..
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (gameInfo->sndFileData.size()) {
|
||||
const std::string &data = gameInfo->sndFileData;
|
||||
at3Reader = new AT3PlusReader(data);
|
||||
lastPlaybackTime = 0.0;
|
||||
}
|
||||
}
|
||||
|
||||
double now = time_now();
|
||||
if (at3Reader) {
|
||||
int sz = lastPlaybackTime <= 0.0 ? 44100 / 60 : (int)((now - lastPlaybackTime) * 44100);
|
||||
@ -336,3 +312,33 @@ int PlayBackgroundAudio() {
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Stuff that should be on the UI thread only, like anything to do with
|
||||
// g_gameInfoCache.
|
||||
void UpdateBackgroundAudio() {
|
||||
// If there's a game, and some time has passed since the selected game
|
||||
// last changed... (to prevent crazy amount of reads when skipping through a list)
|
||||
if (bgGamePath.size() && (time_now_d() - gameLastChanged > 0.5)) {
|
||||
std::lock_guard<std::mutex> lock(g_bgMutex);
|
||||
if (!at3Reader) {
|
||||
// Grab some audio from the current game and play it.
|
||||
if (!g_gameInfoCache)
|
||||
return;
|
||||
|
||||
std::shared_ptr<GameInfo> gameInfo = g_gameInfoCache->GetInfo(NULL, bgGamePath, GAMEINFO_WANTSND);
|
||||
if (!gameInfo)
|
||||
return;
|
||||
|
||||
if (gameInfo->pending) {
|
||||
// Should try again shortly..
|
||||
return;
|
||||
}
|
||||
|
||||
if (gameInfo->sndFileData.size()) {
|
||||
const std::string &data = gameInfo->sndFileData;
|
||||
at3Reader = new AT3PlusReader(data);
|
||||
lastPlaybackTime = 0.0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -4,3 +4,4 @@
|
||||
|
||||
void SetBackgroundAudioGame(const std::string &path);
|
||||
int PlayBackgroundAudio();
|
||||
void UpdateBackgroundAudio();
|
||||
|
@ -734,6 +734,7 @@ void GameInfoCache::WaitUntilDone(std::shared_ptr<GameInfo> &info) {
|
||||
|
||||
|
||||
// Runs on the main thread. Only call from render() and similar, not update()!
|
||||
// Can also be called from the audio thread for menu background music.
|
||||
std::shared_ptr<GameInfo> GameInfoCache::GetInfo(Draw::DrawContext *draw, const std::string &gamePath, int wantFlags) {
|
||||
std::shared_ptr<GameInfo> info;
|
||||
|
||||
|
@ -959,6 +959,12 @@ void RenderOverlays(UIContext *dc, void *userdata) {
|
||||
void NativeRender(GraphicsContext *graphicsContext) {
|
||||
g_GameManager.Update();
|
||||
|
||||
if (GetUIState() != UISTATE_INGAME) {
|
||||
// Note: We do this from NativeRender so that the graphics context is
|
||||
// guaranteed valid, to be safe - g_gameInfoCache messes around with textures.
|
||||
UpdateBackgroundAudio();
|
||||
}
|
||||
|
||||
float xres = dp_xres;
|
||||
float yres = dp_yres;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user