1 /*
2 * Intel MediaSDK QSV encoder utility functions
3 *
4 * copyright (c) 2013 Yukinori Yamazoe
5 * copyright (c) 2015 Anton Khirnov
6 *
7 * This file is part of FFmpeg.
8 *
9 * FFmpeg is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public
11 * License as published by the Free Software Foundation; either
12 * version 2.1 of the License, or (at your option) any later version.
13 *
14 * FFmpeg is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
18 *
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with FFmpeg; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22 */
23
24 #include "config_components.h"
25
26 #include <string.h>
27 #include <sys/types.h>
28 #include <mfx/mfxvideo.h>
29
30 #include "libavutil/common.h"
31 #include "libavutil/hwcontext.h"
32 #include "libavutil/hwcontext_qsv.h"
33 #include "libavutil/mem.h"
34 #include "libavutil/log.h"
35 #include "libavutil/time.h"
36 #include "libavutil/imgutils.h"
37 #include "libavcodec/bytestream.h"
38
39 #include "avcodec.h"
40 #include "internal.h"
41 #include "packet_internal.h"
42 #include "qsv.h"
43 #include "qsv_internal.h"
44 #include "qsvenc.h"
45
46 struct profile_names {
47 mfxU16 profile;
48 const char *name;
49 };
50
51 static const struct profile_names avc_profiles[] = {
52 { MFX_PROFILE_AVC_BASELINE, "avc baseline" },
53 { MFX_PROFILE_AVC_MAIN, "avc main" },
54 { MFX_PROFILE_AVC_EXTENDED, "avc extended" },
55 { MFX_PROFILE_AVC_HIGH, "avc high" },
56 { MFX_PROFILE_AVC_HIGH_422, "avc high 422" },
57 { MFX_PROFILE_AVC_CONSTRAINED_BASELINE, "avc constrained baseline" },
58 { MFX_PROFILE_AVC_CONSTRAINED_HIGH, "avc constrained high" },
59 { MFX_PROFILE_AVC_PROGRESSIVE_HIGH, "avc progressive high" },
60 };
61
62 static const struct profile_names mpeg2_profiles[] = {
63 { MFX_PROFILE_MPEG2_SIMPLE, "mpeg2 simple" },
64 { MFX_PROFILE_MPEG2_MAIN, "mpeg2 main" },
65 { MFX_PROFILE_MPEG2_HIGH, "mpeg2 high" },
66 };
67
68 static const struct profile_names hevc_profiles[] = {
69 { MFX_PROFILE_HEVC_MAIN, "hevc main" },
70 { MFX_PROFILE_HEVC_MAIN10, "hevc main10" },
71 { MFX_PROFILE_HEVC_MAINSP, "hevc mainsp" },
72 { MFX_PROFILE_HEVC_REXT, "hevc rext" },
73 #if QSV_VERSION_ATLEAST(1, 32)
74 { MFX_PROFILE_HEVC_SCC, "hevc scc" },
75 #endif
76 };
77
78 static const struct profile_names vp9_profiles[] = {
79 { MFX_PROFILE_VP9_0, "vp9 0" },
80 { MFX_PROFILE_VP9_1, "vp9 1" },
81 { MFX_PROFILE_VP9_2, "vp9 2" },
82 { MFX_PROFILE_VP9_3, "vp9 3" },
83 };
84
85 typedef struct QSVPacket {
86 AVPacket pkt;
87 mfxSyncPoint *sync;
88 mfxBitstream *bs;
89 } QSVPacket;
90
print_profile(enum AVCodecID codec_id, mfxU16 profile)91 static const char *print_profile(enum AVCodecID codec_id, mfxU16 profile)
92 {
93 const struct profile_names *profiles;
94 int i, num_profiles;
95
96 switch (codec_id) {
97 case AV_CODEC_ID_H264:
98 profiles = avc_profiles;
99 num_profiles = FF_ARRAY_ELEMS(avc_profiles);
100 break;
101
102 case AV_CODEC_ID_MPEG2VIDEO:
103 profiles = mpeg2_profiles;
104 num_profiles = FF_ARRAY_ELEMS(mpeg2_profiles);
105 break;
106
107 case AV_CODEC_ID_HEVC:
108 profiles = hevc_profiles;
109 num_profiles = FF_ARRAY_ELEMS(hevc_profiles);
110 break;
111
112 case AV_CODEC_ID_VP9:
113 profiles = vp9_profiles;
114 num_profiles = FF_ARRAY_ELEMS(vp9_profiles);
115 break;
116
117 default:
118 return "unknown";
119 }
120
121 for (i = 0; i < num_profiles; i++)
122 if (profile == profiles[i].profile)
123 return profiles[i].name;
124
125 return "unknown";
126 }
127
128 static const struct {
129 mfxU16 rc_mode;
130 const char *name;
131 } rc_names[] = {
132 { MFX_RATECONTROL_CBR, "CBR" },
133 { MFX_RATECONTROL_VBR, "VBR" },
134 { MFX_RATECONTROL_CQP, "CQP" },
135 #if QSV_HAVE_AVBR
136 { MFX_RATECONTROL_AVBR, "AVBR" },
137 #endif
138 { MFX_RATECONTROL_LA, "LA" },
139 { MFX_RATECONTROL_ICQ, "ICQ" },
140 { MFX_RATECONTROL_LA_ICQ, "LA_ICQ" },
141 #if QSV_HAVE_VCM
142 { MFX_RATECONTROL_VCM, "VCM" },
143 #endif
144 { MFX_RATECONTROL_LA_EXT, "LA_EXT" },
145 { MFX_RATECONTROL_LA_HRD, "LA_HRD" },
146 { MFX_RATECONTROL_QVBR, "QVBR" },
147 };
148
149 #define UPDATE_PARAM(a, b) \
150 do { \
151 if ((a) != (b)) { \
152 a = b; \
153 updated = 1; \
154 } \
155 } while (0) \
156
print_ratecontrol(mfxU16 rc_mode)157 static const char *print_ratecontrol(mfxU16 rc_mode)
158 {
159 int i;
160 for (i = 0; i < FF_ARRAY_ELEMS(rc_names); i++)
161 if (rc_mode == rc_names[i].rc_mode)
162 return rc_names[i].name;
163 return "unknown";
164 }
165
print_threestate(mfxU16 val)166 static const char *print_threestate(mfxU16 val)
167 {
168 if (val == MFX_CODINGOPTION_ON)
169 return "ON";
170 else if (val == MFX_CODINGOPTION_OFF)
171 return "OFF";
172 return "unknown";
173 }
174
dump_video_param(AVCodecContext *avctx, QSVEncContext *q, mfxExtBuffer **coding_opts)175 static void dump_video_param(AVCodecContext *avctx, QSVEncContext *q,
176 mfxExtBuffer **coding_opts)
177 {
178 mfxInfoMFX *info = &q->param.mfx;
179
180 // co is always at index 1
181 mfxExtCodingOption *co = (mfxExtCodingOption*)coding_opts[1];
182 mfxExtCodingOption2 *co2 = NULL;
183 mfxExtCodingOption3 *co3 = NULL;
184 mfxExtHEVCTiles *exthevctiles = NULL;
185
186 if (q->co2_idx > 0)
187 co2 = (mfxExtCodingOption2*)coding_opts[q->co2_idx];
188
189 if (q->co3_idx > 0)
190 co3 = (mfxExtCodingOption3*)coding_opts[q->co3_idx];
191
192 if (q->exthevctiles_idx > 0)
193 exthevctiles = (mfxExtHEVCTiles *)coding_opts[q->exthevctiles_idx];
194
195 av_log(avctx, AV_LOG_VERBOSE, "profile: %s; level: %"PRIu16"\n",
196 print_profile(avctx->codec_id, info->CodecProfile), info->CodecLevel);
197
198 av_log(avctx, AV_LOG_VERBOSE, "GopPicSize: %"PRIu16"; GopRefDist: %"PRIu16"; GopOptFlag: ",
199 info->GopPicSize, info->GopRefDist);
200 if (info->GopOptFlag & MFX_GOP_CLOSED)
201 av_log(avctx, AV_LOG_VERBOSE, "closed ");
202 if (info->GopOptFlag & MFX_GOP_STRICT)
203 av_log(avctx, AV_LOG_VERBOSE, "strict ");
204 av_log(avctx, AV_LOG_VERBOSE, "; IdrInterval: %"PRIu16"\n", info->IdrInterval);
205
206 av_log(avctx, AV_LOG_VERBOSE, "TargetUsage: %"PRIu16"; RateControlMethod: %s\n",
207 info->TargetUsage, print_ratecontrol(info->RateControlMethod));
208
209 if (info->RateControlMethod == MFX_RATECONTROL_CBR ||
210 info->RateControlMethod == MFX_RATECONTROL_VBR
211 #if QSV_HAVE_VCM
212 || info->RateControlMethod == MFX_RATECONTROL_VCM
213 #endif
214 ) {
215 av_log(avctx, AV_LOG_VERBOSE,
216 "BufferSizeInKB: %"PRIu16"; InitialDelayInKB: %"PRIu16"; TargetKbps: %"PRIu16"; MaxKbps: %"PRIu16"; BRCParamMultiplier: %"PRIu16"\n",
217 info->BufferSizeInKB, info->InitialDelayInKB, info->TargetKbps, info->MaxKbps, info->BRCParamMultiplier);
218 } else if (info->RateControlMethod == MFX_RATECONTROL_CQP) {
219 av_log(avctx, AV_LOG_VERBOSE, "QPI: %"PRIu16"; QPP: %"PRIu16"; QPB: %"PRIu16"\n",
220 info->QPI, info->QPP, info->QPB);
221 }
222 #if QSV_HAVE_AVBR
223 else if (info->RateControlMethod == MFX_RATECONTROL_AVBR) {
224 av_log(avctx, AV_LOG_VERBOSE,
225 "TargetKbps: %"PRIu16"; Accuracy: %"PRIu16"; Convergence: %"PRIu16"; BRCParamMultiplier: %"PRIu16"\n",
226 info->TargetKbps, info->Accuracy, info->Convergence, info->BRCParamMultiplier);
227 }
228 #endif
229 else if (info->RateControlMethod == MFX_RATECONTROL_LA
230 || info->RateControlMethod == MFX_RATECONTROL_LA_HRD
231 ) {
232 av_log(avctx, AV_LOG_VERBOSE,
233 "TargetKbps: %"PRIu16"; BRCParamMultiplier: %"PRIu16"\n",
234 info->TargetKbps, info->BRCParamMultiplier);
235 } else if (info->RateControlMethod == MFX_RATECONTROL_ICQ ||
236 info->RateControlMethod == MFX_RATECONTROL_LA_ICQ)
237 av_log(avctx, AV_LOG_VERBOSE, "ICQQuality: %"PRIu16"\n", info->ICQQuality);
238 av_log(avctx, AV_LOG_VERBOSE, "NumSlice: %"PRIu16"; NumRefFrame: %"PRIu16"\n",
239 info->NumSlice, info->NumRefFrame);
240 av_log(avctx, AV_LOG_VERBOSE, "RateDistortionOpt: %s\n",
241 print_threestate(co->RateDistortionOpt));
242
243 av_log(avctx, AV_LOG_VERBOSE, "RecoveryPointSEI: %s\n", print_threestate(co->RecoveryPointSEI));
244 av_log(avctx, AV_LOG_VERBOSE, "VDENC: %s\n", print_threestate(info->LowPower));
245
246 if (avctx->codec_id == AV_CODEC_ID_H264) {
247 av_log(avctx, AV_LOG_VERBOSE, "Entropy coding: %s; MaxDecFrameBuffering: %"PRIu16"\n",
248 co->CAVLC == MFX_CODINGOPTION_ON ? "CAVLC" : "CABAC", co->MaxDecFrameBuffering);
249 av_log(avctx, AV_LOG_VERBOSE,
250 "NalHrdConformance: %s; SingleSeiNalUnit: %s; VuiVclHrdParameters: %s VuiNalHrdParameters: %s\n",
251 print_threestate(co->NalHrdConformance), print_threestate(co->SingleSeiNalUnit),
252 print_threestate(co->VuiVclHrdParameters), print_threestate(co->VuiNalHrdParameters));
253 } else if ((avctx->codec_id == AV_CODEC_ID_HEVC) && QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 28)) {
254 av_log(avctx, AV_LOG_VERBOSE,
255 "NalHrdConformance: %s; VuiNalHrdParameters: %s\n",
256 print_threestate(co->NalHrdConformance), print_threestate(co->VuiNalHrdParameters));
257 }
258
259 av_log(avctx, AV_LOG_VERBOSE, "FrameRateExtD: %"PRIu32"; FrameRateExtN: %"PRIu32" \n",
260 info->FrameInfo.FrameRateExtD, info->FrameInfo.FrameRateExtN);
261
262 if (co2) {
263 if ((info->RateControlMethod == MFX_RATECONTROL_VBR && q->extbrc && q->look_ahead_depth > 0) ||
264 (info->RateControlMethod == MFX_RATECONTROL_LA) ||
265 (info->RateControlMethod == MFX_RATECONTROL_LA_HRD) ||
266 (info->RateControlMethod == MFX_RATECONTROL_LA_ICQ))
267 av_log(avctx, AV_LOG_VERBOSE, "LookAheadDepth: %"PRIu16"\n", co2->LookAheadDepth);
268
269 av_log(avctx, AV_LOG_VERBOSE, "IntRefType: %"PRIu16"; IntRefCycleSize: %"PRIu16"; IntRefQPDelta: %"PRId16"\n",
270 co2->IntRefType, co2->IntRefCycleSize, co2->IntRefQPDelta);
271
272 av_log(avctx, AV_LOG_VERBOSE, "MaxFrameSize: %d; ", co2->MaxFrameSize);
273 av_log(avctx, AV_LOG_VERBOSE, "MaxSliceSize: %d; ", co2->MaxSliceSize);
274 av_log(avctx, AV_LOG_VERBOSE, "\n");
275
276 av_log(avctx, AV_LOG_VERBOSE,
277 "BitrateLimit: %s; MBBRC: %s; ExtBRC: %s\n",
278 print_threestate(co2->BitrateLimit), print_threestate(co2->MBBRC),
279 print_threestate(co2->ExtBRC));
280
281 av_log(avctx, AV_LOG_VERBOSE, "Trellis: ");
282 if (co2->Trellis & MFX_TRELLIS_OFF) {
283 av_log(avctx, AV_LOG_VERBOSE, "off");
284 } else if (!co2->Trellis) {
285 av_log(avctx, AV_LOG_VERBOSE, "auto");
286 } else {
287 if (co2->Trellis & MFX_TRELLIS_I) av_log(avctx, AV_LOG_VERBOSE, "I");
288 if (co2->Trellis & MFX_TRELLIS_P) av_log(avctx, AV_LOG_VERBOSE, "P");
289 if (co2->Trellis & MFX_TRELLIS_B) av_log(avctx, AV_LOG_VERBOSE, "B");
290 }
291 av_log(avctx, AV_LOG_VERBOSE, "\n");
292
293 av_log(avctx, AV_LOG_VERBOSE,
294 "RepeatPPS: %s; NumMbPerSlice: %"PRIu16"; LookAheadDS: ",
295 print_threestate(co2->RepeatPPS), co2->NumMbPerSlice);
296 switch (co2->LookAheadDS) {
297 case MFX_LOOKAHEAD_DS_OFF: av_log(avctx, AV_LOG_VERBOSE, "off"); break;
298 case MFX_LOOKAHEAD_DS_2x: av_log(avctx, AV_LOG_VERBOSE, "2x"); break;
299 case MFX_LOOKAHEAD_DS_4x: av_log(avctx, AV_LOG_VERBOSE, "4x"); break;
300 default: av_log(avctx, AV_LOG_VERBOSE, "unknown"); break;
301 }
302 av_log(avctx, AV_LOG_VERBOSE, "\n");
303
304 av_log(avctx, AV_LOG_VERBOSE, "AdaptiveI: %s; AdaptiveB: %s; BRefType: ",
305 print_threestate(co2->AdaptiveI), print_threestate(co2->AdaptiveB));
306 switch (co2->BRefType) {
307 case MFX_B_REF_OFF: av_log(avctx, AV_LOG_VERBOSE, "off"); break;
308 case MFX_B_REF_PYRAMID: av_log(avctx, AV_LOG_VERBOSE, "pyramid"); break;
309 default: av_log(avctx, AV_LOG_VERBOSE, "auto"); break;
310 }
311
312 av_log(avctx, AV_LOG_VERBOSE,
313 "MinQPI: %"PRIu8"; MaxQPI: %"PRIu8"; MinQPP: %"PRIu8"; MaxQPP: %"PRIu8"; MinQPB: %"PRIu8"; MaxQPB: %"PRIu8"\n",
314 co2->MinQPI, co2->MaxQPI, co2->MinQPP, co2->MaxQPP, co2->MinQPB, co2->MaxQPB);
315 av_log(avctx, AV_LOG_VERBOSE, "DisableDeblockingIdc: %"PRIu32" \n", co2->DisableDeblockingIdc);
316 }
317
318 if (co3) {
319 if (info->RateControlMethod == MFX_RATECONTROL_QVBR)
320 av_log(avctx, AV_LOG_VERBOSE, "QVBRQuality: %"PRIu16"\n", co3->QVBRQuality);
321
322 av_log(avctx, AV_LOG_VERBOSE, "PRefType: ");
323 switch (co3->PRefType) {
324 case MFX_P_REF_DEFAULT: av_log(avctx, AV_LOG_VERBOSE, "default"); break;
325 case MFX_P_REF_SIMPLE: av_log(avctx, AV_LOG_VERBOSE, "simple"); break;
326 case MFX_P_REF_PYRAMID: av_log(avctx, AV_LOG_VERBOSE, "pyramid"); break;
327 default: av_log(avctx, AV_LOG_VERBOSE, "unknown"); break;
328 }
329 av_log(avctx, AV_LOG_VERBOSE, "\n");
330
331 if (avctx->codec_id == AV_CODEC_ID_HEVC)
332 av_log(avctx, AV_LOG_VERBOSE,"GPB: %s\n", print_threestate(co3->GPB));
333
334 av_log(avctx, AV_LOG_VERBOSE, "TransformSkip: %s \n", print_threestate(co3->TransformSkip));
335 av_log(avctx, AV_LOG_VERBOSE, "IntRefCycleDist: %"PRId16"\n", co3->IntRefCycleDist);
336 av_log(avctx, AV_LOG_VERBOSE, "LowDelayBRC: %s\n", print_threestate(co3->LowDelayBRC));
337 av_log(avctx, AV_LOG_VERBOSE, "MaxFrameSizeI: %d; ", co3->MaxFrameSizeI);
338 av_log(avctx, AV_LOG_VERBOSE, "MaxFrameSizeP: %d\n", co3->MaxFrameSizeP);
339 }
340
341 if (exthevctiles) {
342 av_log(avctx, AV_LOG_VERBOSE, "NumTileColumns: %"PRIu16"; NumTileRows: %"PRIu16"\n",
343 exthevctiles->NumTileColumns, exthevctiles->NumTileRows);
344 }
345 }
346
dump_video_vp9_param(AVCodecContext *avctx, QSVEncContext *q, mfxExtBuffer **coding_opts)347 static void dump_video_vp9_param(AVCodecContext *avctx, QSVEncContext *q,
348 mfxExtBuffer **coding_opts)
349 {
350 mfxInfoMFX *info = &q->param.mfx;
351 mfxExtVP9Param *vp9_param = NULL;
352 mfxExtCodingOption2 *co2 = NULL;
353
354 if (q->vp9_idx >= 0)
355 vp9_param = (mfxExtVP9Param *)coding_opts[q->vp9_idx];
356
357 if (q->co2_idx >= 0)
358 co2 = (mfxExtCodingOption2*)coding_opts[q->co2_idx];
359
360 av_log(avctx, AV_LOG_VERBOSE, "profile: %s \n",
361 print_profile(avctx->codec_id, info->CodecProfile));
362
363 av_log(avctx, AV_LOG_VERBOSE, "GopPicSize: %"PRIu16"; GopRefDist: %"PRIu16"; GopOptFlag: ",
364 info->GopPicSize, info->GopRefDist);
365 if (info->GopOptFlag & MFX_GOP_CLOSED)
366 av_log(avctx, AV_LOG_VERBOSE, "closed ");
367 if (info->GopOptFlag & MFX_GOP_STRICT)
368 av_log(avctx, AV_LOG_VERBOSE, "strict ");
369 av_log(avctx, AV_LOG_VERBOSE, "; IdrInterval: %"PRIu16"\n", info->IdrInterval);
370
371 av_log(avctx, AV_LOG_VERBOSE, "TargetUsage: %"PRIu16"; RateControlMethod: %s\n",
372 info->TargetUsage, print_ratecontrol(info->RateControlMethod));
373
374 if (info->RateControlMethod == MFX_RATECONTROL_CBR ||
375 info->RateControlMethod == MFX_RATECONTROL_VBR) {
376 av_log(avctx, AV_LOG_VERBOSE,
377 "BufferSizeInKB: %"PRIu16"; InitialDelayInKB: %"PRIu16"; TargetKbps: %"PRIu16"; MaxKbps: %"PRIu16"; BRCParamMultiplier: %"PRIu16"\n",
378 info->BufferSizeInKB, info->InitialDelayInKB, info->TargetKbps, info->MaxKbps, info->BRCParamMultiplier);
379 } else if (info->RateControlMethod == MFX_RATECONTROL_CQP) {
380 av_log(avctx, AV_LOG_VERBOSE, "QPI: %"PRIu16"; QPP: %"PRIu16"; QPB: %"PRIu16"\n",
381 info->QPI, info->QPP, info->QPB);
382 }
383 else if (info->RateControlMethod == MFX_RATECONTROL_ICQ) {
384 av_log(avctx, AV_LOG_VERBOSE, "ICQQuality: %"PRIu16"\n", info->ICQQuality);
385 }
386 else {
387 av_log(avctx, AV_LOG_VERBOSE, "Unsupported ratecontrol method: %d \n", info->RateControlMethod);
388 }
389
390 av_log(avctx, AV_LOG_VERBOSE, "NumRefFrame: %"PRIu16"\n", info->NumRefFrame);
391 av_log(avctx, AV_LOG_VERBOSE, "FrameRateExtD: %"PRIu32"; FrameRateExtN: %"PRIu32" \n",
392 info->FrameInfo.FrameRateExtD, info->FrameInfo.FrameRateExtN);
393
394 if (co2) {
395 av_log(avctx, AV_LOG_VERBOSE,
396 "IntRefType: %"PRIu16"; IntRefCycleSize: %"PRIu16"; IntRefQPDelta: %"PRId16"\n",
397 co2->IntRefType, co2->IntRefCycleSize, co2->IntRefQPDelta);
398
399 av_log(avctx, AV_LOG_VERBOSE, "MaxFrameSize: %d; ", co2->MaxFrameSize);
400 av_log(avctx, AV_LOG_VERBOSE, "\n");
401
402 av_log(avctx, AV_LOG_VERBOSE,
403 "BitrateLimit: %s; MBBRC: %s; ExtBRC: %s\n",
404 print_threestate(co2->BitrateLimit), print_threestate(co2->MBBRC),
405 print_threestate(co2->ExtBRC));
406
407 av_log(avctx, AV_LOG_VERBOSE, "VDENC: %s\n", print_threestate(info->LowPower));
408
409 av_log(avctx, AV_LOG_VERBOSE,
410 "MinQPI: %"PRIu8"; MaxQPI: %"PRIu8"; MinQPP: %"PRIu8"; MaxQPP: %"PRIu8"; MinQPB: %"PRIu8"; MaxQPB: %"PRIu8"\n",
411 co2->MinQPI, co2->MaxQPI, co2->MinQPP, co2->MaxQPP, co2->MinQPB, co2->MaxQPB);
412 }
413
414 if (vp9_param) {
415 av_log(avctx, AV_LOG_VERBOSE, "WriteIVFHeaders: %s \n",
416 print_threestate(vp9_param->WriteIVFHeaders));
417 }
418 }
419
dump_video_mjpeg_param(AVCodecContext *avctx, QSVEncContext *q)420 static void dump_video_mjpeg_param(AVCodecContext *avctx, QSVEncContext *q)
421 {
422 mfxInfoMFX *info = &q->param.mfx;
423
424 av_log(avctx, AV_LOG_VERBOSE, "Interleaved: %"PRIu16" \n", info->Interleaved);
425 av_log(avctx, AV_LOG_VERBOSE, "Quality: %"PRIu16" \n", info->Quality);
426 av_log(avctx, AV_LOG_VERBOSE, "RestartInterval: %"PRIu16" \n", info->RestartInterval);
427
428 av_log(avctx, AV_LOG_VERBOSE, "FrameRateExtD: %"PRIu32"; FrameRateExtN: %"PRIu32" \n",
429 info->FrameInfo.FrameRateExtD, info->FrameInfo.FrameRateExtN);
430 }
431
select_rc_mode(AVCodecContext *avctx, QSVEncContext *q)432 static int select_rc_mode(AVCodecContext *avctx, QSVEncContext *q)
433 {
434 const char *rc_desc;
435 mfxU16 rc_mode;
436
437 int want_la = q->look_ahead;
438 int want_qscale = !!(avctx->flags & AV_CODEC_FLAG_QSCALE);
439 int want_vcm = q->vcm;
440
441 if (want_vcm && !QSV_HAVE_VCM) {
442 av_log(avctx, AV_LOG_ERROR,
443 "VCM ratecontrol mode requested, but is not supported by this SDK version\n");
444 return AVERROR(ENOSYS);
445 }
446
447 if (want_la + want_qscale + want_vcm > 1) {
448 av_log(avctx, AV_LOG_ERROR,
449 "More than one of: { constant qscale, lookahead, VCM } requested, "
450 "only one of them can be used at a time.\n");
451 return AVERROR(EINVAL);
452 }
453
454 if (want_qscale) {
455 rc_mode = MFX_RATECONTROL_CQP;
456 rc_desc = "constant quantization parameter (CQP)";
457 }
458 #if QSV_HAVE_VCM
459 else if (want_vcm) {
460 rc_mode = MFX_RATECONTROL_VCM;
461 rc_desc = "video conferencing mode (VCM)";
462 }
463 #endif
464 else if (want_la) {
465 rc_mode = MFX_RATECONTROL_LA;
466 rc_desc = "VBR with lookahead (LA)";
467
468 if (avctx->global_quality > 0) {
469 rc_mode = MFX_RATECONTROL_LA_ICQ;
470 rc_desc = "intelligent constant quality with lookahead (LA_ICQ)";
471 }
472 }
473 else if (avctx->global_quality > 0 && !avctx->rc_max_rate) {
474 rc_mode = MFX_RATECONTROL_ICQ;
475 rc_desc = "intelligent constant quality (ICQ)";
476 }
477 else if (avctx->rc_max_rate == avctx->bit_rate) {
478 rc_mode = MFX_RATECONTROL_CBR;
479 rc_desc = "constant bitrate (CBR)";
480 }
481 #if QSV_HAVE_AVBR
482 else if (!avctx->rc_max_rate) {
483 rc_mode = MFX_RATECONTROL_AVBR;
484 rc_desc = "average variable bitrate (AVBR)";
485 }
486 #endif
487 else if (avctx->global_quality > 0) {
488 rc_mode = MFX_RATECONTROL_QVBR;
489 rc_desc = "constant quality with VBR algorithm (QVBR)";
490 }
491 else {
492 rc_mode = MFX_RATECONTROL_VBR;
493 rc_desc = "variable bitrate (VBR)";
494 }
495
496 q->param.mfx.RateControlMethod = rc_mode;
497 av_log(avctx, AV_LOG_VERBOSE, "Using the %s ratecontrol method\n", rc_desc);
498
499 return 0;
500 }
501
check_enc_param(AVCodecContext *avctx, QSVEncContext *q)502 static int check_enc_param(AVCodecContext *avctx, QSVEncContext *q)
503 {
504 mfxVideoParam param_out = { .mfx.CodecId = q->param.mfx.CodecId };
505 mfxStatus ret;
506
507 #define UNMATCH(x) (param_out.mfx.x != q->param.mfx.x)
508
509 ret = MFXVideoENCODE_Query(q->session, &q->param, ¶m_out);
510
511 if (ret < 0) {
512 if (UNMATCH(CodecId))
513 av_log(avctx, AV_LOG_ERROR, "Current codec type is unsupported\n");
514 if (UNMATCH(CodecProfile))
515 av_log(avctx, AV_LOG_ERROR, "Current profile is unsupported\n");
516 if (UNMATCH(RateControlMethod))
517 av_log(avctx, AV_LOG_ERROR, "Selected ratecontrol mode is unsupported\n");
518 if (UNMATCH(LowPower))
519 av_log(avctx, AV_LOG_ERROR, "Low power mode is unsupported\n");
520 if (UNMATCH(FrameInfo.FrameRateExtN) || UNMATCH(FrameInfo.FrameRateExtD))
521 av_log(avctx, AV_LOG_ERROR, "Current frame rate is unsupported\n");
522 if (UNMATCH(FrameInfo.PicStruct))
523 av_log(avctx, AV_LOG_ERROR, "Current picture structure is unsupported\n");
524 if (UNMATCH(FrameInfo.Width) || UNMATCH(FrameInfo.Height))
525 av_log(avctx, AV_LOG_ERROR, "Current resolution is unsupported\n");
526 if (UNMATCH(FrameInfo.FourCC))
527 av_log(avctx, AV_LOG_ERROR, "Current pixel format is unsupported\n");
528 return 0;
529 }
530 return 1;
531 }
532
init_video_param_jpeg(AVCodecContext *avctx, QSVEncContext *q)533 static int init_video_param_jpeg(AVCodecContext *avctx, QSVEncContext *q)
534 {
535 enum AVPixelFormat sw_format = avctx->pix_fmt == AV_PIX_FMT_QSV ?
536 avctx->sw_pix_fmt : avctx->pix_fmt;
537 const AVPixFmtDescriptor *desc;
538 int ret;
539
540 ret = ff_qsv_codec_id_to_mfx(avctx->codec_id);
541 if (ret < 0)
542 return AVERROR_BUG;
543 q->param.mfx.CodecId = ret;
544
545 if (avctx->level > 0)
546 q->param.mfx.CodecLevel = avctx->level;
547 q->param.mfx.CodecProfile = q->profile;
548
549 desc = av_pix_fmt_desc_get(sw_format);
550 if (!desc)
551 return AVERROR_BUG;
552
553 ret = ff_qsv_map_pixfmt(sw_format, &q->param.mfx.FrameInfo.FourCC);
554 if (ret < 0)
555 return AVERROR_BUG;
556
557 q->param.mfx.FrameInfo.CropX = 0;
558 q->param.mfx.FrameInfo.CropY = 0;
559 q->param.mfx.FrameInfo.CropW = avctx->width;
560 q->param.mfx.FrameInfo.CropH = avctx->height;
561 q->param.mfx.FrameInfo.AspectRatioW = avctx->sample_aspect_ratio.num;
562 q->param.mfx.FrameInfo.AspectRatioH = avctx->sample_aspect_ratio.den;
563 q->param.mfx.FrameInfo.ChromaFormat = MFX_CHROMAFORMAT_YUV420 +
564 !desc->log2_chroma_w + !desc->log2_chroma_h;
565 q->param.mfx.FrameInfo.BitDepthLuma = desc->comp[0].depth;
566 q->param.mfx.FrameInfo.BitDepthChroma = desc->comp[0].depth;
567 q->param.mfx.FrameInfo.Shift = desc->comp[0].depth > 8;
568
569 q->param.mfx.FrameInfo.Width = FFALIGN(avctx->width, 16);
570 q->param.mfx.FrameInfo.Height = FFALIGN(avctx->height, 16);
571
572 if (avctx->hw_frames_ctx) {
573 AVHWFramesContext *frames_ctx = (AVHWFramesContext *)avctx->hw_frames_ctx->data;
574 AVQSVFramesContext *frames_hwctx = frames_ctx->hwctx;
575 q->param.mfx.FrameInfo.Width = frames_hwctx->surfaces[0].Info.Width;
576 q->param.mfx.FrameInfo.Height = frames_hwctx->surfaces[0].Info.Height;
577 }
578
579 if (avctx->framerate.den > 0 && avctx->framerate.num > 0) {
580 q->param.mfx.FrameInfo.FrameRateExtN = avctx->framerate.num;
581 q->param.mfx.FrameInfo.FrameRateExtD = avctx->framerate.den;
582 } else {
583 q->param.mfx.FrameInfo.FrameRateExtN = avctx->time_base.den;
584 q->param.mfx.FrameInfo.FrameRateExtD = avctx->time_base.num;
585 }
586
587 q->param.mfx.Interleaved = 1;
588 q->param.mfx.Quality = av_clip(avctx->global_quality, 1, 100);
589 q->param.mfx.RestartInterval = 0;
590
591 q->width_align = 16;
592 q->height_align = 16;
593
594 q->param.mfx.FrameInfo.Width = FFALIGN(avctx->width, q->width_align);
595 q->param.mfx.FrameInfo.Height = FFALIGN(avctx->height, q->height_align);
596
597 return 0;
598 }
599
init_video_param(AVCodecContext *avctx, QSVEncContext *q)600 static int init_video_param(AVCodecContext *avctx, QSVEncContext *q)
601 {
602 enum AVPixelFormat sw_format = avctx->pix_fmt == AV_PIX_FMT_QSV ?
603 avctx->sw_pix_fmt : avctx->pix_fmt;
604 const AVPixFmtDescriptor *desc;
605 float quant;
606 int target_bitrate_kbps, max_bitrate_kbps, brc_param_multiplier;
607 int buffer_size_in_kilobytes, initial_delay_in_kilobytes;
608 int ret;
609
610 ret = ff_qsv_codec_id_to_mfx(avctx->codec_id);
611 if (ret < 0)
612 return AVERROR_BUG;
613 q->param.mfx.CodecId = ret;
614
615 if (avctx->level > 0)
616 q->param.mfx.CodecLevel = avctx->level;
617
618 if (avctx->compression_level == FF_COMPRESSION_DEFAULT) {
619 avctx->compression_level = q->preset;
620 } else if (avctx->compression_level >= 0) {
621 if (avctx->compression_level > MFX_TARGETUSAGE_BEST_SPEED) {
622 av_log(avctx, AV_LOG_WARNING, "Invalid compression level: "
623 "valid range is 0-%d, using %d instead\n",
624 MFX_TARGETUSAGE_BEST_SPEED, MFX_TARGETUSAGE_BEST_SPEED);
625 avctx->compression_level = MFX_TARGETUSAGE_BEST_SPEED;
626 }
627 }
628
629 if (q->low_power == 1) {
630 q->param.mfx.LowPower = MFX_CODINGOPTION_ON;
631 } else if (q->low_power == -1)
632 q->param.mfx.LowPower = MFX_CODINGOPTION_UNKNOWN;
633 else
634 q->param.mfx.LowPower = MFX_CODINGOPTION_OFF;
635
636 q->param.mfx.CodecProfile = q->profile;
637 q->param.mfx.TargetUsage = avctx->compression_level;
638 q->param.mfx.GopPicSize = FFMAX(0, avctx->gop_size);
639 q->param.mfx.GopRefDist = FFMAX(-1, avctx->max_b_frames) + 1;
640 q->param.mfx.GopOptFlag = avctx->flags & AV_CODEC_FLAG_CLOSED_GOP ?
641 MFX_GOP_CLOSED : MFX_GOP_STRICT;
642 q->param.mfx.IdrInterval = q->idr_interval;
643 q->param.mfx.NumSlice = avctx->slices;
644 q->param.mfx.NumRefFrame = FFMAX(0, avctx->refs);
645 q->param.mfx.EncodedOrder = 0;
646 q->param.mfx.BufferSizeInKB = 0;
647
648 desc = av_pix_fmt_desc_get(sw_format);
649 if (!desc)
650 return AVERROR_BUG;
651
652 ret = ff_qsv_map_pixfmt(sw_format, &q->param.mfx.FrameInfo.FourCC);
653 if (ret < 0)
654 return AVERROR_BUG;
655
656 q->param.mfx.FrameInfo.CropX = 0;
657 q->param.mfx.FrameInfo.CropY = 0;
658 q->param.mfx.FrameInfo.CropW = avctx->width;
659 q->param.mfx.FrameInfo.CropH = avctx->height;
660 q->param.mfx.FrameInfo.AspectRatioW = avctx->sample_aspect_ratio.num;
661 q->param.mfx.FrameInfo.AspectRatioH = avctx->sample_aspect_ratio.den;
662 q->param.mfx.FrameInfo.ChromaFormat = MFX_CHROMAFORMAT_YUV420 +
663 !desc->log2_chroma_w + !desc->log2_chroma_h;
664 q->param.mfx.FrameInfo.BitDepthLuma = desc->comp[0].depth;
665 q->param.mfx.FrameInfo.BitDepthChroma = desc->comp[0].depth;
666 q->param.mfx.FrameInfo.Shift = desc->comp[0].depth > 8;
667
668 // If the minor version is greater than or equal to 19,
669 // then can use the same alignment settings as H.264 for HEVC
670 q->width_align = (avctx->codec_id != AV_CODEC_ID_HEVC ||
671 QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 19)) ? 16 : 32;
672 q->param.mfx.FrameInfo.Width = FFALIGN(avctx->width, q->width_align);
673
674 if (avctx->flags & AV_CODEC_FLAG_INTERLACED_DCT) {
675 // it is important that PicStruct be setup correctly from the
676 // start--otherwise, encoding doesn't work and results in a bunch
677 // of incompatible video parameter errors
678 q->param.mfx.FrameInfo.PicStruct = MFX_PICSTRUCT_FIELD_TFF;
679 // height alignment always must be 32 for interlaced video
680 q->height_align = 32;
681 } else {
682 q->param.mfx.FrameInfo.PicStruct = MFX_PICSTRUCT_PROGRESSIVE;
683 // for progressive video, the height should be aligned to 16 for
684 // H.264. For HEVC, depending on the version of MFX, it should be
685 // either 32 or 16. The lower number is better if possible.
686 q->height_align = avctx->codec_id == AV_CODEC_ID_HEVC ? 32 : 16;
687 }
688 q->param.mfx.FrameInfo.Height = FFALIGN(avctx->height, q->height_align);
689
690 if (avctx->hw_frames_ctx) {
691 AVHWFramesContext *frames_ctx = (AVHWFramesContext*)avctx->hw_frames_ctx->data;
692 AVQSVFramesContext *frames_hwctx = frames_ctx->hwctx;
693 q->param.mfx.FrameInfo.Width = frames_hwctx->surfaces[0].Info.Width;
694 q->param.mfx.FrameInfo.Height = frames_hwctx->surfaces[0].Info.Height;
695 }
696
697 if (avctx->framerate.den > 0 && avctx->framerate.num > 0) {
698 q->param.mfx.FrameInfo.FrameRateExtN = avctx->framerate.num;
699 q->param.mfx.FrameInfo.FrameRateExtD = avctx->framerate.den;
700 } else {
701 q->param.mfx.FrameInfo.FrameRateExtN = avctx->time_base.den;
702 q->param.mfx.FrameInfo.FrameRateExtD = avctx->time_base.num;
703 }
704
705 ret = select_rc_mode(avctx, q);
706 if (ret < 0)
707 return ret;
708
709 //libmfx BRC parameters are 16 bits thus maybe overflow, then BRCParamMultiplier is needed
710 buffer_size_in_kilobytes = avctx->rc_buffer_size / 8000;
711 initial_delay_in_kilobytes = avctx->rc_initial_buffer_occupancy / 8000;
712 target_bitrate_kbps = avctx->bit_rate / 1000;
713 max_bitrate_kbps = avctx->rc_max_rate / 1000;
714 brc_param_multiplier = (FFMAX(FFMAX3(target_bitrate_kbps, max_bitrate_kbps, buffer_size_in_kilobytes),
715 initial_delay_in_kilobytes) + 0x10000) / 0x10000;
716
717 switch (q->param.mfx.RateControlMethod) {
718 case MFX_RATECONTROL_CBR:
719 case MFX_RATECONTROL_VBR:
720 if (q->extbrc) {
721 q->extco2.LookAheadDepth = q->look_ahead_depth;
722 }
723 #if QSV_HAVE_VCM
724 case MFX_RATECONTROL_VCM:
725 #endif
726 case MFX_RATECONTROL_QVBR:
727 q->param.mfx.BufferSizeInKB = buffer_size_in_kilobytes / brc_param_multiplier;
728 q->param.mfx.InitialDelayInKB = initial_delay_in_kilobytes / brc_param_multiplier;
729 q->param.mfx.TargetKbps = target_bitrate_kbps / brc_param_multiplier;
730 q->param.mfx.MaxKbps = max_bitrate_kbps / brc_param_multiplier;
731 q->param.mfx.BRCParamMultiplier = brc_param_multiplier;
732 if (q->param.mfx.RateControlMethod == MFX_RATECONTROL_QVBR)
733 q->extco3.QVBRQuality = av_clip(avctx->global_quality, 0, 51);
734 break;
735 case MFX_RATECONTROL_CQP:
736 quant = avctx->global_quality / FF_QP2LAMBDA;
737
738 q->param.mfx.QPI = av_clip(quant * fabs(avctx->i_quant_factor) + avctx->i_quant_offset, 0, 51);
739 q->param.mfx.QPP = av_clip(quant, 0, 51);
740 q->param.mfx.QPB = av_clip(quant * fabs(avctx->b_quant_factor) + avctx->b_quant_offset, 0, 51);
741
742 break;
743 #if QSV_HAVE_AVBR
744 case MFX_RATECONTROL_AVBR:
745 q->param.mfx.TargetKbps = target_bitrate_kbps / brc_param_multiplier;
746 q->param.mfx.Convergence = q->avbr_convergence;
747 q->param.mfx.Accuracy = q->avbr_accuracy;
748 q->param.mfx.BRCParamMultiplier = brc_param_multiplier;
749 break;
750 #endif
751 case MFX_RATECONTROL_LA:
752 q->param.mfx.TargetKbps = target_bitrate_kbps / brc_param_multiplier;
753 q->extco2.LookAheadDepth = q->look_ahead_depth;
754 q->param.mfx.BRCParamMultiplier = brc_param_multiplier;
755 break;
756 case MFX_RATECONTROL_LA_ICQ:
757 q->extco2.LookAheadDepth = q->look_ahead_depth;
758 case MFX_RATECONTROL_ICQ:
759 q->param.mfx.ICQQuality = av_clip(avctx->global_quality, 1, 51);
760 break;
761 }
762
763 // The HEVC encoder plugin currently fails with some old libmfx version if coding options
764 // are provided. Can't find the extract libmfx version which fixed it, just enable it from
765 // V1.28 in order to keep compatibility security.
766 if (((avctx->codec_id != AV_CODEC_ID_HEVC) || QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 28))
767 && (avctx->codec_id != AV_CODEC_ID_VP9)) {
768 q->extco.Header.BufferId = MFX_EXTBUFF_CODING_OPTION;
769 q->extco.Header.BufferSz = sizeof(q->extco);
770
771 q->extco.PicTimingSEI = q->pic_timing_sei ?
772 MFX_CODINGOPTION_ON : MFX_CODINGOPTION_UNKNOWN;
773
774 if (q->rdo >= 0)
775 q->extco.RateDistortionOpt = q->rdo > 0 ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
776
777 if (avctx->codec_id == AV_CODEC_ID_H264) {
778 q->extco.CAVLC = q->cavlc ? MFX_CODINGOPTION_ON
779 : MFX_CODINGOPTION_UNKNOWN;
780
781 if (avctx->strict_std_compliance != FF_COMPLIANCE_NORMAL)
782 q->extco.NalHrdConformance = avctx->strict_std_compliance > FF_COMPLIANCE_NORMAL ?
783 MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
784
785 if (q->single_sei_nal_unit >= 0)
786 q->extco.SingleSeiNalUnit = q->single_sei_nal_unit ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
787 if (q->recovery_point_sei >= 0)
788 q->extco.RecoveryPointSEI = q->recovery_point_sei ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
789 q->extco.MaxDecFrameBuffering = q->max_dec_frame_buffering;
790 q->extco.AUDelimiter = q->aud ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
791 } else if (avctx->codec_id == AV_CODEC_ID_HEVC) {
792 if (avctx->strict_std_compliance != FF_COMPLIANCE_NORMAL)
793 q->extco.NalHrdConformance = avctx->strict_std_compliance > FF_COMPLIANCE_NORMAL ?
794 MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
795
796 if (q->recovery_point_sei >= 0)
797 q->extco.RecoveryPointSEI = q->recovery_point_sei ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
798
799 q->extco.AUDelimiter = q->aud ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
800 }
801
802 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extco;
803
804 if (avctx->codec_id == AV_CODEC_ID_H264) {
805 if (q->bitrate_limit >= 0)
806 q->extco2.BitrateLimit = q->bitrate_limit ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
807
808 if (avctx->trellis >= 0)
809 q->extco2.Trellis = (avctx->trellis == 0) ? MFX_TRELLIS_OFF : (MFX_TRELLIS_I | MFX_TRELLIS_P | MFX_TRELLIS_B);
810 else
811 q->extco2.Trellis = MFX_TRELLIS_UNKNOWN;
812
813 q->extco2.LookAheadDS = q->look_ahead_downsampling;
814 q->extco2.RepeatPPS = q->repeat_pps ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
815
816 if (q->adaptive_i >= 0)
817 q->extco2.AdaptiveI = q->adaptive_i ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
818 if (q->adaptive_b >= 0)
819 q->extco2.AdaptiveB = q->adaptive_b ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
820 }
821
822 if (avctx->codec_id == AV_CODEC_ID_H264 || avctx->codec_id == AV_CODEC_ID_HEVC) {
823 if (q->extbrc >= 0)
824 q->extco2.ExtBRC = q->extbrc ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
825 if (q->max_frame_size >= 0)
826 q->extco2.MaxFrameSize = q->max_frame_size;
827 if (q->int_ref_type >= 0)
828 q->extco2.IntRefType = q->int_ref_type;
829 if (q->int_ref_cycle_size >= 0)
830 q->extco2.IntRefCycleSize = q->int_ref_cycle_size;
831 if (q->int_ref_qp_delta != INT16_MIN)
832 q->extco2.IntRefQPDelta = q->int_ref_qp_delta;
833 if (q->max_slice_size >= 0)
834 q->extco2.MaxSliceSize = q->max_slice_size;
835 q->extco2.DisableDeblockingIdc = q->dblk_idc;
836
837 if (q->b_strategy >= 0)
838 q->extco2.BRefType = q->b_strategy ? MFX_B_REF_PYRAMID : MFX_B_REF_OFF;
839 if ((avctx->qmin >= 0 && avctx->qmax >= 0 && avctx->qmin > avctx->qmax) ||
840 (q->max_qp_i >= 0 && q->min_qp_i >= 0 && q->min_qp_i > q->max_qp_i) ||
841 (q->max_qp_p >= 0 && q->min_qp_p >= 0 && q->min_qp_p > q->max_qp_p) ||
842 (q->max_qp_b >= 0 && q->min_qp_b >= 0 && q->min_qp_b > q->max_qp_b)) {
843 av_log(avctx, AV_LOG_ERROR,
844 "qmin and or qmax are set but invalid,"
845 " please make sure min <= max\n");
846 return AVERROR(EINVAL);
847 }
848 if (avctx->qmin >= 0) {
849 q->extco2.MinQPI = avctx->qmin > 51 ? 51 : avctx->qmin;
850 q->extco2.MinQPP = q->extco2.MinQPB = q->extco2.MinQPI;
851 }
852 if (avctx->qmax >= 0) {
853 q->extco2.MaxQPI = avctx->qmax > 51 ? 51 : avctx->qmax;
854 q->extco2.MaxQPP = q->extco2.MaxQPB = q->extco2.MaxQPI;
855 }
856 if (q->min_qp_i >= 0)
857 q->extco2.MinQPI = q->min_qp_i > 51 ? 51 : q->min_qp_i;
858 if (q->max_qp_i >= 0)
859 q->extco2.MaxQPI = q->max_qp_i > 51 ? 51 : q->max_qp_i;
860 if (q->min_qp_p >= 0)
861 q->extco2.MinQPP = q->min_qp_p > 51 ? 51 : q->min_qp_p;
862 if (q->max_qp_p >= 0)
863 q->extco2.MaxQPP = q->max_qp_p > 51 ? 51 : q->max_qp_p;
864 if (q->min_qp_b >= 0)
865 q->extco2.MinQPB = q->min_qp_b > 51 ? 51 : q->min_qp_b;
866 if (q->max_qp_b >= 0)
867 q->extco2.MaxQPB = q->max_qp_b > 51 ? 51 : q->max_qp_b;
868 if (q->mbbrc >= 0)
869 q->extco2.MBBRC = q->mbbrc ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
870
871 q->extco2.Header.BufferId = MFX_EXTBUFF_CODING_OPTION2;
872 q->extco2.Header.BufferSz = sizeof(q->extco2);
873
874 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extco2;
875 }
876
877 if (avctx->codec_id == AV_CODEC_ID_H264) {
878 #if QSV_HAVE_MF
879 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 25)) {
880 q->extmfp.Header.BufferId = MFX_EXTBUFF_MULTI_FRAME_PARAM;
881 q->extmfp.Header.BufferSz = sizeof(q->extmfp);
882
883 q->extmfp.MFMode = q->mfmode;
884 av_log(avctx,AV_LOG_VERBOSE,"MFMode:%d\n", q->extmfp.MFMode);
885 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extmfp;
886 }
887 #endif
888 }
889 q->extco3.Header.BufferId = MFX_EXTBUFF_CODING_OPTION3;
890 q->extco3.Header.BufferSz = sizeof(q->extco3);
891
892 if (avctx->codec_id == AV_CODEC_ID_HEVC ||
893 avctx->codec_id == AV_CODEC_ID_H264) {
894 switch (q->p_strategy) {
895 case 0:
896 q->extco3.PRefType = MFX_P_REF_DEFAULT;
897 break;
898 case 1:
899 q->extco3.PRefType = MFX_P_REF_SIMPLE;
900 break;
901 case 2:
902 q->extco3.PRefType = MFX_P_REF_PYRAMID;
903 break;
904 default:
905 q->extco3.PRefType = MFX_P_REF_DEFAULT;
906 av_log(avctx, AV_LOG_WARNING,
907 "invalid p_strategy, set to default\n");
908 break;
909 }
910 if (q->extco3.PRefType == MFX_P_REF_PYRAMID &&
911 avctx->max_b_frames != 0) {
912 av_log(avctx, AV_LOG_WARNING,
913 "Please set max_b_frames(-bf) to 0 to enable P-pyramid\n");
914 }
915 if (q->int_ref_cycle_dist >= 0)
916 q->extco3.IntRefCycleDist = q->int_ref_cycle_dist;
917 if (q->low_delay_brc >= 0)
918 q->extco3.LowDelayBRC = q->low_delay_brc ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
919 if (q->max_frame_size_i >= 0)
920 q->extco3.MaxFrameSizeI = q->max_frame_size_i;
921 if (q->max_frame_size_p >= 0)
922 q->extco3.MaxFrameSizeP = q->max_frame_size_p;
923 }
924
925 if (avctx->codec_id == AV_CODEC_ID_HEVC) {
926 if (q->transform_skip >= 0)
927 q->extco3.TransformSkip = q->transform_skip ? MFX_CODINGOPTION_ON :
928 MFX_CODINGOPTION_OFF;
929 else
930 q->extco3.TransformSkip = MFX_CODINGOPTION_UNKNOWN;
931 q->extco3.GPB = q->gpb ? MFX_CODINGOPTION_ON : MFX_CODINGOPTION_OFF;
932 }
933 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extco3;
934 }
935
936 if (avctx->codec_id == AV_CODEC_ID_VP9) {
937 q->extvp9param.Header.BufferId = MFX_EXTBUFF_VP9_PARAM;
938 q->extvp9param.Header.BufferSz = sizeof(q->extvp9param);
939 q->extvp9param.WriteIVFHeaders = MFX_CODINGOPTION_OFF;
940 #if QSV_HAVE_EXT_VP9_TILES
941 q->extvp9param.NumTileColumns = q->tile_cols;
942 q->extvp9param.NumTileRows = q->tile_rows;
943 #endif
944 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extvp9param;
945 }
946
947 if (avctx->codec_id == AV_CODEC_ID_HEVC) {
948 q->exthevctiles.Header.BufferId = MFX_EXTBUFF_HEVC_TILES;
949 q->exthevctiles.Header.BufferSz = sizeof(q->exthevctiles);
950 q->exthevctiles.NumTileColumns = q->tile_cols;
951 q->exthevctiles.NumTileRows = q->tile_rows;
952 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->exthevctiles;
953 }
954
955 q->extvsi.VideoFullRange = (avctx->color_range == AVCOL_RANGE_JPEG);
956 q->extvsi.ColourDescriptionPresent = 0;
957
958 if (avctx->color_primaries != AVCOL_PRI_UNSPECIFIED ||
959 avctx->color_trc != AVCOL_TRC_UNSPECIFIED ||
960 avctx->colorspace != AVCOL_SPC_UNSPECIFIED) {
961 q->extvsi.ColourDescriptionPresent = 1;
962 q->extvsi.ColourPrimaries = avctx->color_primaries;
963 q->extvsi.TransferCharacteristics = avctx->color_trc;
964 q->extvsi.MatrixCoefficients = avctx->colorspace;
965 }
966
967 if (q->extvsi.VideoFullRange || q->extvsi.ColourDescriptionPresent) {
968 q->extvsi.Header.BufferId = MFX_EXTBUFF_VIDEO_SIGNAL_INFO;
969 q->extvsi.Header.BufferSz = sizeof(q->extvsi);
970 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->extvsi;
971 }
972
973 if (!check_enc_param(avctx,q)) {
974 av_log(avctx, AV_LOG_ERROR,
975 "some encoding parameters are not supported by the QSV "
976 "runtime. Please double check the input parameters.\n");
977 return AVERROR(ENOSYS);
978 }
979
980 return 0;
981 }
982
qsv_retrieve_enc_jpeg_params(AVCodecContext *avctx, QSVEncContext *q)983 static int qsv_retrieve_enc_jpeg_params(AVCodecContext *avctx, QSVEncContext *q)
984 {
985 int ret = 0;
986
987 ret = MFXVideoENCODE_GetVideoParam(q->session, &q->param);
988 if (ret < 0)
989 return ff_qsv_print_error(avctx, ret,
990 "Error calling GetVideoParam");
991
992 q->packet_size = q->param.mfx.BufferSizeInKB * q->param.mfx.BRCParamMultiplier * 1000;
993
994 // for qsv mjpeg the return value maybe 0 so alloc the buffer
995 if (q->packet_size == 0)
996 q->packet_size = q->param.mfx.FrameInfo.Height * q->param.mfx.FrameInfo.Width * 4;
997
998 dump_video_mjpeg_param(avctx, q);
999
1000 return 0;
1001 }
1002
qsv_retrieve_enc_vp9_params(AVCodecContext *avctx, QSVEncContext *q)1003 static int qsv_retrieve_enc_vp9_params(AVCodecContext *avctx, QSVEncContext *q)
1004 {
1005 int ret = 0;
1006 mfxExtVP9Param vp9_extend_buf = {
1007 .Header.BufferId = MFX_EXTBUFF_VP9_PARAM,
1008 .Header.BufferSz = sizeof(vp9_extend_buf),
1009 };
1010
1011 mfxExtCodingOption2 co2 = {
1012 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION2,
1013 .Header.BufferSz = sizeof(co2),
1014 };
1015
1016 mfxExtCodingOption3 co3 = {
1017 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION3,
1018 .Header.BufferSz = sizeof(co3),
1019 };
1020
1021 mfxExtBuffer *ext_buffers[3];
1022 int ext_buf_num = 0;
1023
1024 q->co2_idx = q->co3_idx = q->vp9_idx = -1;
1025
1026 // It is possible the runtime doesn't support the given ext buffer
1027 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 6)) {
1028 q->co2_idx = ext_buf_num;
1029 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&co2;
1030 }
1031
1032 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 11)) {
1033 q->co3_idx = ext_buf_num;
1034 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&co3;
1035 }
1036
1037 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 26)) {
1038 q->vp9_idx = ext_buf_num;
1039 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&vp9_extend_buf;
1040 }
1041
1042 q->param.ExtParam = ext_buffers;
1043 q->param.NumExtParam = ext_buf_num;
1044
1045 ret = MFXVideoENCODE_GetVideoParam(q->session, &q->param);
1046 if (ret < 0)
1047 return ff_qsv_print_error(avctx, ret,
1048 "Error calling GetVideoParam");
1049
1050 q->packet_size = q->param.mfx.BufferSizeInKB * q->param.mfx.BRCParamMultiplier * 1000;
1051
1052 dump_video_vp9_param(avctx, q, ext_buffers);
1053
1054 return 0;
1055 }
1056
qsv_retrieve_enc_params(AVCodecContext *avctx, QSVEncContext *q)1057 static int qsv_retrieve_enc_params(AVCodecContext *avctx, QSVEncContext *q)
1058 {
1059 AVCPBProperties *cpb_props;
1060
1061 uint8_t sps_buf[128];
1062 uint8_t pps_buf[128];
1063
1064 mfxExtCodingOptionSPSPPS extradata = {
1065 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION_SPSPPS,
1066 .Header.BufferSz = sizeof(extradata),
1067 .SPSBuffer = sps_buf, .SPSBufSize = sizeof(sps_buf),
1068 .PPSBuffer = pps_buf, .PPSBufSize = sizeof(pps_buf)
1069 };
1070
1071 mfxExtCodingOption co = {
1072 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION,
1073 .Header.BufferSz = sizeof(co),
1074 };
1075 mfxExtCodingOption2 co2 = {
1076 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION2,
1077 .Header.BufferSz = sizeof(co2),
1078 };
1079 mfxExtCodingOption3 co3 = {
1080 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION3,
1081 .Header.BufferSz = sizeof(co3),
1082 };
1083
1084 uint8_t vps_buf[128];
1085 mfxExtCodingOptionVPS extradata_vps = {
1086 .Header.BufferId = MFX_EXTBUFF_CODING_OPTION_VPS,
1087 .Header.BufferSz = sizeof(extradata_vps),
1088 .VPSBuffer = vps_buf,
1089 .VPSBufSize = sizeof(vps_buf),
1090 };
1091
1092 mfxExtHEVCTiles hevc_tile_buf = {
1093 .Header.BufferId = MFX_EXTBUFF_HEVC_TILES,
1094 .Header.BufferSz = sizeof(hevc_tile_buf),
1095 };
1096
1097 mfxExtBuffer *ext_buffers[6];
1098
1099 int need_pps = avctx->codec_id != AV_CODEC_ID_MPEG2VIDEO;
1100 int ret, ext_buf_num = 0, extradata_offset = 0;
1101
1102 q->co2_idx = q->co3_idx = q->exthevctiles_idx = -1;
1103 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&extradata;
1104 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&co;
1105
1106 // It is possible the runtime doesn't support the given ext buffer
1107 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 6)) {
1108 q->co2_idx = ext_buf_num;
1109 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&co2;
1110 }
1111
1112 if (QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 11)) {
1113 q->co3_idx = ext_buf_num;
1114 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&co3;
1115 }
1116
1117 q->hevc_vps = ((avctx->codec_id == AV_CODEC_ID_HEVC) && QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 17));
1118 if (q->hevc_vps)
1119 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&extradata_vps;
1120 if (avctx->codec_id == AV_CODEC_ID_HEVC && QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 13)) {
1121 q->exthevctiles_idx = ext_buf_num;
1122 ext_buffers[ext_buf_num++] = (mfxExtBuffer*)&hevc_tile_buf;
1123 }
1124
1125 q->param.ExtParam = ext_buffers;
1126 q->param.NumExtParam = ext_buf_num;
1127
1128 ret = MFXVideoENCODE_GetVideoParam(q->session, &q->param);
1129 if (ret < 0)
1130 return ff_qsv_print_error(avctx, ret,
1131 "Error calling GetVideoParam");
1132
1133 q->packet_size = q->param.mfx.BufferSizeInKB * q->param.mfx.BRCParamMultiplier * 1000;
1134
1135 if (!extradata.SPSBufSize || (need_pps && !extradata.PPSBufSize)
1136 || (q->hevc_vps && !extradata_vps.VPSBufSize)
1137 ) {
1138 av_log(avctx, AV_LOG_ERROR, "No extradata returned from libmfx.\n");
1139 return AVERROR_UNKNOWN;
1140 }
1141
1142 avctx->extradata_size = extradata.SPSBufSize + need_pps * extradata.PPSBufSize;
1143 avctx->extradata_size += q->hevc_vps * extradata_vps.VPSBufSize;
1144
1145 avctx->extradata = av_malloc(avctx->extradata_size + AV_INPUT_BUFFER_PADDING_SIZE);
1146 if (!avctx->extradata)
1147 return AVERROR(ENOMEM);
1148
1149 if (q->hevc_vps) {
1150 memcpy(avctx->extradata, vps_buf, extradata_vps.VPSBufSize);
1151 extradata_offset += extradata_vps.VPSBufSize;
1152 }
1153
1154 memcpy(avctx->extradata + extradata_offset, sps_buf, extradata.SPSBufSize);
1155 extradata_offset += extradata.SPSBufSize;
1156 if (need_pps) {
1157 memcpy(avctx->extradata + extradata_offset, pps_buf, extradata.PPSBufSize);
1158 extradata_offset += extradata.PPSBufSize;
1159 }
1160 memset(avctx->extradata + avctx->extradata_size, 0, AV_INPUT_BUFFER_PADDING_SIZE);
1161
1162 cpb_props = ff_add_cpb_side_data(avctx);
1163 if (!cpb_props)
1164 return AVERROR(ENOMEM);
1165 cpb_props->max_bitrate = avctx->rc_max_rate;
1166 cpb_props->min_bitrate = avctx->rc_min_rate;
1167 cpb_props->avg_bitrate = avctx->bit_rate;
1168 cpb_props->buffer_size = avctx->rc_buffer_size;
1169
1170 dump_video_param(avctx, q, ext_buffers);
1171
1172 return 0;
1173 }
1174
qsv_init_opaque_alloc(AVCodecContext *avctx, QSVEncContext *q)1175 static int qsv_init_opaque_alloc(AVCodecContext *avctx, QSVEncContext *q)
1176 {
1177 AVQSVContext *qsv = avctx->hwaccel_context;
1178 mfxFrameSurface1 *surfaces;
1179 int nb_surfaces, i;
1180
1181 nb_surfaces = qsv->nb_opaque_surfaces + q->req.NumFrameSuggested;
1182
1183 q->opaque_alloc_buf = av_buffer_allocz(sizeof(*surfaces) * nb_surfaces);
1184 if (!q->opaque_alloc_buf)
1185 return AVERROR(ENOMEM);
1186
1187 q->opaque_surfaces = av_malloc_array(nb_surfaces, sizeof(*q->opaque_surfaces));
1188 if (!q->opaque_surfaces)
1189 return AVERROR(ENOMEM);
1190
1191 surfaces = (mfxFrameSurface1*)q->opaque_alloc_buf->data;
1192 for (i = 0; i < nb_surfaces; i++) {
1193 surfaces[i].Info = q->req.Info;
1194 q->opaque_surfaces[i] = surfaces + i;
1195 }
1196
1197 q->opaque_alloc.Header.BufferId = MFX_EXTBUFF_OPAQUE_SURFACE_ALLOCATION;
1198 q->opaque_alloc.Header.BufferSz = sizeof(q->opaque_alloc);
1199 q->opaque_alloc.In.Surfaces = q->opaque_surfaces;
1200 q->opaque_alloc.In.NumSurface = nb_surfaces;
1201 q->opaque_alloc.In.Type = q->req.Type;
1202
1203 q->extparam_internal[q->nb_extparam_internal++] = (mfxExtBuffer *)&q->opaque_alloc;
1204
1205 qsv->nb_opaque_surfaces = nb_surfaces;
1206 qsv->opaque_surfaces = q->opaque_alloc_buf;
1207 qsv->opaque_alloc_type = q->req.Type;
1208
1209 return 0;
1210 }
1211
qsvenc_init_session(AVCodecContext *avctx, QSVEncContext *q)1212 static int qsvenc_init_session(AVCodecContext *avctx, QSVEncContext *q)
1213 {
1214 int ret;
1215
1216 if (avctx->hwaccel_context) {
1217 AVQSVContext *qsv = avctx->hwaccel_context;
1218 q->session = qsv->session;
1219 } else if (avctx->hw_frames_ctx) {
1220 q->frames_ctx.hw_frames_ctx = av_buffer_ref(avctx->hw_frames_ctx);
1221 if (!q->frames_ctx.hw_frames_ctx)
1222 return AVERROR(ENOMEM);
1223
1224 ret = ff_qsv_init_session_frames(avctx, &q->internal_qs.session,
1225 &q->frames_ctx, q->load_plugins,
1226 q->param.IOPattern == MFX_IOPATTERN_IN_OPAQUE_MEMORY,
1227 MFX_GPUCOPY_OFF);
1228 if (ret < 0) {
1229 av_buffer_unref(&q->frames_ctx.hw_frames_ctx);
1230 return ret;
1231 }
1232
1233 q->session = q->internal_qs.session;
1234 } else if (avctx->hw_device_ctx) {
1235 ret = ff_qsv_init_session_device(avctx, &q->internal_qs.session,
1236 avctx->hw_device_ctx, q->load_plugins,
1237 MFX_GPUCOPY_OFF);
1238 if (ret < 0)
1239 return ret;
1240
1241 q->session = q->internal_qs.session;
1242 } else {
1243 ret = ff_qsv_init_internal_session(avctx, &q->internal_qs,
1244 q->load_plugins, MFX_GPUCOPY_OFF);
1245 if (ret < 0)
1246 return ret;
1247
1248 q->session = q->internal_qs.session;
1249 }
1250
1251 return 0;
1252 }
1253
ff_qsv_enc_init(AVCodecContext *avctx, QSVEncContext *q)1254 int ff_qsv_enc_init(AVCodecContext *avctx, QSVEncContext *q)
1255 {
1256 int iopattern = 0;
1257 int opaque_alloc = 0;
1258 int ret;
1259
1260 q->param.AsyncDepth = q->async_depth;
1261
1262 q->async_fifo = av_fifo_alloc2(q->async_depth, sizeof(QSVPacket), 0);
1263 if (!q->async_fifo)
1264 return AVERROR(ENOMEM);
1265
1266 if (avctx->hwaccel_context) {
1267 AVQSVContext *qsv = avctx->hwaccel_context;
1268
1269 iopattern = qsv->iopattern;
1270 opaque_alloc = qsv->opaque_alloc;
1271 }
1272
1273 if (avctx->hw_frames_ctx) {
1274 AVHWFramesContext *frames_ctx = (AVHWFramesContext*)avctx->hw_frames_ctx->data;
1275 AVQSVFramesContext *frames_hwctx = frames_ctx->hwctx;
1276
1277 if (!iopattern) {
1278 if (frames_hwctx->frame_type & MFX_MEMTYPE_OPAQUE_FRAME)
1279 iopattern = MFX_IOPATTERN_IN_OPAQUE_MEMORY;
1280 else if (frames_hwctx->frame_type &
1281 (MFX_MEMTYPE_VIDEO_MEMORY_DECODER_TARGET | MFX_MEMTYPE_VIDEO_MEMORY_PROCESSOR_TARGET))
1282 iopattern = MFX_IOPATTERN_IN_VIDEO_MEMORY;
1283 }
1284 }
1285
1286 if (!iopattern)
1287 iopattern = MFX_IOPATTERN_IN_SYSTEM_MEMORY;
1288 q->param.IOPattern = iopattern;
1289 ff_qsv_print_iopattern(avctx, iopattern, "Encoder");
1290
1291 ret = qsvenc_init_session(avctx, q);
1292 if (ret < 0)
1293 return ret;
1294
1295 ret = MFXQueryVersion(q->session,&q->ver);
1296 if (ret < 0) {
1297 return ff_qsv_print_error(avctx, ret,
1298 "Error querying mfx version");
1299 }
1300
1301 // in the mfxInfoMFX struct, JPEG is different from other codecs
1302 switch (avctx->codec_id) {
1303 case AV_CODEC_ID_MJPEG:
1304 ret = init_video_param_jpeg(avctx, q);
1305 break;
1306 default:
1307 ret = init_video_param(avctx, q);
1308 break;
1309 }
1310 if (ret < 0)
1311 return ret;
1312
1313 if (avctx->hwaccel_context) {
1314 AVQSVContext *qsv = avctx->hwaccel_context;
1315 int i, j;
1316
1317 q->extparam = av_calloc(qsv->nb_ext_buffers + q->nb_extparam_internal,
1318 sizeof(*q->extparam));
1319 if (!q->extparam)
1320 return AVERROR(ENOMEM);
1321
1322 q->param.ExtParam = q->extparam;
1323 for (i = 0; i < qsv->nb_ext_buffers; i++)
1324 q->param.ExtParam[i] = qsv->ext_buffers[i];
1325 q->param.NumExtParam = qsv->nb_ext_buffers;
1326
1327 for (i = 0; i < q->nb_extparam_internal; i++) {
1328 for (j = 0; j < qsv->nb_ext_buffers; j++) {
1329 if (qsv->ext_buffers[j]->BufferId == q->extparam_internal[i]->BufferId)
1330 break;
1331 }
1332 if (j < qsv->nb_ext_buffers)
1333 continue;
1334
1335 q->param.ExtParam[q->param.NumExtParam++] = q->extparam_internal[i];
1336 }
1337 } else {
1338 q->param.ExtParam = q->extparam_internal;
1339 q->param.NumExtParam = q->nb_extparam_internal;
1340 }
1341
1342 ret = MFXVideoENCODE_Query(q->session, &q->param, &q->param);
1343 if (ret == MFX_WRN_PARTIAL_ACCELERATION) {
1344 av_log(avctx, AV_LOG_WARNING, "Encoder will work with partial HW acceleration\n");
1345 } else if (ret < 0) {
1346 return ff_qsv_print_error(avctx, ret,
1347 "Error querying encoder params");
1348 }
1349
1350 ret = MFXVideoENCODE_QueryIOSurf(q->session, &q->param, &q->req);
1351 if (ret < 0)
1352 return ff_qsv_print_error(avctx, ret,
1353 "Error querying (IOSurf) the encoding parameters");
1354
1355 if (opaque_alloc) {
1356 ret = qsv_init_opaque_alloc(avctx, q);
1357 if (ret < 0)
1358 return ret;
1359 }
1360
1361 ret = MFXVideoENCODE_Init(q->session, &q->param);
1362 if (ret < 0)
1363 return ff_qsv_print_error(avctx, ret,
1364 "Error initializing the encoder");
1365 else if (ret > 0)
1366 ff_qsv_print_warning(avctx, ret,
1367 "Warning in encoder initialization");
1368
1369 switch (avctx->codec_id) {
1370 case AV_CODEC_ID_MJPEG:
1371 ret = qsv_retrieve_enc_jpeg_params(avctx, q);
1372 break;
1373 case AV_CODEC_ID_VP9:
1374 ret = qsv_retrieve_enc_vp9_params(avctx, q);
1375 break;
1376 default:
1377 ret = qsv_retrieve_enc_params(avctx, q);
1378 break;
1379 }
1380 if (ret < 0) {
1381 av_log(avctx, AV_LOG_ERROR, "Error retrieving encoding parameters.\n");
1382 return ret;
1383 }
1384
1385 q->avctx = avctx;
1386
1387 return 0;
1388 }
1389
free_encoder_ctrl_payloads(mfxEncodeCtrl* enc_ctrl)1390 static void free_encoder_ctrl_payloads(mfxEncodeCtrl* enc_ctrl)
1391 {
1392 if (enc_ctrl) {
1393 int i;
1394 for (i = 0; i < enc_ctrl->NumPayload && i < QSV_MAX_ENC_PAYLOAD; i++) {
1395 av_freep(&enc_ctrl->Payload[i]);
1396 }
1397 enc_ctrl->NumPayload = 0;
1398 }
1399 }
1400
free_encoder_ctrl_extparam(mfxEncodeCtrl* enc_ctrl)1401 static void free_encoder_ctrl_extparam(mfxEncodeCtrl* enc_ctrl)
1402 {
1403 if (enc_ctrl) {
1404 int i;
1405 for (i = 0; i < enc_ctrl->NumExtParam && i < QSV_MAX_ENC_EXTPARAM; i++) {
1406 if (enc_ctrl->ExtParam[i])
1407 av_freep(&(enc_ctrl->ExtParam[i]));
1408 }
1409 enc_ctrl->NumExtParam = 0;
1410 }
1411 }
1412
clear_unused_frames(QSVEncContext *q)1413 static void clear_unused_frames(QSVEncContext *q)
1414 {
1415 QSVFrame *cur = q->work_frames;
1416 while (cur) {
1417 if (cur->used && !cur->surface.Data.Locked) {
1418 free_encoder_ctrl_payloads(&cur->enc_ctrl);
1419 free_encoder_ctrl_extparam(&cur->enc_ctrl);
1420 //do not reuse enc_ctrl from previous frame
1421 memset(&cur->enc_ctrl, 0, sizeof(cur->enc_ctrl));
1422 cur->enc_ctrl.Payload = cur->payloads;
1423 cur->enc_ctrl.ExtParam = cur->extparam;
1424 if (cur->frame->format == AV_PIX_FMT_QSV) {
1425 av_frame_unref(cur->frame);
1426 }
1427 cur->used = 0;
1428 }
1429 cur = cur->next;
1430 }
1431 }
1432
get_free_frame(QSVEncContext *q, QSVFrame **f)1433 static int get_free_frame(QSVEncContext *q, QSVFrame **f)
1434 {
1435 QSVFrame *frame, **last;
1436
1437 clear_unused_frames(q);
1438
1439 frame = q->work_frames;
1440 last = &q->work_frames;
1441 while (frame) {
1442 if (!frame->used) {
1443 *f = frame;
1444 frame->used = 1;
1445 return 0;
1446 }
1447
1448 last = &frame->next;
1449 frame = frame->next;
1450 }
1451
1452 frame = av_mallocz(sizeof(*frame));
1453 if (!frame)
1454 return AVERROR(ENOMEM);
1455 frame->frame = av_frame_alloc();
1456 if (!frame->frame) {
1457 av_freep(&frame);
1458 return AVERROR(ENOMEM);
1459 }
1460 frame->enc_ctrl.Payload = frame->payloads;
1461 frame->enc_ctrl.ExtParam = frame->extparam;
1462 *last = frame;
1463
1464 *f = frame;
1465 frame->used = 1;
1466
1467 return 0;
1468 }
1469
submit_frame(QSVEncContext *q, const AVFrame *frame, QSVFrame **new_frame)1470 static int submit_frame(QSVEncContext *q, const AVFrame *frame,
1471 QSVFrame **new_frame)
1472 {
1473 QSVFrame *qf;
1474 int ret;
1475
1476 ret = get_free_frame(q, &qf);
1477 if (ret < 0)
1478 return ret;
1479
1480 if (frame->format == AV_PIX_FMT_QSV) {
1481 ret = av_frame_ref(qf->frame, frame);
1482 if (ret < 0)
1483 return ret;
1484
1485 qf->surface = *(mfxFrameSurface1*)qf->frame->data[3];
1486
1487 if (q->frames_ctx.mids) {
1488 ret = ff_qsv_find_surface_idx(&q->frames_ctx, qf);
1489 if (ret < 0)
1490 return ret;
1491
1492 qf->surface.Data.MemId = &q->frames_ctx.mids[ret];
1493 }
1494 } else {
1495 /* make a copy if the input is not padded as libmfx requires */
1496 /* and to make allocation continious for data[0]/data[1] */
1497 if ((frame->height & 31 || frame->linesize[0] & (q->width_align - 1)) ||
1498 (frame->data[1] - frame->data[0] != frame->linesize[0] * FFALIGN(qf->frame->height, q->height_align))) {
1499 qf->frame->height = FFALIGN(frame->height, q->height_align);
1500 qf->frame->width = FFALIGN(frame->width, q->width_align);
1501
1502 qf->frame->format = frame->format;
1503
1504 if (!qf->frame->data[0]) {
1505 ret = av_frame_get_buffer(qf->frame, q->width_align);
1506 if (ret < 0)
1507 return ret;
1508 }
1509
1510 qf->frame->height = frame->height;
1511 qf->frame->width = frame->width;
1512
1513 ret = av_frame_copy(qf->frame, frame);
1514 if (ret < 0) {
1515 av_frame_unref(qf->frame);
1516 return ret;
1517 }
1518 } else {
1519 av_frame_unref(qf->frame);
1520 ret = av_frame_ref(qf->frame, frame);
1521 if (ret < 0)
1522 return ret;
1523 }
1524
1525 qf->surface.Info = q->param.mfx.FrameInfo;
1526
1527 qf->surface.Info.PicStruct =
1528 !frame->interlaced_frame ? MFX_PICSTRUCT_PROGRESSIVE :
1529 frame->top_field_first ? MFX_PICSTRUCT_FIELD_TFF :
1530 MFX_PICSTRUCT_FIELD_BFF;
1531 if (frame->repeat_pict == 1)
1532 qf->surface.Info.PicStruct |= MFX_PICSTRUCT_FIELD_REPEATED;
1533 else if (frame->repeat_pict == 2)
1534 qf->surface.Info.PicStruct |= MFX_PICSTRUCT_FRAME_DOUBLING;
1535 else if (frame->repeat_pict == 4)
1536 qf->surface.Info.PicStruct |= MFX_PICSTRUCT_FRAME_TRIPLING;
1537
1538 ret = ff_qsv_map_frame_to_surface(qf->frame, &qf->surface);
1539 if (ret < 0) {
1540 av_log(q->avctx, AV_LOG_ERROR, "map frame to surface failed.\n");
1541 return ret;
1542 }
1543 }
1544 qf->surface.Data.TimeStamp = av_rescale_q(frame->pts, q->avctx->time_base, (AVRational){1, 90000});
1545
1546 *new_frame = qf;
1547
1548 return 0;
1549 }
1550
print_interlace_msg(AVCodecContext *avctx, QSVEncContext *q)1551 static void print_interlace_msg(AVCodecContext *avctx, QSVEncContext *q)
1552 {
1553 if (q->param.mfx.CodecId == MFX_CODEC_AVC) {
1554 if (q->param.mfx.CodecProfile == MFX_PROFILE_AVC_BASELINE ||
1555 q->param.mfx.CodecLevel < MFX_LEVEL_AVC_21 ||
1556 q->param.mfx.CodecLevel > MFX_LEVEL_AVC_41)
1557 av_log(avctx, AV_LOG_WARNING,
1558 "Interlaced coding is supported"
1559 " at Main/High Profile Level 2.2-4.0\n");
1560 }
1561 }
1562
set_roi_encode_ctrl(AVCodecContext *avctx, const AVFrame *frame, mfxEncodeCtrl *enc_ctrl)1563 static int set_roi_encode_ctrl(AVCodecContext *avctx, const AVFrame *frame,
1564 mfxEncodeCtrl *enc_ctrl)
1565 {
1566 AVFrameSideData *sd = NULL;
1567 int mb_size;
1568
1569 if (avctx->codec_id == AV_CODEC_ID_H264)
1570 mb_size = 16;
1571 else if (avctx->codec_id == AV_CODEC_ID_H265)
1572 mb_size = 32;
1573 else
1574 return 0;
1575
1576 if (frame)
1577 sd = av_frame_get_side_data(frame, AV_FRAME_DATA_REGIONS_OF_INTEREST);
1578
1579 if (sd) {
1580 mfxExtEncoderROI *enc_roi = NULL;
1581 AVRegionOfInterest *roi;
1582 uint32_t roi_size;
1583 int nb_roi, i;
1584
1585 roi = (AVRegionOfInterest *)sd->data;
1586 roi_size = roi->self_size;
1587 if (!roi_size || sd->size % roi_size) {
1588 av_log(avctx, AV_LOG_ERROR, "Invalid ROI Data.\n");
1589 return AVERROR(EINVAL);
1590 }
1591 nb_roi = sd->size / roi_size;
1592 if (nb_roi > QSV_MAX_ROI_NUM) {
1593 av_log(avctx, AV_LOG_WARNING, "More ROIs set than "
1594 "supported by driver (%d > %d).\n",
1595 nb_roi, QSV_MAX_ROI_NUM);
1596 nb_roi = QSV_MAX_ROI_NUM;
1597 }
1598
1599 enc_roi = av_mallocz(sizeof(*enc_roi));
1600 if (!enc_roi)
1601 return AVERROR(ENOMEM);
1602 enc_roi->Header.BufferId = MFX_EXTBUFF_ENCODER_ROI;
1603 enc_roi->Header.BufferSz = sizeof(*enc_roi);
1604 enc_roi->NumROI = nb_roi;
1605 enc_roi->ROIMode = MFX_ROI_MODE_QP_DELTA;
1606 for (i = 0; i < nb_roi; i++) {
1607 roi = (AVRegionOfInterest *)(sd->data + roi_size * i);
1608 enc_roi->ROI[i].Top = FFALIGN(roi->top, mb_size);
1609 enc_roi->ROI[i].Bottom = FFALIGN(roi->bottom, mb_size);
1610 enc_roi->ROI[i].Left = FFALIGN(roi->left, mb_size);
1611 enc_roi->ROI[i].Right = FFALIGN(roi->right, mb_size);
1612 enc_roi->ROI[i].DeltaQP =
1613 roi->qoffset.num * 51 / roi->qoffset.den;
1614 av_log(avctx, AV_LOG_DEBUG, "ROI: (%d,%d)-(%d,%d) -> %+d.\n",
1615 roi->top, roi->left, roi->bottom, roi->right,
1616 enc_roi->ROI[i].DeltaQP);
1617 }
1618 enc_ctrl->ExtParam[enc_ctrl->NumExtParam] = (mfxExtBuffer *)enc_roi;
1619 enc_ctrl->NumExtParam++;
1620 }
1621 return 0;
1622 }
1623
update_qp(AVCodecContext *avctx, QSVEncContext *q, const AVFrame *frame)1624 static int update_qp(AVCodecContext *avctx, QSVEncContext *q,
1625 const AVFrame *frame)
1626 {
1627 int updated = 0, qp = 0, new_qp;
1628 char *tail;
1629 AVDictionaryEntry *entry = NULL;
1630
1631 if (avctx->codec_id != AV_CODEC_ID_H264 && avctx->codec_id != AV_CODEC_ID_HEVC)
1632 return 0;
1633
1634 entry = av_dict_get(frame->metadata, "qsv_config_qp", NULL, 0);
1635 if (entry && q->param.mfx.RateControlMethod == MFX_RATECONTROL_CQP) {
1636 qp = strtol(entry->value, &tail, 10);
1637 if (*tail) {
1638 av_log(avctx, AV_LOG_WARNING, "Invalid qsv_config_qp string. Ignore this metadata\n");
1639 return 0;
1640 }
1641 if (qp < 0 || qp > 51) {
1642 av_log(avctx, AV_LOG_WARNING, "Invalid qp, clip to 0 ~ 51\n");
1643 qp = av_clip(qp, 0, 51);
1644 }
1645 av_log(avctx, AV_LOG_DEBUG, "Configure qp: %d\n",qp);
1646 UPDATE_PARAM(q->param.mfx.QPP, qp);
1647 new_qp = av_clip(qp * fabs(avctx->i_quant_factor) +
1648 avctx->i_quant_offset, 0, 51);
1649 UPDATE_PARAM(q->param.mfx.QPI, new_qp);
1650 new_qp = av_clip(qp * fabs(avctx->b_quant_factor) +
1651 avctx->b_quant_offset, 0, 51);
1652 UPDATE_PARAM(q->param.mfx.QPB, new_qp);
1653 av_log(avctx, AV_LOG_DEBUG,
1654 "using fixed qp = %d/%d/%d for idr/p/b frames\n",
1655 q->param.mfx.QPI, q->param.mfx.QPP, q->param.mfx.QPB);
1656 }
1657 return updated;
1658 }
1659
update_parameters(AVCodecContext *avctx, QSVEncContext *q, const AVFrame *frame)1660 static int update_parameters(AVCodecContext *avctx, QSVEncContext *q,
1661 const AVFrame *frame)
1662 {
1663 int needReset = 0, ret = 0;
1664
1665 if (!frame)
1666 return 0;
1667
1668 needReset = update_qp(avctx, q, frame);
1669 if (!needReset)
1670 return 0;
1671
1672 if (avctx->hwaccel_context) {
1673 AVQSVContext *qsv = avctx->hwaccel_context;
1674 int i, j;
1675 q->param.ExtParam = q->extparam;
1676 for (i = 0; i < qsv->nb_ext_buffers; i++)
1677 q->param.ExtParam[i] = qsv->ext_buffers[i];
1678 q->param.NumExtParam = qsv->nb_ext_buffers;
1679
1680 for (i = 0; i < q->nb_extparam_internal; i++) {
1681 for (j = 0; j < qsv->nb_ext_buffers; j++) {
1682 if (qsv->ext_buffers[j]->BufferId == q->extparam_internal[i]->BufferId)
1683 break;
1684 }
1685 if (j < qsv->nb_ext_buffers)
1686 continue;
1687 q->param.ExtParam[q->param.NumExtParam++] = q->extparam_internal[i];
1688 }
1689 } else {
1690 q->param.ExtParam = q->extparam_internal;
1691 q->param.NumExtParam = q->nb_extparam_internal;
1692 }
1693 av_log(avctx, AV_LOG_DEBUG, "Parameter change, call msdk reset.\n");
1694 ret = MFXVideoENCODE_Reset(q->session, &q->param);
1695 if (ret < 0)
1696 return ff_qsv_print_error(avctx, ret, "Error during resetting");
1697
1698 return 0;
1699 }
1700
encode_frame(AVCodecContext *avctx, QSVEncContext *q, const AVFrame *frame)1701 static int encode_frame(AVCodecContext *avctx, QSVEncContext *q,
1702 const AVFrame *frame)
1703 {
1704 QSVPacket pkt = { { 0 } };
1705 mfxExtAVCEncodedFrameInfo *enc_info = NULL;
1706 mfxExtBuffer **enc_buf = NULL;
1707
1708 mfxFrameSurface1 *surf = NULL;
1709 QSVFrame *qsv_frame = NULL;
1710 mfxEncodeCtrl* enc_ctrl = NULL;
1711 int ret;
1712
1713 if (frame) {
1714 ret = submit_frame(q, frame, &qsv_frame);
1715 if (ret < 0) {
1716 av_log(avctx, AV_LOG_ERROR, "Error submitting the frame for encoding.\n");
1717 return ret;
1718 }
1719 }
1720 if (qsv_frame) {
1721 surf = &qsv_frame->surface;
1722 enc_ctrl = &qsv_frame->enc_ctrl;
1723
1724 if (frame->pict_type == AV_PICTURE_TYPE_I) {
1725 enc_ctrl->FrameType = MFX_FRAMETYPE_I | MFX_FRAMETYPE_REF;
1726 if (q->forced_idr)
1727 enc_ctrl->FrameType |= MFX_FRAMETYPE_IDR;
1728 }
1729 }
1730
1731 ret = av_new_packet(&pkt.pkt, q->packet_size);
1732 if (ret < 0) {
1733 av_log(avctx, AV_LOG_ERROR, "Error allocating the output packet\n");
1734 return ret;
1735 }
1736
1737 pkt.bs = av_mallocz(sizeof(*pkt.bs));
1738 if (!pkt.bs)
1739 goto nomem;
1740 pkt.bs->Data = pkt.pkt.data;
1741 pkt.bs->MaxLength = pkt.pkt.size;
1742
1743 if (avctx->codec_id == AV_CODEC_ID_H264) {
1744 enc_info = av_mallocz(sizeof(*enc_info));
1745 if (!enc_info)
1746 goto nomem;
1747
1748 enc_info->Header.BufferId = MFX_EXTBUFF_ENCODED_FRAME_INFO;
1749 enc_info->Header.BufferSz = sizeof (*enc_info);
1750 pkt.bs->NumExtParam = 1;
1751 enc_buf = av_mallocz(sizeof(mfxExtBuffer *));
1752 if (!enc_buf)
1753 goto nomem;
1754 enc_buf[0] = (mfxExtBuffer *)enc_info;
1755
1756 pkt.bs->ExtParam = enc_buf;
1757 }
1758
1759 if (q->set_encode_ctrl_cb) {
1760 q->set_encode_ctrl_cb(avctx, frame, &qsv_frame->enc_ctrl);
1761 }
1762
1763 if ((avctx->codec_id == AV_CODEC_ID_H264 ||
1764 avctx->codec_id == AV_CODEC_ID_H265) &&
1765 enc_ctrl && QSV_RUNTIME_VERSION_ATLEAST(q->ver, 1, 8)) {
1766 ret = set_roi_encode_ctrl(avctx, frame, enc_ctrl);
1767 if (ret < 0)
1768 goto free;
1769 }
1770
1771 pkt.sync = av_mallocz(sizeof(*pkt.sync));
1772 if (!pkt.sync)
1773 goto nomem;
1774
1775 do {
1776 ret = MFXVideoENCODE_EncodeFrameAsync(q->session, enc_ctrl, surf, pkt.bs, pkt.sync);
1777 if (ret == MFX_WRN_DEVICE_BUSY)
1778 av_usleep(500);
1779 } while (ret == MFX_WRN_DEVICE_BUSY || ret == MFX_WRN_IN_EXECUTION);
1780
1781 if (ret > 0)
1782 ff_qsv_print_warning(avctx, ret, "Warning during encoding");
1783
1784 if (ret < 0) {
1785 ret = (ret == MFX_ERR_MORE_DATA) ?
1786 0 : ff_qsv_print_error(avctx, ret, "Error during encoding");
1787 goto free;
1788 }
1789
1790 if (ret == MFX_WRN_INCOMPATIBLE_VIDEO_PARAM && frame && frame->interlaced_frame)
1791 print_interlace_msg(avctx, q);
1792
1793 ret = 0;
1794
1795 if (*pkt.sync) {
1796 av_fifo_write(q->async_fifo, &pkt, 1);
1797 } else {
1798 free:
1799 av_freep(&pkt.sync);
1800 av_packet_unref(&pkt.pkt);
1801 av_freep(&pkt.bs);
1802 if (avctx->codec_id == AV_CODEC_ID_H264) {
1803 av_freep(&enc_info);
1804 av_freep(&enc_buf);
1805 }
1806 }
1807
1808 return ret;
1809 nomem:
1810 ret = AVERROR(ENOMEM);
1811 goto free;
1812 }
1813
ff_qsv_encode(AVCodecContext *avctx, QSVEncContext *q, AVPacket *pkt, const AVFrame *frame, int *got_packet)1814 int ff_qsv_encode(AVCodecContext *avctx, QSVEncContext *q,
1815 AVPacket *pkt, const AVFrame *frame, int *got_packet)
1816 {
1817 int ret;
1818
1819 ret = update_parameters(avctx, q, frame);
1820 if (ret < 0)
1821 return ret;
1822
1823 ret = encode_frame(avctx, q, frame);
1824 if (ret < 0)
1825 return ret;
1826
1827 if ((av_fifo_can_read(q->async_fifo) >= q->async_depth) ||
1828 (!frame && av_fifo_can_read(q->async_fifo))) {
1829 QSVPacket qpkt;
1830 mfxExtAVCEncodedFrameInfo *enc_info;
1831 mfxExtBuffer **enc_buf;
1832 enum AVPictureType pict_type;
1833
1834 av_fifo_read(q->async_fifo, &qpkt, 1);
1835
1836 do {
1837 ret = MFXVideoCORE_SyncOperation(q->session, *qpkt.sync, 1000);
1838 } while (ret == MFX_WRN_IN_EXECUTION);
1839
1840 qpkt.pkt.dts = av_rescale_q(qpkt.bs->DecodeTimeStamp, (AVRational){1, 90000}, avctx->time_base);
1841 qpkt.pkt.pts = av_rescale_q(qpkt.bs->TimeStamp, (AVRational){1, 90000}, avctx->time_base);
1842 qpkt.pkt.size = qpkt.bs->DataLength;
1843
1844 if (qpkt.bs->FrameType & MFX_FRAMETYPE_IDR || qpkt.bs->FrameType & MFX_FRAMETYPE_xIDR) {
1845 qpkt.pkt.flags |= AV_PKT_FLAG_KEY;
1846 pict_type = AV_PICTURE_TYPE_I;
1847 } else if (qpkt.bs->FrameType & MFX_FRAMETYPE_I || qpkt.bs->FrameType & MFX_FRAMETYPE_xI)
1848 pict_type = AV_PICTURE_TYPE_I;
1849 else if (qpkt.bs->FrameType & MFX_FRAMETYPE_P || qpkt.bs->FrameType & MFX_FRAMETYPE_xP)
1850 pict_type = AV_PICTURE_TYPE_P;
1851 else if (qpkt.bs->FrameType & MFX_FRAMETYPE_B || qpkt.bs->FrameType & MFX_FRAMETYPE_xB)
1852 pict_type = AV_PICTURE_TYPE_B;
1853 else if (qpkt.bs->FrameType == MFX_FRAMETYPE_UNKNOWN) {
1854 pict_type = AV_PICTURE_TYPE_NONE;
1855 av_log(avctx, AV_LOG_WARNING, "Unknown FrameType, set pict_type to AV_PICTURE_TYPE_NONE.\n");
1856 } else {
1857 av_log(avctx, AV_LOG_ERROR, "Invalid FrameType:%d.\n", qpkt.bs->FrameType);
1858 return AVERROR_INVALIDDATA;
1859 }
1860
1861 if (avctx->codec_id == AV_CODEC_ID_H264) {
1862 enc_buf = qpkt.bs->ExtParam;
1863 enc_info = (mfxExtAVCEncodedFrameInfo *)(*enc_buf);
1864 ff_side_data_set_encoder_stats(&qpkt.pkt,
1865 enc_info->QP * FF_QP2LAMBDA, NULL, 0, pict_type);
1866 av_freep(&enc_info);
1867 av_freep(&enc_buf);
1868 }
1869 av_freep(&qpkt.bs);
1870 av_freep(&qpkt.sync);
1871
1872 av_packet_move_ref(pkt, &qpkt.pkt);
1873
1874 *got_packet = 1;
1875 }
1876
1877 return 0;
1878 }
1879
ff_qsv_enc_close(AVCodecContext *avctx, QSVEncContext *q)1880 int ff_qsv_enc_close(AVCodecContext *avctx, QSVEncContext *q)
1881 {
1882 QSVFrame *cur;
1883
1884 if (q->session)
1885 MFXVideoENCODE_Close(q->session);
1886
1887 q->session = NULL;
1888 ff_qsv_close_internal_session(&q->internal_qs);
1889
1890 av_buffer_unref(&q->frames_ctx.hw_frames_ctx);
1891 av_buffer_unref(&q->frames_ctx.mids_buf);
1892
1893 cur = q->work_frames;
1894 while (cur) {
1895 q->work_frames = cur->next;
1896 av_frame_free(&cur->frame);
1897 free_encoder_ctrl_extparam(&cur->enc_ctrl);
1898 free_encoder_ctrl_payloads(&cur->enc_ctrl);
1899 av_freep(&cur);
1900 cur = q->work_frames;
1901 }
1902
1903 if (q->async_fifo) {
1904 QSVPacket pkt;
1905 while (av_fifo_read(q->async_fifo, &pkt, 1) >= 0) {
1906 if (avctx->codec_id == AV_CODEC_ID_H264) {
1907 mfxExtBuffer **enc_buf = pkt.bs->ExtParam;
1908 mfxExtAVCEncodedFrameInfo *enc_info = (mfxExtAVCEncodedFrameInfo *)(*enc_buf);
1909 av_freep(&enc_info);
1910 av_freep(&enc_buf);
1911 }
1912 av_freep(&pkt.sync);
1913 av_freep(&pkt.bs);
1914 av_packet_unref(&pkt.pkt);
1915 }
1916 av_fifo_freep2(&q->async_fifo);
1917 }
1918
1919 av_freep(&q->opaque_surfaces);
1920 av_buffer_unref(&q->opaque_alloc_buf);
1921
1922 av_freep(&q->extparam);
1923
1924 return 0;
1925 }
1926
1927 const AVCodecHWConfigInternal *const ff_qsv_enc_hw_configs[] = {
1928 HW_CONFIG_ENCODER_FRAMES(QSV, QSV),
1929 HW_CONFIG_ENCODER_DEVICE(NV12, QSV),
1930 HW_CONFIG_ENCODER_DEVICE(P010, QSV),
1931 NULL,
1932 };
1933