记录<一次点播的无法seek的问题跟踪>的bug的完整排查思路
创始人
2024-01-22 16:45:21

文章目录

  • 一. 问题背景
  • 二. 问题跟踪
    • 1. 首先怀疑的是解析pts出错了?
    • 2. ffmpeg解析的pts是多少呢?
  • 参考文档:

一. 问题背景

长达26个小时的KPL直播.Seek到中间偏后的时候会卡死不动.但是前面1-2个小时可以Seek.

二. 问题跟踪

大家有兴趣可以先看看Mac上终端调试FFmpeg任意版本源码的最佳实践

这个问题刚开始跟踪的时候,首先想到的是是不是视频源的问题.是用vlc和flv去尝试.奇怪的是vlc也不支持.但是ffmpeg支持.
此时我们来跟踪问题,发现到了JitterBuffer层之后无法往解码层送数据

// 正在 seek
if (packet->pts - packet->start_pts < seek_to_timestamp_) {
LOG_DEBUG("OnAudioPacketDemuxed, drop audio packet : %lld, start : %lld, seek time : %lld", packet->pts, packet->start_pts, seek_to_timestamp_);
return true;
}

两者相减为负数,我们要去seek的pts不对.到底为什么不对呢?

1. 首先怀疑的是解析pts出错了?

因为此流地址是

http://xxx/playlist_eof.m3u8

我们下载后看里面ts文件可知

流的第一个ts分片:
http://xxx_1.ts?start=0&end=2475019&type=mpegts
pts=8171962796中间的某一个:
http://xxx_525.ts?start=24645672&end=26180503&type=mpegts
pts=4399514004最后一个:
http://xxx_1302.ts?start=24598860&end=25023363&type=mpegts
pts=6771267804

现在通过ffmpeg工具查看ts分片后得知:

ffplay http://xxx_1.ts\?start\=0\&end\=2475019\&type\=mpegts

可正常播放.
然后用命令行看一下pts.

ffprobe -show_packets http://xxx_1.ts\?start\=0\&end\=2475019\&type\=mpegts或者ffprobe -of xml -show_streams http://xxx_1.ts\?start\=0\&end\=2475019\&type\=mpegts

可以看到start_pts是8171962796


看起来也没有pts也和上面和代码解复用之后拿到的pts是一样的.那么就是说解析到的pts是对的.那么为什么会出现pts先逐渐增大,然后变小后再增大的问题呢?

2. ffmpeg解析的pts是多少呢?

起始值一样.但是我seek拖到中途之后pts竞然没有变小.通过

static int64_t wrap_timestamp(const AVStream *st, int64_t timestamp)
{
if (st->pts_wrap_behavior != AV_PTS_WRAP_IGNORE &&
st->pts_wrap_reference != AV_NOPTS_VALUE && timestamp != AV_NOPTS_VALUE) {
if (st->pts_wrap_behavior == AV_PTS_WRAP_ADD_OFFSET &&
timestamp < st->pts_wrap_reference)
return timestamp + (1ULL << st->pts_wrap_bits);
else if (st->pts_wrap_behavior == AV_PTS_WRAP_SUB_OFFSET &&
timestamp >= st->pts_wrap_reference)
return timestamp - (1ULL << st->pts_wrap_bits);
}
return timestamp;
}

打断点可知,这里对pts如果小区

对时间戳循环到头的处理:
ts流中的三个时间戳,pts(33bit),dts(33bit),pcr(42bit)
当时间戳增加到语法无法容纳时,产生时间戳循环,时间线开始变小,循环点计算方式是:将要设置的值减去时间戳最大值,将差值写入语法结构。
编码器设置时钟,以及解码器自己的系统时钟在达到最大值后,都根据此方式计算,不会产生时钟的不连续。
现在加上这一段即可

//ts流中的时间戳,pts(33bit),dts(33bit)
//当时间戳增加到语法无法容纳时,产生时间戳循环,时间线开始变小,循环点计算方式是:将要设置的值减去时间戳最大值,将差值写入语法结构。
int64_t TsParser::getVideoRevisedPts(int64_t pts){
if(video_packet_){
int64_t startPts_Real = video_start_pts_*kTimeBase; //转换成ms之前的从流中获取的时间戳
if(pts < startPts_Real){
pts += kMaxPtsFrame;
}
}
return pts;
}int64_t TsParser::getAudioRevisedPts(int64_t pts){
if(audio_packet_){
int64_t startPts_Real = audio_start_pts_*kTimeBase; //转换成ms之前的从流中获取的时间戳
if(pts < startPts_Real){
pts += kMaxPtsFrame;
}
}
return pts;
}

关于更多的格式的具体细节可以参考30分钟学会FLV和HLS

参考文档:

1.总结TS中的pcr、dts、pts问题

相关内容

热门资讯

猫咪吃了塑料袋怎么办 猫咪误食... 你知道吗?塑料袋放久了会长猫哦!要说猫咪对塑料袋的喜爱程度完完全全可以媲美纸箱家里只要一有塑料袋的响...
埃菲尔铁塔在哪 中国仿建埃菲尔... 2019年4月26日,广西南宁市,街头惊现一座巨型山寨版埃菲尔铁塔,高约20米,白色塔身,造型逼真,...
ps局部放大 放大某个部位的图... 软件类学习建议:边看边练习,可以先收藏后学习。一、使用Ctrl快捷键放大:Ctrl + +缩小:Ct...
苗族的传统节日 贵州苗族节日有... 【岜沙苗族芦笙节】岜沙,苗语叫“分送”,距从江县城7.5公里,是世界上最崇拜树木并以树为神的枪手部落...
北京的名胜古迹 北京最著名的景... 北京从元代开始,逐渐走上帝国首都的道路,先是成为大辽朝五大首都之一的南京城,随着金灭辽,金代从海陵王...
应用未安装解决办法 平板应用未... ---IT小技术,每天Get一个小技能!一、前言描述苹果IPad2居然不能安装怎么办?与此IPad不...
脚上的穴位图 脚面经络图对应的... 人体穴位作用图解大全更清晰直观的标注了各个人体穴位的作用,包括头部穴位图、胸部穴位图、背部穴位图、胳...
长白山自助游攻略 吉林长白山游... 昨天介绍了西坡的景点详细请看链接:一个人的旅行,据说能看到长白山天池全凭运气,您的运气如何?今日介绍...
世界上最漂亮的人 世界上最漂亮... 此前在某网上,选出了全球265万颜值姣好的女性。从这些数量庞大的女性群体中,人们投票选出了心目中最美...
埃菲尔铁塔在哪 中国仿建埃菲尔... 2019年4月26日,广西南宁市,街头惊现一座巨型山寨版埃菲尔铁塔,高约20米,白色塔身,造型逼真,...
苗族的传统节日 贵州苗族节日有... 【岜沙苗族芦笙节】岜沙,苗语叫“分送”,距从江县城7.5公里,是世界上最崇拜树木并以树为神的枪手部落...
衡水一中在哪 兰州分校衡水一中 新甘肃客户端兰州6月6日讯(新甘肃·甘肃日报记者 曹立萍)今天上午,由中铁二十局市政公司承建的河北衡...
北京的名胜古迹 北京最著名的景... 北京从元代开始,逐渐走上帝国首都的道路,先是成为大辽朝五大首都之一的南京城,随着金灭辽,金代从海陵王...