[PATCH v2 1/6] winegstreamer: Split wg_sample wrapper helpers to a separate source.

Rémi Bernon wine at gitlab.winehq.org
Mon Jun 13 08:13:57 CDT 2022


From: Rémi Bernon <rbernon at codeweavers.com>

Signed-off-by: Rémi Bernon <rbernon at codeweavers.com>
---
 dlls/winegstreamer/Makefile.in |   1 +
 dlls/winegstreamer/mfplat.c    | 176 ----------------------------
 dlls/winegstreamer/wg_sample.c | 203 +++++++++++++++++++++++++++++++++
 3 files changed, 204 insertions(+), 176 deletions(-)
 create mode 100644 dlls/winegstreamer/wg_sample.c

diff --git a/dlls/winegstreamer/Makefile.in b/dlls/winegstreamer/Makefile.in
index 50f4dc861d4..6e3517dcb36 100644
--- a/dlls/winegstreamer/Makefile.in
+++ b/dlls/winegstreamer/Makefile.in
@@ -17,6 +17,7 @@ C_SRCS = \
 	wg_allocator.c \
 	wg_format.c \
 	wg_parser.c \
+	wg_sample.c \
 	wg_transform.c \
 	wm_asyncreader.c \
 	wm_reader.c \
diff --git a/dlls/winegstreamer/mfplat.c b/dlls/winegstreamer/mfplat.c
index 157ed3ad2f2..c5ca4b15c0f 100644
--- a/dlls/winegstreamer/mfplat.c
+++ b/dlls/winegstreamer/mfplat.c
@@ -958,179 +958,3 @@ void mf_media_type_to_wg_format(IMFMediaType *type, struct wg_format *format)
     else
         FIXME("Unrecognized major type %s.\n", debugstr_guid(&major_type));
 }
