void packetmgr_del_packet( qqpacketmgr* mgr, qqpacket* p ) { if( p->match ){ loop_remove( &mgr->sent_loop, p->match ); delete_func( p->match ); } delete_func( p ); }
int handle_packet( qqclient* qq, qqpacket* p, uchar* data, int len ) { qqpacketmgr* mgr = &qq->packetmgr; mgr->recv_packets ++; bytebuffer* buf; NEW( buf, sizeof( bytebuffer ) ); if( !buf ){ DBG("error: no enough memory to allocate buf."); return -99; } buf->pos = 0; buf->len = buf->size = len; memcpy( buf->data, data, buf->len ); //get packet info if( qq->network == TCP || qq->network == PROXY_HTTP ) get_word( buf ); //packet len p->head = get_byte( buf ); p->tail = buf->data[buf->len-1]; if( p->head != 0x02 || p->tail!=0x03 || buf->len > 2000 ){ DBG("[%u] wrong packet. len=%d head: %d tail: %d", qq->number, buf->len, p->head, p->tail ); DEL( buf ); return -1; } p->version = get_word( buf ); p->command = get_word( buf ); p->seqno = get_word( buf ); uint chk_repeat = (p->seqno<<16)|p->command; //check repeat if( loop_search( &mgr->recv_loop, (void*)chk_repeat, repeat_searcher ) == NULL ){ loop_push_to_tail( &mgr->recv_loop, (void*)chk_repeat ); p->match = match_packet( mgr, p ); p->time_alive = time(NULL); //do a test if ( !p->buf ){ DBG("%u: Error impossible. p->buf: %x p->command: %x", qq->number, p->buf, p->command ); } //deal with the packet process_packet( qq, p, buf ); qqpacket* t; while( (t = loop_pop_from_tail( &mgr->temp_loop )) ){ loop_push_to_head( &mgr->ready_loop, t ); } if( p->match ){ loop_remove( &mgr->sent_loop, p->match ); delete_func( p->match ); } p->match = NULL; mgr->failed_packets = 0; }else{ // DBG("repeated packet: cmd: %x seqno:%x", p->command, p->seqno ); } DEL( buf ); check_ready_packets( qq ); return 0; }
static void* webqq_guarder( void* data ) { int counter = 0; DBG (("webqq_guarder")); while( webqq_running ){ time_t timenow = time(NULL); counter ++; user* u; do{ u = loop_search( &user_loop, (void*)timenow, guarder_searcher ); if( u ){ DBG("removing qq: %u time1: %u - time2: %u > 120", ((qqclient*)u->qq)->number, timenow, u->update_time ); loop_remove( &user_loop, (void*)u ); delete_func( (void*)u ); } }while( u ); SLEEP( 1 ); } DBG (("end.")); return NULL; }
int packetmgr_check_packet( struct qqclient* qq, int timeout ) { qqpacketmgr *mgr = &qq->packetmgr; qqpacket* p; time_t timeout_time = time(NULL) - timeout; //when locked, cannot recv packet till unlock. do{ p = loop_search( &mgr->sent_loop, (void*)timeout_time, timeout_searcher ); if( p ){ loop_remove( &mgr->sent_loop, p ); } if( p ){ if( p->send_times >= 10 ){ MSG("[%u] Failed to send the packet. command: %x\n", qq->number, p->command ); if( p->command == QQ_CMD_SEND_IM ){ buddy_msg_callback( qq, 10000, time(NULL), "刚才某条消息发送失败。" ); } //make an event to tell the program that we have a //problem. char event[64]; sprintf( event, "sendfailed^$%d^$%d", p->command, p->seqno ); qqclient_put_event( qq, event ); delete_func( p ); mgr->failed_packets ++; //To avoid too many failed packets, just shut it down. if( mgr->failed_packets > 5 || qq->process != P_LOGIN ){ qqclient_set_process( qq, P_ERROR ); } }else{ DBG("[%u] resend packet cmd: %x", qq->number, p->command ); packetmgr_put_urge( qq, p, 1 ); } } }while( 0 && p ); check_ready_packets(qq); return 0; }
EXPORT void webqq_remove( user* u ) { loop_remove( &user_loop, u ); delete_func( (void*) u ); }