xref: /netbsd-src/external/ibm-public/postfix/dist/src/postconf/postconf_main.c (revision fdd524d4ccd2bb0c6f67401e938dabf773eb0372)
1 /*	$NetBSD: postconf_main.c,v 1.1.1.3 2014/07/06 19:27:53 tron Exp $	*/
2 
3 /*++
4 /* NAME
5 /*	postconf_main 3
6 /* SUMMARY
7 /*	basic support for main.cf
8 /* SYNOPSIS
9 /*	#include <postconf.h>
10 /*
11 /*	void	pcf_read_parameters()
12 /*
13 /*	void	pcf_show_parameters(fp, mode, param_class, names)
14 /*	VSTREAM	*fp;
15 /*	int	mode;
16 /*	int	param_class;
17 /*	char	**names;
18 /* DESCRIPTION
19 /*	pcf_read_parameters() reads parameters from main.cf.
20 /*
21 /*	pcf_set_parameters() takes an array of \fIname=value\fR
22 /*	pairs and overrides settings read with pcf_read_parameters().
23 /*
24 /*	pcf_show_parameters() writes main.cf parameters to the
25 /*	specified output stream.
26 /*
27 /*	Arguments:
28 /* .IP fp
29 /*	Output stream.
30 /* .IP mode
31 /*	Bit-wise OR of zero or more of the following:
32 /* .RS
33 /* .IP PCF_FOLD_LINE
34 /*	Fold long lines.
35 /* .IP PCF_SHOW_DEFS
36 /*	Output default parameter values.
37 /* .IP PCF_SHOW_NONDEF
38 /*	Output explicit settings only.
39 /* .IP PCF_HIDE_NAME
40 /*	Output parameter values without the "name =" prefix.
41 /* .IP PCF_SHOW_EVAL
42 /*	Expand $name in parameter values.
43 /* .RE
44 /* .IP param_class
45 /*	Bit-wise OR of one or more of the following:
46 /* .RS
47 /* .IP PCF_PARAM_FLAG_BUILTIN
48 /*	Show built-in parameters.
49 /* .IP PCF_PARAM_FLAG_SERVICE
50 /*	Show service-defined parameters.
51 /* .IP PCF_PARAM_FLAG_USER
52 /*	Show user-defined parameters.
53 /* .RE
54 /* .IP names
55 /*	List of zero or more parameter names. If the list is empty,
56 /*	output all parameters.
57 /* DIAGNOSTICS
58 /*	Problems are reported to the standard error stream.
59 /* LICENSE
60 /* .ad
61 /* .fi
62 /*	The Secure Mailer license must be distributed with this software.
63 /* AUTHOR(S)
64 /*	Wietse Venema
65 /*	IBM T.J. Watson Research
66 /*	P.O. Box 704
67 /*	Yorktown Heights, NY 10598, USA
68 /*--*/
69 
70 /* System library. */
71 
72 #include <sys_defs.h>
73 #include <stdarg.h>
74 #include <stdlib.h>
75 #include <string.h>
76 
77 /* Utility library. */
78 
79 #include <msg.h>
80 #include <mymalloc.h>
81 #include <vstream.h>
82 #include <vstring.h>
83 #include <readlline.h>
84 #include <dict.h>
85 #include <stringops.h>
86 #include <htable.h>
87 #include <mac_expand.h>
88 
89 /* Global library. */
90 
91 #include <mail_params.h>
92 #include <mail_conf.h>
93 
94 /* Application-specific. */
95 
96 #include <postconf.h>
97 
98 #define STR(x) vstring_str(x)
99 
100 /* pcf_read_parameters - read parameter info from file */
101 
102 void    pcf_read_parameters(void)
103 {
104     char   *path;
105 
106     /*
107      * A direct rip-off of mail_conf_read(). XXX Avoid code duplication by
108      * better code decomposition.
109      */
110     pcf_set_config_dir();
111     path = concatenate(var_config_dir, "/", MAIN_CONF_FILE, (char *) 0);
112     if (dict_load_file_xt(CONFIG_DICT, path) == 0)
113 	msg_fatal("open %s: %m", path);
114     myfree(path);
115 }
116 
117 /* pcf_set_parameters - add or override name=value pairs */
118 
119 void    pcf_set_parameters(char **name_val_array)
120 {
121     char   *name, *value, *junk;
122     const char *err;
123     char  **cpp;
124 
125     for (cpp = name_val_array; *cpp; cpp++) {
126 	junk = mystrdup(*cpp);
127 	if ((err = split_nameval(junk, &name, &value)) != 0)
128 	    msg_fatal("invalid parameter override: %s: %s", *cpp, err);
129 	mail_conf_update(name, value);
130 	myfree(junk);
131     }
132 }
133 
134 /* pcf_print_parameter - show specific parameter */
135 
136 static void pcf_print_parameter(VSTREAM *fp, int mode, const char *name,
137 				        PCF_PARAM_NODE *node)
138 {
139     const char *value;
140 
141     /*
142      * Use the default or actual value.
143      */
144     value = pcf_lookup_parameter_value(mode, name, (PCF_MASTER_ENT *) 0, node);
145 
146     /*
147      * Optionally expand $name in the parameter value. Print the result with
148      * or without the name= prefix.
149      */
150     if (value != 0) {
151 	if ((mode & PCF_SHOW_EVAL) != 0 && PCF_RAW_PARAMETER(node) == 0)
152 	    value = pcf_expand_parameter_value((VSTRING *) 0, mode, value,
153 					       (PCF_MASTER_ENT *) 0);
154 	if ((mode & PCF_HIDE_NAME) == 0) {
155 	    pcf_print_line(fp, mode, "%s = %s\n", name, value);
156 	} else {
157 	    pcf_print_line(fp, mode, "%s\n", value);
158 	}
159 	if (msg_verbose)
160 	    vstream_fflush(fp);
161     }
162 }
163 
164 /* pcf_comp_names - qsort helper */
165 
166 static int pcf_comp_names(const void *a, const void *b)
167 {
168     PCF_PARAM_INFO **ap = (PCF_PARAM_INFO **) a;
169     PCF_PARAM_INFO **bp = (PCF_PARAM_INFO **) b;
170 
171     return (strcmp(PCF_PARAM_INFO_NAME(ap[0]),
172 		   PCF_PARAM_INFO_NAME(bp[0])));
173 }
174 
175 /* pcf_show_parameters - show parameter info */
176 
177 void    pcf_show_parameters(VSTREAM *fp, int mode, int param_class, char **names)
178 {
179     PCF_PARAM_INFO **list;
180     PCF_PARAM_INFO **ht;
181     char  **namep;
182     PCF_PARAM_NODE *node;
183 
184     /*
185      * Show all parameters.
186      */
187     if (*names == 0) {
188 	list = PCF_PARAM_TABLE_LIST(pcf_param_table);
189 	qsort((char *) list, pcf_param_table->used, sizeof(*list),
190 	      pcf_comp_names);
191 	for (ht = list; *ht; ht++)
192 	    if (param_class & PCF_PARAM_INFO_NODE(*ht)->flags)
193 		pcf_print_parameter(fp, mode, PCF_PARAM_INFO_NAME(*ht),
194 				    PCF_PARAM_INFO_NODE(*ht));
195 	myfree((char *) list);
196 	return;
197     }
198 
199     /*
200      * Show named parameters.
201      */
202     for (namep = names; *namep; namep++) {
203 	if ((node = PCF_PARAM_TABLE_FIND(pcf_param_table, *namep)) == 0) {
204 	    msg_warn("%s: unknown parameter", *namep);
205 	} else {
206 	    pcf_print_parameter(fp, mode, *namep, node);
207 	}
208     }
209 }
210