media/mtransport/third_party/nICEr/src/stun/stun_msg.c

branch
TOR_BUG_9701
changeset 8
97036ab72558
equal deleted inserted replaced
-1:000000000000 0:0761e37c687a
1 /*
2 Copyright (c) 2007, Adobe Systems, Incorporated
3 All rights reserved.
4
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions are
7 met:
8
9 * Redistributions of source code must retain the above copyright
10 notice, this list of conditions and the following disclaimer.
11
12 * Redistributions in binary form must reproduce the above copyright
13 notice, this list of conditions and the following disclaimer in the
14 documentation and/or other materials provided with the distribution.
15
16 * Neither the name of Adobe Systems, Network Resonance nor the names of its
17 contributors may be used to endorse or promote products derived from
18 this software without specific prior written permission.
19
20 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21 "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23 A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24 OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25 SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26 LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 */
32
33
34 static char *RCSSTRING __UNUSED__="$Id: stun_msg.c,v 1.2 2008/04/28 18:21:30 ekr Exp $";
35
36 #include <errno.h>
37 #include <csi_platform.h>
38
39 #ifdef WIN32
40 #include <winsock2.h>
41 #include <stdlib.h>
42 #include <io.h>
43 #include <time.h>
44 #else /* UNIX */
45 #include <string.h>
46 #endif /* end UNIX */
47 #include <assert.h>
48
49 #include "stun.h"
50
51
52 int
53 nr_stun_message_create(nr_stun_message **msg)
54 {
55 int _status;
56 nr_stun_message *m = 0;
57
58 m = RCALLOC(sizeof(*m));
59 if (!m)
60 ABORT(R_NO_MEMORY);
61
62 TAILQ_INIT(&m->attributes);
63
64 *msg = m;
65
66 _status=0;
67 abort:
68 return(_status);
69 }
70
71 int
72 nr_stun_message_create2(nr_stun_message **msg, UCHAR *buffer, int length)
73 {
74 int r,_status;
75 nr_stun_message *m = 0;
76
77 if (length > sizeof(m->buffer)) {
78 ABORT(R_BAD_DATA);
79 }
80
81 if ((r=nr_stun_message_create(&m)))
82 ABORT(r);
83
84 memcpy(m->buffer, buffer, length);
85 m->length = length;
86
87 *msg = m;
88
89 _status=0;
90 abort:
91 return(_status);
92 }
93
94 int
95 nr_stun_message_destroy(nr_stun_message **msg)
96 {
97 int _status;
98 nr_stun_message_attribute_head *attrs;
99 nr_stun_message_attribute *attr;
100
101 if (msg && *msg) {
102 attrs = &(*msg)->attributes;
103 while (!TAILQ_EMPTY(attrs)) {
104 attr = TAILQ_FIRST(attrs);
105 nr_stun_message_attribute_destroy(*msg, &attr);
106 }
107
108 RFREE(*msg);
109
110 *msg = 0;
111 }
112
113 _status=0;
114 /* abort: */
115 return(_status);
116 }
117
118 int
119 nr_stun_message_attribute_create(nr_stun_message *msg, nr_stun_message_attribute **attr)
120 {
121 int _status;
122 nr_stun_message_attribute *a = 0;
123
124 a = RCALLOC(sizeof(*a));
125 if (!a)
126 ABORT(R_NO_MEMORY);
127
128 TAILQ_INSERT_TAIL(&msg->attributes, a, entry);
129
130 *attr = a;
131
132 _status=0;
133 abort:
134 return(_status);
135 }
136
137 int
138 nr_stun_message_attribute_destroy(nr_stun_message *msg, nr_stun_message_attribute **attr)
139 {
140 int _status;
141 nr_stun_message_attribute *a = 0;
142
143 if (attr && *attr) {
144 a = *attr;
145 TAILQ_REMOVE(&msg->attributes, a, entry);
146
147 RFREE(a);
148
149 *attr = 0;
150 }
151
152 _status=0;
153 /* abort: */
154 return(_status);
155 }
156
157 int
158 nr_stun_message_has_attribute(nr_stun_message *msg, UINT2 type, nr_stun_message_attribute **attribute)
159 {
160 nr_stun_message_attribute *attr = 0;
161
162 if (attribute)
163 *attribute = 0;
164
165 TAILQ_FOREACH(attr, &msg->attributes, entry) {
166 if (attr->type == type)
167 break;
168 }
169
170 if (!attr || attr->invalid)
171 return 0; /* does not have */
172
173 if (attribute)
174 *attribute = attr;
175
176 return 1; /* has */
177 }
178
179 #define NR_STUN_MESSAGE_ADD_ATTRIBUTE(__type, __code) \
180 { \
181 int r,_status; \
182 nr_stun_message_attribute *attr = 0; \
183 if ((r=nr_stun_message_attribute_create(msg, &attr))) \
184 ABORT(r); \
185 attr->type = (__type); \
186 { __code } \
187 _status=0; \
188 abort: \
189 if (_status) RFREE(attr); \
190 return(_status); \
191 }
192
193
194 int
195 nr_stun_message_add_alternate_server_attribute(nr_stun_message *msg, nr_transport_addr *alternate_server)
196 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
197 NR_STUN_ATTR_ALTERNATE_SERVER,
198 {
199 if ((r=nr_transport_addr_copy(&attr->u.alternate_server, alternate_server)))
200 ABORT(r);
201 }
202 )
203
204 int
205 nr_stun_message_add_error_code_attribute(nr_stun_message *msg, UINT2 number, char *reason)
206 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
207 NR_STUN_ATTR_ERROR_CODE,
208 {
209 attr->u.error_code.number = number;
210 strlcpy(attr->u.error_code.reason, reason, sizeof(attr->u.error_code.reason));
211 }
212 )
213
214 int
215 nr_stun_message_add_fingerprint_attribute(nr_stun_message *msg)
216 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
217 NR_STUN_ATTR_FINGERPRINT,
218 {}
219 )
220
221 int
222 nr_stun_message_add_message_integrity_attribute(nr_stun_message *msg, Data *password)
223 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
224 NR_STUN_ATTR_MESSAGE_INTEGRITY,
225 {
226 if (sizeof(attr->u.message_integrity.password) < password->len)
227 ABORT(R_BAD_DATA);
228
229 memcpy(attr->u.message_integrity.password, password->data, password->len);
230 attr->u.message_integrity.passwordlen = password->len;
231 }
232 )
233
234 int
235 nr_stun_message_add_nonce_attribute(nr_stun_message *msg, char *nonce)
236 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
237 NR_STUN_ATTR_NONCE,
238 { strlcpy(attr->u.nonce, nonce, sizeof(attr->u.nonce)); }
239 )
240
241 int
242 nr_stun_message_add_realm_attribute(nr_stun_message *msg, char *realm)
243 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
244 NR_STUN_ATTR_REALM,
245 { strlcpy(attr->u.realm, realm, sizeof(attr->u.realm)); }
246 )
247
248 int
249 nr_stun_message_add_server_attribute(nr_stun_message *msg, char *server_name)
250 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
251 NR_STUN_ATTR_SERVER,
252 { strlcpy(attr->u.server_name, server_name, sizeof(attr->u.server_name)); }
253 )
254
255 int
256 nr_stun_message_add_unknown_attributes_attribute(nr_stun_message *msg, nr_stun_attr_unknown_attributes *unknown_attributes)
257 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
258 NR_STUN_ATTR_UNKNOWN_ATTRIBUTES,
259 { memcpy(&attr->u.unknown_attributes, unknown_attributes, sizeof(attr->u.unknown_attributes)); }
260 )
261
262 int
263 nr_stun_message_add_username_attribute(nr_stun_message *msg, char *username)
264 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
265 NR_STUN_ATTR_USERNAME,
266 { strlcpy(attr->u.username, username, sizeof(attr->u.username)); }
267 )
268
269 int
270 nr_stun_message_add_requested_transport_attribute(nr_stun_message *msg, UCHAR protocol)
271 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
272 NR_STUN_ATTR_REQUESTED_TRANSPORT,
273 { attr->u.requested_transport = protocol; }
274 )
275
276 int
277 nr_stun_message_add_xor_mapped_address_attribute(nr_stun_message *msg, nr_transport_addr *mapped_address)
278 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
279 NR_STUN_ATTR_XOR_MAPPED_ADDRESS,
280 {
281 if ((r=nr_transport_addr_copy(&attr->u.xor_mapped_address.unmasked, mapped_address)))
282 ABORT(r);
283 }
284 )
285
286 int
287 nr_stun_message_add_xor_peer_address_attribute(nr_stun_message *msg, nr_transport_addr *peer_address)
288 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
289 NR_STUN_ATTR_XOR_PEER_ADDRESS,
290 {
291 if ((r=nr_transport_addr_copy(&attr->u.xor_mapped_address.unmasked, peer_address)))
292 ABORT(r);
293 }
294 )
295
296 #ifdef USE_ICE
297 int
298 nr_stun_message_add_ice_controlled_attribute(nr_stun_message *msg, UINT8 ice_controlled)
299 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
300 NR_STUN_ATTR_ICE_CONTROLLED,
301 { attr->u.ice_controlled = ice_controlled; }
302 )
303
304 int
305 nr_stun_message_add_ice_controlling_attribute(nr_stun_message *msg, UINT8 ice_controlling)
306 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
307 NR_STUN_ATTR_ICE_CONTROLLING,
308 { attr->u.ice_controlling = ice_controlling; }
309 )
310
311 int
312 nr_stun_message_add_priority_attribute(nr_stun_message *msg, UINT4 priority)
313 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
314 NR_STUN_ATTR_PRIORITY,
315 { attr->u.priority = priority; }
316 )
317
318 int
319 nr_stun_message_add_use_candidate_attribute(nr_stun_message *msg)
320 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
321 NR_STUN_ATTR_USE_CANDIDATE,
322 {}
323 )
324 #endif /* USE_ICE */
325
326 #ifdef USE_TURN
327 int
328 nr_stun_message_add_data_attribute(nr_stun_message *msg, UCHAR *data, int length)
329
330 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
331 NR_STUN_ATTR_DATA,
332 {
333 if (length > NR_STUN_MAX_MESSAGE_SIZE)
334 ABORT(R_BAD_ARGS);
335
336 memcpy(attr->u.data.data, data, length);
337 attr->u.data.length=length;
338 }
339 )
340
341 int
342 nr_stun_message_add_lifetime_attribute(nr_stun_message *msg, UINT4 lifetime_secs)
343 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
344 NR_STUN_ATTR_LIFETIME,
345 { attr->u.lifetime_secs = lifetime_secs; }
346 )
347
348 #endif /* USE_TURN */
349
350 #ifdef USE_STUND_0_96
351 int
352 nr_stun_message_add_change_request_attribute(nr_stun_message *msg, UINT4 change_request)
353 NR_STUN_MESSAGE_ADD_ATTRIBUTE(
354 NR_STUN_ATTR_OLD_CHANGE_REQUEST,
355 { attr->u.change_request = change_request; }
356 )
357 #endif /* USE_STUND_0_96 */
358

mercurial