Import IP Filter 4.1.13
This commit is contained in:
parent
74f74123f3
commit
83043906d8
@ -1,28 +1,29 @@
|
||||
Copyright (C) 1993-2002 by Darren Reed.
|
||||
|
||||
The author accepts no responsibility for the use of this software and
|
||||
provides it on an ``as is'' basis without express or implied warranty.
|
||||
|
||||
Redistribution and use, with or without modification, in source and binary
|
||||
forms, are permitted provided that this notice is preserved in its entirety
|
||||
and due credit is given to the original author and the contributors.
|
||||
|
||||
The licence and distribution terms for any publically available version or
|
||||
derivative of this code cannot be changed. i.e. this code cannot simply be
|
||||
copied, in part or in whole, and put under another distribution licence
|
||||
[including the GNU Public Licence.]
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
SUCH DAMAGE.
|
||||
|
||||
I hate legalese, don't you ?
|
||||
|
||||
/*
|
||||
* Copyright (C) 1993-2001 by Darren Reed.
|
||||
*
|
||||
* The author accepts no responsibility for the use of this software and
|
||||
* provides it on an ``as is'' basis without express or implied warranty.
|
||||
*
|
||||
* Redistribution and use, with or without modification, in source and binary
|
||||
* forms, are permitted provided that this notice is preserved in its entirety
|
||||
* and due credit is given to the original author and the contributors.
|
||||
*
|
||||
* The licence and distribution terms for any publically available version or
|
||||
* derivative of this code cannot be changed. i.e. this code cannot simply be
|
||||
* copied, in part or in whole, and put under another distribution licence
|
||||
* [including the GNU Public Licence.]
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* I hate legalese, don't you ?
|
||||
*/
|
||||
|
@ -137,7 +137,7 @@ struct file;
|
||||
|
||||
#if !defined(lint)
|
||||
static const char sccsid[] = "@(#)fil.c 1.36 6/5/96 (C) 1993-2000 Darren Reed";
|
||||
static const char rcsid[] = "@(#)$Id: fil.c,v 2.243.2.70 2005/12/07 08:15:16 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: fil.c,v 2.243.2.78 2006/03/29 11:19:54 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
#ifndef _KERNEL
|
||||
@ -145,12 +145,6 @@ static const char rcsid[] = "@(#)$Id: fil.c,v 2.243.2.70 2005/12/07 08:15:16 dar
|
||||
# include "ipt.h"
|
||||
# include "bpf-ipf.h"
|
||||
extern int opts;
|
||||
|
||||
# define FR_VERBOSE(verb_pr) verbose verb_pr
|
||||
# define FR_DEBUG(verb_pr) debug verb_pr
|
||||
#else /* #ifndef _KERNEL */
|
||||
# define FR_VERBOSE(verb_pr)
|
||||
# define FR_DEBUG(verb_pr)
|
||||
#endif /* _KERNEL */
|
||||
|
||||
|
||||
@ -1972,24 +1966,23 @@ u_32_t pass;
|
||||
* it, except for increasing the hit counter.
|
||||
*/
|
||||
if ((passt & FR_CALLNOW) != 0) {
|
||||
frentry_t *frs;
|
||||
|
||||
ATOMIC_INC64(fr->fr_hits);
|
||||
if ((fr->fr_func != NULL) &&
|
||||
(fr->fr_func != (ipfunc_t)-1)) {
|
||||
frentry_t *frs;
|
||||
(fr->fr_func == (ipfunc_t)-1))
|
||||
continue;
|
||||
|
||||
frs = fin->fin_fr;
|
||||
fin->fin_fr = fr;
|
||||
fr = (*fr->fr_func)(fin, &passt);
|
||||
if (fr == NULL) {
|
||||
fin->fin_fr = frs;
|
||||
continue;
|
||||
}
|
||||
passt = fr->fr_flags;
|
||||
fin->fin_fr = fr;
|
||||
}
|
||||
} else {
|
||||
frs = fin->fin_fr;
|
||||
fin->fin_fr = fr;
|
||||
fr = (*fr->fr_func)(fin, &passt);
|
||||
if (fr == NULL) {
|
||||
fin->fin_fr = frs;
|
||||
continue;
|
||||
}
|
||||
passt = fr->fr_flags;
|
||||
}
|
||||
fin->fin_fr = fr;
|
||||
|
||||
#ifdef IPFILTER_LOG
|
||||
/*
|
||||
@ -2021,18 +2014,20 @@ u_32_t pass;
|
||||
(void) strncpy(fin->fin_group, fr->fr_group, FR_GROUPLEN);
|
||||
if (fr->fr_grp != NULL) {
|
||||
fin->fin_fr = *fr->fr_grp;
|
||||
pass = fr_scanlist(fin, pass);
|
||||
passt = fr_scanlist(fin, pass);
|
||||
if (fin->fin_fr == NULL) {
|
||||
fin->fin_rule = rulen;
|
||||
(void) strncpy(fin->fin_group, fr->fr_group,
|
||||
FR_GROUPLEN);
|
||||
fin->fin_fr = fr;
|
||||
passt = pass;
|
||||
}
|
||||
if (fin->fin_flx & FI_DONTCACHE)
|
||||
logged = 1;
|
||||
pass = passt;
|
||||
}
|
||||
|
||||
if (pass & FR_QUICK) {
|
||||
if (passt & FR_QUICK) {
|
||||
/*
|
||||
* Finally, if we've asked to track state for this
|
||||
* packet, set it up. Add state for "quick" rules
|
||||
@ -2044,6 +2039,7 @@ u_32_t pass;
|
||||
!(fin->fin_flx & FI_STATE)) {
|
||||
int out = fin->fin_out;
|
||||
|
||||
fin->fin_fr = fr;
|
||||
if (fr_addstate(fin, NULL, 0) != NULL) {
|
||||
ATOMIC_INCL(frstats[out].fr_ads);
|
||||
} else {
|
||||
@ -2193,7 +2189,8 @@ u_32_t *passp;
|
||||
if (FR_ISAUTH(pass)) {
|
||||
if (fr_newauth(fin->fin_m, fin) != 0) {
|
||||
#ifdef _KERNEL
|
||||
fin->fin_m = *fin->fin_mp = NULL;
|
||||
if ((pass & FR_RETMASK) == 0)
|
||||
fin->fin_m = *fin->fin_mp = NULL;
|
||||
#else
|
||||
;
|
||||
#endif
|
||||
@ -2233,21 +2230,6 @@ u_32_t *passp;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Finally, if we've asked to track state for this packet, set it up.
|
||||
*/
|
||||
if ((pass & FR_KEEPSTATE) && !(fin->fin_flx & FI_STATE)) {
|
||||
if (fr_addstate(fin, NULL, 0) != NULL) {
|
||||
ATOMIC_INCL(frstats[out].fr_ads);
|
||||
} else {
|
||||
ATOMIC_INCL(frstats[out].fr_bads);
|
||||
if (FR_ISPASS(pass)) {
|
||||
pass &= ~FR_CMDMASK;
|
||||
pass |= FR_BLOCK;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fr = fin->fin_fr;
|
||||
|
||||
if (passp != NULL)
|
||||
@ -2313,8 +2295,6 @@ int out;
|
||||
#ifdef USE_INET6
|
||||
ip6_t *ip6;
|
||||
#endif
|
||||
SPL_INT(s);
|
||||
|
||||
/*
|
||||
* The first part of fr_check() deals with making sure that what goes
|
||||
* into the filtering engine makes some sense. Information about the
|
||||
@ -2328,6 +2308,8 @@ int out;
|
||||
|
||||
if ((u_int)ip & 0x3)
|
||||
return 2;
|
||||
# else
|
||||
SPL_INT(s);
|
||||
# endif
|
||||
|
||||
READ_ENTER(&ipf_global);
|
||||
@ -2493,6 +2475,23 @@ int out;
|
||||
if ((pass & FR_NOMATCH) || (fr == NULL))
|
||||
fr = fr_firewall(fin, &pass);
|
||||
|
||||
/*
|
||||
* If we've asked to track state for this packet, set it up.
|
||||
* Here rather than fr_firewall because fr_checkauth may decide
|
||||
* to return a packet for "keep state"
|
||||
*/
|
||||
if ((pass & FR_KEEPSTATE) && !(fin->fin_flx & FI_STATE)) {
|
||||
if (fr_addstate(fin, NULL, 0) != NULL) {
|
||||
ATOMIC_INCL(frstats[out].fr_ads);
|
||||
} else {
|
||||
ATOMIC_INCL(frstats[out].fr_bads);
|
||||
if (FR_ISPASS(pass)) {
|
||||
pass &= ~FR_CMDMASK;
|
||||
pass |= FR_BLOCK;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fin->fin_fr = fr;
|
||||
|
||||
/*
|
||||
@ -2547,7 +2546,7 @@ int out;
|
||||
|
||||
RWLOCK_EXIT(&ipf_mutex);
|
||||
|
||||
if (pass & (FR_RETRST|FR_RETICMP)) {
|
||||
if ((pass & FR_RETMASK) != 0) {
|
||||
/*
|
||||
* Should we return an ICMP packet to indicate error
|
||||
* status passing through the packet filter ?
|
||||
@ -2573,6 +2572,14 @@ int out;
|
||||
ATOMIC_INCL(frstats[1].fr_ret);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* When using return-* with auth rules, the auth code
|
||||
* takes over disposing of this packet.
|
||||
*/
|
||||
if (FR_ISAUTH(pass) && (fin->fin_m != NULL)) {
|
||||
fin->fin_m = *fin->fin_mp = NULL;
|
||||
}
|
||||
} else {
|
||||
if (pass & FR_RETRST)
|
||||
fin->fin_error = ECONNRESET;
|
||||
@ -2786,10 +2793,10 @@ int len;
|
||||
/* */
|
||||
/* Expects ip_len to be in host byte order when called. */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
u_short fr_cksum(m, ip, l4proto, l4hdr)
|
||||
u_short fr_cksum(m, ip, l4proto, l4hdr, l3len)
|
||||
mb_t *m;
|
||||
ip_t *ip;
|
||||
int l4proto;
|
||||
int l4proto, l3len;
|
||||
void *l4hdr;
|
||||
{
|
||||
u_short *sp, slen, sumsave, l4hlen, *csump;
|
||||
@ -2814,7 +2821,7 @@ void *l4hdr;
|
||||
if (IP_V(ip) == 4) {
|
||||
#endif
|
||||
hlen = IP_HL(ip) << 2;
|
||||
slen = ip->ip_len - hlen;
|
||||
slen = l3len - hlen;
|
||||
sum = htons((u_short)l4proto);
|
||||
sum += htons(slen);
|
||||
sp = (u_short *)&ip->ip_src;
|
||||
@ -2826,9 +2833,9 @@ void *l4hdr;
|
||||
} else if (IP_V(ip) == 6) {
|
||||
ip6 = (ip6_t *)ip;
|
||||
hlen = sizeof(*ip6);
|
||||
slen = ntohs(ip6->ip6_plen);
|
||||
slen = ntohs(l3len);
|
||||
sum = htons((u_short)l4proto);
|
||||
sum += htons(slen);
|
||||
sum += slen;
|
||||
sp = (u_short *)&ip6->ip6_src;
|
||||
sum += *sp++; /* ip6_src */
|
||||
sum += *sp++;
|
||||
@ -3059,7 +3066,7 @@ void *l4hdr;
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)uipc_mbuf.c 8.2 (Berkeley) 1/4/94
|
||||
* $Id: fil.c,v 2.243.2.70 2005/12/07 08:15:16 darrenr Exp $
|
||||
* $Id: fil.c,v 2.243.2.78 2006/03/29 11:19:54 darrenr Exp $
|
||||
*/
|
||||
/*
|
||||
* Copy data from an mbuf chain starting "off" bytes from the beginning,
|
||||
@ -3472,7 +3479,7 @@ int proto, flags;
|
||||
char *memstr(src, dst, slen, dlen)
|
||||
const char *src;
|
||||
char *dst;
|
||||
int slen, dlen;
|
||||
size_t slen, dlen;
|
||||
{
|
||||
char *s = NULL;
|
||||
|
||||
@ -3760,13 +3767,7 @@ size_t size;
|
||||
caddr_t ca;
|
||||
int err;
|
||||
|
||||
# if SOLARIS
|
||||
err = COPYIN(dst, (caddr_t)&ca, sizeof(ca));
|
||||
if (err != 0)
|
||||
return err;
|
||||
# else
|
||||
bcopy(dst, (caddr_t)&ca, sizeof(ca));
|
||||
# endif
|
||||
err = COPYOUT(src, ca, size);
|
||||
return err;
|
||||
}
|
||||
@ -4886,7 +4887,7 @@ ipftq_t *ifq;
|
||||
ifq->ifq_next->ifq_pnext = ifq->ifq_pnext;
|
||||
|
||||
MUTEX_DESTROY(&ifq->ifq_lock);
|
||||
fr_userifqs--;
|
||||
ATOMIC_DEC(fr_userifqs);
|
||||
KFREE(ifq);
|
||||
}
|
||||
|
||||
@ -4908,8 +4909,6 @@ ipftqent_t *tqe;
|
||||
ipftq_t *ifq;
|
||||
|
||||
ifq = tqe->tqe_ifq;
|
||||
if (ifq == NULL)
|
||||
return;
|
||||
|
||||
MUTEX_ENTER(&ifq->ifq_lock);
|
||||
|
||||
@ -4981,24 +4980,21 @@ ipftqent_t *tqe;
|
||||
tqe->tqe_die = fr_ticks + ifq->ifq_ttl;
|
||||
|
||||
MUTEX_ENTER(&ifq->ifq_lock);
|
||||
if (tqe->tqe_next == NULL) { /* at the end already ? */
|
||||
MUTEX_EXIT(&ifq->ifq_lock);
|
||||
return;
|
||||
if (tqe->tqe_next != NULL) { /* at the end already ? */
|
||||
/*
|
||||
* Remove from list
|
||||
*/
|
||||
*tqe->tqe_pnext = tqe->tqe_next;
|
||||
tqe->tqe_next->tqe_pnext = tqe->tqe_pnext;
|
||||
|
||||
/*
|
||||
* Make it the last entry.
|
||||
*/
|
||||
tqe->tqe_next = NULL;
|
||||
tqe->tqe_pnext = ifq->ifq_tail;
|
||||
*ifq->ifq_tail = tqe;
|
||||
ifq->ifq_tail = &tqe->tqe_next;
|
||||
}
|
||||
|
||||
/*
|
||||
* Remove from list
|
||||
*/
|
||||
*tqe->tqe_pnext = tqe->tqe_next;
|
||||
tqe->tqe_next->tqe_pnext = tqe->tqe_pnext;
|
||||
|
||||
/*
|
||||
* Make it the last entry.
|
||||
*/
|
||||
tqe->tqe_next = NULL;
|
||||
tqe->tqe_pnext = ifq->ifq_tail;
|
||||
*ifq->ifq_tail = tqe;
|
||||
ifq->ifq_tail = &tqe->tqe_next;
|
||||
MUTEX_EXIT(&ifq->ifq_lock);
|
||||
}
|
||||
|
||||
@ -5050,46 +5046,44 @@ ipftq_t *oifq, *nifq;
|
||||
* Is the operation here going to be a no-op ?
|
||||
*/
|
||||
MUTEX_ENTER(&oifq->ifq_lock);
|
||||
if (oifq == nifq && *oifq->ifq_tail == tqe) {
|
||||
MUTEX_EXIT(&oifq->ifq_lock);
|
||||
return;
|
||||
if ((oifq != nifq) || (*oifq->ifq_tail != tqe)) {
|
||||
/*
|
||||
* Remove from the old queue
|
||||
*/
|
||||
*tqe->tqe_pnext = tqe->tqe_next;
|
||||
if (tqe->tqe_next)
|
||||
tqe->tqe_next->tqe_pnext = tqe->tqe_pnext;
|
||||
else
|
||||
oifq->ifq_tail = tqe->tqe_pnext;
|
||||
tqe->tqe_next = NULL;
|
||||
|
||||
/*
|
||||
* If we're moving from one queue to another, release the
|
||||
* lock on the old queue and get a lock on the new queue.
|
||||
* For user defined queues, if we're moving off it, call
|
||||
* delete in case it can now be freed.
|
||||
*/
|
||||
if (oifq != nifq) {
|
||||
tqe->tqe_ifq = NULL;
|
||||
|
||||
(void) fr_deletetimeoutqueue(oifq);
|
||||
|
||||
MUTEX_EXIT(&oifq->ifq_lock);
|
||||
|
||||
MUTEX_ENTER(&nifq->ifq_lock);
|
||||
|
||||
tqe->tqe_ifq = nifq;
|
||||
nifq->ifq_ref++;
|
||||
}
|
||||
|
||||
/*
|
||||
* Add to the bottom of the new queue
|
||||
*/
|
||||
tqe->tqe_die = fr_ticks + nifq->ifq_ttl;
|
||||
tqe->tqe_pnext = nifq->ifq_tail;
|
||||
*nifq->ifq_tail = tqe;
|
||||
nifq->ifq_tail = &tqe->tqe_next;
|
||||
}
|
||||
|
||||
/*
|
||||
* Remove from the old queue
|
||||
*/
|
||||
*tqe->tqe_pnext = tqe->tqe_next;
|
||||
if (tqe->tqe_next)
|
||||
tqe->tqe_next->tqe_pnext = tqe->tqe_pnext;
|
||||
else
|
||||
oifq->ifq_tail = tqe->tqe_pnext;
|
||||
tqe->tqe_next = NULL;
|
||||
|
||||
/*
|
||||
* If we're moving from one queue to another, release the lock on the
|
||||
* old queue and get a lock on the new queue. For user defined queues,
|
||||
* if we're moving off it, call delete in case it can now be freed.
|
||||
*/
|
||||
if (oifq != nifq) {
|
||||
tqe->tqe_ifq = NULL;
|
||||
|
||||
(void) fr_deletetimeoutqueue(oifq);
|
||||
|
||||
MUTEX_EXIT(&oifq->ifq_lock);
|
||||
|
||||
MUTEX_ENTER(&nifq->ifq_lock);
|
||||
|
||||
tqe->tqe_ifq = nifq;
|
||||
nifq->ifq_ref++;
|
||||
}
|
||||
|
||||
/*
|
||||
* Add to the bottom of the new queue
|
||||
*/
|
||||
tqe->tqe_die = fr_ticks + nifq->ifq_ttl;
|
||||
tqe->tqe_pnext = nifq->ifq_tail;
|
||||
*nifq->ifq_tail = tqe;
|
||||
nifq->ifq_tail = &tqe->tqe_next;
|
||||
MUTEX_EXIT(&nifq->ifq_lock);
|
||||
}
|
||||
|
||||
@ -5573,7 +5567,7 @@ fr_info_t *fin;
|
||||
|
||||
if (dosum)
|
||||
sum = fr_cksum(fin->fin_m, fin->fin_ip,
|
||||
fin->fin_p, fin->fin_dp);
|
||||
fin->fin_p, fin->fin_dp, fin->fin_plen);
|
||||
#if SOLARIS && defined(_KERNEL) && (SOLARIS2 >= 6) && defined(ICK_VALID)
|
||||
}
|
||||
#endif
|
||||
|
@ -117,12 +117,13 @@ extern struct ifqueue ipintrq; /* ip packet input queue */
|
||||
/* END OF INCLUDES */
|
||||
|
||||
#if !defined(lint)
|
||||
static const char rcsid[] = "@(#)$Id: ip_auth.c,v 2.73.2.5 2005/06/12 07:18:14 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_auth.c,v 2.73.2.13 2006/03/29 11:19:55 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
|
||||
#if SOLARIS
|
||||
#if SOLARIS && defined(_KERNEL)
|
||||
extern kcondvar_t ipfauthwait;
|
||||
extern struct pollhead iplpollhead[IPL_LOGSIZE];
|
||||
#endif /* SOLARIS */
|
||||
#if defined(linux) && defined(_KERNEL)
|
||||
wait_queue_head_t fr_authnext_linux;
|
||||
@ -317,7 +318,7 @@ fr_info_t *fin;
|
||||
|
||||
fra = fr_auth + i;
|
||||
fra->fra_index = i;
|
||||
fra->fra_pass = 0;
|
||||
fra->fra_pass = fin->fin_fr->fr_flags;
|
||||
fra->fra_age = fr_defaultauthage;
|
||||
bcopy((char *)fin, (char *)&fra->fra_info, sizeof(*fin));
|
||||
#if !defined(sparc) && !defined(m68k)
|
||||
@ -339,17 +340,15 @@ fr_info_t *fin;
|
||||
}
|
||||
#endif
|
||||
#if SOLARIS && defined(_KERNEL)
|
||||
COPYIFNAME(fin->fin_ifp, fra->fra_info.fin_ifname);
|
||||
m->b_rptr -= qpi->qpi_off;
|
||||
fr_authpkts[i] = *(mblk_t **)fin->fin_mp;
|
||||
fra->fra_q = qpi->qpi_q; /* The queue can disappear! */
|
||||
fra->fra_m = *fin->fin_mp;
|
||||
fra->fra_info.fin_mp = &fra->fra_m;
|
||||
cv_signal(&ipfauthwait);
|
||||
pollwakeup(&iplpollhead[IPL_LOGAUTH], POLLIN|POLLRDNORM);
|
||||
#else
|
||||
# if defined(BSD) && !defined(sparc) && (BSD >= 199306)
|
||||
if (!fin->fin_out) {
|
||||
ip->ip_len = htons(ip->ip_len);
|
||||
ip->ip_off = htons(ip->ip_off);
|
||||
}
|
||||
# endif
|
||||
fr_authpkts[i] = m;
|
||||
WAKEUP(&fr_authnext,0);
|
||||
#endif
|
||||
@ -362,15 +361,15 @@ caddr_t data;
|
||||
ioctlcmd_t cmd;
|
||||
int mode;
|
||||
{
|
||||
frauth_t auth, *au = &auth, *fra;
|
||||
int i, error = 0, len;
|
||||
char *t;
|
||||
mb_t *m;
|
||||
#if defined(_KERNEL) && !defined(MENTAT) && !defined(linux) && \
|
||||
(!defined(__FreeBSD_version) || (__FreeBSD_version < 501000))
|
||||
struct ifqueue *ifq;
|
||||
SPL_INT(s);
|
||||
#endif
|
||||
frauth_t auth, *au = &auth, *fra;
|
||||
int i, error = 0, len;
|
||||
char *t;
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
@ -399,10 +398,14 @@ int mode;
|
||||
case SIOCAUTHW:
|
||||
fr_authioctlloop:
|
||||
error = fr_inobj(data, au, IPFOBJ_FRAUTH);
|
||||
if (error != 0)
|
||||
break;
|
||||
READ_ENTER(&ipf_auth);
|
||||
if ((fr_authnext != fr_authend) && fr_authpkts[fr_authnext]) {
|
||||
error = fr_outobj(data, &fr_auth[fr_authnext],
|
||||
IPFOBJ_FRAUTH);
|
||||
if (error != 0)
|
||||
break;
|
||||
if (auth.fra_len != 0 && auth.fra_buf != NULL) {
|
||||
/*
|
||||
* Copy packet contents out to user space if
|
||||
@ -416,11 +419,12 @@ int mode;
|
||||
for (t = auth.fra_buf; m && (len > 0); ) {
|
||||
i = MIN(M_LEN(m), len);
|
||||
error = copyoutptr(MTOD(m, char *),
|
||||
t, i);
|
||||
&t, i);
|
||||
len -= i;
|
||||
t += i;
|
||||
if (error != 0)
|
||||
break;
|
||||
m = m->m_next;
|
||||
}
|
||||
}
|
||||
RWLOCK_EXIT(&ipf_auth);
|
||||
@ -473,10 +477,8 @@ int mode;
|
||||
#endif
|
||||
MUTEX_EXIT(&ipf_authmx);
|
||||
READ_ENTER(&ipf_global);
|
||||
if (error == 0) {
|
||||
READ_ENTER(&ipf_auth);
|
||||
if (error == 0)
|
||||
goto fr_authioctlloop;
|
||||
}
|
||||
break;
|
||||
|
||||
case SIOCAUTHR:
|
||||
@ -487,6 +489,7 @@ int mode;
|
||||
WRITE_ENTER(&ipf_auth);
|
||||
i = au->fra_index;
|
||||
fra = fr_auth + i;
|
||||
error = 0;
|
||||
if ((i < 0) || (i >= fr_authsize) ||
|
||||
(fra->fra_info.fin_id != au->fra_info.fin_id)) {
|
||||
RWLOCK_EXIT(&ipf_auth);
|
||||
@ -501,7 +504,11 @@ int mode;
|
||||
#ifdef _KERNEL
|
||||
if ((m != NULL) && (au->fra_info.fin_out != 0)) {
|
||||
# ifdef MENTAT
|
||||
error = !putq(fra->fra_q, m);
|
||||
error = ipf_inject(&fra->fra_info);
|
||||
if (error != 0) {
|
||||
FREE_MB_T(m);
|
||||
error = ENOBUFS;
|
||||
}
|
||||
# else /* MENTAT */
|
||||
# if defined(linux) || defined(AIX)
|
||||
# else
|
||||
@ -521,7 +528,11 @@ int mode;
|
||||
fr_authstats.fas_sendok++;
|
||||
} else if (m) {
|
||||
# ifdef MENTAT
|
||||
error = !putq(fra->fra_q, m);
|
||||
error = ipf_inject(&fra->fra_info);
|
||||
if (error != 0) {
|
||||
FREE_MB_T(m);
|
||||
error = ENOBUFS;
|
||||
}
|
||||
# else /* MENTAT */
|
||||
# if defined(linux) || defined(AIX)
|
||||
# else
|
||||
@ -552,10 +563,6 @@ int mode;
|
||||
fr_authstats.fas_queok++;
|
||||
} else
|
||||
error = EINVAL;
|
||||
# ifdef MENTAT
|
||||
if (error != 0)
|
||||
error = EINVAL;
|
||||
# else /* MENTAT */
|
||||
/*
|
||||
* If we experience an error which will result in the packet
|
||||
* not being processed, make sure we advance to the next one.
|
||||
@ -579,7 +586,6 @@ int mode;
|
||||
}
|
||||
}
|
||||
}
|
||||
# endif /* MENTAT */
|
||||
#endif /* _KERNEL */
|
||||
SPL_X(s);
|
||||
break;
|
||||
@ -794,3 +800,9 @@ int fr_authflush()
|
||||
|
||||
return num_flushed;
|
||||
}
|
||||
|
||||
|
||||
int fr_auth_waiting()
|
||||
{
|
||||
return (fr_authnext != fr_authend) && fr_authpkts[fr_authnext];
|
||||
}
|
||||
|
@ -3,7 +3,7 @@
|
||||
*
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* $Id: ip_auth.h,v 2.16 2003/07/25 12:29:56 darrenr Exp $
|
||||
* $Id: ip_auth.h,v 2.16.2.2 2006/03/16 06:45:49 darrenr Exp $
|
||||
*
|
||||
*/
|
||||
#ifndef __IP_AUTH_H__
|
||||
@ -20,6 +20,7 @@ typedef struct frauth {
|
||||
char *fra_buf;
|
||||
#ifdef MENTAT
|
||||
queue_t *fra_q;
|
||||
mb_t *fra_m;
|
||||
#endif
|
||||
} frauth_t;
|
||||
|
||||
@ -60,5 +61,6 @@ extern mb_t **fr_authpkts;
|
||||
extern int fr_newauth __P((mb_t *, fr_info_t *));
|
||||
extern int fr_preauthcmd __P((ioctlcmd_t, frentry_t *, frentry_t **));
|
||||
extern int fr_auth_ioctl __P((caddr_t, ioctlcmd_t, int));
|
||||
extern int fr_auth_waiting __P((void));
|
||||
|
||||
#endif /* __IP_AUTH_H__ */
|
||||
|
@ -4,7 +4,7 @@
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* @(#)ip_compat.h 1.8 1/14/96
|
||||
* $Id: ip_compat.h,v 2.142.2.33 2005/12/04 23:40:17 darrenr Exp $
|
||||
* $Id: ip_compat.h,v 2.142.2.36 2006/03/26 05:50:29 darrenr Exp $
|
||||
*/
|
||||
|
||||
#ifndef __IP_COMPAT_H__
|
||||
@ -441,6 +441,7 @@ extern void *get_unit __P((char *, int));
|
||||
wakeup(id + x); \
|
||||
spinunlock(_l); \
|
||||
}
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define KMALLOC(a, b) MALLOC((a), b, sizeof(*(a)), M_IOSYS, M_NOWAIT)
|
||||
# define KMALLOCS(a, b, c) MALLOC((a), b, (c), M_IOSYS, M_NOWAIT)
|
||||
# define KFREE(x) kmem_free((char *)(x), sizeof(*(x)))
|
||||
@ -578,6 +579,7 @@ typedef struct {
|
||||
# define UIOMOVE(a,b,c,d) uiomove((caddr_t)a,b,c,d)
|
||||
# define SLEEP(id, n) sleep((id), PZERO+1)
|
||||
# define WAKEUP(id,x) wakeup(id+x)
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define KFREE(x) kmem_free((char *)(x), sizeof(*(x)))
|
||||
# define KFREES(x,s) kmem_free((char *)(x), (s))
|
||||
# define GETIFP(n,v) ifunit(n)
|
||||
@ -659,6 +661,7 @@ typedef struct mbuf mb_t;
|
||||
# define GETIFP(n, v) ifunit(n)
|
||||
# define GET_MINOR getminor
|
||||
# define WAKEUP(id,x) wakeup(id + x)
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define COPYIN(a,b,c) copyin((caddr_t)(a), (caddr_t)(b), (c))
|
||||
# define COPYOUT(a,b,c) copyout((caddr_t)(a), (caddr_t)(b), (c))
|
||||
# define BCOPYIN(a,b,c) bcopy((caddr_t)(a), (caddr_t)(b), (c))
|
||||
@ -1029,6 +1032,7 @@ typedef u_int32_t u_32_t;
|
||||
# define KFREES(x,s) kmem_free((char *)(x), (s))
|
||||
# define SLEEP(id, n) sleep((id), PZERO+1)
|
||||
# define WAKEUP(id,x) wakeup(id + x)
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define UIOMOVE(a,b,c,d) uiomove((caddr_t)a,b,c,d)
|
||||
# define IPF_PANIC(x,y) if (x) { printf y; panic("ipf_panic"); }
|
||||
|
||||
@ -1074,6 +1078,7 @@ struct ip6_ext {
|
||||
# define FREE_MB_T(m) kfree_skb(m)
|
||||
# define GETKTIME(x) do_gettimeofday((struct timeval *)x)
|
||||
# define SLEEP(x,s) 0, interruptible_sleep_on(x##_linux)
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define WAKEUP(x,y) wake_up(x##_linux + y)
|
||||
# define UIOMOVE(a,b,c,d) uiomove(a,b,c,d)
|
||||
# define USE_MUTEXES
|
||||
@ -1265,6 +1270,7 @@ extern void* getifp __P((char *, int));
|
||||
# define GET_MINOR minor
|
||||
# define SLEEP(id, n) sleepx((id), PZERO+1, 0)
|
||||
# define WAKEUP(id,x) wakeup(id)
|
||||
# define POLLWAKEUP(x) ;
|
||||
# define COPYIN(a,b,c) copyin((caddr_t)(a), (caddr_t)(b), (c))
|
||||
# define COPYOUT(a,b,c) copyout((caddr_t)(a), (caddr_t)(b), (c))
|
||||
# define BCOPYIN(a,b,c) bcopy((caddr_t)(a), (caddr_t)(b), (c))
|
||||
@ -1429,6 +1435,7 @@ typedef struct mb_s {
|
||||
# define FREE_MB_T(x)
|
||||
# define SLEEP(x,y) 1;
|
||||
# define WAKEUP(x,y) ;
|
||||
# define POLLWAKEUP(y) ;
|
||||
# define IPF_PANIC(x,y) ;
|
||||
# define PANIC(x,y) ;
|
||||
# define SPL_NET(x) ;
|
||||
@ -1451,6 +1458,7 @@ typedef struct mb_s {
|
||||
# define UIOMOVE(a,b,c,d) ipfuiomove(a,b,c,d)
|
||||
extern void m_copydata __P((mb_t *, int, int, caddr_t));
|
||||
extern int ipfuiomove __P((caddr_t, int, int, struct uio *));
|
||||
extern int bcopywrap __P((void *, void *, size_t));
|
||||
# ifndef CACHE_HASH
|
||||
# define CACHE_HASH(x) ((IFNAME(fin->fin_ifp)[0] + \
|
||||
((struct ifnet *)fin->fin_ifp)->if_unit) & 7)
|
||||
@ -1529,6 +1537,9 @@ typedef struct ip6_hdr ip6_t;
|
||||
#endif
|
||||
|
||||
#if defined(_KERNEL)
|
||||
# ifdef BSD
|
||||
extern struct selinfo ipfselwait[];
|
||||
# endif
|
||||
# ifdef MENTAT
|
||||
# define COPYDATA mb_copydata
|
||||
# define COPYBACK mb_copyback
|
||||
@ -1578,6 +1589,7 @@ MALLOC_DECLARE(M_IPFILTER);
|
||||
# define UIOMOVE(a,b,c,d) uiomove(a,b,d)
|
||||
# define SLEEP(id, n) tsleep((id), PPAUSE|PCATCH, n, 0)
|
||||
# define WAKEUP(id,x) wakeup(id+x)
|
||||
# define POLLWAKEUP(x) selwakeup(ipfselwait+x)
|
||||
# define GETIFP(n, v) ifunit(n)
|
||||
# endif /* (Free)BSD */
|
||||
|
||||
|
@ -4,7 +4,7 @@
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* @(#)ip_fil.h 1.35 6/5/96
|
||||
* $Id: ip_fil.h,v 2.170.2.23 2005/12/04 23:39:28 darrenr Exp $
|
||||
* $Id: ip_fil.h,v 2.170.2.29 2006/03/29 11:19:55 darrenr Exp $
|
||||
*/
|
||||
|
||||
#ifndef __IP_FIL_H__
|
||||
@ -305,6 +305,7 @@ typedef struct fr_info {
|
||||
#ifdef MENTAT
|
||||
mb_t *fin_qfm; /* pointer to mblk where pkt starts */
|
||||
void *fin_qpi;
|
||||
char fin_ifname[LIFNAMSIZ];
|
||||
#endif
|
||||
#ifdef __sgi
|
||||
void *fin_hbuf;
|
||||
@ -1133,6 +1134,17 @@ typedef struct ipftune {
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef _KERNEL
|
||||
# define FR_VERBOSE(verb_pr)
|
||||
# define FR_DEBUG(verb_pr)
|
||||
#else
|
||||
extern void debug __P((char *, ...));
|
||||
extern void verbose __P((char *, ...));
|
||||
# define FR_VERBOSE(verb_pr) verbose verb_pr
|
||||
# define FR_DEBUG(verb_pr) debug verb_pr
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef _KERNEL
|
||||
extern int fr_check __P((struct ip *, int, void *, int, mb_t **));
|
||||
extern int (*fr_checkp) __P((ip_t *, int, void *, int, mb_t **));
|
||||
@ -1148,6 +1160,7 @@ extern int iplioctl __P((int, ioctlcmd_t, caddr_t, int));
|
||||
extern int iplopen __P((dev_t, int));
|
||||
extern int iplclose __P((dev_t, int));
|
||||
extern void m_freem __P((mb_t *));
|
||||
extern int bcopywrap __P((void *, void *, size_t));
|
||||
#else /* #ifndef _KERNEL */
|
||||
# if defined(__NetBSD__) && defined(PFIL_HOOKS)
|
||||
extern void ipfilterattach __P((int));
|
||||
@ -1259,7 +1272,7 @@ extern ipfrwlock_t ipf_mutex, ipf_global, ip_poolrw, ipf_ipidfrag;
|
||||
extern ipfrwlock_t ipf_frag, ipf_state, ipf_nat, ipf_natfrag, ipf_auth;
|
||||
extern ipfrwlock_t ipf_frcache;
|
||||
|
||||
extern char *memstr __P((const char *, char *, int, int));
|
||||
extern char *memstr __P((const char *, char *, size_t, size_t));
|
||||
extern int count4bits __P((u_32_t));
|
||||
extern int frrequest __P((int, ioctlcmd_t, caddr_t, int, int));
|
||||
extern char *getifname __P((struct ifnet *));
|
||||
@ -1316,6 +1329,7 @@ extern void fr_delgroup __P((char *, minor_t, int));
|
||||
extern frgroup_t *fr_findgroup __P((char *, minor_t, int, frgroup_t ***));
|
||||
|
||||
extern int fr_loginit __P((void));
|
||||
extern int ipflog_canread __P((int));
|
||||
extern int ipflog_clear __P((minor_t));
|
||||
extern int ipflog_read __P((minor_t, uio_t *));
|
||||
extern int ipflog __P((fr_info_t *, u_int));
|
||||
@ -1324,7 +1338,7 @@ extern void fr_logunload __P((void));
|
||||
|
||||
extern frentry_t *fr_acctpkt __P((fr_info_t *, u_32_t *));
|
||||
extern int fr_copytolog __P((int, char *, int));
|
||||
extern u_short fr_cksum __P((mb_t *, ip_t *, int, void *));
|
||||
extern u_short fr_cksum __P((mb_t *, ip_t *, int, void *, int));
|
||||
extern void fr_deinitialise __P((void));
|
||||
extern frentry_t *fr_dolog __P((fr_info_t *, u_32_t *));
|
||||
extern frentry_t *fr_dstgrpmap __P((fr_info_t *, u_32_t *));
|
||||
|
@ -5,7 +5,7 @@
|
||||
*/
|
||||
#if !defined(lint)
|
||||
static const char sccsid[] = "@(#)ip_fil.c 2.41 6/5/96 (C) 1993-2000 Darren Reed";
|
||||
static const char rcsid[] = "@(#)$Id: ip_fil_freebsd.c,v 2.53.2.27 2005/08/20 13:48:19 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_fil_freebsd.c,v 2.53.2.32 2006/03/25 13:03:01 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
#if defined(KERNEL) || defined(_KERNEL)
|
||||
@ -55,6 +55,7 @@ static const char rcsid[] = "@(#)$Id: ip_fil_freebsd.c,v 2.53.2.27 2005/08/20 13
|
||||
#endif
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/selinfo.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#if __FreeBSD_version >= 300000
|
||||
@ -131,6 +132,7 @@ int ipf_locks_done = 0;
|
||||
#if (__FreeBSD_version >= 300000)
|
||||
struct callout_handle fr_slowtimer_ch;
|
||||
#endif
|
||||
struct selinfo ipfselwait[IPL_LOGSIZE];
|
||||
|
||||
#if (__FreeBSD_version >= 500011)
|
||||
# include <sys/conf.h>
|
||||
@ -300,6 +302,7 @@ int iplattach()
|
||||
fr_checkp = fr_check;
|
||||
}
|
||||
|
||||
bzero((char *)ipfselwait, sizeof(ipfselwait));
|
||||
bzero((char *)frcache, sizeof(frcache));
|
||||
fr_running = 1;
|
||||
|
||||
@ -476,9 +479,11 @@ int mode;
|
||||
}
|
||||
|
||||
SPL_NET(s);
|
||||
READ_ENTER(&ipf_global);
|
||||
|
||||
error = fr_ioctlswitch(unit, data, cmd, mode);
|
||||
if (error != -1) {
|
||||
RWLOCK_EXIT(&ipf_global);
|
||||
SPL_X(s);
|
||||
return error;
|
||||
}
|
||||
@ -619,7 +624,10 @@ int mode;
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
|
||||
RWLOCK_EXIT(&ipf_global);
|
||||
SPL_X(s);
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
@ -742,14 +750,18 @@ dev_t dev;
|
||||
#endif
|
||||
register struct uio *uio;
|
||||
{
|
||||
u_int xmin = GET_MINOR(dev);
|
||||
|
||||
if (xmin < 0)
|
||||
return ENXIO;
|
||||
|
||||
# ifdef IPFILTER_SYNC
|
||||
if (GET_MINOR(dev) == IPL_LOGSYNC)
|
||||
if (xmin == IPL_LOGSYNC)
|
||||
return ipfsync_read(uio);
|
||||
# endif
|
||||
|
||||
#ifdef IPFILTER_LOG
|
||||
return ipflog_read(GET_MINOR(dev), uio);
|
||||
return ipflog_read(xmin, uio);
|
||||
#else
|
||||
return ENXIO;
|
||||
#endif
|
||||
@ -1155,6 +1167,8 @@ frdest_t *fdp;
|
||||
u_short ip_off;
|
||||
frentry_t *fr;
|
||||
|
||||
ro = NULL;
|
||||
|
||||
#ifdef M_WRITABLE
|
||||
/*
|
||||
* HOT FIX/KLUDGE:
|
||||
@ -1168,15 +1182,15 @@ frdest_t *fdp;
|
||||
* problem.
|
||||
*/
|
||||
if (M_WRITABLE(m) == 0) {
|
||||
if ((m0 = m_dup(m, M_DONTWAIT)) != 0) {
|
||||
m0 = m_dup(m, M_DONTWAIT);
|
||||
if (m0 != 0) {
|
||||
FREE_MB_T(m);
|
||||
m = m0;
|
||||
*mpp = m;
|
||||
} else {
|
||||
error = ENOBUFS;
|
||||
FREE_MB_T(m);
|
||||
*mpp = NULL;
|
||||
fr_frouteok[1]++;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@ -1218,18 +1232,8 @@ frdest_t *fdp;
|
||||
goto bad;
|
||||
}
|
||||
|
||||
/*
|
||||
* 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) && (fin->fin_rev != 0)) {
|
||||
if ((ifp != NULL) && (fdp == &fr->fr_tif))
|
||||
return -1;
|
||||
}
|
||||
if (fdp != NULL) {
|
||||
if (fdp->fd_ip.s_addr != 0)
|
||||
dst->sin_addr = fdp->fd_ip;
|
||||
}
|
||||
if ((fdp != NULL) && (fdp->fd_ip.s_addr != 0))
|
||||
dst->sin_addr = fdp->fd_ip;
|
||||
|
||||
dst->sin_len = sizeof(*dst);
|
||||
rtalloc(ro);
|
||||
@ -1346,6 +1350,7 @@ frdest_t *fdp;
|
||||
else
|
||||
mhip->ip_off |= IP_MF;
|
||||
mhip->ip_len = htons((u_short)(len + mhlen));
|
||||
*mnext = m;
|
||||
m->m_next = m_copy(m0, off, len);
|
||||
if (m->m_next == 0) {
|
||||
error = ENOBUFS; /* ??? */
|
||||
@ -1356,7 +1361,6 @@ frdest_t *fdp;
|
||||
mhip->ip_off = htons((u_short)mhip->ip_off);
|
||||
mhip->ip_sum = 0;
|
||||
mhip->ip_sum = in_cksum(m, mhlen);
|
||||
*mnext = m;
|
||||
mnext = &m->m_act;
|
||||
}
|
||||
/*
|
||||
@ -1385,7 +1389,7 @@ frdest_t *fdp;
|
||||
else
|
||||
fr_frouteok[1]++;
|
||||
|
||||
if (ro->ro_rt) {
|
||||
if ((ro != NULL) && (ro->ro_rt != NULL)) {
|
||||
RTFREE(ro->ro_rt);
|
||||
}
|
||||
*mpp = NULL;
|
||||
@ -1488,6 +1492,9 @@ struct in_addr *inp, *inpmask;
|
||||
else if (atype == FRI_PEERADDR)
|
||||
sock = ifa->ifa_dstaddr;
|
||||
|
||||
if (sock == NULL)
|
||||
return -1;
|
||||
|
||||
#ifdef USE_INET6
|
||||
if (v == 6) {
|
||||
return fr_ifpfillv6addr(atype, (struct sockaddr_in6 *)sock,
|
||||
|
@ -100,7 +100,7 @@ extern struct timeout fr_slowtimer_ch;
|
||||
|
||||
#if !defined(lint)
|
||||
static const char sccsid[] = "@(#)ip_frag.c 1.11 3/24/96 (C) 1993-2000 Darren Reed";
|
||||
static const char rcsid[] = "@(#)$Id: ip_frag.c,v 2.77.2.4 2005/08/20 13:48:21 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_frag.c,v 2.77.2.5 2006/02/26 08:26:54 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
|
||||
@ -224,6 +224,7 @@ ipfr_t *table[];
|
||||
{
|
||||
ipfr_t *fra, frag;
|
||||
u_int idx, off;
|
||||
frentry_t *fr;
|
||||
ip_t *ip;
|
||||
|
||||
if (ipfr_inuse >= IPFT_SIZE)
|
||||
@ -275,12 +276,9 @@ ipfr_t *table[];
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fra->ipfr_rule = fin->fin_fr;
|
||||
if (fra->ipfr_rule != NULL) {
|
||||
|
||||
frentry_t *fr;
|
||||
|
||||
fr = fin->fin_fr;
|
||||
fr = fin->fin_fr;
|
||||
fra->ipfr_rule = fr;
|
||||
if (fr != NULL) {
|
||||
MUTEX_ENTER(&fr->fr_lock);
|
||||
fr->fr_ref++;
|
||||
MUTEX_EXIT(&fr->fr_lock);
|
||||
|
@ -6,7 +6,7 @@
|
||||
* Simple FTP transparent proxy for in-kernel use. For use with the NAT
|
||||
* code.
|
||||
*
|
||||
* $Id: ip_ftp_pxy.c,v 2.88.2.16 2005/12/04 23:39:27 darrenr Exp $
|
||||
* $Id: ip_ftp_pxy.c,v 2.88.2.19 2006/04/01 10:14:53 darrenr Exp $
|
||||
*/
|
||||
|
||||
#define IPF_FTP_PROXY
|
||||
@ -366,7 +366,7 @@ int dlen;
|
||||
fi.fin_fi.fi_daddr = nat->nat_inip.s_addr;
|
||||
ip->ip_dst = nat->nat_inip;
|
||||
}
|
||||
(void) fr_addstate(&fi, &nat2->nat_state, SI_W_DPORT);
|
||||
(void) fr_addstate(&fi, NULL, SI_W_DPORT);
|
||||
if (fi.fin_state != NULL)
|
||||
fr_statederef(&fi, (ipstate_t **)&fi.fin_state);
|
||||
}
|
||||
@ -728,7 +728,7 @@ u_int data_ip;
|
||||
fi.fin_fi.fi_daddr = nat->nat_inip.s_addr;
|
||||
ip->ip_dst = nat->nat_inip;
|
||||
}
|
||||
(void) fr_addstate(&fi, &nat2->nat_state, sflags);
|
||||
(void) fr_addstate(&fi, NULL, sflags);
|
||||
if (fi.fin_state != NULL)
|
||||
fr_statederef(&fi, (ipstate_t **)&fi.fin_state);
|
||||
}
|
||||
@ -1027,13 +1027,14 @@ int rv;
|
||||
if (ippr_ftp_debug > 4)
|
||||
printf("ippr_ftp_process: mlen %d\n", mlen);
|
||||
|
||||
if (mlen <= 0) {
|
||||
if ((tcp->th_flags & TH_OPENING) == TH_OPENING) {
|
||||
f->ftps_seq[0] = thseq + 1;
|
||||
t->ftps_seq[0] = thack;
|
||||
}
|
||||
if ((mlen == 0) && ((tcp->th_flags & TH_OPENING) == TH_OPENING)) {
|
||||
f->ftps_seq[0] = thseq + 1;
|
||||
t->ftps_seq[0] = thack;
|
||||
return 0;
|
||||
} else if (mlen < 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
aps = nat->nat_aps;
|
||||
|
||||
sel = aps->aps_sel[1 - rv];
|
||||
@ -1423,7 +1424,7 @@ int dlen;
|
||||
ap += *s++ - '0';
|
||||
}
|
||||
|
||||
if (!s)
|
||||
if (!*s)
|
||||
return 0;
|
||||
|
||||
if (*s == '|')
|
||||
|
@ -1,5 +1,3 @@
|
||||
/* $FreeBSD$ */
|
||||
|
||||
/*
|
||||
* Copyright 2001, QNX Software Systems Ltd. All Rights Reserved
|
||||
*
|
||||
@ -248,7 +246,7 @@ nat_t *nat;
|
||||
tcp = (tcphdr_t *)fin->fin_dp;
|
||||
ipaddr = nat->nat_inip.s_addr;
|
||||
data = (caddr_t)tcp + (TCP_OFF(tcp) << 2);
|
||||
datlen = ip->ip_len - fin->fin_hlen - (TCP_OFF(tcp) << 2);
|
||||
datlen = fin->fin_dlen - (TCP_OFF(tcp) << 2);
|
||||
if (find_port(ipaddr, data, datlen, &off, &port) == 0) {
|
||||
fr_info_t fi;
|
||||
nat_t *nat2;
|
||||
|
@ -3,7 +3,7 @@
|
||||
*
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* $Id: ip_log.c,v 2.75.2.7 2005/06/11 07:47:44 darrenr Exp $
|
||||
* $Id: ip_log.c,v 2.75.2.11 2006/03/26 13:50:47 darrenr Exp $
|
||||
*/
|
||||
#include <sys/param.h>
|
||||
#if defined(KERNEL) || defined(_KERNEL)
|
||||
@ -65,6 +65,10 @@ struct file;
|
||||
# include <sys/dir.h>
|
||||
# endif
|
||||
# include <sys/mbuf.h>
|
||||
# include <sys/select.h>
|
||||
# if __FreeBSD_version >= 500000
|
||||
# include <sys/selinfo.h>
|
||||
# endif
|
||||
#else
|
||||
# if !defined(__hpux) && defined(_KERNEL)
|
||||
# include <sys/filio.h>
|
||||
@ -145,6 +149,7 @@ wait_queue_head_t iplh_linux[IPL_LOGSIZE];
|
||||
# endif
|
||||
# if SOLARIS
|
||||
extern kcondvar_t iplwait;
|
||||
extern struct pollhead iplpollhead[IPL_LOGSIZE];
|
||||
# endif
|
||||
|
||||
iplog_t **iplh[IPL_LOGSIZE], *iplt[IPL_LOGSIZE], *ipll[IPL_LOGSIZE];
|
||||
@ -503,9 +508,11 @@ int *types, cnt;
|
||||
# if SOLARIS && defined(_KERNEL)
|
||||
cv_signal(&iplwait);
|
||||
MUTEX_EXIT(&ipl_mutex);
|
||||
pollwakeup(&iplpollhead[dev], POLLRDNORM);
|
||||
# else
|
||||
MUTEX_EXIT(&ipl_mutex);
|
||||
WAKEUP(iplh,dev);
|
||||
WAKEUP(iplh, dev);
|
||||
POLLWAKEUP(dev);
|
||||
# endif
|
||||
SPL_X(s);
|
||||
# ifdef IPL_SELECT
|
||||
@ -663,4 +670,19 @@ minor_t unit;
|
||||
SPL_X(s);
|
||||
return used;
|
||||
}
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------ */
|
||||
/* Function: ipflog_canread */
|
||||
/* Returns: int - 0 == no data to read, 1 = data present */
|
||||
/* Parameters: unit(I) - device we are reading from */
|
||||
/* */
|
||||
/* Returns an indication of whether or not there is data present in the */
|
||||
/* current buffer for the selected ipf device. */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
int ipflog_canread(unit)
|
||||
int unit;
|
||||
{
|
||||
return iplt[unit] != NULL;
|
||||
}
|
||||
#endif /* IPFILTER_LOG */
|
||||
|
@ -107,7 +107,7 @@ extern struct ifnet vpnif;
|
||||
|
||||
#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.195.2.47 2005/11/14 17:13:35 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_nat.c,v 2.195.2.56 2006/04/01 10:15:34 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
|
||||
@ -191,7 +191,7 @@ static int nat_siocaddnat __P((ipnat_t *, ipnat_t **, int));
|
||||
static void nat_siocdelnat __P((ipnat_t *, ipnat_t **, int));
|
||||
static int nat_finalise __P((fr_info_t *, nat_t *, natinfo_t *,
|
||||
tcphdr_t *, nat_t **, int));
|
||||
static void nat_resolverule __P((ipnat_t *));
|
||||
static int nat_resolverule __P((ipnat_t *));
|
||||
static nat_t *fr_natclone __P((fr_info_t *, nat_t *));
|
||||
static void nat_mssclamp __P((tcphdr_t *, u_32_t, fr_info_t *, u_short *));
|
||||
static int nat_wildok __P((nat_t *, int, int, int, int));
|
||||
@ -865,11 +865,8 @@ int getlock;
|
||||
{
|
||||
int error = 0, i, j;
|
||||
|
||||
nat_resolverule(n);
|
||||
if (n->in_plabel[0] != '\0') {
|
||||
if (n->in_apr == NULL)
|
||||
return ENOENT;
|
||||
}
|
||||
if (nat_resolverule(n) != 0)
|
||||
return ENOENT;
|
||||
|
||||
if ((n->in_age[0] == 0) && (n->in_age[1] != 0))
|
||||
return EINVAL;
|
||||
@ -994,7 +991,7 @@ int getlock;
|
||||
/* from information passed to the kernel, then add it to the appropriate */
|
||||
/* NAT rule table(s). */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
static void nat_resolverule(n)
|
||||
static int nat_resolverule(n)
|
||||
ipnat_t *n;
|
||||
{
|
||||
n->in_ifnames[0][LIFNAMSIZ - 1] = '\0';
|
||||
@ -1005,12 +1002,15 @@ ipnat_t *n;
|
||||
(void) strncpy(n->in_ifnames[1], n->in_ifnames[0], LIFNAMSIZ);
|
||||
n->in_ifps[1] = n->in_ifps[0];
|
||||
} else {
|
||||
n->in_ifps[1] = fr_resolvenic(n->in_ifnames[0], 4);
|
||||
n->in_ifps[1] = fr_resolvenic(n->in_ifnames[1], 4);
|
||||
}
|
||||
|
||||
if (n->in_plabel[0] != '\0') {
|
||||
n->in_apr = appr_lookup(n->in_p, n->in_plabel);
|
||||
if (n->in_apr == NULL)
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -1338,23 +1338,31 @@ int getlock;
|
||||
|
||||
ATOMIC_INC(nat_stats.ns_rules);
|
||||
|
||||
nat_resolverule(in);
|
||||
if (nat_resolverule(in) != 0) {
|
||||
error = ESRCH;
|
||||
goto junkput;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Check that the NAT entry doesn't already exist in the kernel.
|
||||
*
|
||||
* For NAT_OUTBOUND, we're lookup for a duplicate MAP entry. To do
|
||||
* this, we check to see if the inbound combination of addresses and
|
||||
* ports is already known. Similar logic is applied for NAT_INBOUND.
|
||||
*
|
||||
*/
|
||||
bzero((char *)&fin, sizeof(fin));
|
||||
fin.fin_p = nat->nat_p;
|
||||
fin.fin_ifp = nat->nat_ifps[0];
|
||||
if (nat->nat_dir == NAT_OUTBOUND) {
|
||||
fin.fin_data[0] = ntohs(nat->nat_oport);
|
||||
fin.fin_data[1] = ntohs(nat->nat_outport);
|
||||
fin.fin_ifp = nat->nat_ifps[1];
|
||||
if (getlock) {
|
||||
READ_ENTER(&ipf_nat);
|
||||
}
|
||||
n = nat_inlookup(&fin, 0, fin.fin_p, nat->nat_oip,
|
||||
nat->nat_inip);
|
||||
n = nat_inlookup(&fin, nat->nat_flags, fin.fin_p,
|
||||
nat->nat_oip, nat->nat_inip);
|
||||
if (getlock) {
|
||||
RWLOCK_EXIT(&ipf_nat);
|
||||
}
|
||||
@ -1365,12 +1373,11 @@ int getlock;
|
||||
} else if (nat->nat_dir == NAT_INBOUND) {
|
||||
fin.fin_data[0] = ntohs(nat->nat_outport);
|
||||
fin.fin_data[1] = ntohs(nat->nat_oport);
|
||||
fin.fin_ifp = nat->nat_ifps[0];
|
||||
if (getlock) {
|
||||
READ_ENTER(&ipf_nat);
|
||||
}
|
||||
n = nat_outlookup(&fin, 0, fin.fin_p, nat->nat_outip,
|
||||
nat->nat_oip);
|
||||
n = nat_outlookup(&fin, nat->nat_flags, fin.fin_p,
|
||||
nat->nat_outip, nat->nat_oip);
|
||||
if (getlock) {
|
||||
RWLOCK_EXIT(&ipf_nat);
|
||||
}
|
||||
@ -1435,6 +1442,12 @@ int getlock;
|
||||
fr->fr_ref = 1;
|
||||
(void) fr_outobj(data, ipnn, IPFOBJ_NATSAVE);
|
||||
bcopy((char *)&ipnn->ipn_fr, (char *)fr, sizeof(*fr));
|
||||
|
||||
fr->fr_ref = 1;
|
||||
fr->fr_dsize = 0;
|
||||
fr->fr_data = NULL;
|
||||
fr->fr_type = FR_T_NONE;
|
||||
|
||||
MUTEX_NUKE(&fr->fr_lock);
|
||||
MUTEX_INIT(&fr->fr_lock, "nat-filter rule lock");
|
||||
} else {
|
||||
@ -1574,6 +1587,9 @@ int logtype;
|
||||
MUTEX_EXIT(&ipf_nat_new);
|
||||
return;
|
||||
}
|
||||
/*
|
||||
* At this point, nat_ref can be either 0 or -1
|
||||
*/
|
||||
|
||||
#ifdef IPFILTER_SYNC
|
||||
if (nat->nat_sync)
|
||||
@ -2152,6 +2168,9 @@ natinfo_t *ni;
|
||||
/* structure for a "MAP" rule (outgoing NAT translation); (2) deal with */
|
||||
/* creating a new NAT structure for a "RDR" rule (incoming NAT translation) */
|
||||
/* and (3) building that structure and putting it into the NAT table(s). */
|
||||
/* */
|
||||
/* NOTE: natsave should NOT be used top point back to an ipstate_t struct */
|
||||
/* as it can result in memory being corrupted. */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
nat_t *nat_new(fin, np, natsave, flags, direction)
|
||||
fr_info_t *fin;
|
||||
@ -2245,6 +2264,7 @@ int direction;
|
||||
natl = nat_outlookup(fin, nflags, (u_int)fin->fin_p,
|
||||
fin->fin_src, fin->fin_dst);
|
||||
if (natl != NULL) {
|
||||
KFREE(nat);
|
||||
nat = natl;
|
||||
goto done;
|
||||
}
|
||||
@ -2262,6 +2282,7 @@ int direction;
|
||||
natl = nat_inlookup(fin, nflags, (u_int)fin->fin_p,
|
||||
fin->fin_src, fin->fin_dst);
|
||||
if (natl != NULL) {
|
||||
KFREE(nat);
|
||||
nat = natl;
|
||||
goto done;
|
||||
}
|
||||
@ -2375,7 +2396,12 @@ int direction;
|
||||
|
||||
np = ni->nai_np;
|
||||
|
||||
COPYIFNAME(fin->fin_ifp, nat->nat_ifnames[0]);
|
||||
if (np->in_ifps[0] != NULL) {
|
||||
COPYIFNAME(np->in_ifps[0], nat->nat_ifnames[0]);
|
||||
}
|
||||
if (np->in_ifps[1] != NULL) {
|
||||
COPYIFNAME(np->in_ifps[1], nat->nat_ifnames[1]);
|
||||
}
|
||||
#ifdef IPFILTER_SYNC
|
||||
if ((nat->nat_flags & SI_CLONE) == 0)
|
||||
nat->nat_sync = ipfsync_new(SMC_NAT, fin, nat);
|
||||
@ -2383,7 +2409,8 @@ int direction;
|
||||
|
||||
nat->nat_me = natsave;
|
||||
nat->nat_dir = direction;
|
||||
nat->nat_ifps[0] = fin->fin_ifp;
|
||||
nat->nat_ifps[0] = np->in_ifps[0];
|
||||
nat->nat_ifps[1] = np->in_ifps[1];
|
||||
nat->nat_ptr = np;
|
||||
nat->nat_p = fin->fin_p;
|
||||
nat->nat_mssclamp = np->in_mssclamp;
|
||||
@ -2470,7 +2497,7 @@ int rev;
|
||||
nat->nat_ifnames[0][LIFNAMSIZ - 1] = '\0';
|
||||
nat->nat_ifps[0] = fr_resolvenic(nat->nat_ifnames[0], 4);
|
||||
|
||||
if (nat->nat_ifnames[1][0] !='\0') {
|
||||
if (nat->nat_ifnames[1][0] != '\0') {
|
||||
nat->nat_ifnames[1][LIFNAMSIZ - 1] = '\0';
|
||||
nat->nat_ifps[1] = fr_resolvenic(nat->nat_ifnames[1], 4);
|
||||
} else {
|
||||
@ -2818,8 +2845,9 @@ int dir;
|
||||
*
|
||||
* Since the port fields are part of the TCP/UDP checksum
|
||||
* of the offending IP packet, you need to adjust that checksum
|
||||
* as well... but, if you change, you must change the icmp
|
||||
* checksum *again*, to reflect that change.
|
||||
* as well... except that the change in the port numbers should
|
||||
* be offset by the checksum change, so we only need to change
|
||||
* the ICMP checksum if we only change the ports.
|
||||
*
|
||||
* To further complicate: the TCP checksum is not in the first
|
||||
* 8 bytes of the offending ip packet, so it most likely is not
|
||||
@ -2854,21 +2882,14 @@ int dir;
|
||||
* The UDP checksum is optional, only adjust it if
|
||||
* it has been set.
|
||||
*/
|
||||
if ((oip->ip_p == IPPROTO_UDP) &&
|
||||
(dlen >= 8) && (*csump != 0)) {
|
||||
if (oip->ip_p == IPPROTO_UDP) {
|
||||
sumd = sum1 - sum2;
|
||||
sumd2 += sumd;
|
||||
|
||||
sum1 = ntohs(*csump);
|
||||
fix_datacksum(csump, sumd);
|
||||
sum2 = ntohs(*csump);
|
||||
|
||||
/*
|
||||
* Fix ICMP checksum to compenstate
|
||||
* UDP checksum adjustment.
|
||||
*/
|
||||
CALC_SUMD(sum1, sum2, sumd);
|
||||
sumd2 += sumd;
|
||||
if ((dlen >= 8) && (*csump != 0)) {
|
||||
fix_datacksum(csump, sumd);
|
||||
} else {
|
||||
sumd2 += sumd;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2877,20 +2898,10 @@ int dir;
|
||||
* the other direction compared to the ICMP message.
|
||||
*/
|
||||
if (oip->ip_p == IPPROTO_TCP) {
|
||||
sumd = sum1 - sum2;
|
||||
|
||||
if (dlen >= 18) {
|
||||
sumd = sum1 - sum2;
|
||||
sumd2 += sumd;
|
||||
|
||||
sum1 = ntohs(*csump);
|
||||
fix_datacksum(csump, sumd);
|
||||
sum2 = ntohs(*csump);
|
||||
|
||||
/*
|
||||
* Fix ICMP checksum to compensate
|
||||
* TCP checksum adjustment.
|
||||
*/
|
||||
CALC_SUMD(sum1, sum2, sumd);
|
||||
sumd2 += sumd;
|
||||
} else {
|
||||
sumd = sum2 - sum1 + 1;
|
||||
sumd2 += sumd;
|
||||
@ -2910,21 +2921,14 @@ int dir;
|
||||
* The UDP checksum is optional, only adjust
|
||||
* it if it has been set.
|
||||
*/
|
||||
if ((oip->ip_p == IPPROTO_UDP) &&
|
||||
(dlen >= 8) && (*csump != 0)) {
|
||||
if (oip->ip_p == IPPROTO_UDP) {
|
||||
sumd = sum1 - sum2;
|
||||
sumd2 += sumd;
|
||||
|
||||
sum1 = ntohs(*csump);
|
||||
fix_datacksum(csump, sumd);
|
||||
sum2 = ntohs(*csump);
|
||||
|
||||
/*
|
||||
* Fix ICMP checksum to compensate
|
||||
* UDP checksum adjustment.
|
||||
*/
|
||||
CALC_SUMD(sum1, sum2, sumd);
|
||||
sumd2 += sumd;
|
||||
if ((dlen >= 8) && (*csump != 0)) {
|
||||
fix_datacksum(csump, sumd);
|
||||
} else {
|
||||
sumd2 += sumd;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2933,20 +2937,10 @@ int dir;
|
||||
* the other direction compared to the ICMP message.
|
||||
*/
|
||||
if (oip->ip_p == IPPROTO_TCP) {
|
||||
sumd = sum1 - sum2;
|
||||
|
||||
if (dlen >= 18) {
|
||||
sumd = sum1 - sum2;
|
||||
sumd2 += sumd;
|
||||
|
||||
sum1 = ntohs(*csump);
|
||||
fix_datacksum(csump, sumd);
|
||||
sum2 = ntohs(*csump);
|
||||
|
||||
/*
|
||||
* Fix ICMP checksum to compensate
|
||||
* TCP checksum adjustment.
|
||||
*/
|
||||
CALC_SUMD(sum1, sum2, sumd);
|
||||
sumd2 += sumd;
|
||||
} else {
|
||||
if (nat->nat_dir == NAT_INBOUND)
|
||||
sumd = sum2 - sum1;
|
||||
@ -3039,10 +3033,7 @@ struct in_addr src , mapdst;
|
||||
void *ifp;
|
||||
u_int hv;
|
||||
|
||||
if (fin != NULL)
|
||||
ifp = fin->fin_ifp;
|
||||
else
|
||||
ifp = NULL;
|
||||
ifp = fin->fin_ifp;
|
||||
sport = 0;
|
||||
dport = 0;
|
||||
gre = NULL;
|
||||
@ -3074,17 +3065,13 @@ struct in_addr src , mapdst;
|
||||
hv = NAT_HASH_FN(src.s_addr, hv + sport, ipf_nattable_sz);
|
||||
nat = nat_table[1][hv];
|
||||
for (; nat; nat = nat->nat_hnext[1]) {
|
||||
nflags = nat->nat_flags;
|
||||
if (nat->nat_ifps[0] != NULL) {
|
||||
if ((ifp != NULL) && (ifp != nat->nat_ifps[0]))
|
||||
continue;
|
||||
} else if (ifp != NULL)
|
||||
nat->nat_ifps[0] = ifp;
|
||||
|
||||
if (ifp != NULL) {
|
||||
if (nat->nat_dir == NAT_REDIRECT) {
|
||||
if (ifp != nat->nat_ifps[0])
|
||||
continue;
|
||||
} else {
|
||||
if (ifp != nat->nat_ifps[1])
|
||||
continue;
|
||||
}
|
||||
}
|
||||
nflags = nat->nat_flags;
|
||||
|
||||
if (nat->nat_oip.s_addr == src.s_addr &&
|
||||
nat->nat_outip.s_addr == dst &&
|
||||
@ -3149,15 +3136,11 @@ struct in_addr src , mapdst;
|
||||
|
||||
nat = nat_table[1][hv];
|
||||
for (; nat; nat = nat->nat_hnext[1]) {
|
||||
if (ifp != NULL) {
|
||||
if (nat->nat_dir == NAT_REDIRECT) {
|
||||
if (ifp != nat->nat_ifps[0])
|
||||
continue;
|
||||
} else {
|
||||
if (ifp != nat->nat_ifps[1])
|
||||
continue;
|
||||
}
|
||||
}
|
||||
if (nat->nat_ifps[0] != NULL) {
|
||||
if ((ifp != NULL) && (ifp != nat->nat_ifps[0]))
|
||||
continue;
|
||||
} else if (ifp != NULL)
|
||||
nat->nat_ifps[0] = ifp;
|
||||
|
||||
if (nat->nat_p != fin->fin_p)
|
||||
continue;
|
||||
@ -3324,17 +3307,13 @@ struct in_addr src , dst;
|
||||
hv = NAT_HASH_FN(dst.s_addr, hv + dport, ipf_nattable_sz);
|
||||
nat = nat_table[0][hv];
|
||||
for (; nat; nat = nat->nat_hnext[0]) {
|
||||
nflags = nat->nat_flags;
|
||||
if (nat->nat_ifps[1] != NULL) {
|
||||
if ((ifp != NULL) && (ifp != nat->nat_ifps[1]))
|
||||
continue;
|
||||
} else if (ifp != NULL)
|
||||
nat->nat_ifps[1] = ifp;
|
||||
|
||||
if (ifp != NULL) {
|
||||
if (nat->nat_dir == NAT_REDIRECT) {
|
||||
if (ifp != nat->nat_ifps[1])
|
||||
continue;
|
||||
} else {
|
||||
if (ifp != nat->nat_ifps[0])
|
||||
continue;
|
||||
}
|
||||
}
|
||||
nflags = nat->nat_flags;
|
||||
|
||||
if (nat->nat_inip.s_addr == srcip &&
|
||||
nat->nat_oip.s_addr == dst.s_addr &&
|
||||
@ -3389,15 +3368,11 @@ struct in_addr src , dst;
|
||||
|
||||
nat = nat_table[0][hv];
|
||||
for (; nat; nat = nat->nat_hnext[0]) {
|
||||
if (ifp != NULL) {
|
||||
if (nat->nat_dir == NAT_REDIRECT) {
|
||||
if (ifp != nat->nat_ifps[1])
|
||||
continue;
|
||||
} else {
|
||||
if (ifp != nat->nat_ifps[0])
|
||||
continue;
|
||||
}
|
||||
}
|
||||
if (nat->nat_ifps[1] != NULL) {
|
||||
if ((ifp != NULL) && (ifp != nat->nat_ifps[1]))
|
||||
continue;
|
||||
} else if (ifp != NULL)
|
||||
nat->nat_ifps[1] = ifp;
|
||||
|
||||
if (nat->nat_p != fin->fin_p)
|
||||
continue;
|
||||
@ -3446,6 +3421,16 @@ struct in_addr src , dst;
|
||||
/* entry for. */
|
||||
/* */
|
||||
/* Lookup the NAT tables to search for a matching redirect */
|
||||
/* The contents of natlookup_t should imitate those found in a packet that */
|
||||
/* would be translated - ie a packet coming in for RDR or going out for MAP.*/
|
||||
/* We can do the lookup in one of two ways, imitating an inbound or */
|
||||
/* outbound packet. By default we assume outbound, unless IPN_IN is set. */
|
||||
/* For IN, the fields are set as follows: */
|
||||
/* nl_real* = source information */
|
||||
/* nl_out* = destination information (translated) */
|
||||
/* For an out packet, the fields are set like this: */
|
||||
/* nl_in* = source information (untranslated) */
|
||||
/* nl_out* = destination information (translated) */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
nat_t *nat_lookupredir(np)
|
||||
natlookup_t *np;
|
||||
@ -3707,7 +3692,7 @@ u_32_t *passp;
|
||||
hv = NAT_HASH_FN(iph, 0, ipf_natrules_sz);
|
||||
for (np = nat_rules[hv]; np; np = np->in_mnext)
|
||||
{
|
||||
if ((np->in_ifps[0] && (np->in_ifps[0] != ifp)))
|
||||
if ((np->in_ifps[1] && (np->in_ifps[1] != ifp)))
|
||||
continue;
|
||||
if (np->in_v != fin->fin_v)
|
||||
continue;
|
||||
@ -4346,8 +4331,8 @@ void fr_natexpire()
|
||||
{
|
||||
ipftq_t *ifq, *ifqnext;
|
||||
ipftqent_t *tqe, *tqn;
|
||||
SPL_INT(s);
|
||||
int i;
|
||||
SPL_INT(s);
|
||||
|
||||
SPL_NET(s);
|
||||
WRITE_ENTER(&ipf_nat);
|
||||
|
@ -4,7 +4,7 @@
|
||||
* Simple PPTP transparent proxy for in-kernel use. For use with the NAT
|
||||
* code.
|
||||
*
|
||||
* $Id: ip_pptp_pxy.c,v 2.10.2.11 2005/12/04 23:39:27 darrenr Exp $
|
||||
* $Id: ip_pptp_pxy.c,v 2.10.2.13 2006/03/17 10:40:05 darrenr Exp $
|
||||
*
|
||||
*/
|
||||
#define IPF_PPTP_PROXY
|
||||
@ -93,7 +93,8 @@ nat_t *nat;
|
||||
if (nat_outlookup(fin, 0, IPPROTO_GRE, nat->nat_inip,
|
||||
ip->ip_dst) != NULL) {
|
||||
if (ippr_pptp_debug > 0)
|
||||
printf("ippr_pptp_new: GRE session already exists\n");
|
||||
printf("ippr_pptp_new: GRE session %s\n",
|
||||
"already exists");
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -101,7 +102,8 @@ nat_t *nat;
|
||||
KMALLOCS(aps->aps_data, pptp_pxy_t *, sizeof(*pptp));
|
||||
if (aps->aps_data == NULL) {
|
||||
if (ippr_pptp_debug > 0)
|
||||
printf("ippr_pptp_new: malloc for aps_data failed\n");
|
||||
printf("ippr_pptp_new: malloc for aps_data %s\n",
|
||||
"failed");
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -208,10 +210,12 @@ pptp_pxy_t *pptp;
|
||||
RWLOCK_EXIT(&ipf_state);
|
||||
} else {
|
||||
RWLOCK_EXIT(&ipf_state);
|
||||
if (nat->nat_dir == NAT_INBOUND)
|
||||
fi.fin_fi.fi_daddr = nat2->nat_inip.s_addr;
|
||||
else
|
||||
fi.fin_fi.fi_saddr = nat2->nat_inip.s_addr;
|
||||
if (nat2 != NULL) {
|
||||
if (nat->nat_dir == NAT_INBOUND)
|
||||
fi.fin_fi.fi_daddr = nat2->nat_inip.s_addr;
|
||||
else
|
||||
fi.fin_fi.fi_saddr = nat2->nat_inip.s_addr;
|
||||
}
|
||||
fi.fin_ifp = NULL;
|
||||
pptp->pptp_state = fr_addstate(&fi, &pptp->pptp_state,
|
||||
0);
|
||||
|
@ -103,7 +103,7 @@ struct file;
|
||||
/* END OF INCLUDES */
|
||||
|
||||
#if !defined(lint)
|
||||
static const char rcsid[] = "@(#)$Id: ip_proxy.c,v 2.62.2.14 2005/06/18 02:41:33 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_proxy.c,v 2.62.2.16 2006/03/29 11:19:56 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
static int appr_fixseqack __P((fr_info_t *, ip_t *, ap_session_t *, int ));
|
||||
@ -323,8 +323,7 @@ int mode;
|
||||
if (error == 0)
|
||||
error = appr_ctl(&ctl);
|
||||
|
||||
if ((ctl.apc_dsize > 0) && (ptr != NULL) &&
|
||||
(ctl.apc_data == ptr)) {
|
||||
if (ptr != NULL) {
|
||||
KFREES(ptr, ctl.apc_dsize);
|
||||
}
|
||||
break;
|
||||
@ -563,8 +562,8 @@ nat_t *nat;
|
||||
if (err != 0) {
|
||||
short adjlen = err & 0xffff;
|
||||
|
||||
s1 = LONG_SUM(ip->ip_len - adjlen);
|
||||
s2 = LONG_SUM(ip->ip_len);
|
||||
s1 = LONG_SUM(fin->fin_plen - adjlen);
|
||||
s2 = LONG_SUM(fin->fin_plen);
|
||||
CALC_SUMD(s1, s2, sd);
|
||||
fix_outcksum(fin, &ip->ip_sum, sd);
|
||||
}
|
||||
@ -584,19 +583,23 @@ nat_t *nat;
|
||||
#if SOLARIS && defined(_KERNEL) && (SOLARIS2 >= 6)
|
||||
if (dosum)
|
||||
tcp->th_sum = fr_cksum(fin->fin_qfm, ip,
|
||||
IPPROTO_TCP, tcp);
|
||||
IPPROTO_TCP, tcp,
|
||||
fin->fin_plen);
|
||||
#else
|
||||
tcp->th_sum = fr_cksum(fin->fin_m, ip,
|
||||
IPPROTO_TCP, tcp);
|
||||
IPPROTO_TCP, tcp,
|
||||
fin->fin_plen);
|
||||
#endif
|
||||
} else if ((udp != NULL) && (udp->uh_sum != 0)) {
|
||||
#if SOLARIS && defined(_KERNEL) && (SOLARIS2 >= 6)
|
||||
if (dosum)
|
||||
udp->uh_sum = fr_cksum(fin->fin_qfm, ip,
|
||||
IPPROTO_UDP, udp);
|
||||
IPPROTO_UDP, udp,
|
||||
fin->fin_plen);
|
||||
#else
|
||||
udp->uh_sum = fr_cksum(fin->fin_m, ip,
|
||||
IPPROTO_UDP, udp);
|
||||
IPPROTO_UDP, udp,
|
||||
fin->fin_plen);
|
||||
#endif
|
||||
}
|
||||
aps->aps_bytes += fin->fin_plen;
|
||||
@ -687,9 +690,9 @@ int inc;
|
||||
tcp = (tcphdr_t *)fin->fin_dp;
|
||||
out = fin->fin_out;
|
||||
/*
|
||||
* ip_len has already been adjusted by 'inc'.
|
||||
* fin->fin_plen has already been adjusted by 'inc'.
|
||||
*/
|
||||
nlen = ip->ip_len;
|
||||
nlen = fin->fin_plen;
|
||||
nlen -= (IP_HL(ip) << 2) + (TCP_OFF(tcp) << 2);
|
||||
|
||||
inc2 = inc;
|
||||
|
@ -3,7 +3,7 @@
|
||||
*
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* $Id: ip_rcmd_pxy.c,v 1.41.2.5 2005/10/02 04:20:07 darrenr Exp $
|
||||
* $Id: ip_rcmd_pxy.c,v 1.41.2.6 2006/04/01 10:14:54 darrenr Exp $
|
||||
*
|
||||
* Simple RCMD transparent proxy for in-kernel use. For use with the NAT
|
||||
* code.
|
||||
@ -202,7 +202,7 @@ nat_t *nat;
|
||||
fi.fin_fi.fi_daddr = nat->nat_inip.s_addr;
|
||||
ip->ip_dst = nat->nat_inip;
|
||||
}
|
||||
(void) fr_addstate(&fi, &nat2->nat_state, SI_W_DPORT);
|
||||
(void) fr_addstate(&fi, NULL, SI_W_DPORT);
|
||||
if (fi.fin_state != NULL)
|
||||
fr_statederef(&fi, (ipstate_t **)&fi.fin_state);
|
||||
}
|
||||
|
@ -58,7 +58,7 @@ struct file;
|
||||
|
||||
#if !defined(lint)
|
||||
static const char sccsid[] = "@(#)ip_state.c 1.8 6/5/96 (C) 1993-2000 Darren Reed";
|
||||
static const char rcsid[] = "@(#)$Id: ip_scan.c,v 2.40.2.4 2005/08/20 13:48:24 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_scan.c,v 2.40.2.6 2006/03/26 23:06:49 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
#ifdef IPFILTER_SCAN /* endif at bottom of file */
|
||||
@ -84,18 +84,23 @@ int ipsc_matchstr __P((sinfo_t *, char *, int));
|
||||
int ipsc_matchisc __P((ipscan_t *, ipstate_t *, int, int, int *));
|
||||
int ipsc_match __P((ipstate_t *));
|
||||
|
||||
static int ipsc_inited = 0;
|
||||
|
||||
|
||||
int ipsc_init()
|
||||
{
|
||||
RWLOCK_INIT(&ipsc_rwlock, "ip scan rwlock");
|
||||
ipsc_inited = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void fr_scanunload()
|
||||
{
|
||||
RW_DESTROY(&ipsc_rwlock);
|
||||
if (ipsc_inited == 1) {
|
||||
RW_DESTROY(&ipsc_rwlock);
|
||||
ipsc_inited = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -431,6 +436,8 @@ ipstate_t *is;
|
||||
}
|
||||
if (k == 1)
|
||||
isc = lm;
|
||||
if (isc == NULL)
|
||||
return 0;
|
||||
|
||||
/*
|
||||
* No matches or partial matches, so reset the respective
|
||||
|
@ -107,7 +107,7 @@ struct file;
|
||||
|
||||
#if !defined(lint)
|
||||
static const char sccsid[] = "@(#)ip_state.c 1.8 6/5/96 (C) 1993-2000 Darren Reed";
|
||||
static const char rcsid[] = "@(#)$Id: ip_state.c,v 2.186.2.36 2005/12/04 22:25:36 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_state.c,v 2.186.2.41 2006/04/01 10:16:28 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
static ipstate_t **ips_table = NULL;
|
||||
@ -668,6 +668,7 @@ caddr_t data;
|
||||
fr->fr_ref = 0;
|
||||
fr->fr_dsize = 0;
|
||||
fr->fr_data = NULL;
|
||||
fr->fr_type = FR_T_NONE;
|
||||
|
||||
fr_resolvedest(&fr->fr_tif, fr->fr_v);
|
||||
fr_resolvedest(&fr->fr_dif, fr->fr_v);
|
||||
@ -801,6 +802,11 @@ int rev;
|
||||
/* Inserts it into the state table and appends to the bottom of the active */
|
||||
/* list. If the capacity of the table has reached the maximum allowed then */
|
||||
/* the call will fail and a flush is scheduled for the next timeout call. */
|
||||
/* */
|
||||
/* NOTE: The use of stsave to point to nat_state will result in memory */
|
||||
/* corruption. It should only be used to point to objects that will */
|
||||
/* either outlive this (not expired) or will deref the ip_state_t */
|
||||
/* when they are deleted. */
|
||||
/* ------------------------------------------------------------------------ */
|
||||
ipstate_t *fr_addstate(fin, stsave, flags)
|
||||
fr_info_t *fin;
|
||||
@ -823,28 +829,30 @@ u_int flags;
|
||||
if ((fin->fin_flx & FI_OOW) && !(fin->fin_tcpf & TH_SYN))
|
||||
return NULL;
|
||||
|
||||
fr = fin->fin_fr;
|
||||
if ((fr->fr_statemax == 0) && (ips_num == fr_statemax)) {
|
||||
ATOMIC_INCL(ips_stats.iss_max);
|
||||
fr_state_doflush = 1;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* If a "keep state" rule has reached the maximum number of references
|
||||
* to it, then schedule an automatic flush in case we can clear out
|
||||
* some "dead old wood".
|
||||
* some "dead old wood". Note that because the lock isn't held on
|
||||
* fr it is possible that we could overflow. The cost of overflowing
|
||||
* is being ignored here as the number by which it can overflow is
|
||||
* a product of the number of simultaneous threads that could be
|
||||
* executing in here, so a limit of 100 won't result in 200, but could
|
||||
* result in 101 or 102.
|
||||
*/
|
||||
MUTEX_ENTER(&fr->fr_lock);
|
||||
if ((fr != NULL) && (fr->fr_statemax != 0) &&
|
||||
(fr->fr_statecnt >= fr->fr_statemax)) {
|
||||
MUTEX_EXIT(&fr->fr_lock);
|
||||
ATOMIC_INCL(ips_stats.iss_maxref);
|
||||
fr_state_doflush = 1;
|
||||
return NULL;
|
||||
fr = fin->fin_fr;
|
||||
if (fr != NULL) {
|
||||
if ((ips_num == fr_statemax) && (fr->fr_statemax == 0)) {
|
||||
ATOMIC_INCL(ips_stats.iss_max);
|
||||
fr_state_doflush = 1;
|
||||
return NULL;
|
||||
}
|
||||
if ((fr->fr_statemax != 0) &&
|
||||
(fr->fr_statecnt >= fr->fr_statemax)) {
|
||||
ATOMIC_INCL(ips_stats.iss_maxref);
|
||||
fr_state_doflush = 1;
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
fr->fr_statecnt++;
|
||||
MUTEX_EXIT(&fr->fr_lock);
|
||||
|
||||
pass = (fr == NULL) ? 0 : fr->fr_flags;
|
||||
|
||||
@ -1046,16 +1054,16 @@ u_int flags;
|
||||
break;
|
||||
}
|
||||
if (is != NULL)
|
||||
goto cantaddstate;
|
||||
return NULL;
|
||||
|
||||
if (ips_stats.iss_bucketlen[hv] >= fr_state_maxbucket) {
|
||||
ATOMIC_INCL(ips_stats.iss_bucketfull);
|
||||
goto cantaddstate;
|
||||
return NULL;
|
||||
}
|
||||
KMALLOC(is, ipstate_t *);
|
||||
if (is == NULL) {
|
||||
ATOMIC_INCL(ips_stats.iss_nomem);
|
||||
goto cantaddstate;
|
||||
return NULL;
|
||||
}
|
||||
bcopy((char *)&ips, (char *)is, sizeof(*is));
|
||||
/*
|
||||
@ -1140,6 +1148,7 @@ u_int flags;
|
||||
is->is_optmsk[0] &= ~0x8;
|
||||
is->is_optmsk[1] &= ~0x8;
|
||||
}
|
||||
is->is_me = stsave;
|
||||
is->is_sec = fin->fin_secmsk;
|
||||
is->is_secmsk = 0xffff;
|
||||
is->is_auth = fin->fin_auth;
|
||||
@ -1154,7 +1163,6 @@ u_int flags;
|
||||
is->is_pass &= ~(FR_LOGFIRST|FR_LOG);
|
||||
|
||||
READ_ENTER(&ipf_state);
|
||||
is->is_me = stsave;
|
||||
|
||||
fr_stinsert(is, fin->fin_rev);
|
||||
|
||||
@ -1188,14 +1196,6 @@ u_int flags;
|
||||
(void) fr_newfrag(fin, pass ^ FR_KEEPSTATE);
|
||||
|
||||
return is;
|
||||
|
||||
cantaddstate:
|
||||
if (fr != NULL) {
|
||||
MUTEX_ENTER(&fr->fr_lock);
|
||||
fr->fr_statecnt--;
|
||||
MUTEX_EXIT(&fr->fr_lock);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
@ -1455,18 +1455,6 @@ int flags;
|
||||
win = ntohs(tcp->th_win);
|
||||
else
|
||||
win = ntohs(tcp->th_win) << fdata->td_winscale;
|
||||
#if 0
|
||||
/*
|
||||
* XXX - This is a kludge is here because IPFilter doesn't track SACK
|
||||
* options in TCP packets. This is not a trivial to do if one is to
|
||||
* consider the performance impact of it. So instead, if the
|
||||
* receiver has said SACK is ok, double the allowed window size.
|
||||
* This is disabled for testing of another workaround for a problem
|
||||
* with Microsoft Windows - see below.
|
||||
*/
|
||||
if ((tdata->td_winflags & TCP_SACK_PERMIT) != 0)
|
||||
win *= 2;
|
||||
#endif
|
||||
|
||||
/*
|
||||
* A window of 0 produces undesirable behaviour from this function.
|
||||
@ -1553,6 +1541,39 @@ int flags;
|
||||
(fdata->td_winflags & TCP_SACK_PERMIT) &&
|
||||
(tdata->td_winflags & TCP_SACK_PERMIT)) {
|
||||
inseq = 1;
|
||||
/*
|
||||
* Sometimes a TCP RST will be generated with only the ACK field
|
||||
* set to non-zero.
|
||||
*/
|
||||
} else if ((seq == 0) && (tcpflags == (TH_RST|TH_ACK)) &&
|
||||
(ackskew >= -1) && (ackskew <= 1)) {
|
||||
inseq = 1;
|
||||
} else if (!(flags & IS_TCPFSM)) {
|
||||
int i;
|
||||
|
||||
i = (fin->fin_rev << 1) + fin->fin_out;
|
||||
|
||||
#if 0
|
||||
if (is_pkts[i]0 == 0) {
|
||||
/*
|
||||
* Picking up a connection in the middle, the "next"
|
||||
* packet seen from a direction that is new should be
|
||||
* accepted, even if it appears out of sequence.
|
||||
*/
|
||||
inseq = 1;
|
||||
} else
|
||||
#endif
|
||||
if (!(fdata->td_winflags &
|
||||
(TCP_WSCALE_SEEN|TCP_WSCALE_FIRST))) {
|
||||
/*
|
||||
* No TCPFSM and no window scaling, so make some
|
||||
* extra guesses.
|
||||
*/
|
||||
if ((seq == fdata->td_maxend) && (ackskew == 0))
|
||||
inseq = 1;
|
||||
else if (SEQ_GE(seq + maxwin, fdata->td_end - maxwin))
|
||||
inseq = 1;
|
||||
}
|
||||
}
|
||||
|
||||
if (inseq) {
|
||||
@ -2339,7 +2360,8 @@ ipftq_t **ifqp;
|
||||
if ((is->is_p != pr) || (is->is_v != v))
|
||||
continue;
|
||||
is = fr_matchsrcdst(fin, is, &src, &dst, NULL, FI_CMP);
|
||||
if (is != NULL &&
|
||||
if ((is != NULL) &&
|
||||
(ic->icmp_id == is->is_icmp.ici_id) &&
|
||||
fr_matchicmpqueryreply(v, &is->is_icmp,
|
||||
ic, fin->fin_rev)) {
|
||||
if (fin->fin_rev)
|
||||
@ -2432,11 +2454,13 @@ ipftq_t **ifqp;
|
||||
break;
|
||||
}
|
||||
|
||||
if ((is != NULL) && ((is->is_sti.tqe_flags & TQE_RULEBASED) != 0) &&
|
||||
(is->is_tqehead[fin->fin_rev] != NULL))
|
||||
ifq = is->is_tqehead[fin->fin_rev];
|
||||
if (ifq != NULL && ifqp != NULL)
|
||||
*ifqp = ifq;
|
||||
if (is != NULL) {
|
||||
if (((is->is_sti.tqe_flags & TQE_RULEBASED) != 0) &&
|
||||
(is->is_tqehead[fin->fin_rev] != NULL))
|
||||
ifq = is->is_tqehead[fin->fin_rev];
|
||||
if (ifq != NULL && ifqp != NULL)
|
||||
*ifqp = ifq;
|
||||
}
|
||||
return is;
|
||||
}
|
||||
|
||||
|
@ -96,7 +96,7 @@ struct file;
|
||||
/* END OF INCLUDES */
|
||||
|
||||
#if !defined(lint)
|
||||
static const char rcsid[] = "@(#)$Id: ip_sync.c,v 2.40.2.5 2005/09/04 12:51:12 darrenr Exp $";
|
||||
static const char rcsid[] = "@(#)$Id: ip_sync.c,v 2.40.2.7 2006/03/19 14:59:39 darrenr Exp $";
|
||||
#endif
|
||||
|
||||
#define SYNC_STATETABSZ 256
|
||||
@ -702,7 +702,6 @@ int ipfsync_nat(sp, data)
|
||||
synchdr_t *sp;
|
||||
void *data;
|
||||
{
|
||||
synclogent_t sle;
|
||||
syncupdent_t su;
|
||||
nat_t *n, *nat;
|
||||
synclist_t *sl;
|
||||
@ -714,8 +713,6 @@ void *data;
|
||||
switch (sp->sm_cmd)
|
||||
{
|
||||
case SMC_CREATE :
|
||||
bcopy(data, &sle, sizeof(sle));
|
||||
|
||||
KMALLOC(n, nat_t *);
|
||||
if (n == NULL) {
|
||||
err = ENOMEM;
|
||||
@ -729,9 +726,7 @@ void *data;
|
||||
break;
|
||||
}
|
||||
|
||||
WRITE_ENTER(&ipf_nat);
|
||||
|
||||
nat = &sle.sle_un.sleu_ipn;
|
||||
nat = (nat_t *)data;
|
||||
bzero((char *)n, offsetof(nat_t, nat_age));
|
||||
bcopy((char *)&nat->nat_age, (char *)&n->nat_age,
|
||||
sizeof(*n) - offsetof(nat_t, nat_age));
|
||||
@ -741,6 +736,8 @@ void *data;
|
||||
sl->sl_idx = -1;
|
||||
sl->sl_ipn = n;
|
||||
sl->sl_num = ntohl(sp->sm_num);
|
||||
|
||||
WRITE_ENTER(&ipf_nat);
|
||||
sl->sl_pnext = syncstatetab + hv;
|
||||
sl->sl_next = syncstatetab[hv];
|
||||
if (syncstatetab[hv] != NULL)
|
||||
@ -1005,4 +1002,16 @@ int mode;
|
||||
{
|
||||
return EINVAL;
|
||||
}
|
||||
|
||||
|
||||
int ipfsync_canread()
|
||||
{
|
||||
return !((sl_tail == sl_idx) && (su_tail == su_idx));
|
||||
}
|
||||
|
||||
|
||||
int ipfsync_canwrite()
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
#endif /* IPFILTER_SYNC */
|
||||
|
@ -4,7 +4,7 @@
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* @(#)ip_fil.h 1.35 6/5/96
|
||||
* $Id: ip_sync.h,v 2.11.2.2 2004/11/04 19:29:07 darrenr Exp $
|
||||
* $Id: ip_sync.h,v 2.11.2.3 2006/03/19 14:59:39 darrenr Exp $
|
||||
*/
|
||||
|
||||
#ifndef __IP_SYNC_H__
|
||||
@ -111,5 +111,7 @@ extern int ipfsync_nat __P((synchdr_t *sp, void *data));
|
||||
extern int ipfsync_state __P((synchdr_t *sp, void *data));
|
||||
extern int ipfsync_read __P((struct uio *uio));
|
||||
extern int ipfsync_write __P((struct uio *uio));
|
||||
extern int ipfsync_canread __P((void));
|
||||
extern int ipfsync_canwrite __P((void));
|
||||
|
||||
#endif /* IP_SYNC */
|
||||
|
@ -4,14 +4,14 @@
|
||||
* See the IPFILTER.LICENCE file for details on licencing.
|
||||
*
|
||||
* @(#)ipl.h 1.21 6/5/96
|
||||
* $Id: ipl.h,v 2.52.2.11 2005/12/04 22:37:24 darrenr Exp $
|
||||
* $Id: ipl.h,v 2.52.2.14 2006/04/01 20:09:42 darrenr Exp $
|
||||
*/
|
||||
|
||||
#ifndef __IPL_H__
|
||||
#define __IPL_H__
|
||||
|
||||
#define IPL_VERSION "IP Filter: v4.1.10"
|
||||
#define IPL_VERSION "IP Filter: v4.1.13"
|
||||
|
||||
#define IPFILTER_VERSION 4011000
|
||||
#define IPFILTER_VERSION 4011300
|
||||
|
||||
#endif
|
||||
|
@ -12,6 +12,10 @@
|
||||
#include <sys/conf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/sysctl.h>
|
||||
#include <sys/select.h>
|
||||
#if __FreeBSD_version >= 500000
|
||||
# include <sys/selinfo.h>
|
||||
#endif
|
||||
#include <net/if.h>
|
||||
#include <netinet/in_systm.h>
|
||||
#include <netinet/in.h>
|
||||
@ -24,6 +28,9 @@
|
||||
#include <netinet/ip_nat.h>
|
||||
#include <netinet/ip_auth.h>
|
||||
#include <netinet/ip_frag.h>
|
||||
#include <netinet/ip_sync.h>
|
||||
|
||||
extern struct selinfo ipfselwait[IPL_LOGSIZE];
|
||||
|
||||
#if __FreeBSD_version >= 502116
|
||||
static struct cdev *ipf_devs[IPL_LOGSIZE];
|
||||
@ -92,6 +99,10 @@ SYSCTL_IPF(_net_inet_ipf, OID_AUTO, fr_minttl, CTLFLAG_RW, &fr_minttl, 0, "");
|
||||
|
||||
#define CDEV_MAJOR 79
|
||||
#if __FreeBSD_version >= 501000
|
||||
# include <sys/poll.h>
|
||||
# include <sys/select.h>
|
||||
static int iplpoll(struct cdev *dev, int events, struct thread *td);
|
||||
|
||||
static struct cdevsw ipl_cdevsw = {
|
||||
# if __FreeBSD_version >= 502103
|
||||
.d_version = D_VERSION,
|
||||
@ -103,6 +114,7 @@ static struct cdevsw ipl_cdevsw = {
|
||||
.d_write = iplwrite,
|
||||
.d_ioctl = iplioctl,
|
||||
.d_name = "ipl",
|
||||
.d_poll = iplpoll,
|
||||
# if __FreeBSD_version < 600000
|
||||
.d_maj = CDEV_MAJOR,
|
||||
# endif
|
||||
@ -114,7 +126,7 @@ static struct cdevsw ipl_cdevsw = {
|
||||
/* read */ iplread,
|
||||
/* write */ iplwrite,
|
||||
/* ioctl */ iplioctl,
|
||||
/* poll */ nopoll,
|
||||
/* poll */ iplpoll,
|
||||
/* mmap */ nommap,
|
||||
/* strategy */ nostrategy,
|
||||
/* name */ "ipl",
|
||||
@ -270,3 +282,51 @@ sysctl_ipf_int ( SYSCTL_HANDLER_ARGS )
|
||||
return (error);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if __FreeBSD_version >= 501000
|
||||
static int
|
||||
iplpoll(struct cdev *dev, int events, struct thread *td)
|
||||
{
|
||||
u_int xmin = GET_MINOR(dev);
|
||||
int revents;
|
||||
|
||||
if (xmin < 0 || xmin > IPL_LOGMAX)
|
||||
return 0;
|
||||
|
||||
revents = 0;
|
||||
|
||||
switch (xmin)
|
||||
{
|
||||
case IPL_LOGIPF :
|
||||
case IPL_LOGNAT :
|
||||
case IPL_LOGSTATE :
|
||||
#ifdef IPFILTER_LOG
|
||||
if ((events & (POLLIN | POLLRDNORM)) && ipflog_canread(xmin))
|
||||
revents |= events & (POLLIN | POLLRDNORM);
|
||||
#endif
|
||||
break;
|
||||
case IPL_LOGAUTH :
|
||||
if ((events & (POLLIN | POLLRDNORM)) && fr_auth_waiting())
|
||||
revents |= events & (POLLIN | POLLRDNORM);
|
||||
break;
|
||||
case IPL_LOGSYNC :
|
||||
#ifdef IPFILTER_SYNC
|
||||
if ((events & (POLLIN | POLLRDNORM)) && ipfsync_canread())
|
||||
revents |= events & (POLLIN | POLLRDNORM);
|
||||
if ((events & (POLLOUT | POLLWRNORM)) && ipfsync_canwrite())
|
||||
revents |= events & (POLLOUT | POLLWRNORM);
|
||||
#endif
|
||||
break;
|
||||
case IPL_LOGSCAN :
|
||||
case IPL_LOGLOOKUP :
|
||||
default :
|
||||
break;
|
||||
}
|
||||
|
||||
if ((revents == 0) && ((events & (POLLIN|POLLRDNORM)) != 0))
|
||||
selrecord(td, &ipfselwait[xmin]);
|
||||
|
||||
return revents;
|
||||
}
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user