[vlc-devel] [PATCH 12/17] directx_va: move the pre-allocated hw_surface in directx_va

Steve Lhomme robux4 at videolabs.io
Tue Jun 20 17:45:44 CEST 2017


---
 modules/codec/avcodec/d3d11va.c             | 22 ++++++++++++----------
 modules/codec/avcodec/directx_va.h          |  3 +++
 modules/codec/avcodec/dxva2.c               | 18 +++++++++---------
 modules/codec/avcodec/va_surface.c          |  4 ++--
 modules/codec/avcodec/va_surface_internal.h |  3 +--
 5 files changed, 27 insertions(+), 23 deletions(-)

diff --git a/modules/codec/avcodec/d3d11va.c b/modules/codec/avcodec/d3d11va.c
index a51763b8bd..c27ee90df0 100644
--- a/modules/codec/avcodec/d3d11va.c
+++ b/modules/codec/avcodec/d3d11va.c
@@ -165,7 +165,7 @@ void SetupAVCodecContext(vlc_va_t *va)
     sys->hw.decoder = dx_sys->decoder;
     sys->hw.cfg = &sys->cfg;
     sys->hw.surface_count = dx_sys->va_pool.surface_count;
-    sys->hw.surface = dx_sys->va_pool.hw_surface;
+    sys->hw.surface = dx_sys->hw_surface;
     sys->hw.context_mutex = sys->context_mutex;
 
     if (IsEqualGUID(&dx_sys->input, &DXVA_Intel_H264_NoFGT_ClearVideo))
@@ -238,8 +238,10 @@ done:
     return pic_ctx;
 }
 
