Skip to content
项目
群组
代码片段
帮助
当前项目
正在载入...
登录 / 注册
切换导航面板
Z
ZLMediaKit
概览
Overview
Details
Activity
Cycle Analytics
版本库
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
问题
0
Issues
0
列表
Board
标记
里程碑
合并请求
0
Merge Requests
0
CI / CD
CI / CD
流水线
作业
日程表
图表
维基
Wiki
代码片段
Snippets
成员
Collapse sidebar
Close sidebar
活动
图像
聊天
创建新问题
作业
提交
Issue Boards
Open sidebar
张翔宇
ZLMediaKit
Commits
26d458d0
Unverified
Commit
26d458d0
authored
Jan 09, 2022
by
alexliyu7352
Committed by
GitHub
Jan 09, 2022
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
增加ffmpeg拉流自动重启时间, 避免长时间拉流导致的声音不同步现象 (#1346)
parent
819599ac
显示空白字符变更
内嵌
并排
正在显示
2 个修改的文件
包含
24 行增加
和
2 行删除
+24
-2
conf/config.ini
+2
-0
server/FFmpegSource.cpp
+22
-2
没有找到文件。
conf/config.ini
查看文件 @
26d458d0
...
...
@@ -26,6 +26,8 @@ snap=%s -i %s -y -f mjpeg -t 0.001 %s
#FFmpeg日志的路径,如果置空则不生成FFmpeg日志
#可以为相对(相对于本可执行程序目录)或绝对路径
log
=
./ffmpeg/ffmpeg.log
# 自动重启的时间(秒), 默认为0, 也就是不自动重启. 主要是为了避免长时间ffmpeg拉流导致的不同步现象
restart_sec
=
0
[general]
#是否启用虚拟主机
...
...
server/FFmpegSource.cpp
查看文件 @
26d458d0
...
...
@@ -22,6 +22,7 @@ const string kBin = FFmpeg_FIELD"bin";
const
string
kCmd
=
FFmpeg_FIELD
"cmd"
;
const
string
kLog
=
FFmpeg_FIELD
"log"
;
const
string
kSnap
=
FFmpeg_FIELD
"snap"
;
const
string
kRestartSec
=
FFmpeg_FIELD
"restart_sec"
;
onceToken
token
([]()
{
#ifdef _WIN32
...
...
@@ -35,6 +36,7 @@ onceToken token([]() {
mINI
::
Instance
()[
kLog
]
=
"./ffmpeg/ffmpeg.log"
;
mINI
::
Instance
()[
kCmd
]
=
"%s -re -i %s -c:a aac -strict -2 -ar 44100 -ab 48k -c:v libx264 -f flv %s"
;
mINI
::
Instance
()[
kSnap
]
=
"%s -i %s -y -f mjpeg -t 0.001 %s"
;
mINI
::
Instance
()[
kRestartSec
]
=
0
;
});
}
...
...
@@ -202,17 +204,27 @@ void FFmpegSource::findAsync(int maxWaitMS, const function<void(const MediaSourc
*/
void
FFmpegSource
::
startTimer
(
int
timeout_ms
)
{
weak_ptr
<
FFmpegSource
>
weakSelf
=
shared_from_this
();
GET_CONFIG
(
uint64_t
,
ffmpeg_restart_sec
,
FFmpeg
::
kRestartSec
);
_timer
=
std
::
make_shared
<
Timer
>
(
1.0
f
,
[
weakSelf
,
timeout_ms
]()
{
auto
strongSelf
=
weakSelf
.
lock
();
if
(
!
strongSelf
)
{
//自身已经销毁
return
false
;
}
bool
needRestart
=
ffmpeg_restart_sec
>
0
&&
strongSelf
->
_replay_ticker
.
elapsedTime
()
>
ffmpeg_restart_sec
*
1000
;
if
(
is_local_ip
(
strongSelf
->
_media_info
.
_host
))
{
//推流给自己的,我们通过检查是否已经注册来判断FFmpeg是否工作正常
strongSelf
->
findAsync
(
0
,
[
&
](
const
MediaSource
::
Ptr
&
src
)
{
//同步查找流
if
(
!
src
)
{
if
(
!
src
||
needRestart
)
{
if
(
needRestart
){
strongSelf
->
_replay_ticker
.
resetTime
();
if
(
strongSelf
->
_process
.
wait
(
false
)){
//FFmpeg进程还在运行,超时就关闭它
strongSelf
->
_process
.
kill
(
2000
);
}
InfoL
<<
"FFmpeg即将重启, 将会继续拉流 "
<<
strongSelf
->
_src_url
;
}
//流不在线,重新拉流, 这里原先是10秒超时,实际发现10秒不够,改成20秒了
if
(
strongSelf
->
_replay_ticker
.
elapsedTime
()
>
20
*
1000
){
//上次重试时间超过10秒,那么再重试FFmpeg拉流
...
...
@@ -223,7 +235,15 @@ void FFmpegSource::startTimer(int timeout_ms) {
});
}
else
{
//推流给其他服务器的,我们通过判断FFmpeg进程是否在线,如果FFmpeg推流中断,那么它应该会自动退出
if
(
!
strongSelf
->
_process
.
wait
(
false
))
{
if
(
!
strongSelf
->
_process
.
wait
(
false
)
||
needRestart
)
{
if
(
needRestart
){
strongSelf
->
_replay_ticker
.
resetTime
();
if
(
strongSelf
->
_process
.
wait
(
false
)){
//FFmpeg进程还在运行,超时就关闭它
strongSelf
->
_process
.
kill
(
2000
);
}
InfoL
<<
"FFmpeg即将重启, 将会继续拉流 "
<<
strongSelf
->
_src_url
;
}
//ffmpeg不在线,重新拉流
strongSelf
->
play
(
strongSelf
->
_ffmpeg_cmd_key
,
strongSelf
->
_src_url
,
strongSelf
->
_dst_url
,
timeout_ms
,
[
weakSelf
](
const
SockException
&
ex
)
{
if
(
!
ex
){
...
...
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论