使用 GStreamer 播放传入的 RTP 流

发布于 2024-08-14 11:46:12 字数 6166 浏览 3 评论 0原文

我正在开发一个 GStreamer 应用程序,并在为传入 RTP 流实现播放器方面遇到了一些困难。我正在尝试围绕 gstrtpbin 元素构建一个管道。我正在尝试使用 gst-launch 结构对管道进行建模:

VIDEO_CAPS="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264"

gst-launch -v udpsrc caps=$VIDEO_CAPS port=4444 \
              ! gstrtpbin .recv_rtp_sink_0 \
              ! rtph264depay ! ffdec_h264 ! xvimagesink

当我启动脚本时,GStreamer 报告这些错误:

Setting pipeline to PAUSED ...
Pipeline is live and does not need PREROLL ...
Setting pipeline to PLAYING ...
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0: ntp-ns-base = 3469468914024449000
New clock: GstSystemClock
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0.GstProxyPad:proxypad0: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_src: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:src: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_src_0_960476599_33.GstProxyPad:proxypad1: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264, payload=(int)33
ERROR: from element /GstPipeline:pipeline0/GstUDPSrc:udpsrc0: Internal data flow error.
Additional debug info:
gstbasesrc.c(2378): gst_base_src_loop (): /GstPipeline:pipeline0/GstUDPSrc:udpsrc0:
streaming task paused, reason not-linked (-1)
Execution ended after 209381685 ns.
Setting pipeline to PAUSED ...
Setting pipeline to READY ...
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_src_0_960476599_33: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:src_33: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:src: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:src_960476599: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_src: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0: caps = NULL
/GstPipeline:pipeline0/GstUDPSrc:udpsrc0.GstPad:src: caps = NULL
Setting pipeline to NULL ...
Freeing pipeline ...

我应该提到它适用于 playbin 和 SDP 文件。例如这个文件:

v=0
o=- 1188340656180883 1 IN IP4 127.0.0.1
s=Session streamed by GStreamer
i=server.sh
t=0 0
a=tool:GStreamer
a=type:broadcast
m=video 4444 RTP/AVP 96
c=IN IP4 127.0.0.1
a=rtpmap:96 H264/90000

可用于像这样播放流:

gst-launch -vvv playbin uri=file://`pwd`/stream.sdp

为了完整性:我正在使用 VLC 发送数据。这是命令:

vlc -I rc /usr/local/movies/sample.mp4 \
    --screen-fps=10 :screen-caching=100 \
    --sout='#transcode{vcodec=h264,venc=x264{bframes=0,keyint=40},vb=512}:\
                   rtp{mux=ts,dst=127.0.0.1,port=4444}'

有人能帮我理解为什么 gst-launch 脚本失败吗?错误“原因未链接”让我认为 gstrtpbin 和 rtph264depay 元素之间的链接已损坏。但我不知道如何解决它。

编辑
按照 RAOF 的建议,我修复了命令中的一些错误。不过,我正在使用 ffdec_h264 和 autovideosink,因为在我的 Windows 系统上,我没有安装 Fluh264dec 和 xvimage 接收器插件:

gst-launch-0.10 udpsrc port=4444 caps="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264" ! .recv_rtp_sink_0 gstrtpbin ! rtpmp2tdepay ! mpegtsdemux ! ffdec_h264 ! autovideosink 

这会导致新的错误:

0:00:00.743000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.744000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.745000000   516   024070A8 ERROR                 ffmpeg .:0:: decode_slice_header error
0:00:00.745000000   516   024070A8 ERROR                 ffmpeg .:0:: no frame!
0:00:00.812000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.813000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existi
...
ERROR: from element /GstPipeline:pipeline0/GstUDPSrc:udpsrc0: Internal data flow
 error.
Additional debug info:
..\Source\gstreamer\libs\gst\base\gstbasesrc.c(2378): gst_base_src_loop (): /Gst
Pipeline:pipeline0/GstUDPSrc:udpsrc0:
streaming task paused, reason not-negotiated (-4)
Execution ended after 4790000000 ns.
Setting pipeline to PAUSED ...
Setting pipeline to READY ...
Setting pipeline to NULL ...
Freeing pipeline ...

我仍在尝试找出如何解决此问题。如果您能提供帮助,请随时提供帮助。

编辑2
我使用SDP解决方案再次进行测试,发现也出现了“不存在的PPS”错误,但视频确实播放了。另一方面,致命的“内部数据流错误”仅在使用自定义管道解决方案时才会显示。 我怀疑“不存在的 PPS”错误是由 x264 编码器引起的。 “内部数据流错误”一定是由我的管道中的错误引起的,或者可能是某些 Windows 插件中的错误引起的。我会做一些进一步的研究...

