summaryrefslogtreecommitdiffstats
path: root/libhb/vadxva2.h
blob: 43f5047cdc9dc2712fee60fa4be35b27e469f78a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
/* vadxva2.h

   Copyright (c) 2003-2015 HandBrake Team
   This file is part of the HandBrake source code
   Homepage: <http://handbrake.fr/>.
   It may be used under the terms of the GNU General Public License v2.
   For full terms see the file COPYING file or visit http://www.gnu.org/licenses/gpl-2.0.html

   Authors: Peng Gao <peng@multicorewareinc.com> <http://www.multicorewareinc.com/>
            Li   Cao <li@multicorewareinc.com> <http://www.multicorewareinc.com/>

 */

#ifdef USE_HWD

#ifndef HB_VA_DXVA2_H
#define HB_VA_DXVA2_H

#include "hbffmpeg.h"
#include "d3d9.h"
#include "libavcodec/dxva2.h"
#include "dxva2api.h"
#include "common.h"
#include "opencl.h"
#include "openclwrapper.h"

#define HB_FOURCC( a, b, c, d ) ( ((uint32_t)a) | ( ((uint32_t)b) << 8 ) | ( ((uint32_t)c) << 16 ) | ( ((uint32_t)d) << 24 ) )
#define MAKEFOURCC( a, b, c, d ) ((DWORD)(BYTE)(a) | ((DWORD)(BYTE)(b) << 8) | ((DWORD)(BYTE)(c) << 16) | ((DWORD)(BYTE)(d) << 24 ))
#define HB_CODEC_YV12 HB_FOURCC( 'Y', 'V', '1', '2' )
#define HB_CODEC_NV12 HB_FOURCC( 'N', 'V', '1', '2' )
#define DXVA2_E_NOT_INITIALIZED     MAKE_HRESULT( 1, 4, 4096 )
#define DXVA2_E_NEW_VIDEO_DEVICE    MAKE_HRESULT( 1, 4, 4097 )
#define DXVA2_E_VIDEO_DEVICE_LOCKED MAKE_HRESULT( 1, 4, 4098 )
#define DXVA2_E_NOT_AVAILABLE       MAKE_HRESULT( 1, 4, 4099 )
#define VA_DXVA2_MAX_SURFACE_COUNT (64)

