GstElement *mcast_udpsink[2];
GSocket *mcast_socket_v4[2];
GSocket *mcast_socket_v6[2];
- GList *mcast_clients;
/* for TCP transport */
GstElement *appsrc[2];
(GDestroyNotify) gst_caps_unref);
}
-typedef struct _UdpClientAddrInfo UdpClientAddrInfo;
-
-struct _UdpClientAddrInfo
-{
- gchar *address;
- guint rtp_port;
- guint add_count; /* how often this address has been added */
-};
-
-static void
-free_mcast_client (gpointer data)
-{
- UdpClientAddrInfo *client = data;
-
- g_free (client->address);
- g_free (client);
-}
-
static void
gst_rtsp_stream_finalize (GObject * obj)
{
}
g_free (priv->multicast_iface);
- g_list_free_full (priv->mcast_clients, (GDestroyNotify) free_mcast_client);
gst_object_unref (priv->payloader);
if (priv->srcpad)
g_clear_object (&inetaddr);
- if (multicast && (ct->ttl > 0) && (ct->ttl <= priv->max_mcast_ttl)) {
- GST_DEBUG ("setting mcast ttl to %d", ct->ttl);
- g_socket_set_multicast_ttl (rtp_socket, ct->ttl);
- g_socket_set_multicast_ttl (rtcp_socket, ct->ttl);
- }
-
socket_out[0] = rtp_socket;
socket_out[1] = rtcp_socket;
*server_addr_out = addr;
}
}
-/* must be called with lock */
-static gboolean
-add_mcast_client_addr (GstRTSPStream * stream, const gchar * destination,
- guint rtp_port, guint rtcp_port)
-{
- GstRTSPStreamPrivate *priv;
- GList *walk;
- UdpClientAddrInfo *client;
- GInetAddress *inet;
-
- priv = stream->priv;
-
- if (destination == NULL)
- return FALSE;
-
- inet = g_inet_address_new_from_string (destination);
- if (inet == NULL)
- goto invalid_address;
-
- if (!g_inet_address_get_is_multicast (inet)) {
- g_object_unref (inet);
- goto invalid_address;
- }
- g_object_unref (inet);
-
- for (walk = priv->mcast_clients; walk; walk = g_list_next (walk)) {
- UdpClientAddrInfo *cli = walk->data;
-
- if ((g_strcmp0 (cli->address, destination) == 0) &&
- (cli->rtp_port == rtp_port)) {
- GST_DEBUG ("requested destination already exists: %s:%u-%u",
- destination, rtp_port, rtcp_port);
- cli->add_count++;
- return TRUE;
- }
- }
-
- client = g_new0 (UdpClientAddrInfo, 1);
- client->address = g_strdup (destination);
- client->rtp_port = rtp_port;
- client->add_count = 1;
- priv->mcast_clients = g_list_prepend (priv->mcast_clients, client);
-
- GST_DEBUG ("added mcast client %s:%u-%u", destination, rtp_port, rtcp_port);
-
- return TRUE;
-
-invalid_address:
- {
- GST_WARNING_OBJECT (stream, "Multicast address is invalid: %s",
- destination);
- return FALSE;
- }
-}
-
-/* must be called with lock */
-static gboolean
-remove_mcast_client_addr (GstRTSPStream * stream, const gchar * destination,
- guint rtp_port, guint rtcp_port)
-{
- GstRTSPStreamPrivate *priv;
- GList *walk;
-
- priv = stream->priv;
-
- if (destination == NULL)
- goto no_destination;
-
- for (walk = priv->mcast_clients; walk; walk = g_list_next (walk)) {
- UdpClientAddrInfo *cli = walk->data;
-
- if ((g_strcmp0 (cli->address, destination) == 0) &&
- (cli->rtp_port == rtp_port)) {
- cli->add_count--;
-
- if (!cli->add_count) {
- priv->mcast_clients = g_list_remove (priv->mcast_clients, cli);
- free_mcast_client (cli);
- }
- return TRUE;
- }
- }
-
- GST_WARNING_OBJECT (stream, "Address not found");
- return FALSE;
-
-no_destination:
- {
- GST_WARNING_OBJECT (stream, "No destination has been provided");
- return FALSE;
- }
-}
-
-
/**
* gst_rtsp_stream_allocate_udp_sockets:
* @stream: a #GstRTSPStream
return ttl;
}
-/**
- * gst_rtsp_stream_verify_mcast_ttl:
- * @stream: a #GstRTSPStream
- * @ttl: a requested multicast ttl
- *
- * Check if the requested multicast ttl value is allowed.
- *
- * Returns: TRUE if the requested ttl value is allowed.
- *
- */
-gboolean
-gst_rtsp_stream_verify_mcast_ttl (GstRTSPStream * stream, guint ttl)
-{
- gboolean res = FALSE;
-
- g_mutex_lock (&stream->priv->lock);
- if ((ttl > 0) && (ttl <= stream->priv->max_mcast_ttl))
- res = TRUE;
- g_mutex_unlock (&stream->priv->lock);
-
- return res;
-}
-
/* executed from streaming thread */
static void
caps_notify (GstPad * pad, GParamSpec * unused, GstRTSPStream * stream)
}
static gboolean
-check_mcast_client_addr (GstRTSPStream * stream, const GstRTSPTransport * tr)
+check_mcast_part_for_transport (GstRTSPStream * stream,
+ const GstRTSPTransport * tr)
{
GstRTSPStreamPrivate *priv = stream->priv;
- GList *walk;
-
- if (priv->mcast_clients == NULL)
- goto no_addr;
+ GInetAddress *inetaddr;
+ GSocketFamily family;
+ GstRTSPAddress *mcast_addr;
- if (tr == NULL)
- goto no_transport;
+ /* Check if it's a ipv4 or ipv6 transport */
+ inetaddr = g_inet_address_new_from_string (tr->destination);
+ family = g_inet_address_get_family (inetaddr);
+ g_object_unref (inetaddr);
- if (tr->destination == NULL)
- goto no_destination;
+ /* Select fields corresponding to the family */
+ if (family == G_SOCKET_FAMILY_IPV4) {
+ mcast_addr = priv->mcast_addr_v4;
+ } else {
+ mcast_addr = priv->mcast_addr_v6;
+ }
- for (walk = priv->mcast_clients; walk; walk = g_list_next (walk)) {
- UdpClientAddrInfo *cli = walk->data;
+ /* We support only one mcast group per family, make sure this transport
+ * matches it. */
+ if (!mcast_addr)
+ goto no_addr;
- if ((g_strcmp0 (cli->address, tr->destination) == 0) &&
- (cli->rtp_port == tr->port.min))
- return TRUE;
- }
+ if (g_ascii_strcasecmp (tr->destination, mcast_addr->address) != 0 ||
+ tr->port.min != mcast_addr->port ||
+ tr->port.max != mcast_addr->port + mcast_addr->n_ports - 1 ||
+ tr->ttl != mcast_addr->ttl)
+ goto wrong_addr;
- return FALSE;
+ return TRUE;
no_addr:
{
"has been reserved");
return FALSE;
}
-no_transport:
- {
- GST_WARNING_OBJECT (stream, "Adding mcast transport, but no transport "
- "has been provided");
- return FALSE;
- }
-no_destination:
+wrong_addr:
{
GST_WARNING_OBJECT (stream, "Adding mcast transport, but it doesn't match "
"the reserved address");
if (add) {
GST_INFO ("adding %s:%d-%d", dest, min, max);
- if (!check_mcast_client_addr (stream, tr))
+ if (!check_mcast_part_for_transport (stream, tr))
goto mcast_error;
- add_client (priv->mcast_udpsink[0], priv->mcast_udpsink[1], dest, min,
- max);
+ /* FIXME: Is it ok to set ttl-mc if media is shared? */
if (tr->ttl > 0) {
GST_INFO ("setting ttl-mc %d", tr->ttl);
if (priv->mcast_udpsink[0])
g_object_set (G_OBJECT (priv->mcast_udpsink[1]), "ttl-mc", tr->ttl,
NULL);
}
+ add_client (priv->mcast_udpsink[0], priv->mcast_udpsink[1], dest, min,
+ max);
priv->transports = g_list_prepend (priv->transports, trans);
} else {
GST_INFO ("removing %s:%d-%d", dest, min, max);
- if (!remove_mcast_client_addr (stream, dest, min, max))
- GST_WARNING_OBJECT (stream,
- "Failed to remove multicast address: %s:%d-%d", dest, min, max);
remove_client (priv->mcast_udpsink[0], priv->mcast_udpsink[1], dest,
min, max);
priv->transports = g_list_remove (priv->transports, trans);
}
/**
- * gst_rtsp_stream_add_multicast_client_address:
- * @stream: a #GstRTSPStream
- * @destination: (transfer none): a multicast address to add
- * @rtp_port: RTP port
- * @rtcp_port: RTCP port
- * @family: socket family
- *
- * Add multicast client address to stream. At this point, the sockets that
- * will stream RTP and RTCP data to @destination are supposed to be
- * allocated.
- *
- * Returns: %TRUE if @destination can be addedd and handled by @stream.
- */
-gboolean
-gst_rtsp_stream_add_multicast_client_address (GstRTSPStream * stream,
- const gchar * destination, guint rtp_port, guint rtcp_port,
- GSocketFamily family)
-{
- GstRTSPStreamPrivate *priv;
-
- g_return_val_if_fail (GST_IS_RTSP_STREAM (stream), FALSE);
- g_return_val_if_fail (destination != NULL, FALSE);
-
- priv = stream->priv;
- g_mutex_lock (&priv->lock);
- if ((family == G_SOCKET_FAMILY_IPV4) && (priv->mcast_socket_v4[0] == NULL))
- goto socket_error;
- else if ((family == G_SOCKET_FAMILY_IPV6) &&
- (priv->mcast_socket_v6[0] == NULL))
- goto socket_error;
-
- if (!add_mcast_client_addr (stream, destination, rtp_port, rtcp_port))
- goto add_addr_error;
- g_mutex_unlock (&priv->lock);
-
- return TRUE;
-
-socket_error:
- {
- GST_WARNING_OBJECT (stream,
- "Failed to add multicast address: no udp socket");
- g_mutex_unlock (&priv->lock);
- return FALSE;
- }
-add_addr_error:
- {
- GST_WARNING_OBJECT (stream,
- "Failed to add multicast address: invalid address");
- g_mutex_unlock (&priv->lock);
- return FALSE;
- }
-}
-
-/**
- * gst_rtsp_stream_get_multicast_client_addresses
- * @stream: a #GstRTSPStream
- *
- * Get all multicast client addresses that RTP data will be sent to
- *
- * Returns: A comma separated list of host:port pairs with destinations
- */
-gchar *
-gst_rtsp_stream_get_multicast_client_addresses (GstRTSPStream * stream)
-{
- GstRTSPStreamPrivate *priv;
- GString *str;
- GList *clients;
-
- g_return_val_if_fail (GST_IS_RTSP_STREAM (stream), NULL);
-
- priv = stream->priv;
- str = g_string_new ("");
-
- g_mutex_lock (&priv->lock);
- clients = priv->mcast_clients;
- while (clients != NULL) {
- UdpClientAddrInfo *client;
-
- client = (UdpClientAddrInfo *) clients->data;
- clients = g_list_next (clients);
- g_string_append_printf (str, "%s:%d%s", client->address, client->rtp_port,
- (clients != NULL ? "," : ""));
- }
- g_mutex_unlock (&priv->lock);
-
- return g_string_free (str, FALSE);
-}
-
-/**
* gst_rtsp_stream_set_seqnum:
* @stream: a #GstRTSPStream
* @seqnum: a new sequence number
}
static gboolean
-test_setup_response_461 (GstRTSPClient * client,
- GstRTSPMessage * response, gboolean close, gpointer user_data)
-{
- GstRTSPStatusCode code;
- const gchar *reason;
- GstRTSPVersion version;
- gchar *str;
-
- fail_unless (expected_transport == NULL);
-
- fail_unless (gst_rtsp_message_get_type (response) ==
- GST_RTSP_MESSAGE_RESPONSE);
-
- fail_unless (gst_rtsp_message_parse_response (response, &code, &reason,
- &version)
- == GST_RTSP_OK);
- fail_unless (code == GST_RTSP_STS_UNSUPPORTED_TRANSPORT);
- fail_unless (g_str_equal (reason, "Unsupported transport"));
- fail_unless (version == GST_RTSP_VERSION_1_0);
-
- fail_unless (gst_rtsp_message_get_header (response, GST_RTSP_HDR_CSEQ, &str,
- 0) == GST_RTSP_OK);
- fail_unless (atoi (str) == cseq++);
-
-
- return TRUE;
-}
-
-static gboolean
test_teardown_response_200 (GstRTSPClient * client,
GstRTSPMessage * response, gboolean close, gpointer user_data)
{
}
static GstRTSPClient *
-setup_multicast_client (guint max_ttl)
+setup_multicast_client (void)
{
GstRTSPClient *client;
GstRTSPSessionPool *session_pool;
"media.factory.construct", G_TYPE_BOOLEAN, TRUE, NULL);
gst_rtsp_mount_points_add_factory (mount_points, "/test", factory);
gst_rtsp_client_set_mount_points (client, mount_points);
- gst_rtsp_media_factory_set_max_mcast_ttl (factory, max_ttl);
thread_pool = gst_rtsp_thread_pool_new ();
gst_rtsp_client_set_thread_pool (client, thread_pool);
GstRTSPMessage request = { 0, };
gchar *str;
- client = setup_multicast_client (1);
+ client = setup_multicast_client ();
/* simple SETUP for non-existing url */
fail_unless (gst_rtsp_message_init_request (&request, GST_RTSP_SETUP,
GstRTSPMessage request = { 0, };
gchar *str;
- client = setup_multicast_client (1);
+ client = setup_multicast_client ();
expected_session_timeout = 20;
g_signal_connect (G_OBJECT (client), "new-session",
GstRTSPMessage request = { 0, };
gchar *str;
- client = setup_multicast_client (1);
+ client = setup_multicast_client ();
/* simple SETUP with a valid URI and multicast and a specific dest,
* but ignore it */
GstRTSPSessionPool *session_pool;
GstRTSPContext ctx = { NULL };
- client = setup_multicast_client (1);
+ client = setup_multicast_client ();
ctx.client = client;
ctx.auth = gst_rtsp_auth_new ();
GST_END_TEST;
static void
-mcast_transport_two_clients (gboolean shared, const gchar * transport1,
- const gchar * expected_transport1, const gchar * addr1,
- const gchar * transport2, const gchar * expected_transport2,
- const gchar * addr2)
+mcast_transport_specific_two_clients (gboolean shared)
{
- GstRTSPClient *client1, *client2;
+ GstRTSPClient *client, *client2;
GstRTSPMessage request = { 0, };
gchar *str;
GstRTSPSessionPool *session_pool;
GstRTSPAddressPool *address_pool;
GstRTSPThreadPool *thread_pool;
gchar *session_id1;
- gchar *client_addr = NULL;
mount_points = gst_rtsp_mount_points_new ();
factory = gst_rtsp_media_factory_new ();
thread_pool = gst_rtsp_thread_pool_new ();
/* first multicast client with transport specific request */
- client1 = gst_rtsp_client_new ();
- gst_rtsp_client_set_session_pool (client1, session_pool);
- gst_rtsp_client_set_mount_points (client1, mount_points);
- gst_rtsp_client_set_thread_pool (client1, thread_pool);
+ client = gst_rtsp_client_new ();
+ gst_rtsp_client_set_session_pool (client, session_pool);
+ gst_rtsp_client_set_mount_points (client, mount_points);
+ gst_rtsp_client_set_thread_pool (client, thread_pool);
- ctx.client = client1;
+ ctx.client = client;
ctx.auth = gst_rtsp_auth_new ();
ctx.token =
gst_rtsp_token_new (GST_RTSP_TOKEN_TRANSPORT_CLIENT_SETTINGS,
"user", NULL);
gst_rtsp_context_push_current (&ctx);
- expected_transport = expected_transport1;
+ expected_transport = "RTP/AVP;multicast;destination=233.252.0.1;"
+ "ttl=1;port=5000-5001;mode=\"PLAY\"";
/* send SETUP request */
fail_unless (gst_rtsp_message_init_request (&request, GST_RTSP_SETUP,
"rtsp://localhost/test/stream=0") == GST_RTSP_OK);
str = g_strdup_printf ("%d", cseq);
gst_rtsp_message_take_header (&request, GST_RTSP_HDR_CSEQ, str);
- gst_rtsp_message_add_header (&request, GST_RTSP_HDR_TRANSPORT, transport1);
+ gst_rtsp_message_add_header (&request, GST_RTSP_HDR_TRANSPORT,
+ expected_transport);
- gst_rtsp_client_set_send_func (client1, test_setup_response_200_multicast,
+ gst_rtsp_client_set_send_func (client, test_setup_response_200_multicast,
NULL, NULL);
- fail_unless (gst_rtsp_client_handle_message (client1,
+ fail_unless (gst_rtsp_client_handle_message (client,
&request) == GST_RTSP_OK);
gst_rtsp_message_unset (&request);
expected_transport = NULL;
str = g_strdup_printf ("%d", cseq);
gst_rtsp_message_take_header (&request, GST_RTSP_HDR_CSEQ, str);
gst_rtsp_message_add_header (&request, GST_RTSP_HDR_SESSION, session_id);
- gst_rtsp_client_set_send_func (client1, test_response_200, NULL, NULL);
- fail_unless (gst_rtsp_client_handle_message (client1,
+ gst_rtsp_client_set_send_func (client, test_response_200, NULL, NULL);
+ fail_unless (gst_rtsp_client_handle_message (client,
&request) == GST_RTSP_OK);
gst_rtsp_message_unset (&request);
-
- /* check address */
- client_addr = gst_rtsp_stream_get_multicast_client_addresses (ctx.stream);
- fail_if (client_addr == NULL);
- fail_unless (g_str_equal (client_addr, addr1));
- g_free (client_addr);
-
gst_rtsp_context_pop_current (&ctx);
session_id1 = session_id;
"user", NULL);
gst_rtsp_context_push_current (&ctx2);
- expected_transport = expected_transport2;
+ expected_transport = "RTP/AVP;multicast;destination=233.252.0.2;"
+ "ttl=1;port=5002-5003;mode=\"PLAY\"";
/* send SETUP request */
fail_unless (gst_rtsp_message_init_request (&request, GST_RTSP_SETUP,
"rtsp://localhost/test/stream=0") == GST_RTSP_OK);
str = g_strdup_printf ("%d", cseq);
gst_rtsp_message_take_header (&request, GST_RTSP_HDR_CSEQ, str);
- gst_rtsp_message_add_header (&request, GST_RTSP_HDR_TRANSPORT, transport2);
+ gst_rtsp_message_add_header (&request, GST_RTSP_HDR_TRANSPORT,
+ expected_transport);
gst_rtsp_client_set_send_func (client2, test_setup_response_200_multicast,
NULL, NULL);
&request) == GST_RTSP_OK);
gst_rtsp_message_unset (&request);
- /* check addresses */
- client_addr = gst_rtsp_stream_get_multicast_client_addresses (ctx2.stream);
- fail_if (client_addr == NULL);
- if (shared) {
- if (g_str_equal (addr1, addr2)) {
- fail_unless (g_str_equal (client_addr, addr1));
- } else {
- gchar *addr_str = g_strdup_printf ("%s,%s", addr2, addr1);
- fail_unless (g_str_equal (client_addr, addr_str));
- g_free (addr_str);
- }
- } else {
- fail_unless (g_str_equal (client_addr, addr2));
- }
- g_free (client_addr);
-
send_teardown (client2);
gst_rtsp_context_pop_current (&ctx2);
gst_rtsp_context_push_current (&ctx);
session_id = session_id1;
- send_teardown (client1);
+ send_teardown (client);
gst_rtsp_context_pop_current (&ctx);
- teardown_client (client1);
+ teardown_client (client);
teardown_client (client2);
g_object_unref (ctx.auth);
g_object_unref (ctx2.auth);
* CASE: media is shared */
GST_START_TEST
(test_client_multicast_transport_specific_two_clients_shared_media) {
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=1;port=5002-5003;mode=\"PLAY\"";
- const gchar *expected_transport_2 = transport_client_2;
- const gchar *addr_client_2 = "233.252.0.2:5002";
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
+ mcast_transport_specific_two_clients (TRUE);
}
GST_END_TEST;
* CASE: media is not shared */
GST_START_TEST (test_client_multicast_transport_specific_two_clients)
{
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=1;port=5002-5003;mode=\"PLAY\"";
- const gchar *expected_transport_2 = transport_client_2;
- const gchar *addr_client_2 = "233.252.0.2:5002";
-
- mcast_transport_two_clients (FALSE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-
-/* test if two multicast clients can choose the same transport settings.
- * CASE: media is shared */
-GST_START_TEST
- (test_client_multicast_transport_specific_two_clients_shared_media_same_transport)
-{
-
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = transport_client_1;
- const gchar *expected_transport_2 = expected_transport_1;
- const gchar *addr_client_2 = addr_client_1;
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-
-/* test if two multicast clients get the same transport settings without
- * requesting specific transport.
- * CASE: media is shared */
-GST_START_TEST (test_client_multicast_two_clients_shared_media)
-{
- const gchar *transport_client_1 = "RTP/AVP;multicast;mode=\"PLAY\"";
- const gchar *expected_transport_1 =
- "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = transport_client_1;
- const gchar *expected_transport_2 = expected_transport_1;
- const gchar *addr_client_2 = addr_client_1;
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-
-/* test if two multicast clients get the different transport settings: the first client
- * requests the specific transport configuration while the second client lets
- * the server select the multicast address and the ports.
- * CASE: media is shared */
-GST_START_TEST
- (test_client_multicast_two_clients_first_specific_transport_shared_media) {
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;mode=\"PLAY\"";
- const gchar *expected_transport_2 = expected_transport_1;
- const gchar *addr_client_2 = addr_client_1;
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-/* test if two multicast clients get the different transport settings: the first client lets
- * the server select the multicast address and the ports while the second client requests
- * the specific transport configuration.
- * CASE: media is shared */
-GST_START_TEST
- (test_client_multicast_two_clients_second_specific_transport_shared_media) {
- const gchar *transport_client_1 = "RTP/AVP;multicast;mode=\"PLAY\"";
- const gchar *expected_transport_1 =
- "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=1;port=5000-5001;mode=\"PLAY\"";
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=2;port=5004-5005;mode=\"PLAY\"";
- const gchar *expected_transport_2 = transport_client_2;
- const gchar *addr_client_2 = "233.252.0.2:5004";
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-
-/* test if the maximum ttl multicast value is chosen by the server
- * CASE: the first client provides the highest ttl value */
-GST_START_TEST (test_client_multicast_max_ttl_first_client)
-{
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=3;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=1;port=5002-5003;mode=\"PLAY\"";
- const gchar *expected_transport_2 =
- "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=3;port=5002-5003;mode=\"PLAY\"";
- const gchar *addr_client_2 = "233.252.0.2:5002";
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-
-/* test if the maximum ttl multicast value is chosen by the server
- * CASE: the second client provides the highest ttl value */
-GST_START_TEST (test_client_multicast_max_ttl_second_client)
-{
- const gchar *transport_client_1 = "RTP/AVP;multicast;destination=233.252.0.1;"
- "ttl=2;port=5000-5001;mode=\"PLAY\"";
- const gchar *expected_transport_1 = transport_client_1;
- const gchar *addr_client_1 = "233.252.0.1:5000";
-
- const gchar *transport_client_2 = "RTP/AVP;multicast;destination=233.252.0.2;"
- "ttl=4;port=5002-5003;mode=\"PLAY\"";
- const gchar *expected_transport_2 = transport_client_2;
- const gchar *addr_client_2 = "233.252.0.2:5002";
-
- mcast_transport_two_clients (TRUE, transport_client_1,
- expected_transport_1, addr_client_1, transport_client_2,
- expected_transport_2, addr_client_2);
-}
-
-GST_END_TEST;
-GST_START_TEST (test_client_multicast_invalid_ttl)
-{
- GstRTSPClient *client;
- GstRTSPMessage request = { 0, };
- gchar *str;
- GstRTSPSessionPool *session_pool;
- GstRTSPContext ctx = { NULL };
-
- client = setup_multicast_client (3);
-
- ctx.client = client;
- ctx.auth = gst_rtsp_auth_new ();
- ctx.token =
- gst_rtsp_token_new (GST_RTSP_TOKEN_TRANSPORT_CLIENT_SETTINGS,
- G_TYPE_BOOLEAN, TRUE, GST_RTSP_TOKEN_MEDIA_FACTORY_ROLE, G_TYPE_STRING,
- "user", NULL);
- gst_rtsp_context_push_current (&ctx);
-
- /* simple SETUP with an invalid ttl=0 */
- fail_unless (gst_rtsp_message_init_request (&request, GST_RTSP_SETUP,
- "rtsp://localhost/test/stream=0") == GST_RTSP_OK);
- str = g_strdup_printf ("%d", cseq);
- gst_rtsp_message_take_header (&request, GST_RTSP_HDR_CSEQ, str);
- gst_rtsp_message_add_header (&request, GST_RTSP_HDR_TRANSPORT,
- "RTP/AVP;multicast;destination=233.252.0.1;ttl=0;port=5000-5001;");
-
- gst_rtsp_client_set_send_func (client, test_setup_response_461, NULL, NULL);
- fail_unless (gst_rtsp_client_handle_message (client,
- &request) == GST_RTSP_OK);
- gst_rtsp_message_unset (&request);
-
- session_pool = gst_rtsp_client_get_session_pool (client);
- fail_unless (session_pool != NULL);
- fail_unless (gst_rtsp_session_pool_get_n_sessions (session_pool) == 0);
- g_object_unref (session_pool);
-
- teardown_client (client);
- g_object_unref (ctx.auth);
- gst_rtsp_token_unref (ctx.token);
- gst_rtsp_context_pop_current (&ctx);
+ mcast_transport_specific_two_clients (FALSE);
}
GST_END_TEST;
test_client_multicast_transport_specific_two_clients_shared_media);
tcase_add_test (tc, test_client_multicast_transport_specific_two_clients);
tcase_add_test (tc,
- test_client_multicast_transport_specific_two_clients_shared_media_same_transport);
- tcase_add_test (tc, test_client_multicast_two_clients_shared_media);
- tcase_add_test (tc,
- test_client_multicast_two_clients_first_specific_transport_shared_media);
- tcase_add_test (tc,
- test_client_multicast_two_clients_second_specific_transport_shared_media);
- tcase_add_test (tc,
test_client_multicast_transport_specific_no_address_in_pool);
- tcase_add_test (tc, test_client_multicast_max_ttl_first_client);
- tcase_add_test (tc, test_client_multicast_max_ttl_second_client);
- tcase_add_test (tc, test_client_multicast_invalid_ttl);
return s;
}