director.h revision c3a2a487e23a282e59254b82deb9344ed0306bb2
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen#ifndef DIRECTOR_H
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen#define DIRECTOR_H
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
bdd36cfdba3ff66d25570a9ff568d69e1eb543cfTimo Sirainen#include "net.h"
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen#include "director-settings.h"
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
aa797403d51ff047727b77d64532001d6b6cc21aTimo Sirainen#define DIRECTOR_VERSION_NAME "director"
aa797403d51ff047727b77d64532001d6b6cc21aTimo Sirainen#define DIRECTOR_VERSION_MAJOR 1
ae32667c54480d329eed994b3defab89cd76c077Timo Sirainen#define DIRECTOR_VERSION_MINOR 7
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainen
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen/* weak users supported in protocol */
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainen#define DIRECTOR_VERSION_WEAK_USERS 1
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen/* director ring remove supported */
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen#define DIRECTOR_VERSION_RING_REMOVE 2
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen/* quit reason supported */
dff32d11a411a24f3b76003c1ae22c5a960f180eTimo Sirainen#define DIRECTOR_VERSION_QUIT 3
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen/* user-kick supported */
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen#define DIRECTOR_VERSION_USER_KICK 4
eb209d12e3b1cfed564c35cf19fdb1bf7fcc6811Timo Sirainen/* options supported in handshake */
eb209d12e3b1cfed564c35cf19fdb1bf7fcc6811Timo Sirainen#define DIRECTOR_VERSION_OPTIONS 5
09060303d565e15d54e42b4ef722f9d3c26f5336Timo Sirainen/* user tags supported */
09060303d565e15d54e42b4ef722f9d3c26f5336Timo Sirainen#define DIRECTOR_VERSION_TAGS 5
a5ddfd7a8b473f73135b93d5e081e470a87f0f7eTimo Sirainen/* up/down state is tracked */
a5ddfd7a8b473f73135b93d5e081e470a87f0f7eTimo Sirainen#define DIRECTOR_VERSION_UPDOWN 6
ae32667c54480d329eed994b3defab89cd76c077Timo Sirainen/* user tag version 2 supported */
ae32667c54480d329eed994b3defab89cd76c077Timo Sirainen#define DIRECTOR_VERSION_TAGS_V2 7
aa797403d51ff047727b77d64532001d6b6cc21aTimo Sirainen
8c2b4a45f17a5cb13bb01058ca37798cf48d91baTimo Sirainen/* Minimum time between even attempting to communicate with a director that
8c2b4a45f17a5cb13bb01058ca37798cf48d91baTimo Sirainen failed due to a protocol error. */
8c2b4a45f17a5cb13bb01058ca37798cf48d91baTimo Sirainen#define DIRECTOR_PROTOCOL_FAILURE_RETRY_SECS 60
8c2b4a45f17a5cb13bb01058ca37798cf48d91baTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenstruct director;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenstruct mail_host;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenstruct user;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainentypedef void director_state_change_callback_t(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenstruct director {
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen const struct director_settings *set;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen /* IP and port of this director. self_host->ip/port must equal these. */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct ip_addr self_ip;
009217abb57a24a4076092e8e4e165545747839eStephan Bosch in_port_t self_port;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
009217abb57a24a4076092e8e4e165545747839eStephan Bosch in_port_t test_port;
00e7c3010f7da4a49881a7feb05e413af353af0aTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct director_host *self_host;
5f5713d6468dca1acf3d350dd8a33057331f78c5Timo Sirainen /* left and right connections are set only after they have finished
5f5713d6468dca1acf3d350dd8a33057331f78c5Timo Sirainen handshaking. until then they're in the connections list, although
5f5713d6468dca1acf3d350dd8a33057331f78c5Timo Sirainen updates are still sent to them during handshaking if the USER list
5f5713d6468dca1acf3d350dd8a33057331f78c5Timo Sirainen is long. */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct director_connection *left, *right;
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen /* all director connections */
4ee00532a265bdfb38539d811fcd12d51210ac35Timo Sirainen ARRAY(struct director_connection *) connections;
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen struct timeout *to_reconnect;
433f5c9cc560a8cbff47257513d0bacb1cf250f4Timo Sirainen struct timeout *to_sync;
3ee8a7ee6912c7caa4e83d3ce5a5db1590a7ffcdTimo Sirainen struct timeout *to_callback;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
edd318d5866ac3fbc6e8df28fb24a4dfef93c884Timo Sirainen /* current mail hosts */
cf9d67e4a9bfee31cf3be05244555d51a3d1b9feTimo Sirainen struct mail_host_list *mail_hosts;
edd318d5866ac3fbc6e8df28fb24a4dfef93c884Timo Sirainen /* original mail hosts configured in config file.
edd318d5866ac3fbc6e8df28fb24a4dfef93c884Timo Sirainen this is used only for doveadm lookups */
edd318d5866ac3fbc6e8df28fb24a4dfef93c884Timo Sirainen struct mail_host_list *orig_config_hosts;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen /* temporary user -> host associations */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct user_directory *users;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen /* these requests are waiting for directors to be in synced */
4ee00532a265bdfb38539d811fcd12d51210ac35Timo Sirainen ARRAY(struct director_request *) pending_requests;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct timeout *to_request;
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen struct timeout *to_handshake_warning;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen director_state_change_callback_t *state_change_callback;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen /* director hosts are sorted by IP (and port) */
4ee00532a265bdfb38539d811fcd12d51210ac35Timo Sirainen ARRAY(struct director_host *) dir_hosts;
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen struct timeout *to_remove_dirs;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainen struct ipc_client *ipc_proxy;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen unsigned int sync_seq;
58b8a301b7b36047f10a592751094fbed86d6f0cTimo Sirainen unsigned int ring_change_counter;
58b8a301b7b36047f10a592751094fbed86d6f0cTimo Sirainen unsigned int last_sync_sent_ring_change_counter;
aa797403d51ff047727b77d64532001d6b6cc21aTimo Sirainen /* the lowest minor version supported by the ring */
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainen unsigned int ring_min_version;
152db3f90f298b7fb2dbbd4276f0fc30a9bc30f6Timo Sirainen time_t ring_last_sync_time;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
89d6cd658eabf46e07e40037b0e641ed9be1a2a3Timo Sirainen time_t ring_first_alone;
89d6cd658eabf46e07e40037b0e641ed9be1a2a3Timo Sirainen
ece0a20249ce26208db3415ba2e79423678856f8Timo Sirainen uint64_t num_requests;
ece0a20249ce26208db3415ba2e79423678856f8Timo Sirainen uint64_t ring_traffic_input, ring_traffic_output;
ece0a20249ce26208db3415ba2e79423678856f8Timo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen /* director ring handshaking is complete.
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen director can start serving clients. */
0dffa25d211be541ee3c953b23566a1a990789dfTimo Sirainen bool ring_handshaked:1;
0dffa25d211be541ee3c953b23566a1a990789dfTimo Sirainen bool ring_handshake_warning_sent:1;
0dffa25d211be541ee3c953b23566a1a990789dfTimo Sirainen bool ring_synced:1;
0dffa25d211be541ee3c953b23566a1a990789dfTimo Sirainen bool sync_frozen:1;
0dffa25d211be541ee3c953b23566a1a990789dfTimo Sirainen bool sync_pending:1;
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen};
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
1df39b899804fd1dbc560f75382364822935c857Timo Sirainenextern bool director_debug;
1df39b899804fd1dbc560f75382364822935c857Timo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen/* Create a new director. If listen_ip specifies an actual IP, it's used with
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen listen_port for finding ourself from the director_servers setting.
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen listen_port is used regardless by director_host_add_from_string() for hosts
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen without specified port. */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenstruct director *
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainendirector_init(const struct director_settings *set,
009217abb57a24a4076092e8e4e165545747839eStephan Bosch const struct ip_addr *listen_ip, in_port_t listen_port,
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen director_state_change_callback_t *callback);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_deinit(struct director **dir);
c4900d31385344bfadaee53a897daeafdb3063d8Timo Sirainenvoid director_find_self(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen/* Start connecting to other directors */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_connect(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
4aab01f4eade3d278b61471516c062ce30a84b5fTimo Sirainenvoid director_set_ring_handshaked(struct director *dir);
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainenvoid director_set_ring_synced(struct director *dir);
152db3f90f298b7fb2dbbd4276f0fc30a9bc30f6Timo Sirainenvoid director_set_ring_unsynced(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_set_state_changed(struct director *dir);
aa797403d51ff047727b77d64532001d6b6cc21aTimo Sirainenvoid director_sync_send(struct director *dir, struct director_host *host,
468c28dfb03613ab8d487b5aebc985a969193aceTimo Sirainen uint32_t seq, unsigned int minor_version,
abe29107f5dce932d28a00912d2d75a01021bef1Timo Sirainen unsigned int timestamp, unsigned int hosts_hash);
433f5c9cc560a8cbff47257513d0bacb1cf250f4Timo Sirainenbool director_resend_sync(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainenvoid director_notify_ring_added(struct director_host *added_host,
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen struct director_host *src);
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainenvoid director_ring_remove(struct director_host *removed_host,
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen struct director_host *src);
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_update_host(struct director *dir, struct director_host *src,
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen struct mail_host *host) ATTR_NULL(3);
abe29107f5dce932d28a00912d2d75a01021bef1Timo Sirainenvoid director_resend_hosts(struct director *dir);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_remove_host(struct director *dir, struct director_host *src,
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen struct mail_host *host) ATTR_NULL(2, 3);
5e9bb72de1209cd39fdf3e95bdb26e047cc5594eTimo Sirainenvoid director_flush_host(struct director *dir, struct director_host *src,
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen struct mail_host *host) ATTR_NULL(3);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_update_user(struct director *dir, struct director_host *src,
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen struct user *user);
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainenvoid director_update_user_weak(struct director *dir, struct director_host *src,
ab779efe68458cf6fdcaa4f99527685d5563df0aTimo Sirainen struct director_connection *src_conn,
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen struct user *user) ATTR_NULL(3);
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainenvoid director_move_user(struct director *dir, struct director_host *src,
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen unsigned int username_hash, struct mail_host *host)
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen ATTR_NULL(3);
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainenvoid director_kick_user(struct director *dir, struct director_host *src,
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen struct director_host *orig_src, const char *username)
550d2fe097e95f12e8fa60ef52753ea7fe53d4eaTimo Sirainen ATTR_NULL(3);
36e091dc733c6cd690c5aae6e411e41adb1eca73Timo Sirainenvoid director_kick_user_hash(struct director *dir, struct director_host *src,
36e091dc733c6cd690c5aae6e411e41adb1eca73Timo Sirainen struct director_host *orig_src,
36e091dc733c6cd690c5aae6e411e41adb1eca73Timo Sirainen unsigned int username_hash,
36e091dc733c6cd690c5aae6e411e41adb1eca73Timo Sirainen const struct ip_addr *except_ip)
36e091dc733c6cd690c5aae6e411e41adb1eca73Timo Sirainen ATTR_NULL(3);
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainenvoid director_user_killed(struct director *dir, unsigned int username_hash);
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainenvoid director_user_killed_everywhere(struct director *dir,
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainen struct director_host *src,
15ab2452b0220a115f4351ad9d7fd5ec70ae7966Timo Sirainen struct director_host *orig_src,
a10ed8c47534b4c6b6bf2711ccfe577e720a47b4Timo Sirainen unsigned int username_hash) ATTR_NULL(3);
b6b9c99fefbbc662bd9a0006566133c4480bf0e8Timo Sirainenvoid director_user_weak(struct director *dir, struct user *user);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainenvoid director_sync_freeze(struct director *dir);
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainenvoid director_sync_thaw(struct director *dir);
0a53eb0283d7ec28c6105f61e118b96fce8ecb95Timo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen/* Send data to all directors using both left and right connections
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen (unless they're the same). */
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenvoid director_update_send(struct director *dir, struct director_host *src,
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen const char *cmd);
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainenvoid director_update_send_version(struct director *dir,
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen struct director_host *src,
e4194f4703eeec32b432371ae30fc8f25ab720d8Timo Sirainen unsigned int min_version, const char *cmd);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainenint director_connect_host(struct director *dir, struct director_host *host);
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen
c3a2a487e23a282e59254b82deb9344ed0306bb2Timo Sirainenvoid directors_init(void);
c3a2a487e23a282e59254b82deb9344ed0306bb2Timo Sirainenvoid directors_deinit(void);
c3a2a487e23a282e59254b82deb9344ed0306bb2Timo Sirainen
1df39b899804fd1dbc560f75382364822935c857Timo Sirainenvoid dir_debug(const char *fmt, ...) ATTR_FORMAT(1, 2);
1df39b899804fd1dbc560f75382364822935c857Timo Sirainen
2670cd577aa57eb9f915a4f4220ae48c9b4fc5fbTimo Sirainen#endif