Nikolay Sivov : mf/session: Implement IsRateSupported().

Alexandre Julliard julliard at winehq.org
Mon Nov 8 15:45:05 CST 2021


Module: wine
Branch: master
Commit: d8bbbfd589c3a766165d54e8389420f80b75c0af
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=d8bbbfd589c3a766165d54e8389420f80b75c0af

Author: Nikolay Sivov <nsivov at codeweavers.com>
Date:   Mon Nov  8 11:41:45 2021 +0300

mf/session: Implement IsRateSupported().

Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 dlls/mf/session.c | 80 +++++++++++++++++++++++++++++++++++++++++++++++++++++--
 1 file changed, 78 insertions(+), 2 deletions(-)

diff --git a/dlls/mf/session.c b/dlls/mf/session.c
index e3d77864494..c4dc6419b87 100644
--- a/dlls/mf/session.c
+++ b/dlls/mf/session.c
@@ -3537,6 +3537,80 @@ static HRESULT session_get_presentation_rate(struct media_session *session, MFRA
     return hr;
 }
 
+static HRESULT session_is_presentation_rate_supported(struct media_session *session, BOOL thin, float rate,
+        float *nearest_rate)
+{
+    IMFRateSupport *rate_support;
+    struct media_source *source;
+    struct media_sink *sink;
+    float value = 0.0f, tmp;
+    unsigned int flags;
+    HRESULT hr = S_OK;
+
+    if (!nearest_rate) nearest_rate = &tmp;
+
+    if (rate == 0.0f)
+    {
+        *nearest_rate = 1.0f;
+        return S_OK;
+    }
+
+    EnterCriticalSection(&session->cs);
+
+    if (session->presentation.topo_status != MF_TOPOSTATUS_INVALID)
+    {
+        LIST_FOR_EACH_ENTRY(source, &session->presentation.sources, struct media_source, entry)
+        {
+            if (FAILED(hr = MFGetService((IUnknown *)source->source, &MF_RATE_CONTROL_SERVICE, &IID_IMFRateSupport,
+                    (void **)&rate_support)))
+            {
+                value = 1.0f;
+                break;
+            }
+
+            value = rate;
+            if (FAILED(hr = IMFRateSupport_IsRateSupported(rate_support, thin, rate, &value)))
+                WARN("Source does not support rate %f, hr %#x.\n", rate, hr);
+            IMFRateSupport_Release(rate_support);
+
+            /* Only "first" source is considered. */
+            break;
+        }
+
+        if (SUCCEEDED(hr))
+        {
+            /* For sinks only check if rate is supported, ignoring nearest values. */
+            LIST_FOR_EACH_ENTRY(sink, &session->presentation.sinks, struct media_sink, entry)
+            {
+                flags = 0;
+                if (FAILED(hr = IMFMediaSink_GetCharacteristics(sink->sink, &flags)))
+                    break;
+
+                if (flags & MEDIASINK_RATELESS)
+                    continue;
+
+                if (FAILED(MFGetService((IUnknown *)sink->sink, &MF_RATE_CONTROL_SERVICE, &IID_IMFRateSupport,
+                        (void **)&rate_support)))
+                    continue;
+
+                hr = IMFRateSupport_IsRateSupported(rate_support, thin, rate, NULL);
+                IMFRateSupport_Release(rate_support);
+                if (FAILED(hr))
+                {
+                    WARN("Sink %p does not support rate %f, hr %#x.\n", sink->sink, rate, hr);
+                    break;
+                }
+            }
+        }
+    }
+
+    LeaveCriticalSection(&session->cs);
+
+    *nearest_rate = value;
+
+    return hr;
+}
+
 static HRESULT WINAPI session_rate_support_GetSlowestRate(IMFRateSupport *iface, MFRATE_DIRECTION direction,
         BOOL thin, float *rate)
 {
@@ -3560,9 +3634,11 @@ static HRESULT WINAPI session_rate_support_GetFastestRate(IMFRateSupport *iface,
 static HRESULT WINAPI session_rate_support_IsRateSupported(IMFRateSupport *iface, BOOL thin, float rate,
         float *nearest_supported_rate)
 {
-    FIXME("%p, %d, %f, %p.\n", iface, thin, rate, nearest_supported_rate);
+    struct media_session *session = impl_session_from_IMFRateSupport(iface);
 
-    return E_NOTIMPL;
+    TRACE("%p, %d, %f, %p.\n", iface, thin, rate, nearest_supported_rate);
+
+    return session_is_presentation_rate_supported(session, thin, rate, nearest_supported_rate);
 }
 
 static const IMFRateSupportVtbl session_rate_support_vtbl =




More information about the wine-cvs mailing list