From 9692814502223574b575931d32ddd458b9476bb6 Mon Sep 17 00:00:00 2001 From: James Ross-Gowan Date: Sun, 29 Jan 2017 23:59:24 +1100 Subject: win32: add COM-specific SAFE_RELEASE to windows_utils.h See: https://msdn.microsoft.com/en-us/library/windows/desktop/dd743946.aspx Microsoft example code often uses a SAFE_RELEASE macro like the one in the above link. This makes it easier to avoid errors when releasing COM interfaces. It also reduces noise in COM-heavy code. ao_wasapi.h also had a macro called SAFE_RELEASE, though unlike the version above, its SAFE_RELEASE macro accepted a second parameter which allowed it to destroy arbitrary objects other than just COM interfaces. This renames ao_wasapi's SAFE_RELEASE to SAFE_DESTROY, which should more accurately reflect what it does and prevent confusion with the Microsoft version. --- audio/out/ao_wasapi.c | 12 +++++------ audio/out/ao_wasapi.h | 2 +- audio/out/ao_wasapi_changenotify.c | 2 +- audio/out/ao_wasapi_utils.c | 41 ++++++++++++++++++-------------------- 4 files changed, 27 insertions(+), 30 deletions(-) (limited to 'audio') diff --git a/audio/out/ao_wasapi.c b/audio/out/ao_wasapi.c index b2e035d3dc..3a4c341387 100644 --- a/audio/out/ao_wasapi.c +++ b/audio/out/ao_wasapi.c @@ -255,9 +255,9 @@ static void uninit(struct ao *ao) "while waiting for audio thread to terminate\n"); } - SAFE_RELEASE(state->hInitDone, CloseHandle(state->hInitDone)); - SAFE_RELEASE(state->hWake, CloseHandle(state->hWake)); - SAFE_RELEASE(state->hAudioThread,CloseHandle(state->hAudioThread)); + SAFE_DESTROY(state->hInitDone, CloseHandle(state->hInitDone)); + SAFE_DESTROY(state->hWake, CloseHandle(state->hWake)); + SAFE_DESTROY(state->hAudioThread,CloseHandle(state->hAudioThread)); wasapi_change_uninit(ao); @@ -305,7 +305,7 @@ static int init(struct ao *ao) } WaitForSingleObject(state->hInitDone, INFINITE); // wait on init complete - SAFE_RELEASE(state->hInitDone,CloseHandle(state->hInitDone)); + SAFE_DESTROY(state->hInitDone,CloseHandle(state->hInitDone)); if (FAILED(state->init_ret)) { if (!ao->probing) MP_FATAL(ao, "Received failure from audio thread\n"); @@ -418,10 +418,10 @@ static int thread_control(struct ao *ao, enum aocontrol cmd, void *arg) do { IAudioSessionControl_SetDisplayName(state->pSessionControl, title, NULL); - SAFE_RELEASE(tmp, CoTaskMemFree(tmp)); + SAFE_DESTROY(tmp, CoTaskMemFree(tmp)); IAudioSessionControl_GetDisplayName(state->pSessionControl, &tmp); } while (lstrcmpW(title, tmp)); - SAFE_RELEASE(tmp, CoTaskMemFree(tmp)); + SAFE_DESTROY(tmp, CoTaskMemFree(tmp)); talloc_free(title); return CONTROL_OK; } diff --git a/audio/out/ao_wasapi.h b/audio/out/ao_wasapi.h index 65f16d11c1..8f6e38867c 100644 --- a/audio/out/ao_wasapi.h +++ b/audio/out/ao_wasapi.h @@ -47,7 +47,7 @@ void wasapi_change_uninit(struct ao* ao); #define EXIT_ON_ERROR(hres) \ do { if (FAILED(hres)) { goto exit_label; } } while(0) -#define SAFE_RELEASE(unk, release) \ +#define SAFE_DESTROY(unk, release) \ do { if ((unk) != NULL) { release; (unk) = NULL; } } while(0) #define mp_format_res_str(hres) \ diff --git a/audio/out/ao_wasapi_changenotify.c b/audio/out/ao_wasapi_changenotify.c index e1b3a9d604..b9806e0adb 100644 --- a/audio/out/ao_wasapi_changenotify.c +++ b/audio/out/ao_wasapi_changenotify.c @@ -242,5 +242,5 @@ void wasapi_change_uninit(struct ao *ao) change->pEnumerator, (IMMNotificationClient *)change); } - SAFE_RELEASE(change->pEnumerator, IMMDeviceEnumerator_Release(change->pEnumerator)); + SAFE_RELEASE(change->pEnumerator); } diff --git a/audio/out/ao_wasapi_utils.c b/audio/out/ao_wasapi_utils.c index 4667b57ae8..a449dbec10 100644 --- a/audio/out/ao_wasapi_utils.c +++ b/audio/out/ao_wasapi_utils.c @@ -539,8 +539,7 @@ static void init_session_display(struct wasapi_state *state) { return; exit_label: // if we got here then the session control is useless - release it - SAFE_RELEASE(state->pSessionControl, - IAudioSessionControl_Release(state->pSessionControl)); + SAFE_RELEASE(state->pSessionControl); MP_WARN(state, "Error setting audio session display name: %s\n", mp_HRESULT_to_str(hr)); return; @@ -571,10 +570,8 @@ static void init_volume_control(struct wasapi_state *state) return; exit_label: state->vol_hw_support = 0; - SAFE_RELEASE(state->pEndpointVolume, - IAudioEndpointVolume_Release(state->pEndpointVolume)); - SAFE_RELEASE(state->pAudioVolume, - ISimpleAudioVolume_Release(state->pAudioVolume)); + SAFE_RELEASE(state->pEndpointVolume); + SAFE_RELEASE(state->pAudioVolume); MP_WARN(state, "Error setting up volume control: %s\n", mp_HRESULT_to_str(hr)); } @@ -707,7 +704,7 @@ exit_label: if (FAILED(hr)) mp_warn(l, "Failed getting device name: %s\n", mp_HRESULT_to_str(hr)); PropVariantClear(&devname); - SAFE_RELEASE(pProps, IPropertyStore_Release(pProps)); + SAFE_RELEASE(pProps); return namestr ? namestr : talloc_strdup(talloc_ctx, ""); } @@ -722,7 +719,7 @@ static struct device_desc *get_device_desc(struct mp_log *l, IMMDevice *pDevice) struct device_desc *d = talloc_zero(NULL, struct device_desc); d->deviceID = talloc_memdup(d, deviceID, (wcslen(deviceID) + 1) * sizeof(wchar_t)); - SAFE_RELEASE(deviceID, CoTaskMemFree(deviceID)); + SAFE_DESTROY(deviceID, CoTaskMemFree(deviceID)); char *full_id = mp_to_utf8(NULL, d->deviceID); bstr id = bstr0(full_id); @@ -745,8 +742,8 @@ static void destroy_enumerator(struct enumerator *e) { if (!e) return; - SAFE_RELEASE(e->pDevices, IMMDeviceCollection_Release(e->pDevices)); - SAFE_RELEASE(e->pEnumerator, IMMDeviceEnumerator_Release(e->pEnumerator)); + SAFE_RELEASE(e->pDevices); + SAFE_RELEASE(e->pEnumerator); talloc_free(e); } @@ -782,7 +779,7 @@ static struct device_desc *device_desc_for_num(struct enumerator *e, UINT i) return NULL; } struct device_desc *d = get_device_desc(e->log, pDevice); - SAFE_RELEASE(pDevice, IMMDevice_Release(pDevice)); + SAFE_RELEASE(pDevice); return d; } @@ -797,7 +794,7 @@ static struct device_desc *default_device_desc(struct enumerator *e) return NULL; } struct device_desc *d = get_device_desc(e->log, pDevice); - SAFE_RELEASE(pDevice, IMMDevice_Release(pDevice)); + SAFE_RELEASE(pDevice); return d; } @@ -834,7 +831,7 @@ static HRESULT load_device(struct mp_log *l, exit_label: if (FAILED(hr)) mp_err(l, "Error loading selected device: %s\n", mp_HRESULT_to_str(hr)); - SAFE_RELEASE(pEnumerator, IMMDeviceEnumerator_Release(pEnumerator)); + SAFE_RELEASE(pEnumerator); return hr; } @@ -908,7 +905,7 @@ LPWSTR wasapi_find_deviceID(struct ao *ao) BSTR_P(device), d->id, d->name); } } - SAFE_RELEASE(d, talloc_free(d)); + SAFE_DESTROY(d, talloc_free(d)); } if (!deviceID) @@ -969,13 +966,13 @@ void wasapi_thread_uninit(struct ao *ao) if (state->pAudioClient) IAudioClient_Stop(state->pAudioClient); - SAFE_RELEASE(state->pRenderClient, IAudioRenderClient_Release(state->pRenderClient)); - SAFE_RELEASE(state->pAudioClock, IAudioClock_Release(state->pAudioClock)); - SAFE_RELEASE(state->pAudioVolume, ISimpleAudioVolume_Release(state->pAudioVolume)); - SAFE_RELEASE(state->pEndpointVolume, IAudioEndpointVolume_Release(state->pEndpointVolume)); - SAFE_RELEASE(state->pSessionControl, IAudioSessionControl_Release(state->pSessionControl)); - SAFE_RELEASE(state->pAudioClient, IAudioClient_Release(state->pAudioClient)); - SAFE_RELEASE(state->pDevice, IMMDevice_Release(state->pDevice)); - SAFE_RELEASE(state->hTask, AvRevertMmThreadCharacteristics(state->hTask)); + SAFE_RELEASE(state->pRenderClient); + SAFE_RELEASE(state->pAudioClock); + SAFE_RELEASE(state->pAudioVolume); + SAFE_RELEASE(state->pEndpointVolume); + SAFE_RELEASE(state->pSessionControl); + SAFE_RELEASE(state->pAudioClient); + SAFE_RELEASE(state->pDevice); + SAFE_DESTROY(state->hTask, AvRevertMmThreadCharacteristics(state->hTask)); MP_DBG(ao, "Thread uninit done\n"); } -- cgit v1.2.3