X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fv4l2_m2m_enc.c;h=474e6bef897756a842dfb6788539fdb317aaf48b;hb=9f6a06d9271a11781717fd0b134db2bcd716508e;hp=636e1a96dde014d1d32c04655860a7960bf3701a;hpb=c0a647644f2703e1da980dcf988cefd81528d8c9;p=ffmpeg diff --git a/libavcodec/v4l2_m2m_enc.c b/libavcodec/v4l2_m2m_enc.c index 636e1a96dde..474e6bef897 100644 --- a/libavcodec/v4l2_m2m_enc.c +++ b/libavcodec/v4l2_m2m_enc.c @@ -58,10 +58,10 @@ static inline void v4l2_set_ext_ctrl(V4L2m2mContext *s, unsigned int id, signed /* set ctrl*/ ctrl.value = value; - ctrl.id = id ; + ctrl.id = id; if (ioctl(s->fd, VIDIOC_S_EXT_CTRLS, &ctrls) < 0) - av_log(s->avctx, AV_LOG_WARNING, "Failed to set %s\n", name); + av_log(s->avctx, AV_LOG_WARNING, "Failed to set %s: %s\n", name, strerror(errno)); else av_log(s->avctx, AV_LOG_DEBUG, "Encoder: %s = %d\n", name, value); } @@ -245,6 +245,11 @@ static int v4l2_send_frame(AVCodecContext *avctx, const AVFrame *frame) V4L2m2mContext *s = ((V4L2m2mPriv*)avctx->priv_data)->context; V4L2Context *const output = &s->output; +#ifdef V4L2_CID_MPEG_VIDEO_FORCE_KEY_FRAME + if (frame && frame->pict_type == AV_PICTURE_TYPE_I) + v4l2_set_ext_ctrl(s, MPEG_CID(FORCE_KEY_FRAME), 0, "force key frame"); +#endif + return ff_v4l2_context_enqueue_frame(output, frame); } @@ -261,7 +266,7 @@ static int v4l2_receive_packet(AVCodecContext *avctx, AVPacket *avpkt) if (!output->streamon) { ret = ff_v4l2_context_set_status(output, VIDIOC_STREAMON); if (ret) { - av_log(avctx, AV_LOG_ERROR, "VIDIOC_STREAMOFF failed on output context\n"); + av_log(avctx, AV_LOG_ERROR, "VIDIOC_STREAMON failed on output context\n"); return ret; } } @@ -282,9 +287,10 @@ static av_cold int v4l2_encode_init(AVCodecContext *avctx) { V4L2Context *capture, *output; V4L2m2mContext *s; + V4L2m2mPriv *priv = avctx->priv_data; int ret; - ret = ff_v4l2_m2m_create_context(avctx, &s); + ret = ff_v4l2_m2m_create_context(priv, &s); if (ret < 0) return ret; @@ -303,15 +309,21 @@ static av_cold int v4l2_encode_init(AVCodecContext *avctx) capture->av_codec_id = avctx->codec_id; capture->av_pix_fmt = AV_PIX_FMT_NONE; - ret = ff_v4l2_m2m_codec_init(avctx); + ret = ff_v4l2_m2m_codec_init(priv); if (ret) { av_log(avctx, AV_LOG_ERROR, "can't configure encoder\n"); return ret; } + s->avctx = avctx; return v4l2_prepare_encoder(s); } +static av_cold int v4l2_encode_close(AVCodecContext *avctx) +{ + return ff_v4l2_m2m_codec_end(avctx->priv_data); +} + #define OFFSET(x) offsetof(V4L2m2mPriv, x) #define FLAGS AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_ENCODING_PARAM @@ -322,28 +334,30 @@ static const AVOption options[] = { { NULL }, }; +#define M2MENC_CLASS(NAME) \ + static const AVClass v4l2_m2m_ ## NAME ## _enc_class = { \ + .class_name = #NAME "_v4l2m2m_encoder", \ + .item_name = av_default_item_name, \ + .option = options, \ + .version = LIBAVUTIL_VERSION_INT, \ + }; + #define M2MENC(NAME, LONGNAME, CODEC) \ -static const AVClass v4l2_m2m_ ## NAME ## _enc_class = {\ - .class_name = #NAME "_v4l2_m2m_encoder",\ - .item_name = av_default_item_name,\ - .option = options,\ - .version = LIBAVUTIL_VERSION_INT,\ -};\ -\ -AVCodec ff_ ## NAME ## _v4l2m2m_encoder = { \ - .name = #NAME "_v4l2m2m" ,\ - .long_name = NULL_IF_CONFIG_SMALL("V4L2 mem2mem " LONGNAME " encoder wrapper"),\ - .type = AVMEDIA_TYPE_VIDEO,\ - .id = CODEC ,\ - .priv_data_size = sizeof(V4L2m2mPriv),\ - .priv_class = &v4l2_m2m_ ## NAME ##_enc_class,\ - .init = v4l2_encode_init,\ - .send_frame = v4l2_send_frame,\ - .receive_packet = v4l2_receive_packet,\ - .close = ff_v4l2_m2m_codec_end,\ - .capabilities = AV_CODEC_CAP_HARDWARE | AV_CODEC_CAP_DELAY, \ - .wrapper_name = "v4l2m2m", \ -}; + M2MENC_CLASS(NAME) \ + AVCodec ff_ ## NAME ## _v4l2m2m_encoder = { \ + .name = #NAME "_v4l2m2m" , \ + .long_name = NULL_IF_CONFIG_SMALL("V4L2 mem2mem " LONGNAME " encoder wrapper"), \ + .type = AVMEDIA_TYPE_VIDEO, \ + .id = CODEC , \ + .priv_data_size = sizeof(V4L2m2mPriv), \ + .priv_class = &v4l2_m2m_ ## NAME ##_enc_class, \ + .init = v4l2_encode_init, \ + .send_frame = v4l2_send_frame, \ + .receive_packet = v4l2_receive_packet, \ + .close = v4l2_encode_close, \ + .capabilities = AV_CODEC_CAP_HARDWARE | AV_CODEC_CAP_DELAY, \ + .wrapper_name = "v4l2m2m", \ + }; M2MENC(mpeg4,"MPEG4", AV_CODEC_ID_MPEG4); M2MENC(h263, "H.263", AV_CODEC_ID_H263);