annotate dxva2_h264.c @ 12530:63edd10ad4bc libavcodec tip

Try to fix crashes introduced by r25218 r25218 made assumptions about the existence of past reference frames that weren't necessarily true.
author darkshikari
date Tue, 28 Sep 2010 09:06:22 +0000
parents 9434d9083b94
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
1 /*
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
2 * DXVA2 H264 HW acceleration.
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
3 *
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
4 * copyright (c) 2009 Laurent Aimar
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
5 *
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
6 * This file is part of FFmpeg.
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
7 *
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
8 * FFmpeg is free software; you can redistribute it and/or
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
9 * modify it under the terms of the GNU Lesser General Public
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
10 * License as published by the Free Software Foundation; either
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
11 * version 2.1 of the License, or (at your option) any later version.
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
12 *
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
13 * FFmpeg is distributed in the hope that it will be useful,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
16 * Lesser General Public License for more details.
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
17 *
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
18 * You should have received a copy of the GNU Lesser General Public
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
19 * License along with FFmpeg; if not, write to the Free Software
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
21 */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
22
10980
9f771d4312ed Moved reusable functions from dxva2_h264.c to dxva2.c
fenrir
parents: 10979
diff changeset
23 #include "dxva2_internal.h"
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
24 #include "h264.h"
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
25 #include "h264data.h"
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
26
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
27 struct dxva2_picture_context {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
28 DXVA_PicParams_H264 pp;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
29 DXVA_Qmatrix_H264 qm;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
30 unsigned slice_count;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
31 DXVA_Slice_H264_Short slice_short[MAX_SLICES];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
32 DXVA_Slice_H264_Long slice_long[MAX_SLICES];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
33 const uint8_t *bitstream;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
34 unsigned bitstream_size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
35 };
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
36
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
37 static void fill_picture_entry(DXVA_PicEntry_H264 *pic,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
38 unsigned index, unsigned flag)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
39 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
40 assert((index&0x7f) == index && (flag&0x01) == flag);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
41 pic->bPicEntry = index | (flag << 7);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
42 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
43
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
44 static void fill_picture_parameters(struct dxva_context *ctx, const H264Context *h,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
45 DXVA_PicParams_H264 *pp)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
46 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
47 const MpegEncContext *s = &h->s;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
48 const Picture *current_picture = s->current_picture_ptr;
11734
f85c4e46272e Fixed h264 long term support with dxva2 AVHWAccel.
fenrir
parents: 11560
diff changeset
49 int i, j;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
50
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
51 memset(pp, 0, sizeof(*pp));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
52 /* Configure current picture */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
53 fill_picture_entry(&pp->CurrPic,
10976
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
54 ff_dxva2_get_surface_index(ctx, current_picture),
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
55 s->picture_structure == PICT_BOTTOM_FIELD);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
56 /* Configure the set of references */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
57 pp->UsedForReferenceFlags = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
58 pp->NonExistingFrameFlags = 0;
11734
f85c4e46272e Fixed h264 long term support with dxva2 AVHWAccel.
fenrir
parents: 11560
diff changeset
59 for (i = 0, j = 0; i < FF_ARRAY_ELEMS(pp->RefFrameList); i++) {
11735
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
60 const Picture *r;
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
61 if (j < h->short_ref_count) {
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
62 r = h->short_ref[j++];
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
63 } else {
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
64 r = NULL;
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
65 while (!r && j < h->short_ref_count + 16)
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
66 r = h->long_ref[j++ - h->short_ref_count];
9434d9083b94 Reindent after last commit on dxva2 h264 AVHWAccel.
fenrir
parents: 11734
diff changeset
67 }
11734
f85c4e46272e Fixed h264 long term support with dxva2 AVHWAccel.
fenrir
parents: 11560
diff changeset
68 if (r) {
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
69 fill_picture_entry(&pp->RefFrameList[i],
10976
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
70 ff_dxva2_get_surface_index(ctx, r),
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
71 r->long_ref != 0);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
72
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
73 if ((r->reference & PICT_TOP_FIELD) && r->field_poc[0] != INT_MAX)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
74 pp->FieldOrderCntList[i][0] = r->field_poc[0];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
75 if ((r->reference & PICT_BOTTOM_FIELD) && r->field_poc[1] != INT_MAX)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
76 pp->FieldOrderCntList[i][1] = r->field_poc[1];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
77
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
78 pp->FrameNumList[i] = r->long_ref ? r->pic_id : r->frame_num;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
79 if (r->reference & PICT_TOP_FIELD)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
80 pp->UsedForReferenceFlags |= 1 << (2*i + 0);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
81 if (r->reference & PICT_BOTTOM_FIELD)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
82 pp->UsedForReferenceFlags |= 1 << (2*i + 1);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
83 } else {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
84 pp->RefFrameList[i].bPicEntry = 0xff;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
85 pp->FieldOrderCntList[i][0] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
86 pp->FieldOrderCntList[i][1] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
87 pp->FrameNumList[i] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
88 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
89 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
90
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
91 pp->wFrameWidthInMbsMinus1 = s->mb_width - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
92 pp->wFrameHeightInMbsMinus1 = s->mb_height - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
93 pp->num_ref_frames = h->sps.ref_frame_count;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
94
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
95 pp->wBitFields = ((s->picture_structure != PICT_FRAME) << 0) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
96 (h->sps.mb_aff << 1) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
97 (h->sps.residual_color_transform_flag << 2) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
98 /* sp_for_switch_flag (not implemented by FFmpeg) */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
99 (0 << 3) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
100 (h->sps.chroma_format_idc << 4) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
101 ((h->nal_ref_idc != 0) << 6) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
102 (h->pps.constrained_intra_pred << 7) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
103 (h->pps.weighted_pred << 8) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
104 (h->pps.weighted_bipred_idc << 9) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
105 /* MbsConsecutiveFlag */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
106 (1 << 11) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
107 (h->sps.frame_mbs_only_flag << 12) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
108 (h->pps.transform_8x8_mode << 13) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
109 ((h->sps.level_idc >= 31) << 14) |
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
110 /* IntraPicFlag (Modified if we detect a non
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
111 * intra slice in decode_slice) */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
112 (1 << 15);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
113
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
114 pp->bit_depth_luma_minus8 = h->sps.bit_depth_luma - 8;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
115 pp->bit_depth_chroma_minus8 = h->sps.bit_depth_chroma - 8;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
116 pp->Reserved16Bits = 3; /* FIXME is there a way to detect the right mode ? */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
117 pp->StatusReportFeedbackNumber = 1 + ctx->report_id++;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
118 pp->CurrFieldOrderCnt[0] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
119 if ((s->picture_structure & PICT_TOP_FIELD) &&
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
120 current_picture->field_poc[0] != INT_MAX)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
121 pp->CurrFieldOrderCnt[0] = current_picture->field_poc[0];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
122 pp->CurrFieldOrderCnt[1] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
123 if ((s->picture_structure & PICT_BOTTOM_FIELD) &&
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
124 current_picture->field_poc[1] != INT_MAX)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
125 pp->CurrFieldOrderCnt[1] = current_picture->field_poc[1];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
126 pp->pic_init_qs_minus26 = h->pps.init_qs - 26;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
127 pp->chroma_qp_index_offset = h->pps.chroma_qp_index_offset[0];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
128 pp->second_chroma_qp_index_offset = h->pps.chroma_qp_index_offset[1];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
129 pp->ContinuationFlag = 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
130 pp->pic_init_qp_minus26 = h->pps.init_qp - 26;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
131 pp->num_ref_idx_l0_active_minus1 = h->pps.ref_count[0] - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
132 pp->num_ref_idx_l1_active_minus1 = h->pps.ref_count[1] - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
133 pp->Reserved8BitsA = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
134 pp->frame_num = h->frame_num;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
135 pp->log2_max_frame_num_minus4 = h->sps.log2_max_frame_num - 4;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
136 pp->pic_order_cnt_type = h->sps.poc_type;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
137 if (h->sps.poc_type == 0)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
138 pp->log2_max_pic_order_cnt_lsb_minus4 = h->sps.log2_max_poc_lsb - 4;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
139 else if (h->sps.poc_type == 1)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
140 pp->delta_pic_order_always_zero_flag = h->sps.delta_pic_order_always_zero_flag;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
141 pp->direct_8x8_inference_flag = h->sps.direct_8x8_inference_flag;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
142 pp->entropy_coding_mode_flag = h->pps.cabac;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
143 pp->pic_order_present_flag = h->pps.pic_order_present;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
144 pp->num_slice_groups_minus1 = h->pps.slice_group_count - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
145 pp->slice_group_map_type = h->pps.mb_slice_group_map_type;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
146 pp->deblocking_filter_control_present_flag = h->pps.deblocking_filter_parameters_present;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
147 pp->redundant_pic_cnt_present_flag= h->pps.redundant_pic_cnt_present;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
148 pp->Reserved8BitsB = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
149 pp->slice_group_change_rate_minus1= 0; /* XXX not implemented by FFmpeg */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
150 //pp->SliceGroupMap[810]; /* XXX not implemented by FFmpeg */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
151 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
152
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
153 static void fill_scaling_lists(const H264Context *h, DXVA_Qmatrix_H264 *qm)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
154 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
155 unsigned i, j;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
156 memset(qm, 0, sizeof(*qm));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
157 for (i = 0; i < 6; i++)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
158 for (j = 0; j < 16; j++)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
159 qm->bScalingLists4x4[i][j] = h->pps.scaling_matrix4[i][zigzag_scan[j]];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
160
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
161 for (i = 0; i < 2; i++)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
162 for (j = 0; j < 64; j++)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
163 qm->bScalingLists8x8[i][j] = h->pps.scaling_matrix8[i][ff_zigzag_direct[j]];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
164 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
165
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
166 static int is_slice_short(struct dxva_context *ctx)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
167 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
168 assert(ctx->cfg->ConfigBitstreamRaw == 1 ||
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
169 ctx->cfg->ConfigBitstreamRaw == 2);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
170 return ctx->cfg->ConfigBitstreamRaw == 2;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
171 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
172
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
173 static void fill_slice_short(DXVA_Slice_H264_Short *slice,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
174 unsigned position, unsigned size)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
175 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
176 memset(slice, 0, sizeof(*slice));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
177 slice->BSNALunitDataLocation = position;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
178 slice->SliceBytesInBuffer = size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
179 slice->wBadSliceChopping = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
180 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
181
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
182 static void fill_slice_long(AVCodecContext *avctx, DXVA_Slice_H264_Long *slice,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
183 unsigned position, unsigned size)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
184 {
10988
3824ef98a6b8 Added a few missing consts in dxva_h264.
fenrir
parents: 10980
diff changeset
185 const H264Context *h = avctx->priv_data;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
186 struct dxva_context *ctx = avctx->hwaccel_context;
10988
3824ef98a6b8 Added a few missing consts in dxva_h264.
fenrir
parents: 10980
diff changeset
187 const MpegEncContext *s = &h->s;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
188 unsigned list;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
189
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
190 memset(slice, 0, sizeof(*slice));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
191 slice->BSNALunitDataLocation = position;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
192 slice->SliceBytesInBuffer = size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
193 slice->wBadSliceChopping = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
194
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
195 slice->first_mb_in_slice = (s->mb_y >> FIELD_OR_MBAFF_PICTURE) * s->mb_width + s->mb_x;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
196 slice->NumMbsForSlice = 0; /* XXX it is set once we have all slices */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
197 slice->BitOffsetToSliceData = get_bits_count(&s->gb) + 8;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
198 slice->slice_type = ff_h264_get_slice_type(h);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
199 if (h->slice_type_fixed)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
200 slice->slice_type += 5;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
201 slice->luma_log2_weight_denom = h->luma_log2_weight_denom;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
202 slice->chroma_log2_weight_denom = h->chroma_log2_weight_denom;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
203 if (h->list_count > 0)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
204 slice->num_ref_idx_l0_active_minus1 = h->ref_count[0] - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
205 if (h->list_count > 1)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
206 slice->num_ref_idx_l1_active_minus1 = h->ref_count[1] - 1;
10979
776dba50775c Move +52 from the loop filter to the alpha/beta offsets in the context.
michael
parents: 10976
diff changeset
207 slice->slice_alpha_c0_offset_div2 = h->slice_alpha_c0_offset / 2 - 26;
776dba50775c Move +52 from the loop filter to the alpha/beta offsets in the context.
michael
parents: 10976
diff changeset
208 slice->slice_beta_offset_div2 = h->slice_beta_offset / 2 - 26;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
209 slice->Reserved8Bits = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
210
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
211 for (list = 0; list < 2; list++) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
212 unsigned i;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
213 for (i = 0; i < FF_ARRAY_ELEMS(slice->RefPicList[list]); i++) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
214 if (list < h->list_count && i < h->ref_count[list]) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
215 const Picture *r = &h->ref_list[list][i];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
216 unsigned plane;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
217 fill_picture_entry(&slice->RefPicList[list][i],
10976
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
218 ff_dxva2_get_surface_index(ctx, r),
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
219 r->reference == PICT_BOTTOM_FIELD);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
220 for (plane = 0; plane < 3; plane++) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
221 int w, o;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
222 if (plane == 0 && h->luma_weight_flag[list]) {
11364
4b64693d115d Fixed DXVA2 H264 hwaccel after luma/chroma_weight changes.
fenrir
parents: 11347
diff changeset
223 w = h->luma_weight[i][list][0];
4b64693d115d Fixed DXVA2 H264 hwaccel after luma/chroma_weight changes.
fenrir
parents: 11347
diff changeset
224 o = h->luma_weight[i][list][1];
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
225 } else if (plane >= 1 && h->chroma_weight_flag[list]) {
11364
4b64693d115d Fixed DXVA2 H264 hwaccel after luma/chroma_weight changes.
fenrir
parents: 11347
diff changeset
226 w = h->chroma_weight[i][list][plane-1][0];
4b64693d115d Fixed DXVA2 H264 hwaccel after luma/chroma_weight changes.
fenrir
parents: 11347
diff changeset
227 o = h->chroma_weight[i][list][plane-1][1];
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
228 } else {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
229 w = 1 << (plane == 0 ? h->luma_log2_weight_denom :
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
230 h->chroma_log2_weight_denom);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
231 o = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
232 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
233 slice->Weights[list][i][plane][0] = w;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
234 slice->Weights[list][i][plane][1] = o;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
235 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
236 } else {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
237 unsigned plane;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
238 slice->RefPicList[list][i].bPicEntry = 0xff;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
239 for (plane = 0; plane < 3; plane++) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
240 slice->Weights[list][i][plane][0] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
241 slice->Weights[list][i][plane][1] = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
242 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
243 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
244 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
245 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
246 slice->slice_qs_delta = 0; /* XXX not implemented by FFmpeg */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
247 slice->slice_qp_delta = s->qscale - h->pps.init_qp;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
248 slice->redundant_pic_cnt = h->redundant_pic_count;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
249 if (h->slice_type == FF_B_TYPE)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
250 slice->direct_spatial_mv_pred_flag = h->direct_spatial_mv_pred;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
251 slice->cabac_init_idc = h->pps.cabac ? h->cabac_init_idc : 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
252 if (h->deblocking_filter < 2)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
253 slice->disable_deblocking_filter_idc = 1 - h->deblocking_filter;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
254 else
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
255 slice->disable_deblocking_filter_idc = h->deblocking_filter;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
256 slice->slice_id = h->current_slice - 1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
257 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
258
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
259 static int commit_bitstream_and_slice_buffer(AVCodecContext *avctx,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
260 DXVA2_DecodeBufferDesc *bs,
10974
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
261 DXVA2_DecodeBufferDesc *sc)
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
262 {
10988
3824ef98a6b8 Added a few missing consts in dxva_h264.
fenrir
parents: 10980
diff changeset
263 const H264Context *h = avctx->priv_data;
3824ef98a6b8 Added a few missing consts in dxva_h264.
fenrir
parents: 10980
diff changeset
264 const MpegEncContext *s = &h->s;
10974
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
265 const unsigned mb_count = s->mb_width * s->mb_height;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
266 struct dxva_context *ctx = avctx->hwaccel_context;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
267 const Picture *current_picture = h->s.current_picture_ptr;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
268 struct dxva2_picture_context *ctx_pic = current_picture->hwaccel_picture_private;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
269 DXVA_Slice_H264_Short *slice = NULL;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
270 uint8_t *dxva_data, *current, *end;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
271 unsigned dxva_size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
272 void *slice_data;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
273 unsigned slice_size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
274 unsigned padding;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
275 unsigned i;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
276
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
277 /* Create an annex B bitstream buffer with only slice NAL and finalize slice */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
278 if (FAILED(IDirectXVideoDecoder_GetBuffer(ctx->decoder,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
279 DXVA2_BitStreamDateBufferType,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
280 &dxva_data, &dxva_size)))
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
281 return -1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
282 current = dxva_data;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
283 end = dxva_data + dxva_size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
284
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
285 for (i = 0; i < ctx_pic->slice_count; i++) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
286 static const uint8_t start_code[] = { 0, 0, 1 };
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
287 static const unsigned start_code_size = sizeof(start_code);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
288 unsigned position, size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
289
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
290 assert(offsetof(DXVA_Slice_H264_Short, BSNALunitDataLocation) ==
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
291 offsetof(DXVA_Slice_H264_Long, BSNALunitDataLocation));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
292 assert(offsetof(DXVA_Slice_H264_Short, SliceBytesInBuffer) ==
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
293 offsetof(DXVA_Slice_H264_Long, SliceBytesInBuffer));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
294
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
295 if (is_slice_short(ctx))
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
296 slice = &ctx_pic->slice_short[i];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
297 else
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
298 slice = (DXVA_Slice_H264_Short*)&ctx_pic->slice_long[i];
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
299
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
300 position = slice->BSNALunitDataLocation;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
301 size = slice->SliceBytesInBuffer;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
302 if (start_code_size + size > end - current) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
303 av_log(avctx, AV_LOG_ERROR, "Failed to build bitstream");
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
304 break;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
305 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
306
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
307 slice->BSNALunitDataLocation = current - dxva_data;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
308 slice->SliceBytesInBuffer = start_code_size + size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
309
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
310 if (!is_slice_short(ctx)) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
311 DXVA_Slice_H264_Long *slice_long = (DXVA_Slice_H264_Long*)slice;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
312 if (i < ctx_pic->slice_count - 1)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
313 slice_long->NumMbsForSlice =
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
314 slice_long[1].first_mb_in_slice - slice_long[0].first_mb_in_slice;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
315 else
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
316 slice_long->NumMbsForSlice = mb_count - slice_long->first_mb_in_slice;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
317 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
318
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
319 memcpy(current, start_code, start_code_size);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
320 current += start_code_size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
321
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
322 memcpy(current, &ctx_pic->bitstream[position], size);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
323 current += size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
324 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
325 padding = FFMIN(128 - ((current - dxva_data) & 127), end - current);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
326 if (slice && padding > 0) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
327 memset(current, 0, padding);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
328 current += padding;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
329
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
330 slice->SliceBytesInBuffer += padding;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
331 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
332 if (FAILED(IDirectXVideoDecoder_ReleaseBuffer(ctx->decoder,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
333 DXVA2_BitStreamDateBufferType)))
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
334 return -1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
335 if (i < ctx_pic->slice_count)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
336 return -1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
337
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
338 memset(bs, 0, sizeof(*bs));
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
339 bs->CompressedBufferType = DXVA2_BitStreamDateBufferType;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
340 bs->DataSize = current - dxva_data;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
341 bs->NumMBsInBuffer = mb_count;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
342
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
343 if (is_slice_short(ctx)) {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
344 slice_data = ctx_pic->slice_short;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
345 slice_size = ctx_pic->slice_count * sizeof(*ctx_pic->slice_short);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
346 } else {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
347 slice_data = ctx_pic->slice_long;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
348 slice_size = ctx_pic->slice_count * sizeof(*ctx_pic->slice_long);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
349 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
350 assert((bs->DataSize & 127) == 0);
10976
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
351 return ff_dxva2_commit_buffer(avctx, ctx, sc,
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
352 DXVA2_SliceControlBufferType,
b3e3f5cb4b46 Added ff_dxva2_ prefix to get_surface(_index) and commit_buffer functions.
fenrir
parents: 10975
diff changeset
353 slice_data, slice_size, mb_count);
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
354 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
355
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
356
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
357 static int start_frame(AVCodecContext *avctx,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
358 av_unused const uint8_t *buffer,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
359 av_unused uint32_t size)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
360 {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
361 const H264Context *h = avctx->priv_data;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
362 struct dxva_context *ctx = avctx->hwaccel_context;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
363 struct dxva2_picture_context *ctx_pic = h->s.current_picture_ptr->hwaccel_picture_private;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
364
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
365 if (!ctx->decoder || !ctx->cfg || ctx->surface_count <= 0)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
366 return -1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
367 assert(ctx_pic);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
368
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
369 /* Fill up DXVA_PicParams_H264 */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
370 fill_picture_parameters(ctx, h, &ctx_pic->pp);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
371
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
372 /* Fill up DXVA_Qmatrix_H264 */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
373 fill_scaling_lists(h, &ctx_pic->qm);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
374
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
375 ctx_pic->slice_count = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
376 ctx_pic->bitstream_size = 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
377 ctx_pic->bitstream = NULL;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
378 return 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
379 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
380
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
381 static int decode_slice(AVCodecContext *avctx,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
382 const uint8_t *buffer, uint32_t size)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
383 {
10988
3824ef98a6b8 Added a few missing consts in dxva_h264.
fenrir
parents: 10980
diff changeset
384 const H264Context *h = avctx->priv_data;
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
385 struct dxva_context *ctx = avctx->hwaccel_context;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
386 const Picture *current_picture = h->s.current_picture_ptr;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
387 struct dxva2_picture_context *ctx_pic = current_picture->hwaccel_picture_private;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
388 unsigned position;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
389
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
390 if (ctx_pic->slice_count >= MAX_SLICES)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
391 return -1;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
392
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
393 if (!ctx_pic->bitstream)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
394 ctx_pic->bitstream = buffer;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
395 ctx_pic->bitstream_size += size;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
396
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
397 position = buffer - ctx_pic->bitstream;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
398 if (is_slice_short(ctx))
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
399 fill_slice_short(&ctx_pic->slice_short[ctx_pic->slice_count],
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
400 position, size);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
401 else
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
402 fill_slice_long(avctx, &ctx_pic->slice_long[ctx_pic->slice_count],
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
403 position, size);
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
404 ctx_pic->slice_count++;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
405
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
406 if (h->slice_type != FF_I_TYPE && h->slice_type != FF_SI_TYPE)
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
407 ctx_pic->pp.wBitFields &= ~(1 << 15); /* Set IntraPicFlag to 0 */
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
408 return 0;
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
409 }
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
410
10974
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
411 static int end_frame(AVCodecContext *avctx)
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
412 {
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
413 H264Context *h = avctx->priv_data;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
414 MpegEncContext *s = &h->s;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
415 struct dxva2_picture_context *ctx_pic =
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
416 h->s.current_picture_ptr->hwaccel_picture_private;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
417
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
418 if (ctx_pic->slice_count <= 0 || ctx_pic->bitstream_size <= 0)
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
419 return -1;
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
420 return ff_dxva2_common_end_frame(avctx, s,
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
421 &ctx_pic->pp, sizeof(ctx_pic->pp),
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
422 &ctx_pic->qm, sizeof(ctx_pic->qm),
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
423 commit_bitstream_and_slice_buffer);
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
424 }
b1ccfdc1b409 Moved reusable code from dxva2_h264.c:end_frame to ff_dxva2_common_end_frame.
fenrir
parents: 10952
diff changeset
425
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
426 AVHWAccel h264_dxva2_hwaccel = {
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
427 .name = "h264_dxva2",
11560
8a4984c5cacc Define AVMediaType enum, and use it instead of enum CodecType, which
stefano
parents: 11364
diff changeset
428 .type = AVMEDIA_TYPE_VIDEO,
10952
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
429 .id = CODEC_ID_H264,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
430 .pix_fmt = PIX_FMT_DXVA2_VLD,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
431 .capabilities = 0,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
432 .start_frame = start_frame,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
433 .decode_slice = decode_slice,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
434 .end_frame = end_frame,
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
435 .priv_data_size = sizeof(struct dxva2_picture_context),
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
436 };
ea8f891d997d H264 DXVA2 implementation
fenrir
parents:
diff changeset
437