aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChris Robinson <[email protected]>2018-02-04 00:01:12 -0800
committerChris Robinson <[email protected]>2018-02-04 00:01:12 -0800
commit9b878c64f9ec83adc4886db553ca184952ff50b4 (patch)
treedb4df8b93f71ac2f0887d803f98314d8994011ea
parent1f61472e77faa0b57231b19236272d3e4d67fbc0 (diff)
Make the Connected state atomic
Also don't send the Disconnected event more than once.
-rw-r--r--Alc/ALc.c20
-rw-r--r--Alc/ALu.c3
-rw-r--r--Alc/backends/alsa.c18
-rw-r--r--Alc/backends/dsound.c14
-rw-r--r--Alc/backends/jack.c3
-rw-r--r--Alc/backends/null.c13
-rw-r--r--Alc/backends/opensl.c3
-rw-r--r--Alc/backends/oss.c3
-rw-r--r--Alc/backends/pulseaudio.c13
-rw-r--r--Alc/backends/qsa.c13
-rw-r--r--Alc/backends/sndio.c14
-rw-r--r--Alc/backends/solaris.c3
-rw-r--r--Alc/backends/wave.c13
-rw-r--r--Alc/backends/winmm.c24
-rw-r--r--OpenAL32/Include/alMain.h2
-rw-r--r--OpenAL32/alSource.c2
16 files changed, 82 insertions, 79 deletions
diff --git a/Alc/ALc.c b/Alc/ALc.c
index 3c9598ca..915addac 100644
--- a/Alc/ALc.c
+++ b/Alc/ALc.c
@@ -3248,7 +3248,7 @@ static ALCsizei GetIntegerv(ALCdevice *device, ALCenum param, ALCsizei size, ALC
values[i++] = ALC_CAPTURE_SAMPLES;
values[i++] = V0(device->Backend,availableSamples)();
values[i++] = ALC_CONNECTED;
- values[i++] = device->Connected;
+ values[i++] = ATOMIC_LOAD(&device->Connected, almemory_order_relaxed);
almtx_unlock(&device->BackendLock);
values[i++] = 0;
@@ -3268,7 +3268,7 @@ static ALCsizei GetIntegerv(ALCdevice *device, ALCenum param, ALCsizei size, ALC
return 1;
case ALC_CONNECTED:
- values[0] = device->Connected;
+ values[0] = ATOMIC_LOAD(&device->Connected, almemory_order_acquire);
return 1;
default:
@@ -3457,7 +3457,7 @@ static ALCsizei GetIntegerv(ALCdevice *device, ALCenum param, ALCsizei size, ALC
return 1;
case ALC_CONNECTED:
- values[0] = device->Connected;
+ values[0] = ATOMIC_LOAD(&device->Connected, almemory_order_acquire);
return 1;
case ALC_HRTF_SOFT:
@@ -3764,7 +3764,8 @@ ALC_API ALCcontext* ALC_APIENTRY alcCreateContext(ALCdevice *device, const ALCin
* properly cleaned up after being made.
*/
LockLists();
- if(!VerifyDevice(&device) || device->Type == Capture || !device->Connected)
+ if(!VerifyDevice(&device) || device->Type == Capture ||
+ !ATOMIC_LOAD(&device->Connected, almemory_order_relaxed))
{
UnlockLists();
alcSetError(device, ALC_INVALID_DEVICE);
@@ -4034,7 +4035,7 @@ ALC_API ALCdevice* ALC_APIENTRY alcOpenDevice(const ALCchar *deviceName)
//Validate device
InitRef(&device->ref, 1);
- device->Connected = ALC_TRUE;
+ ATOMIC_INIT(&device->Connected, ALC_TRUE);
device->Type = Playback;
ATOMIC_INIT(&device->LastError, ALC_NO_ERROR);
@@ -4290,7 +4291,7 @@ ALC_API ALCdevice* ALC_APIENTRY alcCaptureOpenDevice(const ALCchar *deviceName,
//Validate device
InitRef(&device->ref, 1);
- device->Connected = ALC_TRUE;
+ ATOMIC_INIT(&device->Connected, ALC_TRUE);
device->Type = Capture;
InitDevice(device);
@@ -4389,7 +4390,7 @@ ALC_API void ALC_APIENTRY alcCaptureStart(ALCdevice *device)
else
{
almtx_lock(&device->BackendLock);
- if(!device->Connected)
+ if(!ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
alcSetError(device, ALC_INVALID_DEVICE);
else if(!(device->Flags&DEVICE_RUNNING))
{
@@ -4474,7 +4475,7 @@ ALC_API ALCdevice* ALC_APIENTRY alcLoopbackOpenDeviceSOFT(const ALCchar *deviceN
//Validate device
InitRef(&device->ref, 1);
- device->Connected = ALC_TRUE;
+ ATOMIC_INIT(&device->Connected, ALC_TRUE);
device->Type = Loopback;
ATOMIC_INIT(&device->LastError, ALC_NO_ERROR);
@@ -4675,7 +4676,8 @@ ALC_API ALCboolean ALC_APIENTRY alcResetDeviceSOFT(ALCdevice *device, const ALCi
ALCenum err;
LockLists();
- if(!VerifyDevice(&device) || device->Type == Capture || !device->Connected)
+ if(!VerifyDevice(&device) || device->Type == Capture ||
+ !ATOMIC_LOAD(&device->Connected, almemory_order_relaxed))
{
UnlockLists();
alcSetError(device, ALC_INVALID_DEVICE);
diff --git a/Alc/ALu.c b/Alc/ALu.c
index 9f4f7a30..2435558d 100644
--- a/Alc/ALu.c
+++ b/Alc/ALu.c
@@ -1857,7 +1857,8 @@ void aluHandleDisconnect(ALCdevice *device, const char *msg, ...)
va_list args;
int msglen;
- device->Connected = ALC_FALSE;
+ if(!ATOMIC_EXCHANGE(&device->Connected, AL_FALSE, almemory_order_acq_rel))
+ return;
evt.EnumType = EventType_Disconnected;
evt.Type = AL_EVENT_TYPE_DISCONNECTED_SOFT;
diff --git a/Alc/backends/alsa.c b/Alc/backends/alsa.c
index 72e2936f..c75749de 100644
--- a/Alc/backends/alsa.c
+++ b/Alc/backends/alsa.c
@@ -438,7 +438,7 @@ typedef struct ALCplaybackAlsa {
ALvoid *buffer;
ALsizei size;
- volatile int killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCplaybackAlsa;
@@ -468,6 +468,8 @@ static void ALCplaybackAlsa_Construct(ALCplaybackAlsa *self, ALCdevice *device)
self->pcmHandle = NULL;
self->buffer = NULL;
+
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
void ALCplaybackAlsa_Destruct(ALCplaybackAlsa *self)
@@ -495,7 +497,7 @@ static int ALCplaybackAlsa_mixerProc(void *ptr)
update_size = device->UpdateSize;
num_updates = device->NumUpdates;
- while(!self->killNow)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire))
{
int state = verify_state(self->pcmHandle);
if(state < 0)
@@ -585,7 +587,7 @@ static int ALCplaybackAlsa_mixerNoMMapProc(void *ptr)
update_size = device->UpdateSize;
num_updates = device->NumUpdates;
- while(!self->killNow)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire))
{
int state = verify_state(self->pcmHandle);
if(state < 0)
@@ -910,7 +912,7 @@ static ALCboolean ALCplaybackAlsa_start(ALCplaybackAlsa *self)
}
thread_func = ALCplaybackAlsa_mixerProc;
}
- self->killNow = 0;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, thread_func, self) != althrd_success)
{
ERR("Could not create playback thread\n");
@@ -931,10 +933,8 @@ static void ALCplaybackAlsa_stop(ALCplaybackAlsa *self)
{
int res;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- self->killNow = 1;
althrd_join(self->thread, &res);
al_free(self->buffer);
@@ -1207,7 +1207,7 @@ static ALCenum ALCcaptureAlsa_captureSamples(ALCcaptureAlsa *self, ALCvoid *buff
}
self->last_avail -= samples;
- while(device->Connected && samples > 0)
+ while(ATOMIC_LOAD(&device->Connected, almemory_order_acquire) && samples > 0)
{
snd_pcm_sframes_t amt = 0;
@@ -1275,7 +1275,7 @@ static ALCuint ALCcaptureAlsa_availableSamples(ALCcaptureAlsa *self)
ALCdevice *device = STATIC_CAST(ALCbackend, self)->mDevice;
snd_pcm_sframes_t avail = 0;
- if(device->Connected && self->doCapture)
+ if(ATOMIC_LOAD(&device->Connected, almemory_order_acquire) && self->doCapture)
avail = snd_pcm_avail_update(self->pcmHandle);
if(avail < 0)
{
diff --git a/Alc/backends/dsound.c b/Alc/backends/dsound.c
index bca8b7f0..0040a840 100644
--- a/Alc/backends/dsound.c
+++ b/Alc/backends/dsound.c
@@ -185,7 +185,7 @@ typedef struct ALCdsoundPlayback {
IDirectSoundNotify *Notifies;
HANDLE NotifyEvent;
- volatile int killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCdsoundPlayback;
@@ -217,6 +217,7 @@ static void ALCdsoundPlayback_Construct(ALCdsoundPlayback *self, ALCdevice *devi
self->Buffer = NULL;
self->Notifies = NULL;
self->NotifyEvent = NULL;
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCdsoundPlayback_Destruct(ALCdsoundPlayback *self)
@@ -276,7 +277,8 @@ FORCE_ALIGN static int ALCdsoundPlayback_mixerProc(void *ptr)
FragSize = device->UpdateSize * FrameSize;
IDirectSoundBuffer_GetCurrentPosition(self->Buffer, &LastCursor, NULL);
- while(!self->killNow)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
// Get current play cursor
IDirectSoundBuffer_GetCurrentPosition(self->Buffer, &PlayCursor, NULL);
@@ -636,7 +638,7 @@ retry_open:
static ALCboolean ALCdsoundPlayback_start(ALCdsoundPlayback *self)
{
- self->killNow = 0;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCdsoundPlayback_mixerProc, self) != althrd_success)
return ALC_FALSE;
@@ -647,10 +649,8 @@ static void ALCdsoundPlayback_stop(ALCdsoundPlayback *self)
{
int res;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- self->killNow = 1;
althrd_join(self->thread, &res);
IDirectSoundBuffer_Stop(self->Buffer);
@@ -930,7 +930,7 @@ static ALCuint ALCdsoundCapture_availableSamples(ALCdsoundCapture *self)
DWORD FrameSize;
HRESULT hr;
- if(!device->Connected)
+ if(!ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
goto done;
FrameSize = FrameSizeFromDevFmt(device->FmtChans, device->FmtType, device->AmbiOrder);
diff --git a/Alc/backends/jack.c b/Alc/backends/jack.c
index 2f17bbf6..e6f4b435 100644
--- a/Alc/backends/jack.c
+++ b/Alc/backends/jack.c
@@ -312,7 +312,8 @@ static int ALCjackPlayback_mixerProc(void *arg)
althrd_setname(althrd_current(), MIXER_THREAD_NAME);
ALCjackPlayback_lock(self);
- while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
ALuint todo, len1, len2;
diff --git a/Alc/backends/null.c b/Alc/backends/null.c
index d17c8bda..2c2db54e 100644
--- a/Alc/backends/null.c
+++ b/Alc/backends/null.c
@@ -36,7 +36,7 @@
typedef struct ALCnullBackend {
DERIVE_FROM_TYPE(ALCbackend);
- volatile int killNow;
+ ATOMIC(int) killNow;
althrd_t thread;
} ALCnullBackend;
@@ -65,6 +65,8 @@ static void ALCnullBackend_Construct(ALCnullBackend *self, ALCdevice *device)
{
ALCbackend_Construct(STATIC_CAST(ALCbackend, self), device);
SET_VTABLE2(ALCnullBackend, ALCbackend, self);
+
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
@@ -86,7 +88,8 @@ static int ALCnullBackend_mixerProc(void *ptr)
ERR("Failed to get starting time\n");
return 1;
}
- while(!self->killNow && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
if(altimespec_get(&now, AL_TIME_UTC) != AL_TIME_UTC)
{
@@ -142,7 +145,7 @@ static ALCboolean ALCnullBackend_reset(ALCnullBackend *self)
static ALCboolean ALCnullBackend_start(ALCnullBackend *self)
{
- self->killNow = 0;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCnullBackend_mixerProc, self) != althrd_success)
return ALC_FALSE;
return ALC_TRUE;
@@ -152,10 +155,8 @@ static void ALCnullBackend_stop(ALCnullBackend *self)
{
int res;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- self->killNow = 1;
althrd_join(self->thread, &res);
}
diff --git a/Alc/backends/opensl.c b/Alc/backends/opensl.c
index 93d2e521..b20d7841 100644
--- a/Alc/backends/opensl.c
+++ b/Alc/backends/opensl.c
@@ -266,7 +266,8 @@ static int ALCopenslPlayback_mixerProc(void *arg)
padding = ll_ringbuffer_write_space(self->mRing) - device->NumUpdates;
ALCopenslPlayback_lock(self);
- while(ATOMIC_LOAD_SEQ(&self->mKillNow) == AL_FALSE && device->Connected)
+ while(!ATOMIC_LOAD(&self->mKillNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
size_t todo, len0, len1;
diff --git a/Alc/backends/oss.c b/Alc/backends/oss.c
index 9b0c2d42..faf3ee99 100644
--- a/Alc/backends/oss.c
+++ b/Alc/backends/oss.c
@@ -284,7 +284,8 @@ static int ALCplaybackOSS_mixerProc(void *ptr)
frame_size = FrameSizeFromDevFmt(device->FmtChans, device->FmtType, device->AmbiOrder);
ALCplaybackOSS_lock(self);
- while(!ATOMIC_LOAD_SEQ(&self->killNow) && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
FD_ZERO(&wfds);
FD_SET(self->fd, &wfds);
diff --git a/Alc/backends/pulseaudio.c b/Alc/backends/pulseaudio.c
index 6ba82cd2..96794e20 100644
--- a/Alc/backends/pulseaudio.c
+++ b/Alc/backends/pulseaudio.c
@@ -472,7 +472,7 @@ typedef struct ALCpulsePlayback {
pa_stream *stream;
pa_context *context;
- volatile ALboolean killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCpulsePlayback;
@@ -515,6 +515,7 @@ static void ALCpulsePlayback_Construct(ALCpulsePlayback *self, ALCdevice *device
self->loop = NULL;
AL_STRING_INIT(self->device_name);
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCpulsePlayback_Destruct(ALCpulsePlayback *self)
@@ -829,7 +830,8 @@ static int ALCpulsePlayback_mixerProc(void *ptr)
pa_threaded_mainloop_lock(self->loop);
frame_size = pa_frame_size(&self->spec);
- while(!self->killNow && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
len = pa_stream_writable_size(self->stream);
if(len < 0)
@@ -1141,7 +1143,7 @@ static ALCboolean ALCpulsePlayback_reset(ALCpulsePlayback *self)
static ALCboolean ALCpulsePlayback_start(ALCpulsePlayback *self)
{
- self->killNow = AL_FALSE;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCpulsePlayback_mixerProc, self) != althrd_success)
return ALC_FALSE;
return ALC_TRUE;
@@ -1152,10 +1154,9 @@ static void ALCpulsePlayback_stop(ALCpulsePlayback *self)
pa_operation *o;
int res;
- if(!self->stream || self->killNow)
+ if(!self->stream || ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
- self->killNow = AL_TRUE;
/* Signal the main loop in case PulseAudio isn't sending us audio requests
* (e.g. if the device is suspended). We need to lock the mainloop in case
* the mixer is between checking the killNow flag but before waiting for
@@ -1705,7 +1706,7 @@ static ALCuint ALCpulseCapture_availableSamples(ALCpulseCapture *self)
ALCdevice *device = STATIC_CAST(ALCbackend,self)->mDevice;
size_t readable = self->cap_remain;
- if(device->Connected)
+ if(ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
ssize_t got;
pa_threaded_mainloop_lock(self->loop);
diff --git a/Alc/backends/qsa.c b/Alc/backends/qsa.c
index 484cadaa..8f87779b 100644
--- a/Alc/backends/qsa.c
+++ b/Alc/backends/qsa.c
@@ -46,7 +46,7 @@ typedef struct {
ALvoid* buffer;
ALsizei size;
- volatile int killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} qsa_data;
@@ -206,7 +206,7 @@ FORCE_ALIGN static int qsa_proc_playback(void *ptr)
);
V0(device->Backend,lock)();
- while(!data->killNow)
+ while(!ATOMIC_LOAD(&data->killNow, almemory_order_acquire))
{
FD_ZERO(&wfds);
FD_SET(data->audio_fd, &wfds);
@@ -232,7 +232,7 @@ FORCE_ALIGN static int qsa_proc_playback(void *ptr)
len = data->size;
write_ptr = data->buffer;
aluMixData(device, write_ptr, len/frame_size);
- while(len>0 && !data->killNow)
+ while(len>0 && !ATOMIC_LOAD(&data->killNow, almemory_order_acquire))
{
int wrote = snd_pcm_plugin_write(data->pcmHandle, write_ptr, len);
if(wrote <= 0)
@@ -282,6 +282,7 @@ static ALCenum qsa_open_playback(PlaybackWrapper *self, const ALCchar* deviceNam
data = (qsa_data*)calloc(1, sizeof(qsa_data));
if(data == NULL)
return ALC_OUT_OF_MEMORY;
+ ATOMIC_INIT(&data->killNow, AL_TRUE);
if(!deviceName)
deviceName = qsaDevice;
@@ -595,7 +596,7 @@ static ALCboolean qsa_start_playback(PlaybackWrapper *self)
{
qsa_data *data = self->ExtraData;
- data->killNow = 0;
+ ATOMIC_STORE(&data->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&data->thread, qsa_proc_playback, self) != althrd_success)
return ALC_FALSE;
@@ -607,10 +608,8 @@ static void qsa_stop_playback(PlaybackWrapper *self)
qsa_data *data = self->ExtraData;
int res;
- if(data->killNow)
+ if(ATOMIC_EXCHANGE(&data->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- data->killNow = 1;
althrd_join(data->thread, &res);
}
diff --git a/Alc/backends/sndio.c b/Alc/backends/sndio.c
index 06a434d9..5aea457b 100644
--- a/Alc/backends/sndio.c
+++ b/Alc/backends/sndio.c
@@ -43,7 +43,7 @@ typedef struct ALCsndioBackend {
ALvoid *mix_data;
ALsizei data_size;
- volatile int killNow;
+ ATOMIC(int) killNow;
althrd_t thread;
} ALCsndioBackend;
@@ -75,6 +75,7 @@ static void ALCsndioBackend_Construct(ALCsndioBackend *self, ALCdevice *device)
self->sndHandle = NULL;
self->mix_data = NULL;
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCsndioBackend_Destruct(ALCsndioBackend *self)
@@ -102,7 +103,8 @@ static int ALCsndioBackend_mixerProc(void *ptr)
frameSize = FrameSizeFromDevFmt(device->FmtChans, device->FmtType, device->AmbiOrder);
- while(!self->killNow && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
ALsizei len = self->data_size;
ALubyte *WritePtr = self->mix_data;
@@ -110,7 +112,7 @@ static int ALCsndioBackend_mixerProc(void *ptr)
ALCsndioBackend_lock(self);
aluMixData(device, WritePtr, len/frameSize);
ALCsndioBackend_unlock(self);
- while(len > 0 && !self->killNow)
+ while(len > 0 && !ATOMIC_LOAD(&self->killNow, almemory_order_acquire))
{
wrote = sio_write(self->sndHandle, WritePtr, len);
if(wrote == 0)
@@ -253,7 +255,7 @@ static ALCboolean ALCsndioBackend_start(ALCsndioBackend *self)
return ALC_FALSE;
}
- self->killNow = 0;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCsndioBackend_mixerProc, self) != althrd_success)
{
sio_stop(self->sndHandle);
@@ -267,10 +269,8 @@ static void ALCsndioBackend_stop(ALCsndioBackend *self)
{
int res;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- self->killNow = 1;
althrd_join(self->thread, &res);
if(!sio_stop(self->sndHandle))
diff --git a/Alc/backends/solaris.c b/Alc/backends/solaris.c
index fdc62562..f1c4aeaa 100644
--- a/Alc/backends/solaris.c
+++ b/Alc/backends/solaris.c
@@ -120,7 +120,8 @@ static int ALCsolarisBackend_mixerProc(void *ptr)
frame_size = FrameSizeFromDevFmt(device->FmtChans, device->FmtType, device->AmbiOrder);
ALCsolarisBackend_lock(self);
- while(!ATOMIC_LOAD_SEQ(&self->killNow) && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
FD_ZERO(&wfds);
FD_SET(self->fd, &wfds);
diff --git a/Alc/backends/wave.c b/Alc/backends/wave.c
index 13ffaeec..557c2bf2 100644
--- a/Alc/backends/wave.c
+++ b/Alc/backends/wave.c
@@ -77,7 +77,7 @@ typedef struct ALCwaveBackend {
ALvoid *mBuffer;
ALuint mSize;
- volatile int killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCwaveBackend;
@@ -110,7 +110,7 @@ static void ALCwaveBackend_Construct(ALCwaveBackend *self, ALCdevice *device)
self->mBuffer = NULL;
self->mSize = 0;
- self->killNow = 1;
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCwaveBackend_Destruct(ALCwaveBackend *self)
@@ -143,7 +143,8 @@ static int ALCwaveBackend_mixerProc(void *ptr)
ERR("Failed to get starting time\n");
return 1;
}
- while(!self->killNow && device->Connected)
+ while(!ATOMIC_LOAD(&self->killNow, almemory_order_acquire) &&
+ ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
if(altimespec_get(&now, AL_TIME_UTC) != AL_TIME_UTC)
{
@@ -355,7 +356,7 @@ static ALCboolean ALCwaveBackend_start(ALCwaveBackend *self)
return ALC_FALSE;
}
- self->killNow = 0;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCwaveBackend_mixerProc, self) != althrd_success)
{
free(self->mBuffer);
@@ -373,10 +374,8 @@ static void ALCwaveBackend_stop(ALCwaveBackend *self)
long size;
int res;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- self->killNow = 1;
althrd_join(self->thread, &res);
free(self->mBuffer);
diff --git a/Alc/backends/winmm.c b/Alc/backends/winmm.c
index 59164441..d6ecd7a9 100644
--- a/Alc/backends/winmm.c
+++ b/Alc/backends/winmm.c
@@ -148,7 +148,7 @@ typedef struct ALCwinmmPlayback {
WAVEFORMATEX Format;
- volatile ALboolean killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCwinmmPlayback;
@@ -180,7 +180,7 @@ static void ALCwinmmPlayback_Construct(ALCwinmmPlayback *self, ALCdevice *device
InitRef(&self->WaveBuffersCommitted, 0);
self->OutHdl = NULL;
- self->killNow = AL_TRUE;
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCwinmmPlayback_Destruct(ALCwinmmPlayback *self)
@@ -224,7 +224,7 @@ FORCE_ALIGN static int ALCwinmmPlayback_mixerProc(void *arg)
if(msg.message != WOM_DONE)
continue;
- if(self->killNow)
+ if(ATOMIC_LOAD(&self->killNow, almemory_order_acquire))
{
if(ReadRef(&self->WaveBuffersCommitted) == 0)
break;
@@ -371,7 +371,7 @@ static ALCboolean ALCwinmmPlayback_start(ALCwinmmPlayback *self)
ALint BufferSize;
ALuint i;
- self->killNow = AL_FALSE;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCwinmmPlayback_mixerProc, self) != althrd_success)
return ALC_FALSE;
@@ -402,11 +402,8 @@ static void ALCwinmmPlayback_stop(ALCwinmmPlayback *self)
void *buffer = NULL;
int i;
- if(self->killNow)
+ if(ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
return;
-
- // Set flag to stop processing headers
- self->killNow = AL_TRUE;
althrd_join(self->thread, &i);
// Release the wave buffers
@@ -433,7 +430,7 @@ typedef struct ALCwinmmCapture {
WAVEFORMATEX Format;
- volatile ALboolean killNow;
+ ATOMIC(ALenum) killNow;
althrd_t thread;
} ALCwinmmCapture;
@@ -465,7 +462,7 @@ static void ALCwinmmCapture_Construct(ALCwinmmCapture *self, ALCdevice *device)
InitRef(&self->WaveBuffersCommitted, 0);
self->InHdl = NULL;
- self->killNow = AL_TRUE;
+ ATOMIC_INIT(&self->killNow, AL_TRUE);
}
static void ALCwinmmCapture_Destruct(ALCwinmmCapture *self)
@@ -474,9 +471,8 @@ static void ALCwinmmCapture_Destruct(ALCwinmmCapture *self)
int i;
/* Tell the processing thread to quit and wait for it to do so. */
- if(!self->killNow)
+ if(!ATOMIC_EXCHANGE(&self->killNow, AL_TRUE, almemory_order_acq_rel))
{
- self->killNow = AL_TRUE;
PostThreadMessage(self->thread, WM_QUIT, 0, 0);
althrd_join(self->thread, &i);
@@ -536,7 +532,7 @@ static int ALCwinmmCapture_captureProc(void *arg)
continue;
/* Don't wait for other buffers to finish before quitting. We're
* closing so we don't need them. */
- if(self->killNow)
+ if(ATOMIC_LOAD(&self->killNow, almemory_order_acquire))
break;
WaveHdr = ((WAVEHDR*)msg.lParam);
@@ -656,7 +652,7 @@ static ALCenum ALCwinmmCapture_open(ALCwinmmCapture *self, const ALCchar *name)
IncrementRef(&self->WaveBuffersCommitted);
}
- self->killNow = AL_FALSE;
+ ATOMIC_STORE(&self->killNow, AL_FALSE, almemory_order_release);
if(althrd_create(&self->thread, ALCwinmmCapture_captureProc, self) != althrd_success)
goto failure;
diff --git a/OpenAL32/Include/alMain.h b/OpenAL32/Include/alMain.h
index 5c2435a4..baf610b8 100644
--- a/OpenAL32/Include/alMain.h
+++ b/OpenAL32/Include/alMain.h
@@ -466,7 +466,7 @@ struct ALCdevice_struct
{
RefCount ref;
- ALCboolean Connected;
+ ATOMIC(ALenum) Connected;
enum DeviceType Type;
ALuint Frequency;
diff --git a/OpenAL32/alSource.c b/OpenAL32/alSource.c
index c20226ca..8c8b2149 100644
--- a/OpenAL32/alSource.c
+++ b/OpenAL32/alSource.c
@@ -2518,7 +2518,7 @@ AL_API ALvoid AL_APIENTRY alSourcePlayv(ALsizei n, const ALuint *sources)
device = context->Device;
ALCdevice_Lock(device);
/* If the device is disconnected, go right to stopped. */
- if(!device->Connected)
+ if(!ATOMIC_LOAD(&device->Connected, almemory_order_acquire))
{
for(i = 0;i < n;i++)
{