Mercurial > pidgin.yaz
changeset 835:88f8f98de02d
[gaim-migrate @ 845]
libfaim changes. should improve reliablity and stability.
committer: Tailor Script <tailor@pidgin.im>
author | Eric Warmenhoven <eric@warmenhoven.org> |
---|---|
date | Sun, 03 Sep 2000 23:22:05 +0000 |
parents | bac7089491c1 |
children | 15d005f8baaf |
files | libfaim/CHANGES libfaim/aim_buddylist.c libfaim/aim_im.c libfaim/aim_info.c libfaim/aim_misc.c libfaim/aim_rxhandlers.c libfaim/aim_rxqueue.c libfaim/aim_snac.c libfaim/faim/aim.h |
diffstat | 9 files changed, 234 insertions(+), 44 deletions(-) [+] |
line wrap: on
line diff
--- a/libfaim/CHANGES Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/CHANGES Sun Sep 03 23:22:05 2000 +0000 @@ -1,6 +1,15 @@ No release numbers ------------------ + - Sat Sep 2 23:42:37 UTC 2000 + - Hopefully fix aim_snac.c bugs + - Add Buddy List Rights parser (max buddies and max watchers) + - Fix rather major problem in rxhandlers caused by missing breaks + - Add reason code for msgerr (0004/0001) callback + - Add BOS Rights parser (max permit / max deny) + - Add locate error (0002/0001) parser + - Add parser for missed calls (0004/000a) + - Fri Sep 1 23:34:28 UTC 2000 - Switched the read()s in rxqueue to use recv() - Should fix the big message problem and the big buddy list problem
--- a/libfaim/aim_buddylist.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_buddylist.c Sun Sep 03 23:22:05 2000 +0000 @@ -86,3 +86,43 @@ return( sess->snac_nextid++ ); } +int aim_parse_buddyrights(struct aim_session_t *sess, + struct command_rx_struct *command, ...) +{ + rxcallback_t userfunc = NULL; + int ret=1; + struct aim_tlvlist_t *tlvlist; + struct aim_tlv_t *tlv; + unsigned short maxbuddies = 0, maxwatchers = 0; + + /* + * TLVs follow + */ + if (!(tlvlist = aim_readtlvchain(command->data+10, command->commandlen-10))) + return ret; + + /* + * TLV type 0x0001: Maximum number of buddies. + */ + if ((tlv = aim_gettlv(tlvlist, 0x0001, 1))) { + maxbuddies = aimutil_get16(tlv->value); + } + + /* + * TLV type 0x0002: Maximum number of watchers. + * + * XXX: what the hell is a watcher? + * + */ + if ((tlv = aim_gettlv(tlvlist, 0x0002, 1))) { + maxwatchers = aimutil_get16(tlv->value); + } + + userfunc = aim_callhandler(command->conn, 0x0003, 0x0003); + if (userfunc) + ret = userfunc(sess, command, maxbuddies, maxwatchers); + + aim_freetlvchain(&tlvlist); + + return ret; +}
--- a/libfaim/aim_im.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_im.c Sun Sep 03 23:22:05 2000 +0000 @@ -856,6 +856,8 @@ struct aim_snac_t *snac = NULL; int ret = 0; rxcallback_t userfunc = NULL; + char *dest; + unsigned short reason = 0; /* * Get SNAC from packet and look it up @@ -872,14 +874,18 @@ if (!snac) { printf("faim: msgerr: got an ICBM-failed error on an unknown SNAC ID! (%08lx)\n", snacid); - } + dest = NULL; + } else + dest = snac->data; + + reason = aimutil_get16(command->data+10); /* * Call client. */ userfunc = aim_callhandler(command->conn, 0x0004, 0x0001); if (userfunc) - ret = userfunc(sess, command, (snac)?snac->data:"(UNKNOWN)"); + ret = userfunc(sess, command, dest, reason); else ret = 0; @@ -892,3 +898,47 @@ } +int aim_parse_missedcall(struct aim_session_t *sess, + struct command_rx_struct *command) +{ + int i, ret = 1; + rxcallback_t userfunc = NULL; + unsigned short channel, nummissed, reason; + struct aim_userinfo_s userinfo; + + i = 10; /* Skip SNAC header */ + + + /* + * XXX: supposedly, this entire packet can repeat as many times + * as necessary. Should implement that. + */ + + /* + * Channel ID. + */ + channel = aimutil_get16(command->data+i); + i += 2; + + /* + * Extract the standard user info block. + */ + i += aim_extractuserinfo(command->data+i, &userinfo); + + nummissed = aimutil_get16(command->data+i); + i += 2; + + reason = aimutil_get16(command->data+i); + i += 2; + + /* + * Call client. + */ + userfunc = aim_callhandler(command->conn, 0x0004, 0x000a); + if (userfunc) + ret = userfunc(sess, command, channel, &userinfo, nummissed, reason); + else + ret = 0; + + return ret; +}
--- a/libfaim/aim_info.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_info.c Sun Sep 03 23:22:05 2000 +0000 @@ -57,6 +57,49 @@ return (sess->snac_nextid++); } +int aim_parse_locateerr(struct aim_session_t *sess, + struct command_rx_struct *command) +{ + u_long snacid = 0x000000000; + struct aim_snac_t *snac = NULL; + int ret = 0; + rxcallback_t userfunc = NULL; + char *dest; + unsigned short reason = 0; + + /* + * Get SNAC from packet and look it up + * the list of unrepliedto/outstanding + * SNACs. + * + */ + snacid = aimutil_get32(command->data+6); + snac = aim_remsnac(sess, snacid); + + if (!snac) { + printf("faim: locerr: got an locate-failed error on an unknown SNAC ID! (%08lx)\n", snacid); + dest = NULL; + } else + dest = snac->data; + + reason = aimutil_get16(command->data+10); + + /* + * Call client. + */ + userfunc = aim_callhandler(command->conn, 0x0002, 0x0001); + if (userfunc) + ret = userfunc(sess, command, dest, reason); + else + ret = 0; + + if (snac) { + free(snac->data); + free(snac); + } + + return ret; +} /* * Capability blocks.
--- a/libfaim/aim_misc.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_misc.c Sun Sep 03 23:22:05 2000 +0000 @@ -260,6 +260,45 @@ return aim_genericreq_l(sess, conn, 0x0009, 0x0004, &mask); } +int aim_parse_bosrights(struct aim_session_t *sess, + struct command_rx_struct *command, ...) +{ + rxcallback_t userfunc = NULL; + int ret=1; + struct aim_tlvlist_t *tlvlist; + struct aim_tlv_t *tlv; + unsigned short maxpermits = 0, maxdenies = 0; + + /* + * TLVs follow + */ + if (!(tlvlist = aim_readtlvchain(command->data+10, command->commandlen-10))) + return ret; + + /* + * TLV type 0x0001: Maximum number of buddies on permit list. + */ + if ((tlv = aim_gettlv(tlvlist, 0x0001, 1))) { + maxpermits = aimutil_get16(tlv->value); + } + + /* + * TLV type 0x0002: Maximum number of buddies on deny list. + * + */ + if ((tlv = aim_gettlv(tlvlist, 0x0002, 1))) { + maxdenies = aimutil_get16(tlv->value); + } + + userfunc = aim_callhandler(command->conn, 0x0009, 0x0003); + if (userfunc) + ret = userfunc(sess, command, maxpermits, maxdenies); + + aim_freetlvchain(&tlvlist); + + return ret; +} + /* * aim_bos_clientready() *
--- a/libfaim/aim_rxhandlers.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_rxhandlers.c Sun Sep 03 23:22:05 2000 +0000 @@ -431,10 +431,11 @@ workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_GEN, AIM_CB_GEN_DEFAULT, workingPtr); break; } + break; case 0x0002: /* Family: Location */ switch (subtype) { case 0x0001: - workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, 0x0002, 0x0001, workingPtr); + workingPtr->handled = aim_parse_locateerr(sess, workingPtr); break; case 0x0003: workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, 0x0002, 0x0003, workingPtr); @@ -446,13 +447,14 @@ workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_LOC, AIM_CB_LOC_DEFAULT, workingPtr); break; } + break; case 0x0003: /* Family: Buddy List */ switch (subtype) { case 0x0001: workingPtr->handled = aim_parse_generalerrs(sess, workingPtr); break; case 0x0003: - workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, 0x0003, 0x0003, workingPtr); + workingPtr->handled = aim_parse_buddyrights(sess, workingPtr); break; case 0x000b: /* oncoming buddy */ workingPtr->handled = aim_parse_oncoming_middle(sess, workingPtr); @@ -479,7 +481,7 @@ workingPtr->handled = aim_parse_incoming_im_middle(sess, workingPtr); break; case 0x000a: - workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, 0x0004, 0x000a, workingPtr); + workingPtr->handled = aim_parse_missedcall(sess, workingPtr); break; case 0x000c: workingPtr->handled = aim_parse_msgack_middle(sess, workingPtr); @@ -492,7 +494,7 @@ if (subtype == 0x0001) workingPtr->handled = aim_parse_generalerrs(sess, workingPtr); else if (subtype == 0x0003) - workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, 0x0009, 0x0003, workingPtr); + workingPtr->handled = aim_parse_bosrights(sess, workingPtr); else workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_BOS, AIM_CB_BOS_DEFAULT, workingPtr); break; @@ -508,7 +510,7 @@ workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_LOK, AIM_CB_LOK_DEFAULT, workingPtr); } break; - case 0x000b: + case 0x000b: { if (subtype == 0x0001) workingPtr->handled = aim_parse_generalerrs(sess, workingPtr); else if (subtype == 0x0002) @@ -516,15 +518,16 @@ else workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_STS, AIM_CB_STS_DEFAULT, workingPtr); break; - case AIM_CB_FAM_SPECIAL: - workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, family, subtype, workingPtr); - break; + } + case AIM_CB_FAM_SPECIAL: + workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, family, subtype, workingPtr); + break; default: workingPtr->handled = aim_callhandler_noparam(sess, workingPtr->conn, AIM_CB_FAM_SPECIAL, AIM_CB_SPECIAL_UNKNOWN, workingPtr); break; - } + } /* switch(family) */ break; - } + } /* AIM_CONN_TYPE_BOS */ case AIM_CONN_TYPE_CHATNAV: { u_short family; u_short subtype;
--- a/libfaim/aim_rxqueue.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_rxqueue.c Sun Sep 03 23:22:05 2000 +0000 @@ -42,7 +42,6 @@ */ faim_mutex_lock(&conn->active); if (recv(conn->fd, generic, 6, MSG_WAITALL) < 6){ - printf("faim: flap: read underflow (header)\n"); aim_conn_close(conn); faim_mutex_unlock(&conn->active); return -1; @@ -91,7 +90,6 @@ /* read the data portion of the packet */ if (recv(conn->fd, newrx->data, newrx->commandlen, MSG_WAITALL) < newrx->commandlen){ - printf("faim: flap: read underflow (payload)\n"); free(newrx->data); free(newrx); aim_conn_close(conn);
--- a/libfaim/aim_snac.c Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/aim_snac.c Sun Sep 03 23:22:05 2000 +0000 @@ -37,7 +37,7 @@ u_long aim_newsnac(struct aim_session_t *sess, struct aim_snac_t *newsnac) { - struct aim_snac_t *snac = NULL, *cur = NULL; + struct aim_snac_t *snac = NULL; int index; if (!newsnac) @@ -56,6 +56,8 @@ sess->snac_hash[index] = snac; faim_mutex_unlock(&sess->snac_hash_locks[index]); + printf("faim: cached snac %lx\n", snac->id); + return(snac->id); } @@ -77,11 +79,9 @@ faim_mutex_lock(&sess->snac_hash_locks[index]); if (!sess->snac_hash[index]) ; - else if (!sess->snac_hash[index]->next) { - if (sess->snac_hash[index]->id == id) { - cur = sess->snac_hash[index]; - sess->snac_hash[index] = NULL; - } + else if (sess->snac_hash[index]->id == id) { + cur = sess->snac_hash[index]; + sess->snac_hash[index] = cur->next; } else { cur = sess->snac_hash[index]; while (cur->next) { @@ -111,36 +111,41 @@ int aim_cleansnacs(struct aim_session_t *sess, int maxage) { - struct aim_snac_t *cur; - struct aim_snac_t *remed = NULL; + struct aim_snac_t *cur, *next, *prev = NULL; time_t curtime; int i; for (i = 0; i < FAIM_SNAC_HASH_SIZE; i++) { faim_mutex_lock(&sess->snac_hash_locks[i]); - if (!sess->snac_hash[i]) - ; - else if (!sess->snac_hash[i]->next) { - if ((sess->snac_hash[i]->issuetime + maxage) >= curtime) { - remed = sess->snac_hash[i]; - if(remed->data) - free(remed->data); - free(remed); - sess->snac_hash[i] = NULL; + if (!sess->snac_hash[i]) { + faim_mutex_unlock(&sess->snac_hash_locks[i]); + continue; + } + + curtime = time(NULL); /* done here in case we waited for the lock */ + + cur = sess->snac_hash[i]; + while (cur) { + next = cur->next; + if ((curtime - cur->issuetime) > maxage) { + if (sess->snac_hash[i] == cur) + prev = sess->snac_hash[i] = next; + else + prev->next = next; + + printf("faim: killing ancient snac %lx (%lx)\n", cur->id, curtime - cur->issuetime); + + /* XXX should we have destructors here? */ + if (cur->data) + free(cur->data); + free(cur); + + } else { + prev = cur; } - } else { - cur = sess->snac_hash[i]; - while(cur && cur->next) { - if ((cur->next->issuetime + maxage) >= curtime) { - remed = cur->next; - cur->next = cur->next->next; - if (remed->data) - free(remed->data); - free(remed); - } - cur = cur->next; - } + cur = next; } + faim_mutex_unlock(&sess->snac_hash_locks[i]); }
--- a/libfaim/faim/aim.h Sat Sep 02 12:46:05 2000 +0000 +++ b/libfaim/faim/aim.h Sun Sep 03 23:22:05 2000 +0000 @@ -544,6 +544,8 @@ u_long aim_seticbmparam(struct aim_session_t *, struct aim_conn_t *conn); int aim_parse_msgerror_middle(struct aim_session_t *, struct command_rx_struct *); int aim_negchan_middle(struct aim_session_t *sess, struct command_rx_struct *command); +int aim_parse_bosrights(struct aim_session_t *sess, struct command_rx_struct *command, ...); +int aim_parse_missedcall(struct aim_session_t *sess, struct command_rx_struct *command); struct aim_conn_t * aim_directim_initiate(struct aim_session_t *, struct aim_conn_t *, struct aim_directim_priv *, char *); int aim_send_im_direct(struct aim_session_t *, struct aim_conn_t *, char *); @@ -654,7 +656,7 @@ int aim_putuserinfo(u_char *buf, int buflen, struct aim_userinfo_s *info); int aim_sendbuddyoncoming(struct aim_session_t *sess, struct aim_conn_t *conn, struct aim_userinfo_s *info); int aim_sendbuddyoffgoing(struct aim_session_t *sess, struct aim_conn_t *conn, char *sn); - +int aim_parse_locateerr(struct aim_session_t *sess, struct command_rx_struct *command); /* aim_auth.c */ int aim_auth_sendcookie(struct aim_session_t *, struct aim_conn_t *, u_char *); @@ -664,6 +666,7 @@ /* aim_buddylist.c */ u_long aim_add_buddy(struct aim_session_t *, struct aim_conn_t *, char *); u_long aim_remove_buddy(struct aim_session_t *, struct aim_conn_t *, char *); +int aim_parse_buddyrights(struct aim_session_t *sess, struct command_rx_struct *command, ...); /* aim_search.c */ u_long aim_usersearch_address(struct aim_session_t *, struct aim_conn_t *, char *);