ffi-tox 0.1.1 → 0.1.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (153) hide show
  1. checksums.yaml +4 -4
  2. data/ProjectTox-Core/AUTHORS +0 -0
  3. data/ProjectTox-Core/ChangeLog +0 -0
  4. data/ProjectTox-Core/INSTALL +370 -0
  5. data/ProjectTox-Core/INSTALL.md +455 -56
  6. data/ProjectTox-Core/Makefile.am +35 -0
  7. data/ProjectTox-Core/NEWS +0 -0
  8. data/ProjectTox-Core/README +43 -0
  9. data/ProjectTox-Core/README.md +34 -44
  10. data/ProjectTox-Core/auto_tests/Makefile.inc +110 -0
  11. data/ProjectTox-Core/auto_tests/TCP_test.c +519 -0
  12. data/ProjectTox-Core/auto_tests/assoc_test.c +160 -0
  13. data/ProjectTox-Core/auto_tests/crypto_test.c +302 -0
  14. data/ProjectTox-Core/auto_tests/dht_test.c +362 -0
  15. data/ProjectTox-Core/auto_tests/encryptsave_test.c +104 -0
  16. data/ProjectTox-Core/auto_tests/friends_test.c +238 -0
  17. data/ProjectTox-Core/auto_tests/helpers.h +15 -0
  18. data/ProjectTox-Core/auto_tests/messenger_test.c +365 -0
  19. data/ProjectTox-Core/auto_tests/network_test.c +171 -0
  20. data/ProjectTox-Core/auto_tests/onion_test.c +363 -0
  21. data/ProjectTox-Core/auto_tests/skeleton_test.c +49 -0
  22. data/ProjectTox-Core/auto_tests/tox_test.c +454 -0
  23. data/ProjectTox-Core/auto_tests/toxav_basic_test.c +597 -0
  24. data/ProjectTox-Core/auto_tests/toxav_many_test.c +402 -0
  25. data/ProjectTox-Core/autogen.sh +6 -0
  26. data/ProjectTox-Core/build/Makefile.am +14 -0
  27. data/ProjectTox-Core/configure.ac +694 -0
  28. data/ProjectTox-Core/dist-build/android-arm.sh +3 -0
  29. data/ProjectTox-Core/dist-build/android-armv7.sh +3 -0
  30. data/ProjectTox-Core/dist-build/android-build.sh +59 -0
  31. data/ProjectTox-Core/dist-build/android-mips.sh +3 -0
  32. data/ProjectTox-Core/dist-build/android-x86.sh +3 -0
  33. data/ProjectTox-Core/docs/Group-Chats.md +71 -0
  34. data/ProjectTox-Core/docs/Hardening.txt +60 -0
  35. data/ProjectTox-Core/docs/Hardening_docs.txt +30 -0
  36. data/ProjectTox-Core/docs/Prevent_Tracking.txt +160 -0
  37. data/ProjectTox-Core/docs/TCP_Network.txt +154 -0
  38. data/ProjectTox-Core/docs/TODO +62 -0
  39. data/ProjectTox-Core/docs/Tox_middle_level_network_protocol.txt +120 -0
  40. data/ProjectTox-Core/docs/av_api.md +194 -0
  41. data/ProjectTox-Core/libtoxav.pc.in +11 -0
  42. data/ProjectTox-Core/libtoxcore.pc.in +11 -0
  43. data/ProjectTox-Core/m4/ax_have_epoll.m4 +104 -0
  44. data/ProjectTox-Core/m4/ax_pthread.m4 +317 -0
  45. data/ProjectTox-Core/m4/pkg.m4 +199 -0
  46. data/ProjectTox-Core/other/DHT_bootstrap.c +121 -58
  47. data/ProjectTox-Core/other/DHTnodes +3 -0
  48. data/ProjectTox-Core/other/Makefile.inc +20 -0
  49. data/ProjectTox-Core/other/bootstrap_node_packets.c +65 -0
  50. data/ProjectTox-Core/other/tox.png +0 -0
  51. data/ProjectTox-Core/testing/DHT_test.c +170 -98
  52. data/ProjectTox-Core/testing/Makefile.inc +112 -0
  53. data/ProjectTox-Core/testing/Messenger_test.c +133 -69
  54. data/ProjectTox-Core/testing/dns3_test.c +115 -0
  55. data/ProjectTox-Core/testing/misc_tools.c +59 -13
  56. data/ProjectTox-Core/testing/nTox.c +1127 -264
  57. data/ProjectTox-Core/testing/nTox.h +10 -19
  58. data/ProjectTox-Core/testing/tox_shell.c +159 -0
  59. data/ProjectTox-Core/testing/tox_sync.c +299 -0
  60. data/ProjectTox-Core/tools/README +11 -0
  61. data/ProjectTox-Core/tools/astylerc +11 -0
  62. data/ProjectTox-Core/tools/pre-commit +17 -0
  63. data/ProjectTox-Core/toxav/Makefile.inc +36 -0
  64. data/ProjectTox-Core/toxav/codec.c +357 -0
  65. data/ProjectTox-Core/toxav/codec.h +116 -0
  66. data/ProjectTox-Core/toxav/msi.c +1949 -0
  67. data/ProjectTox-Core/toxav/msi.h +267 -0
  68. data/ProjectTox-Core/toxav/rtp.c +600 -0
  69. data/ProjectTox-Core/toxav/rtp.h +196 -0
  70. data/ProjectTox-Core/toxav/toxav.c +1148 -0
  71. data/ProjectTox-Core/toxav/toxav.h +389 -0
  72. data/ProjectTox-Core/toxcore/DHT.c +2521 -0
  73. data/ProjectTox-Core/toxcore/DHT.h +412 -0
  74. data/ProjectTox-Core/toxcore/LAN_discovery.c +322 -0
  75. data/ProjectTox-Core/{core → toxcore}/LAN_discovery.h +17 -12
  76. data/ProjectTox-Core/toxcore/Makefile.inc +67 -0
  77. data/ProjectTox-Core/toxcore/Messenger.c +3006 -0
  78. data/ProjectTox-Core/toxcore/Messenger.h +818 -0
  79. data/ProjectTox-Core/toxcore/TCP_client.c +858 -0
  80. data/ProjectTox-Core/toxcore/TCP_client.h +156 -0
  81. data/ProjectTox-Core/toxcore/TCP_server.c +1332 -0
  82. data/ProjectTox-Core/toxcore/TCP_server.h +181 -0
  83. data/ProjectTox-Core/toxcore/assoc.c +1033 -0
  84. data/ProjectTox-Core/toxcore/assoc.h +104 -0
  85. data/ProjectTox-Core/toxcore/crypto_core.c +278 -0
  86. data/ProjectTox-Core/toxcore/crypto_core.h +151 -0
  87. data/ProjectTox-Core/toxcore/friend_requests.c +175 -0
  88. data/ProjectTox-Core/toxcore/friend_requests.h +83 -0
  89. data/ProjectTox-Core/toxcore/group_chats.c +837 -0
  90. data/ProjectTox-Core/toxcore/group_chats.h +199 -0
  91. data/ProjectTox-Core/toxcore/list.c +256 -0
  92. data/ProjectTox-Core/toxcore/list.h +85 -0
  93. data/ProjectTox-Core/toxcore/logger.c +153 -0
  94. data/ProjectTox-Core/toxcore/logger.h +84 -0
  95. data/ProjectTox-Core/toxcore/misc_tools.h +70 -0
  96. data/ProjectTox-Core/toxcore/net_crypto.c +2753 -0
  97. data/ProjectTox-Core/toxcore/net_crypto.h +410 -0
  98. data/ProjectTox-Core/toxcore/network.c +979 -0
  99. data/ProjectTox-Core/toxcore/network.h +367 -0
  100. data/ProjectTox-Core/toxcore/onion.c +540 -0
  101. data/ProjectTox-Core/toxcore/onion.h +150 -0
  102. data/ProjectTox-Core/toxcore/onion_announce.c +433 -0
  103. data/ProjectTox-Core/toxcore/onion_announce.h +139 -0
  104. data/ProjectTox-Core/toxcore/onion_client.c +1347 -0
  105. data/ProjectTox-Core/toxcore/onion_client.h +253 -0
  106. data/ProjectTox-Core/toxcore/ping.c +346 -0
  107. data/ProjectTox-Core/toxcore/ping.h +47 -0
  108. data/ProjectTox-Core/toxcore/ping_array.c +162 -0
  109. data/ProjectTox-Core/toxcore/ping_array.h +75 -0
  110. data/ProjectTox-Core/toxcore/tox.c +940 -0
  111. data/ProjectTox-Core/toxcore/tox.h +734 -0
  112. data/ProjectTox-Core/toxcore/util.c +193 -0
  113. data/ProjectTox-Core/toxcore/util.h +63 -0
  114. data/ProjectTox-Core/toxdns/Makefile.inc +29 -0
  115. data/ProjectTox-Core/toxdns/toxdns.c +238 -0
  116. data/ProjectTox-Core/toxdns/toxdns.h +88 -0
  117. data/ProjectTox-Core/toxencryptsave/Makefile.inc +45 -0
  118. data/ProjectTox-Core/toxencryptsave/toxencryptsave.c +179 -0
  119. data/ProjectTox-Core/toxencryptsave/toxencryptsave.h +74 -0
  120. data/interfaces/libtox.i +2 -6
  121. data/lib/ffi-tox/libtox.rb +406 -28
  122. metadata +124 -46
  123. data/ProjectTox-Core/CMakeLists.txt +0 -50
  124. data/ProjectTox-Core/cmake/FindLIBCONFIG.cmake +0 -15
  125. data/ProjectTox-Core/cmake/FindNaCl.cmake +0 -17
  126. data/ProjectTox-Core/cmake/FindSODIUM.cmake +0 -15
  127. data/ProjectTox-Core/core/CMakeLists.txt +0 -19
  128. data/ProjectTox-Core/core/DHT.c +0 -1104
  129. data/ProjectTox-Core/core/DHT.h +0 -111
  130. data/ProjectTox-Core/core/LAN_discovery.c +0 -79
  131. data/ProjectTox-Core/core/Lossless_UDP.c +0 -755
  132. data/ProjectTox-Core/core/Lossless_UDP.h +0 -106
  133. data/ProjectTox-Core/core/Messenger.c +0 -596
  134. data/ProjectTox-Core/core/Messenger.h +0 -165
  135. data/ProjectTox-Core/core/friend_requests.c +0 -131
  136. data/ProjectTox-Core/core/friend_requests.h +0 -51
  137. data/ProjectTox-Core/core/net_crypto.c +0 -575
  138. data/ProjectTox-Core/core/net_crypto.h +0 -134
  139. data/ProjectTox-Core/core/network.c +0 -205
  140. data/ProjectTox-Core/core/network.h +0 -134
  141. data/ProjectTox-Core/docs/commands.md +0 -25
  142. data/ProjectTox-Core/docs/start_guide.de.md +0 -40
  143. data/ProjectTox-Core/docs/start_guide.md +0 -38
  144. data/ProjectTox-Core/other/CMakeLists.txt +0 -9
  145. data/ProjectTox-Core/testing/CMakeLists.txt +0 -18
  146. data/ProjectTox-Core/testing/DHT_cryptosendfiletest.c +0 -228
  147. data/ProjectTox-Core/testing/DHT_sendfiletest.c +0 -176
  148. data/ProjectTox-Core/testing/Lossless_UDP_testclient.c +0 -214
  149. data/ProjectTox-Core/testing/Lossless_UDP_testserver.c +0 -201
  150. data/ProjectTox-Core/testing/misc_tools.h +0 -29
  151. data/ProjectTox-Core/testing/nTox_win32.c +0 -387
  152. data/ProjectTox-Core/testing/nTox_win32.h +0 -40
  153. data/ProjectTox-Core/testing/rect.py +0 -45
