summaryrefslogtreecommitdiffstats
path: root/src/postconf/postconf_main.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/postconf/postconf_main.c')
-rw-r--r--src/postconf/postconf_main.c216
1 files changed, 216 insertions, 0 deletions
diff --git a/src/postconf/postconf_main.c b/src/postconf/postconf_main.c
new file mode 100644
index 0000000..07485f1
--- /dev/null
+++ b/src/postconf/postconf_main.c
@@ -0,0 +1,216 @@
+/*++
+/* NAME
+/* postconf_main 3
+/* SUMMARY
+/* basic support for main.cf
+/* SYNOPSIS
+/* #include <postconf.h>
+/*
+/* void pcf_read_parameters()
+/*
+/* void pcf_show_parameters(fp, mode, param_class, names)
+/* VSTREAM *fp;
+/* int mode;
+/* int param_class;
+/* char **names;
+/* DESCRIPTION
+/* pcf_read_parameters() reads parameters from main.cf.
+/*
+/* pcf_set_parameters() takes an array of \fIname=value\fR
+/* pairs and overrides settings read with pcf_read_parameters().
+/*
+/* pcf_show_parameters() writes main.cf parameters to the
+/* specified output stream.
+/*
+/* Arguments:
+/* .IP fp
+/* Output stream.
+/* .IP mode
+/* Bit-wise OR of zero or more of the following:
+/* .RS
+/* .IP PCF_FOLD_LINE
+/* Fold long lines.
+/* .IP PCF_SHOW_DEFS
+/* Output default parameter values.
+/* .IP PCF_SHOW_NONDEF
+/* Output explicit settings only.
+/* .IP PCF_HIDE_NAME
+/* Output parameter values without the "name =" prefix.
+/* .IP PCF_SHOW_EVAL
+/* Expand $name in parameter values.
+/* .RE
+/* .IP param_class
+/* Bit-wise OR of one or more of the following:
+/* .RS
+/* .IP PCF_PARAM_FLAG_BUILTIN
+/* Show built-in parameters.
+/* .IP PCF_PARAM_FLAG_SERVICE
+/* Show service-defined parameters.
+/* .IP PCF_PARAM_FLAG_USER
+/* Show user-defined parameters.
+/* .RE
+/* .IP names
+/* List of zero or more parameter names. If the list is empty,
+/* output all parameters.
+/* DIAGNOSTICS
+/* Problems are reported to the standard error stream.
+/* LICENSE
+/* .ad
+/* .fi
+/* The Secure Mailer license must be distributed with this software.
+/* AUTHOR(S)
+/* Wietse Venema
+/* IBM T.J. Watson Research
+/* P.O. Box 704
+/* Yorktown Heights, NY 10598, USA
+/*
+/* Wietse Venema
+/* Google, Inc.
+/* 111 8th Avenue
+/* New York, NY 10011, USA
+/*--*/
+
+/* System library. */
+
+#include <sys_defs.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <string.h>
+
+/* Utility library. */
+
+#include <msg.h>
+#include <mymalloc.h>
+#include <vstream.h>
+#include <vstring.h>
+#include <readlline.h>
+#include <dict.h>
+#include <stringops.h>
+#include <htable.h>
+#include <mac_expand.h>
+
+/* Global library. */
+
+#include <mail_params.h>
+#include <mail_conf.h>
+
+/* Application-specific. */
+
+#include <postconf.h>
+
+#define STR(x) vstring_str(x)
+
+/* pcf_read_parameters - read parameter info from file */
+
+void pcf_read_parameters(void)
+{
+ char *path;
+
+ /*
+ * A direct rip-off of mail_conf_read(). XXX Avoid code duplication by
+ * better code decomposition.
+ */
+ pcf_set_config_dir();
+ path = concatenate(var_config_dir, "/", MAIN_CONF_FILE, (char *) 0);
+ if (dict_load_file_xt(CONFIG_DICT, path) == 0)
+ msg_fatal("open %s: %m", path);
+ myfree(path);
+}
+
+/* pcf_set_parameters - add or override name=value pairs */
+
+void pcf_set_parameters(char **name_val_array)
+{
+ char *name, *value, *junk;
+ const char *err;
+ char **cpp;
+
+ for (cpp = name_val_array; *cpp; cpp++) {
+ junk = mystrdup(*cpp);
+ if ((err = split_nameval(junk, &name, &value)) != 0)
+ msg_fatal("invalid parameter override: %s: %s", *cpp, err);
+ mail_conf_update(name, value);
+ myfree(junk);
+ }
+}
+
+/* pcf_print_parameter - show specific parameter */
+
+static void pcf_print_parameter(VSTREAM *fp, int mode, const char *name,
+ PCF_PARAM_NODE *node)
+{
+ const char *value;
+
+ /*
+ * Use the default or actual value.
+ */
+ value = pcf_lookup_parameter_value(mode, name, (PCF_MASTER_ENT *) 0, node);
+
+ /*
+ * Optionally expand $name in the parameter value. Print the result with
+ * or without the name= prefix.
+ */
+ if (value != 0) {
+ if (mode & PCF_HIDE_VALUE) {
+ pcf_print_line(fp, mode, "%s\n", name);
+ } else {
+ if ((mode & PCF_SHOW_EVAL) != 0 && PCF_RAW_PARAMETER(node) == 0)
+ value = pcf_expand_parameter_value((VSTRING *) 0, mode, value,
+ (PCF_MASTER_ENT *) 0);
+ if ((mode & PCF_HIDE_NAME) == 0) {
+ pcf_print_line(fp, mode, "%s = %s\n", name, value);
+ } else {
+ pcf_print_line(fp, mode, "%s\n", value);
+ }
+ }
+ if (msg_verbose)
+ vstream_fflush(fp);
+ }
+}
+
+/* pcf_comp_names - qsort helper */
+
+static int pcf_comp_names(const void *a, const void *b)
+{
+ PCF_PARAM_INFO **ap = (PCF_PARAM_INFO **) a;
+ PCF_PARAM_INFO **bp = (PCF_PARAM_INFO **) b;
+
+ return (strcmp(PCF_PARAM_INFO_NAME(ap[0]),
+ PCF_PARAM_INFO_NAME(bp[0])));
+}
+
+/* pcf_show_parameters - show parameter info */
+
+void pcf_show_parameters(VSTREAM *fp, int mode, int param_class, char **names)
+{
+ PCF_PARAM_INFO **list;
+ PCF_PARAM_INFO **ht;
+ char **namep;
+ PCF_PARAM_NODE *node;
+
+ /*
+ * Show all parameters.
+ */
+ if (*names == 0) {
+ list = PCF_PARAM_TABLE_LIST(pcf_param_table);
+ qsort((void *) list, pcf_param_table->used, sizeof(*list),
+ pcf_comp_names);
+ for (ht = list; *ht; ht++)
+ if (param_class & PCF_PARAM_INFO_NODE(*ht)->flags)
+ pcf_print_parameter(fp, mode, PCF_PARAM_INFO_NAME(*ht),
+ PCF_PARAM_INFO_NODE(*ht));
+ myfree((void *) list);
+ return;
+ }
+
+ /*
+ * Show named parameters.
+ */
+ for (namep = names; *namep; namep++) {
+ if ((node = PCF_PARAM_TABLE_FIND(pcf_param_table, *namep)) == 0) {
+ msg_warn("%s: unknown parameter", *namep);
+ } else {
+ pcf_print_parameter(fp, mode, *namep, node);
+ }
+ }
+}