static int _parse_pes(PES_BUFFER *p, uint8_t *buf, unsigned len)
{
    int result = 0;

    if (len < 6) {
        BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
        return -1;
    }
    if (buf[0] || buf[1] || buf[2] != 1) {
        BD_DEBUG(DBG_DECODE, "invalid PES header (00 00 01)");
        return -1;
    }

    // Parse PES header
    unsigned pes_pid    = buf[3];
    unsigned pes_length = buf[4] << 8 | buf[5];
    unsigned hdr_len    = 6;

    if (pes_pid != 0xbf) {

        if (len < 9) {
            BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
            return -1;
        }

        unsigned pts_exists = buf[7] & 0x80;
        unsigned dts_exists = buf[7] & 0x40;
        hdr_len += buf[8] + 3;

        if (len < hdr_len) {
            BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
            return -1;
        }

        if (pts_exists) {
            p->pts = _parse_timestamp(buf + 9);
        }
        if (dts_exists) {
            p->dts = _parse_timestamp(buf + 14);
        }
    }

    result = pes_length + 6 - hdr_len;

    if (_realloc(p, BD_MAX(result, 0x100)) < 0) {
        return -1;
    }

    p->len = len - hdr_len;
    memcpy(p->buf, buf + hdr_len, p->len);

    return result;
}
Exemple #2
0
/*
 * _add_ts()
 * - add ts payload to buffer.
 * - parse PES header if pusi is set.
 * - return:
 *   < 0   error (incorrect PES header)
 *   = 0   PES packet continue
 *   > 0   PES packet payload length from PES header
 */
static int _add_ts(PES_BUFFER *p, unsigned pusi, uint8_t *buf, unsigned len)
{
    int result = 0;

    if (pusi) {
        // Parse PES header
        unsigned pes_length = buf[4] << 8 | buf[5];
        unsigned pts_exists = buf[7] & 0x80;
        unsigned dts_exists = buf[7] & 0x40;
        unsigned hdr_len    = buf[8] + 9;

        if (buf[0] || buf[1] || buf[2] != 1) {
            BD_DEBUG(DBG_DECODE, "invalid PES header (00 00 01)");
            return -1;
        }

        if (len < hdr_len) {
            BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
            return -1;
        }

        if (pts_exists) {
            p->pts = _parse_timestamp(buf + 9);
        }
        if (dts_exists) {
            p->dts = _parse_timestamp(buf + 14);
        }

        buf += hdr_len;
        len -= hdr_len;

        result = pes_length + 6 - hdr_len;
    }

    // realloc
    if (p->size < p->len + len) {
        p->size *= 2;
        p->buf   = realloc(p->buf, p->size);
    }

    // append
    memcpy(p->buf + p->len, buf, len);
    p->len += len;

    return result;
}
Exemple #3
0
/*
 * _add_ts()
 * - add ts payload to buffer.
 * - parse PES header if pusi is set.
 * - return:
 *   < 0   error (incorrect PES header)
 *   = 0   PES packet continue
 *   > 0   PES packet payload length from PES header
 */
static int _add_ts(PES_BUFFER *p, unsigned pusi, uint8_t *buf, unsigned len)
{
    int result = 0;

    if (pusi) {

        if (len < 6) {
            BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
            return -1;
        }
        if (buf[0] || buf[1] || buf[2] != 1) {
            BD_DEBUG(DBG_DECODE, "invalid PES header (00 00 01)");
            return -1;
        }

        // Parse PES header
        unsigned pes_pid    = buf[3];
        unsigned pes_length = buf[4] << 8 | buf[5];
        unsigned hdr_len    = 6;

        if (pes_pid != 0xbf) {

            if (len < 9) {
                BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
                return -1;
            }

            unsigned pts_exists = buf[7] & 0x80;
            unsigned dts_exists = buf[7] & 0x40;
            hdr_len += buf[8] + 3;

            if (len < hdr_len) {
                BD_DEBUG(DBG_DECODE, "invalid BDAV TS (PES header not in single TS packet)\n");
                return -1;
            }

            if (pts_exists) {
                p->pts = _parse_timestamp(buf + 9);
            }
            if (dts_exists) {
                p->dts = _parse_timestamp(buf + 14);
            }
        }

        buf += hdr_len;
        len -= hdr_len;

        result = pes_length + 6 - hdr_len;
    }

    // realloc
    if (p->size < p->len + len) {
        uint8_t *tmp;
        p->size *= 2;
        p->size = BD_MAX(p->size, BD_MAX(result, 0x100));
        tmp     = realloc(p->buf, p->size);
        if (!tmp) {
            BD_DEBUG(DBG_DECODE | DBG_CRIT, "out of memory\n");
            p->size = 0;
            return -1;
        }
        p->buf = tmp;
    }

    // append
    memcpy(p->buf + p->len, buf, len);
    p->len += len;

    return result;
}