summaryrefslogtreecommitdiffstats
path: root/loader/dshow
diff options
context:
space:
mode:
Diffstat (limited to 'loader/dshow')
-rw-r--r--loader/dshow/DS_Filter.c7
-rw-r--r--loader/dshow/allocator.c8
-rw-r--r--loader/dshow/graph.c163
-rw-r--r--loader/dshow/graph.h57
-rw-r--r--loader/dshow/guids.c4
-rw-r--r--loader/dshow/guids.h2
-rw-r--r--loader/dshow/interfaces.h28
7 files changed, 265 insertions, 4 deletions
diff --git a/loader/dshow/DS_Filter.c b/loader/dshow/DS_Filter.c
index e3102cf264..693d59c25f 100644
--- a/loader/dshow/DS_Filter.c
+++ b/loader/dshow/DS_Filter.c
@@ -5,6 +5,7 @@
#include "config.h"
#include "DS_Filter.h"
+#include "graph.h"
#include "loader/drv.h"
#include "loader/com.h"
#include <stdio.h>
@@ -125,6 +126,7 @@ DS_Filter* DS_FilterCreate(const char* dllname, const GUID* id,
// char eb[250];
const char* em = NULL;
MemAllocator* tempAll;
+ FilterGraph* graph;
ALLOCATOR_PROPERTIES props,props1;
DS_Filter* This = malloc(sizeof(DS_Filter));
if (!This)
@@ -166,6 +168,7 @@ DS_Filter* DS_FilterCreate(const char* dllname, const GUID* id,
ULONG fetched;
HRESULT result;
unsigned int i;
+ static const uint16_t filter_name[] = { 'F', 'i', 'l', 't', 'e', 'r', 0 };
This->m_iHandle = LoadLibraryA(dllname);
if (!This->m_iHandle)
@@ -199,6 +202,10 @@ DS_Filter* DS_FilterCreate(const char* dllname, const GUID* id,
em = "object does not provide IBaseFilter interface";
break;
}
+
+ graph = FilterGraphCreate();
+ result = This->m_pFilter->vt->JoinFilterGraph(This->m_pFilter, (IFilterGraph*)graph, filter_name);
+
// enumerate pins
result = This->m_pFilter->vt->EnumPins(This->m_pFilter, &enum_pins);
if (result || !enum_pins)
diff --git a/loader/dshow/allocator.c b/loader/dshow/allocator.c
index b75f1bebfb..a90bd9d3d2 100644
--- a/loader/dshow/allocator.c
+++ b/loader/dshow/allocator.c
@@ -116,7 +116,7 @@ static inline avm_list_t* avm_list_find(avm_list_t* head, void* member)
static long MemAllocator_CreateAllocator(GUID* clsid, const GUID* iid, void** ppv)
{
- IMemAllocator* p;
+ IUnknown* p;
int result;
if (!ppv)
return -1;
@@ -124,9 +124,9 @@ static long MemAllocator_CreateAllocator(GUID* clsid, const GUID* iid, void** pp
if (memcmp(clsid, &CLSID_MemoryAllocator, sizeof(GUID)))
return -1;
- p = (IMemAllocator*) MemAllocatorCreate();
- result = p->vt->QueryInterface((IUnknown*)p, iid, ppv);
- p->vt->Release((IUnknown*)p);
+ p = (IUnknown*) MemAllocatorCreate();
+ result = p->vt->QueryInterface(p, iid, ppv);
+ p->vt->Release(p);
return result;
}
diff --git a/loader/dshow/graph.c b/loader/dshow/graph.c
new file mode 100644
index 0000000000..01bf6c7253
--- /dev/null
+++ b/loader/dshow/graph.c
@@ -0,0 +1,163 @@
+/*
+ * Implemention of FilterGraph. Based on allocator.c.
+ * Copyright 2010 Steinar H. Gunderson
+ *
+ * This file is part of MPlayer.
+ *
+ * MPlayer is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * MPlayer is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with MPlayer; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Modified for use with MPlayer, detailed changelog at
+ * http://svn.mplayerhq.hu/mplayer/trunk/
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "config.h"
+#include "loader/com.h"
+#include "loader/dshow/graph.h"
+#include "loader/wine/winerror.h"
+
+// How many FilterGraph objects exist.
+// Used for knowing when to register and unregister the class in COM.
+static int GraphKeeper = 0;
+
+static long FilterGraph_CreateGraph(GUID* clsid, const GUID* iid, void** ppv)
+{
+ IUnknown* p;
+ int result;
+ if (!ppv)
+ return -1;
+ *ppv = 0;
+ if (memcmp(clsid, &CLSID_FilterGraph, sizeof(*clsid)))
+ return -1;
+
+ p = (IUnknown*) FilterGraphCreate();
+ result = p->vt->QueryInterface(p, iid, ppv);
+ p->vt->Release(p);
+
+ return result;
+}
+
+static void FilterGraph_Destroy(FilterGraph* This)
+{
+ Debug printf("FilterGraph_Destroy(%p) called (%d, %d)\n", This, This->refcount, GraphKeeper);
+#ifdef WIN32_LOADER
+ if (--GraphKeeper == 0)
+ UnregisterComClass(&CLSID_FilterGraph, FilterGraph_CreateGraph);
+#endif
+ free(This->vt);
+ free(This);
+}
+
+HRESULT STDCALL FilterGraph_AddFilter(FilterGraph* This,
+ IBaseFilter* pFilter,
+ unsigned short* pName)
+{
+ Debug printf("FilterGraph_AddFilter(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_RemoveFilter(FilterGraph* This, IBaseFilter* pFilter)
+{
+ Debug printf("FilterGraph_RemoveFilter(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_EnumFilters(FilterGraph* This, IEnumFilters** ppEnum)
+{
+ Debug printf("FilterGraph_EnumFilters(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_FindFilterByName(FilterGraph* This,
+ unsigned short* pName,
+ IBaseFilter** ppFilter)
+{
+ Debug printf("FilterGraph_FindFilterByName(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_ConnectDirect(FilterGraph* This,
+ IPin* ppinOut,
+ IPin* ppinIn,
+ const AM_MEDIA_TYPE* pmt)
+{
+ Debug printf("FilterGraph_ConnectDirect(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_Reconnect(FilterGraph* This, IPin* ppin)
+{
+ Debug printf("FilterGraph_Reconnect(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_Disconnect(FilterGraph* This, IPin* ppin)
+{
+ Debug printf("FilterGraph_Disconnect(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+HRESULT STDCALL FilterGraph_SetDefaultSyncSource(FilterGraph* This)
+{
+ Debug printf("FilterGraph_SetDefaultSyncSource(%p) called\n", This);
+ return E_NOTIMPL;
+}
+
+IMPLEMENT_IUNKNOWN(FilterGraph)
+
+FilterGraph* FilterGraphCreate()
+{
+ FilterGraph* This = calloc(1, sizeof(*This));
+
+ if (!This)
+ return NULL;
+
+ Debug printf("FilterGraphCreate() called -> %p\n", This);
+
+ This->refcount = 1;
+
+ This->vt = calloc(1, sizeof(*This->vt));
+
+ if (!This->vt) {
+ free(This);
+ return NULL;
+ }
+
+ This->vt->QueryInterface = FilterGraph_QueryInterface;
+ This->vt->AddRef = FilterGraph_AddRef;
+ This->vt->Release = FilterGraph_Release;
+
+ This->vt->AddFilter = FilterGraph_AddFilter;
+ This->vt->RemoveFilter = FilterGraph_RemoveFilter;
+ This->vt->EnumFilters = FilterGraph_EnumFilters;
+ This->vt->FindFilterByName = FilterGraph_FindFilterByName;
+ This->vt->ConnectDirect = FilterGraph_ConnectDirect;
+ This->vt->Reconnect = FilterGraph_Reconnect;
+ This->vt->Disconnect = FilterGraph_Disconnect;
+ This->vt->SetDefaultSyncSource = FilterGraph_SetDefaultSyncSource;
+
+ This->interfaces[0] = IID_IUnknown;
+ This->interfaces[1] = IID_IFilterGraph;
+
+#ifdef WIN32_LOADER
+ if (GraphKeeper++ == 0)
+ RegisterComClass(&CLSID_FilterGraph, FilterGraph_CreateGraph);
+#endif
+
+ return This;
+}
+
diff --git a/loader/dshow/graph.h b/loader/dshow/graph.h
new file mode 100644
index 0000000000..7667f5a39e
--- /dev/null
+++ b/loader/dshow/graph.h
@@ -0,0 +1,57 @@
+#ifndef MPLAYER_GRAPH_H
+#define MPLAYER_GRAPH_H
+
+/*
+ * Copyright 2010 Steinar H. Gunderson
+ *
+ * This file is part of MPlayer.
+ *
+ * MPlayer is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * MPlayer is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with MPlayer; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+#include "interfaces.h"
+#include "cmediasample.h"
+
+typedef struct FilterGraph FilterGraph;
+
+struct FilterGraph {
+ IFilterGraph_vt* vt;
+ DECLARE_IUNKNOWN();
+ GUID interfaces[2];
+
+ HRESULT STDCALL (*AddFilter)(FilterGraph* This,
+ /* [in] */ IBaseFilter* pFilter,
+ /* [string][in] */ unsigned short* pName);
+ HRESULT STDCALL (*RemoveFilter)(FilterGraph* This,
+ /* [in] */ IBaseFilter* pFilter);
+ HRESULT STDCALL (*EnumFilters)(FilterGraph* This,
+ /* [out] */ IEnumFilters** ppEnum);
+ HRESULT STDCALL (*FindFilterByName)(FilterGraph* This,
+ /* [string][in] */ unsigned short* pName,
+ /* [out] */ IBaseFilter** ppFilter);
+ HRESULT STDCALL (*ConnectDirect)(FilterGraph* This,
+ /* [in] */ IPin* ppinOut,
+ /* [in] */ IPin* ppinIn,
+ /* [in] */ const AM_MEDIA_TYPE* pmt);
+ HRESULT STDCALL (*Reconnect)(FilterGraph* This,
+ /* [in] */ IPin* ppin);
+ HRESULT STDCALL (*Disconnect)(FilterGraph* This,
+ /* [in] */ IPin* ppin);
+ HRESULT STDCALL (*SetDefaultSyncSource)(FilterGraph* This);
+};
+
+FilterGraph* FilterGraphCreate(void);
+
+#endif /* MPLAYER_GRAPH_H */
diff --git a/loader/dshow/guids.c b/loader/dshow/guids.c
index 73cf7f5456..5d793bb14d 100644
--- a/loader/dshow/guids.c
+++ b/loader/dshow/guids.c
@@ -11,6 +11,8 @@ const GUID IID_IBaseFilter={0x56a86895, 0x0ad4, 0x11ce,
{0xb0, 0x3a, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}};
const GUID IID_IEnumPins={0x56a86892, 0x0ad4, 0x11ce,
{0xb0, 0x3a, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}};
+const GUID IID_IFilterGraph={0x56a8689f, 0x0ad4, 0x11ce,
+ {0xb0, 0x3a, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}};
const GUID IID_IEnumMediaTypes={0x89c31040, 0x846b, 0x11ce,
{0x97, 0xd3, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}};
const GUID IID_IMemInputPin={0x56a8689d, 0x0ad4, 0x11ce,
@@ -64,6 +66,8 @@ const GUID MEDIASUBTYPE_I420={0x30323449, 0x0000, 0x0010,
{0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}};
const GUID MEDIASUBTYPE_IF09={0x39304649, 0x0000, 0x0010,
{0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}};
+const GUID CLSID_FilterGraph={0xe436ebb3, 0x524f, 0x11ce,
+ {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}};
const GUID CLSID_MemoryAllocator={0x1e651cc0, 0xb199, 0x11d0,
{0x82, 0x12, 0x00, 0xc0, 0x4f, 0xc3, 0x2c, 0x45}};
const GUID IID_DivxHidden={0x598eba01, 0xb49a, 0x11d2,
diff --git a/loader/dshow/guids.h b/loader/dshow/guids.h
index 80686558b4..76a4970d27 100644
--- a/loader/dshow/guids.h
+++ b/loader/dshow/guids.h
@@ -46,6 +46,7 @@ typedef GUID IID;
extern const GUID IID_IBaseFilter;
extern const GUID IID_IEnumPins;
extern const GUID IID_IEnumMediaTypes;
+extern const GUID IID_IFilterGraph;
extern const GUID IID_IMemInputPin;
extern const GUID IID_IMemAllocator;
extern const GUID IID_IMediaSample;
@@ -54,6 +55,7 @@ extern const GUID IID_Iv50Hidden;
extern const GUID CLSID_DivxDecompressorCF;
extern const GUID IID_IDivxFilterInterface;
extern const GUID CLSID_IV50_Decoder;
+extern const GUID CLSID_FilterGraph;
extern const GUID CLSID_MemoryAllocator;
extern const GUID MEDIATYPE_Video;
// avoid a clash with MinGW-W64 libuuid
diff --git a/loader/dshow/interfaces.h b/loader/dshow/interfaces.h
index 5c927a55be..af9544ada5 100644
--- a/loader/dshow/interfaces.h
+++ b/loader/dshow/interfaces.h
@@ -329,4 +329,32 @@ struct IDivxFilterInterface_vt
HRESULT STDCALL ( *get_AspectRatio )(IDivxFilterInterface* This, int* x, IDivxFilterInterface* Thisit, int* y);
};
+typedef struct IEnumFilters IEnumFilters;
+
+typedef struct IFilterGraph_vt
+{
+ INHERIT_IUNKNOWN();
+
+ HRESULT STDCALL ( *AddFilter )(IFilterGraph* This,
+ /* [in] */ IBaseFilter* pFilter,
+ /* [string][in] */ unsigned short* pName);
+ HRESULT STDCALL ( *RemoveFilter )(IFilterGraph* This,
+ /* [in] */ IBaseFilter* pFilter);
+ HRESULT STDCALL ( *EnumFilters )(IFilterGraph* This,
+ /* [out] */ IEnumFilters** ppEnum);
+ HRESULT STDCALL ( *FindFilterByName )(IFilterGraph* This,
+ /* [string][in] */ unsigned short* pName,
+ /* [out] */ IBaseFilter** ppFilter);
+ HRESULT STDCALL ( *ConnectDirect )(IFilterGraph* This,
+ /* [in] */ IPin* ppinOut,
+ /* [in] */ IPin* ppinIn,
+ /* [in] */ const AM_MEDIA_TYPE* pmt);
+ HRESULT STDCALL ( *Reconnect )(IFilterGraph* This,
+ /* [in] */ IPin* ppin);
+ HRESULT STDCALL ( *Disconnect )(IFilterGraph* This,
+ /* [in] */ IPin* ppin);
+ HRESULT STDCALL ( *SetDefaultSyncSource )(IFilterGraph* This);
+} IFilterGraph_vt;
+struct IFilterGraph { IFilterGraph_vt *vt; };
+
#endif /*MPLAYER_INTERFACES_H */