1*fb1b10abSAndroid Build Coastguard Worker /*
2*fb1b10abSAndroid Build Coastguard Worker * Copyright (c) 2010 The WebM project authors. All Rights Reserved.
3*fb1b10abSAndroid Build Coastguard Worker *
4*fb1b10abSAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license
5*fb1b10abSAndroid Build Coastguard Worker * that can be found in the LICENSE file in the root of the source
6*fb1b10abSAndroid Build Coastguard Worker * tree. An additional intellectual property rights grant can be found
7*fb1b10abSAndroid Build Coastguard Worker * in the file PATENTS. All contributing project authors may
8*fb1b10abSAndroid Build Coastguard Worker * be found in the AUTHORS file in the root of the source tree.
9*fb1b10abSAndroid Build Coastguard Worker */
10*fb1b10abSAndroid Build Coastguard Worker
11*fb1b10abSAndroid Build Coastguard Worker #include <limits.h>
12*fb1b10abSAndroid Build Coastguard Worker #include <stdint.h>
13*fb1b10abSAndroid Build Coastguard Worker #include <stdlib.h>
14*fb1b10abSAndroid Build Coastguard Worker #include <string.h>
15*fb1b10abSAndroid Build Coastguard Worker
16*fb1b10abSAndroid Build Coastguard Worker #include "./vpx_config.h"
17*fb1b10abSAndroid Build Coastguard Worker #include "./vp8_rtcd.h"
18*fb1b10abSAndroid Build Coastguard Worker #include "./vpx_dsp_rtcd.h"
19*fb1b10abSAndroid Build Coastguard Worker #include "./vpx_scale_rtcd.h"
20*fb1b10abSAndroid Build Coastguard Worker #include "vpx/vpx_encoder.h"
21*fb1b10abSAndroid Build Coastguard Worker #include "vpx/internal/vpx_codec_internal.h"
22*fb1b10abSAndroid Build Coastguard Worker #include "vpx_version.h"
23*fb1b10abSAndroid Build Coastguard Worker #include "vpx_mem/vpx_mem.h"
24*fb1b10abSAndroid Build Coastguard Worker #include "vpx_ports/static_assert.h"
25*fb1b10abSAndroid Build Coastguard Worker #include "vpx_ports/system_state.h"
26*fb1b10abSAndroid Build Coastguard Worker #include "vpx_util/vpx_timestamp.h"
27*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTITHREAD
28*fb1b10abSAndroid Build Coastguard Worker #include "vp8/encoder/ethreading.h"
29*fb1b10abSAndroid Build Coastguard Worker #endif
30*fb1b10abSAndroid Build Coastguard Worker #include "vp8/encoder/onyx_int.h"
31*fb1b10abSAndroid Build Coastguard Worker #include "vpx/vp8cx.h"
32*fb1b10abSAndroid Build Coastguard Worker #include "vp8/encoder/firstpass.h"
33*fb1b10abSAndroid Build Coastguard Worker #include "vp8/common/onyx.h"
34*fb1b10abSAndroid Build Coastguard Worker #include "vp8/common/common.h"
35*fb1b10abSAndroid Build Coastguard Worker
36*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg {
37*fb1b10abSAndroid Build Coastguard Worker struct vpx_codec_pkt_list *pkt_list;
38*fb1b10abSAndroid Build Coastguard Worker int cpu_used; /** available cpu percentage in 1/16*/
39*fb1b10abSAndroid Build Coastguard Worker /** if encoder decides to uses alternate reference frame */
40*fb1b10abSAndroid Build Coastguard Worker unsigned int enable_auto_alt_ref;
41*fb1b10abSAndroid Build Coastguard Worker unsigned int noise_sensitivity;
42*fb1b10abSAndroid Build Coastguard Worker unsigned int Sharpness;
43*fb1b10abSAndroid Build Coastguard Worker unsigned int static_thresh;
44*fb1b10abSAndroid Build Coastguard Worker unsigned int token_partitions;
45*fb1b10abSAndroid Build Coastguard Worker unsigned int arnr_max_frames; /* alt_ref Noise Reduction Max Frame Count */
46*fb1b10abSAndroid Build Coastguard Worker unsigned int arnr_strength; /* alt_ref Noise Reduction Strength */
47*fb1b10abSAndroid Build Coastguard Worker unsigned int arnr_type; /* alt_ref filter type */
48*fb1b10abSAndroid Build Coastguard Worker vp8e_tuning tuning;
49*fb1b10abSAndroid Build Coastguard Worker unsigned int cq_level; /* constrained quality level */
50*fb1b10abSAndroid Build Coastguard Worker unsigned int rc_max_intra_bitrate_pct;
51*fb1b10abSAndroid Build Coastguard Worker unsigned int gf_cbr_boost_pct;
52*fb1b10abSAndroid Build Coastguard Worker unsigned int screen_content_mode;
53*fb1b10abSAndroid Build Coastguard Worker };
54*fb1b10abSAndroid Build Coastguard Worker
55*fb1b10abSAndroid Build Coastguard Worker static struct vp8_extracfg default_extracfg = {
56*fb1b10abSAndroid Build Coastguard Worker NULL,
57*fb1b10abSAndroid Build Coastguard Worker #if !(CONFIG_REALTIME_ONLY)
58*fb1b10abSAndroid Build Coastguard Worker 0, /* cpu_used */
59*fb1b10abSAndroid Build Coastguard Worker #else
60*fb1b10abSAndroid Build Coastguard Worker 4, /* cpu_used */
61*fb1b10abSAndroid Build Coastguard Worker #endif
62*fb1b10abSAndroid Build Coastguard Worker 0, /* enable_auto_alt_ref */
63*fb1b10abSAndroid Build Coastguard Worker 0, /* noise_sensitivity */
64*fb1b10abSAndroid Build Coastguard Worker 0, /* Sharpness */
65*fb1b10abSAndroid Build Coastguard Worker 0, /* static_thresh */
66*fb1b10abSAndroid Build Coastguard Worker #if (CONFIG_REALTIME_ONLY & CONFIG_ONTHEFLY_BITPACKING)
67*fb1b10abSAndroid Build Coastguard Worker VP8_EIGHT_TOKENPARTITION,
68*fb1b10abSAndroid Build Coastguard Worker #else
69*fb1b10abSAndroid Build Coastguard Worker VP8_ONE_TOKENPARTITION, /* token_partitions */
70*fb1b10abSAndroid Build Coastguard Worker #endif
71*fb1b10abSAndroid Build Coastguard Worker 0, /* arnr_max_frames */
72*fb1b10abSAndroid Build Coastguard Worker 3, /* arnr_strength */
73*fb1b10abSAndroid Build Coastguard Worker 3, /* arnr_type*/
74*fb1b10abSAndroid Build Coastguard Worker 0, /* tuning*/
75*fb1b10abSAndroid Build Coastguard Worker 10, /* cq_level */
76*fb1b10abSAndroid Build Coastguard Worker 0, /* rc_max_intra_bitrate_pct */
77*fb1b10abSAndroid Build Coastguard Worker 0, /* gf_cbr_boost_pct */
78*fb1b10abSAndroid Build Coastguard Worker 0, /* screen_content_mode */
79*fb1b10abSAndroid Build Coastguard Worker };
80*fb1b10abSAndroid Build Coastguard Worker
81*fb1b10abSAndroid Build Coastguard Worker struct vpx_codec_alg_priv {
82*fb1b10abSAndroid Build Coastguard Worker vpx_codec_priv_t base;
83*fb1b10abSAndroid Build Coastguard Worker vpx_codec_enc_cfg_t cfg;
84*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg vp8_cfg;
85*fb1b10abSAndroid Build Coastguard Worker vpx_rational64_t timestamp_ratio;
86*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pts_t pts_offset;
87*fb1b10abSAndroid Build Coastguard Worker unsigned char pts_offset_initialized;
88*fb1b10abSAndroid Build Coastguard Worker VP8_CONFIG oxcf;
89*fb1b10abSAndroid Build Coastguard Worker struct VP8_COMP *cpi;
90*fb1b10abSAndroid Build Coastguard Worker unsigned char *cx_data;
91*fb1b10abSAndroid Build Coastguard Worker unsigned int cx_data_sz;
92*fb1b10abSAndroid Build Coastguard Worker vpx_image_t preview_img;
93*fb1b10abSAndroid Build Coastguard Worker unsigned int next_frame_flag;
94*fb1b10abSAndroid Build Coastguard Worker vp8_postproc_cfg_t preview_ppcfg;
95*fb1b10abSAndroid Build Coastguard Worker /* pkt_list size depends on the maximum number of lagged frames allowed. */
96*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pkt_list_decl(64) pkt_list;
97*fb1b10abSAndroid Build Coastguard Worker unsigned int fixed_kf_cntr;
98*fb1b10abSAndroid Build Coastguard Worker vpx_enc_frame_flags_t control_frame_flags;
99*fb1b10abSAndroid Build Coastguard Worker };
100*fb1b10abSAndroid Build Coastguard Worker
101*fb1b10abSAndroid Build Coastguard Worker // Called by vp8e_set_config() and vp8e_encode() only. Must not be called
102*fb1b10abSAndroid Build Coastguard Worker // by vp8e_init() because the `error` paramerer (cpi->common.error) will be
103*fb1b10abSAndroid Build Coastguard Worker // destroyed by vpx_codec_enc_init_ver() after vp8e_init() returns an error.
104*fb1b10abSAndroid Build Coastguard Worker // See the "IMPORTANT" comment in vpx_codec_enc_init_ver().
update_error_state(vpx_codec_alg_priv_t * ctx,const struct vpx_internal_error_info * error)105*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t update_error_state(
106*fb1b10abSAndroid Build Coastguard Worker vpx_codec_alg_priv_t *ctx, const struct vpx_internal_error_info *error) {
107*fb1b10abSAndroid Build Coastguard Worker const vpx_codec_err_t res = error->error_code;
108*fb1b10abSAndroid Build Coastguard Worker
109*fb1b10abSAndroid Build Coastguard Worker if (res != VPX_CODEC_OK)
110*fb1b10abSAndroid Build Coastguard Worker ctx->base.err_detail = error->has_detail ? error->detail : NULL;
111*fb1b10abSAndroid Build Coastguard Worker
112*fb1b10abSAndroid Build Coastguard Worker return res;
113*fb1b10abSAndroid Build Coastguard Worker }
114*fb1b10abSAndroid Build Coastguard Worker
115*fb1b10abSAndroid Build Coastguard Worker #undef ERROR
116*fb1b10abSAndroid Build Coastguard Worker #define ERROR(str) \
117*fb1b10abSAndroid Build Coastguard Worker do { \
118*fb1b10abSAndroid Build Coastguard Worker ctx->base.err_detail = str; \
119*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM; \
120*fb1b10abSAndroid Build Coastguard Worker } while (0)
121*fb1b10abSAndroid Build Coastguard Worker
122*fb1b10abSAndroid Build Coastguard Worker #define RANGE_CHECK(p, memb, lo, hi) \
123*fb1b10abSAndroid Build Coastguard Worker do { \
124*fb1b10abSAndroid Build Coastguard Worker if (!(((p)->memb == (lo) || (p)->memb > (lo)) && (p)->memb <= (hi))) \
125*fb1b10abSAndroid Build Coastguard Worker ERROR(#memb " out of range [" #lo ".." #hi "]"); \
126*fb1b10abSAndroid Build Coastguard Worker } while (0)
127*fb1b10abSAndroid Build Coastguard Worker
128*fb1b10abSAndroid Build Coastguard Worker #define RANGE_CHECK_HI(p, memb, hi) \
129*fb1b10abSAndroid Build Coastguard Worker do { \
130*fb1b10abSAndroid Build Coastguard Worker if (!((p)->memb <= (hi))) ERROR(#memb " out of range [.." #hi "]"); \
131*fb1b10abSAndroid Build Coastguard Worker } while (0)
132*fb1b10abSAndroid Build Coastguard Worker
133*fb1b10abSAndroid Build Coastguard Worker #define RANGE_CHECK_LO(p, memb, lo) \
134*fb1b10abSAndroid Build Coastguard Worker do { \
135*fb1b10abSAndroid Build Coastguard Worker if (!((p)->memb >= (lo))) ERROR(#memb " out of range [" #lo "..]"); \
136*fb1b10abSAndroid Build Coastguard Worker } while (0)
137*fb1b10abSAndroid Build Coastguard Worker
138*fb1b10abSAndroid Build Coastguard Worker #define RANGE_CHECK_BOOL(p, memb) \
139*fb1b10abSAndroid Build Coastguard Worker do { \
140*fb1b10abSAndroid Build Coastguard Worker if (!!((p)->memb) != (p)->memb) ERROR(#memb " expected boolean"); \
141*fb1b10abSAndroid Build Coastguard Worker } while (0)
142*fb1b10abSAndroid Build Coastguard Worker
validate_config(vpx_codec_alg_priv_t * ctx,const vpx_codec_enc_cfg_t * cfg,const struct vp8_extracfg * vp8_cfg,int finalize)143*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t validate_config(vpx_codec_alg_priv_t *ctx,
144*fb1b10abSAndroid Build Coastguard Worker const vpx_codec_enc_cfg_t *cfg,
145*fb1b10abSAndroid Build Coastguard Worker const struct vp8_extracfg *vp8_cfg,
146*fb1b10abSAndroid Build Coastguard Worker int finalize) {
147*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_w, 1, 16383); /* 14 bits available */
148*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_h, 1, 16383); /* 14 bits available */
149*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_timebase.den, 1, 1000000000);
150*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_timebase.num, 1, 1000000000);
151*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, g_profile, 3);
152*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_max_quantizer, 63);
153*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_min_quantizer, cfg->rc_max_quantizer);
154*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, g_threads, 64);
155*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_REALTIME_ONLY
156*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, g_lag_in_frames, 0);
157*fb1b10abSAndroid Build Coastguard Worker #elif CONFIG_MULTI_RES_ENCODING
158*fb1b10abSAndroid Build Coastguard Worker if (ctx->base.enc.total_encoders > 1) RANGE_CHECK_HI(cfg, g_lag_in_frames, 0);
159*fb1b10abSAndroid Build Coastguard Worker #else
160*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, g_lag_in_frames, 25);
161*fb1b10abSAndroid Build Coastguard Worker #endif
162*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, rc_end_usage, VPX_VBR, VPX_Q);
163*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_undershoot_pct, 100);
164*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_overshoot_pct, 100);
165*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_2pass_vbr_bias_pct, 100);
166*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, kf_mode, VPX_KF_DISABLED, VPX_KF_AUTO);
167*fb1b10abSAndroid Build Coastguard Worker
168*fb1b10abSAndroid Build Coastguard Worker /* TODO: add spatial re-sampling support and frame dropping in
169*fb1b10abSAndroid Build Coastguard Worker * multi-res-encoder.*/
170*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTI_RES_ENCODING
171*fb1b10abSAndroid Build Coastguard Worker if (ctx->base.enc.total_encoders > 1)
172*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_resize_allowed, 0);
173*fb1b10abSAndroid Build Coastguard Worker #else
174*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_BOOL(cfg, rc_resize_allowed);
175*fb1b10abSAndroid Build Coastguard Worker #endif
176*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_dropframe_thresh, 100);
177*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_resize_up_thresh, 100);
178*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, rc_resize_down_thresh, 100);
179*fb1b10abSAndroid Build Coastguard Worker
180*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_REALTIME_ONLY
181*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_pass, VPX_RC_ONE_PASS, VPX_RC_ONE_PASS);
182*fb1b10abSAndroid Build Coastguard Worker #elif CONFIG_MULTI_RES_ENCODING
183*fb1b10abSAndroid Build Coastguard Worker if (ctx->base.enc.total_encoders > 1)
184*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_pass, VPX_RC_ONE_PASS, VPX_RC_ONE_PASS);
185*fb1b10abSAndroid Build Coastguard Worker #else
186*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, g_pass, VPX_RC_ONE_PASS, VPX_RC_LAST_PASS);
187*fb1b10abSAndroid Build Coastguard Worker #endif
188*fb1b10abSAndroid Build Coastguard Worker
189*fb1b10abSAndroid Build Coastguard Worker /* VP8 does not support a lower bound on the keyframe interval in
190*fb1b10abSAndroid Build Coastguard Worker * automatic keyframe placement mode.
191*fb1b10abSAndroid Build Coastguard Worker */
192*fb1b10abSAndroid Build Coastguard Worker if (cfg->kf_mode != VPX_KF_DISABLED && cfg->kf_min_dist != cfg->kf_max_dist &&
193*fb1b10abSAndroid Build Coastguard Worker cfg->kf_min_dist > 0)
194*fb1b10abSAndroid Build Coastguard Worker ERROR(
195*fb1b10abSAndroid Build Coastguard Worker "kf_min_dist not supported in auto mode, use 0 "
196*fb1b10abSAndroid Build Coastguard Worker "or kf_max_dist instead.");
197*fb1b10abSAndroid Build Coastguard Worker
198*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_BOOL(vp8_cfg, enable_auto_alt_ref);
199*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, cpu_used, -16, 16);
200*fb1b10abSAndroid Build Coastguard Worker
201*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_REALTIME_ONLY && !CONFIG_TEMPORAL_DENOISING
202*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, noise_sensitivity, 0, 0);
203*fb1b10abSAndroid Build Coastguard Worker #else
204*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(vp8_cfg, noise_sensitivity, 6);
205*fb1b10abSAndroid Build Coastguard Worker #endif
206*fb1b10abSAndroid Build Coastguard Worker
207*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, token_partitions, VP8_ONE_TOKENPARTITION,
208*fb1b10abSAndroid Build Coastguard Worker VP8_EIGHT_TOKENPARTITION);
209*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(vp8_cfg, Sharpness, 7);
210*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, arnr_max_frames, 0, 15);
211*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(vp8_cfg, arnr_strength, 6);
212*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, arnr_type, 1, 3);
213*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, cq_level, 0, 63);
214*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(vp8_cfg, screen_content_mode, 2);
215*fb1b10abSAndroid Build Coastguard Worker if (finalize && (cfg->rc_end_usage == VPX_CQ || cfg->rc_end_usage == VPX_Q))
216*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(vp8_cfg, cq_level, cfg->rc_min_quantizer,
217*fb1b10abSAndroid Build Coastguard Worker cfg->rc_max_quantizer);
218*fb1b10abSAndroid Build Coastguard Worker
219*fb1b10abSAndroid Build Coastguard Worker #if !(CONFIG_REALTIME_ONLY)
220*fb1b10abSAndroid Build Coastguard Worker if (cfg->g_pass == VPX_RC_LAST_PASS) {
221*fb1b10abSAndroid Build Coastguard Worker size_t packet_sz = sizeof(FIRSTPASS_STATS);
222*fb1b10abSAndroid Build Coastguard Worker int n_packets = (int)(cfg->rc_twopass_stats_in.sz / packet_sz);
223*fb1b10abSAndroid Build Coastguard Worker FIRSTPASS_STATS *stats;
224*fb1b10abSAndroid Build Coastguard Worker
225*fb1b10abSAndroid Build Coastguard Worker if (!cfg->rc_twopass_stats_in.buf)
226*fb1b10abSAndroid Build Coastguard Worker ERROR("rc_twopass_stats_in.buf not set.");
227*fb1b10abSAndroid Build Coastguard Worker
228*fb1b10abSAndroid Build Coastguard Worker if (cfg->rc_twopass_stats_in.sz % packet_sz)
229*fb1b10abSAndroid Build Coastguard Worker ERROR("rc_twopass_stats_in.sz indicates truncated packet.");
230*fb1b10abSAndroid Build Coastguard Worker
231*fb1b10abSAndroid Build Coastguard Worker if (cfg->rc_twopass_stats_in.sz < 2 * packet_sz)
232*fb1b10abSAndroid Build Coastguard Worker ERROR("rc_twopass_stats_in requires at least two packets.");
233*fb1b10abSAndroid Build Coastguard Worker
234*fb1b10abSAndroid Build Coastguard Worker stats = (void *)((char *)cfg->rc_twopass_stats_in.buf +
235*fb1b10abSAndroid Build Coastguard Worker (n_packets - 1) * packet_sz);
236*fb1b10abSAndroid Build Coastguard Worker
237*fb1b10abSAndroid Build Coastguard Worker if ((int)(stats->count + 0.5) != n_packets - 1)
238*fb1b10abSAndroid Build Coastguard Worker ERROR("rc_twopass_stats_in missing EOS stats packet");
239*fb1b10abSAndroid Build Coastguard Worker }
240*fb1b10abSAndroid Build Coastguard Worker #endif
241*fb1b10abSAndroid Build Coastguard Worker
242*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, ts_number_layers, 1, 5);
243*fb1b10abSAndroid Build Coastguard Worker
244*fb1b10abSAndroid Build Coastguard Worker if (cfg->ts_number_layers > 1) {
245*fb1b10abSAndroid Build Coastguard Worker unsigned int i;
246*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, ts_periodicity, 16);
247*fb1b10abSAndroid Build Coastguard Worker
248*fb1b10abSAndroid Build Coastguard Worker for (i = 1; i < cfg->ts_number_layers; ++i) {
249*fb1b10abSAndroid Build Coastguard Worker if (cfg->ts_target_bitrate[i] <= cfg->ts_target_bitrate[i - 1] &&
250*fb1b10abSAndroid Build Coastguard Worker cfg->rc_target_bitrate > 0)
251*fb1b10abSAndroid Build Coastguard Worker ERROR("ts_target_bitrate entries are not strictly increasing");
252*fb1b10abSAndroid Build Coastguard Worker }
253*fb1b10abSAndroid Build Coastguard Worker
254*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, ts_rate_decimator[cfg->ts_number_layers - 1], 1, 1);
255*fb1b10abSAndroid Build Coastguard Worker for (i = cfg->ts_number_layers - 2; i > 0; i--) {
256*fb1b10abSAndroid Build Coastguard Worker if (cfg->ts_rate_decimator[i - 1] != 2 * cfg->ts_rate_decimator[i])
257*fb1b10abSAndroid Build Coastguard Worker ERROR("ts_rate_decimator factors are not powers of 2");
258*fb1b10abSAndroid Build Coastguard Worker }
259*fb1b10abSAndroid Build Coastguard Worker
260*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK_HI(cfg, ts_layer_id[i], cfg->ts_number_layers - 1);
261*fb1b10abSAndroid Build Coastguard Worker }
262*fb1b10abSAndroid Build Coastguard Worker
263*fb1b10abSAndroid Build Coastguard Worker #if (CONFIG_REALTIME_ONLY & CONFIG_ONTHEFLY_BITPACKING)
264*fb1b10abSAndroid Build Coastguard Worker if (cfg->g_threads > (1 << vp8_cfg->token_partitions))
265*fb1b10abSAndroid Build Coastguard Worker ERROR("g_threads cannot be bigger than number of token partitions");
266*fb1b10abSAndroid Build Coastguard Worker #endif
267*fb1b10abSAndroid Build Coastguard Worker
268*fb1b10abSAndroid Build Coastguard Worker // The range below shall be further tuned.
269*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, use_vizier_rc_params, 0, 1);
270*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, active_wq_factor.den, 1, 1000);
271*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, err_per_mb_factor.den, 1, 1000);
272*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, sr_default_decay_limit.den, 1, 1000);
273*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, sr_diff_factor.den, 1, 1000);
274*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, kf_err_per_mb_factor.den, 1, 1000);
275*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, kf_frame_min_boost_factor.den, 1, 1000);
276*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, kf_frame_max_boost_subs_factor.den, 1, 1000);
277*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, kf_max_total_boost_factor.den, 1, 1000);
278*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, gf_max_total_boost_factor.den, 1, 1000);
279*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, gf_frame_max_boost_factor.den, 1, 1000);
280*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, zm_factor.den, 1, 1000);
281*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, rd_mult_inter_qp_fac.den, 1, 1000);
282*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, rd_mult_arf_qp_fac.den, 1, 1000);
283*fb1b10abSAndroid Build Coastguard Worker RANGE_CHECK(cfg, rd_mult_key_qp_fac.den, 1, 1000);
284*fb1b10abSAndroid Build Coastguard Worker
285*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
286*fb1b10abSAndroid Build Coastguard Worker }
287*fb1b10abSAndroid Build Coastguard Worker
validate_img(vpx_codec_alg_priv_t * ctx,const vpx_image_t * img)288*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t validate_img(vpx_codec_alg_priv_t *ctx,
289*fb1b10abSAndroid Build Coastguard Worker const vpx_image_t *img) {
290*fb1b10abSAndroid Build Coastguard Worker switch (img->fmt) {
291*fb1b10abSAndroid Build Coastguard Worker case VPX_IMG_FMT_YV12:
292*fb1b10abSAndroid Build Coastguard Worker case VPX_IMG_FMT_I420:
293*fb1b10abSAndroid Build Coastguard Worker case VPX_IMG_FMT_NV12: break;
294*fb1b10abSAndroid Build Coastguard Worker default:
295*fb1b10abSAndroid Build Coastguard Worker ERROR(
296*fb1b10abSAndroid Build Coastguard Worker "Invalid image format. Only YV12, I420 and NV12 images are "
297*fb1b10abSAndroid Build Coastguard Worker "supported");
298*fb1b10abSAndroid Build Coastguard Worker }
299*fb1b10abSAndroid Build Coastguard Worker
300*fb1b10abSAndroid Build Coastguard Worker if ((img->d_w != ctx->cfg.g_w) || (img->d_h != ctx->cfg.g_h))
301*fb1b10abSAndroid Build Coastguard Worker ERROR("Image size must match encoder init configuration size");
302*fb1b10abSAndroid Build Coastguard Worker
303*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
304*fb1b10abSAndroid Build Coastguard Worker }
305*fb1b10abSAndroid Build Coastguard Worker
set_vp8e_config(VP8_CONFIG * oxcf,vpx_codec_enc_cfg_t cfg,struct vp8_extracfg vp8_cfg,vpx_codec_priv_enc_mr_cfg_t * mr_cfg)306*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_vp8e_config(VP8_CONFIG *oxcf,
307*fb1b10abSAndroid Build Coastguard Worker vpx_codec_enc_cfg_t cfg,
308*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg vp8_cfg,
309*fb1b10abSAndroid Build Coastguard Worker vpx_codec_priv_enc_mr_cfg_t *mr_cfg) {
310*fb1b10abSAndroid Build Coastguard Worker oxcf->multi_threaded = cfg.g_threads;
311*fb1b10abSAndroid Build Coastguard Worker oxcf->Version = cfg.g_profile;
312*fb1b10abSAndroid Build Coastguard Worker
313*fb1b10abSAndroid Build Coastguard Worker oxcf->Width = cfg.g_w;
314*fb1b10abSAndroid Build Coastguard Worker oxcf->Height = cfg.g_h;
315*fb1b10abSAndroid Build Coastguard Worker oxcf->timebase = cfg.g_timebase;
316*fb1b10abSAndroid Build Coastguard Worker
317*fb1b10abSAndroid Build Coastguard Worker oxcf->error_resilient_mode = cfg.g_error_resilient;
318*fb1b10abSAndroid Build Coastguard Worker
319*fb1b10abSAndroid Build Coastguard Worker switch (cfg.g_pass) {
320*fb1b10abSAndroid Build Coastguard Worker case VPX_RC_ONE_PASS: oxcf->Mode = MODE_BESTQUALITY; break;
321*fb1b10abSAndroid Build Coastguard Worker case VPX_RC_FIRST_PASS: oxcf->Mode = MODE_FIRSTPASS; break;
322*fb1b10abSAndroid Build Coastguard Worker case VPX_RC_LAST_PASS: oxcf->Mode = MODE_SECONDPASS_BEST; break;
323*fb1b10abSAndroid Build Coastguard Worker }
324*fb1b10abSAndroid Build Coastguard Worker
325*fb1b10abSAndroid Build Coastguard Worker if (cfg.g_pass == VPX_RC_FIRST_PASS || cfg.g_pass == VPX_RC_ONE_PASS) {
326*fb1b10abSAndroid Build Coastguard Worker oxcf->allow_lag = 0;
327*fb1b10abSAndroid Build Coastguard Worker oxcf->lag_in_frames = 0;
328*fb1b10abSAndroid Build Coastguard Worker } else {
329*fb1b10abSAndroid Build Coastguard Worker oxcf->allow_lag = (cfg.g_lag_in_frames) > 0;
330*fb1b10abSAndroid Build Coastguard Worker oxcf->lag_in_frames = cfg.g_lag_in_frames;
331*fb1b10abSAndroid Build Coastguard Worker }
332*fb1b10abSAndroid Build Coastguard Worker
333*fb1b10abSAndroid Build Coastguard Worker oxcf->allow_df = (cfg.rc_dropframe_thresh > 0);
334*fb1b10abSAndroid Build Coastguard Worker oxcf->drop_frames_water_mark = cfg.rc_dropframe_thresh;
335*fb1b10abSAndroid Build Coastguard Worker
336*fb1b10abSAndroid Build Coastguard Worker oxcf->allow_spatial_resampling = cfg.rc_resize_allowed;
337*fb1b10abSAndroid Build Coastguard Worker oxcf->resample_up_water_mark = cfg.rc_resize_up_thresh;
338*fb1b10abSAndroid Build Coastguard Worker oxcf->resample_down_water_mark = cfg.rc_resize_down_thresh;
339*fb1b10abSAndroid Build Coastguard Worker
340*fb1b10abSAndroid Build Coastguard Worker if (cfg.rc_end_usage == VPX_VBR) {
341*fb1b10abSAndroid Build Coastguard Worker oxcf->end_usage = USAGE_LOCAL_FILE_PLAYBACK;
342*fb1b10abSAndroid Build Coastguard Worker } else if (cfg.rc_end_usage == VPX_CBR) {
343*fb1b10abSAndroid Build Coastguard Worker oxcf->end_usage = USAGE_STREAM_FROM_SERVER;
344*fb1b10abSAndroid Build Coastguard Worker } else if (cfg.rc_end_usage == VPX_CQ) {
345*fb1b10abSAndroid Build Coastguard Worker oxcf->end_usage = USAGE_CONSTRAINED_QUALITY;
346*fb1b10abSAndroid Build Coastguard Worker } else if (cfg.rc_end_usage == VPX_Q) {
347*fb1b10abSAndroid Build Coastguard Worker oxcf->end_usage = USAGE_CONSTANT_QUALITY;
348*fb1b10abSAndroid Build Coastguard Worker }
349*fb1b10abSAndroid Build Coastguard Worker
350*fb1b10abSAndroid Build Coastguard Worker // Cap the target rate to 1000 Mbps to avoid some integer overflows in
351*fb1b10abSAndroid Build Coastguard Worker // target bandwidth calculations.
352*fb1b10abSAndroid Build Coastguard Worker oxcf->target_bandwidth = VPXMIN(cfg.rc_target_bitrate, 1000000);
353*fb1b10abSAndroid Build Coastguard Worker oxcf->rc_max_intra_bitrate_pct = vp8_cfg.rc_max_intra_bitrate_pct;
354*fb1b10abSAndroid Build Coastguard Worker oxcf->gf_cbr_boost_pct = vp8_cfg.gf_cbr_boost_pct;
355*fb1b10abSAndroid Build Coastguard Worker
356*fb1b10abSAndroid Build Coastguard Worker oxcf->best_allowed_q = cfg.rc_min_quantizer;
357*fb1b10abSAndroid Build Coastguard Worker oxcf->worst_allowed_q = cfg.rc_max_quantizer;
358*fb1b10abSAndroid Build Coastguard Worker oxcf->cq_level = vp8_cfg.cq_level;
359*fb1b10abSAndroid Build Coastguard Worker oxcf->fixed_q = -1;
360*fb1b10abSAndroid Build Coastguard Worker
361*fb1b10abSAndroid Build Coastguard Worker oxcf->under_shoot_pct = cfg.rc_undershoot_pct;
362*fb1b10abSAndroid Build Coastguard Worker oxcf->over_shoot_pct = cfg.rc_overshoot_pct;
363*fb1b10abSAndroid Build Coastguard Worker
364*fb1b10abSAndroid Build Coastguard Worker oxcf->maximum_buffer_size_in_ms = cfg.rc_buf_sz;
365*fb1b10abSAndroid Build Coastguard Worker oxcf->starting_buffer_level_in_ms = cfg.rc_buf_initial_sz;
366*fb1b10abSAndroid Build Coastguard Worker oxcf->optimal_buffer_level_in_ms = cfg.rc_buf_optimal_sz;
367*fb1b10abSAndroid Build Coastguard Worker
368*fb1b10abSAndroid Build Coastguard Worker oxcf->maximum_buffer_size = cfg.rc_buf_sz;
369*fb1b10abSAndroid Build Coastguard Worker oxcf->starting_buffer_level = cfg.rc_buf_initial_sz;
370*fb1b10abSAndroid Build Coastguard Worker oxcf->optimal_buffer_level = cfg.rc_buf_optimal_sz;
371*fb1b10abSAndroid Build Coastguard Worker
372*fb1b10abSAndroid Build Coastguard Worker oxcf->two_pass_vbrbias = cfg.rc_2pass_vbr_bias_pct;
373*fb1b10abSAndroid Build Coastguard Worker oxcf->two_pass_vbrmin_section = cfg.rc_2pass_vbr_minsection_pct;
374*fb1b10abSAndroid Build Coastguard Worker oxcf->two_pass_vbrmax_section = cfg.rc_2pass_vbr_maxsection_pct;
375*fb1b10abSAndroid Build Coastguard Worker
376*fb1b10abSAndroid Build Coastguard Worker oxcf->auto_key =
377*fb1b10abSAndroid Build Coastguard Worker cfg.kf_mode == VPX_KF_AUTO && cfg.kf_min_dist != cfg.kf_max_dist;
378*fb1b10abSAndroid Build Coastguard Worker oxcf->key_freq = cfg.kf_max_dist;
379*fb1b10abSAndroid Build Coastguard Worker
380*fb1b10abSAndroid Build Coastguard Worker oxcf->number_of_layers = cfg.ts_number_layers;
381*fb1b10abSAndroid Build Coastguard Worker oxcf->periodicity = cfg.ts_periodicity;
382*fb1b10abSAndroid Build Coastguard Worker
383*fb1b10abSAndroid Build Coastguard Worker if (oxcf->number_of_layers > 1) {
384*fb1b10abSAndroid Build Coastguard Worker memcpy(oxcf->target_bitrate, cfg.ts_target_bitrate,
385*fb1b10abSAndroid Build Coastguard Worker sizeof(cfg.ts_target_bitrate));
386*fb1b10abSAndroid Build Coastguard Worker memcpy(oxcf->rate_decimator, cfg.ts_rate_decimator,
387*fb1b10abSAndroid Build Coastguard Worker sizeof(cfg.ts_rate_decimator));
388*fb1b10abSAndroid Build Coastguard Worker memcpy(oxcf->layer_id, cfg.ts_layer_id, sizeof(cfg.ts_layer_id));
389*fb1b10abSAndroid Build Coastguard Worker }
390*fb1b10abSAndroid Build Coastguard Worker
391*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTI_RES_ENCODING
392*fb1b10abSAndroid Build Coastguard Worker /* When mr_cfg is NULL, oxcf->mr_total_resolutions and oxcf->mr_encoder_id
393*fb1b10abSAndroid Build Coastguard Worker * are both memset to 0, which ensures the correct logic under this
394*fb1b10abSAndroid Build Coastguard Worker * situation.
395*fb1b10abSAndroid Build Coastguard Worker */
396*fb1b10abSAndroid Build Coastguard Worker if (mr_cfg) {
397*fb1b10abSAndroid Build Coastguard Worker oxcf->mr_total_resolutions = mr_cfg->mr_total_resolutions;
398*fb1b10abSAndroid Build Coastguard Worker oxcf->mr_encoder_id = mr_cfg->mr_encoder_id;
399*fb1b10abSAndroid Build Coastguard Worker oxcf->mr_down_sampling_factor.num = mr_cfg->mr_down_sampling_factor.num;
400*fb1b10abSAndroid Build Coastguard Worker oxcf->mr_down_sampling_factor.den = mr_cfg->mr_down_sampling_factor.den;
401*fb1b10abSAndroid Build Coastguard Worker oxcf->mr_low_res_mode_info = mr_cfg->mr_low_res_mode_info;
402*fb1b10abSAndroid Build Coastguard Worker }
403*fb1b10abSAndroid Build Coastguard Worker #else
404*fb1b10abSAndroid Build Coastguard Worker (void)mr_cfg;
405*fb1b10abSAndroid Build Coastguard Worker #endif
406*fb1b10abSAndroid Build Coastguard Worker
407*fb1b10abSAndroid Build Coastguard Worker oxcf->cpu_used = vp8_cfg.cpu_used;
408*fb1b10abSAndroid Build Coastguard Worker if (cfg.g_pass == VPX_RC_FIRST_PASS) {
409*fb1b10abSAndroid Build Coastguard Worker oxcf->cpu_used = VPXMAX(4, oxcf->cpu_used);
410*fb1b10abSAndroid Build Coastguard Worker }
411*fb1b10abSAndroid Build Coastguard Worker oxcf->encode_breakout = vp8_cfg.static_thresh;
412*fb1b10abSAndroid Build Coastguard Worker oxcf->play_alternate = vp8_cfg.enable_auto_alt_ref;
413*fb1b10abSAndroid Build Coastguard Worker oxcf->noise_sensitivity = vp8_cfg.noise_sensitivity;
414*fb1b10abSAndroid Build Coastguard Worker oxcf->Sharpness = vp8_cfg.Sharpness;
415*fb1b10abSAndroid Build Coastguard Worker oxcf->token_partitions = vp8_cfg.token_partitions;
416*fb1b10abSAndroid Build Coastguard Worker
417*fb1b10abSAndroid Build Coastguard Worker oxcf->two_pass_stats_in = cfg.rc_twopass_stats_in;
418*fb1b10abSAndroid Build Coastguard Worker oxcf->output_pkt_list = vp8_cfg.pkt_list;
419*fb1b10abSAndroid Build Coastguard Worker
420*fb1b10abSAndroid Build Coastguard Worker oxcf->arnr_max_frames = vp8_cfg.arnr_max_frames;
421*fb1b10abSAndroid Build Coastguard Worker oxcf->arnr_strength = vp8_cfg.arnr_strength;
422*fb1b10abSAndroid Build Coastguard Worker oxcf->arnr_type = vp8_cfg.arnr_type;
423*fb1b10abSAndroid Build Coastguard Worker
424*fb1b10abSAndroid Build Coastguard Worker oxcf->tuning = vp8_cfg.tuning;
425*fb1b10abSAndroid Build Coastguard Worker
426*fb1b10abSAndroid Build Coastguard Worker oxcf->screen_content_mode = vp8_cfg.screen_content_mode;
427*fb1b10abSAndroid Build Coastguard Worker
428*fb1b10abSAndroid Build Coastguard Worker /*
429*fb1b10abSAndroid Build Coastguard Worker printf("Current VP8 Settings: \n");
430*fb1b10abSAndroid Build Coastguard Worker printf("target_bandwidth: %d\n", oxcf->target_bandwidth);
431*fb1b10abSAndroid Build Coastguard Worker printf("noise_sensitivity: %d\n", oxcf->noise_sensitivity);
432*fb1b10abSAndroid Build Coastguard Worker printf("Sharpness: %d\n", oxcf->Sharpness);
433*fb1b10abSAndroid Build Coastguard Worker printf("cpu_used: %d\n", oxcf->cpu_used);
434*fb1b10abSAndroid Build Coastguard Worker printf("Mode: %d\n", oxcf->Mode);
435*fb1b10abSAndroid Build Coastguard Worker printf("auto_key: %d\n", oxcf->auto_key);
436*fb1b10abSAndroid Build Coastguard Worker printf("key_freq: %d\n", oxcf->key_freq);
437*fb1b10abSAndroid Build Coastguard Worker printf("end_usage: %d\n", oxcf->end_usage);
438*fb1b10abSAndroid Build Coastguard Worker printf("under_shoot_pct: %d\n", oxcf->under_shoot_pct);
439*fb1b10abSAndroid Build Coastguard Worker printf("over_shoot_pct: %d\n", oxcf->over_shoot_pct);
440*fb1b10abSAndroid Build Coastguard Worker printf("starting_buffer_level: %d\n", oxcf->starting_buffer_level);
441*fb1b10abSAndroid Build Coastguard Worker printf("optimal_buffer_level: %d\n", oxcf->optimal_buffer_level);
442*fb1b10abSAndroid Build Coastguard Worker printf("maximum_buffer_size: %d\n", oxcf->maximum_buffer_size);
443*fb1b10abSAndroid Build Coastguard Worker printf("fixed_q: %d\n", oxcf->fixed_q);
444*fb1b10abSAndroid Build Coastguard Worker printf("worst_allowed_q: %d\n", oxcf->worst_allowed_q);
445*fb1b10abSAndroid Build Coastguard Worker printf("best_allowed_q: %d\n", oxcf->best_allowed_q);
446*fb1b10abSAndroid Build Coastguard Worker printf("allow_spatial_resampling: %d\n", oxcf->allow_spatial_resampling);
447*fb1b10abSAndroid Build Coastguard Worker printf("resample_down_water_mark: %d\n", oxcf->resample_down_water_mark);
448*fb1b10abSAndroid Build Coastguard Worker printf("resample_up_water_mark: %d\n", oxcf->resample_up_water_mark);
449*fb1b10abSAndroid Build Coastguard Worker printf("allow_df: %d\n", oxcf->allow_df);
450*fb1b10abSAndroid Build Coastguard Worker printf("drop_frames_water_mark: %d\n", oxcf->drop_frames_water_mark);
451*fb1b10abSAndroid Build Coastguard Worker printf("two_pass_vbrbias: %d\n", oxcf->two_pass_vbrbias);
452*fb1b10abSAndroid Build Coastguard Worker printf("two_pass_vbrmin_section: %d\n", oxcf->two_pass_vbrmin_section);
453*fb1b10abSAndroid Build Coastguard Worker printf("two_pass_vbrmax_section: %d\n", oxcf->two_pass_vbrmax_section);
454*fb1b10abSAndroid Build Coastguard Worker printf("allow_lag: %d\n", oxcf->allow_lag);
455*fb1b10abSAndroid Build Coastguard Worker printf("lag_in_frames: %d\n", oxcf->lag_in_frames);
456*fb1b10abSAndroid Build Coastguard Worker printf("play_alternate: %d\n", oxcf->play_alternate);
457*fb1b10abSAndroid Build Coastguard Worker printf("Version: %d\n", oxcf->Version);
458*fb1b10abSAndroid Build Coastguard Worker printf("multi_threaded: %d\n", oxcf->multi_threaded);
459*fb1b10abSAndroid Build Coastguard Worker printf("encode_breakout: %d\n", oxcf->encode_breakout);
460*fb1b10abSAndroid Build Coastguard Worker */
461*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
462*fb1b10abSAndroid Build Coastguard Worker }
463*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_config(vpx_codec_alg_priv_t * ctx,const vpx_codec_enc_cfg_t * cfg)464*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_config(vpx_codec_alg_priv_t *ctx,
465*fb1b10abSAndroid Build Coastguard Worker const vpx_codec_enc_cfg_t *cfg) {
466*fb1b10abSAndroid Build Coastguard Worker vpx_codec_err_t res;
467*fb1b10abSAndroid Build Coastguard Worker
468*fb1b10abSAndroid Build Coastguard Worker if (cfg->g_w != ctx->cfg.g_w || cfg->g_h != ctx->cfg.g_h) {
469*fb1b10abSAndroid Build Coastguard Worker if (cfg->g_lag_in_frames > 1 || cfg->g_pass != VPX_RC_ONE_PASS)
470*fb1b10abSAndroid Build Coastguard Worker ERROR("Cannot change width or height after initialization");
471*fb1b10abSAndroid Build Coastguard Worker if ((ctx->cpi->initial_width && (int)cfg->g_w > ctx->cpi->initial_width) ||
472*fb1b10abSAndroid Build Coastguard Worker (ctx->cpi->initial_height && (int)cfg->g_h > ctx->cpi->initial_height))
473*fb1b10abSAndroid Build Coastguard Worker ERROR("Cannot increase width or height larger than their initial values");
474*fb1b10abSAndroid Build Coastguard Worker }
475*fb1b10abSAndroid Build Coastguard Worker
476*fb1b10abSAndroid Build Coastguard Worker /* Prevent increasing lag_in_frames. This check is stricter than it needs
477*fb1b10abSAndroid Build Coastguard Worker * to be -- the limit is not increasing past the first lag_in_frames
478*fb1b10abSAndroid Build Coastguard Worker * value, but we don't track the initial config, only the last successful
479*fb1b10abSAndroid Build Coastguard Worker * config.
480*fb1b10abSAndroid Build Coastguard Worker */
481*fb1b10abSAndroid Build Coastguard Worker if ((cfg->g_lag_in_frames > ctx->cfg.g_lag_in_frames))
482*fb1b10abSAndroid Build Coastguard Worker ERROR("Cannot increase lag_in_frames");
483*fb1b10abSAndroid Build Coastguard Worker
484*fb1b10abSAndroid Build Coastguard Worker res = validate_config(ctx, cfg, &ctx->vp8_cfg, 0);
485*fb1b10abSAndroid Build Coastguard Worker if (res != VPX_CODEC_OK) return res;
486*fb1b10abSAndroid Build Coastguard Worker
487*fb1b10abSAndroid Build Coastguard Worker if (setjmp(ctx->cpi->common.error.jmp)) {
488*fb1b10abSAndroid Build Coastguard Worker const vpx_codec_err_t codec_err =
489*fb1b10abSAndroid Build Coastguard Worker update_error_state(ctx, &ctx->cpi->common.error);
490*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
491*fb1b10abSAndroid Build Coastguard Worker vpx_clear_system_state();
492*fb1b10abSAndroid Build Coastguard Worker assert(codec_err != VPX_CODEC_OK);
493*fb1b10abSAndroid Build Coastguard Worker return codec_err;
494*fb1b10abSAndroid Build Coastguard Worker }
495*fb1b10abSAndroid Build Coastguard Worker
496*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 1;
497*fb1b10abSAndroid Build Coastguard Worker ctx->cfg = *cfg;
498*fb1b10abSAndroid Build Coastguard Worker set_vp8e_config(&ctx->oxcf, ctx->cfg, ctx->vp8_cfg, NULL);
499*fb1b10abSAndroid Build Coastguard Worker vp8_change_config(ctx->cpi, &ctx->oxcf);
500*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTITHREAD
501*fb1b10abSAndroid Build Coastguard Worker if (vp8cx_create_encoder_threads(ctx->cpi)) {
502*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
503*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_ERROR;
504*fb1b10abSAndroid Build Coastguard Worker }
505*fb1b10abSAndroid Build Coastguard Worker #endif
506*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
507*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
508*fb1b10abSAndroid Build Coastguard Worker }
509*fb1b10abSAndroid Build Coastguard Worker
get_quantizer(vpx_codec_alg_priv_t * ctx,va_list args)510*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t get_quantizer(vpx_codec_alg_priv_t *ctx, va_list args) {
511*fb1b10abSAndroid Build Coastguard Worker int *const arg = va_arg(args, int *);
512*fb1b10abSAndroid Build Coastguard Worker if (arg == NULL) return VPX_CODEC_INVALID_PARAM;
513*fb1b10abSAndroid Build Coastguard Worker *arg = vp8_get_quantizer(ctx->cpi);
514*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
515*fb1b10abSAndroid Build Coastguard Worker }
516*fb1b10abSAndroid Build Coastguard Worker
get_quantizer64(vpx_codec_alg_priv_t * ctx,va_list args)517*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t get_quantizer64(vpx_codec_alg_priv_t *ctx,
518*fb1b10abSAndroid Build Coastguard Worker va_list args) {
519*fb1b10abSAndroid Build Coastguard Worker int *const arg = va_arg(args, int *);
520*fb1b10abSAndroid Build Coastguard Worker if (arg == NULL) return VPX_CODEC_INVALID_PARAM;
521*fb1b10abSAndroid Build Coastguard Worker *arg = vp8_reverse_trans(vp8_get_quantizer(ctx->cpi));
522*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
523*fb1b10abSAndroid Build Coastguard Worker }
524*fb1b10abSAndroid Build Coastguard Worker
update_extracfg(vpx_codec_alg_priv_t * ctx,const struct vp8_extracfg * extra_cfg)525*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t update_extracfg(vpx_codec_alg_priv_t *ctx,
526*fb1b10abSAndroid Build Coastguard Worker const struct vp8_extracfg *extra_cfg) {
527*fb1b10abSAndroid Build Coastguard Worker const vpx_codec_err_t res = validate_config(ctx, &ctx->cfg, extra_cfg, 0);
528*fb1b10abSAndroid Build Coastguard Worker if (res == VPX_CODEC_OK) {
529*fb1b10abSAndroid Build Coastguard Worker ctx->vp8_cfg = *extra_cfg;
530*fb1b10abSAndroid Build Coastguard Worker set_vp8e_config(&ctx->oxcf, ctx->cfg, ctx->vp8_cfg, NULL);
531*fb1b10abSAndroid Build Coastguard Worker vp8_change_config(ctx->cpi, &ctx->oxcf);
532*fb1b10abSAndroid Build Coastguard Worker }
533*fb1b10abSAndroid Build Coastguard Worker return res;
534*fb1b10abSAndroid Build Coastguard Worker }
535*fb1b10abSAndroid Build Coastguard Worker
set_cpu_used(vpx_codec_alg_priv_t * ctx,va_list args)536*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_cpu_used(vpx_codec_alg_priv_t *ctx, va_list args) {
537*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
538*fb1b10abSAndroid Build Coastguard Worker extra_cfg.cpu_used = CAST(VP8E_SET_CPUUSED, args);
539*fb1b10abSAndroid Build Coastguard Worker // Use fastest speed setting (speed 16 or -16) if it's set beyond the range.
540*fb1b10abSAndroid Build Coastguard Worker extra_cfg.cpu_used = VPXMIN(16, extra_cfg.cpu_used);
541*fb1b10abSAndroid Build Coastguard Worker extra_cfg.cpu_used = VPXMAX(-16, extra_cfg.cpu_used);
542*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
543*fb1b10abSAndroid Build Coastguard Worker }
544*fb1b10abSAndroid Build Coastguard Worker
set_enable_auto_alt_ref(vpx_codec_alg_priv_t * ctx,va_list args)545*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_enable_auto_alt_ref(vpx_codec_alg_priv_t *ctx,
546*fb1b10abSAndroid Build Coastguard Worker va_list args) {
547*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
548*fb1b10abSAndroid Build Coastguard Worker extra_cfg.enable_auto_alt_ref = CAST(VP8E_SET_ENABLEAUTOALTREF, args);
549*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
550*fb1b10abSAndroid Build Coastguard Worker }
551*fb1b10abSAndroid Build Coastguard Worker
set_noise_sensitivity(vpx_codec_alg_priv_t * ctx,va_list args)552*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_noise_sensitivity(vpx_codec_alg_priv_t *ctx,
553*fb1b10abSAndroid Build Coastguard Worker va_list args) {
554*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
555*fb1b10abSAndroid Build Coastguard Worker extra_cfg.noise_sensitivity = CAST(VP8E_SET_NOISE_SENSITIVITY, args);
556*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
557*fb1b10abSAndroid Build Coastguard Worker }
558*fb1b10abSAndroid Build Coastguard Worker
set_sharpness(vpx_codec_alg_priv_t * ctx,va_list args)559*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_sharpness(vpx_codec_alg_priv_t *ctx, va_list args) {
560*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
561*fb1b10abSAndroid Build Coastguard Worker extra_cfg.Sharpness = CAST(VP8E_SET_SHARPNESS, args);
562*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
563*fb1b10abSAndroid Build Coastguard Worker }
564*fb1b10abSAndroid Build Coastguard Worker
set_static_thresh(vpx_codec_alg_priv_t * ctx,va_list args)565*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_static_thresh(vpx_codec_alg_priv_t *ctx,
566*fb1b10abSAndroid Build Coastguard Worker va_list args) {
567*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
568*fb1b10abSAndroid Build Coastguard Worker extra_cfg.static_thresh = CAST(VP8E_SET_STATIC_THRESHOLD, args);
569*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
570*fb1b10abSAndroid Build Coastguard Worker }
571*fb1b10abSAndroid Build Coastguard Worker
set_token_partitions(vpx_codec_alg_priv_t * ctx,va_list args)572*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_token_partitions(vpx_codec_alg_priv_t *ctx,
573*fb1b10abSAndroid Build Coastguard Worker va_list args) {
574*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
575*fb1b10abSAndroid Build Coastguard Worker extra_cfg.token_partitions = CAST(VP8E_SET_TOKEN_PARTITIONS, args);
576*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
577*fb1b10abSAndroid Build Coastguard Worker }
578*fb1b10abSAndroid Build Coastguard Worker
set_arnr_max_frames(vpx_codec_alg_priv_t * ctx,va_list args)579*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_arnr_max_frames(vpx_codec_alg_priv_t *ctx,
580*fb1b10abSAndroid Build Coastguard Worker va_list args) {
581*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
582*fb1b10abSAndroid Build Coastguard Worker extra_cfg.arnr_max_frames = CAST(VP8E_SET_ARNR_MAXFRAMES, args);
583*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
584*fb1b10abSAndroid Build Coastguard Worker }
585*fb1b10abSAndroid Build Coastguard Worker
set_arnr_strength(vpx_codec_alg_priv_t * ctx,va_list args)586*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_arnr_strength(vpx_codec_alg_priv_t *ctx,
587*fb1b10abSAndroid Build Coastguard Worker va_list args) {
588*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
589*fb1b10abSAndroid Build Coastguard Worker extra_cfg.arnr_strength = CAST(VP8E_SET_ARNR_STRENGTH, args);
590*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
591*fb1b10abSAndroid Build Coastguard Worker }
592*fb1b10abSAndroid Build Coastguard Worker
set_arnr_type(vpx_codec_alg_priv_t * ctx,va_list args)593*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_arnr_type(vpx_codec_alg_priv_t *ctx, va_list args) {
594*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
595*fb1b10abSAndroid Build Coastguard Worker extra_cfg.arnr_type = CAST(VP8E_SET_ARNR_TYPE, args);
596*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
597*fb1b10abSAndroid Build Coastguard Worker }
598*fb1b10abSAndroid Build Coastguard Worker
set_tuning(vpx_codec_alg_priv_t * ctx,va_list args)599*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_tuning(vpx_codec_alg_priv_t *ctx, va_list args) {
600*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
601*fb1b10abSAndroid Build Coastguard Worker extra_cfg.tuning = CAST(VP8E_SET_TUNING, args);
602*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
603*fb1b10abSAndroid Build Coastguard Worker }
604*fb1b10abSAndroid Build Coastguard Worker
set_cq_level(vpx_codec_alg_priv_t * ctx,va_list args)605*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_cq_level(vpx_codec_alg_priv_t *ctx, va_list args) {
606*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
607*fb1b10abSAndroid Build Coastguard Worker extra_cfg.cq_level = CAST(VP8E_SET_CQ_LEVEL, args);
608*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
609*fb1b10abSAndroid Build Coastguard Worker }
610*fb1b10abSAndroid Build Coastguard Worker
set_rc_max_intra_bitrate_pct(vpx_codec_alg_priv_t * ctx,va_list args)611*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_rc_max_intra_bitrate_pct(vpx_codec_alg_priv_t *ctx,
612*fb1b10abSAndroid Build Coastguard Worker va_list args) {
613*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
614*fb1b10abSAndroid Build Coastguard Worker extra_cfg.rc_max_intra_bitrate_pct =
615*fb1b10abSAndroid Build Coastguard Worker CAST(VP8E_SET_MAX_INTRA_BITRATE_PCT, args);
616*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
617*fb1b10abSAndroid Build Coastguard Worker }
618*fb1b10abSAndroid Build Coastguard Worker
ctrl_set_rc_gf_cbr_boost_pct(vpx_codec_alg_priv_t * ctx,va_list args)619*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t ctrl_set_rc_gf_cbr_boost_pct(vpx_codec_alg_priv_t *ctx,
620*fb1b10abSAndroid Build Coastguard Worker va_list args) {
621*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
622*fb1b10abSAndroid Build Coastguard Worker extra_cfg.gf_cbr_boost_pct = CAST(VP8E_SET_GF_CBR_BOOST_PCT, args);
623*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
624*fb1b10abSAndroid Build Coastguard Worker }
625*fb1b10abSAndroid Build Coastguard Worker
set_screen_content_mode(vpx_codec_alg_priv_t * ctx,va_list args)626*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_screen_content_mode(vpx_codec_alg_priv_t *ctx,
627*fb1b10abSAndroid Build Coastguard Worker va_list args) {
628*fb1b10abSAndroid Build Coastguard Worker struct vp8_extracfg extra_cfg = ctx->vp8_cfg;
629*fb1b10abSAndroid Build Coastguard Worker extra_cfg.screen_content_mode = CAST(VP8E_SET_SCREEN_CONTENT_MODE, args);
630*fb1b10abSAndroid Build Coastguard Worker return update_extracfg(ctx, &extra_cfg);
631*fb1b10abSAndroid Build Coastguard Worker }
632*fb1b10abSAndroid Build Coastguard Worker
ctrl_set_rtc_external_ratectrl(vpx_codec_alg_priv_t * ctx,va_list args)633*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t ctrl_set_rtc_external_ratectrl(vpx_codec_alg_priv_t *ctx,
634*fb1b10abSAndroid Build Coastguard Worker va_list args) {
635*fb1b10abSAndroid Build Coastguard Worker VP8_COMP *cpi = ctx->cpi;
636*fb1b10abSAndroid Build Coastguard Worker const unsigned int data = CAST(VP8E_SET_RTC_EXTERNAL_RATECTRL, args);
637*fb1b10abSAndroid Build Coastguard Worker if (data) {
638*fb1b10abSAndroid Build Coastguard Worker cpi->cyclic_refresh_mode_enabled = 0;
639*fb1b10abSAndroid Build Coastguard Worker cpi->rt_always_update_correction_factor = 1;
640*fb1b10abSAndroid Build Coastguard Worker cpi->rt_drop_recode_on_overshoot = 0;
641*fb1b10abSAndroid Build Coastguard Worker }
642*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
643*fb1b10abSAndroid Build Coastguard Worker }
644*fb1b10abSAndroid Build Coastguard Worker
vp8e_mr_alloc_mem(const vpx_codec_enc_cfg_t * cfg,void ** mem_loc)645*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_mr_alloc_mem(const vpx_codec_enc_cfg_t *cfg,
646*fb1b10abSAndroid Build Coastguard Worker void **mem_loc) {
647*fb1b10abSAndroid Build Coastguard Worker vpx_codec_err_t res = VPX_CODEC_OK;
648*fb1b10abSAndroid Build Coastguard Worker
649*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTI_RES_ENCODING
650*fb1b10abSAndroid Build Coastguard Worker LOWER_RES_FRAME_INFO *shared_mem_loc;
651*fb1b10abSAndroid Build Coastguard Worker int mb_rows = ((cfg->g_w + 15) >> 4);
652*fb1b10abSAndroid Build Coastguard Worker int mb_cols = ((cfg->g_h + 15) >> 4);
653*fb1b10abSAndroid Build Coastguard Worker
654*fb1b10abSAndroid Build Coastguard Worker shared_mem_loc = calloc(1, sizeof(LOWER_RES_FRAME_INFO));
655*fb1b10abSAndroid Build Coastguard Worker if (!shared_mem_loc) {
656*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_MEM_ERROR;
657*fb1b10abSAndroid Build Coastguard Worker }
658*fb1b10abSAndroid Build Coastguard Worker
659*fb1b10abSAndroid Build Coastguard Worker shared_mem_loc->mb_info =
660*fb1b10abSAndroid Build Coastguard Worker calloc(mb_rows * mb_cols, sizeof(LOWER_RES_MB_INFO));
661*fb1b10abSAndroid Build Coastguard Worker if (!(shared_mem_loc->mb_info)) {
662*fb1b10abSAndroid Build Coastguard Worker free(shared_mem_loc);
663*fb1b10abSAndroid Build Coastguard Worker res = VPX_CODEC_MEM_ERROR;
664*fb1b10abSAndroid Build Coastguard Worker } else {
665*fb1b10abSAndroid Build Coastguard Worker *mem_loc = (void *)shared_mem_loc;
666*fb1b10abSAndroid Build Coastguard Worker res = VPX_CODEC_OK;
667*fb1b10abSAndroid Build Coastguard Worker }
668*fb1b10abSAndroid Build Coastguard Worker #else
669*fb1b10abSAndroid Build Coastguard Worker (void)cfg;
670*fb1b10abSAndroid Build Coastguard Worker (void)mem_loc;
671*fb1b10abSAndroid Build Coastguard Worker #endif
672*fb1b10abSAndroid Build Coastguard Worker return res;
673*fb1b10abSAndroid Build Coastguard Worker }
674*fb1b10abSAndroid Build Coastguard Worker
vp8e_init(vpx_codec_ctx_t * ctx,vpx_codec_priv_enc_mr_cfg_t * mr_cfg)675*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_init(vpx_codec_ctx_t *ctx,
676*fb1b10abSAndroid Build Coastguard Worker vpx_codec_priv_enc_mr_cfg_t *mr_cfg) {
677*fb1b10abSAndroid Build Coastguard Worker vpx_codec_err_t res = VPX_CODEC_OK;
678*fb1b10abSAndroid Build Coastguard Worker
679*fb1b10abSAndroid Build Coastguard Worker vp8_rtcd();
680*fb1b10abSAndroid Build Coastguard Worker vpx_dsp_rtcd();
681*fb1b10abSAndroid Build Coastguard Worker vpx_scale_rtcd();
682*fb1b10abSAndroid Build Coastguard Worker
683*fb1b10abSAndroid Build Coastguard Worker if (!ctx->priv) {
684*fb1b10abSAndroid Build Coastguard Worker struct vpx_codec_alg_priv *priv =
685*fb1b10abSAndroid Build Coastguard Worker (struct vpx_codec_alg_priv *)vpx_calloc(1, sizeof(*priv));
686*fb1b10abSAndroid Build Coastguard Worker
687*fb1b10abSAndroid Build Coastguard Worker if (!priv) {
688*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_MEM_ERROR;
689*fb1b10abSAndroid Build Coastguard Worker }
690*fb1b10abSAndroid Build Coastguard Worker
691*fb1b10abSAndroid Build Coastguard Worker ctx->priv = (vpx_codec_priv_t *)priv;
692*fb1b10abSAndroid Build Coastguard Worker ctx->priv->init_flags = ctx->init_flags;
693*fb1b10abSAndroid Build Coastguard Worker
694*fb1b10abSAndroid Build Coastguard Worker if (ctx->config.enc) {
695*fb1b10abSAndroid Build Coastguard Worker /* Update the reference to the config structure to an
696*fb1b10abSAndroid Build Coastguard Worker * internal copy.
697*fb1b10abSAndroid Build Coastguard Worker */
698*fb1b10abSAndroid Build Coastguard Worker priv->cfg = *ctx->config.enc;
699*fb1b10abSAndroid Build Coastguard Worker ctx->config.enc = &priv->cfg;
700*fb1b10abSAndroid Build Coastguard Worker }
701*fb1b10abSAndroid Build Coastguard Worker
702*fb1b10abSAndroid Build Coastguard Worker priv->vp8_cfg = default_extracfg;
703*fb1b10abSAndroid Build Coastguard Worker priv->vp8_cfg.pkt_list = &priv->pkt_list.head;
704*fb1b10abSAndroid Build Coastguard Worker
705*fb1b10abSAndroid Build Coastguard Worker priv->cx_data_sz = priv->cfg.g_w * priv->cfg.g_h * 3 / 2 * 2;
706*fb1b10abSAndroid Build Coastguard Worker
707*fb1b10abSAndroid Build Coastguard Worker if (priv->cx_data_sz < 32768) priv->cx_data_sz = 32768;
708*fb1b10abSAndroid Build Coastguard Worker
709*fb1b10abSAndroid Build Coastguard Worker priv->cx_data = malloc(priv->cx_data_sz);
710*fb1b10abSAndroid Build Coastguard Worker
711*fb1b10abSAndroid Build Coastguard Worker if (!priv->cx_data) {
712*fb1b10abSAndroid Build Coastguard Worker priv->cx_data_sz = 0;
713*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_MEM_ERROR;
714*fb1b10abSAndroid Build Coastguard Worker }
715*fb1b10abSAndroid Build Coastguard Worker
716*fb1b10abSAndroid Build Coastguard Worker if (mr_cfg) {
717*fb1b10abSAndroid Build Coastguard Worker ctx->priv->enc.total_encoders = mr_cfg->mr_total_resolutions;
718*fb1b10abSAndroid Build Coastguard Worker } else {
719*fb1b10abSAndroid Build Coastguard Worker ctx->priv->enc.total_encoders = 1;
720*fb1b10abSAndroid Build Coastguard Worker }
721*fb1b10abSAndroid Build Coastguard Worker
722*fb1b10abSAndroid Build Coastguard Worker vp8_initialize_enc();
723*fb1b10abSAndroid Build Coastguard Worker
724*fb1b10abSAndroid Build Coastguard Worker res = validate_config(priv, &priv->cfg, &priv->vp8_cfg, 0);
725*fb1b10abSAndroid Build Coastguard Worker
726*fb1b10abSAndroid Build Coastguard Worker if (!res) {
727*fb1b10abSAndroid Build Coastguard Worker priv->pts_offset_initialized = 0;
728*fb1b10abSAndroid Build Coastguard Worker priv->timestamp_ratio.den = priv->cfg.g_timebase.den;
729*fb1b10abSAndroid Build Coastguard Worker priv->timestamp_ratio.num = (int64_t)priv->cfg.g_timebase.num;
730*fb1b10abSAndroid Build Coastguard Worker priv->timestamp_ratio.num *= TICKS_PER_SEC;
731*fb1b10abSAndroid Build Coastguard Worker reduce_ratio(&priv->timestamp_ratio);
732*fb1b10abSAndroid Build Coastguard Worker
733*fb1b10abSAndroid Build Coastguard Worker set_vp8e_config(&priv->oxcf, priv->cfg, priv->vp8_cfg, mr_cfg);
734*fb1b10abSAndroid Build Coastguard Worker priv->cpi = vp8_create_compressor(&priv->oxcf);
735*fb1b10abSAndroid Build Coastguard Worker if (!priv->cpi) res = VPX_CODEC_MEM_ERROR;
736*fb1b10abSAndroid Build Coastguard Worker }
737*fb1b10abSAndroid Build Coastguard Worker }
738*fb1b10abSAndroid Build Coastguard Worker
739*fb1b10abSAndroid Build Coastguard Worker return res;
740*fb1b10abSAndroid Build Coastguard Worker }
741*fb1b10abSAndroid Build Coastguard Worker
vp8e_destroy(vpx_codec_alg_priv_t * ctx)742*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_destroy(vpx_codec_alg_priv_t *ctx) {
743*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTI_RES_ENCODING
744*fb1b10abSAndroid Build Coastguard Worker /* Free multi-encoder shared memory */
745*fb1b10abSAndroid Build Coastguard Worker if (ctx->oxcf.mr_total_resolutions > 0 &&
746*fb1b10abSAndroid Build Coastguard Worker (ctx->oxcf.mr_encoder_id == ctx->oxcf.mr_total_resolutions - 1)) {
747*fb1b10abSAndroid Build Coastguard Worker LOWER_RES_FRAME_INFO *shared_mem_loc =
748*fb1b10abSAndroid Build Coastguard Worker (LOWER_RES_FRAME_INFO *)ctx->oxcf.mr_low_res_mode_info;
749*fb1b10abSAndroid Build Coastguard Worker free(shared_mem_loc->mb_info);
750*fb1b10abSAndroid Build Coastguard Worker free(ctx->oxcf.mr_low_res_mode_info);
751*fb1b10abSAndroid Build Coastguard Worker }
752*fb1b10abSAndroid Build Coastguard Worker #endif
753*fb1b10abSAndroid Build Coastguard Worker
754*fb1b10abSAndroid Build Coastguard Worker free(ctx->cx_data);
755*fb1b10abSAndroid Build Coastguard Worker vp8_remove_compressor(&ctx->cpi);
756*fb1b10abSAndroid Build Coastguard Worker vpx_free(ctx);
757*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
758*fb1b10abSAndroid Build Coastguard Worker }
759*fb1b10abSAndroid Build Coastguard Worker
image2yuvconfig(const vpx_image_t * img,YV12_BUFFER_CONFIG * yv12)760*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t image2yuvconfig(const vpx_image_t *img,
761*fb1b10abSAndroid Build Coastguard Worker YV12_BUFFER_CONFIG *yv12) {
762*fb1b10abSAndroid Build Coastguard Worker const int y_w = img->d_w;
763*fb1b10abSAndroid Build Coastguard Worker const int y_h = img->d_h;
764*fb1b10abSAndroid Build Coastguard Worker const int uv_w = (img->d_w + 1) / 2;
765*fb1b10abSAndroid Build Coastguard Worker const int uv_h = (img->d_h + 1) / 2;
766*fb1b10abSAndroid Build Coastguard Worker vpx_codec_err_t res = VPX_CODEC_OK;
767*fb1b10abSAndroid Build Coastguard Worker yv12->y_buffer = img->planes[VPX_PLANE_Y];
768*fb1b10abSAndroid Build Coastguard Worker yv12->u_buffer = img->planes[VPX_PLANE_U];
769*fb1b10abSAndroid Build Coastguard Worker yv12->v_buffer = img->planes[VPX_PLANE_V];
770*fb1b10abSAndroid Build Coastguard Worker
771*fb1b10abSAndroid Build Coastguard Worker yv12->y_crop_width = y_w;
772*fb1b10abSAndroid Build Coastguard Worker yv12->y_crop_height = y_h;
773*fb1b10abSAndroid Build Coastguard Worker yv12->y_width = y_w;
774*fb1b10abSAndroid Build Coastguard Worker yv12->y_height = y_h;
775*fb1b10abSAndroid Build Coastguard Worker yv12->uv_crop_width = uv_w;
776*fb1b10abSAndroid Build Coastguard Worker yv12->uv_crop_height = uv_h;
777*fb1b10abSAndroid Build Coastguard Worker yv12->uv_width = uv_w;
778*fb1b10abSAndroid Build Coastguard Worker yv12->uv_height = uv_h;
779*fb1b10abSAndroid Build Coastguard Worker
780*fb1b10abSAndroid Build Coastguard Worker yv12->y_stride = img->stride[VPX_PLANE_Y];
781*fb1b10abSAndroid Build Coastguard Worker yv12->uv_stride = img->stride[VPX_PLANE_U];
782*fb1b10abSAndroid Build Coastguard Worker
783*fb1b10abSAndroid Build Coastguard Worker yv12->border = (img->stride[VPX_PLANE_Y] - img->w) / 2;
784*fb1b10abSAndroid Build Coastguard Worker return res;
785*fb1b10abSAndroid Build Coastguard Worker }
786*fb1b10abSAndroid Build Coastguard Worker
pick_quickcompress_mode(vpx_codec_alg_priv_t * ctx,unsigned long duration,vpx_enc_deadline_t deadline)787*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t pick_quickcompress_mode(vpx_codec_alg_priv_t *ctx,
788*fb1b10abSAndroid Build Coastguard Worker unsigned long duration,
789*fb1b10abSAndroid Build Coastguard Worker vpx_enc_deadline_t deadline) {
790*fb1b10abSAndroid Build Coastguard Worker int new_qc;
791*fb1b10abSAndroid Build Coastguard Worker
792*fb1b10abSAndroid Build Coastguard Worker #if !(CONFIG_REALTIME_ONLY)
793*fb1b10abSAndroid Build Coastguard Worker /* Use best quality mode if no deadline is given. */
794*fb1b10abSAndroid Build Coastguard Worker new_qc = MODE_BESTQUALITY;
795*fb1b10abSAndroid Build Coastguard Worker
796*fb1b10abSAndroid Build Coastguard Worker if (deadline) {
797*fb1b10abSAndroid Build Coastguard Worker /* Convert duration parameter from stream timebase to microseconds */
798*fb1b10abSAndroid Build Coastguard Worker VPX_STATIC_ASSERT(TICKS_PER_SEC > 1000000 &&
799*fb1b10abSAndroid Build Coastguard Worker (TICKS_PER_SEC % 1000000) == 0);
800*fb1b10abSAndroid Build Coastguard Worker
801*fb1b10abSAndroid Build Coastguard Worker if (duration > UINT64_MAX / (uint64_t)ctx->timestamp_ratio.num) {
802*fb1b10abSAndroid Build Coastguard Worker ERROR("duration is too big");
803*fb1b10abSAndroid Build Coastguard Worker }
804*fb1b10abSAndroid Build Coastguard Worker uint64_t duration_us =
805*fb1b10abSAndroid Build Coastguard Worker duration * (uint64_t)ctx->timestamp_ratio.num /
806*fb1b10abSAndroid Build Coastguard Worker ((uint64_t)ctx->timestamp_ratio.den * (TICKS_PER_SEC / 1000000));
807*fb1b10abSAndroid Build Coastguard Worker
808*fb1b10abSAndroid Build Coastguard Worker /* If the deadline is more that the duration this frame is to be shown,
809*fb1b10abSAndroid Build Coastguard Worker * use good quality mode. Otherwise use realtime mode.
810*fb1b10abSAndroid Build Coastguard Worker */
811*fb1b10abSAndroid Build Coastguard Worker new_qc = (deadline > duration_us) ? MODE_GOODQUALITY : MODE_REALTIME;
812*fb1b10abSAndroid Build Coastguard Worker }
813*fb1b10abSAndroid Build Coastguard Worker
814*fb1b10abSAndroid Build Coastguard Worker #else
815*fb1b10abSAndroid Build Coastguard Worker (void)duration;
816*fb1b10abSAndroid Build Coastguard Worker new_qc = MODE_REALTIME;
817*fb1b10abSAndroid Build Coastguard Worker #endif
818*fb1b10abSAndroid Build Coastguard Worker
819*fb1b10abSAndroid Build Coastguard Worker if (deadline == VPX_DL_REALTIME) {
820*fb1b10abSAndroid Build Coastguard Worker new_qc = MODE_REALTIME;
821*fb1b10abSAndroid Build Coastguard Worker } else if (ctx->cfg.g_pass == VPX_RC_FIRST_PASS) {
822*fb1b10abSAndroid Build Coastguard Worker new_qc = MODE_FIRSTPASS;
823*fb1b10abSAndroid Build Coastguard Worker } else if (ctx->cfg.g_pass == VPX_RC_LAST_PASS) {
824*fb1b10abSAndroid Build Coastguard Worker new_qc =
825*fb1b10abSAndroid Build Coastguard Worker (new_qc == MODE_BESTQUALITY) ? MODE_SECONDPASS_BEST : MODE_SECONDPASS;
826*fb1b10abSAndroid Build Coastguard Worker }
827*fb1b10abSAndroid Build Coastguard Worker
828*fb1b10abSAndroid Build Coastguard Worker if (ctx->oxcf.Mode != new_qc) {
829*fb1b10abSAndroid Build Coastguard Worker ctx->oxcf.Mode = new_qc;
830*fb1b10abSAndroid Build Coastguard Worker vp8_change_config(ctx->cpi, &ctx->oxcf);
831*fb1b10abSAndroid Build Coastguard Worker }
832*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
833*fb1b10abSAndroid Build Coastguard Worker }
834*fb1b10abSAndroid Build Coastguard Worker
set_reference_and_update(vpx_codec_alg_priv_t * ctx,vpx_enc_frame_flags_t flags)835*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t set_reference_and_update(vpx_codec_alg_priv_t *ctx,
836*fb1b10abSAndroid Build Coastguard Worker vpx_enc_frame_flags_t flags) {
837*fb1b10abSAndroid Build Coastguard Worker /* Handle Flags */
838*fb1b10abSAndroid Build Coastguard Worker if (((flags & VP8_EFLAG_NO_UPD_GF) && (flags & VP8_EFLAG_FORCE_GF)) ||
839*fb1b10abSAndroid Build Coastguard Worker ((flags & VP8_EFLAG_NO_UPD_ARF) && (flags & VP8_EFLAG_FORCE_ARF))) {
840*fb1b10abSAndroid Build Coastguard Worker ctx->base.err_detail = "Conflicting flags.";
841*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
842*fb1b10abSAndroid Build Coastguard Worker }
843*fb1b10abSAndroid Build Coastguard Worker
844*fb1b10abSAndroid Build Coastguard Worker if (flags &
845*fb1b10abSAndroid Build Coastguard Worker (VP8_EFLAG_NO_REF_LAST | VP8_EFLAG_NO_REF_GF | VP8_EFLAG_NO_REF_ARF)) {
846*fb1b10abSAndroid Build Coastguard Worker int ref = 7;
847*fb1b10abSAndroid Build Coastguard Worker
848*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_REF_LAST) ref ^= VP8_LAST_FRAME;
849*fb1b10abSAndroid Build Coastguard Worker
850*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_REF_GF) ref ^= VP8_GOLD_FRAME;
851*fb1b10abSAndroid Build Coastguard Worker
852*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_REF_ARF) ref ^= VP8_ALTR_FRAME;
853*fb1b10abSAndroid Build Coastguard Worker
854*fb1b10abSAndroid Build Coastguard Worker vp8_use_as_reference(ctx->cpi, ref);
855*fb1b10abSAndroid Build Coastguard Worker }
856*fb1b10abSAndroid Build Coastguard Worker
857*fb1b10abSAndroid Build Coastguard Worker if (flags &
858*fb1b10abSAndroid Build Coastguard Worker (VP8_EFLAG_NO_UPD_LAST | VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF |
859*fb1b10abSAndroid Build Coastguard Worker VP8_EFLAG_FORCE_GF | VP8_EFLAG_FORCE_ARF)) {
860*fb1b10abSAndroid Build Coastguard Worker int upd = 7;
861*fb1b10abSAndroid Build Coastguard Worker
862*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_UPD_LAST) upd ^= VP8_LAST_FRAME;
863*fb1b10abSAndroid Build Coastguard Worker
864*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_UPD_GF) upd ^= VP8_GOLD_FRAME;
865*fb1b10abSAndroid Build Coastguard Worker
866*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_UPD_ARF) upd ^= VP8_ALTR_FRAME;
867*fb1b10abSAndroid Build Coastguard Worker
868*fb1b10abSAndroid Build Coastguard Worker vp8_update_reference(ctx->cpi, upd);
869*fb1b10abSAndroid Build Coastguard Worker }
870*fb1b10abSAndroid Build Coastguard Worker
871*fb1b10abSAndroid Build Coastguard Worker if (flags & VP8_EFLAG_NO_UPD_ENTROPY) {
872*fb1b10abSAndroid Build Coastguard Worker vp8_update_entropy(ctx->cpi, 0);
873*fb1b10abSAndroid Build Coastguard Worker }
874*fb1b10abSAndroid Build Coastguard Worker
875*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
876*fb1b10abSAndroid Build Coastguard Worker }
877*fb1b10abSAndroid Build Coastguard Worker
vp8e_encode(vpx_codec_alg_priv_t * ctx,const vpx_image_t * img,vpx_codec_pts_t pts,unsigned long duration,vpx_enc_frame_flags_t enc_flags,vpx_enc_deadline_t deadline)878*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_encode(vpx_codec_alg_priv_t *ctx,
879*fb1b10abSAndroid Build Coastguard Worker const vpx_image_t *img, vpx_codec_pts_t pts,
880*fb1b10abSAndroid Build Coastguard Worker unsigned long duration,
881*fb1b10abSAndroid Build Coastguard Worker vpx_enc_frame_flags_t enc_flags,
882*fb1b10abSAndroid Build Coastguard Worker vpx_enc_deadline_t deadline) {
883*fb1b10abSAndroid Build Coastguard Worker volatile vpx_codec_err_t res = VPX_CODEC_OK;
884*fb1b10abSAndroid Build Coastguard Worker // Make a copy as volatile to avoid -Wclobbered with longjmp.
885*fb1b10abSAndroid Build Coastguard Worker volatile vpx_enc_frame_flags_t flags = enc_flags;
886*fb1b10abSAndroid Build Coastguard Worker volatile vpx_codec_pts_t pts_val = pts;
887*fb1b10abSAndroid Build Coastguard Worker
888*fb1b10abSAndroid Build Coastguard Worker if (!ctx->cfg.rc_target_bitrate) {
889*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_MULTI_RES_ENCODING
890*fb1b10abSAndroid Build Coastguard Worker if (!ctx->cpi) return VPX_CODEC_ERROR;
891*fb1b10abSAndroid Build Coastguard Worker if (ctx->cpi->oxcf.mr_total_resolutions > 1) {
892*fb1b10abSAndroid Build Coastguard Worker LOWER_RES_FRAME_INFO *low_res_frame_info =
893*fb1b10abSAndroid Build Coastguard Worker (LOWER_RES_FRAME_INFO *)ctx->cpi->oxcf.mr_low_res_mode_info;
894*fb1b10abSAndroid Build Coastguard Worker if (!low_res_frame_info) return VPX_CODEC_ERROR;
895*fb1b10abSAndroid Build Coastguard Worker low_res_frame_info->skip_encoding_prev_stream = 1;
896*fb1b10abSAndroid Build Coastguard Worker if (ctx->cpi->oxcf.mr_encoder_id == 0)
897*fb1b10abSAndroid Build Coastguard Worker low_res_frame_info->skip_encoding_base_stream = 1;
898*fb1b10abSAndroid Build Coastguard Worker }
899*fb1b10abSAndroid Build Coastguard Worker #endif
900*fb1b10abSAndroid Build Coastguard Worker return res;
901*fb1b10abSAndroid Build Coastguard Worker }
902*fb1b10abSAndroid Build Coastguard Worker
903*fb1b10abSAndroid Build Coastguard Worker if (img) res = validate_img(ctx, img);
904*fb1b10abSAndroid Build Coastguard Worker
905*fb1b10abSAndroid Build Coastguard Worker if (!res) res = validate_config(ctx, &ctx->cfg, &ctx->vp8_cfg, 1);
906*fb1b10abSAndroid Build Coastguard Worker
907*fb1b10abSAndroid Build Coastguard Worker if (!res) res = pick_quickcompress_mode(ctx, duration, deadline);
908*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pkt_list_init(&ctx->pkt_list);
909*fb1b10abSAndroid Build Coastguard Worker
910*fb1b10abSAndroid Build Coastguard Worker // If no flags are set in the encode call, then use the frame flags as
911*fb1b10abSAndroid Build Coastguard Worker // defined via the control function: vp8e_set_frame_flags.
912*fb1b10abSAndroid Build Coastguard Worker if (!flags) {
913*fb1b10abSAndroid Build Coastguard Worker flags = ctx->control_frame_flags;
914*fb1b10abSAndroid Build Coastguard Worker }
915*fb1b10abSAndroid Build Coastguard Worker ctx->control_frame_flags = 0;
916*fb1b10abSAndroid Build Coastguard Worker
917*fb1b10abSAndroid Build Coastguard Worker if (!res) res = set_reference_and_update(ctx, flags);
918*fb1b10abSAndroid Build Coastguard Worker
919*fb1b10abSAndroid Build Coastguard Worker /* Handle fixed keyframe intervals */
920*fb1b10abSAndroid Build Coastguard Worker if (ctx->cfg.kf_mode == VPX_KF_AUTO &&
921*fb1b10abSAndroid Build Coastguard Worker ctx->cfg.kf_min_dist == ctx->cfg.kf_max_dist) {
922*fb1b10abSAndroid Build Coastguard Worker if (++ctx->fixed_kf_cntr > ctx->cfg.kf_min_dist) {
923*fb1b10abSAndroid Build Coastguard Worker flags |= VPX_EFLAG_FORCE_KF;
924*fb1b10abSAndroid Build Coastguard Worker ctx->fixed_kf_cntr = 1;
925*fb1b10abSAndroid Build Coastguard Worker }
926*fb1b10abSAndroid Build Coastguard Worker }
927*fb1b10abSAndroid Build Coastguard Worker
928*fb1b10abSAndroid Build Coastguard Worker /* Initialize the encoder instance on the first frame*/
929*fb1b10abSAndroid Build Coastguard Worker if (!res && ctx->cpi) {
930*fb1b10abSAndroid Build Coastguard Worker unsigned int lib_flags;
931*fb1b10abSAndroid Build Coastguard Worker int64_t dst_time_stamp, dst_end_time_stamp;
932*fb1b10abSAndroid Build Coastguard Worker size_t size, cx_data_sz;
933*fb1b10abSAndroid Build Coastguard Worker unsigned char *cx_data;
934*fb1b10abSAndroid Build Coastguard Worker unsigned char *cx_data_end;
935*fb1b10abSAndroid Build Coastguard Worker int comp_data_state = 0;
936*fb1b10abSAndroid Build Coastguard Worker
937*fb1b10abSAndroid Build Coastguard Worker if (setjmp(ctx->cpi->common.error.jmp)) {
938*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
939*fb1b10abSAndroid Build Coastguard Worker res = update_error_state(ctx, &ctx->cpi->common.error);
940*fb1b10abSAndroid Build Coastguard Worker vpx_clear_system_state();
941*fb1b10abSAndroid Build Coastguard Worker return res;
942*fb1b10abSAndroid Build Coastguard Worker }
943*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 1;
944*fb1b10abSAndroid Build Coastguard Worker
945*fb1b10abSAndroid Build Coastguard Worker /* Set up internal flags */
946*fb1b10abSAndroid Build Coastguard Worker if (ctx->base.init_flags & VPX_CODEC_USE_PSNR) {
947*fb1b10abSAndroid Build Coastguard Worker ((VP8_COMP *)ctx->cpi)->b_calculate_psnr = 1;
948*fb1b10abSAndroid Build Coastguard Worker }
949*fb1b10abSAndroid Build Coastguard Worker
950*fb1b10abSAndroid Build Coastguard Worker if (ctx->base.init_flags & VPX_CODEC_USE_OUTPUT_PARTITION) {
951*fb1b10abSAndroid Build Coastguard Worker ((VP8_COMP *)ctx->cpi)->output_partition = 1;
952*fb1b10abSAndroid Build Coastguard Worker }
953*fb1b10abSAndroid Build Coastguard Worker
954*fb1b10abSAndroid Build Coastguard Worker /* Convert API flags to internal codec lib flags */
955*fb1b10abSAndroid Build Coastguard Worker lib_flags = (flags & VPX_EFLAG_FORCE_KF) ? FRAMEFLAGS_KEY : 0;
956*fb1b10abSAndroid Build Coastguard Worker
957*fb1b10abSAndroid Build Coastguard Worker if (img != NULL) {
958*fb1b10abSAndroid Build Coastguard Worker YV12_BUFFER_CONFIG sd;
959*fb1b10abSAndroid Build Coastguard Worker
960*fb1b10abSAndroid Build Coastguard Worker if (!ctx->pts_offset_initialized) {
961*fb1b10abSAndroid Build Coastguard Worker ctx->pts_offset = pts_val;
962*fb1b10abSAndroid Build Coastguard Worker ctx->pts_offset_initialized = 1;
963*fb1b10abSAndroid Build Coastguard Worker }
964*fb1b10abSAndroid Build Coastguard Worker if (pts_val < ctx->pts_offset) {
965*fb1b10abSAndroid Build Coastguard Worker vpx_internal_error(&ctx->cpi->common.error, VPX_CODEC_INVALID_PARAM,
966*fb1b10abSAndroid Build Coastguard Worker "pts is smaller than initial pts");
967*fb1b10abSAndroid Build Coastguard Worker }
968*fb1b10abSAndroid Build Coastguard Worker pts_val -= ctx->pts_offset;
969*fb1b10abSAndroid Build Coastguard Worker if (pts_val > INT64_MAX / ctx->timestamp_ratio.num) {
970*fb1b10abSAndroid Build Coastguard Worker vpx_internal_error(
971*fb1b10abSAndroid Build Coastguard Worker &ctx->cpi->common.error, VPX_CODEC_INVALID_PARAM,
972*fb1b10abSAndroid Build Coastguard Worker "conversion of relative pts to ticks would overflow");
973*fb1b10abSAndroid Build Coastguard Worker }
974*fb1b10abSAndroid Build Coastguard Worker dst_time_stamp =
975*fb1b10abSAndroid Build Coastguard Worker pts_val * ctx->timestamp_ratio.num / ctx->timestamp_ratio.den;
976*fb1b10abSAndroid Build Coastguard Worker #if ULONG_MAX > INT64_MAX
977*fb1b10abSAndroid Build Coastguard Worker if (duration > INT64_MAX) {
978*fb1b10abSAndroid Build Coastguard Worker vpx_internal_error(&ctx->cpi->common.error, VPX_CODEC_INVALID_PARAM,
979*fb1b10abSAndroid Build Coastguard Worker "duration is too big");
980*fb1b10abSAndroid Build Coastguard Worker }
981*fb1b10abSAndroid Build Coastguard Worker #endif
982*fb1b10abSAndroid Build Coastguard Worker if (pts_val > INT64_MAX - (int64_t)duration) {
983*fb1b10abSAndroid Build Coastguard Worker vpx_internal_error(&ctx->cpi->common.error, VPX_CODEC_INVALID_PARAM,
984*fb1b10abSAndroid Build Coastguard Worker "relative pts + duration is too big");
985*fb1b10abSAndroid Build Coastguard Worker }
986*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pts_t pts_end = pts_val + (int64_t)duration;
987*fb1b10abSAndroid Build Coastguard Worker if (pts_end > INT64_MAX / ctx->timestamp_ratio.num) {
988*fb1b10abSAndroid Build Coastguard Worker vpx_internal_error(
989*fb1b10abSAndroid Build Coastguard Worker &ctx->cpi->common.error, VPX_CODEC_INVALID_PARAM,
990*fb1b10abSAndroid Build Coastguard Worker "conversion of relative pts + duration to ticks would overflow");
991*fb1b10abSAndroid Build Coastguard Worker }
992*fb1b10abSAndroid Build Coastguard Worker dst_end_time_stamp =
993*fb1b10abSAndroid Build Coastguard Worker pts_end * ctx->timestamp_ratio.num / ctx->timestamp_ratio.den;
994*fb1b10abSAndroid Build Coastguard Worker
995*fb1b10abSAndroid Build Coastguard Worker res = image2yuvconfig(img, &sd);
996*fb1b10abSAndroid Build Coastguard Worker
997*fb1b10abSAndroid Build Coastguard Worker if (vp8_receive_raw_frame(ctx->cpi, ctx->next_frame_flag | lib_flags, &sd,
998*fb1b10abSAndroid Build Coastguard Worker dst_time_stamp, dst_end_time_stamp)) {
999*fb1b10abSAndroid Build Coastguard Worker VP8_COMP *cpi = (VP8_COMP *)ctx->cpi;
1000*fb1b10abSAndroid Build Coastguard Worker res = update_error_state(ctx, &cpi->common.error);
1001*fb1b10abSAndroid Build Coastguard Worker }
1002*fb1b10abSAndroid Build Coastguard Worker
1003*fb1b10abSAndroid Build Coastguard Worker /* reset for next frame */
1004*fb1b10abSAndroid Build Coastguard Worker ctx->next_frame_flag = 0;
1005*fb1b10abSAndroid Build Coastguard Worker }
1006*fb1b10abSAndroid Build Coastguard Worker
1007*fb1b10abSAndroid Build Coastguard Worker cx_data = ctx->cx_data;
1008*fb1b10abSAndroid Build Coastguard Worker cx_data_sz = ctx->cx_data_sz;
1009*fb1b10abSAndroid Build Coastguard Worker cx_data_end = ctx->cx_data + cx_data_sz;
1010*fb1b10abSAndroid Build Coastguard Worker lib_flags = 0;
1011*fb1b10abSAndroid Build Coastguard Worker
1012*fb1b10abSAndroid Build Coastguard Worker while (cx_data_sz >= ctx->cx_data_sz / 2) {
1013*fb1b10abSAndroid Build Coastguard Worker comp_data_state = vp8_get_compressed_data(
1014*fb1b10abSAndroid Build Coastguard Worker ctx->cpi, &lib_flags, &size, cx_data, cx_data_end, &dst_time_stamp,
1015*fb1b10abSAndroid Build Coastguard Worker &dst_end_time_stamp, !img);
1016*fb1b10abSAndroid Build Coastguard Worker
1017*fb1b10abSAndroid Build Coastguard Worker if (comp_data_state == VPX_CODEC_CORRUPT_FRAME) {
1018*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
1019*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_CORRUPT_FRAME;
1020*fb1b10abSAndroid Build Coastguard Worker } else if (comp_data_state == -1) {
1021*fb1b10abSAndroid Build Coastguard Worker break;
1022*fb1b10abSAndroid Build Coastguard Worker }
1023*fb1b10abSAndroid Build Coastguard Worker
1024*fb1b10abSAndroid Build Coastguard Worker if (size) {
1025*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pts_t round, delta;
1026*fb1b10abSAndroid Build Coastguard Worker vpx_codec_cx_pkt_t pkt;
1027*fb1b10abSAndroid Build Coastguard Worker VP8_COMP *cpi = (VP8_COMP *)ctx->cpi;
1028*fb1b10abSAndroid Build Coastguard Worker
1029*fb1b10abSAndroid Build Coastguard Worker /* Add the frame packet to the list of returned packets. */
1030*fb1b10abSAndroid Build Coastguard Worker round = (vpx_codec_pts_t)ctx->timestamp_ratio.num / 2;
1031*fb1b10abSAndroid Build Coastguard Worker if (round > 0) --round;
1032*fb1b10abSAndroid Build Coastguard Worker delta = (dst_end_time_stamp - dst_time_stamp);
1033*fb1b10abSAndroid Build Coastguard Worker pkt.kind = VPX_CODEC_CX_FRAME_PKT;
1034*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.pts =
1035*fb1b10abSAndroid Build Coastguard Worker (dst_time_stamp * ctx->timestamp_ratio.den + round) /
1036*fb1b10abSAndroid Build Coastguard Worker ctx->timestamp_ratio.num +
1037*fb1b10abSAndroid Build Coastguard Worker ctx->pts_offset;
1038*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.duration =
1039*fb1b10abSAndroid Build Coastguard Worker (unsigned long)((delta * ctx->timestamp_ratio.den + round) /
1040*fb1b10abSAndroid Build Coastguard Worker ctx->timestamp_ratio.num);
1041*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.flags = lib_flags << 16;
1042*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.width[0] = cpi->common.Width;
1043*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.height[0] = cpi->common.Height;
1044*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.spatial_layer_encoded[0] = 1;
1045*fb1b10abSAndroid Build Coastguard Worker
1046*fb1b10abSAndroid Build Coastguard Worker if (lib_flags & FRAMEFLAGS_KEY) {
1047*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.flags |= VPX_FRAME_IS_KEY;
1048*fb1b10abSAndroid Build Coastguard Worker }
1049*fb1b10abSAndroid Build Coastguard Worker
1050*fb1b10abSAndroid Build Coastguard Worker if (!cpi->common.show_frame) {
1051*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.flags |= VPX_FRAME_IS_INVISIBLE;
1052*fb1b10abSAndroid Build Coastguard Worker
1053*fb1b10abSAndroid Build Coastguard Worker /* This timestamp should be as close as possible to the
1054*fb1b10abSAndroid Build Coastguard Worker * prior PTS so that if a decoder uses pts to schedule when
1055*fb1b10abSAndroid Build Coastguard Worker * to do this, we start right after last frame was decoded.
1056*fb1b10abSAndroid Build Coastguard Worker * Invisible frames have no duration.
1057*fb1b10abSAndroid Build Coastguard Worker */
1058*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.pts =
1059*fb1b10abSAndroid Build Coastguard Worker ((cpi->last_time_stamp_seen * ctx->timestamp_ratio.den + round) /
1060*fb1b10abSAndroid Build Coastguard Worker ctx->timestamp_ratio.num) +
1061*fb1b10abSAndroid Build Coastguard Worker ctx->pts_offset + 1;
1062*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.duration = 0;
1063*fb1b10abSAndroid Build Coastguard Worker }
1064*fb1b10abSAndroid Build Coastguard Worker
1065*fb1b10abSAndroid Build Coastguard Worker if (cpi->droppable) pkt.data.frame.flags |= VPX_FRAME_IS_DROPPABLE;
1066*fb1b10abSAndroid Build Coastguard Worker
1067*fb1b10abSAndroid Build Coastguard Worker if (cpi->output_partition) {
1068*fb1b10abSAndroid Build Coastguard Worker int i;
1069*fb1b10abSAndroid Build Coastguard Worker const int num_partitions =
1070*fb1b10abSAndroid Build Coastguard Worker (1 << cpi->common.multi_token_partition) + 1;
1071*fb1b10abSAndroid Build Coastguard Worker
1072*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.flags |= VPX_FRAME_IS_FRAGMENT;
1073*fb1b10abSAndroid Build Coastguard Worker
1074*fb1b10abSAndroid Build Coastguard Worker for (i = 0; i < num_partitions; ++i) {
1075*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_REALTIME_ONLY & CONFIG_ONTHEFLY_BITPACKING
1076*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.buf = cpi->partition_d[i];
1077*fb1b10abSAndroid Build Coastguard Worker #else
1078*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.buf = cx_data;
1079*fb1b10abSAndroid Build Coastguard Worker cx_data += cpi->partition_sz[i];
1080*fb1b10abSAndroid Build Coastguard Worker cx_data_sz -= cpi->partition_sz[i];
1081*fb1b10abSAndroid Build Coastguard Worker #endif
1082*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.sz = cpi->partition_sz[i];
1083*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.partition_id = i;
1084*fb1b10abSAndroid Build Coastguard Worker /* don't set the fragment bit for the last partition */
1085*fb1b10abSAndroid Build Coastguard Worker if (i == (num_partitions - 1)) {
1086*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.flags &= ~VPX_FRAME_IS_FRAGMENT;
1087*fb1b10abSAndroid Build Coastguard Worker }
1088*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pkt_list_add(&ctx->pkt_list.head, &pkt);
1089*fb1b10abSAndroid Build Coastguard Worker }
1090*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_REALTIME_ONLY & CONFIG_ONTHEFLY_BITPACKING
1091*fb1b10abSAndroid Build Coastguard Worker /* In lagged mode the encoder can buffer multiple frames.
1092*fb1b10abSAndroid Build Coastguard Worker * We don't want this in partitioned output because
1093*fb1b10abSAndroid Build Coastguard Worker * partitions are spread all over the output buffer.
1094*fb1b10abSAndroid Build Coastguard Worker * So, force an exit!
1095*fb1b10abSAndroid Build Coastguard Worker */
1096*fb1b10abSAndroid Build Coastguard Worker cx_data_sz -= ctx->cx_data_sz / 2;
1097*fb1b10abSAndroid Build Coastguard Worker #endif
1098*fb1b10abSAndroid Build Coastguard Worker } else {
1099*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.buf = cx_data;
1100*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.sz = size;
1101*fb1b10abSAndroid Build Coastguard Worker pkt.data.frame.partition_id = -1;
1102*fb1b10abSAndroid Build Coastguard Worker vpx_codec_pkt_list_add(&ctx->pkt_list.head, &pkt);
1103*fb1b10abSAndroid Build Coastguard Worker cx_data += size;
1104*fb1b10abSAndroid Build Coastguard Worker cx_data_sz -= size;
1105*fb1b10abSAndroid Build Coastguard Worker }
1106*fb1b10abSAndroid Build Coastguard Worker }
1107*fb1b10abSAndroid Build Coastguard Worker }
1108*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->common.error.setjmp = 0;
1109*fb1b10abSAndroid Build Coastguard Worker }
1110*fb1b10abSAndroid Build Coastguard Worker
1111*fb1b10abSAndroid Build Coastguard Worker return res;
1112*fb1b10abSAndroid Build Coastguard Worker }
1113*fb1b10abSAndroid Build Coastguard Worker
vp8e_get_cxdata(vpx_codec_alg_priv_t * ctx,vpx_codec_iter_t * iter)1114*fb1b10abSAndroid Build Coastguard Worker static const vpx_codec_cx_pkt_t *vp8e_get_cxdata(vpx_codec_alg_priv_t *ctx,
1115*fb1b10abSAndroid Build Coastguard Worker vpx_codec_iter_t *iter) {
1116*fb1b10abSAndroid Build Coastguard Worker return vpx_codec_pkt_list_get(&ctx->pkt_list.head, iter);
1117*fb1b10abSAndroid Build Coastguard Worker }
1118*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_reference(vpx_codec_alg_priv_t * ctx,va_list args)1119*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_reference(vpx_codec_alg_priv_t *ctx,
1120*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1121*fb1b10abSAndroid Build Coastguard Worker vpx_ref_frame_t *data = va_arg(args, vpx_ref_frame_t *);
1122*fb1b10abSAndroid Build Coastguard Worker
1123*fb1b10abSAndroid Build Coastguard Worker if (data) {
1124*fb1b10abSAndroid Build Coastguard Worker vpx_ref_frame_t *frame = (vpx_ref_frame_t *)data;
1125*fb1b10abSAndroid Build Coastguard Worker YV12_BUFFER_CONFIG sd;
1126*fb1b10abSAndroid Build Coastguard Worker
1127*fb1b10abSAndroid Build Coastguard Worker image2yuvconfig(&frame->img, &sd);
1128*fb1b10abSAndroid Build Coastguard Worker vp8_set_reference(ctx->cpi, frame->frame_type, &sd);
1129*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1130*fb1b10abSAndroid Build Coastguard Worker } else {
1131*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1132*fb1b10abSAndroid Build Coastguard Worker }
1133*fb1b10abSAndroid Build Coastguard Worker }
1134*fb1b10abSAndroid Build Coastguard Worker
vp8e_get_reference(vpx_codec_alg_priv_t * ctx,va_list args)1135*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_get_reference(vpx_codec_alg_priv_t *ctx,
1136*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1137*fb1b10abSAndroid Build Coastguard Worker vpx_ref_frame_t *data = va_arg(args, vpx_ref_frame_t *);
1138*fb1b10abSAndroid Build Coastguard Worker
1139*fb1b10abSAndroid Build Coastguard Worker if (data) {
1140*fb1b10abSAndroid Build Coastguard Worker vpx_ref_frame_t *frame = (vpx_ref_frame_t *)data;
1141*fb1b10abSAndroid Build Coastguard Worker YV12_BUFFER_CONFIG sd;
1142*fb1b10abSAndroid Build Coastguard Worker
1143*fb1b10abSAndroid Build Coastguard Worker image2yuvconfig(&frame->img, &sd);
1144*fb1b10abSAndroid Build Coastguard Worker vp8_get_reference(ctx->cpi, frame->frame_type, &sd);
1145*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1146*fb1b10abSAndroid Build Coastguard Worker } else {
1147*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1148*fb1b10abSAndroid Build Coastguard Worker }
1149*fb1b10abSAndroid Build Coastguard Worker }
1150*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_previewpp(vpx_codec_alg_priv_t * ctx,va_list args)1151*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_previewpp(vpx_codec_alg_priv_t *ctx,
1152*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1153*fb1b10abSAndroid Build Coastguard Worker #if CONFIG_POSTPROC
1154*fb1b10abSAndroid Build Coastguard Worker vp8_postproc_cfg_t *data = va_arg(args, vp8_postproc_cfg_t *);
1155*fb1b10abSAndroid Build Coastguard Worker
1156*fb1b10abSAndroid Build Coastguard Worker if (data) {
1157*fb1b10abSAndroid Build Coastguard Worker ctx->preview_ppcfg = *((vp8_postproc_cfg_t *)data);
1158*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1159*fb1b10abSAndroid Build Coastguard Worker } else {
1160*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1161*fb1b10abSAndroid Build Coastguard Worker }
1162*fb1b10abSAndroid Build Coastguard Worker #else
1163*fb1b10abSAndroid Build Coastguard Worker (void)ctx;
1164*fb1b10abSAndroid Build Coastguard Worker (void)args;
1165*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INCAPABLE;
1166*fb1b10abSAndroid Build Coastguard Worker #endif
1167*fb1b10abSAndroid Build Coastguard Worker }
1168*fb1b10abSAndroid Build Coastguard Worker
vp8e_get_preview(vpx_codec_alg_priv_t * ctx)1169*fb1b10abSAndroid Build Coastguard Worker static vpx_image_t *vp8e_get_preview(vpx_codec_alg_priv_t *ctx) {
1170*fb1b10abSAndroid Build Coastguard Worker YV12_BUFFER_CONFIG sd;
1171*fb1b10abSAndroid Build Coastguard Worker vp8_ppflags_t flags;
1172*fb1b10abSAndroid Build Coastguard Worker vp8_zero(flags);
1173*fb1b10abSAndroid Build Coastguard Worker
1174*fb1b10abSAndroid Build Coastguard Worker if (ctx->preview_ppcfg.post_proc_flag) {
1175*fb1b10abSAndroid Build Coastguard Worker flags.post_proc_flag = ctx->preview_ppcfg.post_proc_flag;
1176*fb1b10abSAndroid Build Coastguard Worker flags.deblocking_level = ctx->preview_ppcfg.deblocking_level;
1177*fb1b10abSAndroid Build Coastguard Worker flags.noise_level = ctx->preview_ppcfg.noise_level;
1178*fb1b10abSAndroid Build Coastguard Worker }
1179*fb1b10abSAndroid Build Coastguard Worker
1180*fb1b10abSAndroid Build Coastguard Worker if (0 == vp8_get_preview_raw_frame(ctx->cpi, &sd, &flags)) {
1181*fb1b10abSAndroid Build Coastguard Worker /*
1182*fb1b10abSAndroid Build Coastguard Worker vpx_img_wrap(&ctx->preview_img, VPX_IMG_FMT_YV12,
1183*fb1b10abSAndroid Build Coastguard Worker sd.y_width + 2*VP8BORDERINPIXELS,
1184*fb1b10abSAndroid Build Coastguard Worker sd.y_height + 2*VP8BORDERINPIXELS,
1185*fb1b10abSAndroid Build Coastguard Worker 1,
1186*fb1b10abSAndroid Build Coastguard Worker sd.buffer_alloc);
1187*fb1b10abSAndroid Build Coastguard Worker vpx_img_set_rect(&ctx->preview_img,
1188*fb1b10abSAndroid Build Coastguard Worker VP8BORDERINPIXELS, VP8BORDERINPIXELS,
1189*fb1b10abSAndroid Build Coastguard Worker sd.y_width, sd.y_height);
1190*fb1b10abSAndroid Build Coastguard Worker */
1191*fb1b10abSAndroid Build Coastguard Worker
1192*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.bps = 12;
1193*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.planes[VPX_PLANE_Y] = sd.y_buffer;
1194*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.planes[VPX_PLANE_U] = sd.u_buffer;
1195*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.planes[VPX_PLANE_V] = sd.v_buffer;
1196*fb1b10abSAndroid Build Coastguard Worker
1197*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.fmt = VPX_IMG_FMT_I420;
1198*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.x_chroma_shift = 1;
1199*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.y_chroma_shift = 1;
1200*fb1b10abSAndroid Build Coastguard Worker
1201*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.d_w = sd.y_width;
1202*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.d_h = sd.y_height;
1203*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.stride[VPX_PLANE_Y] = sd.y_stride;
1204*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.stride[VPX_PLANE_U] = sd.uv_stride;
1205*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.stride[VPX_PLANE_V] = sd.uv_stride;
1206*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.w = sd.y_width;
1207*fb1b10abSAndroid Build Coastguard Worker ctx->preview_img.h = sd.y_height;
1208*fb1b10abSAndroid Build Coastguard Worker
1209*fb1b10abSAndroid Build Coastguard Worker return &ctx->preview_img;
1210*fb1b10abSAndroid Build Coastguard Worker } else {
1211*fb1b10abSAndroid Build Coastguard Worker return NULL;
1212*fb1b10abSAndroid Build Coastguard Worker }
1213*fb1b10abSAndroid Build Coastguard Worker }
1214*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_frame_flags(vpx_codec_alg_priv_t * ctx,va_list args)1215*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_frame_flags(vpx_codec_alg_priv_t *ctx,
1216*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1217*fb1b10abSAndroid Build Coastguard Worker int frame_flags = va_arg(args, int);
1218*fb1b10abSAndroid Build Coastguard Worker ctx->control_frame_flags = frame_flags;
1219*fb1b10abSAndroid Build Coastguard Worker return set_reference_and_update(ctx, frame_flags);
1220*fb1b10abSAndroid Build Coastguard Worker }
1221*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_temporal_layer_id(vpx_codec_alg_priv_t * ctx,va_list args)1222*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_temporal_layer_id(vpx_codec_alg_priv_t *ctx,
1223*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1224*fb1b10abSAndroid Build Coastguard Worker int layer_id = va_arg(args, int);
1225*fb1b10abSAndroid Build Coastguard Worker if (layer_id < 0 || layer_id >= (int)ctx->cfg.ts_number_layers) {
1226*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1227*fb1b10abSAndroid Build Coastguard Worker }
1228*fb1b10abSAndroid Build Coastguard Worker ctx->cpi->temporal_layer_id = layer_id;
1229*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1230*fb1b10abSAndroid Build Coastguard Worker }
1231*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_roi_map(vpx_codec_alg_priv_t * ctx,va_list args)1232*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_roi_map(vpx_codec_alg_priv_t *ctx,
1233*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1234*fb1b10abSAndroid Build Coastguard Worker vpx_roi_map_t *data = va_arg(args, vpx_roi_map_t *);
1235*fb1b10abSAndroid Build Coastguard Worker
1236*fb1b10abSAndroid Build Coastguard Worker if (data) {
1237*fb1b10abSAndroid Build Coastguard Worker vpx_roi_map_t *roi = (vpx_roi_map_t *)data;
1238*fb1b10abSAndroid Build Coastguard Worker
1239*fb1b10abSAndroid Build Coastguard Worker if (!vp8_set_roimap(ctx->cpi, roi->roi_map, roi->rows, roi->cols,
1240*fb1b10abSAndroid Build Coastguard Worker roi->delta_q, roi->delta_lf, roi->static_threshold)) {
1241*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1242*fb1b10abSAndroid Build Coastguard Worker } else {
1243*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1244*fb1b10abSAndroid Build Coastguard Worker }
1245*fb1b10abSAndroid Build Coastguard Worker } else {
1246*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1247*fb1b10abSAndroid Build Coastguard Worker }
1248*fb1b10abSAndroid Build Coastguard Worker }
1249*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_activemap(vpx_codec_alg_priv_t * ctx,va_list args)1250*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_activemap(vpx_codec_alg_priv_t *ctx,
1251*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1252*fb1b10abSAndroid Build Coastguard Worker vpx_active_map_t *data = va_arg(args, vpx_active_map_t *);
1253*fb1b10abSAndroid Build Coastguard Worker
1254*fb1b10abSAndroid Build Coastguard Worker if (data) {
1255*fb1b10abSAndroid Build Coastguard Worker vpx_active_map_t *map = (vpx_active_map_t *)data;
1256*fb1b10abSAndroid Build Coastguard Worker
1257*fb1b10abSAndroid Build Coastguard Worker if (!vp8_set_active_map(ctx->cpi, map->active_map, map->rows, map->cols)) {
1258*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1259*fb1b10abSAndroid Build Coastguard Worker } else {
1260*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1261*fb1b10abSAndroid Build Coastguard Worker }
1262*fb1b10abSAndroid Build Coastguard Worker } else {
1263*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1264*fb1b10abSAndroid Build Coastguard Worker }
1265*fb1b10abSAndroid Build Coastguard Worker }
1266*fb1b10abSAndroid Build Coastguard Worker
vp8e_set_scalemode(vpx_codec_alg_priv_t * ctx,va_list args)1267*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_err_t vp8e_set_scalemode(vpx_codec_alg_priv_t *ctx,
1268*fb1b10abSAndroid Build Coastguard Worker va_list args) {
1269*fb1b10abSAndroid Build Coastguard Worker vpx_scaling_mode_t *data = va_arg(args, vpx_scaling_mode_t *);
1270*fb1b10abSAndroid Build Coastguard Worker
1271*fb1b10abSAndroid Build Coastguard Worker if (data) {
1272*fb1b10abSAndroid Build Coastguard Worker int res;
1273*fb1b10abSAndroid Build Coastguard Worker vpx_scaling_mode_t scalemode = *(vpx_scaling_mode_t *)data;
1274*fb1b10abSAndroid Build Coastguard Worker res = vp8_set_internal_size(ctx->cpi, scalemode.h_scaling_mode,
1275*fb1b10abSAndroid Build Coastguard Worker scalemode.v_scaling_mode);
1276*fb1b10abSAndroid Build Coastguard Worker
1277*fb1b10abSAndroid Build Coastguard Worker if (!res) {
1278*fb1b10abSAndroid Build Coastguard Worker /*force next frame a key frame to effect scaling mode */
1279*fb1b10abSAndroid Build Coastguard Worker ctx->next_frame_flag |= FRAMEFLAGS_KEY;
1280*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_OK;
1281*fb1b10abSAndroid Build Coastguard Worker } else {
1282*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1283*fb1b10abSAndroid Build Coastguard Worker }
1284*fb1b10abSAndroid Build Coastguard Worker } else {
1285*fb1b10abSAndroid Build Coastguard Worker return VPX_CODEC_INVALID_PARAM;
1286*fb1b10abSAndroid Build Coastguard Worker }
1287*fb1b10abSAndroid Build Coastguard Worker }
1288*fb1b10abSAndroid Build Coastguard Worker
1289*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_ctrl_fn_map_t vp8e_ctf_maps[] = {
1290*fb1b10abSAndroid Build Coastguard Worker { VP8_SET_REFERENCE, vp8e_set_reference },
1291*fb1b10abSAndroid Build Coastguard Worker { VP8_COPY_REFERENCE, vp8e_get_reference },
1292*fb1b10abSAndroid Build Coastguard Worker { VP8_SET_POSTPROC, vp8e_set_previewpp },
1293*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_FRAME_FLAGS, vp8e_set_frame_flags },
1294*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_TEMPORAL_LAYER_ID, vp8e_set_temporal_layer_id },
1295*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ROI_MAP, vp8e_set_roi_map },
1296*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ACTIVEMAP, vp8e_set_activemap },
1297*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_SCALEMODE, vp8e_set_scalemode },
1298*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_CPUUSED, set_cpu_used },
1299*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_NOISE_SENSITIVITY, set_noise_sensitivity },
1300*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ENABLEAUTOALTREF, set_enable_auto_alt_ref },
1301*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_SHARPNESS, set_sharpness },
1302*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_STATIC_THRESHOLD, set_static_thresh },
1303*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_TOKEN_PARTITIONS, set_token_partitions },
1304*fb1b10abSAndroid Build Coastguard Worker { VP8E_GET_LAST_QUANTIZER, get_quantizer },
1305*fb1b10abSAndroid Build Coastguard Worker { VP8E_GET_LAST_QUANTIZER_64, get_quantizer64 },
1306*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ARNR_MAXFRAMES, set_arnr_max_frames },
1307*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ARNR_STRENGTH, set_arnr_strength },
1308*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_ARNR_TYPE, set_arnr_type },
1309*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_TUNING, set_tuning },
1310*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_CQ_LEVEL, set_cq_level },
1311*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_MAX_INTRA_BITRATE_PCT, set_rc_max_intra_bitrate_pct },
1312*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_SCREEN_CONTENT_MODE, set_screen_content_mode },
1313*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_GF_CBR_BOOST_PCT, ctrl_set_rc_gf_cbr_boost_pct },
1314*fb1b10abSAndroid Build Coastguard Worker { VP8E_SET_RTC_EXTERNAL_RATECTRL, ctrl_set_rtc_external_ratectrl },
1315*fb1b10abSAndroid Build Coastguard Worker { -1, NULL },
1316*fb1b10abSAndroid Build Coastguard Worker };
1317*fb1b10abSAndroid Build Coastguard Worker
1318*fb1b10abSAndroid Build Coastguard Worker static vpx_codec_enc_cfg_map_t vp8e_usage_cfg_map[] = {
1319*fb1b10abSAndroid Build Coastguard Worker { 0,
1320*fb1b10abSAndroid Build Coastguard Worker {
1321*fb1b10abSAndroid Build Coastguard Worker 0, /* g_usage (unused) */
1322*fb1b10abSAndroid Build Coastguard Worker 0, /* g_threads */
1323*fb1b10abSAndroid Build Coastguard Worker 0, /* g_profile */
1324*fb1b10abSAndroid Build Coastguard Worker
1325*fb1b10abSAndroid Build Coastguard Worker 320, /* g_width */
1326*fb1b10abSAndroid Build Coastguard Worker 240, /* g_height */
1327*fb1b10abSAndroid Build Coastguard Worker VPX_BITS_8, /* g_bit_depth */
1328*fb1b10abSAndroid Build Coastguard Worker 8, /* g_input_bit_depth */
1329*fb1b10abSAndroid Build Coastguard Worker
1330*fb1b10abSAndroid Build Coastguard Worker { 1, 30 }, /* g_timebase */
1331*fb1b10abSAndroid Build Coastguard Worker
1332*fb1b10abSAndroid Build Coastguard Worker 0, /* g_error_resilient */
1333*fb1b10abSAndroid Build Coastguard Worker
1334*fb1b10abSAndroid Build Coastguard Worker VPX_RC_ONE_PASS, /* g_pass */
1335*fb1b10abSAndroid Build Coastguard Worker
1336*fb1b10abSAndroid Build Coastguard Worker 0, /* g_lag_in_frames */
1337*fb1b10abSAndroid Build Coastguard Worker
1338*fb1b10abSAndroid Build Coastguard Worker 0, /* rc_dropframe_thresh */
1339*fb1b10abSAndroid Build Coastguard Worker 0, /* rc_resize_allowed */
1340*fb1b10abSAndroid Build Coastguard Worker 1, /* rc_scaled_width */
1341*fb1b10abSAndroid Build Coastguard Worker 1, /* rc_scaled_height */
1342*fb1b10abSAndroid Build Coastguard Worker 60, /* rc_resize_down_thresh */
1343*fb1b10abSAndroid Build Coastguard Worker 30, /* rc_resize_up_thresh */
1344*fb1b10abSAndroid Build Coastguard Worker
1345*fb1b10abSAndroid Build Coastguard Worker VPX_VBR, /* rc_end_usage */
1346*fb1b10abSAndroid Build Coastguard Worker { NULL, 0 }, /* rc_twopass_stats_in */
1347*fb1b10abSAndroid Build Coastguard Worker { NULL, 0 }, /* rc_firstpass_mb_stats_in */
1348*fb1b10abSAndroid Build Coastguard Worker 256, /* rc_target_bitrate */
1349*fb1b10abSAndroid Build Coastguard Worker 4, /* rc_min_quantizer */
1350*fb1b10abSAndroid Build Coastguard Worker 63, /* rc_max_quantizer */
1351*fb1b10abSAndroid Build Coastguard Worker 100, /* rc_undershoot_pct */
1352*fb1b10abSAndroid Build Coastguard Worker 100, /* rc_overshoot_pct */
1353*fb1b10abSAndroid Build Coastguard Worker
1354*fb1b10abSAndroid Build Coastguard Worker 6000, /* rc_max_buffer_size */
1355*fb1b10abSAndroid Build Coastguard Worker 4000, /* rc_buffer_initial_size; */
1356*fb1b10abSAndroid Build Coastguard Worker 5000, /* rc_buffer_optimal_size; */
1357*fb1b10abSAndroid Build Coastguard Worker
1358*fb1b10abSAndroid Build Coastguard Worker 50, /* rc_two_pass_vbrbias */
1359*fb1b10abSAndroid Build Coastguard Worker 0, /* rc_two_pass_vbrmin_section */
1360*fb1b10abSAndroid Build Coastguard Worker 400, /* rc_two_pass_vbrmax_section */
1361*fb1b10abSAndroid Build Coastguard Worker 0, // rc_2pass_vbr_corpus_complexity (only has meaningfull for VP9)
1362*fb1b10abSAndroid Build Coastguard Worker
1363*fb1b10abSAndroid Build Coastguard Worker /* keyframing settings (kf) */
1364*fb1b10abSAndroid Build Coastguard Worker VPX_KF_AUTO, /* g_kfmode*/
1365*fb1b10abSAndroid Build Coastguard Worker 0, /* kf_min_dist */
1366*fb1b10abSAndroid Build Coastguard Worker 128, /* kf_max_dist */
1367*fb1b10abSAndroid Build Coastguard Worker
1368*fb1b10abSAndroid Build Coastguard Worker VPX_SS_DEFAULT_LAYERS, /* ss_number_layers */
1369*fb1b10abSAndroid Build Coastguard Worker { 0 },
1370*fb1b10abSAndroid Build Coastguard Worker { 0 }, /* ss_target_bitrate */
1371*fb1b10abSAndroid Build Coastguard Worker 1, /* ts_number_layers */
1372*fb1b10abSAndroid Build Coastguard Worker { 0 }, /* ts_target_bitrate */
1373*fb1b10abSAndroid Build Coastguard Worker { 0 }, /* ts_rate_decimator */
1374*fb1b10abSAndroid Build Coastguard Worker 0, /* ts_periodicity */
1375*fb1b10abSAndroid Build Coastguard Worker { 0 }, /* ts_layer_id */
1376*fb1b10abSAndroid Build Coastguard Worker { 0 }, /* layer_target_bitrate */
1377*fb1b10abSAndroid Build Coastguard Worker 0, /* temporal_layering_mode */
1378*fb1b10abSAndroid Build Coastguard Worker 0, /* use_vizier_rc_params */
1379*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* active_wq_factor */
1380*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* err_per_mb_factor */
1381*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* sr_default_decay_limit */
1382*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* sr_diff_factor */
1383*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* kf_err_per_mb_factor */
1384*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* kf_frame_min_boost_factor */
1385*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* kf_frame_max_boost_first_factor */
1386*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* kf_frame_max_boost_subs_factor */
1387*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* kf_max_total_boost_factor */
1388*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* gf_max_total_boost_factor */
1389*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* gf_frame_max_boost_factor */
1390*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* zm_factor */
1391*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* rd_mult_inter_qp_fac */
1392*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* rd_mult_arf_qp_fac */
1393*fb1b10abSAndroid Build Coastguard Worker { 1, 1 }, /* rd_mult_key_qp_fac */
1394*fb1b10abSAndroid Build Coastguard Worker } },
1395*fb1b10abSAndroid Build Coastguard Worker };
1396*fb1b10abSAndroid Build Coastguard Worker
1397*fb1b10abSAndroid Build Coastguard Worker #ifndef VERSION_STRING
1398*fb1b10abSAndroid Build Coastguard Worker #define VERSION_STRING
1399*fb1b10abSAndroid Build Coastguard Worker #endif
1400*fb1b10abSAndroid Build Coastguard Worker CODEC_INTERFACE(vpx_codec_vp8_cx) = {
1401*fb1b10abSAndroid Build Coastguard Worker "WebM Project VP8 Encoder" VERSION_STRING,
1402*fb1b10abSAndroid Build Coastguard Worker VPX_CODEC_INTERNAL_ABI_VERSION,
1403*fb1b10abSAndroid Build Coastguard Worker VPX_CODEC_CAP_ENCODER | VPX_CODEC_CAP_PSNR | VPX_CODEC_CAP_OUTPUT_PARTITION,
1404*fb1b10abSAndroid Build Coastguard Worker /* vpx_codec_caps_t caps; */
1405*fb1b10abSAndroid Build Coastguard Worker vp8e_init, /* vpx_codec_init_fn_t init; */
1406*fb1b10abSAndroid Build Coastguard Worker vp8e_destroy, /* vpx_codec_destroy_fn_t destroy; */
1407*fb1b10abSAndroid Build Coastguard Worker vp8e_ctf_maps, /* vpx_codec_ctrl_fn_map_t *ctrl_maps; */
1408*fb1b10abSAndroid Build Coastguard Worker {
1409*fb1b10abSAndroid Build Coastguard Worker NULL, /* vpx_codec_peek_si_fn_t peek_si; */
1410*fb1b10abSAndroid Build Coastguard Worker NULL, /* vpx_codec_get_si_fn_t get_si; */
1411*fb1b10abSAndroid Build Coastguard Worker NULL, /* vpx_codec_decode_fn_t decode; */
1412*fb1b10abSAndroid Build Coastguard Worker NULL, /* vpx_codec_frame_get_fn_t frame_get; */
1413*fb1b10abSAndroid Build Coastguard Worker NULL, /* vpx_codec_set_fb_fn_t set_fb_fn; */
1414*fb1b10abSAndroid Build Coastguard Worker },
1415*fb1b10abSAndroid Build Coastguard Worker {
1416*fb1b10abSAndroid Build Coastguard Worker 1, /* 1 cfg map */
1417*fb1b10abSAndroid Build Coastguard Worker vp8e_usage_cfg_map, /* vpx_codec_enc_cfg_map_t cfg_maps; */
1418*fb1b10abSAndroid Build Coastguard Worker vp8e_encode, /* vpx_codec_encode_fn_t encode; */
1419*fb1b10abSAndroid Build Coastguard Worker vp8e_get_cxdata, /* vpx_codec_get_cx_data_fn_t get_cx_data; */
1420*fb1b10abSAndroid Build Coastguard Worker vp8e_set_config,
1421*fb1b10abSAndroid Build Coastguard Worker NULL,
1422*fb1b10abSAndroid Build Coastguard Worker vp8e_get_preview,
1423*fb1b10abSAndroid Build Coastguard Worker vp8e_mr_alloc_mem,
1424*fb1b10abSAndroid Build Coastguard Worker } /* encoder functions */
1425*fb1b10abSAndroid Build Coastguard Worker };
1426