static const GUID DXVA_NoEncrypt = { 0x1b81bed0, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID IID_IDirectXVideoDecoderService = {0xfc51a551, 0xd5e7, 0x11d9, {0xaf, 0x55, 0x00, 0x05, 0x4e, 0x43, 0xff, 0x02}};
static const GUID DXVA2_ModeMPEG2_MoComp = { 0xe6a9f44b, 0x61b0, 0x4563, {0x9e, 0xa4, 0x63, 0xd2, 0xa3, 0xc6, 0xfe, 0x66} };
static const GUID DXVA2_ModeMPEG2_IDCT = { 0xbf22ad00, 0x03ea, 0x4690, {0x80, 0x77, 0x47, 0x33, 0x46, 0x20, 0x9b, 0x7e} };
static const GUID DXVA2_ModeMPEG2_VLD = { 0xee27417f, 0x5e28, 0x4e65, {0xbe, 0xea, 0x1d, 0x26, 0xb5, 0x08, 0xad, 0xc9} };
static const GUID DXVA2_ModeH264_A = { 0x1b81be64, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeH264_B = { 0x1b81be65, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeH264_C = { 0x1b81be66, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeH264_D = { 0x1b81be67, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeH264_E = { 0x1b81be68, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeH264_F = { 0x1b81be69, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVADDI_Intel_ModeH264_A = { 0x604F8E64, 0x4951, 0x4c54, {0x88, 0xFE, 0xAB, 0xD2, 0x5C, 0x15, 0xB3, 0xD6} };
static const GUID DXVADDI_Intel_ModeH264_C = { 0x604F8E66, 0x4951, 0x4c54, {0x88, 0xFE, 0xAB, 0xD2, 0x5C, 0x15, 0xB3, 0xD6} };
static const GUID DXVADDI_Intel_ModeH264_E = { 0x604F8E68, 0x4951, 0x4c54, {0x88, 0xFE, 0xAB, 0xD2, 0x5C, 0x15, 0xB3, 0xD6} };
static const GUID DXVA2_ModeWMV8_A = { 0x1b81be80, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeWMV8_B = { 0x1b81be81, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeWMV9_A = { 0x1b81be90, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeWMV9_B = { 0x1b81be91, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeWMV9_C = { 0x1b81be94, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeVC1_A = { 0x1b81beA0, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeVC1_B = { 0x1b81beA1, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeVC1_C = { 0x1b81beA2, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };
static const GUID DXVA2_ModeVC1_D = { 0x1b81beA3, 0xa0c7, 0x11d3, {0xb9, 0x84, 0x00, 0xc0, 0x4f, 0x2e, 0x73, 0xc5} };

typedef struct
{
    int width;
    int height;
    int rate;
    int rate_base;

}hb_dx_format;

typedef struct
{
    LPDIRECT3DSURFACE9 d3d;
    int                refcount;
    unsigned int       order;

} hb_va_surface_t;

typedef struct
{
    uint8_t *base;
    uint8_t *buffer;
    size_t  size;

} hb_copy_cache_t;

typedef struct
{
    const char *name;
    D3DFORMAT  format;
    uint32_t   codec;

} hb_d3d_format_t;

typedef struct
{
    const char *name;
    const GUID *guid;
    int        codec;
} hb_dx_mode_t;

typedef struct
{
    char                            *description;
    int                             codec_id;
    uint32_t                        i_chroma;
    int                             width;
    int                             height;
    HINSTANCE                       hd3d9_dll;
    HINSTANCE                       hdxva2_dll;
    D3DPRESENT_PARAMETERS           d3dpp;
    LPDIRECT3D9                     d3dobj;
    D3DADAPTER_IDENTIFIER9          d3dai;
    LPDIRECT3DDEVICE9               d3ddev;
    UINT                            token;
    IDirect3DDeviceManager9         *devmng;
    HANDLE                          device;
    IDirectXVideoDecoderService     *vs;
    GUID                            input;
    D3DFORMAT                       render;
    DXVA2_ConfigPictureDecode       cfg;
    IDirectXVideoDecoder            *decoder;
    D3DFORMAT                       output;
    struct dxva_context             hw;
    unsigned                        surface_count;
    unsigned                        surface_order;
    int                             surface_width;
    int                             surface_height;
    uint32_t                        surface_chroma;
    hb_va_surface_t                 surface[VA_DXVA2_MAX_SURFACE_COUNT];
    LPDIRECT3DSURFACE9              hw_surface[VA_DXVA2_MAX_SURFACE_COUNT];
    IDirectXVideoProcessorService   *ps;
    IDirectXVideoProcessor          *vp;
    int64_t input_pts[2];
    int64_t input_dts;
    int     do_job;

    // running nv12toyuv kernel.
    cl_kernel nv12toyuv;
    cl_mem cl_mem_nv12;
    cl_mem cl_mem_yuv;
    uint8_t * nv12toyuv_tmp_in;
    uint8_t * nv12toyuv_tmp_out;
} hb_va_dxva2_t;

typedef struct FilterLink_T
{
    cl_mem cl_inbuf;
    cl_mem cl_outbuf;

    uint8_t *mem_inbuf;
    uint8_t *mem_outbuf;
    int width;
    int height;
    int linesizeY;
    int linesizeUV;
    int inmemdataflag;
    int outmemdataflag;
    int incldataflag;
    int outcldataflag;
    int framenum;
    int outputSize; 
} T_FilterLink;

static const hb_d3d_format_t d3d_formats[] =
{
    { "YV12",   MAKEFOURCC( 'Y', 'V', '1', '2' ),    HB_CODEC_YV12 },
    { "NV12",   MAKEFOURCC( 'N', 'V', '1', '2' ),    HB_CODEC_NV12 },
    { NULL, 0, 0 }
};

static const hb_dx_mode_t dxva2_modes[] =
{
    { "DXVA2_ModeMPEG2_VLD",    &DXVA2_ModeMPEG2_VLD,     AV_CODEC_ID_MPEG2VIDEO },
    { "DXVA2_ModeMPEG2_MoComp", &DXVA2_ModeMPEG2_MoComp,  0 },
    { "DXVA2_ModeMPEG2_IDCT",   &DXVA2_ModeMPEG2_IDCT,    0 },

    { "H.264 variable-length decoder (VLD), FGT",               &DXVA2_ModeH264_F,         AV_CODEC_ID_H264 },
    { "H.264 VLD, no FGT",                                      &DXVA2_ModeH264_E,         AV_CODEC_ID_H264 },
    { "H.264 VLD, no FGT (Intel)",                              &DXVADDI_Intel_ModeH264_E, AV_CODEC_ID_H264 },
    { "H.264 IDCT, FGT",                                        &DXVA2_ModeH264_D,         0             },
    { "H.264 inverse discrete cosine transform (IDCT), no FGT", &DXVA2_ModeH264_C,         0             },
    { "H.264 inverse discrete cosine transform (IDCT), no FGT (Intel)", &DXVADDI_Intel_ModeH264_C, 0     },
    { "H.264 MoComp, FGT",                                      &DXVA2_ModeH264_B,         0             },
    { "H.264 motion compensation (MoComp), no FGT",             &DXVA2_ModeH264_A,         0             },
    { "H.264 motion compensation (MoComp), no FGT (Intel)",     &DXVADDI_Intel_ModeH264_A, 0             },

    { "Windows Media Video 8 MoComp",           &DXVA2_ModeWMV8_B, 0 },
    { "Windows Media Video 8 post processing",  &DXVA2_ModeWMV8_A, 0 },

    {  "Windows Media Video 9 IDCT",            &DXVA2_ModeWMV9_C, 0 },
    {  "Windows Media Video 9 MoComp",          &DXVA2_ModeWMV9_B, 0 },
    {  "Windows Media Video 9 post processing", &DXVA2_ModeWMV9_A, 0 },

    { "VC-1 VLD",             &DXVA2_ModeVC1_D, AV_CODEC_ID_VC1 },
    { "VC-1 VLD",             &DXVA2_ModeVC1_D, AV_CODEC_ID_WMV3 },
    { "VC-1 IDCT",            &DXVA2_ModeVC1_C, 0 },
    { "VC-1 MoComp",          &DXVA2_ModeVC1_B, 0 },
    { "VC-1 post processing", &DXVA2_ModeVC1_A, 0 },

    { NULL, NULL, 0 }
};

int hb_va_get_frame_buf( hb_va_dxva2_t *dxva2, AVCodecContext *p_context, AVFrame *frame );
int hb_va_extract( hb_va_dxva2_t *dxva2, uint8_t *dst, AVFrame *frame, int job_w, int job_h, int *crop, hb_oclscale_t *os, int use_opencl, int use_decomb, int use_detelecine );
enum PixelFormat hb_ffmpeg_get_format( AVCodecContext *, const enum PixelFormat * );
hb_va_dxva2_t *hb_va_create_dxva2( hb_va_dxva2_t *dxva2, int codec_id );
void hb_va_new_dxva2( hb_va_dxva2_t *dxva2, AVCodecContext *p_context );
void hb_va_release( hb_va_dxva2_t *dxva2, AVFrame *frame );
void  hb_va_close( hb_va_dxva2_t *dxva2 );
int hb_check_hwd_fmt( int fmt );

#endif // HB_VA_DXVA2_H

#endif // USE_HWD