Mercurial > pidgin
comparison libpurple/media/backend-fs2.c @ 32766:fd1b4bbefc6b
Port to Farstream
Farstream is the new name of Farsight.
The changes to support Farstream are from ocrete. rlaager modified the
patch to retain the Farsight code using #ifdef HAVE_FARSIGHT.
committer: Richard Laager <rlaager@wiktel.com>
author | olivier.crete@collabora.com |
---|---|
date | Thu, 05 Apr 2012 03:18:40 +0000 |
parents | 60bd913072f7 |
children | cb2084b4a463 |
comparison
equal
deleted
inserted
replaced
32765:60bd913072f7 | 32766:fd1b4bbefc6b |
---|---|
1 /** | 1 /** |
2 * @file backend-fs2.c Farsight 2 backend for media API | 2 * @file backend-fs2.c Farstream backend for media API |
3 * @ingroup core | 3 * @ingroup core |
4 */ | 4 */ |
5 | 5 |
6 /* purple | 6 /* purple |
7 * | 7 * |
32 #include "backend-iface.h" | 32 #include "backend-iface.h" |
33 #include "debug.h" | 33 #include "debug.h" |
34 #include "network.h" | 34 #include "network.h" |
35 #include "media-gst.h" | 35 #include "media-gst.h" |
36 | 36 |
37 #ifdef HAVE_FARSIGHT | |
37 #include <gst/farsight/fs-conference-iface.h> | 38 #include <gst/farsight/fs-conference-iface.h> |
38 #include <gst/farsight/fs-element-added-notifier.h> | 39 #include <gst/farsight/fs-element-added-notifier.h> |
40 #else | |
41 #include <farstream/fs-conference.h> | |
42 #include <farstream/fs-element-added-notifier.h> | |
43 #include <farstream/fs-utils.h> | |
44 #endif | |
39 | 45 |
40 /** @copydoc _PurpleMediaBackendFs2Class */ | 46 /** @copydoc _PurpleMediaBackendFs2Class */ |
41 typedef struct _PurpleMediaBackendFs2Class PurpleMediaBackendFs2Class; | 47 typedef struct _PurpleMediaBackendFs2Class PurpleMediaBackendFs2Class; |
42 /** @copydoc _PurpleMediaBackendFs2Private */ | 48 /** @copydoc _PurpleMediaBackendFs2Private */ |
43 typedef struct _PurpleMediaBackendFs2Private PurpleMediaBackendFs2Private; | 49 typedef struct _PurpleMediaBackendFs2Private PurpleMediaBackendFs2Private; |
110 { | 116 { |
111 PurpleMediaBackendFs2Session *session; | 117 PurpleMediaBackendFs2Session *session; |
112 gchar *participant; | 118 gchar *participant; |
113 FsStream *stream; | 119 FsStream *stream; |
114 | 120 |
121 #ifndef HAVE_FARSIGHT | |
122 gboolean supports_add; | |
123 #endif | |
124 | |
115 GstElement *src; | 125 GstElement *src; |
116 GstElement *tee; | 126 GstElement *tee; |
117 GstElement *volume; | 127 GstElement *volume; |
118 GstElement *level; | 128 GstElement *level; |
119 GstElement *fakesink; | 129 GstElement *fakesink; |
145 PurpleMedia *media; | 155 PurpleMedia *media; |
146 GstElement *confbin; | 156 GstElement *confbin; |
147 FsConference *conference; | 157 FsConference *conference; |
148 gchar *conference_type; | 158 gchar *conference_type; |
149 | 159 |
160 #ifndef HAVE_FARSIGHT | |
161 FsElementAddedNotifier *notifier; | |
162 #endif | |
163 | |
150 GHashTable *sessions; | 164 GHashTable *sessions; |
151 GHashTable *participants; | 165 GHashTable *participants; |
152 | 166 |
153 GList *streams; | 167 GList *streams; |
154 | 168 |
209 PurpleMediaBackendFs2Private *priv = | 223 PurpleMediaBackendFs2Private *priv = |
210 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(obj); | 224 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(obj); |
211 GList *iter = NULL; | 225 GList *iter = NULL; |
212 | 226 |
213 purple_debug_info("backend-fs2", "purple_media_backend_fs2_dispose\n"); | 227 purple_debug_info("backend-fs2", "purple_media_backend_fs2_dispose\n"); |
228 | |
229 #ifndef HAVE_FARSIGHT | |
230 if (priv->notifier) { | |
231 g_object_unref(priv->notifier); | |
232 priv->notifier = NULL; | |
233 } | |
234 #endif | |
214 | 235 |
215 if (priv->confbin) { | 236 if (priv->confbin) { |
216 GstElement *pipeline; | 237 GstElement *pipeline; |
217 | 238 |
218 pipeline = purple_media_manager_get_pipeline( | 239 pipeline = purple_media_manager_get_pipeline( |
844 | 865 |
845 if (!FS_IS_CONFERENCE(src) || !PURPLE_IS_MEDIA_BACKEND(self) || | 866 if (!FS_IS_CONFERENCE(src) || !PURPLE_IS_MEDIA_BACKEND(self) || |
846 priv->conference != FS_CONFERENCE(src)) | 867 priv->conference != FS_CONFERENCE(src)) |
847 return; | 868 return; |
848 | 869 |
870 #ifdef HAVE_FARSIGHT | |
849 if (gst_structure_has_name(msg->structure, "farsight-error")) { | 871 if (gst_structure_has_name(msg->structure, "farsight-error")) { |
872 #else | |
873 if (gst_structure_has_name(msg->structure, "farstream-error")) { | |
874 #endif | |
850 FsError error_no; | 875 FsError error_no; |
851 gst_structure_get_enum(msg->structure, "error-no", | 876 gst_structure_get_enum(msg->structure, "error-no", |
852 FS_TYPE_ERROR, (gint*)&error_no); | 877 FS_TYPE_ERROR, (gint*)&error_no); |
853 switch (error_no) { | 878 switch (error_no) { |
854 case FS_ERROR_NO_CODECS: | 879 case FS_ERROR_NO_CODECS: |
857 " GStreamer codecs found" | 882 " GStreamer codecs found" |
858 " in GStreamer plugins" | 883 " in GStreamer plugins" |
859 " packages.")); | 884 " packages.")); |
860 purple_media_end(priv->media, NULL, NULL); | 885 purple_media_end(priv->media, NULL, NULL); |
861 break; | 886 break; |
887 #ifdef HAVE_FARSIGHT | |
862 case FS_ERROR_NO_CODECS_LEFT: | 888 case FS_ERROR_NO_CODECS_LEFT: |
863 purple_media_error(priv->media, _("No codecs" | 889 purple_media_error(priv->media, _("No codecs" |
864 " left. Your codec" | 890 " left. Your codec" |
865 " preferences in" | 891 " preferences in" |
866 " fs-codecs.conf are too" | 892 " fs-codecs.conf are too" |
872 * Unknown CName is only a problem for the | 898 * Unknown CName is only a problem for the |
873 * multicast transmitter which isn't used. | 899 * multicast transmitter which isn't used. |
874 * It is also deprecated. | 900 * It is also deprecated. |
875 */ | 901 */ |
876 break; | 902 break; |
903 #endif | |
877 default: | 904 default: |
878 purple_debug_error("backend-fs2", | 905 purple_debug_error("backend-fs2", |
906 #ifdef HAVE_FARSIGHT | |
879 "farsight-error: %i: %s\n", | 907 "farsight-error: %i: %s\n", |
908 #else | |
909 "farstream-error: %i: %s\n", | |
910 #endif | |
880 error_no, | 911 error_no, |
881 gst_structure_get_string( | 912 gst_structure_get_string( |
882 msg->structure, "error-msg")); | 913 msg->structure, "error-msg")); |
883 break; | 914 break; |
884 } | 915 } |
885 | 916 |
886 if (FS_ERROR_IS_FATAL(error_no)) { | 917 if (FS_ERROR_IS_FATAL(error_no)) { |
918 #ifdef HAVE_FARSIGHT | |
887 purple_media_error(priv->media, _("A non-recoverable " | 919 purple_media_error(priv->media, _("A non-recoverable " |
888 "Farsight2 error has occurred.")); | 920 "Farsight2 error has occurred.")); |
921 #else | |
922 purple_media_error(priv->media, _("A non-recoverable " | |
923 "Farstream error has occurred.")); | |
924 #endif | |
889 purple_media_end(priv->media, NULL, NULL); | 925 purple_media_end(priv->media, NULL, NULL); |
890 } | 926 } |
891 } else if (gst_structure_has_name(msg->structure, | 927 } else if (gst_structure_has_name(msg->structure, |
928 #ifdef HAVE_FARSIGHT | |
892 "farsight-new-local-candidate")) { | 929 "farsight-new-local-candidate")) { |
930 #else | |
931 "farstream-new-local-candidate")) { | |
932 #endif | |
893 const GValue *value; | 933 const GValue *value; |
894 FsStream *stream; | 934 FsStream *stream; |
895 FsCandidate *local_candidate; | 935 FsCandidate *local_candidate; |
896 PurpleMediaCandidate *candidate; | 936 PurpleMediaCandidate *candidate; |
897 FsParticipant *participant; | 937 FsParticipant *participant; |
922 candidate = candidate_from_fs(local_candidate); | 962 candidate = candidate_from_fs(local_candidate); |
923 g_signal_emit_by_name(self, "new-candidate", | 963 g_signal_emit_by_name(self, "new-candidate", |
924 session->id, name, candidate); | 964 session->id, name, candidate); |
925 g_object_unref(candidate); | 965 g_object_unref(candidate); |
926 } else if (gst_structure_has_name(msg->structure, | 966 } else if (gst_structure_has_name(msg->structure, |
967 #ifdef HAVE_FARSIGHT | |
927 "farsight-local-candidates-prepared")) { | 968 "farsight-local-candidates-prepared")) { |
969 #else | |
970 "farstream-local-candidates-prepared")) { | |
971 #endif | |
928 const GValue *value; | 972 const GValue *value; |
929 FsStream *stream; | 973 FsStream *stream; |
930 FsParticipant *participant; | 974 FsParticipant *participant; |
931 PurpleMediaBackendFs2Session *session; | 975 PurpleMediaBackendFs2Session *session; |
932 gchar *name; | 976 gchar *name; |
940 g_object_unref(participant); | 984 g_object_unref(participant); |
941 | 985 |
942 g_signal_emit_by_name(self, "candidates-prepared", | 986 g_signal_emit_by_name(self, "candidates-prepared", |
943 session->id, name); | 987 session->id, name); |
944 } else if (gst_structure_has_name(msg->structure, | 988 } else if (gst_structure_has_name(msg->structure, |
989 #ifdef HAVE_FARSIGHT | |
945 "farsight-new-active-candidate-pair")) { | 990 "farsight-new-active-candidate-pair")) { |
991 #else | |
992 "farstream-new-active-candidate-pair")) { | |
993 #endif | |
946 const GValue *value; | 994 const GValue *value; |
947 FsStream *stream; | 995 FsStream *stream; |
948 FsCandidate *local_candidate; | 996 FsCandidate *local_candidate; |
949 FsCandidate *remote_candidate; | 997 FsCandidate *remote_candidate; |
950 FsParticipant *participant; | 998 FsParticipant *participant; |
974 session->id, name, lcandidate, rcandidate); | 1022 session->id, name, lcandidate, rcandidate); |
975 | 1023 |
976 g_object_unref(lcandidate); | 1024 g_object_unref(lcandidate); |
977 g_object_unref(rcandidate); | 1025 g_object_unref(rcandidate); |
978 } else if (gst_structure_has_name(msg->structure, | 1026 } else if (gst_structure_has_name(msg->structure, |
1027 #ifdef HAVE_FARSIGHT | |
979 "farsight-recv-codecs-changed")) { | 1028 "farsight-recv-codecs-changed")) { |
1029 #else | |
1030 "farstream-recv-codecs-changed")) { | |
1031 #endif | |
980 const GValue *value; | 1032 const GValue *value; |
981 GList *codecs; | 1033 GList *codecs; |
982 FsCodec *codec; | 1034 FsCodec *codec; |
983 | 1035 |
984 value = gst_structure_get_value(msg->structure, "codecs"); | 1036 value = gst_structure_get_value(msg->structure, "codecs"); |
985 codecs = g_value_get_boxed(value); | 1037 codecs = g_value_get_boxed(value); |
986 codec = codecs->data; | 1038 codec = codecs->data; |
987 | 1039 |
988 purple_debug_info("backend-fs2", | 1040 purple_debug_info("backend-fs2", |
1041 #ifdef HAVE_FARSIGHT | |
989 "farsight-recv-codecs-changed: %s\n", | 1042 "farsight-recv-codecs-changed: %s\n", |
1043 #else | |
1044 "farstream-recv-codecs-changed: %s\n", | |
1045 #endif | |
990 codec->encoding_name); | 1046 codec->encoding_name); |
991 } else if (gst_structure_has_name(msg->structure, | 1047 } else if (gst_structure_has_name(msg->structure, |
1048 #ifdef HAVE_FARSIGHT | |
992 "farsight-component-state-changed")) { | 1049 "farsight-component-state-changed")) { |
1050 #else | |
1051 "farstream-component-state-changed")) { | |
1052 #endif | |
993 const GValue *value; | 1053 const GValue *value; |
994 FsStreamState fsstate; | 1054 FsStreamState fsstate; |
995 guint component; | 1055 guint component; |
996 const gchar *state; | 1056 const gchar *state; |
997 | 1057 |
1023 state = "UNKNOWN"; | 1083 state = "UNKNOWN"; |
1024 break; | 1084 break; |
1025 } | 1085 } |
1026 | 1086 |
1027 purple_debug_info("backend-fs2", | 1087 purple_debug_info("backend-fs2", |
1088 #ifdef HAVE_FARSIGHT | |
1028 "farsight-component-state-changed: " | 1089 "farsight-component-state-changed: " |
1090 #else | |
1091 "farstream-component-state-changed: " | |
1092 #endif | |
1029 "component: %u state: %s\n", | 1093 "component: %u state: %s\n", |
1030 component, state); | 1094 component, state); |
1031 } else if (gst_structure_has_name(msg->structure, | 1095 } else if (gst_structure_has_name(msg->structure, |
1096 #ifdef HAVE_FARSIGHT | |
1032 "farsight-send-codec-changed")) { | 1097 "farsight-send-codec-changed")) { |
1098 #else | |
1099 "farstream-send-codec-changed")) { | |
1100 #endif | |
1033 const GValue *value; | 1101 const GValue *value; |
1034 FsCodec *codec; | 1102 FsCodec *codec; |
1035 gchar *codec_str; | 1103 gchar *codec_str; |
1036 | 1104 |
1037 value = gst_structure_get_value(msg->structure, "codec"); | 1105 value = gst_structure_get_value(msg->structure, "codec"); |
1038 codec = g_value_get_boxed(value); | 1106 codec = g_value_get_boxed(value); |
1039 codec_str = fs_codec_to_string(codec); | 1107 codec_str = fs_codec_to_string(codec); |
1040 | 1108 |
1041 purple_debug_info("backend-fs2", | 1109 purple_debug_info("backend-fs2", |
1110 #ifdef HAVE_FARSIGHT | |
1042 "farsight-send-codec-changed: codec: %s\n", | 1111 "farsight-send-codec-changed: codec: %s\n", |
1112 #else | |
1113 "farstream-send-codec-changed: codec: %s\n", | |
1114 #endif | |
1043 codec_str); | 1115 codec_str); |
1044 | 1116 |
1045 g_free(codec_str); | 1117 g_free(codec_str); |
1046 } else if (gst_structure_has_name(msg->structure, | 1118 } else if (gst_structure_has_name(msg->structure, |
1119 #ifdef HAVE_FARSIGHT | |
1047 "farsight-codecs-changed")) { | 1120 "farsight-codecs-changed")) { |
1121 #else | |
1122 "farstream-codecs-changed")) { | |
1123 #endif | |
1048 const GValue *value; | 1124 const GValue *value; |
1049 FsSession *fssession; | 1125 FsSession *fssession; |
1050 GList *sessions; | 1126 GList *sessions; |
1051 | 1127 |
1052 value = gst_structure_get_value(msg->structure, "session"); | 1128 value = gst_structure_get_value(msg->structure, "session"); |
1218 | 1294 |
1219 if (stream->remote_candidates == NULL || | 1295 if (stream->remote_candidates == NULL || |
1220 purple_media_is_initiator(media, sid, name)) | 1296 purple_media_is_initiator(media, sid, name)) |
1221 return; | 1297 return; |
1222 | 1298 |
1299 #ifdef HAVE_FARSIGHT | |
1223 fs_stream_set_remote_candidates(stream->stream, | 1300 fs_stream_set_remote_candidates(stream->stream, |
1224 stream->remote_candidates, &err); | 1301 stream->remote_candidates, &err); |
1302 #else | |
1303 if (stream->supports_add) | |
1304 fs_stream_add_remote_candidates(stream->stream, | |
1305 stream->remote_candidates, &err); | |
1306 else | |
1307 fs_stream_force_remote_candidates(stream->stream, | |
1308 stream->remote_candidates, &err); | |
1309 #endif | |
1225 | 1310 |
1226 if (err == NULL) | 1311 if (err == NULL) |
1227 return; | 1312 return; |
1228 | 1313 |
1229 purple_debug_error("backend-fs2", "Error adding " | 1314 purple_debug_error("backend-fs2", "Error adding " |
1299 PurpleMediaBackendFs2Private *priv = | 1384 PurpleMediaBackendFs2Private *priv = |
1300 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(self); | 1385 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(self); |
1301 GstElement *pipeline; | 1386 GstElement *pipeline; |
1302 GstBus *bus; | 1387 GstBus *bus; |
1303 gchar *name; | 1388 gchar *name; |
1389 #ifndef HAVE_FARSIGHT | |
1390 GKeyFile *default_props; | |
1391 #endif | |
1304 | 1392 |
1305 priv->conference = FS_CONFERENCE( | 1393 priv->conference = FS_CONFERENCE( |
1306 gst_element_factory_make(priv->conference_type, NULL)); | 1394 gst_element_factory_make(priv->conference_type, NULL)); |
1307 | 1395 |
1308 if (priv->conference == NULL) { | 1396 if (priv->conference == NULL) { |
1340 if (bus == NULL) { | 1428 if (bus == NULL) { |
1341 purple_debug_error("backend-fs2", | 1429 purple_debug_error("backend-fs2", |
1342 "Couldn't get the pipeline's bus.\n"); | 1430 "Couldn't get the pipeline's bus.\n"); |
1343 return FALSE; | 1431 return FALSE; |
1344 } | 1432 } |
1433 | |
1434 #ifndef HAVE_FARSIGHT | |
1435 default_props = fs_utils_get_default_element_properties(GST_ELEMENT(priv->conference)); | |
1436 if (default_props != NULL) { | |
1437 priv->notifier = fs_element_added_notifier_new(); | |
1438 fs_element_added_notifier_add(priv->notifier, | |
1439 GST_BIN(priv->confbin)); | |
1440 fs_element_added_notifier_set_properties_from_keyfile(priv->notifier, default_props); | |
1441 } | |
1442 #endif | |
1345 | 1443 |
1346 g_signal_connect(G_OBJECT(bus), "message", | 1444 g_signal_connect(G_OBJECT(bus), "message", |
1347 G_CALLBACK(gst_bus_cb), self); | 1445 G_CALLBACK(gst_bus_cb), self); |
1348 gst_object_unref(bus); | 1446 gst_object_unref(bus); |
1349 | 1447 |
1557 /* | 1655 /* |
1558 * Removes a 5-7 second delay before | 1656 * Removes a 5-7 second delay before |
1559 * receiving the src-pad-added signal. | 1657 * receiving the src-pad-added signal. |
1560 * Only works for non-multicast FsRtpSessions. | 1658 * Only works for non-multicast FsRtpSessions. |
1561 */ | 1659 */ |
1660 #ifdef HAVE_FARSIGHT | |
1562 if (is_nice || !strcmp(transmitter, "rawudp")) | 1661 if (is_nice || !strcmp(transmitter, "rawudp")) |
1662 #else | |
1663 if (!!strcmp(transmitter, "multicast")) | |
1664 #endif | |
1563 g_object_set(G_OBJECT(session->session), | 1665 g_object_set(G_OBJECT(session->session), |
1564 "no-rtcp-timeout", 0, NULL); | 1666 "no-rtcp-timeout", 0, NULL); |
1565 | 1667 |
1566 /* | 1668 /* |
1567 * Hack to make x264 work with Gmail video. | 1669 * Hack to make x264 work with Gmail video. |
1610 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(self); | 1712 PURPLE_MEDIA_BACKEND_FS2_GET_PRIVATE(self); |
1611 FsParticipant *participant; | 1713 FsParticipant *participant; |
1612 GError *err = NULL; | 1714 GError *err = NULL; |
1613 | 1715 |
1614 participant = fs_conference_new_participant( | 1716 participant = fs_conference_new_participant( |
1717 #ifdef HAVE_FARSIGHT | |
1615 priv->conference, name, &err); | 1718 priv->conference, name, &err); |
1719 #else | |
1720 priv->conference, &err); | |
1721 #endif | |
1616 | 1722 |
1617 if (err) { | 1723 if (err) { |
1618 purple_debug_error("backend-fs2", | 1724 purple_debug_error("backend-fs2", |
1619 "Error creating participant: %s\n", | 1725 "Error creating participant: %s\n", |
1620 err->message); | 1726 err->message); |
1621 g_error_free(err); | 1727 g_error_free(err); |
1622 return FALSE; | 1728 return FALSE; |
1623 } | 1729 } |
1730 | |
1731 #ifndef HAVE_FARSIGHT | |
1732 if (g_object_class_find_property(G_OBJECT_GET_CLASS(participant), | |
1733 "cname")) { | |
1734 g_object_set(participant, "cname", name, NULL); | |
1735 } | |
1736 #endif | |
1624 | 1737 |
1625 if (!priv->participants) { | 1738 if (!priv->participants) { |
1626 purple_debug_info("backend-fs2", | 1739 purple_debug_info("backend-fs2", |
1627 "Creating hash table for participants\n"); | 1740 "Creating hash table for participants\n"); |
1628 priv->participants = g_hash_table_new_full(g_str_hash, | 1741 priv->participants = g_hash_table_new_full(g_str_hash, |
1793 purple_debug_error("backend-fs2", "Couldn't find " | 1906 purple_debug_error("backend-fs2", "Couldn't find " |
1794 "participant to create stream.\n"); | 1907 "participant to create stream.\n"); |
1795 return FALSE; | 1908 return FALSE; |
1796 } | 1909 } |
1797 | 1910 |
1798 for (i = 0 ; i < num_params ; i++) { | 1911 #ifndef HAVE_FARSIGHT |
1799 if (purple_strequal(params[i].name, "relay-info")) { | |
1800 got_turn_from_prpl = TRUE; | |
1801 break; | |
1802 } | |
1803 } | |
1804 | |
1805 _params = g_new0(GParameter, num_params + 3); | |
1806 memcpy(_params, params, sizeof(GParameter) * num_params); | |
1807 | |
1808 /* set the controlling mode parameter */ | |
1809 _params[_num_params].name = "controlling-mode"; | |
1810 g_value_init(&_params[_num_params].value, G_TYPE_BOOLEAN); | |
1811 g_value_set_boolean(&_params[_num_params].value, initiator); | |
1812 ++_num_params; | |
1813 | |
1814 if (stun_ip) { | |
1815 purple_debug_info("backend-fs2", | |
1816 "Setting stun-ip on new stream: %s\n", stun_ip); | |
1817 | |
1818 _params[_num_params].name = "stun-ip"; | |
1819 g_value_init(&_params[_num_params].value, G_TYPE_STRING); | |
1820 g_value_set_string(&_params[_num_params].value, stun_ip); | |
1821 ++_num_params; | |
1822 } | |
1823 | |
1824 if (turn_ip && !strcmp("nice", transmitter) && !got_turn_from_prpl) { | |
1825 GValueArray *relay_info = g_value_array_new(0); | |
1826 gint port; | |
1827 const gchar *username = purple_prefs_get_string( | |
1828 "/purple/network/turn_username"); | |
1829 const gchar *password = purple_prefs_get_string( | |
1830 "/purple/network/turn_password"); | |
1831 | |
1832 /* UDP */ | |
1833 port = purple_prefs_get_int("/purple/network/turn_port"); | |
1834 if (port > 0) { | |
1835 relay_info = append_relay_info(relay_info, turn_ip, port, username, | |
1836 password, "udp"); | |
1837 } | |
1838 | |
1839 /* TCP */ | |
1840 port = purple_prefs_get_int("/purple/network/turn_port_tcp"); | |
1841 if (port > 0) { | |
1842 relay_info = append_relay_info(relay_info, turn_ip, port, username, | |
1843 password, "tcp"); | |
1844 } | |
1845 | |
1846 /* TURN over SSL is only supported by libnice for Google's "psuedo" SSL mode | |
1847 at this time */ | |
1848 | |
1849 purple_debug_info("backend-fs2", | |
1850 "Setting relay-info on new stream\n"); | |
1851 _params[_num_params].name = "relay-info"; | |
1852 g_value_init(&_params[_num_params].value, | |
1853 G_TYPE_VALUE_ARRAY); | |
1854 g_value_set_boxed(&_params[_num_params].value, | |
1855 relay_info); | |
1856 g_value_array_free(relay_info); | |
1857 _num_params++; | |
1858 } | |
1859 | |
1860 fsstream = fs_session_new_stream(session->session, participant, | 1912 fsstream = fs_session_new_stream(session->session, participant, |
1861 initiator == TRUE ? type_direction : | 1913 initiator == TRUE ? type_direction : |
1862 (type_direction & FS_DIRECTION_RECV), transmitter, | 1914 (type_direction & FS_DIRECTION_RECV), &err); |
1863 _num_params, _params, &err); | |
1864 g_free(_params); | |
1865 | 1915 |
1866 if (fsstream == NULL) { | 1916 if (fsstream == NULL) { |
1867 if (err) { | 1917 if (err) { |
1868 purple_debug_error("backend-fs2", | 1918 purple_debug_error("backend-fs2", |
1869 "Error creating stream: %s\n", | 1919 "Error creating stream: %s\n", |
1873 } else | 1923 } else |
1874 purple_debug_error("backend-fs2", | 1924 purple_debug_error("backend-fs2", |
1875 "Error creating stream\n"); | 1925 "Error creating stream\n"); |
1876 return FALSE; | 1926 return FALSE; |
1877 } | 1927 } |
1928 #endif | |
1929 | |
1930 for (i = 0 ; i < num_params ; i++) { | |
1931 if (purple_strequal(params[i].name, "relay-info")) { | |
1932 got_turn_from_prpl = TRUE; | |
1933 break; | |
1934 } | |
1935 } | |
1936 | |
1937 _params = g_new0(GParameter, num_params + 3); | |
1938 memcpy(_params, params, sizeof(GParameter) * num_params); | |
1939 | |
1940 /* set the controlling mode parameter */ | |
1941 _params[_num_params].name = "controlling-mode"; | |
1942 g_value_init(&_params[_num_params].value, G_TYPE_BOOLEAN); | |
1943 g_value_set_boolean(&_params[_num_params].value, initiator); | |
1944 ++_num_params; | |
1945 | |
1946 if (stun_ip) { | |
1947 purple_debug_info("backend-fs2", | |
1948 "Setting stun-ip on new stream: %s\n", stun_ip); | |
1949 | |
1950 _params[_num_params].name = "stun-ip"; | |
1951 g_value_init(&_params[_num_params].value, G_TYPE_STRING); | |
1952 g_value_set_string(&_params[_num_params].value, stun_ip); | |
1953 ++_num_params; | |
1954 } | |
1955 | |
1956 if (turn_ip && !strcmp("nice", transmitter) && !got_turn_from_prpl) { | |
1957 GValueArray *relay_info = g_value_array_new(0); | |
1958 gint port; | |
1959 const gchar *username = purple_prefs_get_string( | |
1960 "/purple/network/turn_username"); | |
1961 const gchar *password = purple_prefs_get_string( | |
1962 "/purple/network/turn_password"); | |
1963 | |
1964 /* UDP */ | |
1965 port = purple_prefs_get_int("/purple/network/turn_port"); | |
1966 if (port > 0) { | |
1967 relay_info = append_relay_info(relay_info, turn_ip, port, username, | |
1968 password, "udp"); | |
1969 } | |
1970 | |
1971 /* TCP */ | |
1972 port = purple_prefs_get_int("/purple/network/turn_port_tcp"); | |
1973 if (port > 0) { | |
1974 relay_info = append_relay_info(relay_info, turn_ip, port, username, | |
1975 password, "tcp"); | |
1976 } | |
1977 | |
1978 /* TURN over SSL is only supported by libnice for Google's "psuedo" SSL mode | |
1979 at this time */ | |
1980 | |
1981 purple_debug_info("backend-fs2", | |
1982 "Setting relay-info on new stream\n"); | |
1983 _params[_num_params].name = "relay-info"; | |
1984 g_value_init(&_params[_num_params].value, | |
1985 G_TYPE_VALUE_ARRAY); | |
1986 g_value_set_boxed(&_params[_num_params].value, | |
1987 relay_info); | |
1988 g_value_array_free(relay_info); | |
1989 _num_params++; | |
1990 } | |
1991 | |
1992 #ifdef HAVE_FARSIGHT | |
1993 fsstream = fs_session_new_stream(session->session, participant, | |
1994 initiator == TRUE ? type_direction : | |
1995 (type_direction & FS_DIRECTION_RECV), transmitter, | |
1996 _num_params, _params, &err); | |
1997 g_free(_params); | |
1998 | |
1999 if (fsstream == NULL) { | |
2000 if (err) { | |
2001 purple_debug_error("backend-fs2", | |
2002 "Error creating stream: %s\n", | |
2003 err && err->message ? | |
2004 err->message : "NULL"); | |
2005 g_error_free(err); | |
2006 } else | |
2007 purple_debug_error("backend-fs2", | |
2008 "Error creating stream\n"); | |
2009 return FALSE; | |
2010 } | |
2011 #else | |
2012 if (!fs_stream_set_transmitter(fsstream, transmitter, | |
2013 _params, _num_params, &err)) { | |
2014 purple_debug_error("backend-fs2", | |
2015 "Could not set transmitter %s: %s.\n", | |
2016 transmitter, err->message); | |
2017 g_clear_error(&err); | |
2018 g_free(_params); | |
2019 return FALSE; | |
2020 } | |
2021 g_free(_params); | |
2022 #endif | |
1878 | 2023 |
1879 stream = g_new0(PurpleMediaBackendFs2Stream, 1); | 2024 stream = g_new0(PurpleMediaBackendFs2Stream, 1); |
1880 stream->participant = g_strdup(who); | 2025 stream->participant = g_strdup(who); |
1881 stream->session = session; | 2026 stream->session = session; |
1882 stream->stream = fsstream; | 2027 stream->stream = fsstream; |
2028 #ifndef HAVE_FARSTREAM | |
2029 stream->supports_add = !strcmp(transmitter, "nice"); | |
2030 #endif | |
1883 | 2031 |
1884 priv->streams = g_list_append(priv->streams, stream); | 2032 priv->streams = g_list_append(priv->streams, stream); |
1885 | 2033 |
1886 g_signal_connect(G_OBJECT(fsstream), "src-pad-added", | 2034 g_signal_connect(G_OBJECT(fsstream), "src-pad-added", |
1887 G_CALLBACK(src_pad_added_cb), stream); | 2035 G_CALLBACK(src_pad_added_cb), stream); |
1990 candidate_list_to_fs(remote_candidates)); | 2138 candidate_list_to_fs(remote_candidates)); |
1991 | 2139 |
1992 if (purple_media_is_initiator(priv->media, sess_id, participant) || | 2140 if (purple_media_is_initiator(priv->media, sess_id, participant) || |
1993 purple_media_accepted( | 2141 purple_media_accepted( |
1994 priv->media, sess_id, participant)) { | 2142 priv->media, sess_id, participant)) { |
2143 #ifdef HAVE_FARSIGHT | |
1995 fs_stream_set_remote_candidates(stream->stream, | 2144 fs_stream_set_remote_candidates(stream->stream, |
1996 stream->remote_candidates, &err); | 2145 stream->remote_candidates, &err); |
2146 #else | |
2147 if (stream->supports_add) | |
2148 fs_stream_add_remote_candidates(stream->stream, | |
2149 stream->remote_candidates, &err); | |
2150 else | |
2151 fs_stream_force_remote_candidates(stream->stream, | |
2152 stream->remote_candidates, &err); | |
2153 #endif | |
1997 | 2154 |
1998 if (err) { | 2155 if (err) { |
1999 purple_debug_error("backend-fs2", "Error adding remote" | 2156 purple_debug_error("backend-fs2", "Error adding remote" |
2000 " candidates: %s\n", err->message); | 2157 " candidates: %s\n", err->message); |
2001 g_error_free(err); | 2158 g_error_free(err); |
2021 if (session == NULL) | 2178 if (session == NULL) |
2022 return FALSE; | 2179 return FALSE; |
2023 | 2180 |
2024 if (session->type & (PURPLE_MEDIA_SEND_AUDIO | | 2181 if (session->type & (PURPLE_MEDIA_SEND_AUDIO | |
2025 PURPLE_MEDIA_SEND_VIDEO)) { | 2182 PURPLE_MEDIA_SEND_VIDEO)) { |
2183 #ifdef HAVE_FARSIGHT | |
2026 g_object_get(session->session, | 2184 g_object_get(session->session, |
2027 "codecs-ready", &ret, NULL); | 2185 "codecs-ready", &ret, NULL); |
2186 #else | |
2187 GList *codecs = NULL; | |
2188 | |
2189 g_object_get(session->session, | |
2190 "codecs", &codecs, NULL); | |
2191 if (codecs) { | |
2192 fs_codec_list_destroy (codecs); | |
2193 ret = TRUE; | |
2194 } | |
2195 #endif | |
2028 } else | 2196 } else |
2029 ret = TRUE; | 2197 ret = TRUE; |
2030 } else { | 2198 } else { |
2031 GList *values = g_hash_table_get_values(priv->sessions); | 2199 GList *values = g_hash_table_get_values(priv->sessions); |
2032 | 2200 |
2033 for (; values; values = g_list_delete_link(values, values)) { | 2201 for (; values; values = g_list_delete_link(values, values)) { |
2034 PurpleMediaBackendFs2Session *session = values->data; | 2202 PurpleMediaBackendFs2Session *session = values->data; |
2203 | |
2035 if (session->type & (PURPLE_MEDIA_SEND_AUDIO | | 2204 if (session->type & (PURPLE_MEDIA_SEND_AUDIO | |
2036 PURPLE_MEDIA_SEND_VIDEO)) { | 2205 PURPLE_MEDIA_SEND_VIDEO)) { |
2206 #ifdef HAVE_FARSIGHT | |
2037 g_object_get(session->session, | 2207 g_object_get(session->session, |
2038 "codecs-ready", &ret, NULL); | 2208 "codecs-ready", &ret, NULL); |
2039 if (ret == FALSE) | 2209 if (ret == FALSE) |
2040 break; | 2210 break; |
2211 #else | |
2212 GList *codecs = NULL; | |
2213 | |
2214 g_object_get(session->session, | |
2215 "codecs", &codecs, NULL); | |
2216 if (codecs) { | |
2217 fs_codec_list_destroy (codecs); | |
2218 ret = TRUE; | |
2219 } else { | |
2220 ret = FALSE; | |
2221 break; | |
2222 } | |
2223 #endif | |
2041 } else | 2224 } else |
2042 ret = TRUE; | 2225 ret = TRUE; |
2043 } | 2226 } |
2044 | 2227 |
2045 if (values != NULL) | 2228 if (values != NULL) |