整理ffmpeg 细节分析;

来源:互联网 发布:mac word空白页 编辑:程序博客网 时间:2024/05/17 04:09
int ffio_fdopen(AVIOContext **s, URLContext *h){    uint8_t *buffer;    int buffer_size, max_packet_size;    max_packet_size = h->max_packet_size;    if (max_packet_size) {        buffer_size = max_packet_size; /* no need to bufferize more than one packet */    } else {        buffer_size = IO_BUFFER_SIZE;    }    buffer = av_malloc(buffer_size);    if (!buffer)        return AVERROR(ENOMEM);    *s = avio_alloc_context(buffer, buffer_size, h->flags & AVIO_FLAG_WRITE, h,                            (void*)ffurl_read, (void*)ffurl_write, (void*)ffurl_seek);    if (!*s) {        av_free(buffer);        return AVERROR(ENOMEM);    }    (*s)->direct = h->flags & AVIO_FLAG_DIRECT;    (*s)->seekable = h->is_streamed ? 0 : AVIO_SEEKABLE_NORMAL;    (*s)->max_packet_size = max_packet_size;    if(h->prot) {        (*s)->read_pause = (int (*)(void *, int))h->prot->url_read_pause;        (*s)->read_seek  = (int64_t (*)(void *, int, int64_t, int))h->prot->url_read_seek;    }    (*s)->av_class = &ffio_url_class;    return 0;}
AVIOContext *avio_alloc_context(                  unsigned char *buffer,                  int buffer_size,                  int write_flag,                  void *opaque,                  int (*read_packet)(void *opaque, uint8_t *buf, int buf_size),                  int (*write_packet)(void *opaque, uint8_t *buf, int buf_size),                  int64_t (*seek)(void *opaque, int64_t offset, int whence)){    AVIOContext *s = av_mallocz(sizeof(AVIOContext));    if (!s)        return NULL;    ffio_init_context(s, buffer, buffer_size, write_flag, opaque,                  read_packet, write_packet, seek);    return s;}


int ffio_init_context(AVIOContext *s,                  unsigned char *buffer,                  int buffer_size,                  int write_flag,                  void *opaque,                  int (*read_packet)(void *opaque, uint8_t *buf, int buf_size),                  int (*write_packet)(void *opaque, uint8_t *buf, int buf_size),                  int64_t (*seek)(void *opaque, int64_t offset, int whence)){  <strong><span style="color:#3366ff;">  s->buffer      = buffer;    s->orig_buffer_size =    s->buffer_size = buffer_size;    s->buf_ptr     = buffer;    s->opaque      = opaque;</span></strong>    s->direct      = 0;    url_resetbuf(s, write_flag ? AVIO_FLAG_WRITE : AVIO_FLAG_READ);    s->write_packet    = write_packet;    s->read_packet     = read_packet;    s->seek            = seek;   <span style="color:#3366ff;"><strong> s->pos             = 0;</strong></span>    s->must_flush      = 0;    s->eof_reached     = 0;    s->error           = 0;    s->seekable        = seek ? AVIO_SEEKABLE_NORMAL : 0;    s->max_packet_size = 0;    s->update_checksum = NULL;    if (!read_packet && !write_flag) {        s->pos     = buffer_size;        s->buf_end = s->buffer + buffer_size;    }    s->read_pause = NULL;    s->read_seek  = NULL;    return 0;}


int64_t avio_seek(AVIOContext *s, int64_t offset, int whence){    int64_t offset1;    int64_t pos;    int force = whence & AVSEEK_FORCE;    int buffer_size;    whence &= ~AVSEEK_FORCE;    if(!s)        return AVERROR(EINVAL);    buffer_size = s->buf_end - s->buffer;    pos = s->pos - (s->write_flag ? 0 : buffer_size);    if (whence != SEEK_CUR && whence != SEEK_SET)        return AVERROR(EINVAL);    if (whence == SEEK_CUR) {        offset1 = pos + (s->buf_ptr - s->buffer);        if (offset == 0)            return offset1;        offset += offset1;    }    offset1 = offset - pos;    if (!s->must_flush && (!s->direct || !s->seek) &&        offset1 >= 0 && offset1 <= buffer_size) {        /* can do the seek inside the buffer */        s->buf_ptr = s->buffer + offset1;    } else if ((!s->seekable ||               offset1 <= s->buf_end + SHORT_SEEK_THRESHOLD - s->buffer) &&               !s->write_flag && offset1 >= 0 &&               (!s->direct || !s->seek) &&              (whence != SEEK_END || force)) {        while(s->pos < offset && !s->eof_reached)            fill_buffer(s);        if (s->eof_reached)            return AVERROR_EOF;        s->buf_ptr = s->buf_end + offset - s->pos;    } else if(!s->write_flag && offset1 < 0 && -offset1 < buffer_size>>1 && s->seek && offset > 0) {        int64_t res;        pos -= FFMIN(buffer_size>>1, pos);        if ((res = s->seek(s->opaque, pos, SEEK_SET)) < 0)            return res;        s->buf_end =        s->buf_ptr = s->buffer;        s->pos = pos;        s->eof_reached = 0;        fill_buffer(s);        return avio_seek(s, offset, SEEK_SET | force);    } else {        int64_t res;        if (s->write_flag) {            flush_buffer(s);            s->must_flush = 1;        }        if (!s->seek)            return AVERROR(EPIPE);        if ((res = s->seek(s->opaque, offset, SEEK_SET)) < 0)            return res;        s->seek_count ++;        if (!s->write_flag)            s->buf_end = s->buffer;        s->buf_ptr = s->buffer;        s->pos = offset;    }    s->eof_reached = 0;    return offset;}


0 0
原创粉丝点击