Skip to content

Commit

Permalink
rtsp-media-factory: expose API to disable RTCP
Browse files Browse the repository at this point in the history
This is supported by the RFC, and can be useful on systems where
allocating two consecutive ports is problematic, and RTCP is not
necessary.

Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-rtsp-server/-/merge_requests/159>
  • Loading branch information
MathieuDuponchelle committed Oct 10, 2020
1 parent 5029335 commit 1730940
Show file tree
Hide file tree
Showing 7 changed files with 232 additions and 45 deletions.
5 changes: 5 additions & 0 deletions examples/test-launch.c
Original file line number Diff line number Diff line change
Expand Up @@ -22,12 +22,16 @@
#include <gst/rtsp-server/rtsp-server.h>

#define DEFAULT_RTSP_PORT "8554"
#define DEFAULT_DISABLE_RTCP FALSE

static char *port = (char *) DEFAULT_RTSP_PORT;
static gboolean disable_rtcp = DEFAULT_DISABLE_RTCP;

static GOptionEntry entries[] = {
{"port", 'p', 0, G_OPTION_ARG_STRING, &port,
"Port to listen on (default: " DEFAULT_RTSP_PORT ")", "PORT"},
{"disable-rtcp", '\0', 0, G_OPTION_ARG_NONE, &disable_rtcp,
"Whether RTCP should be disabled (default false)", NULL},
{NULL}
};

Expand Down Expand Up @@ -70,6 +74,7 @@ main (int argc, char *argv[])
factory = gst_rtsp_media_factory_new ();
gst_rtsp_media_factory_set_launch (factory, argv[1]);
gst_rtsp_media_factory_set_shared (factory, TRUE);
gst_rtsp_media_factory_set_enable_rtcp (factory, !disable_rtcp);

/* attach the test factory to the /test url */
gst_rtsp_mount_points_add_factory (mounts, "/test", factory);
Expand Down
81 changes: 81 additions & 0 deletions gst/rtsp-server/rtsp-media-factory.c
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
#include "config.h"
#endif

#include "rtsp-server-internal.h"
#include "rtsp-media-factory.h"

#define GST_RTSP_MEDIA_FACTORY_GET_LOCK(f) (&(GST_RTSP_MEDIA_FACTORY_CAST(f)->priv->lock))
Expand All @@ -65,6 +66,7 @@ struct _GstRTSPMediaFactoryPrivate
gchar *multicast_iface;
guint max_mcast_ttl;
gboolean bind_mcast_address;
gboolean enable_rtcp;

GstClockTime rtx_time;
guint latency;
Expand Down Expand Up @@ -95,6 +97,7 @@ struct _GstRTSPMediaFactoryPrivate
#define DEFAULT_STOP_ON_DISCONNECT TRUE
#define DEFAULT_DO_RETRANSMISSION FALSE
#define DEFAULT_DSCP_QOS (-1)
#define DEFAULT_ENABLE_RTCP TRUE

enum
{
Expand All @@ -113,6 +116,7 @@ enum
PROP_MAX_MCAST_TTL,
PROP_BIND_MCAST_ADDRESS,
PROP_DSCP_QOS,
PROP_ENABLE_RTCP,
PROP_LAST
};

Expand Down Expand Up @@ -247,6 +251,18 @@ gst_rtsp_media_factory_class_init (GstRTSPMediaFactoryClass * klass)
DEFAULT_BIND_MCAST_ADDRESS,
G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

