# include <config.h>
#endif
-#undef _WIN32_WINNT
-#define _WIN32_WINNT 0x600 /* Windows Vista */
#define INITGUID
#define COBJMACROS
#define CONST_VTABLE
#include <stdlib.h>
+#include <math.h>
#include <assert.h>
#include <audiopolicy.h>
#include <mmdeviceapi.h>
#include <vlc_modules.h>
#include "audio_output/mmdevice.h"
+#if (_WIN32_WINNT < 0x600)
+static VOID WINAPI (*InitializeConditionVariable)(PCONDITION_VARIABLE);
+static BOOL WINAPI (*SleepConditionVariableCS)(PCONDITION_VARIABLE,
+ PCRITICAL_SECTION, DWORD);
+static VOID WINAPI (*WakeConditionVariable)(PCONDITION_VARIABLE);
+#define LOOKUP(s) \
+ if (((s) = (void *)GetProcAddress(h, #s)) == NULL) return FALSE
+
+BOOL WINAPI DllMain(HINSTANCE, DWORD, LPVOID); /* avoid warning */
+BOOL WINAPI DllMain(HINSTANCE dll, DWORD reason, LPVOID reserved)
+{
+ (void) dll;
+ (void) reserved;
+
+ switch (reason)
+ {
+ case DLL_PROCESS_ATTACH:
+ {
+ HANDLE h = GetModuleHandle(TEXT("kernel32.dll"));
+ if (unlikely(h == NULL))
+ return FALSE;
+ LOOKUP(InitializeConditionVariable);
+ LOOKUP(SleepConditionVariableCS);
+ LOOKUP(WakeConditionVariable);
+ break;
+ }
+ }
+ return TRUE;
+}
+#endif
+
DEFINE_GUID (GUID_VLC_AUD_OUT, 0x4533f59d, 0x59ee, 0x00c6,
0xad, 0xb2, 0xc6, 0x8b, 0x50, 0x1a, 0x66, 0x55);
+#if !VLC_WINSTORE_APP
static int TryEnterMTA(vlc_object_t *obj)
{
HRESULT hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);
return 0;
}
#define TryEnterMTA(o) TryEnterMTA(VLC_OBJECT(o))
+#endif
static void EnterMTA(void)
{
CoUninitialize();
}
+#if !VLC_WINSTORE_APP
static wchar_t default_device[1] = L"";
+#endif
struct aout_sys_t
{
{
aout_sys_t *sys = aout->sys;
+ vol = vol * vol * vol; /* ISimpleAudioVolume is tapered linearly. */
EnterCriticalSection(&sys->lock);
sys->volume = vol;
WakeConditionVariable(&sys->work);
msg_Dbg(aout, "simple volume changed: %f, muting %sabled", vol,
mute ? "en" : "dis");
- aout_VolumeReport(aout, vol);
+ aout_VolumeReport(aout, cbrtf(vol));
aout_MuteReport(aout, mute == TRUE);
(void) ctx;
return S_OK;
if (flow != eRender)
return S_OK;
- if (role != eConsole) /* FIXME? use eMultimedia instead */
+ if (role != eConsole)
return S_OK;
msg_Dbg(aout, "default device changed: %ls", wid); /* TODO? migrate */
hr = AUDCLNT_E_DEVICE_INVALIDATED;
while (hr == AUDCLNT_E_DEVICE_INVALIDATED)
- { /* Default device selected by policy */
+ { /* Default device selected by policy and with stream routing.
+ * "Do not use eMultimedia" says MSDN. */
msg_Dbg(aout, "using default device");
hr = IMMDeviceEnumerator_GetDefaultAudioEndpoint(it, eRender,
eConsole, &sys->dev);
static int Start(audio_output_t *aout, audio_sample_format_t *restrict fmt)
{
aout_sys_t *sys = aout->sys;
+#if !VLC_WINSTORE_APP
if (sys->dev == NULL)
return -1;
+#endif
aout_stream_t *s = vlc_object_create(aout, sizeof (*s));
if (unlikely(s == NULL))
sys->module = vlc_module_load(s, "aout stream", NULL, false,
aout_stream_Start, s, fmt, &hr);
- if (hr != AUDCLNT_E_DEVICE_INVALIDATED || DeviceSelect(aout, NULL))
+ if (hr != AUDCLNT_E_DEVICE_INVALIDATED
+#if !VLC_WINSTORE_APP
+ || DeviceSelect(aout, NULL)
+#endif
+ )
break;
}
LeaveMTA();
goto error;
}
- DeviceSelect(aout, NULL);
+ EnterCriticalSection(&sys->lock);
+ while (sys->device != NULL)
+ SleepConditionVariableCS(&sys->ready, &sys->lock, INFINITE);
+ LeaveCriticalSection(&sys->lock);
LeaveMTA(); /* Leave MTA after thread has entered MTA */
#else
sys->client = var_InheritAddress(aout, "mmdevice-audioclient");