Mercurial > pidgin
annotate src/protocols/gg/lib/pubdir.c @ 12421:f71d6b79ec81
[gaim-migrate @ 14728]
size_t is always unsigned (except perhaps on Unix systems before the introduction of ISO C, which we don't support).
committer: Tailor Script <tailor@pidgin.im>
author | Richard Laager <rlaager@wiktel.com> |
---|---|
date | Thu, 08 Dec 2005 22:27:29 +0000 |
parents | 3c536224f0d0 |
children |
rev | line source |
---|---|
11546
3c536224f0d0
[gaim-migrate @ 13801]
Daniel Atallah <daniel.atallah@gmail.com>
parents:
11360
diff
changeset
|
1 /* $Id: pubdir.c 13801 2005-09-14 19:10:39Z datallah $ */ |
11360 | 2 |
3 /* | |
4 * (C) Copyright 2001-2002 Wojtek Kaniewski <wojtekka@irc.pl> | |
5 * Dawid Jarosz <dawjar@poczta.onet.pl> | |
6 * | |
7 * This program is free software; you can redistribute it and/or modify | |
8 * it under the terms of the GNU Lesser General Public License Version | |
9 * 2.1 as published by the Free Software Foundation. | |
10 * | |
11 * This program is distributed in the hope that it will be useful, | |
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
14 * GNU Lesser General Public License for more details. | |
15 * | |
16 * You should have received a copy of the GNU Lesser General Public | |
17 * License along with this program; if not, write to the Free Software | |
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, | |
19 * USA. | |
20 */ | |
21 | |
22 #include <ctype.h> | |
23 #include <errno.h> | |
24 #include <stdarg.h> | |
25 #include <stdio.h> | |
26 #include <stdlib.h> | |
27 #include <string.h> | |
28 #include <unistd.h> | |
29 | |
30 #include "libgadu.h" | |
31 | |
32 /* | |
33 * gg_register3() | |
34 * | |
35 * rozpoczyna rejestrację użytkownika protokołem GG 6.0. wymaga wcześniejszego | |
36 * pobrania tokenu za pomocą funkcji gg_token(). | |
37 * | |
38 * - email - adres e-mail klienta | |
39 * - password - hasło klienta | |
40 * - tokenid - identyfikator tokenu | |
41 * - tokenval - wartość tokenu | |
42 * - async - połączenie asynchroniczne | |
43 * | |
44 * zaalokowana struct gg_http, którą poźniej należy zwolnić | |
45 * funkcją gg_register_free(), albo NULL jeśli wystąpił błąd. | |
46 */ | |
47 struct gg_http *gg_register3(const char *email, const char *password, const char *tokenid, const char *tokenval, int async) | |
48 { | |
49 struct gg_http *h; | |
50 char *__pwd, *__email, *__tokenid, *__tokenval, *form, *query; | |
51 | |
52 if (!email || !password || !tokenid || !tokenval) { | |
53 gg_debug(GG_DEBUG_MISC, "=> register, NULL parameter\n"); | |
54 errno = EFAULT; | |
55 return NULL; | |
56 } | |
57 | |
58 __pwd = gg_urlencode(password); | |
59 __email = gg_urlencode(email); | |
60 __tokenid = gg_urlencode(tokenid); | |
61 __tokenval = gg_urlencode(tokenval); | |
62 | |
63 if (!__pwd || !__email || !__tokenid || !__tokenval) { | |
64 gg_debug(GG_DEBUG_MISC, "=> register, not enough memory for form fields\n"); | |
65 free(__pwd); | |
66 free(__email); | |
67 free(__tokenid); | |
68 free(__tokenval); | |
69 return NULL; | |
70 } | |
71 | |
72 form = gg_saprintf("pwd=%s&email=%s&tokenid=%s&tokenval=%s&code=%u", | |
73 __pwd, __email, __tokenid, __tokenval, | |
74 gg_http_hash("ss", email, password)); | |
75 | |
76 free(__pwd); | |
77 free(__email); | |
78 free(__tokenid); | |
79 free(__tokenval); | |
80 | |
81 if (!form) { | |
82 gg_debug(GG_DEBUG_MISC, "=> register, not enough memory for form query\n"); | |
83 return NULL; | |
84 } | |
85 | |
86 gg_debug(GG_DEBUG_MISC, "=> register, %s\n", form); | |
87 | |
88 query = gg_saprintf( | |
89 "Host: " GG_REGISTER_HOST "\r\n" | |
90 "Content-Type: application/x-www-form-urlencoded\r\n" | |
91 "User-Agent: " GG_HTTP_USERAGENT "\r\n" | |
92 "Content-Length: %d\r\n" | |
93 "Pragma: no-cache\r\n" | |
94 "\r\n" | |
95 "%s", | |
96 (int) strlen(form), form); | |
97 | |
98 free(form); | |
99 | |
100 if (!query) { | |
101 gg_debug(GG_DEBUG_MISC, "=> register, not enough memory for query\n"); | |
102 return NULL; | |
103 } | |
104 | |
105 if (!(h = gg_http_connect(GG_REGISTER_HOST, GG_REGISTER_PORT, async, "POST", "/appsvc/fmregister3.asp", query))) { | |
106 gg_debug(GG_DEBUG_MISC, "=> register, gg_http_connect() failed mysteriously\n"); | |
107 free(query); | |
108 return NULL; | |
109 } | |
110 | |
111 h->type = GG_SESSION_REGISTER; | |
112 | |
113 free(query); | |
114 | |
115 h->callback = gg_pubdir_watch_fd; | |
116 h->destroy = gg_pubdir_free; | |
117 | |
118 if (!async) | |
119 gg_pubdir_watch_fd(h); | |
120 | |
121 return h; | |
122 } | |
123 | |
124 /* | |
125 * gg_unregister3() | |
126 * | |
127 * usuwa konto użytkownika z serwera protokołem GG 6.0 | |
128 * | |
129 * - uin - numerek GG | |
130 * - password - hasło klienta | |
131 * - tokenid - identyfikator tokenu | |
132 * - tokenval - wartość tokenu | |
133 * - async - połączenie asynchroniczne | |
134 * | |
135 * zaalokowana struct gg_http, którą poźniej należy zwolnić | |
136 * funkcją gg_unregister_free(), albo NULL jeśli wystąpił błąd. | |
137 */ | |
138 struct gg_http *gg_unregister3(uin_t uin, const char *password, const char *tokenid, const char *tokenval, int async) | |
139 { | |
140 struct gg_http *h; | |
141 char *__fmpwd, *__pwd, *__tokenid, *__tokenval, *form, *query; | |
142 | |
143 if (!password || !tokenid || !tokenval) { | |
144 gg_debug(GG_DEBUG_MISC, "=> unregister, NULL parameter\n"); | |
145 errno = EFAULT; | |
146 return NULL; | |
147 } | |
11546
3c536224f0d0
[gaim-migrate @ 13801]
Daniel Atallah <daniel.atallah@gmail.com>
parents:
11360
diff
changeset
|
148 |
11360 | 149 __pwd = gg_saprintf("%ld", random()); |
150 __fmpwd = gg_urlencode(password); | |
151 __tokenid = gg_urlencode(tokenid); | |
152 __tokenval = gg_urlencode(tokenval); | |
153 | |
154 if (!__fmpwd || !__pwd || !__tokenid || !__tokenval) { | |
155 gg_debug(GG_DEBUG_MISC, "=> unregister, not enough memory for form fields\n"); | |
156 free(__pwd); | |
157 free(__fmpwd); | |
158 free(__tokenid); | |
159 free(__tokenval); | |
160 return NULL; | |
161 } | |
162 | |
163 form = gg_saprintf("fmnumber=%d&fmpwd=%s&delete=1&pwd=%s&email=deletedaccount@gadu-gadu.pl&tokenid=%s&tokenval=%s&code=%u", uin, __fmpwd, __pwd, __tokenid, __tokenval, gg_http_hash("ss", "deletedaccount@gadu-gadu.pl", __pwd)); | |
164 | |
165 free(__fmpwd); | |
166 free(__pwd); | |
167 free(__tokenid); | |
168 free(__tokenval); | |
169 | |
170 if (!form) { | |
171 gg_debug(GG_DEBUG_MISC, "=> unregister, not enough memory for form query\n"); | |
172 return NULL; | |
173 } | |
174 | |
175 gg_debug(GG_DEBUG_MISC, "=> unregister, %s\n", form); | |
176 | |
177 query = gg_saprintf( | |
178 "Host: " GG_REGISTER_HOST "\r\n" | |
179 "Content-Type: application/x-www-form-urlencoded\r\n" | |
180 "User-Agent: " GG_HTTP_USERAGENT "\r\n" | |
181 "Content-Length: %d\r\n" | |
182 "Pragma: no-cache\r\n" | |
183 "\r\n" | |
184 "%s", | |
185 (int) strlen(form), form); | |
186 | |
187 free(form); | |
188 | |
189 if (!query) { | |
190 gg_debug(GG_DEBUG_MISC, "=> unregister, not enough memory for query\n"); | |
191 return NULL; | |
192 } | |
193 | |
194 if (!(h = gg_http_connect(GG_REGISTER_HOST, GG_REGISTER_PORT, async, "POST", "/appsvc/fmregister3.asp", query))) { | |
195 gg_debug(GG_DEBUG_MISC, "=> unregister, gg_http_connect() failed mysteriously\n"); | |
196 free(query); | |
197 return NULL; | |
198 } | |
199 | |
200 h->type = GG_SESSION_UNREGISTER; | |
201 | |
202 free(query); | |
203 | |
204 h->callback = gg_pubdir_watch_fd; | |
205 h->destroy = gg_pubdir_free; | |
206 | |
207 if (!async) | |
208 gg_pubdir_watch_fd(h); | |
209 | |
210 return h; | |
211 } | |
212 | |
213 /* | |
214 * gg_change_passwd4() | |
215 * | |
216 * wysyła żądanie zmiany hasła zgodnie z protokołem GG 6.0. wymaga | |
217 * wcześniejszego pobrania tokenu za pomocą funkcji gg_token(). | |
218 * | |
219 * - uin - numer | |
220 * - email - adres e-mail | |
221 * - passwd - stare hasło | |
222 * - newpasswd - nowe hasło | |
223 * - tokenid - identyfikator tokenu | |
224 * - tokenval - wartość tokenu | |
225 * - async - połączenie asynchroniczne | |
226 * | |
227 * zaalokowana struct gg_http, którą poźniej należy zwolnić | |
228 * funkcją gg_change_passwd_free(), albo NULL jeśli wystąpił błąd. | |
229 */ | |
230 struct gg_http *gg_change_passwd4(uin_t uin, const char *email, const char *passwd, const char *newpasswd, const char *tokenid, const char *tokenval, int async) | |
231 { | |
232 struct gg_http *h; | |
233 char *form, *query, *__email, *__fmpwd, *__pwd, *__tokenid, *__tokenval; | |
234 | |
235 if (!uin || !email || !passwd || !newpasswd || !tokenid || !tokenval) { | |
236 gg_debug(GG_DEBUG_MISC, "=> change, NULL parameter\n"); | |
237 errno = EFAULT; | |
238 return NULL; | |
239 } | |
240 | |
241 __fmpwd = gg_urlencode(passwd); | |
242 __pwd = gg_urlencode(newpasswd); | |
243 __email = gg_urlencode(email); | |
244 __tokenid = gg_urlencode(tokenid); | |
245 __tokenval = gg_urlencode(tokenval); | |
246 | |
247 if (!__fmpwd || !__pwd || !__email || !__tokenid || !__tokenval) { | |
248 gg_debug(GG_DEBUG_MISC, "=> change, not enough memory for form fields\n"); | |
249 free(__fmpwd); | |
250 free(__pwd); | |
251 free(__email); | |
252 free(__tokenid); | |
253 free(__tokenval); | |
254 return NULL; | |
255 } | |
256 | |
257 if (!(form = gg_saprintf("fmnumber=%d&fmpwd=%s&pwd=%s&email=%s&tokenid=%s&tokenval=%s&code=%u", uin, __fmpwd, __pwd, __email, __tokenid, __tokenval, gg_http_hash("ss", email, newpasswd)))) { | |
258 gg_debug(GG_DEBUG_MISC, "=> change, not enough memory for form fields\n"); | |
259 free(__fmpwd); | |
260 free(__pwd); | |
261 free(__email); | |
262 free(__tokenid); | |
263 free(__tokenval); | |
264 | |
265 return NULL; | |
266 } | |
267 | |
268 free(__fmpwd); | |
269 free(__pwd); | |
270 free(__email); | |
271 free(__tokenid); | |
272 free(__tokenval); | |
273 | |
274 gg_debug(GG_DEBUG_MISC, "=> change, %s\n", form); | |
275 | |
276 query = gg_saprintf( | |
277 "Host: " GG_REGISTER_HOST "\r\n" | |
278 "Content-Type: application/x-www-form-urlencoded\r\n" | |
279 "User-Agent: " GG_HTTP_USERAGENT "\r\n" | |
280 "Content-Length: %d\r\n" | |
281 "Pragma: no-cache\r\n" | |
282 "\r\n" | |
283 "%s", | |
284 (int) strlen(form), form); | |
285 | |
286 free(form); | |
287 | |
288 if (!query) { | |
289 gg_debug(GG_DEBUG_MISC, "=> change, not enough memory for query\n"); | |
290 return NULL; | |
291 } | |
292 | |
293 if (!(h = gg_http_connect(GG_REGISTER_HOST, GG_REGISTER_PORT, async, "POST", "/appsvc/fmregister3.asp", query))) { | |
294 gg_debug(GG_DEBUG_MISC, "=> change, gg_http_connect() failed mysteriously\n"); | |
295 free(query); | |
296 return NULL; | |
297 } | |
298 | |
299 h->type = GG_SESSION_PASSWD; | |
300 | |
301 free(query); | |
302 | |
303 h->callback = gg_pubdir_watch_fd; | |
304 h->destroy = gg_pubdir_free; | |
305 | |
306 if (!async) | |
307 gg_pubdir_watch_fd(h); | |
308 | |
309 return h; | |
310 } | |
311 | |
312 /* | |
313 * gg_remind_passwd3() | |
314 * | |
315 * wysyła żądanie przypomnienia hasła e-mailem. | |
316 * | |
317 * - uin - numer | |
318 * - email - adres e-mail taki, jak ten zapisany na serwerze | |
319 * - async - połączenie asynchroniczne | |
320 * - tokenid - identyfikator tokenu | |
321 * - tokenval - wartość tokenu | |
322 * | |
323 * zaalokowana struct gg_http, którą poźniej należy zwolnić | |
324 * funkcją gg_remind_passwd_free(), albo NULL jeśli wystąpił błąd. | |
325 */ | |
326 struct gg_http *gg_remind_passwd3(uin_t uin, const char *email, const char *tokenid, const char *tokenval, int async) | |
327 { | |
328 struct gg_http *h; | |
329 char *form, *query, *__tokenid, *__tokenval, *__email; | |
330 | |
331 if (!tokenid || !tokenval || !email) { | |
332 gg_debug(GG_DEBUG_MISC, "=> remind, NULL parameter\n"); | |
333 errno = EFAULT; | |
334 return NULL; | |
335 } | |
336 | |
337 __tokenid = gg_urlencode(tokenid); | |
338 __tokenval = gg_urlencode(tokenval); | |
339 __email = gg_urlencode(email); | |
340 | |
341 if (!__tokenid || !__tokenval || !__email) { | |
342 gg_debug(GG_DEBUG_MISC, "=> remind, not enough memory for form fields\n"); | |
343 free(__tokenid); | |
344 free(__tokenval); | |
345 free(__email); | |
346 return NULL; | |
347 } | |
348 | |
349 if (!(form = gg_saprintf("userid=%d&code=%u&tokenid=%s&tokenval=%s&email=%s", uin, gg_http_hash("u", uin), __tokenid, __tokenval, __email))) { | |
350 gg_debug(GG_DEBUG_MISC, "=> remind, not enough memory for form fields\n"); | |
351 free(__tokenid); | |
352 free(__tokenval); | |
353 free(__email); | |
354 return NULL; | |
355 } | |
356 | |
357 free(__tokenid); | |
358 free(__tokenval); | |
359 free(__email); | |
360 | |
361 gg_debug(GG_DEBUG_MISC, "=> remind, %s\n", form); | |
362 | |
363 query = gg_saprintf( | |
364 "Host: " GG_REMIND_HOST "\r\n" | |
365 "Content-Type: application/x-www-form-urlencoded\r\n" | |
366 "User-Agent: " GG_HTTP_USERAGENT "\r\n" | |
367 "Content-Length: %d\r\n" | |
368 "Pragma: no-cache\r\n" | |
369 "\r\n" | |
370 "%s", | |
371 (int) strlen(form), form); | |
372 | |
373 free(form); | |
374 | |
375 if (!query) { | |
376 gg_debug(GG_DEBUG_MISC, "=> remind, not enough memory for query\n"); | |
377 return NULL; | |
378 } | |
379 | |
380 if (!(h = gg_http_connect(GG_REMIND_HOST, GG_REMIND_PORT, async, "POST", "/appsvc/fmsendpwd3.asp", query))) { | |
381 gg_debug(GG_DEBUG_MISC, "=> remind, gg_http_connect() failed mysteriously\n"); | |
382 free(query); | |
383 return NULL; | |
384 } | |
385 | |
386 h->type = GG_SESSION_REMIND; | |
387 | |
388 free(query); | |
389 | |
390 h->callback = gg_pubdir_watch_fd; | |
391 h->destroy = gg_pubdir_free; | |
392 | |
393 if (!async) | |
394 gg_pubdir_watch_fd(h); | |
395 | |
396 return h; | |
397 } | |
398 | |
399 /* | |
400 * gg_pubdir_watch_fd() | |
401 * | |
402 * przy asynchronicznych operacjach na katalogu publicznym należy wywoływać | |
403 * tę funkcję przy zmianach na obserwowanym deskryptorze. | |
404 * | |
405 * - h - struktura opisująca połączenie | |
406 * | |
407 * jeśli wszystko poszło dobrze to 0, inaczej -1. operacja będzie | |
408 * zakończona, jeśli h->state == GG_STATE_DONE. jeśli wystąpi jakiś | |
409 * błąd, to będzie tam GG_STATE_ERROR i odpowiedni kod błędu w h->error. | |
410 */ | |
411 int gg_pubdir_watch_fd(struct gg_http *h) | |
412 { | |
413 struct gg_pubdir *p; | |
414 char *tmp; | |
415 | |
416 if (!h) { | |
417 errno = EFAULT; | |
418 return -1; | |
419 } | |
420 | |
421 if (h->state == GG_STATE_ERROR) { | |
422 gg_debug(GG_DEBUG_MISC, "=> pubdir, watch_fd issued on failed session\n"); | |
423 errno = EINVAL; | |
424 return -1; | |
425 } | |
426 | |
427 if (h->state != GG_STATE_PARSING) { | |
428 if (gg_http_watch_fd(h) == -1) { | |
429 gg_debug(GG_DEBUG_MISC, "=> pubdir, http failure\n"); | |
430 errno = EINVAL; | |
431 return -1; | |
432 } | |
433 } | |
434 | |
435 if (h->state != GG_STATE_PARSING) | |
436 return 0; | |
437 | |
438 h->state = GG_STATE_DONE; | |
439 | |
440 if (!(h->data = p = malloc(sizeof(struct gg_pubdir)))) { | |
441 gg_debug(GG_DEBUG_MISC, "=> pubdir, not enough memory for results\n"); | |
442 return -1; | |
443 } | |
444 | |
445 p->success = 0; | |
446 p->uin = 0; | |
447 | |
448 gg_debug(GG_DEBUG_MISC, "=> pubdir, let's parse \"%s\"\n", h->body); | |
449 | |
450 if ((tmp = strstr(h->body, "success")) || (tmp = strstr(h->body, "results"))) { | |
451 p->success = 1; | |
452 if (tmp[7] == ':') | |
453 p->uin = strtol(tmp + 8, NULL, 0); | |
454 gg_debug(GG_DEBUG_MISC, "=> pubdir, success (uin=%d)\n", p->uin); | |
455 } else | |
456 gg_debug(GG_DEBUG_MISC, "=> pubdir, error.\n"); | |
457 | |
458 return 0; | |
459 } | |
460 | |
461 /* | |
462 * gg_pubdir_free() | |
463 * | |
464 * zwalnia pamięć po efektach operacji na katalogu publicznym. | |
465 * | |
466 * - h - zwalniana struktura | |
467 */ | |
468 void gg_pubdir_free(struct gg_http *h) | |
469 { | |
470 if (!h) | |
471 return; | |
472 | |
473 free(h->data); | |
474 gg_http_free(h); | |
475 } | |
476 | |
477 /* | |
478 * gg_token() | |
479 * | |
480 * pobiera z serwera token do autoryzacji zakładania konta, usuwania | |
481 * konta i zmiany hasła. | |
482 * | |
483 * zaalokowana struct gg_http, którą poźniej należy zwolnić | |
484 * funkcją gg_token_free(), albo NULL jeśli wystąpił błąd. | |
485 */ | |
486 struct gg_http *gg_token(int async) | |
487 { | |
488 struct gg_http *h; | |
489 const char *query; | |
490 | |
491 query = "Host: " GG_REGISTER_HOST "\r\n" | |
492 "Content-Type: application/x-www-form-urlencoded\r\n" | |
493 "User-Agent: " GG_HTTP_USERAGENT "\r\n" | |
494 "Content-Length: 0\r\n" | |
495 "Pragma: no-cache\r\n" | |
496 "\r\n"; | |
497 | |
498 if (!(h = gg_http_connect(GG_REGISTER_HOST, GG_REGISTER_PORT, async, "POST", "/appsvc/regtoken.asp", query))) { | |
499 gg_debug(GG_DEBUG_MISC, "=> token, gg_http_connect() failed mysteriously\n"); | |
500 return NULL; | |
501 } | |
502 | |
503 h->type = GG_SESSION_TOKEN; | |
504 | |
505 h->callback = gg_token_watch_fd; | |
506 h->destroy = gg_token_free; | |
507 | |
508 if (!async) | |
509 gg_token_watch_fd(h); | |
510 | |
511 return h; | |
512 } | |
513 | |
514 /* | |
515 * gg_token_watch_fd() | |
516 * | |
517 * przy asynchronicznych operacjach związanych z tokenem należy wywoływać | |
518 * tę funkcję przy zmianach na obserwowanym deskryptorze. | |
519 * | |
520 * - h - struktura opisująca połączenie | |
521 * | |
522 * jeśli wszystko poszło dobrze to 0, inaczej -1. operacja będzie | |
523 * zakończona, jeśli h->state == GG_STATE_DONE. jeśli wystąpi jakiś | |
524 * błąd, to będzie tam GG_STATE_ERROR i odpowiedni kod błędu w h->error. | |
525 */ | |
526 int gg_token_watch_fd(struct gg_http *h) | |
527 { | |
528 if (!h) { | |
529 errno = EFAULT; | |
530 return -1; | |
531 } | |
532 | |
533 if (h->state == GG_STATE_ERROR) { | |
534 gg_debug(GG_DEBUG_MISC, "=> token, watch_fd issued on failed session\n"); | |
535 errno = EINVAL; | |
536 return -1; | |
537 } | |
538 | |
539 if (h->state != GG_STATE_PARSING) { | |
540 if (gg_http_watch_fd(h) == -1) { | |
541 gg_debug(GG_DEBUG_MISC, "=> token, http failure\n"); | |
542 errno = EINVAL; | |
543 return -1; | |
544 } | |
545 } | |
546 | |
547 if (h->state != GG_STATE_PARSING) | |
548 return 0; | |
549 | |
550 /* jeśli h->data jest puste, to ściągaliśmy tokenid i url do niego, | |
551 * ale jeśli coś tam jest, to znaczy, że mamy drugi etap polegający | |
552 * na pobieraniu tokenu. */ | |
553 if (!h->data) { | |
554 int width, height, length; | |
555 char *url = NULL, *tokenid = NULL, *path, *headers; | |
556 const char *host; | |
557 struct gg_http *h2; | |
558 struct gg_token *t; | |
559 | |
560 gg_debug(GG_DEBUG_MISC, "=> token body \"%s\"\n", h->body); | |
561 | |
562 if (h->body && (!(url = malloc(strlen(h->body))) || !(tokenid = malloc(strlen(h->body))))) { | |
563 gg_debug(GG_DEBUG_MISC, "=> token, not enough memory for results\n"); | |
564 free(url); | |
565 return -1; | |
566 } | |
567 | |
568 if (!h->body || sscanf(h->body, "%d %d %d\r\n%s\r\n%s", &width, &height, &length, tokenid, url) != 5) { | |
569 gg_debug(GG_DEBUG_MISC, "=> token, parsing failed\n"); | |
570 free(url); | |
571 free(tokenid); | |
572 errno = EINVAL; | |
573 return -1; | |
574 } | |
575 | |
576 /* dostaliśmy tokenid i wszystkie niezbędne informacje, | |
577 * więc pobierzmy obrazek z tokenem */ | |
578 | |
579 if (strncmp(url, "http://", 7)) { | |
580 path = gg_saprintf("%s?tokenid=%s", url, tokenid); | |
581 host = GG_REGISTER_HOST; | |
582 } else { | |
583 char *slash = strchr(url + 7, '/'); | |
584 | |
585 if (slash) { | |
586 path = gg_saprintf("%s?tokenid=%s", slash, tokenid); | |
587 *slash = 0; | |
588 host = url + 7; | |
589 } else { | |
590 gg_debug(GG_DEBUG_MISC, "=> token, url parsing failed\n"); | |
591 free(url); | |
592 free(tokenid); | |
593 errno = EINVAL; | |
594 return -1; | |
595 } | |
596 } | |
597 | |
598 if (!path) { | |
599 gg_debug(GG_DEBUG_MISC, "=> token, not enough memory for token url\n"); | |
600 free(url); | |
601 free(tokenid); | |
602 return -1; | |
603 } | |
604 | |
605 if (!(headers = gg_saprintf("Host: %s\r\nUser-Agent: " GG_HTTP_USERAGENT "\r\n\r\n", host))) { | |
606 gg_debug(GG_DEBUG_MISC, "=> token, not enough memory for token url\n"); | |
607 free(path); | |
608 free(url); | |
609 free(tokenid); | |
610 return -1; | |
611 } | |
612 | |
613 if (!(h2 = gg_http_connect(host, GG_REGISTER_PORT, h->async, "GET", path, headers))) { | |
614 gg_debug(GG_DEBUG_MISC, "=> token, gg_http_connect() failed mysteriously\n"); | |
615 free(headers); | |
616 free(url); | |
617 free(path); | |
618 free(tokenid); | |
619 return -1; | |
620 } | |
621 | |
622 free(headers); | |
623 free(path); | |
624 free(url); | |
625 | |
626 memcpy(h, h2, sizeof(struct gg_http)); | |
627 free(h2); | |
628 | |
629 h->type = GG_SESSION_TOKEN; | |
630 | |
631 h->callback = gg_token_watch_fd; | |
632 h->destroy = gg_token_free; | |
633 | |
634 if (!h->async) | |
635 gg_token_watch_fd(h); | |
636 | |
637 if (!(h->data = t = malloc(sizeof(struct gg_token)))) { | |
638 gg_debug(GG_DEBUG_MISC, "=> token, not enough memory for token data\n"); | |
639 free(tokenid); | |
640 return -1; | |
641 } | |
642 | |
643 t->width = width; | |
644 t->height = height; | |
645 t->length = length; | |
646 t->tokenid = tokenid; | |
647 } else { | |
648 /* obrazek mamy w h->body */ | |
649 h->state = GG_STATE_DONE; | |
650 } | |
651 | |
652 return 0; | |
653 } | |
654 | |
655 /* | |
656 * gg_token_free() | |
657 * | |
658 * zwalnia pamięć po efektach pobierania tokenu. | |
659 * | |
660 * - h - zwalniana struktura | |
661 */ | |
662 void gg_token_free(struct gg_http *h) | |
663 { | |
664 struct gg_token *t; | |
665 | |
666 if (!h) | |
667 return; | |
668 | |
669 if ((t = h->data)) | |
670 free(t->tokenid); | |
671 | |
672 free(h->data); | |
673 gg_http_free(h); | |
674 } | |
675 | |
676 /* | |
677 * Local variables: | |
678 * c-indentation-style: k&r | |
679 * c-basic-offset: 8 | |
680 * indent-tabs-mode: notnil | |
681 * End: | |
682 * | |
683 * vim: shiftwidth=8: | |
684 */ |