2 * Unit tests for dmusic functions
4 * Copyright (C) 2012 Christian Costa
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
25 #include "wine/test.h"
33 static BOOL
compare_time(REFERENCE_TIME x
, REFERENCE_TIME y
, unsigned int max_diff
)
35 REFERENCE_TIME diff
= x
> y
? x
- y
: y
- x
;
36 return diff
<= max_diff
;
39 static void test_dmusic(void)
41 IDirectMusic
*dmusic
= NULL
;
44 DMUS_PORTCAPS port_caps
;
45 DMUS_PORTPARAMS port_params
;
46 IDirectMusicPort
*port
= NULL
;
48 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic
, (LPVOID
*)&dmusic
);
49 ok(hr
== S_OK
, "Cannot create DirectMusic object (%x)\n", hr
);
51 port_params
.dwSize
= sizeof(port_params
);
52 port_params
.dwValidParams
= DMUS_PORTPARAMS_CHANNELGROUPS
| DMUS_PORTPARAMS_AUDIOCHANNELS
;
53 port_params
.dwChannelGroups
= 1;
54 port_params
.dwAudioChannels
= 2;
56 /* No port can be created before SetDirectSound is called */
57 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, &port_params
, &port
, NULL
);
58 ok(hr
== DMUS_E_DSOUND_NOT_SET
, "IDirectMusic_CreatePort returned: %x\n", hr
);
60 hr
= IDirectMusic_SetDirectSound(dmusic
, NULL
, NULL
);
61 ok(hr
== S_OK
, "IDirectMusic_SetDirectSound returned: %x\n", hr
);
63 /* Check wrong params */
64 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, &port_params
, &port
, (IUnknown
*)dmusic
);
65 ok(hr
== CLASS_E_NOAGGREGATION
, "IDirectMusic_CreatePort returned: %x\n", hr
);
66 hr
= IDirectMusic_CreatePort(dmusic
, NULL
, &port_params
, &port
, NULL
);
67 ok(hr
== E_POINTER
, "IDirectMusic_CreatePort returned: %x\n", hr
);
68 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, NULL
, &port
, NULL
);
69 ok(hr
== E_INVALIDARG
, "IDirectMusic_CreatePort returned: %x\n", hr
);
70 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, &port_params
, NULL
, NULL
);
71 ok(hr
== E_POINTER
, "IDirectMusic_CreatePort returned: %x\n", hr
);
73 /* Test creation of default port with GUID_NULL */
74 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, &port_params
, &port
, NULL
);
75 ok(hr
== S_OK
, "IDirectMusic_CreatePort returned: %x\n", hr
);
77 port_caps
.dwSize
= sizeof(port_caps
);
78 while (IDirectMusic_EnumPort(dmusic
, index
, &port_caps
) == S_OK
)
80 ok(port_caps
.dwSize
== sizeof(port_caps
), "DMUS_PORTCAPS dwSize member is wrong (%u)\n", port_caps
.dwSize
);
81 trace("Port %u:\n", index
);
82 trace(" dwFlags = %x\n", port_caps
.dwFlags
);
83 trace(" guidPort = %s\n", wine_dbgstr_guid(&port_caps
.guidPort
));
84 trace(" dwClass = %u\n", port_caps
.dwClass
);
85 trace(" dwType = %u\n", port_caps
.dwType
);
86 trace(" dwMemorySize = %u\n", port_caps
.dwMemorySize
);
87 trace(" dwMaxChannelGroups = %u\n", port_caps
.dwMaxChannelGroups
);
88 trace(" dwMaxVoices = %u\n", port_caps
.dwMaxVoices
);
89 trace(" dwMaxAudioChannels = %u\n", port_caps
.dwMaxAudioChannels
);
90 trace(" dwEffectFlags = %x\n", port_caps
.dwEffectFlags
);
91 trace(" wszDescription = %s\n", wine_dbgstr_w(port_caps
.wszDescription
));
96 IDirectMusicPort_Release(port
);
97 IDirectMusic_Release(dmusic
);
100 static ULONG
get_refcount(IDirectSound
*iface
)
102 IDirectSound_AddRef(iface
);
103 return IDirectSound_Release(iface
);
106 static void test_setdsound(void)
108 IDirectMusic
*dmusic
;
109 IDirectSound
*dsound
, *dsound2
;
110 DMUS_PORTPARAMS params
;
111 IDirectMusicPort
*port
= NULL
;
115 params
.dwSize
= sizeof(params
);
116 params
.dwValidParams
= DMUS_PORTPARAMS_CHANNELGROUPS
| DMUS_PORTPARAMS_AUDIOCHANNELS
;
117 params
.dwChannelGroups
= 1;
118 params
.dwAudioChannels
= 2;
120 /* Old dsound without SetCooperativeLevel() */
121 hr
= DirectSoundCreate(NULL
, &dsound
, NULL
);
122 if (hr
== DSERR_NODRIVER
) {
126 ok(hr
== S_OK
, "DirectSoundCreate failed: %08x\n", hr
);
127 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic8
,
129 ok(hr
== S_OK
, "DirectMusic create failed: %08x\n", hr
);
130 hr
= IDirectMusic_SetDirectSound(dmusic
, dsound
, NULL
);
131 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
132 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, ¶ms
, &port
, NULL
);
133 ok(hr
== S_OK
, "CreatePort returned: %x\n", hr
);
134 IDirectMusicPort_Release(port
);
135 IDirectMusic_Release(dmusic
);
136 IDirectSound_Release(dsound
);
138 /* dsound ref counting */
139 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic8
,
141 ok(hr
== S_OK
, "DirectMusic create failed: %08x\n", hr
);
142 hr
= DirectSoundCreate8(NULL
, (IDirectSound8
**)&dsound
, NULL
);
143 ok(hr
== S_OK
, "DirectSoundCreate failed: %08x\n", hr
);
144 hr
= IDirectSound_SetCooperativeLevel(dsound
, GetForegroundWindow(), DSSCL_PRIORITY
);
145 ok(hr
== S_OK
, "SetCooperativeLevel failed: %08x\n", hr
);
146 hr
= IDirectMusic_SetDirectSound(dmusic
, dsound
, NULL
);
147 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
148 ref
= get_refcount(dsound
);
149 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
150 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, ¶ms
, &port
, NULL
);
151 ok(hr
== S_OK
, "CreatePort returned: %x\n", hr
);
152 ref
= get_refcount(dsound
);
153 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
154 IDirectMusicPort_AddRef(port
);
155 ref
= IDirectMusicPort_Release(port
);
156 ok(ref
== 1, "port ref count got %d expected 1\n", ref
);
157 hr
= IDirectMusicPort_Activate(port
, TRUE
);
158 ok(hr
== S_OK
, "Port Activate returned: %x\n", hr
);
159 ref
= get_refcount(dsound
);
160 ok(ref
== 4, "dsound ref count got %d expected 4\n", ref
);
161 IDirectMusicPort_AddRef(port
);
162 ref
= IDirectMusicPort_Release(port
);
163 ok(ref
== 1, "port ref count got %d expected 1\n", ref
);
165 /* Releasing dsound from dmusic */
166 hr
= IDirectMusic_SetDirectSound(dmusic
, NULL
, NULL
);
167 ok(hr
== DMUS_E_DSOUND_ALREADY_SET
, "SetDirectSound failed: %08x\n", hr
);
168 hr
= IDirectMusicPort_Activate(port
, FALSE
);
169 ok(hr
== S_OK
, "Port Activate returned: %x\n", hr
);
170 ref
= get_refcount(dsound
);
171 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
172 hr
= IDirectMusic_SetDirectSound(dmusic
, NULL
, NULL
);
173 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
174 ref
= get_refcount(dsound
);
175 ok(ref
== 1, "dsound ref count got %d expected 1\n", ref
);
177 /* Setting the same dsound twice */
178 hr
= IDirectMusic_SetDirectSound(dmusic
, dsound
, NULL
);
179 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
180 ref
= get_refcount(dsound
);
181 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
182 hr
= IDirectMusic_SetDirectSound(dmusic
, dsound
, NULL
);
183 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
184 ref
= get_refcount(dsound
);
185 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
187 /* Replacing one dsound with another */
188 hr
= DirectSoundCreate8(NULL
, (IDirectSound8
**)&dsound2
, NULL
);
189 ok(hr
== S_OK
, "DirectSoundCreate failed: %08x\n", hr
);
190 hr
= IDirectMusic_SetDirectSound(dmusic
, dsound2
, NULL
);
191 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
192 ref
= get_refcount(dsound
);
193 ok(ref
== 1, "dsound ref count got %d expected 1\n", ref
);
194 ref
= get_refcount(dsound2
);
195 ok(ref
== 2, "dsound2 ref count got %d expected 2\n", ref
);
197 /* Replacing the dsound in the port */
198 hr
= IDirectMusicPort_SetDirectSound(port
, dsound
, NULL
);
199 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
200 ref
= get_refcount(dsound
);
201 ok(ref
== 2, "dsound ref count got %d expected 2\n", ref
);
202 ref
= get_refcount(dsound2
);
203 ok(ref
== 2, "dsound2 ref count got %d expected 2\n", ref
);
204 /* Setting the dsound again on the port will mess with the parent dmusic */
205 hr
= IDirectMusicPort_SetDirectSound(port
, dsound
, NULL
);
206 ok(hr
== S_OK
, "SetDirectSound failed: %08x\n", hr
);
207 ref
= get_refcount(dsound
);
208 ok(ref
== 3, "dsound ref count got %d expected 3\n", ref
);
209 ref
= get_refcount(dsound2
);
210 ok(ref
== 1, "dsound2 ref count got %d expected 1\n", ref
);
211 IDirectSound_AddRef(dsound2
); /* Crash prevention */
212 hr
= IDirectMusicPort_Activate(port
, TRUE
);
213 ok(hr
== S_OK
, "Activate returned: %x\n", hr
);
214 ref
= get_refcount(dsound
);
215 ok(ref
== 4, "dsound ref count got %d expected 4\n", ref
);
216 ref
= get_refcount(dsound2
);
217 ok(ref
== 2, "dsound2 ref count got %d expected 2\n", ref
);
218 hr
= IDirectMusicPort_Activate(port
, TRUE
);
219 ok(hr
== S_FALSE
, "Activate returned: %x\n", hr
);
220 ref
= get_refcount(dsound
);
221 ok(ref
== 4, "dsound ref count got %d expected 4\n", ref
);
222 ref
= get_refcount(dsound2
);
223 ok(ref
== 2, "dsound2 ref count got %d expected 2\n", ref
);
225 /* Deactivating the port messes with the dsound refcount in the parent dmusic */
226 hr
= IDirectMusicPort_Activate(port
, FALSE
);
227 ok(hr
== S_OK
, "Port Activate returned: %x\n", hr
);
228 ref
= get_refcount(dsound
);
229 ok(ref
== 3, "dsound ref count got %d expected 3\n", ref
);
230 ref
= get_refcount(dsound2
);
231 ok(ref
== 1, "dsound2 ref count got %d expected 1\n", ref
);
232 hr
= IDirectMusicPort_Activate(port
, FALSE
);
233 ok(hr
== S_FALSE
, "Port Activate returned: %x\n", hr
);
234 ref
= get_refcount(dsound
);
235 ok(ref
== 3, "dsound ref count got %d expected 3\n", ref
);
236 ref
= get_refcount(dsound2
);
237 ok(ref
== 1, "dsound2 ref count got %d expected 1\n", ref
);
239 IDirectMusicPort_Release(port
);
240 IDirectMusic_Release(dmusic
);
241 while (IDirectSound_Release(dsound
));
244 static void test_dmbuffer(void)
246 IDirectMusic
*dmusic
;
247 IDirectMusicBuffer
*dmbuffer
= NULL
;
249 DMUS_BUFFERDESC desc
;
256 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic
, (LPVOID
*)&dmusic
);
257 ok(hr
== S_OK
, "Cannot create DirectMusic object (%x)\n", hr
);
259 desc
.dwSize
= sizeof(DMUS_BUFFERDESC
);
261 desc
.cbBuffer
= 1023;
262 memcpy(&desc
.guidBufferFormat
, &GUID_NULL
, sizeof(GUID
));
264 hr
= IDirectMusic_CreateMusicBuffer(dmusic
, &desc
, &dmbuffer
, NULL
);
265 ok(hr
== S_OK
, "IDirectMusic_CreateMusicBuffer return %x\n", hr
);
267 hr
= IDirectMusicBuffer_GetBufferFormat(dmbuffer
, &format
);
268 ok(hr
== S_OK
, "IDirectMusicBuffer_GetBufferFormat returned %x\n", hr
);
269 ok(IsEqualGUID(&format
, &KSDATAFORMAT_SUBTYPE_MIDI
), "Wrong format returned %s\n", wine_dbgstr_guid(&format
));
270 hr
= IDirectMusicBuffer_GetMaxBytes(dmbuffer
, &size
);
271 ok(hr
== S_OK
, "IDirectMusicBuffer_GetMaxBytes returned %x\n", hr
);
272 ok(size
== 1024, "Buffer size is %u instead of 1024\n", size
);
274 hr
= IDirectMusicBuffer_GetStartTime(dmbuffer
, &time
);
275 ok(hr
== DMUS_E_BUFFER_EMPTY
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
276 hr
= IDirectMusicBuffer_SetStartTime(dmbuffer
, 10);
277 ok(hr
== S_OK
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
278 hr
= IDirectMusicBuffer_GetStartTime(dmbuffer
, &time
);
279 ok(hr
== DMUS_E_BUFFER_EMPTY
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
281 hr
= IDirectMusicBuffer_PackStructured(dmbuffer
, 20, 0, 0);
282 ok(hr
== DMUS_E_INVALID_EVENT
, "IDirectMusicBuffer_PackStructured returned %x\n", hr
);
283 hr
= IDirectMusicBuffer_PackStructured(dmbuffer
, 20, 0, 0x000090); /* note on : chan 0, note 0 & vel 0 */
284 ok(hr
== S_OK
, "IDirectMusicBuffer_PackStructured returned %x\n", hr
);
285 hr
= IDirectMusicBuffer_PackStructured(dmbuffer
, 30, 0, 0x000080); /* note off : chan 0, note 0 & vel 0 */
286 ok(hr
== S_OK
, "IDirectMusicBuffer_PackStructured returned %x\n", hr
);
287 hr
= IDirectMusicBuffer_GetUsedBytes(dmbuffer
, &bytes
);
288 ok(hr
== S_OK
, "IDirectMusicBuffer_GetUsedBytes returned %x\n", hr
);
289 ok(bytes
== 48, "Buffer size is %u instead of 48\n", bytes
);
291 hr
= IDirectMusicBuffer_GetStartTime(dmbuffer
, &time
);
292 ok(hr
== S_OK
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
293 ok(time
== 20, "Buffer start time is wrong\n");
294 hr
= IDirectMusicBuffer_SetStartTime(dmbuffer
, 40);
295 ok(hr
== S_OK
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
296 hr
= IDirectMusicBuffer_GetStartTime(dmbuffer
, &time
);
297 ok(hr
== S_OK
, "IDirectMusicBuffer_GetStartTime returned %x\n", hr
);
298 ok(time
== 40, "Buffer start time is wrong\n");
300 hr
= IDirectMusicBuffer_GetRawBufferPtr(dmbuffer
, &data
);
301 ok(hr
== S_OK
, "IDirectMusicBuffer_GetRawBufferPtr returned %x\n", hr
);
304 DMUS_EVENTHEADER
* header
;
307 /* Check message 1 */
308 header
= (DMUS_EVENTHEADER
*)data
;
309 data
+= sizeof(DMUS_EVENTHEADER
);
310 ok(header
->cbEvent
== 3, "cbEvent is %u instead of 3\n", header
->cbEvent
);
311 ok(header
->dwChannelGroup
== 0, "dwChannelGroup is %u instead of 0\n", header
->dwChannelGroup
);
312 ok(header
->rtDelta
== 0, "rtDelta is %s instead of 0\n", wine_dbgstr_longlong(header
->rtDelta
));
313 ok(header
->dwFlags
== DMUS_EVENT_STRUCTURED
, "dwFlags is %x instead of %x\n", header
->dwFlags
, DMUS_EVENT_STRUCTURED
);
314 message
= *(DWORD
*)data
& 0xffffff; /* Only 3 bytes are relevant */
315 data
+= sizeof(DWORD
);
316 ok(message
== 0x000090, "Message is %0x instead of 0x000090\n", message
);
318 /* Check message 2 */
319 header
= (DMUS_EVENTHEADER
*)data
;
320 data
+= sizeof(DMUS_EVENTHEADER
);
321 ok(header
->cbEvent
== 3, "cbEvent is %u instead of 3\n", header
->cbEvent
);
322 ok(header
->dwChannelGroup
== 0, "dwChannelGroup is %u instead of 0\n", header
->dwChannelGroup
);
323 ok(header
->rtDelta
== 10, "rtDelta is %s instead of 0\n", wine_dbgstr_longlong(header
->rtDelta
));
324 ok(header
->dwFlags
== DMUS_EVENT_STRUCTURED
, "dwFlags is %x instead of %x\n", header
->dwFlags
, DMUS_EVENT_STRUCTURED
);
325 message
= *(DWORD
*)data
& 0xffffff; /* Only 3 bytes are relevant */
326 ok(message
== 0x000080, "Message 2 is %0x instead of 0x000080\n", message
);
330 IDirectMusicBuffer_Release(dmbuffer
);
331 IDirectMusic_Release(dmusic
);
334 static void test_COM(void)
336 IDirectMusic8
*dm8
= (IDirectMusic8
*)0xdeadbeef;
342 /* COM aggregation */
343 hr
= CoCreateInstance(&CLSID_DirectMusic
, (IUnknown
*)0xdeadbeef, CLSCTX_INPROC_SERVER
, &IID_IUnknown
,
345 ok(hr
== CLASS_E_NOAGGREGATION
,
346 "DirectMusic8 create failed: %08x, expected CLASS_E_NOAGGREGATION\n", hr
);
347 ok(!dm8
, "dm8 = %p\n", dm8
);
350 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusicObject
,
352 ok(hr
== E_NOINTERFACE
, "DirectMusic8 create failed: %08x, expected E_NOINTERFACE\n", hr
);
354 /* Same refcount for DirectMusic and DirectMusic8 */
355 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic8
,
357 if (hr
== E_NOINTERFACE
)
359 win_skip("DirectMusic too old (no IDirectMusic8)\n");
362 ok(hr
== S_OK
, "DirectMusic8 create failed: %08x, expected S_OK\n", hr
);
363 refcount
= IDirectMusic8_AddRef(dm8
);
364 ok(refcount
== 2, "refcount == %u, expected 2\n", refcount
);
366 hr
= IDirectMusic8_QueryInterface(dm8
, &IID_IDirectMusic
, (void**)&dm
);
367 ok(hr
== S_OK
, "QueryInterface for IID_IDirectMusic failed: %08x\n", hr
);
368 refcount
= IDirectMusic_AddRef(dm
);
369 ok(refcount
== 4, "refcount == %u, expected 4\n", refcount
);
370 IDirectMusic_Release(dm
);
372 hr
= IDirectMusic8_QueryInterface(dm8
, &IID_IUnknown
, (void**)&unk
);
373 ok(hr
== S_OK
, "QueryInterface for IID_IUnknown failed: %08x\n", hr
);
374 refcount
= IUnknown_AddRef(unk
);
375 ok(refcount
== 5, "refcount == %u, expected 5\n", refcount
);
376 refcount
= IUnknown_Release(unk
);
378 ok(refcount
== 4, "refcount == %u, expected 4\n", refcount
);
379 while (IDirectMusic8_Release(dm8
));
382 static void test_COM_dmcoll(void)
384 IDirectMusicCollection
*dmc
= (IDirectMusicCollection
*)0xdeadbeef;
385 IDirectMusicObject
*dmo
;
391 /* COM aggregation */
392 hr
= CoCreateInstance(&CLSID_DirectMusicCollection
, (IUnknown
*)0xdeadbeef, CLSCTX_INPROC_SERVER
,
393 &IID_IUnknown
, (void**)&dmc
);
394 ok(hr
== CLASS_E_NOAGGREGATION
,
395 "DirectMusicCollection create failed: %08x, expected CLASS_E_NOAGGREGATION\n", hr
);
396 ok(!dmc
, "dmc = %p\n", dmc
);
399 hr
= CoCreateInstance(&CLSID_DirectMusicCollection
, NULL
, CLSCTX_INPROC_SERVER
,
400 &IID_IClassFactory
, (void**)&dmc
);
401 ok(hr
== E_NOINTERFACE
, "DirectMusicCollection create failed: %08x, expected E_NOINTERFACE\n", hr
);
403 /* Same refcount for all DirectMusicCollection interfaces */
404 hr
= CoCreateInstance(&CLSID_DirectMusicCollection
, NULL
, CLSCTX_INPROC_SERVER
,
405 &IID_IDirectMusicCollection
, (void**)&dmc
);
406 ok(hr
== S_OK
, "DirectMusicCollection create failed: %08x, expected S_OK\n", hr
);
407 refcount
= IDirectMusicCollection_AddRef(dmc
);
408 ok(refcount
== 2, "refcount == %u, expected 2\n", refcount
);
410 hr
= IDirectMusicCollection_QueryInterface(dmc
, &IID_IDirectMusicObject
, (void**)&dmo
);
411 ok(hr
== S_OK
, "QueryInterface for IID_IDirectMusicObject failed: %08x\n", hr
);
412 refcount
= IDirectMusicObject_AddRef(dmo
);
413 ok(refcount
== 4, "refcount == %u, expected 4\n", refcount
);
414 refcount
= IDirectMusicObject_Release(dmo
);
416 hr
= IDirectMusicCollection_QueryInterface(dmc
, &IID_IPersistStream
, (void**)&ps
);
417 ok(hr
== S_OK
, "QueryInterface for IID_IPersistStream failed: %08x\n", hr
);
418 refcount
= IPersistStream_AddRef(ps
);
419 ok(refcount
== 5, "refcount == %u, expected 5\n", refcount
);
420 refcount
= IPersistStream_Release(ps
);
422 hr
= IDirectMusicCollection_QueryInterface(dmc
, &IID_IUnknown
, (void**)&unk
);
423 ok(hr
== S_OK
, "QueryInterface for IID_IUnknown failed: %08x\n", hr
);
424 refcount
= IUnknown_AddRef(unk
);
425 ok(refcount
== 6, "refcount == %u, expected 6\n", refcount
);
426 refcount
= IUnknown_Release(unk
);
428 ok(refcount
== 5, "refcount == %u, expected 5\n", refcount
);
429 while (IDirectMusicCollection_Release(dmc
));
432 static void test_dmcoll(void)
434 IDirectMusicCollection
*dmc
;
435 IDirectMusicObject
*dmo
;
437 DMUS_OBJECTDESC desc
;
442 hr
= CoCreateInstance(&CLSID_DirectMusicCollection
, NULL
, CLSCTX_INPROC_SERVER
,
443 &IID_IDirectMusicCollection
, (void**)&dmc
);
444 ok(hr
== S_OK
, "DirectMusicCollection create failed: %08x, expected S_OK\n", hr
);
446 /* IDirectMusicObject */
447 hr
= IDirectMusicCollection_QueryInterface(dmc
, &IID_IDirectMusicObject
, (void**)&dmo
);
448 ok(hr
== S_OK
, "QueryInterface for IID_IDirectMusicObject failed: %08x\n", hr
);
449 hr
= IDirectMusicObject_GetDescriptor(dmo
, NULL
);
450 ok(hr
== E_POINTER
, "IDirectMusicObject_GetDescriptor: expected E_POINTER, got %08x\n", hr
);
451 hr
= IDirectMusicObject_SetDescriptor(dmo
, NULL
);
452 ok(hr
== E_POINTER
, "IDirectMusicObject_SetDescriptor: expected E_POINTER, got %08x\n", hr
);
453 ZeroMemory(&desc
, sizeof(desc
));
454 hr
= IDirectMusicObject_GetDescriptor(dmo
, &desc
);
455 ok(hr
== S_OK
, "IDirectMusicObject_GetDescriptor failed: %08x\n", hr
);
456 ok(desc
.dwValidData
== DMUS_OBJ_CLASS
,
457 "Fresh object has more valid data (%08x) than DMUS_OBJ_CLASS\n", desc
.dwValidData
);
458 /* DMUS_OBJ_CLASS is immutable */
459 desc
.dwValidData
= DMUS_OBJ_CLASS
;
460 hr
= IDirectMusicObject_SetDescriptor(dmo
, &desc
);
461 ok(hr
== S_FALSE
, "IDirectMusicObject_SetDescriptor failed: %08x\n", hr
);
462 ok(!desc
.dwValidData
, "dwValidData wasn't cleared: %08x\n", desc
.dwValidData
);
463 desc
.dwValidData
= DMUS_OBJ_CLASS
;
464 desc
.guidClass
= CLSID_DirectMusicSegment
;
465 hr
= IDirectMusicObject_SetDescriptor(dmo
, &desc
);
466 ok(hr
== S_FALSE
&& !desc
.dwValidData
, "IDirectMusicObject_SetDescriptor failed: %08x\n", hr
);
467 hr
= IDirectMusicObject_GetDescriptor(dmo
, &desc
);
468 ok(hr
== S_OK
, "IDirectMusicObject_GetDescriptor failed: %08x\n", hr
);
469 ok(IsEqualGUID(&desc
.guidClass
, &CLSID_DirectMusicCollection
),
470 "guidClass changed, should be CLSID_DirectMusicCollection\n");
472 /* Unimplemented IPersistStream methods*/
473 hr
= IDirectMusicCollection_QueryInterface(dmc
, &IID_IPersistStream
, (void**)&ps
);
474 ok(hr
== S_OK
, "QueryInterface for IID_IPersistStream failed: %08x\n", hr
);
475 hr
= IPersistStream_GetClassID(ps
, &class);
476 ok(hr
== E_NOTIMPL
, "IPersistStream_GetClassID failed: %08x\n", hr
);
477 hr
= IPersistStream_IsDirty(ps
);
478 ok(hr
== S_FALSE
, "IPersistStream_IsDirty failed: %08x\n", hr
);
479 hr
= IPersistStream_GetSizeMax(ps
, &size
);
480 ok(hr
== E_NOTIMPL
, "IPersistStream_GetSizeMax failed: %08x\n", hr
);
481 hr
= IPersistStream_Save(ps
, NULL
, TRUE
);
482 ok(hr
== E_NOTIMPL
, "IPersistStream_Save failed: %08x\n", hr
);
484 while (IDirectMusicCollection_Release(dmc
));
487 static BOOL
missing_dmusic(void)
490 HRESULT hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic
,
493 if (hr
== S_OK
&& dm
)
495 IDirectMusic_Release(dm
);
501 static void test_COM_synthport(void)
503 IDirectMusic
*dmusic
= NULL
;
504 IDirectMusicPort
*port
= NULL
;
505 IDirectMusicPortDownload
*dmpd
;
506 IDirectMusicThru
*dmt
;
508 IReferenceClock
*clock
;
510 DMUS_PORTPARAMS port_params
;
514 /* Create a IDirectMusicPort */
515 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic
,
517 ok(hr
== S_OK
, "Cannot create DirectMusic object (%x)\n", hr
);
518 port_params
.dwSize
= sizeof(port_params
);
519 port_params
.dwValidParams
= DMUS_PORTPARAMS_CHANNELGROUPS
| DMUS_PORTPARAMS_AUDIOCHANNELS
;
520 port_params
.dwChannelGroups
= 1;
521 port_params
.dwAudioChannels
= 2;
522 hr
= IDirectMusic_SetDirectSound(dmusic
, NULL
, NULL
);
523 ok(hr
== S_OK
, "IDirectMusic_SetDirectSound returned: %x\n", hr
);
524 hr
= IDirectMusic_CreatePort(dmusic
, &GUID_NULL
, &port_params
, &port
, NULL
);
525 ok(hr
== S_OK
, "IDirectMusic_CreatePort returned: %x\n", hr
);
527 /* Same refcount for all DirectMusicPort interfaces */
528 refcount
= IDirectMusicPort_AddRef(port
);
529 ok(refcount
== 2, "refcount == %u, expected 2\n", refcount
);
531 hr
= IDirectMusicPort_QueryInterface(port
, &IID_IDirectMusicPortDownload
, (void**)&dmpd
);
532 ok(hr
== S_OK
, "QueryInterface for IID_IDirectMusicPortDownload failed: %08x\n", hr
);
533 refcount
= IDirectMusicPortDownload_AddRef(dmpd
);
534 ok(refcount
== 4, "refcount == %u, expected 4\n", refcount
);
535 IDirectMusicPortDownload_Release(dmpd
);
537 hr
= IDirectMusicPort_QueryInterface(port
, &IID_IKsControl
, (void**)&iksc
);
538 ok(hr
== S_OK
, "QueryInterface for IID_IKsControl failed: %08x\n", hr
);
539 refcount
= IKsControl_AddRef(iksc
);
540 ok(refcount
== 5, "refcount == %u, expected 5\n", refcount
);
541 IKsControl_Release(iksc
);
543 hr
= IDirectMusicPort_QueryInterface(port
, &IID_IUnknown
, (void**)&unk
);
544 ok(hr
== S_OK
, "QueryInterface for IID_IUnknown failed: %08x\n", hr
);
545 refcount
= IUnknown_AddRef(unk
);
546 ok(refcount
== 6, "refcount == %u, expected 6\n", refcount
);
547 IUnknown_Release(unk
);
549 /* Unsupported interface */
550 hr
= IDirectMusicPort_QueryInterface(port
, &IID_IDirectMusicThru
, (void**)&dmt
);
551 todo_wine
ok(hr
== E_NOINTERFACE
, "QueryInterface for IID_IDirectMusicThru failed: %08x\n", hr
);
552 hr
= IDirectMusicPort_QueryInterface(port
, &IID_IReferenceClock
, (void**)&clock
);
553 ok(hr
== E_NOINTERFACE
, "QueryInterface for IID_IReferenceClock failed: %08x\n", hr
);
555 while (IDirectMusicPort_Release(port
));
564 #define CHUNK_HDR_SIZE (sizeof(FOURCC) + sizeof(DWORD))
566 /* Generate a RIFF file format stream from an array of FOURCC ids.
567 RIFF and LIST need to be followed by the form type respectively list type,
568 followed by the chunks of the list and terminated with 0. */
569 static IStream
*gen_riff_stream(const FOURCC
*ids
)
571 static const LARGE_INTEGER zero
;
573 DWORD
*sizes
[4]; /* Stack for the sizes of RIFF and LIST chunks */
580 ck
= (struct chunk
*)p
;
584 *sizes
[level
] = p
- (char *)sizes
[level
] - sizeof(DWORD
);
590 sizes
[level
] = &ck
->size
;
594 case DMUS_FOURCC_GUID_CHUNK
:
595 ck
->size
= sizeof(GUID_NULL
);
597 memcpy(p
, &GUID_NULL
, sizeof(GUID_NULL
));
600 case DMUS_FOURCC_VERSION_CHUNK
:
602 DMUS_VERSION ver
= {5, 8};
604 ck
->size
= sizeof(ver
);
606 memcpy(p
, &ver
, sizeof(ver
));
610 case mmioFOURCC('I','N','A','M'):
614 p
+= ck
->size
+ 1; /* WORD aligned */
618 /* Just convert the FOURCC id to a WCHAR string */
621 ck
->size
= 5 * sizeof(WCHAR
);
624 s
[0] = (char)(ck
->id
);
625 s
[1] = (char)(ck
->id
>> 8);
626 s
[2] = (char)(ck
->id
>> 16);
627 s
[3] = (char)(ck
->id
>> 24);
632 } while (level
>= 0);
634 ck
= (struct chunk
*)riff
;
635 CreateStreamOnHGlobal(NULL
, TRUE
, &stream
);
636 IStream_Write(stream
, riff
, ck
->size
+ CHUNK_HDR_SIZE
, NULL
);
637 IStream_Seek(stream
, zero
, STREAM_SEEK_SET
, NULL
);
642 static void test_parsedescriptor(void)
644 IDirectMusicObject
*dmo
;
646 DMUS_OBJECTDESC desc
= {0};
648 const FOURCC alldesc
[] =
650 FOURCC_RIFF
, FOURCC_DLS
, DMUS_FOURCC_CATEGORY_CHUNK
, FOURCC_LIST
,
651 DMUS_FOURCC_UNFO_LIST
, DMUS_FOURCC_UNAM_CHUNK
, DMUS_FOURCC_UCOP_CHUNK
,
652 DMUS_FOURCC_UCMT_CHUNK
, DMUS_FOURCC_USBJ_CHUNK
, 0, DMUS_FOURCC_VERSION_CHUNK
,
653 DMUS_FOURCC_GUID_CHUNK
, 0
655 const FOURCC dupes
[] =
657 FOURCC_RIFF
, FOURCC_DLS
, DMUS_FOURCC_CATEGORY_CHUNK
, DMUS_FOURCC_CATEGORY_CHUNK
,
658 DMUS_FOURCC_VERSION_CHUNK
, DMUS_FOURCC_VERSION_CHUNK
, DMUS_FOURCC_GUID_CHUNK
,
659 DMUS_FOURCC_GUID_CHUNK
, FOURCC_LIST
, DMUS_FOURCC_INFO_LIST
, mmioFOURCC('I','N','A','M'), 0,
660 FOURCC_LIST
, DMUS_FOURCC_INFO_LIST
, mmioFOURCC('I','N','A','M'), 0, 0
662 FOURCC empty
[] = {FOURCC_RIFF
, FOURCC_DLS
, 0};
665 FOURCC_RIFF
, FOURCC_DLS
, FOURCC_LIST
, DMUS_FOURCC_UNFO_LIST
,
666 mmioFOURCC('I','N','A','M'), 0, 0
669 hr
= CoCreateInstance(&CLSID_DirectMusicCollection
, NULL
, CLSCTX_INPROC_SERVER
,
670 &IID_IDirectMusicObject
, (void **)&dmo
);
671 ok(hr
== S_OK
, "DirectMusicCollection create failed: %08x, expected S_OK\n", hr
);
674 hr
= IDirectMusicObject_GetDescriptor(dmo
, &desc
);
675 ok(hr
== S_OK
, "GetDescriptor failed: %08x, expected S_OK\n", hr
);
676 ok(desc
.dwValidData
== DMUS_OBJ_CLASS
, "Got valid data %#x, expected DMUS_OBJ_OBJECT\n",
678 ok(IsEqualGUID(&desc
.guidClass
, &CLSID_DirectMusicCollection
),
679 "Got class guid %s, expected CLSID_DirectMusicCollection\n",
680 wine_dbgstr_guid(&desc
.guidClass
));
682 /* Empty RIFF stream */
683 stream
= gen_riff_stream(empty
);
684 memset(&desc
, 0, sizeof(desc
));
685 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
686 ok(hr
== S_OK
, "ParseDescriptor failed: %08x, expected S_OK\n", hr
);
687 ok(desc
.dwValidData
== DMUS_OBJ_CLASS
, "Got valid data %#x, expected DMUS_OBJ_CLASS\n",
689 ok(IsEqualGUID(&desc
.guidClass
, &CLSID_DirectMusicCollection
),
690 "Got class guid %s, expected CLSID_DirectMusicCollection\n",
691 wine_dbgstr_guid(&desc
.guidClass
));
692 IStream_Release(stream
);
695 memset(&desc
, 0, sizeof(desc
));
696 hr
= IDirectMusicObject_ParseDescriptor(dmo
, NULL
, &desc
);
697 ok(hr
== E_POINTER
, "ParseDescriptor failed: %08x, expected E_POINTER\n", hr
);
698 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, NULL
);
699 ok(hr
== E_POINTER
, "ParseDescriptor failed: %08x, expected E_POINTER\n", hr
);
702 empty
[1] = DMUS_FOURCC_CONTAINER_FORM
;
703 stream
= gen_riff_stream(empty
);
704 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
705 ok(hr
== DMUS_E_NOTADLSCOL
, "ParseDescriptor failed: %08x, expected DMUS_E_NOTADLSCOL\n", hr
);
706 IStream_Release(stream
);
708 /* All desc chunks */
709 stream
= gen_riff_stream(alldesc
);
710 memset(&desc
, 0, sizeof(desc
));
711 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
712 ok(hr
== S_OK
, "ParseDescriptor failed: %08x, expected S_OK\n", hr
);
713 ok(desc
.dwValidData
== (DMUS_OBJ_CLASS
| DMUS_OBJ_VERSION
),
714 "Got valid data %#x, expected DMUS_OBJ_CLASS | DMUS_OBJ_VERSION\n", desc
.dwValidData
);
715 ok(IsEqualGUID(&desc
.guidClass
, &CLSID_DirectMusicCollection
),
716 "Got class guid %s, expected CLSID_DirectMusicCollection\n",
717 wine_dbgstr_guid(&desc
.guidClass
));
718 ok(IsEqualGUID(&desc
.guidObject
, &GUID_NULL
), "Got object guid %s, expected GUID_NULL\n",
719 wine_dbgstr_guid(&desc
.guidClass
));
720 ok(desc
.vVersion
.dwVersionMS
== 5 && desc
.vVersion
.dwVersionLS
== 8,
721 "Got version %u.%u, expected 5.8\n", desc
.vVersion
.dwVersionMS
,
722 desc
.vVersion
.dwVersionLS
);
723 IStream_Release(stream
);
725 /* UNFO list with INAM */
726 inam
[3] = DMUS_FOURCC_UNFO_LIST
;
727 stream
= gen_riff_stream(inam
);
728 memset(&desc
, 0, sizeof(desc
));
729 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
730 ok(hr
== S_OK
, "ParseDescriptor failed: %08x, expected S_OK\n", hr
);
731 ok(desc
.dwValidData
== DMUS_OBJ_CLASS
, "Got valid data %#x, expected DMUS_OBJ_CLASS\n",
733 IStream_Release(stream
);
735 /* INFO list with INAM */
736 inam
[3] = DMUS_FOURCC_INFO_LIST
;
737 stream
= gen_riff_stream(inam
);
738 memset(&desc
, 0, sizeof(desc
));
739 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
740 ok(hr
== S_OK
, "ParseDescriptor failed: %08x, expected S_OK\n", hr
);
741 ok(desc
.dwValidData
== (DMUS_OBJ_CLASS
| DMUS_OBJ_NAME
),
742 "Got valid data %#x, expected DMUS_OBJ_CLASS | DMUS_OBJ_NAME\n", desc
.dwValidData
);
743 ok(!lstrcmpW(desc
.wszName
, L
"INAM"), "Got name '%s', expected 'INAM'\n",
744 wine_dbgstr_w(desc
.wszName
));
745 IStream_Release(stream
);
747 /* Duplicated chunks */
748 stream
= gen_riff_stream(dupes
);
749 memset(&desc
, 0, sizeof(desc
));
750 hr
= IDirectMusicObject_ParseDescriptor(dmo
, stream
, &desc
);
751 ok(hr
== S_OK
, "ParseDescriptor failed: %08x, expected S_OK\n", hr
);
752 ok(desc
.dwValidData
== (DMUS_OBJ_CLASS
| DMUS_OBJ_NAME
| DMUS_OBJ_VERSION
),
753 "Got valid data %#x, expected DMUS_OBJ_CLASS | DMUS_OBJ_NAME | DMUS_OBJ_VERSION\n",
755 ok(!lstrcmpW(desc
.wszName
, L
"INAM"), "Got name '%s', expected 'INAM'\n",
756 wine_dbgstr_w(desc
.wszName
));
757 IStream_Release(stream
);
759 IDirectMusicObject_Release(dmo
);
762 static void test_master_clock(void)
764 static const GUID guid_system_clock
= {0x58d58419, 0x71b4, 0x11d1, {0xa7, 0x4c, 0x00, 0x00, 0xf8, 0x75, 0xac, 0x12}};
765 static const GUID guid_dsound_clock
= {0x58d58420, 0x71b4, 0x11d1, {0xa7, 0x4c, 0x00, 0x00, 0xf8, 0x75, 0xac, 0x12}};
766 IReferenceClock
*clock
, *clock2
;
767 REFERENCE_TIME time1
, time2
;
768 LARGE_INTEGER counter
, freq
;
769 DMUS_CLOCKINFO clock_info
;
770 IDirectMusic
*dmusic
;
776 hr
= CoCreateInstance(&CLSID_DirectMusic
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IDirectMusic
, (void **)&dmusic
);
777 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
779 hr
= IDirectMusic_GetMasterClock(dmusic
, NULL
, NULL
);
780 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
782 memset(&guid
, 0xcc, sizeof(guid
));
783 hr
= IDirectMusic_GetMasterClock(dmusic
, &guid
, NULL
);
784 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
785 todo_wine
ok(IsEqualGUID(&guid
, &guid_system_clock
), "Got guid %s.\n", wine_dbgstr_guid(&guid
));
787 clock
= (IReferenceClock
*)0xdeadbeef;
788 hr
= IDirectMusic_GetMasterClock(dmusic
, NULL
, &clock
);
789 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
790 ok(clock
&& clock
!= (IReferenceClock
*)0xdeadbeef, "Got clock %p.\n", clock
);
792 hr
= IDirectMusic_GetMasterClock(dmusic
, NULL
, &clock2
);
793 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
794 ok(clock2
== clock
, "Clocks didn't match.\n");
795 IReferenceClock_Release(clock2
);
797 memset(&guid
, 0xcc, sizeof(guid
));
798 hr
= IDirectMusic_GetMasterClock(dmusic
, &guid
, &clock2
);
799 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
800 todo_wine
ok(IsEqualGUID(&guid
, &guid_system_clock
), "Got guid %s.\n", wine_dbgstr_guid(&guid
));
801 ok(clock2
== clock
, "Clocks didn't match.\n");
802 IReferenceClock_Release(clock2
);
804 QueryPerformanceFrequency(&freq
);
805 QueryPerformanceCounter(&counter
);
806 hr
= IReferenceClock_GetTime(clock
, &time1
);
807 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
808 time2
= counter
.QuadPart
* 10000000.0 / freq
.QuadPart
;
809 ok(compare_time(time1
, time2
, 20 * 10000), "Expected about %s, got %s.\n",
810 wine_dbgstr_longlong(time2
), wine_dbgstr_longlong(time1
));
812 hr
= IReferenceClock_GetTime(clock
, &time2
);
813 ok(hr
== (time2
== time1
? S_FALSE
: S_OK
), "Got hr %#x.\n", hr
);
816 hr
= IReferenceClock_GetTime(clock
, &time2
);
817 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
818 ok(time2
- time1
> 80 * 10000, "Expected about %s, but got %s.\n",
819 wine_dbgstr_longlong(time1
+ 100 * 10000), wine_dbgstr_longlong(time2
));
821 hr
= IReferenceClock_AdviseTime(clock
, 0, 0, NULL
, &cookie
);
822 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
824 hr
= IReferenceClock_AdvisePeriodic(clock
, 0, 0, NULL
, &cookie
);
825 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
827 hr
= IReferenceClock_Unadvise(clock
, 0);
828 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
830 IReferenceClock_Release(clock
);
832 hr
= IDirectMusic_EnumMasterClock(dmusic
, 0, NULL
);
833 todo_wine
ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
835 memset(&clock_info
, 0xcc, sizeof(DMUS_CLOCKINFO
));
836 clock_info
.dwSize
= sizeof(DMUS_CLOCKINFO7
);
837 hr
= IDirectMusic_EnumMasterClock(dmusic
, 0, &clock_info
);
838 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
839 ok(clock_info
.ctType
== DMUS_CLOCK_SYSTEM
, "Got type %#x.\n", clock_info
.ctType
);
840 ok(IsEqualGUID(&clock_info
.guidClock
, &guid_system_clock
), "Got guid %s.\n",
841 wine_dbgstr_guid(&clock_info
.guidClock
));
842 ok(clock_info
.dwFlags
== 0xcccccccc, "Got flags %#x.\n", clock_info
.dwFlags
);
844 memset(&clock_info
, 0xcc, sizeof(DMUS_CLOCKINFO
));
845 clock_info
.dwSize
= sizeof(DMUS_CLOCKINFO7
);
846 hr
= IDirectMusic_EnumMasterClock(dmusic
, 1, &clock_info
);
847 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
848 ok(clock_info
.ctType
== DMUS_CLOCK_SYSTEM
, "Got type %#x.\n", clock_info
.ctType
);
849 ok(IsEqualGUID(&clock_info
.guidClock
, &guid_dsound_clock
), "Got guid %s.\n",
850 wine_dbgstr_guid(&clock_info
.guidClock
));
851 ok(clock_info
.dwFlags
== 0xcccccccc, "Got flags %#x.\n", clock_info
.dwFlags
);
853 memset(&clock_info
, 0xcc, sizeof(DMUS_CLOCKINFO
));
854 clock_info
.dwSize
= sizeof(DMUS_CLOCKINFO7
);
855 hr
= IDirectMusic_EnumMasterClock(dmusic
, 2, &clock_info
);
856 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
858 ref
= IDirectMusic_Release(dmusic
);
859 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
864 CoInitializeEx(NULL
, COINIT_MULTITHREADED
);
866 if (missing_dmusic())
868 skip("DirectMusic not available\n");
874 test_COM_synthport();
879 test_parsedescriptor();