Commit 70d9664f authored by Dmitry Kovalev's avatar Dmitry Kovalev
Browse files

Adding API to get vpx encoder/decoder interface.

Change-Id: I137e5e6585356792913e1e84da6c0a439c5153a5
parent 9453c647
...@@ -82,9 +82,9 @@ int main(int argc, char **argv) { ...@@ -82,9 +82,9 @@ int main(int argc, char **argv) {
int frame_cnt = 0; int frame_cnt = 0;
FILE *outfile = NULL; FILE *outfile = NULL;
vpx_codec_ctx_t codec; vpx_codec_ctx_t codec;
vpx_codec_iface_t *iface = NULL;
VpxVideoReader *reader = NULL; VpxVideoReader *reader = NULL;
const VpxVideoInfo *info = NULL; const VpxVideoInfo *info = NULL;
const VpxInterface *decoder = NULL;
exec_name = argv[0]; exec_name = argv[0];
...@@ -100,13 +100,13 @@ int main(int argc, char **argv) { ...@@ -100,13 +100,13 @@ int main(int argc, char **argv) {
info = vpx_video_reader_get_info(reader); info = vpx_video_reader_get_info(reader);
iface = get_codec_interface(info->codec_fourcc); decoder = get_vpx_decoder_by_fourcc(info->codec_fourcc);
if (!iface) if (!decoder)
die("Unknown input codec."); die("Unknown input codec.");
printf("Using %s\n", vpx_codec_iface_name(iface)); printf("Using %s\n", vpx_codec_iface_name(decoder->interface()));
if (vpx_codec_dec_init(&codec, iface, NULL, 0)) if (vpx_codec_dec_init(&codec, decoder->interface(), NULL, 0))
die_codec(&codec, "Failed to initialize decoder"); die_codec(&codec, "Failed to initialize decoder");
while (vpx_video_reader_read_frame(reader)) { while (vpx_video_reader_read_frame(reader)) {
......
...@@ -76,7 +76,7 @@ int main(int argc, char **argv) { ...@@ -76,7 +76,7 @@ int main(int argc, char **argv) {
int frame_cnt = 0; int frame_cnt = 0;
FILE *outfile = NULL; FILE *outfile = NULL;
vpx_codec_ctx_t codec; vpx_codec_ctx_t codec;
vpx_codec_iface_t *iface = NULL; const VpxInterface *decoder = NULL;
VpxVideoReader *reader = NULL; VpxVideoReader *reader = NULL;
const VpxVideoInfo *info = NULL; const VpxVideoInfo *info = NULL;
int n = 0; int n = 0;
...@@ -104,13 +104,13 @@ int main(int argc, char **argv) { ...@@ -104,13 +104,13 @@ int main(int argc, char **argv) {
info = vpx_video_reader_get_info(reader); info = vpx_video_reader_get_info(reader);
iface = get_codec_interface(info->codec_fourcc); decoder = get_vpx_decoder_by_fourcc(info->codec_fourcc);
if (!iface) if (!decoder)
die("Unknown input codec."); die("Unknown input codec.");
printf("Using %s\n", vpx_codec_iface_name(iface)); printf("Using %s\n", vpx_codec_iface_name(decoder->interface()));
if (vpx_codec_dec_init(&codec, iface, NULL, 0)) if (vpx_codec_dec_init(&codec, decoder->interface(), NULL, 0))
die_codec(&codec, "Failed to initialize decoder."); die_codec(&codec, "Failed to initialize decoder.");
while (vpx_video_reader_read_frame(reader)) { while (vpx_video_reader_read_frame(reader)) {
......
...@@ -64,8 +64,8 @@ int main(int argc, char **argv) { ...@@ -64,8 +64,8 @@ int main(int argc, char **argv) {
FILE *outfile = NULL; FILE *outfile = NULL;
vpx_codec_ctx_t codec; vpx_codec_ctx_t codec;
vpx_codec_err_t res; vpx_codec_err_t res;
vpx_codec_iface_t *iface = NULL;
VpxVideoReader *reader = NULL; VpxVideoReader *reader = NULL;
const VpxInterface *decoder = NULL;
const VpxVideoInfo *info = NULL; const VpxVideoInfo *info = NULL;
exec_name = argv[0]; exec_name = argv[0];
...@@ -82,17 +82,16 @@ int main(int argc, char **argv) { ...@@ -82,17 +82,16 @@ int main(int argc, char **argv) {
info = vpx_video_reader_get_info(reader); info = vpx_video_reader_get_info(reader);
iface = get_codec_interface(info->codec_fourcc); decoder = get_vpx_decoder_by_fourcc(info->codec_fourcc);
if (!iface) if (!decoder)
die("Unknown input codec."); die("Unknown input codec.");
printf("Using %s\n", vpx_codec_iface_name(iface)); printf("Using %s\n", vpx_codec_iface_name(decoder->interface()));
res = vpx_codec_dec_init(&codec, iface, NULL, VPX_CODEC_USE_POSTPROC); res = vpx_codec_dec_init(&codec, decoder->interface(), NULL,
if (res == VPX_CODEC_INCAPABLE) { VPX_CODEC_USE_POSTPROC);
printf("NOTICE: Postproc not supported.\n"); if (res == VPX_CODEC_INCAPABLE)
res = vpx_codec_dec_init(&codec, iface, NULL, 0); die_codec(&codec, "Postproc not supported by this decoder.");
}
if (res) if (res)
die_codec(&codec, "Failed to initialize decoder."); die_codec(&codec, "Failed to initialize decoder.");
......
...@@ -101,8 +101,8 @@ int main(int argc, char **argv) { ...@@ -101,8 +101,8 @@ int main(int argc, char **argv) {
int frame_cnt = 0; int frame_cnt = 0;
FILE *outfile = NULL; FILE *outfile = NULL;
vpx_codec_ctx_t codec; vpx_codec_ctx_t codec;
vpx_codec_iface_t *iface = NULL;
VpxVideoReader *reader = NULL; VpxVideoReader *reader = NULL;
const VpxInterface *decoder = NULL;
const VpxVideoInfo *info = NULL; const VpxVideoInfo *info = NULL;
exec_name = argv[0]; exec_name = argv[0];
...@@ -119,13 +119,13 @@ int main(int argc, char **argv) { ...@@ -119,13 +119,13 @@ int main(int argc, char **argv) {
info = vpx_video_reader_get_info(reader); info = vpx_video_reader_get_info(reader);
iface = get_codec_interface(info->codec_fourcc); decoder = get_vpx_decoder_by_fourcc(info->codec_fourcc);
if (!iface) if (!decoder)
die("Unknown input codec."); die("Unknown input codec.");
printf("Using %s\n", vpx_codec_iface_name(iface)); printf("Using %s\n", vpx_codec_iface_name(decoder->interface()));
if (vpx_codec_dec_init(&codec, iface, NULL, 0)) if (vpx_codec_dec_init(&codec, decoder->interface(), NULL, 0))
die_codec(&codec, "Failed to initialize decoder."); die_codec(&codec, "Failed to initialize decoder.");
while (vpx_video_reader_read_frame(reader)) { while (vpx_video_reader_read_frame(reader)) {
......
...@@ -86,18 +86,16 @@ ...@@ -86,18 +86,16 @@
#include <string.h> #include <string.h>
#define VPX_CODEC_DISABLE_COMPAT 1 #define VPX_CODEC_DISABLE_COMPAT 1
#include "vpx/vp8cx.h"
#include "vpx/vpx_encoder.h" #include "vpx/vpx_encoder.h"
#include "./tools_common.h" #include "./tools_common.h"
#include "./video_writer.h" #include "./video_writer.h"
#define interface (vpx_codec_vp8_cx())
static const char *exec_name; static const char *exec_name;
void usage_exit() { void usage_exit() {
fprintf(stderr, "Usage: %s <width> <height> <infile> <outfile>\n", exec_name); fprintf(stderr, "Usage: %s <codec> <width> <height> <infile> <outfile>\n",
exec_name);
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
} }
...@@ -110,17 +108,27 @@ int main(int argc, char **argv) { ...@@ -110,17 +108,27 @@ int main(int argc, char **argv) {
vpx_codec_err_t res; vpx_codec_err_t res;
VpxVideoInfo info = {0}; VpxVideoInfo info = {0};
VpxVideoWriter *writer = NULL; VpxVideoWriter *writer = NULL;
const VpxInterface *encoder = NULL;
const int fps = 30; // TODO(dkovalev) add command line argument const int fps = 30; // TODO(dkovalev) add command line argument
const int bitrate = 200; // kbit/s TODO(dkovalev) add command line argument const int bitrate = 200; // kbit/s TODO(dkovalev) add command line argument
const char *const codec_arg = argv[1];
const char *const width_arg = argv[2];
const char *const height_arg = argv[3];
const char *const infile_arg = argv[4];
const char *const outfile_arg = argv[5];
exec_name = argv[0]; exec_name = argv[0];
if (argc != 5) if (argc != 6)
die("Invalid number of arguments"); die("Invalid number of arguments");
info.codec_fourcc = VP8_FOURCC; encoder = get_vpx_encoder_by_name(codec_arg);
info.frame_width = strtol(argv[1], NULL, 0); if (!encoder)
info.frame_height = strtol(argv[2], NULL, 0); die("Unsupported codec.");
info.codec_fourcc = encoder->fourcc;
info.frame_width = strtol(width_arg, NULL, 0);
info.frame_height = strtol(height_arg, NULL, 0);
info.time_base.numerator = 1; info.time_base.numerator = 1;
info.time_base.denominator = fps; info.time_base.denominator = fps;
...@@ -136,9 +144,9 @@ int main(int argc, char **argv) { ...@@ -136,9 +144,9 @@ int main(int argc, char **argv) {
die("Failed to allocate image."); die("Failed to allocate image.");
} }
printf("Using %s\n", vpx_codec_iface_name(interface)); printf("Using %s\n", vpx_codec_iface_name(encoder->interface()));
res = vpx_codec_enc_config_default(interface, &cfg, 0); res = vpx_codec_enc_config_default(encoder->interface(), &cfg, 0);
if (res) if (res)
die_codec(&codec, "Failed to get default codec config."); die_codec(&codec, "Failed to get default codec config.");
...@@ -148,14 +156,14 @@ int main(int argc, char **argv) { ...@@ -148,14 +156,14 @@ int main(int argc, char **argv) {
cfg.g_timebase.den = info.time_base.denominator; cfg.g_timebase.den = info.time_base.denominator;
cfg.rc_target_bitrate = bitrate; cfg.rc_target_bitrate = bitrate;
writer = vpx_video_writer_open(argv[4], kContainerIVF, &info); writer = vpx_video_writer_open(outfile_arg, kContainerIVF, &info);
if (!writer) if (!writer)
die("Failed to open %s for writing.", argv[4]); die("Failed to open %s for writing.", outfile_arg);
if (!(infile = fopen(argv[3], "rb"))) if (!(infile = fopen(infile_arg, "rb")))
die("Failed to open %s for reading.", argv[3]); die("Failed to open %s for reading.", infile_arg);
if (vpx_codec_enc_init(&codec, interface, &cfg, 0)) if (vpx_codec_enc_init(&codec, encoder->interface(), &cfg, 0))
die_codec(&codec, "Failed to initialize encoder"); die_codec(&codec, "Failed to initialize encoder");
while (vpx_img_read(&raw, infile)) { while (vpx_img_read(&raw, infile)) {
......
...@@ -53,18 +53,16 @@ ...@@ -53,18 +53,16 @@
#include <string.h> #include <string.h>
#define VPX_CODEC_DISABLE_COMPAT 1 #define VPX_CODEC_DISABLE_COMPAT 1
#include "vpx/vp8cx.h"
#include "vpx/vpx_encoder.h" #include "vpx/vpx_encoder.h"
#include "./tools_common.h" #include "./tools_common.h"
#include "./video_writer.h" #include "./video_writer.h"
#define interface (vpx_codec_vp8_cx())
static const char *exec_name; static const char *exec_name;
void usage_exit() { void usage_exit() {
fprintf(stderr, "Usage: %s <width> <height> <infile> <outfile>\n", exec_name); fprintf(stderr, "Usage: %s <codec> <width> <height> <infile> <outfile>\n",
exec_name);
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
} }
...@@ -130,18 +128,29 @@ int main(int argc, char **argv) { ...@@ -130,18 +128,29 @@ int main(int argc, char **argv) {
vpx_codec_err_t res; vpx_codec_err_t res;
vpx_fixed_buf_t stats = {0}; vpx_fixed_buf_t stats = {0};
VpxVideoInfo info = {0}; VpxVideoInfo info = {0};
const VpxInterface *encoder = NULL;
int pass; int pass;
const int fps = 30; // TODO(dkovalev) add command line argument const int fps = 30; // TODO(dkovalev) add command line argument
const int bitrate = 200; // kbit/s TODO(dkovalev) add command line argument const int bitrate = 200; // kbit/s TODO(dkovalev) add command line argument
const char *const codec_arg = argv[1];
if (argc != 5) const char *const width_arg = argv[2];
const char *const height_arg = argv[3];
const char *const infile_arg = argv[4];
const char *const outfile_arg = argv[5];
exec_name = argv[0];
if (argc != 6)
die("Invalid number of arguments."); die("Invalid number of arguments.");
info.codec_fourcc = VP8_FOURCC; encoder = get_vpx_encoder_by_name(codec_arg);
if (!encoder)
die("Unsupported codec.");
info.codec_fourcc = encoder->fourcc;
info.time_base.numerator = 1; info.time_base.numerator = 1;
info.time_base.denominator = fps; info.time_base.denominator = fps;
info.frame_width = strtol(argv[1], NULL, 0); info.frame_width = strtol(width_arg, NULL, 0);
info.frame_height = strtol(argv[2], NULL, 0); info.frame_height = strtol(height_arg, NULL, 0);
if (info.frame_width <= 0 || if (info.frame_width <= 0 ||
info.frame_height <= 0 || info.frame_height <= 0 ||
...@@ -155,13 +164,13 @@ int main(int argc, char **argv) { ...@@ -155,13 +164,13 @@ int main(int argc, char **argv) {
die("Failed to allocate image", info.frame_width, info.frame_height); die("Failed to allocate image", info.frame_width, info.frame_height);
} }
writer = vpx_video_writer_open(argv[4], kContainerIVF, &info); writer = vpx_video_writer_open(outfile_arg, kContainerIVF, &info);
if (!writer) if (!writer)
die("Failed to open %s for writing", argv[4]); die("Failed to open %s for writing", outfile_arg);
printf("Using %s\n", vpx_codec_iface_name(interface)); printf("Using %s\n", vpx_codec_iface_name(encoder->interface()));
res = vpx_codec_enc_config_default(interface, &cfg, 0); res = vpx_codec_enc_config_default(encoder->interface(), &cfg, 0);
if (res) if (res)
die_codec(&codec, "Failed to get default codec config."); die_codec(&codec, "Failed to get default codec config.");
...@@ -181,10 +190,10 @@ int main(int argc, char **argv) { ...@@ -181,10 +190,10 @@ int main(int argc, char **argv) {
cfg.rc_twopass_stats_in = stats; cfg.rc_twopass_stats_in = stats;
} }
if (!(infile = fopen(argv[3], "rb"))) if (!(infile = fopen(infile_arg, "rb")))
die("Failed to open %s for reading", argv[3]); die("Failed to open %s for reading", infile_arg);
if (vpx_codec_enc_init(&codec, interface, &cfg, 0)) if (vpx_codec_enc_init(&codec, encoder->interface(), &cfg, 0))
die_codec(&codec, "Failed to initialize encoder"); die_codec(&codec, "Failed to initialize encoder");
while (vpx_img_read(&raw, infile)) { while (vpx_img_read(&raw, infile)) {
......
...@@ -360,9 +360,7 @@ int main(int argc, char **argv) { ...@@ -360,9 +360,7 @@ int main(int argc, char **argv) {
int flag_periodicity = 1; int flag_periodicity = 1;
int max_intra_size_pct; int max_intra_size_pct;
vpx_svc_layer_id_t layer_id = {0, 0}; vpx_svc_layer_id_t layer_id = {0, 0};
char *codec_type; const VpxInterface *encoder = NULL;
vpx_codec_iface_t *(*interface)(void);
unsigned int fourcc;
struct VpxInputContext input_ctx = {0}; struct VpxInputContext input_ctx = {0};
exec_name = argv[0]; exec_name = argv[0];
...@@ -373,23 +371,11 @@ int main(int argc, char **argv) { ...@@ -373,23 +371,11 @@ int main(int argc, char **argv) {
argv[0]); argv[0]);
} }
codec_type = argv[3]; encoder = get_vpx_encoder_by_name(argv[3]);
if (strncmp(codec_type, "vp9", 3) == 0) { if (!encoder)
#if CONFIG_VP9_ENCODER die("Unsupported codec.");
interface = vpx_codec_vp9_cx;
fourcc = VP9_FOURCC; printf("Using %s\n", vpx_codec_iface_name(encoder->interface()));
#else
die("Encoder vp9 selected but not configured");
#endif
} else {
#if CONFIG_VP8_ENCODER
interface = vpx_codec_vp8_cx;
fourcc = VP8_FOURCC;
#else
die("Encoder vp8 selected but not configured");
#endif
}
printf("Using %s\n", vpx_codec_iface_name(interface()));
width = strtol(argv[4], NULL, 0); width = strtol(argv[4], NULL, 0);
height = strtol(argv[5], NULL, 0); height = strtol(argv[5], NULL, 0);
...@@ -411,7 +397,7 @@ int main(int argc, char **argv) { ...@@ -411,7 +397,7 @@ int main(int argc, char **argv) {
} }
// Populate encoder configuration. // Populate encoder configuration.
res = vpx_codec_enc_config_default(interface(), &cfg, 0); res = vpx_codec_enc_config_default(encoder->interface(), &cfg, 0);
if (res) { if (res) {
printf("Failed to get config: %s\n", vpx_codec_err_to_string(res)); printf("Failed to get config: %s\n", vpx_codec_err_to_string(res));
return EXIT_FAILURE; return EXIT_FAILURE;
...@@ -467,7 +453,7 @@ int main(int argc, char **argv) { ...@@ -467,7 +453,7 @@ int main(int argc, char **argv) {
for (i = 0; i < cfg.ts_number_layers; ++i) { for (i = 0; i < cfg.ts_number_layers; ++i) {
char file_name[PATH_MAX]; char file_name[PATH_MAX];
VpxVideoInfo info; VpxVideoInfo info;
info.codec_fourcc = fourcc; info.codec_fourcc = encoder->fourcc;
info.frame_width = cfg.g_w; info.frame_width = cfg.g_w;
info.frame_height = cfg.g_h; info.frame_height = cfg.g_h;
info.time_base.numerator = cfg.g_timebase.num; info.time_base.numerator = cfg.g_timebase.num;
...@@ -482,12 +468,12 @@ int main(int argc, char **argv) { ...@@ -482,12 +468,12 @@ int main(int argc, char **argv) {
cfg.ss_number_layers = 1; cfg.ss_number_layers = 1;
// Initialize codec. // Initialize codec.
if (vpx_codec_enc_init(&codec, interface(), &cfg, 0)) if (vpx_codec_enc_init(&codec, encoder->interface(), &cfg, 0))
die_codec(&codec, "Failed to initialize encoder"); die_codec(&codec, "Failed to initialize encoder");
vpx_codec_control(&codec, VP8E_SET_CPUUSED, -6); vpx_codec_control(&codec, VP8E_SET_CPUUSED, -6);
vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, 1); vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, 1);
if (strncmp(codec_type, "vp9", 3) == 0) { if (strncmp(encoder->name, "vp9", 3) == 0) {
vpx_codec_control(&codec, VP8E_SET_CPUUSED, 3); vpx_codec_control(&codec, VP8E_SET_CPUUSED, 3);
vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, 0); vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, 0);
if (vpx_codec_control(&codec, VP9E_SET_SVC, 1)) { if (vpx_codec_control(&codec, VP9E_SET_SVC, 1)) {
......
...@@ -15,6 +15,10 @@ ...@@ -15,6 +15,10 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#if CONFIG_VP8_ENCODER || CONFIG_VP9_ENCODER
#include "vpx/vp8cx.h"
#endif
#if CONFIG_VP8_DECODER || CONFIG_VP9_DECODER #if CONFIG_VP8_DECODER || CONFIG_VP9_DECODER
#include "vpx/vp8dx.h" #include "vpx/vp8dx.h"
#endif #endif
...@@ -144,19 +148,75 @@ int read_yuv_frame(struct VpxInputContext *input_ctx, vpx_image_t *yuv_frame) { ...@@ -144,19 +148,75 @@ int read_yuv_frame(struct VpxInputContext *input_ctx, vpx_image_t *yuv_frame) {
return shortread; return shortread;
} }
vpx_codec_iface_t *get_codec_interface(unsigned int fourcc) { static const VpxInterface vpx_encoders[] = {
switch (fourcc) { #if CONFIG_VP8_ENCODER
{"vp8", VP8_FOURCC, &vpx_codec_vp8_cx},
#endif
#if CONFIG_VP9_ENCODER
{"vp9", VP9_FOURCC, &vpx_codec_vp9_cx},
#endif
};
int get_vpx_encoder_count() {
return sizeof(vpx_encoders) / sizeof(vpx_encoders[0]);
}
const VpxInterface *get_vpx_encoder_by_index(int i) {
return &vpx_encoders[i];
}
const VpxInterface *get_vpx_encoder_by_name(const char *name) {
int i;
for (i = 0; i < get_vpx_encoder_count(); ++i) {
const VpxInterface *encoder = get_vpx_encoder_by_index(i);
if (strcmp(encoder->name, name) == 0)
return encoder;
}
return NULL;
}
static const VpxInterface vpx_decoders[] = {
#if CONFIG_VP8_DECODER #if CONFIG_VP8_DECODER
case VP8_FOURCC: {"vp8", VP8_FOURCC, &vpx_codec_vp8_dx},
return vpx_codec_vp8_dx();
#endif #endif
#if CONFIG_VP9_DECODER #if CONFIG_VP9_DECODER
case VP9_FOURCC: {"vp9", VP9_FOURCC, &vpx_codec_vp9_dx},
return vpx_codec_vp9_dx();
#endif #endif
default: };
return NULL;
int get_vpx_decoder_count() {
return sizeof(vpx_decoders) / sizeof(vpx_decoders[0]);
}
const VpxInterface *get_vpx_decoder_by_index(int i) {
return &vpx_decoders[i];
}
const VpxInterface *get_vpx_decoder_by_name(const char *name) {
int i;
for (i = 0; i < get_vpx_decoder_count(); ++i) {
const VpxInterface *const decoder = get_vpx_decoder_by_index(i);
if (strcmp(decoder->name, name) == 0)
return decoder;
} }
return NULL;
}
const VpxInterface *get_vpx_decoder_by_fourcc(uint32_t fourcc) {
int i;
for (i = 0; i < get_vpx_decoder_count(); ++i) {
const VpxInterface *const decoder = get_vpx_decoder_by_index(i);
if (decoder->fourcc == fourcc)
return decoder;
}
return NULL; return NULL;
} }