/**
* GstRTSPMediaFactory:enable-rtcp:
*
* Whether the created media should send and receive RTCP
*
* Since: 1.20
*/
g_object_class_install_property (gobject_class, PROP_ENABLE_RTCP,
g_param_spec_boolean ("enable-rtcp", "Enable RTCP",
"Whether the created media should send and receive RTCP",
DEFAULT_ENABLE_RTCP, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

g_object_class_install_property (gobject_class, PROP_DSCP_QOS,
g_param_spec_int ("dscp-qos", "DSCP QoS",
"The IP DSCP field to use", -1, 63,
Expand Down Expand Up @@ -295,6 +311,7 @@ gst_rtsp_media_factory_init (GstRTSPMediaFactory * factory)
priv->do_retransmission = DEFAULT_DO_RETRANSMISSION;
priv->max_mcast_ttl = DEFAULT_MAX_MCAST_TTL;
priv->bind_mcast_address = DEFAULT_BIND_MCAST_ADDRESS;
priv->enable_rtcp = DEFAULT_ENABLE_RTCP;
priv->dscp_qos = DEFAULT_DSCP_QOS;

g_mutex_init (&priv->lock);
Expand Down Expand Up @@ -381,6 +398,10 @@ gst_rtsp_media_factory_get_property (GObject * object, guint propid,
case PROP_DSCP_QOS:
g_value_set_int (value, gst_rtsp_media_factory_get_dscp_qos (factory));
break;
case PROP_ENABLE_RTCP:
g_value_set_boolean (value,
gst_rtsp_media_factory_is_enable_rtcp (factory));
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, propid, pspec);
}
Expand Down Expand Up @@ -442,6 +463,10 @@ gst_rtsp_media_factory_set_property (GObject * object, guint propid,
case PROP_DSCP_QOS:
gst_rtsp_media_factory_set_dscp_qos (factory, g_value_get_int (value));
break;
case PROP_ENABLE_RTCP:
gst_rtsp_media_factory_set_enable_rtcp (factory,
g_value_get_boolean (value));
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, propid, pspec);
}
Expand Down Expand Up @@ -1686,6 +1711,57 @@ gst_rtsp_media_factory_is_bind_mcast_address (GstRTSPMediaFactory * factory)
return result;
}

/**
* gst_rtsp_media_factory_set_enable_rtcp:
* @factory: a #GstRTSPMediaFactory
* @enable: the new value
*
* Decide whether the created media should send and receive RTCP
*
* Since: 1.20
*/
void
gst_rtsp_media_factory_set_enable_rtcp (GstRTSPMediaFactory * factory,
gboolean enable)
{
GstRTSPMediaFactoryPrivate *priv;

g_return_if_fail (GST_IS_RTSP_MEDIA_FACTORY (factory));

priv = factory->priv;

GST_RTSP_MEDIA_FACTORY_LOCK (factory);
priv->enable_rtcp = enable;
GST_RTSP_MEDIA_FACTORY_UNLOCK (factory);
}

/**
* gst_rtsp_media_factory_is_enable_rtcp:
* @factory: a #GstRTSPMediaFactory
*
* Check if created media will send and receive RTCP
*
* Returns: %TRUE if created media will send and receive RTCP
*
* Since: 1.20
*/
gboolean
gst_rtsp_media_factory_is_enable_rtcp (GstRTSPMediaFactory * factory)
{
GstRTSPMediaFactoryPrivate *priv;
gboolean result;

g_return_val_if_fail (GST_IS_RTSP_MEDIA_FACTORY (factory), FALSE);

priv = factory->priv;

GST_RTSP_MEDIA_FACTORY_LOCK (factory);
result = priv->enable_rtcp;
GST_RTSP_MEDIA_FACTORY_UNLOCK (factory);

return result;
}

static gchar *
default_gen_key (GstRTSPMediaFactory * factory, const GstRTSPUrl * url)
{
Expand Down Expand Up @@ -1757,6 +1833,7 @@ default_construct (GstRTSPMediaFactory * factory, const GstRTSPUrl * url)
GstElement *element, *pipeline;
GstRTSPMediaFactoryClass *klass;
GType media_gtype;
gboolean enable_rtcp;

klass = GST_RTSP_MEDIA_FACTORY_GET_CLASS (factory);

Expand All @@ -1769,13 +1846,17 @@ default_construct (GstRTSPMediaFactory * factory, const GstRTSPUrl * url)

GST_RTSP_MEDIA_FACTORY_LOCK (factory);
media_gtype = factory->priv->media_gtype;
enable_rtcp = factory->priv->enable_rtcp;
GST_RTSP_MEDIA_FACTORY_UNLOCK (factory);

/* create a new empty media */
media =
g_object_new (media_gtype, "element", element, "transport-mode",
factory->priv->transport_mode, NULL);

/* We need to call this prior to collecting streams */
gst_rtsp_media_set_enable_rtcp (media, enable_rtcp);

gst_rtsp_media_collect_streams (media);

pipeline = klass->create_pipeline (factory, media);
Expand Down
7 changes: 7 additions & 0 deletions gst/rtsp-server/rtsp-media-factory.h
Original file line number Diff line number Diff line change
Expand Up @@ -258,6 +258,13 @@ void gst_rtsp_media_factory_set_dscp_qos (GstRTSPMediaFactory *
GST_RTSP_SERVER_API
gint gst_rtsp_media_factory_get_dscp_qos (GstRTSPMediaFactory * factory);

GST_RTSP_SERVER_API
void gst_rtsp_media_factory_set_enable_rtcp (GstRTSPMediaFactory * factory,
gboolean enable);

GST_RTSP_SERVER_API
gboolean gst_rtsp_media_factory_is_enable_rtcp (GstRTSPMediaFactory * factory);

/* creating the media from the factory and a url */

GST_RTSP_SERVER_API
Expand Down
18 changes: 18 additions & 0 deletions gst/rtsp-server/rtsp-media.c
Original file line number Diff line number Diff line change
Expand Up @@ -112,6 +112,7 @@ struct _GstRTSPMediaPrivate
gchar *multicast_iface;
guint max_mcast_ttl;
gboolean bind_mcast_address;
gboolean enable_rtcp;
gboolean blocked;
GstRTSPTransportMode transport_mode;
gboolean stop_on_disconnect;
Expand Down Expand Up @@ -180,6 +181,7 @@ struct _GstRTSPMediaPrivate
#define DEFAULT_MAX_MCAST_TTL 255
#define DEFAULT_BIND_MCAST_ADDRESS FALSE
#define DEFAULT_DO_RATE_CONTROL TRUE
#define DEFAULT_ENABLE_RTCP TRUE

#define DEFAULT_DO_RETRANSMISSION FALSE

Expand Down Expand Up @@ -492,6 +494,7 @@ gst_rtsp_media_init (GstRTSPMedia * media)
priv->do_retransmission = DEFAULT_DO_RETRANSMISSION;
priv->max_mcast_ttl = DEFAULT_MAX_MCAST_TTL;
priv->bind_mcast_address = DEFAULT_BIND_MCAST_ADDRESS;
priv->enable_rtcp = DEFAULT_ENABLE_RTCP;
priv->do_rate_control = DEFAULT_DO_RATE_CONTROL;
priv->dscp_qos = DEFAULT_DSCP_QOS;
priv->expected_async_done = FALSE;
Expand Down Expand Up @@ -2104,6 +2107,20 @@ gst_rtsp_media_is_bind_mcast_address (GstRTSPMedia * media)
return result;
}

void
gst_rtsp_media_set_enable_rtcp (GstRTSPMedia * media, gboolean enable)
{
GstRTSPMediaPrivate *priv;

g_return_if_fail (GST_IS_RTSP_MEDIA (media));

priv = media->priv;

g_mutex_lock (&priv->lock);
priv->enable_rtcp = enable;
g_mutex_unlock (&priv->lock);
}

static GList *
_find_payload_types (GstRTSPMedia * media)
{
Expand Down Expand Up @@ -2425,6 +2442,7 @@ gst_rtsp_media_create_stream (GstRTSPMedia * media, GstElement * payloader,
gst_rtsp_stream_set_multicast_iface (stream, priv->multicast_iface);
gst_rtsp_stream_set_max_mcast_ttl (stream, priv->max_mcast_ttl);
gst_rtsp_stream_set_bind_mcast_address (stream, priv->bind_mcast_address);
gst_rtsp_stream_set_enable_rtcp (stream, priv->enable_rtcp);
gst_rtsp_stream_set_profiles (stream, priv->profiles);
gst_rtsp_stream_set_protocols (stream, priv->protocols);
gst_rtsp_stream_set_retransmission_time (stream, priv->rtx_time);
Expand Down
3 changes: 3 additions & 0 deletions gst/rtsp-server/rtsp-server-internal.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,9 @@ gboolean gst_rtsp_stream_transport_check_back_pressure (GstRTSPS

gboolean gst_rtsp_stream_is_tcp_receiver (GstRTSPStream * stream);

void gst_rtsp_media_set_enable_rtcp (GstRTSPMedia *media, gboolean enable);
void gst_rtsp_stream_set_enable_rtcp (GstRTSPStream *stream, gboolean enable);

G_END_DECLS

#endif /* __GST_RTSP_SERVER_INTERNAL_H__ */
Loading

0 comments on commit 1730940

Please sign in to comment.