main.c revision 726e5e80865853b31ce51f9977f1fb339a43f301
45312f52ff3a3d4c137447be4c7556500c2f8bf2Timo Sirainen/* Copyright (c) 2002-2011 Dovecot authors, see the included COPYING file */
211ed7806d8715ec2280ffbf5d10f0d6e4f1beb2Timo Sirainen#define AUTH_PENALTY_ANVIL_PATH "anvil-auth-penalty"
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainenstatic ARRAY_DEFINE(listeners, struct auth_socket_listener);
2767104d81e97a109f0aa9758792bfa1da325a97Timo Sirainen "[%u wait, %u passdb, %u userdb]",
2767104d81e97a109f0aa9758792bfa1da325a97Timo Sirainen auth_request_state_count[AUTH_REQUEST_STATE_NEW] +
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen auth_request_state_count[AUTH_REQUEST_STATE_MECH_CONTINUE] +
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen auth_request_state_count[AUTH_REQUEST_STATE_FINISHED],
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen auth_request_state_count[AUTH_REQUEST_STATE_PASSDB],
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen auth_request_state_count[AUTH_REQUEST_STATE_USERDB]));
252db51b6c0a605163326b3ea5d09e9936ca3b29Timo Sirainenstatic const char *const *read_global_settings(void)
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen struct master_service_settings_output set_output;
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen unsigned int i, count;
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen auth_set_pool = pool_alloconly_create("auth settings", 8192);
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen auth_settings_read(NULL, auth_set_pool, &set_output);
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen /* strdup() the service names, because they're allocated from
252db51b6c0a605163326b3ea5d09e9936ca3b29Timo Sirainen set parser pool, and we'll later clear it. */
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen count = str_array_length(set_output.specific_services);
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen services = p_new(auth_set_pool, const char *, count + 1);
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen for (i = 0; i < count; i++) {
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainenauth_socket_type_get(int listen_fd, const char **path_r)
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen /* figure out if this is a server or network socket by
6ef7e31619edfaa17ed044b45861d106a86191efTimo Sirainen checking the socket path name. */
5238111c460098d9cc8cc22527026138a278b9a4Timo Sirainen i_fatal("getunixname(%d) failed: %m", listen_fd);
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen /* not UNIX socket. let's just assume it's an
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen auth client. */
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainenstatic void listeners_init(void)
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen unsigned int i, n;
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen n = master_service_get_socket_count(master_service);
b92e979748a22925b0770d3004eaab043ed69574Timo Sirainen for (i = 0; i < n; i++) {
0ce5f96804e81cb0f857e7df32c0272f1eed9377Timo Sirainenstatic bool auth_module_filter(const char *name, void *context ATTR_UNUSED)
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen /* this is lazily loaded */
0dbcf4026ff8471b4d6d2e14f7e52321396bf087Timo Sirainenstatic void main_preinit(void)
0ce5f96804e81cb0f857e7df32c0272f1eed9377Timo Sirainen const char *const *services;
6cc0546c058f3e6253c6f99727b28dd602712974Timo Sirainen /* Open /dev/urandom before chrooting */
6cc0546c058f3e6253c6f99727b28dd602712974Timo Sirainen /* Load built-in SQL drivers (if any) */
0ce5f96804e81cb0f857e7df32c0272f1eed9377Timo Sirainen /* Initialize databases so their configuration files can be readable
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen only by root. Also load all modules here. */
555ebb032f9b8f0cdb66f27ce7374734833e7cacTimo Sirainen /* init schemes before plugins are loaded */
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen mod_set.version = master_service_get_version_string(master_service);
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen modules = module_dir_load(AUTH_MODULE_DIR, NULL, &mod_set);
c9bf63e9094761767a63ac6b189bcf60bcffdc44Timo Sirainen auth_penalty = auth_penalty_init(AUTH_PENALTY_ANVIL_PATH);
989cafb9d84d8c98d6441fc1ab45b4c37762a98aTimo Sirainen mech_reg = mech_register_init(global_auth_settings);
ecc81625167ed96c04c02aa190a1ea5baa65b474Timo Sirainen auths_preinit(global_auth_settings, auth_set_pool,
8cdb3234fe3c77e477c7a0e6934678f58fc54d4dTimo Sirainen /* Password lookups etc. may require roots, allow it. */
8cdb3234fe3c77e477c7a0e6934678f58fc54d4dTimo Sirainen mod_set.version = master_service_get_version_string(master_service);
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen modules = module_dir_load_missing(modules, AUTH_MODULE_DIR, names,
252db51b6c0a605163326b3ea5d09e9936ca3b29Timo Sirainenstatic void main_init(void)
8f32e59200da904613506f5649ffa4d9f5989cebTimo Sirainen /* If auth caches aren't used, just ignore these signals */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* workers have only a single connection from the master
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen auth process */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen master_service_set_client_limit(master_service, 1);
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* caching is handled only by the main auth process */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainenstatic void main_deinit(void)
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* cancel all pending anvil penalty lookups */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* deinit auth workers, which aborts pending requests */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* deinit passdbs and userdbs. it aborts any pending async requests. */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* flush pending requests */
8ab3d88c56dff2f567193f80cc29821a64e576d1Timo Sirainen /* there are no more auth requests */
struct auth_socket_listener *l;
switch (l->type) {
case AUTH_SOCKET_MASTER:
case AUTH_SOCKET_USERDB:
case AUTH_SOCKET_LOGIN_CLIENT:
case AUTH_SOCKET_CLIENT:
i_unreached();
static void auth_die(void)
return FATAL_DEFAULT;
main_preinit();
main_init();
main_deinit();