[Telepathy-commits] [telepathy-sofiasip/text-fixes] Tightened up the code for call channel group membership changes
Mikhail Zabaluev
mikhail.zabaluev at nokia.com
Thu Oct 16 04:54:51 PDT 2008
The actual changes and emissions are now concentrated in the callback
for protocol session state changes, plus the cases when a call termination
reason and text is obtained from the protocol messages.
---
src/sip-media-channel.c | 228 +++++++++++++++++++----------------------------
1 files changed, 92 insertions(+), 136 deletions(-)
diff --git a/src/sip-media-channel.c b/src/sip-media-channel.c
index f80b8e1..6ab861d 100644
--- a/src/sip-media-channel.c
+++ b/src/sip-media-channel.c
@@ -49,7 +49,6 @@ static void channel_iface_init (gpointer, gpointer);
static void media_signalling_iface_init (gpointer, gpointer);
static void streamed_media_iface_init (gpointer, gpointer);
static void dtmf_iface_init (gpointer, gpointer);
-static void priv_group_mixin_iface_init (gpointer, gpointer);
static void call_state_iface_init (gpointer, gpointer);
static void hold_iface_init (gpointer, gpointer);
@@ -62,7 +61,7 @@ G_DEFINE_TYPE_WITH_CODE (TpsipMediaChannel, tpsip_media_channel,
tp_properties_mixin_iface_init);
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_CHANNEL, channel_iface_init);
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_CHANNEL_INTERFACE_GROUP,
- priv_group_mixin_iface_init);
+ tp_group_mixin_iface_init);
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_CHANNEL_INTERFACE_MEDIA_SIGNALLING,
media_signalling_iface_init);
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_CHANNEL_INTERFACE_DTMF,
@@ -858,44 +857,16 @@ tpsip_media_channel_receive_invite (TpsipMediaChannel *self,
{
TpsipMediaChannelPrivate *priv = TPSIP_MEDIA_CHANNEL_GET_PRIVATE (self);
TpBaseConnection *conn = TP_BASE_CONNECTION (priv->conn);
- TpHandleRepoIface *contact_repo;
- TpIntSet *pending_set;
g_assert (priv->creator != conn->self_handle);
+ g_assert (priv->session == NULL);
- contact_repo = tp_base_connection_get_handles (conn, TP_HANDLE_TYPE_CONTACT);
-
- if (priv->session == NULL)
- {
- /* note: start the local stream-engine; once the local
- * media are ready, reply with nua_respond() */
- priv_create_session (self, nh, priv->creator);
- g_assert (priv->session != NULL);
- tpsip_media_session_receive_invite (priv->session);
- }
- else
- /* FIXME: This shall really be an assertion */
- g_warning ("session already exists");
-
- /* add self_handle to local pending */
-
- pending_set = tp_intset_new ();
- tp_intset_add (pending_set, conn->self_handle);
-
- tp_group_mixin_change_members ((GObject *) self, "INVITE received",
- NULL, /* add */
- NULL, /* remove */
- pending_set, /* local pending */
- NULL, /* remote pending */
- priv->creator, /* actor */
- TP_CHANNEL_GROUP_CHANGE_REASON_INVITED);
-
- tp_intset_destroy (pending_set);
+ /* Start the local stream-engine; once the local
+ * media are ready, reply with nua_respond() */
+ priv_create_session (self, nh, priv->creator);
- /* No adding more members to the incoming call, removing is OK */
- tp_group_mixin_change_flags ((GObject *) self,
- TP_CHANNEL_GROUP_FLAG_CAN_REMOVE,
- TP_CHANNEL_GROUP_FLAG_CAN_ADD);
+ g_assert (priv->session != NULL);
+ tpsip_media_session_receive_invite (priv->session);
}
static gboolean
@@ -921,6 +892,7 @@ tpsip_media_channel_peer_error (TpsipMediaChannel *self,
guint status,
const char* message)
{
+ TpGroupMixin *mixin = TP_GROUP_MIXIN (self);
TpIntSet *set;
guint reason = TP_CHANNEL_GROUP_CHANGE_REASON_ERROR;
@@ -957,6 +929,7 @@ tpsip_media_channel_peer_error (TpsipMediaChannel *self,
set = tp_intset_new ();
tp_intset_add (set, peer);
+ tp_intset_add (set, mixin->self_handle);
tp_group_mixin_change_members ((GObject *)self, message,
NULL, set, NULL, NULL, peer, reason);
tp_intset_destroy (set);
@@ -1042,7 +1015,7 @@ priv_nua_i_cancel_cb (TpsipMediaChannel *self,
}
if (message == NULL || !g_utf8_validate (message, -1, NULL))
- message = "Cancelled";
+ message = "";
set = tp_intset_new ();
tp_intset_add (set, peer);
@@ -1157,11 +1130,13 @@ static void priv_session_state_changed_cb (TpsipMediaSession *session,
{
TpsipMediaChannelPrivate *priv = TPSIP_MEDIA_CHANNEL_GET_PRIVATE (channel);
TpGroupMixin *mixin = TP_GROUP_MIXIN (channel);
+ TpHandle self_handle;
TpHandle peer;
TpIntSet *set = NULL;
DEBUG("enter");
+ self_handle = mixin->self_handle;
peer = tpsip_media_session_get_peer (session);
switch (state)
@@ -1169,57 +1144,95 @@ static void priv_session_state_changed_cb (TpsipMediaSession *session,
case TPSIP_MEDIA_SESSION_STATE_INVITE_SENT:
set = tp_intset_new ();
- g_assert (priv->creator == mixin->self_handle);
+ g_assert (priv->creator == self_handle);
/* add the peer to remote pending */
tp_intset_add (set, peer);
tp_group_mixin_change_members ((GObject *)channel,
- "INVITE sent",
+ "",
NULL, /* add */
NULL, /* remove */
NULL, /* local pending */
set, /* remote pending */
- mixin->self_handle, /* actor */
+ self_handle, /* actor */
TP_CHANNEL_GROUP_CHANGE_REASON_INVITED);
- /* update flags: allow adding, removal and rescinding */
+ /* update flags: allow removal and rescinding, no more adding */
tp_group_mixin_change_flags ((GObject *)channel,
- TP_CHANNEL_GROUP_FLAG_CAN_ADD
- | TP_CHANNEL_GROUP_FLAG_CAN_REMOVE
- | TP_CHANNEL_GROUP_FLAG_CAN_RESCIND,
- 0);
+ TP_CHANNEL_GROUP_FLAG_CAN_REMOVE | TP_CHANNEL_GROUP_FLAG_CAN_RESCIND,
+ TP_CHANNEL_GROUP_FLAG_CAN_ADD);
+
+ break;
+
+ case TPSIP_MEDIA_SESSION_STATE_INVITE_RECEIVED:
+ set = tp_intset_new ();
+
+ /* add ourself to local pending */
+ tp_intset_add (set, self_handle);
+ tp_group_mixin_change_members ((GObject *) channel, "",
+ NULL, /* add */
+ NULL, /* remove */
+ set, /* local pending */
+ NULL, /* remote pending */
+ priv->creator, /* actor */
+ TP_CHANNEL_GROUP_CHANGE_REASON_INVITED);
+
+ /* No adding more members to the incoming call, removing is OK */
+ tp_group_mixin_change_flags ((GObject *) channel,
+ TP_CHANNEL_GROUP_FLAG_CAN_REMOVE,
+ TP_CHANNEL_GROUP_FLAG_CAN_ADD);
break;
+
case TPSIP_MEDIA_SESSION_STATE_ACTIVE:
- if (priv->creator == mixin->self_handle)
+ if (priv->creator == self_handle)
{
- /* add the peer to the member list */
+ if (!tp_handle_set_is_member (mixin->remote_pending, peer))
+ break; /* no-op */
+
set = tp_intset_new ();
+ /* the peer has promoted itself to members */
tp_intset_add (set, peer);
- tp_group_mixin_change_members ((GObject *)channel,
- "Call active",
+ tp_group_mixin_change_members ((GObject *)channel, "",
set, /* add */
NULL, /* remove */
NULL,
NULL,
- 0, 0);
+ peer, 0);
+ }
+ else
+ {
+ if (!tp_handle_set_is_member (mixin->local_pending, self_handle))
+ break; /* no-op */
- /* update flags: allow removal, deny adding and rescinding */
- tp_group_mixin_change_flags ((GObject *)channel,
- TP_CHANNEL_GROUP_FLAG_CAN_REMOVE,
- TP_CHANNEL_GROUP_FLAG_CAN_ADD
- | TP_CHANNEL_GROUP_FLAG_CAN_RESCIND);
+ set = tp_intset_new ();
+
+ /* promote ourselves to members */
+ tp_intset_add (set, self_handle);
+ tp_group_mixin_change_members ((GObject *)channel, "",
+ set, /* add */
+ NULL, /* remove */
+ NULL,
+ NULL,
+ self_handle, 0);
}
+
+ /* update flags: allow removal, deny adding and rescinding */
+ tp_group_mixin_change_flags ((GObject *)channel,
+ TP_CHANNEL_GROUP_FLAG_CAN_REMOVE,
+ TP_CHANNEL_GROUP_FLAG_CAN_ADD
+ | TP_CHANNEL_GROUP_FLAG_CAN_RESCIND);
+
break;
+
case TPSIP_MEDIA_SESSION_STATE_ENDED:
set = tp_intset_new ();
/* remove us and the peer from the member list */
- tp_intset_add (set, mixin->self_handle);
+ tp_intset_add (set, self_handle);
tp_intset_add (set, peer);
- tp_group_mixin_change_members ((GObject *)channel,
- "Call ended",
+ tp_group_mixin_change_members ((GObject *)channel, "",
NULL, /* add */
set, /* remove */
NULL,
@@ -1394,26 +1407,11 @@ tpsip_media_channel_add_member (GObject *iface,
if (priv->creator == mixin->self_handle)
{
/* case a: outgoing call (we are the initiator, a new handle added) */
- TpIntSet *set;
-
priv_outbound_call (self, handle);
- /* make remote pending */
- set = tp_intset_new ();
- tp_intset_add (set, handle);
- tp_group_mixin_change_members (iface, "Sending INVITE",
- NULL, /* add */
- NULL, /* remove */
- NULL, /* local pending */
- set, /* remote pending */
- mixin->self_handle, 0);
- tp_intset_destroy (set);
-
- /* and update flags accordingly */
- tp_group_mixin_change_flags (iface,
- TP_CHANNEL_GROUP_FLAG_CAN_ADD | TP_CHANNEL_GROUP_FLAG_CAN_REMOVE |
- TP_CHANNEL_GROUP_FLAG_CAN_RESCIND,
- 0);
+ /* disallow addition of any new members */
+ tp_group_mixin_change_flags ((GObject *) self,
+ 0, TP_CHANNEL_GROUP_FLAG_CAN_ADD);
return TRUE;
}
@@ -1422,22 +1420,9 @@ tpsip_media_channel_add_member (GObject *iface,
tp_handle_set_is_member (mixin->local_pending, handle))
{
/* case b: an incoming invite */
- TpIntSet *set;
-
DEBUG("accepting an incoming invite");
-
g_return_val_if_fail (priv->session != NULL, FALSE);
- set = tp_intset_new ();
- tp_intset_add (set, handle);
- tp_group_mixin_change_members (iface, "Incoming call accepted",
- set, /* add */
- NULL, /* remove */
- NULL, /* local pending */
- NULL, /* remote pending */
- 0, 0);
- tp_intset_destroy (set);
-
tpsip_media_session_accept (priv->session);
return TRUE;
@@ -1493,46 +1478,33 @@ tpsip_media_channel_remove_with_reason (GObject *obj,
return FALSE;
}
- /* We handle only one case: removal of the self handle from local pending
- * due to the user rejecting the call */
- /* FIXME: handle also rescinding and removal of self from members */
- if (priv->session &&
- handle == mixin->self_handle &&
- tp_handle_set_is_member (mixin->local_pending, handle))
+ if (priv->session == NULL)
{
- TpIntSet *set;
+ g_set_error (error, TP_ERRORS, TP_ERROR_NOT_AVAILABLE,
+ "handle %u cannot be removed in the current state", handle);
+
+ return FALSE;
+ }
+
+ if (handle == mixin->self_handle
+ && tp_handle_set_is_member (mixin->local_pending, handle))
+ {
+ /* The user has rejected the call */
gint status;
status = tpsip_status_from_tp_reason (reason);
/* XXX: raise NotAvailable if it's the wrong state? */
tpsip_media_session_respond (priv->session, status, message);
-
- set = tp_intset_new ();
- tp_intset_add (set, handle);
- tp_group_mixin_change_members (obj,
- message,
- NULL, /* add */
- set, /* remove */
- NULL, /* add local pending */
- NULL, /* add remote pending */
- 0, /* actor */
- reason);
- tp_intset_destroy (set);
-
- /* no more adding to this channel */
- tp_group_mixin_change_flags (obj,
- 0,
- TP_CHANNEL_GROUP_FLAG_CAN_ADD);
-
- return TRUE;
+ }
+ else
+ {
+ /* Want to terminate the call in whatever other situation;
+ * rescinding is handled by sending CANCEL */
+ tpsip_media_session_terminate (priv->session);
}
- g_assert_not_reached();
-
- g_set_error (error, TP_ERRORS, TP_ERROR_NOT_IMPLEMENTED,
- "Can't map this member change to protocol behavior");
- return FALSE;
+ return TRUE;
}
static void
@@ -1719,22 +1691,6 @@ dtmf_iface_init (gpointer g_iface, gpointer iface_data)
}
static void
-priv_group_mixin_iface_init (gpointer g_iface, gpointer iface_data)
-{
-#if 0
- TpSvcChannelInterfaceGroupClass *klass =
- (TpSvcChannelInterfaceGroupClass *)g_iface;
-#endif
-
- tp_group_mixin_iface_init (g_iface, iface_data);
-
-#if 0
- tp_svc_channel_interface_group_implement_add_members (klass,
- priv_add_members);
-#endif
-}
-
-static void
call_state_iface_init (gpointer g_iface,
gpointer iface_data)
{
--
1.5.6.5
More information about the Telepathy-commits
mailing list