1
2
3
4
5
6
7
8
9
10
11
12
13
14
15#include <assert.h>
16#include <inttypes.h>
17#include <limits.h>
18#include <math.h>
19#include <stdio.h>
20#include <stdlib.h>
21#include <string.h>
22
23#include <memory>
24
25#include "config/aom_config.h"
26
27#if CONFIG_AV1_DECODER
29#endif
32#include "aom/aom_integer.h"
34#include "aom_dsp/bitwriter_buffer.h"
35#include "aom_ports/aom_timer.h"
36#include "av1/ratectrl_rtc.h"
37#include "common/args.h"
38#include "common/tools_common.h"
39#include "common/video_writer.h"
40#include "examples/encoder_util.h"
41#include "examples/multilayer_metadata.h"
42
43#define OPTION_BUFFER_SIZE 1024
44#define MAX_NUM_SPATIAL_LAYERS 4
45
46typedef struct {
47 const char *output_filename;
48 char options[OPTION_BUFFER_SIZE];
49 struct AvxInputContext input_ctx[MAX_NUM_SPATIAL_LAYERS];
50 int speed;
51 int aq_mode;
52 int layering_mode;
53 int output_obu;
54 int decode;
55 int tune_content;
56 int show_psnr;
57 bool use_external_rc;
58 bool scale_factors_explicitly_set;
59 const char *multilayer_metadata_file;
60} AppInput;
61
62typedef enum {
63 QUANTIZER = 0,
64 BITRATE,
65 SCALE_FACTOR,
66 AUTO_ALT_REF,
67 ALL_OPTION_TYPES
68} LAYER_OPTION_TYPE;
69
70static const arg_def_t outputfile =
71 ARG_DEF("o", "output", 1, "Output filename");
72static const arg_def_t frames_arg =
73 ARG_DEF("f", "frames", 1, "Number of frames to encode");
74static const arg_def_t threads_arg =
75 ARG_DEF("th", "threads", 1, "Number of threads to use");
76static const arg_def_t width_arg = ARG_DEF("w", "width", 1, "Source width");
77static const arg_def_t height_arg = ARG_DEF("h", "height", 1, "Source height");
78static const arg_def_t timebase_arg =
79 ARG_DEF("t", "timebase", 1, "Timebase (num/den)");
80static const arg_def_t bitrate_arg = ARG_DEF(
81 "b", "target-bitrate", 1, "Encoding bitrate, in kilobits per second");
82static const arg_def_t spatial_layers_arg =
83 ARG_DEF("sl", "spatial-layers", 1, "Number of spatial SVC layers");
84static const arg_def_t temporal_layers_arg =
85 ARG_DEF("tl", "temporal-layers", 1, "Number of temporal SVC layers");
86static const arg_def_t layering_mode_arg =
87 ARG_DEF("lm", "layering-mode", 1, "Temporal layering scheme.");
88static const arg_def_t kf_dist_arg =
89 ARG_DEF("k", "kf-dist", 1, "Number of frames between keyframes");
90static const arg_def_t scale_factors_arg =
91 ARG_DEF("r", "scale-factors", 1, "Scale factors (lowest to highest layer)");
92static const arg_def_t min_q_arg =
93 ARG_DEF(NULL, "min-q", 1, "Minimum quantizer");
94static const arg_def_t max_q_arg =
95 ARG_DEF(NULL, "max-q", 1, "Maximum quantizer");
96static const arg_def_t speed_arg =
97 ARG_DEF("sp", "speed", 1, "Speed configuration");
98static const arg_def_t aqmode_arg =
99 ARG_DEF("aq", "aqmode", 1, "AQ mode off/on");
100static const arg_def_t bitrates_arg =
101 ARG_DEF("bl", "bitrates", 1,
102 "Bitrates[spatial_layer * num_temporal_layer + temporal_layer]");
103static const arg_def_t dropframe_thresh_arg =
104 ARG_DEF(NULL, "drop-frame", 1, "Temporal resampling threshold (buf %)");
105static const arg_def_t error_resilient_arg =
106 ARG_DEF(NULL, "error-resilient", 1, "Error resilient flag");
107static const arg_def_t output_obu_arg =
108 ARG_DEF(NULL, "output-obu", 1,
109 "Write OBUs when set to 1. Otherwise write IVF files.");
110static const arg_def_t test_decode_arg =
111 ARG_DEF(NULL, "test-decode", 1,
112 "Attempt to test decoding the output when set to 1. Default is 1.");
113static const arg_def_t psnr_arg =
114 ARG_DEF(NULL, "psnr", -1, "Show PSNR in status line.");
115static const arg_def_t ext_rc_arg =
116 ARG_DEF(NULL, "use-ext-rc", 0, "Use external rate control.");
117static const struct arg_enum_list tune_content_enum[] = {
118 { "default", AOM_CONTENT_DEFAULT },
119 { "screen", AOM_CONTENT_SCREEN },
120 { "film", AOM_CONTENT_FILM },
121 { NULL, 0 }
122};
123static const arg_def_t tune_content_arg = ARG_DEF_ENUM(
124 NULL, "tune-content", 1, "Tune content type", tune_content_enum);
125#if CONFIG_CWG_E050
126static const arg_def_t multilayer_metadata_file_arg =
127 ARG_DEF("ml", "multilayer_metadata_file", 1,
128 "Experimental: path to multilayer metadata file");
129#endif
130
131#if CONFIG_AV1_HIGHBITDEPTH
132static const struct arg_enum_list bitdepth_enum[] = { {
"8",
AOM_BITS_8 },
134 { NULL, 0 } };
135
136static const arg_def_t bitdepth_arg = ARG_DEF_ENUM(
137 "d", "bit-depth", 1, "Bit depth for codec 8 or 10. ", bitdepth_enum);
138#endif
139
140static const arg_def_t *svc_args[] = {
141 &frames_arg,
142 &outputfile,
143 &width_arg,
144 &height_arg,
145 &timebase_arg,
146 &bitrate_arg,
147 &spatial_layers_arg,
148 &kf_dist_arg,
149 &scale_factors_arg,
150 &min_q_arg,
151 &max_q_arg,
152 &temporal_layers_arg,
153 &layering_mode_arg,
154 &threads_arg,
155 &aqmode_arg,
156#if CONFIG_AV1_HIGHBITDEPTH
157 &bitdepth_arg,
158#endif
159 &speed_arg,
160 &bitrates_arg,
161 &dropframe_thresh_arg,
162 &error_resilient_arg,
163 &output_obu_arg,
164 &test_decode_arg,
165 &tune_content_arg,
166 &psnr_arg,
167#if CONFIG_CWG_E050
168 &multilayer_metadata_file_arg,
169#endif
170 NULL,
171};
172
173#define zero(Dest) memset(&(Dest), 0, sizeof(Dest))
174
175static const char *exec_name;
176
177void usage_exit(void) {
178 fprintf(stderr,
179 "Usage: %s <options> input_filename [input_filename ...] -o "
180 "output_filename\n",
181 exec_name);
182 fprintf(stderr, "Options:\n");
183 arg_show_usage(stderr, svc_args);
184 fprintf(
185 stderr,
186 "Input files must be y4m or yuv.\n"
187 "If multiple input files are specified, they correspond to spatial "
188 "layers, and there should be as many as there are spatial layers.\n"
189 "All input files must have the same width, height, frame rate and number "
190 "of frames.\n"
191 "If only one file is specified, it is used for all spatial layers.\n");
192 exit(EXIT_FAILURE);
193}
194
195static int file_is_y4m(const char detect[4]) {
196 return memcmp(detect, "YUV4", 4) == 0;
197}
198
199static int fourcc_is_ivf(const char detect[4]) {
200 if (memcmp(detect, "DKIF", 4) == 0) {
201 return 1;
202 }
203 return 0;
204}
205
206static const int option_max_values[ALL_OPTION_TYPES] = { 63, INT_MAX, INT_MAX,
207 1 };
208
209static const int option_min_values[ALL_OPTION_TYPES] = { 0, 0, 1, 0 };
210
211static void open_input_file(struct AvxInputContext *input,
213
214 input->file = strcmp(input->filename, "-") ? fopen(input->filename, "rb")
215 : set_binary_mode(stdin);
216
217 if (!input->file) fatal("Failed to open input file");
218
219 if (!fseeko(input->file, 0, SEEK_END)) {
220
221
222
223 input->length = ftello(input->file);
224 rewind(input->file);
225 }
226
227
228 input->pixel_aspect_ratio.numerator = 1;
229 input->pixel_aspect_ratio.denominator = 1;
230
231
232
233
234 input->detect.buf_read = fread(input->detect.buf, 1, 4, input->file);
235 input->detect.position = 0;
236
237 if (input->detect.buf_read == 4 && file_is_y4m(input->detect.buf)) {
238 if (y4m_input_open(&input->y4m, input->file, input->detect.buf, 4, csp,
239 input->only_i420) >= 0) {
240 input->file_type = FILE_TYPE_Y4M;
241 input->width = input->y4m.pic_w;
242 input->height = input->y4m.pic_h;
243 input->pixel_aspect_ratio.numerator = input->y4m.par_n;
244 input->pixel_aspect_ratio.denominator = input->y4m.par_d;
245 input->framerate.numerator = input->y4m.fps_n;
246 input->framerate.denominator = input->y4m.fps_d;
247 input->fmt = input->y4m.aom_fmt;
248 input->bit_depth = static_cast<aom_bit_depth_t>(input->y4m.bit_depth);
249 } else {
250 fatal("Unsupported Y4M stream.");
251 }
252 } else if (input->detect.buf_read == 4 && fourcc_is_ivf(input->detect.buf)) {
253 fatal("IVF is not supported as input.");
254 } else {
255 input->file_type = FILE_TYPE_RAW;
256 }
257}
258
259static aom_codec_err_t extract_option(LAYER_OPTION_TYPE type,
char *input,
260 int *value0, int *value1) {
261 if (type == SCALE_FACTOR) {
262 *value0 = (int)strtol(input, &input, 10);
264 *value1 = (int)strtol(input, &input, 10);
265
266 if (*value0 < option_min_values[SCALE_FACTOR] ||
267 *value1 < option_min_values[SCALE_FACTOR] ||
268 *value0 > option_max_values[SCALE_FACTOR] ||
269 *value1 > option_max_values[SCALE_FACTOR] ||
270 *value0 > *value1)
272 } else {
273 *value0 = atoi(input);
274 if (*value0 < option_min_values[type] || *value0 > option_max_values[type])
276 }
278}
279
282 int *option0, int *option1) {
284 char *input_string;
285 char *token;
286 const char *delim = ",";
288 int i = 0;
289
290 if (type == BITRATE)
291 num_layers =
293
294 if (input == NULL || option0 == NULL ||
295 (option1 == NULL && type == SCALE_FACTOR))
297
298 const size_t input_length = strlen(input);
299 input_string = reinterpret_cast<char *>(malloc(input_length + 1));
301 memcpy(input_string, input, input_length + 1);
302 token = strtok(input_string, delim);
303 for (i = 0; i < num_layers; ++i) {
304 if (token != NULL) {
305 res = extract_option(type, token, option0 + i, option1 + i);
307 token = strtok(NULL, delim);
308 } else {
310 break;
311 }
312 }
313 free(input_string);
314 return res;
315}
316
317static void parse_command_line(int argc, const char **argv_,
318 AppInput *app_input,
321 struct arg arg;
322 char **argv = NULL;
323 char **argi = NULL;
324 char **argj = NULL;
325 char string_options[1024] = { 0 };
326
327
330 app_input->layering_mode = 0;
331 app_input->output_obu = 0;
332 app_input->decode = 1;
335
336
337 argv = argv_dup(argc - 1, argv_ + 1);
338 if (!argv) {
339 fprintf(stderr, "Error allocating argument list\n");
340 exit(EXIT_FAILURE);
341 }
342 for (argi = argj = argv; (*argj = *argi); argi += arg.argv_step) {
343 arg.argv_step = 1;
344
345 if (arg_match(&arg, &outputfile, argi)) {
346 app_input->output_filename = arg.val;
347 } else if (arg_match(&arg, &width_arg, argi)) {
348 enc_cfg->
g_w = arg_parse_uint(&arg);
349 } else if (arg_match(&arg, &height_arg, argi)) {
350 enc_cfg->
g_h = arg_parse_uint(&arg);
351 } else if (arg_match(&arg, &timebase_arg, argi)) {
352 enc_cfg->
g_timebase = arg_parse_rational(&arg);
353 } else if (arg_match(&arg, &bitrate_arg, argi)) {
355 } else if (arg_match(&arg, &spatial_layers_arg, argi)) {
357 } else if (arg_match(&arg, &temporal_layers_arg, argi)) {
359 } else if (arg_match(&arg, &speed_arg, argi)) {
360 app_input->speed = arg_parse_uint(&arg);
361 if (app_input->speed > 11) {
362 aom_tools_warn("Mapping speed %d to speed 11.\n", app_input->speed);
363 }
364 } else if (arg_match(&arg, &aqmode_arg, argi)) {
365 app_input->aq_mode = arg_parse_uint(&arg);
366 } else if (arg_match(&arg, &threads_arg, argi)) {
367 enc_cfg->
g_threads = arg_parse_uint(&arg);
368 } else if (arg_match(&arg, &layering_mode_arg, argi)) {
369 app_input->layering_mode = arg_parse_int(&arg);
370 } else if (arg_match(&arg, &kf_dist_arg, argi)) {
373 } else if (arg_match(&arg, &scale_factors_arg, argi)) {
377 app_input->scale_factors_explicitly_set = true;
379 die("Failed to parse scale factors: %s\n",
381 }
382 } else if (arg_match(&arg, &min_q_arg, argi)) {
384 } else if (arg_match(&arg, &max_q_arg, argi)) {
386#if CONFIG_AV1_HIGHBITDEPTH
387 } else if (arg_match(&arg, &bitdepth_arg, argi)) {
394 break;
398 break;
399 default:
400 die(
"Error: Invalid bit depth selected (%d)\n", enc_cfg->
g_bit_depth);
401 }
402#endif
403 } else if (arg_match(&arg, &dropframe_thresh_arg, argi)) {
405 } else if (arg_match(&arg, &error_resilient_arg, argi)) {
408 die("Invalid value for error resilient (0, 1): %d.",
410 } else if (arg_match(&arg, &output_obu_arg, argi)) {
411 app_input->output_obu = arg_parse_uint(&arg);
412 if (app_input->output_obu != 0 && app_input->output_obu != 1)
413 die("Invalid value for obu output flag (0, 1): %d.",
414 app_input->output_obu);
415 } else if (arg_match(&arg, &test_decode_arg, argi)) {
416 app_input->decode = arg_parse_uint(&arg);
417 if (app_input->decode != 0 && app_input->decode != 1)
418 die("Invalid value for test decode flag (0, 1): %d.",
419 app_input->decode);
420 } else if (arg_match(&arg, &tune_content_arg, argi)) {
421 app_input->tune_content = arg_parse_enum_or_int(&arg);
422 printf("tune content %d\n", app_input->tune_content);
423 } else if (arg_match(&arg, &psnr_arg, argi)) {
424 app_input->show_psnr = 1;
425 } else if (arg_match(&arg, &ext_rc_arg, argi)) {
426 app_input->use_external_rc = true;
427#if CONFIG_CWG_E050
428 } else if (arg_match(&arg, &multilayer_metadata_file_arg, argi)) {
429 app_input->multilayer_metadata_file = arg.val;
430#endif
431 } else {
432 ++argj;
433 }
434 }
435
436
437 for (argi = argj = argv; (*argj = *argi); argi += arg.argv_step) {
438 arg.argv_step = 1;
439 if (arg_match(&arg, &bitrates_arg, argi)) {
444 }
445 } else {
446 ++argj;
447 }
448 }
449
450
451 if (strlen(string_options) > 0)
452 strncpy(app_input->options, string_options, OPTION_BUFFER_SIZE);
453
454
455 for (argi = argv; *argi; ++argi)
456 if (argi[0][0] == '-' && strlen(argi[0]) > 1)
457 die("Error: Unrecognized option %s\n", *argi);
458
459 if (argv[0] == NULL) {
460 usage_exit();
461 }
462
463 int input_count = 0;
464 while (argv[input_count] != NULL && input_count < MAX_NUM_SPATIAL_LAYERS) {
465 app_input->input_ctx[input_count].filename = argv[input_count];
466 ++input_count;
467 }
469 die("Error: Number of input files does not match number of spatial layers");
470 }
471 if (argv[input_count] != NULL) {
472 die("Error: Too many input files specified, there should be at most %d",
473 MAX_NUM_SPATIAL_LAYERS);
474 }
475
476 free(argv);
477
478 for (int i = 0; i < input_count; ++i) {
480 if (app_input->input_ctx[i].file_type == FILE_TYPE_Y4M) {
481 if (enc_cfg->
g_w == 0 || enc_cfg->
g_h == 0) {
482
483 enc_cfg->
g_w = app_input->input_ctx[i].width;
484 enc_cfg->
g_h = app_input->input_ctx[i].height;
485
486 enc_cfg->
g_timebase.
num = app_input->input_ctx[i].framerate.denominator;
487 enc_cfg->
g_timebase.
den = app_input->input_ctx[i].framerate.numerator;
488 }
else if (enc_cfg->
g_w != app_input->input_ctx[i].width ||
489 enc_cfg->
g_h != app_input->input_ctx[i].height ||
491 app_input->input_ctx[i].framerate.denominator ||
493 app_input->input_ctx[i].framerate.numerator) {
494 die("Error: Input file dimensions and/or frame rate mismatch");
495 }
496 }
497 }
498 if (enc_cfg->
g_w == 0 || enc_cfg->
g_h == 0) {
499 die("Error: Input file dimensions not set, use -w and -h");
500 }
501
502 if (enc_cfg->
g_w < 16 || enc_cfg->
g_w % 2 || enc_cfg->
g_h < 16 ||
504 die(
"Invalid resolution: %d x %d\n", enc_cfg->
g_w, enc_cfg->
g_h);
505
506 printf(
507 "Codec %s\n"
508 "layers: %d\n"
509 "width %u, height: %u\n"
510 "num: %d, den: %d, bitrate: %u\n"
511 "gop size: %u\n",
516}
517
518static const int mode_to_num_temporal_layers[12] = {
519 1, 2, 3, 3, 2, 1, 1, 3, 3, 3, 3, 3,
520};
521static const int mode_to_num_spatial_layers[12] = {
522 1, 1, 1, 1, 1, 2, 3, 2, 3, 3, 3, 3,
523};
524
525
526struct RateControlMetrics {
527
529
531
533
535
537
539
541
542
543 double avg_st_encoding_bitrate;
544
545 double variance_st_encoding_bitrate;
546
547 int window_size;
548
549 int window_count;
551};
552
553static const int REF_FRAMES = 8;
554
555static const int INTER_REFS_PER_FRAME = 7;
556
557
558enum {
559 SVC_LAST_FRAME = 0,
560 SVC_LAST2_FRAME,
561 SVC_LAST3_FRAME,
562 SVC_GOLDEN_FRAME,
563 SVC_BWDREF_FRAME,
564 SVC_ALTREF2_FRAME,
565 SVC_ALTREF_FRAME
566};
567
568static int read_frame(
struct AvxInputContext *input_ctx,
aom_image_t *img) {
569 FILE *f = input_ctx->file;
570 y4m_input *y4m = &input_ctx->y4m;
571 int shortread = 0;
572
573 if (input_ctx->file_type == FILE_TYPE_Y4M) {
574 if (y4m_input_fetch_frame(y4m, f, img) < 1) return 0;
575 } else {
576 shortread = read_yuv_frame(input_ctx, img);
577 }
578
579 return !shortread;
580}
581
582static void close_input_file(struct AvxInputContext *input) {
583 fclose(input->file);
584 if (input->file_type == FILE_TYPE_Y4M) y4m_input_close(&input->y4m);
585}
586
587
588
589
590
591
592
593static void set_rate_control_metrics(struct RateControlMetrics *rc,
594 double framerate, int ss_number_layers,
595 int ts_number_layers) {
597 ts_rate_decimator[0] = 1;
598 if (ts_number_layers == 2) {
599 ts_rate_decimator[0] = 2;
600 ts_rate_decimator[1] = 1;
601 }
602 if (ts_number_layers == 3) {
603 ts_rate_decimator[0] = 4;
604 ts_rate_decimator[1] = 2;
605 ts_rate_decimator[2] = 1;
606 }
607
608
609 for (int sl = 0; sl < ss_number_layers; ++sl) {
610 int i = sl * ts_number_layers;
611 rc->layer_framerate[0] = framerate / ts_rate_decimator[0];
612 rc->layer_pfb[i] =
613 1000.0 * rc->layer_target_bitrate[i] / rc->layer_framerate[0];
614 for (int tl = 0; tl < ts_number_layers; ++tl) {
615 i = sl * ts_number_layers + tl;
616 if (tl > 0) {
617 rc->layer_framerate[tl] = framerate / ts_rate_decimator[tl];
618 rc->layer_pfb[i] =
619 1000.0 *
620 (rc->layer_target_bitrate[i] - rc->layer_target_bitrate[i - 1]) /
621 (rc->layer_framerate[tl] - rc->layer_framerate[tl - 1]);
622 }
623 rc->layer_input_frames[tl] = 0;
624 rc->layer_enc_frames[tl] = 0;
625 rc->layer_encoding_bitrate[i] = 0.0;
626 rc->layer_avg_frame_size[i] = 0.0;
627 rc->layer_avg_rate_mismatch[i] = 0.0;
628 }
629 }
630 rc->window_count = 0;
631 rc->window_size = 15;
632 rc->avg_st_encoding_bitrate = 0.0;
633 rc->variance_st_encoding_bitrate = 0.0;
634}
635
636static void printout_rate_control_summary(struct RateControlMetrics *rc,
637 int frame_cnt, int ss_number_layers,
638 int ts_number_layers) {
639 int tot_num_frames = 0;
640 double perc_fluctuation = 0.0;
641 printf("Total number of processed frames: %d\n\n", frame_cnt - 1);
642 printf("Rate control layer stats for %d layer(s):\n\n", ts_number_layers);
643 for (int sl = 0; sl < ss_number_layers; ++sl) {
644 tot_num_frames = 0;
645 for (int tl = 0; tl < ts_number_layers; ++tl) {
646 int i = sl * ts_number_layers + tl;
647 const int num_dropped =
648 tl > 0 ? rc->layer_input_frames[tl] - rc->layer_enc_frames[tl]
649 : rc->layer_input_frames[tl] - rc->layer_enc_frames[tl] - 1;
650 tot_num_frames += rc->layer_input_frames[tl];
651 rc->layer_encoding_bitrate[i] = 0.001 * rc->layer_framerate[tl] *
652 rc->layer_encoding_bitrate[i] /
653 tot_num_frames;
654 rc->layer_avg_frame_size[i] =
655 rc->layer_avg_frame_size[i] / rc->layer_enc_frames[tl];
656 rc->layer_avg_rate_mismatch[i] =
657 100.0 * rc->layer_avg_rate_mismatch[i] / rc->layer_enc_frames[tl];
658 printf("For layer#: %d %d \n", sl, tl);
659 printf("Bitrate (target vs actual): %d %f\n", rc->layer_target_bitrate[i],
660 rc->layer_encoding_bitrate[i]);
661 printf("Average frame size (target vs actual): %f %f\n", rc->layer_pfb[i],
662 rc->layer_avg_frame_size[i]);
663 printf("Average rate_mismatch: %f\n", rc->layer_avg_rate_mismatch[i]);
664 printf(
665 "Number of input frames, encoded (non-key) frames, "
666 "and perc dropped frames: %d %d %f\n",
667 rc->layer_input_frames[tl], rc->layer_enc_frames[tl],
668 100.0 * num_dropped / rc->layer_input_frames[tl]);
669 printf("\n");
670 }
671 }
672 rc->avg_st_encoding_bitrate = rc->avg_st_encoding_bitrate / rc->window_count;
673 rc->variance_st_encoding_bitrate =
674 rc->variance_st_encoding_bitrate / rc->window_count -
675 (rc->avg_st_encoding_bitrate * rc->avg_st_encoding_bitrate);
676 perc_fluctuation = 100.0 * sqrt(rc->variance_st_encoding_bitrate) /
677 rc->avg_st_encoding_bitrate;
678 printf("Short-time stats, for window of %d frames:\n", rc->window_size);
679 printf("Average, rms-variance, and percent-fluct: %f %f %f\n",
680 rc->avg_st_encoding_bitrate, sqrt(rc->variance_st_encoding_bitrate),
681 perc_fluctuation);
682 if (frame_cnt - 1 != tot_num_frames)
683 die("Error: Number of input frames not equal to output!\n");
684}
685
686
687static void set_layer_pattern(
691 int spatial_layer_id, int is_key_frame, int ksvc_mode, int speed) {
692
693
694 int use_rps_example = 0;
695 int i;
696 int enable_longterm_temporal_ref = 1;
697 int shift = (layering_mode == 8) ? 2 : 0;
698 int simulcast_mode = (layering_mode == 11);
699 *use_svc_control = 1;
701 int lag_index = 0;
702 int base_count = superframe_cnt >> 2;
706
707
708
709 for (i = 0; i < INTER_REFS_PER_FRAME; i++) ref_frame_config->
ref_idx[i] = i;
710 for (i = 0; i < INTER_REFS_PER_FRAME; i++) ref_frame_config->
reference[i] = 0;
711 for (i = 0; i < REF_FRAMES; i++) ref_frame_config->
refresh[i] = 0;
712
713 if (ksvc_mode) {
714
715
716 layering_mode = 9;
717 }
718 switch (layering_mode) {
719 case 0:
720 if (use_rps_example == 0) {
721
724 ref_frame_config->
refresh[0] = 1;
725 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
726 } else {
727
728
729
730
731
732 int last_idx = 0;
733 int last_idx_refresh = 0;
734 int gld_idx = 0;
735 int alt_ref_idx = 0;
736 int lag_alt = 4;
737 int lag_gld = 8;
740 int sh = 8;
741
742 if (superframe_cnt > 1) last_idx = (superframe_cnt - 1) % sh;
743
744 last_idx_refresh = superframe_cnt % sh;
745
746 if (superframe_cnt > lag_gld) gld_idx = (superframe_cnt - lag_gld) % sh;
747
748 if (superframe_cnt > lag_alt)
749 alt_ref_idx = (superframe_cnt - lag_alt) % sh;
750
751
752 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
753 ref_frame_config->
ref_idx[i] = last_idx;
754
755 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = last_idx;
756 ref_frame_config->
ref_idx[SVC_LAST2_FRAME] = last_idx_refresh;
757 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = gld_idx;
758 ref_frame_config->
ref_idx[SVC_ALTREF_FRAME] = alt_ref_idx;
759
760 ref_frame_config->
refresh[last_idx_refresh] = 1;
761
762 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
763 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 1;
764 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
765
766 if (superframe_cnt % 200 == 0 && superframe_cnt > 0) {
767 ref_frame_config->
reference[SVC_LAST_FRAME] = 0;
768 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 0;
769 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
770
771
772
773 if (superframe_cnt % 400 == 0 && superframe_cnt > 0) {
774 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = gld_idx;
775 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
776 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 0;
777 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 0;
778 }
779 }
780 }
781 break;
782 case 1:
783
784
785
786
787 base_count = superframe_cnt >> 1;
788 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
789
790 lag_index = 5;
791 if (base_count > 0) {
792 lag_index = 5 + (base_count % 3);
793 if (superframe_cnt % 2 != 0) lag_index = 5 + ((base_count + 1) % 3);
794 }
795
796 ref_frame_config->
ref_idx[SVC_ALTREF_FRAME] = lag_index;
797 if (superframe_cnt % 2 == 0) {
799
800 ref_frame_config->
refresh[0] = 1;
801 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
802
803 ref_frame_config->
refresh[lag_index] = 1;
804
805 if (base_count % 32 == 0) ref_frame_config->
refresh[3] = 1;
806 } else {
808
809 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
810 }
811
813 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
814 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 1;
815 }
816 break;
817 case 2:
818
819
820
821
822 if (superframe_cnt % 4 == 0) {
823
825
826 ref_frame_config->
refresh[0] = 1;
827 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
828 } else if ((superframe_cnt - 1) % 4 == 0) {
830
831 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
832 } else if ((superframe_cnt - 2) % 4 == 0) {
834
835 ref_frame_config->
refresh[1] = 1;
836 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
837 } else if ((superframe_cnt - 3) % 4 == 0) {
839
840
841
842 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
843 ref_frame_config->
ref_idx[SVC_LAST2_FRAME] = 0;
844 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
845 }
846 break;
847 case 3:
848
849
850
851
852
853
854
855 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
856
857 lag_index = 5;
858 if (base_count > 0) {
859 lag_index = 5 + (base_count % 3);
860 if (superframe_cnt % 4 != 0) lag_index = 5 + ((base_count + 1) % 3);
861 }
862
863 ref_frame_config->
ref_idx[SVC_ALTREF_FRAME] = lag_index;
864 if (superframe_cnt % 4 == 0) {
865
867
868 ref_frame_config->
refresh[0] = 1;
869 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
870
871 if (base_count % 10 == 0) ref_frame_config->
refresh[3] = 1;
872
873 ref_frame_config->
refresh[lag_index] = 1;
874 } else if ((superframe_cnt - 1) % 4 == 0) {
876
877 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
878 } else if ((superframe_cnt - 2) % 4 == 0) {
880
881 ref_frame_config->
refresh[1] = 1;
882 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
883 } else if ((superframe_cnt - 3) % 4 == 0) {
885
886
887
888 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
889 ref_frame_config->
ref_idx[SVC_LAST2_FRAME] = 0;
890 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
891 }
892
893 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
894 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 1;
895
896 if (speed >= 7) {
899 }
900 break;
901 case 4:
902
903
904
905
906
907 if (superframe_cnt % 4 == 0) {
908
910
911 ref_frame_config->
refresh[0] = 1;
912 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
913 } else if ((superframe_cnt - 1) % 4 == 0) {
915
916 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
917 } else if ((superframe_cnt - 2) % 4 == 0) {
919
920 ref_frame_config->
refresh[3] = 1;
921 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
922 } else if ((superframe_cnt - 3) % 4 == 0) {
924
925 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
926 }
927 break;
928 case 5:
929
932
933 ref_frame_config->
refresh[0] = 1;
934 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
936
937
938 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
939 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 0;
940 ref_frame_config->
refresh[1] = 1;
941 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
942 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
943 }
944 break;
945 case 6:
946
947
948
949
950
953
954 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
955 ref_frame_config->
ref_idx[i] = 0;
956 ref_frame_config->
refresh[0] = 1;
957 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
959
960
961
962 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
963 ref_frame_config->
ref_idx[i] = 0;
964 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
965 ref_frame_config->
refresh[1] = 1;
966 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
967 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
969
970
971
972 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
973 ref_frame_config->
ref_idx[i] = 1;
974 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
975 ref_frame_config->
refresh[2] = 1;
976 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
977 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
978
979
980 if (enable_longterm_temporal_ref) {
981 ref_frame_config->
ref_idx[SVC_ALTREF_FRAME] = REF_FRAMES - 1;
982 ref_frame_config->
reference[SVC_ALTREF_FRAME] = 1;
983 if (base_count % 10 == 0)
984 ref_frame_config->
refresh[REF_FRAMES - 1] = 1;
985 }
986 }
987 break;
988 case 7:
989
990 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
991 if (superframe_cnt % 4 == 0) {
992
995
996
997 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
998 ref_frame_config->
ref_idx[i] = 0;
999 ref_frame_config->
refresh[0] = 1;
1001
1002 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1003 ref_frame_config->
ref_idx[i] = 0;
1004 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1005 ref_frame_config->
refresh[1] = 1;
1006 }
1007 } else if ((superframe_cnt - 1) % 4 == 0) {
1008
1011 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1012 ref_frame_config->
ref_idx[i] = 0;
1013 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1014 ref_frame_config->
refresh[3] = 1;
1016
1017
1018
1019 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1020 ref_frame_config->
ref_idx[i] = 3;
1021 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1022 }
1023 } else if ((superframe_cnt - 2) % 4 == 0) {
1024
1027
1028
1029
1030 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1031 ref_frame_config->
ref_idx[i] = 0;
1032 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 5 - shift;
1033 ref_frame_config->
refresh[5 - shift] = 1;
1035
1036
1037
1038 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1039 ref_frame_config->
ref_idx[i] = 5 - shift;
1040 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1041 ref_frame_config->
ref_idx[SVC_LAST3_FRAME] = 6 - shift;
1042 ref_frame_config->
refresh[6 - shift] = 1;
1043 }
1044 } else if ((superframe_cnt - 3) % 4 == 0) {
1045
1048
1049
1050
1051 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1052 ref_frame_config->
ref_idx[i] = 0;
1053 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 5 - shift;
1054 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1055 ref_frame_config->
refresh[3] = 1;
1057
1058
1059 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1060 ref_frame_config->
ref_idx[i] = 0;
1061 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 6 - shift;
1062 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1063 }
1064 }
1065 break;
1066 case 8:
1067
1068
1069
1070
1071
1072
1073 case 9:
1074
1075
1076
1077
1078
1079 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1080 if (superframe_cnt % 4 == 0) {
1081
1084
1085
1086 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1087 ref_frame_config->
ref_idx[i] = 0;
1088 ref_frame_config->
refresh[0] = 1;
1090
1091
1092
1093 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1094 ref_frame_config->
ref_idx[i] = 0;
1095 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1096 ref_frame_config->
refresh[1] = 1;
1098
1099
1100
1101 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1102 ref_frame_config->
ref_idx[i] = 1;
1103 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1104 ref_frame_config->
refresh[2] = 1;
1105 }
1106 } else if ((superframe_cnt - 1) % 4 == 0) {
1107
1110
1111
1112
1113 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1114 ref_frame_config->
ref_idx[i] = 0;
1115 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1116 ref_frame_config->
refresh[3] = 1;
1118
1119
1120
1121 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1122 ref_frame_config->
ref_idx[i] = 3;
1123 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1124 ref_frame_config->
ref_idx[SVC_LAST2_FRAME] = 4;
1125 ref_frame_config->
refresh[4] = 1;
1127
1128
1129
1130 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1131 ref_frame_config->
ref_idx[i] = 4;
1132 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1133 }
1134 } else if ((superframe_cnt - 2) % 4 == 0) {
1135
1138
1139
1140
1141 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1142 ref_frame_config->
ref_idx[i] = 0;
1143 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 5 - shift;
1144 ref_frame_config->
refresh[5 - shift] = 1;
1146
1147
1148
1149 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1150 ref_frame_config->
ref_idx[i] = 5 - shift;
1151 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1152 ref_frame_config->
ref_idx[SVC_LAST3_FRAME] = 6 - shift;
1153 ref_frame_config->
refresh[6 - shift] = 1;
1155
1156
1157
1158 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1159 ref_frame_config->
ref_idx[i] = 6 - shift;
1160 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1161 ref_frame_config->
ref_idx[SVC_LAST3_FRAME] = 7 - shift;
1162 ref_frame_config->
refresh[7 - shift] = 1;
1163 }
1164 } else if ((superframe_cnt - 3) % 4 == 0) {
1165
1168
1169
1170
1171 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1172 ref_frame_config->
ref_idx[i] = 0;
1173 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 5 - shift;
1174 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1175 ref_frame_config->
refresh[3] = 1;
1177
1178
1179 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1180 ref_frame_config->
ref_idx[i] = 0;
1181 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 6 - shift;
1182 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1183 ref_frame_config->
ref_idx[SVC_LAST2_FRAME] = 4;
1184 ref_frame_config->
refresh[4] = 1;
1186
1187
1188 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1189 ref_frame_config->
ref_idx[i] = 0;
1190 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 7 - shift;
1191 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 4;
1192 }
1193 }
1194 break;
1195 case 11:
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1216
1217 for (i = 0; i < REF_FRAMES; i++) ref_frame_config->
refresh[i] = 0;
1218 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1219 ref_frame_config->
ref_idx[i] = 0;
1220
1221 if (is_key_frame) {
1223
1224
1225
1226 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 0;
1227 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 1;
1228 ref_frame_config->
refresh[0] = 1;
1229 ref_frame_config->
refresh[1] = 1;
1231
1232
1233
1234 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1235 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 3;
1236 ref_frame_config->
refresh[2] = 1;
1237 ref_frame_config->
refresh[3] = 1;
1239
1240
1241
1242 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 4;
1243 ref_frame_config->
ref_idx[SVC_GOLDEN_FRAME] = 5;
1244 ref_frame_config->
refresh[4] = 1;
1245 ref_frame_config->
refresh[5] = 1;
1246 }
1247 } else if (superframe_cnt % 4 == 0) {
1248
1251
1252
1253
1254 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1255 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1256 ref_frame_config->
ref_idx[i] = 1;
1257 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 0;
1258 ref_frame_config->
refresh[0] = 1;
1260
1261
1262
1263 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1264 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1265 ref_frame_config->
ref_idx[i] = 3;
1266 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1267 ref_frame_config->
refresh[2] = 1;
1269
1270
1271
1272 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1273 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1274 ref_frame_config->
ref_idx[i] = 5;
1275 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 4;
1276 ref_frame_config->
refresh[4] = 1;
1277 }
1278 } else if ((superframe_cnt - 1) % 4 == 0) {
1279
1282
1283
1284 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1285 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1286 ref_frame_config->
ref_idx[i] = 1;
1287 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 0;
1289
1290
1291 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1292 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1293 ref_frame_config->
ref_idx[i] = 3;
1294 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1296
1297
1298 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1299 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1300 ref_frame_config->
ref_idx[i] = 5;
1301 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 4;
1302 }
1303 } else if ((superframe_cnt - 2) % 4 == 0) {
1304
1307
1308
1309
1310 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1311 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1312 ref_frame_config->
ref_idx[i] = 1;
1313 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 0;
1314 ref_frame_config->
refresh[1] = 1;
1316
1317
1318
1319 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1320 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1321 ref_frame_config->
ref_idx[i] = 3;
1322 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 2;
1323 ref_frame_config->
refresh[3] = 1;
1325
1326
1327
1328 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1329 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1330 ref_frame_config->
ref_idx[i] = 5;
1331 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 4;
1332 ref_frame_config->
refresh[5] = 1;
1333 }
1334 } else if ((superframe_cnt - 3) % 4 == 0) {
1335
1338
1339
1340 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1341 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1342 ref_frame_config->
ref_idx[i] = 0;
1343 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 1;
1345
1346
1347 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1348 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1349 ref_frame_config->
ref_idx[i] = 2;
1350 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 3;
1352
1353
1354 ref_frame_config->
reference[SVC_LAST_FRAME] = 1;
1355 for (i = 0; i < INTER_REFS_PER_FRAME; i++)
1356 ref_frame_config->
ref_idx[i] = 4;
1357 ref_frame_config->
ref_idx[SVC_LAST_FRAME] = 5;
1358 }
1359 }
1361
1362 ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 1;
1363 if (ksvc_mode) {
1364
1365
1366 if (!is_key_frame) ref_frame_config->
reference[SVC_GOLDEN_FRAME] = 0;
1367 }
1369
1370
1371 ref_frame_config->
reference[SVC_LAST_FRAME] = 0;
1372 }
1373 }
1374
1375
1376
1377
1378 if (!simulcast_mode && enable_longterm_temporal_ref &&
1380 ref_frame_config->
ref_idx[SVC_ALTREF_FRAME] = REF_FRAMES - 1;
1381 if (!is_key_frame) ref_frame_config->
reference[SVC_ALTREF_FRAME] = 1;
1383 ref_frame_config->
refresh[REF_FRAMES - 1] = 1;
1384 }
1385 break;
1386 default: assert(0); die("Error: Unsupported temporal layering mode!\n");
1387 }
1388}
1389
1390static void write_literal(struct aom_write_bit_buffer *wb, uint32_t data,
1391 uint8_t bits, uint32_t offset = 0) {
1392 if (bits > 32) {
1393 die("Invalid bits value %d > 32\n", bits);
1394 }
1395 const uint32_t max = static_cast<uint32_t>(((uint64_t)1 << bits) - 1);
1396 if (data < offset || (data - offset) > max) {
1397 die("Invalid data, value %u out of range [%u, %" PRIu64 "]\n", data, offset,
1398 (uint64_t)max + offset);
1399 }
1400 aom_wb_write_unsigned_literal(wb, data - offset, bits);
1401}
1402
1403static void write_depth_representation_element(
1404 struct aom_write_bit_buffer *buffer,
1405 const std::pair<libaom_examples::DepthRepresentationElement, bool>
1406 &element) {
1407 if (!element.second) {
1408 return;
1409 }
1410 write_literal(buffer, element.first.sign_flag, 1);
1411 write_literal(buffer, element.first.exponent, 7);
1412 if (element.first.mantissa_len == 0 || element.first.mantissa_len > 32) {
1413 die("Invalid mantissan_len %d\n", element.first.mantissa_len);
1414 }
1415 write_literal(buffer, element.first.mantissa_len - 1, 5);
1416 write_literal(buffer, element.first.mantissa, element.first.mantissa_len);
1417}
1418
1419static void write_color_properties(
1420 struct aom_write_bit_buffer *buffer,
1421 const std::pair<libaom_examples::ColorProperties, bool> &color_properties) {
1422 write_literal(buffer, color_properties.second, 1);
1423 if (color_properties.second) {
1424 write_literal(buffer, color_properties.first.color_range, 1);
1425 write_literal(buffer, color_properties.first.color_primaries, 8);
1426 write_literal(buffer, color_properties.first.transfer_characteristics, 8);
1427 write_literal(buffer, color_properties.first.matrix_coefficients, 8);
1428 } else {
1429 write_literal(buffer, 0, 1);
1430 }
1431}
1432
1433static void add_multilayer_metadata(
1434 aom_image_t *frame,
const libaom_examples::MultilayerMetadata &multilayer) {
1435
1436
1437 std::vector<uint8_t> data(66000 * multilayer.layers.size());
1438 struct aom_write_bit_buffer buffer = { data.data(), 0 };
1439
1440 write_literal(&buffer, multilayer.use_case, 6);
1441 if (multilayer.layers.empty()) {
1442 die("Invalid multilayer metadata, no layers found\n");
1443 } else if (multilayer.layers.size() > MAX_NUM_SPATIAL_LAYERS) {
1444 die("Invalid multilayer metadata, too many layers (max is %d)\n",
1445 MAX_NUM_SPATIAL_LAYERS);
1446 }
1447 write_literal(&buffer, (int)multilayer.layers.size() - 1, 2);
1448 assert(buffer.bit_offset % 8 == 0);
1449 for (size_t i = 0; i < multilayer.layers.size(); ++i) {
1450 const libaom_examples::LayerMetadata &layer = multilayer.layers[i];
1451
1452
1453 const int bytes_reserved_for_size = 3;
1454
1455 write_literal(&buffer, 0, bytes_reserved_for_size * 8);
1456 const uint32_t metadata_start = buffer.bit_offset;
1457 write_literal(&buffer, (int)i, 2);
1458 write_literal(&buffer, layer.layer_type, 5);
1459 write_literal(&buffer, layer.luma_plane_only_flag, 1);
1460 write_literal(&buffer, layer.layer_view_type, 3);
1461 write_literal(&buffer, layer.group_id, 2);
1462 write_literal(&buffer, layer.layer_dependency_idc, 3);
1463 write_literal(&buffer, layer.layer_metadata_scope, 2);
1464 write_literal(&buffer, 0, 4);
1465
1466 if (i > 0) {
1467 write_color_properties(&buffer, layer.layer_color_description);
1468 } else {
1469 write_literal(&buffer, 0, 2);
1470 }
1471 assert(buffer.bit_offset % 8 == 0);
1472
1473 if (layer.layer_type == libaom_examples::MULTILAYER_LAYER_TYPE_ALPHA &&
1474 layer.layer_metadata_scope >= libaom_examples::SCOPE_GLOBAL) {
1475 const libaom_examples::AlphaInformation &alpha_info =
1476 layer.global_alpha_info;
1477 write_literal(&buffer, alpha_info.alpha_use_idc, 3);
1478 write_literal(&buffer, alpha_info.alpha_bit_depth, 3, 8);
1479 write_literal(&buffer, alpha_info.alpha_clip_idc, 2);
1480 write_literal(&buffer, alpha_info.alpha_incr_flag, 1);
1481 write_literal(&buffer, alpha_info.alpha_transparent_value,
1482 alpha_info.alpha_bit_depth + 1);
1483 write_literal(&buffer, alpha_info.alpha_opaque_value,
1484 alpha_info.alpha_bit_depth + 1);
1485 if (buffer.bit_offset % 8 != 0) {
1486
1487 write_literal(&buffer, 0, 8 - (buffer.bit_offset % 8));
1488 }
1489 assert(buffer.bit_offset % 8 == 0);
1490
1491 if (alpha_info.alpha_use_idc == libaom_examples::ALPHA_STRAIGHT) {
1492 write_literal(&buffer, 0, 6);
1493 write_color_properties(&buffer, alpha_info.alpha_color_description);
1494 } else if (alpha_info.alpha_use_idc ==
1495 libaom_examples::ALPHA_SEGMENTATION) {
1496 write_literal(&buffer, 0, 7);
1497 write_literal(&buffer, !alpha_info.label_type_id.empty(), 1);
1498 if (!alpha_info.label_type_id.empty()) {
1499 const size_t num_values =
1500 std::abs(alpha_info.alpha_transparent_value -
1501 alpha_info.alpha_opaque_value) +
1502 1;
1503 if (!alpha_info.label_type_id.empty() &&
1504 alpha_info.label_type_id.size() != num_values) {
1505 die("Invalid multilayer metadata, label_type_id size must be "
1506 "equal to the range of alpha values between "
1507 "alpha_transparent_value and alpha_opaque_value (expected "
1508 "%d values, found %d values)\n",
1509 (int)num_values, (int)alpha_info.label_type_id.size());
1510 }
1511 for (size_t j = 0; j < num_values; ++j) {
1512 write_literal(&buffer, alpha_info.label_type_id[j], 16);
1513 }
1514 }
1515 }
1516 assert(buffer.bit_offset % 8 == 0);
1517 } else if (layer.layer_type ==
1518 libaom_examples::MULTILAYER_LAYER_TYPE_DEPTH &&
1519 layer.layer_metadata_scope >= libaom_examples::SCOPE_GLOBAL) {
1520 const libaom_examples::DepthInformation &depth_info =
1521 layer.global_depth_info;
1522 write_literal(&buffer, depth_info.z_near.second, 1);
1523 write_literal(&buffer, depth_info.z_far.second, 1);
1524 write_literal(&buffer, depth_info.d_min.second, 1);
1525 write_literal(&buffer, depth_info.d_max.second, 1);
1526 write_literal(&buffer, depth_info.depth_representation_type, 4);
1527 if (depth_info.d_min.second || depth_info.d_max.second) {
1528 write_literal(&buffer, depth_info.disparity_ref_view_id, 2);
1529 }
1530 write_depth_representation_element(&buffer, depth_info.z_near);
1531 write_depth_representation_element(&buffer, depth_info.z_far);
1532 write_depth_representation_element(&buffer, depth_info.d_min);
1533 write_depth_representation_element(&buffer, depth_info.d_max);
1534 if (depth_info.depth_representation_type == 3) {
1535 write_literal(&buffer, depth_info.depth_nonlinear_precision, 4,
1536 8);
1537 if (depth_info.depth_nonlinear_representation_model.empty() ||
1538 depth_info.depth_nonlinear_representation_model.size() > (1 << 6)) {
1539 die("Invalid multilayer metadata, if depth_nonlinear_precision "
1540 "== 3, depth_nonlinear_representation_model must have 1 to "
1541 "%d elements, found %d elements\n",
1542 1 << 6,
1543 (int)depth_info.depth_nonlinear_representation_model.size());
1544 }
1545 write_literal(
1546 &buffer,
1547 (int)depth_info.depth_nonlinear_representation_model.size() - 1, 6);
1548 const int bit_depth = depth_info.depth_nonlinear_precision;
1549 for (const uint32_t v :
1550 depth_info.depth_nonlinear_representation_model) {
1551 write_literal(&buffer, v, bit_depth);
1552 }
1553 }
1554 if (buffer.bit_offset % 8 != 0) {
1555 write_literal(&buffer, 0, 8 - (buffer.bit_offset % 8));
1556 }
1557 assert(buffer.bit_offset % 8 == 0);
1558 }
1559
1560 assert(buffer.bit_offset % 8 == 0);
1561
1562 const int metadata_size_bytes = (buffer.bit_offset - metadata_start) / 8;
1563 const uint8_t size_pos = metadata_start / 8 - bytes_reserved_for_size;
1564 size_t coded_size;
1565 if (aom_uleb_encode_fixed_size(metadata_size_bytes, bytes_reserved_for_size,
1566 bytes_reserved_for_size,
1567 &buffer.bit_buffer[size_pos], &coded_size)) {
1568
1569 die("Error: Failed to write metadata size\n");
1570 }
1571 }
1572 assert(buffer.bit_offset % 8 == 0);
1574 buffer.bit_buffer, buffer.bit_offset / 8,
1576 die("Error: Failed to add metadata\n");
1577 }
1578}
1579
1580#if CONFIG_AV1_DECODER
1581
1582
1584 const int frames_out) {
1586 int mismatch = 0;
1587
1588
1591
1592#if CONFIG_AV1_HIGHBITDEPTH
1598 &enc_hbd_img,
1600 enc_img.
d_w, enc_img.
d_h, 16);
1601 aom_img_truncate_16_to_8(&enc_hbd_img, &enc_img);
1602 enc_img = enc_hbd_img;
1603 }
1607 &dec_hbd_img,
1609 dec_img.
d_w, dec_img.
d_h, 16);
1610 aom_img_truncate_16_to_8(&dec_hbd_img, &dec_img);
1611 dec_img = dec_hbd_img;
1612 }
1613 }
1614#endif
1615
1616 if (!aom_compare_img(&enc_img, &dec_img)) {
1617 int y[4], u[4], v[4];
1618#if CONFIG_AV1_HIGHBITDEPTH
1620 aom_find_mismatch_high(&enc_img, &dec_img, y, u, v);
1621 } else {
1622 aom_find_mismatch(&enc_img, &dec_img, y, u, v);
1623 }
1624#else
1625 aom_find_mismatch(&enc_img, &dec_img, y, u, v);
1626#endif
1627 fprintf(stderr,
1628 "Encode/decode mismatch on frame %d at"
1629 " Y[%d, %d] {%d/%d},"
1630 " U[%d, %d] {%d/%d},"
1631 " V[%d, %d] {%d/%d}\n",
1632 frames_out, y[0], y[1], y[2], y[3], u[0], u[1], u[2], u[3], v[0],
1633 v[1], v[2], v[3]);
1634 mismatch = 1;
1635 }
1636
1639 return mismatch;
1640}
1641#endif
1642
1643struct psnr_stats {
1644
1645 uint64_t psnr_sse_total[2];
1646 uint64_t psnr_samples_total[2];
1647 double psnr_totals[2][4];
1648 int psnr_count[2];
1649};
1650
1651static void show_psnr(struct psnr_stats *psnr_stream, double peak) {
1652 double ovpsnr;
1653
1654 if (!psnr_stream->psnr_count[0]) return;
1655
1656 fprintf(stderr, "\nPSNR (Overall/Avg/Y/U/V)");
1657 ovpsnr = sse_to_psnr((double)psnr_stream->psnr_samples_total[0], peak,
1658 (double)psnr_stream->psnr_sse_total[0]);
1659 fprintf(stderr, " %.3f", ovpsnr);
1660
1661 for (int i = 0; i < 4; i++) {
1662 fprintf(stderr, " %.3f",
1663 psnr_stream->psnr_totals[0][i] / psnr_stream->psnr_count[0]);
1664 }
1665 fprintf(stderr, "\n");
1666}
1667
1668static aom::AV1RateControlRtcConfig create_rtc_rc_config(
1670 aom::AV1RateControlRtcConfig rc_cfg;
1671 rc_cfg.width = cfg.
g_w;
1672 rc_cfg.height = cfg.
g_h;
1681
1682 rc_cfg.max_intra_bitrate_pct = 300;
1684
1685 rc_cfg.ss_number_layers = 1;
1686 rc_cfg.ts_number_layers = 1;
1687 rc_cfg.scaling_factor_num[0] = 1;
1688 rc_cfg.scaling_factor_den[0] = 1;
1689 rc_cfg.layer_target_bitrate[0] = static_cast<int>(rc_cfg.target_bandwidth);
1690 rc_cfg.max_quantizers[0] = rc_cfg.max_quantizer;
1691 rc_cfg.min_quantizers[0] = rc_cfg.min_quantizer;
1692 rc_cfg.aq_mode = app_input.aq_mode;
1693
1694 return rc_cfg;
1695}
1696
1697static int qindex_to_quantizer(int qindex) {
1698
1699
1700 static const int quantizer_to_qindex[] = {
1701 0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 44, 48,
1702 52, 56, 60, 64, 68, 72, 76, 80, 84, 88, 92, 96, 100,
1703 104, 108, 112, 116, 120, 124, 128, 132, 136, 140, 144, 148, 152,
1704 156, 160, 164, 168, 172, 176, 180, 184, 188, 192, 196, 200, 204,
1705 208, 212, 216, 220, 224, 228, 232, 236, 240, 244, 249, 255,
1706 };
1707 for (int quantizer = 0; quantizer < 64; ++quantizer)
1708 if (quantizer_to_qindex[quantizer] >= qindex) return quantizer;
1709
1710 return 63;
1711}
1712
1716
1717 map.
rows = (cfg->
g_h + 15) / 16;
1718 map.
cols = (cfg->
g_w + 15) / 16;
1719
1721 if (!map.
active_map) die(
"Failed to allocate active map");
1722
1723
1724 for (
unsigned int i = 0; i < map.
rows; ++i) {
1725 for (
unsigned int j = 0; j < map.
cols; ++j) {
1726 int index = map.
cols * i + j;
1728 if (frame_cnt < 300) {
1730 } else if (frame_cnt >= 300) {
1731 if (i < map.rows / 2 && j >= map.
cols / 2) map.
active_map[index] = 0;
1732 }
1733 }
1734 }
1735
1737 die_codec(codec, "Failed to set active map");
1738
1740}
1741
1742int main(int argc, const char **argv) {
1743 AppInput app_input;
1746 AvxVideoWriter *total_layer_file = NULL;
1747 FILE *total_layer_obu_file = NULL;
1749 int frame_cnt = 0;
1751 int frame_avail;
1752 int got_data = 0;
1753 int flags = 0;
1754 int i;
1755 int pts = 0;
1756 int frame_duration = 1;
1761
1762#if CONFIG_INTERNAL_STATS
1763 FILE *stats_file = fopen("opsnr.stt", "a");
1764 if (stats_file == NULL) {
1765 die("Cannot open opsnr.stt\n");
1766 }
1767#endif
1768#if CONFIG_AV1_DECODER
1770#endif
1771
1772 struct RateControlMetrics rc;
1773 int64_t cx_time = 0;
1776 double sum_bitrate = 0.0;
1777 double sum_bitrate2 = 0.0;
1778 double framerate = 30.0;
1779 int use_svc_control = 1;
1780 int set_err_resil_frame = 0;
1781 int test_changing_bitrate = 0;
1782 zero(rc.layer_target_bitrate);
1784 memset(&app_input, 0, sizeof(AppInput));
1785 memset(&svc_params, 0, sizeof(svc_params));
1786
1787
1788
1789 const int test_dynamic_scaling_single_layer = 0;
1790
1791
1792 const int test_speed_per_layer = 0;
1793
1794
1795 const int test_active_maps = 0;
1796
1797
1798 for (i = 0; i < MAX_NUM_SPATIAL_LAYERS; ++i) {
1799 app_input.input_ctx[i].framerate.numerator = 30;
1800 app_input.input_ctx[i].framerate.denominator = 1;
1801 app_input.input_ctx[i].only_i420 = 0;
1802 app_input.input_ctx[i].bit_depth =
AOM_BITS_8;
1803 }
1804 app_input.speed = 7;
1805 exec_name = argv[0];
1806
1807
1812 }
1813
1814
1816
1830
1831 parse_command_line(argc, argv, &app_input, &svc_params, &cfg);
1832
1835
1836 unsigned int width = cfg.
g_w;
1837 unsigned int height = cfg.
g_h;
1838
1839 if (app_input.layering_mode >= 0) {
1840 if (ts_number_layers !=
1841 mode_to_num_temporal_layers[app_input.layering_mode] ||
1842 ss_number_layers !=
1843 mode_to_num_spatial_layers[app_input.layering_mode]) {
1844 die("Number of layers doesn't match layering mode.");
1845 }
1846 }
1847
1848 bool has_non_y4m_input = false;
1850 if (app_input.input_ctx[i].file_type != FILE_TYPE_Y4M) {
1851 has_non_y4m_input = true;
1852 break;
1853 }
1854 }
1855
1856 if (has_non_y4m_input) {
1858 die("Failed to allocate image (%dx%d)", width, height);
1859 }
1860 }
1861
1863
1866
1867 unsigned int total_rate = 0;
1868 for (i = 0; i < ss_number_layers; i++) {
1869 total_rate +=
1870 svc_params
1872 }
1874 die("Incorrect total target bitrate, expected: %d", total_rate);
1875 }
1876
1878 if (ts_number_layers == 2) {
1881 } else if (ts_number_layers == 3) {
1885 }
1886
1887 libaom_examples::MultilayerMetadata multilayer_metadata;
1888 if (app_input.multilayer_metadata_file != NULL) {
1889 if (!libaom_examples::parse_multilayer_file(
1890 app_input.multilayer_metadata_file, &multilayer_metadata)) {
1891 die("Failed to parse multilayer metadata");
1892 }
1893 libaom_examples::print_multilayer_metadata(multilayer_metadata);
1894 }
1895
1897 set_rate_control_metrics(&rc, framerate, ss_number_layers, ts_number_layers);
1898
1899 AvxVideoInfo info;
1900 info.codec_fourcc = get_fourcc_by_aom_encoder(encoder);
1901 info.frame_width = cfg.
g_w;
1902 info.frame_height = cfg.
g_h;
1905
1906 for (int sl = 0; sl < ss_number_layers; ++sl) {
1907 for (int tl = 0; tl < ts_number_layers; ++tl) {
1908 i = sl * ts_number_layers + tl;
1909 char file_name[PATH_MAX];
1910 snprintf(file_name, sizeof(file_name), "%s_%d.av1",
1911 app_input.output_filename, i);
1912 if (app_input.output_obu) {
1913 obu_files[i] = fopen(file_name, "wb");
1914 if (!obu_files[i]) die("Failed to open %s for writing", file_name);
1915 } else {
1916 outfile[i] = aom_video_writer_open(file_name, kContainerIVF, &info);
1917 if (!outfile[i]) die("Failed to open %s for writing", file_name);
1918 }
1919 }
1920 }
1921 if (app_input.output_obu) {
1922 total_layer_obu_file = fopen(app_input.output_filename, "wb");
1923 if (!total_layer_obu_file)
1924 die("Failed to open %s for writing", app_input.output_filename);
1925 } else {
1926 total_layer_file =
1927 aom_video_writer_open(app_input.output_filename, kContainerIVF, &info);
1928 if (!total_layer_file)
1929 die("Failed to open %s for writing", app_input.output_filename);
1930 }
1931
1932
1938 die_codec(&codec, "Failed to initialize encoder");
1939
1940#if CONFIG_AV1_DECODER
1941 if (app_input.decode) {
1943 die_codec(&decoder, "Failed to initialize decoder");
1944 }
1945#endif
1946
1963
1964
1970
1972
1974 if (app_input.tune_content == AOM_CONTENT_SCREEN) {
1976
1978 }
1979
1980 if (app_input.use_external_rc) {
1982 }
1983
1985
1988
1990
1993 for (i = 0; i < ss_number_layers * ts_number_layers; ++i) {
1996 }
1997 if (!app_input.scale_factors_explicitly_set) {
1998 for (i = 0; i < ss_number_layers; ++i) {
2001 }
2002 if (ss_number_layers == 2) {
2005 } else if (ss_number_layers == 3) {
2010 }
2011 }
2013
2014
2015
2016
2017
2018 {
2019 const int max_intra_size_pct = 300;
2021 max_intra_size_pct);
2022 }
2023
2024 for (int lx = 0; lx < ts_number_layers * ss_number_layers; lx++) {
2025 cx_time_layer[lx] = 0;
2026 frame_cnt_layer[lx] = 0;
2027 }
2028
2029 std::unique_ptr<aom::AV1RateControlRTC> rc_api;
2030 if (app_input.use_external_rc) {
2031 const aom::AV1RateControlRtcConfig rc_cfg =
2032 create_rtc_rc_config(cfg, app_input);
2033 rc_api = aom::AV1RateControlRTC::Create(rc_cfg);
2034 }
2035
2036 frame_avail = 1;
2037 struct psnr_stats psnr_stream;
2038 memset(&psnr_stream, 0, sizeof(psnr_stream));
2039 while (frame_avail || got_data) {
2040 struct aom_usec_timer timer;
2041 frame_avail = read_frame(&(app_input.input_ctx[0]), &raw);
2042
2043 for (int slx = 0; slx < ss_number_layers; slx++) {
2044 if (slx > 0 && app_input.input_ctx[slx].filename != NULL) {
2045 const int previous_layer_frame_avail = frame_avail;
2046 frame_avail = read_frame(&(app_input.input_ctx[slx]), &raw);
2047 if (previous_layer_frame_avail != frame_avail) {
2048 die("Mismatch in number of frames between spatial layer input files");
2049 }
2050 }
2051
2054 int layer = 0;
2055
2056 int is_key_frame = (frame_cnt % cfg.
kf_max_dist) == 0;
2057
2058 if (app_input.layering_mode >= 0) {
2059
2060
2061 set_layer_pattern(app_input.layering_mode, frame_cnt, &layer_id,
2062 &ref_frame_config, &ref_frame_comp_pred,
2063 &use_svc_control, slx, is_key_frame,
2064 (app_input.layering_mode == 10), app_input.speed);
2066 if (use_svc_control) {
2068 &ref_frame_config);
2070 &ref_frame_comp_pred);
2071 }
2072 if (app_input.multilayer_metadata_file != NULL) {
2073 add_multilayer_metadata(&raw, multilayer_metadata);
2074 }
2075
2076 if (test_speed_per_layer) {
2077 int speed_per_layer = 10;
2090 }
2092 }
2093 } else {
2094
2095
2096
2099 if (ts_number_layers == 2) {
2101 } else if (ts_number_layers == 3) {
2102 if (frame_cnt % 2 != 0)
2104 else if ((frame_cnt > 1) && ((frame_cnt - 2) % 4 == 0))
2106 }
2108 }
2109
2111
2112
2113
2114
2115
2116
2117
2118 const int err_resil_mode =
2121 err_resil_mode);
2122 }
2123
2125 if (frame_avail && slx == 0) ++rc.layer_input_frames[layer];
2126
2127 if (test_dynamic_scaling_single_layer) {
2128
2129
2130 int frame_2x2 = 200;
2131 int frame_4x4 = 400;
2132 int frame_2x2up = 600;
2133 int frame_orig = 800;
2134 if (frame_cnt >= frame_2x2 && frame_cnt < frame_4x4) {
2135
2138 } else if (frame_cnt >= frame_4x4 && frame_cnt < frame_2x2up) {
2139
2142 } else if (frame_cnt >= frame_2x2up && frame_cnt < frame_orig) {
2143
2146 } else if (frame_cnt >= frame_orig) {
2147
2150 }
2151 if (frame_cnt == frame_2x2 || frame_cnt == frame_4x4 ||
2152 frame_cnt == frame_2x2up || frame_cnt == frame_orig) {
2153
2154
2155
2156
2157
2158 for (i = 0; i < REF_FRAMES; i++) ref_frame_config.
refresh[i] = 1;
2159 if (use_svc_control) {
2161 &ref_frame_config);
2163 &ref_frame_comp_pred);
2164 }
2165 }
2166 }
2167
2168
2169 if (test_changing_bitrate && frame_cnt % 2 == 0) {
2170 if (frame_cnt < 500)
2172 else
2174
2178
2179
2182 die_codec(&codec, "Failed to SET_BITRATE_ONE_PASS_CBR");
2183 }
2184
2185 if (rc_api) {
2186 aom::AV1FrameParamsRTC frame_params;
2187
2188 frame_params.spatial_layer_id = 0;
2189 frame_params.temporal_layer_id = 0;
2190 frame_params.frame_type =
2191 is_key_frame ? aom::kKeyFrame : aom::kInterFrame;
2192 rc_api->ComputeQP(frame_params);
2193 const int current_qp = rc_api->GetQP();
2195 qindex_to_quantizer(current_qp))) {
2196 die_codec(&codec, "Failed to SET_QUANTIZER_ONE_PASS");
2197 }
2198 }
2199
2200 if (test_active_maps) set_active_map(&cfg, &codec, frame_cnt);
2201
2202
2203 aom_usec_timer_start(&timer);
2205 die_codec(&codec, "Failed to encode frame");
2206 aom_usec_timer_mark(&timer);
2207 cx_time += aom_usec_timer_elapsed(&timer);
2208 cx_time_layer[layer] += aom_usec_timer_elapsed(&timer);
2209 frame_cnt_layer[layer] += 1;
2210
2211
2212 int content_flag = 0;
2214 &content_flag)) {
2215 die_codec(&codec, "Failed to GET_HIGH_MOTION_CONTENT_SCREEN_RTC");
2216 }
2217
2218 got_data = 0;
2219
2220 int ss_layers_write = (app_input.layering_mode == 11)
2222 : ss_number_layers;
2224 switch (pkt->
kind) {
2227 ++sl) {
2229 ++tl) {
2230 int j = sl * ts_number_layers + tl;
2231 if (app_input.output_obu) {
2233 obu_files[j]);
2234 } else {
2235 aom_video_writer_write_frame(
2236 outfile[j],
2237 reinterpret_cast<const uint8_t *
>(pkt->
data.
frame.
buf),
2239 }
2241 rc.layer_encoding_bitrate[j] += 8.0 * pkt->
data.
frame.
sz;
2242 }
2243 }
2244 got_data = 1;
2245
2246 if (app_input.output_obu) {
2248 total_layer_obu_file);
2249 } else {
2250 aom_video_writer_write_frame(
2251 total_layer_file,
2252 reinterpret_cast<const uint8_t *
>(pkt->
data.
frame.
buf),
2254 }
2255
2259 assert(j >= 0);
2260 rc.layer_avg_frame_size[j] += 8.0 * pkt->
data.
frame.
sz;
2261 rc.layer_avg_rate_mismatch[j] +=
2262 fabs(8.0 * pkt->
data.
frame.
sz - rc.layer_pfb[j]) /
2263 rc.layer_pfb[j];
2265 }
2266
2267 if (rc_api) {
2269 }
2270
2271
2272
2273
2274 if (frame_cnt > rc.window_size && slx == ss_number_layers - 1) {
2275 sum_bitrate += 0.001 * 8.0 * pkt->
data.
frame.
sz * framerate;
2276 rc.window_size = (rc.window_size <= 0) ? 1 : rc.window_size;
2277 if (frame_cnt % rc.window_size == 0) {
2278 rc.window_count += 1;
2279 rc.avg_st_encoding_bitrate += sum_bitrate / rc.window_size;
2280 rc.variance_st_encoding_bitrate +=
2281 (sum_bitrate / rc.window_size) *
2282 (sum_bitrate / rc.window_size);
2283 sum_bitrate = 0.0;
2284 }
2285 }
2286
2287 if (frame_cnt > rc.window_size + rc.window_size / 2 &&
2288 slx == ss_number_layers - 1) {
2289 sum_bitrate2 += 0.001 * 8.0 * pkt->
data.
frame.
sz * framerate;
2290 if (frame_cnt > 2 * rc.window_size &&
2291 frame_cnt % rc.window_size == 0) {
2292 rc.window_count += 1;
2293 rc.avg_st_encoding_bitrate += sum_bitrate2 / rc.window_size;
2294 rc.variance_st_encoding_bitrate +=
2295 (sum_bitrate2 / rc.window_size) *
2296 (sum_bitrate2 / rc.window_size);
2297 sum_bitrate2 = 0.0;
2298 }
2299 }
2300
2301#if CONFIG_AV1_DECODER
2302 if (app_input.decode) {
2304 &decoder,
2305 reinterpret_cast<const uint8_t *
>(pkt->
data.
frame.
buf),
2307 die_codec(&decoder, "Failed to decode frame");
2308 }
2309#endif
2310
2311 break;
2313 if (app_input.show_psnr) {
2314 psnr_stream.psnr_sse_total[0] += pkt->
data.
psnr.sse[0];
2315 psnr_stream.psnr_samples_total[0] += pkt->
data.
psnr.samples[0];
2316 for (int plane = 0; plane < 4; plane++) {
2317 psnr_stream.psnr_totals[0][plane] += pkt->
data.
psnr.psnr[plane];
2318 }
2319 psnr_stream.psnr_count[0]++;
2320 }
2321 break;
2322 default: break;
2323 }
2324 }
2325#if CONFIG_AV1_DECODER
2326 if (got_data && app_input.decode) {
2327
2328
2329 if ((ss_number_layers > 1 || ts_number_layers > 1) &&
2332 if (test_decode(&codec, &decoder, frame_cnt)) {
2333#if CONFIG_INTERNAL_STATS
2334 fprintf(stats_file, "First mismatch occurred in frame %d\n",
2335 frame_cnt);
2336 fclose(stats_file);
2337#endif
2338 fatal("Mismatch seen");
2339 }
2340 }
2341 }
2342#endif
2343 }
2344 ++frame_cnt;
2345 pts += frame_duration;
2346 }
2347
2348 for (i = 0; i < MAX_NUM_SPATIAL_LAYERS; ++i) {
2349 if (app_input.input_ctx[i].filename == NULL) {
2350 break;
2351 }
2352 close_input_file(&(app_input.input_ctx[i]));
2353 }
2354 printout_rate_control_summary(&rc, frame_cnt, ss_number_layers,
2355 ts_number_layers);
2356
2357 printf("\n");
2358 for (int slx = 0; slx < ss_number_layers; slx++)
2359 for (int tlx = 0; tlx < ts_number_layers; tlx++) {
2360 int lx = slx * ts_number_layers + tlx;
2361 printf("Per layer encoding time/FPS stats for encoder: %d %d %d %f %f \n",
2362 slx, tlx, frame_cnt_layer[lx],
2363 (float)cx_time_layer[lx] / (double)(frame_cnt_layer[lx] * 1000),
2364 1000000 * (double)frame_cnt_layer[lx] / (double)cx_time_layer[lx]);
2365 }
2366
2367 printf("\n");
2368 printf("Frame cnt and encoding time/FPS stats for encoding: %d %f %f\n",
2369 frame_cnt, 1000 * (float)cx_time / (double)(frame_cnt * 1000000),
2370 1000000 * (double)frame_cnt / (double)cx_time);
2371
2372 if (app_input.show_psnr) {
2373 show_psnr(&psnr_stream, 255.0);
2374 }
2375
2377
2378#if CONFIG_AV1_DECODER
2379 if (app_input.decode) {
2381 die_codec(&decoder, "Failed to destroy decoder");
2382 }
2383#endif
2384
2385#if CONFIG_INTERNAL_STATS
2386 fprintf(stats_file, "No mismatch detected in recon buffers\n");
2387 fclose(stats_file);
2388#endif
2389
2390
2391 for (i = 0; i < ss_number_layers * ts_number_layers; ++i)
2392 aom_video_writer_close(outfile[i]);
2393 aom_video_writer_close(total_layer_file);
2394
2395 if (has_non_y4m_input) {
2397 }
2398 return EXIT_SUCCESS;
2399}
Describes the decoder algorithm interface to applications.
Describes the encoder algorithm interface to applications.
Describes the aom image descriptor and associated operations.
@ AOM_MIF_KEY_FRAME
Definition aom_image.h:166
@ AOM_CSP_UNKNOWN
Definition aom_image.h:143
enum aom_chroma_sample_position aom_chroma_sample_position_t
List of chroma sample positions.
#define AOM_IMG_FMT_HIGHBITDEPTH
Definition aom_image.h:38
aom_image_t * aom_img_alloc(aom_image_t *img, aom_img_fmt_t fmt, unsigned int d_w, unsigned int d_h, unsigned int align)
Open a descriptor, allocating storage for the underlying image.
@ AOM_IMG_FMT_I420
Definition aom_image.h:45
enum aom_img_fmt aom_img_fmt_t
List of supported image formats.
int aom_img_add_metadata(aom_image_t *img, uint32_t type, const uint8_t *data, size_t sz, aom_metadata_insert_flags_t insert_flag)
Add metadata to image.
struct aom_image aom_image_t
Image Descriptor.
void aom_img_free(aom_image_t *img)
Close an image descriptor.
Provides definitions for using AOM or AV1 encoder algorithm within the aom Codec Interface.
#define AOM_MAX_LAYERS
Definition aomcx.h:1720
struct aom_svc_params aom_svc_params_t
#define AOM_MAX_TS_LAYERS
Definition aomcx.h:1722
aom_codec_iface_t * aom_codec_av1_cx(void)
The interface to the AV1 encoder.
struct aom_svc_layer_id aom_svc_layer_id_t
struct aom_active_map aom_active_map_t
aom active region map
struct aom_svc_ref_frame_comp_pred aom_svc_ref_frame_comp_pred_t
struct aom_svc_ref_frame_config aom_svc_ref_frame_config_t
@ AOM_FULL_SUPERFRAME_DROP
Definition aomcx.h:1782
@ AV1E_SET_BITRATE_ONE_PASS_CBR
Codec control to set the target bitrate in kilobits per second, unsigned int parameter....
Definition aomcx.h:1536
@ AV1E_SET_ENABLE_SMOOTH_INTRA
Codec control function to turn on / off smooth intra modes usage, int parameter.
Definition aomcx.h:1077
@ AV1E_SET_ENABLE_TPL_MODEL
Codec control function to enable RDO modulated by frame temporal dependency, unsigned int parameter.
Definition aomcx.h:414
@ AV1E_SET_AQ_MODE
Codec control function to set adaptive quantization mode, unsigned int parameter.
Definition aomcx.h:474
@ AV1E_SET_SVC_LAYER_ID
Codec control function to set the layer id, aom_svc_layer_id_t* parameter.
Definition aomcx.h:1285
@ AV1E_SET_SVC_REF_FRAME_CONFIG
Codec control function to set the reference frame config, aom_svc_ref_frame_config_t* parameter.
Definition aomcx.h:1295
@ AV1E_SET_TUNE_CONTENT
Codec control function to set content type, aom_tune_content parameter.
Definition aomcx.h:503
@ AV1E_SET_CDF_UPDATE_MODE
Codec control function to set CDF update mode, unsigned int parameter.
Definition aomcx.h:512
@ AV1E_SET_ENABLE_ANGLE_DELTA
Codec control function to turn on/off intra angle delta, int parameter.
Definition aomcx.h:1124
@ AV1E_SET_MV_COST_UPD_FREQ
Control to set frequency of the cost updates for motion vectors, unsigned int parameter.
Definition aomcx.h:1263
@ AV1E_SET_INTRA_DEFAULT_TX_ONLY
Control to use default tx type only for intra modes, int parameter.
Definition aomcx.h:1212
@ AV1E_SET_SVC_REF_FRAME_COMP_PRED
Codec control function to set reference frame compound prediction. aom_svc_ref_frame_comp_pred_t* par...
Definition aomcx.h:1400
@ AV1E_SET_ENABLE_INTRABC
Codec control function to turn on/off intra block copy mode, int parameter.
Definition aomcx.h:1120
@ AV1E_SET_ENABLE_WARPED_MOTION
Codec control function to turn on / off warped motion usage at sequence level, int parameter.
Definition aomcx.h:1045
@ AV1E_SET_RTC_EXTERNAL_RC
Codec control function to set flag for rate control used by external encoders.
Definition aomcx.h:1435
@ AV1E_SET_COEFF_COST_UPD_FREQ
Control to set frequency of the cost updates for coefficients, unsigned int parameter.
Definition aomcx.h:1243
@ AV1E_SET_ENABLE_CDEF
Codec control function to encode with CDEF, unsigned int parameter.
Definition aomcx.h:677
@ AOME_SET_ACTIVEMAP
Codec control function to pass an Active map to encoder, aom_active_map_t* parameter.
Definition aomcx.h:190
@ AV1E_SET_DV_COST_UPD_FREQ
Control to set frequency of the cost updates for intrabc motion vectors, unsigned int parameter.
Definition aomcx.h:1366
@ AV1E_SET_SVC_FRAME_DROP_MODE
Codec control to set the frame drop mode for SVC, unsigned int parameter. The valid values are consta...
Definition aomcx.h:1549
@ AV1E_SET_SVC_PARAMS
Codec control function to set SVC parameters, aom_svc_params_t* parameter.
Definition aomcx.h:1290
@ AV1E_SET_ENABLE_FILTER_INTRA
Codec control function to turn on / off filter intra usage at sequence level, int parameter.
Definition aomcx.h:1066
@ AV1E_SET_ENABLE_PALETTE
Codec control function to turn on/off palette mode, int parameter.
Definition aomcx.h:1116
@ AV1E_SET_ENABLE_CFL_INTRA
Codec control function to turn on / off CFL uv intra mode usage, int parameter.
Definition aomcx.h:1095
@ AOME_SET_MAX_INTRA_BITRATE_PCT
Codec control function to set max data rate for intra frames, unsigned int parameter.
Definition aomcx.h:312
@ AV1E_SET_ERROR_RESILIENT_MODE
Codec control function to enable error_resilient_mode, int parameter.
Definition aomcx.h:448
@ AV1E_SET_ENABLE_OBMC
Codec control function to predict with OBMC mode, unsigned int parameter.
Definition aomcx.h:704
@ AV1E_SET_AUTO_TILES
Codec control to set auto tiling, unsigned int parameter. Value of 1 means encoder will set number of...
Definition aomcx.h:1557
@ AV1E_SET_LOOPFILTER_CONTROL
Codec control to control loop filter.
Definition aomcx.h:1415
@ AOME_SET_SCALEMODE
Codec control function to set encoder scaling mode for the next frame to be coded,...
Definition aomcx.h:197
@ AV1E_SET_ENABLE_ORDER_HINT
Codec control function to turn on / off frame order hint (int parameter). Affects: joint compound mod...
Definition aomcx.h:872
@ AV1E_SET_DELTAQ_MODE
Codec control function to set the delta q mode, unsigned int parameter.
Definition aomcx.h:1140
@ AV1E_SET_POSTENCODE_DROP_RTC
Codec control to enable post encode frame drop for RTC encoding, int parameter.
Definition aomcx.h:1573
@ AV1E_SET_ENABLE_GLOBAL_MOTION
Codec control function to turn on / off global motion usage for a sequence, int parameter.
Definition aomcx.h:1035
@ AOME_SET_CPUUSED
Codec control function to set encoder internal speed settings, int parameter.
Definition aomcx.h:220
@ AV1E_GET_HIGH_MOTION_CONTENT_SCREEN_RTC
Codec control to get the high motion content flag, used for screen content realtime (RTC) encoding,...
Definition aomcx.h:1564
@ AV1E_SET_GF_CBR_BOOST_PCT
Boost percentage for Golden Frame in CBR mode, unsigned int parameter.
Definition aomcx.h:345
@ AV1E_SET_QUANTIZER_ONE_PASS
Codec control to set quantizer for the next frame, int parameter.
Definition aomcx.h:1498
@ AV1E_SET_MODE_COST_UPD_FREQ
Control to set frequency of the cost updates for mode, unsigned int parameter.
Definition aomcx.h:1253
@ AV1E_SET_MAX_CONSEC_FRAME_DROP_MS_CBR
Codec control to set the maximum number of consecutive frame drops, in units of time (milliseconds),...
Definition aomcx.h:1579
@ AV1_GET_NEW_FRAME_IMAGE
Codec control function to get a pointer to the new frame.
Definition aom.h:70
const char * aom_codec_iface_name(aom_codec_iface_t *iface)
Return the name for a given interface.
enum aom_bit_depth aom_bit_depth_t
Bit depth for codecThis enumeration determines the bit depth of the codec.
aom_codec_err_t aom_codec_control(aom_codec_ctx_t *ctx, int ctrl_id,...)
Algorithm Control.
long aom_codec_flags_t
Initialization-time Feature Enabling.
Definition aom_codec.h:232
struct aom_codec_ctx aom_codec_ctx_t
Codec context structure.
const struct aom_codec_iface aom_codec_iface_t
Codec interface structure.
Definition aom_codec.h:271
aom_codec_err_t aom_codec_destroy(aom_codec_ctx_t *ctx)
Destroy a codec instance.
const char * aom_codec_err_to_string(aom_codec_err_t err)
Convert error number to printable string.
aom_codec_err_t
Algorithm return codes.
Definition aom_codec.h:155
#define AOM_CODEC_CONTROL_TYPECHECKED(ctx, id, data)
aom_codec_control wrapper macro (adds type-checking, less flexible)
Definition aom_codec.h:542
const void * aom_codec_iter_t
Iterator.
Definition aom_codec.h:305
#define AOM_FRAME_IS_KEY
Definition aom_codec.h:288
@ AOM_BITS_8
Definition aom_codec.h:336
@ AOM_BITS_10
Definition aom_codec.h:337
@ AOM_CODEC_INVALID_PARAM
An application-supplied parameter is not valid.
Definition aom_codec.h:200
@ AOM_CODEC_MEM_ERROR
Memory operation failed.
Definition aom_codec.h:163
@ AOM_CODEC_OK
Operation completed without error.
Definition aom_codec.h:157
aom_codec_err_t aom_codec_decode(aom_codec_ctx_t *ctx, const uint8_t *data, size_t data_sz, void *user_priv)
Decode data.
#define aom_codec_dec_init(ctx, iface, cfg, flags)
Convenience macro for aom_codec_dec_init_ver()
Definition aom_decoder.h:129
const aom_codec_cx_pkt_t * aom_codec_get_cx_data(aom_codec_ctx_t *ctx, aom_codec_iter_t *iter)
Encoded data iterator.
struct aom_codec_cx_pkt aom_codec_cx_pkt_t
Encoder output packet.
aom_codec_err_t aom_codec_encode(aom_codec_ctx_t *ctx, const aom_image_t *img, aom_codec_pts_t pts, unsigned long duration, aom_enc_frame_flags_t flags)
Encode a frame.
#define aom_codec_enc_init(ctx, iface, cfg, flags)
Convenience macro for aom_codec_enc_init_ver()
Definition aom_encoder.h:943
aom_codec_err_t aom_codec_enc_config_default(aom_codec_iface_t *iface, aom_codec_enc_cfg_t *cfg, unsigned int usage)
Get the default configuration for a usage.
struct aom_codec_enc_cfg aom_codec_enc_cfg_t
Encoder configuration structure.
#define AOM_USAGE_REALTIME
usage parameter analogous to AV1 REALTIME mode.
Definition aom_encoder.h:1016
#define AOM_CODEC_USE_HIGHBITDEPTH
Definition aom_encoder.h:80
#define AOM_CODEC_USE_PSNR
Initialization-time Feature Enabling.
Definition aom_encoder.h:79
@ AOM_CBR
Definition aom_encoder.h:187
@ AOM_KF_AUTO
Definition aom_encoder.h:202
@ AOM_CODEC_PSNR_PKT
Definition aom_encoder.h:113
@ AOM_CODEC_CX_FRAME_PKT
Definition aom_encoder.h:110
unsigned int rows
Definition aomcx.h:1638
unsigned int cols
Definition aomcx.h:1639
unsigned char * active_map
specify an on (1) or off (0) each 16x16 region within a frame
Definition aomcx.h:1637
size_t sz
Definition aom_encoder.h:127
enum aom_codec_cx_pkt_kind kind
Definition aom_encoder.h:123
double psnr[4]
Definition aom_encoder.h:145
union aom_codec_cx_pkt::@202210014045072156205127107315337341215221351166 data
aom_codec_frame_flags_t flags
Definition aom_encoder.h:132
struct aom_codec_cx_pkt::@202210014045072156205127107315337341215221351166::@052232317104146204273007241322037340334334344046 frame
void * buf
Definition aom_encoder.h:126
unsigned int g_input_bit_depth
Bit-depth of the input frames.
Definition aom_encoder.h:475
unsigned int rc_dropframe_thresh
Temporal resampling configuration, if supported by the codec.
Definition aom_encoder.h:540
struct aom_rational g_timebase
Stream timebase units.
Definition aom_encoder.h:489
unsigned int g_usage
Algorithm specific "usage" value.
Definition aom_encoder.h:399
unsigned int rc_buf_sz
Decoder Buffer Size.
Definition aom_encoder.h:705
unsigned int g_h
Height of the frame.
Definition aom_encoder.h:435
enum aom_kf_mode kf_mode
Keyframe placement mode.
Definition aom_encoder.h:768
enum aom_rc_mode rc_end_usage
Rate control algorithm to use.
Definition aom_encoder.h:623
unsigned int g_threads
Maximum number of threads to use.
Definition aom_encoder.h:407
unsigned int kf_min_dist
Keyframe minimum interval.
Definition aom_encoder.h:777
unsigned int g_lag_in_frames
Allow lagged encoding.
Definition aom_encoder.h:518
unsigned int rc_buf_initial_sz
Decoder Buffer Initial Size.
Definition aom_encoder.h:714
unsigned int g_profile
Bitstream profile to use.
Definition aom_encoder.h:417
aom_bit_depth_t g_bit_depth
Bit-depth of the codec.
Definition aom_encoder.h:467
unsigned int g_w
Width of the frame.
Definition aom_encoder.h:426
unsigned int rc_undershoot_pct
Rate control adaptation undershoot control.
Definition aom_encoder.h:681
unsigned int kf_max_dist
Keyframe maximum interval.
Definition aom_encoder.h:786
aom_codec_er_flags_t g_error_resilient
Enable error resilient modes.
Definition aom_encoder.h:497
unsigned int rc_max_quantizer
Maximum (Worst Quality) Quantizer.
Definition aom_encoder.h:668
unsigned int rc_buf_optimal_sz
Decoder Buffer Optimal Size.
Definition aom_encoder.h:723
unsigned int rc_min_quantizer
Minimum (Best Quality) Quantizer.
Definition aom_encoder.h:658
unsigned int rc_target_bitrate
Target data rate.
Definition aom_encoder.h:644
unsigned int rc_resize_mode
Mode for spatial resampling, if supported by the codec.
Definition aom_encoder.h:549
unsigned int rc_overshoot_pct
Rate control adaptation overshoot control.
Definition aom_encoder.h:690
aom_img_fmt_t fmt
Definition aom_image.h:183
unsigned int d_w
Definition aom_image.h:197
unsigned int d_h
Definition aom_image.h:198
int num
Definition aom_encoder.h:165
int den
Definition aom_encoder.h:166
aom image scaling mode
Definition aomcx.h:1647
int temporal_layer_id
Definition aomcx.h:1727
int spatial_layer_id
Definition aomcx.h:1726
int max_quantizers[32]
Definition aomcx.h:1739
int number_spatial_layers
Definition aomcx.h:1737
int layer_target_bitrate[32]
Definition aomcx.h:1744
int framerate_factor[8]
Definition aomcx.h:1746
int min_quantizers[32]
Definition aomcx.h:1740
int scaling_factor_den[4]
Definition aomcx.h:1742
int number_temporal_layers
Definition aomcx.h:1738
int scaling_factor_num[4]
Definition aomcx.h:1741
int use_comp_pred[3]
Definition aomcx.h:1776
int reference[7]
Definition aomcx.h:1766
int refresh[8]
Definition aomcx.h:1769
int ref_idx[7]
Definition aomcx.h:1768