gstreamer代理rtspsrc到tcpserver

时间:2017-06-20 09:55:11

标签: c gstreamer rtsp

我需要创建从rtspsrc到tcpserversink的代理。这一行是工作

gst-launch-0.10 rtspsrc location=rtsp://192.168.111.203:8554/video ! capsfilter caps='application/x-rtp,payload=26' ! rtpjpegdepay ! queue ! multipartmux ! tcpserversink port=5555

但是这段代码不起作用

void Video_Initialise_RTSP (const char* pAddress, int Port){
gVideoInit = 0;
gVideoStream = 0;
GError *error = NULL;
/* Initialize Gstreamer */
gst_init (0, NULL);

pipeline = gst_pipeline_new ("stream-camera");

bus = gst_pipeline_get_bus (GST_PIPELINE (pipeline) );
gst_bus_add_signal_watch (bus);
g_signal_connect (bus, "message", (GCallback) cb_message, pipeline);

rtsp_src = gst_element_factory_make ("rtspsrc", "my_rstp");
const char * rtsp_url = "rtsp://192.168.111.203:8554/video";
g_object_set (G_OBJECT (rtsp_src), "location", rtsp_url, NULL);

caps_filter_rtsp = gst_element_factory_make ("capsfilter", "caps_filter_rtsp");
GstCaps * caps = gst_caps_new_simple ("application/x-rtp",
                                          "payload", G_TYPE_INT, 26, NULL);
g_object_set (G_OBJECT (caps_filter_rtsp), "caps", caps, NULL);

rtpdepay = gst_element_factory_make ("rtpjpegdepay", "rtpjpeg_depay");
rtsp_queue = gst_element_factory_make ("queue", "rtsp_queue");

mux_filter = gst_element_factory_make ("multipartmux", "mux_filter");
image_sink = gst_element_factory_make ("tcpserversink", "image_sink");
g_object_set (G_OBJECT (image_sink), "host", "localhost", "port", 5555, NULL);
gst_bin_add_many (GST_BIN (pipeline), rtsp_src, caps_filter_rtsp, rtpdepay, dec_filter,
                                      rtsp_queue,
                                       mux_filter, image_sink, NULL);
gst_element_link_many (rtsp_src, caps_filter_rtsp, rtpdepay, dec_filter,
                                      rtsp_queue,
                                      mux_filter, image_sink, NULL);

gst_element_set_state (pipeline, GST_STATE_PLAYING);
}

int main (int   argc, char *argv[]){
GMainLoop *loop = g_main_loop_new (NULL, FALSE);

Video_Initialise_RTSP("localhost", 5555);

g_main_loop_run (loop);


return 0;
}

输出程序:

  

面部管道错误!   错误:内部数据流错误。   [调试详细信息:gstbasesrc.c(2625):gst_base_src_loop():/ GstPipeline:stream-camera / GstRTSPSrc:my_rstp / GstUDPSrc:udpsrc0:   流媒体任务已暂停,原因未链接(-1)]

为什么呢?我做错了什么?

1 个答案:

答案 0 :(得分:0)

rtspsrc需要动态添加pad,如示例所示:

    // RTSP pad added handler
    void GstWork::rtsp_pad_added_handler (GstElement *src, GstPad *new_pad,gpointer user_data)
    {
        GstPad * sink_pad = gst_element_get_static_pad(static_cast<GstElement *>(user_data), "sink");
        g_print("Received new pad '%s' from '%s':\n", GST_PAD_NAME(new_pad),GST_ELEMENT_NAME(src));

        // Check the new pad's name
        if ( !g_str_has_prefix(GST_PAD_NAME(new_pad), "recv_rtp_src_") )
        {
             g_print("  It is not the right pad.  Need recv_rtp_src_.Ignoring.\n");
         }
    else
    {
        // If our converter is already linked, we have nothing to do here
        if ( gst_pad_is_linked(sink_pad) )
        {
            g_print(" Sink pad from %s already linked. Ignoring.\n", GST_ELEMENT_NAME (src));
        }
        else
        {
#ifdef USE_GSTREAMER_1_0
            GstCaps * new_pad_caps = gst_pad_get_pad_template_caps(new_pad);
#else
            GstCaps * new_pad_caps = gst_pad_get_caps (new_pad);
#endif
            GstStructure * new_pad_struct = gst_caps_get_structure (new_pad_caps, 0);
            const gchar *new_pad_type = gst_structure_get_name (new_pad_struct);

            // Attempt the link
            GstPadLinkReturn ret = gst_pad_link (new_pad, sink_pad);
            if ( GST_PAD_LINK_FAILED(ret) )
            {
                g_print("  Type is '%s' but link failed.\n", new_pad_type);
            }
            else
            {
                g_print("  Link succeeded (type '%s').\n", new_pad_type);
            }

            gst_caps_unref(new_pad_caps);
        }
    }

    gst_object_unref(sink_pad);
}

在功能中:

    // Connect to the pad-added signal for the rtpbin.  This allows us to link
    // the dynamic RTP source pad to the depayloader when it is created.
    g_signal_connect (rtsp_src, "pad-added", G_CALLBACK(GstWork::rtsp_pad_added_handler), rtsp_queue);