|
root / base / usr / src / cmd / ipf / lib / extras.c
extras.c C 113 lines 2.3 KB
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
/*
 * Copyright (C) 1993-2001 by Darren Reed.
 *
 * See the IPFILTER.LICENCE file for details on licencing.
 *
 * $Id: extras.c,v 1.12 2002/07/13 12:06:49 darrenr Exp $
 */

#include "ipf.h"


/*
 * deal with extra bits on end of the line
 */
int	extras(cp, fr, linenum)
char	***cp;
struct	frentry	*fr;
int     linenum;
{
	u_short	secmsk;
	u_long	opts;
	int	notopt;

	opts = 0;
	secmsk = 0;
	notopt = 0;
	(*cp)++;
	if (!**cp)
		return -1;

	while (**cp) {
		if (!strcasecmp(**cp, "not") || !strcasecmp(**cp, "no")) {
			notopt = 1;
			(*cp)++;
			continue;
		} else if (!strncasecmp(**cp, "ipopt", 5)) {
			if (!notopt)
				fr->fr_flx |= FI_OPTIONS;
			fr->fr_mflx |= FI_OPTIONS;
			goto nextopt;
		} else if (!strcasecmp(**cp, "lowttl")) {
			if (!notopt)
				fr->fr_flx |= FI_LOWTTL;
			fr->fr_mflx |= FI_LOWTTL;
			goto nextopt;
		} else if (!strcasecmp(**cp, "bad-src")) {
			if (!notopt)
				fr->fr_flx |= FI_BADSRC;
			fr->fr_mflx |= FI_BADSRC;
			goto nextopt;
		} else if (!strncasecmp(**cp, "mbcast", 6)) {
			if (!notopt)
				fr->fr_flx |= FI_MBCAST;
			fr->fr_mflx |= FI_MBCAST;
			goto nextopt;
		} else if (!strncasecmp(**cp, "nat", 3)) {
			if (!notopt)
				fr->fr_flx |= FI_NATED;
			fr->fr_mflx |= FI_NATED;
			goto nextopt;
		} else if (!strncasecmp(**cp, "frag", 4)) {
			if (!notopt)
				fr->fr_flx |= FI_FRAG;
			fr->fr_mflx |= FI_FRAG;
			goto nextopt;
		} else if (!strncasecmp(**cp, "opt", 3)) {
			if (!*(*cp + 1)) {
				fprintf(stderr, "%d: opt missing arguements\n",
					linenum);
				return -1;
			}
			(*cp)++;
			if (!(opts = optname(cp, &secmsk, linenum)))
				return -1;

			if (notopt) {
				if (!secmsk) {
					fr->fr_optmask |= opts;
				} else {
					fr->fr_optmask |= (opts & ~0x0100);
					fr->fr_secmask |= secmsk;
				}
				fr->fr_secbits &= ~secmsk;
				fr->fr_optbits &= ~opts;
			} else {
				fr->fr_optmask |= opts;
				fr->fr_secmask |= secmsk;
				fr->fr_optbits |= opts;
				fr->fr_secbits |= secmsk;
			}
		} else if (!strncasecmp(**cp, "short", 5)) {
			if (fr->fr_tcpf) {
				fprintf(stderr,
				"%d: short cannot be used with TCP flags\n",
					linenum);
				return -1;
			}

			if (!notopt)
				fr->fr_flx |= FI_SHORT;
			fr->fr_mflx |= FI_SHORT;
			goto nextopt;
		} else
			return -1;
nextopt:
		notopt = 0;
		opts = 0;
		secmsk = 0;
		(*cp)++;
	}
	return 0;
}