Added support for direct sound capture and a real direct sound capture
driver. Capture now works with some skipping. Full duplex does not but I will be working on that next.
This commit is contained in:
parent
4c9e56b163
commit
5be7f69d72
|
@ -56,7 +56,11 @@ static HRESULT WINAPI IDirectSoundNotifyImpl_QueryInterface(
|
|||
ICOM_THIS(IDirectSoundNotifyImpl,iface);
|
||||
|
||||
TRACE("(%p,%s,%p)\n",This,debugstr_guid(riid),ppobj);
|
||||
return IDirectSoundBuffer8_QueryInterface((LPDIRECTSOUNDBUFFER8)This->dsb, riid, ppobj);
|
||||
if (This->dsb)
|
||||
return IDirectSoundBuffer8_QueryInterface((LPDIRECTSOUNDBUFFER8)This->dsb, riid, ppobj);
|
||||
else if (This->dscb)
|
||||
return IDirectSoundCaptureBuffer8_QueryInterface((LPDIRECTSOUNDCAPTUREBUFFER8)This->dscb, riid, ppobj);
|
||||
return DSERR_GENERIC;
|
||||
}
|
||||
|
||||
static ULONG WINAPI IDirectSoundNotifyImpl_AddRef(LPDIRECTSOUNDNOTIFY iface) {
|
||||
|
@ -77,7 +81,10 @@ static ULONG WINAPI IDirectSoundNotifyImpl_Release(LPDIRECTSOUNDNOTIFY iface) {
|
|||
|
||||
ref = InterlockedDecrement(&(This->ref));
|
||||
if (!ref) {
|
||||
IDirectSoundBuffer8_Release((LPDIRECTSOUNDBUFFER8)This->dsb);
|
||||
if (This->dsb)
|
||||
IDirectSoundBuffer8_Release((LPDIRECTSOUNDBUFFER8)This->dsb);
|
||||
else if (This->dscb)
|
||||
IDirectSoundCaptureBuffer_Release((LPDIRECTSOUNDCAPTUREBUFFER8)This->dscb);
|
||||
HeapFree(GetProcessHeap(),0,This);
|
||||
return 0;
|
||||
}
|
||||
|
@ -96,17 +103,30 @@ static HRESULT WINAPI IDirectSoundNotifyImpl_SetNotificationPositions(
|
|||
TRACE("notify at %ld to 0x%08lx\n",
|
||||
notify[i].dwOffset,(DWORD)notify[i].hEventNotify);
|
||||
}
|
||||
This->dsb->notifies = HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,This->dsb->notifies,(This->dsb->nrofnotifies+howmuch)*sizeof(DSBPOSITIONNOTIFY));
|
||||
memcpy( This->dsb->notifies+This->dsb->nrofnotifies,
|
||||
notify,
|
||||
howmuch*sizeof(DSBPOSITIONNOTIFY)
|
||||
);
|
||||
This->dsb->nrofnotifies+=howmuch;
|
||||
if (This->dsb) {
|
||||
This->dsb->notifies = HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,This->dsb->notifies,(This->dsb->nrofnotifies+howmuch)*sizeof(DSBPOSITIONNOTIFY));
|
||||
memcpy( This->dsb->notifies+This->dsb->nrofnotifies,
|
||||
notify,
|
||||
howmuch*sizeof(DSBPOSITIONNOTIFY)
|
||||
);
|
||||
This->dsb->nrofnotifies+=howmuch;
|
||||
} else if (This->dscb) {
|
||||
TRACE("notifies = %p, nrofnotifies = %d\n", This->dscb->notifies, This->dscb->nrofnotifies);
|
||||
This->dscb->notifies = HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,This->dscb->notifies,(This->dscb->nrofnotifies+howmuch)*sizeof(DSBPOSITIONNOTIFY));
|
||||
memcpy( This->dscb->notifies+This->dscb->nrofnotifies,
|
||||
notify,
|
||||
howmuch*sizeof(DSBPOSITIONNOTIFY)
|
||||
);
|
||||
This->dscb->nrofnotifies+=howmuch;
|
||||
TRACE("notifies = %p, nrofnotifies = %d\n", This->dscb->notifies, This->dscb->nrofnotifies);
|
||||
}
|
||||
else
|
||||
return DSERR_INVALIDPARAM;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
static ICOM_VTABLE(IDirectSoundNotify) dsnvt =
|
||||
ICOM_VTABLE(IDirectSoundNotify) dsnvt =
|
||||
{
|
||||
ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
|
||||
IDirectSoundNotifyImpl_QueryInterface,
|
||||
|
@ -798,6 +818,7 @@ static HRESULT WINAPI IDirectSoundBufferImpl_QueryInterface(
|
|||
dsn = (IDirectSoundNotifyImpl*)HeapAlloc(GetProcessHeap(),0,sizeof(*dsn));
|
||||
dsn->ref = 1;
|
||||
dsn->dsb = This;
|
||||
dsn->dscb = 0;
|
||||
IDirectSoundBuffer8_AddRef(iface);
|
||||
ICOM_VTBL(dsn) = &dsnvt;
|
||||
*ppobj = (LPVOID)dsn;
|
||||
|
@ -815,7 +836,7 @@ static HRESULT WINAPI IDirectSoundBufferImpl_QueryInterface(
|
|||
return E_FAIL;
|
||||
}
|
||||
|
||||
if ( IsEqualGUID( &IID_IDirectSound3DListener, riid ) ) {
|
||||
if ( IsEqualGUID( &IID_IDirectSound3DListener, riid ) ) {
|
||||
ERR("app requested IDirectSound3DListener on secondary buffer\n");
|
||||
*ppobj = NULL;
|
||||
return E_FAIL;
|
||||
|
@ -850,7 +871,7 @@ static ICOM_VTABLE(IDirectSoundBuffer8) dsbvt =
|
|||
IDirectSoundBufferImpl_GetFormat,
|
||||
IDirectSoundBufferImpl_GetVolume,
|
||||
IDirectSoundBufferImpl_GetPan,
|
||||
IDirectSoundBufferImpl_GetFrequency,
|
||||
IDirectSoundBufferImpl_GetFrequency,
|
||||
IDirectSoundBufferImpl_GetStatus,
|
||||
IDirectSoundBufferImpl_Initialize,
|
||||
IDirectSoundBufferImpl_Lock,
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -83,7 +83,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(dsound);
|
|||
|
||||
IDirectSoundImpl* dsound = NULL;
|
||||
|
||||
static HRESULT mmErr(UINT err)
|
||||
HRESULT mmErr(UINT err)
|
||||
{
|
||||
switch(err) {
|
||||
case MMSYSERR_NOERROR:
|
||||
|
@ -91,13 +91,18 @@ static HRESULT mmErr(UINT err)
|
|||
case MMSYSERR_ALLOCATED:
|
||||
return DSERR_ALLOCATED;
|
||||
case MMSYSERR_INVALHANDLE:
|
||||
case WAVERR_STILLPLAYING:
|
||||
return DSERR_GENERIC; /* FIXME */
|
||||
case MMSYSERR_NODRIVER:
|
||||
return DSERR_NODRIVER;
|
||||
case MMSYSERR_NOMEM:
|
||||
return DSERR_OUTOFMEMORY;
|
||||
case MMSYSERR_INVALPARAM:
|
||||
case WAVERR_BADFORMAT:
|
||||
case WAVERR_UNPREPARED:
|
||||
return DSERR_INVALIDPARAM;
|
||||
case MMSYSERR_NOTSUPPORTED:
|
||||
return DSERR_UNSUPPORTED;
|
||||
default:
|
||||
FIXME("Unknown MMSYS error %d\n",err);
|
||||
return DSERR_GENERIC;
|
||||
|
|
|
@ -37,6 +37,8 @@ extern int ds_snd_queue_min;
|
|||
*/
|
||||
typedef struct IDirectSoundImpl IDirectSoundImpl;
|
||||
typedef struct IDirectSoundBufferImpl IDirectSoundBufferImpl;
|
||||
typedef struct IDirectSoundCaptureImpl IDirectSoundCaptureImpl;
|
||||
typedef struct IDirectSoundCaptureBufferImpl IDirectSoundCaptureBufferImpl;
|
||||
typedef struct IDirectSoundNotifyImpl IDirectSoundNotifyImpl;
|
||||
typedef struct IDirectSound3DListenerImpl IDirectSound3DListenerImpl;
|
||||
typedef struct IDirectSound3DBufferImpl IDirectSound3DBufferImpl;
|
||||
|
@ -68,9 +70,9 @@ struct IDirectSoundImpl
|
|||
int nrofbuffers;
|
||||
IDirectSoundBufferImpl** buffers;
|
||||
IDirectSound3DListenerImpl* listener;
|
||||
RTL_RWLOCK lock;
|
||||
CRITICAL_SECTION mixlock;
|
||||
DSVOLUMEPAN volpan;
|
||||
RTL_RWLOCK lock;
|
||||
CRITICAL_SECTION mixlock;
|
||||
DSVOLUMEPAN volpan;
|
||||
};
|
||||
|
||||
/*****************************************************************************
|
||||
|
@ -125,6 +127,64 @@ HRESULT WINAPI PrimaryBuffer_Create(
|
|||
PrimaryBufferImpl **pdsb,
|
||||
LPDSBUFFERDESC dsbd);
|
||||
|
||||
/*****************************************************************************
|
||||
* IDirectSoundCapture implementation structure
|
||||
*/
|
||||
struct IDirectSoundCaptureImpl
|
||||
{
|
||||
/* IUnknown fields */
|
||||
ICOM_VFIELD(IDirectSoundCapture);
|
||||
DWORD ref;
|
||||
|
||||
/* IDirectSoundCaptureImpl fields */
|
||||
GUID guid;
|
||||
BOOL initialized;
|
||||
|
||||
/* DirectSound driver stuff */
|
||||
PIDSCDRIVER driver;
|
||||
DSDRIVERDESC drvdesc;
|
||||
DSDRIVERCAPS drvcaps;
|
||||
PIDSDRIVERBUFFER hwbuf;
|
||||
|
||||
/* wave driver info */
|
||||
HWAVEIN hwi;
|
||||
|
||||
/* more stuff */
|
||||
LPBYTE buffer;
|
||||
DWORD buflen;
|
||||
DWORD read_position;
|
||||
|
||||
/* FIXME: this should be a pointer because it can be bigger */
|
||||
WAVEFORMATEX wfx;
|
||||
|
||||
DWORD formats;
|
||||
DWORD channels;
|
||||
IDirectSoundCaptureBufferImpl* capture_buffer;
|
||||
DWORD state;
|
||||
LPWAVEHDR pwave;
|
||||
int index;
|
||||
CRITICAL_SECTION lock;
|
||||
};
|
||||
|
||||
/*****************************************************************************
|
||||
* IDirectSoundCaptureBuffer implementation structure
|
||||
*/
|
||||
struct IDirectSoundCaptureBufferImpl
|
||||
{
|
||||
/* IUnknown fields */
|
||||
ICOM_VFIELD(IDirectSoundCaptureBuffer8);
|
||||
DWORD ref;
|
||||
|
||||
/* IDirectSoundCaptureBufferImpl fields */
|
||||
IDirectSoundCaptureImpl* dsound;
|
||||
CRITICAL_SECTION lock;
|
||||
/* FIXME: don't need this */
|
||||
LPDSCBUFFERDESC pdscbd;
|
||||
LPDSBPOSITIONNOTIFY notifies;
|
||||
int nrofnotifies;
|
||||
DWORD flags;
|
||||
};
|
||||
|
||||
/*****************************************************************************
|
||||
* IDirectSoundNotify implementation structure
|
||||
*/
|
||||
|
@ -134,7 +194,8 @@ struct IDirectSoundNotifyImpl
|
|||
ICOM_VFIELD(IDirectSoundNotify);
|
||||
DWORD ref;
|
||||
/* IDirectSoundNotifyImpl fields */
|
||||
IDirectSoundBufferImpl* dsb;
|
||||
IDirectSoundBufferImpl* dsb;
|
||||
IDirectSoundCaptureBufferImpl* dscb;
|
||||
};
|
||||
|
||||
/*****************************************************************************
|
||||
|
@ -218,10 +279,11 @@ void DSOUND_PerformMix(void);
|
|||
void CALLBACK DSOUND_timer(UINT timerID, UINT msg, DWORD dwUser, DWORD dw1, DWORD dw2);
|
||||
void CALLBACK DSOUND_callback(HWAVEOUT hwo, UINT msg, DWORD dwUser, DWORD dw1, DWORD dw2);
|
||||
|
||||
#define STATE_STOPPED 0
|
||||
#define STATE_STARTING 1
|
||||
#define STATE_PLAYING 2
|
||||
#define STATE_STOPPING 3
|
||||
#define STATE_STOPPED 0
|
||||
#define STATE_STARTING 1
|
||||
#define STATE_PLAYING 2
|
||||
#define STATE_CAPTURING 2
|
||||
#define STATE_STOPPING 3
|
||||
|
||||
#define DSOUND_FREQSHIFT (14)
|
||||
|
||||
|
@ -232,3 +294,6 @@ struct PrimaryBuffer {
|
|||
PIDSDRIVERBUFFER hwbuf;
|
||||
DWORD state;
|
||||
};
|
||||
|
||||
extern ICOM_VTABLE(IDirectSoundNotify) dsnvt;
|
||||
extern HRESULT mmErr(UINT err);
|
||||
|
|
|
@ -47,27 +47,6 @@
|
|||
|
||||
WINE_DEFAULT_DEBUG_CHANNEL(dsound);
|
||||
|
||||
static HRESULT mmErr(UINT err)
|
||||
{
|
||||
switch(err) {
|
||||
case MMSYSERR_NOERROR:
|
||||
return DS_OK;
|
||||
case MMSYSERR_ALLOCATED:
|
||||
return DSERR_ALLOCATED;
|
||||
case MMSYSERR_INVALHANDLE:
|
||||
return DSERR_GENERIC; /* FIXME */
|
||||
case MMSYSERR_NODRIVER:
|
||||
return DSERR_NODRIVER;
|
||||
case MMSYSERR_NOMEM:
|
||||
return DSERR_OUTOFMEMORY;
|
||||
case MMSYSERR_INVALPARAM:
|
||||
return DSERR_INVALIDPARAM;
|
||||
default:
|
||||
FIXME("Unknown MMSYS error %d\n",err);
|
||||
return DSERR_GENERIC;
|
||||
}
|
||||
}
|
||||
|
||||
void DSOUND_RecalcPrimary(IDirectSoundImpl *This)
|
||||
{
|
||||
DWORD sw;
|
||||
|
|
|
@ -22,9 +22,9 @@
|
|||
#include <stdlib.h>
|
||||
|
||||
#include "wine/test.h"
|
||||
#include "wine/debug.h"
|
||||
#include "dsound.h"
|
||||
|
||||
|
||||
/* The time slice determines how often we will service the buffer and the
|
||||
* buffer will be four time slices long
|
||||
*/
|
||||
|
@ -369,7 +369,7 @@ static BOOL WINAPI dsenum_callback(LPGUID lpGuid, LPCSTR lpcstrDescription,
|
|||
WAVEFORMATEX wfx;
|
||||
DSCAPS dscaps;
|
||||
|
||||
trace("Testing %s - %s\n",lpcstrDescription,lpcstrModule);
|
||||
trace("Testing %s - %s : %s\n",lpcstrDescription,lpcstrModule,wine_dbgstr_guid(lpGuid));
|
||||
rc=DirectSoundCreate(lpGuid,&dso,NULL);
|
||||
ok(rc==DS_OK,"DirectSoundCreate failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
|
@ -388,6 +388,12 @@ static BOOL WINAPI dsenum_callback(LPGUID lpGuid, LPCSTR lpcstrDescription,
|
|||
dscaps.dwMaxSecondarySampleRate);
|
||||
}
|
||||
|
||||
/* We must call SetCooperativeLevel before calling CreateSoundBuffer */
|
||||
rc=IDirectSound_SetCooperativeLevel(dso,get_hwnd(),DSSCL_PRIORITY);
|
||||
ok(rc==DS_OK,"SetCooperativeLevel failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
goto EXIT;
|
||||
|
||||
/* Testing the primary buffer */
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=DSBCAPS_PRIMARYBUFFER;
|
||||
|
@ -402,6 +408,12 @@ static BOOL WINAPI dsenum_callback(LPGUID lpGuid, LPCSTR lpcstrDescription,
|
|||
IDirectSoundBuffer_Release(dsbo);
|
||||
}
|
||||
|
||||
/* Set the CooperativeLevel back to normal */
|
||||
rc=IDirectSound_SetCooperativeLevel(dso,get_hwnd(),DSSCL_NORMAL);
|
||||
ok(rc==DS_OK,"SetCooperativeLevel failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
goto EXIT;
|
||||
|
||||
/* Testing secondary buffers */
|
||||
init_format(&wfx,11025,8,1);
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
|
@ -446,7 +458,344 @@ static void dsound_out_tests()
|
|||
ok(rc==DS_OK,"DirectSoundEnumerate failed: %ld\n",rc);
|
||||
}
|
||||
|
||||
#define NOTIFICATIONS 5
|
||||
|
||||
typedef struct {
|
||||
char* wave;
|
||||
DWORD wave_len;
|
||||
|
||||
LPDIRECTSOUNDCAPTUREBUFFER dscbo;
|
||||
LPWAVEFORMATEX wfx;
|
||||
DSBPOSITIONNOTIFY posnotify[NOTIFICATIONS];
|
||||
HANDLE event;
|
||||
LPDIRECTSOUNDNOTIFY notify;
|
||||
|
||||
DWORD buffer_size;
|
||||
DWORD read;
|
||||
DWORD offset;
|
||||
|
||||
DWORD last_pos;
|
||||
} capture_state_t;
|
||||
|
||||
static int capture_buffer_service(capture_state_t* state)
|
||||
{
|
||||
HRESULT rc;
|
||||
LPVOID ptr1,ptr2;
|
||||
DWORD len1,len2;
|
||||
DWORD capture_pos,read_pos;
|
||||
LONG size;
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_GetCurrentPosition(state->dscbo,&capture_pos,&read_pos);
|
||||
ok(rc==DS_OK,"GetCurrentPosition failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return 0;
|
||||
|
||||
size = state->wfx->nAvgBytesPerSec/NOTIFICATIONS;
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_Lock(state->dscbo,state->offset,size,&ptr1,&len1,&ptr2,&len2,0);
|
||||
ok(rc==DS_OK,"Lock failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return 0;
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_Unlock(state->dscbo,ptr1,len1,ptr2,len2);
|
||||
ok(rc==DS_OK,"Unlock failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return 0;
|
||||
|
||||
state->offset = (state->offset + size) % state->wfx->nAvgBytesPerSec;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void test_capture_buffer(LPDIRECTSOUNDCAPTURE dsco, LPDIRECTSOUNDCAPTUREBUFFER dscbo)
|
||||
{
|
||||
HRESULT rc;
|
||||
DSCBCAPS dscbcaps;
|
||||
WAVEFORMATEX wfx;
|
||||
DWORD size,status;
|
||||
capture_state_t state;
|
||||
int i;
|
||||
|
||||
/* Private dsound.dll: Error: Invalid caps pointer */
|
||||
rc=IDirectSoundCaptureBuffer_GetCaps(dscbo,0);
|
||||
ok(rc==DSERR_INVALIDPARAM,"GetCaps should have failed: 0x%lx\n",rc);
|
||||
|
||||
/* Private dsound.dll: Error: Invalid caps pointer */
|
||||
dscbcaps.dwSize=0;
|
||||
rc=IDirectSoundCaptureBuffer_GetCaps(dscbo,&dscbcaps);
|
||||
ok(rc==DSERR_INVALIDPARAM,"GetCaps should have failed: 0x%lx\n",rc);
|
||||
|
||||
dscbcaps.dwSize=sizeof(dscbcaps);
|
||||
rc=IDirectSoundCaptureBuffer_GetCaps(dscbo,&dscbcaps);
|
||||
ok(rc==DS_OK,"GetCaps failed: 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
trace(" Caps: size = %ld flags=0x%08lx buffer size=%ld\n",
|
||||
dscbcaps.dwSize,dscbcaps.dwFlags,dscbcaps.dwBufferBytes);
|
||||
}
|
||||
|
||||
/* Query the format size. Note that it may not match sizeof(wfx) */
|
||||
/* Private dsound.dll: Error: Either pwfxFormat or pdwSizeWritten must be non-NULL */
|
||||
rc=IDirectSoundCaptureBuffer_GetFormat(dscbo,NULL,0,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,
|
||||
"GetFormat should have returned an error: rc=0x%lx\n",rc);
|
||||
|
||||
size=0;
|
||||
rc=IDirectSoundCaptureBuffer_GetFormat(dscbo,NULL,0,&size);
|
||||
ok(rc==DS_OK && size!=0,
|
||||
"GetFormat should have returned the needed size: rc=0x%lx size=%ld\n",
|
||||
rc,size);
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_GetFormat(dscbo,&wfx,sizeof(wfx),NULL);
|
||||
ok(rc==DS_OK,"GetFormat failed: 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
trace(" tag=0x%04x %ldx%dx%d avg.B/s=%ld align=%d\n",
|
||||
wfx.wFormatTag,wfx.nSamplesPerSec,wfx.wBitsPerSample,
|
||||
wfx.nChannels,wfx.nAvgBytesPerSec,wfx.nBlockAlign);
|
||||
}
|
||||
|
||||
/* Private dsound.dll: Error: Invalid status pointer */
|
||||
rc=IDirectSoundCaptureBuffer_GetStatus(dscbo,0);
|
||||
ok(rc==DSERR_INVALIDPARAM,"GetStatus should have failed: 0x%lx\n",rc);
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_GetStatus(dscbo,&status);
|
||||
ok(rc==DS_OK,"GetStatus failed: 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
trace(" status=0x%04lx\n",status);
|
||||
}
|
||||
|
||||
ZeroMemory(&state, sizeof(state));
|
||||
state.dscbo=dscbo;
|
||||
state.wfx=&wfx;
|
||||
state.buffer_size=dscbcaps.dwBufferBytes;
|
||||
state.event = CreateEvent( NULL, FALSE, FALSE, NULL );
|
||||
|
||||
/* FIXME: I couldn't get this to work in vc6. */
|
||||
{
|
||||
GUID IID_IDirectSoundNotifyX = { 0xb0210783, 0x89cd, 0x11d0,{ 0xaf, 0x8, 0x0, 0xa0, 0xc9, 0x25, 0xcd, 0x16 } };
|
||||
rc=IDirectSoundCapture_QueryInterface(dscbo,&IID_IDirectSoundNotifyX,(void **)&(state.notify));
|
||||
}
|
||||
ok(rc==DS_OK,"QueryInterface failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
|
||||
for (i = 0; i < NOTIFICATIONS; i++) {
|
||||
state.posnotify[i].dwOffset = (i * (dscbcaps.dwBufferBytes / NOTIFICATIONS)) + (dscbcaps.dwBufferBytes / NOTIFICATIONS) - 1;
|
||||
state.posnotify[i].hEventNotify = state.event;
|
||||
}
|
||||
|
||||
rc=IDirectSoundNotify_SetNotificationPositions(state.notify,NOTIFICATIONS,state.posnotify);
|
||||
ok(rc==DS_OK,"SetNotificationPositions failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_Start(dscbo,DSCBSTART_LOOPING);
|
||||
ok(rc==DS_OK,"Start: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_GetStatus(dscbo,&status);
|
||||
ok(rc==DS_OK,"GetStatus failed: 0x%lx\n",rc);
|
||||
ok(status==(DSCBSTATUS_CAPTURING|DSCBSTATUS_LOOPING),
|
||||
"GetStatus: bad status: %lx",status);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
|
||||
/* wait for the notifications */
|
||||
for (i = 0; i < (NOTIFICATIONS * 2); i++) {
|
||||
rc=MsgWaitForMultipleObjects( 1, &(state.event), FALSE, 100, QS_ALLEVENTS );
|
||||
ok(rc==WAIT_OBJECT_0,"MsgWaitForMultipleObjects failed: 0x%lx\n",rc);
|
||||
if (rc!=WAIT_OBJECT_0)
|
||||
break;
|
||||
if (!capture_buffer_service(&state))
|
||||
break;
|
||||
}
|
||||
|
||||
rc=IDirectSoundCaptureBuffer_Stop(dscbo);
|
||||
ok(rc==DS_OK,"Stop: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
rc=IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
ok(rc==DS_OK,"Release: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
return;
|
||||
}
|
||||
|
||||
static BOOL WINAPI dscenum_callback(LPGUID lpGuid, LPCSTR lpcstrDescription,
|
||||
LPCSTR lpcstrModule, LPVOID lpContext)
|
||||
{
|
||||
HRESULT rc;
|
||||
LPDIRECTSOUNDCAPTURE dsco=NULL;
|
||||
LPDIRECTSOUNDCAPTUREBUFFER dscbo=NULL;
|
||||
DSCBUFFERDESC bufdesc;
|
||||
WAVEFORMATEX wfx;
|
||||
DSCCAPS dsccaps;
|
||||
|
||||
/* Private dsound.dll: Error: Invalid interface buffer */
|
||||
trace("Testing %s - %s : %s\n",lpcstrDescription,lpcstrModule,wine_dbgstr_guid(lpGuid));
|
||||
rc=DirectSoundCaptureCreate(lpGuid,NULL,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"DirectSoundCaptureCreate didn't fail: 0x%lx\n",rc);
|
||||
if (rc==DS_OK)
|
||||
IDirectSoundCapture_Release(dsco);
|
||||
|
||||
rc=DirectSoundCaptureCreate(lpGuid,&dsco,NULL);
|
||||
ok(rc==DS_OK,"DirectSoundCaptureCreate failed: 0x%lx\n",rc);
|
||||
if (rc!=DS_OK)
|
||||
goto EXIT;
|
||||
|
||||
/* Private dsound.dll: Error: Invalid caps buffer */
|
||||
rc=IDirectSoundCapture_GetCaps(dsco,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"GetCaps should have failed: 0x%lx\n",rc);
|
||||
|
||||
/* Private dsound.dll: Error: Invalid caps buffer */
|
||||
dsccaps.dwSize=0;
|
||||
rc=IDirectSoundCapture_GetCaps(dsco,&dsccaps);
|
||||
ok(rc==DSERR_INVALIDPARAM,"GetCaps should have failed: 0x%lx\n",rc);
|
||||
|
||||
dsccaps.dwSize=sizeof(dsccaps);
|
||||
rc=IDirectSoundCapture_GetCaps(dsco,&dsccaps);
|
||||
ok(rc==DS_OK,"GetCaps failed: 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
trace(" DirectSoundCapture Caps: size=%ld flags=0x%08lx formats=%ld channels=%ld\n",
|
||||
dsccaps.dwSize,dsccaps.dwFlags,dsccaps.dwFormats,dsccaps.dwChannels);
|
||||
}
|
||||
|
||||
/* Private dsound.dll: Error: Invalid size */
|
||||
/* Private dsound.dll: Error: Invalid capture buffer description */
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=0;
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=0;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=NULL;
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"CreateCaptureBuffer should have failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
/* Private dsound.dll: Error: Invalid buffer size */
|
||||
/* Private dsound.dll: Error: Invalid capture buffer description */
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=0;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=NULL;
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"CreateCaptureBuffer should have failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
/* Private dsound.dll: Error: Invalid buffer size */
|
||||
/* Private dsound.dll: Error: Invalid capture buffer description */
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
ZeroMemory(&wfx, sizeof(wfx));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=0;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"CreateCaptureBuffer should have failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
/* Private dsound.dll: Error: Invalid buffer size */
|
||||
/* Private dsound.dll: Error: Invalid capture buffer description */
|
||||
init_format(&wfx,11025,8,1);
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=0;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DSERR_INVALIDPARAM,"CreateCaptureBuffer should have failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
init_format(&wfx,11025,8,1);
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=wfx.nAvgBytesPerSec;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
trace(" Testing the capture buffer at %ldx%dx%d\n",
|
||||
wfx.nSamplesPerSec,wfx.wBitsPerSample,wfx.nChannels);
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DS_OK,"CreateCaptureBuffer failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
test_capture_buffer(dsco, dscbo);
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
init_format(&wfx,11025,8,1);
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=DSCBCAPS_WAVEMAPPED;
|
||||
bufdesc.dwBufferBytes=wfx.nAvgBytesPerSec;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
trace(" Testing the capture buffer at %ldx%dx%d\n",
|
||||
wfx.nSamplesPerSec,wfx.wBitsPerSample,wfx.nChannels);
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DS_OK,"CreateCaptureBuffer failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
test_capture_buffer(dsco, dscbo);
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
init_format(&wfx,11025,16,2);
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=0;
|
||||
bufdesc.dwBufferBytes=wfx.nAvgBytesPerSec;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
trace(" Testing the capture buffer at %ldx%dx%d\n",
|
||||
wfx.nSamplesPerSec,wfx.wBitsPerSample,wfx.nChannels);
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DS_OK,"CreateCaptureBuffer failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
test_capture_buffer(dsco, dscbo);
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
init_format(&wfx,11025,16,2);
|
||||
ZeroMemory(&bufdesc, sizeof(bufdesc));
|
||||
bufdesc.dwSize=sizeof(bufdesc);
|
||||
bufdesc.dwFlags=DSCBCAPS_WAVEMAPPED;
|
||||
bufdesc.dwBufferBytes=wfx.nAvgBytesPerSec;
|
||||
bufdesc.dwReserved=0;
|
||||
bufdesc.lpwfxFormat=&wfx;
|
||||
trace(" Testing the capture buffer at %ldx%dx%d\n",
|
||||
wfx.nSamplesPerSec,wfx.wBitsPerSample,wfx.nChannels);
|
||||
rc=IDirectSoundCapture_CreateCaptureBuffer(dsco,&bufdesc,&dscbo,NULL);
|
||||
ok(rc==DS_OK,"CreateCaptureBuffer failed to create a capture buffer 0x%lx\n",rc);
|
||||
if (rc==DS_OK) {
|
||||
test_capture_buffer(dsco, dscbo);
|
||||
IDirectSoundCaptureBuffer_Release(dscbo);
|
||||
}
|
||||
|
||||
EXIT:
|
||||
if (dsco!=NULL)
|
||||
IDirectSoundCapture_Release(dsco);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void dsound_in_tests()
|
||||
{
|
||||
HRESULT rc;
|
||||
rc=DirectSoundCaptureEnumerateA(&dscenum_callback,NULL);
|
||||
ok(rc==DS_OK,"DirectSoundCaptureEnumerate failed: %ld\n",rc);
|
||||
}
|
||||
|
||||
START_TEST(dsound)
|
||||
{
|
||||
dsound_out_tests();
|
||||
dsound_in_tests();
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue