[vlc-devel] [PATCH] [RFC] always output an opaque D3D9 surface from DXVA

Rémi Denis-Courmont remi at remlab.net
Thu Apr 23 22:58:20 CEST 2015


Le jeudi 23 avril 2015, 17:11:19 Steve Lhomme a écrit :
> This is a test code to show how DXVA direct rendering could be done.
> 
> When avcodec asks for an AVFrame, the vout and its decoder pool is already
> created. So we use the D3D9 device from the picture_t coming from that pool
> to recreate the DXVA2 decoder surface.
> 
> This is working fine for normal playback, seeking, opening files of
> same/different dimensions.
> 
> The decoder of D3D9 surface is created in the vout wrapper (like all the
> others) but with a dirty hack for now.
> 
> This code also works with direct rendering to D3D9, not included in this
> patch.
> 
> The changes to the other va->Setup callback are not done and it's a
> temporary test code. ---
>  include/vlc_fourcc.h            |   3 +
>  modules/codec/avcodec/dxva2.c   | 173 ++++++++++++++++++++++------
>  modules/codec/avcodec/va.h      |   6 +-
>  modules/codec/avcodec/video.c   |  19 +--
>  modules/video_chroma/copy.c     |  40 +++++--
>  src/Makefile.am                 |   2 +
>  src/misc/fourcc.c               |   3 +
>  src/video_output/vout_wrapper.c |  17 ++-
>  src/win32/direct3d9_pool.c      | 248
> ++++++++++++++++++++++++++++++++++++++++ src/win32/direct3d9_pool.h      | 
> 39 +++++++
>  10 files changed, 491 insertions(+), 59 deletions(-)
>  create mode 100644 src/win32/direct3d9_pool.c
>  create mode 100644 src/win32/direct3d9_pool.h
> 
> diff --git a/include/vlc_fourcc.h b/include/vlc_fourcc.h
> index 5d30ece..df82f6f 100644
> --- a/include/vlc_fourcc.h
> +++ b/include/vlc_fourcc.h
> @@ -332,6 +332,9 @@
>  /* Broadcom MMAL opaque buffer type */
>  #define VLC_CODEC_MMAL_OPAQUE     VLC_FOURCC('M','M','A','L')
> 
> +/* DXVA2 opaque video surface for use with D3D9 */
> +#define VLC_CODEC_D3D9_OPAQUE     VLC_FOURCC('D','X','A','9')
> +
>  /* Image codec (video) */
>  #define VLC_CODEC_PNG             VLC_FOURCC('p','n','g',' ')
>  #define VLC_CODEC_PPM             VLC_FOURCC('p','p','m',' ')
> diff --git a/modules/codec/avcodec/dxva2.c b/modules/codec/avcodec/dxva2.c
> index db9820f..4382e24 100644
> --- a/modules/codec/avcodec/dxva2.c
> +++ b/modules/codec/avcodec/dxva2.c
> @@ -42,6 +42,7 @@
>  #include <vlc_cpu.h>
>  #include <vlc_plugin.h>
>  #include <vlc_codecs.h>
> +#include <vlc_filter.h>
> 
>  #include <libavcodec/avcodec.h>
>  #    define DXVA2API_USE_BITFIELDS
> @@ -55,12 +56,19 @@
>  static int Open(vlc_va_t *, AVCodecContext *, const es_format_t *);
>  static void Close(vlc_va_t *, AVCodecContext *);
> 
> +static int  OpenFilter( vlc_object_t * );
> +static void CloseFilter( vlc_object_t * );
> +
>  vlc_module_begin()
>      set_description(N_("DirectX Video Acceleration (DXVA) 2.0"))
>      set_capability("hw decoder", 0)
>      set_category(CAT_INPUT)
>      set_subcategory(SUBCAT_INPUT_VCODEC)
>      set_callbacks(Open, Close)
> +    add_submodule()
> +        set_description( N_("DXVA2 surface to planes") )
> +        set_capability( "video filter2", 10 )
> +        set_callbacks( OpenFilter, CloseFilter )
>  vlc_module_end()
> 
>  #include <windows.h>
> @@ -348,6 +356,11 @@ struct vlc_va_sys_t
>      LPDIRECT3DSURFACE9 hw_surface[VA_DXVA2_MAX_SURFACE_COUNT];
>  };
> 
> +struct picture_sys_t
> +{
> +    LPDIRECT3DSURFACE9 surface;
> +};
> +
>  /* */
>  static int D3dCreateDevice(vlc_va_t *);
>  static void D3dDestroyDevice(vlc_va_sys_t *);
> @@ -369,9 +382,49 @@ static void DxCreateVideoConversion(vlc_va_sys_t *);
>  static void DxDestroyVideoConversion(vlc_va_sys_t *);
> 
>  /* */
> -static int Setup(vlc_va_t *va, AVCodecContext *avctx, vlc_fourcc_t *chroma)
> +static int Setup(vlc_va_t *va, AVCodecContext *avctx, vlc_fourcc_t
> *chroma, picture_t *p_test_output) {

I think it is preferable for the hardware context to be made available already 
at Open(). (Also I would pass the picture_sys_t cast to void, rather than the 
whole picture_t. It would be slightly less ugly.)

Besides Setup needs to go away separately. It should be folded into Open() 
(for all plugins). libavcodec has to call get_format() again if the resolution 
changes. 

-- 
Rémi Denis-Courmont
http://www.remlab.net/




More information about the vlc-devel mailing list