void auth_client_connection_destroy(struct auth_client_connection **_conn)
{
        struct auth_client_connection *conn = *_conn;

	*_conn = NULL;
	if (conn->fd == -1)
		return;

	DLLIST_REMOVE(&auth_client_connections, conn);

	i_stream_close(conn->input);
	o_stream_close(conn->output);

	if (conn->io != NULL)
		io_remove(&conn->io);

	net_disconnect(conn->fd);
	conn->fd = -1;

	if (conn->request_handler != NULL) {
		auth_request_handler_abort_requests(conn->request_handler);
		auth_request_handler_destroy(&conn->request_handler);
	}

        master_service_client_connection_destroyed(master_service);
        auth_client_connection_unref(&conn);
}
Пример #2
0
void lmtp_client_close(struct lmtp_client *client)
{
	if (client->dns_lookup != NULL)
		dns_lookup_abort(&client->dns_lookup);
	if (client->to != NULL)
		timeout_remove(&client->to);
	if (client->io != NULL)
		io_remove(&client->io);
	if (client->input != NULL)
		i_stream_close(client->input);
	if (client->output != NULL)
		o_stream_close(client->output);
	if (client->fd != -1) {
		net_disconnect(client->fd);
		client->fd = -1;
	}
	if (client->data_input != NULL)
		i_stream_unref(&client->data_input);
	client->output_finished = TRUE;

	if (!client->finish_called) {
		client->finish_called = TRUE;
		client->finish_callback(client->finish_context);
	}
}
static void
auth_postfix_connection_destroy(struct auth_postfix_connection **_conn)
{
        struct auth_postfix_connection *conn = *_conn;

	*_conn = NULL;
	if (conn->destroyed)
		return;
	conn->destroyed = TRUE;

	DLLIST_REMOVE(&auth_postfix_connections, conn);

	if (conn->input != NULL)
		i_stream_close(conn->input);
	if (conn->output != NULL)
		o_stream_close(conn->output);
	if (conn->io != NULL)
		io_remove(&conn->io);
	if (conn->fd != -1) {
		if (close(conn->fd) < 0)
			i_error("close(%s): %m", conn->path);
		conn->fd = -1;
	}

	master_service_client_connection_destroyed(master_service);
	auth_postfix_connection_unref(&conn);
}
Пример #4
0
static void client_destroy(struct client *client)
{
	char **app;

	i_set_failure_prefix("imap-urlauth[%s](%s): ",
			     my_pid, client->access_user);

	if (client->url != NULL) {
		/* deinitialize url */
		i_stream_close(client->input);
		o_stream_close(client->output);
		(void)client_run_url(client);
		i_assert(client->url == NULL);
	}

	imap_urlauth_worker_client_count--;
	DLLIST_REMOVE(&imap_urlauth_worker_clients, client);

	if (client->urlauth_ctx != NULL)
		imap_urlauth_deinit(&client->urlauth_ctx);

	if (client->mail_user != NULL)
		mail_user_unref(&client->mail_user);

	if (client->io != NULL)
		io_remove(&client->io);
	if (client->ctrl_io != NULL)
		io_remove(&client->ctrl_io);
	if (client->to_idle != NULL)
		timeout_remove(&client->to_idle);

	if (client->input != NULL)
		i_stream_destroy(&client->input);
	if (client->output != NULL)
		o_stream_destroy(&client->output);

	if (client->ctrl_input != NULL)
		i_stream_destroy(&client->ctrl_input);
	if (client->ctrl_output != NULL)
		o_stream_destroy(&client->ctrl_output);

	if (client->fd_in >= 0)
		net_disconnect(client->fd_in);
	if (client->fd_out >= 0 && client->fd_in != client->fd_out)
		net_disconnect(client->fd_out);
	if (client->fd_ctrl >= 0)
		net_disconnect(client->fd_ctrl);

	if (client->service_user != NULL)
		mail_storage_service_user_free(&client->service_user);
	i_free(client->access_user);
	array_foreach_modifiable(&client->access_apps, app)
		i_free(*app);
	array_free(&client->access_apps);
	i_free(client);

	imap_urlauth_worker_refresh_proctitle();
	master_service_client_connection_destroyed(master_service);
}
Пример #5
0
static void
o_stream_ssl_close(struct iostream_private *stream, bool close_parent)
{
	struct ssl_ostream *sstream = (struct ssl_ostream *)stream;

	if (close_parent)
		o_stream_close(sstream->ssl_io->plain_output);
}
Пример #6
0
static void o_stream_default_close(struct iostream_private *stream,
				   bool close_parent)
{
	struct ostream_private *_stream = (struct ostream_private *)stream;

	(void)o_stream_flush(&_stream->ostream);
	if (close_parent && _stream->parent != NULL)
		o_stream_close(_stream->parent);
}
Пример #7
0
static void o_stream_lzma_close(struct iostream_private *stream,
				bool close_parent)
{
	struct lzma_ostream *zstream = (struct lzma_ostream *)stream;

	lzma_end(&zstream->strm);
	if (close_parent)
		o_stream_close(zstream->ostream.parent);
}
Пример #8
0
static int
cmd_dsync_server_run(struct doveadm_mail_cmd_context *_ctx,
		     struct mail_user *user)
{
	struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx;
	struct dsync_ibc *ibc;
	struct dsync_brain *brain;
	string_t *temp_prefix, *state_str = NULL;
	enum dsync_brain_sync_type sync_type;
	const char *name;

