ffmpeg 源代码简单分析 : av_read_frame()(二)

2014-11-23 23:55:22 · 作者: · 浏览: 15
NULL;
st->cur_pkt.side_data_elems = 0;
st->cur_pkt.side_data = NULL;
compute_pkt_fields(s, st, NULL, pkt);
s->cur_st = NULL;
if ((s->iformat->flags & AVFMT_GENERIC_INDEX) &&
(pkt->flags & AV_PKT_FLAG_KEY) && pkt->dts != AV_NOPTS_VALUE) {
ff_reduce_index(s, st->index);
av_add_index_entry(st, pkt->pos, pkt->dts, 0, 0, AVINDEX_KEYFRAME);
}
break;
} //需要解析
else if (st->cur_len > 0 && st->discard < AVDISCARD_ALL) {
//解析
len = av_parser_parse2(st->parser, st->codec, &pkt->data, &pkt->size,
st->cur_ptr, st->cur_len,
st->cur_pkt.pts, st->cur_pkt.dts,
st->cur_pkt.pos);
st->cur_pkt.pts = AV_NOPTS_VALUE;
st->cur_pkt.dts = AV_NOPTS_VALUE;
/* increment read pointer */
st->cur_ptr += len;
st->cur_len -= len;
/* return packet if any */
if (pkt->size) {
got_packet:
pkt->duration = 0;
pkt->stream_index = st->index;
pkt->pts = st->parser->pts;
pkt->dts = st->parser->dts;
pkt->pos = st->parser->pos;
if(pkt->data == st->cur_pkt.data && pkt->size == st->cur_pkt.size){
s->cur_st = NULL;
pkt->destruct= st->cur_pkt.destruct;
st->cur_pkt.destruct= NULL;
st->cur_pkt.data = NULL;
assert(st->cur_len == 0);
}else{
pkt->destruct = NULL;
}
compute_pkt_fields(s, st, st->parser, pkt);
if((s->iformat->flags & AVFMT_GENERIC_INDEX) && pkt->flags & AV_PKT_FLAG_KEY){
int64_t pos= (st->parser->flags & PARSER_FLAG_COMPLETE_FRAMES) pkt->pos : st->parser->frame_offset;
ff_reduce_index(s, st->index);
av_add_index_entry(st, pos, pkt->dts,
0, 0, AVINDEX_KEYFRAME);
}
break;
}
} else {
/* free packet */
av_free_packet(&st->cur_pkt);
s->cur_st = NULL;
}
} else {
AVPacket cur_pkt;
/* read next packet */
//读取AVPacket,老版本里只有av_read_packet,现在被封装了
ret = av_read_packet(s, &cur_pkt);
if (ret < 0) {
if (ret == AVERROR(EAGAIN))
return ret;
/* return the last frames, if any */
for(i = 0; i < s->nb_streams; i++) {
st = s->streams[i];
if (st->parser && st->need_parsing) {
av_parser_parse2(st->parser, st->codec,
&pkt->data, &pkt->size,
NULL, 0,
AV_NOPTS_VALUE, AV_NOPTS_VALUE,
AV_NOPTS_VALUE);
if (pkt->size)
goto got_packet;
}
}
/* no more packets: really terminate parsing */
return ret;
}
st = s->streams[cur_pkt.stream_index];
st->cur_pkt= cur_pkt;
if(st->cur_pkt