Commit 41150ad4 authored by Tom Finegan's avatar Tom Finegan

Add obu_sizing experiment.

Writes PRE_OBU_SIZE_BYTES (currently 4) bytes padded unsigned LEB128
encoded integers in OBU size fields when enabled:

$ cmake path/to/aom -DCONFIG_OBU=1 -DCONFIG_OBU_SIZING=1 && cmake --build .

Requires CONFIG_OBU.

BUG=aomedia:1125

Change-Id: I4d184ef0c8587d24e9c8c3e63237ea5003386c6a
parent b3bb318d
...@@ -1400,7 +1400,7 @@ static aom_codec_err_t encoder_encode(aom_codec_alg_priv_t *ctx, ...@@ -1400,7 +1400,7 @@ static aom_codec_err_t encoder_encode(aom_codec_alg_priv_t *ctx,
#if CONFIG_OBU #if CONFIG_OBU
// move data PRE_OBU_SIZE_BYTES + 1 bytes and insert OBU_TD preceded by // move data PRE_OBU_SIZE_BYTES + 1 bytes and insert OBU_TD preceded by
// optional 4 byte size // 4 byte size
uint32_t obu_size = 1; uint32_t obu_size = 1;
if (ctx->pending_cx_data) { if (ctx->pending_cx_data) {
const size_t index_sz = PRE_OBU_SIZE_BYTES + 1; const size_t index_sz = PRE_OBU_SIZE_BYTES + 1;
...@@ -1411,9 +1411,17 @@ static aom_codec_err_t encoder_encode(aom_codec_alg_priv_t *ctx, ...@@ -1411,9 +1411,17 @@ static aom_codec_err_t encoder_encode(aom_codec_alg_priv_t *ctx,
OBU_TEMPORAL_DELIMITER, 0, OBU_TEMPORAL_DELIMITER, 0,
(uint8_t *)(ctx->pending_cx_data + PRE_OBU_SIZE_BYTES)); (uint8_t *)(ctx->pending_cx_data + PRE_OBU_SIZE_BYTES));
obu_size += write_temporal_delimiter_obu(); obu_size += write_temporal_delimiter_obu();
#if CONFIG_OBU_SIZING
// OBUs are preceded by an unsigned leb128 coded unsigned integer padded
// to PRE_OBU_SIZE_BYTES bytes.
if (write_uleb_obu_size(obu_size, ctx->pending_cx_data) != AOM_CODEC_OK)
return AOM_CODEC_ERROR;
#else
mem_put_le32(ctx->pending_cx_data, obu_size); mem_put_le32(ctx->pending_cx_data, obu_size);
#endif // CONFIG_OBU_SIZING
pkt.data.frame.sz += (obu_size + PRE_OBU_SIZE_BYTES); pkt.data.frame.sz += (obu_size + PRE_OBU_SIZE_BYTES);
#endif #endif // CONFIG_OBU
pkt.data.frame.pts = ticks_to_timebase_units(timebase, dst_time_stamp); pkt.data.frame.pts = ticks_to_timebase_units(timebase, dst_time_stamp);
pkt.data.frame.flags = get_frame_pkt_flags(cpi, lib_flags); pkt.data.frame.flags = get_frame_pkt_flags(cpi, lib_flags);
......
...@@ -175,10 +175,20 @@ void av1_decode_frame_from_obus(struct AV1Decoder *pbi, const uint8_t *data, ...@@ -175,10 +175,20 @@ void av1_decode_frame_from_obus(struct AV1Decoder *pbi, const uint8_t *data,
struct aom_read_bit_buffer rb; struct aom_read_bit_buffer rb;
size_t obu_header_size, obu_payload_size = 0; size_t obu_header_size, obu_payload_size = 0;
av1_init_read_bit_buffer(pbi, &rb, data + PRE_OBU_SIZE_BYTES, data_end); av1_init_read_bit_buffer(pbi, &rb, data + PRE_OBU_SIZE_BYTES, data_end);
#if CONFIG_OBU_SIZING
// OBUs are preceded by an unsigned leb128 coded unsigned integer padded to
// PRE_OBU_SIZE_BYTES bytes.
uint32_t u_obu_size = 0;
aom_uleb_decode(data, PRE_OBU_SIZE_BYTES, &u_obu_size);
const size_t obu_size = (size_t)u_obu_size;
#else
// every obu is preceded by PRE_OBU_SIZE_BYTES-byte size of obu (obu header // every obu is preceded by PRE_OBU_SIZE_BYTES-byte size of obu (obu header
// + payload size) // + payload size)
// The obu size is only needed for tile group OBUs // The obu size is only needed for tile group OBUs
const size_t obu_size = mem_get_le32(data); const size_t obu_size = mem_get_le32(data);
#endif // CONFIG_OBU_SIZING
const OBU_TYPE obu_type = read_obu_header(&rb, &obu_header_size); const OBU_TYPE obu_type = read_obu_header(&rb, &obu_header_size);
data += (PRE_OBU_SIZE_BYTES + obu_header_size); data += (PRE_OBU_SIZE_BYTES + obu_header_size);
if (data_end < data) { if (data_end < data) {
......
...@@ -4367,6 +4367,22 @@ uint32_t write_obu_header(OBU_TYPE obu_type, int obu_extension, ...@@ -4367,6 +4367,22 @@ uint32_t write_obu_header(OBU_TYPE obu_type, int obu_extension,
return size; return size;
} }
#if CONFIG_OBU_SIZING
int write_uleb_obu_size(uint32_t obu_size, uint8_t *dest) {
size_t coded_obu_size = 0;
// Encode an unsigned leb128 coded unsigned integer padded to
// PRE_OBU_SIZE_BYTES bytes.
if (aom_uleb_encode_fixed_size(obu_size, PRE_OBU_SIZE_BYTES,
PRE_OBU_SIZE_BYTES, dest, &coded_obu_size) ||
coded_obu_size != PRE_OBU_SIZE_BYTES) {
return AOM_CODEC_ERROR;
}
return AOM_CODEC_OK;
}
#endif // CONFIG_OBU_SIZING
static uint32_t write_sequence_header_obu(AV1_COMP *cpi, uint8_t *const dst) { static uint32_t write_sequence_header_obu(AV1_COMP *cpi, uint8_t *const dst) {
AV1_COMMON *const cm = &cpi->common; AV1_COMMON *const cm = &cpi->common;
struct aom_write_bit_buffer wb = { dst, 0 }; struct aom_write_bit_buffer wb = { dst, 0 };
...@@ -4670,8 +4686,13 @@ static uint32_t write_tiles_in_tg_obus(AV1_COMP *const cpi, uint8_t *const dst, ...@@ -4670,8 +4686,13 @@ static uint32_t write_tiles_in_tg_obus(AV1_COMP *const cpi, uint8_t *const dst,
// size of this tile // size of this tile
mem_put_le32(buf->data, tile_size); mem_put_le32(buf->data, tile_size);
} else { } else {
// write current tile group size // write current tile group size
mem_put_le32(data, curr_tg_data_size); #if CONFIG_OBU_SIZING
if (write_uleb_obu_size(curr_tg_data_size, data) != AOM_CODEC_OK)
assert(0);
#else
mem_put_le32(data, curr_tg_data_size);
#endif // CONFIG_OBU_SIZING
} }
total_size += tile_size; total_size += tile_size;
...@@ -4683,7 +4704,7 @@ static uint32_t write_tiles_in_tg_obus(AV1_COMP *const cpi, uint8_t *const dst, ...@@ -4683,7 +4704,7 @@ static uint32_t write_tiles_in_tg_obus(AV1_COMP *const cpi, uint8_t *const dst,
return (uint32_t)total_size; return (uint32_t)total_size;
} }
#endif #endif // CONFIG_OBU
int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) { int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) {
uint8_t *data = dst; uint8_t *data = dst;
...@@ -4695,7 +4716,7 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) { ...@@ -4695,7 +4716,7 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) {
uint32_t obu_size; uint32_t obu_size;
uint8_t *frame_header_location; uint8_t *frame_header_location;
uint32_t frame_header_size; uint32_t frame_header_size;
#endif #endif // CONFIG_OBU
(void)cm; (void)cm;
#if CONFIG_BITSTREAM_DEBUG #if CONFIG_BITSTREAM_DEBUG
bitstream_queue_reset_write(); bitstream_queue_reset_write();
...@@ -4710,7 +4731,14 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) { ...@@ -4710,7 +4731,14 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) {
write_obu_header(OBU_SEQUENCE_HEADER, 0, data + PRE_OBU_SIZE_BYTES); write_obu_header(OBU_SEQUENCE_HEADER, 0, data + PRE_OBU_SIZE_BYTES);
obu_size += obu_size +=
write_sequence_header_obu(cpi, data + PRE_OBU_SIZE_BYTES + obu_size); write_sequence_header_obu(cpi, data + PRE_OBU_SIZE_BYTES + obu_size);
#if CONFIG_OBU_SIZING
if (write_uleb_obu_size(obu_size, data) != AOM_CODEC_OK)
return AOM_CODEC_ERROR;
#else
mem_put_le32(data, obu_size); mem_put_le32(data, obu_size);
#endif // CONFIG_OBU_SIZING
data += obu_size + PRE_OBU_SIZE_BYTES; data += obu_size + PRE_OBU_SIZE_BYTES;
} }
...@@ -4728,7 +4756,14 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) { ...@@ -4728,7 +4756,14 @@ int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dst, size_t *size) {
#endif #endif
data + PRE_OBU_SIZE_BYTES + obu_size); data + PRE_OBU_SIZE_BYTES + obu_size);
obu_size += frame_header_size; obu_size += frame_header_size;
#if CONFIG_OBU_SIZING
if (write_uleb_obu_size(obu_size, data) != AOM_CODEC_OK)
return AOM_CODEC_ERROR;
#else
mem_put_le32(data, obu_size); mem_put_le32(data, obu_size);
#endif // CONFIG_OBU_SIZING
data += obu_size + PRE_OBU_SIZE_BYTES; data += obu_size + PRE_OBU_SIZE_BYTES;
if (cm->show_existing_frame) { if (cm->show_existing_frame) {
......
...@@ -27,7 +27,11 @@ void write_sequence_header(AV1_COMP *cpi, struct aom_write_bit_buffer *wb); ...@@ -27,7 +27,11 @@ void write_sequence_header(AV1_COMP *cpi, struct aom_write_bit_buffer *wb);
#if CONFIG_OBU #if CONFIG_OBU
uint32_t write_obu_header(OBU_TYPE obu_type, int obu_extension, uint32_t write_obu_header(OBU_TYPE obu_type, int obu_extension,
uint8_t *const dst); uint8_t *const dst);
#endif
#if CONFIG_OBU_SIZING
int write_uleb_obu_size(uint32_t obu_size, uint8_t *dest);
#endif // CONFIG_OBU_SIZING
#endif // CONFIG_OBU
int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dest, size_t *size); int av1_pack_bitstream(AV1_COMP *const cpi, uint8_t *dest, size_t *size);
......
...@@ -148,6 +148,7 @@ set(CONFIG_NEW_QUANT 0 CACHE NUMBER "AV1 experiment flag.") ...@@ -148,6 +148,7 @@ set(CONFIG_NEW_QUANT 0 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_NO_FRAME_CONTEXT_SIGNALING 0 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_NO_FRAME_CONTEXT_SIGNALING 0 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_OBU 1 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_OBU 1 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_OBU_NO_IVF 0 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_OBU_NO_IVF 0 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_OBU_SIZING 0 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_OPT_REF_MV 0 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_OPT_REF_MV 0 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_PALETTE_THROUGHPUT 1 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_PALETTE_THROUGHPUT 1 CACHE NUMBER "AV1 experiment flag.")
set(CONFIG_PARALLEL_DEBLOCKING 1 CACHE NUMBER "AV1 experiment flag.") set(CONFIG_PARALLEL_DEBLOCKING 1 CACHE NUMBER "AV1 experiment flag.")
......
...@@ -60,8 +60,13 @@ int obu_read_temporal_unit(FILE *infile, uint8_t **buffer, size_t *bytes_read, ...@@ -60,8 +60,13 @@ int obu_read_temporal_unit(FILE *infile, uint8_t **buffer, size_t *bytes_read,
break; break;
} }
// otherwise, read the OBU payload into memory // otherwise, read the OBU payload into memory
#if CONFIG_OBU_SIZING
aom_uleb_decode(data, PRE_OBU_SIZE_BYTES, &obu_size);
#else
obu_size = mem_get_le32(data); obu_size = mem_get_le32(data);
#endif // CONFIG_OBU_SIZING
// fprintf(stderr, "Found OBU of type %d and size %d\n", // fprintf(stderr, "Found OBU of type %d and size %d\n",
// ((data[PRE_OBU_SIZE_BYTES] >> 3) & 0xF), obu_size); // ((data[PRE_OBU_SIZE_BYTES] >> 3) & 0xF), obu_size);
obu_size--; // removing the byte of the header already read obu_size--; // removing the byte of the header already read
...@@ -82,7 +87,7 @@ int obu_read_temporal_unit(FILE *infile, uint8_t **buffer, size_t *bytes_read, ...@@ -82,7 +87,7 @@ int obu_read_temporal_unit(FILE *infile, uint8_t **buffer, size_t *bytes_read,
int file_is_obu(struct AvxInputContext *input_ctx) { int file_is_obu(struct AvxInputContext *input_ctx) {
uint8_t obutd[PRE_OBU_SIZE_BYTES + OBU_HEADER_SIZE_BYTES]; uint8_t obutd[PRE_OBU_SIZE_BYTES + OBU_HEADER_SIZE_BYTES];
int size; uint32_t size;
#if !CONFIG_OBU #if !CONFIG_OBU
warn("obudec.c requires CONFIG_OBU"); warn("obudec.c requires CONFIG_OBU");
...@@ -91,7 +96,13 @@ int file_is_obu(struct AvxInputContext *input_ctx) { ...@@ -91,7 +96,13 @@ int file_is_obu(struct AvxInputContext *input_ctx) {
// Reading the first OBU TD to enable TU end detection at TD start. // Reading the first OBU TD to enable TU end detection at TD start.
fread(obutd, 1, PRE_OBU_SIZE_BYTES + OBU_HEADER_SIZE_BYTES, input_ctx->file); fread(obutd, 1, PRE_OBU_SIZE_BYTES + OBU_HEADER_SIZE_BYTES, input_ctx->file);
#if CONFIG_OBU_SIZING
aom_uleb_decode(obutd, PRE_OBU_SIZE_BYTES, &size);
#else
size = mem_get_le32(obutd); size = mem_get_le32(obutd);
#endif // CONFIG_OBU_SIZING
if (size != 1) { if (size != 1) {
warn("Expected first OBU size to be 1, got %d", size); warn("Expected first OBU size to be 1, got %d", size);
return 0; return 0;
......
...@@ -21,6 +21,7 @@ ...@@ -21,6 +21,7 @@
#error "obu_parser.cc requires CONFIG_OBU" #error "obu_parser.cc requires CONFIG_OBU"
#endif #endif
#include "aom/aom_integer.h"
#include "aom_ports/mem_ops.h" #include "aom_ports/mem_ops.h"
#include "tools/obu_parser.h" #include "tools/obu_parser.h"
...@@ -170,7 +171,14 @@ bool DumpObu(const uint8_t *data, int length) { ...@@ -170,7 +171,14 @@ bool DumpObu(const uint8_t *data, int length) {
return false; return false;
} }
#if CONFIG_OBU_SIZING
uint32_t obu_size = 0;
aom_uleb_decode(data + consumed, kObuLengthFieldSizeBytes, &obu_size);
const int current_obu_length = static_cast<int>(obu_size);
#else
const int current_obu_length = mem_get_le32(data + consumed); const int current_obu_length = mem_get_le32(data + consumed);
#endif // CONFIG_OBU_SIZING
if (current_obu_length > remaining) { if (current_obu_length > remaining) {
fprintf(stderr, fprintf(stderr,
"OBU parsing failed at offset %d with bad length of %d " "OBU parsing failed at offset %d with bad length of %d "
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment