Skip to content

Commit

Permalink
av1 work (#402)
Browse files Browse the repository at this point in the history
* av1 work

* fix ci errors

* bump coverage
  • Loading branch information
alfredh authored Jun 17, 2022
1 parent 239b378 commit d9834e8
Show file tree
Hide file tree
Showing 3 changed files with 272 additions and 2 deletions.
18 changes: 18 additions & 0 deletions include/re_av1.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,19 @@
*/


enum obu_type {
AV1_OBU_SEQUENCE_HEADER = 1,
AV1_OBU_TEMPORAL_DELIMITER = 2,
AV1_OBU_FRAME_HEADER = 3,
AV1_OBU_TILE_GROUP = 4,
AV1_OBU_METADATA = 5,
AV1_OBU_FRAME = 6,
AV1_OBU_REDUNDANT_FRAME_HEADER = 7,
AV1_OBU_TILE_LIST = 8,
AV1_OBU_PADDING = 15,
};


/* OBU (Open Bitstream Units) */

/**
Expand All @@ -29,6 +42,8 @@ int av1_obu_encode(struct mbuf *mb, uint8_t type, bool has_size,
int av1_obu_decode(struct av1_obu_hdr *hdr, struct mbuf *mb);
int av1_obu_print(struct re_printf *pf, const struct av1_obu_hdr *hdr);
unsigned av1_obu_count(const uint8_t *buf, size_t size);
unsigned av1_obu_count_rtp(const uint8_t *buf, size_t size);
const char *av1_obu_name(enum obu_type type);


/*
Expand All @@ -43,6 +58,9 @@ typedef int (av1_packet_h)(bool marker, uint64_t rtp_ts,
int av1_packetize(bool *newp, bool marker, uint64_t rtp_ts,
const uint8_t *buf, size_t len, size_t maxlen,
av1_packet_h *pkth, void *arg);
int av1_packetize_high(bool *newp, bool marker, uint64_t rtp_ts,
const uint8_t *buf, size_t len, size_t maxlen,
av1_packet_h *pkth, void *arg);


enum {
Expand Down
67 changes: 65 additions & 2 deletions src/av1/obu.c
Original file line number Diff line number Diff line change
Expand Up @@ -193,8 +193,9 @@ int av1_obu_print(struct re_printf *pf, const struct av1_obu_hdr *hdr)
if (!hdr)
return 0;

return re_hprintf(pf, "type=%u x=%d s=%d size=%zu",
hdr->type, hdr->x, hdr->s, hdr->size);
return re_hprintf(pf, "type=%u,%s x=%d s=%d size=%zu",
hdr->type, av1_obu_name(hdr->type),
hdr->x, hdr->s, hdr->size);
}


Expand Down Expand Up @@ -226,3 +227,65 @@ unsigned av1_obu_count(const uint8_t *buf, size_t size)

return count;
}


unsigned av1_obu_count_rtp(const uint8_t *buf, size_t size)
{
struct mbuf wrap = {
.buf = (uint8_t *)buf,
.size = size,
.pos = 0,
.end = size
};
unsigned count = 0;

while (mbuf_get_left(&wrap) > 1) {

struct av1_obu_hdr hdr;

int err = av1_obu_decode(&hdr, &wrap);
if (err) {
DEBUG_WARNING("count: could not decode OBU"
" [%zu bytes]: %m\n", size, err);
return 0;
}

switch (hdr.type) {

case AV1_OBU_SEQUENCE_HEADER:
case AV1_OBU_FRAME_HEADER:
case AV1_OBU_METADATA:
case AV1_OBU_FRAME:
case AV1_OBU_REDUNDANT_FRAME_HEADER:
case AV1_OBU_TILE_LIST:
++count;
break;

default:
break;
}

mbuf_advance(&wrap, hdr.size);
}

return count;
}


const char *av1_obu_name(enum obu_type type)
{
switch (type) {

case AV1_OBU_SEQUENCE_HEADER: return "OBU_SEQUENCE_HEADER";
case AV1_OBU_TEMPORAL_DELIMITER: return "OBU_TEMPORAL_DELIMITER";
case AV1_OBU_FRAME_HEADER: return "OBU_FRAME_HEADER";
case AV1_OBU_REDUNDANT_FRAME_HEADER:
return "OBU_REDUNDANT_FRAME_HEADER";
case AV1_OBU_FRAME: return "OBU_FRAME";
case AV1_OBU_TILE_GROUP: return "OBU_TILE_GROUP";
case AV1_OBU_METADATA: return "OBU_METADATA";
case AV1_OBU_TILE_LIST: return "OBU_TILE_LIST";
case AV1_OBU_PADDING: return "OBU_PADDING";
default: return "???";
}
}
189 changes: 189 additions & 0 deletions src/av1/pkt.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,17 @@

#include <string.h>
#include <re_types.h>
#include <re_fmt.h>
#include <re_mem.h>
#include <re_mbuf.h>
#include <re_av1.h>


#define DEBUG_MODULE "av1"
#define DEBUG_LEVEL 5
#include <re_dbg.h>


static void hdr_encode(uint8_t hdr[AV1_AGGR_HDR_SIZE],
bool z, bool y, uint8_t w, bool n)
{
Expand Down Expand Up @@ -64,3 +71,185 @@ int av1_packetize(bool *newp, bool marker, uint64_t rtp_ts,

return err;
}


static struct mbuf *encode_obu(uint8_t type, const uint8_t *p, size_t len)
{
struct mbuf *mb = mbuf_alloc(len);
const bool has_size = false; /* NOTE */
int err;

if (!mb)
return NULL;

err = av1_obu_encode(mb, type, has_size, len, p);
if (err) {
mem_deref(mb);
return NULL;
}

mb->pos = 0;

return mb;
}