	if (_ctx->conn != NULL) {
		/* doveadm-server connection. start with a success reply.
		   after that follows the regular dsync protocol. */
		ctx->fd_in = ctx->fd_out = -1;
		ctx->input = _ctx->conn->input;
		ctx->output = _ctx->conn->output;
		o_stream_nsend(ctx->output, "\n+\n", 3);
		i_set_failure_prefix("dsync-server(%s): ", user->username);
		name = i_stream_get_name(ctx->input);
	} else {
		/* the log messages go via stderr to the remote dsync,
		   so the names are reversed */
		i_set_failure_prefix("dsync-remote(%s): ", user->username);
		name = "local";
	}

	doveadm_user_init_dsync(user);

	temp_prefix = t_str_new(64);
	mail_user_set_get_temp_prefix(temp_prefix, user->set);

	ibc = cmd_dsync_icb_stream_init(ctx, name, str_c(temp_prefix));
	brain = dsync_brain_slave_init(user, ibc, FALSE);

	io_loop_run(current_ioloop);

	if (ctx->replicator_notify) {
		state_str = t_str_new(128);
		dsync_brain_get_state(brain, state_str);
	}
	sync_type = dsync_brain_get_sync_type(brain);

	if (dsync_brain_deinit(&brain) < 0)
		_ctx->exit_code = EX_TEMPFAIL;
	dsync_ibc_deinit(&ibc);

	if (_ctx->conn != NULL) {
		/* make sure nothing more is written by the generic doveadm
		   connection code */
		o_stream_close(_ctx->conn->output);
	}