I'm developing a GStreamer application and struggling bit with implementing a player for incoming RTP streams. I am trying to construct a pipeline around the gstrtpbin element. I'm trying to model the pipeline using a gst-launch construction:

VIDEO_CAPS="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264"

gst-launch -v udpsrc caps=$VIDEO_CAPS port=4444 \
              ! gstrtpbin .recv_rtp_sink_0 \
              ! rtph264depay ! ffdec_h264 ! xvimagesink

When I launch the script GStreamer reports these errors:

Setting pipeline to PAUSED ...
Pipeline is live and does not need PREROLL ...
Setting pipeline to PLAYING ...
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0: ntp-ns-base = 3469468914024449000
New clock: GstSystemClock
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0.GstProxyPad:proxypad0: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_src: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:src: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:sink: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_src_0_960476599_33.GstProxyPad:proxypad1: caps = application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264, payload=(int)33
ERROR: from element /GstPipeline:pipeline0/GstUDPSrc:udpsrc0: Internal data flow error.
Additional debug info:
gstbasesrc.c(2378): gst_base_src_loop (): /GstPipeline:pipeline0/GstUDPSrc:udpsrc0:
streaming task paused, reason not-linked (-1)
Execution ended after 209381685 ns.
Setting pipeline to PAUSED ...
Setting pipeline to READY ...
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_src_0_960476599_33: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:src_33: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpPtDemux:rtpptdemux0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpJitterBuffer:rtpjitterbuffer0.GstPad:src: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:src_960476599: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSsrcDemux:rtpssrcdemux0.GstPad:sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_src: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0/GstRtpSession:rtpsession0.GstPad:recv_rtp_sink: caps = NULL
/GstPipeline:pipeline0/GstRtpBin:rtpbin0.GstGhostPad:recv_rtp_sink_0: caps = NULL
/GstPipeline:pipeline0/GstUDPSrc:udpsrc0.GstPad:src: caps = NULL
Setting pipeline to NULL ...
Freeing pipeline ...

I should mention that it works with a playbin and SDP file. For example this file:

v=0
o=- 1188340656180883 1 IN IP4 127.0.0.1
s=Session streamed by GStreamer
i=server.sh
t=0 0
a=tool:GStreamer
a=type:broadcast
m=video 4444 RTP/AVP 96
c=IN IP4 127.0.0.1
a=rtpmap:96 H264/90000

Can be used to play the stream like this:

gst-launch -vvv playbin uri=file://`pwd`/stream.sdp

For completeness: I am using VLC to send data. This is the command:

vlc -I rc /usr/local/movies/sample.mp4 \
    --screen-fps=10 :screen-caching=100 \
    --sout='#transcode{vcodec=h264,venc=x264{bframes=0,keyint=40},vb=512}:\
                   rtp{mux=ts,dst=127.0.0.1,port=4444}'

Would someone help me understand why the gst-launch script fails? The error "reason not-linked" makes me think that the link between gstrtpbin and the rtph264depay elements is broken. But I don't know how to fix it.

Edit
Following RAOF's suggestions I fixed a few errors in my command. However I am using ffdec_h264 and autovideosink because on my Windows system I don't have the fluh264dec and xvimage sink plugins installed:

gst-launch-0.10 udpsrc port=4444 caps="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264" ! .recv_rtp_sink_0 gstrtpbin ! rtpmp2tdepay ! mpegtsdemux ! ffdec_h264 ! autovideosink 

Which leads to new errors:

0:00:00.743000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.744000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.745000000   516   024070A8 ERROR                 ffmpeg .:0:: decode_slice_header error
0:00:00.745000000   516   024070A8 ERROR                 ffmpeg .:0:: no frame!
0:00:00.812000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existing PPS referenced
0:00:00.813000000   516   024070A8 ERROR                 ffmpeg .:0:: non-existi
...
ERROR: from element /GstPipeline:pipeline0/GstUDPSrc:udpsrc0: Internal data flow
 error.
Additional debug info:
..\Source\gstreamer\libs\gst\base\gstbasesrc.c(2378): gst_base_src_loop (): /Gst
Pipeline:pipeline0/GstUDPSrc:udpsrc0:
streaming task paused, reason not-negotiated (-4)
Execution ended after 4790000000 ns.
Setting pipeline to PAUSED ...
Setting pipeline to READY ...
Setting pipeline to NULL ...
Freeing pipeline ...

I'm still trying to figure out how to fix this. If you can help, then feel free to do so.