static int copy_obus(struct mbuf *mb_pkt, const uint8_t *buf, size_t size,
bool w0)
{
struct mbuf wrap = {
.buf = (uint8_t *)buf,
.size = size,
.pos = 0,
.end = size
};
struct mbuf *mb_obu = NULL;
int err = 0;

while (mbuf_get_left(&wrap) >= 2) {

struct av1_obu_hdr hdr;
bool last;

err = av1_obu_decode(&hdr, &wrap);
if (err) {
DEBUG_WARNING("av1: encode: hdr dec error (%m)\n",
err);
return err;
}

last = (hdr.size == mbuf_get_left(&wrap));

switch (hdr.type) {

case AV1_OBU_SEQUENCE_HEADER:
case AV1_OBU_FRAME_HEADER:
case AV1_OBU_METADATA:
case AV1_OBU_FRAME:
case AV1_OBU_REDUNDANT_FRAME_HEADER:
case AV1_OBU_TILE_LIST:
mb_obu = encode_obu(hdr.type, mbuf_buf(&wrap),
hdr.size);
if (!mb_obu) {
err = ENOMEM;
goto out;
}

if (last) {
if (w0)
err = av1_leb128_encode(mb_pkt,
mb_obu->end);
}
else {
err = av1_leb128_encode(mb_pkt, mb_obu->end);
}

if (err)
goto out;

err = mbuf_write_mem(mb_pkt, mb_obu->buf, mb_obu->end);
if (err)
goto out;

break;

case AV1_OBU_TEMPORAL_DELIMITER:
case AV1_OBU_TILE_GROUP:
case AV1_OBU_PADDING:
/* skip */
break;

default:
DEBUG_WARNING("av1: unknown obu type %u\n", hdr.type);
break;
}

mbuf_advance(&wrap, hdr.size);

mb_obu = mem_deref(mb_obu);
}

out:
mem_deref(mb_obu);
return err;
}


static int av1_packetize_internal(bool *newp, bool marker, uint64_t rtp_ts,
const uint8_t *buf, size_t len,
size_t maxlen, uint8_t w,
av1_packet_h *pkth, void *arg)
{
uint8_t hdr[AV1_AGGR_HDR_SIZE];
bool cont = false;
int err = 0;


if (w > 3) {
DEBUG_WARNING("w too large\n");
return EPROTO;
}

maxlen -= sizeof(hdr);

while (len > maxlen) {

hdr_encode(hdr, cont, true, w, *newp);
*newp = false;

err |= pkth(false, rtp_ts, hdr, sizeof(hdr), buf, maxlen, arg);

buf += maxlen;
len -= maxlen;
cont = true;
}

hdr_encode(hdr, cont, false, w, *newp);
*newp = false;

err |= pkth(marker, rtp_ts, hdr, sizeof(hdr), buf, len, arg);

return err;
}


int av1_packetize_high(bool *newp, bool marker, uint64_t rtp_ts,
const uint8_t *buf, size_t len, size_t maxlen,
av1_packet_h *pkth, void *arg)
{
struct mbuf *mb_pkt;
unsigned count = 0;
uint8_t w;
int err;

if (!newp || !buf || !len || maxlen < (AV1_AGGR_HDR_SIZE + 1) || !pkth)
return EINVAL;

mb_pkt = mbuf_alloc(len);
if (!mb_pkt)
return ENOMEM;

count = av1_obu_count_rtp(buf, len);

if (count > 3) {
w = 0;
}
else {
w = count;
}

err = copy_obus(mb_pkt, buf, len, count > 3);
if (err)
goto out;

err = av1_packetize_internal(newp, marker, rtp_ts,
mb_pkt->buf, mb_pkt->end, maxlen,
w,
pkth, arg);
if (err)
goto out;

out:
mem_deref(mb_pkt);
return err;
}

0 comments on commit d9834e8

Please sign in to comment.