/* * XXX this is nearly as ugly as proxyconnect(). */ int aim_conn_completeconnect(aim_session_t *sess, aim_conn_t *conn) { fd_set fds, wfds; struct timeval tv; int res, error = ETIMEDOUT; aim_rxcallback_t userfunc; if (!conn || (conn->fd == -1)) return -1; if (!(conn->status & AIM_CONN_STATUS_INPROGRESS)) return -1; FD_ZERO(&fds); FD_SET(conn->fd, &fds); FD_ZERO(&wfds); FD_SET(conn->fd, &wfds); tv.tv_sec = 0; tv.tv_usec = 0; if ((res = select(conn->fd+1, &fds, &wfds, NULL, &tv)) == -1) { error = errno; aim_conn_close(conn); errno = error; return -1; } else if (res == 0) { return 0; /* hasn't really completed yet... */ } if (FD_ISSET(conn->fd, &fds) || FD_ISSET(conn->fd, &wfds)) { socklen_t len = sizeof(error); if (getsockopt(conn->fd, SOL_SOCKET, SO_ERROR, &error, &len) < 0) error = errno; } if (error) { aim_conn_close(conn); errno = error; return -1; } sock_make_blocking(conn->fd); conn->status &= ~AIM_CONN_STATUS_INPROGRESS; if ((userfunc = aim_callhandler(sess, conn, AIM_CB_FAM_SPECIAL, AIM_CB_SPECIAL_CONNCOMPLETE))) userfunc(sess, NULL, conn); /* Flush out the queues if there was something waiting for this conn */ aim_tx_flushqueue(sess); return 0; }
/* * XXX this is nearly as ugly as proxyconnect(). */ faim_export int aim_conn_completeconnect(aim_session_t *sess, aim_conn_t *conn) { aim_rxcallback_t userfunc; if (!conn || (conn->fd == -1)) return -1; if (!(conn->status & AIM_CONN_STATUS_INPROGRESS)) return -1; fcntl(conn->fd, F_SETFL, 0); conn->status &= ~AIM_CONN_STATUS_INPROGRESS; if ((userfunc = aim_callhandler(sess, conn, AIM_CB_FAM_SPECIAL, AIM_CB_SPECIAL_CONNCOMPLETE))) userfunc(sess, NULL, conn); /* Flush out the queues if there was something waiting for this conn */ aim_tx_flushqueue(sess); return 0; }