@@ -0,0 +1,267 @@
1
+ /** msi.h
2
+ *
3
+ * Copyright (C) 2013 Tox project All Rights Reserved.
4
+ *
5
+ * This file is part of Tox.
6
+ *
7
+ * Tox is free software: you can redistribute it and/or modify
8
+ * it under the terms of the GNU General Public License as published by
9
+ * the Free Software Foundation, either version 3 of the License, or
10
+ * (at your option) any later version.
11
+ *
12
+ * Tox is distributed in the hope that it will be useful,
13
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
+ * GNU General Public License for more details.
16
+ *
17
+ * You should have received a copy of the GNU General Public License
18
+ * along with Tox. If not, see <http://www.gnu.org/licenses/>.
19
+ *
20
+ */
21
+
22
+ #ifndef __TOXMSI
23
+ #define __TOXMSI
24
+
25
+ #include <inttypes.h>
26
+ #include <pthread.h>
27
+
28
+ #include "../toxcore/Messenger.h"
29
+
30
+ typedef uint8_t MSICallIDType[12];
31
+ typedef uint8_t MSIReasonStrType[255];
32
+ typedef void ( *MSICallbackType ) ( void *agent, int32_t call_idx, void *arg );
33
+
34
+
35
+ /**
36
+ * @brief Call type identifier. Also used as rtp callback prefix.
37
+ */
38
+ typedef enum {
39
+ type_audio = 192,
40
+ type_video
41
+ } MSICallType;
42
+
43
+
44
+ /**
45
+ * @brief Call state identifiers.
46
+ */
47
+ typedef enum {
48
+ call_inviting, /* when sending call invite */
49
+ call_starting, /* when getting call invite */
50
+ call_active,
51
+ call_hold,
52
+ call_hanged_up
53
+
54
+ } MSICallState;
55
+
56
+
57
+ /**
58
+ * @brief Encoding settings.
59
+ */
60
+ typedef struct _MSICodecSettings {
61
+ MSICallType call_type;
62
+
63
+ uint32_t video_bitrate; /* In kbits/s */
64
+ uint16_t max_video_width; /* In px */
65
+ uint16_t max_video_height; /* In px */
66
+
67
+ uint32_t audio_bitrate; /* In bits/s */
68
+ uint16_t audio_frame_duration; /* In ms */
69
+ uint32_t audio_sample_rate; /* In Hz */
70
+ uint32_t audio_channels;
71
+ } MSICSettings;
72
+
73
+
74
+ /**
75
+ * @brief Callbacks ids that handle the states
76
+ */
77
+ typedef enum {
78
+ /* Requests */
79
+ MSI_OnInvite,
80
+ MSI_OnStart,
81
+ MSI_OnCancel,
82
+ MSI_OnReject,
83
+ MSI_OnEnd,
84
+
85
+ /* Responses */
86
+ MSI_OnRinging,
87
+ MSI_OnStarting,
88
+ MSI_OnEnding,
89
+
90
+ /* Protocol */
91
+ MSI_OnRequestTimeout,
92
+ MSI_OnPeerTimeout,
93
+ MSI_OnMediaChange
94
+ } MSICallbackID;
95
+
96
+ /**
97
+ * @brief Callbacks container
98
+ */
99
+ typedef struct _MSICallbackCont {
100
+ MSICallbackType function;
101
+ void *data;
102
+ } MSICallbackCont;
103
+
104
+ /**
105
+ * @brief The call struct.
106
+ *
107
+ */
108
+ typedef struct _MSICall { /* Call info structure */
109
+ struct _MSISession *session; /* Session pointer */
110
+
111
+ MSICallState state;
112
+
113
+ MSICSettings csettings_local; /* Local call settings */
114
+ MSICSettings *csettings_peer; /* Peers call settings */
115
+
116
+ MSICallIDType id; /* Random value identifying the call */
117
+
118
+ int ringing_tout_ms; /* Ringing timeout in ms */
119
+
120
+ int request_timer_id; /* Timer id for outgoing request/action */
121
+ int ringing_timer_id; /* Timer id for ringing timeout */
122
+
123
+
124
+ pthread_mutex_t mutex; /* */
125
+ uint32_t *peers;
126
+ uint16_t peer_count;
127
+
128
+ int32_t call_idx; /* Index of this call in MSISession */
129
+ } MSICall;
130
+
131
+
132
+ /**
133
+ * @brief Control session struct
134
+ *
135
+ */
136
+ typedef struct _MSISession {
137
+
138
+ /* Call handlers */
139
+ MSICall **calls;
140
+ int32_t max_calls;
141
+
142
+ void *agent_handler;
143
+ Messenger *messenger_handle;
144
+
145
+ uint32_t frequ;
146
+ uint32_t call_timeout; /* Time of the timeout for some action to end; 0 if infinite */
147
+
148
+ pthread_mutex_t mutex;
149
+
150
+ void *timer_handler;
151
+ MSICallbackCont callbacks[11]; /* Callbacks used by this session */
152
+ } MSISession;
153
+
154
+ /**
155
+ * @brief Callback setter.
156
+ *
157
+ * @param session The container.
158
+ * @param callback The callback.
159
+ * @param id The id.
160
+ * @return void
161
+ */
162
+ void msi_register_callback(MSISession *session, MSICallbackType callback, MSICallbackID id, void *userdata);
163
+
164
+
165
+ /**
166
+ * @brief Start the control session.
167
+ *
168
+ * @param messenger Tox* object.
169
+ * @param max_calls Amount of calls possible
170
+ * @return MSISession* The created session.
171
+ * @retval NULL Error occurred.
172
+ */
173
+ MSISession *msi_init_session ( Messenger *messenger, int32_t max_calls );
174
+
175
+
176
+ /**
177
+ * @brief Terminate control session.
178
+ *
179
+ * @param session The session
180
+ * @return int
181
+ */
182
+ int msi_terminate_session ( MSISession *session );
183
+
184
+
185
+ /**
186
+ * @brief Send invite request to friend_id.
187
+ *
188
+ * @param session Control session.
189
+ * @param call_index Set to new call index.
190
+ * @param call_type Type of the call. Audio or Video(both audio and video)
191
+ * @param rngsec Ringing timeout.
192
+ * @param friend_id The friend.
193
+ * @return int
194
+ */
195
+ int msi_invite ( MSISession *session, int32_t *call_index, MSICSettings csettings, uint32_t rngsec,
196
+ uint32_t friend_id );
197
+
198
+
199
+ /**
200
+ * @brief Hangup active call.
201
+ *
202
+ * @param session Control session.
203
+ * @param call_index To which call is this action handled.
204
+ * @return int
205
+ * @retval -1 Error occurred.
206
+ * @retval 0 Success.
207
+ */
208
+ int msi_hangup ( MSISession *session, int32_t call_index );
209
+
210
+
211
+ /**
212
+ * @brief Answer active call request.
213
+ *
214
+ * @param session Control session.
215
+ * @param call_index To which call is this action handled.
216
+ * @param call_type Answer with Audio or Video(both).
217
+ * @return int
218
+ */
219
+ int msi_answer ( MSISession *session, int32_t call_index, MSICSettings csettings );
220
+
221
+
222
+ /**
223
+ * @brief Cancel request.
224
+ *
225
+ * @param session Control session.
226
+ * @param call_index To which call is this action handled.
227
+ * @param peer To which peer.
228
+ * @param reason Set optional reason header. Pass NULL if none.
229
+ * @return int
230
+ */
231
+ int msi_cancel ( MSISession *session, int32_t call_index, uint32_t peer, const char *reason );
232
+
233
+
234
+ /**
235
+ * @brief Reject request.
236
+ *
237
+ * @param session Control session.
238
+ * @param call_index To which call is this action handled.
239
+ * @param reason Set optional reason header. Pass NULL if none.
240
+ * @return int
241
+ */
242
+ int msi_reject ( MSISession *session, int32_t call_index, const char *reason );
243
+
244
+
245
+ /**
246
+ * @brief Send invite request to friend_id.
247
+ *
248
+ * @param session Control session.
249
+ * @param call_index Call index.
250
+ * @param call_type Type of the call. Audio or Video(both audio and video)
251
+ * @param rngsec Ringing timeout.
252
+ * @param friend_id The friend.
253
+ * @return int
254
+ */
255
+ int msi_change_csettings ( MSISession *session, int32_t call_index, MSICSettings csettings );
256
+
257
+
258
+ /**
259
+ * @brief Terminate the current call.
260
+ *
261
+ * @param session Control session.
262
+ * @param call_index To which call is this action handled.
263
+ * @return int
264
+ */
265
+ int msi_stopcall ( MSISession *session, int32_t call_index );
266
+
267
+ #endif /* __TOXMSI */
@@ -0,0 +1,600 @@
1
+ /** rtp.c
2
+ *
3
+ * Copyright (C) 2013 Tox project All Rights Reserved.
4
+ *
5
+ * This file is part of Tox.
6
+ *
7
+ * Tox is free software: you can redistribute it and/or modify
8
+ * it under the terms of the GNU General Public License as published by
9
+ * the Free Software Foundation, either version 3 of the License, or
10
+ * (at your option) any later version.
11
+ *
12
+ * Tox is distributed in the hope that it will be useful,
13
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
+ * GNU General Public License for more details.
16
+ *
17
+ * You should have received a copy of the GNU General Public License
18
+ * along with Tox. If not, see <http://www.gnu.org/licenses/>.
19
+ *
20
+ */
21
+
22
+ #ifdef HAVE_CONFIG_H
23
+ #include "config.h"
24
+ #endif /* HAVE_CONFIG_H */
25
+
26
+ #include "../toxcore/logger.h"
27
+ #include "../toxcore/util.h"
28
+
29
+ #include "rtp.h"
30
+ #include <stdlib.h>
31
+ void toxav_handle_packet(RTPSession *_session, RTPMessage *_msg);
32
+
33
+ #define size_32 4
34
+
35
+ #define ADD_FLAG_VERSION(_h, _v) do { ( _h->flags ) &= 0x3F; ( _h->flags ) |= ( ( ( _v ) << 6 ) & 0xC0 ); } while(0)
36
+ #define ADD_FLAG_PADDING(_h, _v) do { if ( _v > 0 ) _v = 1; ( _h->flags ) &= 0xDF; ( _h->flags ) |= ( ( ( _v ) << 5 ) & 0x20 ); } while(0)
37
+ #define ADD_FLAG_EXTENSION(_h, _v) do { if ( _v > 0 ) _v = 1; ( _h->flags ) &= 0xEF;( _h->flags ) |= ( ( ( _v ) << 4 ) & 0x10 ); } while(0)
38
+ #define ADD_FLAG_CSRCC(_h, _v) do { ( _h->flags ) &= 0xF0; ( _h->flags ) |= ( ( _v ) & 0x0F ); } while(0)
39
+ #define ADD_SETTING_MARKER(_h, _v) do { if ( _v > 1 ) _v = 1; ( _h->marker_payloadt ) &= 0x7F; ( _h->marker_payloadt ) |= ( ( ( _v ) << 7 ) /*& 0x80 */ ); } while(0)
40
+ #define ADD_SETTING_PAYLOAD(_h, _v) do { if ( _v > 127 ) _v = 127; ( _h->marker_payloadt ) &= 0x80; ( _h->marker_payloadt ) |= ( ( _v ) /* & 0x7F */ ); } while(0)
41
+
42
+ #define GET_FLAG_VERSION(_h) (( _h->flags & 0xd0 ) >> 6)
43
+ #define GET_FLAG_PADDING(_h) (( _h->flags & 0x20 ) >> 5)
44
+ #define GET_FLAG_EXTENSION(_h) (( _h->flags & 0x10 ) >> 4)
45
+ #define GET_FLAG_CSRCC(_h) ( _h->flags & 0x0f )
46
+ #define GET_SETTING_MARKER(_h) (( _h->marker_payloadt ) >> 7)
47
+ #define GET_SETTING_PAYLOAD(_h) ((_h->marker_payloadt) & 0x7f)
48
+
49
+ /**
50
+ * @brief Checks if message came in late.
51
+ *
52
+ * @param session Control session.
53
+ * @param msg The message.
54
+ * @return int
55
+ * @retval -1 The message came in order.
56
+ * @retval 0 The message came late.
57
+ */
58
+ inline__ int check_late_message (RTPSession *session, RTPMessage *msg)
59
+ {
60
+ /*
61
+ * Check Sequence number. If this new msg has lesser number then the session->rsequnum
62
+ * it shows that the message came in late. Also check timestamp to be 100% certain.
63
+ *
64
+ */
65
+ return ( msg->header->sequnum < session->rsequnum && msg->header->timestamp < session->timestamp ) ? 0 : -1;
66
+ }
67
+
68
+
69
+ /**
70
+ * @brief Extracts header from payload.
71
+ *
72
+ * @param payload The payload.
73
+ * @param length The size of payload.
74
+ * @return RTPHeader* Extracted header.
75
+ * @retval NULL Error occurred while extracting header.
76
+ */
77
+ RTPHeader *extract_header ( const uint8_t *payload, int length )
78
+ {
79
+ if ( !payload || !length ) {
80
+ LOGGER_WARNING("No payload to extract!");
81
+ return NULL;
82
+ }
83
+
84
+ RTPHeader *_retu = calloc(1, sizeof (RTPHeader));
85
+
86
+ if ( !_retu ) {
87
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
88
+ return NULL;
89
+ }
90
+
91
+ bytes_to_U16(&_retu->sequnum, payload);
92
+
93
+ const uint8_t *_it = payload + 2;
94
+
95
+ _retu->flags = *_it;
96
+ ++_it;
97
+
98
+ /* This indicates if the first 2 bits are valid.
99
+ * Now it may happen that this is out of order but
100
+ * it cuts down chances of parsing some invalid value
101
+ */
102
+
103
+ if ( GET_FLAG_VERSION(_retu) != RTP_VERSION ) {
104
+ /* Deallocate */
105
+ LOGGER_WARNING("Invalid version!");
106
+ free(_retu);
107
+ return NULL;
108
+ }
109
+
110
+ /*
111
+ * Added a check for the size of the header little sooner so
112
+ * I don't need to parse the other stuff if it's bad
113
+ */
114
+ uint8_t _cc = GET_FLAG_CSRCC ( _retu );
115
+ int _length = 12 /* Minimum header len */ + ( _cc * 4 );
116
+
117
+ if ( length < _length ) {
118
+ /* Deallocate */
119
+ LOGGER_WARNING("Length invalid!");
120
+ free(_retu);
121
+ return NULL;
122
+ }
123
+
124
+ memset(_retu->csrc, 0, 16 * sizeof (uint32_t));
125
+
126
+ _retu->marker_payloadt = *_it;
127
+ ++_it;
128
+ _retu->length = _length;
129
+
130
+
131
+ bytes_to_U32(&_retu->timestamp, _it);
132
+ _it += 4;
133
+ bytes_to_U32(&_retu->ssrc, _it);
134
+
135
+ uint8_t _x;
136
+
137
+ for ( _x = 0; _x < _cc; _x++ ) {
138
+ _it += 4;
139
+ bytes_to_U32(&(_retu->csrc[_x]), _it);
140
+ }
141
+
142
+ return _retu;
143
+ }
144
+
145
+ /**
146
+ * @brief Extracts external header from payload. Must be called AFTER extract_header()!
147
+ *
148
+ * @param payload The ITERATED payload.
149
+ * @param length The size of payload.
150
+ * @return RTPExtHeader* Extracted extension header.
151
+ * @retval NULL Error occurred while extracting extension header.
152
+ */
153
+ RTPExtHeader *extract_ext_header ( const uint8_t *payload, uint16_t length )
154
+ {
155
+ const uint8_t *_it = payload;
156
+
157
+ RTPExtHeader *_retu = calloc(1, sizeof (RTPExtHeader));
158
+
159
+ if ( !_retu ) {
160
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
161
+ return NULL;
162
+ }
163
+
164
+ uint16_t _ext_length;
165
+ bytes_to_U16(&_ext_length, _it);
166
+ _it += 2;
167
+
168
+
169
+ if ( length < ( _ext_length * sizeof(uint32_t) ) ) {
170
+ LOGGER_WARNING("Length invalid!");
171
+ free(_retu);
172
+ return NULL;
173
+ }
174
+
175
+ _retu->length = _ext_length;
176
+ bytes_to_U16(&_retu->type, _it);
177
+ _it += 2;
178
+
179
+ if ( !(_retu->table = calloc(_ext_length, sizeof (uint32_t))) ) {
180
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
181
+ free(_retu);
182
+ return NULL;
183
+ }
184
+
185
+ uint16_t _x;
186
+
187
+ for ( _x = 0; _x < _ext_length; _x++ ) {
188
+ _it += 4;
189
+ bytes_to_U32(&(_retu->table[_x]), _it);
190
+ }
191
+
192
+ return _retu;
193
+ }
194
+
195
+ /**
196
+ * @brief Adds header to payload. Make sure _payload_ has enough space.
197
+ *
198
+ * @param header The header.
199
+ * @param payload The payload.
200
+ * @return uint8_t* Iterated position.
201
+ */
202
+ uint8_t *add_header ( RTPHeader *header, uint8_t *payload )
203
+ {
204
+ uint8_t _cc = GET_FLAG_CSRCC ( header );
205
+
206
+ uint8_t *_it = payload;
207
+
208
+
209
+ /* Add sequence number first */
210
+ U16_to_bytes(_it, header->sequnum);
211
+ _it += 2;
212
+
213
+ *_it = header->flags;
214
+ ++_it;
215
+ *_it = header->marker_payloadt;
216
+ ++_it;
217
+
218
+
219
+ U32_to_bytes( _it, header->timestamp);
220
+ _it += 4;
221
+ U32_to_bytes( _it, header->ssrc);
222
+
223
+ uint8_t _x;
224
+
225
+ for ( _x = 0; _x < _cc; _x++ ) {
226
+ _it += 4;
227
+ U32_to_bytes( _it, header->csrc[_x]);
228
+ }
229
+
230
+ return _it + 4;
231
+ }
232
+
233
+ /**
234
+ * @brief Adds extension header to payload. Make sure _payload_ has enough space.
235
+ *
236
+ * @param header The header.
237
+ * @param payload The payload.
238
+ * @return uint8_t* Iterated position.
239
+ */
240
+ uint8_t *add_ext_header ( RTPExtHeader *header, uint8_t *payload )
241
+ {
242
+ uint8_t *_it = payload;
243
+
244
+ U16_to_bytes(_it, header->length);
245
+ _it += 2;
246
+ U16_to_bytes(_it, header->type);
247
+ _it -= 2; /* Return to 0 position */
248
+
249
+ if ( header->table ) {
250
+ uint16_t _x;
251
+
252
+ for ( _x = 0; _x < header->length; _x++ ) {
253
+ _it += 4;
254
+ U32_to_bytes(_it, header->table[_x]);
255
+ }
256
+ }
257
+
258
+ return _it + 4;
259
+ }
260
+
261
+ /**
262
+ * @brief Builds header from control session values.
263
+ *
264
+ * @param session Control session.
265
+ * @return RTPHeader* Created header.
266
+ */
267
+ RTPHeader *build_header ( RTPSession *session )
268
+ {
269
+ RTPHeader *_retu = calloc ( 1, sizeof (RTPHeader) );
270
+
271
+ if ( !_retu ) {
272
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
273
+ return NULL;
274
+ }
275
+
276
+ ADD_FLAG_VERSION ( _retu, session->version );
277
+ ADD_FLAG_PADDING ( _retu, session->padding );
278
+ ADD_FLAG_EXTENSION ( _retu, session->extension );
279
+ ADD_FLAG_CSRCC ( _retu, session->cc );
280
+ ADD_SETTING_MARKER ( _retu, session->marker );
281
+ ADD_SETTING_PAYLOAD ( _retu, session->payload_type );
282
+
283
+ _retu->sequnum = session->sequnum;
284
+ _retu->timestamp = current_time_monotonic(); /* milliseconds */
285
+ _retu->ssrc = session->ssrc;
286
+
287
+ int i;
288
+
289
+ for ( i = 0; i < session->cc; i++ )
290
+ _retu->csrc[i] = session->csrc[i];
291
+
292
+ _retu->length = 12 /* Minimum header len */ + ( session->cc * size_32 );
293
+
294
+ return _retu;
295
+ }
296
+
297
+
298
+ /**
299
+ * @brief Parses data into RTPMessage struct. Stores headers separately from the payload data
300
+ * and so the length variable is set accordingly. _sequnum_ argument is
301
+ * passed by the handle_packet() since it's parsed already.
302
+ *
303
+ * @param session Control session.
304
+ * @param sequnum Sequence number that's parsed from payload in handle_packet()
305
+ * @param data Payload data.
306
+ * @param length Payload size.
307
+ * @return RTPMessage*
308
+ * @retval NULL Error occurred.
309
+ */
310
+ RTPMessage *msg_parse ( const uint8_t *data, int length )
311
+ {
312
+ RTPMessage *_retu = calloc(1, sizeof (RTPMessage));
313
+
314
+ _retu->header = extract_header ( data, length ); /* It allocates memory and all */
315
+
316
+ if ( !_retu->header ) {
317
+ LOGGER_WARNING("Header failed to extract!");
318
+ free(_retu);
319
+ return NULL;
320
+ }
321
+
322
+ uint16_t _from_pos = _retu->header->length;
323
+ _retu->length = length - _from_pos;
324
+
325
+
326
+
327
+ if ( GET_FLAG_EXTENSION ( _retu->header ) ) {
328
+ _retu->ext_header = extract_ext_header ( data + _from_pos, length );
329
+
330
+ if ( _retu->ext_header ) {
331
+ _retu->length -= ( 4 /* Minimum ext header len */ + _retu->ext_header->length * size_32 );
332
+ _from_pos += ( 4 /* Minimum ext header len */ + _retu->ext_header->length * size_32 );
333
+ } else { /* Error */
334
+ LOGGER_WARNING("Ext Header failed to extract!");
335
+ rtp_free_msg(NULL, _retu);
336
+ return NULL;
337
+ }
338
+ } else {
339
+ _retu->ext_header = NULL;
340
+ }
341
+
342
+ if ( length - _from_pos <= MAX_RTP_SIZE )
343
+ memcpy ( _retu->data, data + _from_pos, length - _from_pos );
344
+ else {
345
+ LOGGER_WARNING("Invalid length!");
346
+ rtp_free_msg(NULL, _retu);
347
+ return NULL;
348
+ }
349
+
350
+ _retu->next = NULL;
351
+
352
+ return _retu;
353
+ }
354
+
355
+ /**
356
+ * @brief Callback for networking core.
357
+ *
358
+ * @param object RTPSession object.
359
+ * @param ip_port Where the message comes from.
360
+ * @param data Message data.
361
+ * @param length Message length.
362
+ * @return int
363
+ * @retval -1 Error occurred.
364
+ * @retval 0 Success.
365
+ */
366
+ int rtp_handle_packet ( void *object, const uint8_t *data, uint32_t length )
367
+ {
368
+ RTPSession *_session = object;
369
+ RTPMessage *_msg;
370
+
371
+ if ( !_session || length < 13 ) { /* 12 is the minimum length for rtp + desc. byte */
372
+ LOGGER_WARNING("No session or invalid length of received buffer!");
373
+ return -1;
374
+ }
375
+
376
+ _msg = msg_parse ( data + 1, length - 1 );
377
+
378
+ if ( !_msg ) {
379
+ LOGGER_WARNING("Could not parse message!");
380
+ return -1;
381
+ }
382
+
383
+ /* Check if message came in late */
384
+ if ( check_late_message(_session, _msg) < 0 ) { /* Not late */
385
+ _session->rsequnum = _msg->header->sequnum;
386
+ _session->timestamp = _msg->header->timestamp;
387
+ }
388
+
389
+ toxav_handle_packet(_session, _msg);
390
+
391
+ return 0;
392
+ }
393
+
394
+
395
+
396
+ /**
397
+ * @brief Stores headers and payload data in one container ( data )
398
+ * and the length is set accordingly. Returned message is used for sending _only_.
399
+ *
400
+ * @param session The control session.
401
+ * @param data Payload data to send ( This is what you pass ).
402
+ * @param length Size of the payload data.
403
+ * @return RTPMessage* Created message.
404
+ * @retval NULL Error occurred.
405
+ */
406
+ RTPMessage *rtp_new_message ( RTPSession *session, const uint8_t *data, uint32_t length )
407
+ {
408
+ if ( !session ) {
409
+ LOGGER_WARNING("No session!");
410
+ return NULL;
411
+ }
412
+
413
+ uint8_t *_from_pos;
414
+ RTPMessage *_retu = calloc(1, sizeof (RTPMessage));
415
+
416
+ if ( !_retu ) {
417
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
418
+ return NULL;
419
+ }
420
+
421
+ /* Sets header values and copies the extension header in _retu */
422
+ _retu->header = build_header ( session ); /* It allocates memory and all */
423
+ _retu->ext_header = session->ext_header;
424
+
425
+
426
+ uint32_t _total_length = length + _retu->header->length + 1;
427
+
428
+ _retu->data[0] = session->prefix;
429
+
430
+ if ( _retu->ext_header ) {
431
+ _total_length += ( 4 /* Minimum ext header len */ + _retu->ext_header->length * size_32 );
432
+
433
+ _from_pos = add_header ( _retu->header, _retu->data + 1 );
434
+ _from_pos = add_ext_header ( _retu->ext_header, _from_pos + 1 );
435
+ } else {
436
+ _from_pos = add_header ( _retu->header, _retu->data + 1 );
437
+ }
438
+
439
+ /*
440
+ * Parses the extension header into the message
441
+ * Of course if any
442
+ */
443
+
444
+ /* Appends _data on to _retu->_data */
445
+ memcpy ( _from_pos, data, length );
446
+
447
+ _retu->length = _total_length;
448
+
449
+ _retu->next = NULL;
450
+
451
+ return _retu;
452
+ }
453
+
454
+
455
+ /**
456
+ * @brief Sends data to _RTPSession::dest
457
+ *
458
+ * @param session The session.
459
+ * @param messenger Tox* object.
460
+ * @param data The payload.
461
+ * @param length Size of the payload.
462
+ * @return int
463
+ * @retval -1 On error.
464
+ * @retval 0 On success.
465
+ */
466
+ int rtp_send_msg ( RTPSession *session, Messenger *messenger, const uint8_t *data, uint16_t length )
467
+ {
468
+ RTPMessage *msg = rtp_new_message (session, data, length);
469
+
470
+ if ( !msg ) {
471
+ LOGGER_WARNING("No session!");
472
+ return -1;
473
+ }
474
+
475
+ if ( -1 == send_custom_lossy_packet(messenger, session->dest, msg->data, msg->length) ) {
476
+ LOGGER_WARNING("Failed to send full packet! std error: %s", strerror(errno));
477
+ rtp_free_msg ( session, msg );
478
+ return -1;
479
+ }
480
+
481
+
482
+ /* Set sequ number */
483
+ session->sequnum = session->sequnum >= MAX_SEQU_NUM ? 0 : session->sequnum + 1;
484
+ rtp_free_msg ( session, msg );
485
+
486
+ return 0;
487
+ }
488
+
489
+
490
+ /**
491
+ * @brief Speaks for it self.
492
+ *
493
+ * @param session The control session msg belongs to. You set it as NULL when freeing recved messages.
494
+ * Otherwise set it to session the message was created from.
495
+ * @param msg The message.
496
+ * @return void
497
+ */
498
+ void rtp_free_msg ( RTPSession *session, RTPMessage *msg )
499
+ {
500
+ if ( !session ) {
501
+ if ( msg->ext_header ) {
502
+ free ( msg->ext_header->table );
503
+ free ( msg->ext_header );
504
+ }
505
+ } else {
506
+ if ( msg->ext_header && session->ext_header != msg->ext_header ) {
507
+ free ( msg->ext_header->table );
508
+ free ( msg->ext_header );
509
+ }
510
+ }
511
+
512
+ free ( msg->header );
513
+ free ( msg );
514
+ }
515
+
516
+ /**
517
+ * @brief Must be called before calling any other rtp function. It's used
518
+ * to initialize RTP control session.
519
+ *
520
+ * @param payload_type Type of payload used to send. You can use values in toxmsi.h::MSICallType
521
+ * @param messenger Tox* object.
522
+ * @param friend_num Friend id.
523
+ * @return RTPSession* Created control session.
524
+ * @retval NULL Error occurred.
525
+ */
526
+ RTPSession *rtp_init_session ( int payload_type, Messenger *messenger, int friend_num )
527
+ {
528
+ RTPSession *_retu = calloc(1, sizeof(RTPSession));
529
+
530
+ if ( !_retu ) {
531
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
532
+ return NULL;
533
+ }
534
+
535
+ if ( -1 == custom_lossy_packet_registerhandler(messenger, friend_num, payload_type, rtp_handle_packet, _retu)) {
536
+ LOGGER_ERROR("Error setting custom register handler for rtp session");
537
+ free(_retu);
538
+ return NULL;
539
+ }
540
+
541
+ LOGGER_DEBUG("Registered packet handler: pt: %d; fid: %d", payload_type, friend_num);
542
+
543
+ _retu->version = RTP_VERSION; /* It's always 2 */
544
+ _retu->padding = 0; /* If some additional data is needed about the packet */
545
+ _retu->extension = 0; /* If extension to header is needed */
546
+ _retu->cc = 1; /* Amount of contributors */
547
+ _retu->csrc = NULL; /* Container */
548
+ _retu->ssrc = random_int();
549
+ _retu->marker = 0;
550
+ _retu->payload_type = payload_type % 128;
551
+
552
+ _retu->dest = friend_num;
553
+
554
+ _retu->rsequnum = _retu->sequnum = 0;
555
+
556
+ _retu->ext_header = NULL; /* When needed allocate */
557
+
558
+
559
+ if ( !(_retu->csrc = calloc(1, sizeof (uint32_t))) ) {
560
+ LOGGER_WARNING("Alloc failed! Program might misbehave!");
561
+ free(_retu);
562
+ return NULL;
563
+ }
564
+
565
+ _retu->csrc[0] = _retu->ssrc; /* Set my ssrc to the list receive */
566
+
567
+ /* Also set payload type as prefix */
568
+ _retu->prefix = payload_type;
569
+
570
+ /*
571
+ *
572
+ */
573
+ return _retu;
574
+ }
575
+
576
+
577
+ /**
578
+ * @brief Terminate the session.
579
+ *
580
+ * @param session The session.
581
+ * @param messenger The messenger who owns the session
582
+ * @return int
583
+ * @retval -1 Error occurred.
584
+ * @retval 0 Success.
585
+ */
586
+ void rtp_terminate_session ( RTPSession *session, Messenger *messenger )
587
+ {
588
+ if ( !session ) return;
589
+
590
+ custom_lossy_packet_registerhandler(messenger, session->dest, session->prefix, NULL, NULL);
591
+
592
+ free ( session->ext_header );
593
+ free ( session->csrc );
594
+
595
+ LOGGER_DEBUG("Terminated RTP session: %p", session);
596
+
597
+ /* And finally free session */
598
+ free ( session );
599
+
600
+ }