summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCharles Pigott <charlespigott@googlemail.com>2021-07-21 10:32:33 +0100
committerGitHub <noreply@github.com>2021-07-21 10:32:33 +0100
commit6c33b4ed284eabebc1077ef4093502b150ec71b8 (patch)
tree989b42222d96671d4edf69e86f89ebc3cde75834
parentdd54e4c8352b1f2215691f6d6b333868e760fbbd (diff)
downloadopenttd-master.tar.xz
Fix #8335: Race condition in music mixer (#9450)HEADmaster
-rw-r--r--src/mixer.cpp35
1 files changed, 21 insertions, 14 deletions
diff --git a/src/mixer.cpp b/src/mixer.cpp
index d892a573c..b9b20fccf 100644
--- a/src/mixer.cpp
+++ b/src/mixer.cpp
@@ -9,12 +9,13 @@
#include "stdafx.h"
#include <math.h>
+#include <mutex>
#include "core/math_func.hpp"
#include "framerate_type.h"
#include "settings_type.h"
#include "safeguards.h"
-#include "mixer.h"
+#include "mixer.h"
struct MixerChannel {
bool active;
@@ -39,6 +40,7 @@ static MixerChannel _channels[8];
static uint32 _play_rate = 11025;
static uint32 _max_size = UINT_MAX;
static MxStreamCallback _music_stream = nullptr;
+static std::mutex _music_stream_mutex;
/**
* The theoretical maximum volume for a single sound sample. Multiple sound
@@ -152,8 +154,11 @@ void MxMixSamples(void *buffer, uint samples)
/* Clear the buffer */
memset(buffer, 0, sizeof(int16) * 2 * samples);
- /* Fetch music if a sampled stream is available */
- if (_music_stream) _music_stream((int16*)buffer, samples);
+ {
+ std::lock_guard<std::mutex> lock{ _music_stream_mutex };
+ /* Fetch music if a sampled stream is available */
+ if (_music_stream) _music_stream((int16*)buffer, samples);
+ }
/* Apply simple x^3 scaling to master effect volume. This increases the
* perceived difference in loudness to better match expectations. effect_vol
@@ -227,22 +232,24 @@ void MxSetChannelVolume(MixerChannel *mc, uint volume, float pan)
void MxActivateChannel(MixerChannel *mc)
{
mc->active = true;
-}
-
-/**
- * Set source of PCM music
- * @param music_callback Function that will be called to fill sample buffers with music data.
- * @return Sample rate of mixer, which the buffers supplied to the callback must be rendered at.
- */
-uint32 MxSetMusicSource(MxStreamCallback music_callback)
-{
- _music_stream = music_callback;
- return _play_rate;
+}
+
+/**
+ * Set source of PCM music
+ * @param music_callback Function that will be called to fill sample buffers with music data.
+ * @return Sample rate of mixer, which the buffers supplied to the callback must be rendered at.
+ */
+uint32 MxSetMusicSource(MxStreamCallback music_callback)
+{
+ std::lock_guard<std::mutex> lock{ _music_stream_mutex };
+ _music_stream = music_callback;
+ return _play_rate;
}
bool MxInitialize(uint rate)
{
+ std::lock_guard<std::mutex> lock{ _music_stream_mutex };
_play_rate = rate;
_max_size = UINT_MAX / _play_rate;
_music_stream = nullptr; /* rate may have changed, any music source is now invalid */