Skip to content

Commit 706e329

Browse files
mfleiszakallabeth
authored andcommitted
rdpsnd: Add synchronization to winmm backend
1 parent ae27728 commit 706e329

File tree

1 file changed

+18
-3
lines changed

1 file changed

+18
-3
lines changed

channels/rdpsnd/client/winmm/rdpsnd_winmm.c

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ struct rdpsnd_winmm_plugin
5454
UINT32 latency;
5555
HANDLE hThread;
5656
DWORD threadId;
57+
CRITICAL_SECTION cs;
5758
};
5859

5960
static BOOL rdpsnd_winmm_convert_format(const AUDIO_FORMAT* in, WAVEFORMATEX* out)
@@ -96,6 +97,7 @@ static BOOL rdpsnd_winmm_set_format(rdpsndDevicePlugin* device, const AUDIO_FORM
9697
static DWORD WINAPI waveOutProc(LPVOID lpParameter)
9798
{
9899
MSG msg;
100+
rdpsndWinmmPlugin* winmm = (rdpsndWinmmPlugin*)lpParameter;
99101
while (GetMessage(&msg, NULL, 0, 0))
100102
{
101103
if (msg.message == MM_WOM_CLOSE)
@@ -107,7 +109,9 @@ static DWORD WINAPI waveOutProc(LPVOID lpParameter)
107109
{
108110
/* free buffer */
109111
LPWAVEHDR waveHdr = (LPWAVEHDR)msg.lParam;
112+
EnterCriticalSection(&winmm->cs);
110113
waveOutUnprepareHeader((HWAVEOUT)msg.wParam, waveHdr, sizeof(WAVEHDR));
114+
LeaveCriticalSection(&winmm->cs);
111115
free(waveHdr->lpData);
112116
free(waveHdr);
113117
}
@@ -128,7 +132,7 @@ static BOOL rdpsnd_winmm_open(rdpsndDevicePlugin* device, const AUDIO_FORMAT* fo
128132
if (!rdpsnd_winmm_set_format(device, format, latency))
129133
return FALSE;
130134

131-
winmm->hThread = CreateThread(NULL, 0, waveOutProc, NULL, 0, &winmm->threadId);
135+
winmm->hThread = CreateThread(NULL, 0, waveOutProc, winmm, 0, &winmm->threadId);
132136
if (!winmm->hThread)
133137
{
134138
WLog_Print(winmm->log, WLOG_ERROR, "CreateThread failed: %" PRIu32 "", GetLastError());
@@ -162,6 +166,8 @@ static void rdpsnd_winmm_close(rdpsndDevicePlugin* device)
162166

163167
if (winmm->hWaveOut)
164168
{
169+
EnterCriticalSection(&winmm->cs);
170+
165171
mmResult = waveOutReset(winmm->hWaveOut);
166172
if (mmResult != MMSYSERR_NOERROR)
167173
WLog_Print(winmm->log, WLOG_ERROR, "waveOutReset failure: %" PRIu32 "", mmResult);
@@ -170,6 +176,8 @@ static void rdpsnd_winmm_close(rdpsndDevicePlugin* device)
170176
if (mmResult != MMSYSERR_NOERROR)
171177
WLog_Print(winmm->log, WLOG_ERROR, "waveOutClose failure: %" PRIu32 "", mmResult);
172178

179+
LeaveCriticalSection(&winmm->cs);
180+
173181
winmm->hWaveOut = NULL;
174182
}
175183

@@ -188,6 +196,7 @@ static void rdpsnd_winmm_free(rdpsndDevicePlugin* device)
188196
if (winmm)
189197
{
190198
rdpsnd_winmm_close(device);
199+
DeleteCriticalSection(&winmm->cs);
191200
free(winmm);
192201
}
193202
}
@@ -269,22 +278,27 @@ static UINT rdpsnd_winmm_play(rdpsndDevicePlugin* device, const BYTE* data, size
269278
memcpy(lpWaveHdr->lpData, data, size);
270279
lpWaveHdr->dwBufferLength = (DWORD)size;
271280

281+
EnterCriticalSection(&winmm->cs);
282+
272283
mmResult = waveOutPrepareHeader(winmm->hWaveOut, lpWaveHdr, sizeof(WAVEHDR));
273284
if (mmResult != MMSYSERR_NOERROR)
274285
{
275286
WLog_Print(winmm->log, WLOG_ERROR, "waveOutPrepareHeader failure: %" PRIu32 "", mmResult);
276-
goto fail;
287+
goto failCS;
277288
}
278289

279290
mmResult = waveOutWrite(winmm->hWaveOut, lpWaveHdr, sizeof(WAVEHDR));
280291
if (mmResult != MMSYSERR_NOERROR)
281292
{
282293
WLog_Print(winmm->log, WLOG_ERROR, "waveOutWrite failure: %" PRIu32 "", mmResult);
283294
waveOutUnprepareHeader(winmm->hWaveOut, lpWaveHdr, sizeof(WAVEHDR));
284-
goto fail;
295+
goto failCS;
285296
}
286297

298+
LeaveCriticalSection(&winmm->cs);
287299
return winmm->latency;
300+
failCS:
301+
LeaveCriticalSection(&winmm->cs);
288302
fail:
289303
if (lpWaveHdr)
290304
free(lpWaveHdr->lpData);
@@ -332,6 +346,7 @@ UINT freerdp_rdpsnd_client_subsystem_entry(PFREERDP_RDPSND_DEVICE_ENTRY_POINTS p
332346
winmm->device.Close = rdpsnd_winmm_close;
333347
winmm->device.Free = rdpsnd_winmm_free;
334348
winmm->log = WLog_Get(TAG);
349+
InitializeCriticalSection(&winmm->cs);
335350

336351
args = pEntryPoints->args;
337352
rdpsnd_winmm_parse_addin_args((rdpsndDevicePlugin*)winmm, args);

0 commit comments

Comments
 (0)