	if (ctx->replicator_notify && _ctx->exit_code == 0)
		dsync_replicator_notify(ctx, sync_type, str_c(state_str));
	return _ctx->exit_code == 0 ? 0 : -1;
}
Пример #9
0
static void o_stream_bzlib_close(struct iostream_private *stream,
				 bool close_parent)
{
	struct bzlib_ostream *zstream = (struct bzlib_ostream *)stream;

	(void)o_stream_flush(&zstream->ostream.ostream);
	(void)BZ2_bzCompressEnd(&zstream->zs);
	if (close_parent)
		o_stream_close(zstream->ostream.parent);
}
Пример #10
0
static void o_stream_zlib_close(struct iostream_private *stream,
				bool close_parent)
{
	struct zlib_ostream *zstream = (struct zlib_ostream *)stream;

	(void)o_stream_flush(&zstream->ostream.ostream);
	(void)deflateEnd(&zstream->zs);
	if (close_parent)
		o_stream_close(zstream->ostream.parent);
}
Пример #11
0
void o_stream_copy_error_from_parent(struct ostream_private *_stream)
{
	struct ostream *src = _stream->parent;
	struct ostream *dest = &_stream->ostream;

	dest->stream_errno = src->stream_errno;
	dest->last_failed_errno = src->last_failed_errno;
	dest->overflow = src->overflow;
	if (src->closed)
		o_stream_close(dest);
}
Пример #12
0
static void o_stream_cmp_close(struct iostream_private *stream,
			       bool close_parent)
{
	struct cmp_ostream *cstream = (struct cmp_ostream *)stream;

	if (cstream->input == NULL)
		return;

	i_stream_unref(&cstream->input);
	if (close_parent)
		o_stream_close(cstream->ostream.parent);
}
Пример #13
0
static void openssl_iostream_destroy(struct ssl_iostream *ssl_io)
{
	(void)SSL_shutdown(ssl_io->ssl);
	(void)openssl_iostream_more(ssl_io);
	(void)o_stream_flush(ssl_io->plain_output);
	/* close the plain i/o streams, because their fd may be closed soon,
	   but we may still keep this ssl-iostream referenced until later. */
	i_stream_close(ssl_io->plain_input);
	o_stream_close(ssl_io->plain_output);

	ssl_iostream_unref(&ssl_io);
}
Пример #14
0
static void o_stream_zlib_close(struct iostream_private *stream,
				bool close_parent)
{
	struct zlib_ostream *zstream = (struct zlib_ostream *)stream;

	i_assert(zstream->ostream.finished ||
		 zstream->ostream.ostream.stream_errno != 0 ||
		 zstream->ostream.error_handling_disabled);
	(void)deflateEnd(&zstream->zs);
	if (close_parent)
		o_stream_close(zstream->ostream.parent);
}
Пример #15
0
static void
http_transfer_chunked_ostream_close(struct iostream_private *stream,
				    bool close_parent)
{
	struct http_transfer_chunked_ostream *tcstream =
		(struct http_transfer_chunked_ostream *)stream;

	(void)o_stream_send(tcstream->ostream.parent, "0\r\n\r\n", 5);
	(void)o_stream_flush(&tcstream->ostream.ostream);
	if (close_parent)
		o_stream_close(tcstream->ostream.parent);
}
Пример #16
0
static void openssl_iostream_destroy(struct ssl_iostream *ssl_io)
{
	if (SSL_shutdown(ssl_io->ssl) != 1) {
		/* if bidirectional shutdown fails we need to clear
		   the error queue */
		openssl_iostream_clear_errors();
	}
	(void)openssl_iostream_more(ssl_io);
	(void)o_stream_flush(ssl_io->plain_output);
	/* close the plain i/o streams, because their fd may be closed soon,
	   but we may still keep this ssl-iostream referenced until later. */
	i_stream_close(ssl_io->plain_input);
	o_stream_close(ssl_io->plain_output);

	ssl_iostream_unref(&ssl_io);
}
static void notify_connection_destroy(struct notify_connection *conn)
{
    i_assert(conn->fd != -1);

    if (!CONNECTION_IS_FIFO(conn))
        master_service_client_connection_destroyed(master_service);

    DLLIST_REMOVE(&conns, conn);

    io_remove(&conn->io);
    i_stream_close(conn->input);
    if (conn->output != NULL)
        o_stream_close(conn->output);
    net_disconnect(conn->fd);
    conn->fd = -1;

    notify_connection_unref(conn);
}
Пример #18
0
static void
o_stream_mail_filter_close(struct iostream_private *stream, bool close_parent)
{
	struct mail_filter_ostream *mstream =
		(struct mail_filter_ostream *)stream;

	if (mstream->ext_in != NULL)
		i_stream_destroy(&mstream->ext_in);
	if (mstream->ext_out != NULL)
		o_stream_destroy(&mstream->ext_out);
	if (mstream->fd != -1) {
		if (close(mstream->fd) < 0)
			i_error("ext-filter: close() failed: %m");
		mstream->fd = -1;
	}
	if (close_parent)
		o_stream_close(mstream->ostream.parent);
}
Пример #19
0
static void notify_connection_destroy(struct notify_connection *conn)
{
	if (conn->destroyed)
		return;
	conn->destroyed = TRUE;

	DLLIST_REMOVE(&connections, conn);

	io_remove(&conn->io);
	i_stream_close(conn->input);
	o_stream_close(conn->output);
	if (close(conn->fd) < 0)
		i_error("close(notify connection) failed: %m");
	conn->fd = -1;

	notify_connection_unref(&conn);
	master_service_client_connection_destroyed(master_service);
}
Пример #20
0
void client_disconnect(struct client *client, const char *reason)
{
	i_assert(reason != NULL);

	if (client->disconnected)
		return;

	i_info("Disconnected: %s %s", reason, client_stats(client));
	client->disconnected = TRUE;
	o_stream_nflush(client->output);
	o_stream_uncork(client->output);

	i_stream_close(client->input);
	o_stream_close(client->output);

	if (client->to_idle != NULL)
		timeout_remove(&client->to_idle);
	client->to_idle = timeout_add(0, client_destroy_timeout, client);
}
Пример #21
0
static int openssl_iostream_handshake(struct ssl_iostream *ssl_io)
{
	const char *error = NULL;
	int ret;

	i_assert(!ssl_io->handshaked);

	if (ssl_io->ctx->client_ctx) {
		while ((ret = SSL_connect(ssl_io->ssl)) <= 0) {
			ret = openssl_iostream_handle_error(ssl_io, ret,
							    "SSL_connect()");
			if (ret <= 0)
				return ret;
		}
	} else {
		while ((ret = SSL_accept(ssl_io->ssl)) <= 0) {
			ret = openssl_iostream_handle_error(ssl_io, ret,
							    "SSL_accept()");
			if (ret <= 0)
				return ret;
		}
	}
	/* handshake finished */
	(void)openssl_iostream_bio_sync(ssl_io);

	if (ssl_io->handshake_callback != NULL) {
		if (ssl_io->handshake_callback(&error, ssl_io->handshake_context) < 0) {
			i_assert(error != NULL);
			i_stream_close(ssl_io->plain_input);
			o_stream_close(ssl_io->plain_output);
			openssl_iostream_set_error(ssl_io, error);
			ssl_io->handshake_failed = TRUE;
			errno = EINVAL;
			return -1;
		}
	}
	i_free_and_null(ssl_io->last_error);
	ssl_io->handshaked = TRUE;

	if (ssl_io->ssl_output != NULL)
		(void)o_stream_flush(ssl_io->ssl_output);
	return 1;
}
Пример #22
0
void auth_worker_client_destroy(struct auth_worker_client **_client)
{
	struct auth_worker_client *client = *_client;

	*_client = NULL;
	if (client->fd == -1)
		return;

	i_stream_close(client->input);
	o_stream_close(client->output);

	if (client->io != NULL)
		io_remove(&client->io);

	net_disconnect(client->fd);
	client->fd = -1;
	auth_worker_client_unref(&client);

	auth_worker_client = NULL;
	master_service_client_connection_destroyed(master_service);
}
Пример #23
0
void connection_disconnect(struct connection *conn)
{
	if (conn->to != NULL)
		timeout_remove(&conn->to);
	if (conn->io != NULL)
		io_remove(&conn->io);
	if (conn->input != NULL) {
		i_stream_close(conn->input);
		i_stream_destroy(&conn->input);
	}
	if (conn->output != NULL) {
		o_stream_close(conn->output);
		o_stream_destroy(&conn->output);
	}
	if (conn->fd_in != -1) {
		if (close(conn->fd_in) < 0)
			i_error("close(%s) failed: %m", conn->name);
		if (conn->fd_in != conn->fd_out && close(conn->fd_out) < 0)
			i_error("close(%s/out) failed: %m", conn->name);
		conn->fd_in = conn->fd_out = -1;
	}
}
Пример #24
0
void client_destroy(struct client *client, const char *reason)
{
	if (client->destroyed)
		return;
	client->destroyed = TRUE;

	if (!client->login_success && reason != NULL) {
		reason = t_strconcat(reason, " ",
			client_get_extra_disconnect_reason(client), NULL);
	}
	if (reason != NULL)
		client_log(client, reason);

	if (last_client == client)
		last_client = client->prev;
	DLLIST_REMOVE(&clients, client);

	if (client->input != NULL)
		i_stream_close(client->input);
	if (client->output != NULL)
		o_stream_close(client->output);

	if (client->master_tag != 0) {
		i_assert(client->auth_request == NULL);
		i_assert(client->authenticating);
		i_assert(client->refcount > 1);
		client->authenticating = FALSE;
		master_auth_request_abort(master_auth, client->master_tag);
		client->refcount--;
	} else if (client->auth_request != NULL) {
		i_assert(client->authenticating);
		sasl_server_auth_abort(client);
	} else {
		i_assert(!client->authenticating);
	}

	if (client->io != NULL)
		io_remove(&client->io);
	if (client->to_disconnect != NULL)
		timeout_remove(&client->to_disconnect);
	if (client->to_auth_waiting != NULL)
		timeout_remove(&client->to_auth_waiting);
	if (client->auth_response != NULL)
		str_free(&client->auth_response);

	if (client->fd != -1) {
		net_disconnect(client->fd);
		client->fd = -1;
	}

	if (client->proxy_password != NULL) {
		safe_memset(client->proxy_password, 0,
			    strlen(client->proxy_password));
		i_free_and_null(client->proxy_password);
	}

	if (client->proxy_sasl_client != NULL)
		dsasl_client_free(&client->proxy_sasl_client);
	if (client->login_proxy != NULL)
		login_proxy_free(&client->login_proxy);
	if (client->v.destroy != NULL)
		client->v.destroy(client);
	if (client_unref(&client) && initial_service_count == 1) {
		/* as soon as this connection is done with proxying
		   (or whatever), the process will die. there's no need for
		   authentication anymore, so close the connection.
		   do this only with initial service_count=1, in case there
		   are other clients with pending authentications */
		auth_client_disconnect(auth_client, "unnecessary connection");
	}
	login_client_destroyed();
	login_refresh_proctitle();
}
Пример #25
0
static void client_default_destroy(struct client *client, const char *reason)
{
	struct client_command_context *cmd;
	const char *cmd_status = "";

	i_assert(!client->destroyed);
	client->destroyed = TRUE;

	if (!client->disconnected) {
		client->disconnected = TRUE;
		if (reason == NULL) {
			reason = io_stream_get_disconnect_reason(client->input,
								 client->output);
			cmd_status = client_get_commands_status(client);
		}
		i_info("%s%s %s", reason, cmd_status, client_stats(client));
	}

	i_stream_close(client->input);
	o_stream_close(client->output);

	/* finish off all the queued commands. */
	if (client->output_cmd_lock != NULL)
		client_command_cancel(&client->output_cmd_lock);
	while (client->command_queue != NULL) {
		cmd = client->command_queue;
		client_command_cancel(&cmd);
	}
	/* handle the input_lock command last. it might have been waiting on
	   other queued commands (although we probably should just drop the
	   command at that point since it hasn't started running. but this may
	   change in future). */
	if (client->input_lock != NULL)
		client_command_cancel(&client->input_lock);

	if (client->mailbox != NULL) {
		client_search_updates_free(client);
		mailbox_free(&client->mailbox);
	}
	if (client->notify_ctx != NULL)
		imap_notify_deinit(&client->notify_ctx);
	if (client->urlauth_ctx != NULL)
		imap_urlauth_deinit(&client->urlauth_ctx);
	if (client->anvil_sent) {
		master_service_anvil_send(master_service, t_strconcat(
			"DISCONNECT\t", my_pid, "\timap/",
			mail_user_get_anvil_userip_ident(client->user),
			"\n", NULL));
	}
	mail_user_unref(&client->user);

	if (client->free_parser != NULL)
		imap_parser_unref(&client->free_parser);
	if (client->io != NULL)
		io_remove(&client->io);
	if (client->to_idle_output != NULL)
		timeout_remove(&client->to_idle_output);
	if (client->to_delayed_input != NULL)
		timeout_remove(&client->to_delayed_input);
	timeout_remove(&client->to_idle);

	i_stream_destroy(&client->input);
	o_stream_destroy(&client->output);

	net_disconnect(client->fd_in);
	if (client->fd_in != client->fd_out)
		net_disconnect(client->fd_out);

	if (array_is_created(&client->search_saved_uidset))
		array_free(&client->search_saved_uidset);
	if (array_is_created(&client->search_updates))
		array_free(&client->search_updates);
	pool_unref(&client->command_pool);
	mail_storage_service_user_free(&client->service_user);

	imap_client_count--;
	DLLIST_REMOVE(&imap_clients, client);
	pool_unref(&client->pool);

	master_service_client_connection_destroyed(master_service);
	imap_refresh_proctitle();
}