From 2754c750922aba74bacabc0e7723ce563059e11f Mon Sep 17 00:00:00 2001 From: Andrew Eikum Date: Mon, 18 Jul 2011 11:19:35 -0500 Subject: [PATCH] winmm: Perform Open and Close callbacks from client thread. --- dlls/winmm/tests/wave.c | 5 ++++ dlls/winmm/waveform.c | 64 ++++++++++++++++++++++++++++++++++------- 2 files changed, 59 insertions(+), 10 deletions(-) diff --git a/dlls/winmm/tests/wave.c b/dlls/winmm/tests/wave.c index 5bf77534f65..921216bf68f 100644 --- a/dlls/winmm/tests/wave.c +++ b/dlls/winmm/tests/wave.c @@ -37,6 +37,8 @@ #include "winmm_test.h" +static DWORD g_tid; + static void test_multiple_waveopens(void) { HWAVEOUT handle1, handle2; @@ -559,6 +561,8 @@ static void CALLBACK callback_func(HWAVEOUT hwo, UINT uMsg, DWORD_PTR dwInstance, DWORD dwParam1, DWORD dwParam2) { + if(uMsg == WOM_OPEN || uMsg == WOM_CLOSE) + ok(GetCurrentThreadId() == g_tid, "Got different thread ID\n"); SetEvent((HANDLE)dwInstance); } @@ -648,6 +652,7 @@ static void wave_out_test_deviceOut(int device, double duration, return; } wout=NULL; + g_tid = GetCurrentThreadId(); rc=waveOutOpen(&wout,device,pwfx,callback,callback_instance,flags); /* Note: Win9x doesn't know WAVE_FORMAT_DIRECT */ /* It is acceptable to fail on formats that are not specified to work */ diff --git a/dlls/winmm/waveform.c b/dlls/winmm/waveform.c index 5121bb7c74d..a06d12f5fc0 100644 --- a/dlls/winmm/waveform.c +++ b/dlls/winmm/waveform.c @@ -998,8 +998,6 @@ static LRESULT WOD_Open(WINMM_OpenInfo *info) LeaveCriticalSection(&device->lock); - WINMM_NotifyClient(&cb_info, WOM_OPEN, 0, 0); - return MMSYSERR_NOERROR; error: @@ -1069,8 +1067,6 @@ static LRESULT WID_Open(WINMM_OpenInfo *info) LeaveCriticalSection(&device->lock); - WINMM_NotifyClient(&cb_info, WIM_OPEN, 0, 0); - return MMSYSERR_NOERROR; error: @@ -1143,8 +1139,6 @@ static LRESULT WOD_Close(HWAVEOUT hwave) LeaveCriticalSection(&device->lock); - WINMM_NotifyClient(&cb_info, WOM_CLOSE, 0, 0); - return MMSYSERR_NOERROR; } @@ -1167,8 +1161,6 @@ static LRESULT WID_Close(HWAVEIN hwave) LeaveCriticalSection(&device->lock); - WINMM_NotifyClient(&cb_info, WIM_CLOSE, 0, 0); - return MMSYSERR_NOERROR; } @@ -2325,6 +2317,7 @@ MMRESULT WINAPI waveOutOpen(LPHWAVEOUT lphWaveOut, UINT uDeviceID, LRESULT res; HRESULT hr; WINMM_OpenInfo info; + WINMM_CBInfo cb_info; TRACE("(%p, %u, %p, %lx, %lx, %08x)\n", lphWaveOut, uDeviceID, lpFormat, dwCallback, dwInstance, dwFlags); @@ -2354,6 +2347,13 @@ MMRESULT WINAPI waveOutOpen(LPHWAVEOUT lphWaveOut, UINT uDeviceID, if(lphWaveOut) *lphWaveOut = (HWAVEOUT)info.handle; + cb_info.flags = HIWORD(dwFlags & CALLBACK_TYPEMASK); + cb_info.callback = dwCallback; + cb_info.user = dwInstance; + cb_info.hwave = info.handle; + + WINMM_NotifyClient(&cb_info, WOM_OPEN, 0, 0); + return res; } @@ -2362,12 +2362,30 @@ MMRESULT WINAPI waveOutOpen(LPHWAVEOUT lphWaveOut, UINT uDeviceID, */ UINT WINAPI waveOutClose(HWAVEOUT hWaveOut) { + UINT res; + WINMM_Device *device; + WINMM_CBInfo cb_info; + TRACE("(%p)\n", hWaveOut); if(!WINMM_StartDevicesThread()) return MMSYSERR_ERROR; - return SendMessageW(g_devices_hwnd, WODM_CLOSE, (WPARAM)hWaveOut, 0); + device = WINMM_GetDeviceFromHWAVE((HWAVE)hWaveOut); + + if(!WINMM_ValidateAndLock(device)) + return MMSYSERR_INVALHANDLE; + + memcpy(&cb_info, &device->cb_info, sizeof(cb_info)); + + LeaveCriticalSection(&device->lock); + + res = SendMessageW(g_devices_hwnd, WODM_CLOSE, (WPARAM)hWaveOut, 0); + + if(res == MMSYSERR_NOERROR) + WINMM_NotifyClient(&cb_info, WOM_CLOSE, 0, 0); + + return res; } /************************************************************************** @@ -2978,6 +2996,7 @@ MMRESULT WINAPI waveInOpen(HWAVEIN* lphWaveIn, UINT uDeviceID, LRESULT res; HRESULT hr; WINMM_OpenInfo info; + WINMM_CBInfo cb_info; TRACE("(%p, %x, %p, %lx, %lx, %08x)\n", lphWaveIn, uDeviceID, lpFormat, dwCallback, dwInstance, dwFlags); @@ -3007,6 +3026,13 @@ MMRESULT WINAPI waveInOpen(HWAVEIN* lphWaveIn, UINT uDeviceID, if(lphWaveIn) *lphWaveIn = (HWAVEIN)info.handle; + cb_info.flags = HIWORD(dwFlags & CALLBACK_TYPEMASK); + cb_info.callback = dwCallback; + cb_info.user = dwInstance; + cb_info.hwave = info.handle; + + WINMM_NotifyClient(&cb_info, WIM_OPEN, 0, 0); + return res; } @@ -3015,12 +3041,30 @@ MMRESULT WINAPI waveInOpen(HWAVEIN* lphWaveIn, UINT uDeviceID, */ UINT WINAPI waveInClose(HWAVEIN hWaveIn) { + WINMM_Device *device; + WINMM_CBInfo cb_info; + UINT res; + TRACE("(%p)\n", hWaveIn); if(!WINMM_StartDevicesThread()) return MMSYSERR_ERROR; - return SendMessageW(g_devices_hwnd, WIDM_CLOSE, (WPARAM)hWaveIn, 0); + device = WINMM_GetDeviceFromHWAVE((HWAVE)hWaveIn); + + if(!WINMM_ValidateAndLock(device)) + return MMSYSERR_INVALHANDLE; + + memcpy(&cb_info, &device->cb_info, sizeof(cb_info)); + + LeaveCriticalSection(&device->lock); + + res = SendMessageW(g_devices_hwnd, WIDM_CLOSE, (WPARAM)hWaveIn, 0); + + if(res == MMSYSERR_NOERROR) + WINMM_NotifyClient(&cb_info, WIM_CLOSE, 0, 0); + + return res; } /**************************************************************************