xref: /illumos-gate/usr/src/cmd/ipf/lib/common/printfr.c (revision d6c23f6f)
1 /*
2  * Copyright (C) 2000-2005 by Darren Reed.
3  *
4  * See the IPFILTER.LICENCE file for details on licencing.
5  *
6  * $Id: printfr.c,v 1.43.2.12 2005/06/12 07:18:42 darrenr Exp $
7  *
8  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
9  * Use is subject to license terms.
10  */
11 
12 #pragma ident	"%Z%%M%	%I%	%E% SMI"
13 
14 #include "ipf.h"
15 
16 /*
17  * print the filter structure in a useful way
18  */
printfr(fp,iocfunc)19 void	printfr(fp, iocfunc)
20 struct	frentry	*fp;
21 ioctlfunc_t	iocfunc;
22 {
23 	struct protoent	*p;
24 	u_short	sec[2];
25 	u_32_t type;
26 	u_char *t;
27 	char *s;
28 	int pr;
29 
30 	pr = -2;
31 	type = fp->fr_type & ~FR_T_BUILTIN;
32 
33 	if ((fp->fr_type & FR_T_BUILTIN) != 0)
34 		printf("# Builtin: ");
35 
36 	if (fp->fr_collect != 0)
37 		printf("%u ", fp->fr_collect);
38 
39 	if (fp->fr_type == FR_T_CALLFUNC) {
40 		;
41 	} else if (fp->fr_func != NULL) {
42 		printf("call");
43 		if ((fp->fr_flags & FR_CALLNOW) != 0)
44 			printf(" now");
45 		s = kvatoname(fp->fr_func, iocfunc);
46 		printf(" %s/%u", s ? s : "?", fp->fr_arg);
47 	} else if (FR_ISPASS(fp->fr_flags))
48 		printf("pass");
49 	else if (FR_ISBLOCK(fp->fr_flags)) {
50 		printf("block");
51 		if (fp->fr_flags & FR_RETICMP) {
52 			if ((fp->fr_flags & FR_RETMASK) == FR_FAKEICMP)
53 				printf(" return-icmp-as-dest");
54 			else if ((fp->fr_flags & FR_RETMASK) == FR_RETICMP)
55 				printf(" return-icmp");
56 			if (fp->fr_icode) {
57 				if (fp->fr_icode <= MAX_ICMPCODE)
58 					printf("(%s)",
59 						icmpcodes[(int)fp->fr_icode]);
60 				else
61 					printf("(%d)", fp->fr_icode);
62 			}
63 		} else if ((fp->fr_flags & FR_RETMASK) == FR_RETRST)
64 			printf(" return-rst");
65 	} else if ((fp->fr_flags & FR_LOGMASK) == FR_LOG) {
66 		printlog(fp);
67 	} else if (FR_ISACCOUNT(fp->fr_flags))
68 		printf("count");
69 	else if (FR_ISAUTH(fp->fr_flags))
70 		printf("auth");
71 	else if (FR_ISPREAUTH(fp->fr_flags))
72 		printf("preauth");
73 	else if (FR_ISNOMATCH(fp->fr_flags))
74 		printf("nomatch");
75 	else if (FR_ISSKIP(fp->fr_flags))
76 		printf("skip %u", fp->fr_arg);
77 	else {
78 		printf("%x", fp->fr_flags);
79 	}
80 
81 	if (fp->fr_flags & FR_OUTQUE)
82 		printf(" out ");
83 	else
84 		printf(" in ");
85 
86 	if (((fp->fr_flags & FR_LOGB) == FR_LOGB) ||
87 	    ((fp->fr_flags & FR_LOGP) == FR_LOGP)) {
88 		printlog(fp);
89 		putchar(' ');
90 	}
91 
92 	if (fp->fr_flags & FR_QUICK)
93 		printf("quick ");
94 
95 	if (*fp->fr_ifname) {
96 		printifname("on ", fp->fr_ifname, fp->fr_ifa);
97 		if (*fp->fr_ifnames[1] && strcmp(fp->fr_ifnames[1], "*"))
98 			printifname(",", fp->fr_ifnames[1], fp->fr_ifas[1]);
99 		putchar(' ');
100 	}
101 
102 	if (*fp->fr_dif.fd_ifname || (fp->fr_flags & FR_DUP))
103 		print_toif("dup-to", &fp->fr_dif);
104 	if (*fp->fr_tif.fd_ifname)
105 		print_toif("to", &fp->fr_tif);
106 	if (*fp->fr_rif.fd_ifname)
107 		print_toif("reply-to", &fp->fr_rif);
108 	if (fp->fr_flags & FR_FASTROUTE)
109 		printf("fastroute ");
110 
111 	if ((*fp->fr_ifnames[2] && strcmp(fp->fr_ifnames[2], "*")) ||
112 	    (*fp->fr_ifnames[3] && strcmp(fp->fr_ifnames[3], "*"))) {
113 		if (fp->fr_flags & FR_OUTQUE)
114 			printf("in-via ");
115 		else
116 			printf("out-via ");
117 
118 		if (*fp->fr_ifnames[2]) {
119 			printifname("", fp->fr_ifnames[2],
120 				    fp->fr_ifas[2]);
121 			putchar(' ');
122 
123 			if (*fp->fr_ifnames[3]) {
124 				printifname(",", fp->fr_ifnames[3],
125 					    fp->fr_ifas[3]);
126 			}
127 		}
128 	}
129 
130 	if (type == FR_T_IPF) {
131 		if (fp->fr_mip.fi_tos)
132 			printf("tos %#x ", fp->fr_tos);
133 		if (fp->fr_mip.fi_ttl)
134 			printf("ttl %d ", fp->fr_ttl);
135 		if (fp->fr_flx & FI_TCPUDP) {
136 			printf("proto tcp/udp ");
137 			pr = -1;
138 		} else if (fp->fr_mip.fi_p) {
139 			pr = fp->fr_ip.fi_p;
140 			p = getprotobynumber(pr);
141 			printf("proto ");
142 			printproto(p, pr, NULL);
143 			putchar(' ');
144 		}
145 	}
146 
147 	if (type == FR_T_NONE) {
148 		printf("all");
149 	} else if (type == FR_T_IPF) {
150 		printf("from %s", fp->fr_flags & FR_NOTSRCIP ? "!" : "");
151 		printaddr(fp->fr_v, fp->fr_satype, fp->fr_ifname,
152 			  &fp->fr_src.s_addr, &fp->fr_smsk.s_addr);
153 		if (fp->fr_scmp)
154 			printportcmp(pr, &fp->fr_tuc.ftu_src);
155 
156 		printf(" to %s", fp->fr_flags & FR_NOTDSTIP ? "!" : "");
157 		printaddr(fp->fr_v, fp->fr_datype, fp->fr_ifname,
158 			  &fp->fr_dst.s_addr, &fp->fr_dmsk.s_addr);
159 		if (fp->fr_dcmp)
160 			printportcmp(pr, &fp->fr_tuc.ftu_dst);
161 
162 		if ((fp->fr_proto == IPPROTO_ICMP
163 #ifdef	USE_INET6
164 		    || fp->fr_proto == IPPROTO_ICMPV6
165 #endif
166 		    ) && fp->fr_icmpm) {
167 			int	type = fp->fr_icmp, code;
168 
169 			type = ntohs(fp->fr_icmp);
170 			code = type & 0xff;
171 			type /= 256;
172 			if (type < (sizeof(icmptypes) / sizeof(char *) - 1) &&
173 			    icmptypes[type] && fp->fr_proto == IPPROTO_ICMP)
174 				printf(" icmp-type %s", icmptypes[type]);
175 			else
176 				printf(" icmp-type %d", type);
177 			if (ntohs(fp->fr_icmpm) & 0xff)
178 				printf(" code %d", code);
179 		}
180 		if ((fp->fr_proto == IPPROTO_TCP) &&
181 		    (fp->fr_tcpf || fp->fr_tcpfm)) {
182 			printf(" flags ");
183 			if (fp->fr_tcpf & ~TCPF_ALL)
184 				printf("0x%x", fp->fr_tcpf);
185 			else
186 				for (s = flagset, t = flags; *s; s++, t++)
187 					if (fp->fr_tcpf & *t)
188 						(void)putchar(*s);
189 			if (fp->fr_tcpfm) {
190 				(void)putchar('/');
191 				if (fp->fr_tcpfm & ~TCPF_ALL)
192 					printf("0x%x", fp->fr_tcpfm);
193 				else
194 					for (s = flagset, t = flags; *s;
195 					     s++, t++)
196 						if (fp->fr_tcpfm & *t)
197 							(void)putchar(*s);
198 			}
199 		}
200 	} else if (type == FR_T_BPFOPC) {
201 		fakebpf_t *fb;
202 		int i;
203 
204 		printf("bpf-v%d { \"", fp->fr_v);
205 		i = fp->fr_dsize / sizeof(*fb);
206 
207 		for (fb = fp->fr_data, s = ""; i; i--, fb++, s = " ")
208 			printf("%s%#x %#x %#x %#x", s, fb->fb_c, fb->fb_t,
209 			       fb->fb_f, fb->fb_k);
210 
211 		printf("\" }");
212 	} else if (type == FR_T_COMPIPF) {
213 		;
214 	} else if (type == FR_T_CALLFUNC) {
215 		printf("call function at %p", fp->fr_data);
216 	} else {
217 		printf("[unknown filter type %#x]", fp->fr_type);
218 	}
219 
220 	if ((type == FR_T_IPF) &&
221 	    ((fp->fr_flx & FI_WITH) || (fp->fr_mflx & FI_WITH) ||
222 	     fp->fr_optbits || fp->fr_optmask ||
223 	     fp->fr_secbits || fp->fr_secmask)) {
224 		char *comma = " ";
225 
226 		printf(" with");
227 		if (fp->fr_optbits || fp->fr_optmask ||
228 		    fp->fr_secbits || fp->fr_secmask) {
229 			sec[0] = fp->fr_secmask;
230 			sec[1] = fp->fr_secbits;
231 			if (fp->fr_v == 4)
232 				optprint(sec, fp->fr_optmask, fp->fr_optbits);
233 #ifdef	USE_INET6
234 			else
235 				optprintv6(sec, fp->fr_optmask,
236 					   fp->fr_optbits);
237 #endif
238 		} else if (fp->fr_mflx & FI_OPTIONS) {
239 			fputs(comma, stdout);
240 			if (!(fp->fr_flx & FI_OPTIONS))
241 				printf("not ");
242 			printf("ipopts");
243 			comma = ",";
244 		}
245 		if (fp->fr_mflx & FI_SHORT) {
246 			fputs(comma, stdout);
247 			if (!(fp->fr_flx & FI_SHORT))
248 				printf("not ");
249 			printf("short");
250 			comma = ",";
251 		}
252 		if (fp->fr_mflx & FI_FRAG) {
253 			fputs(comma, stdout);
254 			if (!(fp->fr_flx & FI_FRAG))
255 				printf("not ");
256 			printf("frag");
257 			comma = ",";
258 		}
259 		if (fp->fr_mflx & FI_FRAGBODY) {
260 			fputs(comma, stdout);
261 			if (!(fp->fr_flx & FI_FRAGBODY))
262 				printf("not ");
263 			printf("frag-body");
264 			comma = ",";
265 		}
266 		if (fp->fr_mflx & FI_NATED) {
267 			fputs(comma, stdout);
268 			if (!(fp->fr_flx & FI_NATED))
269 				printf("not ");
270 			printf("nat");
271 			comma = ",";
272 		}
273 		if (fp->fr_mflx & FI_LOWTTL) {
274 			fputs(comma, stdout);
275 			if (!(fp->fr_flx & FI_LOWTTL))
276 				printf("not ");
277 			printf("lowttl");
278 			comma = ",";
279 		}
280 		if (fp->fr_mflx & FI_BAD) {
281 			fputs(comma, stdout);
282 			if (!(fp->fr_flx & FI_BAD))
283 				printf("not ");
284 			printf("bad");
285 			comma = ",";
286 		}
287 		if (fp->fr_mflx & FI_BADSRC) {
288 			fputs(comma, stdout);
289 			if (!(fp->fr_flx & FI_BADSRC))
290 				printf("not ");
291 			printf("bad-src");
292 			comma = ",";
293 		}
294 		if (fp->fr_mflx & FI_BADNAT) {
295 			fputs(comma, stdout);
296 			if (!(fp->fr_flx & FI_BADNAT))
297 				printf("not ");
298 			printf("bad-nat");
299 			comma = ",";
300 		}
301 		if (fp->fr_mflx & FI_OOW) {
302 			fputs(comma, stdout);
303 			if (!(fp->fr_flx & FI_OOW))
304 				printf("not ");
305 			printf("oow");
306 		}
307 		if (fp->fr_mflx & FI_MULTICAST) {
308 			fputs(comma, stdout);
309 			if (!(fp->fr_flx & FI_MULTICAST))
310 				printf("not ");
311 			printf("mcast");
312 			comma = ",";
313 		}
314 		if (fp->fr_mflx & FI_BROADCAST) {
315 			fputs(comma, stdout);
316 			if (!(fp->fr_flx & FI_BROADCAST))
317 				printf("not ");
318 			printf("bcast");
319 			comma = ",";
320 		}
321 		if (fp->fr_mflx & FI_MBCAST) {
322 			fputs(comma, stdout);
323 			if (!(fp->fr_flx & FI_MBCAST))
324 				printf("not ");
325 			printf("mbcast");
326 			comma = ",";
327 		}
328 		if (fp->fr_mflx & FI_STATE) {
329 			fputs(comma, stdout);
330 			if (!(fp->fr_flx & FI_STATE))
331 				printf("not ");
332 			printf("state");
333 			comma = ",";
334 		}
335 	}
336 
337 	if (fp->fr_flags & FR_KEEPSTATE) {
338 		printf(" keep state");
339 		if ((fp->fr_flags & (FR_STSTRICT|FR_NEWISN|FR_NOICMPERR|FR_STATESYNC)) ||
340 		    (fp->fr_statemax != 0) || (fp->fr_age[0] != 0)) {
341 			char *comma = "";
342 			printf(" (");
343 			if (fp->fr_statemax != 0) {
344 				printf("limit %u", fp->fr_statemax);
345 				comma = ",";
346 			}
347 			if (fp->fr_flags & FR_STSTRICT) {
348 				printf("%sstrict", comma);
349 				comma = ",";
350 			}
351 			if (fp->fr_flags & FR_NEWISN) {
352 				printf("%snewisn", comma);
353 				comma = ",";
354 			}
355 			if (fp->fr_flags & FR_NOICMPERR) {
356 				printf("%sno-icmp-err", comma);
357 				comma = ",";
358 			}
359 			if (fp->fr_flags & FR_STATESYNC) {
360 				printf("%ssync", comma);
361 				comma = ",";
362 			}
363 			if (fp->fr_age[0] || fp->fr_age[1])
364 				printf("%sage %d/%d", comma, fp->fr_age[0],
365 				       fp->fr_age[1]);
366 			printf(")");
367 		}
368 	}
369 	if (fp->fr_flags & FR_KEEPFRAG) {
370 		printf(" keep frags");
371 		if (fp->fr_flags & (FR_FRSTRICT)) {
372 			printf(" (");
373 			if (fp->fr_flags & FR_FRSTRICT)
374 				printf(" strict");
375 			printf(" )");
376 
377 		}
378 	}
379 	if (fp->fr_isc != (struct ipscan *)-1) {
380 		if (fp->fr_isctag[0])
381 			printf(" scan %s", fp->fr_isctag);
382 		else
383 			printf(" scan *");
384 	}
385 	if (*fp->fr_grhead != '\0')
386 		printf(" head %s", fp->fr_grhead);
387 	if (*fp->fr_group != '\0')
388 		printf(" group %s", fp->fr_group);
389 	if (fp->fr_logtag != FR_NOLOGTAG || *fp->fr_nattag.ipt_tag) {
390 		char *s = "";
391 
392 		printf(" set-tag(");
393 		if (fp->fr_logtag != FR_NOLOGTAG) {
394 			printf("log=%u", fp->fr_logtag);
395 			s = ", ";
396 		}
397 		if (*fp->fr_nattag.ipt_tag) {
398 			printf("%snat=%-.*s", s, IPFTAG_LEN,
399 				fp->fr_nattag.ipt_tag);
400 		}
401 		printf(")");
402 	}
403 	if (fp->fr_pps)
404 		printf(" pps %d", fp->fr_pps);
405 	(void)putchar('\n');
406 }
407