WinGui: Fix another instance of the Caliburn vs Json.net sillyness where objects...
[HandBrake.git] / libhb / enc_qsv.c
blob2f19b36f0b91517222110d2f4b9ca522cd70e810
1 /* ********************************************************************* *\
3 Copyright (C) 2013 Intel Corporation. All rights reserved.
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions are met:
7 - Redistributions of source code must retain the above copyright notice,
8 this list of conditions and the following disclaimer.
9 - Redistributions in binary form must reproduce the above copyright notice,
10 this list of conditions and the following disclaimer in the documentation
11 and/or other materials provided with the distribution.
12 - Neither the name of Intel Corporation nor the names of its contributors
13 may be used to endorse or promote products derived from this software
14 without specific prior written permission.
16 THIS SOFTWARE IS PROVIDED BY INTEL CORPORATION "AS IS" AND ANY EXPRESS OR
17 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 IN NO EVENT SHALL INTEL CORPORATION BE LIABLE FOR ANY DIRECT, INDIRECT,
20 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 \* ********************************************************************* */
29 #ifdef USE_QSV
31 #include "hb.h"
32 #include "nal_units.h"
33 #include "qsv_common.h"
34 #include "qsv_memory.h"
35 #include "h264_common.h"
38 * The frame info struct remembers information about each frame across calls to
39 * the encoder. Since frames are uniquely identified by their timestamp, we use
40 * some bits of the timestamp as an index. The LSB is chosen so that two
41 * successive frames will have different values in the bits over any plausible
42 * range of frame rates (starting with bit 8 allows any frame rate slower than
43 * 352fps). The MSB determines the size of the array. It is chosen so that two
44 * frames can't use the same slot during the encoder's max frame delay so that,
45 * up to some minimum frame rate, frames are guaranteed to map to different
46 * slots (an MSB of 17 which is 2^(17-8+1) = 1024 slots guarantees no collisions
47 * down to a rate of 0.7 fps).
49 #define FRAME_INFO_MAX2 (8) // 2^8 = 256; 90000/256 = 352 frames/sec
50 #define FRAME_INFO_MIN2 (17) // 2^17 = 128K; 90000/131072 = 0.7 frames/sec
51 #define FRAME_INFO_SIZE (1 << (FRAME_INFO_MIN2 - FRAME_INFO_MAX2 + 1))
52 #define FRAME_INFO_MASK (FRAME_INFO_SIZE - 1)
54 int encqsvInit (hb_work_object_t*, hb_job_t*);
55 int encqsvWork (hb_work_object_t*, hb_buffer_t**, hb_buffer_t**);
56 void encqsvClose(hb_work_object_t*);
58 hb_work_object_t hb_encqsv =
60 WORK_ENCQSV,
61 "H.264/AVC encoder (Intel QSV)",
62 encqsvInit,
63 encqsvWork,
64 encqsvClose
67 struct hb_work_private_s
69 hb_job_t *job;
70 uint32_t frames_in;
71 uint32_t frames_out;
72 int64_t last_start;
74 hb_qsv_param_t param;
75 av_qsv_space enc_space;
76 hb_qsv_info_t *qsv_info;
78 hb_list_t *delayed_chapters;
79 int64_t next_chapter_pts;
81 #define BFRM_DELAY_MAX 16
82 uint32_t *init_delay;
83 int bfrm_delay;
84 int64_t init_pts[BFRM_DELAY_MAX + 1];
85 hb_list_t *list_dts;
87 int64_t frame_duration[FRAME_INFO_SIZE];
89 int async_depth;
90 int max_async_depth;
92 // if encode-only, system memory used
93 int is_sys_mem;
94 mfxSession mfx_session;
95 struct SwsContext *sws_context_to_nv12;
97 // whether to expect input from VPP or from QSV decode
98 int is_vpp_present;
100 // whether the encoder is initialized
101 int init_done;
103 hb_list_t *delayed_processing;
104 hb_list_t *encoded_frames;
106 hb_list_t *loaded_plugins;
109 // used in delayed_chapters list
110 struct chapter_s
112 int index;
113 int64_t start;
116 static void hb_qsv_add_new_dts(hb_list_t *list, int64_t new_dts)
118 if (list != NULL)
120 int64_t *item = malloc(sizeof(int64_t));
121 if (item != NULL)
123 *item = new_dts;
124 hb_list_add(list, item);
129 static int64_t hb_qsv_pop_next_dts(hb_list_t *list)
131 int64_t next_dts = INT64_MIN;
132 if (list != NULL && hb_list_count(list) > 0)
134 int64_t *item = hb_list_item(list, 0);
135 if (item != NULL)
137 next_dts = *item;
138 hb_list_rem(list, item);
139 free(item);
142 return next_dts;
145 static void save_frame_duration(hb_work_private_t *pv, hb_buffer_t *buf)
147 int i = (buf->s.start >> FRAME_INFO_MAX2) & FRAME_INFO_MASK;
148 pv->frame_duration[i] = buf->s.stop - buf->s.start;
151 static int64_t get_frame_duration(hb_work_private_t *pv, hb_buffer_t *buf)
153 int i = (buf->s.start >> FRAME_INFO_MAX2) & FRAME_INFO_MASK;
154 return pv->frame_duration[i];
157 static void qsv_handle_breftype(hb_work_private_t *pv)
160 * If B-pyramid is not possible (not supported, incompatible profile, etc.)
161 * we don't need to adjust any settings, just sanitize it to off and return.
163 if (!(pv->qsv_info->capabilities & HB_QSV_CAP_B_REF_PYRAMID))
165 /* B-pyramid support not implemented */
166 goto unsupported;
168 else if (pv->param.videoParam->mfx.GopPicSize &&
169 pv->param.videoParam->mfx.GopPicSize <= 3)
171 /* GOP size must be at least 4 for B-pyramid */
172 goto unsupported;
174 else if (pv->param.videoParam->mfx.GopRefDist &&
175 pv->param.videoParam->mfx.GopRefDist <= 2)
177 /* We need 2 consecutive B-frames for B-pyramid (GopRefDist >= 3) */
178 goto unsupported;
180 else if (pv->qsv_info->codec_id == MFX_CODEC_AVC)
182 switch (pv->param.videoParam->mfx.CodecProfile)
184 case MFX_PROFILE_AVC_BASELINE:
185 case MFX_PROFILE_AVC_CONSTRAINED_HIGH:
186 case MFX_PROFILE_AVC_CONSTRAINED_BASELINE:
187 goto unsupported; // B-frames not allowed by profile
188 default:
189 break;
193 /* Handle B-pyramid auto (on for CQP, off otherwise) */
194 if (pv->param.gop.b_pyramid < 0)
196 pv->param.gop.b_pyramid = pv->param.videoParam->mfx.RateControlMethod == MFX_RATECONTROL_CQP;
199 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_BREFTYPE)
201 /* B-pyramid can be controlled directly */
202 if (pv->param.gop.b_pyramid)
204 pv->param.codingOption2.BRefType = MFX_B_REF_PYRAMID;
206 else
208 pv->param.codingOption2.BRefType = MFX_B_REF_OFF;
211 else
214 * We can't control B-pyramid directly, do it indirectly by
215 * adjusting GopRefDist, GopPicSize and NumRefFrame instead.
217 pv->param.codingOption2.BRefType = MFX_B_REF_UNKNOWN;
220 * pyramid_ref_dist is the closest B-pyramid compatible
221 * value (multiple of 2, >= 4) to the requested GopRefDist.
223 int pyramid_ref_dist = 4;
224 while (pv->param.videoParam->mfx.GopRefDist > pyramid_ref_dist)
226 pyramid_ref_dist *= 2;
229 if (pv->param.gop.b_pyramid)
231 /* GopRefDist must be B-pyramid compatible */
232 pv->param.videoParam->mfx.GopRefDist = pyramid_ref_dist;
235 * GopPicSize must be a multiple of GopRefDist.
237 * Note: GopPicSize == 0 should always result in a value
238 * that doesn't cause Media SDK to disable B-pyramid.
240 if (pv->param.videoParam->mfx.GopPicSize)
242 pv->param.videoParam->mfx.GopPicSize = FFALIGN(pv->param.videoParam->mfx.GopPicSize,
243 pv->param.videoParam->mfx.GopRefDist);
247 * NumRefFrame must be greater than 3 and than half of GopRefDist.
248 * Otherwise, Media SDK may sometimes decide to disable B-pyramid
249 * (whereas sometimes it will simply sanitize NumRefFrame instead).
251 * Note: Media SDK handles the NumRefFrame == 0 case for us.
253 if (pv->param.videoParam->mfx.NumRefFrame)
255 pv->param.videoParam->mfx.NumRefFrame = FFMAX(pv->param.videoParam->mfx.NumRefFrame,
256 pv->param.videoParam->mfx.GopRefDist / 2);
257 pv->param.videoParam->mfx.NumRefFrame = FFMAX(pv->param.videoParam->mfx.NumRefFrame, 3);
260 else if (pv->param.videoParam->mfx.GopRefDist == 0 ||
261 pv->param.videoParam->mfx.GopRefDist == pyramid_ref_dist)
264 * GopRefDist is either B-pyramid compatible or unknown (and thus
265 * potentially compatible), so adjust it to force-disable B-pyramid.
267 pv->param.videoParam->mfx.GopRefDist = pyramid_ref_dist - 1;
271 return;
273 unsupported:
274 pv->param.gop.b_pyramid = 0;
275 pv->param.codingOption2.BRefType = MFX_B_REF_OFF;
278 int qsv_enc_init(hb_work_private_t *pv)
280 av_qsv_context *qsv = pv->job->qsv.ctx;
281 hb_job_t *job = pv->job;
282 mfxVersion version;
283 mfxStatus sts;
284 mfxIMPL impl;
285 int i;
287 if (pv->init_done)
289 return 0;
292 if (qsv == NULL)
294 if (!pv->is_sys_mem)
296 hb_error("qsv_enc_init: decode enabled but no context!");
297 return 3;
299 job->qsv.ctx = qsv = av_mallocz(sizeof(av_qsv_context));
302 av_qsv_space *qsv_encode = qsv->enc_space;
303 if (qsv_encode == NULL)
305 // if only for encode
306 if (pv->is_sys_mem)
308 // no need to use additional sync as encode only -> single thread
309 av_qsv_add_context_usage(qsv, 0);
311 // re-use the session from encqsvInit
312 qsv->mfx_session = pv->mfx_session;
314 qsv->enc_space = qsv_encode = &pv->enc_space;
317 if (!pv->is_sys_mem)
319 if (!pv->is_vpp_present && job->list_filter != NULL)
321 for (i = 0; i < hb_list_count(job->list_filter); i++)
323 hb_filter_object_t *filter = hb_list_item(job->list_filter, i);
324 if (filter->id == HB_FILTER_QSV_PRE ||
325 filter->id == HB_FILTER_QSV_POST ||
326 filter->id == HB_FILTER_QSV)
328 pv->is_vpp_present = 1;
329 break;
334 if (pv->is_vpp_present)
336 if (qsv->vpp_space == NULL)
338 return 2;
340 for (i = 0; i < av_qsv_list_count(qsv->vpp_space); i++)
342 av_qsv_space *vpp = av_qsv_list_item(qsv->vpp_space, i);
343 if (!vpp->is_init_done)
345 return 2;
350 av_qsv_space *dec_space = qsv->dec_space;
351 if (dec_space == NULL || !dec_space->is_init_done)
353 return 2;
356 else
358 pv->sws_context_to_nv12 = hb_sws_get_context(
359 job->width, job->height,
360 AV_PIX_FMT_YUV420P,
361 job->width, job->height,
362 AV_PIX_FMT_NV12,
363 SWS_LANCZOS|SWS_ACCURATE_RND);
366 // allocate tasks
367 qsv_encode->p_buf_max_size = AV_QSV_BUF_SIZE_DEFAULT;
368 qsv_encode->tasks = av_qsv_list_init(HAVE_THREADS);
369 for (i = 0; i < pv->max_async_depth; i++)
371 av_qsv_task *task = av_mallocz(sizeof(av_qsv_task));
372 task->bs = av_mallocz(sizeof(mfxBitstream));
373 task->bs->Data = av_mallocz(sizeof(uint8_t) * qsv_encode->p_buf_max_size);
374 task->bs->MaxLength = qsv_encode->p_buf_max_size;
375 task->bs->DataLength = 0;
376 task->bs->DataOffset = 0;
377 av_qsv_list_add(qsv_encode->tasks, task);
380 // setup surface allocation
381 pv->param.videoParam->IOPattern = (pv->is_sys_mem ?
382 MFX_IOPATTERN_IN_SYSTEM_MEMORY :
383 MFX_IOPATTERN_IN_OPAQUE_MEMORY);
384 memset(&qsv_encode->request, 0, sizeof(mfxFrameAllocRequest) * 2);
385 sts = MFXVideoENCODE_QueryIOSurf(qsv->mfx_session,
386 pv->param.videoParam,
387 &qsv_encode->request[0]);
388 if (sts < MFX_ERR_NONE) // ignore warnings
390 hb_error("qsv_enc_init: MFXVideoENCODE_QueryIOSurf failed (%d)", sts);
391 *job->done_error = HB_ERROR_INIT;
392 *job->die = 1;
393 return -1;
396 // allocate surfaces
397 if (pv->is_sys_mem)
399 qsv_encode->surface_num = FFMIN(qsv_encode->request[0].NumFrameSuggested +
400 pv->max_async_depth, AV_QSV_SURFACE_NUM);
401 if (qsv_encode->surface_num <= 0)
403 qsv_encode->surface_num = AV_QSV_SURFACE_NUM;
405 for (i = 0; i < qsv_encode->surface_num; i++)
407 mfxFrameSurface1 *surface = av_mallocz(sizeof(mfxFrameSurface1));
408 mfxFrameInfo info = pv->param.videoParam->mfx.FrameInfo;
409 surface->Info = info;
410 surface->Data.Pitch = info.Width;
411 surface->Data.Y = av_mallocz(info.Width * info.Height);
412 surface->Data.VU = av_mallocz(info.Width * info.Height / 2);
413 qsv_encode->p_surfaces[i] = surface;
416 else
418 av_qsv_space *in_space = qsv->dec_space;
419 if (pv->is_vpp_present)
421 // we get our input from VPP instead
422 in_space = av_qsv_list_item(qsv->vpp_space,
423 av_qsv_list_count(qsv->vpp_space) - 1);
425 // introduced in API 1.3
426 memset(&qsv_encode->ext_opaque_alloc, 0, sizeof(mfxExtOpaqueSurfaceAlloc));
427 qsv_encode->ext_opaque_alloc.Header.BufferId = MFX_EXTBUFF_OPAQUE_SURFACE_ALLOCATION;
428 qsv_encode->ext_opaque_alloc.Header.BufferSz = sizeof(mfxExtOpaqueSurfaceAlloc);
429 qsv_encode->ext_opaque_alloc.In.Surfaces = in_space->p_surfaces;
430 qsv_encode->ext_opaque_alloc.In.NumSurface = in_space->surface_num;
431 qsv_encode->ext_opaque_alloc.In.Type = qsv_encode->request[0].Type;
432 pv->param.videoParam->ExtParam[pv->param.videoParam->NumExtParam++] = (mfxExtBuffer*)&qsv_encode->ext_opaque_alloc;
435 // allocate sync points
436 qsv_encode->sync_num = (qsv_encode->surface_num ?
437 FFMIN(qsv_encode->surface_num, AV_QSV_SYNC_NUM) :
438 AV_QSV_SYNC_NUM);
439 for (i = 0; i < qsv_encode->sync_num; i++)
441 qsv_encode->p_syncp[i] = av_mallocz(sizeof(av_qsv_sync));
442 AV_QSV_CHECK_POINTER(qsv_encode->p_syncp[i], MFX_ERR_MEMORY_ALLOC);
443 qsv_encode->p_syncp[i]->p_sync = av_mallocz(sizeof(mfxSyncPoint));
444 AV_QSV_CHECK_POINTER(qsv_encode->p_syncp[i]->p_sync, MFX_ERR_MEMORY_ALLOC);
447 // log actual implementation details now that we know them
448 if ((MFXQueryIMPL (qsv->mfx_session, &impl) == MFX_ERR_NONE) &&
449 (MFXQueryVersion(qsv->mfx_session, &version) == MFX_ERR_NONE))
451 hb_log("qsv_enc_init: using '%s' implementation, API: %"PRIu16".%"PRIu16"",
452 hb_qsv_impl_get_name(impl), version.Major, version.Minor);
454 else
456 hb_log("qsv_enc_init: MFXQueryIMPL/MFXQueryVersion failure");
459 // if not re-using encqsvInit's MFX session, load required plug-ins here
460 if (pv->loaded_plugins == NULL)
462 pv->loaded_plugins = hb_qsv_load_plugins(pv->qsv_info, qsv->mfx_session, version);
463 if (pv->loaded_plugins == NULL)
465 hb_error("qsv_enc_init: hb_qsv_load_plugins failed");
466 *job->done_error = HB_ERROR_INIT;
467 *job->die = 1;
468 return -1;
472 // initialize the encoder
473 sts = MFXVideoENCODE_Init(qsv->mfx_session, pv->param.videoParam);
474 if (sts < MFX_ERR_NONE) // ignore warnings
476 hb_error("qsv_enc_init: MFXVideoENCODE_Init failed (%d)", sts);
477 *job->done_error = HB_ERROR_INIT;
478 *job->die = 1;
479 return -1;
481 qsv_encode->is_init_done = 1;
483 pv->init_done = 1;
484 return 0;
487 /***********************************************************************
488 * encqsvInit
489 ***********************************************************************
491 **********************************************************************/
492 int encqsvInit(hb_work_object_t *w, hb_job_t *job)
494 hb_work_private_t *pv = calloc(1, sizeof(hb_work_private_t));
495 w->private_data = pv;
497 pv->job = job;
498 pv->is_sys_mem = hb_qsv_decode_is_enabled(job) == 0;
499 pv->qsv_info = hb_qsv_info_get(job->vcodec);
500 pv->delayed_processing = hb_list_init();
501 pv->encoded_frames = hb_list_init();
502 pv->last_start = INT64_MIN;
504 pv->next_chapter_pts = AV_NOPTS_VALUE;
505 pv->delayed_chapters = hb_list_init();
507 // default encoding parameters
508 if (hb_qsv_param_default_preset(&pv->param, &pv->enc_space.m_mfxVideoParam,
509 pv->qsv_info, job->encoder_preset))
511 hb_error("encqsvInit: hb_qsv_param_default_preset failed");
512 return -1;
515 // set AsyncDepth to match that of decode and VPP
516 pv->param.videoParam->AsyncDepth = job->qsv.async_depth;
518 // enable and set colorimetry (video signal information)
519 pv->param.videoSignalInfo.ColourDescriptionPresent = 1;
520 switch (job->color_matrix_code)
522 case 4:
523 // custom
524 pv->param.videoSignalInfo.ColourPrimaries = job->color_prim;
525 pv->param.videoSignalInfo.TransferCharacteristics = job->color_transfer;
526 pv->param.videoSignalInfo.MatrixCoefficients = job->color_matrix;
527 break;
528 case 3:
529 // ITU BT.709 HD content
530 pv->param.videoSignalInfo.ColourPrimaries = HB_COLR_PRI_BT709;
531 pv->param.videoSignalInfo.TransferCharacteristics = HB_COLR_TRA_BT709;
532 pv->param.videoSignalInfo.MatrixCoefficients = HB_COLR_MAT_BT709;
533 break;
534 case 2:
535 // ITU BT.601 DVD or SD TV content (PAL)
536 pv->param.videoSignalInfo.ColourPrimaries = HB_COLR_PRI_EBUTECH;
537 pv->param.videoSignalInfo.TransferCharacteristics = HB_COLR_TRA_BT709;
538 pv->param.videoSignalInfo.MatrixCoefficients = HB_COLR_MAT_SMPTE170M;
539 break;
540 case 1:
541 // ITU BT.601 DVD or SD TV content (NTSC)
542 pv->param.videoSignalInfo.ColourPrimaries = HB_COLR_PRI_SMPTEC;
543 pv->param.videoSignalInfo.TransferCharacteristics = HB_COLR_TRA_BT709;
544 pv->param.videoSignalInfo.MatrixCoefficients = HB_COLR_MAT_SMPTE170M;
545 break;
546 default:
547 // detected during scan
548 pv->param.videoSignalInfo.ColourPrimaries = job->title->color_prim;
549 pv->param.videoSignalInfo.TransferCharacteristics = job->title->color_transfer;
550 pv->param.videoSignalInfo.MatrixCoefficients = job->title->color_matrix;
551 break;
554 // parse user-specified encoder options, if present
555 if (job->encoder_options != NULL && *job->encoder_options)
557 hb_dict_t *options_list;
558 options_list = hb_encopts_to_dict(job->encoder_options, job->vcodec);
560 hb_dict_iter_t iter;
561 for (iter = hb_dict_iter_init(options_list);
562 iter != HB_DICT_ITER_DONE;
563 iter = hb_dict_iter_next(options_list, iter))
565 const char *key = hb_dict_iter_key(iter);
566 hb_value_t *value = hb_dict_iter_value(iter);
567 char *str = hb_value_get_string_xform(value);
569 switch (hb_qsv_param_parse(&pv->param, pv->qsv_info, key, str))
571 case HB_QSV_PARAM_OK:
572 break;
574 case HB_QSV_PARAM_BAD_NAME:
575 hb_log("encqsvInit: hb_qsv_param_parse: bad key %s", key);
576 break;
577 case HB_QSV_PARAM_BAD_VALUE:
578 hb_log("encqsvInit: hb_qsv_param_parse: bad value %s for key %s",
579 str, key);
580 break;
581 case HB_QSV_PARAM_UNSUPPORTED:
582 hb_log("encqsvInit: hb_qsv_param_parse: unsupported option %s",
583 key);
584 break;
586 case HB_QSV_PARAM_ERROR:
587 default:
588 hb_log("encqsvInit: hb_qsv_param_parse: unknown error");
589 break;
591 free(str);
593 hb_dict_free(&options_list);
596 // reload colorimetry in case values were set in encoder_options
597 if (pv->param.videoSignalInfo.ColourDescriptionPresent)
599 job->color_matrix_code = 4;
600 job->color_prim = pv->param.videoSignalInfo.ColourPrimaries;
601 job->color_transfer = pv->param.videoSignalInfo.TransferCharacteristics;
602 job->color_matrix = pv->param.videoSignalInfo.MatrixCoefficients;
604 else
606 job->color_matrix_code = 0;
607 job->color_prim = HB_COLR_PRI_UNDEF;
608 job->color_transfer = HB_COLR_TRA_UNDEF;
609 job->color_matrix = HB_COLR_MAT_UNDEF;
612 // sanitize values that may exceed the Media SDK variable size
613 hb_rational_t par;
614 hb_limit_rational(&par.num, &par.den,
615 job->par.num, job->par.den, UINT16_MAX);
617 // some encoding parameters are used by filters to configure their output
618 if (pv->param.videoParam->mfx.FrameInfo.PicStruct != MFX_PICSTRUCT_PROGRESSIVE)
620 job->qsv.enc_info.align_height = AV_QSV_ALIGN32(job->height);
622 else
624 job->qsv.enc_info.align_height = AV_QSV_ALIGN16(job->height);
626 job->qsv.enc_info.align_width = AV_QSV_ALIGN16(job->width);
627 job->qsv.enc_info.pic_struct = pv->param.videoParam->mfx.FrameInfo.PicStruct;
628 job->qsv.enc_info.is_init_done = 1;
630 // encode to H.264 and set FrameInfo
631 pv->param.videoParam->mfx.CodecId = MFX_CODEC_AVC;
632 pv->param.videoParam->mfx.CodecLevel = MFX_LEVEL_UNKNOWN;
633 pv->param.videoParam->mfx.CodecProfile = MFX_PROFILE_UNKNOWN;
634 pv->param.videoParam->mfx.FrameInfo.FourCC = MFX_FOURCC_NV12;
635 pv->param.videoParam->mfx.FrameInfo.ChromaFormat = MFX_CHROMAFORMAT_YUV420;
636 pv->param.videoParam->mfx.FrameInfo.FrameRateExtN = job->vrate.num;
637 pv->param.videoParam->mfx.FrameInfo.FrameRateExtD = job->vrate.den;
638 pv->param.videoParam->mfx.FrameInfo.AspectRatioW = par.num;
639 pv->param.videoParam->mfx.FrameInfo.AspectRatioH = par.den;
640 pv->param.videoParam->mfx.FrameInfo.CropX = 0;
641 pv->param.videoParam->mfx.FrameInfo.CropY = 0;
642 pv->param.videoParam->mfx.FrameInfo.CropW = job->width;
643 pv->param.videoParam->mfx.FrameInfo.CropH = job->height;
644 pv->param.videoParam->mfx.FrameInfo.PicStruct = job->qsv.enc_info.pic_struct;
645 pv->param.videoParam->mfx.FrameInfo.Width = job->qsv.enc_info.align_width;
646 pv->param.videoParam->mfx.FrameInfo.Height = job->qsv.enc_info.align_height;
648 // parse user-specified codec profile and level
649 if (hb_qsv_profile_parse(&pv->param, pv->qsv_info, job->encoder_profile))
651 hb_error("encqsvInit: bad profile %s", job->encoder_profile);
652 return -1;
654 if (hb_qsv_level_parse(&pv->param, pv->qsv_info, job->encoder_level))
656 hb_error("encqsvInit: bad level %s", job->encoder_level);
657 return -1;
660 // interlaced encoding is not always possible
661 if (pv->param.videoParam->mfx.CodecId == MFX_CODEC_AVC &&
662 pv->param.videoParam->mfx.FrameInfo.PicStruct != MFX_PICSTRUCT_PROGRESSIVE)
664 if (pv->param.videoParam->mfx.CodecProfile == MFX_PROFILE_AVC_CONSTRAINED_BASELINE ||
665 pv->param.videoParam->mfx.CodecProfile == MFX_PROFILE_AVC_BASELINE ||
666 pv->param.videoParam->mfx.CodecProfile == MFX_PROFILE_AVC_PROGRESSIVE_HIGH)
668 hb_error("encqsvInit: profile %s doesn't support interlaced encoding",
669 hb_qsv_profile_name(MFX_CODEC_AVC,
670 pv->param.videoParam->mfx.CodecProfile));
671 return -1;
673 if ((pv->param.videoParam->mfx.CodecLevel >= MFX_LEVEL_AVC_1b &&
674 pv->param.videoParam->mfx.CodecLevel <= MFX_LEVEL_AVC_2) ||
675 (pv->param.videoParam->mfx.CodecLevel >= MFX_LEVEL_AVC_42))
677 hb_error("encqsvInit: level %s doesn't support interlaced encoding",
678 hb_qsv_level_name(MFX_CODEC_AVC,
679 pv->param.videoParam->mfx.CodecLevel));
680 return -1;
684 // sanitize ICQ
685 if (!(pv->qsv_info->capabilities & HB_QSV_CAP_RATECONTROL_ICQ))
687 // ICQ not supported
688 pv->param.rc.icq = 0;
690 else
692 pv->param.rc.icq = pv->param.rc.icq && job->vquality >= 0;
695 // sanitize lookahead
696 if (!(pv->qsv_info->capabilities & HB_QSV_CAP_RATECONTROL_LA))
698 // lookahead not supported
699 pv->param.rc.lookahead = 0;
701 else if ((pv->param.rc.lookahead) &&
702 (pv->qsv_info->capabilities & HB_QSV_CAP_RATECONTROL_LAi) == 0 &&
703 (pv->param.videoParam->mfx.FrameInfo.PicStruct != MFX_PICSTRUCT_PROGRESSIVE))
705 // lookahead enabled but we can't use it
706 hb_log("encqsvInit: LookAhead not used (LookAhead is progressive-only)");
707 pv->param.rc.lookahead = 0;
709 else
711 pv->param.rc.lookahead = pv->param.rc.lookahead && (pv->param.rc.icq || job->vquality < 0);
714 // set VBV here (this will be overridden for CQP and ignored for LA)
715 // only set BufferSizeInKB, InitialDelayInKB and MaxKbps if we have
716 // them - otheriwse Media SDK will pick values for us automatically
717 if (pv->param.rc.vbv_buffer_size > 0)
719 if (pv->param.rc.vbv_buffer_init > 1.0)
721 pv->param.videoParam->mfx.InitialDelayInKB = (pv->param.rc.vbv_buffer_init / 8);
723 else if (pv->param.rc.vbv_buffer_init > 0.0)
725 pv->param.videoParam->mfx.InitialDelayInKB = (pv->param.rc.vbv_buffer_size *
726 pv->param.rc.vbv_buffer_init / 8);
728 pv->param.videoParam->mfx.BufferSizeInKB = (pv->param.rc.vbv_buffer_size / 8);
730 if (pv->param.rc.vbv_max_bitrate > 0)
732 pv->param.videoParam->mfx.MaxKbps = pv->param.rc.vbv_max_bitrate;
735 // set rate control paremeters
736 if (job->vquality >= 0)
738 if (pv->param.rc.icq)
740 // introduced in API 1.8
741 if (pv->param.rc.lookahead)
743 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_LA_ICQ;
745 else
747 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_ICQ;
749 pv->param.videoParam->mfx.ICQQuality = HB_QSV_CLIP3(1, 51, job->vquality);
751 else
753 // introduced in API 1.1
754 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_CQP;
755 pv->param.videoParam->mfx.QPI = HB_QSV_CLIP3(0, 51, job->vquality + pv->param.rc.cqp_offsets[0]);
756 pv->param.videoParam->mfx.QPP = HB_QSV_CLIP3(0, 51, job->vquality + pv->param.rc.cqp_offsets[1]);
757 pv->param.videoParam->mfx.QPB = HB_QSV_CLIP3(0, 51, job->vquality + pv->param.rc.cqp_offsets[2]);
758 // CQP + ExtBRC can cause bad output
759 pv->param.codingOption2.ExtBRC = MFX_CODINGOPTION_OFF;
762 else if (job->vbitrate > 0)
764 if (pv->param.rc.lookahead)
766 // introduced in API 1.7
767 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_LA;
768 pv->param.videoParam->mfx.TargetKbps = job->vbitrate;
769 // ignored, but some drivers will change AsyncDepth because of it
770 pv->param.codingOption2.ExtBRC = MFX_CODINGOPTION_OFF;
772 else
774 // introduced in API 1.0
775 if (job->vbitrate == pv->param.rc.vbv_max_bitrate)
777 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_CBR;
779 else
781 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_VBR;
783 pv->param.videoParam->mfx.TargetKbps = job->vbitrate;
786 else
788 hb_error("encqsvInit: invalid rate control (%d, %d)",
789 job->vquality, job->vbitrate);
790 return -1;
793 // if VBV is enabled but ignored, log it
794 if (pv->param.rc.vbv_max_bitrate > 0 || pv->param.rc.vbv_buffer_size > 0)
796 switch (pv->param.videoParam->mfx.RateControlMethod)
798 case MFX_RATECONTROL_LA:
799 case MFX_RATECONTROL_LA_ICQ:
800 hb_log("encqsvInit: LookAhead enabled, ignoring VBV");
801 break;
802 case MFX_RATECONTROL_ICQ:
803 hb_log("encqsvInit: ICQ rate control, ignoring VBV");
804 break;
805 default:
806 break;
810 // set the GOP structure
811 if (pv->param.gop.gop_ref_dist < 0)
813 if (pv->param.videoParam->mfx.RateControlMethod == MFX_RATECONTROL_CQP)
815 pv->param.gop.gop_ref_dist = 4;
817 else
819 pv->param.gop.gop_ref_dist = 3;
822 pv->param.videoParam->mfx.GopRefDist = pv->param.gop.gop_ref_dist;
824 // set the keyframe interval
825 if (pv->param.gop.gop_pic_size < 0)
827 int rate = (int)((double)job->vrate.num / (double)job->vrate.den + 0.5);
828 if (pv->param.videoParam->mfx.RateControlMethod == MFX_RATECONTROL_CQP)
830 // ensure B-pyramid is enabled for CQP on Haswell
831 pv->param.gop.gop_pic_size = 32;
833 else
835 // set the keyframe interval based on the framerate
836 pv->param.gop.gop_pic_size = rate;
839 pv->param.videoParam->mfx.GopPicSize = pv->param.gop.gop_pic_size;
841 // sanitize some settings that affect memory consumption
842 if (!pv->is_sys_mem)
844 // limit these to avoid running out of resources (causes hang)
845 pv->param.videoParam->mfx.GopRefDist = FFMIN(pv->param.videoParam->mfx.GopRefDist,
846 pv->param.rc.lookahead ? 8 : 16);
847 pv->param.codingOption2.LookAheadDepth = FFMIN(pv->param.codingOption2.LookAheadDepth,
848 pv->param.rc.lookahead ? (48 - pv->param.videoParam->mfx.GopRefDist -
849 3 * !pv->param.videoParam->mfx.GopRefDist) : 0);
851 else
853 // encode-only is a bit less sensitive to memory issues
854 pv->param.videoParam->mfx.GopRefDist = FFMIN(pv->param.videoParam->mfx.GopRefDist, 16);
855 pv->param.codingOption2.LookAheadDepth = FFMIN(pv->param.codingOption2.LookAheadDepth,
856 pv->param.rc.lookahead ? 100 : 0);
858 if (pv->param.rc.lookahead)
860 // LookAheadDepth 10 will cause a hang with some driver versions
861 pv->param.codingOption2.LookAheadDepth = FFMAX(pv->param.codingOption2.LookAheadDepth, 11);
865 * We may need to adjust GopRefDist, GopPicSize and
866 * NumRefFrame to enable or disable B-pyramid, so do it last.
868 qsv_handle_breftype(pv);
871 * init a dummy encode-only session to get the SPS/PPS
872 * and the final output settings sanitized by Media SDK
873 * this is fine since the actual encode will use the same
874 * values for all parameters relevant to the H.264 bitstream
876 mfxStatus err;
877 mfxVersion version;
878 mfxVideoParam videoParam;
879 mfxExtBuffer *extParamArray[3];
880 mfxSession session = (mfxSession)0;
881 mfxExtCodingOption option1_buf, *option1 = &option1_buf;
882 mfxExtCodingOption2 option2_buf, *option2 = &option2_buf;
883 mfxExtCodingOptionSPSPPS sps_pps_buf, *sps_pps = &sps_pps_buf;
884 version.Major = HB_QSV_MINVERSION_MAJOR;
885 version.Minor = HB_QSV_MINVERSION_MINOR;
886 err = MFXInit(pv->qsv_info->implementation, &version, &session);
887 if (err != MFX_ERR_NONE)
889 hb_error("encqsvInit: MFXInit failed (%d)", err);
890 return -1;
893 /* Query the API version for hb_qsv_load_plugins */
894 err = MFXQueryVersion(session, &version);
895 if (err != MFX_ERR_NONE)
897 hb_error("encqsvInit: MFXQueryVersion failed (%d)", err);
898 MFXClose(session);
899 return -1;
902 /* Load required MFX plug-ins */
903 pv->loaded_plugins = hb_qsv_load_plugins(pv->qsv_info, session, version);
904 if (pv->loaded_plugins == NULL)
906 hb_error("encqsvInit: hb_qsv_load_plugins failed");
907 MFXClose(session);
908 return -1;
911 err = MFXVideoENCODE_Init(session, pv->param.videoParam);
912 // workaround for the early 15.33.x driver, should be removed later
913 #define HB_DRIVER_FIX_33
914 #ifdef HB_DRIVER_FIX_33
915 int la_workaround = 0;
916 if (err < MFX_ERR_NONE &&
917 pv->param.videoParam->mfx.RateControlMethod == MFX_RATECONTROL_LA)
919 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_CBR;
920 err = MFXVideoENCODE_Init(session, pv->param.videoParam);
921 la_workaround = 1;
923 #endif
924 if (err < MFX_ERR_NONE) // ignore warnings
926 hb_error("encqsvInit: MFXVideoENCODE_Init failed (%d)", err);
927 hb_qsv_unload_plugins(&pv->loaded_plugins, session, version);
928 MFXClose(session);
929 return -1;
931 memset(&videoParam, 0, sizeof(mfxVideoParam));
932 videoParam.ExtParam = extParamArray;
933 videoParam.NumExtParam = 0;
934 // introduced in API 1.3
935 memset(sps_pps, 0, sizeof(mfxExtCodingOptionSPSPPS));
936 sps_pps->Header.BufferId = MFX_EXTBUFF_CODING_OPTION_SPSPPS;
937 sps_pps->Header.BufferSz = sizeof(mfxExtCodingOptionSPSPPS);
938 sps_pps->SPSId = 0;
939 sps_pps->SPSBuffer = w->config->h264.sps;
940 sps_pps->SPSBufSize = sizeof(w->config->h264.sps);
941 sps_pps->PPSId = 0;
942 sps_pps->PPSBuffer = w->config->h264.pps;
943 sps_pps->PPSBufSize = sizeof(w->config->h264.pps);
944 videoParam.ExtParam[videoParam.NumExtParam++] = (mfxExtBuffer*)sps_pps;
945 // introduced in API 1.0
946 memset(option1, 0, sizeof(mfxExtCodingOption));
947 option1->Header.BufferId = MFX_EXTBUFF_CODING_OPTION;
948 option1->Header.BufferSz = sizeof(mfxExtCodingOption);
949 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION1)
951 videoParam.ExtParam[videoParam.NumExtParam++] = (mfxExtBuffer*)option1;
953 // introduced in API 1.6
954 memset(option2, 0, sizeof(mfxExtCodingOption2));
955 option2->Header.BufferId = MFX_EXTBUFF_CODING_OPTION2;
956 option2->Header.BufferSz = sizeof(mfxExtCodingOption2);
957 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2)
959 videoParam.ExtParam[videoParam.NumExtParam++] = (mfxExtBuffer*)option2;
961 err = MFXVideoENCODE_GetVideoParam(session, &videoParam);
962 MFXVideoENCODE_Close(session);
963 if (err == MFX_ERR_NONE)
965 // remove 32-bit NAL prefix (0x00 0x00 0x00 0x01)
966 w->config->h264.sps_length = sps_pps->SPSBufSize - 4;
967 memmove(w->config->h264.sps, w->config->h264.sps + 4,
968 w->config->h264.sps_length);
969 w->config->h264.pps_length = sps_pps->PPSBufSize - 4;
970 memmove(w->config->h264.pps, w->config->h264.pps + 4,
971 w->config->h264.pps_length);
973 else
975 hb_error("encqsvInit: MFXVideoENCODE_GetVideoParam failed (%d)", err);
976 hb_qsv_unload_plugins(&pv->loaded_plugins, session, version);
977 MFXClose(session);
978 return -1;
981 #ifdef HB_DRIVER_FIX_33
982 if (la_workaround)
984 videoParam.mfx.RateControlMethod =
985 pv->param.videoParam->mfx.RateControlMethod = MFX_RATECONTROL_LA;
986 option2->LookAheadDepth = pv->param.codingOption2.LookAheadDepth;
987 hb_log("encqsvInit: using LookAhead workaround (\"early 33 fix\")");
989 #endif
991 // when using system memory, we re-use this same session
992 if (pv->is_sys_mem)
994 pv->mfx_session = session;
996 else
998 hb_qsv_unload_plugins(&pv->loaded_plugins, session, version);
999 MFXClose(session);
1002 /* B-frame related setup */
1003 if (videoParam.mfx.GopRefDist > 1)
1005 /* the muxer needs to know to the init_delay */
1006 switch (pv->qsv_info->codec_id)
1008 case MFX_CODEC_AVC:
1009 pv->init_delay = &w->config->h264.init_delay;
1010 break;
1011 default: // unreachable
1012 break;
1015 /* let the muxer know that it should expect B-frames */
1016 job->areBframes = 1;
1018 /* holds the PTS sequence in display order, used to generate DTS */
1019 pv->list_dts = hb_list_init();
1022 // log code path and main output settings
1023 hb_log("encqsvInit: using %s path",
1024 pv->is_sys_mem ? "encode-only" : "full QSV");
1025 hb_log("encqsvInit: %s %s profile @ level %s",
1026 hb_qsv_codec_name (videoParam.mfx.CodecId),
1027 hb_qsv_profile_name(videoParam.mfx.CodecId, videoParam.mfx.CodecProfile),
1028 hb_qsv_level_name (videoParam.mfx.CodecId, videoParam.mfx.CodecLevel));
1029 hb_log("encqsvInit: TargetUsage %"PRIu16" AsyncDepth %"PRIu16"",
1030 videoParam.mfx.TargetUsage, videoParam.AsyncDepth);
1031 hb_log("encqsvInit: GopRefDist %"PRIu16" GopPicSize %"PRIu16" NumRefFrame %"PRIu16"",
1032 videoParam.mfx.GopRefDist, videoParam.mfx.GopPicSize, videoParam.mfx.NumRefFrame);
1033 if (pv->qsv_info->capabilities & HB_QSV_CAP_B_REF_PYRAMID)
1035 hb_log("encqsvInit: BFramesMax %d BRefType %s",
1036 videoParam.mfx.GopRefDist > 1 ?
1037 videoParam.mfx.GopRefDist - 1 : 0,
1038 pv->param.gop.b_pyramid ? "pyramid" : "off");
1040 else
1042 hb_log("encqsvInit: BFramesMax %d",
1043 videoParam.mfx.GopRefDist > 1 ?
1044 videoParam.mfx.GopRefDist - 1 : 0);
1046 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_IB_ADAPT)
1048 if (option2->AdaptiveI != MFX_CODINGOPTION_OFF ||
1049 option2->AdaptiveB != MFX_CODINGOPTION_OFF)
1051 if (videoParam.mfx.GopRefDist > 1)
1053 hb_log("encqsvInit: AdaptiveI %s AdaptiveB %s",
1054 hb_qsv_codingoption_get_name(option2->AdaptiveI),
1055 hb_qsv_codingoption_get_name(option2->AdaptiveB));
1057 else
1059 hb_log("encqsvInit: AdaptiveI %s",
1060 hb_qsv_codingoption_get_name(option2->AdaptiveI));
1064 if (videoParam.mfx.RateControlMethod == MFX_RATECONTROL_CQP)
1066 char qpi[7], qpp[9], qpb[9];
1067 snprintf(qpi, sizeof(qpi), "QPI %"PRIu16"", videoParam.mfx.QPI);
1068 snprintf(qpp, sizeof(qpp), " QPP %"PRIu16"", videoParam.mfx.QPP);
1069 snprintf(qpb, sizeof(qpb), " QPB %"PRIu16"", videoParam.mfx.QPB);
1070 hb_log("encqsvInit: RateControlMethod CQP with %s%s%s", qpi,
1071 videoParam.mfx.GopPicSize > 1 ? qpp : "",
1072 videoParam.mfx.GopRefDist > 1 ? qpb : "");
1074 else
1076 switch (videoParam.mfx.RateControlMethod)
1078 case MFX_RATECONTROL_LA:
1079 hb_log("encqsvInit: RateControlMethod LA TargetKbps %"PRIu16" LookAheadDepth %"PRIu16"",
1080 videoParam.mfx.TargetKbps, option2->LookAheadDepth);
1081 break;
1082 case MFX_RATECONTROL_LA_ICQ:
1083 hb_log("encqsvInit: RateControlMethod LA_ICQ ICQQuality %"PRIu16" LookAheadDepth %"PRIu16"",
1084 videoParam.mfx.ICQQuality, option2->LookAheadDepth);
1085 break;
1086 case MFX_RATECONTROL_ICQ:
1087 hb_log("encqsvInit: RateControlMethod ICQ ICQQuality %"PRIu16"",
1088 videoParam.mfx.ICQQuality);
1089 break;
1090 case MFX_RATECONTROL_CBR:
1091 case MFX_RATECONTROL_VBR:
1092 hb_log("encqsvInit: RateControlMethod %s TargetKbps %"PRIu16" MaxKbps %"PRIu16" BufferSizeInKB %"PRIu16" InitialDelayInKB %"PRIu16"",
1093 videoParam.mfx.RateControlMethod == MFX_RATECONTROL_CBR ? "CBR" : "VBR",
1094 videoParam.mfx.TargetKbps, videoParam.mfx.MaxKbps,
1095 videoParam.mfx.BufferSizeInKB, videoParam.mfx.InitialDelayInKB);
1096 break;
1097 default:
1098 hb_log("encqsvInit: invalid rate control method %"PRIu16"",
1099 videoParam.mfx.RateControlMethod);
1100 return -1;
1103 if ((pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_LA_DOWNS) &&
1104 (videoParam.mfx.RateControlMethod == MFX_RATECONTROL_LA ||
1105 videoParam.mfx.RateControlMethod == MFX_RATECONTROL_LA_ICQ))
1107 switch (option2->LookAheadDS)
1109 case MFX_LOOKAHEAD_DS_UNKNOWN:
1110 hb_log("encqsvInit: LookAheadDS unknown (auto)");
1111 break;
1112 case MFX_LOOKAHEAD_DS_OFF: // default
1113 break;
1114 case MFX_LOOKAHEAD_DS_2x:
1115 hb_log("encqsvInit: LookAheadDS 2x");
1116 break;
1117 case MFX_LOOKAHEAD_DS_4x:
1118 hb_log("encqsvInit: LookAheadDS 4x");
1119 break;
1120 default:
1121 hb_log("encqsvInit: invalid LookAheadDS value 0x%"PRIx16"",
1122 option2->LookAheadDS);
1123 break;
1126 switch (videoParam.mfx.FrameInfo.PicStruct)
1128 case MFX_PICSTRUCT_PROGRESSIVE: // default
1129 break;
1130 case MFX_PICSTRUCT_FIELD_TFF:
1131 hb_log("encqsvInit: PicStruct top field first");
1132 break;
1133 case MFX_PICSTRUCT_FIELD_BFF:
1134 hb_log("encqsvInit: PicStruct bottom field first");
1135 break;
1136 default:
1137 hb_error("encqsvInit: invalid PicStruct value 0x%"PRIx16"",
1138 videoParam.mfx.FrameInfo.PicStruct);
1139 return -1;
1141 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION1)
1143 if (videoParam.mfx.CodecId == MFX_CODEC_AVC)
1145 if (option1->CAVLC != MFX_CODINGOPTION_OFF)
1147 hb_log("encqsvInit: CAVLC %s",
1148 hb_qsv_codingoption_get_name(option1->CAVLC));
1152 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_EXTBRC)
1154 if (option2->ExtBRC != MFX_CODINGOPTION_OFF)
1156 hb_log("encqsvInit: ExtBRC %s",
1157 hb_qsv_codingoption_get_name(option2->ExtBRC));
1160 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_MBBRC)
1162 if (option2->MBBRC != MFX_CODINGOPTION_ON)
1164 hb_log("encqsvInit: MBBRC %s",
1165 hb_qsv_codingoption_get_name(option2->MBBRC));
1168 if (pv->qsv_info->capabilities & HB_QSV_CAP_OPTION2_TRELLIS)
1170 switch (option2->Trellis)
1172 case MFX_TRELLIS_OFF: // default
1173 break;
1174 case MFX_TRELLIS_UNKNOWN:
1175 hb_log("encqsvInit: Trellis unknown (auto)");
1176 break;
1177 default:
1178 hb_log("encqsvInit: Trellis on (%s%s%s)",
1179 (option2->Trellis & MFX_TRELLIS_I) ? "I" : "",
1180 (option2->Trellis & MFX_TRELLIS_P) &&
1181 (videoParam.mfx.GopPicSize > 1) ? "P" : "",
1182 (option2->Trellis & MFX_TRELLIS_B) &&
1183 (videoParam.mfx.GopRefDist > 1) ? "B" : "");
1184 break;
1188 // AsyncDepth has now been set and/or modified by Media SDK
1189 pv->max_async_depth = videoParam.AsyncDepth;
1190 pv->async_depth = 0;
1192 return 0;
1195 void encqsvClose(hb_work_object_t *w)
1197 hb_work_private_t *pv = w->private_data;
1198 mfxVersion version;
1199 int i;
1201 if (pv != NULL && pv->job != NULL && pv->job->qsv.ctx != NULL &&
1202 pv->job->qsv.ctx->is_context_active)
1205 av_qsv_context *qsv_ctx = pv->job->qsv.ctx;
1206 av_qsv_space *qsv_enc_space = pv->job->qsv.ctx->enc_space;
1208 if (qsv_enc_space != NULL)
1210 if (qsv_enc_space->is_init_done)
1212 for (i = av_qsv_list_count(qsv_enc_space->tasks); i > 1; i--)
1214 av_qsv_task *task = av_qsv_list_item(qsv_enc_space->tasks,
1215 i - 1);
1216 if (task != NULL)
1218 if (task->bs != NULL)
1220 av_freep(&task->bs->Data);
1222 av_qsv_list_rem(qsv_enc_space->tasks, task);
1223 av_freep(&task->bs);
1224 av_freep(&task);
1227 av_qsv_list_close(&qsv_enc_space->tasks);
1229 for (i = 0; i < qsv_enc_space->surface_num; i++)
1231 if (pv->is_sys_mem)
1233 av_freep(&qsv_enc_space->p_surfaces[i]->Data.VU);
1234 av_freep(&qsv_enc_space->p_surfaces[i]->Data.Y);
1236 av_freep(&qsv_enc_space->p_surfaces[i]);
1238 qsv_enc_space->surface_num = 0;
1240 for (i = 0; i < qsv_enc_space->sync_num; i++)
1242 av_freep(&qsv_enc_space->p_syncp[i]->p_sync);
1243 av_freep(&qsv_enc_space->p_syncp[i]);
1245 qsv_enc_space->sync_num = 0;
1247 qsv_enc_space->is_init_done = 0;
1250 if (qsv_ctx != NULL)
1252 /* Unload MFX plug-ins */
1253 if (MFXQueryVersion(qsv_ctx->mfx_session, &version) == MFX_ERR_NONE)
1255 hb_qsv_unload_plugins(&pv->loaded_plugins, qsv_ctx->mfx_session, version);
1258 /* QSV context cleanup and MFXClose */
1259 av_qsv_context_clean(qsv_ctx);
1261 if (pv->is_sys_mem)
1263 av_freep(&qsv_ctx);
1268 if (pv != NULL)
1270 if (pv->delayed_processing != NULL)
1272 /* the list is already empty */
1273 hb_list_close(&pv->delayed_processing);
1275 if (pv->sws_context_to_nv12 != NULL)
1277 sws_freeContext(pv->sws_context_to_nv12);
1279 if (pv->list_dts != NULL)
1281 int64_t *item;
1282 while ((item = hb_list_item(pv->list_dts, 0)) != NULL)
1284 hb_list_rem(pv->list_dts, item);
1285 free(item);
1287 hb_list_close(&pv->list_dts);
1289 if (pv->delayed_chapters != NULL)
1291 struct chapter_s *item;
1292 while ((item = hb_list_item(pv->delayed_chapters, 0)) != NULL)
1294 hb_list_rem(pv->delayed_chapters, item);
1295 free(item);
1297 hb_list_close(&pv->delayed_chapters);
1299 if (pv->encoded_frames != NULL)
1301 hb_buffer_t *item;
1302 while ((item = hb_list_item(pv->encoded_frames, 0)) != NULL)
1304 hb_list_rem(pv->encoded_frames, item);
1305 hb_buffer_close(&item);
1307 hb_list_close(&pv->encoded_frames);
1311 free(pv);
1312 w->private_data = NULL;
1315 static void save_chapter(hb_work_private_t *pv, hb_buffer_t *buf)
1318 * Since there may be several frames buffered in the encoder, remember the
1319 * timestamp so when this frame finally pops out of the encoder we'll mark
1320 * its buffer as the start of a chapter.
1322 if (pv->next_chapter_pts == AV_NOPTS_VALUE)
1324 pv->next_chapter_pts = buf->s.start;
1328 * Chapter markers are sometimes so close we can get a new
1329 * one before the previous goes through the encoding queue.
1331 * Dropping markers can cause weird side-effects downstream,
1332 * including but not limited to missing chapters in the
1333 * output, so we need to save it somehow.
1335 struct chapter_s *item = malloc(sizeof(struct chapter_s));
1337 if (item != NULL)
1339 item->start = buf->s.start;
1340 item->index = buf->s.new_chap;
1341 hb_list_add(pv->delayed_chapters, item);
1344 /* don't let 'work_loop' put a chapter mark on the wrong buffer */
1345 buf->s.new_chap = 0;
1348 static void restore_chapter(hb_work_private_t *pv, hb_buffer_t *buf)
1350 /* we're no longer looking for this chapter */
1351 pv->next_chapter_pts = AV_NOPTS_VALUE;
1353 /* get the chapter index from the list */
1354 struct chapter_s *item = hb_list_item(pv->delayed_chapters, 0);
1356 if (item != NULL)
1358 /* we're done with this chapter */
1359 hb_list_rem(pv->delayed_chapters, item);
1360 buf->s.new_chap = item->index;
1361 free(item);
1363 /* we may still have another pending chapter */
1364 item = hb_list_item(pv->delayed_chapters, 0);
1366 if (item != NULL)
1369 * we're looking for this chapter now
1370 * we still need it, don't remove it
1372 pv->next_chapter_pts = item->start;
1377 static void compute_init_delay(hb_work_private_t *pv, mfxBitstream *bs)
1379 if (pv->init_delay == NULL)
1381 return; // not needed or already set
1385 * In the MP4 container, DT(0) = STTS(0) = 0.
1387 * Which gives us:
1388 * CT(0) = CTTS(0) + STTS(0) = CTTS(0) = PTS(0) - DTS(0)
1389 * When DTS(0) < PTS(0), we then have:
1390 * CT(0) > 0 for video, but not audio (breaks A/V sync).
1392 * This is typically solved by writing an edit list shifting
1393 * video samples by the initial delay, PTS(0) - DTS(0).
1395 * See:
1396 * ISO/IEC 14496-12:2008(E), ISO base media file format
1397 * - 8.6.1.2 Decoding Time to Sample Box
1399 if (pv->qsv_info->capabilities & HB_QSV_CAP_MSDK_API_1_6)
1401 /* compute init_delay (in ticks) based on the DTS provided by MSDK. */
1402 int64_t init_delay = bs->TimeStamp - bs->DecodeTimeStamp;
1405 * we also need to know the delay in frames to generate DTS.
1407 * compute it based on the init_delay and average frame duration,
1408 * and account for potential rounding errors due to the timebase.
1410 double avg_frame_dur = ((double)pv->job->vrate.den /
1411 (double)pv->job->vrate.num * 90000.);
1413 pv->bfrm_delay = (init_delay + (avg_frame_dur / 2)) / avg_frame_dur;
1415 if (pv->bfrm_delay < 1 || pv->bfrm_delay > BFRM_DELAY_MAX)
1417 hb_log("compute_init_delay: "
1418 "invalid delay %d (PTS: %"PRIu64", DTS: %"PRId64")",
1419 pv->bfrm_delay, bs->TimeStamp, bs->DecodeTimeStamp);
1421 /* we have B-frames, the frame delay should be at least 1 */
1422 if (pv->bfrm_delay < 1)
1424 mfxStatus sts;
1425 mfxVideoParam videoParam;
1426 mfxSession session = pv->job->qsv.ctx->mfx_session;
1428 memset(&videoParam, 0, sizeof(mfxVideoParam));
1430 sts = MFXVideoENCODE_GetVideoParam(session, &videoParam);
1431 if (sts != MFX_ERR_NONE)
1433 hb_log("compute_init_delay: "
1434 "MFXVideoENCODE_GetVideoParam failed (%d)", sts);
1435 pv->bfrm_delay = 1;
1437 else
1439 /* usually too large, but should cover all cases */
1440 pv->bfrm_delay = FFMIN(pv->frames_in - 1,
1441 videoParam.mfx.GopRefDist - 1);
1445 pv->bfrm_delay = FFMIN(BFRM_DELAY_MAX, pv->bfrm_delay);
1448 pv->init_delay[0] = pv->init_pts[pv->bfrm_delay] - pv->init_pts[0];
1450 else
1453 * we can't get the DTS from MSDK, so we need to generate our own.
1455 * B-pyramid not possible here, so the delay in frames is always 1.
1457 pv->bfrm_delay = 1;
1458 pv->init_delay[0] = pv->init_pts[1] - pv->init_pts[0];
1461 /* This can come in handy */
1462 hb_deep_log(2, "compute_init_delay: %"PRId64" (%d frames)", pv->init_delay[0], pv->bfrm_delay);
1464 /* The delay only needs to be set once. */
1465 pv->init_delay = NULL;
1468 static int qsv_frame_is_key(mfxU16 FrameType)
1470 return ((FrameType & MFX_FRAMETYPE_IDR) ||
1471 (FrameType == MFX_FRAMETYPE_UNKNOWN));
1474 static void qsv_bitstream_slurp(hb_work_private_t *pv, mfxBitstream *bs)
1477 * we need to convert the encoder's Annex B output
1478 * to an MP4-compatible format (ISO/IEC 14496-15).
1480 hb_buffer_t *buf = hb_nal_bitstream_annexb_to_mp4(bs->Data + bs->DataOffset,
1481 bs->DataLength);
1482 if (buf == NULL)
1484 hb_error("encqsv: hb_nal_bitstream_annexb_to_mp4 failed");
1485 goto fail;
1487 bs->DataLength = bs->DataOffset = 0;
1488 bs->MaxLength = pv->job->qsv.ctx->enc_space->p_buf_max_size;
1490 buf->s.frametype = hb_qsv_frametype_xlat(bs->FrameType, &buf->s.flags);
1491 buf->s.start = buf->s.renderOffset = bs->TimeStamp;
1492 buf->s.stop = buf->s.start + get_frame_duration(pv, buf);
1493 buf->s.duration = buf->s.stop - buf->s.start;
1495 /* compute the init_delay before setting the DTS */
1496 compute_init_delay(pv, bs);
1499 * Generate VFR-compatible output DTS based on input PTS.
1501 * Depends on the B-frame delay:
1503 * 0: ipts0, ipts1, ipts2...
1504 * 1: ipts0 - ipts1, ipts1 - ipts1, ipts1, ipts2...
1505 * 2: ipts0 - ipts2, ipts1 - ipts2, ipts2 - ipts2, ipts1...
1506 * ...and so on.
1508 if (pv->bfrm_delay)
1510 if (pv->frames_out <= pv->bfrm_delay)
1512 buf->s.renderOffset = (pv->init_pts[pv->frames_out] -
1513 pv->init_pts[pv->bfrm_delay]);
1515 else
1517 buf->s.renderOffset = hb_qsv_pop_next_dts(pv->list_dts);
1521 /* check if B-pyramid is used even though it's disabled */
1522 if ((pv->param.gop.b_pyramid == 0) &&
1523 (bs->FrameType & MFX_FRAMETYPE_B) &&
1524 (bs->FrameType & MFX_FRAMETYPE_REF))
1526 hb_log("encqsv: BPyramid off not respected (delay: %d)", pv->bfrm_delay);
1528 /* don't pollute the log unnecessarily */
1529 pv->param.gop.b_pyramid = 1;
1532 /* check for PTS < DTS */
1533 if (buf->s.start < buf->s.renderOffset)
1535 hb_log("encqsv: PTS %"PRId64" < DTS %"PRId64" for frame %d with type '%s'",
1536 buf->s.start, buf->s.renderOffset, pv->frames_out + 1,
1537 hb_qsv_frametype_name(bs->FrameType));
1541 * If we have a chapter marker pending and this frame's PTS
1542 * is at or after the marker's PTS, use it as the chapter start.
1544 if (pv->next_chapter_pts != AV_NOPTS_VALUE &&
1545 pv->next_chapter_pts <= buf->s.start &&
1546 qsv_frame_is_key(bs->FrameType))
1548 restore_chapter(pv, buf);
1551 hb_list_add(pv->encoded_frames, buf);
1552 pv->frames_out++;
1553 return;
1555 fail:
1556 *pv->job->done_error = HB_ERROR_UNKNOWN;
1557 *pv->job->die = 1;
1560 static int qsv_enc_work(hb_work_private_t *pv,
1561 av_qsv_list *qsv_atom,
1562 mfxFrameSurface1 *surface)
1564 mfxStatus sts;
1565 av_qsv_context *qsv_ctx = pv->job->qsv.ctx;
1566 av_qsv_space *qsv_enc_space = pv->job->qsv.ctx->enc_space;
1570 int sync_idx = av_qsv_get_free_sync(qsv_enc_space, qsv_ctx);
1571 if (sync_idx == -1)
1573 hb_error("encqsv: av_qsv_get_free_sync failed");
1574 return -1;
1576 av_qsv_task *task = av_qsv_list_item(qsv_enc_space->tasks,
1577 pv->async_depth);
1581 sts = MFXVideoENCODE_EncodeFrameAsync(qsv_ctx->mfx_session,
1582 NULL, surface, task->bs,
1583 qsv_enc_space->p_syncp[sync_idx]->p_sync);
1585 if (sts == MFX_ERR_MORE_DATA || (sts >= MFX_ERR_NONE &&
1586 sts != MFX_WRN_DEVICE_BUSY))
1588 if (surface != NULL && !pv->is_sys_mem)
1590 ff_qsv_atomic_dec(&surface->Data.Locked);
1594 if (sts == MFX_ERR_MORE_DATA)
1596 if (qsv_atom != NULL)
1598 hb_list_add(pv->delayed_processing, qsv_atom);
1600 ff_qsv_atomic_dec(&qsv_enc_space->p_syncp[sync_idx]->in_use);
1601 break;
1603 else if (sts < MFX_ERR_NONE)
1605 hb_error("encqsv: MFXVideoENCODE_EncodeFrameAsync failed (%d)", sts);
1606 return -1;
1608 else if (sts == MFX_WRN_DEVICE_BUSY)
1610 av_qsv_sleep(10); // device is busy, wait then repeat the call
1611 continue;
1613 else
1615 av_qsv_stage *new_stage = av_qsv_stage_init();
1616 new_stage->type = AV_QSV_ENCODE;
1617 new_stage->in.p_surface = surface;
1618 new_stage->out.sync = qsv_enc_space->p_syncp[sync_idx];
1619 new_stage->out.p_bs = task->bs;
1620 task->stage = new_stage;
1621 pv->async_depth++;
1623 if (qsv_atom != NULL)
1625 av_qsv_add_stagee(&qsv_atom, new_stage, HAVE_THREADS);
1627 else
1629 /* encode-only or flushing */
1630 av_qsv_list *new_qsv_atom = av_qsv_list_init(HAVE_THREADS);
1631 av_qsv_add_stagee(&new_qsv_atom, new_stage, HAVE_THREADS);
1632 av_qsv_list_add (qsv_ctx->pipes, new_qsv_atom);
1635 int i = hb_list_count(pv->delayed_processing);
1636 while (--i >= 0)
1638 av_qsv_list *item = hb_list_item(pv->delayed_processing, i);
1640 if (item != NULL)
1642 hb_list_rem(pv->delayed_processing, item);
1643 av_qsv_flush_stages(qsv_ctx->pipes, &item);
1646 break;
1649 ff_qsv_atomic_dec(&qsv_enc_space->p_syncp[sync_idx]->in_use);
1650 break;
1652 while (sts >= MFX_ERR_NONE);
1656 if (pv->async_depth == 0) break;
1658 /* we've done enough asynchronous operations or we're flushing */
1659 if (pv->async_depth >= pv->max_async_depth || surface == NULL)
1661 av_qsv_task *task = av_qsv_list_item(qsv_enc_space->tasks, 0);
1662 pv->async_depth--;
1664 /* perform a sync operation to get the output bitstream */
1665 av_qsv_wait_on_sync(qsv_ctx, task->stage);
1667 if (task->bs->DataLength > 0)
1669 av_qsv_list *pipe = av_qsv_pipe_by_stage(qsv_ctx->pipes,
1670 task->stage);
1671 av_qsv_flush_stages(qsv_ctx->pipes, &pipe);
1673 /* get the encoded frame from the bitstream */
1674 qsv_bitstream_slurp(pv, task->bs);
1676 /* shift for fifo */
1677 if (pv->async_depth)
1679 av_qsv_list_rem(qsv_enc_space->tasks, task);
1680 av_qsv_list_add(qsv_enc_space->tasks, task);
1682 task->stage = NULL;
1686 while (surface == NULL);
1688 while (surface == NULL && sts != MFX_ERR_MORE_DATA);
1690 return 0;
1693 static hb_buffer_t* link_buffer_list(hb_list_t *list)
1695 hb_buffer_t *buf, *prev = NULL, *out = NULL;
1697 while ((buf = hb_list_item(list, 0)) != NULL)
1699 hb_list_rem(list, buf);
1701 if (prev == NULL)
1703 prev = out = buf;
1705 else
1707 prev->next = buf;
1708 prev = buf;
1712 return out;
1715 int encqsvWork(hb_work_object_t *w, hb_buffer_t **buf_in, hb_buffer_t **buf_out)
1717 hb_work_private_t *pv = w->private_data;
1718 hb_buffer_t *in = *buf_in;
1719 hb_job_t *job = pv->job;
1721 while (qsv_enc_init(pv) >= 2)
1723 av_qsv_sleep(1); // encoding not initialized, wait and repeat the call
1726 if (*job->die)
1728 goto fail; // unrecoverable error, don't attempt to encode
1732 * EOF on input. Flush the decoder, then send the
1733 * EOF downstream to let the muxer know we're done.
1735 if (in->s.flags & HB_BUF_FLAG_EOF)
1737 qsv_enc_work(pv, NULL, NULL);
1738 hb_list_add(pv->encoded_frames, in);
1739 *buf_out = link_buffer_list(pv->encoded_frames);
1740 *buf_in = NULL; // don't let 'work_loop' close this buffer
1741 return HB_WORK_DONE;
1744 mfxFrameSurface1 *surface = NULL;
1745 av_qsv_list *qsv_atom = NULL;
1746 av_qsv_context *qsv_ctx = job->qsv.ctx;
1747 av_qsv_space *qsv_enc_space = job->qsv.ctx->enc_space;
1749 if (pv->is_sys_mem)
1751 mfxFrameInfo *info = &pv->param.videoParam->mfx.FrameInfo;
1752 int surface_index = av_qsv_get_free_surface(qsv_enc_space, qsv_ctx, info,
1753 QSV_PART_ANY);
1754 if (surface_index == -1)
1756 hb_error("encqsv: av_qsv_get_free_surface failed");
1757 goto fail;
1760 surface = qsv_enc_space->p_surfaces[surface_index];
1761 qsv_yuv420_to_nv12(pv->sws_context_to_nv12, surface, in);
1763 else
1765 qsv_atom = in->qsv_details.qsv_atom;
1766 surface = av_qsv_get_last_stage(qsv_atom)->out.p_surface;
1769 * QSV decoding fills the QSV context's dts_seq list, we need to
1770 * pop this surface's DTS so dts_seq doesn't grow unnecessarily.
1772 av_qsv_dts_pop(qsv_ctx);
1776 * Debugging code to check that the upstream modules have generated
1777 * a continuous, self-consistent frame stream.
1779 if (pv->last_start > in->s.start)
1781 hb_log("encqsv: input continuity error, "
1782 "last start %"PRId64" start %"PRId64"",
1783 pv->last_start, in->s.start);
1785 pv->last_start = in->s.start;
1787 /* for DTS generation */
1788 if (pv->frames_in <= BFRM_DELAY_MAX)
1790 pv->init_pts[pv->frames_in] = in->s.start;
1792 if (pv->frames_in)
1794 hb_qsv_add_new_dts(pv->list_dts, in->s.start);
1796 pv->frames_in++;
1799 * Chapters have to start with a keyframe, so request one here.
1801 * Using an mfxEncodeCtrl structure to force key frame generation is not
1802 * possible when using a lookahead and frame reordering, so instead do
1803 * the following before encoding the frame attached to the chapter:
1805 * - flush the encoder to encode and retrieve any buffered frames
1807 * - do a hard reset (MFXVideoENCODE_Close, then Init) of
1808 * the encoder to make sure the next frame is a keyframe
1810 * The hard reset ensures encoding resumes with a clean state, avoiding
1811 * miscellaneous hard-to-disagnose issues that may occur when resuming
1812 * an encode after flushing the encoder or using MFXVideoENCODE_Reset.
1814 if (in->s.new_chap > 0 && job->chapter_markers)
1816 mfxStatus sts;
1818 if (qsv_enc_work(pv, NULL, NULL) < 0)
1820 goto fail;
1823 sts = MFXVideoENCODE_Close(qsv_ctx->mfx_session);
1824 if (sts != MFX_ERR_NONE)
1826 hb_error("encqsv: MFXVideoENCODE_Close failed (%d)", sts);
1827 goto fail;
1830 sts = MFXVideoENCODE_Init(qsv_ctx->mfx_session, pv->param.videoParam);
1831 if (sts < MFX_ERR_NONE)
1833 hb_error("encqsv: MFXVideoENCODE_Init failed (%d)", sts);
1834 goto fail;
1837 save_chapter(pv, in);
1841 * If interlaced encoding is requested during encoder initialization,
1842 * but the input mfxFrameSurface1 is flagged as progressive here,
1843 * the output bitstream will be progressive (according to MediaInfo).
1845 * Assume the user knows what he's doing (say he is e.g. encoding a
1846 * progressive-flagged source using interlaced compression - he may
1847 * well have a good reason to do so; mis-flagged sources do exist).
1849 surface->Info.PicStruct = pv->param.videoParam->mfx.FrameInfo.PicStruct;
1850 surface->Data.TimeStamp = in->s.start;
1851 save_frame_duration(pv, in);
1854 * Now that the input surface is setup, we can encode it.
1856 if (qsv_enc_work(pv, qsv_atom, surface) < 0)
1858 goto fail;
1861 *buf_out = link_buffer_list(pv->encoded_frames);
1862 return HB_WORK_OK;
1864 fail:
1865 if (*job->done_error == HB_ERROR_NONE)
1867 *job->done_error = HB_ERROR_UNKNOWN;
1869 *job->die = 1;
1870 *buf_out = NULL;
1871 return HB_WORK_ERROR;
1874 #endif // USE_QSV