ReactOS  0.4.14-dev-368-gfa26425
memallocator.c
Go to the documentation of this file.
1 /*
2  * Memory Allocator and Media Sample Implementation
3  *
4  * Copyright 2003 Robert Shearman
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20 
21 #include <assert.h>
22 #include <limits.h>
23 #include <stdarg.h>
24 
25 #include "windef.h"
26 #include "winbase.h"
27 #include "vfwmsgs.h"
28 
29 #include "quartz_private.h"
30 #include "wine/debug.h"
31 
33 
34 typedef struct StdMediaSample2
35 {
40  struct list listentry;
44 
45 typedef struct BaseMemAllocator
46 {
48 
61  struct list free_list;
62  struct list used_list;
65 
67 {
68  return CONTAINING_RECORD(iface, BaseMemAllocator, IMemAllocator_iface);
69 }
70 
71 static const IMemAllocatorVtbl BaseMemAllocator_VTable;
72 static const IMediaSample2Vtbl StdMediaSample2_VTable;
74 
75 #define AM_SAMPLE2_PROP_SIZE_WRITABLE FIELD_OFFSET(AM_SAMPLE2_PROPERTIES, pbBuffer)
76 
77 #define INVALID_MEDIA_TIME (((ULONGLONG)0x7fffffff << 32) | 0xffffffff)
78 
80  HRESULT (* fnFree)(IMemAllocator *),
81  HRESULT (* fnVerify)(IMemAllocator *, ALLOCATOR_PROPERTIES *),
82  HRESULT (* fnBufferPrepare)(IMemAllocator *, StdMediaSample2 *, DWORD),
83  HRESULT (* fnBufferReleased)(IMemAllocator *, StdMediaSample2 *),
84  void (* fnDestroyed)(IMemAllocator *),
85  CRITICAL_SECTION *pCritSect,
86  BaseMemAllocator * pMemAlloc)
87 {
88  assert(fnAlloc && fnFree && fnDestroyed);
89 
90  pMemAlloc->IMemAllocator_iface.lpVtbl = &BaseMemAllocator_VTable;
91 
92  pMemAlloc->ref = 1;
93  ZeroMemory(&pMemAlloc->props, sizeof(pMemAlloc->props));
94  list_init(&pMemAlloc->free_list);
95  list_init(&pMemAlloc->used_list);
96  pMemAlloc->fnAlloc = fnAlloc;
97  pMemAlloc->fnFree = fnFree;
98  pMemAlloc->fnVerify = fnVerify;
99  pMemAlloc->fnBufferPrepare = fnBufferPrepare;
100  pMemAlloc->fnBufferReleased = fnBufferReleased;
101  pMemAlloc->fnDestroyed = fnDestroyed;
102  pMemAlloc->bDecommitQueued = FALSE;
103  pMemAlloc->bCommitted = FALSE;
104  pMemAlloc->hSemWaiting = NULL;
105  pMemAlloc->lWaiting = 0;
106  pMemAlloc->pCritSect = pCritSect;
107 
108  return S_OK;
109 }
110 
112 {
114  TRACE("(%p)->(%s, %p)\n", This, qzdebugstr_guid(riid), ppv);
115 
116  *ppv = NULL;
117 
119  *ppv = &This->IMemAllocator_iface;
120  else if (IsEqualIID(riid, &IID_IMemAllocator))
121  *ppv = &This->IMemAllocator_iface;
122 
123  if (*ppv)
124  {
125  IUnknown_AddRef((IUnknown *)(*ppv));
126  return S_OK;
127  }
128 
129  FIXME("No interface for %s!\n", qzdebugstr_guid(riid));
130 
131  return E_NOINTERFACE;
132 }
133 
135 {
138 
139  TRACE("(%p)->() AddRef from %d\n", iface, ref - 1);
140 
141  return ref;
142 }
143 
145 {
148 
149  TRACE("(%p)->() Release from %d\n", iface, ref + 1);
150 
151  if (!ref)
152  {
153  CloseHandle(This->hSemWaiting);
154  if (This->bCommitted)
155  This->fnFree(iface);
156 
157  This->fnDestroyed(iface);
158  return 0;
159  }
160  return ref;
161 }
162 
164 {
166  HRESULT hr;
167 
168  TRACE("(%p)->(%p, %p)\n", This, pRequest, pActual);
169 
170  EnterCriticalSection(This->pCritSect);
171  {
172  if (!list_empty(&This->used_list))
174  else if (This->bCommitted)
176  else if (pRequest->cbAlign == 0)
177  hr = VFW_E_BADALIGN;
178  else
179  {
180  if (This->fnVerify)
181  hr = This->fnVerify(iface, pRequest);
182  else
183  hr = S_OK;
184 
185  if (SUCCEEDED(hr))
186  This->props = *pRequest;
187 
188  *pActual = This->props;
189  }
190  }
191  LeaveCriticalSection(This->pCritSect);
192 
193  return hr;
194 }
195 
197 {
199  HRESULT hr = S_OK;
200 
201  TRACE("(%p)->(%p)\n", This, pProps);
202 
203  EnterCriticalSection(This->pCritSect);
204  {
205  memcpy(pProps, &This->props, sizeof(*pProps));
206  }
207  LeaveCriticalSection(This->pCritSect);
208 
209  return hr;
210 }
211 
213 {
215  HRESULT hr;
216 
217  TRACE("(%p)->()\n", This);
218 
219  EnterCriticalSection(This->pCritSect);
220  {
221  if (!This->props.cbAlign)
222  hr = VFW_E_BADALIGN;
223  else if (!This->props.cbBuffer)
225  else if (!This->props.cBuffers)
227  else if (This->bDecommitQueued && This->bCommitted)
228  {
229  This->bDecommitQueued = FALSE;
230  hr = S_OK;
231  }
232  else if (This->bCommitted)
233  hr = S_OK;
234  else
235  {
236  if (!(This->hSemWaiting = CreateSemaphoreW(NULL, This->props.cBuffers, This->props.cBuffers, NULL)))
237  {
238  ERR("Couldn't create semaphore (error was %u)\n", GetLastError());
240  }
241  else
242  {
243  hr = This->fnAlloc(iface);
244  if (SUCCEEDED(hr))
245  This->bCommitted = TRUE;
246  else
247  ERR("fnAlloc failed with error 0x%x\n", hr);
248  }
249  }
250  }
251  LeaveCriticalSection(This->pCritSect);
252 
253  return hr;
254 }
255 
257 {
259  HRESULT hr;
260 
261  TRACE("(%p)->()\n", This);
262 
263  EnterCriticalSection(This->pCritSect);
264  {
265  if (!This->bCommitted)
266  hr = S_OK;
267  else
268  {
269  if (!list_empty(&This->used_list))
270  {
271  This->bDecommitQueued = TRUE;
272  /* notify ALL waiting threads that they cannot be allocated a buffer any more */
273  ReleaseSemaphore(This->hSemWaiting, This->lWaiting, NULL);
274 
275  hr = S_OK;
276  }
277  else
278  {
279  if (This->lWaiting != 0)
280  ERR("Waiting: %d\n", This->lWaiting);
281 
282  This->bCommitted = FALSE;
283  CloseHandle(This->hSemWaiting);
284  This->hSemWaiting = NULL;
285 
286  hr = This->fnFree(iface);
287  if (FAILED(hr))
288  ERR("fnFree failed with error 0x%x\n", hr);
289  }
290  }
291  }
292  LeaveCriticalSection(This->pCritSect);
293 
294  return hr;
295 }
296 
298 {
300  HRESULT hr = S_OK;
301 
302  /* NOTE: The pStartTime and pEndTime parameters are not applied to the sample.
303  * The allocator might use these values to determine which buffer it retrieves */
304 
305  TRACE("(%p)->(%p, %p, %p, %x)\n", This, pSample, pStartTime, pEndTime, dwFlags);
306 
307  *pSample = NULL;
308 
309  EnterCriticalSection(This->pCritSect);
310  if (!This->bCommitted || This->bDecommitQueued)
311  {
312  WARN("Not committed\n");
314  }
315  else
316  ++This->lWaiting;
317  LeaveCriticalSection(This->pCritSect);
318  if (FAILED(hr))
319  return hr;
320 
321  if (WaitForSingleObject(This->hSemWaiting, (dwFlags & AM_GBF_NOWAIT) ? 0 : INFINITE) != WAIT_OBJECT_0)
322  {
323  EnterCriticalSection(This->pCritSect);
324  --This->lWaiting;
325  LeaveCriticalSection(This->pCritSect);
326  WARN("Timed out\n");
327  return VFW_E_TIMEOUT;
328  }
329 
330  EnterCriticalSection(This->pCritSect);
331  {
332  --This->lWaiting;
333  if (!This->bCommitted)
335  else if (This->bDecommitQueued)
336  hr = VFW_E_TIMEOUT;
337  else
338  {
339  StdMediaSample2 *ms;
340  struct list * free = list_head(&This->free_list);
341  list_remove(free);
342  list_add_head(&This->used_list, free);
343 
344  ms = LIST_ENTRY(free, StdMediaSample2, listentry);
345  assert(ms->ref == 0);
346  *pSample = (IMediaSample *)&ms->IMediaSample2_iface;
347  IMediaSample_AddRef(*pSample);
348  }
349  }
350  LeaveCriticalSection(This->pCritSect);
351 
352  if (hr != S_OK)
353  WARN("%08x\n", hr);
354  return hr;
355 }
356 
358 {
360  StdMediaSample2 * pStdSample = unsafe_impl_from_IMediaSample(pSample);
361  HRESULT hr = S_OK;
362 
363  TRACE("(%p)->(%p)\n", This, pSample);
364 
365  /* FIXME: make sure that sample is currently on the used list */
366 
367  /* FIXME: we should probably check the ref count on the sample before freeing
368  * it to make sure that it is not still in use */
369  EnterCriticalSection(This->pCritSect);
370  {
371  if (!This->bCommitted)
372  ERR("Releasing a buffer when the allocator is not committed?!?\n");
373 
374  /* remove from used_list */
375  list_remove(&pStdSample->listentry);
376 
377  list_add_head(&This->free_list, &pStdSample->listentry);
378 
379  if (list_empty(&This->used_list) && This->bDecommitQueued && This->bCommitted)
380  {
381  HRESULT hrfree;
382 
383  if (This->lWaiting != 0)
384  ERR("Waiting: %d\n", This->lWaiting);
385 
386  This->bCommitted = FALSE;
387  This->bDecommitQueued = FALSE;
388 
389  CloseHandle(This->hSemWaiting);
390  This->hSemWaiting = NULL;
391 
392  if (FAILED(hrfree = This->fnFree(iface)))
393  ERR("fnFree failed with error 0x%x\n", hrfree);
394  }
395  }
396  LeaveCriticalSection(This->pCritSect);
397 
398  /* notify a waiting thread that there is now a free buffer */
399  if (This->hSemWaiting && !ReleaseSemaphore(This->hSemWaiting, 1, NULL))
400  {
401  ERR("ReleaseSemaphore failed with error %u\n", GetLastError());
403  }
404 
405  return hr;
406 }
407 
408 static const IMemAllocatorVtbl BaseMemAllocator_VTable =
409 {
419 };
420 
421 static HRESULT StdMediaSample2_Construct(BYTE * pbBuffer, LONG cbBuffer, IMemAllocator * pParent, StdMediaSample2 ** ppSample)
422 {
423  assert(pbBuffer && pParent && (cbBuffer > 0));
424 
425  if (!(*ppSample = CoTaskMemAlloc(sizeof(StdMediaSample2))))
426  return E_OUTOFMEMORY;
427 
428  (*ppSample)->IMediaSample2_iface.lpVtbl = &StdMediaSample2_VTable;
429  (*ppSample)->ref = 0;
430  ZeroMemory(&(*ppSample)->props, sizeof((*ppSample)->props));
431 
432  /* NOTE: no need to AddRef as the parent is guaranteed to be around
433  * at least as long as us and we don't want to create circular
434  * dependencies on the ref count */
435  (*ppSample)->pParent = pParent;
436  (*ppSample)->props.cbData = sizeof(AM_SAMPLE2_PROPERTIES);
437  (*ppSample)->props.cbBuffer = (*ppSample)->props.lActual = cbBuffer;
438  (*ppSample)->props.pbBuffer = pbBuffer;
439  (*ppSample)->tMediaStart = INVALID_MEDIA_TIME;
440  (*ppSample)->tMediaEnd = 0;
441 
442  return S_OK;
443 }
444 
446 {
447  /* NOTE: does not remove itself from the list it belongs to */
449 }
450 
452 {
453  return CONTAINING_RECORD(iface, StdMediaSample2, IMediaSample2_iface);
454 }
455 
457 {
458  TRACE("(%s, %p)\n", qzdebugstr_guid(riid), ppv);
459 
460  *ppv = NULL;
461 
462  if (IsEqualIID(riid, &IID_IUnknown) || IsEqualIID(riid, &IID_IMediaSample) ||
463  IsEqualIID(riid, &IID_IMediaSample2))
464  {
465  *ppv = iface;
466  IMediaSample2_AddRef(iface);
467  return S_OK;
468  }
469 
470  FIXME("No interface for %s!\n", qzdebugstr_guid(riid));
471  return E_NOINTERFACE;
472 }
473 
475 {
478 
479  TRACE("(%p)->(): new ref = %d\n", This, ref);
480 
481  return ref;
482 }
483 
485 {
488 
489  TRACE("(%p)->(): new ref = %d\n", This, ref);
490 
491  if (!ref)
492  {
493  if (This->pParent)
494  IMemAllocator_ReleaseBuffer(This->pParent, (IMediaSample *)iface);
495  else
497  }
498  return ref;
499 }
500 
502 {
504 
505  TRACE("(%p)->(%p)\n", iface, ppBuffer);
506 
507  *ppBuffer = This->props.pbBuffer;
508 
509  if (!*ppBuffer)
510  {
511  ERR("Requested an unlocked surface and trying to lock regardless\n");
512  return E_FAIL;
513  }
514 
515  return S_OK;
516 }
517 
519 {
521 
522  TRACE("StdMediaSample2_GetSize()\n");
523 
524  return This->props.cbBuffer;
525 }
526 
528 {
530  HRESULT hr;
531 
532  TRACE("(%p)->(%p, %p)\n", iface, pStart, pEnd);
533 
534  if (!(This->props.dwSampleFlags & AM_SAMPLE_TIMEVALID))
536  else if (!(This->props.dwSampleFlags & AM_SAMPLE_STOPVALID))
537  {
538  *pStart = This->props.tStart;
539  *pEnd = This->props.tStart + 1;
540 
542  }
543  else
544  {
545  *pStart = This->props.tStart;
546  *pEnd = This->props.tStop;
547 
548  hr = S_OK;
549  }
550 
551  return hr;
552 }
553 
555 {
557 
558  TRACE("(%p)->(%p, %p)\n", iface, pStart, pEnd);
559 
560  if (pStart)
561  {
562  This->props.tStart = *pStart;
563  This->props.dwSampleFlags |= AM_SAMPLE_TIMEVALID;
564  }
565  else
566  This->props.dwSampleFlags &= ~AM_SAMPLE_TIMEVALID;
567 
568  if (pEnd)
569  {
570  This->props.tStop = *pEnd;
571  This->props.dwSampleFlags |= AM_SAMPLE_STOPVALID;
572  }
573  else
574  This->props.dwSampleFlags &= ~AM_SAMPLE_STOPVALID;
575 
576  return S_OK;
577 }
578 
580 {
582 
583  TRACE("(%p)->()\n", iface);
584 
585  return (This->props.dwSampleFlags & AM_SAMPLE_SPLICEPOINT) ? S_OK : S_FALSE;
586 }
587 
589 {
591 
592  TRACE("(%p)->(%s)\n", iface, bIsSyncPoint ? "TRUE" : "FALSE");
593 
594  if (bIsSyncPoint)
595  This->props.dwSampleFlags |= AM_SAMPLE_SPLICEPOINT;
596  else
597  This->props.dwSampleFlags &= ~AM_SAMPLE_SPLICEPOINT;
598 
599  return S_OK;
600 }
601 
603 {
605 
606  TRACE("(%p)->()\n", iface);
607 
608  return (This->props.dwSampleFlags & AM_SAMPLE_PREROLL) ? S_OK : S_FALSE;
609 }
610 
612 {
614 
615  TRACE("(%p)->(%s)\n", iface, bIsPreroll ? "TRUE" : "FALSE");
616 
617  if (bIsPreroll)
618  This->props.dwSampleFlags |= AM_SAMPLE_PREROLL;
619  else
620  This->props.dwSampleFlags &= ~AM_SAMPLE_PREROLL;
621 
622  return S_OK;
623 }
624 
626 {
628 
629  TRACE("(%p)->()\n", iface);
630 
631  return This->props.lActual;
632 }
633 
635 {
637 
638  TRACE("(%p)->(%d)\n", iface, len);
639 
640  if ((len > This->props.cbBuffer) || (len < 0))
641  {
642  WARN("Tried to set length to %d, while max is %d\n", len, This->props.cbBuffer);
643  return VFW_E_BUFFER_OVERFLOW;
644  }
645  else
646  {
647  This->props.lActual = len;
648  return S_OK;
649  }
650 }
651 
653 {
655 
656  TRACE("(%p)->(%p)\n", iface, ppMediaType);
657 
658  if (!This->props.pMediaType) {
659  /* Make sure we return a NULL pointer (required by native Quartz dll) */
660  if (ppMediaType)
661  *ppMediaType = NULL;
662  return S_FALSE;
663  }
664 
665  if (!(*ppMediaType = CoTaskMemAlloc(sizeof(AM_MEDIA_TYPE))))
666  return E_OUTOFMEMORY;
667 
668  return CopyMediaType(*ppMediaType, This->props.pMediaType);
669 }
670 
672 {
674 
675  TRACE("(%p)->(%p)\n", iface, pMediaType);
676 
677  if (This->props.pMediaType)
678  {
679  FreeMediaType(This->props.pMediaType);
680  This->props.pMediaType = NULL;
681  }
682  if (!pMediaType)
683  return S_FALSE;
684  if (!(This->props.pMediaType = CoTaskMemAlloc(sizeof(AM_MEDIA_TYPE))))
685  return E_OUTOFMEMORY;
686 
687  return CopyMediaType(This->props.pMediaType, pMediaType);
688 }
689 
691 {
693 
694  TRACE("(%p)->()\n", iface);
695 
696  return (This->props.dwSampleFlags & AM_SAMPLE_DATADISCONTINUITY) ? S_OK : S_FALSE;
697 }
698 
700 {
702 
703  TRACE("(%p)->(%s)\n", iface, bIsDiscontinuity ? "TRUE" : "FALSE");
704 
705  if (bIsDiscontinuity)
706  This->props.dwSampleFlags |= AM_SAMPLE_DATADISCONTINUITY;
707  else
708  This->props.dwSampleFlags &= ~AM_SAMPLE_DATADISCONTINUITY;
709 
710  return S_OK;
711 }
712 
714 {
716 
717  TRACE("(%p)->(%p, %p)\n", iface, pStart, pEnd);
718 
719  if (This->tMediaStart == INVALID_MEDIA_TIME)
721 
722  *pStart = This->tMediaStart;
723  *pEnd = This->tMediaEnd;
724 
725  return S_OK;
726 }
727 
729 {
731 
732  TRACE("(%p)->(%p, %p)\n", iface, pStart, pEnd);
733 
734  if (pStart)
735  This->tMediaStart = *pStart;
736  else
737  This->tMediaStart = INVALID_MEDIA_TIME;
738 
739  if (pEnd)
740  This->tMediaEnd = *pEnd;
741  else
742  This->tMediaEnd = 0;
743 
744  return S_OK;
745 }
746 
747 static HRESULT WINAPI StdMediaSample2_GetProperties(IMediaSample2 * iface, DWORD cbProperties, BYTE * pbProperties)
748 {
750 
751  TRACE("(%p)->(%d, %p)\n", iface, cbProperties, pbProperties);
752 
753  memcpy(pbProperties, &This->props, min(cbProperties, sizeof(This->props)));
754 
755  return S_OK;
756 }
757 
758 static HRESULT WINAPI StdMediaSample2_SetProperties(IMediaSample2 * iface, DWORD cbProperties, const BYTE * pbProperties)
759 {
761 
762  TRACE("(%p)->(%d, %p)\n", iface, cbProperties, pbProperties);
763 
764  /* NOTE: pbBuffer and cbBuffer are read-only */
765  memcpy(&This->props, pbProperties, min(cbProperties, AM_SAMPLE2_PROP_SIZE_WRITABLE));
766 
767  return S_OK;
768 }
769 
770 static const IMediaSample2Vtbl StdMediaSample2_VTable =
771 {
793 };
794 
796 {
797  IMediaSample2 *iface2 = (IMediaSample2 *)iface;
798 
799  if (!iface)
800  return NULL;
801  assert(iface2->lpVtbl == &StdMediaSample2_VTable);
802  return impl_from_IMediaSample2(iface2);
803 }
804 
805 typedef struct StdMemAllocator
806 {
811 
813 {
814  return CONTAINING_RECORD(iface, StdMemAllocator, base.IMemAllocator_iface);
815 }
816 
818 {
820  StdMediaSample2 * pSample = NULL;
821  SYSTEM_INFO si;
822  LONG i;
823 
824  assert(list_empty(&This->base.free_list));
825 
826  /* check alignment */
827  GetSystemInfo(&si);
828 
829  /* we do not allow a courser alignment than the OS page size */
830  if ((si.dwPageSize % This->base.props.cbAlign) != 0)
831  return VFW_E_BADALIGN;
832 
833  /* FIXME: each sample has to have its buffer start on the right alignment.
834  * We don't do this at the moment */
835 
836  /* allocate memory */
837  This->pMemory = VirtualAlloc(NULL, (This->base.props.cbBuffer + This->base.props.cbPrefix) * This->base.props.cBuffers, MEM_COMMIT, PAGE_READWRITE);
838 
839  if (!This->pMemory)
840  return E_OUTOFMEMORY;
841 
842  for (i = This->base.props.cBuffers - 1; i >= 0; i--)
843  {
844  /* pbBuffer does not start at the base address, it starts at base + cbPrefix */
845  BYTE * pbBuffer = (BYTE *)This->pMemory + i * (This->base.props.cbBuffer + This->base.props.cbPrefix) + This->base.props.cbPrefix;
846 
847  StdMediaSample2_Construct(pbBuffer, This->base.props.cbBuffer, iface, &pSample);
848 
849  list_add_head(&This->base.free_list, &pSample->listentry);
850  }
851 
852  return S_OK;
853 }
854 
856 {
858  struct list * cursor;
859 
860  if (!list_empty(&This->base.used_list))
861  {
862  WARN("Freeing allocator with outstanding samples!\n");
863  while ((cursor = list_head(&This->base.used_list)) != NULL)
864  {
865  StdMediaSample2 *pSample;
867  pSample = LIST_ENTRY(cursor, StdMediaSample2, listentry);
868  pSample->pParent = NULL;
869  }
870  }
871 
872  while ((cursor = list_head(&This->base.free_list)) != NULL)
873  {
876  }
877 
878  /* free memory */
879  if (!VirtualFree(This->pMemory, 0, MEM_RELEASE))
880  {
881  ERR("Couldn't free memory. Error: %u\n", GetLastError());
883  }
884 
885  return S_OK;
886 }
887 
889 {
891 
892  This->csState.DebugInfo->Spare[0] = 0;
893  DeleteCriticalSection(&This->csState);
894 
896 }
897 
899 {
900  StdMemAllocator * pMemAlloc;
901  HRESULT hr;
902 
903  *ppv = NULL;
904 
905  if (lpUnkOuter)
906  return CLASS_E_NOAGGREGATION;
907 
908  if (!(pMemAlloc = CoTaskMemAlloc(sizeof(*pMemAlloc))))
909  return E_OUTOFMEMORY;
910 
911  InitializeCriticalSection(&pMemAlloc->csState);
912  pMemAlloc->csState.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": StdMemAllocator.csState");
913 
914  pMemAlloc->pMemory = NULL;
915 
917  *ppv = pMemAlloc;
918  else
919  CoTaskMemFree(pMemAlloc);
920 
921  return hr;
922 }
#define HRESULT
Definition: msvc.h:9
HRESULT(* fnBufferPrepare)(IMemAllocator *, StdMediaSample2 *, DWORD flags)
Definition: memallocator.c:54
#define VFW_E_BADALIGN
Definition: vfwmsgs.h:53
#define REFIID
Definition: guiddef.h:118
#define TRUE
Definition: types.h:120
static HRESULT WINAPI BaseMemAllocator_SetProperties(IMemAllocator *iface, ALLOCATOR_PROPERTIES *pRequest, ALLOCATOR_PROPERTIES *pActual)
Definition: memallocator.c:163
#define CloseHandle
Definition: compat.h:406
#define E_NOINTERFACE
Definition: winerror.h:2364
#define HRESULT_FROM_WIN32(x)
Definition: winerror.h:92
struct png_info_def **typedef void(__cdecl typeof(png_destroy_read_struct))(struct png_struct_def **
Definition: typeof.h:49
VOID WINAPI CoTaskMemFree(LPVOID ptr)
Definition: ifs.c:420
#define DWORD_PTR
Definition: treelist.c:76
HRESULT hr
Definition: shlfolder.c:183
static HRESULT WINAPI StdMediaSample2_GetPointer(IMediaSample2 *iface, BYTE **ppBuffer)
Definition: memallocator.c:501
HANDLE WINAPI DECLSPEC_HOTPATCH CreateSemaphoreW(IN LPSECURITY_ATTRIBUTES lpSemaphoreAttributes OPTIONAL, IN LONG lInitialCount, IN LONG lMaximumCount, IN LPCWSTR lpName OPTIONAL)
Definition: synch.c:444
#define AM_SAMPLE2_PROP_SIZE_WRITABLE
Definition: memallocator.c:75
LONGLONG tMediaStart
Definition: memallocator.c:41
static HRESULT WINAPI BaseMemAllocator_QueryInterface(IMemAllocator *iface, REFIID riid, LPVOID *ppv)
Definition: memallocator.c:111
REFIID riid
Definition: precomp.h:44
const char * qzdebugstr_guid(const GUID *id)
Definition: main.c:279
#define free
Definition: debug_ros.c:5
#define WARN(fmt,...)
Definition: debug.h:111
__WINE_SERVER_LIST_INLINE void list_add_head(struct list *list, struct list *elem)
Definition: list.h:96
REFIID LPVOID * ppv
Definition: atlbase.h:39
#define INVALID_MEDIA_TIME
Definition: memallocator.c:77
HRESULT(* fnBufferReleased)(IMemAllocator *, StdMediaSample2 *)
Definition: memallocator.c:55
#define assert(x)
Definition: debug.h:53
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1059
#define ZeroMemory
Definition: winbase.h:1642
LONGLONG tMediaEnd
Definition: memallocator.c:42
static HRESULT WINAPI StdMediaSample2_SetSyncPoint(IMediaSample2 *iface, BOOL bIsSyncPoint)
Definition: memallocator.c:588
static LONG WINAPI StdMediaSample2_GetSize(IMediaSample2 *iface)
Definition: memallocator.c:518
static HRESULT WINAPI StdMediaSample2_IsDiscontinuity(IMediaSample2 *iface)
Definition: memallocator.c:690
IMemAllocator * pParent
Definition: memallocator.c:39
#define VFW_E_SAMPLE_TIME_NOT_SET
Definition: vfwmsgs.h:104
struct StdMemAllocator StdMemAllocator
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
#define E_FAIL
Definition: ddrawi.h:102
#define MEM_COMMIT
Definition: nt_native.h:1313
Definition: send.c:47
HRESULT(* fnVerify)(IMemAllocator *, ALLOCATOR_PROPERTIES *)
Definition: memallocator.c:53
static StdMediaSample2 * unsafe_impl_from_IMediaSample(IMediaSample *iface)
Definition: memallocator.c:795
static HRESULT WINAPI StdMediaSample2_GetMediaTime(IMediaSample2 *iface, LONGLONG *pStart, LONGLONG *pEnd)
Definition: memallocator.c:713
static HRESULT WINAPI StdMediaSample2_SetActualDataLength(IMediaSample2 *iface, LONG len)
Definition: memallocator.c:634
__WINE_SERVER_LIST_INLINE struct list * list_head(const struct list *list)
Definition: list.h:131
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82
BaseMemAllocator base
Definition: memallocator.c:807
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
struct BaseMemAllocator BaseMemAllocator
LPVOID NTAPI VirtualAlloc(IN LPVOID lpAddress, IN SIZE_T dwSize, IN DWORD flAllocationType, IN DWORD flProtect)
Definition: virtmem.c:74
static HRESULT WINAPI StdMediaSample2_SetProperties(IMediaSample2 *iface, DWORD cbProperties, const BYTE *pbProperties)
Definition: memallocator.c:758
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
static HRESULT WINAPI BaseMemAllocator_GetBuffer(IMemAllocator *iface, IMediaSample **pSample, REFERENCE_TIME *pStartTime, REFERENCE_TIME *pEndTime, DWORD dwFlags)
Definition: memallocator.c:297
IMemAllocator IMemAllocator_iface
Definition: memallocator.c:47
unsigned int BOOL
Definition: ntddk_ex.h:94
long LONG
Definition: pedump.c:60
static void StdMemAllocator_Destroy(IMemAllocator *iface)
Definition: memallocator.c:888
static LPUNKNOWN
Definition: ndr_ole.c:49
static StdMemAllocator * StdMemAllocator_from_IMemAllocator(IMemAllocator *iface)
Definition: memallocator.c:812
static void FreeMediaType(AM_MEDIA_TYPE *pMediaType)
Definition: filtergraph.c:692
static HRESULT BaseMemAllocator_Init(HRESULT(*fnAlloc)(IMemAllocator *), HRESULT(*fnFree)(IMemAllocator *), HRESULT(*fnVerify)(IMemAllocator *, ALLOCATOR_PROPERTIES *), HRESULT(*fnBufferPrepare)(IMemAllocator *, StdMediaSample2 *, DWORD), HRESULT(*fnBufferReleased)(IMemAllocator *, StdMediaSample2 *), void(*fnDestroyed)(IMemAllocator *), CRITICAL_SECTION *pCritSect, BaseMemAllocator *pMemAlloc)
Definition: memallocator.c:79
GLenum GLint ref
Definition: glext.h:6028
#define FIXME(fmt,...)
Definition: debug.h:110
static ULONG WINAPI StdMediaSample2_AddRef(IMediaSample2 *iface)
Definition: memallocator.c:474
#define S_FALSE
Definition: winerror.h:2357
#define VFW_E_ALREADY_COMMITTED
Definition: vfwmsgs.h:54
struct list free_list
Definition: memallocator.c:61
HRESULT StdMemAllocator_create(LPUNKNOWN lpUnkOuter, LPVOID *ppv)
Definition: memallocator.c:898
static StdMediaSample2 * impl_from_IMediaSample2(IMediaSample2 *iface)
Definition: memallocator.c:451
VOID WINAPI InitializeCriticalSection(OUT LPCRITICAL_SECTION lpCriticalSection)
Definition: synch.c:751
struct StdMediaSample2 StdMediaSample2
smooth NULL
Definition: ftsmooth.c:416
static const IMemAllocatorVtbl BaseMemAllocator_VTable
Definition: memallocator.c:71
static HRESULT WINAPI StdMediaSample2_GetTime(IMediaSample2 *iface, REFERENCE_TIME *pStart, REFERENCE_TIME *pEnd)
Definition: memallocator.c:527
static HRESULT WINAPI StdMediaSample2_QueryInterface(IMediaSample2 *iface, REFIID riid, void **ppv)
Definition: memallocator.c:456
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
HRESULT(* fnFree)(IMemAllocator *)
Definition: memallocator.c:52
static HRESULT WINAPI StdMediaSample2_GetMediaType(IMediaSample2 *iface, AM_MEDIA_TYPE **ppMediaType)
Definition: memallocator.c:652
int64_t LONGLONG
Definition: typedefs.h:66
__WINE_SERVER_LIST_INLINE void list_remove(struct list *elem)
Definition: list.h:108
#define TRACE(s)
Definition: solgame.cpp:4
#define WAIT_OBJECT_0
Definition: winbase.h:387
#define VFW_E_TIMEOUT
Definition: vfwmsgs.h:85
static void StdMediaSample2_Delete(StdMediaSample2 *This)
Definition: memallocator.c:445
LONGLONG REFERENCE_TIME
Definition: dmusicks.h:9
void WINAPI DeleteCriticalSection(PCRITICAL_SECTION)
static HRESULT WINAPI StdMediaSample2_SetTime(IMediaSample2 *iface, REFERENCE_TIME *pStart, REFERENCE_TIME *pEnd)
Definition: memallocator.c:554
LONG HRESULT
Definition: typedefs.h:77
const GUID IID_IUnknown
#define WINAPI
Definition: msvc.h:8
static HRESULT WINAPI BaseMemAllocator_GetProperties(IMemAllocator *iface, ALLOCATOR_PROPERTIES *pProps)
Definition: memallocator.c:196
ALLOCATOR_PROPERTIES props
Definition: memallocator.c:50
WINE_DEFAULT_DEBUG_CHANNEL(quartz)
unsigned long DWORD
Definition: ntddk_ex.h:95
static HRESULT CopyMediaType(AM_MEDIA_TYPE *pDest, const AM_MEDIA_TYPE *pSrc)
Definition: filtergraph.c:706
PCRITICAL_SECTION_DEBUG DebugInfo
Definition: winbase.h:866
GLbitfield flags
Definition: glext.h:7161
static HRESULT WINAPI BaseMemAllocator_Commit(IMemAllocator *iface)
Definition: memallocator.c:212
#define VFW_E_BUFFER_OVERFLOW
Definition: vfwmsgs.h:52
#define InterlockedDecrement
Definition: armddk.h:52
_In_ PCCERT_CONTEXT _In_ DWORD dwFlags
Definition: wincrypt.h:1175
static HRESULT WINAPI StdMediaSample2_SetDiscontinuity(IMediaSample2 *iface, BOOL bIsDiscontinuity)
Definition: memallocator.c:699
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
unsigned char BYTE
Definition: mem.h:68
Definition: _list.h:228
#define CLASS_E_NOAGGREGATION
Definition: winerror.h:2662
CRITICAL_SECTION * pCritSect
Definition: memallocator.c:63
struct list listentry
Definition: memallocator.c:40
static HRESULT WINAPI StdMediaSample2_SetPreroll(IMediaSample2 *iface, BOOL bIsPreroll)
Definition: memallocator.c:611
static HRESULT StdMediaSample2_Construct(BYTE *pbBuffer, LONG cbBuffer, IMemAllocator *pParent, StdMediaSample2 **ppSample)
Definition: memallocator.c:421
#define ERR(fmt,...)
Definition: debug.h:109
#define VFW_E_MEDIA_TIME_NOT_SET
Definition: vfwmsgs.h:105
static LONG WINAPI StdMediaSample2_GetActualDataLength(IMediaSample2 *iface)
Definition: memallocator.c:625
CRITICAL_SECTION csState
Definition: memallocator.c:808
__WINE_SERVER_LIST_INLINE int list_empty(const struct list *list)
Definition: list.h:143
#define S_OK
Definition: intsafe.h:59
DWORD dwPageSize
Definition: winbase.h:1133
static HRESULT StdMemAllocator_Alloc(IMemAllocator *iface)
Definition: memallocator.c:817
void(* fnDestroyed)(IMemAllocator *)
Definition: memallocator.c:56
static const IMediaSample2Vtbl StdMediaSample2_VTable
Definition: memallocator.c:72
AM_SAMPLE2_PROPERTIES props
Definition: memallocator.c:38
struct tagAM_SAMPLE2_PROPERTIES AM_SAMPLE2_PROPERTIES
#define InterlockedIncrement
Definition: armddk.h:53
const char cursor[]
Definition: icontest.c:13
#define VFW_E_BUFFERS_OUTSTANDING
Definition: vfwmsgs.h:55
struct list used_list
Definition: memallocator.c:62
VOID WINAPI GetSystemInfo(IN LPSYSTEM_INFO lpSystemInfo)
Definition: sysinfo.c:142
#define min(a, b)
Definition: monoChain.cc:55
static ULONG WINAPI StdMediaSample2_Release(IMediaSample2 *iface)
Definition: memallocator.c:484
#define VFW_E_SIZENOTSET
Definition: vfwmsgs.h:57
#define VFW_E_NOT_COMMITTED
Definition: vfwmsgs.h:56
BOOL WINAPI DECLSPEC_HOTPATCH ReleaseSemaphore(IN HANDLE hSemaphore, IN LONG lReleaseCount, IN LPLONG lpPreviousCount)
Definition: synch.c:542
#define VFW_E_BUFFER_NOTSET
Definition: vfwmsgs.h:51
#define MEM_RELEASE
Definition: nt_native.h:1316
__WINE_SERVER_LIST_INLINE void list_init(struct list *list)
Definition: list.h:149
static BaseMemAllocator * impl_from_IMemAllocator(IMemAllocator *iface)
Definition: memallocator.c:66
static HRESULT WINAPI StdMediaSample2_SetMediaTime(IMediaSample2 *iface, LONGLONG *pStart, LONGLONG *pEnd)
Definition: memallocator.c:728
unsigned int ULONG
Definition: retypes.h:1
#define VFW_S_NO_STOP_TIME
Definition: vfwmsgs.h:34
static HRESULT StdMemAllocator_Free(IMemAllocator *iface)
Definition: memallocator.c:855
static HRESULT WINAPI StdMediaSample2_SetMediaType(IMediaSample2 *iface, AM_MEDIA_TYPE *pMediaType)
Definition: memallocator.c:671
static HRESULT WINAPI BaseMemAllocator_ReleaseBuffer(IMemAllocator *iface, IMediaSample *pSample)
Definition: memallocator.c:357
BOOL NTAPI VirtualFree(IN LPVOID lpAddress, IN SIZE_T dwSize, IN DWORD dwFreeType)
Definition: virtmem.c:128
static HRESULT WINAPI StdMediaSample2_GetProperties(IMediaSample2 *iface, DWORD cbProperties, BYTE *pbProperties)
Definition: memallocator.c:747
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
#define LIST_ENTRY(type)
Definition: queue.h:175
#define INFINITE
Definition: serial.h:102
static HRESULT WINAPI StdMediaSample2_IsPreroll(IMediaSample2 *iface)
Definition: memallocator.c:602
IMediaSample2 IMediaSample2_iface
Definition: memallocator.c:36
static ULONG WINAPI BaseMemAllocator_AddRef(IMemAllocator *iface)
Definition: memallocator.c:134
static ULONG WINAPI BaseMemAllocator_Release(IMemAllocator *iface)
Definition: memallocator.c:144
LPVOID WINAPI CoTaskMemAlloc(SIZE_T size)
Definition: ifs.c:404
static HRESULT WINAPI BaseMemAllocator_Decommit(IMemAllocator *iface)
Definition: memallocator.c:256
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
static HRESULT WINAPI StdMediaSample2_IsSyncPoint(IMediaSample2 *iface)
Definition: memallocator.c:579
#define SUCCEEDED(hr)
Definition: intsafe.h:57
DWORD_PTR Spare[8/sizeof(DWORD_PTR)]
Definition: winbase.h:859
HRESULT(* fnAlloc)(IMemAllocator *)
Definition: memallocator.c:51
#define PAGE_READWRITE
Definition: nt_native.h:1304