問題描述
在3年前我當時基於EasyDarwin為用戶開發了一款RTSP拉模式轉發的程序,也發布了一篇博客《用Darwin開發RTSP級聯服務器(拉模式轉發)》,當時考慮的很簡單,只要將RTSP源的sdp和RTP流拉取過來,不做任何變動立即轉發即可實現拉模式轉發了,而且CPU占用也會非常低,基本上就是跑一個數傳,其效果也正如預期的那樣,一個EasyDarwin拉模式轉發的服務器,可以帶動很多個IPC的流分發,再次以RTSP+RTP協議的形式分發出去;
但是,近期有我們的一位EasyDarwin的用戶反饋道:轉發大部分的IPC都是沒有問題的,但是轉發海康的某幾款設備的時候,總是會出現花屏,而且是必現的!?!
問題排查
再次重新操刀負責此事,我決定拆分拉模式轉發的流程,做排除法進行分析:
- 第一步是IPC到EasyDarwin的數據是否完整;
- 第二步是EasyDarwin的RTSPClient的數據是否完整;
- 第三步是RTSPClient是否將有效的數據丟掉了;
我們先從第三部分開始,直接通過EasyRTSPClient從EasyDarwin獲取轉發的RTSP流,存儲到文件,其試用方法可以參考博客《[工具]利用EasyRTSPClient工具檢查攝像機RTSP流不能播放原因以及排查音視頻數據無法播放問題》,我發現存儲下來的H.264文件確實就是花屏的;
我們再從第一部分開始排查,我們選擇從服務器端打印RTP序列號的方式來進行的,因為比較簡單,當發現上一個RTP Number跟下一個RTP Number不連續的時候,我們就打印日志,結果發現,始終都很連續,非常穩定!排除此部分的問題!
再排查第二個部分就是EasyDarwin到RTSPClient的RTP流是否完整了,這一部分我們采用了wireshark抓包的方式,查看RTP Sequence是否是連續的,結果發現也是RTP非常連續的,沒有遺漏,也就是說,數據也確實都完整地轉發到了客戶端!排除此部分的問題!
那么問題就出在了RTSPClient階段,是如何將收到的數據,卻給丟掉了!
通過反復打印EasyRTSPClient中的日志,我們發現了一段代碼如圖:
海康的RTP流在RTP中設置的Padding為True,也就是尾部有附加數據,而我們轉發的時候卻只轉發的RTP部分,附帶的部分沒有進行轉發,結果就導致RTSPClient將這部分數據認為是不完整的數據,直接丟掉了,那么就導致了花屏的產生!
解決方案
我們在EasyDarwin中人為地將Padding字段設置為0就可以了,這樣附加數據也不用轉發了,只轉發視頻部分:
關於EasyRTSPClient
EasyRTSPClient是一套非常穩定、易用、支持重連的RTSPClient工具,SDK形式提供,接口調用非常簡單,再也不用像調用live555那樣處理整個RTSP OPTIONS/DESCRIBE/SETUP/PLAY的復雜流程,擔心內存釋放的問題了,全平台支持(包括Windows/Linux 32&64,ARM各平台,Android,iOS),支持RTP Over TCP/UDP,支持斷線重連,連續維護與迭代超過5年,能夠接入市面上99%以上的IPC,調用簡單且成熟穩定!
獲取更多信息
Copyright © EasyDarwin.org 2012-2017