Merge commit '772c87c5a658f36d7c0612f5da583fc2bfa54f79'
authorHendrik Leppkes <h.leppkes@gmail.com>
Thu, 22 Oct 2015 13:46:52 +0000 (15:46 +0200)
committerHendrik Leppkes <h.leppkes@gmail.com>
Thu, 22 Oct 2015 13:46:52 +0000 (15:46 +0200)
* commit '772c87c5a658f36d7c0612f5da583fc2bfa54f79':
  qsvenc: support passing arbitrary external buffers to the encoder

Merged-by: Hendrik Leppkes <h.leppkes@gmail.com>
1  2 
libavcodec/qsvenc.c
libavcodec/qsvenc.h

@@@ -157,29 -134,7 +157,27 @@@ static int init_video_param(AVCodecCont
          q->extco.CAVLC                = avctx->coder_type == FF_CODER_TYPE_VLC ?
                                          MFX_CODINGOPTION_ON : MFX_CODINGOPTION_UNKNOWN;
  
-         q->extparam[0] = (mfxExtBuffer *)&q->extco;
 +        q->extco.PicTimingSEI         = q->pic_timing_sei ?
 +                                        MFX_CODINGOPTION_ON : MFX_CODINGOPTION_UNKNOWN;
 +
-         q->extparam[1] = (mfxExtBuffer *)&q->extco2;
+         q->extparam_internal[0] = (mfxExtBuffer *)&q->extco;
 +
 +#if QSV_VERSION_ATLEAST(1,6)
 +        q->extco2.Header.BufferId      = MFX_EXTBUFF_CODING_OPTION2;
 +        q->extco2.Header.BufferSz      = sizeof(q->extco2);
 +
 +#if QSV_VERSION_ATLEAST(1,7)
 +        // valid value range is from 10 to 100 inclusive
 +        // to instruct the encoder to use the default value this should be set to zero
 +        q->extco2.LookAheadDepth        = q->look_ahead_depth != 0 ? FFMAX(10, q->look_ahead_depth) : 0;
 +#endif
 +#if QSV_VERSION_ATLEAST(1,8)
 +        q->extco2.LookAheadDS           = q->look_ahead_downsampling;
 +#endif
 +
-         q->param.ExtParam    = q->extparam;
-         q->param.NumExtParam = FF_ARRAY_ELEMS(q->extparam);
++        q->extparam_internal[1] = (mfxExtBuffer *)&q->extco2;
 +
 +#endif
      }
  
      return 0;
@@@ -278,10 -225,37 +276,39 @@@ int ff_qsv_enc_init(AVCodecContext *avc
          return ff_qsv_error(ret);
      }
  
+     if (avctx->hwaccel_context) {
+         AVQSVContext *qsv = avctx->hwaccel_context;
+         int i, j;
+         q->extparam = av_mallocz_array(qsv->nb_ext_buffers + FF_ARRAY_ELEMS(q->extparam_internal),
+                                        sizeof(*q->extparam));
+         if (!q->extparam)
+             return AVERROR(ENOMEM);
+         q->param.ExtParam = q->extparam;
+         for (i = 0; i < qsv->nb_ext_buffers; i++)
+             q->param.ExtParam[i] = qsv->ext_buffers[i];
+         q->param.NumExtParam = qsv->nb_ext_buffers;
+         for (i = 0; i < FF_ARRAY_ELEMS(q->extparam_internal); i++) {
+             for (j = 0; j < qsv->nb_ext_buffers; j++) {
+                 if (qsv->ext_buffers[j]->BufferId == q->extparam_internal[i]->BufferId)
+                     break;
+             }
+             if (j < qsv->nb_ext_buffers)
+                 continue;
+             q->param.ExtParam[q->param.NumExtParam++] = q->extparam_internal[i];
+         }
+     } else {
+         q->param.ExtParam    = q->extparam_internal;
+         q->param.NumExtParam = FF_ARRAY_ELEMS(q->extparam_internal);
+     }
      ret = MFXVideoENCODE_Init(q->session, &q->param);
 -    if (ret < 0) {
 +    if (MFX_WRN_PARTIAL_ACCELERATION==ret) {
 +        av_log(avctx, AV_LOG_WARNING, "Encoder will work with partial HW acceleration\n");
 +    } else if (ret < 0) {
          av_log(avctx, AV_LOG_ERROR, "Error initializing the encoder\n");
          return ff_qsv_error(ret);
      }
@@@ -50,12 -49,8 +50,13 @@@ typedef struct QSVEncContext 
      mfxFrameAllocRequest req;
  
      mfxExtCodingOption  extco;
-     mfxExtBuffer *extparam[2];
 +#if QSV_VERSION_ATLEAST(1,6)
 +    mfxExtCodingOption2 extco2;
-     mfxExtBuffer *extparam[1];
++    mfxExtBuffer  *extparam_internal[2];
 +#else
+     mfxExtBuffer  *extparam_internal[1];
 +#endif
+     mfxExtBuffer **extparam;
  
      AVFifoBuffer *async_fifo;