From c2e865be9182adc4cc78658a507fd1415fb05efb Mon Sep 17 00:00:00 2001
From: Dom Cobley <popcornmix@gmail.com>
Date: Tue, 20 Jun 2023 15:13:09 +0100
Subject: [PATCH 09/13] CDVDVideoCodecDRMPRIME: Support decoding to DRMPRIME
 with sw deinterlace

We can map a YUV style DRM_PRIME buffer back to AV_PIX_FMT_YUV420P
to allow subsquent sw deinterlace
---
 .../DVDCodecs/Video/DVDVideoCodecDRMPRIME.cpp | 22 +++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/xbmc/cores/VideoPlayer/DVDCodecs/Video/DVDVideoCodecDRMPRIME.cpp b/xbmc/cores/VideoPlayer/DVDCodecs/Video/DVDVideoCodecDRMPRIME.cpp
index a5d340525d69..c228a75f8b90 100644
--- a/xbmc/cores/VideoPlayer/DVDCodecs/Video/DVDVideoCodecDRMPRIME.cpp
+++ b/xbmc/cores/VideoPlayer/DVDCodecs/Video/DVDVideoCodecDRMPRIME.cpp
@@ -704,6 +704,9 @@ bool CDVDVideoCodecDRMPRIME::FilterOpen(const std::string& filters, AVPixelForma
   if (filters.find("deinterlace") != std::string::npos && pix_fmt == AV_PIX_FMT_YUV420P)
      pix_fmt = AV_PIX_FMT_DRM_PRIME;
 
+  if (filters.find("bwdif") != std::string::npos && pix_fmt == AV_PIX_FMT_DRM_PRIME)
+     pix_fmt = AV_PIX_FMT_YUV420P;
+
   if (m_pFilterGraph)
     FilterClose();
 
@@ -870,6 +873,25 @@ CDVDVideoCodec::VCReturn CDVDVideoCodecDRMPRIME::ProcessFilterIn()
     m_pFrame->data[0] = reinterpret_cast<uint8_t*>(descriptor);
     m_pFrame->format = AV_PIX_FMT_DRM_PRIME;
   }
+  // hw decoded buffers submitted to sw decoder need mapping of planes for cpu to access
+  else if (m_pFrame->format == AV_PIX_FMT_DRM_PRIME && m_pFilterGraph && m_pFilterIn->outputs[0]->format == AV_PIX_FMT_YUV420P)
+  {
+    AVFrame *frame = av_frame_alloc();
+    frame->width = m_pFrame->width;
+    frame->height = m_pFrame->height;
+    frame->format = AV_PIX_FMT_YUV420P;
+    int ret = av_hwframe_map(frame, m_pFrame, (int)AV_HWFRAME_MAP_READ);
+    if (ret < 0)
+    {
+      char err[AV_ERROR_MAX_STRING_SIZE] = {};
+      av_strerror(ret, err, AV_ERROR_MAX_STRING_SIZE);
+      CLog::Log(LOGERROR, "CDVDVideoCodecDRMPRIME::{} - av_hwframe_map failed: {} ({})",
+                __FUNCTION__, err, ret);
+      return VC_ERROR;
+    }
+    av_frame_unref(m_pFrame);
+    av_frame_move_ref(m_pFrame, frame);
+  }
 
   int ret = av_buffersrc_add_frame(m_pFilterIn, m_pFrame);
   if (ret < 0)
-- 
2.39.5

