ffmpeg处理hikvision平台PS流
既然是PS流,当然要仔细研究一下iso13818-1规范,本来想自己写PS流的解析代码,但考虑到已经有众多的PS流解析开源代码,咱就不必自己再造个汽车轮子了,趁着自己熟悉ffmpeg,还是用ffmpeg去解析吧,但没承想掉进一个大坑。。。
用ffmpeg的好处是,可以通过avio的方式,将内存中的ps流送入ffmpeg进行自动化的处理,通过探测流格式,寻找流,自动确定对应的流格式和音视频编码,自动拼帧,最终demux得到音频帧和视频帧。这样,不管是复合流(PS流或TS流),还是裸流(H.264或H.265等),都能用同一种机制进行处理,代码简洁。但坏处就是,必须对ffmpeg非常熟悉才行,如果稍有不慎掉坑了,必须要自己翻出来。。。
不幸的是,我也掉坑了。程序开发完毕,信心满满的进行测试,发现取到的PS流分离出H.265视频帧并转发到视频会议,视频会议中的IPC分屏小几率偶尔会闪一下屏,客户能不能忍咱不知道,但作为处女座人士,不能忍,遂一步步的排查原因。
首先怀疑是不是视频会议解码H.265解错了?毕竟视频会议的H.265 codec部分也是我刚加上的,虽然也通过了测试,但毕竟心里没有底气。于是就抓包分析,不幸的是又卡在H.265上,tcpdump抓包如果是H.264码流,大把的分析工具可以分离出码流,如果是H.265的抓包,一时没有找到合适的,毕竟H.265跟H.264的RTP打包规则有些差别,不通用。一怒之下,自己写了一个简单的分离程序,分离出了H.265码流,然后使用播放工具播放,发现果然也是有闪屏现象,于是首先排除了视频会议的问题。
其次,是不是RTP打包H.265时搞错了?于是在RTP打包发送之前将H.265码流录制下来,使用播放工具播放,发现竟然也有闪屏现象。晕倒,竟然是ffmpeg分离出的H.265视频帧就有问题了!是hikvision的PS流有问题,还是ffmpeg分离265视频帧有问题?面对业界内的两个大牌,我无语了。只好将hikvision SDK接口回调中的PS流录制下来,使用ffplay播放,也有闪屏现象,再改用potplayer播放,神奇了,potplayer如丝滑般流畅。于是,焦点集中在了ffmpeg上。
从输入PS流到取到H265视频帧,ffmpeg其实经历了2步:分析PS包和使用parser分析H265,哪一步有问题呢?
决定先从PS包分析查起。用winhex打开录制的PS文件,定位到闪屏时程序日志记录的position:
00 00 01 BA 4D 0C AD BF 84 01 00 00 03 FE FF FF
00 00 01 BF 00 00 01 E0 13 FA 8C 80 07 23 43 2B
00 00 01 BA是PS头,之后有10个固定的字节,其中第十个字节的后3位是stuffing填充长度,在本例中是FE,FE&7等于6,则其后的6个字节是stuffing填充字节,咨询hikvision,说这stuffing他们一般用来填充帧序号,好吧,不管是什么都可以略过。但是等等,这stuffing字节怎么恰好有00 00 01 BF?凭着对H264 H265以及PS的了解,对00 00 01还是敏感的,这个熟悉的起始码出现的实在太不是时候了,难不成ffmpeg把这个stuffing里面的字节认成了PS里面的PRIVATE_STREAM_2,从而造成错误?于是赶紧查看ffmpeg里面的PS解析代码。
ffmpeg中的PS解析在mpeg.c文件中的mpegps_read_packet函数中,此函数先解析PS头,然后根据不同的pes取出不同的媒体流。既然是在BA头中的stuffing中发现的00 00 01起始头,肯定要查看解析PS头的函数,于是继续定位到mpeg.c的mpegps_read_pes_header函数,果然看出了端倪!
if (startcode == PACK_START_CODE){
goto redo;
}
mpegps_read_pes_header查找到00 00 01 BA后,没跳过PS头,而是直接goto redo去找下一个00 00 01起始码,而上述PS头的stuffing填充中恰好有00 00 01 BF,于是ffmpeg便搜索到了一个PRIVATE_STREAM_2!想不到大名鼎鼎的ffmpeg竟然也出了一个如此低级的错误!
定位出原因就很容易修改ffmpeg代码了,跳过9字节的固定头,取出10字节中的stuffing长度,再跳过stuffing长度的填充数,然后goto redo就可以了。重新编译ffmpeg,测试程序,果然OK了!
if (startcode == PACK_START_CODE){
avio_skip(s->pb,9);
avio_skip(s->pb,avio_r8(s->pb)&0x7);
goto redo;
ffmpeg处理hikvision平台PS流相关推荐
- ffmpeg解码ps流部分代码以及PS播放器demo
之前的设备研发算是告一段落了,最近一直在忙视频监控平台的架构以及实现,想把自己的设备接到自己的平台里,设备上的码流是ps流,要在平台里解码ps流->解码成h264->yuv->rgb ...
- 使用ffmpeg来探测GB28181的ps流
GB28181 GB28181 是我国内的标准,现在到2016修订后比较成熟,有很多可取之处,当然,依然是建立在sip协议之上,比起rtmp协议来说,他的优点是复用了rtp协议和sdp协议,这一点很优 ...
- ffmpeg添加mpeg ps流的pcm的解码支持
ffmpeg原本不支持mpeg ps流,原因有两个.首先在编码时,ffmpeg没有在流中写入psm头:其次,在解码时,只在读文件头的时候判断了流的类型,而ps流中,流类型是在psm头中的,这样ffmp ...
- 海康摄像头PS流格式解析(RTP/PS/H264)
海康威视视频录像以PS格式打包,解析的过程按照PS包-->system header--->program stream map--->音视频PES包一路下来,海康在包中自定义了一些 ...
- RTP协议全解(H264码流和PS流)
1 视频编码的原理 1.1 一个图像或者一个视频序列进行压缩,产生码流. 对图像的处理即是:帧内预测编码 其预测值P,是由已编码的图像做参考,经运动补偿得到的.预测图像P和当前帧Fn相减,得到两图像的 ...
- ps流 转发_一种国标PS流转RTMP直播流的实时转换方法与流程
本发明属于视频技术领域,具体涉及一种国标ps流转rtmp直播流的实时转换方法. 背景技术: ps流全称是节目流(programstream),将一个节目的多个组成部分按照它们之间的互相关系进行组织并加 ...
- javaCV简单解析gb28181的rtp ps流,并推流到rtmp服务
本文转自javacv社区三群管理员"赶在时间前面":过去的过去了的博客,感谢大佬倾情贡献,支持javacv社区发展和壮大. 国标gb28181全系列都可以参考过去的过去了的博客,再 ...
- gb28181简单解包rtp ps流,推出rtmp(java版基于springboot):六、解包rtp ps流,推出rtmp
解析流程参考 https://blog.csdn.net/chen495810242/article/details/39207305 代码基于github上的修改 https://github.co ...
- RTP载荷PS流全面分析
1.PS流封包格式 视频关键帧的封装: RTP|PS header|PS system header|PS system Map|PES header|H264 data 视频非关键帧的封装:R ...
- 最简单的GB28181视频PS流播放器。
一 从PS流中提取h264和aac. 移步:https://blog.csdn.net/qq_39805297/article/details/107083322 二 基于ffmpeg解码h264获取 ...
最新文章
- python语言包含的错误,Python语言程序中包含的错误,一般分为三种,以下____________不是其中的一种...
- python gevent缺点_python的flask框架结合gevent性能反而大幅度下降?
- 天骄2 mysql错误_凤舞天骄一键版和钟隐3合1版的大多数问题解决方案
- CAP 理论、BASE 理论、FLP 理论
- python开发总结
- UnicodeDecodeError: 'ascii' codec can't decode byte 0xf6 in position 0: ordinal not in range(128)
- Python安全攻防-从入门到入狱
- 购买计算机键盘,键盘安装步骤是怎样的 怎样选购电脑键盘
- 打印101-150之间的质数
- java openxml word_OpenXml读取word内容的实例
- 集合差集操作:a - b 的含义为在集合a中,但不在b中的元素集合。
- 剑指offer 面试题46 python版+解析:把数字翻译成字符串
- 【U8+】修改或删除凭证提示此分录两清
- 谷歌地图 图片保存_Google如何在地图上跟踪并保存您的一举一动
- Linux 中的内存使用率计算方式
- 关于互联网用户的隐私保护
- 1639_perror的函数功能以及简单测试
- ubuntu windows 分别安装openslide
- python助教酱酱是谁_papi酱个人资料
- 读书感受 之 《AI·未来》
热门文章
- Android界面布局基本属性
- Silverlight-Cailburn应用框架
- pytorch不加载fc_Pytorch自己加载单通道图片用作数据集训练的实例
- python皮卡丘编程代码_Python高级编程-(Part 6 部署代码)
- 网络编程 - 实现文件传送
- cocos2d-x自制工具07:打印cocos2d-x的节点树
- mysql 在update中实现子查询的方式
- 二分图最大权匹配:Kuhn-Munkres算法
- 李洪强iOS开发之OC[011] - 有参方法的声明实现以及调用练习
- PHP网站安装程序制作的原理、步骤、注意事项和示例代码