Edit2
I tested again using the SDP solution and observed that the "non-existing PPS" errors also occur, but the video does play. On the other hand, the fatal "internal data flow error" only shows when using the custom pipeline solution.
I suspect that the "non-existing PPS" errors are caused by the x264 encoder. The "internal data flow error" must be caused by an error in my pipeline, or perhaps a bug in some Windows plugin. I'll so some further research...

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

陈年往事 2024-08-21 11:46:12

据我所知,你有两个问题:

首先,接收器规范的顺序似乎很重要:而不是 ... ! gstrtpbin .recv_rtp_sink_0! ... 你需要有...! .recv_rtp_sink_0 gstrtpbin ! ...

其次,vlc 正在发送 MPEG2 传输流 - 您在 rtp 流输出描述符中有 mux=ts - 但您正在尝试卸载原始 h264 流。您需要解负载 ts 流,然后将其解复用以获取 h264 流数据。

所以,最后,管道

gst-launch-0.10 -v udpsrc port=4444 \
caps="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264" \
! .recv_rtp_sink_0 gstrtpbin ! rtpmp2tdepay \
! mpegtsdemux ! fluh264dec ! xvimagesink

对我有用,使用 TS 解复用器 (mpegtsdemux) 和 h264 解码器 (fluh264dec)。

As far as I can tell, you've got two problems there:

Firstly, it seems the order of sink specification is important: rather than ... ! gstrtpbin .recv_rtp_sink_0 ! ... you need to have ... ! .recv_rtp_sink_0 gstrtpbin ! ....

Secondly, vlc is sending an MPEG2 transport stream - you've got mux=ts in the rtp streaming output descriptor - but you're trying to depayload a raw h264 stream. You need to depayload the ts stream, and then demux it to get at the h264 stream data.

So, finally, the pipeline

gst-launch-0.10 -v udpsrc port=4444 \
caps="application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264" \
! .recv_rtp_sink_0 gstrtpbin ! rtpmp2tdepay \
! mpegtsdemux ! fluh264dec ! xvimagesink

works for me, using the TS demuxer (mpegtsdemux) and h264 decoder (fluh264dec).

愚人国度 2024-08-21 11:46:12
gst-launch-0.10 -vvvv rtspsrc location=rtsp://192.168.250.100:554 latency=100 ! \
application/x-rtp,media="video",payload=99,clock-rate=90000,encoding-name="H264"  ! \
rtph264depay !  ffdec_h264 ! ffmpegcolorspace ! xvimagesink

这对我来说适用于“Grandtec Electronic MegaPixel WIFI CAM”

gst-launch-0.10 -vvvv rtspsrc location=rtsp://192.168.250.100:554 latency=100 ! \
application/x-rtp,media="video",payload=99,clock-rate=90000,encoding-name="H264"  ! \
rtph264depay !  ffdec_h264 ! ffmpegcolorspace ! xvimagesink

this worked for me with a "Grandtec Electronic MegaPixel WIFI CAM"

じ违心 2024-08-21 11:46:12

你也可以尝试一下这个。

gst-launch-0.10 -v rtspsrc location="rtsp://10.107.2.217/StreamingSetting?version=1.0&action=getRTSPStream&ChannelID=1&ChannelName=Channel1"
用户 id=admin 用户密码=admin123
caps =“应用程序/ x-rtp,媒体=(字符串)视频,时钟速率=(int)90000,编码名称=(字符串)H264,有效负载=(int)96,ssrc =(uint)237526004,时钟-基=(uint)1584170994,seqnum-base=(uint)42626”端口=554! rtph264depay队列延迟=0! h264解析!解码bin2!队列泄漏=1! autovideosink

当您在网络上的流媒体安全时,它也可以工作,并且它可以在

rtsp://10.107.2.217

RTSP 端口:554

< code>视频编解码器:H.264

希望对你们有帮助。

You can also try this one.

gst-launch-0.10 -v rtspsrc location="rtsp://10.107.2.217/StreamingSetting?version=1.0&action=getRTSPStream&ChannelID=1&ChannelName=Channel1"
user-id=admin user-pw=admin123
caps=" application/x-rtp,media=(string)video,clock-rate=(int)90000,encoding-name=(string)H264,payload=(int)96,ssrc=(uint)237526004,clock-base=(uint)1584170994,seqnum-base=(uint)42626" port=554 ! rtph264depay queue-delay=0 ! h264parse ! decodebin2 ! queue leaky=1 ! autovideosink

Its also work when your streaming on Network is secure,and its works on

rtsp://10.107.2.217

RTSP Port : 554

Video Codec : H.264

Hope, its helpful to you guys.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文