# HG changeset patch # User Mark Doliner # Date 1144640257 0 # Node ID 6c34fbb75bbd211e7aa797019cc31cd4b3a4eb48 # Parent a79d422bfe6228d6d2d70d2a47871d92e5096837 [gaim-migrate @ 15994] Disconnect the account with a decent error message when there are problems with an oscar FLAP connection. This needed to be added after I removed it when rewriting things for non-blocking I/O. committer: Tailor Script diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/flap_connection.c --- a/src/protocols/oscar/flap_connection.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/flap_connection.c Mon Apr 10 03:37:37 2006 +0000 @@ -229,13 +229,16 @@ flap_connection_destroy_cb(gpointer data) { FlapConnection *conn; + OscarData *od; + GaimAccount *account; conn = data; + od = conn->od; gaim_debug_info("oscar", "Destroying oscar connection of " "type 0x%04hx\n", conn->type); - flap_connection_close(conn->od, conn); + flap_connection_close(od, conn); if (conn->watcher_incoming != 0) gaim_input_remove(conn->watcher_incoming); @@ -248,7 +251,7 @@ * Free conn->internal, if necessary */ if (conn->type == SNAC_FAMILY_CHAT) - flap_connection_destroy_chat(conn->od, conn); + flap_connection_destroy_chat(od, conn); if (conn->inside != NULL) { @@ -260,18 +263,38 @@ free(inside); } - conn->od->oscar_connections = g_list_remove(conn->od->oscar_connections, conn); + od->oscar_connections = g_list_remove(od->oscar_connections, conn); + g_free(conn); - g_free(conn); + account = gaim_connection_get_account(od->gc); + if ((od->oscar_connections == NULL) && (!account->disconnecting)) + { + /* No more FLAP connections! Sign off this GaimConnection! */ + const gchar *tmp; + if (conn->disconnect_reason == OSCAR_DISCONNECT_REMOTE_CLOSED) + tmp = _("Server closed the connection."); + else if (conn->disconnect_reason == OSCAR_DISCONNECT_LOST_CONNECTION) + tmp = _("Lost connection with server for an unknown reason."); + else if (conn->disconnect_reason == OSCAR_DISCONNECT_INVALID_DATA) + tmp = _("Received invalid data on connection with server."); + else if (conn->disconnect_reason == OSCAR_DISCONNECT_COULD_NOT_CONNECT) + tmp = _("Could not establish a connection with the server."); + else + tmp = NULL; + + if (tmp != NULL) + gaim_connection_error(od->gc, tmp); + } return FALSE; } void -flap_connection_destroy(FlapConnection *conn) +flap_connection_destroy(FlapConnection *conn, OscarDisconnectReason reason) { if (conn->destroy_timeout != 0) gaim_timeout_remove(conn->destroy_timeout); + conn->disconnect_reason = reason; flap_connection_destroy_cb(conn); } @@ -282,7 +305,7 @@ * for some reason. */ void -flap_connection_schedule_destroy(FlapConnection *conn) +flap_connection_schedule_destroy(FlapConnection *conn, OscarDisconnectReason reason) { if (conn->destroy_timeout != 0) /* Already taken care of */ @@ -290,6 +313,7 @@ gaim_debug_info("oscar", "Scheduling destruction of FLAP " "connection of type 0x%04hx\n", conn->type); + conn->disconnect_reason = reason; conn->destroy_timeout = gaim_timeout_add(0, flap_connection_destroy_cb, conn); } @@ -594,7 +618,8 @@ gaim_debug_warning("oscar", "Expecting FLAP version " "0x00000001 but received FLAP version %08lx. Closing connection.\n", flap_version); - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_INVALID_DATA); } else conn->connected = TRUE; @@ -638,8 +663,8 @@ /* Check if the FLAP server closed the connection */ if (read == 0) { - /* TODO: Print an error? Server closed connection. */ - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_REMOTE_CLOSED); break; } @@ -651,8 +676,8 @@ break; /* Error! */ - /* TODO: Print an error? Lost connection with server. */ - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_LOST_CONNECTION); break; } @@ -666,7 +691,8 @@ /* All FLAP frames must start with the byte 0x2a */ if (aimutil_get8(&header[0]) != 0x2a) { - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_INVALID_DATA); break; } @@ -689,7 +715,8 @@ /* Check if the FLAP server closed the connection */ if (read == 0) { - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_REMOTE_CLOSED); break; } @@ -700,8 +727,8 @@ break; /* Error! */ - /* TODO: Print an error? Lost connection with server. */ - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_LOST_CONNECTION); break; } @@ -745,7 +772,7 @@ return; /* Error! */ - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, OSCAR_DISCONNECT_LOST_CONNECTION); return; } diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/odc.c --- a/src/protocols/oscar/odc.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/odc.c Mon Apr 10 03:37:37 2006 +0000 @@ -36,30 +36,30 @@ { const gchar *tmp; - if (conn->disconnect_reason == PEER_DISCONNECT_REMOTE_CLOSED) + if (conn->disconnect_reason == OSCAR_DISCONNECT_REMOTE_CLOSED) { - tmp = _("Remote user closed the connection."); + tmp = _("The remote user has closed the connection."); } - else if (conn->disconnect_reason == PEER_DISCONNECT_REMOTE_REFUSED) + else if (conn->disconnect_reason == OSCAR_DISCONNECT_REMOTE_REFUSED) { - tmp = _("Remote user declined your request."); + tmp = _("The remote user has declined your request."); } - else if (conn->disconnect_reason == PEER_DISCONNECT_LOST_CONNECTION) + else if (conn->disconnect_reason == OSCAR_DISCONNECT_LOST_CONNECTION) { - tmp = _("Lost connection with remote user for an unknown reason."); + tmp = _("Lost connection with the remote user for an unknown reason."); } - else if (conn->disconnect_reason == PEER_DISCONNECT_INVALID_DATA) + else if (conn->disconnect_reason == OSCAR_DISCONNECT_INVALID_DATA) { - tmp = _("Received invalid data on connection."); + tmp = _("Received invalid data on connection with remote user."); } - else if (conn->disconnect_reason == PEER_DISCONNECT_COULD_NOT_CONNECT) + else if (conn->disconnect_reason == OSCAR_DISCONNECT_COULD_NOT_CONNECT) { - tmp = _("Could not establish connection with remote user."); + tmp = _("Could not establish a connection with the remote user."); } else /* * We shouldn't print a message for some disconnect_reasons. - * Like PEER_DISCONNECT_LOCAL_CLOSED. + * Like OSCAR_DISCONNECT_LOCAL_CLOSED. */ tmp = NULL; @@ -452,7 +452,7 @@ /* Check if the remote user closed the connection */ if (read == 0) { - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_CLOSED); return; } @@ -462,7 +462,7 @@ /* No worries */ return; - peer_connection_destroy(conn, PEER_DISCONNECT_LOST_CONNECTION); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOST_CONNECTION); return; } @@ -536,7 +536,7 @@ */ gaim_debug_info("oscar", "Received an incorrect cookie. " "Closing connection.\n"); - peer_connection_destroy(conn, PEER_DISCONNECT_INVALID_DATA); + peer_connection_destroy(conn, OSCAR_DISCONNECT_INVALID_DATA); g_free(frame); return; } diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/oft.c --- a/src/protocols/oscar/oft.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/oft.c Mon Apr 10 03:37:37 2006 +0000 @@ -307,7 +307,7 @@ { gaim_debug_info("oscar", "Received an incorrect cookie. " "Closing connection.\n"); - peer_connection_destroy(conn, PEER_DISCONNECT_INVALID_DATA); + peer_connection_destroy(conn, OSCAR_DISCONNECT_INVALID_DATA); return; } @@ -415,7 +415,7 @@ conn->xfer->fd = -1; peer_oft_send_done(conn); - conn->disconnect_reason = PEER_DISCONNECT_DONE; + conn->disconnect_reason = OSCAR_DISCONNECT_DONE; conn->sending_data_timer = gaim_timeout_add(100, destroy_connection_when_done_sending_data, conn); } @@ -524,7 +524,7 @@ if (conn == NULL) return; - peer_connection_destroy(conn, PEER_DISCONNECT_LOCAL_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOCAL_CLOSED); } /*******************************************************************/ diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/oscar.c --- a/src/protocols/oscar/oscar.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/oscar.c Mon Apr 10 03:37:37 2006 +0000 @@ -912,7 +912,7 @@ /* Destroy the chat_connection */ od->oscar_chats = g_slist_remove(od->oscar_chats, cc); - flap_connection_schedule_destroy(cc->conn); + flap_connection_schedule_destroy(cc->conn, OSCAR_DISCONNECT_DONE); oscar_chat_destroy(cc); } @@ -967,7 +967,8 @@ if (conn->type == SNAC_FAMILY_LOCATE) gaim_connection_error(gc, _("Could not connect to BOS server")); else /* Maybe we should call this for BOS connections, too? */ - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, + OSCAR_DISCONNECT_COULD_NOT_CONNECT); destroy_new_conn_data(new_conn_data); return; } @@ -1336,13 +1337,12 @@ return 1; } - gaim_debug_misc("oscar", "Reg status: %hu\n", info->regstatus); gaim_debug_misc("oscar", "E-mail: %s\n", (info->email != NULL) ? info->email : "null"); gaim_debug_misc("oscar", "BOSIP: %s\n", info->bosip); gaim_debug_info("oscar", "Closing auth connection...\n"); - flap_connection_schedule_destroy(conn); + flap_connection_schedule_destroy(conn, OSCAR_DISCONNECT_DONE); for (i = 0; i < strlen(info->bosip); i++) { if (info->bosip[i] == ':') { @@ -1644,7 +1644,8 @@ if (gaim_proxy_connect(account, host, port, connection_established_cb, new_conn_data) != 0) { - flap_connection_schedule_destroy(new_conn_data->conn); + flap_connection_schedule_destroy(new_conn_data->conn, + OSCAR_DISCONNECT_COULD_NOT_CONNECT); gaim_debug_error("oscar", "Unable to connect to FLAP server " "of type 0x%04hx\n", redir->group); destroy_new_conn_data(new_conn_data); @@ -2054,7 +2055,7 @@ */ if (conn != NULL) { - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_CLOSED); } } else if (args->status == AIM_RENDEZVOUS_CONNECTED) @@ -2595,7 +2596,7 @@ } else { - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_REFUSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_REFUSED); } } else @@ -6263,7 +6264,7 @@ if (!conn->ready) aim_im_sendch2_cancel(conn); - peer_connection_destroy(conn, PEER_DISCONNECT_LOCAL_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOCAL_CLOSED); } } diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/oscar.h --- a/src/protocols/oscar/oscar.h Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/oscar.h Mon Apr 10 03:37:37 2006 +0000 @@ -287,6 +287,18 @@ typedef enum { + OSCAR_DISCONNECT_DONE, + OSCAR_DISCONNECT_LOCAL_CLOSED, + OSCAR_DISCONNECT_REMOTE_CLOSED, + OSCAR_DISCONNECT_REMOTE_REFUSED, + OSCAR_DISCONNECT_LOST_CONNECTION, + OSCAR_DISCONNECT_INVALID_DATA, + OSCAR_DISCONNECT_COULD_NOT_CONNECT, + OSCAR_DISCONNECT_RETRYING +} OscarDisconnectReason; + +typedef enum +{ OSCAR_CAPABILITY_BUDDYICON = 0x00000001, OSCAR_CAPABILITY_TALK = 0x00000002, OSCAR_CAPABILITY_DIRECTIM = 0x00000004, @@ -349,11 +361,12 @@ struct _FlapConnection { OscarData *od; /**< Pointer to parent session. */ - int fd; + gboolean connected; time_t lastactivity; /**< Time of last transmit. */ - gboolean connected; guint destroy_timeout; + OscarDisconnectReason disconnect_reason; + int fd; FlapFrame buffer_incoming; GaimCircBuffer *buffer_outgoing; guint watcher_incoming; @@ -550,8 +563,8 @@ FlapConnection *flap_connection_new(OscarData *, int type); void flap_connection_addgroup(FlapConnection *conn, guint16 group); void flap_connection_close(OscarData *od, FlapConnection *conn); -void flap_connection_destroy(FlapConnection *conn); -void flap_connection_schedule_destroy(FlapConnection *conn); +void flap_connection_destroy(FlapConnection *conn, OscarDisconnectReason reason); +void flap_connection_schedule_destroy(FlapConnection *conn, OscarDisconnectReason reason); FlapConnection *flap_connection_findbygroup(OscarData *od, guint16 group); FlapConnection *flap_connection_getbytype(OscarData *, int type); FlapConnection *flap_connection_getbytype_all(OscarData *, int type); @@ -612,7 +625,7 @@ #define AIM_OFT_SUBTYPE_SEND_FILE 0x0001 #define AIM_OFT_SUBTYPE_SEND_DIR 0x0002 #define AIM_OFT_SUBTYPE_GET_FILE 0x0011 -#define AIM_OPT_SUBTYPE_GET_LIST 0x0012 +#define AIM_OFT_SUBTYPE_GET_LIST 0x0012 #define AIM_TRANSFER_DENY_NOTSUPPORTED 0x0000 #define AIM_TRANSFER_DENY_DECLINE 0x0001 diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/oscar_data.c --- a/src/protocols/oscar/oscar_data.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/oscar_data.c Mon Apr 10 03:37:37 2006 +0000 @@ -108,11 +108,12 @@ if (od->getinfotimer > 0) gaim_timeout_remove(od->getinfotimer); while (od->oscar_connections != NULL) - flap_connection_destroy(od->oscar_connections->data); + flap_connection_destroy(od->oscar_connections->data, + OSCAR_DISCONNECT_DONE); while (od->peer_connections != NULL) peer_connection_destroy(od->peer_connections->data, - PEER_DISCONNECT_LOCAL_CLOSED); + OSCAR_DISCONNECT_LOCAL_CLOSED); if (od->handlerlist != NULL) aim_clearhandlers(od); diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/peer.c --- a/src/protocols/oscar/peer.c Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/peer.c Mon Apr 10 03:37:37 2006 +0000 @@ -191,8 +191,8 @@ (status != GAIM_XFER_STATUS_CANCEL_LOCAL) && (status != GAIM_XFER_STATUS_CANCEL_REMOTE)) { - if ((conn->disconnect_reason == PEER_DISCONNECT_REMOTE_CLOSED) || - (conn->disconnect_reason == PEER_DISCONNECT_REMOTE_REFUSED)) + if ((conn->disconnect_reason == OSCAR_DISCONNECT_REMOTE_CLOSED) || + (conn->disconnect_reason == OSCAR_DISCONNECT_REMOTE_REFUSED)) gaim_xfer_cancel_remote(conn->xfer); else gaim_xfer_cancel_local(conn->xfer); @@ -214,7 +214,7 @@ } void -peer_connection_destroy(PeerConnection *conn, PeerDisconnectReason reason) +peer_connection_destroy(PeerConnection *conn, OscarDisconnectReason reason) { conn->disconnect_reason = reason; if (conn->destroy_timeout != 0) @@ -223,7 +223,7 @@ } void -peer_connection_schedule_destroy(PeerConnection *conn, PeerDisconnectReason reason) +peer_connection_schedule_destroy(PeerConnection *conn, OscarDisconnectReason reason) { if (conn->destroy_timeout != 0) /* Already taken care of */ @@ -271,7 +271,7 @@ /* Check if the remote user closed the connection */ if (read == 0) { - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_CLOSED); return; } @@ -282,7 +282,7 @@ /* No worries */ return; - peer_connection_destroy(conn, PEER_DISCONNECT_LOST_CONNECTION); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOST_CONNECTION); return; } @@ -303,7 +303,7 @@ "Closing connection.\n", conn->magic[0], conn->magic[1], conn->magic[2], conn->magic[3], header[0], header[1], header[2], header[3]); - peer_connection_destroy(conn, PEER_DISCONNECT_INVALID_DATA); + peer_connection_destroy(conn, OSCAR_DISCONNECT_INVALID_DATA); return; } @@ -322,7 +322,7 @@ /* Check if the remote user closed the connection */ if (read == 0) { - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_CLOSED); return; } @@ -332,7 +332,7 @@ /* No worries */ return; - peer_connection_destroy(conn, PEER_DISCONNECT_LOST_CONNECTION); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOST_CONNECTION); return; } @@ -389,7 +389,7 @@ return; if (conn->ready) - peer_connection_schedule_destroy(conn, PEER_DISCONNECT_LOST_CONNECTION); + peer_connection_schedule_destroy(conn, OSCAR_DISCONNECT_LOST_CONNECTION); else { /* @@ -764,7 +764,7 @@ g_free(new_conn_data); /* Give up! */ - peer_connection_destroy(conn, PEER_DISCONNECT_COULD_NOT_CONNECT); + peer_connection_destroy(conn, OSCAR_DISCONNECT_COULD_NOT_CONNECT); } /** @@ -798,7 +798,7 @@ } /* Cancel the old connection and try again */ - peer_connection_destroy(conn, PEER_DISCONNECT_RETRYING); + peer_connection_destroy(conn, OSCAR_DISCONNECT_RETRYING); } } @@ -841,7 +841,7 @@ aim_im_denytransfer(conn->od, conn->sn, conn->cookie, AIM_TRANSFER_DENY_DECLINE); - peer_connection_destroy(conn, PEER_DISCONNECT_LOCAL_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_LOCAL_CLOSED); } /** @@ -894,7 +894,7 @@ /* Close the old direct IM and start a new one */ gaim_debug_info("oscar", "Received new direct IM request " "from %s. Destroying old connection.\n", sn); - peer_connection_destroy(conn, PEER_DISCONNECT_REMOTE_CLOSED); + peer_connection_destroy(conn, OSCAR_DISCONNECT_REMOTE_CLOSED); } } diff -r a79d422bfe62 -r 6c34fbb75bbd src/protocols/oscar/peer.h --- a/src/protocols/oscar/peer.h Mon Apr 10 02:47:43 2006 +0000 +++ b/src/protocols/oscar/peer.h Mon Apr 10 03:37:37 2006 +0000 @@ -33,18 +33,6 @@ typedef struct _NewPeerConnectionData NewPeerConnectionData; typedef struct _PeerConnection PeerConnection; -typedef enum -{ - PEER_DISCONNECT_DONE, - PEER_DISCONNECT_LOCAL_CLOSED, - PEER_DISCONNECT_REMOTE_CLOSED, - PEER_DISCONNECT_REMOTE_REFUSED, - PEER_DISCONNECT_LOST_CONNECTION, - PEER_DISCONNECT_INVALID_DATA, - PEER_DISCONNECT_COULD_NOT_CONNECT, - PEER_DISCONNECT_RETRYING -} PeerDisconnectReason; - #define PEER_CONNECTION_FLAG_INITIATED_BY_ME 0x0001 #define PEER_CONNECTION_FLAG_APPROVED 0x0002 #define PEER_CONNECTION_FLAG_TRIED_VERIFIEDIP 0x0004 @@ -163,7 +151,7 @@ int flags; /**< Bitmask of PEER_CONNECTION_FLAG_ */ time_t lastactivity; /**< Time of last transmit. */ guint destroy_timeout; - PeerDisconnectReason disconnect_reason; + OscarDisconnectReason disconnect_reason; /** * A pointer to either an OdcFrame or an OftFrame. @@ -221,8 +209,8 @@ */ PeerConnection *peer_connection_new(OscarData *od, OscarCapability type, const char *sn); -void peer_connection_destroy(PeerConnection *conn, PeerDisconnectReason reason); -void peer_connection_schedule_destroy(PeerConnection *conn, PeerDisconnectReason reason); +void peer_connection_destroy(PeerConnection *conn, OscarDisconnectReason reason); +void peer_connection_schedule_destroy(PeerConnection *conn, OscarDisconnectReason reason); PeerConnection *peer_connection_find_by_type(OscarData *od, const char *sn, OscarCapability type); PeerConnection *peer_connection_find_by_cookie(OscarData *od, const char *sn, const guchar *cookie);