-
-struct wg_sample_queue
-{
-    CRITICAL_SECTION cs;
-    struct list samples;
-};
-
-struct mf_sample
-{
-    IMFSample *sample;
-    IMFMediaBuffer *media_buffer;
-    struct wg_sample wg_sample;
-    struct list entry;
-};
-
-HRESULT wg_sample_create_mf(IMFSample *sample, struct wg_sample **out)
-{
-    DWORD current_length, max_length;
-    struct mf_sample *mf_sample;
-    BYTE *buffer;
-    HRESULT hr;
-
-    if (!(mf_sample = calloc(1, sizeof(*mf_sample))))
-        return E_OUTOFMEMORY;
-    if (FAILED(hr = IMFSample_ConvertToContiguousBuffer(sample, &mf_sample->media_buffer)))
-        goto out;
-    if (FAILED(hr = IMFMediaBuffer_Lock(mf_sample->media_buffer, &buffer, &max_length, &current_length)))
-        goto out;
-
-    IMFSample_AddRef((mf_sample->sample = sample));
-    mf_sample->wg_sample.data = buffer;
-    mf_sample->wg_sample.size = current_length;
-    mf_sample->wg_sample.max_size = max_length;
-
-    TRACE("Created mf_sample %p for sample %p.\n", mf_sample, sample);
-    *out = &mf_sample->wg_sample;
-    return S_OK;
-
-out:
-    if (mf_sample->media_buffer)
-        IMFMediaBuffer_Release(mf_sample->media_buffer);
-    free(mf_sample);
-    return hr;
-}
-
-void wg_sample_release(struct wg_sample *wg_sample)
-{
-    struct mf_sample *mf_sample = CONTAINING_RECORD(wg_sample, struct mf_sample, wg_sample);
-
-    if (InterlockedOr(&wg_sample->refcount, 0))
-    {
-        ERR("Sample %p is still in use, trouble ahead!\n", wg_sample);
-        return;
-    }
-
-    IMFMediaBuffer_Unlock(mf_sample->media_buffer);
-    IMFMediaBuffer_Release(mf_sample->media_buffer);
-    IMFSample_Release(mf_sample->sample);
-
-    free(mf_sample);
-}
-
-static void wg_sample_queue_begin_append(struct wg_sample_queue *queue, struct wg_sample *wg_sample)
-{
-    struct mf_sample *mf_sample = CONTAINING_RECORD(wg_sample, struct mf_sample, wg_sample);
-
-    /* make sure a concurrent wg_sample_queue_flush call won't release the sample until we're done */
-    InterlockedIncrement(&wg_sample->refcount);
-    mf_sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_REFCOUNT;
-
-    EnterCriticalSection(&queue->cs);
-    list_add_tail(&queue->samples, &mf_sample->entry);
-    LeaveCriticalSection(&queue->cs);
-}
-
-static void wg_sample_queue_end_append(struct wg_sample_queue *queue, struct wg_sample *wg_sample)
-{
-    /* release temporary ref taken in wg_sample_queue_begin_append */
-    InterlockedDecrement(&wg_sample->refcount);
-
-    wg_sample_queue_flush(queue, false);
-}
-
-void wg_sample_queue_flush(struct wg_sample_queue *queue, bool all)
-{
-    struct mf_sample *mf_sample, *next;
-
-    EnterCriticalSection(&queue->cs);
-
-    LIST_FOR_EACH_ENTRY_SAFE(mf_sample, next, &queue->samples, struct mf_sample, entry)
-    {
-        if (!InterlockedOr(&mf_sample->wg_sample.refcount, 0) || all)
-        {
-            list_remove(&mf_sample->entry);
-            wg_sample_release(&mf_sample->wg_sample);
-        }
-    }
-
-    LeaveCriticalSection(&queue->cs);
-}
-
-HRESULT wg_sample_queue_create(struct wg_sample_queue **out)
-{
-    struct wg_sample_queue *queue;
-
-    if (!(queue = calloc(1, sizeof(*queue))))
-        return E_OUTOFMEMORY;
-
-    InitializeCriticalSection(&queue->cs);
-    queue->cs.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": cs");
-    list_init(&queue->samples);
-
-    TRACE("Created sample queue %p\n", queue);
-    *out = queue;
-
-    return S_OK;
-}
-
-void wg_sample_queue_destroy(struct wg_sample_queue *queue)
-{
-    wg_sample_queue_flush(queue, true);
-
-    queue->cs.DebugInfo->Spare[0] = 0;
-    InitializeCriticalSection(&queue->cs);
-
-    free(queue);
-}
-
-HRESULT wg_transform_push_mf(struct wg_transform *transform, struct wg_sample *wg_sample,
-        struct wg_sample_queue *queue)
-{
-    struct mf_sample *mf_sample = CONTAINING_RECORD(wg_sample, struct mf_sample, wg_sample);
-    LONGLONG time, duration;
-    UINT32 value;
-    HRESULT hr;
-
-    if (SUCCEEDED(IMFSample_GetSampleTime(mf_sample->sample, &time)))
-    {
-        mf_sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_PTS;
-        mf_sample->wg_sample.pts = time;
-    }
-    if (SUCCEEDED(IMFSample_GetSampleDuration(mf_sample->sample, &duration)))
-    {
-        mf_sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_DURATION;
-        mf_sample->wg_sample.duration = duration;
-    }
-    if (SUCCEEDED(IMFSample_GetUINT32(mf_sample->sample, &MFSampleExtension_CleanPoint, &value)) && value)
-        mf_sample->wg_sample.flags |= WG_SAMPLE_FLAG_SYNC_POINT;
-
-    wg_sample_queue_begin_append(queue, wg_sample);
-    hr = wg_transform_push_data(transform, wg_sample);
-    wg_sample_queue_end_append(queue, wg_sample);
-
-    return hr;
-}
-
-HRESULT wg_transform_read_mf(struct wg_transform *transform, struct wg_sample *wg_sample,
-        struct wg_format *format)
-{
-    struct mf_sample *mf_sample = CONTAINING_RECORD(wg_sample, struct mf_sample, wg_sample);
-    HRESULT hr;
-
-    if (FAILED(hr = wg_transform_read_data(transform, wg_sample, format)))
-        return hr;
-
-    IMFMediaBuffer_SetCurrentLength(mf_sample->media_buffer, wg_sample->size);
-
-    if (wg_sample->flags & WG_SAMPLE_FLAG_HAS_PTS)
-        IMFSample_SetSampleTime(mf_sample->sample, wg_sample->pts);
-    if (wg_sample->flags & WG_SAMPLE_FLAG_HAS_DURATION)
-        IMFSample_SetSampleDuration(mf_sample->sample, wg_sample->duration);
-    if (wg_sample->flags & WG_SAMPLE_FLAG_SYNC_POINT)
-        IMFSample_SetUINT32(mf_sample->sample, &MFSampleExtension_CleanPoint, 1);
-
-    return S_OK;
-}
diff --git a/dlls/winegstreamer/wg_sample.c b/dlls/winegstreamer/wg_sample.c
new file mode 100644
index 00000000000..051e6199ec9
--- /dev/null
+++ b/dlls/winegstreamer/wg_sample.c
@@ -0,0 +1,203 @@
+/*
+ * Copyright 2022 Rémi Bernon for CodeWeavers
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#include "gst_private.h"
+
+#include "wmcodecdsp.h"
+#include "mfapi.h"
+
+#include "wine/debug.h"
+#include "wine/list.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(mfplat);
+
+struct wg_sample_queue
+{
+    CRITICAL_SECTION cs;
+    struct list samples;
+};
+
+struct sample
+{
+    IMFSample *sample;
+    IMFMediaBuffer *media_buffer;
+    struct wg_sample wg_sample;
+    struct list entry;
+};
+
+HRESULT wg_sample_create_mf(IMFSample *mf_sample, struct wg_sample **out)
+{
+    DWORD current_length, max_length;
+    struct sample *sample;
+    BYTE *buffer;
+    HRESULT hr;
+
+    if (!(sample = calloc(1, sizeof(*sample))))
+        return E_OUTOFMEMORY;
+    if (FAILED(hr = IMFSample_ConvertToContiguousBuffer(mf_sample, &sample->media_buffer)))
+        goto fail;
+    if (FAILED(hr = IMFMediaBuffer_Lock(sample->media_buffer, &buffer, &max_length, &current_length)))
+        goto fail;
+
+    IMFSample_AddRef((sample->sample = mf_sample));
+    sample->wg_sample.data = buffer;
+    sample->wg_sample.size = current_length;
+    sample->wg_sample.max_size = max_length;
+
+    *out = &sample->wg_sample;
+    TRACE_(mfplat)("Created wg_sample %p for IMFSample %p.\n", *out, mf_sample);
+    return S_OK;
+
+fail:
+    if (sample->media_buffer)
+        IMFMediaBuffer_Release(sample->media_buffer);
+    free(sample);
+    return hr;
+}
+
+void wg_sample_release(struct wg_sample *wg_sample)
+{
+    struct sample *sample = CONTAINING_RECORD(wg_sample, struct sample, wg_sample);
+
+    if (InterlockedOr(&wg_sample->refcount, 0))
+    {
+        ERR("wg_sample %p is still in use, trouble ahead!\n", wg_sample);
+        return;
+    }
+
+    IMFMediaBuffer_Unlock(sample->media_buffer);
+    IMFMediaBuffer_Release(sample->media_buffer);
+    IMFSample_Release(sample->sample);
+
+    free(sample);
+}
+
+static void wg_sample_queue_begin_append(struct wg_sample_queue *queue, struct wg_sample *wg_sample)
+{
+    struct sample *sample = CONTAINING_RECORD(wg_sample, struct sample, wg_sample);
+
+    /* make sure a concurrent wg_sample_queue_flush call won't release the sample until we're done */
+    InterlockedIncrement(&wg_sample->refcount);
+    sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_REFCOUNT;
+
+    EnterCriticalSection(&queue->cs);
+    list_add_tail(&queue->samples, &sample->entry);
+    LeaveCriticalSection(&queue->cs);
+}
+
+static void wg_sample_queue_end_append(struct wg_sample_queue *queue, struct wg_sample *wg_sample)
+{
+    /* release temporary ref taken in wg_sample_queue_begin_append */
+    InterlockedDecrement(&wg_sample->refcount);
+
+    wg_sample_queue_flush(queue, false);
+}
+
+void wg_sample_queue_flush(struct wg_sample_queue *queue, bool all)
+{
+    struct sample *sample, *next;
+
+    EnterCriticalSection(&queue->cs);
+
+    LIST_FOR_EACH_ENTRY_SAFE(sample, next, &queue->samples, struct sample, entry)
+    {
+        if (!InterlockedOr(&sample->wg_sample.refcount, 0) || all)
+        {
+            list_remove(&sample->entry);
+            wg_sample_release(&sample->wg_sample);
+        }
+    }
+
+    LeaveCriticalSection(&queue->cs);
+}
+
+HRESULT wg_sample_queue_create(struct wg_sample_queue **out)
+{
+    struct wg_sample_queue *queue;
+
+    if (!(queue = calloc(1, sizeof(*queue))))
+        return E_OUTOFMEMORY;
+
+    InitializeCriticalSection(&queue->cs);
+    queue->cs.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": cs");
+    list_init(&queue->samples);
+
+    TRACE("Created wg_sample_queue %p.\n", queue);
+    *out = queue;
+
+    return S_OK;
+}
+
+void wg_sample_queue_destroy(struct wg_sample_queue *queue)
+{
+    wg_sample_queue_flush(queue, true);
+
+    queue->cs.DebugInfo->Spare[0] = 0;
+    InitializeCriticalSection(&queue->cs);
+
+    free(queue);
+}
+
+HRESULT wg_transform_push_mf(struct wg_transform *transform, struct wg_sample *wg_sample,
+        struct wg_sample_queue *queue)
+{
+    struct sample *sample = CONTAINING_RECORD(wg_sample, struct sample, wg_sample);
+    LONGLONG time, duration;
+    UINT32 value;
+    HRESULT hr;
+
+    if (SUCCEEDED(IMFSample_GetSampleTime(sample->sample, &time)))
+    {
+        sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_PTS;
+        sample->wg_sample.pts = time;
+    }
+    if (SUCCEEDED(IMFSample_GetSampleDuration(sample->sample, &duration)))
+    {
+        sample->wg_sample.flags |= WG_SAMPLE_FLAG_HAS_DURATION;
+        sample->wg_sample.duration = duration;
+    }
+    if (SUCCEEDED(IMFSample_GetUINT32(sample->sample, &MFSampleExtension_CleanPoint, &value)) && value)
+        sample->wg_sample.flags |= WG_SAMPLE_FLAG_SYNC_POINT;
+
+    wg_sample_queue_begin_append(queue, wg_sample);
+    hr = wg_transform_push_data(transform, wg_sample);
+    wg_sample_queue_end_append(queue, wg_sample);
+
+    return hr;
+}
+
+HRESULT wg_transform_read_mf(struct wg_transform *transform, struct wg_sample *wg_sample,
+        struct wg_format *format)
+{
+    struct sample *sample = CONTAINING_RECORD(wg_sample, struct sample, wg_sample);
+    HRESULT hr;
+
+    if (FAILED(hr = wg_transform_read_data(transform, wg_sample, format)))
+        return hr;
+
+    IMFMediaBuffer_SetCurrentLength(sample->media_buffer, wg_sample->size);
+
+    if (wg_sample->flags & WG_SAMPLE_FLAG_HAS_PTS)
+        IMFSample_SetSampleTime(sample->sample, wg_sample->pts);
+    if (wg_sample->flags & WG_SAMPLE_FLAG_HAS_DURATION)
+        IMFSample_SetSampleDuration(sample->sample, wg_sample->duration);
+    if (wg_sample->flags & WG_SAMPLE_FLAG_SYNC_POINT)
+        IMFSample_SetUINT32(sample->sample, &MFSampleExtension_CleanPoint, 1);
+
+    return S_OK;
+}
-- 
GitLab


https://gitlab.winehq.org/wine/wine/-/merge_requests/220



More information about the wine-devel mailing list