BSD 4_4 release
[unix-history] / usr / src / usr.sbin / amd / amd / info_file.c
CommitLineData
e1a31032 1/*
e1a31032
KM
2 * Copyright (c) 1990 Jan-Simon Pendry
3 * Copyright (c) 1990 Imperial College of Science, Technology & Medicine
ad787160
C
4 * Copyright (c) 1990, 1993
5 * The Regents of the University of California. All rights reserved.
e1a31032
KM
6 *
7 * This code is derived from software contributed to Berkeley by
8 * Jan-Simon Pendry at Imperial College, London.
9 *
ad787160
C
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 * 3. All advertising materials mentioning features or use of this software
19 * must display the following acknowledgement:
20 * This product includes software developed by the University of
21 * California, Berkeley and its contributors.
22 * 4. Neither the name of the University nor the names of its contributors
23 * may be used to endorse or promote products derived from this software
24 * without specific prior written permission.
e1a31032 25 *
ad787160
C
26 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
27 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
30 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 * SUCH DAMAGE.
37 *
38 * @(#)info_file.c 8.1 (Berkeley) 6/6/93
8d2991d5 39 *
332f0791 40 * $Id: info_file.c,v 5.2.2.1 1992/02/09 15:08:28 jsp beta $
8d2991d5 41 *
e1a31032
KM
42 */
43
44/*
45 * Get info from file
46 */
47
48#include "am.h"
49
50#ifdef HAS_FILE_MAPS
51#include <ctype.h>
52#include <sys/stat.h>
53
54#define MAX_LINE_LEN 2048
55
2664d859 56static int read_line P((char *buf, int size, FILE *fp));
e1a31032
KM
57static int read_line(buf, size, fp)
58char *buf;
59int size;
60FILE *fp;
61{
62 int done = 0;
63
64 do {
65 while (fgets(buf, size, fp)) {
66 int len = strlen(buf);
67 done += len;
68 if (len > 1 && buf[len-2] == '\\' &&
69 buf[len-1] == '\n') {
70 int ch;
71 buf += len - 2;
72 size -= len - 2;
8d2991d5 73 *buf = '\n'; buf[1] = '\0';
e1a31032
KM
74 /*
75 * Skip leading white space on next line
76 */
77 while ((ch = getc(fp)) != EOF &&
78 isascii(ch) && isspace(ch))
79 ;
80 (void) ungetc(ch, fp);
81 } else {
82 return done;
83 }
84 }
85 } while (size > 0 && !feof(fp));
86
87 return done;
88}
89
90/*
91 * Try to locate a key in a file
92 */
2664d859 93static int search_or_reload_file P((FILE *fp, char *map, char *key, char **val, mnt_map *m, void (*fn)(mnt_map *m, char*, char*)));
e1a31032
KM
94static int search_or_reload_file(fp, map, key, val, m, fn)
95FILE *fp;
96char *map;
97char *key;
98char **val;
99mnt_map *m;
100void (*fn) P((mnt_map*, char*, char*));
101{
102 char key_val[MAX_LINE_LEN];
103 int chuck = 0;
104 int line_no = 0;
105
106 while (read_line(key_val, sizeof(key_val), fp)) {
107 char *kp;
108 char *cp;
109 char *hash;
110 int len = strlen(key_val);
111 line_no++;
112
113 /*
114 * Make sure we got the whole line
115 */
116 if (key_val[len-1] != '\n') {
117 plog(XLOG_WARNING, "line %d in \"%s\" is too long", line_no, map);
118 chuck = 1;
119 } else {
120 key_val[len-1] = '\0';
121 }
122
123 /*
124 * Strip comments
125 */
126 hash = strchr(key_val, '#');
127 if (hash)
128 *hash = '\0';
129
130 /*
131 * Find start of key
132 */
133 for (kp = key_val; *kp && isascii(*kp) && isspace(*kp); kp++)
134 ;
135
136 /*
137 * Ignore blank lines
138 */
139 if (!*kp)
140 goto again;
141
142 /*
143 * Find end of key
144 */
145 for (cp = kp; *cp&&(!isascii(*cp)||!isspace(*cp)); cp++)
146 ;
147
148 /*
149 * Check whether key matches
150 */
151 if (*cp)
152 *cp++ = '\0';
153
2664d859 154 if (fn || (*key == *kp && strcmp(key, kp) == 0)) {
e1a31032
KM
155 while (*cp && isascii(*cp) && isspace(*cp))
156 cp++;
157 if (*cp) {
158 /*
159 * Return a copy of the data
160 */
161 char *dc = strdup(cp);
2664d859
JSP
162 if (fn) {
163 (*fn)(m, strdup(kp), dc);
164 } else {
e1a31032
KM
165 *val = dc;
166#ifdef DEBUG
2664d859 167 dlog("%s returns %s", key, dc);
e1a31032 168#endif /* DEBUG */
2664d859 169 }
e1a31032
KM
170 if (!fn)
171 return 0;
172 } else {
173 plog(XLOG_USER, "%s: line %d has no value field", map, line_no);
174 }
175 }
176
177again:
178 /*
179 * If the last read didn't get a whole line then
180 * throw away the remainder before continuing...
181 */
182 if (chuck) {
183 while (fgets(key_val, sizeof(key_val), fp) &&
184 !strchr(key_val, '\n'))
185 ;
186 chuck = 0;
187 }
188 }
189
190 return fn ? 0 : ENOENT;
191}
192
2664d859
JSP
193static FILE *file_open P((char *map, time_t *tp));
194static FILE *file_open(map, tp)
e1a31032 195char *map;
2664d859 196time_t *tp;
e1a31032
KM
197{
198 FILE *mapf = fopen(map, "r");
2664d859
JSP
199 if (mapf && tp) {
200 struct stat stb;
201 if (fstat(fileno(mapf), &stb) < 0)
202 *tp = clocktime();
203 else
204 *tp = stb.st_mtime;
205 }
206 return mapf;
207}
208
209int file_init P((char *map, time_t *tp));
210int file_init(map, tp)
211char *map;
212time_t *tp;
213{
214 FILE *mapf = file_open(map, tp);
e1a31032
KM
215 if (mapf) {
216 (void) fclose(mapf);
217 return 0;
218 }
219 return errno;
220}
221
2664d859 222int file_reload P((mnt_map *m, char *map, void (*fn)()));
e1a31032
KM
223int file_reload(m, map, fn)
224mnt_map *m;
225char *map;
226void (*fn)();
227{
2664d859 228 FILE *mapf = file_open(map, (time_t *) 0);
e1a31032
KM
229 if (mapf) {
230 int error = search_or_reload_file(mapf, map, 0, 0, m, fn);
231 (void) fclose(mapf);
232 return error;
233 }
234
235 return errno;
236}
237
2664d859 238int file_search P((mnt_map *m, char *map, char *key, char **pval, time_t *tp));
e1a31032
KM
239int file_search(m, map, key, pval, tp)
240mnt_map *m;
241char *map;
242char *key;
243char **pval;
244time_t *tp;
245{
2664d859
JSP
246 time_t t;
247 FILE *mapf = file_open(map, &t);
e1a31032 248 if (mapf) {
e1a31032 249 int error;
2664d859
JSP
250 if (*tp < t) {
251 *tp = t;
e1a31032
KM
252 error = -1;
253 } else {
254 error = search_or_reload_file(mapf, map, key, pval, 0, 0);
255 }
256 (void) fclose(mapf);
257 return error;
258 }
259
260 return errno;
261}
2664d859
JSP
262
263int file_mtime P((char *map, time_t *tp));
264int file_mtime(map, tp)
265char *map;
266time_t *tp;
267{
268 FILE *mapf = file_open(map, tp);
269 if (mapf) {
270 (void) fclose(mapf);
271 return 0;
272 }
273
274 return errno;
275}
e1a31032 276#endif /* HAS_FILE_MAPS */