2 * Copyright 2010 Maarten Lankhorst for CodeWeavers
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 /* This test is for audio capture specific mechanisms
21 * - IAudioClient with eCapture and IAudioCaptureClient
26 #include "wine/test.h"
36 #include "mmdeviceapi.h"
37 #include "audioclient.h"
39 #define NULL_PTR_ERR MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, RPC_X_NULL_REF_POINTER)
41 static IMMDevice
*dev
= NULL
;
43 static void test_uninitialized(IAudioClient
*ac
)
49 HANDLE handle
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
52 hr
= IAudioClient_GetBufferSize(ac
, &num
);
53 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized GetBufferSize call returns %08x\n", hr
);
55 hr
= IAudioClient_GetStreamLatency(ac
, &t1
);
56 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized GetStreamLatency call returns %08x\n", hr
);
58 hr
= IAudioClient_GetCurrentPadding(ac
, &num
);
59 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized GetCurrentPadding call returns %08x\n", hr
);
61 hr
= IAudioClient_Start(ac
);
62 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized Start call returns %08x\n", hr
);
64 hr
= IAudioClient_Stop(ac
);
65 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized Stop call returns %08x\n", hr
);
67 hr
= IAudioClient_Reset(ac
);
68 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized Reset call returns %08x\n", hr
);
70 hr
= IAudioClient_SetEventHandle(ac
, handle
);
71 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized SetEventHandle call returns %08x\n", hr
);
73 hr
= IAudioClient_GetService(ac
, &IID_IAudioStreamVolume
, (void**)&unk
);
74 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Uninitialized GetService call returns %08x\n", hr
);
79 static void test_capture(IAudioClient
*ac
, HANDLE handle
, WAVEFORMATEX
*wfx
)
81 IAudioCaptureClient
*acc
;
86 UINT64 devpos
, qpcpos
;
88 hr
= IAudioClient_GetService(ac
, &IID_IAudioCaptureClient
, (void**)&acc
);
89 ok(hr
== S_OK
, "IAudioClient_GetService(IID_IAudioCaptureClient) returns %08x\n", hr
);
93 hr
= IAudioCaptureClient_GetNextPacketSize(acc
, NULL
);
94 ok(hr
== E_POINTER
, "IAudioCaptureClient_GetNextPacketSize(NULL) returns %08x\n", hr
);
96 ok(WaitForSingleObject(handle
, 2000) == WAIT_OBJECT_0
, "Waiting on event handle failed!\n");
98 /* frames can be 0 if no data is available yet.. */
99 hr
= IAudioCaptureClient_GetNextPacketSize(acc
, &frames
);
100 ok(hr
== S_OK
, "IAudioCaptureClient_GetNextPacketSize returns %08x\n", hr
);
102 data
= (BYTE
*)(DWORD_PTR
)0xdeadbeef;
103 hr
= IAudioCaptureClient_GetBuffer(acc
, &data
, NULL
, NULL
, NULL
, NULL
);
104 ok(hr
== E_POINTER
, "IAudioCaptureClient_GetBuffer(data, NULL, NULL) returns %08x\n", hr
);
105 ok((DWORD_PTR
)data
== 0xdeadbeef, "data is reset to %p\n", data
);
108 hr
= IAudioCaptureClient_GetBuffer(acc
, NULL
, &frames
, NULL
, NULL
, NULL
);
109 ok(hr
== E_POINTER
, "IAudioCaptureClient_GetBuffer(NULL, &frames, NULL) returns %08x\n", hr
);
110 ok(frames
== 0xdeadbeef, "frames is reset to %08x\n", frames
);
113 hr
= IAudioCaptureClient_GetBuffer(acc
, NULL
, NULL
, &flags
, NULL
, NULL
);
114 ok(hr
== E_POINTER
, "IAudioCaptureClient_GetBuffer(NULL, NULL, &flags) returns %08x\n", hr
);
115 ok(flags
== 0xdeadbeef, "flags is reset to %08x\n", flags
);
117 hr
= IAudioCaptureClient_GetBuffer(acc
, &data
, &frames
, NULL
, NULL
, NULL
);
118 ok(hr
== E_POINTER
, "IAudioCaptureClient_GetBuffer(&ata, &frames, NULL) returns %08x\n", hr
);
120 hr
= IAudioCaptureClient_GetBuffer(acc
, &data
, &frames
, &flags
, &devpos
, &qpcpos
);
121 ok(hr
== S_OK
|| hr
== AUDCLNT_S_BUFFER_EMPTY
, "Valid IAudioCaptureClient_GetBuffer returns %08x\n", hr
);
123 ok(frames
, "Amount of frames locked is 0!\n");
124 else if (hr
== AUDCLNT_S_BUFFER_EMPTY
)
125 ok(!frames
, "Amount of frames locked with empty buffer is %u!\n", frames
);
127 ok(0, "GetBuffer returned %08x\n", hr
);
128 trace("Device position is at %u, amount of frames locked: %u\n", (DWORD
)devpos
, frames
);
131 hr
= IAudioCaptureClient_GetBuffer(acc
, &data
, &frames
, &flags
, &devpos
, &qpcpos
);
132 ok(hr
== AUDCLNT_E_OUT_OF_ORDER
, "Out of order IAudioCaptureClient_GetBuffer returns %08x\n", hr
);
135 hr
= IAudioCaptureClient_ReleaseBuffer(acc
, frames
);
136 ok(hr
== S_OK
, "Releasing buffer returns %08x\n", hr
);
139 hr
= IAudioCaptureClient_ReleaseBuffer(acc
, frames
);
140 ok(hr
== AUDCLNT_E_OUT_OF_ORDER
, "Releasing buffer twice returns %08x\n", hr
);
143 IUnknown_Release(acc
);
146 static void test_audioclient(void)
152 WAVEFORMATEX
*pwfx
, *pwfx2
;
153 REFERENCE_TIME t1
, t2
;
156 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
158 ok(hr
== S_OK
, "Activation failed with %08x\n", hr
);
162 handle
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
164 hr
= IAudioClient_QueryInterface(ac
, &IID_IUnknown
, NULL
);
165 ok(hr
== E_POINTER
, "QueryInterface(NULL) returned %08x\n", hr
);
167 unk
= (void*)(LONG_PTR
)0x12345678;
168 hr
= IAudioClient_QueryInterface(ac
, &IID_NULL
, (void**)&unk
);
169 ok(hr
== E_NOINTERFACE
, "QueryInterface(IID_NULL) returned %08x\n", hr
);
170 ok(!unk
, "QueryInterface(IID_NULL) returned non-null pointer %p\n", unk
);
172 hr
= IAudioClient_QueryInterface(ac
, &IID_IUnknown
, (void**)&unk
);
173 ok(hr
== S_OK
, "QueryInterface(IID_IUnknown) returned %08x\n", hr
);
176 ref
= IUnknown_Release(unk
);
177 ok(ref
== 1, "Released count is %u\n", ref
);
180 hr
= IAudioClient_QueryInterface(ac
, &IID_IAudioClient
, (void**)&unk
);
181 ok(hr
== S_OK
, "QueryInterface(IID_IAudioClient) returned %08x\n", hr
);
184 ref
= IUnknown_Release(unk
);
185 ok(ref
== 1, "Released count is %u\n", ref
);
188 hr
= IAudioClient_GetDevicePeriod(ac
, NULL
, NULL
);
189 ok(hr
== E_POINTER
, "Invalid GetDevicePeriod call returns %08x\n", hr
);
191 hr
= IAudioClient_GetDevicePeriod(ac
, &t1
, NULL
);
192 ok(hr
== S_OK
, "Valid GetDevicePeriod call returns %08x\n", hr
);
194 hr
= IAudioClient_GetDevicePeriod(ac
, NULL
, &t2
);
195 ok(hr
== S_OK
, "Valid GetDevicePeriod call returns %08x\n", hr
);
197 hr
= IAudioClient_GetDevicePeriod(ac
, &t1
, &t2
);
198 ok(hr
== S_OK
, "Valid GetDevicePeriod call returns %08x\n", hr
);
199 trace("Returned periods: %u.%04u ms %u.%04u ms\n",
200 (UINT
)(t1
/10000), (UINT
)(t1
% 10000),
201 (UINT
)(t2
/10000), (UINT
)(t2
% 10000));
203 hr
= IAudioClient_GetMixFormat(ac
, NULL
);
204 ok(hr
== E_POINTER
, "GetMixFormat returns %08x\n", hr
);
206 hr
= IAudioClient_GetMixFormat(ac
, &pwfx
);
207 ok(hr
== S_OK
, "Valid GetMixFormat returns %08x\n", hr
);
211 trace("pwfx: %p\n", pwfx
);
212 trace("Tag: %04x\n", pwfx
->wFormatTag
);
213 trace("bits: %u\n", pwfx
->wBitsPerSample
);
214 trace("chan: %u\n", pwfx
->nChannels
);
215 trace("rate: %u\n", pwfx
->nSamplesPerSec
);
216 trace("align: %u\n", pwfx
->nBlockAlign
);
217 trace("extra: %u\n", pwfx
->cbSize
);
218 ok(pwfx
->wFormatTag
== WAVE_FORMAT_EXTENSIBLE
, "wFormatTag is %x\n", pwfx
->wFormatTag
);
219 if (pwfx
->wFormatTag
== WAVE_FORMAT_EXTENSIBLE
)
221 WAVEFORMATEXTENSIBLE
*pwfxe
= (void*)pwfx
;
222 trace("Res: %u\n", pwfxe
->Samples
.wReserved
);
223 trace("Mask: %x\n", pwfxe
->dwChannelMask
);
225 IsEqualGUID(&pwfxe
->SubFormat
, &KSDATAFORMAT_SUBTYPE_PCM
)?"PCM":
226 (IsEqualGUID(&pwfxe
->SubFormat
,
227 &KSDATAFORMAT_SUBTYPE_IEEE_FLOAT
)?"FLOAT":"Other"));
230 hr
= IAudioClient_IsFormatSupported(ac
, AUDCLNT_SHAREMODE_SHARED
, pwfx
, &pwfx2
);
231 ok(hr
== S_OK
, "Valid IsFormatSupported(Shared) call returns %08x\n", hr
);
232 ok(pwfx2
== NULL
, "pwfx2 is non-null\n");
233 CoTaskMemFree(pwfx2
);
235 hr
= IAudioClient_IsFormatSupported(ac
, AUDCLNT_SHAREMODE_SHARED
, NULL
, NULL
);
236 ok(hr
== E_POINTER
, "IsFormatSupported(NULL) call returns %08x\n", hr
);
238 hr
= IAudioClient_IsFormatSupported(ac
, AUDCLNT_SHAREMODE_SHARED
, pwfx
, NULL
);
239 ok(hr
== E_POINTER
, "IsFormatSupported(Shared,NULL) call returns %08x\n", hr
);
241 hr
= IAudioClient_IsFormatSupported(ac
, AUDCLNT_SHAREMODE_EXCLUSIVE
, pwfx
, NULL
);
242 ok(hr
== S_OK
|| hr
== AUDCLNT_E_UNSUPPORTED_FORMAT
, "IsFormatSupported(Exclusive) call returns %08x\n", hr
);
244 hr
= IAudioClient_IsFormatSupported(ac
, AUDCLNT_SHAREMODE_EXCLUSIVE
, pwfx
, &pwfx2
);
245 ok(hr
== S_OK
|| hr
== AUDCLNT_E_UNSUPPORTED_FORMAT
, "IsFormatSupported(Exclusive) call returns %08x\n", hr
);
246 ok(pwfx2
== NULL
, "pwfx2 non-null on exclusive IsFormatSupported\n");
248 hr
= IAudioClient_IsFormatSupported(ac
, 0xffffffff, pwfx
, NULL
);
249 ok(hr
== E_INVALIDARG
, "IsFormatSupported(0xffffffff) call returns %08x\n", hr
);
252 test_uninitialized(ac
);
254 hr
= IAudioClient_Initialize(ac
, 3, 0, 5000000, 0, pwfx
, NULL
);
255 ok(hr
== AUDCLNT_E_NOT_INITIALIZED
, "Initialize with invalid sharemode returns %08x\n", hr
);
257 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
, 0xffffffff, 5000000, 0, pwfx
, NULL
);
258 ok(hr
== E_INVALIDARG
, "Initialize with invalid flags returns %08x\n", hr
);
260 /* It seems that if length > 2s or periodicity != 0 the length is ignored and call succeeds
261 * Since we can only initialize successfully once skip those tests
263 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
, 0, 5000000, 0, NULL
, NULL
);
264 ok(hr
== E_POINTER
, "Initialize with null format returns %08x\n", hr
);
266 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
, AUDCLNT_STREAMFLAGS_EVENTCALLBACK
, 5000000, 0, pwfx
, NULL
);
267 ok(hr
== S_OK
, "Valid Initialize returns %08x\n", hr
);
271 skip("Cannot initialize %08x, remainder of tests is useless\n", hr
);
276 hr
= IAudioClient_GetStreamLatency(ac
, NULL
);
277 ok(hr
== E_POINTER
, "GetStreamLatency(NULL) call returns %08x\n", hr
);
279 hr
= IAudioClient_GetStreamLatency(ac
, &t1
);
280 ok(hr
== S_OK
, "Valid GetStreamLatency call returns %08x\n", hr
);
281 trace("Returned latency: %u.%04u ms\n",
282 (UINT
)(t1
/10000), (UINT
)(t1
% 10000));
284 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
, 0, 5000000, 0, pwfx
, NULL
);
285 ok(hr
== AUDCLNT_E_ALREADY_INITIALIZED
, "Calling Initialize twice returns %08x\n", hr
);
287 hr
= IAudioClient_SetEventHandle(ac
, NULL
);
288 ok(hr
== E_INVALIDARG
, "SetEventHandle(NULL) returns %08x\n", hr
);
290 hr
= IAudioClient_Start(ac
);
291 ok(hr
== AUDCLNT_E_EVENTHANDLE_NOT_SET
, "Start before SetEventHandle returns %08x\n", hr
);
293 hr
= IAudioClient_SetEventHandle(ac
, handle
);
294 ok(hr
== S_OK
, "SetEventHandle returns %08x\n", hr
);
296 hr
= IAudioClient_Reset(ac
);
297 ok(hr
== S_OK
, "Reset on a resetted stream returns %08x\n", hr
);
299 hr
= IAudioClient_Stop(ac
);
300 ok(hr
== S_FALSE
, "Stop on a stopped stream returns %08x\n", hr
);
302 hr
= IAudioClient_Start(ac
);
303 ok(hr
== S_OK
, "Start on a stopped stream returns %08x\n", hr
);
305 test_capture(ac
, handle
, pwfx
);
307 IAudioClient_Release(ac
);
312 static void test_streamvolume(void)
315 IAudioStreamVolume
*asv
;
321 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
323 ok(hr
== S_OK
, "Activation failed with %08x\n", hr
);
327 hr
= IAudioClient_GetMixFormat(ac
, &fmt
);
328 ok(hr
== S_OK
, "GetMixFormat failed: %08x\n", hr
);
330 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
, 0, 5000000,
332 ok(hr
== S_OK
, "Initialize failed: %08x\n", hr
);
336 hr
= IAudioClient_GetService(ac
, &IID_IAudioStreamVolume
, (void**)&asv
);
337 ok(hr
== S_OK
, "GetService failed: %08x\n", hr
);
339 hr
= IAudioStreamVolume_GetChannelCount(asv
, NULL
);
340 ok(hr
== E_POINTER
, "GetChannelCount gave wrong error: %08x\n", hr
);
342 hr
= IAudioStreamVolume_GetChannelCount(asv
, &chans
);
343 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
344 ok(chans
== fmt
->nChannels
, "GetChannelCount gave wrong number of channels: %d\n", chans
);
346 hr
= IAudioStreamVolume_GetChannelVolume(asv
, fmt
->nChannels
, NULL
);
347 ok(hr
== E_POINTER
, "GetChannelCount gave wrong error: %08x\n", hr
);
349 hr
= IAudioStreamVolume_GetChannelVolume(asv
, fmt
->nChannels
, &vol
);
350 ok(hr
== E_INVALIDARG
, "GetChannelCount gave wrong error: %08x\n", hr
);
352 hr
= IAudioStreamVolume_GetChannelVolume(asv
, 0, NULL
);
353 ok(hr
== E_POINTER
, "GetChannelCount gave wrong error: %08x\n", hr
);
355 hr
= IAudioStreamVolume_GetChannelVolume(asv
, 0, &vol
);
356 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
357 ok(vol
== 1.f
, "Channel volume was not 1: %f\n", vol
);
359 hr
= IAudioStreamVolume_SetChannelVolume(asv
, fmt
->nChannels
, -1.f
);
360 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
362 hr
= IAudioStreamVolume_SetChannelVolume(asv
, 0, -1.f
);
363 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
365 hr
= IAudioStreamVolume_SetChannelVolume(asv
, 0, 2.f
);
366 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
368 hr
= IAudioStreamVolume_SetChannelVolume(asv
, 0, 0.2f
);
369 ok(hr
== S_OK
, "SetChannelVolume failed: %08x\n", hr
);
371 hr
= IAudioStreamVolume_GetChannelVolume(asv
, 0, &vol
);
372 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
373 ok(fabsf(vol
- 0.2f
) < 0.05f
, "Channel volume wasn't 0.2: %f\n", vol
);
375 hr
= IAudioStreamVolume_GetAllVolumes(asv
, 0, NULL
);
376 ok(hr
== E_POINTER
, "GetAllVolumes gave wrong error: %08x\n", hr
);
378 hr
= IAudioStreamVolume_GetAllVolumes(asv
, fmt
->nChannels
, NULL
);
379 ok(hr
== E_POINTER
, "GetAllVolumes gave wrong error: %08x\n", hr
);
381 vols
= HeapAlloc(GetProcessHeap(), 0, fmt
->nChannels
* sizeof(float));
382 ok(vols
!= NULL
, "HeapAlloc failed\n");
384 hr
= IAudioStreamVolume_GetAllVolumes(asv
, fmt
->nChannels
- 1, vols
);
385 ok(hr
== E_INVALIDARG
, "GetAllVolumes gave wrong error: %08x\n", hr
);
387 hr
= IAudioStreamVolume_GetAllVolumes(asv
, fmt
->nChannels
, vols
);
388 ok(hr
== S_OK
, "GetAllVolumes failed: %08x\n", hr
);
389 ok(fabsf(vols
[0] - 0.2f
) < 0.05f
, "Channel 0 volume wasn't 0.2: %f\n", vol
);
390 for(i
= 1; i
< fmt
->nChannels
; ++i
)
391 ok(vols
[i
] == 1.f
, "Channel %d volume is not 1: %f\n", i
, vols
[i
]);
393 hr
= IAudioStreamVolume_SetAllVolumes(asv
, 0, NULL
);
394 ok(hr
== E_POINTER
, "SetAllVolumes gave wrong error: %08x\n", hr
);
396 hr
= IAudioStreamVolume_SetAllVolumes(asv
, fmt
->nChannels
, NULL
);
397 ok(hr
== E_POINTER
, "SetAllVolumes gave wrong error: %08x\n", hr
);
399 hr
= IAudioStreamVolume_SetAllVolumes(asv
, fmt
->nChannels
- 1, vols
);
400 ok(hr
== E_INVALIDARG
, "SetAllVolumes gave wrong error: %08x\n", hr
);
402 hr
= IAudioStreamVolume_SetAllVolumes(asv
, fmt
->nChannels
, vols
);
403 ok(hr
== S_OK
, "SetAllVolumes failed: %08x\n", hr
);
405 HeapFree(GetProcessHeap(), 0, vols
);
406 IAudioStreamVolume_Release(asv
);
407 IAudioClient_Release(ac
);
411 static void test_channelvolume(void)
414 IChannelAudioVolume
*acv
;
420 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
422 ok(hr
== S_OK
, "Activation failed with %08x\n", hr
);
426 hr
= IAudioClient_GetMixFormat(ac
, &fmt
);
427 ok(hr
== S_OK
, "GetMixFormat failed: %08x\n", hr
);
429 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
,
430 AUDCLNT_STREAMFLAGS_NOPERSIST
, 5000000, 0, fmt
, NULL
);
431 ok(hr
== S_OK
, "Initialize failed: %08x\n", hr
);
433 hr
= IAudioClient_GetService(ac
, &IID_IChannelAudioVolume
, (void**)&acv
);
434 ok(hr
== S_OK
, "GetService failed: %08x\n", hr
);
438 hr
= IChannelAudioVolume_GetChannelCount(acv
, NULL
);
439 ok(hr
== NULL_PTR_ERR
, "GetChannelCount gave wrong error: %08x\n", hr
);
441 hr
= IChannelAudioVolume_GetChannelCount(acv
, &chans
);
442 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
443 ok(chans
== fmt
->nChannels
, "GetChannelCount gave wrong number of channels: %d\n", chans
);
445 hr
= IChannelAudioVolume_GetChannelVolume(acv
, fmt
->nChannels
, NULL
);
446 ok(hr
== NULL_PTR_ERR
, "GetChannelCount gave wrong error: %08x\n", hr
);
448 hr
= IChannelAudioVolume_GetChannelVolume(acv
, fmt
->nChannels
, &vol
);
449 ok(hr
== E_INVALIDARG
, "GetChannelCount gave wrong error: %08x\n", hr
);
451 hr
= IChannelAudioVolume_GetChannelVolume(acv
, 0, NULL
);
452 ok(hr
== NULL_PTR_ERR
, "GetChannelCount gave wrong error: %08x\n", hr
);
454 hr
= IChannelAudioVolume_GetChannelVolume(acv
, 0, &vol
);
455 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
456 ok(vol
== 1.f
, "Channel volume was not 1: %f\n", vol
);
458 hr
= IChannelAudioVolume_SetChannelVolume(acv
, fmt
->nChannels
, -1.f
, NULL
);
459 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
461 hr
= IChannelAudioVolume_SetChannelVolume(acv
, 0, -1.f
, NULL
);
462 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
464 hr
= IChannelAudioVolume_SetChannelVolume(acv
, 0, 2.f
, NULL
);
465 ok(hr
== E_INVALIDARG
, "SetChannelVolume gave wrong error: %08x\n", hr
);
467 hr
= IChannelAudioVolume_SetChannelVolume(acv
, 0, 0.2f
, NULL
);
468 ok(hr
== S_OK
, "SetChannelVolume failed: %08x\n", hr
);
470 hr
= IChannelAudioVolume_GetChannelVolume(acv
, 0, &vol
);
471 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
472 ok(fabsf(vol
- 0.2f
) < 0.05f
, "Channel volume wasn't 0.2: %f\n", vol
);
474 hr
= IChannelAudioVolume_GetAllVolumes(acv
, 0, NULL
);
475 ok(hr
== NULL_PTR_ERR
, "GetAllVolumes gave wrong error: %08x\n", hr
);
477 hr
= IChannelAudioVolume_GetAllVolumes(acv
, fmt
->nChannels
, NULL
);
478 ok(hr
== NULL_PTR_ERR
, "GetAllVolumes gave wrong error: %08x\n", hr
);
480 vols
= HeapAlloc(GetProcessHeap(), 0, fmt
->nChannels
* sizeof(float));
481 ok(vols
!= NULL
, "HeapAlloc failed\n");
483 hr
= IChannelAudioVolume_GetAllVolumes(acv
, fmt
->nChannels
- 1, vols
);
484 ok(hr
== E_INVALIDARG
, "GetAllVolumes gave wrong error: %08x\n", hr
);
486 hr
= IChannelAudioVolume_GetAllVolumes(acv
, fmt
->nChannels
, vols
);
487 ok(hr
== S_OK
, "GetAllVolumes failed: %08x\n", hr
);
488 ok(fabsf(vols
[0] - 0.2f
) < 0.05f
, "Channel 0 volume wasn't 0.2: %f\n", vol
);
489 for(i
= 1; i
< fmt
->nChannels
; ++i
)
490 ok(vols
[i
] == 1.f
, "Channel %d volume is not 1: %f\n", i
, vols
[i
]);
492 hr
= IChannelAudioVolume_SetAllVolumes(acv
, 0, NULL
, NULL
);
493 ok(hr
== NULL_PTR_ERR
, "SetAllVolumes gave wrong error: %08x\n", hr
);
495 hr
= IChannelAudioVolume_SetAllVolumes(acv
, fmt
->nChannels
, NULL
, NULL
);
496 ok(hr
== NULL_PTR_ERR
, "SetAllVolumes gave wrong error: %08x\n", hr
);
498 hr
= IChannelAudioVolume_SetAllVolumes(acv
, fmt
->nChannels
- 1, vols
, NULL
);
499 ok(hr
== E_INVALIDARG
, "SetAllVolumes gave wrong error: %08x\n", hr
);
501 hr
= IChannelAudioVolume_SetAllVolumes(acv
, fmt
->nChannels
, vols
, NULL
);
502 ok(hr
== S_OK
, "SetAllVolumes failed: %08x\n", hr
);
504 hr
= IChannelAudioVolume_SetChannelVolume(acv
, 0, 1.0f
, NULL
);
505 ok(hr
== S_OK
, "SetChannelVolume failed: %08x\n", hr
);
507 HeapFree(GetProcessHeap(), 0, vols
);
508 IChannelAudioVolume_Release(acv
);
509 IAudioClient_Release(ac
);
513 static void test_simplevolume(void)
516 ISimpleAudioVolume
*sav
;
522 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
524 ok(hr
== S_OK
, "Activation failed with %08x\n", hr
);
528 hr
= IAudioClient_GetMixFormat(ac
, &fmt
);
529 ok(hr
== S_OK
, "GetMixFormat failed: %08x\n", hr
);
531 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
,
532 AUDCLNT_STREAMFLAGS_NOPERSIST
, 5000000, 0, fmt
, NULL
);
533 ok(hr
== S_OK
, "Initialize failed: %08x\n", hr
);
535 hr
= IAudioClient_GetService(ac
, &IID_ISimpleAudioVolume
, (void**)&sav
);
536 ok(hr
== S_OK
, "GetService failed: %08x\n", hr
);
540 hr
= ISimpleAudioVolume_GetMasterVolume(sav
, NULL
);
541 ok(hr
== NULL_PTR_ERR
, "GetMasterVolume gave wrong error: %08x\n", hr
);
543 hr
= ISimpleAudioVolume_GetMasterVolume(sav
, &vol
);
544 ok(hr
== S_OK
, "GetMasterVolume failed: %08x\n", hr
);
545 ok(vol
== 1.f
, "Master volume wasn't 1: %f\n", vol
);
547 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, -1.f
, NULL
);
548 ok(hr
== E_INVALIDARG
, "SetMasterVolume gave wrong error: %08x\n", hr
);
550 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, 2.f
, NULL
);
551 ok(hr
== E_INVALIDARG
, "SetMasterVolume gave wrong error: %08x\n", hr
);
553 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, 0.2f
, NULL
);
554 ok(hr
== S_OK
, "SetMasterVolume failed: %08x\n", hr
);
556 hr
= ISimpleAudioVolume_GetMasterVolume(sav
, &vol
);
557 ok(hr
== S_OK
, "GetMasterVolume failed: %08x\n", hr
);
558 ok(fabsf(vol
- 0.2f
) < 0.05f
, "Master volume wasn't 0.2: %f\n", vol
);
560 hr
= ISimpleAudioVolume_GetMute(sav
, NULL
);
561 ok(hr
== NULL_PTR_ERR
, "GetMute gave wrong error: %08x\n", hr
);
564 hr
= ISimpleAudioVolume_GetMute(sav
, &mute
);
565 ok(hr
== S_OK
, "GetMute failed: %08x\n", hr
);
566 ok(mute
== FALSE
, "Session is already muted\n");
568 hr
= ISimpleAudioVolume_SetMute(sav
, TRUE
, NULL
);
569 ok(hr
== S_OK
, "SetMute failed: %08x\n", hr
);
572 hr
= ISimpleAudioVolume_GetMute(sav
, &mute
);
573 ok(hr
== S_OK
, "GetMute failed: %08x\n", hr
);
574 ok(mute
== TRUE
, "Session should have been muted\n");
576 hr
= ISimpleAudioVolume_GetMasterVolume(sav
, &vol
);
577 ok(hr
== S_OK
, "GetMasterVolume failed: %08x\n", hr
);
578 ok(fabsf(vol
- 0.2f
) < 0.05f
, "Master volume wasn't 0.2: %f\n", vol
);
580 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, 1.f
, NULL
);
581 ok(hr
== S_OK
, "SetMasterVolume failed: %08x\n", hr
);
584 hr
= ISimpleAudioVolume_GetMute(sav
, &mute
);
585 ok(hr
== S_OK
, "GetMute failed: %08x\n", hr
);
586 ok(mute
== TRUE
, "Session should have been muted\n");
588 hr
= ISimpleAudioVolume_SetMute(sav
, FALSE
, NULL
);
589 ok(hr
== S_OK
, "SetMute failed: %08x\n", hr
);
591 ISimpleAudioVolume_Release(sav
);
592 IAudioClient_Release(ac
);
596 static void test_volume_dependence(void)
598 IAudioClient
*ac
, *ac2
;
599 ISimpleAudioVolume
*sav
;
600 IChannelAudioVolume
*cav
;
601 IAudioStreamVolume
*asv
;
608 hr
= CoCreateGuid(&session
);
609 ok(hr
== S_OK
, "CoCreateGuid failed: %08x\n", hr
);
611 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
613 ok(hr
== S_OK
, "Activation failed with %08x\n", hr
);
615 hr
= IAudioClient_GetMixFormat(ac
, &fmt
);
616 ok(hr
== S_OK
, "GetMixFormat failed: %08x\n", hr
);
618 hr
= IAudioClient_Initialize(ac
, AUDCLNT_SHAREMODE_SHARED
,
619 AUDCLNT_STREAMFLAGS_NOPERSIST
, 5000000, 0, fmt
, &session
);
620 ok(hr
== S_OK
, "Initialize failed: %08x\n", hr
);
622 hr
= IAudioClient_GetService(ac
, &IID_ISimpleAudioVolume
, (void**)&sav
);
623 ok(hr
== S_OK
, "GetService (SimpleAudioVolume) failed: %08x\n", hr
);
625 hr
= IAudioClient_GetService(ac
, &IID_IChannelAudioVolume
, (void**)&cav
);
626 ok(hr
== S_OK
, "GetService (ChannelAudioVolme) failed: %08x\n", hr
);
628 hr
= IAudioClient_GetService(ac
, &IID_IAudioStreamVolume
, (void**)&asv
);
629 ok(hr
== S_OK
, "GetService (AudioStreamVolume) failed: %08x\n", hr
);
633 hr
= IAudioStreamVolume_SetChannelVolume(asv
, 0, 0.2f
);
634 ok(hr
== S_OK
, "ASV_SetChannelVolume failed: %08x\n", hr
);
636 hr
= IChannelAudioVolume_SetChannelVolume(cav
, 0, 0.4f
, NULL
);
637 ok(hr
== S_OK
, "CAV_SetChannelVolume failed: %08x\n", hr
);
639 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, 0.6f
, NULL
);
640 ok(hr
== S_OK
, "SAV_SetMasterVolume failed: %08x\n", hr
);
642 hr
= IAudioStreamVolume_GetChannelVolume(asv
, 0, &vol
);
643 ok(hr
== S_OK
, "ASV_GetChannelVolume failed: %08x\n", hr
);
644 ok(fabsf(vol
- 0.2) < 0.05f
, "ASV_GetChannelVolume gave wrong volume: %f\n", vol
);
646 hr
= IChannelAudioVolume_GetChannelVolume(cav
, 0, &vol
);
647 ok(hr
== S_OK
, "CAV_GetChannelVolume failed: %08x\n", hr
);
648 ok(fabsf(vol
- 0.4) < 0.05f
, "CAV_GetChannelVolume gave wrong volume: %f\n", vol
);
650 hr
= ISimpleAudioVolume_GetMasterVolume(sav
, &vol
);
651 ok(hr
== S_OK
, "SAV_GetMasterVolume failed: %08x\n", hr
);
652 ok(fabsf(vol
- 0.6) < 0.05f
, "SAV_GetMasterVolume gave wrong volume: %f\n", vol
);
654 hr
= IMMDevice_Activate(dev
, &IID_IAudioClient
, CLSCTX_INPROC_SERVER
,
657 IChannelAudioVolume
*cav2
;
658 IAudioStreamVolume
*asv2
;
660 hr
= IAudioClient_Initialize(ac2
, AUDCLNT_SHAREMODE_SHARED
,
661 AUDCLNT_STREAMFLAGS_NOPERSIST
, 5000000, 0, fmt
, &session
);
662 ok(hr
== S_OK
, "Initialize failed: %08x\n", hr
);
664 hr
= IAudioClient_GetService(ac2
, &IID_IChannelAudioVolume
, (void**)&cav2
);
665 ok(hr
== S_OK
, "GetService failed: %08x\n", hr
);
667 hr
= IAudioClient_GetService(ac2
, &IID_IAudioStreamVolume
, (void**)&asv2
);
668 ok(hr
== S_OK
, "GetService failed: %08x\n", hr
);
670 hr
= IChannelAudioVolume_GetChannelVolume(cav2
, 0, &vol
);
671 ok(hr
== S_OK
, "CAV_GetChannelVolume failed: %08x\n", hr
);
672 ok(fabsf(vol
- 0.4) < 0.05f
, "CAV_GetChannelVolume gave wrong volume: %f\n", vol
);
674 hr
= IAudioStreamVolume_GetChannelVolume(asv2
, 0, &vol
);
675 ok(hr
== S_OK
, "ASV_GetChannelVolume failed: %08x\n", hr
);
676 ok(vol
== 1.f
, "ASV_GetChannelVolume gave wrong volume: %f\n", vol
);
678 hr
= IChannelAudioVolume_GetChannelCount(cav2
, &nch
);
679 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
680 ok(nch
== fmt
->nChannels
, "Got wrong channel count, expected %u: %u\n", fmt
->nChannels
, nch
);
682 hr
= IAudioStreamVolume_GetChannelCount(asv2
, &nch
);
683 ok(hr
== S_OK
, "GetChannelCount failed: %08x\n", hr
);
684 ok(nch
== fmt
->nChannels
, "Got wrong channel count, expected %u: %u\n", fmt
->nChannels
, nch
);
686 IAudioStreamVolume_Release(asv2
);
687 IChannelAudioVolume_Release(cav2
);
688 IAudioClient_Release(ac2
);
690 skip("Unable to open the same device twice. Skipping session volume control tests\n");
692 hr
= IChannelAudioVolume_SetChannelVolume(cav
, 0, 1.f
, NULL
);
693 ok(hr
== S_OK
, "CAV_SetChannelVolume failed: %08x\n", hr
);
695 hr
= ISimpleAudioVolume_SetMasterVolume(sav
, 1.f
, NULL
);
696 ok(hr
== S_OK
, "SAV_SetMasterVolume failed: %08x\n", hr
);
699 ISimpleAudioVolume_Release(sav
);
700 IChannelAudioVolume_Release(cav
);
701 IAudioStreamVolume_Release(asv
);
702 IAudioClient_Release(ac
);
708 IMMDeviceEnumerator
*mme
= NULL
;
710 CoInitializeEx(NULL
, COINIT_MULTITHREADED
);
711 hr
= CoCreateInstance(&CLSID_MMDeviceEnumerator
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IMMDeviceEnumerator
, (void**)&mme
);
714 skip("mmdevapi not available: 0x%08x\n", hr
);
718 hr
= IMMDeviceEnumerator_GetDefaultAudioEndpoint(mme
, eCapture
, eMultimedia
, &dev
);
719 ok(hr
== S_OK
|| hr
== E_NOTFOUND
, "GetDefaultAudioEndpoint failed: 0x%08x\n", hr
);
720 if (hr
!= S_OK
|| !dev
)
722 if (hr
== E_NOTFOUND
)
723 skip("No sound card available\n");
725 skip("GetDefaultAudioEndpoint returns 0x%08x\n", hr
);
731 test_channelvolume();
733 test_volume_dependence();
735 IMMDevice_Release(dev
);
739 IMMDeviceEnumerator_Release(mme
);