Commit 5be7f69d authored by Robert Reif's avatar Robert Reif Committed by Alexandre Julliard

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.
parent 4c9e56b1
......@@ -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,
......
......@@ -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;
};
/*****************************************************************************
......@@ -126,6 +128,64 @@ HRESULT WINAPI PrimaryBuffer_Create(
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
*/
struct IDirectSoundNotifyImpl
......@@ -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;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment