1 /* DirectSoundFullDuplex
3 * Copyright 1998 Marcus Meissner
4 * Copyright 1998 Rob Riggs
5 * Copyright 2000-2001 TransGaming Technologies, Inc.
6 * Copyright 2005 Robert Reif
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
29 #include "dsound_private.h"
32 /*****************************************************************************
33 * IDirectSoundFullDuplex implementation structure
35 typedef struct IDirectSoundFullDuplexImpl
37 IDirectSoundFullDuplex IDirectSoundFullDuplex_iface
;
38 IUnknown IUnknown_iface
;
39 IDirectSound8 IDirectSound8_iface
;
40 IDirectSoundCapture IDirectSoundCapture_iface
;
41 LONG ref
, unkref
, ds8ref
, dscref
;
44 /* IDirectSoundFullDuplexImpl fields */
45 IDirectSound8
*renderer_device
;
46 IDirectSoundCapture
*capture_device
;
47 } IDirectSoundFullDuplexImpl
;
50 static void DSOUND_FullDuplexDestroy(IDirectSoundFullDuplexImpl
*This
)
52 if (This
->capture_device
)
53 IDirectSoundCapture_Release(This
->capture_device
);
54 if (This
->renderer_device
)
55 IDirectSound_Release(This
->renderer_device
);
56 HeapFree(GetProcessHeap(), 0, This
);
57 TRACE("(%p) released\n", This
);
60 /*******************************************************************************
63 static inline IDirectSoundFullDuplexImpl
*impl_from_IUnknown(IUnknown
*iface
)
65 return CONTAINING_RECORD(iface
, IDirectSoundFullDuplexImpl
, IUnknown_iface
);
68 static HRESULT WINAPI
IDirectSoundFullDuplex_IUnknown_QueryInterface(
69 IUnknown
*iface
, REFIID riid
, void **ppobj
)
71 IDirectSoundFullDuplexImpl
*This
= impl_from_IUnknown(iface
);
72 TRACE("(%p, %s, %p)\n", This
, debugstr_guid(riid
), ppobj
);
73 return IDirectSoundFullDuplex_QueryInterface(&This
->IDirectSoundFullDuplex_iface
, riid
, ppobj
);
76 static ULONG WINAPI
IDirectSoundFullDuplex_IUnknown_AddRef(IUnknown
*iface
)
78 IDirectSoundFullDuplexImpl
*This
= impl_from_IUnknown(iface
);
81 InterlockedIncrement(&(This
->all_ref
));
82 ref
= InterlockedIncrement(&(This
->unkref
));
83 TRACE("(%p) ref %lu\n", iface
, ref
);
88 static ULONG WINAPI
IDirectSoundFullDuplex_IUnknown_Release(IUnknown
*iface
)
90 IDirectSoundFullDuplexImpl
*This
= impl_from_IUnknown(iface
);
91 ULONG ref
= InterlockedDecrement(&(This
->unkref
));
92 TRACE("(%p) ref %lu\n", iface
, ref
);
93 if(InterlockedDecrement(&(This
->all_ref
)) == 0)
94 DSOUND_FullDuplexDestroy(This
);
98 static const IUnknownVtbl DirectSoundFullDuplex_Unknown_Vtbl
= {
99 IDirectSoundFullDuplex_IUnknown_QueryInterface
,
100 IDirectSoundFullDuplex_IUnknown_AddRef
,
101 IDirectSoundFullDuplex_IUnknown_Release
104 /*******************************************************************************
105 * IDirectSoundFullDuplex_IDirectSound8
107 static inline IDirectSoundFullDuplexImpl
*impl_from_IDirectSound8(IDirectSound8
*iface
)
109 return CONTAINING_RECORD(iface
, IDirectSoundFullDuplexImpl
, IDirectSound8_iface
);
112 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_QueryInterface(
113 IDirectSound8
*iface
, REFIID riid
, void **ppobj
)
115 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
116 TRACE("(%p, %s, %p)\n", This
, debugstr_guid(riid
), ppobj
);
117 return IDirectSoundFullDuplex_QueryInterface(&This
->IDirectSoundFullDuplex_iface
, riid
, ppobj
);
120 static ULONG WINAPI
IDirectSoundFullDuplex_IDirectSound8_AddRef(IDirectSound8
*iface
)
122 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
125 InterlockedIncrement(&(This
->all_ref
));
126 ref
= InterlockedIncrement(&(This
->ds8ref
));
127 TRACE("(%p) ref %lu\n", iface
, ref
);
132 static ULONG WINAPI
IDirectSoundFullDuplex_IDirectSound8_Release(IDirectSound8
*iface
)
134 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
135 ULONG ref
= InterlockedDecrement(&(This
->ds8ref
));
136 TRACE("(%p) ref %lu\n", iface
, ref
);
137 if(InterlockedDecrement(&(This
->all_ref
)) == 0)
138 DSOUND_FullDuplexDestroy(This
);
142 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_CreateSoundBuffer(
143 IDirectSound8
*iface
, LPCDSBUFFERDESC dsbd
, IDirectSoundBuffer
**ppdsb
,
146 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
147 TRACE("(%p,%p,%p,%p)\n",This
,dsbd
,ppdsb
,lpunk
);
148 return IDirectSound8_CreateSoundBuffer(This
->renderer_device
,dsbd
,ppdsb
,lpunk
);
151 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_GetCaps(
152 IDirectSound8
*iface
, DSCAPS
*lpDSCaps
)
154 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
155 TRACE("(%p,%p)\n",This
,lpDSCaps
);
156 return IDirectSound8_GetCaps(This
->renderer_device
, lpDSCaps
);
159 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_DuplicateSoundBuffer(
160 IDirectSound8
*iface
, IDirectSoundBuffer
*psb
, IDirectSoundBuffer
**ppdsb
)
162 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
163 TRACE("(%p,%p,%p)\n",This
,psb
,ppdsb
);
164 return IDirectSound8_DuplicateSoundBuffer(This
->renderer_device
,psb
,ppdsb
);
167 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_SetCooperativeLevel(
168 IDirectSound8
*iface
, HWND hwnd
, DWORD level
)
170 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
171 TRACE("(%p,%p,%lu)\n",This
,hwnd
,level
);
172 return IDirectSound8_SetCooperativeLevel(This
->renderer_device
,hwnd
,level
);
175 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_Compact(IDirectSound8
*iface
)
177 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
178 TRACE("(%p)\n", This
);
179 return IDirectSound8_Compact(This
->renderer_device
);
182 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_GetSpeakerConfig(
183 IDirectSound8
*iface
, DWORD
*lpdwSpeakerConfig
)
185 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
186 TRACE("(%p, %p)\n", This
, lpdwSpeakerConfig
);
187 return IDirectSound8_GetSpeakerConfig(This
->renderer_device
,lpdwSpeakerConfig
);
190 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_SetSpeakerConfig(
191 IDirectSound8
*iface
, DWORD config
)
193 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
194 TRACE("(%p,0x%08lx)\n",This
,config
);
195 return IDirectSound8_SetSpeakerConfig(This
->renderer_device
,config
);
198 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_Initialize(
199 IDirectSound8
*iface
, LPCGUID lpcGuid
)
201 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
202 TRACE("(%p, %s)\n", This
, debugstr_guid(lpcGuid
));
203 return IDirectSound8_Initialize(This
->renderer_device
,lpcGuid
);
206 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSound8_VerifyCertification(
207 IDirectSound8
*iface
, DWORD
*cert
)
209 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSound8(iface
);
210 TRACE("(%p, %p)\n", This
, cert
);
211 return IDirectSound8_VerifyCertification(This
->renderer_device
,cert
);
214 static const IDirectSound8Vtbl DirectSoundFullDuplex_DirectSound8_Vtbl
= {
215 IDirectSoundFullDuplex_IDirectSound8_QueryInterface
,
216 IDirectSoundFullDuplex_IDirectSound8_AddRef
,
217 IDirectSoundFullDuplex_IDirectSound8_Release
,
218 IDirectSoundFullDuplex_IDirectSound8_CreateSoundBuffer
,
219 IDirectSoundFullDuplex_IDirectSound8_GetCaps
,
220 IDirectSoundFullDuplex_IDirectSound8_DuplicateSoundBuffer
,
221 IDirectSoundFullDuplex_IDirectSound8_SetCooperativeLevel
,
222 IDirectSoundFullDuplex_IDirectSound8_Compact
,
223 IDirectSoundFullDuplex_IDirectSound8_GetSpeakerConfig
,
224 IDirectSoundFullDuplex_IDirectSound8_SetSpeakerConfig
,
225 IDirectSoundFullDuplex_IDirectSound8_Initialize
,
226 IDirectSoundFullDuplex_IDirectSound8_VerifyCertification
229 /*******************************************************************************
230 * IDirectSoundFullDuplex_IDirectSoundCapture
232 static inline IDirectSoundFullDuplexImpl
*impl_from_IDirectSoundCapture(IDirectSoundCapture
*iface
)
234 return CONTAINING_RECORD(iface
, IDirectSoundFullDuplexImpl
, IDirectSoundCapture_iface
);
237 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_QueryInterface(
238 IDirectSoundCapture
*iface
, REFIID riid
, void **ppobj
)
240 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
241 TRACE("(%p, %s, %p)\n", This
, debugstr_guid(riid
), ppobj
);
242 return IDirectSoundFullDuplex_QueryInterface(&This
->IDirectSoundFullDuplex_iface
, riid
, ppobj
);
245 static ULONG WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_AddRef(IDirectSoundCapture
*iface
)
247 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
250 InterlockedIncrement(&(This
->all_ref
));
251 ref
= InterlockedIncrement(&(This
->dscref
));
252 TRACE("(%p) ref %lu\n", iface
, ref
);
257 static ULONG WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_Release(IDirectSoundCapture
*iface
)
259 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
260 ULONG ref
= InterlockedDecrement(&(This
->dscref
));
261 TRACE("(%p) ref %lu\n", iface
, ref
);
262 if(InterlockedDecrement(&(This
->all_ref
)) == 0)
263 DSOUND_FullDuplexDestroy(This
);
267 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_CreateCaptureBuffer(
268 IDirectSoundCapture
*iface
, LPCDSCBUFFERDESC lpcDSCBufferDesc
,
269 IDirectSoundCaptureBuffer
**lplpDSCaptureBuffer
, IUnknown
*pUnk
)
271 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
272 TRACE("(%p, %p, %p, %p)\n", This
, lpcDSCBufferDesc
, lplpDSCaptureBuffer
, pUnk
);
273 return IDirectSoundCapture_CreateCaptureBuffer(This
->capture_device
,lpcDSCBufferDesc
,lplpDSCaptureBuffer
,pUnk
);
276 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_GetCaps(
277 IDirectSoundCapture
*iface
, LPDSCCAPS lpDSCCaps
)
279 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
280 TRACE("(%p, %p)\n", This
, lpDSCCaps
);
281 return IDirectSoundCapture_GetCaps(This
->capture_device
, lpDSCCaps
);
284 static HRESULT WINAPI
IDirectSoundFullDuplex_IDirectSoundCapture_Initialize(
285 IDirectSoundCapture
*iface
, LPCGUID lpcGUID
)
287 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundCapture(iface
);
288 TRACE("(%p, %s)\n", This
, debugstr_guid(lpcGUID
));
289 return IDirectSoundCapture_Initialize(This
->capture_device
,lpcGUID
);
292 static const IDirectSoundCaptureVtbl DirectSoundFullDuplex_DirectSoundCapture_Vtbl
= {
293 IDirectSoundFullDuplex_IDirectSoundCapture_QueryInterface
,
294 IDirectSoundFullDuplex_IDirectSoundCapture_AddRef
,
295 IDirectSoundFullDuplex_IDirectSoundCapture_Release
,
296 IDirectSoundFullDuplex_IDirectSoundCapture_CreateCaptureBuffer
,
297 IDirectSoundFullDuplex_IDirectSoundCapture_GetCaps
,
298 IDirectSoundFullDuplex_IDirectSoundCapture_Initialize
301 /***************************************************************************
302 * IDirectSoundFullDuplexImpl
304 static inline IDirectSoundFullDuplexImpl
*impl_from_IDirectSoundFullDuplex(IDirectSoundFullDuplex
*iface
)
306 return CONTAINING_RECORD(iface
, IDirectSoundFullDuplexImpl
, IDirectSoundFullDuplex_iface
);
309 static HRESULT WINAPI
IDirectSoundFullDuplexImpl_QueryInterface(
310 IDirectSoundFullDuplex
*iface
, REFIID riid
, void **ppobj
)
312 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundFullDuplex(iface
);
313 TRACE( "(%p,%s,%p)\n", This
, debugstr_guid(riid
), ppobj
);
316 WARN("invalid parameter\n");
322 if (IsEqualIID(riid
, &IID_IUnknown
)) {
323 *ppobj
= &This
->IUnknown_iface
;
324 IUnknown_AddRef((IUnknown
*)*ppobj
);
326 } else if (IsEqualIID(riid
, &IID_IDirectSoundFullDuplex
)) {
327 *ppobj
= &This
->IDirectSoundFullDuplex_iface
;
328 IUnknown_AddRef((IUnknown
*)*ppobj
);
330 } else if (IsEqualIID(riid
, &IID_IDirectSound
) ||
331 IsEqualIID(riid
, &IID_IDirectSound8
)) {
332 if(This
->renderer_device
!= NULL
)
334 *ppobj
= &This
->IDirectSound8_iface
;
335 IUnknown_AddRef((IUnknown
*)*ppobj
);
338 } else if (IsEqualIID(riid
, &IID_IDirectSoundCapture
)) {
339 if(This
->capture_device
!= NULL
)
341 *ppobj
= &This
->IDirectSoundCapture_iface
;
342 IUnknown_AddRef((IUnknown
*)*ppobj
);
347 return E_NOINTERFACE
;
350 static ULONG WINAPI
IDirectSoundFullDuplexImpl_AddRef(IDirectSoundFullDuplex
*iface
)
352 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundFullDuplex(iface
);
355 InterlockedIncrement(&(This
->all_ref
));
356 ref
= InterlockedIncrement(&(This
->ref
));
357 TRACE("(%p) ref %lu\n", iface
, ref
);
362 static ULONG WINAPI
IDirectSoundFullDuplexImpl_Release(IDirectSoundFullDuplex
*iface
)
364 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundFullDuplex(iface
);
365 ULONG ref
= InterlockedDecrement(&(This
->ref
));
366 TRACE("(%p) ref %lu\n", iface
, ref
);
367 if(InterlockedDecrement(&(This
->all_ref
)) == 0)
368 DSOUND_FullDuplexDestroy(This
);
372 static HRESULT WINAPI
IDirectSoundFullDuplexImpl_Initialize(
373 IDirectSoundFullDuplex
*iface
,
374 LPCGUID pCaptureGuid
, LPCGUID pRendererGuid
,
375 LPCDSCBUFFERDESC lpDscBufferDesc
, LPCDSBUFFERDESC lpDsBufferDesc
,
376 HWND hWnd
, DWORD dwLevel
,
377 IDirectSoundCaptureBuffer8
**lplpDirectSoundCaptureBuffer8
,
378 IDirectSoundBuffer8
**lplpDirectSoundBuffer8
)
380 IDirectSoundFullDuplexImpl
*This
= impl_from_IDirectSoundFullDuplex(iface
);
381 IDirectSoundCaptureBuffer
*capbuffer
;
382 IDirectSoundBuffer
*buffer
;
386 TRACE("(%p,%s,%s,%p,%p,%p,%lx,%p,%p)\n", This
,
387 debugstr_guid(pCaptureGuid
), debugstr_guid(pRendererGuid
),
388 lpDscBufferDesc
, lpDsBufferDesc
, hWnd
, dwLevel
,
389 lplpDirectSoundCaptureBuffer8
, lplpDirectSoundBuffer8
);
391 if(!lplpDirectSoundBuffer8
|| !lplpDirectSoundCaptureBuffer8
)
393 WARN("NULL output pointers\n");
394 return DSERR_INVALIDPARAM
;
397 *lplpDirectSoundCaptureBuffer8
= NULL
;
398 *lplpDirectSoundBuffer8
= NULL
;
400 if(This
->renderer_device
!= NULL
|| This
->capture_device
!= NULL
)
402 WARN("already initialized\n");
403 return DSERR_ALREADYINITIALIZED
;
406 hr
= DSOUND_Create8(&IID_IDirectSound8
, &ptr
);
409 This
->renderer_device
= ptr
;
410 hr
= IDirectSound8_Initialize(This
->renderer_device
, pRendererGuid
);
414 WARN("DirectSoundDevice_Initialize() failed\n");
418 IDirectSound8_SetCooperativeLevel(This
->renderer_device
, hWnd
, dwLevel
);
420 hr
= IDirectSound8_CreateSoundBuffer(This
->renderer_device
, lpDsBufferDesc
,
424 hr
= IDirectSoundBuffer_QueryInterface(buffer
, &IID_IDirectSoundBuffer8
, &ptr
);
425 IDirectSoundBuffer_Release(buffer
);
429 WARN("IDirectSoundBufferImpl_Create() failed\n");
432 *lplpDirectSoundBuffer8
= ptr
;
434 hr
= DSOUND_CaptureCreate8(&IID_IDirectSoundCapture
, &ptr
);
437 This
->capture_device
= ptr
;
438 hr
= IDirectSoundCapture_Initialize(This
->capture_device
, pCaptureGuid
);
442 WARN("DirectSoundCaptureDevice_Initialize() failed\n");
446 hr
= IDirectSoundCapture_CreateCaptureBuffer(This
->capture_device
, lpDscBufferDesc
,
450 hr
= IDirectSoundCaptureBuffer_QueryInterface(capbuffer
, &IID_IDirectSoundCaptureBuffer8
, &ptr
);
451 IDirectSoundCaptureBuffer_Release(capbuffer
);
455 WARN("IDirectSoundCaptureBufferImpl_Create() failed\n");
458 *lplpDirectSoundCaptureBuffer8
= ptr
;
463 static const IDirectSoundFullDuplexVtbl dsfdvt
= {
464 /* IUnknown methods */
465 IDirectSoundFullDuplexImpl_QueryInterface
,
466 IDirectSoundFullDuplexImpl_AddRef
,
467 IDirectSoundFullDuplexImpl_Release
,
469 /* IDirectSoundFullDuplex methods */
470 IDirectSoundFullDuplexImpl_Initialize
473 HRESULT
DSOUND_FullDuplexCreate(
474 REFIID riid
, void **ppDSFD
)
476 IDirectSoundFullDuplexImpl
*This
= NULL
;
479 TRACE("(%s, %p)\n", debugstr_guid(riid
), ppDSFD
);
483 WARN("invalid parameter: ppDSFD == NULL\n");
484 return DSERR_INVALIDPARAM
;
488 if(!IsEqualIID(riid
, &IID_IUnknown
) &&
489 !IsEqualIID(riid
, &IID_IDirectSoundFullDuplex
))
490 return E_NOINTERFACE
;
492 This
= HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY
, sizeof(IDirectSoundFullDuplexImpl
));
495 WARN("out of memory\n");
496 return DSERR_OUTOFMEMORY
;
499 This
->IDirectSoundFullDuplex_iface
.lpVtbl
= &dsfdvt
;
500 This
->IUnknown_iface
.lpVtbl
= &DirectSoundFullDuplex_Unknown_Vtbl
;
501 This
->IDirectSound8_iface
.lpVtbl
= &DirectSoundFullDuplex_DirectSound8_Vtbl
;
502 This
->IDirectSoundCapture_iface
.lpVtbl
= &DirectSoundFullDuplex_DirectSoundCapture_Vtbl
;
510 This
->capture_device
= NULL
;
511 This
->renderer_device
= NULL
;
513 hr
= IDirectSoundFullDuplexImpl_QueryInterface(&This
->IDirectSoundFullDuplex_iface
, riid
, ppDSFD
);
514 if(FAILED(hr
)) DSOUND_FullDuplexDestroy(This
);
518 /***************************************************************************
519 * DirectSoundFullDuplexCreate [DSOUND.10]
521 * Create and initialize a DirectSoundFullDuplex interface.
524 * pcGuidCaptureDevice [I] Address of sound capture device GUID.
525 * pcGuidRenderDevice [I] Address of sound render device GUID.
526 * pcDSCBufferDesc [I] Address of capture buffer description.
527 * pcDSBufferDesc [I] Address of render buffer description.
528 * hWnd [I] Handle to application window.
529 * dwLevel [I] Cooperative level.
530 * ppDSFD [O] Address where full duplex interface returned.
531 * ppDSCBuffer8 [0] Address where capture buffer interface returned.
532 * ppDSBuffer8 [0] Address where render buffer interface returned.
533 * pUnkOuter [I] Must be NULL.
537 * Failure: DSERR_NOAGGREGATION, DSERR_ALLOCATED, DSERR_INVALIDPARAM,
538 * DSERR_OUTOFMEMORY DSERR_INVALIDCALL DSERR_NODRIVER
541 DirectSoundFullDuplexCreate(
542 LPCGUID pcGuidCaptureDevice
, LPCGUID pcGuidRenderDevice
,
543 LPCDSCBUFFERDESC pcDSCBufferDesc
, LPCDSBUFFERDESC pcDSBufferDesc
,
544 HWND hWnd
, DWORD dwLevel
,
545 IDirectSoundFullDuplex
**ppDSFD
,
546 IDirectSoundCaptureBuffer8
**ppDSCBuffer8
,
547 IDirectSoundBuffer8
**ppDSBuffer8
,
553 TRACE("(%s,%s,%p,%p,%p,%lx,%p,%p,%p,%p)\n",
554 debugstr_guid(pcGuidCaptureDevice
), debugstr_guid(pcGuidRenderDevice
),
555 pcDSCBufferDesc
, pcDSBufferDesc
, hWnd
, dwLevel
, ppDSFD
, ppDSCBuffer8
,
556 ppDSBuffer8
, pUnkOuter
);
560 WARN("invalid parameter: ppDSFD == NULL\n");
561 return DSERR_INVALIDPARAM
;
567 WARN("pUnkOuter != 0\n");
568 return DSERR_NOAGGREGATION
;
571 if(pcDSCBufferDesc
== NULL
)
573 WARN("invalid parameter: pcDSCBufferDesc == NULL\n");
574 return DSERR_INVALIDPARAM
;
577 if(pcDSBufferDesc
== NULL
)
579 WARN("invalid parameter: pcDSBufferDesc == NULL\n");
580 return DSERR_INVALIDPARAM
;
584 if(ppDSCBuffer8
== NULL
)
586 WARN("invalid parameter: ppDSCBuffer8 == NULL\n");
587 return DSERR_INVALIDPARAM
;
590 if(ppDSBuffer8
== NULL
)
592 WARN("invalid parameter: ppDSBuffer8 == NULL\n");
593 return DSERR_INVALIDPARAM
;
596 hres
= DSOUND_FullDuplexCreate(&IID_IDirectSoundFullDuplex
, &iface
);
597 if(FAILED(hres
)) return hres
;
600 hres
= IDirectSoundFullDuplexImpl_Initialize(*ppDSFD
,
610 IDirectSoundFullDuplex_Release(*ppDSFD
);
611 WARN("IDirectSoundFullDuplexImpl_Initialize failed\n");