Made the buffer list in the directsound object thread-safe.

This commit is contained in:
Marcus Meissner 2000-02-20 19:16:12 +00:00 committed by Alexandre Julliard
parent 4654c32122
commit f8e4fb0888
1 changed files with 16 additions and 9 deletions

View File

@ -98,6 +98,7 @@ struct IDirectSoundImpl
IDirectSoundBufferImpl* primary; IDirectSoundBufferImpl* primary;
IDirectSound3DListenerImpl* listener; IDirectSound3DListenerImpl* listener;
WAVEFORMATEX wfx; /* current main waveformat */ WAVEFORMATEX wfx; /* current main waveformat */
CRITICAL_SECTION lock;
}; };
/***************************************************************************** /*****************************************************************************
@ -803,7 +804,7 @@ static HRESULT WINAPI IDirectSoundBufferImpl_SetFormat(
} }
/* **** */ /* **** */
EnterCriticalSection(&(primarybuf->lock)); EnterCriticalSection(&(This->dsound->lock));
if (primarybuf->wfx.nSamplesPerSec != wfex->nSamplesPerSec) { if (primarybuf->wfx.nSamplesPerSec != wfex->nSamplesPerSec) {
dsb = dsound->buffers; dsb = dsound->buffers;
@ -829,10 +830,9 @@ static HRESULT WINAPI IDirectSoundBufferImpl_SetFormat(
primarybuf->wfx.nAvgBytesPerSec = primarybuf->wfx.nAvgBytesPerSec =
This->wfx.nSamplesPerSec * This->wfx.nBlockAlign; This->wfx.nSamplesPerSec * This->wfx.nBlockAlign;
DSOUND_CloseAudio(); DSOUND_CloseAudio();
LeaveCriticalSection(&(primarybuf->lock)); LeaveCriticalSection(&(This->dsound->lock));
/* **** */ /* **** */
return DS_OK; return DS_OK;
@ -963,6 +963,7 @@ static DWORD WINAPI IDirectSoundBufferImpl_Release(LPDIRECTSOUNDBUFFER iface) {
if (--This->ref) if (--This->ref)
return This->ref; return This->ref;
EnterCriticalSection(&(This->dsound->lock));
for (i=0;i<This->dsound->nrofbuffers;i++) for (i=0;i<This->dsound->nrofbuffers;i++)
if (This->dsound->buffers[i] == This) if (This->dsound->buffers[i] == This)
break; break;
@ -973,12 +974,11 @@ static DWORD WINAPI IDirectSoundBufferImpl_Release(LPDIRECTSOUNDBUFFER iface) {
This->dsound->nrofbuffers--; This->dsound->nrofbuffers--;
IDirectSound_Release((LPDIRECTSOUND)This->dsound); IDirectSound_Release((LPDIRECTSOUND)This->dsound);
} }
LeaveCriticalSection(&(This->dsound->lock));
DeleteCriticalSection(&(This->lock)); DeleteCriticalSection(&(This->lock));
if (This->ds3db && ICOM_VTBL(This->ds3db)) if (This->ds3db && ICOM_VTBL(This->ds3db))
IDirectSound3DBuffer_Release((LPDIRECTSOUND3DBUFFER)This->ds3db); IDirectSound3DBuffer_Release((LPDIRECTSOUND3DBUFFER)This->ds3db);
if (This->parent) if (This->parent)
/* this is a duplicate buffer */ /* this is a duplicate buffer */
IDirectSoundBuffer_Release((LPDIRECTSOUNDBUFFER)This->parent); IDirectSoundBuffer_Release((LPDIRECTSOUNDBUFFER)This->parent);
@ -1369,12 +1369,15 @@ static HRESULT WINAPI IDirectSoundImpl_CreateSoundBuffer(
memcpy(&((*ippdsb)->dsbd),dsbd,sizeof(*dsbd)); memcpy(&((*ippdsb)->dsbd),dsbd,sizeof(*dsbd));
EnterCriticalSection(&(This->lock));
/* register buffer */ /* register buffer */
if (!(dsbd->dwFlags & DSBCAPS_PRIMARYBUFFER)) { if (!(dsbd->dwFlags & DSBCAPS_PRIMARYBUFFER)) {
This->buffers = (IDirectSoundBufferImpl**)HeapReAlloc(GetProcessHeap(),0,This->buffers,sizeof(IDirectSoundBufferImpl*)*(This->nrofbuffers+1)); This->buffers = (IDirectSoundBufferImpl**)HeapReAlloc(GetProcessHeap(),0,This->buffers,sizeof(IDirectSoundBufferImpl*)*(This->nrofbuffers+1));
This->buffers[This->nrofbuffers] = *ippdsb; This->buffers[This->nrofbuffers] = *ippdsb;
This->nrofbuffers++; This->nrofbuffers++;
} }
LeaveCriticalSection(&(This->lock));
IDirectSound_AddRef(iface); IDirectSound_AddRef(iface);
if (dsbd->lpwfxFormat) if (dsbd->lpwfxFormat)
@ -1439,10 +1442,12 @@ static HRESULT WINAPI IDirectSoundImpl_DuplicateSoundBuffer(
(*ippdsb)->parent = ipdsb; (*ippdsb)->parent = ipdsb;
memcpy(&((*ippdsb)->wfx), &(ipdsb->wfx), sizeof((*ippdsb)->wfx)); memcpy(&((*ippdsb)->wfx), &(ipdsb->wfx), sizeof((*ippdsb)->wfx));
/* register buffer */ /* register buffer */
EnterCriticalSection(&(This->lock));
This->buffers = (IDirectSoundBufferImpl**)HeapReAlloc(GetProcessHeap(),0,This->buffers,sizeof(IDirectSoundBufferImpl**)*(This->nrofbuffers+1)); This->buffers = (IDirectSoundBufferImpl**)HeapReAlloc(GetProcessHeap(),0,This->buffers,sizeof(IDirectSoundBufferImpl**)*(This->nrofbuffers+1));
This->buffers[This->nrofbuffers] = *ippdsb; This->buffers[This->nrofbuffers] = *ippdsb;
This->nrofbuffers++; This->nrofbuffers++;
IDirectSound_AddRef(iface); IDirectSound_AddRef(iface);
LeaveCriticalSection(&(This->lock));
return DS_OK; return DS_OK;
} }
@ -2222,7 +2227,7 @@ static DWORD WINAPI DSOUND_thread(LPVOID arg)
} }
#endif #endif
/* RACE: dsound could be deleted */ /* RACE: dsound could be deleted */
IDirectSound_AddRef((LPDIRECTSOUND)dsound); EnterCriticalSection(&(dsound->lock));
if (primarybuf == NULL) { if (primarybuf == NULL) {
/* Should never happen */ /* Should never happen */
WARN("Lost the primary buffer!\n"); WARN("Lost the primary buffer!\n");
@ -2230,11 +2235,12 @@ static DWORD WINAPI DSOUND_thread(LPVOID arg)
ExitThread(0); ExitThread(0);
} }
/* **** */
EnterCriticalSection(&(primarybuf->lock)); EnterCriticalSection(&(primarybuf->lock));
len = DSOUND_MixPrimary(); len = DSOUND_MixPrimary();
LeaveCriticalSection(&(primarybuf->lock)); LeaveCriticalSection(&(primarybuf->lock));
/* **** */ LeaveCriticalSection(&(dsound->lock));
if (primarybuf->playing) if (primarybuf->playing)
len = DSOUND_FRAGLEN > len ? DSOUND_FRAGLEN : len; len = DSOUND_FRAGLEN > len ? DSOUND_FRAGLEN : len;
@ -2247,7 +2253,6 @@ static DWORD WINAPI DSOUND_thread(LPVOID arg)
DSOUND_CloseAudio(); DSOUND_CloseAudio();
Sleep(100); Sleep(100);
} }
IDirectSound_Release((LPDIRECTSOUND)dsound);
} }
ExitThread(0); ExitThread(0);
} }
@ -2309,6 +2314,8 @@ HRESULT WINAPI DirectSoundCreate(REFGUID lpGUID,LPDIRECTSOUND *ppDS,IUnknown *pU
(*ippDS)->wfx.nBlockAlign = 2; (*ippDS)->wfx.nBlockAlign = 2;
(*ippDS)->wfx.wBitsPerSample = 8; (*ippDS)->wfx.wBitsPerSample = 8;
InitializeCriticalSection(&((*ippDS)->lock));
if (!dsound) { if (!dsound) {
HANDLE hnd; HANDLE hnd;
DWORD xid; DWORD xid;