diff options
author | guido <guido@FreeBSD.org> | 2000-01-13 19:01:33 +0000 |
---|---|---|
committer | guido <guido@FreeBSD.org> | 2000-01-13 19:01:33 +0000 |
commit | de7edf803aae7f62d86e24ecb9ea3b9413c978a5 (patch) | |
tree | 3275d83a0aa61e098816f380e7e9ec00773ecef0 /sys/contrib/ipfilter | |
parent | f45fdd3f47eb65e321536ed0dfb9e029ca80a9b8 (diff) | |
download | FreeBSD-src-de7edf803aae7f62d86e24ecb9ea3b9413c978a5.zip FreeBSD-src-de7edf803aae7f62d86e24ecb9ea3b9413c978a5.tar.gz |
Bring over ipfilter kernel sources, including merging the local modifications.
Diffstat (limited to 'sys/contrib/ipfilter')
-rw-r--r-- | sys/contrib/ipfilter/netinet/fil.c | 78 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_auth.c | 13 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_auth.h | 2 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_compat.h | 18 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_fil.c | 101 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_fil.h | 13 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_frag.c | 23 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_ftp_pxy.c | 8 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_log.c | 7 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_nat.c | 111 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_nat.h | 11 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_raudio_pxy.c | 137 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_rcmd_pxy.c | 5 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ip_state.c | 123 | ||||
-rw-r--r-- | sys/contrib/ipfilter/netinet/ipl.h | 3 |
15 files changed, 429 insertions, 224 deletions
diff --git a/sys/contrib/ipfilter/netinet/fil.c b/sys/contrib/ipfilter/netinet/fil.c index cc6d327..cb069f8 100644 --- a/sys/contrib/ipfilter/netinet/fil.c +++ b/sys/contrib/ipfilter/netinet/fil.c @@ -7,7 +7,7 @@ */ #if !defined(lint) static const char sccsid[] = "@(#)fil.c 1.36 6/5/96 (C) 1993-1996 Darren Reed"; -/*static const char rcsid[] = "@(#)$Id: fil.c,v 2.3.2.7 1999/10/21 14:21:40 darrenr Exp $";*/ +/*static const char rcsid[] = "@(#)$Id: fil.c,v 2.3.2.14 1999/12/07 12:53:40 darrenr Exp $";*/ static const char rcsid[] = "@(#)$FreeBSD$"; #endif @@ -20,8 +20,10 @@ static const char rcsid[] = "@(#)$FreeBSD$"; defined(_KERNEL) # include "opt_ipfilter_log.h" #endif -#if defined(_KERNEL) && defined(__FreeBSD_version) && \ - (__FreeBSD_version >= 220000) +#if ((defined(KERNEL) && defined(__FreeBSD_version) && \ + (__FreeBSD_version >= 220000)) || \ + (defined(_KERNEL) && defined(__FreeBSD_version) && \ + (__FreeBSD_version >= 40013))) # include <sys/filio.h> # include <sys/fcntl.h> #else @@ -147,6 +149,9 @@ fr_info_t frcache[2]; static int fr_tcpudpchk __P((frentry_t *, fr_info_t *)); static int frflushlist __P((int, minor_t, int *, frentry_t **)); +#ifdef _KERNEL +static void frsynclist __P((frentry_t *)); +#endif /* @@ -671,6 +676,13 @@ int out; fin->fin_qif = qif; # endif #endif /* _KERNEL */ + + /* + * Be careful here: ip_id is in network byte order when called + * from ip_output() + */ + if (out) + ip->ip_id = ntohs(ip->ip_id); fr_makefrip(hlen, ip, fin); fin->fin_ifp = ifp; fin->fin_out = out; @@ -824,6 +836,10 @@ logit: } } #endif /* IPFILTER_LOG */ + + if (out) + ip->ip_id = htons(ip->ip_id); + #ifdef _KERNEL /* * Only allow FR_DUP to work if a rule matched - it makes no sense to @@ -1165,7 +1181,7 @@ nodata: * SUCH DAMAGE. * * @(#)uipc_mbuf.c 8.2 (Berkeley) 1/4/94 - * $Id: fil.c,v 2.3.2.7 1999/10/21 14:21:40 darrenr Exp $ + * $Id: fil.c,v 2.3.2.14 1999/12/07 12:53:40 darrenr Exp $ */ /* * Copy data from an mbuf chain starting "off" bytes from the beginning, @@ -1358,14 +1374,16 @@ frentry_t **listp; } ATOMIC_DEC(fp->fr_ref); + if (fp->fr_grhead) { + fr_delgroup((u_int)fp->fr_grhead, fp->fr_flags, + unit, set); + fp->fr_grhead = NULL; + } if (fp->fr_ref == 0) { - if (fp->fr_grhead) - fr_delgroup((u_int)fp->fr_grhead, fp->fr_flags, - unit, set); KFREE(fp); + freed++; } else fp->fr_next = NULL; - freed++; } *nfreedp += freed; return freed; @@ -1529,10 +1547,52 @@ struct in_addr *inp; in = sin->sin_addr; # endif /* linux */ # endif /* SOLARIS */ - in.s_addr = ntohl(in.s_addr); *inp = in; return 0; } + + +static void frsynclist(fr) +register frentry_t *fr; +{ + for (; fr; fr = fr->fr_next) { + if (fr->fr_ifa != NULL) { + fr->fr_ifa = GETUNIT(fr->fr_ifname); + if (fr->fr_ifa == NULL) + fr->fr_ifa = (void *)-1; + } + if (fr->fr_grp) + frsynclist(fr->fr_grp); + } +} + + +void frsync() +{ + register struct ifnet *ifp; + +# if !SOLARIS +# if defined(__OpenBSD__) || ((NetBSD >= 199511) && (NetBSD < 1991011)) || \ + (defined(__FreeBSD_version) && (__FreeBSD_version >= 300000)) +# if (NetBSD >= 199905) || defined(__OpenBSD__) + for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_list.tqe_next) +# else + for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_link.tqe_next) +# endif +# else + for (ifp = ifnet; ifp; ifp = ifp->if_next) +# endif + ip_natsync(ifp); +# endif + + WRITE_ENTER(&ipf_mutex); + frsynclist(ipacct[0][fr_active]); + frsynclist(ipacct[1][fr_active]); + frsynclist(ipfilter[0][fr_active]); + frsynclist(ipfilter[1][fr_active]); + RWLOCK_EXIT(&ipf_mutex); +} + #else diff --git a/sys/contrib/ipfilter/netinet/ip_auth.c b/sys/contrib/ipfilter/netinet/ip_auth.c index 2b29cae..0490510 100644 --- a/sys/contrib/ipfilter/netinet/ip_auth.c +++ b/sys/contrib/ipfilter/netinet/ip_auth.c @@ -20,7 +20,8 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <stdlib.h> # include <string.h> #endif -#if defined(_KERNEL) && (__FreeBSD_version >= 220000) +#if ((defined(KERNEL) && (__FreeBSD_version >= 220000)) || \ + (defined(_KERNEL) && (__FreeBSD_version >= 40013))) # include <sys/filio.h> # include <sys/fcntl.h> #else @@ -31,7 +32,7 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <sys/protosw.h> #endif #include <sys/socket.h> -#if (defined(_KERNEL) || defined(KERNEL)) && !defined(linux) +#if defined(_KERNEL) && !defined(linux) # include <sys/systm.h> #endif #if !defined(__SVR4) && !defined(__svr4__) @@ -125,10 +126,10 @@ int fr_authsize = FR_NUMAUTH; int fr_authused = 0; int fr_defaultauthage = 600; fr_authstat_t fr_authstats; -static frauth_t fr_auth[FR_NUMAUTH]; +frauth_t fr_auth[FR_NUMAUTH]; mb_t *fr_authpkts[FR_NUMAUTH]; -static int fr_authstart = 0, fr_authend = 0, fr_authnext = 0; -static frauthent_t *fae_list = NULL; +int fr_authstart = 0, fr_authend = 0, fr_authnext = 0; +frauthent_t *fae_list = NULL; frentry_t *ipauth = NULL; @@ -273,7 +274,7 @@ ip_t *ip; int fr_auth_ioctl(data, cmd, fr, frptr) caddr_t data; -#if defined(__NetBSD__) || defined(__OpenBSD__) || (FreeBSD_version >= 300003) +#if defined(__NetBSD__) || defined(__OpenBSD__) u_long cmd; #else int cmd; diff --git a/sys/contrib/ipfilter/netinet/ip_auth.h b/sys/contrib/ipfilter/netinet/ip_auth.h index a7c640b..e6b5a59 100644 --- a/sys/contrib/ipfilter/netinet/ip_auth.h +++ b/sys/contrib/ipfilter/netinet/ip_auth.h @@ -6,8 +6,8 @@ * to the original author and the contributors. * * $Id: ip_auth.h,v 2.1 1999/08/04 17:29:54 darrenr Exp $ - * * $FreeBSD$ + * */ #ifndef __IP_AUTH_H__ #define __IP_AUTH_H__ diff --git a/sys/contrib/ipfilter/netinet/ip_compat.h b/sys/contrib/ipfilter/netinet/ip_compat.h index 7982a5d..0c8242d 100644 --- a/sys/contrib/ipfilter/netinet/ip_compat.h +++ b/sys/contrib/ipfilter/netinet/ip_compat.h @@ -6,7 +6,7 @@ * to the original author and the contributors. * * @(#)ip_compat.h 1.8 1/14/96 - * $Id: ip_compat.h,v 2.1.2.1 1999/09/18 15:03:51 darrenr Exp $ + * $Id: ip_compat.h,v 2.1.2.3 1999/11/18 13:55:26 darrenr Exp $ * $FreeBSD$ */ @@ -100,6 +100,11 @@ struct ether_addr { # include <inet/ip.h> # include <inet/ip_ire.h> # endif /* _KERNEL */ +# if SOLARIS2 >= 8 +# include <netinet/ip6.h> +# include <inet/ip6.h> +# define ipif_local_addr ipif_lcl_addr +# endif #else # if !defined(__sgi) typedef int minor_t; @@ -201,12 +206,9 @@ typedef unsigned long u_32_t; #if defined(__FreeBSD__) && defined(KERNEL) # if __FreeBSD__ < 3 # include <machine/spl.h> -# else -# if __FreeBSD__ == 3 -# if defined(IPFILTER_LKM) && !defined(ACTUALLY_LKM_NOT_KERNEL) -# define ACTUALLY_LKM_NOT_KERNEL -# endif -# endif +# endif +# if defined(IPFILTER_LKM) && !defined(ACTUALLY_LKM_NOT_KERNEL) +# define ACTUALLY_LKM_NOT_KERNEL # endif #endif /* __FreeBSD__ && KERNEL */ @@ -654,8 +656,8 @@ typedef struct { __u8 ip_hl:4; __u8 ip_v:4; # else - __u8 ip_hl:4; __u8 ip_v:4; + __u8 ip_hl:4; # endif __u8 ip_tos; __u16 ip_len; diff --git a/sys/contrib/ipfilter/netinet/ip_fil.c b/sys/contrib/ipfilter/netinet/ip_fil.c index 9d95eb3..902e3f7 100644 --- a/sys/contrib/ipfilter/netinet/ip_fil.c +++ b/sys/contrib/ipfilter/netinet/ip_fil.c @@ -7,7 +7,7 @@ */ #if !defined(lint) static const char sccsid[] = "@(#)ip_fil.c 2.41 6/5/96 (C) 1993-1995 Darren Reed"; -/*static const char rcsid[] = "@(#)$Id: ip_fil.c,v 2.4.2.7 1999/10/15 13:49:43 darrenr Exp $";*/ +/*static const char rcsid[] = "@(#)$Id: ip_fil.c,v 2.4.2.14 1999/12/11 05:31:08 darrenr Exp $";*/ static const char rcsid[] = "@(#)$FreeBSD$"; #endif @@ -24,7 +24,9 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include "opt_ipfilter_log.h" #endif #if defined(__FreeBSD__) && !defined(__FreeBSD_version) -# if !defined(_KERNEL) || defined(IPFILTER_LKM) +# if defined(_KERNEL) && !defined(IPFILTER_LKM) +# include <sys/osreldate.h> +# else # include <osreldate.h> # endif #endif @@ -130,7 +132,7 @@ int ipl_unreach = ICMP_UNREACH_FILTER; u_long ipl_frouteok[2] = {0, 0}; static void frzerostats __P((caddr_t)); -#if defined(__NetBSD__) || defined(__OpenBSD__) || (__FreeBSD_version >= 300003) +#if defined(__NetBSD__) || defined(__OpenBSD__) static int frrequest __P((int, u_long, caddr_t, int)); #else static int frrequest __P((int, int, caddr_t, int)); @@ -140,6 +142,7 @@ static int (*fr_savep) __P((ip_t *, int, void *, int, struct mbuf **)); static int send_ip __P((struct mbuf *, ip_t *)); # ifdef __sgi extern kmutex_t ipf_rw; +extern KRWLOCK_T ipf_mutex; # endif #else int ipllog __P((void)); @@ -575,42 +578,6 @@ int mode; } -void frsync() -{ -#ifdef _KERNEL - register frentry_t *f; - register struct ifnet *ifp; - -# if defined(__OpenBSD__) || ((NetBSD >= 199511) && (NetBSD < 1991011)) || \ - (defined(__FreeBSD_version) && (__FreeBSD_version >= 300000)) -# if (NetBSD >= 199905) || defined(__OpenBSD__) - for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_list.tqe_next) -# else - for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_link.tqe_next) -# endif -# else - for (ifp = ifnet; ifp; ifp = ifp->if_next) -# endif - ip_natsync(ifp); - - WRITE_ENTER(&ipf_mutex); - for (f = ipacct[0][fr_active]; (f != NULL); f = f->fr_next) - if (f->fr_ifa == (void *)-1) - f->fr_ifa = GETUNIT(f->fr_ifname); - for (f = ipacct[1][fr_active]; (f != NULL); f = f->fr_next) - if (f->fr_ifa == (void *)-1) - f->fr_ifa = GETUNIT(f->fr_ifname); - for (f = ipfilter[0][fr_active]; (f != NULL); f = f->fr_next) - if (f->fr_ifa == (void *)-1) - f->fr_ifa = GETUNIT(f->fr_ifname); - for (f = ipfilter[1][fr_active]; (f != NULL); f = f->fr_next) - if (f->fr_ifa == (void *)-1) - f->fr_ifa = GETUNIT(f->fr_ifname); - RWLOCK_EXIT(&ipf_mutex); -#endif -} - - void fr_forgetifp(ifp) void *ifp; { @@ -636,7 +603,7 @@ void *ifp; static int frrequest(unit, req, data, set) int unit; -#if defined(__NetBSD__) || defined(__OpenBSD__) || (__FreeBSD_version >= 300003) +#if defined(__NetBSD__) || defined(__OpenBSD__) u_long req; #else int req; @@ -738,14 +705,15 @@ caddr_t data; } if (!f) { - ftail = fprev; - if (req != SIOCINAFR && req != SIOCINIFR) + if (req != SIOCINAFR || req != SIOCINIFR) while ((f = *ftail)) ftail = &f->fr_next; - else if (fp->fr_hits) - while (--fp->fr_hits && (f = *ftail)) - ftail = &f->fr_next; - f = NULL; + else { + if (fp->fr_hits) + while (--fp->fr_hits && (f = *ftail)) + ftail = &f->fr_next; + f = NULL; + } } if (req == SIOCDELFR || req == SIOCRMIFR) { @@ -770,7 +738,7 @@ caddr_t data; error = EEXIST; else { if (unit == IPL_LOGAUTH) - return fr_auth_ioctl(data, req, f, ftail); + return fr_auth_ioctl(data, req, fp, ftail); KMALLOC(f, frentry_t *); if (f != NULL) { if (fg && fg->fg_head) @@ -959,6 +927,9 @@ ip_t *ip; ip->ip_ttl = ip_defttl; # endif +# ifdef IPSEC + m->m_pkthdr.rcvif = NULL; +# endif # if defined(__FreeBSD_version) && (__FreeBSD_version >= 220000) { int err; @@ -986,7 +957,7 @@ int send_icmp_err(oip, type, code, ifp, dst) ip_t *oip; int type, code; void *ifp; -struct in_addr dst; +struct in_addr dst; { struct icmp *icmp; struct mbuf *m; @@ -1021,7 +992,6 @@ struct in_addr dst; if (dst.s_addr == 0) { if (fr_ifpaddr(ifp, &dst) == -1) return -1; - dst.s_addr = htonl(dst.s_addr); } nip->ip_src = dst; nip->ip_dst = oip->ip_src; @@ -1108,9 +1078,12 @@ frdest_t *fdp; * In case we're here due to "to <if>" being used with "keep state", * check that we're going in the correct direction. */ - if ((fr != NULL) && (ifp != NULL) && (fin->fin_rev != 0) && - (fdp == &fr->fr_tif)) - return -1; + if ((fr != NULL) && (fin->fin_rev != 0)) { + if ((ifp != NULL) && (fdp == &fr->fr_tif)) + return -1; + dst->sin_addr = ip->ip_dst; + } else + dst->sin_addr = fdp->fd_ip.s_addr ? fdp->fd_ip : ip->ip_dst; # ifdef __bsdi__ dst->sin_len = sizeof(*dst); # endif @@ -1237,6 +1210,10 @@ frdest_t *fdp; error = ENOBUFS; /* ??? */ goto sendorfree; } +# if BSD >= 199306 + m->m_pkthdr.len = mhlen + len; + m->m_pkthdr.rcvif = NULL; +# endif # ifndef sparc mhip->ip_off = htons((u_short)mhip->ip_off); # endif @@ -1280,6 +1257,9 @@ done: RTFREE(ro->ro_rt); return 0; bad: + if (error == EMSGSIZE) + (void) send_icmp_err(ip, ICMP_UNREACH, ICMP_UNREACH_NEEDFRAG, + ifp, ip->ip_dst); m_freem(m); goto done; } @@ -1319,9 +1299,9 @@ ip_t *ip; # if (defined(NetBSD) && (NetBSD <= 1991011) && (NetBSD >= 199606)) || \ (defined(OpenBSD) && (OpenBSD >= 199603)) - snprintf(fname, sizeof(fname), "/tmp/%s", ifp->if_xname); + sprintf(fname, "/tmp/%s", ifp->if_xname); # else - snprintf(fname, sizeof(fname), "/tmp/%s%d", ifp->if_name, ifp->if_unit); + sprintf(fname, "/tmp/%s%d", ifp->if_name, ifp->if_unit); # endif fd = open(fname, O_WRONLY|O_APPEND); if (fd == -1) { @@ -1348,8 +1328,7 @@ char *name; char ifname[32], *s; for (ifa = ifneta; ifa && (ifp = *ifa); ifa++) { - (void) snprintf(ifname, sizeof(ifname), "%s%d", - ifp->if_name, ifp->if_unit); + (void) sprintf(ifname, "%s%d", ifp->if_name, ifp->if_unit); if (!strcmp(name, ifname)) return ifp; } @@ -1401,7 +1380,7 @@ void init_ifp() (defined(OpenBSD) && (OpenBSD >= 199603)) for (ifa = ifneta; ifa && (ifp = *ifa); ifa++) { ifp->if_output = write_output; - snprintf(fname, sizeof(fname), "/tmp/%s", ifp->if_xname); + sprintf(fname, "/tmp/%s", ifp->if_xname); fd = open(fname, O_WRONLY|O_CREAT|O_EXCL|O_TRUNC, 0600); if (fd == -1) perror("open"); @@ -1412,7 +1391,7 @@ void init_ifp() for (ifa = ifneta; ifa && (ifp = *ifa); ifa++) { ifp->if_output = write_output; - snprintf(fname, sizeof(fname), "/tmp/%s%d", ifp->if_name, ifp->if_unit); + sprintf(fname, "/tmp/%s%d", ifp->if_name, ifp->if_unit); fd = open(fname, O_WRONLY|O_CREAT|O_EXCL|O_TRUNC, 0600); if (fd == -1) perror("open"); @@ -1468,4 +1447,10 @@ struct ifnet *ifp; verbose("- TCP RST sent\n"); return 0; } + + +void frsync() +{ + return; +} #endif /* _KERNEL */ diff --git a/sys/contrib/ipfilter/netinet/ip_fil.h b/sys/contrib/ipfilter/netinet/ip_fil.h index aef96ca..789dd3d 100644 --- a/sys/contrib/ipfilter/netinet/ip_fil.h +++ b/sys/contrib/ipfilter/netinet/ip_fil.h @@ -6,7 +6,7 @@ * to the original author and the contributors. * * @(#)ip_fil.h 1.35 6/5/96 - * $Id: ip_fil.h,v 2.3.2.4 1999/10/15 13:42:37 darrenr Exp $ + * $Id: ip_fil.h,v 2.3.2.6 1999/12/17 12:58:16 darrenr Exp $ * $FreeBSD$ */ @@ -107,6 +107,7 @@ typedef struct fr_ip { */ #define FI_W_SPORT 0x00000100 #define FI_W_DPORT 0x00000200 +#define FI_WILD (FI_W_SPORT|FI_W_DPORT) typedef struct fr_info { void *fin_ifp; /* interface packet is `on' */ @@ -307,11 +308,15 @@ typedef struct friostat { struct frentry *f_auth; struct frgroup *f_groups[3][2]; u_long f_froute[2]; - int f_active; /* 1 or 0 - active rule set */ int f_defpass; /* default pass - from fr_pass */ - int f_running; /* 1 if running, else 0 */ - int f_logging; /* 1 if enabled, else 0 */ + char f_active; /* 1 or 0 - active rule set */ + char f_running; /* 1 if running, else 0 */ + char f_logging; /* 1 if enabled, else 0 */ +#if !SOLARIS && defined(sun) + char f_version[25]; /* version string */ +#else char f_version[32]; /* version string */ +#endif } friostat_t; typedef struct optlist { diff --git a/sys/contrib/ipfilter/netinet/ip_frag.c b/sys/contrib/ipfilter/netinet/ip_frag.c index 156a985..54f5a84 100644 --- a/sys/contrib/ipfilter/netinet/ip_frag.c +++ b/sys/contrib/ipfilter/netinet/ip_frag.c @@ -7,7 +7,7 @@ */ #if !defined(lint) static const char sccsid[] = "@(#)ip_frag.c 1.11 3/24/96 (C) 1993-1995 Darren Reed"; -/*static const char rcsid[] = "@(#)$Id: ip_frag.c,v 2.4.2.3 1999/09/18 15:03:54 darrenr Exp $";*/ +/*static const char rcsid[] = "@(#)$Id: ip_frag.c,v 2.4.2.4 1999/11/28 04:52:10 darrenr Exp $";*/ static const char rcsid[] = "@(#)$FreeBSD$"; #endif @@ -25,7 +25,8 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <string.h> # include <stdlib.h> #endif -#if defined(_KERNEL) && (__FreeBSD_version >= 220000) +#if ((defined(KERNEL) && (__FreeBSD_version >= 220000)) || \ + (defined(_KERNEL) && (__FreeBSD_version >= 40013))) # include <sys/filio.h> # include <sys/fcntl.h> #else @@ -88,13 +89,11 @@ extern struct callout_handle ipfr_slowtimer_ch; #endif -static ipfr_t *ipfr_heads[IPFT_SIZE]; -static ipfr_t *ipfr_nattab[IPFT_SIZE]; -static ipfrstat_t ipfr_stats; -static int ipfr_inuse = 0; - -int fr_ipfrttl = 120; /* 60 seconds */ - +ipfr_t *ipfr_heads[IPFT_SIZE]; +ipfr_t *ipfr_nattab[IPFT_SIZE]; +ipfrstat_t ipfr_stats; +int ipfr_inuse = 0, + fr_ipfrttl = 120; /* 60 seconds */ #ifdef _KERNEL # if SOLARIS2 >= 7 extern timeout_id_t ipfr_timer_id; @@ -282,14 +281,14 @@ ipfr_t *table[]; f->ipfr_prev = NULL; table[idx] = f; } - off = ip->ip_off; + off = ip->ip_off & IP_OFFMASK; atoff = off + (fin->fin_dlen >> 3); /* * If we've follwed the fragments, and this is the * last (in order), shrink expiration time. */ - if ((off & IP_OFFMASK) == f->ipfr_off) { - if (!(off & IP_MF)) + if (off == f->ipfr_off) { + if (!(ip->ip_off & IP_MF)) f->ipfr_ttl = 1; else f->ipfr_off = atoff; diff --git a/sys/contrib/ipfilter/netinet/ip_ftp_pxy.c b/sys/contrib/ipfilter/netinet/ip_ftp_pxy.c index 0600617..3ed1853 100644 --- a/sys/contrib/ipfilter/netinet/ip_ftp_pxy.c +++ b/sys/contrib/ipfilter/netinet/ip_ftp_pxy.c @@ -1,8 +1,6 @@ /* * Simple FTP transparent proxy for in-kernel use. For use with the NAT * code. - * - * $Id$ * $FreeBSD$ */ #if SOLARIS && defined(_KERNEL) @@ -166,7 +164,7 @@ nat_t *nat; a4 = a1 & 0xff; a1 >>= 24; olen = s - portbuf; - (void) snprintf(newbuf, sizeof(newbuf), "%s %u,%u,%u,%u,%u,%u\r\n", + (void) sprintf(newbuf, "%s %u,%u,%u,%u,%u,%u\r\n", "PORT", a1, a2, a3, a4, a5, a6); nlen = strlen(newbuf); @@ -215,7 +213,7 @@ nat_t *nat; sum2 -= sum1; sum2 = (sum2 & 0xffff) + (sum2 >> 16); - fix_outcksum(&ip->ip_sum, sum2); + fix_outcksum(&ip->ip_sum, sum2, 0); #endif ip->ip_len += inc; } @@ -410,7 +408,7 @@ nat_t *nat; sum2 -= sum1; sum2 = (sum2 & 0xffff) + (sum2 >> 16); - fix_outcksum(&ip->ip_sum, sum2); + fix_outcksum(&ip->ip_sum, sum2, 0); #endif ip->ip_len += inc; } diff --git a/sys/contrib/ipfilter/netinet/ip_log.c b/sys/contrib/ipfilter/netinet/ip_log.c index 73a411a..57a5bff 100644 --- a/sys/contrib/ipfilter/netinet/ip_log.c +++ b/sys/contrib/ipfilter/netinet/ip_log.c @@ -16,7 +16,10 @@ # include "opt_ipfilter_log.h" #endif #ifdef __FreeBSD__ -# if defined(_KERNEL) && !defined(IPFILTER_LKM) +# if defined(_KERNEL) && !defined(IPFILTER_LKM) +# if !defined(__FreeBSD_version) +# include <sys/osreldate.h> +# endif # if defined(__FreeBSD_version) && (__FreeBSD_version >= 300000) # include "opt_ipfilter.h" # endif @@ -126,7 +129,7 @@ extern kcondvar_t iplwait; iplog_t **iplh[IPL_LOGMAX+1], *iplt[IPL_LOGMAX+1], *ipll[IPL_LOGMAX+1]; size_t iplused[IPL_LOGMAX+1]; -static fr_info_t iplcrc[IPL_LOGMAX+1]; +fr_info_t iplcrc[IPL_LOGMAX+1]; # ifdef linux static struct wait_queue *iplwait[IPL_LOGMAX+1]; # endif diff --git a/sys/contrib/ipfilter/netinet/ip_nat.c b/sys/contrib/ipfilter/netinet/ip_nat.c index be45116..d24849a 100644 --- a/sys/contrib/ipfilter/netinet/ip_nat.c +++ b/sys/contrib/ipfilter/netinet/ip_nat.c @@ -9,7 +9,7 @@ */ #if !defined(lint) static const char sccsid[] = "@(#)ip_nat.c 1.11 6/5/96 (C) 1995 Darren Reed"; -/*static const char rcsid[] = "@(#)$Id: ip_nat.c,v 2.2.2.5 1999/10/05 12:58:33 darrenr Exp $";*/ +/*static const char rcsid[] = "@(#)$Id: ip_nat.c,v 2.2.2.11 1999/12/17 13:05:40 darrenr Exp $";*/ static const char rcsid[] = "@(#)$FreeBSD$"; #endif @@ -31,7 +31,8 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <string.h> # include <stdlib.h> #endif -#if defined(_KERNEL) && (__FreeBSD_version >= 220000) +#if ((defined(KERNEL) && (__FreeBSD_version >= 220000)) || \ + (defined(_KERNEL) && (__FreeBSD_version >= 40013))) # include <sys/filio.h> # include <sys/fcntl.h> #else @@ -114,11 +115,7 @@ extern struct ifnet vpnif; nat_t **nat_table[2] = { NULL, NULL }, *nat_instances = NULL; -#if (SOLARIS || defined(__sgi)) && defined(_KERNEL) ipnat_t *nat_list = NULL; -#else -static ipnat_t *nat_list = NULL; -#endif u_int ipf_nattable_sz = NAT_TABLE_SZ; u_int ipf_natrules_sz = NAT_SIZE; u_int ipf_rdrrules_sz = RDR_SIZE; @@ -129,7 +126,7 @@ ipnat_t **rdr_rules = NULL; u_long fr_defnatage = DEF_NAT_AGE, fr_defnaticmpage = 6; /* 3 seconds */ -static natstat_t nat_stats; +natstat_t nat_stats; #if (SOLARIS || defined(__sgi)) && defined(_KERNEL) extern kmutex_t ipf_rw; extern KRWLOCK_T ipf_nat; @@ -203,15 +200,22 @@ ipnat_t *n; } -void fix_outcksum(sp, n) +void fix_outcksum(sp, n , len) u_short *sp; u_32_t n; +int len; { register u_short sumshort; register u_32_t sum1; if (!n) return; +#if SOLARIS2 >= 6 + else if (n & NAT_HW_CKSUM) { + *sp = n & 0xffff; + return; + } +#endif sum1 = (~ntohs(*sp)) & 0xffff; sum1 += (n); sum1 = (sum1 >> 16) + (sum1 & 0xffff); @@ -222,15 +226,22 @@ u_32_t n; } -void fix_incksum(sp, n) +void fix_incksum(sp, n , len) u_short *sp; u_32_t n; +int len; { register u_short sumshort; register u_32_t sum1; if (!n) return; +#if SOLARIS2 >= 6 + else if (n & NAT_HW_CKSUM) { + *sp = n & 0xffff; + return; + } +#endif #ifdef sparc sum1 = (~(*sp)) & 0xffff; #else @@ -270,7 +281,7 @@ u_32_t n; * Handle ioctls which manipulate the NAT. */ int nat_ioctl(data, cmd, mode) -#if defined(__NetBSD__) || defined(__OpenBSD__) || (__FreeBSD_version >= 300003) +#if defined(__NetBSD__) || defined(__OpenBSD__) u_long cmd; #else int cmd; @@ -317,6 +328,14 @@ int mode; switch (cmd) { +#ifdef IPFILTER_LOG + case SIOCIPFFB : + if (!(mode & FWRITE)) + error = EPERM; + else + *(int *)data = ipflog_clear(IPL_LOGNAT); + break; +#endif case SIOCADNAT : if (!(mode & FWRITE)) { error = EPERM; @@ -669,6 +688,9 @@ int direction; tcphdr_t *tcp = NULL; u_short nflags; u_int hv; +#if SOLARIS && defined(_KERNEL) && (SOLARIS2 >= 6) + qif_t *qf = fin->fin_qif; +#endif nflags = flags & np->in_flags; if (flags & IPN_TCPUDP) { @@ -761,6 +783,7 @@ int direction; KFREE(nat); return NULL; } + in.s_addr = ntohl(in.s_addr); } else if (!in.s_addr && !np->in_outmsk) { /* * 0/0 - use the original source address/port. @@ -832,7 +855,7 @@ int direction; * this is appropriate. */ inb.s_addr = htonl(in.s_addr); - natl = nat_inlookup(fin->fin_ifp, flags, + natl = nat_inlookup(fin->fin_ifp, flags & ~FI_WILD, (u_int)ip->ip_p, ip->ip_dst, inb, (port << 16) | dport); @@ -901,7 +924,21 @@ int direction; } CALC_SUMD(sum1, sum2, sumd); - nat->nat_sumd = (sumd & 0xffff) + (sumd >> 16); + nat->nat_sumd[0] = (sumd & 0xffff) + (sumd >> 16); +#if SOLARIS && defined(_KERNEL) && (SOLARIS2 >= 6) + if ((flags == IPN_TCP) && dohwcksum && + (qf->qf_ill->ill_ick.ick_magic == ICK_M_CTL_MAGIC)) { + if (direction == NAT_OUTBOUND) + sum1 = LONG_SUM(ntohl(in.s_addr)); + else + sum1 = LONG_SUM(ntohl(ip->ip_src.s_addr)); + sum1 += LONG_SUM(ntohl(ip->ip_dst.s_addr)); + sum1 += 30; + sum1 = (sum1 & 0xffff) + (sum1 >> 16); + nat->nat_sumd[1] = NAT_HW_CKSUM|(sum1 & 0xffff); + } else +#endif + nat->nat_sumd[1] = nat->nat_sumd[0]; if ((flags & IPN_TCPUDP) && ((sport != port) || (dport != nport))) { if (direction == NAT_OUTBOUND) @@ -914,7 +951,7 @@ int direction; CALC_SUMD(sum1, sum2, sumd); nat->nat_ipsumd = (sumd & 0xffff) + (sumd >> 16); } else - nat->nat_ipsumd = nat->nat_sumd; + nat->nat_ipsumd = nat->nat_sumd[0]; in.s_addr = htonl(in.s_addr); nat->nat_next = nat_instances; @@ -1047,19 +1084,19 @@ u_int *nflags; CALC_SUMD(sum1, sum2, sumd); if (nat->nat_dir == NAT_OUTBOUND) { - fix_incksum(&oip->ip_sum, sumd); + fix_incksum(&oip->ip_sum, sumd, 0); sumd += (sumd & 0xffff); while (sumd > 0xffff) sumd = (sumd & 0xffff) + (sumd >> 16); - fix_outcksum(&icmp->icmp_cksum, sumd); + fix_outcksum(&icmp->icmp_cksum, sumd, 0); } else { - fix_outcksum(&oip->ip_sum, sumd); + fix_outcksum(&oip->ip_sum, sumd, 0); sumd += (sumd & 0xffff); while (sumd > 0xffff) sumd = (sumd & 0xffff) + (sumd >> 16); - fix_incksum(&icmp->icmp_cksum, sumd); + fix_incksum(&icmp->icmp_cksum, sumd, 0); } @@ -1075,7 +1112,7 @@ u_int *nflags; sum2 = ntohs(nat->nat_inport); CALC_SUMD(sum1, sum2, sumd); tcp->th_sport = nat->nat_inport; - fix_outcksum(&icmp->icmp_cksum, sumd); + fix_outcksum(&icmp->icmp_cksum, sumd, 0); } } else { if (tcp->th_dport != nat->nat_outport) { @@ -1083,7 +1120,7 @@ u_int *nflags; sum2 = ntohs(nat->nat_outport); CALC_SUMD(sum1, sum2, sumd); tcp->th_dport = nat->nat_outport; - fix_incksum(&icmp->icmp_cksum, sumd); + fix_incksum(&icmp->icmp_cksum, sumd, 0); } } } @@ -1356,9 +1393,9 @@ maskloop: */ #if SOLARIS || defined(__sgi) if (nat->nat_dir == NAT_OUTBOUND) - fix_outcksum(&ip->ip_sum, nat->nat_ipsumd); + fix_outcksum(&ip->ip_sum, nat->nat_ipsumd, 0); else - fix_incksum(&ip->ip_sum, nat->nat_ipsumd); + fix_incksum(&ip->ip_sum, nat->nat_ipsumd, 0); #endif if (!(ip->ip_off & IP_OFFMASK) && @@ -1397,9 +1434,11 @@ maskloop: } if (csump) { if (nat->nat_dir == NAT_OUTBOUND) - fix_outcksum(csump, nat->nat_sumd); + fix_outcksum(csump, nat->nat_sumd[1], + ip->ip_len); else - fix_incksum(csump, nat->nat_sumd); + fix_incksum(csump, nat->nat_sumd[1], + ip->ip_len); } } if ((np->in_apr != NULL) && (np->in_dport == 0 || @@ -1489,7 +1528,8 @@ maskloop: ((in.s_addr & np->in_outmsk) == np->in_outip) && ((src.s_addr & np->in_srcmsk) == np->in_srcip) && (np->in_redir & NAT_REDIRECT) && - (!np->in_pmin || np->in_pmin == dport)) { + (!np->in_pmin || np->in_pmin == dport) && + (!np->in_p || np->in_p == ip->ip_p)) { if ((nat = nat_new(np, ip, fin, nflags, NAT_INBOUND))) { np->in_hits++; @@ -1534,9 +1574,9 @@ maskloop: */ #if SOLARIS || defined(__sgi) if (nat->nat_dir == NAT_OUTBOUND) - fix_incksum(&ip->ip_sum, nat->nat_ipsumd); + fix_incksum(&ip->ip_sum, nat->nat_ipsumd, 0); else - fix_outcksum(&ip->ip_sum, nat->nat_ipsumd); + fix_outcksum(&ip->ip_sum, nat->nat_ipsumd, 0); #endif if (!(ip->ip_off & IP_OFFMASK) && !(fin->fin_fi.fi_fl & FI_SHORT)) { @@ -1574,9 +1614,9 @@ maskloop: } if (csump) { if (nat->nat_dir == NAT_OUTBOUND) - fix_incksum(csump, nat->nat_sumd); + fix_incksum(csump, nat->nat_sumd[0], 0); else - fix_outcksum(csump, nat->nat_sumd); + fix_outcksum(csump, nat->nat_sumd[0], 0); } } ATOMIC_INC(nat_stats.ns_mapped[0]); @@ -1680,7 +1720,7 @@ void *ifp; */ sum1 = nat->nat_outip.s_addr; if (fr_ifpaddr(ifp2, &in) != -1) - nat->nat_outip.s_addr = htonl(in.s_addr); + nat->nat_outip = in; sum2 = nat->nat_outip.s_addr; if (sum1 == sum2) @@ -1690,13 +1730,20 @@ void *ifp; * account the new IP#. */ CALC_SUMD(sum1, sum2, sumd); - sumd += nat->nat_sumd; - nat->nat_sumd = (sumd & 0xffff) + (sumd >> 16); + /* XXX - dont change for TCP when solaris does + * hardware checksumming. + */ + sumd += nat->nat_sumd[0]; + nat->nat_sumd[0] = (sumd & 0xffff) + (sumd >> 16); + nat->nat_sumd[1] = nat->nat_sumd[0]; } for (n = nat_list; (n != NULL); n = n->in_next) - if (n->in_ifp == ifp) + if (n->in_ifp == ifp) { n->in_ifp = (void *)GETUNIT(n->in_ifname); + if (!n->in_ifp) + n->in_ifp = (void *)-1; + } RWLOCK_EXIT(&ipf_nat); SPL_X(s); } diff --git a/sys/contrib/ipfilter/netinet/ip_nat.h b/sys/contrib/ipfilter/netinet/ip_nat.h index eeeebec..b931469 100644 --- a/sys/contrib/ipfilter/netinet/ip_nat.h +++ b/sys/contrib/ipfilter/netinet/ip_nat.h @@ -6,7 +6,7 @@ * to the original author and the contributors. * * @(#)ip_nat.h 1.5 2/4/96 - * $Id: ip_nat.h,v 2.1.2.1 1999/08/14 04:47:54 darrenr Exp $ + * $Id: ip_nat.h,v 2.1.2.2 1999/11/28 11:01:51 darrenr Exp $ * $FreeBSD$ */ @@ -58,13 +58,14 @@ #ifndef APR_LABELLEN #define APR_LABELLEN 16 #endif +#define NAT_HW_CKSUM 0x80000000 #define DEF_NAT_AGE 1200 /* 10 minutes (600 seconds) */ typedef struct nat { u_long nat_age; int nat_flags; - u_32_t nat_sumd; + u_32_t nat_sumd[2]; u_32_t nat_ipsumd; void *nat_data; void *nat_aps; /* proxy session */ @@ -220,7 +221,7 @@ extern nat_t *nat_instances; extern ipnat_t **nat_rules; extern ipnat_t **rdr_rules; extern natstat_t nat_stats; -#if defined(__NetBSD__) || defined(__OpenBSD__) || (__FreeBSD_version >= 300003) +#if defined(__NetBSD__) || defined(__OpenBSD__) extern int nat_ioctl __P((caddr_t, u_long, int)); #else extern int nat_ioctl __P((caddr_t, int, int)); @@ -241,7 +242,7 @@ extern int ip_natout __P((ip_t *, fr_info_t *)); extern int ip_natin __P((ip_t *, fr_info_t *)); extern void ip_natunload __P((void)), ip_natexpire __P((void)); extern void nat_log __P((struct nat *, u_int)); -extern void fix_incksum __P((u_short *, u_32_t)); -extern void fix_outcksum __P((u_short *, u_32_t)); +extern void fix_incksum __P((u_short *, u_32_t, int)); +extern void fix_outcksum __P((u_short *, u_32_t, int)); #endif /* __IP_NAT_H__ */ diff --git a/sys/contrib/ipfilter/netinet/ip_raudio_pxy.c b/sys/contrib/ipfilter/netinet/ip_raudio_pxy.c index b76eea5..611dc26 100644 --- a/sys/contrib/ipfilter/netinet/ip_raudio_pxy.c +++ b/sys/contrib/ipfilter/netinet/ip_raudio_pxy.c @@ -1,5 +1,4 @@ /* - * $Id$ * $FreeBSD$ */ #if SOLARIS && defined(_KERNEL) @@ -59,15 +58,12 @@ ip_t *ip; ap_session_t *aps; nat_t *nat; { - char membuf[512 + 1], *s; - int off, dlen, inc = 0; - tcphdr_t *tcp, tcph, *tcp2 = &tcph; raudio_t *rap = aps->aps_data; - u_short sp, dp, id = 0; - struct in_addr swip; - fr_info_t fi; + unsigned char membuf[512 + 1], *s; + u_short id = 0; + tcphdr_t *tcp; + int off, dlen; int len = 0; - nat_t *ipn; mb_t *m; #if SOLARIS mb_t *m1; @@ -89,14 +85,14 @@ nat_t *nat; dlen = msgdsize(m) - off; if (dlen <= 0) return 0; - copyout_mblk(m, off, MIN(sizeof(membuf), dlen), membuf); + copyout_mblk(m, off, MIN(sizeof(membuf), dlen), (char *)membuf); #else m = *(mb_t **)fin->fin_mp; dlen = mbufchainlen(m) - off; if (dlen <= 0) return 0; - m_copydata(m, off, MIN(sizeof(membuf), dlen), membuf); + m_copydata(m, off, MIN(sizeof(membuf), dlen), (char *)membuf); #endif /* * In all the startup parsing, ensure that we don't go outside @@ -106,7 +102,7 @@ nat_t *nat; * Look for the start of connection "PNA" string if not seen yet. */ if (rap->rap_seenpna == 0) { - s = memstr("PNA", membuf, 3, dlen); + s = (u_char *)memstr("PNA", (char *)membuf, 3, dlen); if (s == NULL) return 0; s += 3; @@ -160,38 +156,7 @@ nat_t *nat; rap->rap_gotid = 0; } } - - /* - * Wait until we've seen the end of the start messages and even then - * only proceed further if we're using UDP. - */ - if ((rap->rap_eos == 0) || ((rap->rap_mode & RAP_M_UDP) != RAP_M_UDP)) - return 0; - sp = rap->rap_plport; - dp = 0; - - bcopy((char *)fin, (char *)&fi, sizeof(fi)); - bzero((char *)tcp2, sizeof(*tcp2)); - tcp2->th_sport = htons(sp); - tcp2->th_dport = 0; /* XXX - don't specify remote port */ - tcp2->th_win = htons(8192); - fi.fin_dp = (char *)tcp2; - fi.fin_data[0] = sp; - fi.fin_data[1] = 0; - fi.fin_fr = &raudiofr; - swip = ip->ip_src; - ip->ip_src = nat->nat_inip; - ipn = nat_new(nat->nat_ptr, ip, &fi, IPN_TCP|FI_W_DPORT, NAT_OUTBOUND); - if (ipn != NULL) { - ipn->nat_age = fr_defnatage; - (void) fr_addstate(ip, &fi, FI_W_DPORT); - } - ip->ip_src = swip; - - if ((rap->rap_mode & RAP_M_UDP_ROBUST) == RAP_M_UDP_ROBUST) { - sp = rap->rap_prport; - } - return inc; + return 0; } @@ -201,19 +166,28 @@ ip_t *ip; ap_session_t *aps; nat_t *nat; { - char membuf[IPF_MAXPORTLEN + 1], *s; - int off, dlen; + unsigned char membuf[IPF_MAXPORTLEN + 1], *s; + tcphdr_t *tcp, tcph, *tcp2 = &tcph; raudio_t *rap = aps->aps_data; + struct in_addr swa, swb; u_int a1, a2, a3, a4; - tcphdr_t *tcp; + u_short sp, dp; + int off, dlen; + fr_info_t fi; tcp_seq seq; + nat_t *ipn; + u_char swp; mb_t *m; #if SOLARIS mb_t *m1; #endif - if ((rap->rap_sdone != 0) || - ((rap->rap_mode & RAP_M_UDP_ROBUST) != RAP_M_UDP_ROBUST)) + /* + * Wait until we've seen the end of the start messages and even then + * only proceed further if we're using UDP. If they want to use TCP + * then data is sent back on the same channel that is already open. + */ + if (rap->rap_sdone != 0) return 0; tcp = (tcphdr_t *)fin->fin_dp; @@ -227,13 +201,13 @@ nat_t *nat; if (dlen <= 0) return 0; bzero(membuf, sizeof(membuf)); - copyout_mblk(m, off, MIN(sizeof(membuf), dlen), membuf); + copyout_mblk(m, off, MIN(sizeof(membuf), dlen), (char *)membuf); #else dlen = mbufchainlen(m) - off; if (dlen <= 0) return 0; bzero(membuf, sizeof(membuf)); - m_copydata(m, off, MIN(sizeof(membuf), dlen), membuf); + m_copydata(m, off, MIN(sizeof(membuf), dlen), (char *)membuf); #endif seq = ntohl(tcp->th_seq); @@ -242,7 +216,7 @@ nat_t *nat; * We only care for the first 19 bytes coming back from the server. */ if (rap->rap_sseq == 0) { - s = memstr("PNA", membuf, 3, dlen); + s = (u_char *)memstr("PNA", (char *)membuf, 3, dlen); if (s == NULL) return 0; a1 = s - membuf; @@ -262,13 +236,68 @@ nat_t *nat; } else return 0; - for (a3 = a1, a4 = a2; a4 > 0; a4--, a3++) { + for (a3 = a1, a4 = a2; (a4 > 0) && (a3 < 19) && (a3 >= 0); a4--,a3++) { rap->rap_sbf |= (1 << a3); rap->rap_svr[a3] = *s++; } - if (rap->rap_sbf == 0x7ffff) { /* 19 bits */ - s = rap->rap_svr + 13; + + if ((rap->rap_sbf != 0x7ffff) || (!rap->rap_eos)) /* 19 bits */ + return 0; + rap->rap_sdone = 1; + + s = (u_char *)rap->rap_svr + 11; + if (((*s << 8) | *(s + 1)) == RA_ID_ROBUST) { + s += 2; rap->rap_srport = (*s << 8) | *(s + 1); } + + swp = ip->ip_p; + swa = ip->ip_src; + swb = ip->ip_dst; + + ip->ip_p = IPPROTO_UDP; + ip->ip_src = nat->nat_inip; + ip->ip_dst = nat->nat_oip; + + bcopy((char *)fin, (char *)&fi, sizeof(fi)); + bzero((char *)tcp2, sizeof(*tcp2)); + fi.fin_dp = (char *)tcp2; + fi.fin_fr = &raudiofr; + tcp2->th_win = htons(8192); + + if (((rap->rap_mode & RAP_M_UDP_ROBUST) == RAP_M_UDP_ROBUST) && + (rap->rap_srport != 0)) { + dp = rap->rap_srport; + sp = rap->rap_prport; + tcp2->th_sport = htons(sp); + tcp2->th_dport = htons(dp); + fi.fin_data[0] = dp; + fi.fin_data[1] = sp; + ipn = nat_new(nat->nat_ptr, ip, &fi, + IPN_UDP | (sp ? 0 : FI_W_SPORT), + NAT_OUTBOUND); + if (ipn != NULL) { + ipn->nat_age = fr_defnatage; + (void) fr_addstate(ip, &fi, sp ? 0 : FI_W_SPORT); + } + } + + if ((rap->rap_mode & RAP_M_UDP) == RAP_M_UDP) { + sp = rap->rap_plport; + tcp2->th_sport = htons(sp); + tcp2->th_dport = 0; /* XXX - don't specify remote port */ + fi.fin_data[0] = sp; + fi.fin_data[1] = 0; + ipn = nat_new(nat->nat_ptr, ip, &fi, IPN_UDP|FI_W_DPORT, + NAT_OUTBOUND); + if (ipn != NULL) { + ipn->nat_age = fr_defnatage; + (void) fr_addstate(ip, &fi, FI_W_DPORT); + } + } + + ip->ip_p = swp; + ip->ip_src = swa; + ip->ip_dst = swb; return 0; } diff --git a/sys/contrib/ipfilter/netinet/ip_rcmd_pxy.c b/sys/contrib/ipfilter/netinet/ip_rcmd_pxy.c index f9dc5b3..c8b15d1 100644 --- a/sys/contrib/ipfilter/netinet/ip_rcmd_pxy.c +++ b/sys/contrib/ipfilter/netinet/ip_rcmd_pxy.c @@ -1,10 +1,7 @@ /* - * $Id$ - * $FreeBSD$ - */ -/* * Simple RCMD transparent proxy for in-kernel use. For use with the NAT * code. + * $FreeBSD$ */ #if SOLARIS && defined(_KERNEL) extern kmutex_t ipf_rw; diff --git a/sys/contrib/ipfilter/netinet/ip_state.c b/sys/contrib/ipfilter/netinet/ip_state.c index c0e5a62..599ec27 100644 --- a/sys/contrib/ipfilter/netinet/ip_state.c +++ b/sys/contrib/ipfilter/netinet/ip_state.c @@ -7,7 +7,7 @@ */ #if !defined(lint) static const char sccsid[] = "@(#)ip_state.c 1.8 6/5/96 (C) 1993-1995 Darren Reed"; -/*static const char rcsid[] = "@(#)$Id: ip_state.c,v 2.3.2.9 1999/10/21 14:31:09 darrenr Exp $";*/ +/*static const char rcsid[] = "@(#)$Id: ip_state.c,v 2.3.2.16 1999/12/28 05:24:58 darrenr Exp $";*/ static const char rcsid[] = "@(#)$FreeBSD$"; #endif @@ -29,7 +29,8 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <linux/module.h> # endif #endif -#if defined(_KERNEL) && (__FreeBSD_version >= 220000) +#if ((defined(KERNEL) && (__FreeBSD_version >= 220000)) || \ + (defined(_KERNEL) && (__FreeBSD_version >= 400013))) # include <sys/filio.h> # include <sys/fcntl.h> # if (__FreeBSD_version >= 300000) && !defined(IPFILTER_LKM) @@ -44,7 +45,7 @@ static const char rcsid[] = "@(#)$FreeBSD$"; # include <sys/protosw.h> #endif #include <sys/socket.h> -#if (defined(_KERNEL) || defined(KERNEL)) && !defined(linux) +#if defined(_KERNEL) && !defined(linux) # include <sys/systm.h> #endif #if !defined(__SVR4) && !defined(__svr4__) @@ -97,9 +98,9 @@ static const char rcsid[] = "@(#)$FreeBSD$"; #define TCP_CLOSE (TH_FIN|TH_RST) -static ipstate_t **ips_table = NULL; -static int ips_num = 0; -static ips_stat_t ips_stats; +ipstate_t **ips_table = NULL; +int ips_num = 0; +ips_stat_t ips_stats; #if (SOLARIS || defined(__sgi)) && defined(_KERNEL) extern KRWLOCK_T ipf_state, ipf_mutex; extern kmutex_t ipf_rw; @@ -201,10 +202,6 @@ int which; } else isp = &is->is_next; } - if (fr_state_doflush) { - (void) fr_state_flush(1); - fr_state_doflush = 0; - } RWLOCK_EXIT(&ipf_state); SPL_X(s); return removed; @@ -232,6 +229,14 @@ int mode; } else error = EINVAL; break; +#ifdef IPFILTER_LOG + case SIOCIPFFB : + if (!(mode & FWRITE)) + error = EPERM; + else + *(int *)data = ipflog_clear(IPL_LOGSTATE); + break; +#endif case SIOCGIPST : IWCOPY((caddr_t)fr_statetstats(), data, sizeof(ips_stat_t)); break; @@ -347,9 +352,11 @@ u_int flags; { register tcphdr_t *tcp = (tcphdr_t *)fin->fin_dp; + is->is_dport = tcp->th_dport; + is->is_sport = tcp->th_sport; if ((flags & (FI_W_DPORT|FI_W_SPORT)) == 0) { - hv += (is->is_dport = tcp->th_dport); - hv += (is->is_sport = tcp->th_sport); + hv += tcp->th_dport; + hv += tcp->th_sport; } ATOMIC_INC(ips_stats.iss_udp); is->is_age = fr_udptimeout; @@ -657,12 +664,14 @@ fr_info_t *fin; register u_short sport, dport; register u_char pr; struct icmp *ic; + u_short savelen; fr_info_t ofin; - u_int hv, dest; tcphdr_t *tcp; + icmphdr_t *icmp; frentry_t *fr; ip_t *oip; int type; + u_int hv; /* * Does it at least have the return (basic) IP header ? @@ -684,6 +693,70 @@ fr_info_t *fin; oip = (ip_t *)((char *)fin->fin_dp + ICMPERR_ICMPHLEN); if (ip->ip_len < ICMPERR_MAXPKTLEN + ((oip->ip_hl - 5) << 2)) return NULL; + + if (oip->ip_p == IPPROTO_ICMP) { + + icmp = (icmphdr_t *)((char *)oip + (oip->ip_hl << 2)); + + /* + * a ICMP error can only be generated as a result of an + * ICMP query, not as the response on an ICMP error + * + * XXX theoretically ICMP_ECHOREP and the other reply's are + * ICMP query's as well, but adding them here seems strange XXX + */ + if ((icmp->icmp_type != ICMP_ECHO) && + (icmp->icmp_type != ICMP_TSTAMP) && + (icmp->icmp_type != ICMP_IREQ) && + (icmp->icmp_type != ICMP_MASKREQ)) + return NULL; + + /* + * perform a lookup of the ICMP packet in the state table + */ + + hv = (pr = oip->ip_p); + hv += (src.s_addr = oip->ip_src.s_addr); + hv += (dst.s_addr = oip->ip_dst.s_addr); + if (icmp->icmp_type == ICMP_ECHO) { + hv += icmp->icmp_id; + hv += icmp->icmp_seq; + } + hv %= fr_statesize; + + oip->ip_len = ntohs(oip->ip_len); + fr_makefrip(oip->ip_hl << 2, oip, &ofin); + oip->ip_len = htons(oip->ip_len); + ofin.fin_ifp = fin->fin_ifp; + ofin.fin_out = !fin->fin_out; + ofin.fin_mp = NULL; /* if dereferenced, panic XXX */ + + READ_ENTER(&ipf_state); + for (isp = &ips_table[hv]; (is = *isp); isp = &is->is_next) + if ((is->is_p == pr) && + fr_matchsrcdst(is, src, dst, &ofin, NULL)) { + /* + * in the state table ICMP query's are stored + * with the type of the corresponding ICMP + * response. Correct here + */ + if (((is->is_type == ICMP_ECHOREPLY) && + (icmp->icmp_id == is->is_icmp.ics_id) && + (icmp->icmp_seq == is->is_icmp.ics_seq) && + (icmp->icmp_type == ICMP_ECHO)) || + (is->is_type - 1 == ic->icmp_type)) { + ips_stats.iss_hits++; + is->is_pkts++; + is->is_bytes += ip->ip_len; + fr = is->is_rule; + RWLOCK_EXIT(&ipf_state); + return fr; + } + } + RWLOCK_EXIT(&ipf_state); + return NULL; + }; + if ((oip->ip_p != IPPROTO_TCP) && (oip->ip_p != IPPROTO_UDP)) return NULL; @@ -707,9 +780,10 @@ fr_info_t *fin; * watch out here, as ip is in host order and oip in network * order. Any change we make must be undone afterwards. */ - oip->ip_len = ntohs(oip->ip_len); + savelen = oip->ip_len; + oip->ip_len = ip->ip_len - (ip->ip_hl << 2) - ICMPERR_ICMPHLEN; fr_makefrip(oip->ip_hl << 2, oip, &ofin); - oip->ip_len = htons(oip->ip_len); + oip->ip_len = savelen; ofin.fin_ifp = fin->fin_ifp; ofin.fin_out = !fin->fin_out; ofin.fin_mp = NULL; /* if dereferenced, panic XXX */ @@ -730,7 +804,6 @@ fr_info_t *fin; * we must swap src and dst here because the icmp * comes the other way around */ - dest = (is->is_dst.s_addr != src.s_addr); is->is_pkts++; is->is_bytes += ip->ip_len; /* @@ -778,17 +851,20 @@ fr_info_t *fin; switch (ip->ip_p) { case IPPROTO_ICMP : - hv += ic->icmp_id; - hv += ic->icmp_seq; + if ((ic->icmp_type == ICMP_ECHO) || + (ic->icmp_type == ICMP_ECHOREPLY)) { + hv += ic->icmp_id; + hv += ic->icmp_seq; + } hv %= fr_statesize; READ_ENTER(&ipf_state); for (isp = &ips_table[hv]; (is = *isp); isp = &is->is_next) if ((is->is_p == pr) && - (ic->icmp_id == is->is_icmp.ics_id) && - (ic->icmp_seq == is->is_icmp.ics_seq) && fr_matchsrcdst(is, src, dst, fin, NULL)) { if ((is->is_type == ICMP_ECHOREPLY) && - (ic->icmp_type == ICMP_ECHO)) + (ic->icmp_type == ICMP_ECHO) && + (ic->icmp_id == is->is_icmp.ics_id) && + (ic->icmp_seq == is->is_icmp.ics_seq)) ; else if (is->is_type != ic->icmp_type) continue; @@ -819,7 +895,6 @@ retry_tcp: if ((is->is_p == pr) && fr_matchsrcdst(is, src, dst, fin, tcp)) { if (fr_tcpstate(is, fin, ip, tcp)) { - break; #ifndef _KERNEL if (tcp->th_flags & TCP_CLOSE) { *isp = is->is_next; @@ -965,6 +1040,10 @@ void fr_timeoutstate() ips_num--; } else isp = &is->is_next; + if (fr_state_doflush) { + (void) fr_state_flush(1); + fr_state_doflush = 0; + } RWLOCK_EXIT(&ipf_state); SPL_X(s); } diff --git a/sys/contrib/ipfilter/netinet/ipl.h b/sys/contrib/ipfilter/netinet/ipl.h index f29b6fd..39ee74dc 100644 --- a/sys/contrib/ipfilter/netinet/ipl.h +++ b/sys/contrib/ipfilter/netinet/ipl.h @@ -6,13 +6,12 @@ * to the original author and the contributors. * * @(#)ipl.h 1.21 6/5/96 - * $Id$ * $FreeBSD$ */ #ifndef __IPL_H__ #define __IPL_H__ -#define IPL_VERSION "IP Filter: v3.3.3" +#define IPL_VERSION "IP Filter: v3.3.6" #endif |