-static struct va_pic_context* NewSurfacePicContext(vlc_va_t *va, ID3D11VideoDecoderOutputView *surface)
+static struct va_pic_context* NewSurfacePicContext(vlc_va_t *va, int surface_index)
 {
+    directx_sys_t *dx_sys = &va->sys->dx_sys;
+    ID3D11VideoDecoderOutputView *surface = dx_sys->hw_surface[surface_index];
     ID3D11ShaderResourceView *resourceView[D3D11_MAX_SHADER_VIEW];
     ID3D11Resource *p_resource;
     ID3D11VideoDecoderOutputView_GetResource(surface, &p_resource);
@@ -793,7 +795,7 @@ static int DxCreateDecoderSurfaces(vlc_va_t *va, int codec_id, const video_forma
         for (surface_idx = 0; surface_idx < dx_sys->va_pool.surface_count; surface_idx++) {
             picture_t *pic = decoder_NewPicture( (decoder_t*) va->obj.parent );
             sys->extern_pics[surface_idx] = pic;
-            dx_sys->va_pool.hw_surface[surface_idx] = NULL;
+            dx_sys->hw_surface[surface_idx] = NULL;
             if (pic==NULL)
             {
                 msg_Warn(va, "not enough decoder pictures %d out of %d", surface_idx, dx_sys->va_pool.surface_count);
@@ -836,17 +838,17 @@ static int DxCreateDecoderSurfaces(vlc_va_t *va, int codec_id, const video_forma
 
             AllocateShaderView(VLC_OBJECT(va), dx_sys->d3ddev, textureFmt, pic->p_sys->texture, pic->p_sys->slice_index, pic->p_sys->resourceView);
 
-            dx_sys->va_pool.hw_surface[surface_idx] = pic->p_sys->decoder;
+            dx_sys->hw_surface[surface_idx] = pic->p_sys->decoder;
         }
 
         if (!sys->b_extern_pool)
         {
             for (size_t i = 0; i < surface_idx; ++i)
             {
-                if (dx_sys->va_pool.hw_surface[i])
+                if (dx_sys->hw_surface[i])
                 {
-                    ID3D11VideoDecoderOutputView_Release(dx_sys->va_pool.hw_surface[i]);
-                    dx_sys->va_pool.hw_surface[i] = NULL;
+                    ID3D11VideoDecoderOutputView_Release(dx_sys->hw_surface[i]);
+                    dx_sys->hw_surface[i] = NULL;
                 }
                 if (sys->extern_pics[i])
                 {
@@ -895,7 +897,7 @@ static int DxCreateDecoderSurfaces(vlc_va_t *va, int codec_id, const video_forma
             hr = ID3D11VideoDevice_CreateVideoDecoderOutputView( dx_sys->d3ddec,
                                                                  (ID3D11Resource*) p_texture,
                                                                  &viewDesc,
-                                                                 &dx_sys->va_pool.hw_surface[dx_sys->va_pool.surface_count] );
+                                                                 &dx_sys->hw_surface[dx_sys->va_pool.surface_count] );
             if (FAILED(hr)) {
                 msg_Err(va, "CreateVideoDecoderOutputView %d failed. (hr=0x%0lx)", dx_sys->va_pool.surface_count, hr);
                 ID3D11Texture2D_Release(p_texture);
@@ -988,13 +990,13 @@ static void DxDestroySurfaces(vlc_va_t *va)
     directx_sys_t *dx_sys = &va->sys->dx_sys;
     if (dx_sys->va_pool.surface_count && !va->sys->b_extern_pool) {
         ID3D11Resource *p_texture;
-        ID3D11VideoDecoderOutputView_GetResource( dx_sys->va_pool.hw_surface[0], &p_texture );
+        ID3D11VideoDecoderOutputView_GetResource( dx_sys->hw_surface[0], &p_texture );
         ID3D11Resource_Release(p_texture);
         ID3D11Resource_Release(p_texture);
     }
     for (int i = 0; i < dx_sys->va_pool.surface_count; i++)
     {
-        ID3D11VideoDecoderOutputView_Release( dx_sys->va_pool.hw_surface[i] );
+        ID3D11VideoDecoderOutputView_Release( dx_sys->hw_surface[i] );
         for (int j = 0; j < D3D11_MAX_SHADER_VIEW; j++)
         {
             if (va->sys->resourceView[i*D3D11_MAX_SHADER_VIEW + j])
diff --git a/modules/codec/avcodec/directx_va.h b/modules/codec/avcodec/directx_va.h
index 4aa872f3ce..1e6155b8fd 100644
--- a/modules/codec/avcodec/directx_va.h
+++ b/modules/codec/avcodec/directx_va.h
@@ -55,6 +55,9 @@ typedef struct
 {
     va_pool_t             va_pool;
 
+    /* for pre allocation */
+    D3D_DecoderSurface     *hw_surface[MAX_SURFACE_COUNT];
+
     /* DLL */
     HINSTANCE             hdecoder_dll;
     const TCHAR           *psz_decoder_dll;
diff --git a/modules/codec/avcodec/dxva2.c b/modules/codec/avcodec/dxva2.c
index b950bc6abb..52c92d2bbe 100644
--- a/modules/codec/avcodec/dxva2.c
+++ b/modules/codec/avcodec/dxva2.c
@@ -168,7 +168,7 @@ void SetupAVCodecContext(vlc_va_t *va)
     sys->hw.decoder = dx_sys->decoder;
     sys->hw.cfg = &sys->cfg;
     sys->hw.surface_count = dx_sys->va_pool.surface_count;
-    sys->hw.surface = dx_sys->va_pool.hw_surface;
+    sys->hw.surface = dx_sys->hw_surface;
 
     if (IsEqualGUID(&dx_sys->input, &DXVA_Intel_H264_NoFGT_ClearVideo))
         sys->hw.workaround |= FF_DXVA2_WORKAROUND_INTEL_CLEARVIDEO;
@@ -218,10 +218,10 @@ static struct va_pic_context *CreatePicContext(IDirect3DSurface9 *surface)
     return pic_ctx;
 }
 
-static struct va_pic_context* NewSurfacePicContext(vlc_va_t *va, IDirect3DSurface9 *surface)
+static struct va_pic_context* NewSurfacePicContext(vlc_va_t *va, int surface_index)
 {
-    VLC_UNUSED(va);
-    return CreatePicContext(surface);
+    directx_sys_t *dx_sys = &va->sys->dx_sys;
+    return CreatePicContext(dx_sys->hw_surface[surface_index]);
 }
 
 static int Get(vlc_va_t *va, picture_t *pic, uint8_t **data)
@@ -662,7 +662,7 @@ static int DxCreateVideoDecoder(vlc_va_t *va, int codec_id, const video_format_t
                                                          D3DPOOL_DEFAULT,
                                                          0,
                                                          DXVA2_VideoDecoderRenderTarget,
-                                                         sys->va_pool.hw_surface,
+                                                         sys->hw_surface,
                                                          NULL);
     if (FAILED(hr)) {
         msg_Err(va, "IDirectXVideoAccelerationService_CreateSurface %d failed (hr=0x%0lx)", sys->va_pool.surface_count - 1, hr);
@@ -686,7 +686,7 @@ static int DxCreateVideoDecoder(vlc_va_t *va, int codec_id, const video_format_t
     if (FAILED(hr)) {
         msg_Err(va, "extra buffer impossible, avoid a crash (hr=0x%0lx)", hr);
         for (int i = 0; i < sys->va_pool.surface_count; i++)
-            IDirect3DSurface9_Release( sys->va_pool.hw_surface[i] );
+            IDirect3DSurface9_Release( sys->hw_surface[i] );
         sys->va_pool.surface_count = 0;
         return VLC_EGENERIC;
     }
@@ -730,7 +730,7 @@ static int DxCreateVideoDecoder(vlc_va_t *va, int codec_id, const video_format_t
                                                                     &cfg_list))) {
         msg_Err(va, "IDirectXVideoDecoderService_GetDecoderConfigurations failed");
         for (int i = 0; i < sys->va_pool.surface_count; i++)
-            IDirect3DSurface9_Release( sys->va_pool.hw_surface[i] );
+            IDirect3DSurface9_Release( sys->hw_surface[i] );
         sys->va_pool.surface_count = 0;
         return VLC_EGENERIC;
     }
@@ -773,12 +773,12 @@ static int DxCreateVideoDecoder(vlc_va_t *va, int codec_id, const video_format_t
                                                               &sys->input,
                                                               &dsc,
                                                               &p_sys->cfg,
-                                                              sys->va_pool.hw_surface,
+                                                              sys->hw_surface,
                                                               sys->va_pool.surface_count,
                                                               &decoder))) {
         msg_Err(va, "IDirectXVideoDecoderService_CreateVideoDecoder failed");
         for (int i = 0; i < sys->va_pool.surface_count; i++)
-            IDirect3DSurface9_Release( sys->va_pool.hw_surface[i] );
+            IDirect3DSurface9_Release( sys->hw_surface[i] );
         sys->va_pool.surface_count = 0;
         return VLC_EGENERIC;
     }
diff --git a/modules/codec/avcodec/va_surface.c b/modules/codec/avcodec/va_surface.c
index 445b4eac7e..291d134251 100644
--- a/modules/codec/avcodec/va_surface.c
+++ b/modules/codec/avcodec/va_surface.c
@@ -65,7 +65,7 @@ int va_pool_Setup(vlc_va_t *va, va_pool_t *va_pool, const AVCodecContext *avctx,
         return VLC_EGENERIC;
 
     /* */
-    msg_Dbg(va, "va_pool_Setup id %d %dx%d", avctx->codec_id, avctx->coded_width, avctx->coded_height);
+    msg_Dbg(va, "va_pool_Setup id %d %dx%d count: %d", avctx->codec_id, avctx->coded_width, avctx->coded_height, count);
 
     if (count > MAX_SURFACE_COUNT)
         return VLC_EGENERIC;
@@ -102,7 +102,7 @@ int va_pool_Setup(vlc_va_t *va, va_pool_t *va_pool, const AVCodecContext *avctx,
             va_pool->surface_count = i;
             return VLC_ENOMEM;
         }
-        va_pool->surface[i] = va_pool->pf_new_surface_context(va, va_pool->hw_surface[i]);
+        va_pool->surface[i] = va_pool->pf_new_surface_context(va, i);
         if (unlikely(va_pool->surface[i]==NULL))
         {
             free(p_surface);
diff --git a/modules/codec/avcodec/va_surface_internal.h b/modules/codec/avcodec/va_surface_internal.h
index 843c71325d..c4cc54dedc 100644
--- a/modules/codec/avcodec/va_surface_internal.h
+++ b/modules/codec/avcodec/va_surface_internal.h
@@ -55,7 +55,6 @@ typedef struct
     int          surface_height;
 
     struct va_pic_context  *surface[MAX_SURFACE_COUNT];
-    D3D_DecoderSurface     *hw_surface[MAX_SURFACE_COUNT];
 
     int (*pf_create_device)(vlc_va_t *);
     void (*pf_destroy_device)(vlc_va_t *);
@@ -83,7 +82,7 @@ typedef struct
     /**
      * Create a new context for the surface being acquired
      */
-    struct va_pic_context* (*pf_new_surface_context)(vlc_va_t *, D3D_DecoderSurface *);
+    struct va_pic_context* (*pf_new_surface_context)(vlc_va_t *, int surface_index);
 
 } va_pool_t;
 
-- 
2.12.1



More information about the vlc-devel mailing list