From 1db62753d9e3b5d71018889c8ef0a3722a307455 Mon Sep 17 00:00:00 2001 From: Timo Sirainen Date: Thu, 27 May 2010 19:59:39 +0100 Subject: [PATCH] doveadm: mail commands can now be extended more easily by plugins. Also plugins can now override the list of -A users. --HG-- branch : HEAD --- src/doveadm/doveadm-mail-altmove.c | 22 +++----- src/doveadm/doveadm-mail-expunge.c | 22 +++----- src/doveadm/doveadm-mail-fetch.c | 16 +++--- src/doveadm/doveadm-mail-mailbox.c | 24 ++++----- src/doveadm/doveadm-mail-search.c | 22 +++----- src/doveadm/doveadm-mail.c | 87 ++++++++++++++++++++---------- src/doveadm/doveadm-mail.h | 34 ++++++++++-- src/doveadm/doveadm-settings.c | 5 +- src/doveadm/doveadm-settings.h | 2 + src/doveadm/doveadm.c | 16 ++++++ src/doveadm/doveadm.h | 1 + 11 files changed, 153 insertions(+), 98 deletions(-) diff --git a/src/doveadm/doveadm-mail-altmove.c b/src/doveadm/doveadm-mail-altmove.c index 4505eadb09..f4631d808a 100644 --- a/src/doveadm/doveadm-mail-altmove.c +++ b/src/doveadm/doveadm-mail-altmove.c @@ -9,11 +9,6 @@ #include "doveadm-mail-iter.h" #include "doveadm-mail.h" -struct altmove_cmd_context { - struct doveadm_mail_cmd_context ctx; - struct mail_search_args *search_args; -}; - static int cmd_altmove_box(const struct mailbox_info *info, struct mail_search_args *search_args) @@ -47,9 +42,8 @@ static void ns_purge(struct mail_namespace *ns) } static void -cmd_altmove_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) +cmd_altmove_run(struct doveadm_mail_cmd_context *ctx, struct mail_user *user) { - struct altmove_cmd_context *ctx = (struct altmove_cmd_context *)_ctx; const enum mailbox_list_iter_flags iter_flags = MAILBOX_LIST_ITER_RAW_LIST | MAILBOX_LIST_ITER_VIRTUAL_NAMES | @@ -94,11 +88,9 @@ cmd_altmove_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) } } -static void cmd_altmove_init(struct doveadm_mail_cmd_context *_ctx, +static void cmd_altmove_init(struct doveadm_mail_cmd_context *ctx, const char *const args[]) { - struct altmove_cmd_context *ctx = (struct altmove_cmd_context *)_ctx; - if (args[0] == NULL) doveadm_mail_help_name("altmove"); ctx->search_args = doveadm_mail_build_search_args(args); @@ -106,12 +98,12 @@ static void cmd_altmove_init(struct doveadm_mail_cmd_context *_ctx, static struct doveadm_mail_cmd_context *cmd_altmove_alloc(void) { - struct altmove_cmd_context *ctx; + struct doveadm_mail_cmd_context *ctx; - ctx = doveadm_mail_cmd_alloc(struct altmove_cmd_context); - ctx->ctx.init = cmd_altmove_init; - ctx->ctx.run = cmd_altmove_run; - return &ctx->ctx; + ctx = doveadm_mail_cmd_alloc(struct doveadm_mail_cmd_context); + ctx->v.init = cmd_altmove_init; + ctx->v.run = cmd_altmove_run; + return ctx; } struct doveadm_mail_cmd cmd_altmove = { diff --git a/src/doveadm/doveadm-mail-expunge.c b/src/doveadm/doveadm-mail-expunge.c index bc063c5443..2e74e448a4 100644 --- a/src/doveadm/doveadm-mail-expunge.c +++ b/src/doveadm/doveadm-mail-expunge.c @@ -9,11 +9,6 @@ #include "doveadm-mail-iter.h" #include "doveadm-mail.h" -struct expunge_cmd_context { - struct doveadm_mail_cmd_context ctx; - struct mail_search_args *search_args; -}; - static int cmd_expunge_box(const struct mailbox_info *info, struct mail_search_args *search_args) @@ -167,9 +162,8 @@ expunge_search_args_is_msgset_ok(struct mail_search_arg *args) } static void -cmd_expunge_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) +cmd_expunge_run(struct doveadm_mail_cmd_context *ctx, struct mail_user *user) { - struct expunge_cmd_context *ctx = (struct expunge_cmd_context *)_ctx; const enum mailbox_list_iter_flags iter_flags = MAILBOX_LIST_ITER_RAW_LIST | MAILBOX_LIST_ITER_VIRTUAL_NAMES | @@ -195,11 +189,9 @@ cmd_expunge_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) doveadm_mail_list_iter_deinit(&iter); } -static void cmd_expunge_init(struct doveadm_mail_cmd_context *_ctx, +static void cmd_expunge_init(struct doveadm_mail_cmd_context *ctx, const char *const args[]) { - struct expunge_cmd_context *ctx = (struct expunge_cmd_context *)_ctx; - if (args[0] == NULL) doveadm_mail_help_name("expunge"); @@ -209,12 +201,12 @@ static void cmd_expunge_init(struct doveadm_mail_cmd_context *_ctx, static struct doveadm_mail_cmd_context *cmd_expunge_alloc(void) { - struct expunge_cmd_context *ctx; + struct doveadm_mail_cmd_context *ctx; - ctx = doveadm_mail_cmd_alloc(struct expunge_cmd_context); - ctx->ctx.init = cmd_expunge_init; - ctx->ctx.run = cmd_expunge_run; - return &ctx->ctx; + ctx = doveadm_mail_cmd_alloc(struct doveadm_mail_cmd_context); + ctx->v.init = cmd_expunge_init; + ctx->v.run = cmd_expunge_run; + return ctx; } struct doveadm_mail_cmd cmd_expunge = { diff --git a/src/doveadm/doveadm-mail-fetch.c b/src/doveadm/doveadm-mail-fetch.c index 317e4635c8..4a10e956f0 100644 --- a/src/doveadm/doveadm-mail-fetch.c +++ b/src/doveadm/doveadm-mail-fetch.c @@ -20,7 +20,6 @@ struct fetch_cmd_context { struct doveadm_mail_cmd_context ctx; - struct mail_search_args *search_args; struct ostream *output; struct mail *mail; @@ -383,7 +382,8 @@ cmd_fetch_box(struct fetch_cmd_context *ctx, const struct mailbox_info *info) struct mail *mail; struct mailbox_header_lookup_ctx *headers = NULL; - if (doveadm_mail_iter_init(info, ctx->search_args, &trans, &iter) < 0) + if (doveadm_mail_iter_init(info, ctx->ctx.search_args, + &trans, &iter) < 0) return -1; if (array_count(&ctx->header_fields) > 1) { @@ -445,7 +445,7 @@ cmd_fetch_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) struct doveadm_mail_list_iter *iter; const struct mailbox_info *info; - iter = doveadm_mail_list_iter_init(user, ctx->search_args, iter_flags); + iter = doveadm_mail_list_iter_init(user, _ctx->search_args, iter_flags); while ((info = doveadm_mail_list_iter_next(iter)) != NULL) T_BEGIN { (void)cmd_fetch_box(ctx, info); } T_END; @@ -471,11 +471,11 @@ static void cmd_fetch_init(struct doveadm_mail_cmd_context *_ctx, doveadm_mail_help_name("fetch"); parse_fetch_fields(ctx, fetch_fields); - ctx->search_args = doveadm_mail_build_search_args(args + 1); + _ctx->search_args = doveadm_mail_build_search_args(args + 1); ctx->output = o_stream_create_fd(STDOUT_FILENO, 0, FALSE); ctx->hdr = str_new(default_pool, 512); - if (search_args_have_unique_fetch(ctx->search_args)) + if (search_args_have_unique_fetch(_ctx->search_args)) ctx->prefix = ""; else { random_fill_weak(prefix_buf, sizeof(prefix_buf)); @@ -492,9 +492,9 @@ static struct doveadm_mail_cmd_context *cmd_fetch_alloc(void) struct fetch_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct fetch_cmd_context); - ctx->ctx.init = cmd_fetch_init; - ctx->ctx.run = cmd_fetch_run; - ctx->ctx.deinit = cmd_fetch_deinit; + ctx->ctx.v.init = cmd_fetch_init; + ctx->ctx.v.run = cmd_fetch_run; + ctx->ctx.v.deinit = cmd_fetch_deinit; return &ctx->ctx; } diff --git a/src/doveadm/doveadm-mail-mailbox.c b/src/doveadm/doveadm-mail-mailbox.c index 378213c0c8..7fb9b8e761 100644 --- a/src/doveadm/doveadm-mail-mailbox.c +++ b/src/doveadm/doveadm-mail-mailbox.c @@ -96,7 +96,7 @@ doveadm_mailbox_cmd_alloc_size(size_t size) ctx = doveadm_mail_cmd_alloc_size(size); ctx->getopt_args = "78s"; - ctx->parse_arg = cmd_mailbox_parse_arg; + ctx->v.parse_arg = cmd_mailbox_parse_arg; return ctx; } @@ -166,8 +166,8 @@ static struct doveadm_mail_cmd_context *cmd_mailbox_list_alloc(void) struct list_cmd_context *ctx; ctx = doveadm_mailbox_cmd_alloc(struct list_cmd_context); - ctx->ctx.ctx.init = cmd_mailbox_list_init; - ctx->ctx.ctx.run = cmd_mailbox_list_run; + ctx->ctx.ctx.v.init = cmd_mailbox_list_init; + ctx->ctx.ctx.v.run = cmd_mailbox_list_run; return &ctx->ctx.ctx; } @@ -235,8 +235,8 @@ static struct doveadm_mail_cmd_context *cmd_mailbox_create_alloc(void) struct mailbox_cmd_context *ctx; ctx = doveadm_mailbox_cmd_alloc(struct mailbox_cmd_context); - ctx->ctx.ctx.init = cmd_mailbox_create_init; - ctx->ctx.ctx.run = cmd_mailbox_create_run; + ctx->ctx.ctx.v.init = cmd_mailbox_create_init; + ctx->ctx.ctx.v.run = cmd_mailbox_create_run; p_array_init(&ctx->mailboxes, ctx->ctx.ctx.pool, 16); return &ctx->ctx.ctx; } @@ -297,8 +297,8 @@ static struct doveadm_mail_cmd_context *cmd_mailbox_delete_alloc(void) struct mailbox_cmd_context *ctx; ctx = doveadm_mailbox_cmd_alloc(struct mailbox_cmd_context); - ctx->ctx.ctx.init = cmd_mailbox_delete_init; - ctx->ctx.ctx.run = cmd_mailbox_delete_run; + ctx->ctx.ctx.v.init = cmd_mailbox_delete_init; + ctx->ctx.ctx.v.run = cmd_mailbox_delete_run; p_array_init(&ctx->mailboxes, ctx->ctx.ctx.pool, 16); return &ctx->ctx.ctx; } @@ -361,8 +361,8 @@ static struct doveadm_mail_cmd_context *cmd_mailbox_rename_alloc(void) struct rename_cmd_context *ctx; ctx = doveadm_mailbox_cmd_alloc(struct rename_cmd_context); - ctx->ctx.ctx.init = cmd_mailbox_rename_init; - ctx->ctx.ctx.run = cmd_mailbox_rename_run; + ctx->ctx.ctx.v.init = cmd_mailbox_rename_init; + ctx->ctx.ctx.v.run = cmd_mailbox_rename_run; return &ctx->ctx.ctx; } @@ -423,9 +423,9 @@ cmd_mailbox_subscriptions_alloc(bool subscriptions) ctx->ctx.subscriptions = subscriptions; ctx->ctx.ctx.getopt_args = "78"; - ctx->ctx.ctx.parse_arg = cmd_mailbox_parse_arg; - ctx->ctx.ctx.init = cmd_mailbox_subscribe_init; - ctx->ctx.ctx.run = cmd_mailbox_subscribe_run; + ctx->ctx.ctx.v.parse_arg = cmd_mailbox_parse_arg; + ctx->ctx.ctx.v.init = cmd_mailbox_subscribe_init; + ctx->ctx.ctx.v.run = cmd_mailbox_subscribe_run; p_array_init(&ctx->mailboxes, ctx->ctx.ctx.pool, 16); return &ctx->ctx.ctx; } diff --git a/src/doveadm/doveadm-mail-search.c b/src/doveadm/doveadm-mail-search.c index eac69d5167..02174acfd5 100644 --- a/src/doveadm/doveadm-mail-search.c +++ b/src/doveadm/doveadm-mail-search.c @@ -8,11 +8,6 @@ #include -struct search_cmd_context { - struct doveadm_mail_cmd_context ctx; - struct mail_search_args *search_args; -}; - static int cmd_search_box(const struct mailbox_info *info, struct mail_search_args *search_args) @@ -42,9 +37,8 @@ cmd_search_box(const struct mailbox_info *info, } static void -cmd_search_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) +cmd_search_run(struct doveadm_mail_cmd_context *ctx, struct mail_user *user) { - struct search_cmd_context *ctx = (struct search_cmd_context *)_ctx; const enum mailbox_list_iter_flags iter_flags = MAILBOX_LIST_ITER_RAW_LIST | MAILBOX_LIST_ITER_VIRTUAL_NAMES | @@ -60,11 +54,9 @@ cmd_search_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) doveadm_mail_list_iter_deinit(&iter); } -static void cmd_search_init(struct doveadm_mail_cmd_context *_ctx, +static void cmd_search_init(struct doveadm_mail_cmd_context *ctx, const char *const args[]) { - struct search_cmd_context *ctx = (struct search_cmd_context *)_ctx; - if (args[0] == NULL) doveadm_mail_help_name("search"); @@ -73,12 +65,12 @@ static void cmd_search_init(struct doveadm_mail_cmd_context *_ctx, static struct doveadm_mail_cmd_context *cmd_search_alloc(void) { - struct search_cmd_context *ctx; + struct doveadm_mail_cmd_context *ctx; - ctx = doveadm_mail_cmd_alloc(struct search_cmd_context); - ctx->ctx.init = cmd_search_init; - ctx->ctx.run = cmd_search_run; - return &ctx->ctx; + ctx = doveadm_mail_cmd_alloc(struct doveadm_mail_cmd_context); + ctx->v.init = cmd_search_init; + ctx->v.run = cmd_search_run; + return ctx; } struct doveadm_mail_cmd cmd_search = { diff --git a/src/doveadm/doveadm-mail.c b/src/doveadm/doveadm-mail.c index 07792f6930..216b69247d 100644 --- a/src/doveadm/doveadm-mail.c +++ b/src/doveadm/doveadm-mail.c @@ -21,6 +21,9 @@ #include ARRAY_TYPE(doveadm_mail_cmd) doveadm_mail_cmds; +void (*hook_doveadm_mail_init)(struct doveadm_mail_cmd_context *ctx); +struct doveadm_mail_cmd_module_register + doveadm_mail_cmd_module_register = { 0 }; static int killed_signo = 0; @@ -60,7 +63,7 @@ static struct doveadm_mail_cmd_context *cmd_purge_alloc(void) struct doveadm_mail_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct doveadm_mail_cmd_context); - ctx->run = cmd_purge_run; + ctx->v.run = cmd_purge_run; return ctx; } @@ -156,14 +159,13 @@ static struct doveadm_mail_cmd_context *cmd_force_resync_alloc(void) struct force_resync_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct force_resync_cmd_context); - ctx->ctx.init = cmd_force_resync_init; - ctx->ctx.run = cmd_force_resync_run; + ctx->ctx.v.init = cmd_force_resync_init; + ctx->ctx.v.run = cmd_force_resync_run; return &ctx->ctx; } static int doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx, - struct mail_storage_service_ctx *storage_service, const struct mail_storage_service_input *input, const char **error_r) { @@ -173,7 +175,8 @@ doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx, int ret; i_set_failure_prefix(t_strdup_printf("doveadm(%s): ", input->username)); - ret = mail_storage_service_lookup(storage_service, input, + + ret = mail_storage_service_lookup(ctx->storage_service, input, &service_user, &error); if (ret <= 0) { if (ret < 0) { @@ -183,7 +186,7 @@ doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx, return ret; } - ret = mail_storage_service_next(storage_service, service_user, + ret = mail_storage_service_next(ctx->storage_service, service_user, &mail_user); if (ret < 0) { *error_r = "User init failed"; @@ -191,9 +194,9 @@ doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx, return ret; } - ctx->run(ctx, mail_user); - mail_storage_service_user_free(&service_user); + ctx->v.run(ctx, mail_user); mail_user_unref(&mail_user); + mail_storage_service_user_free(&service_user); return 1; } @@ -202,7 +205,6 @@ doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, const char *username, enum mail_storage_service_flags service_flags) { - struct mail_storage_service_ctx *storage_service; struct mail_storage_service_input input; const char *error; int ret; @@ -213,14 +215,17 @@ doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, memset(&input, 0, sizeof(input)); input.username = username; - storage_service = mail_storage_service_init(master_service, NULL, - service_flags); - ret = doveadm_mail_next_user(ctx, storage_service, &input, &error); + ctx->storage_service = mail_storage_service_init(master_service, NULL, + service_flags); + if (hook_doveadm_mail_init != NULL) + hook_doveadm_mail_init(ctx); + + ret = doveadm_mail_next_user(ctx, &input, &error); if (ret < 0) i_fatal("%s", error); else if (ret == 0) i_fatal("User no longer exists"); - mail_storage_service_deinit(&storage_service); + mail_storage_service_deinit(&ctx->storage_service); } static void sig_die(const siginfo_t *si, void *context ATTR_UNUSED) @@ -233,7 +238,6 @@ doveadm_mail_all_users(struct doveadm_mail_cmd_context *ctx, enum mail_storage_service_flags service_flags) { struct mail_storage_service_input input; - struct mail_storage_service_ctx *storage_service; unsigned int user_idx, user_count, interval, n; const char *user, *error; int ret; @@ -243,24 +247,24 @@ doveadm_mail_all_users(struct doveadm_mail_cmd_context *ctx, memset(&input, 0, sizeof(input)); input.service = "doveadm"; - storage_service = mail_storage_service_init(master_service, NULL, - service_flags); - + ctx->storage_service = mail_storage_service_init(master_service, NULL, + service_flags); lib_signals_set_handler(SIGINT, FALSE, sig_die, NULL); lib_signals_set_handler(SIGTERM, FALSE, sig_die, NULL); - user_count = mail_storage_service_all_init(storage_service); + if (hook_doveadm_mail_init != NULL) + hook_doveadm_mail_init(ctx); + + user_count = mail_storage_service_all_init(ctx->storage_service); n = user_count / 10000; for (interval = 10; n > 0 && interval < 1000; interval *= 10) n /= 10; user_idx = 0; - while ((ret = mail_storage_service_all_next(storage_service, - &user)) > 0) { + while ((ret = ctx->v.get_next_user(ctx, &user)) > 0) { input.username = user; T_BEGIN { - ret = doveadm_mail_next_user(ctx, storage_service, - &input, &error); + ret = doveadm_mail_next_user(ctx, &input, &error); if (ret < 0) i_error("%s", error); else if (ret == 0) @@ -285,7 +289,25 @@ doveadm_mail_all_users(struct doveadm_mail_cmd_context *ctx, i_set_failure_prefix("doveadm: "); if (ret < 0) i_error("Failed to iterate through some users"); - mail_storage_service_deinit(&storage_service); + mail_storage_service_deinit(&ctx->storage_service); +} + +static void +doveadm_mail_cmd_init_noop(struct doveadm_mail_cmd_context *ctx ATTR_UNUSED, + const char *const args[] ATTR_UNUSED) +{ +} + +static int +doveadm_mail_cmd_get_next_user(struct doveadm_mail_cmd_context *ctx, + const char **username_r) +{ + return mail_storage_service_all_next(ctx->storage_service, username_r); +} + +static void +doveadm_mail_cmd_deinit_noop(struct doveadm_mail_cmd_context *ctx ATTR_UNUSED) +{ } static void @@ -302,6 +324,15 @@ doveadm_mail_cmd(const struct doveadm_mail_cmd *cmd, int argc, char *argv[]) service_flags |= MAIL_STORAGE_SERVICE_FLAG_DEBUG; ctx = cmd->alloc(); + if (ctx->v.init == NULL) + ctx->v.init = doveadm_mail_cmd_init_noop; + if (ctx->v.get_next_user == NULL) + ctx->v.get_next_user = doveadm_mail_cmd_get_next_user; + if (ctx->v.deinit == NULL) + ctx->v.deinit = doveadm_mail_cmd_deinit_noop; + + p_array_init(&ctx->module_contexts, ctx->pool, 5); + getopt_args = t_strconcat("Au:", ctx->getopt_args, NULL); username = getenv("USER"); while ((c = getopt(argc, argv, getopt_args)) > 0) { @@ -315,7 +346,8 @@ doveadm_mail_cmd(const struct doveadm_mail_cmd *cmd, int argc, char *argv[]) username = optarg; break; default: - if (ctx->parse_arg == NULL || !ctx->parse_arg(ctx, c)) + if (ctx->v.parse_arg == NULL || + !ctx->v.parse_arg(ctx, c)) doveadm_mail_help(cmd); } } @@ -326,16 +358,15 @@ doveadm_mail_cmd(const struct doveadm_mail_cmd *cmd, int argc, char *argv[]) cmd->name, argv[0]); } - if (ctx->init != NULL) - ctx->init(ctx, (const void *)argv); + ctx->v.init(ctx, (const void *)argv); + if (!all_users) { doveadm_mail_single_user(ctx, username, service_flags); } else { service_flags |= MAIL_STORAGE_SERVICE_FLAG_TEMP_PRIV_DROP; doveadm_mail_all_users(ctx, service_flags); } - if (ctx->deinit != NULL) - ctx->deinit(ctx); + ctx->v.deinit(ctx); } static bool diff --git a/src/doveadm/doveadm-mail.h b/src/doveadm/doveadm-mail.h index 234ddcab8b..bd629b5ba6 100644 --- a/src/doveadm/doveadm-mail.h +++ b/src/doveadm/doveadm-mail.h @@ -2,22 +2,46 @@ #define DOVEADM_MAIL_H #include "doveadm.h" +#include "module-context.h" struct mail_user; +struct mail_storage_service_ctx; +struct mail_storage_service_input; +struct mail_storage_service_user; struct doveadm_mail_cmd_context; -struct doveadm_mail_cmd_context { - pool_t pool; - const char *getopt_args; - +struct doveadm_mail_cmd_vfuncs { bool (*parse_arg)(struct doveadm_mail_cmd_context *ctx,int c); void (*init)(struct doveadm_mail_cmd_context *ctx, const char *const args[]); + int (*get_next_user)(struct doveadm_mail_cmd_context *ctx, + const char **username_r); void (*run)(struct doveadm_mail_cmd_context *ctx, struct mail_user *mail_user); void (*deinit)(struct doveadm_mail_cmd_context *ctx); }; +struct doveadm_mail_cmd_module_register { + unsigned int id; +}; + +union doveadm_mail_cmd_module_context { + struct doveadm_mail_cmd_vfuncs super; + struct doveadm_mail_cmd_module_register *reg; +}; + +struct doveadm_mail_cmd_context { + pool_t pool; + const char *getopt_args; + struct mail_storage_service_ctx *storage_service; + /* search args aren't set for all mail commands */ + struct mail_search_args *search_args; + + struct doveadm_mail_cmd_vfuncs v; + + ARRAY_DEFINE(module_contexts, union doveadm_mail_cmd_module_context *); +}; + struct doveadm_mail_cmd { struct doveadm_mail_cmd_context *(*alloc)(void); const char *name; @@ -26,6 +50,8 @@ struct doveadm_mail_cmd { ARRAY_DEFINE_TYPE(doveadm_mail_cmd, struct doveadm_mail_cmd); extern ARRAY_TYPE(doveadm_mail_cmd) doveadm_mail_cmds; +extern void (*hook_doveadm_mail_init)(struct doveadm_mail_cmd_context *ctx); +extern struct doveadm_mail_cmd_module_register doveadm_mail_cmd_module_register; bool doveadm_mail_try_run(const char *cmd_name, int argc, char *argv[]); void doveadm_mail_register_cmd(const struct doveadm_mail_cmd *cmd); diff --git a/src/doveadm/doveadm-settings.c b/src/doveadm/doveadm-settings.c index 7d086752c3..120c97c661 100644 --- a/src/doveadm/doveadm-settings.c +++ b/src/doveadm/doveadm-settings.c @@ -12,6 +12,7 @@ static const struct setting_define doveadm_setting_defines[] = { DEF(SET_STR, base_dir), DEF(SET_STR, mail_plugins), DEF(SET_STR, mail_plugin_dir), + { SET_STRLIST, "plugin", offsetof(struct doveadm_settings, plugin_envs), NULL }, SETTING_DEFINE_LIST_END }; @@ -19,7 +20,9 @@ static const struct setting_define doveadm_setting_defines[] = { const struct doveadm_settings doveadm_default_settings = { .base_dir = PKG_RUNDIR, .mail_plugins = "", - .mail_plugin_dir = MODULEDIR + .mail_plugin_dir = MODULEDIR, + + .plugin_envs = ARRAY_INIT }; const struct setting_parser_info doveadm_setting_parser_info = { diff --git a/src/doveadm/doveadm-settings.h b/src/doveadm/doveadm-settings.h index 622ab46d7f..e01c99b3d8 100644 --- a/src/doveadm/doveadm-settings.h +++ b/src/doveadm/doveadm-settings.h @@ -5,6 +5,8 @@ struct doveadm_settings { const char *base_dir; const char *mail_plugins; const char *mail_plugin_dir; + + ARRAY_DEFINE(plugin_envs, const char *); }; extern const struct setting_parser_info doveadm_setting_parser_info; diff --git a/src/doveadm/doveadm.c b/src/doveadm/doveadm.c index f069021454..c3a76d0b65 100644 --- a/src/doveadm/doveadm.c +++ b/src/doveadm/doveadm.c @@ -57,6 +57,22 @@ const char *unixdate2str(time_t timestamp) return buf; } +const char *doveadm_plugin_getenv(const char *name) +{ + const char *const *envs; + unsigned int i, count; + + if (!array_is_created(&doveadm_settings->plugin_envs)) + return NULL; + + envs = array_get(&doveadm_settings->plugin_envs, &count); + for (i = 0; i < count; i += 2) { + if (strcmp(envs[i], name) == 0) + return envs[i+1]; + } + return NULL; +} + static void cmd_help(int argc, char *argv[]) { const struct doveadm_cmd *cmd; diff --git a/src/doveadm/doveadm.h b/src/doveadm/doveadm.h index 7579cb7994..afe8f4505f 100644 --- a/src/doveadm/doveadm.h +++ b/src/doveadm/doveadm.h @@ -31,6 +31,7 @@ void usage(void) ATTR_NORETURN; void help(const struct doveadm_cmd *cmd); const char *unixdate2str(time_t timestamp); +const char *doveadm_plugin_getenv(const char *name); void doveadm_register_director_commands(void); #endif -- 2.47.3