From c9997d7a54e75e671e5300039459dea352bca544 Mon Sep 17 00:00:00 2001 From: Fabrice Bellet Date: Thu, 10 Mar 2016 14:21:11 +0100 Subject: [PATCH] jingle-content: implement finish_initial_candidates method This patch allows us to enqueue all local candidates, and to send them in a single messages in the finish_initial_candidates() method, instead of sending them one after the other in individual stanzas. This is required by the ICE spec, to make the agent of both peers start the connection check with a complete and identical set of candidates. --- wocky/wocky-jingle-content.c | 13 +++++++++++++ wocky/wocky-jingle-transport-iceudp.c | 26 ++++++++++++++++++++++++++ wocky/wocky-jingle-transport-iface.c | 11 +++++++++++ wocky/wocky-jingle-transport-iface.h | 3 +++ 4 files changed, 53 insertions(+) diff --git a/wocky/wocky-jingle-content.c b/wocky/wocky-jingle-content.c index 1874fed..996d03c 100644 --- a/wocky/wocky-jingle-content.c +++ b/wocky/wocky-jingle-content.c @@ -1423,3 +1423,16 @@ wocky_jingle_content_request_receiving (WockyJingleContent *self, else wocky_jingle_content_change_direction (self, senders); } + +/** + * wocky_jingle_content_finish_initial_candidates: + * @self: the content + * + * Perform actions after all initial candidates have been sent. + */ +void +wocky_jingle_content_finish_initial_candidates (WockyJingleContent *self) +{ + wocky_jingle_transport_iface_finish_initial_candidates ( + self->priv->transport); +} diff --git a/wocky/wocky-jingle-transport-iceudp.c b/wocky/wocky-jingle-transport-iceudp.c index ab4e0ef..02b25c6 100644 --- a/wocky/wocky-jingle-transport-iceudp.c +++ b/wocky/wocky-jingle-transport-iceudp.c @@ -83,6 +83,8 @@ struct _WockyJingleTransportIceUdpPrivate int id_sequence; gboolean dispose_has_run; + gboolean finish_has_run; + gboolean can_send; }; static void @@ -95,6 +97,8 @@ wocky_jingle_transport_iceudp_init (WockyJingleTransportIceUdp *obj) priv->id_sequence = 1; priv->dispose_has_run = FALSE; + priv->finish_has_run = FALSE; + priv->can_send = FALSE; } static void @@ -424,6 +428,11 @@ inject_candidates (WockyJingleTransportIface *obj, WockyJingleTransportIceUdpPrivate *priv = self->priv; const gchar *username = NULL; + priv->can_send = TRUE; + + if (!priv->finish_has_run) + return; + for (; priv->pending_candidates != NULL; priv->pending_candidates = priv->pending_candidates->next) { @@ -506,6 +515,11 @@ send_candidates (WockyJingleTransportIface *iface, WockyJingleTransportIceUdp *self = WOCKY_JINGLE_TRANSPORT_ICEUDP (iface); WockyJingleTransportIceUdpPrivate *priv = self->priv; + priv->can_send = TRUE; + + if (!priv->finish_has_run) + return; + while (priv->pending_candidates != NULL) { WockyNode *trans_node, *sess_node; @@ -527,6 +541,17 @@ send_candidates (WockyJingleTransportIface *iface, DEBUG ("sent all pending candidates"); } +static void +finish_initial_candidates (WockyJingleTransportIface *iface) +{ + WockyJingleTransportIceUdp *self = WOCKY_JINGLE_TRANSPORT_ICEUDP (iface); + WockyJingleTransportIceUdpPrivate *priv = self->priv; + + priv->finish_has_run = TRUE; + if (priv->can_send) + send_candidates (iface, TRUE); +} + /* Takes in a list of slice-allocated WockyJingleCandidate structs */ static void new_local_candidates (WockyJingleTransportIface *obj, GList *new_candidates) @@ -606,6 +631,7 @@ transport_iface_init (gpointer g_iface, gpointer iface_data) klass->get_local_candidates = get_local_candidates; klass->get_transport_type = get_transport_type; klass->get_credentials = get_credentials; + klass->finish_initial_candidates = finish_initial_candidates; } void diff --git a/wocky/wocky-jingle-transport-iface.c b/wocky/wocky-jingle-transport-iface.c index 63a9339..65d8efe 100644 --- a/wocky/wocky-jingle-transport-iface.c +++ b/wocky/wocky-jingle-transport-iface.c @@ -159,6 +159,17 @@ wocky_jingle_transport_iface_get_transport_type (WockyJingleTransportIface *self return virtual_method (); } +void +wocky_jingle_transport_iface_finish_initial_candidates ( + WockyJingleTransportIface *self) +{ + void (*virtual_method) (WockyJingleTransportIface *) = + WOCKY_JINGLE_TRANSPORT_IFACE_GET_CLASS (self)->finish_initial_candidates; + + if (virtual_method != NULL) + virtual_method (self); +} + static void wocky_jingle_transport_iface_base_init (gpointer klass) { diff --git a/wocky/wocky-jingle-transport-iface.h b/wocky/wocky-jingle-transport-iface.h index 2b47d01..8e0967c 100644 --- a/wocky/wocky-jingle-transport-iface.h +++ b/wocky/wocky-jingle-transport-iface.h @@ -58,6 +58,7 @@ struct _WockyJingleTransportIfaceClass { gchar **ufrag, gchar **pwd); WockyJingleTransportType (*get_transport_type) (void); + void (*finish_initial_candidates) (WockyJingleTransportIface *); }; GType wocky_jingle_transport_iface_get_type (void); @@ -93,6 +94,8 @@ GList *wocky_jingle_transport_iface_get_local_candidates (WockyJingleTransportIf WockyJingleTransportType wocky_jingle_transport_iface_get_transport_type (WockyJingleTransportIface *); gboolean jingle_transport_get_credentials (WockyJingleTransportIface *, gchar **ufrag, gchar **pwd); +void wocky_jingle_transport_iface_finish_initial_candidates ( + WockyJingleTransportIface *); WockyJingleTransportIface *wocky_jingle_transport_iface_new ( GType type, WockyJingleContent *content, const gchar *transport_ns); -- 2.5.0