From e05487deeff9c9068f7c972a34eaf906a42bbb13 Mon Sep 17 00:00:00 2001 From: cxh Date: Thu, 22 Jan 2026 10:38:47 +0800 Subject: [PATCH] =?UTF-8?q?=E5=8E=BB=E6=8E=89=E4=B8=8D=E6=94=AF=E6=8C=81?= =?UTF-8?q?=E5=8F=82=E6=95=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/rtmp_manager.cpp | 31 +++++++++++++++++++++++++++++-- 1 file changed, 29 insertions(+), 2 deletions(-) diff --git a/src/rtmp_manager.cpp b/src/rtmp_manager.cpp index 6b120ed..5758015 100644 --- a/src/rtmp_manager.cpp +++ b/src/rtmp_manager.cpp @@ -62,6 +62,23 @@ static void safe_unref(GstObject*& obj) } } +// 安全设置 GStreamer 属性:有则设,无则跳过 +static void try_set_property(GstElement* elem, const char* prop, int value) +{ + if (!elem) return; + + GObjectClass* klass = G_OBJECT_GET_CLASS(elem); + if (klass && g_object_class_find_property(klass, prop)) + { + g_object_set(G_OBJECT(elem), prop, value, nullptr); + LOG_INFO(std::string("[RTMP] Set ") + GST_ELEMENT_NAME(elem) + "." + prop + "=" + std::to_string(value)); + } + else + { + LOG_WARN(std::string("[RTMP] ") + GST_ELEMENT_NAME(elem) + " has NO property '" + prop + "' (skip)"); + } +} + // ======================================================= // 静态成员 // ======================================================= @@ -116,7 +133,7 @@ GstElement* RTMPManager::create_pipeline(const Camera& cam) "! flvmux name=rec_mux streamable=true " "! rtmpsink name=rec_sink location=\"" + record_rtmp + - "\" sync=false async=false protocol=0 " + "\" sync=false async=false " // ===== live branch ===== "t. ! queue max-size-buffers=8 leaky=downstream " @@ -124,7 +141,7 @@ GstElement* RTMPManager::create_pipeline(const Camera& cam) "! queue max-size-buffers=8 leaky=downstream " "! flvmux name=live_mux streamable=true " "! rtmpsink name=live_sink location=\"" + - live_rtmp + "\" sync=false async=false protocol=0 "; + live_rtmp + "\" sync=false async=false "; GError* err = nullptr; GstElement* pipeline = gst_parse_launch(pipeline_str.c_str(), &err); @@ -176,6 +193,16 @@ void RTMPManager::stream_loop(Camera cam, StreamContext* ctx) GstElement* live_valve = gst_bin_get_by_name(GST_BIN(pipeline), "live_valve"); GstElement* record_valve = gst_bin_get_by_name(GST_BIN(pipeline), "record_valve"); + // ===== 对 sink 做“可选属性”配置 ===== + // 某些版本 rtmpsink 有 protocol,有些没有 + try_set_property(rec_sink, "protocol", 0); + try_set_property(live_sink, "protocol", 0); + + // ===== 清理引用 ===== + if (rec_sink) gst_object_unref(rec_sink); + + if (live_sink) gst_object_unref(live_sink); + if (!live_valve || !record_valve) { if (!live_valve) LOG_ERROR("[RTMP] " + key + " - live_valve not found");