client-common-auth.c revision a8c5a86d183db25a57bf193c06b41e092ec2e151
45312f52ff3a3d4c137447be4c7556500c2f8bf2Timo Sirainen/* Copyright (c) 2002-2014 Dovecot authors, see the included COPYING file */
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen#define PROXY_FAILURE_MSG "Account is temporarily unavailable."
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen/* If we've been waiting auth server to respond for over this many milliseconds,
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen send a "waiting" message. */
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen#define AUTH_WAITING_WARNING_TIMEOUT_MSECS (10*1000)
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainenstatic void client_auth_failed(struct client *client)
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen if (client->auth_initializing || client->destroyed)
a12399903f415a7e14c2816cffa2f7a09dcbb097Timo Sirainen client->io = io_add(client->fd, IO_READ, client_input, client);
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainenstatic void client_auth_waiting_timeout(struct client *client)
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen client_log_warn(client, "Auth process not responding, "
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen "delayed sending initial response (greeting)");
a2f250a332dfc1e6cd4ffd196c621eb9dbf7b8a1Timo Sirainen client_notify_status(client, FALSE, client->master_tag == 0 ?
a2f250a332dfc1e6cd4ffd196c621eb9dbf7b8a1Timo Sirainen AUTH_SERVER_WAITING_MSG : AUTH_MASTER_WAITING_MSG);
a2f250a332dfc1e6cd4ffd196c621eb9dbf7b8a1Timo Sirainenvoid client_set_auth_waiting(struct client *client)
a757f31393b9d6fc7760a9dec8363404ab3ae576Timo Sirainenstatic void client_auth_parse_args(struct client *client,
a757f31393b9d6fc7760a9dec8363404ab3ae576Timo Sirainen const char *const *args,
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen reply_r->proxy_timeout_msecs = 1000*atoi(value);
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen else if (strcmp(key, "proxy_nopipelining") == 0)
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen reply_r->ssl_flags |= PROXY_SSL_FLAG_ANY_CERT;
83bb013a99f0936995f9c7a1077822662d8fefdbTimo Sirainen reply_r->port = login_binary->default_ssl_port;
dce5a2719df4fc64a8762d2aa94ba98dcf9cd6feTimo Sirainen reply_r->ssl_flags |= PROXY_SSL_FLAG_ANY_CERT;
dce5a2719df4fc64a8762d2aa94ba98dcf9cd6feTimo Sirainen /* already handled in login-common */
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen i_debug("Ignoring unknown passdb extra field: %s", key);
dce5a2719df4fc64a8762d2aa94ba98dcf9cd6feTimo Sirainenstatic void proxy_free_password(struct client *client)
dce5a2719df4fc64a8762d2aa94ba98dcf9cd6feTimo Sirainen safe_memset(client->proxy_password, 0, strlen(client->proxy_password));
83bb013a99f0936995f9c7a1077822662d8fefdbTimo Sirainenvoid client_proxy_finish_destroy_client(struct client *client)
87460b08cb97b31cde640d4975a6aa2c1d0e7226Timo Sirainen /* input stream got closed in client_send_raw_data().
83bb013a99f0936995f9c7a1077822662d8fefdbTimo Sirainen In most places we don't have to check for this explicitly,
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen but login_proxy_detach() attempts to get and use the
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen istream's fd, which is now -1. */
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen str_printfa(str, "proxy(%s): started proxying to %s:%u",
83bb013a99f0936995f9c7a1077822662d8fefdbTimo Sirainen if (strcmp(client->virtual_user, client->proxy_user) != 0) {
83bb013a99f0936995f9c7a1077822662d8fefdbTimo Sirainen /* remote username is different, log it */
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen str_printfa(str, " (master %s)", client->proxy_master_user);
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainenstatic void client_proxy_error(struct client *client, const char *text)
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainenvoid client_proxy_log_failure(struct client *client, const char *line)
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen str_printfa(str, "proxy(%s): Login failed to %s:%u",
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen if (strcmp(client->virtual_user, client->proxy_user) != 0) {
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen /* remote username is different, log it */
910fa4e4204a73d3d24c03f3059dd24e727ca057Timo Sirainen str_printfa(str, " (master %s)", client->proxy_master_user);
838e367716bbd5e44b4a1691db9cbf72af53e9f0Timo Sirainenvoid client_proxy_failed(struct client *client, bool send_line)
838e367716bbd5e44b4a1691db9cbf72af53e9f0Timo Sirainen client_proxy_error(client, PROXY_FAILURE_MSG);
b19a1420da0618a10edf67c2cfd13c8c8633057aTimo Sirainen dsasl_client_free(&client->proxy_sasl_client);
b19a1420da0618a10edf67c2cfd13c8c8633057aTimo Sirainen /* call this last - it may destroy the client */
b19a1420da0618a10edf67c2cfd13c8c8633057aTimo Sirainenstatic const char *get_disconnect_reason(struct istream *input)
b19a1420da0618a10edf67c2cfd13c8c8633057aTimo Sirainen return errno == 0 || errno == EPIPE ? "Connection closed" :
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen /* we're just freeing the proxy */
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen input = login_proxy_get_istream(client->login_proxy);
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen /* we came here from client_destroy() */
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen /* failed for some reason, probably server disconnected */
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen client_log_err(client, "proxy: Remote input buffer full");
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen "proxy: Remote %s:%u disconnected: %s "
3c52b294054995d62bd1851c5c42b975fd8c22c9Timo Sirainen "(state=%u, duration=%us)%s",
if (!success)
return FALSE;
return TRUE;
const char *reason;
return TRUE;
return FALSE;
return TRUE;
const unsigned char *data;
unsigned int len;
for (i = 0; i < size; i++) {
return i < size;
switch (sasl_reply) {
data);
const char *init_resp)
return TRUE;
if (pass_sent) {
return FALSE;
void clients_notify_auth_connected(void)