3 * Copyright 1998 Marcus Meissner
4 * Copyright 1998 Rob Riggs
5 * Copyright 2000-2002 TransGaming Technologies, Inc.
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 #include <sys/types.h>
26 #include <sys/fcntl.h>
32 #include <math.h> /* Insomnia - pow() function */
43 #include "wine/windef16.h"
44 #include "wine/debug.h"
47 #include "dsound_private.h"
50 WINE_DEFAULT_DEBUG_CHANNEL(dsound
);
53 /*******************************************************************************
57 /* IUnknown methods */
58 static HRESULT WINAPI
IKsPropertySetImpl_QueryInterface(
59 LPKSPROPERTYSET iface
, REFIID riid
, LPVOID
*ppobj
61 ICOM_THIS(IKsPropertySetImpl
,iface
);
63 TRACE("(%p,%s,%p)\n",This
,debugstr_guid(riid
),ppobj
);
64 return IDirectSoundBuffer_QueryInterface((LPDIRECTSOUNDBUFFER8
)This
->dsb
, riid
, ppobj
);
67 static ULONG WINAPI
IKsPropertySetImpl_AddRef(LPKSPROPERTYSET iface
) {
68 ICOM_THIS(IKsPropertySetImpl
,iface
);
71 ulReturn
= InterlockedIncrement(&This
->ref
);
73 IDirectSoundBuffer_AddRef((LPDIRECTSOUND3DBUFFER
)This
->dsb
);
77 static ULONG WINAPI
IKsPropertySetImpl_Release(LPKSPROPERTYSET iface
) {
78 ICOM_THIS(IKsPropertySetImpl
,iface
);
81 ulReturn
= InterlockedDecrement(&This
->ref
);
84 IDirectSoundBuffer_Release((LPDIRECTSOUND3DBUFFER
)This
->dsb
);
88 static HRESULT WINAPI
DSPROPERTY_WaveDeviceMappingA(
94 PDSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_A_DATA ppd
;
95 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p) not implemented!\n",
96 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
98 ppd
= (PDSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_A_DATA
) pPropData
;
101 WARN("invalid parameter: pPropData\n");
102 return DSERR_INVALIDPARAM
;
105 FIXME("DeviceName=%s\n",ppd
->DeviceName
);
106 FIXME("DataFlow=%s\n",
107 ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_RENDER
? "DIRECTSOUNDDEVICE_DATAFLOW_RENDER" :
108 ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
? "DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE" : "UNKNOWN");
110 /* FIXME: match the name to a wave device somehow. */
111 ppd
->DeviceId
= GUID_NULL
;
114 *pcbReturned
= cbPropData
;
115 FIXME("*pcbReturned=%ld\n", *pcbReturned
);
121 static HRESULT WINAPI
DSPROPERTY_WaveDeviceMappingW(
127 PDSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_W_DATA ppd
;
128 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p) not implemented!\n",
129 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
131 ppd
= (PDSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_W_DATA
) pPropData
;
134 WARN("invalid parameter: pPropData\n");
135 return DSERR_INVALIDPARAM
;
138 FIXME("DeviceName=%s\n",debugstr_w(ppd
->DeviceName
));
139 FIXME("DataFlow=%s\n",
140 ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_RENDER
? "DIRECTSOUNDDEVICE_DATAFLOW_RENDER" :
141 ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
? "DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE" : "UNKNOWN");
143 /* FIXME: match the name to a wave device somehow. */
144 ppd
->DeviceId
= GUID_NULL
;
147 *pcbReturned
= cbPropData
;
148 FIXME("*pcbReturned=%ld\n", *pcbReturned
);
154 static HRESULT WINAPI
DSPROPERTY_Description1(
162 PDSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_1_DATA ppd
;
163 TRACE("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
164 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
166 ppd
= (PDSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_1_DATA
) pPropData
;
169 WARN("invalid parameter: pPropData\n");
170 return DSERR_INVALIDPARAM
;
173 TRACE("DeviceId=%s\n",debugstr_guid(&ppd
->DeviceId
));
174 if ( IsEqualGUID( &ppd
->DeviceId
, &GUID_NULL
) ) {
175 /* default device of type specified by ppd->DataFlow */
176 if (ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
) {
177 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE\n");
178 } else if (ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_RENDER
) {
179 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_RENDER\n");
181 TRACE("DataFlow=Unknown(%d)\n", ppd
->DataFlow
);
183 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p) GUID_NULL not implemented!\n",
184 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
185 return E_PROP_ID_UNSUPPORTED
;
187 GetDeviceID(&ppd
->DeviceId
, &dev_guid
);
189 if ( IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultPlayback
) ||
190 IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultVoicePlayback
) ) {
193 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_RENDER\n");
194 ppd
->DataFlow
= DIRECTSOUNDDEVICE_DATAFLOW_RENDER
;
195 wodn
= waveOutGetNumDevs();
196 for (wod
= 0; wod
< wodn
; wod
++) {
197 err
= mmErr(waveOutMessage((HWAVEOUT
)wod
,DRV_QUERYDSOUNDGUID
,(DWORD
)(&guid
),0));
199 if (IsEqualGUID( &dev_guid
, &guid
) ) {
201 ppd
->WaveDeviceId
= wod
;
203 err
= mmErr(waveOutMessage((HWAVEOUT
)wod
,DRV_QUERYDSOUNDDESC
,(DWORD
)&(desc
),0));
205 strncpy(ppd
->DescriptionA
, desc
.szDesc
, sizeof(ppd
->DescriptionA
) - 1);
206 strncpy(ppd
->ModuleA
, desc
.szDrvName
, sizeof(ppd
->ModuleA
) - 1);
207 MultiByteToWideChar( CP_ACP
, 0, desc
.szDesc
, -1, ppd
->DescriptionW
, sizeof(ppd
->DescriptionW
)/sizeof(WCHAR
) );
208 MultiByteToWideChar( CP_ACP
, 0, desc
.szDrvName
, -1, ppd
->ModuleW
, sizeof(ppd
->ModuleW
)/sizeof(WCHAR
) );
211 WARN("waveOutMessage failed\n");
212 return E_PROP_ID_UNSUPPORTED
;
216 WARN("waveOutMessage failed\n");
217 return E_PROP_ID_UNSUPPORTED
;
220 } else if ( IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultCapture
) ||
221 IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultVoiceCapture
) ) {
224 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE\n");
225 ppd
->DataFlow
= DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
;
226 widn
= waveInGetNumDevs();
227 for (wid
= 0; wid
< widn
; wid
++) {
228 err
= mmErr(waveInMessage((HWAVEIN
)wid
,DRV_QUERYDSOUNDGUID
,(DWORD
)(&guid
),0));
230 if (IsEqualGUID( &dev_guid
, &guid
) ) {
232 ppd
->WaveDeviceId
= wid
;
234 err
= mmErr(waveInMessage((HWAVEIN
)wid
,DRV_QUERYDSOUNDDESC
,(DWORD
)&(desc
),0));
236 strncpy(ppd
->DescriptionA
, desc
.szDesc
, sizeof(ppd
->DescriptionA
) - 1);
237 strncpy(ppd
->ModuleA
, desc
.szDrvName
, sizeof(ppd
->ModuleA
) - 1);
238 MultiByteToWideChar( CP_ACP
, 0, desc
.szDesc
, -1, ppd
->DescriptionW
, sizeof(ppd
->DescriptionW
)/sizeof(WCHAR
) );
239 MultiByteToWideChar( CP_ACP
, 0, desc
.szDrvName
, -1, ppd
->ModuleW
, sizeof(ppd
->ModuleW
)/sizeof(WCHAR
) );
242 WARN("waveInMessage failed\n");
243 return E_PROP_ID_UNSUPPORTED
;
248 WARN("waveInMessage failed\n");
249 return E_PROP_ID_UNSUPPORTED
;
253 FIXME("DeviceId=Unknown\n");
254 return E_PROP_ID_UNSUPPORTED
;
258 ppd
->Type
= DIRECTSOUNDDEVICE_TYPE_EMULATED
;
261 *pcbReturned
= cbPropData
;
262 TRACE("*pcbReturned=%ld\n", *pcbReturned
);
268 static HRESULT WINAPI
DSPROPERTY_DescriptionA(
274 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
275 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
276 return E_PROP_ID_UNSUPPORTED
;
279 static HRESULT WINAPI
DSPROPERTY_DescriptionW(
285 PDSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W_DATA ppd
= (PDSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W_DATA
) pPropData
;
288 TRACE("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
289 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
291 TRACE("DeviceId=%s\n",debugstr_guid(&ppd
->DeviceId
));
292 if ( IsEqualGUID( &ppd
->DeviceId
, &GUID_NULL
) ) {
293 /* default device of type specified by ppd->DataFlow */
294 if (ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
) {
295 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE\n");
296 } else if (ppd
->DataFlow
== DIRECTSOUNDDEVICE_DATAFLOW_RENDER
) {
297 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_RENDER\n");
299 TRACE("DataFlow=Unknown(%d)\n", ppd
->DataFlow
);
301 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p) GUID_NULL not implemented!\n",
302 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
303 return E_PROP_ID_UNSUPPORTED
;
305 GetDeviceID(&ppd
->DeviceId
, &dev_guid
);
307 if ( IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultPlayback
) ||
308 IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultVoicePlayback
) ) {
311 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_RENDER\n");
312 ppd
->DataFlow
= DIRECTSOUNDDEVICE_DATAFLOW_RENDER
;
313 wodn
= waveOutGetNumDevs();
314 for (wod
= 0; wod
< wodn
; wod
++) {
315 err
= mmErr(waveOutMessage((HWAVEOUT
)wod
,DRV_QUERYDSOUNDGUID
,(DWORD
)(&guid
),0));
317 if (IsEqualGUID( &dev_guid
, &guid
) ) {
319 ppd
->WaveDeviceId
= wod
;
320 err
= mmErr(waveOutMessage((HWAVEOUT
)wod
,DRV_QUERYDSOUNDDESC
,(DWORD
)&(desc
),0));
322 /* FIXME: this is a memory leak */
323 WCHAR
* wDescription
= HeapAlloc(GetProcessHeap(),0,0x200);
324 WCHAR
* wModule
= HeapAlloc(GetProcessHeap(),0,0x200);
325 WCHAR
* wInterface
= HeapAlloc(GetProcessHeap(),0,0x200);
327 MultiByteToWideChar( CP_ACP
, 0, desc
.szDesc
, -1, wDescription
, 0x100 );
328 MultiByteToWideChar( CP_ACP
, 0, desc
.szDrvName
, -1, wModule
, 0x100 );
329 MultiByteToWideChar( CP_ACP
, 0, "Interface", -1, wInterface
, 0x100 );
331 ppd
->Description
= wDescription
;
332 ppd
->Module
= wModule
;
333 ppd
->Interface
= wInterface
;
336 WARN("waveOutMessage failed\n");
337 return E_PROP_ID_UNSUPPORTED
;
341 WARN("waveOutMessage failed\n");
342 return E_PROP_ID_UNSUPPORTED
;
345 } else if (IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultCapture
) ||
346 IsEqualGUID( &ppd
->DeviceId
, &DSDEVID_DefaultVoiceCapture
) ) {
349 TRACE("DataFlow=DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE\n");
350 ppd
->DataFlow
= DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE
;
351 widn
= waveInGetNumDevs();
352 for (wid
= 0; wid
< widn
; wid
++) {
353 err
= mmErr(waveInMessage((HWAVEIN
)wid
,DRV_QUERYDSOUNDGUID
,(DWORD
)(&guid
),0));
355 if (IsEqualGUID( &dev_guid
, &guid
) ) {
357 ppd
->WaveDeviceId
= wid
;
358 err
= mmErr(waveInMessage((HWAVEIN
)wid
,DRV_QUERYDSOUNDDESC
,(DWORD
)&(desc
),0));
360 /* FIXME: this is a memory leak */
361 WCHAR
* wDescription
= HeapAlloc(GetProcessHeap(),0,0x200);
362 WCHAR
* wModule
= HeapAlloc(GetProcessHeap(),0,0x200);
363 WCHAR
* wInterface
= HeapAlloc(GetProcessHeap(),0,0x200);
365 MultiByteToWideChar( CP_ACP
, 0, desc
.szDesc
, -1, wDescription
, 0x100 );
366 MultiByteToWideChar( CP_ACP
, 0, desc
.szDrvName
, -1, wModule
, 0x100 );
367 MultiByteToWideChar( CP_ACP
, 0, "Interface", -1, wInterface
, 0x100 );
369 ppd
->Description
= wDescription
;
370 ppd
->Module
= wModule
;
371 ppd
->Interface
= wInterface
;
374 WARN("waveInMessage failed\n");
375 return E_PROP_ID_UNSUPPORTED
;
380 WARN("waveInMessage failed\n");
381 return E_PROP_ID_UNSUPPORTED
;
385 FIXME("DeviceId=Unknown\n");
386 return E_PROP_ID_UNSUPPORTED
;
390 ppd
->Type
= DIRECTSOUNDDEVICE_TYPE_EMULATED
;
392 *pcbReturned
= cbPropData
;
393 TRACE("*pcbReturned=%ld\n", *pcbReturned
);
398 static HRESULT WINAPI
DSPROPERTY_Enumerate1(
404 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
405 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
406 return E_PROP_ID_UNSUPPORTED
;
409 static HRESULT WINAPI
DSPROPERTY_EnumerateA(
415 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
416 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
417 return E_PROP_ID_UNSUPPORTED
;
420 static HRESULT WINAPI
DSPROPERTY_EnumerateW(
426 FIXME("(guidPropSet=%s,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
427 debugstr_guid(guidPropSet
),pPropData
,cbPropData
,pcbReturned
);
428 return E_PROP_ID_UNSUPPORTED
;
431 static HRESULT WINAPI
IKsPropertySetImpl_Get(LPKSPROPERTYSET iface
,
432 REFGUID guidPropSet
, ULONG dwPropID
,
433 LPVOID pInstanceData
, ULONG cbInstanceData
,
434 LPVOID pPropData
, ULONG cbPropData
,
437 ICOM_THIS(IKsPropertySetImpl
,iface
);
438 TRACE("(iface=%p,guidPropSet=%s,dwPropID=%ld,pInstanceData=%p,cbInstanceData=%ld,pPropData=%p,cbPropData=%ld,pcbReturned=%p)\n",
439 This
,debugstr_guid(guidPropSet
),dwPropID
,pInstanceData
,cbInstanceData
,pPropData
,cbPropData
,pcbReturned
);
441 if ( IsEqualGUID( &DSPROPSETID_DirectSoundDevice
, guidPropSet
) ) {
443 case DSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_A
:
444 return DSPROPERTY_WaveDeviceMappingA(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
445 case DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_1
:
446 return DSPROPERTY_Description1(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
447 case DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE_1
:
448 return DSPROPERTY_Enumerate1(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
449 case DSPROPERTY_DIRECTSOUNDDEVICE_WAVEDEVICEMAPPING_W
:
450 return DSPROPERTY_WaveDeviceMappingW(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
451 case DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_A
:
452 return DSPROPERTY_DescriptionA(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
453 case DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W
:
454 return DSPROPERTY_DescriptionW(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
455 case DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE_A
:
456 return DSPROPERTY_EnumerateA(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
457 case DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE_W
:
458 return DSPROPERTY_EnumerateW(guidPropSet
,pPropData
,cbPropData
,pcbReturned
);
460 FIXME("unsupported ID: %ld\n",dwPropID
);
464 FIXME("unsupported property: %s\n",debugstr_guid(guidPropSet
));
469 FIXME("*pcbReturned=%ld\n", *pcbReturned
);
472 return E_PROP_ID_UNSUPPORTED
;
475 static HRESULT WINAPI
IKsPropertySetImpl_Set(LPKSPROPERTYSET iface
,
476 REFGUID guidPropSet
, ULONG dwPropID
,
477 LPVOID pInstanceData
, ULONG cbInstanceData
,
478 LPVOID pPropData
, ULONG cbPropData
480 ICOM_THIS(IKsPropertySetImpl
,iface
);
482 FIXME("(%p,%s,%ld,%p,%ld,%p,%ld), stub!\n",This
,debugstr_guid(guidPropSet
),dwPropID
,pInstanceData
,cbInstanceData
,pPropData
,cbPropData
);
483 return E_PROP_ID_UNSUPPORTED
;
486 static HRESULT WINAPI
IKsPropertySetImpl_QuerySupport(LPKSPROPERTYSET iface
,
487 REFGUID guidPropSet
, ULONG dwPropID
, PULONG pTypeSupport
489 ICOM_THIS(IKsPropertySetImpl
,iface
);
491 FIXME("(%p,%s,%ld,%p), stub!\n",This
,debugstr_guid(guidPropSet
),dwPropID
,pTypeSupport
);
492 return E_PROP_ID_UNSUPPORTED
;
495 static ICOM_VTABLE(IKsPropertySet
) iksvt
= {
496 ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
497 IKsPropertySetImpl_QueryInterface
,
498 IKsPropertySetImpl_AddRef
,
499 IKsPropertySetImpl_Release
,
500 IKsPropertySetImpl_Get
,
501 IKsPropertySetImpl_Set
,
502 IKsPropertySetImpl_QuerySupport
505 HRESULT WINAPI
IKsPropertySetImpl_Create(
506 IDirectSoundBufferImpl
*This
,
507 IKsPropertySetImpl
**piks
)
509 IKsPropertySetImpl
*iks
;
511 iks
= (IKsPropertySetImpl
*)HeapAlloc(GetProcessHeap(),0,sizeof(*iks
));
514 iks
->lpVtbl
= &iksvt
;