1cabdff1aSopenharmony_ci/*
2cabdff1aSopenharmony_ci * Generic DCT based hybrid video encoder
3cabdff1aSopenharmony_ci * Copyright (c) 2000, 2001, 2002 Fabrice Bellard
4cabdff1aSopenharmony_ci * Copyright (c) 2002-2004 Michael Niedermayer
5cabdff1aSopenharmony_ci *
6cabdff1aSopenharmony_ci * This file is part of FFmpeg.
7cabdff1aSopenharmony_ci *
8cabdff1aSopenharmony_ci * FFmpeg is free software; you can redistribute it and/or
9cabdff1aSopenharmony_ci * modify it under the terms of the GNU Lesser General Public
10cabdff1aSopenharmony_ci * License as published by the Free Software Foundation; either
11cabdff1aSopenharmony_ci * version 2.1 of the License, or (at your option) any later version.
12cabdff1aSopenharmony_ci *
13cabdff1aSopenharmony_ci * FFmpeg is distributed in the hope that it will be useful,
14cabdff1aSopenharmony_ci * but WITHOUT ANY WARRANTY; without even the implied warranty of
15cabdff1aSopenharmony_ci * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16cabdff1aSopenharmony_ci * Lesser General Public License for more details.
17cabdff1aSopenharmony_ci *
18cabdff1aSopenharmony_ci * You should have received a copy of the GNU Lesser General Public
19cabdff1aSopenharmony_ci * License along with FFmpeg; if not, write to the Free Software
20cabdff1aSopenharmony_ci * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21cabdff1aSopenharmony_ci */
22cabdff1aSopenharmony_ci
23cabdff1aSopenharmony_ci/**
24cabdff1aSopenharmony_ci * @file
25cabdff1aSopenharmony_ci * mpegvideo header.
26cabdff1aSopenharmony_ci */
27cabdff1aSopenharmony_ci
28cabdff1aSopenharmony_ci#ifndef AVCODEC_MPEGVIDEOENC_H
29cabdff1aSopenharmony_ci#define AVCODEC_MPEGVIDEOENC_H
30cabdff1aSopenharmony_ci
31cabdff1aSopenharmony_ci#include <float.h>
32cabdff1aSopenharmony_ci
33cabdff1aSopenharmony_ci#include "libavutil/opt.h"
34cabdff1aSopenharmony_ci#include "mpegvideo.h"
35cabdff1aSopenharmony_ci
36cabdff1aSopenharmony_ci#define UNI_AC_ENC_INDEX(run,level) ((run)*128 + (level))
37cabdff1aSopenharmony_ci
38cabdff1aSopenharmony_ci/* mpegvideo_enc common options */
39cabdff1aSopenharmony_ci#define FF_MPV_FLAG_SKIP_RD      0x0001
40cabdff1aSopenharmony_ci#define FF_MPV_FLAG_STRICT_GOP   0x0002
41cabdff1aSopenharmony_ci#define FF_MPV_FLAG_QP_RD        0x0004
42cabdff1aSopenharmony_ci#define FF_MPV_FLAG_CBP_RD       0x0008
43cabdff1aSopenharmony_ci#define FF_MPV_FLAG_NAQ          0x0010
44cabdff1aSopenharmony_ci#define FF_MPV_FLAG_MV0          0x0020
45cabdff1aSopenharmony_ci
46cabdff1aSopenharmony_ci#define FF_MPV_OPT_CMP_FUNC \
47cabdff1aSopenharmony_ci{ "sad",    "Sum of absolute differences, fast", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_SAD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
48cabdff1aSopenharmony_ci{ "sse",    "Sum of squared errors", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_SSE }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
49cabdff1aSopenharmony_ci{ "satd",   "Sum of absolute Hadamard transformed differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_SATD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
50cabdff1aSopenharmony_ci{ "dct",    "Sum of absolute DCT transformed differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCT }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
51cabdff1aSopenharmony_ci{ "psnr",   "Sum of squared quantization errors, low quality", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_PSNR }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
52cabdff1aSopenharmony_ci{ "bit",    "Number of bits needed for the block", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_BIT }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
53cabdff1aSopenharmony_ci{ "rd",     "Rate distortion optimal, slow", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_RD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
54cabdff1aSopenharmony_ci{ "zero",   "Zero", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_ZERO }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
55cabdff1aSopenharmony_ci{ "vsad",   "Sum of absolute vertical differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_VSAD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
56cabdff1aSopenharmony_ci{ "vsse",   "Sum of squared vertical differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_VSSE }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
57cabdff1aSopenharmony_ci{ "nsse",   "Noise preserving sum of squared differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_NSSE }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
58cabdff1aSopenharmony_ci{ "dct264", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCT264 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
59cabdff1aSopenharmony_ci{ "dctmax", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCTMAX }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
60cabdff1aSopenharmony_ci{ "chroma", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_CHROMA }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
61cabdff1aSopenharmony_ci{ "msad",   "Sum of absolute differences, median predicted", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_MEDIAN_SAD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }
62cabdff1aSopenharmony_ci
63cabdff1aSopenharmony_ci#define FF_MPV_OFFSET(x) offsetof(MpegEncContext, x)
64cabdff1aSopenharmony_ci#define FF_MPV_OPT_FLAGS (AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_ENCODING_PARAM)
65cabdff1aSopenharmony_ci#define FF_MPV_COMMON_OPTS \
66cabdff1aSopenharmony_ciFF_MPV_OPT_CMP_FUNC, \
67cabdff1aSopenharmony_ci{ "mpv_flags",      "Flags common for all mpegvideo-based encoders.", FF_MPV_OFFSET(mpv_flags), AV_OPT_TYPE_FLAGS, { .i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "mpv_flags" },\
68cabdff1aSopenharmony_ci{ "skip_rd",        "RD optimal MB level residual skipping", 0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_SKIP_RD },    0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
69cabdff1aSopenharmony_ci{ "strict_gop",     "Strictly enforce gop size",             0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_STRICT_GOP }, 0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
70cabdff1aSopenharmony_ci{ "qp_rd",          "Use rate distortion optimization for qp selection", 0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_QP_RD },  0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
71cabdff1aSopenharmony_ci{ "cbp_rd",         "use rate distortion optimization for CBP",          0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_CBP_RD }, 0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
72cabdff1aSopenharmony_ci{ "naq",            "normalize adaptive quantization",                   0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_NAQ },    0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
73cabdff1aSopenharmony_ci{ "mv0",            "always try a mb with mv=<0,0>",                     0, AV_OPT_TYPE_CONST, { .i64 = FF_MPV_FLAG_MV0 },    0, 0, FF_MPV_OPT_FLAGS, "mpv_flags" },\
74cabdff1aSopenharmony_ci{ "luma_elim_threshold",   "single coefficient elimination threshold for luminance (negative values also consider dc coefficient)",\
75cabdff1aSopenharmony_ci                                                                      FF_MPV_OFFSET(luma_elim_threshold), AV_OPT_TYPE_INT, { .i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS },\
76cabdff1aSopenharmony_ci{ "chroma_elim_threshold", "single coefficient elimination threshold for chrominance (negative values also consider dc coefficient)",\
77cabdff1aSopenharmony_ci                                                                      FF_MPV_OFFSET(chroma_elim_threshold), AV_OPT_TYPE_INT, { .i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS },\
78cabdff1aSopenharmony_ci{ "quantizer_noise_shaping", NULL,                                  FF_MPV_OFFSET(quantizer_noise_shaping), AV_OPT_TYPE_INT, { .i64 = 0 },       0, INT_MAX, FF_MPV_OPT_FLAGS },\
79cabdff1aSopenharmony_ci{ "error_rate", "Simulate errors in the bitstream to test error concealment.",                                                                                                  \
80cabdff1aSopenharmony_ci                                                                    FF_MPV_OFFSET(error_rate),              AV_OPT_TYPE_INT, { .i64 = 0 },       0, INT_MAX, FF_MPV_OPT_FLAGS },\
81cabdff1aSopenharmony_ci{"qsquish", "how to keep quantizer between qmin and qmax (0 = clip, 1 = use differentiable function)",                                                                          \
82cabdff1aSopenharmony_ci                                                                    FF_MPV_OFFSET(rc_qsquish), AV_OPT_TYPE_FLOAT, {.dbl = 0 }, 0, 99, FF_MPV_OPT_FLAGS},                        \
83cabdff1aSopenharmony_ci{"rc_qmod_amp", "experimental quantizer modulation",                FF_MPV_OFFSET(rc_qmod_amp), AV_OPT_TYPE_FLOAT, {.dbl = 0 }, -FLT_MAX, FLT_MAX, FF_MPV_OPT_FLAGS},           \
84cabdff1aSopenharmony_ci{"rc_qmod_freq", "experimental quantizer modulation",               FF_MPV_OFFSET(rc_qmod_freq), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS},             \
85cabdff1aSopenharmony_ci{"rc_eq", "Set rate control equation. When computing the expression, besides the standard functions "                                                                           \
86cabdff1aSopenharmony_ci          "defined in the section 'Expression Evaluation', the following functions are available: "                                                                             \
87cabdff1aSopenharmony_ci          "bits2qp(bits), qp2bits(qp). Also the following constants are available: iTex pTex tex mv "                                                                           \
88cabdff1aSopenharmony_ci          "fCode iCount mcVar var isI isP isB avgQP qComp avgIITex avgPITex avgPPTex avgBPTex avgTex.",                                                                         \
89cabdff1aSopenharmony_ci                                                                    FF_MPV_OFFSET(rc_eq), AV_OPT_TYPE_STRING,                           .flags = FF_MPV_OPT_FLAGS },            \
90cabdff1aSopenharmony_ci{"rc_init_cplx", "initial complexity for 1-pass encoding",          FF_MPV_OFFSET(rc_initial_cplx), AV_OPT_TYPE_FLOAT, {.dbl = 0 }, -FLT_MAX, FLT_MAX, FF_MPV_OPT_FLAGS},       \
91cabdff1aSopenharmony_ci{"rc_buf_aggressivity", "currently useless",                        FF_MPV_OFFSET(rc_buffer_aggressivity), AV_OPT_TYPE_FLOAT, {.dbl = 1.0 }, -FLT_MAX, FLT_MAX, FF_MPV_OPT_FLAGS}, \
92cabdff1aSopenharmony_ci{"border_mask", "increase the quantizer for macroblocks close to borders", FF_MPV_OFFSET(border_masking), AV_OPT_TYPE_FLOAT, {.dbl = 0 }, -FLT_MAX, FLT_MAX, FF_MPV_OPT_FLAGS},    \
93cabdff1aSopenharmony_ci{"lmin", "minimum Lagrange factor (VBR)",                           FF_MPV_OFFSET(lmin), AV_OPT_TYPE_INT, {.i64 =  2*FF_QP2LAMBDA }, 0, INT_MAX, FF_MPV_OPT_FLAGS },            \
94cabdff1aSopenharmony_ci{"lmax", "maximum Lagrange factor (VBR)",                           FF_MPV_OFFSET(lmax), AV_OPT_TYPE_INT, {.i64 = 31*FF_QP2LAMBDA }, 0, INT_MAX, FF_MPV_OPT_FLAGS },            \
95cabdff1aSopenharmony_ci{"skip_threshold", "Frame skip threshold",                          FF_MPV_OFFSET(frame_skip_threshold), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
96cabdff1aSopenharmony_ci{"skip_factor", "Frame skip factor",                                FF_MPV_OFFSET(frame_skip_factor), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
97cabdff1aSopenharmony_ci{"skip_exp", "Frame skip exponent",                                 FF_MPV_OFFSET(frame_skip_exp), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
98cabdff1aSopenharmony_ci{"skip_cmp", "Frame skip compare function",                         FF_MPV_OFFSET(frame_skip_cmp), AV_OPT_TYPE_INT, {.i64 = FF_CMP_DCTMAX }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
99cabdff1aSopenharmony_ci{"sc_threshold", "Scene change threshold",                          FF_MPV_OFFSET(scenechange_threshold), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
100cabdff1aSopenharmony_ci{"noise_reduction", "Noise reduction",                              FF_MPV_OFFSET(noise_reduction), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
101cabdff1aSopenharmony_ci{"ps", "RTP payload size in bytes",                             FF_MPV_OFFSET(rtp_payload_size), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
102cabdff1aSopenharmony_ci
103cabdff1aSopenharmony_ci#define FF_MPV_COMMON_BFRAME_OPTS \
104cabdff1aSopenharmony_ci{"b_strategy", "Strategy to choose between I/P/B-frames",      FF_MPV_OFFSET(b_frame_strategy), AV_OPT_TYPE_INT, {.i64 = 0 }, 0, 2, FF_MPV_OPT_FLAGS }, \
105cabdff1aSopenharmony_ci{"b_sensitivity", "Adjust sensitivity of b_frame_strategy 1",  FF_MPV_OFFSET(b_sensitivity), AV_OPT_TYPE_INT, {.i64 = 40 }, 1, INT_MAX, FF_MPV_OPT_FLAGS }, \
106cabdff1aSopenharmony_ci{"brd_scale", "Downscale frames for dynamic B-frame decision", FF_MPV_OFFSET(brd_scale), AV_OPT_TYPE_INT, {.i64 = 0 }, 0, 3, FF_MPV_OPT_FLAGS },
107cabdff1aSopenharmony_ci
108cabdff1aSopenharmony_ci#define FF_MPV_COMMON_MOTION_EST_OPTS \
109cabdff1aSopenharmony_ci{"motion_est", "motion estimation algorithm",                       FF_MPV_OFFSET(motion_est), AV_OPT_TYPE_INT, {.i64 = FF_ME_EPZS }, FF_ME_ZERO, FF_ME_XONE, FF_MPV_OPT_FLAGS, "motion_est" },   \
110cabdff1aSopenharmony_ci{ "zero", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = FF_ME_ZERO }, 0, 0, FF_MPV_OPT_FLAGS, "motion_est" }, \
111cabdff1aSopenharmony_ci{ "epzs", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = FF_ME_EPZS }, 0, 0, FF_MPV_OPT_FLAGS, "motion_est" }, \
112cabdff1aSopenharmony_ci{ "xone", NULL, 0, AV_OPT_TYPE_CONST, { .i64 = FF_ME_XONE }, 0, 0, FF_MPV_OPT_FLAGS, "motion_est" }, \
113cabdff1aSopenharmony_ci{"mepc", "Motion estimation bitrate penalty compensation (1.0 = 256)", FF_MPV_OFFSET(me_penalty_compensation), AV_OPT_TYPE_INT, {.i64 = 256 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
114cabdff1aSopenharmony_ci{"mepre", "pre motion estimation", FF_MPV_OFFSET(me_pre), AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS }, \
115cabdff1aSopenharmony_ci{"intra_penalty", "Penalty for intra blocks in block decision", FF_MPV_OFFSET(intra_penalty), AV_OPT_TYPE_INT, {.i64 = 0 }, 0, INT_MAX/2, FF_MPV_OPT_FLAGS }, \
116cabdff1aSopenharmony_ci
117cabdff1aSopenharmony_ciextern const AVClass ff_mpv_enc_class;
118cabdff1aSopenharmony_ci
119cabdff1aSopenharmony_ciint ff_mpv_encode_init(AVCodecContext *avctx);
120cabdff1aSopenharmony_civoid ff_mpv_encode_init_x86(MpegEncContext *s);
121cabdff1aSopenharmony_ci
122cabdff1aSopenharmony_ciint ff_mpv_encode_end(AVCodecContext *avctx);
123cabdff1aSopenharmony_ciint ff_mpv_encode_picture(AVCodecContext *avctx, AVPacket *pkt,
124cabdff1aSopenharmony_ci                          const AVFrame *frame, int *got_packet);
125cabdff1aSopenharmony_ciint ff_mpv_reallocate_putbitbuffer(MpegEncContext *s, size_t threshold, size_t size_increase);
126cabdff1aSopenharmony_ci
127cabdff1aSopenharmony_civoid ff_write_quant_matrix(PutBitContext *pb, uint16_t *matrix);
128cabdff1aSopenharmony_ci
129cabdff1aSopenharmony_ciint ff_dct_encode_init(MpegEncContext *s);
130cabdff1aSopenharmony_civoid ff_dct_encode_init_x86(MpegEncContext *s);
131cabdff1aSopenharmony_ci
132cabdff1aSopenharmony_ciint ff_dct_quantize_c(MpegEncContext *s, int16_t *block, int n, int qscale, int *overflow);
133cabdff1aSopenharmony_civoid ff_convert_matrix(MpegEncContext *s, int (*qmat)[64], uint16_t (*qmat16)[2][64],
134cabdff1aSopenharmony_ci                       const uint16_t *quant_matrix, int bias, int qmin, int qmax, int intra);
135cabdff1aSopenharmony_ci
136cabdff1aSopenharmony_civoid ff_block_permute(int16_t *block, uint8_t *permutation,
137cabdff1aSopenharmony_ci                      const uint8_t *scantable, int last);
138cabdff1aSopenharmony_ci
139cabdff1aSopenharmony_cistatic inline int get_bits_diff(MpegEncContext *s)
140cabdff1aSopenharmony_ci{
141cabdff1aSopenharmony_ci    const int bits = put_bits_count(&s->pb);
142cabdff1aSopenharmony_ci    const int last = s->last_bits;
143cabdff1aSopenharmony_ci
144cabdff1aSopenharmony_ci    s->last_bits = bits;
145cabdff1aSopenharmony_ci
146cabdff1aSopenharmony_ci    return bits - last;
147cabdff1aSopenharmony_ci}
148cabdff1aSopenharmony_ci
149cabdff1aSopenharmony_ci#endif
150