xref: /netbsd-src/external/bsd/ipf/dist/lib/load_file.c (revision 13885a665959c62f13a82b3caedf986eaa17aa31)
1 /*	$NetBSD: load_file.c,v 1.2 2012/07/22 14:27:36 darrenr Exp $	*/
2 
3 /*
4  * Copyright (C) 2012 by Darren Reed.
5  *
6  * See the IPFILTER.LICENCE file for details on licencing.
7  *
8  * Id: load_file.c,v 1.1.1.2 2012/07/22 13:44:39 darrenr Exp $
9  */
10 
11 #include "ipf.h"
12 #include <ctype.h>
13 
14 alist_t *
load_file(char * filename)15 load_file(char *filename)
16 {
17 	alist_t *a, *rtop, *rbot;
18 	char *s, line[1024], *t;
19 	int linenum, not;
20 	FILE *fp;
21 
22 	fp = fopen(filename + 7, "r");
23 	if (fp == NULL) {
24 		fprintf(stderr, "load_file cannot open '%s'\n", filename);
25 		return NULL;
26 	}
27 
28 	a = NULL;
29 	rtop = NULL;
30 	rbot = NULL;
31 	linenum = 0;
32 
33 	while (fgets(line, sizeof(line) - 1, fp)) {
34 		line[sizeof(line) - 1] = '\0';
35 		linenum++;
36 		/*
37 		 * Hunt for CR/LF.  If no LF, stop processing.
38 		 */
39 		s = strchr(line, '\n');
40 		if (s == NULL) {
41 			fprintf(stderr, "%d:%s: line too long\n",
42 				linenum, filename);
43 			fclose(fp);
44 			alist_free(rtop);
45 			return NULL;
46 		}
47 
48 		/*
49 		 * Remove trailing spaces
50 		 */
51 		for (; ISSPACE(*s); s--)
52 			*s = '\0';
53 
54 		s = strchr(line, '\r');
55 		if (s != NULL)
56 			*s = '\0';
57 		for (t = line; ISSPACE(*t); t++)
58 			;
59 		if (*t == '!') {
60 			not = 1;
61 			t++;
62 		} else
63 			not = 0;
64 
65 		/*
66 		 * Remove comment markers
67 		 */
68 		s = strchr(t, '#');
69 		if (s != NULL) {
70 			*s = '\0';
71 			if (s == t)
72 				continue;
73 		}
74 
75 		/*
76 		 * Trim off tailing white spaces
77 		 */
78 		s = strlen(t) + t - 1;
79 		while (ISSPACE(*s))
80 			*s-- = '\0';
81 
82 		a = alist_new(AF_UNSPEC, t);
83 		if (a != NULL) {
84 			a->al_not = not;
85 			if (rbot != NULL)
86 				rbot->al_next = a;
87 			else
88 				rtop = a;
89 			rbot = a;
90 		} else {
91 			fprintf(stderr, "%s:%d unrecognised content :%s\n",
92 				filename, linenum, t);
93 		}
94 	}
95 	fclose(fp);
96 
97 	return rtop;
98 }
99