Changes in protocols/jabber/jabber_util.c [9da0bbf:f0cb961]
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
protocols/jabber/jabber_util.c
r9da0bbf rf0cb961 48 48 call p_s_u() now to send the new prio setting, it would 49 49 send the old setting because the set->value gets changed 50 after the (this)eval returns a non-NULL value.50 when the eval returns a non-NULL value. 51 51 52 52 So now I can choose between implementing post-set … … 129 129 /* Cache a node/packet for later use. Mainly useful for IQ packets if you need 130 130 them when you receive the response. Use this BEFORE sending the packet so 131 it'll get a new id= tag, and do NOT free() the packet after sending it! */131 it'll get a new id= tag, and do NOT free() the packet after writing it! */ 132 132 void jabber_cache_add( struct im_connection *ic, struct xt_node *node, jabber_cache_event func ) 133 133 { … … 252 252 253 253 /* Returns a new string. Don't leak it! */ 254 char *jabber_normalize( c onst char *orig )254 char *jabber_normalize( char *orig ) 255 255 { 256 256 int len, i; … … 320 320 else 321 321 { 322 /* Keep in mind that full_jid currently isn't really323 a full JID... */324 322 new->bare_jid = g_strdup( full_jid ); 325 323 g_hash_table_insert( jd->buddies, new->bare_jid, new ); … … 335 333 { 336 334 /* Let's waste some more bytes of RAM instead of to make 337 memory management a total disaster here. And it saves 338 me one g_free() call in this function. :-P */ 335 memory management a total disaster here.. */ 339 336 new->full_jid = full_jid; 340 337 } … … 356 353 if( ( s = strchr( jid, '/' ) ) ) 357 354 { 358 int none_found = 0;359 360 355 *s = 0; 361 356 if( ( bud = g_hash_table_lookup( jd->buddies, jid ) ) ) … … 375 370 } 376 371 } 377 else 378 { 379 /* This hack is there to make sure that O_CREAT will 380 work if there's already another resouce present 381 for this JID, even if it's an unknown buddy. This 382 is done to handle conferences properly. */ 383 none_found = 1; 384 } 385 386 if( bud == NULL && ( flags & GET_BUDDY_CREAT ) && ( imcb_find_buddy( ic, jid ) || !none_found ) ) 372 373 if( bud == NULL && ( flags & GET_BUDDY_CREAT ) && imcb_find_buddy( ic, jid ) ) 387 374 { 388 375 *s = '/'; … … 431 418 } 432 419 433 /* I'm keeping a separate ext_jid attribute to save a JID that makes sense434 to export to BitlBee. This is mainly for groupchats right now. It's435 a bit of a hack, but I just think having the user nickname in the hostname436 part of the hostmask doesn't look nice on IRC. Normally you can convert437 a normal JID to ext_jid by swapping the part before and after the / and438 replacing the / with a =. But there should be some stripping (@s are439 allowed in Jabber nicks...). */440 struct jabber_buddy *jabber_buddy_by_ext_jid( struct im_connection *ic, char *jid_, get_buddy_flags_t flags )441 {442 struct jabber_buddy *bud;443 char *s, *jid;444 445 jid = jabber_normalize( jid_ );446 447 if( ( s = strchr( jid, '=' ) ) == NULL )448 return NULL;449 450 for( bud = jabber_buddy_by_jid( ic, s + 1, GET_BUDDY_FIRST ); bud; bud = bud->next )451 {452 /* Hmmm, could happen if not all people in the chat are anonymized? */453 if( bud->ext_jid == NULL )454 continue;455 456 if( strcmp( bud->ext_jid, jid ) == 0 )457 break;458 }459 460 g_free( jid );461 462 return bud;463 }464 465 420 /* Remove one specific full JID from our list. Use this when a buddy goes 466 421 off-line (because (s)he can still be online from a different location. … … 486 441 g_hash_table_remove( jd->buddies, bud->bare_jid ); 487 442 g_free( bud->bare_jid ); 488 g_free( bud->ext_jid );489 443 g_free( bud->full_jid ); 490 444 g_free( bud->away_message ); … … 519 473 g_hash_table_replace( jd->buddies, bi->bare_jid, bi->next ); 520 474 521 g_free( bi->ext_jid );522 475 g_free( bi->full_jid ); 523 476 g_free( bi->away_message ); … … 542 495 specified bare JID. Use this when removing someone from the contact 543 496 list, for example. */ 544 int jabber_buddy_remove_bare( struct im_connection *ic, char *bare_jid )497 int jabber_buddy_remove_bare( struct im_connection *ic, char *bare_jid_ ) 545 498 { 546 499 struct jabber_data *jd = ic->proto_data; 547 500 struct jabber_buddy *bud, *next; 548 549 if( strchr( bare_jid, '/' ) ) 501 char *bare_jid; 502 503 if( strchr( bare_jid_, '/' ) ) 550 504 return 0; 551 505 552 if( ( bud = jabber_buddy_by_jid( ic, bare_jid, GET_BUDDY_FIRST ) ) ) 506 bare_jid = jabber_normalize( bare_jid_ ); 507 508 if( ( bud = g_hash_table_lookup( jd->buddies, bare_jid ) ) ) 553 509 { 554 510 /* Most important: Remove the hash reference. We don't know 555 511 this buddy anymore. */ 556 512 g_hash_table_remove( jd->buddies, bud->bare_jid ); 557 g_free( bud->bare_jid );558 513 559 514 /* Deallocate the linked list of resources. */ 560 515 while( bud ) 561 516 { 562 /* ext_jid && anonymous means that this buddy is563 specific to one groupchat (the one we're564 currently cleaning up) so it can be deleted565 completely. */566 if( bud->ext_jid && bud->flags & JBFLAG_IS_ANONYMOUS )567 imcb_remove_buddy( ic, bud->ext_jid, NULL );568 569 517 next = bud->next; 570 g_free( bud->ext_jid );571 518 g_free( bud->full_jid ); 572 519 g_free( bud->away_message ); … … 575 522 } 576 523 524 g_free( bare_jid ); 577 525 return 1; 578 526 } 579 527 else 580 528 { 529 g_free( bare_jid ); 581 530 return 0; 582 531 } 583 532 } 584 585 struct groupchat *jabber_chat_by_name( struct im_connection *ic, const char *name )586 {587 char *normalized = jabber_normalize( name );588 struct groupchat *ret;589 struct jabber_chat *jc;590 591 for( ret = ic->groupchats; ret; ret = ret->next )592 {593 jc = ret->data;594 if( strcmp( normalized, jc->name ) == 0 )595 break;596 }597 g_free( normalized );598 599 return ret;600 }601 602 time_t jabber_get_timestamp( struct xt_node *xt )603 {604 struct tm tp, utc;605 struct xt_node *c;606 time_t res, tres;607 char *s = NULL;608 609 for( c = xt->children; ( c = xt_find_node( c, "x" ) ); c = c->next )610 {611 if( ( s = xt_find_attr( c, "xmlns" ) ) && strcmp( s, XMLNS_DELAY ) == 0 )612 break;613 }614 615 if( !c || !( s = xt_find_attr( c, "stamp" ) ) )616 return 0;617 618 memset( &tp, 0, sizeof( tp ) );619 if( sscanf( s, "%4d%2d%2dT%2d:%2d:%2d", &tp.tm_year, &tp.tm_mon, &tp.tm_mday,620 &tp.tm_hour, &tp.tm_min, &tp.tm_sec ) != 6 )621 return 0;622 623 tp.tm_year -= 1900;624 tp.tm_mon --;625 tp.tm_isdst = -1; /* GRRRRRRRRRRR */626 627 res = mktime( &tp );628 /* Problem is, mktime() just gave us the GMT timestamp for the629 given local time... While the given time WAS NOT local. So630 we should fix this now.631 632 Now I could choose between messing with environment variables633 (kludgy) or using timegm() (not portable)... Or doing the634 following, which I actually prefer... */635 gmtime_r( &res, &utc );636 utc.tm_isdst = -1; /* Once more: GRRRRRRRRRRRRRRRRRR!!! */637 if( utc.tm_hour == tp.tm_hour && utc.tm_min == tp.tm_min )638 /* Sweet! We're in UTC right now... */639 return res;640 641 tres = mktime( &utc );642 res += res - tres;643 644 /* Yes, this is a hack. And it will go wrong around DST changes.645 BUT this is more likely to be threadsafe than messing with646 environment variables, and possibly more portable... */647 648 return res;649 }
Note: See TracChangeset
for help on using the changeset viewer.