NVIDIA DeepStream SDK API Reference

9.1 Release
sources/apps/apps-common/includes/deepstream_common.h
Go to the documentation of this file.
1 /*
2  * SPDX-FileCopyrightText: Copyright (c) 2018-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
3  * SPDX-License-Identifier: Apache-2.0
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 
18 #ifndef __NVGSTDS_COMMON_H__
19 #define __NVGSTDS_COMMON_H__
20 
21 #include <gst/gst.h>
22 #include <stdarg.h>
23 
24 #ifdef __cplusplus
25 extern "C"
26 {
27 #endif
28 
29 #include "deepstream_config.h"
30 
31 /* Global error buffer for capturing last error message */
32 /* Using weak symbol so apps don't need to link deepstream_common.c */
33 __attribute__((weak)) gchar *g_nvds_last_error_message = NULL;
34 
35 /* Helper function to capture and store error messages */
36 static inline void nvds_capture_error(const gchar *func, gint line, const gchar *msg, ...) {
37  va_list args;
38  gchar *formatted_msg;
39  gchar *clean_msg;
40 
41  va_start(args, msg);
42  formatted_msg = g_strdup_vprintf(msg, args);
43  va_end(args);
44 
45  /* Print to console as before */
46  g_print("** ERROR: <%s:%d>: %s\n", func, line, formatted_msg);
47 
48  /* Store in global buffer ONLY IF it's the first error (root cause) */
49  if (!g_nvds_last_error_message) {
50  /* Strip prefix before first colon (e.g. "sink_sub_bin_sink2: error" -> "error") */
51  gchar *colon_pos = strchr(formatted_msg, ':');
52  if (colon_pos) {
53  /* Skip the colon and any leading whitespace */
54  clean_msg = g_strstrip(g_strdup(colon_pos + 1));
55  g_nvds_last_error_message = clean_msg;
56  } else {
57  /* No colon found, use the whole message */
58  g_nvds_last_error_message = g_strdup(formatted_msg);
59  }
60  }
61 
62  g_free(formatted_msg);
63 }
64 
65 #define NVGSTDS_ERR_MSG_V(msg, ...) \
66  nvds_capture_error(__func__, __LINE__, msg, ##__VA_ARGS__)
67 
68 #define NVGSTDS_INFO_MSG_V(msg, ...) \
69  g_print("** INFO: <%s:%d>: " msg "\n", __func__, __LINE__, ##__VA_ARGS__)
70 
71 #define NVGSTDS_WARN_MSG_V(msg, ...) \
72  g_print("** WARN: <%s:%d>: " msg "\n", __func__, __LINE__, ##__VA_ARGS__)
73 
74 #define NVGSTDS_LINK_ELEMENT(elem1, elem2) \
75  do { \
76  if (!gst_element_link (elem1,elem2)) { \
77  GstCaps *src_caps, *sink_caps; \
78  src_caps = gst_pad_query_caps ((GstPad *) (elem1)->srcpads->data, NULL); \
79  sink_caps = gst_pad_query_caps ((GstPad *) (elem2)->sinkpads->data, NULL); \
80  NVGSTDS_ERR_MSG_V ("Failed to link '%s' (%s) and '%s' (%s)", \
81  GST_ELEMENT_NAME (elem1), \
82  gst_caps_to_string (src_caps), \
83  GST_ELEMENT_NAME (elem2), \
84  gst_caps_to_string (sink_caps)); \
85  goto done; \
86  } \
87  } while (0)
88 
89 #define NVGSTDS_LINK_ELEMENT_FULL(elem1, elem1_pad_name, elem2, elem2_pad_name) \
90  do { \
91  GstPad *elem1_pad = gst_element_get_static_pad(elem1, elem1_pad_name); \
92  GstPad *elem2_pad = gst_element_get_static_pad(elem2, elem2_pad_name); \
93  GstPadLinkReturn ret = gst_pad_link (elem1_pad,elem2_pad); \
94  if (ret != GST_PAD_LINK_OK) { \
95  gchar *n1 = gst_pad_get_name (elem1_pad); \
96  gchar *n2 = gst_pad_get_name (elem2_pad); \
97  NVGSTDS_ERR_MSG_V ("Failed to link '%s' and '%s': %d", \
98  n1, n2, ret); \
99  g_free (n1); \
100  g_free (n2); \
101  gst_object_unref (elem1_pad); \
102  gst_object_unref (elem2_pad); \
103  goto done; \
104  } \
105  gst_object_unref (elem1_pad); \
106  gst_object_unref (elem2_pad); \
107  } while (0)
108 
109 #define NVGSTDS_BIN_ADD_GHOST_PAD_NAMED(bin, elem, pad, ghost_pad_name) \
110  do { \
111  GstPad *gstpad = gst_element_get_static_pad (elem, pad); \
112  if (!gstpad) { \
113  NVGSTDS_ERR_MSG_V ("Could not find '%s' in '%s'", pad, \
114  GST_ELEMENT_NAME(elem)); \
115  goto done; \
116  } \
117  gst_element_add_pad (bin, gst_ghost_pad_new (ghost_pad_name, gstpad)); \
118  gst_object_unref (gstpad); \
119  } while (0)
120 
121 #define NVGSTDS_BIN_ADD_GHOST_PAD(bin, elem, pad) \
122  NVGSTDS_BIN_ADD_GHOST_PAD_NAMED (bin, elem, pad, pad)
123 
124 #define NVGSTDS_ELEM_ADD_PROBE(probe_id, elem, pad, probe_func, probe_type, probe_data) \
125  do { \
126  GstPad *gstpad = gst_element_get_static_pad (elem, pad); \
127  if (!gstpad) { \
128  NVGSTDS_ERR_MSG_V ("Could not find '%s' in '%s'", pad, \
129  GST_ELEMENT_NAME(elem)); \
130  goto done; \
131  } \
132  probe_id = gst_pad_add_probe(gstpad, (probe_type), probe_func, probe_data, NULL); \
133  gst_object_unref (gstpad); \
134  } while (0)
135 
136 #define NVGSTDS_ELEM_REMOVE_PROBE(probe_id, elem, pad) \
137  do { \
138  if (probe_id == 0 || !elem) { \
139  break; \
140  } \
141  GstPad *gstpad = gst_element_get_static_pad (elem, pad); \
142  if (!gstpad) { \
143  NVGSTDS_ERR_MSG_V ("Could not find '%s' in '%s'", pad, \
144  GST_ELEMENT_NAME(elem)); \
145  break; \
146  } \
147  gst_pad_remove_probe(gstpad, probe_id); \
148  gst_object_unref (gstpad); \
149  } while (0)
150 
151 #define GET_FILE_PATH(path) ((path) + (((path) && strstr ((path), "file://")) ? 7 : 0))
152 
153 
162 gboolean
163 link_element_to_tee_src_pad (GstElement * tee, GstElement * sinkelem);
164 
174 gboolean
175 link_element_to_streammux_sink_pad (GstElement *streammux, GstElement *elem,
176  gint index);
177 
186 gboolean
187 unlink_element_from_streammux_sink_pad (GstElement *streammux, GstElement *elem);
188 
198 gboolean
199 link_element_to_demux_src_pad (GstElement *demux, GstElement *elem,
200  guint index);
201 
202 /*
203  * Function to replace string with another string.
204  * Make sure @ref src is big enough to accommodate replacements.
205  *
206  * @param[in] str string to search in.
207  * @param[in] replace string to replace.
208  * @param[in] replace_with string to replace @ref replace with.
209  */
210 void
211 str_replace (gchar * str, const gchar * replace, const gchar * replace_with);
212 
213 #ifdef __cplusplus
214 }
215 #endif
216 
217 #endif
nvds_capture_error
static void nvds_capture_error(const gchar *func, gint line, const gchar *msg,...)
Definition: sources/apps/apps-common/includes/deepstream_common.h:36
__attribute__
__attribute__((weak)) gchar *g_nvds_last_error_message
str_replace
void str_replace(gchar *str, const gchar *replace, const gchar *replace_with)
deepstream_config.h
link_element_to_demux_src_pad
gboolean link_element_to_demux_src_pad(GstElement *demux, GstElement *elem, guint index)
Function to link sink pad of an element to source pad of demux element.
link_element_to_tee_src_pad
gboolean link_element_to_tee_src_pad(GstElement *tee, GstElement *sinkelem)
Function to link sink pad of an element to source pad of tee.
link_element_to_streammux_sink_pad
gboolean link_element_to_streammux_sink_pad(GstElement *streammux, GstElement *elem, gint index)
Function to link source pad of an element to sink pad of muxer element.
unlink_element_from_streammux_sink_pad
gboolean unlink_element_from_streammux_sink_pad(GstElement *streammux, GstElement *elem)
Function to unlink source pad of an element from sink pad of muxer element.