Merge "[spatial svc] Remove encoding modes since we only need one mode at this time."

This commit is contained in:
Minghai Shang 2014-06-27 11:48:22 -07:00 committed by Gerrit Code Review
commit 83269ff8ff
4 changed files with 17 additions and 148 deletions

View File

@ -28,16 +28,6 @@
#include "vpx/vpx_encoder.h" #include "vpx/vpx_encoder.h"
#include "./vpxstats.h" #include "./vpxstats.h"
static const struct arg_enum_list encoding_mode_enum[] = {
{"i", INTER_LAYER_PREDICTION_I},
{"alt-ip", ALT_INTER_LAYER_PREDICTION_IP},
{"ip", INTER_LAYER_PREDICTION_IP},
{"gf", USE_GOLDEN_FRAME},
{NULL, 0}
};
static const arg_def_t encoding_mode_arg = ARG_DEF_ENUM(
"m", "encoding-mode", 1, "Encoding mode algorithm", encoding_mode_enum);
static const arg_def_t skip_frames_arg = static const arg_def_t skip_frames_arg =
ARG_DEF("s", "skip-frames", 1, "input frames to skip"); ARG_DEF("s", "skip-frames", 1, "input frames to skip");
static const arg_def_t frames_arg = static const arg_def_t frames_arg =
@ -74,15 +64,13 @@ static const arg_def_t max_bitrate_arg =
ARG_DEF(NULL, "max-bitrate", 1, "Maximum bitrate"); ARG_DEF(NULL, "max-bitrate", 1, "Maximum bitrate");
static const arg_def_t *svc_args[] = { static const arg_def_t *svc_args[] = {
&encoding_mode_arg, &frames_arg, &width_arg, &height_arg, &frames_arg, &width_arg, &height_arg,
&timebase_arg, &bitrate_arg, &skip_frames_arg, &layers_arg, &timebase_arg, &bitrate_arg, &skip_frames_arg, &layers_arg,
&kf_dist_arg, &scale_factors_arg, &quantizers_arg, &passes_arg, &kf_dist_arg, &scale_factors_arg, &quantizers_arg, &passes_arg,
&pass_arg, &fpf_name_arg, &min_q_arg, &max_q_arg, &pass_arg, &fpf_name_arg, &min_q_arg, &max_q_arg,
&min_bitrate_arg, &max_bitrate_arg, NULL &min_bitrate_arg, &max_bitrate_arg, NULL
}; };
static const SVC_ENCODING_MODE default_encoding_mode =
INTER_LAYER_PREDICTION_IP;
static const uint32_t default_frames_to_skip = 0; static const uint32_t default_frames_to_skip = 0;
static const uint32_t default_frames_to_code = 60 * 60; static const uint32_t default_frames_to_code = 60 * 60;
static const uint32_t default_width = 1920; static const uint32_t default_width = 1920;
@ -131,7 +119,6 @@ static void parse_command_line(int argc, const char **argv_,
// initialize SvcContext with parameters that will be passed to vpx_svc_init // initialize SvcContext with parameters that will be passed to vpx_svc_init
svc_ctx->log_level = SVC_LOG_DEBUG; svc_ctx->log_level = SVC_LOG_DEBUG;
svc_ctx->spatial_layers = default_spatial_layers; svc_ctx->spatial_layers = default_spatial_layers;
svc_ctx->encoding_mode = default_encoding_mode;
// start with default encoder configuration // start with default encoder configuration
res = vpx_codec_enc_config_default(vpx_codec_vp9_cx(), enc_cfg, 0); res = vpx_codec_enc_config_default(vpx_codec_vp9_cx(), enc_cfg, 0);
@ -157,9 +144,7 @@ static void parse_command_line(int argc, const char **argv_,
for (argi = argj = argv; (*argj = *argi); argi += arg.argv_step) { for (argi = argj = argv; (*argj = *argi); argi += arg.argv_step) {
arg.argv_step = 1; arg.argv_step = 1;
if (arg_match(&arg, &encoding_mode_arg, argi)) { if (arg_match(&arg, &frames_arg, argi)) {
svc_ctx->encoding_mode = arg_parse_enum_or_int(&arg);
} else if (arg_match(&arg, &frames_arg, argi)) {
app_input->frames_to_code = arg_parse_uint(&arg); app_input->frames_to_code = arg_parse_uint(&arg);
} else if (arg_match(&arg, &width_arg, argi)) { } else if (arg_match(&arg, &width_arg, argi)) {
enc_cfg->g_w = arg_parse_uint(&arg); enc_cfg->g_w = arg_parse_uint(&arg);
@ -264,12 +249,12 @@ static void parse_command_line(int argc, const char **argv_,
printf( printf(
"Codec %s\nframes: %d, skip: %d\n" "Codec %s\nframes: %d, skip: %d\n"
"mode: %d, layers: %d\n" "layers: %d\n"
"width %d, height: %d,\n" "width %d, height: %d,\n"
"num: %d, den: %d, bitrate: %d,\n" "num: %d, den: %d, bitrate: %d,\n"
"gop size: %d\n", "gop size: %d\n",
vpx_codec_iface_name(vpx_codec_vp9_cx()), app_input->frames_to_code, vpx_codec_iface_name(vpx_codec_vp9_cx()), app_input->frames_to_code,
app_input->frames_to_skip, svc_ctx->encoding_mode, app_input->frames_to_skip,
svc_ctx->spatial_layers, enc_cfg->g_w, enc_cfg->g_h, svc_ctx->spatial_layers, enc_cfg->g_w, enc_cfg->g_h,
enc_cfg->g_timebase.num, enc_cfg->g_timebase.den, enc_cfg->g_timebase.num, enc_cfg->g_timebase.den,
enc_cfg->rc_target_bitrate, enc_cfg->kf_max_dist); enc_cfg->rc_target_bitrate, enc_cfg->kf_max_dist);

View File

@ -41,7 +41,6 @@ class SvcTest : public ::testing::Test {
virtual ~SvcTest() {} virtual ~SvcTest() {}
virtual void SetUp() { virtual void SetUp() {
svc_.encoding_mode = INTER_LAYER_PREDICTION_IP;
svc_.log_level = SVC_LOG_DEBUG; svc_.log_level = SVC_LOG_DEBUG;
svc_.log_print = 0; svc_.log_print = 0;
@ -131,22 +130,13 @@ TEST_F(SvcTest, SetLayersOption) {
EXPECT_EQ(3, svc_.spatial_layers); EXPECT_EQ(3, svc_.spatial_layers);
} }
TEST_F(SvcTest, SetEncodingMode) {
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "encoding-mode=alt-ip");
EXPECT_EQ(VPX_CODEC_OK, res);
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
EXPECT_EQ(VPX_CODEC_OK, res);
codec_initialized_ = true;
EXPECT_EQ(ALT_INTER_LAYER_PREDICTION_IP, svc_.encoding_mode);
}
TEST_F(SvcTest, SetMultipleOptions) { TEST_F(SvcTest, SetMultipleOptions) {
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "layers=2 encoding-mode=ip"); vpx_codec_err_t res =
vpx_svc_set_options(&svc_, "layers=2 scale-factors=1/3,2/3");
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_); res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
EXPECT_EQ(VPX_CODEC_OK, res); EXPECT_EQ(VPX_CODEC_OK, res);
codec_initialized_ = true; codec_initialized_ = true;
EXPECT_EQ(2, svc_.spatial_layers); EXPECT_EQ(2, svc_.spatial_layers);
EXPECT_EQ(INTER_LAYER_PREDICTION_IP, svc_.encoding_mode);
} }
TEST_F(SvcTest, SetScaleFactorsOption) { TEST_F(SvcTest, SetScaleFactorsOption) {

View File

@ -194,23 +194,6 @@ static int svc_log(SvcContext *svc_ctx, SVC_LOG_LEVEL level,
return retval; return retval;
} }
static vpx_codec_err_t set_option_encoding_mode(SvcContext *svc_ctx,
const char *value_str) {
if (strcmp(value_str, "i") == 0) {
svc_ctx->encoding_mode = INTER_LAYER_PREDICTION_I;
} else if (strcmp(value_str, "alt-ip") == 0) {
svc_ctx->encoding_mode = ALT_INTER_LAYER_PREDICTION_IP;
} else if (strcmp(value_str, "ip") == 0) {
svc_ctx->encoding_mode = INTER_LAYER_PREDICTION_IP;
} else if (strcmp(value_str, "gf") == 0) {
svc_ctx->encoding_mode = USE_GOLDEN_FRAME;
} else {
svc_log(svc_ctx, SVC_LOG_ERROR, "invalid encoding mode: %s", value_str);
return VPX_CODEC_INVALID_PARAM;
}
return VPX_CODEC_OK;
}
static vpx_codec_err_t parse_quantizer_values(SvcContext *svc_ctx, static vpx_codec_err_t parse_quantizer_values(SvcContext *svc_ctx,
const char *quantizer_values) { const char *quantizer_values) {
char *input_string; char *input_string;
@ -344,10 +327,7 @@ static vpx_codec_err_t parse_options(SvcContext *svc_ctx, const char *options) {
res = VPX_CODEC_INVALID_PARAM; res = VPX_CODEC_INVALID_PARAM;
break; break;
} }
if (strcmp("encoding-mode", option_name) == 0) { if (strcmp("layers", option_name) == 0) {
res = set_option_encoding_mode(svc_ctx, option_value);
if (res != VPX_CODEC_OK) break;
} else if (strcmp("layers", option_name) == 0) {
svc_ctx->spatial_layers = atoi(option_value); svc_ctx->spatial_layers = atoi(option_value);
} else if (strcmp("scale-factors", option_name) == 0) { } else if (strcmp("scale-factors", option_name) == 0) {
res = parse_scale_factors(svc_ctx, option_value); res = parse_scale_factors(svc_ctx, option_value);
@ -591,62 +571,14 @@ static void calculate_enc_frame_flags(SvcContext *svc_ctx) {
return; return;
} }
switch (svc_ctx->encoding_mode) { if (si->layer == 0) {
case ALT_INTER_LAYER_PREDICTION_IP: flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
if (si->layer == 0) { } else if (is_keyframe) {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST); flags = map_vp8_flags(USE_ARF | UPDATE_LAST);
} else if (is_keyframe) { } else {
if (si->layer == si->layers - 1) { flags = map_vp8_flags(USE_LAST | USE_ARF | UPDATE_LAST);
flags = map_vp8_flags(USE_ARF | UPDATE_LAST);
} else {
flags = map_vp8_flags(USE_ARF | UPDATE_LAST | UPDATE_GF);
}
} else {
flags = map_vp8_flags(USE_LAST | USE_ARF | UPDATE_LAST);
}
break;
case INTER_LAYER_PREDICTION_I:
if (si->layer == 0) {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
} else if (is_keyframe) {
flags = map_vp8_flags(USE_ARF | UPDATE_LAST);
} else {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
}
break;
case INTER_LAYER_PREDICTION_IP:
if (si->layer == 0) {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
} else if (is_keyframe) {
flags = map_vp8_flags(USE_ARF | UPDATE_LAST);
} else {
flags = map_vp8_flags(USE_LAST | USE_ARF | UPDATE_LAST);
}
break;
case USE_GOLDEN_FRAME:
if (2 * si->layers - SVC_REFERENCE_FRAMES <= si->layer) {
if (si->layer == 0) {
flags = map_vp8_flags(USE_LAST | USE_GF | UPDATE_LAST);
} else if (is_keyframe) {
flags = map_vp8_flags(USE_ARF | UPDATE_LAST | UPDATE_GF);
} else {
flags = map_vp8_flags(USE_LAST | USE_ARF | USE_GF | UPDATE_LAST);
}
} else {
if (si->layer == 0) {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
} else if (is_keyframe) {
flags = map_vp8_flags(USE_ARF | UPDATE_LAST);
} else {
flags = map_vp8_flags(USE_LAST | UPDATE_LAST);
}
}
break;
default:
svc_log(svc_ctx, SVC_LOG_ERROR, "unexpected encoding mode: %d\n",
svc_ctx->encoding_mode);
break;
} }
si->enc_frame_flags = flags; si->enc_frame_flags = flags;
} }
@ -692,13 +624,6 @@ static void set_svc_parameters(SvcContext *svc_ctx,
svc_params.flags = si->enc_frame_flags; svc_params.flags = si->enc_frame_flags;
layer = si->layer; layer = si->layer;
if (svc_ctx->encoding_mode == ALT_INTER_LAYER_PREDICTION_IP &&
si->frame_within_gop == 0) {
// layers 1 & 3 don't exist in this mode, use the higher one
if (layer == 0 || layer == 2) {
layer += 1;
}
}
if (VPX_CODEC_OK != vpx_svc_get_layer_resolution(svc_ctx, layer, if (VPX_CODEC_OK != vpx_svc_get_layer_resolution(svc_ctx, layer,
&svc_params.width, &svc_params.width,
&svc_params.height)) { &svc_params.height)) {
@ -720,21 +645,8 @@ static void set_svc_parameters(SvcContext *svc_ctx,
svc_params.lst_fb_idx = si->layer; svc_params.lst_fb_idx = si->layer;
// Use buffer i-1 for layer i Alt (Inter-layer prediction) // Use buffer i-1 for layer i Alt (Inter-layer prediction)
if (si->layer != 0) { svc_params.alt_fb_idx = (si->layer > 0) ? si->layer - 1 : 0;
const int use_higher_layer = svc_params.gld_fb_idx = svc_params.lst_fb_idx;
svc_ctx->encoding_mode == ALT_INTER_LAYER_PREDICTION_IP &&
si->frame_within_gop == 0;
svc_params.alt_fb_idx = use_higher_layer ? si->layer - 2 : si->layer - 1;
}
if (svc_ctx->encoding_mode == ALT_INTER_LAYER_PREDICTION_IP) {
svc_params.gld_fb_idx = si->layer + 1;
} else {
if (si->layer < 2 * si->layers - SVC_REFERENCE_FRAMES)
svc_params.gld_fb_idx = svc_params.lst_fb_idx;
else
svc_params.gld_fb_idx = 2 * si->layers - 1 - si->layer;
}
svc_log(svc_ctx, SVC_LOG_DEBUG, "SVC frame: %d, layer: %d, %dx%d, q: %d\n", svc_log(svc_ctx, SVC_LOG_DEBUG, "SVC frame: %d, layer: %d, %dx%d, q: %d\n",
si->encode_frame_count, si->layer, svc_params.width, si->encode_frame_count, si->layer, svc_params.width,
@ -793,11 +705,6 @@ vpx_codec_err_t vpx_svc_encode(SvcContext *svc_ctx, vpx_codec_ctx_t *codec_ctx,
if (rawimg != NULL) { if (rawimg != NULL) {
// encode each layer // encode each layer
for (si->layer = 0; si->layer < si->layers; ++si->layer) { for (si->layer = 0; si->layer < si->layers; ++si->layer) {
if (svc_ctx->encoding_mode == ALT_INTER_LAYER_PREDICTION_IP &&
si->is_keyframe && (si->layer == 1 || si->layer == 3)) {
svc_log(svc_ctx, SVC_LOG_DEBUG, "Skip encoding layer %d\n", si->layer);
continue;
}
calculate_enc_frame_flags(svc_ctx); calculate_enc_frame_flags(svc_ctx);
set_svc_parameters(svc_ctx, codec_ctx); set_svc_parameters(svc_ctx, codec_ctx);
} }
@ -936,7 +843,7 @@ static double calc_psnr(double d) {
// dump accumulated statistics and reset accumulated values // dump accumulated statistics and reset accumulated values
const char *vpx_svc_dump_statistics(SvcContext *svc_ctx) { const char *vpx_svc_dump_statistics(SvcContext *svc_ctx) {
int number_of_frames, number_of_keyframes, encode_frame_count; int number_of_frames, encode_frame_count;
int i, j; int i, j;
uint32_t bytes_total = 0; uint32_t bytes_total = 0;
double scale[COMPONENTS]; double scale[COMPONENTS];
@ -953,14 +860,9 @@ const char *vpx_svc_dump_statistics(SvcContext *svc_ctx) {
if (si->encode_frame_count <= 0) return vpx_svc_get_message(svc_ctx); if (si->encode_frame_count <= 0) return vpx_svc_get_message(svc_ctx);
svc_log(svc_ctx, SVC_LOG_INFO, "\n"); svc_log(svc_ctx, SVC_LOG_INFO, "\n");
number_of_keyframes = encode_frame_count / si->kf_dist + 1;
for (i = 0; i < si->layers; ++i) { for (i = 0; i < si->layers; ++i) {
number_of_frames = encode_frame_count; number_of_frames = encode_frame_count;
if (svc_ctx->encoding_mode == ALT_INTER_LAYER_PREDICTION_IP &&
(i == 1 || i == 3)) {
number_of_frames -= number_of_keyframes;
}
svc_log(svc_ctx, SVC_LOG_INFO, svc_log(svc_ctx, SVC_LOG_INFO,
"Layer %d Average PSNR=[%2.3f, %2.3f, %2.3f, %2.3f], Bytes=[%u]\n", "Layer %d Average PSNR=[%2.3f, %2.3f, %2.3f, %2.3f], Bytes=[%u]\n",
i, (double)si->psnr_sum[i][0] / number_of_frames, i, (double)si->psnr_sum[i][0] / number_of_frames,

View File

@ -23,13 +23,6 @@
extern "C" { extern "C" {
#endif #endif
typedef enum SVC_ENCODING_MODE {
INTER_LAYER_PREDICTION_I,
ALT_INTER_LAYER_PREDICTION_IP,
INTER_LAYER_PREDICTION_IP,
USE_GOLDEN_FRAME
} SVC_ENCODING_MODE;
typedef enum SVC_LOG_LEVEL { typedef enum SVC_LOG_LEVEL {
SVC_LOG_ERROR, SVC_LOG_ERROR,
SVC_LOG_INFO, SVC_LOG_INFO,
@ -39,7 +32,6 @@ typedef enum SVC_LOG_LEVEL {
typedef struct { typedef struct {
// public interface to svc_command options // public interface to svc_command options
int spatial_layers; // number of layers int spatial_layers; // number of layers
SVC_ENCODING_MODE encoding_mode; // svc encoding strategy
SVC_LOG_LEVEL log_level; // amount of information to display SVC_LOG_LEVEL log_level; // amount of information to display
int log_print; // when set, printf log messages instead of returning the int log_print; // when set, printf log messages instead of returning the
// message with svc_get_message // message with svc_get_message