Merge branch 'imap' of https://github.com/bnoordhuis/curl into bnoordhuis-imap

This commit is contained in:
Daniel Stenberg 2011-03-13 00:36:38 +01:00
commit c8fba59731
2 changed files with 42 additions and 7 deletions

View File

@ -108,6 +108,7 @@ static int imap_getsock(struct connectdata *conn,
static CURLcode imap_doing(struct connectdata *conn, static CURLcode imap_doing(struct connectdata *conn,
bool *dophase_done); bool *dophase_done);
static CURLcode imap_setup_connection(struct connectdata * conn); static CURLcode imap_setup_connection(struct connectdata * conn);
static CURLcode imap_state_upgrade_tls(struct connectdata *conn);
/* /*
* IMAP protocol handler. * IMAP protocol handler.
@ -342,17 +343,38 @@ static CURLcode imap_state_starttls_resp(struct connectdata *conn,
result = CURLE_LOGIN_DENIED; result = CURLE_LOGIN_DENIED;
} }
else { else {
/* Curl_ssl_connect is BLOCKING */ if(data->state.used_interface == Curl_if_multi) {
result = Curl_ssl_connect(conn, FIRSTSOCKET); state(conn, IMAP_UPGRADETLS);
if(CURLE_OK == result) { return imap_state_upgrade_tls(conn);
conn->protocol |= PROT_IMAPS; }
result = imap_state_login(conn); else {
result = Curl_ssl_connect(conn, FIRSTSOCKET);
if(CURLE_OK == result) {
conn->protocol |= PROT_IMAPS;
result = imap_state_login(conn);
}
} }
} }
state(conn, IMAP_STOP); state(conn, IMAP_STOP);
return result; return result;
} }
static CURLcode imap_state_upgrade_tls(struct connectdata *conn)
{
struct imap_conn *imapc = &conn->proto.imapc;
CURLcode result;
result = Curl_ssl_connect_nonblocking(conn, FIRSTSOCKET, &imapc->ssldone);
if(imapc->ssldone) {
conn->protocol |= PROT_IMAPS;
result = imap_state_login(conn);
state(conn, IMAP_STOP);
}
return result;
}
/* for LOGIN responses */ /* for LOGIN responses */
static CURLcode imap_state_login_resp(struct connectdata *conn, static CURLcode imap_state_login_resp(struct connectdata *conn,
int imapcode, int imapcode,
@ -524,6 +546,10 @@ static CURLcode imap_statemach_act(struct connectdata *conn)
struct pingpong *pp = &imapc->pp; struct pingpong *pp = &imapc->pp;
size_t nread = 0; size_t nread = 0;
/* busy upgrading the connection; right now all I/O is SSL/TLS, not IMAP */
if(imapc->state == IMAP_UPGRADETLS)
return imap_state_upgrade_tls(conn);
if(pp->sendleft) if(pp->sendleft)
return Curl_pp_flushsend(pp); return Curl_pp_flushsend(pp);
@ -588,7 +614,14 @@ static CURLcode imap_multi_statemach(struct connectdata *conn,
bool *done) bool *done)
{ {
struct imap_conn *imapc = &conn->proto.imapc; struct imap_conn *imapc = &conn->proto.imapc;
CURLcode result = Curl_pp_multi_statemach(&imapc->pp); CURLcode result;
if((conn->protocol & PROT_IMAPS) && !imapc->ssldone) {
result = Curl_ssl_connect_nonblocking(conn, FIRSTSOCKET, &imapc->ssldone);
}
else {
result = Curl_pp_multi_statemach(&imapc->pp);
}
*done = (bool)(imapc->state == IMAP_STOP); *done = (bool)(imapc->state == IMAP_STOP);
@ -700,7 +733,7 @@ static CURLcode imap_connect(struct connectdata *conn,
} }
#endif /* !CURL_DISABLE_HTTP && !CURL_DISABLE_PROXY */ #endif /* !CURL_DISABLE_HTTP && !CURL_DISABLE_PROXY */
if(conn->protocol & PROT_IMAPS) { if((conn->protocol & PROT_IMAPS) && data->state.used_interface != Curl_if_multi) {
/* BLOCKING */ /* BLOCKING */
/* IMAPS is simply imap with SSL for the control channel */ /* IMAPS is simply imap with SSL for the control channel */
/* now, perform the SSL initialization for this socket */ /* now, perform the SSL initialization for this socket */

View File

@ -33,6 +33,7 @@ typedef enum {
a connect */ a connect */
IMAP_LOGIN, IMAP_LOGIN,
IMAP_STARTTLS, IMAP_STARTTLS,
IMAP_UPGRADETLS, /* asynchronously upgrade the connection to SSL/TLS (multi mode only) */
IMAP_SELECT, IMAP_SELECT,
IMAP_FETCH, IMAP_FETCH,
IMAP_LOGOUT, IMAP_LOGOUT,
@ -47,6 +48,7 @@ struct imap_conn {
imapstate state; /* always use imap.c:state() to change state! */ imapstate state; /* always use imap.c:state() to change state! */
int cmdid; /* id number/index */ int cmdid; /* id number/index */
const char *idstr; /* pointer to a string for which to wait for as id */ const char *idstr; /* pointer to a string for which to wait for as id */
bool ssldone; /* is connect() over SSL done? only relevant in multi mode */
}; };
extern const struct Curl_handler Curl_handler_imap; extern const struct Curl_handler Curl_handler_imap;