config-request.c revision 1358e2c58ce29231485a5cfa454756d429ad3d2c
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen/* Copyright (C) 2005-2009 Dovecot authors, see the included COPYING file */
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "lib.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "array.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "str.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "hash.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "ostream.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "settings-parser.h"
72f67d7d7681934bb3d4baaea1d88f79521dee3dTimo Sirainen#include "master-service-settings.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "all-settings.h"
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen#include "config-parser.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen#include "config-request.h"
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainenstruct settings_export_context {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen pool_t pool;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen string_t *value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen string_t *prefix;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen struct hash_table *keys;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen bool export_defaults;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen config_request_callback_t *callback;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen void *context;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen};
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainenstatic bool parsers_are_connected(struct setting_parser_info *root,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen struct setting_parser_info *info)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen{
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen struct setting_parser_info *const *dep, *p;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen /* we're trying to find info or its parents from root's dependencies. */
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (p = info; p != NULL; p = p->parent) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (p == root)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return TRUE;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (root->dependencies != NULL) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (dep = root->dependencies; *dep != NULL; dep++) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (p = info; p != NULL; p = p->parent) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (p == *dep)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return TRUE;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return FALSE;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen}
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainenstatic bool
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainenconfig_setting_parser_is_in_service(const struct config_setting_parser_list *list,
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen const char *module)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen{
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen struct config_setting_parser_list *l;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen if (strcmp(list->module_name, module) == 0)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return TRUE;
72f67d7d7681934bb3d4baaea1d88f79521dee3dTimo Sirainen if (list->root == &master_service_setting_parser_info) {
72f67d7d7681934bb3d4baaea1d88f79521dee3dTimo Sirainen /* everyone wants master service settings */
72f67d7d7681934bb3d4baaea1d88f79521dee3dTimo Sirainen return TRUE;
72f67d7d7681934bb3d4baaea1d88f79521dee3dTimo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (l = config_setting_parsers; l->module_name != NULL; l++) {
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen if (strcmp(l->module_name, module) != 0)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen continue;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen /* see if we can find a way to get from the original parser
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen to this parser */
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (parsers_are_connected(l->root, list->root))
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return TRUE;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen return FALSE;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen}
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainenstatic void settings_export(struct settings_export_context *ctx,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const struct setting_parser_info *info,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const void *set)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen{
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const struct setting_define *def;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const void *value, *default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen void *const *children = NULL;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen unsigned int i, count, prefix_len;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *str;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen char *key;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (def = info->defines; def->key != NULL; def++) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen value = CONST_PTR_OFFSET(set, def->offset);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen default_value = info->defaults == NULL ? NULL :
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen CONST_PTR_OFFSET(info->defaults, def->offset);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen count = 0;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_truncate(ctx->value, 0);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen switch (def->type) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_INTERNAL:
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_BOOL: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const bool *val = value, *dval = default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (ctx->export_defaults ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen dval == NULL || *val != *dval) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append(ctx->value,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen *val ? "yes" : "no");
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_UINT: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const unsigned int *val = value, *dval = default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (ctx->export_defaults ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen dval == NULL || *val != *dval)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_printfa(ctx->value, "%u", *val);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_STR_VARS: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *val = value, *sval;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *_dval = default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *dval = _dval == NULL ? NULL : *_dval;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen i_assert(*val == NULL ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen **val == SETTING_STRVAR_UNEXPANDED[0]);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen sval = *val == NULL ? NULL : (*val + 1);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if ((ctx->export_defaults ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen null_strcmp(sval, dval) != 0) && sval != NULL)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append(ctx->value, sval);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_STR: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *val = value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *_dval = default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *dval = _dval == NULL ? NULL : *_dval;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if ((ctx->export_defaults ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen null_strcmp(*val, dval) != 0) && *val != NULL)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append(ctx->value, *val);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_ENUM: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *val = value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *_dval = default_value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *dval = _dval == NULL ? NULL : *_dval;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen unsigned int len = strlen(*val);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (ctx->export_defaults ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen strncmp(*val, dval, len) != 0 ||
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ((*val)[len] != ':' && (*val)[len] != '\0'))
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append(ctx->value, *val);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_DEFLIST: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const ARRAY_TYPE(void_array) *val = value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (!array_is_created(val))
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen children = array_get(val, &count);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (i = 0; i < count; i++) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (i > 0)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append_c(ctx->value, ' ');
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_printfa(ctx->value, "%u", i);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen case SET_STRLIST: {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const ARRAY_TYPE(const_string) *val = value;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen const char *const *strings;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (!array_is_created(val))
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen key = p_strconcat(ctx->pool, str_c(ctx->prefix),
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen def->key, NULL);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (hash_table_lookup(ctx->keys, key) != NULL) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen /* already added all of these */
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen hash_table_insert(ctx->keys, key, key);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx->callback(key, "0", TRUE, ctx->context);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen strings = array_get(val, &count);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen i_assert(count % 2 == 0);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (i = 0; i < count; i += 2) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str = p_strdup_printf(ctx->pool, "%s%s%c0%c%s",
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_c(ctx->prefix),
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen def->key,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen SETTINGS_SEPARATOR,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen SETTINGS_SEPARATOR,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen strings[i]);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx->callback(str, strings[i+1], FALSE,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx->context);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen count = 0;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen break;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (str_len(ctx->value) > 0) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen key = p_strconcat(ctx->pool, str_c(ctx->prefix),
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen def->key, NULL);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen if (hash_table_lookup(ctx->keys, key) == NULL) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx->callback(key, str_c(ctx->value),
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen def->type == SET_DEFLIST,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx->context);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen hash_table_insert(ctx->keys, key, key);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen prefix_len = str_len(ctx->prefix);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen for (i = 0; i < count; i++) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append(ctx->prefix, def->key);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append_c(ctx->prefix, SETTINGS_SEPARATOR);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_printfa(ctx->prefix, "%u", i);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_append_c(ctx->prefix, SETTINGS_SEPARATOR);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen settings_export(ctx, def->list_info, children[i]);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_truncate(ctx->prefix, prefix_len);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen}
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainenvoid config_request_handle(const struct config_filter *filter,
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen const char *module, enum config_dump_flags flags,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen config_request_callback_t *callback, void *context)
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen{
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen const struct config_setting_parser_list *l;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen struct settings_export_context ctx;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen memset(&ctx, 0, sizeof(ctx));
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.pool = pool_alloconly_create("config request", 10240);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.callback = callback;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.context = context;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.export_defaults = (flags & CONFIG_DUMP_FLAG_DEFAULTS) != 0;
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.value = t_str_new(256);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.prefix = t_str_new(64);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen ctx.keys = hash_table_create(default_pool, ctx.pool, 0,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen str_hash, (hash_cmp_callback_t *)strcmp);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen l = config_filter_match_parsers(config_filter, filter);
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen for (; l->module_name != NULL; l++) {
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen if (*module == '\0' ||
1358e2c58ce29231485a5cfa454756d429ad3d2cTimo Sirainen config_setting_parser_is_in_service(l, module)) {
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen settings_export(&ctx, l->root,
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen settings_parser_get(l->parser));
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen }
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen hash_table_destroy(&ctx.keys);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen pool_unref(&ctx.pool);
e9e5e84ffb2ce2e606a24ce6d930580367562ff0Timo Sirainen}