comparison libpurple/util.c @ 28252:9358464cdf6a

How about we just use a GString instead of this ridiculous RECOVER_MARKED_TEXT macro?
author Mark Doliner <mark@kingant.net>
date Thu, 13 Aug 2009 20:16:23 +0000
parents da22b6d0151e
children 90d108cda54e 703b20fa6c5c
comparison
equal deleted inserted replaced
28251:5f49b2dd8f9b 28252:9358464cdf6a
403 state_encoded_text, state_question4, state_equal2 = state_start 403 state_encoded_text, state_question4, state_equal2 = state_start
404 } encoded_word_state_t; 404 } encoded_word_state_t;
405 encoded_word_state_t state = state_start; 405 encoded_word_state_t state = state_start;
406 const char *cur, *mark; 406 const char *cur, *mark;
407 const char *charset0 = NULL, *encoding0 = NULL, *encoded_text0 = NULL; 407 const char *charset0 = NULL, *encoding0 = NULL, *encoded_text0 = NULL;
408 char *n, *new; 408 GString *new;
409 409
410 /* token can be any CHAR (supposedly ISO8859-1/ISO2022), not just ASCII */ 410 /* token can be any CHAR (supposedly ISO8859-1/ISO2022), not just ASCII */
411 #define token_char_p(c) \ 411 #define token_char_p(c) \
412 (c != ' ' && !iscntrl(c) && !strchr("()<>@,;:\"/[]?.=", c)) 412 (c != ' ' && !iscntrl(c) && !strchr("()<>@,;:\"/[]?.=", c))
413 413
414 /* But encoded-text must be ASCII; alas, isascii() may not exist */ 414 /* But encoded-text must be ASCII; alas, isascii() may not exist */
415 #define encoded_text_char_p(c) \ 415 #define encoded_text_char_p(c) \
416 ((c & 0x80) == 0 && c != '?' && c != ' ' && isgraph(c)) 416 ((c & 0x80) == 0 && c != '?' && c != ' ' && isgraph(c))
417 417
418 #define RECOVER_MARKED_TEXT strncpy(n, mark, cur - mark + 1); \
419 n += cur - mark + 1
420
421 g_return_val_if_fail(str != NULL, NULL); 418 g_return_val_if_fail(str != NULL, NULL);
422 419
423 /* NOTE: Assuming that we need just strlen(str)+1 *may* be wrong. 420 new = g_string_new(NULL);
424 * It would be wrong if one byte (in some unknown encoding) could
425 * expand to >=4 bytes of UTF-8; I don't know if there are such things.
426 */
427 n = new = g_malloc(strlen(str) + 1);
428 421
429 /* Here we will be looking for encoded words and if they seem to be 422 /* Here we will be looking for encoded words and if they seem to be
430 * valid then decode them. 423 * valid then decode them.
431 * They are of this form: =?charset?encoding?text?= 424 * They are of this form: =?charset?encoding?text?=
432 */ 425 */
435 switch (state) { 428 switch (state) {
436 case state_equal1: 429 case state_equal1:
437 if (*cur == '?') { 430 if (*cur == '?') {
438 state = state_question1; 431 state = state_question1;
439 } else { 432 } else {
440 RECOVER_MARKED_TEXT; 433 g_string_append_len(new, mark, cur - mark + 1);
441 state = state_start; 434 state = state_start;
442 } 435 }
443 break; 436 break;
444 case state_question1: 437 case state_question1:
445 if (token_char_p(*cur)) { 438 if (token_char_p(*cur)) {
446 charset0 = cur; 439 charset0 = cur;
447 state = state_charset; 440 state = state_charset;
448 } else { /* This should never happen */ 441 } else { /* This should never happen */
449 RECOVER_MARKED_TEXT; 442 g_string_append_len(new, mark, cur - mark + 1);
450 state = state_start; 443 state = state_start;
451 } 444 }
452 break; 445 break;
453 case state_charset: 446 case state_charset:
454 if (*cur == '?') { 447 if (*cur == '?') {
455 state = state_question2; 448 state = state_question2;
456 } else if (!token_char_p(*cur)) { /* This should never happen */ 449 } else if (!token_char_p(*cur)) { /* This should never happen */
457 RECOVER_MARKED_TEXT; 450 g_string_append_len(new, mark, cur - mark + 1);
458 state = state_start; 451 state = state_start;
459 } 452 }
460 break; 453 break;
461 case state_question2: 454 case state_question2:
462 if (token_char_p(*cur)) { 455 if (token_char_p(*cur)) {
463 encoding0 = cur; 456 encoding0 = cur;
464 state = state_encoding; 457 state = state_encoding;
465 } else { /* This should never happen */ 458 } else { /* This should never happen */
466 RECOVER_MARKED_TEXT; 459 g_string_append_len(new, mark, cur - mark + 1);
467 state = state_start; 460 state = state_start;
468 } 461 }
469 break; 462 break;
470 case state_encoding: 463 case state_encoding:
471 if (*cur == '?') { 464 if (*cur == '?') {
472 state = state_question3; 465 state = state_question3;
473 } else if (!token_char_p(*cur)) { /* This should never happen */ 466 } else if (!token_char_p(*cur)) { /* This should never happen */
474 RECOVER_MARKED_TEXT; 467 g_string_append_len(new, mark, cur - mark + 1);
475 state = state_start; 468 state = state_start;
476 } 469 }
477 break; 470 break;
478 case state_question3: 471 case state_question3:
479 if (encoded_text_char_p(*cur)) { 472 if (encoded_text_char_p(*cur)) {
481 state = state_encoded_text; 474 state = state_encoded_text;
482 } else if (*cur == '?') { /* empty string */ 475 } else if (*cur == '?') { /* empty string */
483 encoded_text0 = cur; 476 encoded_text0 = cur;
484 state = state_question4; 477 state = state_question4;
485 } else { /* This should never happen */ 478 } else { /* This should never happen */
486 RECOVER_MARKED_TEXT; 479 g_string_append_len(new, mark, cur - mark + 1);
487 state = state_start; 480 state = state_start;
488 } 481 }
489 break; 482 break;
490 case state_encoded_text: 483 case state_encoded_text:
491 if (*cur == '?') { 484 if (*cur == '?') {
492 state = state_question4; 485 state = state_question4;
493 } else if (!encoded_text_char_p(*cur)) { 486 } else if (!encoded_text_char_p(*cur)) {
494 RECOVER_MARKED_TEXT; 487 g_string_append_len(new, mark, cur - mark + 1);
495 state = state_start; 488 state = state_start;
496 } 489 }
497 break; 490 break;
498 case state_question4: 491 case state_question4:
499 if (*cur == '=') { /* Got the whole encoded-word */ 492 if (*cur == '=') { /* Got the whole encoded-word */
511 if (decoded) { 504 if (decoded) {
512 gsize len; 505 gsize len;
513 char *converted = g_convert((const gchar *)decoded, dec_len, "utf-8", charset, NULL, &len, NULL); 506 char *converted = g_convert((const gchar *)decoded, dec_len, "utf-8", charset, NULL, &len, NULL);
514 507
515 if (converted) { 508 if (converted) {
516 n = strncpy(n, converted, len) + len; 509 g_string_append_len(new, converted, len);
517 g_free(converted); 510 g_free(converted);
518 } 511 }
519 g_free(decoded); 512 g_free(decoded);
520 } 513 }
521 g_free(charset); 514 g_free(charset);
522 g_free(encoding); 515 g_free(encoding);
523 g_free(encoded_text); 516 g_free(encoded_text);
524 state = state_equal2; /* Restart the FSM */ 517 state = state_equal2; /* Restart the FSM */
525 } else { /* This should never happen */ 518 } else { /* This should never happen */
526 RECOVER_MARKED_TEXT; 519 g_string_append_len(new, mark, cur - mark + 1);
527 state = state_start; 520 state = state_start;
528 } 521 }
529 break; 522 break;
530 default: 523 default:
531 if (*cur == '=') { 524 if (*cur == '=') {
532 mark = cur; 525 mark = cur;
533 state = state_equal1; 526 state = state_equal1;
534 } else { 527 } else {
535 /* Some unencoded text. */ 528 /* Some unencoded text. */
536 *n = *cur; 529 g_string_append_c(new, *cur);
537 n += 1;
538 } 530 }
539 break; 531 break;
540 } /* switch */ 532 } /* switch */
541 } /* for */ 533 } /* for */
542 534
543 if (state != state_start) { 535 if (state != state_start)
544 RECOVER_MARKED_TEXT; 536 g_string_append_len(new, mark, cur - mark + 1);
545 } 537
546 *n = '\0'; 538 return g_string_free(new, FALSE);;
547
548 return new;
549 } 539 }
550 540
551 541
552 /************************************************************************** 542 /**************************************************************************
553 * Date/Time Functions 543 * Date/Time Functions