From 7375f7b5edb1147b7881fc7b2a2245989a6989d0 Mon Sep 17 00:00:00 2001 From: Maarten Lankhorst Date: Fri, 4 Apr 2008 14:29:21 -0700 Subject: [PATCH] quartz: Get rid of code duplication wheel and add a flush function --- dlls/quartz/dsoundrender.c | 34 +---------- dlls/quartz/filesource.c | 20 ++----- dlls/quartz/nullrenderer.c | 37 +---------- dlls/quartz/parser.c | 77 +++--------------------- dlls/quartz/pin.c | 141 ++++++++++++++++++++++--------------------- dlls/quartz/pin.h | 23 ++++--- dlls/quartz/transform.c | 65 +------------------- dlls/quartz/videorenderer.c | 32 +---------- 8 files changed, 105 insertions(+), 324 deletions(-) diff --git a/dlls/quartz/dsoundrender.c b/dlls/quartz/dsoundrender.c index 39fc1bc..7a2d461 100644 --- a/dlls/quartz/dsoundrender.c +++ b/dlls/quartz/dsoundrender.c @@ -96,38 +96,6 @@ static HRESULT sound_mod_rate(IBaseFilter *iface) return S_OK; } - -static HRESULT DSoundRender_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - InputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(InputPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &DSoundRender_InputPin_Vtbl; - pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - - static inline HRESULT DSoundRender_GetPos(DSoundRenderImpl *This, DWORD *pPlayPos, DWORD *pWritePos, REFERENCE_TIME *pRefTime) { HRESULT hr; @@ -324,7 +292,7 @@ HRESULT DSoundRender_create(IUnknown * pUnkOuter, LPVOID * ppv) piInput.dir = PINDIR_INPUT; piInput.pFilter = (IBaseFilter *)pDSoundRender; lstrcpynW(piInput.achName, wcsInputPinName, sizeof(piInput.achName) / sizeof(piInput.achName[0])); - hr = DSoundRender_InputPin_Construct(&piInput, DSoundRender_Sample, (LPVOID)pDSoundRender, DSoundRender_QueryAccept, &pDSoundRender->csFilter, (IPin **)&pDSoundRender->pInputPin); + hr = InputPin_Construct(&DSoundRender_InputPin_Vtbl, &piInput, DSoundRender_Sample, pDSoundRender, DSoundRender_QueryAccept, NULL, &pDSoundRender->csFilter, (IPin **)&pDSoundRender->pInputPin); if (SUCCEEDED(hr)) { diff --git a/dlls/quartz/filesource.c b/dlls/quartz/filesource.c index d922081..8be522c 100644 --- a/dlls/quartz/filesource.c +++ b/dlls/quartz/filesource.c @@ -893,23 +893,18 @@ static HRESULT FileAsyncReaderPin_ConnectSpecific(IPin * iface, IPin * pReceiveP static HRESULT FileAsyncReader_Construct(HANDLE hFile, IBaseFilter * pBaseFilter, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) { - FileAsyncReader * pPinImpl; PIN_INFO piOutput; + HRESULT hr; *ppPin = NULL; - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - piOutput.dir = PINDIR_OUTPUT; piOutput.pFilter = pBaseFilter; strcpyW(piOutput.achName, wszOutputPinName); + hr = OutputPin_Construct(&FileAsyncReaderPin_Vtbl, sizeof(FileAsyncReader), &piOutput, NULL, pBaseFilter, AcceptProcAFR, pCritSec, ppPin); - if (SUCCEEDED(OutputPin_Init(&piOutput, NULL, pBaseFilter, AcceptProcAFR, pCritSec, &pPinImpl->pin))) + if (SUCCEEDED(hr)) { - pPinImpl->pin.pin.lpVtbl = &FileAsyncReaderPin_Vtbl; + FileAsyncReader *pPinImpl = (FileAsyncReader *)*ppPin; pPinImpl->lpVtblAR = &FileAsyncReader_Vtbl; pPinImpl->hFile = hFile; pPinImpl->hEvent = CreateEventW(NULL, 0, 0, NULL); @@ -918,13 +913,8 @@ static HRESULT FileAsyncReader_Construct(HANDLE hFile, IBaseFilter * pBaseFilter pPinImpl->pin.pConnectSpecific = FileAsyncReaderPin_ConnectSpecific; InitializeCriticalSection(&pPinImpl->csList); pPinImpl->csList.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": FileAsyncReader.csList"); - - *ppPin = (IPin *)(&pPinImpl->pin.pin.lpVtbl); - return S_OK; } - - CoTaskMemFree(pPinImpl); - return E_FAIL; + return hr; } /* IAsyncReader */ diff --git a/dlls/quartz/nullrenderer.c b/dlls/quartz/nullrenderer.c index 6b543c5..131ea7e 100644 --- a/dlls/quartz/nullrenderer.c +++ b/dlls/quartz/nullrenderer.c @@ -60,7 +60,7 @@ typedef struct NullRendererImpl IReferenceClock * pClock; FILTER_INFO filterInfo; - InputPin * pInputPin; + InputPin *pInputPin; IPin ** ppPins; IUnknown * pUnkOuter; BOOL bUnkOuterValid; @@ -81,38 +81,6 @@ static const IMemInputPinVtbl MemInputPin_Vtbl = MemInputPin_ReceiveCanBlock }; -static HRESULT NullRenderer_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - InputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(InputPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &NullRenderer_InputPin_Vtbl; - pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - - - static HRESULT NullRenderer_Sample(LPVOID iface, IMediaSample * pSample) { LPBYTE pbSrcStream = NULL; @@ -233,7 +201,7 @@ HRESULT NullRenderer_create(IUnknown * pUnkOuter, LPVOID * ppv) piInput.pFilter = (IBaseFilter *)pNullRenderer; lstrcpynW(piInput.achName, wcsInputPinName, sizeof(piInput.achName) / sizeof(piInput.achName[0])); - hr = NullRenderer_InputPin_Construct(&piInput, NullRenderer_Sample, (LPVOID)pNullRenderer, NullRenderer_QueryAccept, &pNullRenderer->csFilter, (IPin **)&pNullRenderer->pInputPin); + hr = InputPin_Construct(&NullRenderer_InputPin_Vtbl, &piInput, NullRenderer_Sample, (LPVOID)pNullRenderer, NullRenderer_QueryAccept, NULL, &pNullRenderer->csFilter, (IPin **)&pNullRenderer->pInputPin); if (SUCCEEDED(hr)) { @@ -594,6 +562,7 @@ static HRESULT WINAPI NullRenderer_InputPin_EndOfStream(IPin * iface) TRACE("(%p/%p)->()\n", This, iface); + InputPin_EndOfStream(iface); hr = IFilterGraph_QueryInterface(((NullRendererImpl*)This->pin.pinInfo.pFilter)->filterInfo.pGraph, &IID_IMediaEventSink, (LPVOID*)&pEventSink); if (SUCCEEDED(hr)) { diff --git a/dlls/quartz/parser.c b/dlls/quartz/parser.c index b09b397..aec49eb 100644 --- a/dlls/quartz/parser.c +++ b/dlls/quartz/parser.c @@ -47,8 +47,6 @@ static HRESULT Parser_ChangeCurrent(IBaseFilter *iface); static HRESULT Parser_ChangeStop(IBaseFilter *iface); static HRESULT Parser_ChangeRate(IBaseFilter *iface); -static HRESULT Parser_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); - static inline ParserImpl *impl_from_IMediaSeeking( IMediaSeeking *iface ) { return (ParserImpl *)((char*)iface - FIELD_OFFSET(ParserImpl, mediaSeeking.lpVtbl)); @@ -92,7 +90,7 @@ HRESULT Parser_Create(ParserImpl* pParser, const CLSID* pClsid, PFN_PROCESS_SAMP MediaSeekingImpl_Init((IBaseFilter*)pParser, stop, current, rate, &pParser->mediaSeeking, &pParser->csFilter); pParser->mediaSeeking.lpVtbl = &Parser_Seeking_Vtbl; - hr = Parser_InputPin_Construct(&piInput, fnProcessSample, (LPVOID)pParser, fnQueryAccept, &pParser->csFilter, (IPin **)&pParser->pInputPin); + hr = PullPin_Construct(&Parser_InputPin_Vtbl, &piInput, fnProcessSample, (LPVOID)pParser, fnQueryAccept, fnCleanup, &pParser->csFilter, (IPin **)&pParser->pInputPin); if (SUCCEEDED(hr)) { @@ -110,40 +108,6 @@ HRESULT Parser_Create(ParserImpl* pParser, const CLSID* pClsid, PFN_PROCESS_SAMP return hr; } -static HRESULT Parser_OutputPin_Init(const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES * props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, const AM_MEDIA_TYPE * pmt, LPCRITICAL_SECTION pCritSec, Parser_OutputPin * pPinImpl) -{ - pPinImpl->pmt = CoTaskMemAlloc(sizeof(AM_MEDIA_TYPE)); - CopyMediaType(pPinImpl->pmt, pmt); - pPinImpl->dwSamplesProcessed = 0; - - return OutputPin_Init(pPinInfo, props, pUserData, pQueryAccept, pCritSec, &pPinImpl->pin); -} - -static HRESULT Parser_OutputPin_Construct(const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES * props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, const AM_MEDIA_TYPE * pmt, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - Parser_OutputPin * pPinImpl; - - *ppPin = NULL; - - assert(pPinInfo->dir == PINDIR_OUTPUT); - - pPinImpl = CoTaskMemAlloc(sizeof(Parser_OutputPin)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(Parser_OutputPin_Init(pPinInfo, props, pUserData, pQueryAccept, pmt, pCritSec, pPinImpl))) - { - pPinImpl->pin.pin.lpVtbl = &Parser_OutputPin_Vtbl; - - *ppPin = (IPin *)pPinImpl; - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - static HRESULT WINAPI Parser_QueryInterface(IBaseFilter * iface, REFIID riid, LPVOID * ppv) { ParserImpl *This = (ParserImpl *)iface; @@ -521,11 +485,17 @@ HRESULT Parser_AddPin(ParserImpl * This, const PIN_INFO * piOutput, ALLOCATOR_PR This->ppPins = CoTaskMemAlloc((This->cStreams + 2) * sizeof(IPin *)); memcpy(This->ppPins, ppOldPins, (This->cStreams + 1) * sizeof(IPin *)); - hr = Parser_OutputPin_Construct(piOutput, props, NULL, Parser_OutputPin_QueryAccept, amt, &This->csFilter, This->ppPins + This->cStreams + 1); + hr = OutputPin_Construct(&Parser_OutputPin_Vtbl, sizeof(Parser_OutputPin), piOutput, props, NULL, Parser_OutputPin_QueryAccept, &This->csFilter, This->ppPins + This->cStreams + 1); if (SUCCEEDED(hr)) { - ((Parser_OutputPin *)(This->ppPins[This->cStreams + 1]))->pin.pin.pUserData = (LPVOID)This->ppPins[This->cStreams + 1]; + IPin *pPin = This->ppPins[This->cStreams + 1]; + Parser_OutputPin *pin = (Parser_OutputPin *)pPin; + pin->pmt = CoTaskMemAlloc(sizeof(AM_MEDIA_TYPE)); + CopyMediaType(pin->pmt, amt); + pin->dwSamplesProcessed = 0; + + pin->pin.pin.pUserData = (LPVOID)This->ppPins[This->cStreams + 1]; This->cStreams++; CoTaskMemFree(ppOldPins); } @@ -718,35 +688,6 @@ static const IPinVtbl Parser_OutputPin_Vtbl = OutputPin_NewSegment }; -static HRESULT Parser_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - PullPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(PullPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &Parser_InputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - static HRESULT WINAPI Parser_InputPin_Disconnect(IPin * iface) { HRESULT hr; diff --git a/dlls/quartz/pin.c b/dlls/quartz/pin.c index 270a3c5..d88b762 100644 --- a/dlls/quartz/pin.c +++ b/dlls/quartz/pin.c @@ -225,38 +225,8 @@ static HRESULT OutputPin_ConnectSpecific(IPin * iface, IPin * pReceivePin, const return hr; } -HRESULT InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - InputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(InputPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &InputPin_Vtbl; - pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - -/* Note that we don't init the vtables here (like C++ constructor) */ -HRESULT InputPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, InputPin * pPinImpl) +static HRESULT InputPin_Init(const IPinVtbl *InputPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, + QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, InputPin * pPinImpl) { TRACE("\n"); @@ -271,21 +241,24 @@ HRESULT InputPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID /* Input pin attributes */ pPinImpl->fnSampleProc = pSampleProc; + pPinImpl->fnCleanProc = pCleanUp; pPinImpl->pAllocator = NULL; pPinImpl->tStart = 0; pPinImpl->tStop = 0; pPinImpl->dRate = 0; + pPinImpl->pin.lpVtbl = InputPin_Vtbl; + pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; return S_OK; } -HRESULT OutputPin_Init(const PIN_INFO * pPinInfo, const ALLOCATOR_PROPERTIES * props, LPVOID pUserData, - QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, OutputPin * pPinImpl) +static HRESULT OutputPin_Init(const IPinVtbl *OutputPin_Vtbl, const PIN_INFO * pPinInfo, const ALLOCATOR_PROPERTIES * props, LPVOID pUserData, + QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, OutputPin * pPinImpl) { TRACE("\n"); /* Common attributes */ - pPinImpl->pin.lpVtbl = &OutputPin_Vtbl; + pPinImpl->pin.lpVtbl = OutputPin_Vtbl; pPinImpl->pin.refCount = 1; pPinImpl->pin.pConnectedTo = NULL; pPinImpl->pin.fnQueryAccept = pQueryAccept; @@ -309,7 +282,34 @@ HRESULT OutputPin_Init(const PIN_INFO * pPinInfo, const ALLOCATOR_PROPERTIES * p return S_OK; } -HRESULT OutputPin_Construct(const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES *props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) +HRESULT InputPin_Construct(const IPinVtbl *InputPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) +{ + InputPin * pPinImpl; + + *ppPin = NULL; + + if (pPinInfo->dir != PINDIR_INPUT) + { + ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); + return E_INVALIDARG; + } + + pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); + + if (!pPinImpl) + return E_OUTOFMEMORY; + + if (SUCCEEDED(InputPin_Init(InputPin_Vtbl, pPinInfo, pSampleProc, pUserData, pQueryAccept, pCleanUp, pCritSec, pPinImpl))) + { + *ppPin = (IPin *)pPinImpl; + return S_OK; + } + + CoTaskMemFree(pPinImpl); + return E_FAIL; +} + +HRESULT OutputPin_Construct(const IPinVtbl *OutputPin_Vtbl, long outputpin_size, const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES *props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) { OutputPin * pPinImpl; @@ -321,15 +321,15 @@ HRESULT OutputPin_Construct(const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES *pro return E_INVALIDARG; } - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); + assert(outputpin_size >= sizeof(OutputPin)); + + pPinImpl = CoTaskMemAlloc(outputpin_size); if (!pPinImpl) return E_OUTOFMEMORY; - if (SUCCEEDED(OutputPin_Init(pPinInfo, props, pUserData, pQueryAccept, pCritSec, pPinImpl))) + if (SUCCEEDED(OutputPin_Init(OutputPin_Vtbl, pPinInfo, props, pUserData, pQueryAccept, pCritSec, pPinImpl))) { - pPinImpl->pin.lpVtbl = &OutputPin_Vtbl; - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); return S_OK; } @@ -1149,38 +1149,11 @@ HRESULT OutputPin_DeliverDisconnect(OutputPin * This) } -HRESULT PullPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - PullPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(PullPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &PullPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - -HRESULT PullPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, PullPin * pPinImpl) +static HRESULT PullPin_Init(const IPinVtbl *PullPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, + QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, PullPin * pPinImpl) { /* Common attributes */ + pPinImpl->pin.lpVtbl = PullPin_Vtbl; pPinImpl->pin.refCount = 1; pPinImpl->pin.pConnectedTo = NULL; pPinImpl->pin.fnQueryAccept = pQueryAccept; @@ -1191,6 +1164,7 @@ HRESULT PullPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID p /* Input pin attributes */ pPinImpl->fnSampleProc = pSampleProc; + pPinImpl->fnCleanProc = pCleanUp; pPinImpl->fnPreConnect = NULL; pPinImpl->pAlloc = NULL; pPinImpl->pReader = NULL; @@ -1205,6 +1179,33 @@ HRESULT PullPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID p return S_OK; } +HRESULT PullPin_Construct(const IPinVtbl *PullPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) +{ + PullPin * pPinImpl; + + *ppPin = NULL; + + if (pPinInfo->dir != PINDIR_INPUT) + { + ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); + return E_INVALIDARG; + } + + pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); + + if (!pPinImpl) + return E_OUTOFMEMORY; + + if (SUCCEEDED(PullPin_Init(PullPin_Vtbl, pPinInfo, pSampleProc, pUserData, pQueryAccept, pCleanUp, pCritSec, pPinImpl))) + { + *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); + return S_OK; + } + + CoTaskMemFree(pPinImpl); + return E_FAIL; +} + HRESULT WINAPI PullPin_ReceiveConnection(IPin * iface, IPin * pReceivePin, const AM_MEDIA_TYPE * pmt) { PIN_DIRECTION pindirReceive; diff --git a/dlls/quartz/pin.h b/dlls/quartz/pin.h index 44400e6..0991963 100644 --- a/dlls/quartz/pin.h +++ b/dlls/quartz/pin.h @@ -35,6 +35,13 @@ typedef HRESULT (* QUERYACCEPTPROC)(LPVOID userdata, const AM_MEDIA_TYPE * pmt); */ typedef HRESULT (* PRECONNECTPROC)(IPin * iface, IPin * pConnectPin); +/* This function is called whenever a cleanup operation has to occur, + * this is usually after a flush, seek, or end of stream notification. + * This code may even be repeated multiple times, so build your code to + * tolerate this behavior. Return value is ignored and should be S_OK. + */ +typedef HRESULT (* CLEANUPPROC) (LPVOID userdata); + typedef struct IPinImpl { const struct IPinVtbl * lpVtbl; @@ -56,6 +63,7 @@ typedef struct InputPin const IMemInputPinVtbl * lpVtblMemInput; IMemAllocator * pAllocator; SAMPLEPROC fnSampleProc; + CLEANUPPROC fnCleanProc; REFERENCE_TIME tStart; REFERENCE_TIME tStop; double dRate; @@ -82,24 +90,19 @@ typedef struct PullPin PRECONNECTPROC fnPreConnect; HANDLE hThread; HANDLE hEventStateChanged; + CLEANUPPROC fnCleanProc; REFERENCE_TIME rtStart; REFERENCE_TIME rtStop; REFERENCE_TIME rtCurrent; + double dRate; FILTER_STATE state; BOOL stop_playback; - double dRate; } PullPin; -/*** Initializers ***/ -HRESULT InputPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, InputPin * pPinImpl); -HRESULT OutputPin_Init(const PIN_INFO * pPinInfo, const ALLOCATOR_PROPERTIES *props, LPVOID pUserData, - QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, OutputPin * pPinImpl); -HRESULT PullPin_Init(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, PullPin * pPinImpl); - /*** Constructors ***/ -HRESULT InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); -HRESULT OutputPin_Construct(const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES *props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); -HRESULT PullPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); +HRESULT InputPin_Construct(const IPinVtbl *InputPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); +HRESULT OutputPin_Construct(const IPinVtbl *OutputPin_Vtbl, long outputpin_size, const PIN_INFO * pPinInfo, ALLOCATOR_PROPERTIES *props, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); +HRESULT PullPin_Construct(const IPinVtbl *PullPin_Vtbl, const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, CLEANUPPROC pCleanUp, LPCRITICAL_SECTION pCritSec, IPin ** ppPin); /**************************/ /*** Pin Implementation ***/ diff --git a/dlls/quartz/transform.c b/dlls/quartz/transform.c index acf9352..5928ba3 100644 --- a/dlls/quartz/transform.c +++ b/dlls/quartz/transform.c @@ -82,67 +82,6 @@ static HRESULT TransformFilter_Output_QueryAccept(LPVOID iface, const AM_MEDIA_T return S_FALSE; } -static HRESULT TransformFilter_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - InputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(InputPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &TransformFilter_InputPin_Vtbl; - pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - -static HRESULT TransformFilter_OutputPin_Construct(const PIN_INFO * pPinInfo, const ALLOCATOR_PROPERTIES *props, - LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, - LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - OutputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_OUTPUT) - { - ERR("Pin direction(%x) != PINDIR_OUTPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(OutputPin_Init(pPinInfo, props, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &TransformFilter_OutputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - static inline TransformFilterImpl *impl_from_IMediaSeeking( IMediaSeeking *iface ) { @@ -241,7 +180,7 @@ HRESULT TransformFilter_Create(TransformFilterImpl* pTransformFilter, const CLSI piOutput.pFilter = (IBaseFilter *)pTransformFilter; lstrcpynW(piOutput.achName, wcsOutputPinName, sizeof(piOutput.achName) / sizeof(piOutput.achName[0])); - hr = TransformFilter_InputPin_Construct(&piInput, TransformFilter_Sample, pTransformFilter, TransformFilter_Input_QueryAccept, &pTransformFilter->csFilter, &pTransformFilter->ppPins[0]); + hr = InputPin_Construct(&TransformFilter_InputPin_Vtbl, &piInput, TransformFilter_Sample, pTransformFilter, TransformFilter_Input_QueryAccept, NULL, &pTransformFilter->csFilter, &pTransformFilter->ppPins[0]); if (SUCCEEDED(hr)) { @@ -251,7 +190,7 @@ HRESULT TransformFilter_Create(TransformFilterImpl* pTransformFilter, const CLSI props.cbBuffer = 0; /* Will be updated at connection time */ props.cBuffers = 2; - hr = TransformFilter_OutputPin_Construct(&piOutput, &props, pTransformFilter, TransformFilter_Output_QueryAccept, &pTransformFilter->csFilter, &pTransformFilter->ppPins[1]); + hr = OutputPin_Construct(&TransformFilter_OutputPin_Vtbl, sizeof(OutputPin), &piOutput, &props, pTransformFilter, TransformFilter_Output_QueryAccept, &pTransformFilter->csFilter, &pTransformFilter->ppPins[1]); if (FAILED(hr)) ERR("Cannot create output pin (%x)\n", hr); diff --git a/dlls/quartz/videorenderer.c b/dlls/quartz/videorenderer.c index 49aae1e..b331211 100644 --- a/dlls/quartz/videorenderer.c +++ b/dlls/quartz/videorenderer.c @@ -261,36 +261,6 @@ static const IMemInputPinVtbl MemInputPin_Vtbl = MemInputPin_ReceiveCanBlock }; -static HRESULT VideoRenderer_InputPin_Construct(const PIN_INFO * pPinInfo, SAMPLEPROC pSampleProc, LPVOID pUserData, QUERYACCEPTPROC pQueryAccept, LPCRITICAL_SECTION pCritSec, IPin ** ppPin) -{ - InputPin * pPinImpl; - - *ppPin = NULL; - - if (pPinInfo->dir != PINDIR_INPUT) - { - ERR("Pin direction(%x) != PINDIR_INPUT\n", pPinInfo->dir); - return E_INVALIDARG; - } - - pPinImpl = CoTaskMemAlloc(sizeof(*pPinImpl)); - - if (!pPinImpl) - return E_OUTOFMEMORY; - - if (SUCCEEDED(InputPin_Init(pPinInfo, pSampleProc, pUserData, pQueryAccept, pCritSec, pPinImpl))) - { - pPinImpl->pin.lpVtbl = &VideoRenderer_InputPin_Vtbl; - pPinImpl->lpVtblMemInput = &MemInputPin_Vtbl; - - *ppPin = (IPin *)(&pPinImpl->pin.lpVtbl); - return S_OK; - } - - CoTaskMemFree(pPinImpl); - return E_FAIL; -} - static DWORD VideoRenderer_SendSampleData(VideoRendererImpl* This, LPBYTE data, DWORD size) { VIDEOINFOHEADER* format; @@ -467,7 +437,7 @@ HRESULT VideoRenderer_create(IUnknown * pUnkOuter, LPVOID * ppv) piInput.pFilter = (IBaseFilter *)pVideoRenderer; lstrcpynW(piInput.achName, wcsInputPinName, sizeof(piInput.achName) / sizeof(piInput.achName[0])); - hr = VideoRenderer_InputPin_Construct(&piInput, VideoRenderer_Sample, (LPVOID)pVideoRenderer, VideoRenderer_QueryAccept, &pVideoRenderer->csFilter, (IPin **)&pVideoRenderer->pInputPin); + hr = InputPin_Construct(&VideoRenderer_InputPin_Vtbl, &piInput, VideoRenderer_Sample, (LPVOID)pVideoRenderer, VideoRenderer_QueryAccept, NULL, &pVideoRenderer->csFilter, (IPin **)&pVideoRenderer->pInputPin); if (SUCCEEDED(hr)) { -- 1.5.4.1