2 * Copyright (C) 2003 Michael Günnewig
3 * Copyright (C) 2003 CodeWeavers Inc. (Ulrich Czekalla)
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
30 #include "wine/unicode.h"
31 #include "wine/debug.h"
34 WINE_DEFAULT_DEBUG_CHANNEL(msdmo
);
36 #define MSDMO_MAJOR_VERSION 6
38 static const WCHAR szDMORootKey
[] =
40 'D','i','r','e','c','t','S','h','o','w','\\',
41 'M','e','d','i','a','O','b','j','e','c','t','s',0
44 static const WCHAR szDMOInputType
[] =
46 'I','n','p','u','t','T','y','p','e','s',0
49 static const WCHAR szDMOOutputType
[] =
51 'O','u','t','p','u','t','T','y','p','e','s',0
54 static const WCHAR szDMOKeyed
[] =
59 static const WCHAR szDMOCategories
[] =
61 'C','a','t','e','g','o','r','i','e','s',0
64 static const WCHAR szGUIDFmt
[] =
66 '%','0','8','X','-','%','0','4','X','-','%','0','4','X','-','%','0',
67 '2','X','%','0','2','X','-','%','0','2','X','%','0','2','X','%','0','2',
68 'X','%','0','2','X','%','0','2','X','%','0','2','X',0
71 static const WCHAR szCat3Fmt
[] =
73 '%','s','\\','%','s','\\','%','s',0
76 static const WCHAR szCat2Fmt
[] =
78 '%','s','\\','%','s',0
81 static const WCHAR szToGuidFmt
[] =
89 IEnumDMO IEnumDMO_iface
;
95 DMO_PARTIAL_MEDIATYPE
*pInTypes
;
97 DMO_PARTIAL_MEDIATYPE
*pOutTypes
;
101 static inline IEnumDMOImpl
*impl_from_IEnumDMO(IEnumDMO
*iface
)
103 return CONTAINING_RECORD(iface
, IEnumDMOImpl
, IEnumDMO_iface
);
106 static HRESULT
read_types(HKEY root
, LPCWSTR key
, ULONG
*supplied
, ULONG requested
, DMO_PARTIAL_MEDIATYPE
* types
);
108 static const IEnumDMOVtbl edmovt
;
110 static LPWSTR
GUIDToString(LPWSTR lpwstr
, REFGUID lpcguid
)
112 wsprintfW(lpwstr
, szGUIDFmt
, lpcguid
->Data1
, lpcguid
->Data2
,
113 lpcguid
->Data3
, lpcguid
->Data4
[0], lpcguid
->Data4
[1],
114 lpcguid
->Data4
[2], lpcguid
->Data4
[3], lpcguid
->Data4
[4],
115 lpcguid
->Data4
[5], lpcguid
->Data4
[6], lpcguid
->Data4
[7]);
120 static HRESULT
string_to_guid(const WCHAR
*string
, GUID
*guid
)
124 strcpyW(buffer
+ 1, string
);
127 return CLSIDFromString(buffer
, guid
);
130 static BOOL
IsMediaTypeEqual(const DMO_PARTIAL_MEDIATYPE
* mt1
, const DMO_PARTIAL_MEDIATYPE
* mt2
)
133 return (IsEqualCLSID(&mt1
->type
, &mt2
->type
) ||
134 IsEqualCLSID(&mt2
->type
, &GUID_NULL
) ||
135 IsEqualCLSID(&mt1
->type
, &GUID_NULL
)) &&
136 (IsEqualCLSID(&mt1
->subtype
, &mt2
->subtype
) ||
137 IsEqualCLSID(&mt2
->subtype
, &GUID_NULL
) ||
138 IsEqualCLSID(&mt1
->subtype
, &GUID_NULL
));
141 static HRESULT
write_types(HKEY hkey
, LPCWSTR name
, const DMO_PARTIAL_MEDIATYPE
* types
, DWORD count
)
145 if (MSDMO_MAJOR_VERSION
> 5)
147 ret
= RegSetValueExW(hkey
, name
, 0, REG_BINARY
, (const BYTE
*) types
,
148 count
* sizeof(DMO_PARTIAL_MEDIATYPE
));
152 HKEY skey1
,skey2
,skey3
;
156 ret
= RegCreateKeyExW(hkey
, name
, 0, NULL
, REG_OPTION_NON_VOLATILE
,
157 KEY_WRITE
, NULL
, &skey1
, NULL
);
159 return HRESULT_FROM_WIN32(ret
);
161 while (index
< count
)
163 GUIDToString(szGuidKey
,&types
[index
].type
);
164 ret
= RegCreateKeyExW(skey1
, szGuidKey
, 0, NULL
,
165 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &skey2
, NULL
);
166 GUIDToString(szGuidKey
,&types
[index
].subtype
);
167 ret
= RegCreateKeyExW(skey2
, szGuidKey
, 0, NULL
,
168 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &skey3
, NULL
);
176 return HRESULT_FROM_WIN32(ret
);
179 /***************************************************************
180 * DMORegister (MSDMO.@)
182 * Register a DirectX Media Object.
184 HRESULT WINAPI
DMORegister(
187 REFGUID guidCategory
,
190 const DMO_PARTIAL_MEDIATYPE
*pInTypes
,
192 const DMO_PARTIAL_MEDIATYPE
*pOutTypes
203 TRACE("%s %s %s\n", debugstr_w(szName
), debugstr_guid(clsidDMO
), debugstr_guid(guidCategory
));
205 if (IsEqualGUID(guidCategory
, &GUID_NULL
))
208 ret
= RegCreateKeyExW(HKEY_CLASSES_ROOT
, szDMORootKey
, 0, NULL
,
209 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hrkey
, NULL
);
211 return HRESULT_FROM_WIN32(ret
);
213 /* Create clsidDMO key under MediaObjects */
214 ret
= RegCreateKeyExW(hrkey
, GUIDToString(szguid
, clsidDMO
), 0, NULL
,
215 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hkey
, NULL
);
219 /* Set default Name value */
220 ret
= RegSetValueExW(hkey
, NULL
, 0, REG_SZ
, (const BYTE
*) szName
,
221 (strlenW(szName
) + 1) * sizeof(WCHAR
));
224 hres
= write_types(hkey
, szDMOInputType
, pInTypes
, cInTypes
);
226 /* Set OutputTypes */
227 hres
= write_types(hkey
, szDMOOutputType
, pOutTypes
, cOutTypes
);
229 if (dwFlags
& DMO_REGISTERF_IS_KEYED
)
231 /* Create Keyed key */
232 ret
= RegCreateKeyExW(hkey
, szDMOKeyed
, 0, NULL
,
233 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hckey
, NULL
);
239 /* Register the category */
240 ret
= RegCreateKeyExW(hrkey
, szDMOCategories
, 0, NULL
,
241 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hckey
, NULL
);
247 ret
= RegCreateKeyExW(hckey
, GUIDToString(szguid
, guidCategory
), 0, NULL
,
248 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hkey
, NULL
);
251 ret
= RegCreateKeyExW(hkey
, GUIDToString(szguid
, clsidDMO
), 0, NULL
,
252 REG_OPTION_NON_VOLATILE
, KEY_WRITE
, NULL
, &hclskey
, NULL
);
262 RegCloseKey(hclskey
);
266 hres
= HRESULT_FROM_WIN32(ret
);
267 TRACE(" hresult=0x%08x\n", hres
);
271 static HRESULT
unregister_dmo_from_category(const WCHAR
*dmoW
, const WCHAR
*catW
, HKEY categories
)
276 ret
= RegOpenKeyExW(categories
, catW
, 0, KEY_WRITE
, &catkey
);
279 ret
= RegDeleteKeyW(catkey
, dmoW
);
283 return !ret
? S_OK
: S_FALSE
;
286 /***************************************************************
287 * DMOUnregister (MSDMO.@)
289 * Unregister a DirectX Media Object.
291 HRESULT WINAPI
DMOUnregister(REFCLSID dmo
, REFGUID category
)
293 HKEY rootkey
= 0, categorieskey
= 0;
294 WCHAR dmoW
[64], catW
[64];
295 HRESULT hr
= S_FALSE
;
298 TRACE("%s %s\n", debugstr_guid(dmo
), debugstr_guid(category
));
300 ret
= RegOpenKeyExW(HKEY_CLASSES_ROOT
, szDMORootKey
, 0, KEY_WRITE
, &rootkey
);
304 GUIDToString(dmoW
, dmo
);
305 RegDeleteKeyW(rootkey
, dmoW
);
307 /* open 'Categories' */
308 ret
= RegOpenKeyExW(rootkey
, szDMOCategories
, 0, KEY_WRITE
|KEY_ENUMERATE_SUB_KEYS
, &categorieskey
);
309 RegCloseKey(rootkey
);
312 hr
= HRESULT_FROM_WIN32(ret
);
316 /* remove from all categories */
317 if (IsEqualGUID(category
, &GUID_NULL
))
319 DWORD index
= 0, len
= sizeof(catW
)/sizeof(WCHAR
);
321 while (!RegEnumKeyExW(categorieskey
, index
++, catW
, &len
, NULL
, NULL
, NULL
, NULL
))
322 hr
= unregister_dmo_from_category(dmoW
, catW
, categorieskey
);
326 GUIDToString(catW
, category
);
327 hr
= unregister_dmo_from_category(dmoW
, catW
, categorieskey
);
332 RegCloseKey(categorieskey
);
338 /***************************************************************
339 * DMOGetName (MSDMO.@)
341 * Get DMO Name from the registry
343 HRESULT WINAPI
DMOGetName(REFCLSID clsidDMO
, WCHAR name
[])
345 static const INT max_name_len
= 80*sizeof(WCHAR
);
346 DWORD count
= max_name_len
;
351 TRACE("%s %p\n", debugstr_guid(clsidDMO
), name
);
353 if (RegOpenKeyExW(HKEY_CLASSES_ROOT
, szDMORootKey
, 0, KEY_READ
, &hrkey
))
356 ret
= RegOpenKeyExW(hrkey
, GUIDToString(szguid
, clsidDMO
), 0, KEY_READ
, &hkey
);
361 ret
= RegQueryValueExW(hkey
, NULL
, NULL
, NULL
, (LPBYTE
)name
, &count
);
364 if (!ret
&& count
> 1)
366 TRACE("name=%s\n", debugstr_w(name
));
374 static HRESULT
dup_partial_mediatype(const DMO_PARTIAL_MEDIATYPE
*types
, DWORD count
, DMO_PARTIAL_MEDIATYPE
**ret
)
381 *ret
= HeapAlloc(GetProcessHeap(), 0, count
*sizeof(*types
));
383 return E_OUTOFMEMORY
;
385 memcpy(*ret
, types
, count
*sizeof(*types
));
389 /**************************************************************************
390 * IEnumDMO_Constructor
392 static HRESULT
IEnumDMO_Constructor(
393 REFGUID guidCategory
,
396 const DMO_PARTIAL_MEDIATYPE
*pInTypes
,
398 const DMO_PARTIAL_MEDIATYPE
*pOutTypes
,
401 IEnumDMOImpl
* lpedmo
;
406 lpedmo
= HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY
, sizeof(IEnumDMOImpl
));
408 return E_OUTOFMEMORY
;
410 lpedmo
->IEnumDMO_iface
.lpVtbl
= &edmovt
;
413 lpedmo
->category
= *guidCategory
;
414 lpedmo
->dwFlags
= dwFlags
;
415 lpedmo
->cInTypes
= cInTypes
;
416 lpedmo
->cOutTypes
= cOutTypes
;
419 hr
= dup_partial_mediatype(pInTypes
, cInTypes
, &lpedmo
->pInTypes
);
423 hr
= dup_partial_mediatype(pOutTypes
, cOutTypes
, &lpedmo
->pOutTypes
);
427 /* If not filtering by category enum from media objects root */
428 if (IsEqualGUID(guidCategory
, &GUID_NULL
))
430 RegOpenKeyExW(HKEY_CLASSES_ROOT
, szDMORootKey
, 0, KEY_READ
, &lpedmo
->hkey
);
435 WCHAR szKey
[MAX_PATH
];
437 wsprintfW(szKey
, szCat3Fmt
, szDMORootKey
, szDMOCategories
, GUIDToString(szguid
, guidCategory
));
438 RegOpenKeyExW(HKEY_CLASSES_ROOT
, szKey
, 0, KEY_READ
, &lpedmo
->hkey
);
444 IEnumDMO_Release(&lpedmo
->IEnumDMO_iface
);
447 TRACE("returning %p\n", lpedmo
);
448 *obj
= &lpedmo
->IEnumDMO_iface
;
454 /******************************************************************************
457 static ULONG WINAPI
IEnumDMO_fnAddRef(IEnumDMO
* iface
)
459 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
460 ULONG refCount
= InterlockedIncrement(&This
->ref
);
461 TRACE("(%p)->(%d)\n", This
, refCount
);
465 /**************************************************************************
466 * EnumDMO_QueryInterface
468 static HRESULT WINAPI
IEnumDMO_fnQueryInterface(IEnumDMO
* iface
, REFIID riid
, void **ppvObj
)
470 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
472 TRACE("(%p)->(%s %p)\n", This
, debugstr_guid(riid
), ppvObj
);
476 if (IsEqualIID(riid
, &IID_IEnumDMO
) ||
477 IsEqualIID(riid
, &IID_IUnknown
))
480 IEnumDMO_AddRef(iface
);
483 return *ppvObj
? S_OK
: E_NOINTERFACE
;
486 /******************************************************************************
489 static ULONG WINAPI
IEnumDMO_fnRelease(IEnumDMO
* iface
)
491 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
492 ULONG refCount
= InterlockedDecrement(&This
->ref
);
494 TRACE("(%p)->(%d)\n", This
, refCount
);
499 RegCloseKey(This
->hkey
);
500 HeapFree(GetProcessHeap(), 0, This
->pInTypes
);
501 HeapFree(GetProcessHeap(), 0, This
->pOutTypes
);
502 HeapFree(GetProcessHeap(), 0, This
);
508 /******************************************************************************
511 static HRESULT WINAPI
IEnumDMO_fnNext(
516 DWORD
* pcItemsFetched
)
519 WCHAR szNextKey
[MAX_PATH
];
521 WCHAR szKey
[MAX_PATH
];
522 WCHAR szValue
[MAX_PATH
];
529 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
531 TRACE("(%p)->(%d %p %p %p)\n", This
, cItemsToFetch
, pCLSID
, Names
, pcItemsFetched
);
533 if (!pCLSID
|| !Names
)
536 if (!pcItemsFetched
&& cItemsToFetch
> 1)
539 while (count
< cItemsToFetch
)
544 ret
= RegEnumKeyExW(This
->hkey
, This
->index
, szNextKey
, &len
, NULL
, NULL
, NULL
, NULL
);
545 if (ret
!= ERROR_SUCCESS
)
547 hres
= HRESULT_FROM_WIN32(ret
);
551 if (string_to_guid(szNextKey
, &guid
) != S_OK
)
554 TRACE("found %s\n", debugstr_w(szNextKey
));
556 if (!(This
->dwFlags
& DMO_ENUMF_INCLUDE_KEYED
))
558 wsprintfW(szKey
, szCat3Fmt
, szDMORootKey
, szNextKey
, szDMOKeyed
);
559 ret
= RegOpenKeyExW(HKEY_CLASSES_ROOT
, szKey
, 0, KEY_READ
, &hkey
);
560 if (ERROR_SUCCESS
== ret
)
563 /* Skip Keyed entries */
568 wsprintfW(szKey
, szCat2Fmt
, szDMORootKey
, szNextKey
);
569 ret
= RegOpenKeyExW(HKEY_CLASSES_ROOT
, szKey
, 0, KEY_READ
, &hkey
);
570 TRACE("testing %s\n", debugstr_w(szKey
));
576 DMO_PARTIAL_MEDIATYPE
* pInTypes
;
578 hres
= read_types(hkey
, szDMOInputType
, &cInTypes
,
579 sizeof(szValue
)/sizeof(DMO_PARTIAL_MEDIATYPE
),
580 (DMO_PARTIAL_MEDIATYPE
*)szValue
);
588 pInTypes
= (DMO_PARTIAL_MEDIATYPE
*)szValue
;
590 TRACE("read %d intypes for %s:\n", cInTypes
, debugstr_w(szKey
));
591 for (i
= 0; i
< cInTypes
; i
++) {
592 TRACE("intype %d: type %s, subtype %s\n", i
, debugstr_guid(&pInTypes
[i
].type
),
593 debugstr_guid(&pInTypes
[i
].subtype
));
596 for (i
= 0; i
< This
->cInTypes
; i
++)
598 for (j
= 0; j
< cInTypes
; j
++)
600 if (IsMediaTypeEqual(&pInTypes
[j
], &This
->pInTypes
[i
]))
608 if (i
< This
->cInTypes
)
619 DMO_PARTIAL_MEDIATYPE
* pOutTypes
;
621 hres
= read_types(hkey
, szDMOOutputType
, &cOutTypes
,
622 sizeof(szValue
)/sizeof(DMO_PARTIAL_MEDIATYPE
),
623 (DMO_PARTIAL_MEDIATYPE
*)szValue
);
631 pOutTypes
= (DMO_PARTIAL_MEDIATYPE
*)szValue
;
633 TRACE("read %d outtypes for %s:\n", cOutTypes
, debugstr_w(szKey
));
634 for (i
= 0; i
< cOutTypes
; i
++) {
635 TRACE("outtype %d: type %s, subtype %s\n", i
, debugstr_guid(&pOutTypes
[i
].type
),
636 debugstr_guid(&pOutTypes
[i
].subtype
));
639 for (i
= 0; i
< This
->cOutTypes
; i
++)
641 for (j
= 0; j
< cOutTypes
; j
++)
643 if (IsMediaTypeEqual(&pOutTypes
[j
], &This
->pOutTypes
[i
]))
651 if (i
< This
->cOutTypes
)
658 /* Media object wasn't filtered so add it to return list */
660 len
= MAX_PATH
* sizeof(WCHAR
);
661 ret
= RegQueryValueExW(hkey
, NULL
, NULL
, NULL
, (LPBYTE
)szValue
, &len
);
662 if (ERROR_SUCCESS
== ret
)
664 Names
[count
] = CoTaskMemAlloc((strlenW(szValue
) + 1) * sizeof(WCHAR
));
666 strcpyW(Names
[count
], szValue
);
668 wsprintfW(szGuidKey
,szToGuidFmt
,szNextKey
);
669 CLSIDFromString(szGuidKey
, &pCLSID
[count
]);
671 TRACE("found match %s %s\n", debugstr_w(szValue
), debugstr_w(szNextKey
));
676 if (pcItemsFetched
) *pcItemsFetched
= count
;
677 if (count
< cItemsToFetch
)
680 TRACE("<-- %i found\n",count
);
685 /******************************************************************************
688 static HRESULT WINAPI
IEnumDMO_fnSkip(IEnumDMO
* iface
, DWORD cItemsToSkip
)
690 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
692 TRACE("(%p)->(%d)\n", This
, cItemsToSkip
);
693 This
->index
+= cItemsToSkip
;
699 /******************************************************************************
702 static HRESULT WINAPI
IEnumDMO_fnReset(IEnumDMO
* iface
)
704 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
706 TRACE("(%p)\n", This
);
713 /******************************************************************************
716 static HRESULT WINAPI
IEnumDMO_fnClone(IEnumDMO
*iface
, IEnumDMO
**ppEnum
)
718 IEnumDMOImpl
*This
= impl_from_IEnumDMO(iface
);
719 TRACE("(%p)->(%p)\n", This
, ppEnum
);
720 return IEnumDMO_Constructor(&This
->category
, This
->dwFlags
, This
->cInTypes
, This
->pInTypes
,
721 This
->cOutTypes
, This
->pOutTypes
, ppEnum
);
725 /***************************************************************
728 * Enumerate DirectX Media Objects in the registry.
730 HRESULT WINAPI
DMOEnum(
734 const DMO_PARTIAL_MEDIATYPE
*pInTypes
,
736 const DMO_PARTIAL_MEDIATYPE
*pOutTypes
,
739 TRACE("%s 0x%08x %d %p %d %p %p\n", debugstr_guid(category
), flags
, cInTypes
, pInTypes
,
740 cOutTypes
, pOutTypes
, ppEnum
);
747 for (i
= 0; i
< cInTypes
; i
++)
748 TRACE("intype %d - type %s, subtype %s\n", i
, debugstr_guid(&pInTypes
[i
].type
),
749 debugstr_guid(&pInTypes
[i
].subtype
));
753 for (i
= 0; i
< cOutTypes
; i
++)
754 TRACE("outtype %d - type %s, subtype %s\n", i
, debugstr_guid(&pOutTypes
[i
].type
),
755 debugstr_guid(&pOutTypes
[i
].subtype
));
759 return IEnumDMO_Constructor(category
, flags
, cInTypes
,
760 pInTypes
, cOutTypes
, pOutTypes
, ppEnum
);
764 static const IEnumDMOVtbl edmovt
=
766 IEnumDMO_fnQueryInterface
,
776 HRESULT
read_types(HKEY root
, LPCWSTR key
, ULONG
*supplied
, ULONG requested
, DMO_PARTIAL_MEDIATYPE
* types
)
780 if (MSDMO_MAJOR_VERSION
> 5)
785 len
= requested
* sizeof(DMO_PARTIAL_MEDIATYPE
);
786 rc
= RegQueryValueExW(root
, key
, NULL
, NULL
, (LPBYTE
) types
, &len
);
787 ret
= HRESULT_FROM_WIN32(rc
);
789 *supplied
= len
/ sizeof(DMO_PARTIAL_MEDIATYPE
);
797 if (ERROR_SUCCESS
== RegOpenKeyExW(root
, key
, 0, KEY_READ
, &hkey
))
800 WCHAR szNextKey
[MAX_PATH
];
802 LONG rc
= ERROR_SUCCESS
;
804 while (rc
== ERROR_SUCCESS
)
807 rc
= RegEnumKeyExW(hkey
, index
, szNextKey
, &len
, NULL
, NULL
, NULL
, NULL
);
808 if (rc
== ERROR_SUCCESS
)
812 LONG rcs
= ERROR_SUCCESS
;
813 WCHAR szSubKey
[MAX_PATH
];
815 RegOpenKeyExW(hkey
, szNextKey
, 0, KEY_READ
, &subk
);
816 while (rcs
== ERROR_SUCCESS
)
819 rcs
= RegEnumKeyExW(subk
, sub_index
, szSubKey
, &len
, NULL
, NULL
, NULL
, NULL
);
820 if (rcs
== ERROR_SUCCESS
)
822 if (*supplied
>= requested
)
826 rc
= ERROR_MORE_DATA
;
827 rcs
= ERROR_MORE_DATA
;
831 wsprintfW(szGuidKey
,szToGuidFmt
,szNextKey
);
832 CLSIDFromString(szGuidKey
, &types
[*supplied
].type
);
833 wsprintfW(szGuidKey
,szToGuidFmt
,szSubKey
);
834 CLSIDFromString(szGuidKey
, &types
[*supplied
].subtype
);
835 TRACE("Adding type %s subtype %s at index %i\n",
836 debugstr_guid(&types
[*supplied
].type
),
837 debugstr_guid(&types
[*supplied
].subtype
),
852 /***************************************************************
853 * DMOGetTypes (MSDMO.@)
855 HRESULT WINAPI
DMOGetTypes(REFCLSID clsidDMO
,
856 ULONG ulInputTypesRequested
,
857 ULONG
* pulInputTypesSupplied
,
858 DMO_PARTIAL_MEDIATYPE
* pInputTypes
,
859 ULONG ulOutputTypesRequested
,
860 ULONG
* pulOutputTypesSupplied
,
861 DMO_PARTIAL_MEDIATYPE
* pOutputTypes
)
867 TRACE ("(%s,%u,%p,%p,%u,%p,%p)\n", debugstr_guid(clsidDMO
), ulInputTypesRequested
,
868 pulInputTypesSupplied
, pInputTypes
, ulOutputTypesRequested
, pulOutputTypesSupplied
,
871 if (ERROR_SUCCESS
!= RegOpenKeyExW(HKEY_CLASSES_ROOT
, szDMORootKey
, 0,
875 if (ERROR_SUCCESS
!= RegOpenKeyExW(root
,GUIDToString(szguid
,clsidDMO
) , 0,
882 if (ulInputTypesRequested
> 0)
884 ret
= read_types(hkey
, szDMOInputType
, pulInputTypesSupplied
, ulInputTypesRequested
, pInputTypes
);
887 *pulInputTypesSupplied
= 0;
889 if (ulOutputTypesRequested
> 0)
892 ret2
= read_types(hkey
, szDMOOutputType
, pulOutputTypesSupplied
, ulOutputTypesRequested
, pOutputTypes
);
898 *pulOutputTypesSupplied
= 0;