Revert "libwine: Move string functions to libwine_port."
[wine.git] / dlls / mfplat / mediatype.c
blobdddea4ba1b783a85183f392610cc92e4ae08686f
1 /*
2 * Copyright 2017 Alistair Leslie-Hughes
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 #define COBJMACROS
21 #include "mfplat_private.h"
23 #include "wine/debug.h"
25 WINE_DEFAULT_DEBUG_CHANNEL(mfplat);
27 struct media_type
29 struct attributes attributes;
30 IMFMediaType IMFMediaType_iface;
33 struct stream_desc
35 struct attributes attributes;
36 IMFStreamDescriptor IMFStreamDescriptor_iface;
37 IMFMediaTypeHandler IMFMediaTypeHandler_iface;
38 DWORD identifier;
39 IMFMediaType **media_types;
40 unsigned int media_types_count;
41 IMFMediaType *current_type;
42 CRITICAL_SECTION cs;
45 struct presentation_desc_entry
47 IMFStreamDescriptor *descriptor;
48 BOOL selected;
51 struct presentation_desc
53 struct attributes attributes;
54 IMFPresentationDescriptor IMFPresentationDescriptor_iface;
55 struct presentation_desc_entry *descriptors;
56 unsigned int count;
57 CRITICAL_SECTION cs;
60 static HRESULT presentation_descriptor_init(struct presentation_desc *object, DWORD count);
62 static inline struct media_type *impl_from_IMFMediaType(IMFMediaType *iface)
64 return CONTAINING_RECORD(iface, struct media_type, IMFMediaType_iface);
67 static inline struct stream_desc *impl_from_IMFStreamDescriptor(IMFStreamDescriptor *iface)
69 return CONTAINING_RECORD(iface, struct stream_desc, IMFStreamDescriptor_iface);
72 static struct stream_desc *impl_from_IMFMediaTypeHandler(IMFMediaTypeHandler *iface)
74 return CONTAINING_RECORD(iface, struct stream_desc, IMFMediaTypeHandler_iface);
77 static struct presentation_desc *impl_from_IMFPresentationDescriptor(IMFPresentationDescriptor *iface)
79 return CONTAINING_RECORD(iface, struct presentation_desc, IMFPresentationDescriptor_iface);
82 static HRESULT WINAPI mediatype_QueryInterface(IMFMediaType *iface, REFIID riid, void **out)
84 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), out);
86 if (IsEqualIID(riid, &IID_IMFMediaType) ||
87 IsEqualIID(riid, &IID_IMFAttributes) ||
88 IsEqualIID(riid, &IID_IUnknown))
90 *out = iface;
91 IMFMediaType_AddRef(iface);
92 return S_OK;
95 WARN("Unsupported %s.\n", debugstr_guid(riid));
96 *out = NULL;
97 return E_NOINTERFACE;
100 static ULONG WINAPI mediatype_AddRef(IMFMediaType *iface)
102 struct media_type *media_type = impl_from_IMFMediaType(iface);
103 ULONG refcount = InterlockedIncrement(&media_type->attributes.ref);
105 TRACE("%p, refcount %u.\n", iface, refcount);
107 return refcount;
110 static ULONG WINAPI mediatype_Release(IMFMediaType *iface)
112 struct media_type *media_type = impl_from_IMFMediaType(iface);
113 ULONG refcount = InterlockedDecrement(&media_type->attributes.ref);
115 TRACE("%p, refcount %u.\n", iface, refcount);
117 if (!refcount)
119 clear_attributes_object(&media_type->attributes);
120 heap_free(media_type);
123 return refcount;
126 static HRESULT WINAPI mediatype_GetItem(IMFMediaType *iface, REFGUID key, PROPVARIANT *value)
128 struct media_type *media_type = impl_from_IMFMediaType(iface);
130 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
132 return IMFAttributes_GetItem(&media_type->attributes.IMFAttributes_iface, key, value);
135 static HRESULT WINAPI mediatype_GetItemType(IMFMediaType *iface, REFGUID key, MF_ATTRIBUTE_TYPE *type)
137 struct media_type *media_type = impl_from_IMFMediaType(iface);
139 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), type);
141 return IMFAttributes_GetItemType(&media_type->attributes.IMFAttributes_iface, key, type);
144 static HRESULT WINAPI mediatype_CompareItem(IMFMediaType *iface, REFGUID key, REFPROPVARIANT value, BOOL *result)
146 struct media_type *media_type = impl_from_IMFMediaType(iface);
148 TRACE("%p, %s, %p, %p.\n", iface, debugstr_attr(key), value, result);
150 return IMFAttributes_CompareItem(&media_type->attributes.IMFAttributes_iface, key, value, result);
153 static HRESULT WINAPI mediatype_Compare(IMFMediaType *iface, IMFAttributes *attrs, MF_ATTRIBUTES_MATCH_TYPE type,
154 BOOL *result)
156 struct media_type *media_type = impl_from_IMFMediaType(iface);
158 TRACE("%p, %p, %d, %p.\n", iface, attrs, type, result);
160 return IMFAttributes_Compare(&media_type->attributes.IMFAttributes_iface, attrs, type, result);
163 static HRESULT WINAPI mediatype_GetUINT32(IMFMediaType *iface, REFGUID key, UINT32 *value)
165 struct media_type *media_type = impl_from_IMFMediaType(iface);
167 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
169 return IMFAttributes_GetUINT32(&media_type->attributes.IMFAttributes_iface, key, value);
172 static HRESULT WINAPI mediatype_GetUINT64(IMFMediaType *iface, REFGUID key, UINT64 *value)
174 struct media_type *media_type = impl_from_IMFMediaType(iface);
176 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
178 return IMFAttributes_GetUINT64(&media_type->attributes.IMFAttributes_iface, key, value);
181 static HRESULT WINAPI mediatype_GetDouble(IMFMediaType *iface, REFGUID key, double *value)
183 struct media_type *media_type = impl_from_IMFMediaType(iface);
185 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
187 return IMFAttributes_GetDouble(&media_type->attributes.IMFAttributes_iface, key, value);
190 static HRESULT WINAPI mediatype_GetGUID(IMFMediaType *iface, REFGUID key, GUID *value)
192 struct media_type *media_type = impl_from_IMFMediaType(iface);
194 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
196 return IMFAttributes_GetGUID(&media_type->attributes.IMFAttributes_iface, key, value);
199 static HRESULT WINAPI mediatype_GetStringLength(IMFMediaType *iface, REFGUID key, UINT32 *length)
201 struct media_type *media_type = impl_from_IMFMediaType(iface);
203 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), length);
205 return IMFAttributes_GetStringLength(&media_type->attributes.IMFAttributes_iface, key, length);
208 static HRESULT WINAPI mediatype_GetString(IMFMediaType *iface, REFGUID key, WCHAR *value,
209 UINT32 size, UINT32 *length)
211 struct media_type *media_type = impl_from_IMFMediaType(iface);
213 TRACE("%p, %s, %p, %u, %p.\n", iface, debugstr_attr(key), value, size, length);
215 return IMFAttributes_GetString(&media_type->attributes.IMFAttributes_iface, key, value, size, length);
218 static HRESULT WINAPI mediatype_GetAllocatedString(IMFMediaType *iface, REFGUID key,
219 WCHAR **value, UINT32 *length)
221 struct media_type *media_type = impl_from_IMFMediaType(iface);
223 TRACE("%p, %s, %p, %p.\n", iface, debugstr_attr(key), value, length);
225 return IMFAttributes_GetAllocatedString(&media_type->attributes.IMFAttributes_iface, key, value, length);
228 static HRESULT WINAPI mediatype_GetBlobSize(IMFMediaType *iface, REFGUID key, UINT32 *size)
230 struct media_type *media_type = impl_from_IMFMediaType(iface);
232 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), size);
234 return IMFAttributes_GetBlobSize(&media_type->attributes.IMFAttributes_iface, key, size);
237 static HRESULT WINAPI mediatype_GetBlob(IMFMediaType *iface, REFGUID key, UINT8 *buf,
238 UINT32 bufsize, UINT32 *blobsize)
240 struct media_type *media_type = impl_from_IMFMediaType(iface);
242 TRACE("%p, %s, %p, %u, %p.\n", iface, debugstr_attr(key), buf, bufsize, blobsize);
244 return IMFAttributes_GetBlob(&media_type->attributes.IMFAttributes_iface, key, buf, bufsize, blobsize);
247 static HRESULT WINAPI mediatype_GetAllocatedBlob(IMFMediaType *iface, REFGUID key, UINT8 **buf, UINT32 *size)
249 struct media_type *media_type = impl_from_IMFMediaType(iface);
251 TRACE("%p, %s, %p, %p.\n", iface, debugstr_attr(key), buf, size);
253 return IMFAttributes_GetAllocatedBlob(&media_type->attributes.IMFAttributes_iface, key, buf, size);
256 static HRESULT WINAPI mediatype_GetUnknown(IMFMediaType *iface, REFGUID key, REFIID riid, void **obj)
258 struct media_type *media_type = impl_from_IMFMediaType(iface);
260 TRACE("%p, %s, %s, %p.\n", iface, debugstr_attr(key), debugstr_guid(riid), obj);
262 return IMFAttributes_GetUnknown(&media_type->attributes.IMFAttributes_iface, key, riid, obj);
265 static HRESULT WINAPI mediatype_SetItem(IMFMediaType *iface, REFGUID key, REFPROPVARIANT value)
267 struct media_type *media_type = impl_from_IMFMediaType(iface);
269 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), value);
271 return IMFAttributes_SetItem(&media_type->attributes.IMFAttributes_iface, key, value);
274 static HRESULT WINAPI mediatype_DeleteItem(IMFMediaType *iface, REFGUID key)
276 struct media_type *media_type = impl_from_IMFMediaType(iface);
278 TRACE("%p, %s.\n", iface, debugstr_attr(key));
280 return IMFAttributes_DeleteItem(&media_type->attributes.IMFAttributes_iface, key);
283 static HRESULT WINAPI mediatype_DeleteAllItems(IMFMediaType *iface)
285 struct media_type *media_type = impl_from_IMFMediaType(iface);
287 TRACE("%p.\n", iface);
289 return IMFAttributes_DeleteAllItems(&media_type->attributes.IMFAttributes_iface);
292 static HRESULT WINAPI mediatype_SetUINT32(IMFMediaType *iface, REFGUID key, UINT32 value)
294 struct media_type *media_type = impl_from_IMFMediaType(iface);
296 TRACE("%p, %s, %u.\n", iface, debugstr_attr(key), value);
298 return IMFAttributes_SetUINT32(&media_type->attributes.IMFAttributes_iface, key, value);
301 static HRESULT WINAPI mediatype_SetUINT64(IMFMediaType *iface, REFGUID key, UINT64 value)
303 struct media_type *media_type = impl_from_IMFMediaType(iface);
305 TRACE("%p, %s, %s.\n", iface, debugstr_attr(key), wine_dbgstr_longlong(value));
307 return IMFAttributes_SetUINT64(&media_type->attributes.IMFAttributes_iface, key, value);
310 static HRESULT WINAPI mediatype_SetDouble(IMFMediaType *iface, REFGUID key, double value)
312 struct media_type *media_type = impl_from_IMFMediaType(iface);
314 TRACE("%p, %s, %f.\n", iface, debugstr_attr(key), value);
316 return IMFAttributes_SetDouble(&media_type->attributes.IMFAttributes_iface, key, value);
319 static HRESULT WINAPI mediatype_SetGUID(IMFMediaType *iface, REFGUID key, REFGUID value)
321 struct media_type *media_type = impl_from_IMFMediaType(iface);
323 TRACE("%p, %s, %s.\n", iface, debugstr_attr(key), debugstr_guid(value));
325 return IMFAttributes_SetGUID(&media_type->attributes.IMFAttributes_iface, key, value);
328 static HRESULT WINAPI mediatype_SetString(IMFMediaType *iface, REFGUID key, const WCHAR *value)
330 struct media_type *media_type = impl_from_IMFMediaType(iface);
332 TRACE("%p, %s, %s.\n", iface, debugstr_attr(key), debugstr_w(value));
334 return IMFAttributes_SetString(&media_type->attributes.IMFAttributes_iface, key, value);
337 static HRESULT WINAPI mediatype_SetBlob(IMFMediaType *iface, REFGUID key, const UINT8 *buf, UINT32 size)
339 struct media_type *media_type = impl_from_IMFMediaType(iface);
341 TRACE("%p, %s, %p, %u.\n", iface, debugstr_attr(key), buf, size);
343 return IMFAttributes_SetBlob(&media_type->attributes.IMFAttributes_iface, key, buf, size);
346 static HRESULT WINAPI mediatype_SetUnknown(IMFMediaType *iface, REFGUID key, IUnknown *unknown)
348 struct media_type *media_type = impl_from_IMFMediaType(iface);
350 TRACE("%p, %s, %p.\n", iface, debugstr_attr(key), unknown);
352 return IMFAttributes_SetUnknown(&media_type->attributes.IMFAttributes_iface, key, unknown);
355 static HRESULT WINAPI mediatype_LockStore(IMFMediaType *iface)
357 struct media_type *media_type = impl_from_IMFMediaType(iface);
359 TRACE("%p.\n", iface);
361 return IMFAttributes_LockStore(&media_type->attributes.IMFAttributes_iface);
364 static HRESULT WINAPI mediatype_UnlockStore(IMFMediaType *iface)
366 struct media_type *media_type = impl_from_IMFMediaType(iface);
368 TRACE("%p.\n", iface);
370 return IMFAttributes_UnlockStore(&media_type->attributes.IMFAttributes_iface);
373 static HRESULT WINAPI mediatype_GetCount(IMFMediaType *iface, UINT32 *count)
375 struct media_type *media_type = impl_from_IMFMediaType(iface);
377 TRACE("%p, %p.\n", iface, count);
379 return IMFAttributes_GetCount(&media_type->attributes.IMFAttributes_iface, count);
382 static HRESULT WINAPI mediatype_GetItemByIndex(IMFMediaType *iface, UINT32 index, GUID *key, PROPVARIANT *value)
384 struct media_type *media_type = impl_from_IMFMediaType(iface);
386 TRACE("%p, %u, %p, %p.\n", iface, index, key, value);
388 return IMFAttributes_GetItemByIndex(&media_type->attributes.IMFAttributes_iface, index, key, value);
391 static HRESULT WINAPI mediatype_CopyAllItems(IMFMediaType *iface, IMFAttributes *dest)
393 struct media_type *media_type = impl_from_IMFMediaType(iface);
395 TRACE("%p, %p.\n", iface, dest);
397 return IMFAttributes_CopyAllItems(&media_type->attributes.IMFAttributes_iface, dest);
400 static HRESULT WINAPI mediatype_GetMajorType(IMFMediaType *iface, GUID *guid)
402 struct media_type *media_type = impl_from_IMFMediaType(iface);
403 TRACE("%p, %p.\n", iface, guid);
404 return IMFAttributes_GetGUID(&media_type->attributes.IMFAttributes_iface, &MF_MT_MAJOR_TYPE, guid);
407 static HRESULT WINAPI mediatype_IsCompressedFormat(IMFMediaType *iface, BOOL *compressed)
409 struct media_type *media_type = impl_from_IMFMediaType(iface);
410 UINT32 value;
412 TRACE("%p, %p.\n", iface, compressed);
414 if (FAILED(IMFAttributes_GetUINT32(&media_type->attributes.IMFAttributes_iface,
415 &MF_MT_ALL_SAMPLES_INDEPENDENT, &value)))
417 value = 0;
420 *compressed = !value;
422 return S_OK;
425 static HRESULT WINAPI mediatype_IsEqual(IMFMediaType *iface, IMFMediaType *type, DWORD *flags)
427 const DWORD full_equality_flags = MF_MEDIATYPE_EQUAL_MAJOR_TYPES | MF_MEDIATYPE_EQUAL_FORMAT_TYPES |
428 MF_MEDIATYPE_EQUAL_FORMAT_DATA | MF_MEDIATYPE_EQUAL_FORMAT_USER_DATA;
429 struct media_type *media_type = impl_from_IMFMediaType(iface);
430 struct comparand
432 IMFAttributes *type;
433 PROPVARIANT value;
434 UINT32 count;
435 GUID guid;
436 HRESULT hr;
437 } left, right, swp;
438 unsigned int i;
439 BOOL result;
441 TRACE("%p, %p, %p.\n", iface, type, flags);
443 *flags = 0;
445 left.type = &media_type->attributes.IMFAttributes_iface;
446 right.type = (IMFAttributes *)type;
448 if (FAILED(IMFAttributes_GetGUID(left.type, &MF_MT_MAJOR_TYPE, &left.guid)))
449 return E_INVALIDARG;
451 if (FAILED(IMFAttributes_GetGUID(right.type, &MF_MT_MAJOR_TYPE, &right.guid)))
452 return E_INVALIDARG;
454 if (IsEqualGUID(&left.guid, &right.guid))
455 *flags |= MF_MEDIATYPE_EQUAL_MAJOR_TYPES;
457 /* Subtypes equal or both missing. */
458 left.hr = IMFAttributes_GetGUID(left.type, &MF_MT_SUBTYPE, &left.guid);
459 right.hr = IMFAttributes_GetGUID(right.type, &MF_MT_SUBTYPE, &right.guid);
461 if ((SUCCEEDED(left.hr) && SUCCEEDED(right.hr) && IsEqualGUID(&left.guid, &right.guid)) ||
462 (FAILED(left.hr) && FAILED(right.hr)))
464 *flags |= MF_MEDIATYPE_EQUAL_FORMAT_TYPES;
467 /* Format data */
468 IMFAttributes_GetCount(left.type, &left.count);
469 IMFAttributes_GetCount(right.type, &right.count);
471 if (right.count < left.count)
473 swp = left;
474 left = right;
475 right = swp;
478 *flags |= MF_MEDIATYPE_EQUAL_FORMAT_DATA;
480 for (i = 0; i < left.count; ++i)
482 PROPVARIANT value;
483 GUID key;
485 if (SUCCEEDED(IMFAttributes_GetItemByIndex(left.type, i, &key, &value)))
487 if (IsEqualGUID(&key, &MF_MT_USER_DATA) ||
488 IsEqualGUID(&key, &MF_MT_FRAME_RATE_RANGE_MIN) ||
489 IsEqualGUID(&key, &MF_MT_FRAME_RATE_RANGE_MAX))
491 PropVariantClear(&value);
492 continue;
495 result = FALSE;
496 IMFAttributes_CompareItem(right.type, &key, &value, &result);
497 PropVariantClear(&value);
498 if (!result)
500 *flags &= ~MF_MEDIATYPE_EQUAL_FORMAT_DATA;
501 break;
506 /* User data */
507 PropVariantInit(&left.value);
508 left.hr = IMFAttributes_GetItem(left.type, &MF_MT_USER_DATA, &left.value);
509 PropVariantInit(&right.value);
510 right.hr = IMFAttributes_GetItem(right.type, &MF_MT_USER_DATA, &right.value);
512 if (SUCCEEDED(left.hr) && SUCCEEDED(left.hr))
514 result = FALSE;
515 IMFAttributes_CompareItem(left.type, &MF_MT_USER_DATA, &left.value, &result);
517 else if (FAILED(left.hr) && FAILED(left.hr))
518 result = TRUE;
520 PropVariantClear(&left.value);
521 PropVariantClear(&right.value);
523 if (result)
524 *flags |= MF_MEDIATYPE_EQUAL_FORMAT_USER_DATA;
526 return *flags == full_equality_flags ? S_OK : S_FALSE;
529 static HRESULT WINAPI mediatype_GetRepresentation(IMFMediaType *iface, GUID guid, void **representation)
531 FIXME("%p, %s, %p.\n", iface, debugstr_guid(&guid), representation);
533 return E_NOTIMPL;
536 static HRESULT WINAPI mediatype_FreeRepresentation(IMFMediaType *iface, GUID guid, void *representation)
538 FIXME("%p, %s, %p.\n", iface, debugstr_guid(&guid), representation);
540 return E_NOTIMPL;
543 static const IMFMediaTypeVtbl mediatypevtbl =
545 mediatype_QueryInterface,
546 mediatype_AddRef,
547 mediatype_Release,
548 mediatype_GetItem,
549 mediatype_GetItemType,
550 mediatype_CompareItem,
551 mediatype_Compare,
552 mediatype_GetUINT32,
553 mediatype_GetUINT64,
554 mediatype_GetDouble,
555 mediatype_GetGUID,
556 mediatype_GetStringLength,
557 mediatype_GetString,
558 mediatype_GetAllocatedString,
559 mediatype_GetBlobSize,
560 mediatype_GetBlob,
561 mediatype_GetAllocatedBlob,
562 mediatype_GetUnknown,
563 mediatype_SetItem,
564 mediatype_DeleteItem,
565 mediatype_DeleteAllItems,
566 mediatype_SetUINT32,
567 mediatype_SetUINT64,
568 mediatype_SetDouble,
569 mediatype_SetGUID,
570 mediatype_SetString,
571 mediatype_SetBlob,
572 mediatype_SetUnknown,
573 mediatype_LockStore,
574 mediatype_UnlockStore,
575 mediatype_GetCount,
576 mediatype_GetItemByIndex,
577 mediatype_CopyAllItems,
578 mediatype_GetMajorType,
579 mediatype_IsCompressedFormat,
580 mediatype_IsEqual,
581 mediatype_GetRepresentation,
582 mediatype_FreeRepresentation
585 /***********************************************************************
586 * MFCreateMediaType (mfplat.@)
588 HRESULT WINAPI MFCreateMediaType(IMFMediaType **media_type)
590 struct media_type *object;
591 HRESULT hr;
593 TRACE("%p.\n", media_type);
595 if (!media_type)
596 return E_INVALIDARG;
598 object = heap_alloc(sizeof(*object));
599 if (!object)
600 return E_OUTOFMEMORY;
602 if (FAILED(hr = init_attributes_object(&object->attributes, 0)))
604 heap_free(object);
605 return hr;
607 object->IMFMediaType_iface.lpVtbl = &mediatypevtbl;
609 *media_type = &object->IMFMediaType_iface;
611 TRACE("Created media type %p.\n", *media_type);
613 return S_OK;
616 static HRESULT WINAPI stream_descriptor_QueryInterface(IMFStreamDescriptor *iface, REFIID riid, void **out)
618 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), out);
620 if (IsEqualIID(riid, &IID_IMFStreamDescriptor) ||
621 IsEqualIID(riid, &IID_IMFAttributes) ||
622 IsEqualIID(riid, &IID_IUnknown))
624 *out = iface;
625 IMFStreamDescriptor_AddRef(iface);
626 return S_OK;
629 WARN("Unsupported %s.\n", debugstr_guid(riid));
630 *out = NULL;
631 return E_NOINTERFACE;
634 static ULONG WINAPI stream_descriptor_AddRef(IMFStreamDescriptor *iface)
636 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
637 ULONG refcount = InterlockedIncrement(&stream_desc->attributes.ref);
639 TRACE("%p, refcount %u.\n", iface, refcount);
641 return refcount;
644 static ULONG WINAPI stream_descriptor_Release(IMFStreamDescriptor *iface)
646 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
647 ULONG refcount = InterlockedDecrement(&stream_desc->attributes.ref);
648 unsigned int i;
650 TRACE("%p, refcount %u.\n", iface, refcount);
652 if (!refcount)
654 for (i = 0; i < stream_desc->media_types_count; ++i)
656 if (stream_desc->media_types[i])
657 IMFMediaType_Release(stream_desc->media_types[i]);
659 heap_free(stream_desc->media_types);
660 if (stream_desc->current_type)
661 IMFMediaType_Release(stream_desc->current_type);
662 clear_attributes_object(&stream_desc->attributes);
663 DeleteCriticalSection(&stream_desc->cs);
664 heap_free(stream_desc);
667 return refcount;
670 static HRESULT WINAPI stream_descriptor_GetItem(IMFStreamDescriptor *iface, REFGUID key, PROPVARIANT *value)
672 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
673 return IMFAttributes_GetItem(&stream_desc->attributes.IMFAttributes_iface, key, value);
676 static HRESULT WINAPI stream_descriptor_GetItemType(IMFStreamDescriptor *iface, REFGUID key, MF_ATTRIBUTE_TYPE *type)
678 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
679 return IMFAttributes_GetItemType(&stream_desc->attributes.IMFAttributes_iface, key, type);
682 static HRESULT WINAPI stream_descriptor_CompareItem(IMFStreamDescriptor *iface, REFGUID key, REFPROPVARIANT value,
683 BOOL *result)
685 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
686 return IMFAttributes_CompareItem(&stream_desc->attributes.IMFAttributes_iface, key, value, result);
689 static HRESULT WINAPI stream_descriptor_Compare(IMFStreamDescriptor *iface, IMFAttributes *theirs,
690 MF_ATTRIBUTES_MATCH_TYPE type, BOOL *result)
692 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
693 return IMFAttributes_Compare(&stream_desc->attributes.IMFAttributes_iface, theirs, type, result);
696 static HRESULT WINAPI stream_descriptor_GetUINT32(IMFStreamDescriptor *iface, REFGUID key, UINT32 *value)
698 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
699 return IMFAttributes_GetUINT32(&stream_desc->attributes.IMFAttributes_iface, key, value);
702 static HRESULT WINAPI stream_descriptor_GetUINT64(IMFStreamDescriptor *iface, REFGUID key, UINT64 *value)
704 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
705 return IMFAttributes_GetUINT64(&stream_desc->attributes.IMFAttributes_iface, key, value);
708 static HRESULT WINAPI stream_descriptor_GetDouble(IMFStreamDescriptor *iface, REFGUID key, double *value)
710 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
711 return IMFAttributes_GetDouble(&stream_desc->attributes.IMFAttributes_iface, key, value);
714 static HRESULT WINAPI stream_descriptor_GetGUID(IMFStreamDescriptor *iface, REFGUID key, GUID *value)
716 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
717 return IMFAttributes_GetGUID(&stream_desc->attributes.IMFAttributes_iface, key, value);
720 static HRESULT WINAPI stream_descriptor_GetStringLength(IMFStreamDescriptor *iface, REFGUID key, UINT32 *length)
722 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
723 return IMFAttributes_GetStringLength(&stream_desc->attributes.IMFAttributes_iface, key, length);
726 static HRESULT WINAPI stream_descriptor_GetString(IMFStreamDescriptor *iface, REFGUID key, WCHAR *value,
727 UINT32 size, UINT32 *length)
729 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
730 return IMFAttributes_GetString(&stream_desc->attributes.IMFAttributes_iface, key, value, size, length);
733 static HRESULT WINAPI stream_descriptor_GetAllocatedString(IMFStreamDescriptor *iface, REFGUID key,
734 WCHAR **value, UINT32 *length)
736 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
737 return IMFAttributes_GetAllocatedString(&stream_desc->attributes.IMFAttributes_iface, key, value, length);
740 static HRESULT WINAPI stream_descriptor_GetBlobSize(IMFStreamDescriptor *iface, REFGUID key, UINT32 *size)
742 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
743 return IMFAttributes_GetBlobSize(&stream_desc->attributes.IMFAttributes_iface, key, size);
746 static HRESULT WINAPI stream_descriptor_GetBlob(IMFStreamDescriptor *iface, REFGUID key, UINT8 *buf,
747 UINT32 bufsize, UINT32 *blobsize)
749 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
750 return IMFAttributes_GetBlob(&stream_desc->attributes.IMFAttributes_iface, key, buf, bufsize, blobsize);
753 static HRESULT WINAPI stream_descriptor_GetAllocatedBlob(IMFStreamDescriptor *iface, REFGUID key, UINT8 **buf,
754 UINT32 *size)
756 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
757 return IMFAttributes_GetAllocatedBlob(&stream_desc->attributes.IMFAttributes_iface, key, buf, size);
760 static HRESULT WINAPI stream_descriptor_GetUnknown(IMFStreamDescriptor *iface, REFGUID key, REFIID riid, void **ppv)
762 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
763 return IMFAttributes_GetUnknown(&stream_desc->attributes.IMFAttributes_iface, key, riid, ppv);
766 static HRESULT WINAPI stream_descriptor_SetItem(IMFStreamDescriptor *iface, REFGUID key, REFPROPVARIANT value)
768 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
769 return IMFAttributes_SetItem(&stream_desc->attributes.IMFAttributes_iface, key, value);
772 static HRESULT WINAPI stream_descriptor_DeleteItem(IMFStreamDescriptor *iface, REFGUID key)
774 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
775 return IMFAttributes_DeleteItem(&stream_desc->attributes.IMFAttributes_iface, key);
778 static HRESULT WINAPI stream_descriptor_DeleteAllItems(IMFStreamDescriptor *iface)
780 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
781 return IMFAttributes_DeleteAllItems(&stream_desc->attributes.IMFAttributes_iface);
784 static HRESULT WINAPI stream_descriptor_SetUINT32(IMFStreamDescriptor *iface, REFGUID key, UINT32 value)
786 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
787 return IMFAttributes_SetUINT32(&stream_desc->attributes.IMFAttributes_iface, key, value);
790 static HRESULT WINAPI stream_descriptor_SetUINT64(IMFStreamDescriptor *iface, REFGUID key, UINT64 value)
792 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
793 return IMFAttributes_SetUINT64(&stream_desc->attributes.IMFAttributes_iface, key, value);
796 static HRESULT WINAPI stream_descriptor_SetDouble(IMFStreamDescriptor *iface, REFGUID key, double value)
798 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
799 return IMFAttributes_SetDouble(&stream_desc->attributes.IMFAttributes_iface, key, value);
802 static HRESULT WINAPI stream_descriptor_SetGUID(IMFStreamDescriptor *iface, REFGUID key, REFGUID value)
804 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
805 return IMFAttributes_SetGUID(&stream_desc->attributes.IMFAttributes_iface, key, value);
808 static HRESULT WINAPI stream_descriptor_SetString(IMFStreamDescriptor *iface, REFGUID key, const WCHAR *value)
810 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
811 return IMFAttributes_SetString(&stream_desc->attributes.IMFAttributes_iface, key, value);
814 static HRESULT WINAPI stream_descriptor_SetBlob(IMFStreamDescriptor *iface, REFGUID key, const UINT8 *buf, UINT32 size)
816 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
817 return IMFAttributes_SetBlob(&stream_desc->attributes.IMFAttributes_iface, key, buf, size);
820 static HRESULT WINAPI stream_descriptor_SetUnknown(IMFStreamDescriptor *iface, REFGUID key, IUnknown *unknown)
822 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
823 return IMFAttributes_SetUnknown(&stream_desc->attributes.IMFAttributes_iface, key, unknown);
826 static HRESULT WINAPI stream_descriptor_LockStore(IMFStreamDescriptor *iface)
828 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
829 return IMFAttributes_LockStore(&stream_desc->attributes.IMFAttributes_iface);
832 static HRESULT WINAPI stream_descriptor_UnlockStore(IMFStreamDescriptor *iface)
834 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
835 return IMFAttributes_UnlockStore(&stream_desc->attributes.IMFAttributes_iface);
838 static HRESULT WINAPI stream_descriptor_GetCount(IMFStreamDescriptor *iface, UINT32 *items)
840 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
841 return IMFAttributes_GetCount(&stream_desc->attributes.IMFAttributes_iface, items);
844 static HRESULT WINAPI stream_descriptor_GetItemByIndex(IMFStreamDescriptor *iface, UINT32 index, GUID *key, PROPVARIANT *value)
846 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
847 return IMFAttributes_GetItemByIndex(&stream_desc->attributes.IMFAttributes_iface, index, key, value);
850 static HRESULT WINAPI stream_descriptor_CopyAllItems(IMFStreamDescriptor *iface, IMFAttributes *dest)
852 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
853 return IMFAttributes_CopyAllItems(&stream_desc->attributes.IMFAttributes_iface, dest);
856 static HRESULT WINAPI stream_descriptor_GetStreamIdentifier(IMFStreamDescriptor *iface, DWORD *identifier)
858 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
860 TRACE("%p, %p.\n", iface, identifier);
862 *identifier = stream_desc->identifier;
864 return S_OK;
867 static HRESULT WINAPI stream_descriptor_GetMediaTypeHandler(IMFStreamDescriptor *iface, IMFMediaTypeHandler **handler)
869 struct stream_desc *stream_desc = impl_from_IMFStreamDescriptor(iface);
871 TRACE("%p, %p.\n", iface, handler);
873 *handler = &stream_desc->IMFMediaTypeHandler_iface;
874 IMFStreamDescriptor_AddRef(iface);
876 return S_OK;
879 static const IMFStreamDescriptorVtbl streamdescriptorvtbl =
881 stream_descriptor_QueryInterface,
882 stream_descriptor_AddRef,
883 stream_descriptor_Release,
884 stream_descriptor_GetItem,
885 stream_descriptor_GetItemType,
886 stream_descriptor_CompareItem,
887 stream_descriptor_Compare,
888 stream_descriptor_GetUINT32,
889 stream_descriptor_GetUINT64,
890 stream_descriptor_GetDouble,
891 stream_descriptor_GetGUID,
892 stream_descriptor_GetStringLength,
893 stream_descriptor_GetString,
894 stream_descriptor_GetAllocatedString,
895 stream_descriptor_GetBlobSize,
896 stream_descriptor_GetBlob,
897 stream_descriptor_GetAllocatedBlob,
898 stream_descriptor_GetUnknown,
899 stream_descriptor_SetItem,
900 stream_descriptor_DeleteItem,
901 stream_descriptor_DeleteAllItems,
902 stream_descriptor_SetUINT32,
903 stream_descriptor_SetUINT64,
904 stream_descriptor_SetDouble,
905 stream_descriptor_SetGUID,
906 stream_descriptor_SetString,
907 stream_descriptor_SetBlob,
908 stream_descriptor_SetUnknown,
909 stream_descriptor_LockStore,
910 stream_descriptor_UnlockStore,
911 stream_descriptor_GetCount,
912 stream_descriptor_GetItemByIndex,
913 stream_descriptor_CopyAllItems,
914 stream_descriptor_GetStreamIdentifier,
915 stream_descriptor_GetMediaTypeHandler
918 static HRESULT WINAPI mediatype_handler_QueryInterface(IMFMediaTypeHandler *iface, REFIID riid, void **obj)
920 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
922 if (IsEqualIID(riid, &IID_IMFMediaTypeHandler) ||
923 IsEqualIID(riid, &IID_IUnknown))
925 *obj = iface;
926 IMFMediaTypeHandler_AddRef(iface);
927 return S_OK;
930 WARN("Unsupported %s.\n", debugstr_guid(riid));
931 *obj = NULL;
932 return E_NOINTERFACE;
935 static ULONG WINAPI mediatype_handler_AddRef(IMFMediaTypeHandler *iface)
937 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
938 return IMFStreamDescriptor_AddRef(&stream_desc->IMFStreamDescriptor_iface);
941 static ULONG WINAPI mediatype_handler_Release(IMFMediaTypeHandler *iface)
943 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
944 return IMFStreamDescriptor_Release(&stream_desc->IMFStreamDescriptor_iface);
947 static HRESULT WINAPI mediatype_handler_IsMediaTypeSupported(IMFMediaTypeHandler *iface, IMFMediaType *in_type,
948 IMFMediaType **out_type)
950 FIXME("%p, %p, %p.\n", iface, in_type, out_type);
952 return E_NOTIMPL;
955 static HRESULT WINAPI mediatype_handler_GetMediaTypeCount(IMFMediaTypeHandler *iface, DWORD *count)
957 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
959 TRACE("%p, %p.\n", iface, count);
961 *count = stream_desc->media_types_count;
963 return S_OK;
966 static HRESULT WINAPI mediatype_handler_GetMediaTypeByIndex(IMFMediaTypeHandler *iface, DWORD index,
967 IMFMediaType **type)
969 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
971 TRACE("%p, %u, %p.\n", iface, index, type);
973 if (index >= stream_desc->media_types_count)
974 return MF_E_NO_MORE_TYPES;
976 if (stream_desc->media_types[index])
978 *type = stream_desc->media_types[index];
979 IMFMediaType_AddRef(*type);
982 return stream_desc->media_types[index] ? S_OK : E_FAIL;
985 static HRESULT WINAPI mediatype_handler_SetCurrentMediaType(IMFMediaTypeHandler *iface, IMFMediaType *type)
987 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
989 TRACE("%p, %p.\n", iface, type);
991 if (!type)
992 return E_POINTER;
994 EnterCriticalSection(&stream_desc->cs);
995 if (stream_desc->current_type)
996 IMFMediaType_Release(stream_desc->current_type);
997 stream_desc->current_type = type;
998 IMFMediaType_AddRef(stream_desc->current_type);
999 LeaveCriticalSection(&stream_desc->cs);
1001 return S_OK;
1004 static HRESULT WINAPI mediatype_handler_GetCurrentMediaType(IMFMediaTypeHandler *iface, IMFMediaType **type)
1006 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
1007 HRESULT hr = S_OK;
1009 TRACE("%p, %p.\n", iface, type);
1011 EnterCriticalSection(&stream_desc->cs);
1012 if (stream_desc->current_type)
1014 *type = stream_desc->current_type;
1015 IMFMediaType_AddRef(*type);
1017 else
1018 hr = MF_E_NOT_INITIALIZED;
1019 LeaveCriticalSection(&stream_desc->cs);
1021 return hr;
1024 static HRESULT WINAPI mediatype_handler_GetMajorType(IMFMediaTypeHandler *iface, GUID *type)
1026 struct stream_desc *stream_desc = impl_from_IMFMediaTypeHandler(iface);
1027 HRESULT hr;
1029 TRACE("%p, %p.\n", iface, type);
1031 EnterCriticalSection(&stream_desc->cs);
1032 if (stream_desc->current_type)
1033 hr = IMFMediaType_GetGUID(stream_desc->current_type, &MF_MT_MAJOR_TYPE, type);
1034 else
1035 hr = MF_E_ATTRIBUTENOTFOUND;
1036 LeaveCriticalSection(&stream_desc->cs);
1038 return hr;
1041 static const IMFMediaTypeHandlerVtbl mediatypehandlervtbl =
1043 mediatype_handler_QueryInterface,
1044 mediatype_handler_AddRef,
1045 mediatype_handler_Release,
1046 mediatype_handler_IsMediaTypeSupported,
1047 mediatype_handler_GetMediaTypeCount,
1048 mediatype_handler_GetMediaTypeByIndex,
1049 mediatype_handler_SetCurrentMediaType,
1050 mediatype_handler_GetCurrentMediaType,
1051 mediatype_handler_GetMajorType,
1054 /***********************************************************************
1055 * MFCreateStreamDescriptor (mfplat.@)
1057 HRESULT WINAPI MFCreateStreamDescriptor(DWORD identifier, DWORD count,
1058 IMFMediaType **types, IMFStreamDescriptor **descriptor)
1060 struct stream_desc *object;
1061 unsigned int i;
1062 HRESULT hr;
1064 TRACE("%d, %d, %p, %p.\n", identifier, count, types, descriptor);
1066 if (!count)
1067 return E_INVALIDARG;
1069 object = heap_alloc_zero(sizeof(*object));
1070 if (!object)
1071 return E_OUTOFMEMORY;
1073 if (FAILED(hr = init_attributes_object(&object->attributes, 0)))
1075 heap_free(object);
1076 return hr;
1078 object->IMFStreamDescriptor_iface.lpVtbl = &streamdescriptorvtbl;
1079 object->IMFMediaTypeHandler_iface.lpVtbl = &mediatypehandlervtbl;
1080 object->identifier = identifier;
1081 object->media_types = heap_alloc(count * sizeof(*object->media_types));
1082 InitializeCriticalSection(&object->cs);
1083 if (!object->media_types)
1085 IMFStreamDescriptor_Release(&object->IMFStreamDescriptor_iface);
1086 return E_OUTOFMEMORY;
1088 for (i = 0; i < count; ++i)
1090 object->media_types[i] = types[i];
1091 if (object->media_types[i])
1092 IMFMediaType_AddRef(object->media_types[i]);
1094 object->media_types_count = count;
1096 *descriptor = &object->IMFStreamDescriptor_iface;
1098 return S_OK;
1101 static HRESULT WINAPI presentation_descriptor_QueryInterface(IMFPresentationDescriptor *iface, REFIID riid, void **out)
1103 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), out);
1105 if (IsEqualIID(riid, &IID_IMFPresentationDescriptor) ||
1106 IsEqualIID(riid, &IID_IMFAttributes) ||
1107 IsEqualIID(riid, &IID_IUnknown))
1109 *out = iface;
1110 IMFPresentationDescriptor_AddRef(iface);
1111 return S_OK;
1114 WARN("Unsupported %s.\n", debugstr_guid(riid));
1115 *out = NULL;
1116 return E_NOINTERFACE;
1119 static ULONG WINAPI presentation_descriptor_AddRef(IMFPresentationDescriptor *iface)
1121 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1122 ULONG refcount = InterlockedIncrement(&presentation_desc->attributes.ref);
1124 TRACE("%p, refcount %u.\n", iface, refcount);
1126 return refcount;
1129 static ULONG WINAPI presentation_descriptor_Release(IMFPresentationDescriptor *iface)
1131 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1132 ULONG refcount = InterlockedDecrement(&presentation_desc->attributes.ref);
1133 unsigned int i;
1135 TRACE("%p, refcount %u.\n", iface, refcount);
1137 if (!refcount)
1139 for (i = 0; i < presentation_desc->count; ++i)
1141 if (presentation_desc->descriptors[i].descriptor)
1142 IMFStreamDescriptor_Release(presentation_desc->descriptors[i].descriptor);
1144 clear_attributes_object(&presentation_desc->attributes);
1145 DeleteCriticalSection(&presentation_desc->cs);
1146 heap_free(presentation_desc->descriptors);
1147 heap_free(presentation_desc);
1150 return refcount;
1153 static HRESULT WINAPI presentation_descriptor_GetItem(IMFPresentationDescriptor *iface, REFGUID key,
1154 PROPVARIANT *value)
1156 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1157 return IMFAttributes_GetItem(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1160 static HRESULT WINAPI presentation_descriptor_GetItemType(IMFPresentationDescriptor *iface, REFGUID key,
1161 MF_ATTRIBUTE_TYPE *type)
1163 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1164 return IMFAttributes_GetItemType(&presentation_desc->attributes.IMFAttributes_iface, key, type);
1167 static HRESULT WINAPI presentation_descriptor_CompareItem(IMFPresentationDescriptor *iface, REFGUID key,
1168 REFPROPVARIANT value, BOOL *result)
1170 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1171 return IMFAttributes_CompareItem(&presentation_desc->attributes.IMFAttributes_iface, key, value, result);
1174 static HRESULT WINAPI presentation_descriptor_Compare(IMFPresentationDescriptor *iface, IMFAttributes *attrs,
1175 MF_ATTRIBUTES_MATCH_TYPE type, BOOL *result)
1177 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1178 return IMFAttributes_Compare(&presentation_desc->attributes.IMFAttributes_iface, attrs, type, result);
1181 static HRESULT WINAPI presentation_descriptor_GetUINT32(IMFPresentationDescriptor *iface, REFGUID key, UINT32 *value)
1183 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1184 return IMFAttributes_GetUINT32(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1187 static HRESULT WINAPI presentation_descriptor_GetUINT64(IMFPresentationDescriptor *iface, REFGUID key, UINT64 *value)
1189 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1190 return IMFAttributes_GetUINT64(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1193 static HRESULT WINAPI presentation_descriptor_GetDouble(IMFPresentationDescriptor *iface, REFGUID key, double *value)
1195 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1196 return IMFAttributes_GetDouble(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1199 static HRESULT WINAPI presentation_descriptor_GetGUID(IMFPresentationDescriptor *iface, REFGUID key, GUID *value)
1201 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1202 return IMFAttributes_GetGUID(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1205 static HRESULT WINAPI presentation_descriptor_GetStringLength(IMFPresentationDescriptor *iface, REFGUID key,
1206 UINT32 *length)
1208 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1209 return IMFAttributes_GetStringLength(&presentation_desc->attributes.IMFAttributes_iface, key, length);
1212 static HRESULT WINAPI presentation_descriptor_GetString(IMFPresentationDescriptor *iface, REFGUID key, WCHAR *value,
1213 UINT32 size, UINT32 *length)
1215 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1216 return IMFAttributes_GetString(&presentation_desc->attributes.IMFAttributes_iface, key, value, size, length);
1219 static HRESULT WINAPI presentation_descriptor_GetAllocatedString(IMFPresentationDescriptor *iface, REFGUID key,
1220 WCHAR **value, UINT32 *length)
1222 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1223 return IMFAttributes_GetAllocatedString(&presentation_desc->attributes.IMFAttributes_iface, key, value, length);
1226 static HRESULT WINAPI presentation_descriptor_GetBlobSize(IMFPresentationDescriptor *iface, REFGUID key, UINT32 *size)
1228 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1229 return IMFAttributes_GetBlobSize(&presentation_desc->attributes.IMFAttributes_iface, key, size);
1232 static HRESULT WINAPI presentation_descriptor_GetBlob(IMFPresentationDescriptor *iface, REFGUID key, UINT8 *buf,
1233 UINT32 bufsize, UINT32 *blobsize)
1235 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1236 return IMFAttributes_GetBlob(&presentation_desc->attributes.IMFAttributes_iface, key, buf, bufsize, blobsize);
1239 static HRESULT WINAPI presentation_descriptor_GetAllocatedBlob(IMFPresentationDescriptor *iface, REFGUID key,
1240 UINT8 **buf, UINT32 *size)
1242 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1243 return IMFAttributes_GetAllocatedBlob(&presentation_desc->attributes.IMFAttributes_iface, key, buf, size);
1246 static HRESULT WINAPI presentation_descriptor_GetUnknown(IMFPresentationDescriptor *iface, REFGUID key,
1247 REFIID riid, void **ppv)
1249 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1250 return IMFAttributes_GetUnknown(&presentation_desc->attributes.IMFAttributes_iface, key, riid, ppv);
1253 static HRESULT WINAPI presentation_descriptor_SetItem(IMFPresentationDescriptor *iface, REFGUID key,
1254 REFPROPVARIANT value)
1256 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1257 return IMFAttributes_SetItem(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1260 static HRESULT WINAPI presentation_descriptor_DeleteItem(IMFPresentationDescriptor *iface, REFGUID key)
1262 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1263 return IMFAttributes_DeleteItem(&presentation_desc->attributes.IMFAttributes_iface, key);
1266 static HRESULT WINAPI presentation_descriptor_DeleteAllItems(IMFPresentationDescriptor *iface)
1268 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1269 return IMFAttributes_DeleteAllItems(&presentation_desc->attributes.IMFAttributes_iface);
1272 static HRESULT WINAPI presentation_descriptor_SetUINT32(IMFPresentationDescriptor *iface, REFGUID key, UINT32 value)
1274 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1275 return IMFAttributes_SetUINT32(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1278 static HRESULT WINAPI presentation_descriptor_SetUINT64(IMFPresentationDescriptor *iface, REFGUID key, UINT64 value)
1280 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1281 return IMFAttributes_SetUINT64(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1284 static HRESULT WINAPI presentation_descriptor_SetDouble(IMFPresentationDescriptor *iface, REFGUID key, double value)
1286 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1287 return IMFAttributes_SetDouble(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1290 static HRESULT WINAPI presentation_descriptor_SetGUID(IMFPresentationDescriptor *iface, REFGUID key, REFGUID value)
1292 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1293 return IMFAttributes_SetGUID(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1296 static HRESULT WINAPI presentation_descriptor_SetString(IMFPresentationDescriptor *iface, REFGUID key,
1297 const WCHAR *value)
1299 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1300 return IMFAttributes_SetString(&presentation_desc->attributes.IMFAttributes_iface, key, value);
1303 static HRESULT WINAPI presentation_descriptor_SetBlob(IMFPresentationDescriptor *iface, REFGUID key, const UINT8 *buf,
1304 UINT32 size)
1306 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1307 return IMFAttributes_SetBlob(&presentation_desc->attributes.IMFAttributes_iface, key, buf, size);
1310 static HRESULT WINAPI presentation_descriptor_SetUnknown(IMFPresentationDescriptor *iface, REFGUID key,
1311 IUnknown *unknown)
1313 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1314 return IMFAttributes_SetUnknown(&presentation_desc->attributes.IMFAttributes_iface, key, unknown);
1317 static HRESULT WINAPI presentation_descriptor_LockStore(IMFPresentationDescriptor *iface)
1319 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1320 return IMFAttributes_LockStore(&presentation_desc->attributes.IMFAttributes_iface);
1323 static HRESULT WINAPI presentation_descriptor_UnlockStore(IMFPresentationDescriptor *iface)
1325 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1326 return IMFAttributes_UnlockStore(&presentation_desc->attributes.IMFAttributes_iface);
1329 static HRESULT WINAPI presentation_descriptor_GetCount(IMFPresentationDescriptor *iface, UINT32 *items)
1331 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1332 return IMFAttributes_GetCount(&presentation_desc->attributes.IMFAttributes_iface, items);
1335 static HRESULT WINAPI presentation_descriptor_GetItemByIndex(IMFPresentationDescriptor *iface, UINT32 index, GUID *key,
1336 PROPVARIANT *value)
1338 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1339 return IMFAttributes_GetItemByIndex(&presentation_desc->attributes.IMFAttributes_iface, index, key, value);
1342 static HRESULT WINAPI presentation_descriptor_CopyAllItems(IMFPresentationDescriptor *iface, IMFAttributes *dest)
1344 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1345 return IMFAttributes_CopyAllItems(&presentation_desc->attributes.IMFAttributes_iface, dest);
1348 static HRESULT WINAPI presentation_descriptor_GetStreamDescriptorCount(IMFPresentationDescriptor *iface, DWORD *count)
1350 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1352 TRACE("%p, %p.\n", iface, count);
1354 *count = presentation_desc->count;
1356 return S_OK;
1359 static HRESULT WINAPI presentation_descriptor_GetStreamDescriptorByIndex(IMFPresentationDescriptor *iface, DWORD index,
1360 BOOL *selected, IMFStreamDescriptor **descriptor)
1362 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1364 TRACE("%p, %u, %p, %p.\n", iface, index, selected, descriptor);
1366 if (index >= presentation_desc->count)
1367 return E_INVALIDARG;
1369 EnterCriticalSection(&presentation_desc->cs);
1370 *selected = presentation_desc->descriptors[index].selected;
1371 LeaveCriticalSection(&presentation_desc->cs);
1373 *descriptor = presentation_desc->descriptors[index].descriptor;
1374 IMFStreamDescriptor_AddRef(*descriptor);
1376 return S_OK;
1379 static HRESULT WINAPI presentation_descriptor_SelectStream(IMFPresentationDescriptor *iface, DWORD index)
1381 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1383 TRACE("%p, %u.\n", iface, index);
1385 if (index >= presentation_desc->count)
1386 return E_INVALIDARG;
1388 EnterCriticalSection(&presentation_desc->cs);
1389 presentation_desc->descriptors[index].selected = TRUE;
1390 LeaveCriticalSection(&presentation_desc->cs);
1392 return S_OK;
1395 static HRESULT WINAPI presentation_descriptor_DeselectStream(IMFPresentationDescriptor *iface, DWORD index)
1397 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1399 TRACE("%p, %u.\n", iface, index);
1401 if (index >= presentation_desc->count)
1402 return E_INVALIDARG;
1404 EnterCriticalSection(&presentation_desc->cs);
1405 presentation_desc->descriptors[index].selected = FALSE;
1406 LeaveCriticalSection(&presentation_desc->cs);
1408 return S_OK;
1411 static HRESULT WINAPI presentation_descriptor_Clone(IMFPresentationDescriptor *iface,
1412 IMFPresentationDescriptor **descriptor)
1414 struct presentation_desc *presentation_desc = impl_from_IMFPresentationDescriptor(iface);
1415 struct presentation_desc *object;
1416 unsigned int i;
1418 TRACE("%p, %p.\n", iface, descriptor);
1420 object = heap_alloc_zero(sizeof(*object));
1421 if (!object)
1422 return E_OUTOFMEMORY;
1424 presentation_descriptor_init(object, presentation_desc->count);
1426 EnterCriticalSection(&presentation_desc->cs);
1428 for (i = 0; i < presentation_desc->count; ++i)
1430 object->descriptors[i] = presentation_desc->descriptors[i];
1431 IMFStreamDescriptor_AddRef(object->descriptors[i].descriptor);
1433 /* FIXME: copy attributes */
1435 LeaveCriticalSection(&presentation_desc->cs);
1437 *descriptor = &object->IMFPresentationDescriptor_iface;
1439 return S_OK;
1442 static const IMFPresentationDescriptorVtbl presentationdescriptorvtbl =
1444 presentation_descriptor_QueryInterface,
1445 presentation_descriptor_AddRef,
1446 presentation_descriptor_Release,
1447 presentation_descriptor_GetItem,
1448 presentation_descriptor_GetItemType,
1449 presentation_descriptor_CompareItem,
1450 presentation_descriptor_Compare,
1451 presentation_descriptor_GetUINT32,
1452 presentation_descriptor_GetUINT64,
1453 presentation_descriptor_GetDouble,
1454 presentation_descriptor_GetGUID,
1455 presentation_descriptor_GetStringLength,
1456 presentation_descriptor_GetString,
1457 presentation_descriptor_GetAllocatedString,
1458 presentation_descriptor_GetBlobSize,
1459 presentation_descriptor_GetBlob,
1460 presentation_descriptor_GetAllocatedBlob,
1461 presentation_descriptor_GetUnknown,
1462 presentation_descriptor_SetItem,
1463 presentation_descriptor_DeleteItem,
1464 presentation_descriptor_DeleteAllItems,
1465 presentation_descriptor_SetUINT32,
1466 presentation_descriptor_SetUINT64,
1467 presentation_descriptor_SetDouble,
1468 presentation_descriptor_SetGUID,
1469 presentation_descriptor_SetString,
1470 presentation_descriptor_SetBlob,
1471 presentation_descriptor_SetUnknown,
1472 presentation_descriptor_LockStore,
1473 presentation_descriptor_UnlockStore,
1474 presentation_descriptor_GetCount,
1475 presentation_descriptor_GetItemByIndex,
1476 presentation_descriptor_CopyAllItems,
1477 presentation_descriptor_GetStreamDescriptorCount,
1478 presentation_descriptor_GetStreamDescriptorByIndex,
1479 presentation_descriptor_SelectStream,
1480 presentation_descriptor_DeselectStream,
1481 presentation_descriptor_Clone,
1484 static HRESULT presentation_descriptor_init(struct presentation_desc *object, DWORD count)
1486 HRESULT hr;
1488 if (FAILED(hr = init_attributes_object(&object->attributes, 0)))
1489 return hr;
1490 object->IMFPresentationDescriptor_iface.lpVtbl = &presentationdescriptorvtbl;
1491 object->descriptors = heap_alloc_zero(count * sizeof(*object->descriptors));
1492 InitializeCriticalSection(&object->cs);
1493 if (!object->descriptors)
1495 IMFPresentationDescriptor_Release(&object->IMFPresentationDescriptor_iface);
1496 return E_OUTOFMEMORY;
1498 object->count = count;
1500 return S_OK;
1503 /***********************************************************************
1504 * MFCreatePresentationDescriptor (mfplat.@)
1506 HRESULT WINAPI MFCreatePresentationDescriptor(DWORD count, IMFStreamDescriptor **descriptors,
1507 IMFPresentationDescriptor **out)
1509 struct presentation_desc *object;
1510 unsigned int i;
1511 HRESULT hr;
1513 TRACE("%u, %p, %p.\n", count, descriptors, out);
1515 if (!count)
1516 return E_INVALIDARG;
1518 for (i = 0; i < count; ++i)
1520 if (!descriptors[i])
1521 return E_INVALIDARG;
1524 object = heap_alloc_zero(sizeof(*object));
1525 if (!object)
1526 return E_OUTOFMEMORY;
1528 if (FAILED(hr = presentation_descriptor_init(object, count)))
1530 heap_free(object);
1531 return hr;
1534 for (i = 0; i < count; ++i)
1536 object->descriptors[i].descriptor = descriptors[i];
1537 IMFStreamDescriptor_AddRef(object->descriptors[i].descriptor);
1540 *out = &object->IMFPresentationDescriptor_iface;
1542 return S_OK;
1545 struct uncompressed_video_format
1547 const GUID *subtype;
1548 unsigned int bytes_per_pixel;
1551 static int uncompressed_video_format_compare(const void *a, const void *b)
1553 const GUID *guid = a;
1554 const struct uncompressed_video_format *format = b;
1555 return memcmp(guid, format->subtype, sizeof(*guid));
1558 /***********************************************************************
1559 * MFCalculateImageSize (mfplat.@)
1561 HRESULT WINAPI MFCalculateImageSize(REFGUID subtype, UINT32 width, UINT32 height, UINT32 *size)
1563 static const struct uncompressed_video_format video_formats[] =
1565 { &MFVideoFormat_RGB24, 3 },
1566 { &MFVideoFormat_ARGB32, 4 },
1567 { &MFVideoFormat_RGB32, 4 },
1568 { &MFVideoFormat_RGB565, 2 },
1569 { &MFVideoFormat_RGB555, 2 },
1570 { &MFVideoFormat_A2R10G10B10, 4 },
1571 { &MFVideoFormat_RGB8, 1 },
1572 { &MFVideoFormat_A16B16G16R16F, 8 },
1574 struct uncompressed_video_format *format;
1576 TRACE("%s, %u, %u, %p.\n", debugstr_guid(subtype), width, height, size);
1578 format = bsearch(subtype, video_formats, ARRAY_SIZE(video_formats), sizeof(*video_formats),
1579 uncompressed_video_format_compare);
1580 if (format)
1582 *size = ((width * format->bytes_per_pixel + 3) & ~3) * height;
1584 else
1586 *size = 0;
1589 return format ? S_OK : E_INVALIDARG;
1592 /***********************************************************************
1593 * MFCompareFullToPartialMediaType (mfplat.@)
1595 BOOL WINAPI MFCompareFullToPartialMediaType(IMFMediaType *full_type, IMFMediaType *partial_type)
1597 BOOL result;
1598 GUID major;
1600 TRACE("%p, %p.\n", full_type, partial_type);
1602 if (FAILED(IMFMediaType_GetMajorType(partial_type, &major)))
1603 return FALSE;
1605 if (FAILED(IMFMediaType_Compare(partial_type, (IMFAttributes *)full_type, MF_ATTRIBUTES_MATCH_OUR_ITEMS, &result)))
1606 return FALSE;
1608 return result;
1611 /***********************************************************************
1612 * MFWrapMediaType (mfplat.@)
1614 HRESULT WINAPI MFWrapMediaType(IMFMediaType *original, REFGUID major, REFGUID subtype, IMFMediaType **ret)
1616 IMFMediaType *mediatype;
1617 UINT8 *buffer;
1618 UINT32 size;
1619 HRESULT hr;
1621 TRACE("%p, %s, %s, %p.\n", original, debugstr_guid(major), debugstr_guid(subtype), ret);
1623 if (FAILED(hr = MFGetAttributesAsBlobSize((IMFAttributes *)original, &size)))
1624 return hr;
1626 if (!(buffer = heap_alloc(size)))
1627 return E_OUTOFMEMORY;
1629 if (FAILED(hr = MFGetAttributesAsBlob((IMFAttributes *)original, buffer, size)))
1630 goto failed;
1632 if (FAILED(hr = MFCreateMediaType(&mediatype)))
1633 goto failed;
1635 if (FAILED(hr = IMFMediaType_SetGUID(mediatype, &MF_MT_MAJOR_TYPE, major)))
1636 goto failed;
1638 if (FAILED(hr = IMFMediaType_SetGUID(mediatype, &MF_MT_SUBTYPE, subtype)))
1639 goto failed;
1641 if (FAILED(hr = IMFMediaType_SetBlob(mediatype, &MF_MT_WRAPPED_TYPE, buffer, size)))
1642 goto failed;
1644 *ret = mediatype;
1646 failed:
1647 heap_free(buffer);
1649 return hr;
1652 /***********************************************************************
1653 * MFUnwrapMediaType (mfplat.@)
1655 HRESULT WINAPI MFUnwrapMediaType(IMFMediaType *wrapper, IMFMediaType **ret)
1657 IMFMediaType *mediatype;
1658 UINT8 *buffer;
1659 UINT32 size;
1660 HRESULT hr;
1662 TRACE("%p, %p.\n", wrapper, ret);
1664 if (FAILED(hr = MFCreateMediaType(&mediatype)))
1665 return hr;
1667 if (FAILED(hr = IMFMediaType_GetAllocatedBlob(wrapper, &MF_MT_WRAPPED_TYPE, &buffer, &size)))
1669 IMFMediaType_Release(mediatype);
1670 return hr;
1673 hr = MFInitAttributesFromBlob((IMFAttributes *)mediatype, buffer, size);
1674 CoTaskMemFree(buffer);
1675 if (FAILED(hr))
1676 return hr;
1678 *ret = mediatype;
1680 return S_OK;