Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src NPF checkpoint:



details:   https://anonhg.NetBSD.org/src/rev/806678d5166f
branches:  trunk
changeset: 761014:806678d5166f
user:      rmind <rmind%NetBSD.org@localhost>
date:      Tue Jan 18 20:33:45 2011 +0000

description:
NPF checkpoint:
- Add the concept of rule procedure: separate normalization, logging and
  potentially other functions from the rule structure.  Rule procedure can be
  shared amongst the rules.  Separation is both at kernel level (npf_rproc_t)
  and configuration ("procedure" + "apply").
- Fix portmap sharing for NAT policy.
- Update TCP state tracking logic.  Use TCP FSM definitions.
- Add if_byindex(), OK by matt@.  Use in logging for the lookup.
- Fix traceroute ALG and many other bugs; misc clean-up.

diffstat:

 sys/net/if.c                     |   11 +-
 sys/net/if.h                     |   10 +-
 sys/net/npf/npf.c                |    6 +-
 sys/net/npf/npf.h                |   23 +-
 sys/net/npf/npf_alg_icmp.c       |  131 +++++++++-----
 sys/net/npf/npf_ctl.c            |   96 ++++++++--
 sys/net/npf/npf_handler.c        |   48 +++--
 sys/net/npf/npf_impl.h           |   28 +-
 sys/net/npf/npf_inet.c           |   48 ++---
 sys/net/npf/npf_instr.c          |    6 +-
 sys/net/npf/npf_log.c            |   62 +++---
 sys/net/npf/npf_mbuf.c           |   16 +-
 sys/net/npf/npf_nat.c            |  102 +++++++----
 sys/net/npf/npf_ruleset.c        |   89 ++++++---
 sys/net/npf/npf_sendpkt.c        |    6 +-
 sys/net/npf/npf_session.c        |   60 ++++--
 sys/net/npf/npf_state.c          |  199 ++++++++++++++++------
 usr.sbin/npf/npfctl/npf.conf.5   |   39 +++-
 usr.sbin/npf/npfctl/npf_data.c   |  199 +++++++++++-----------
 usr.sbin/npf/npfctl/npf_parser.c |  337 +++++++++++++++++++++-----------------
 usr.sbin/npf/npfctl/npfctl.8     |   37 +++-
 usr.sbin/npf/npfctl/npfctl.c     |   50 +++--
 usr.sbin/npf/npfctl/npfctl.h     |   24 +-
 23 files changed, 984 insertions(+), 643 deletions(-)

diffs (truncated from 3531 to 300 lines):

diff -r e782e874f48c -r 806678d5166f sys/net/if.c
--- a/sys/net/if.c      Tue Jan 18 20:32:53 2011 +0000
+++ b/sys/net/if.c      Tue Jan 18 20:33:45 2011 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: if.c,v 1.249 2010/11/15 22:42:36 pooka Exp $   */
+/*     $NetBSD: if.c,v 1.250 2011/01/18 20:33:45 rmind Exp $   */
 
 /*-
  * Copyright (c) 1999, 2000, 2001, 2008 The NetBSD Foundation, Inc.
@@ -90,7 +90,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: if.c,v 1.249 2010/11/15 22:42:36 pooka Exp $");
+__KERNEL_RCSID(0, "$NetBSD: if.c,v 1.250 2011/01/18 20:33:45 rmind Exp $");
 
 #include "opt_inet.h"
 
@@ -1477,6 +1477,13 @@
        return NULL;
 }
 
+ifnet_t *
+if_byindex(u_int idx)
+{
+
+       return (idx < if_indexlim) ? ifindex2ifnet[idx] : NULL;
+}
+
 /* common */
 int
 ifioctl_common(struct ifnet *ifp, u_long cmd, void *data)
diff -r e782e874f48c -r 806678d5166f sys/net/if.h
--- a/sys/net/if.h      Tue Jan 18 20:32:53 2011 +0000
+++ b/sys/net/if.h      Tue Jan 18 20:33:45 2011 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: if.h,v 1.148 2010/11/15 22:42:36 pooka Exp $   */
+/*     $NetBSD: if.h,v 1.149 2011/01/18 20:33:45 rmind Exp $   */
 
 /*-
  * Copyright (c) 1999, 2000, 2001 The NetBSD Foundation, Inc.
@@ -206,7 +206,7 @@
  */
 TAILQ_HEAD(ifnet_head, ifnet);         /* the actual queue head */
 
-struct ifnet {                         /* and the entries */
+typedef struct ifnet {
        void    *if_softc;              /* lower-level data for this if */
        TAILQ_ENTRY(ifnet) if_list;     /* all struct ifnets are chained */
        TAILQ_HEAD(, ifaddr) if_addrlist; /* linked list of addresses per if */
@@ -296,7 +296,8 @@
                                         * same, they are the same ifnet.
                                         */
        struct sysctllog        *if_sysctl_log;
-};
+} ifnet_t;
+
 #define        if_mtu          if_data.ifi_mtu
 #define        if_type         if_data.ifi_type
 #define        if_addrlen      if_data.ifi_addrlen
@@ -897,6 +898,9 @@
 #endif /* _KERNEL */ /* XXX really ALTQ? */
 
 #ifdef _KERNEL
+
+ifnet_t *      if_byindex(u_int);
+
 /*
  * ifq sysctl support
  */
diff -r e782e874f48c -r 806678d5166f sys/net/npf/npf.c
--- a/sys/net/npf/npf.c Tue Jan 18 20:32:53 2011 +0000
+++ b/sys/net/npf/npf.c Tue Jan 18 20:33:45 2011 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: npf.c,v 1.2 2010/12/18 01:07:25 rmind Exp $    */
+/*     $NetBSD: npf.c,v 1.3 2011/01/18 20:33:45 rmind Exp $    */
 
 /*-
  * Copyright (c) 2009-2010 The NetBSD Foundation, Inc.
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: npf.c,v 1.2 2010/12/18 01:07:25 rmind Exp $");
+__KERNEL_RCSID(0, "$NetBSD: npf.c,v 1.3 2011/01/18 20:33:45 rmind Exp $");
 
 #include <sys/param.h>
 #include <sys/types.h>
@@ -250,9 +250,9 @@
 npf_core_destroy(npf_core_t *nc)
 {
 
-       npf_tableset_destroy(nc->n_tables);
        npf_ruleset_destroy(nc->n_rules);
        npf_ruleset_destroy(nc->n_nat_rules);
+       npf_tableset_destroy(nc->n_tables);
        kmem_free(nc, sizeof(npf_core_t));
 }
 
diff -r e782e874f48c -r 806678d5166f sys/net/npf/npf.h
--- a/sys/net/npf/npf.h Tue Jan 18 20:32:53 2011 +0000
+++ b/sys/net/npf/npf.h Tue Jan 18 20:33:45 2011 +0000
@@ -1,7 +1,7 @@
-/*     $NetBSD: npf.h,v 1.5 2010/12/18 01:07:25 rmind Exp $    */
+/*     $NetBSD: npf.h,v 1.6 2011/01/18 20:33:45 rmind Exp $    */
 
 /*-
- * Copyright (c) 2009-2010 The NetBSD Foundation, Inc.
+ * Copyright (c) 2009-2011 The NetBSD Foundation, Inc.
  * All rights reserved.
  *
  * This material is based upon work partially supported by The
@@ -56,6 +56,7 @@
 struct npf_rule;
 struct npf_hook;
 
+typedef struct npf_rproc       npf_rproc_t;
 typedef struct npf_ruleset     npf_ruleset_t;
 typedef struct npf_rule                npf_rule_t;
 typedef struct npf_hook                npf_hook_t;
@@ -146,7 +147,7 @@
 int            nbuf_find_tag(nbuf_t *, uint32_t, void **);
 
 /* Ruleset interface. */
-npf_rule_t *   npf_rule_alloc(prop_dictionary_t, void *, size_t);
+npf_rule_t *   npf_rule_alloc(prop_dictionary_t, npf_rproc_t *, void *, size_t);
 void           npf_rule_free(npf_rule_t *);
 void           npf_activate_rule(npf_rule_t *);
 void           npf_deactivate_rule(npf_rule_t *);
@@ -162,16 +163,17 @@
 #define        NPF_RULE_DEFAULT                0x0002
 #define        NPF_RULE_FINAL                  0x0004
 #define        NPF_RULE_KEEPSTATE              0x0008
-#define        NPF_RULE_COUNT                  0x0010
-#define        NPF_RULE_LOG                    0x0020
-#define        NPF_RULE_RETRST                 0x0040
-#define        NPF_RULE_RETICMP                0x0080
-#define        NPF_RULE_NORMALIZE              0x0100
+#define        NPF_RULE_RETRST                 0x0010
+#define        NPF_RULE_RETICMP                0x0020
 
 #define        NPF_RULE_IN                     0x10000000
 #define        NPF_RULE_OUT                    0x20000000
 #define        NPF_RULE_DIMASK                 (NPF_RULE_IN | NPF_RULE_OUT)
 
+/* Rule procedure flags. */
+#define        NPF_RPROC_LOG                   0x0001
+#define        NPF_RPROC_NORMALIZE             0x0002
+
 /* Address translation types and flags. */
 #define        NPF_NATIN                       1
 #define        NPF_NATOUT                      2
@@ -226,6 +228,11 @@
        /* Raced packets. */
        NPF_STAT_RACE_SESSION,
        NPF_STAT_RACE_NAT,
+       /* Rule procedure cases. */
+       NPF_STAT_RPROC_LOG,
+       NPF_STAT_RPROC_NORM,
+       /* Other errors. */
+       NPF_STAT_ERROR,
        /* Count (last). */
        NPF_STATS_COUNT
 } npf_stats_t;
diff -r e782e874f48c -r 806678d5166f sys/net/npf/npf_alg_icmp.c
--- a/sys/net/npf/npf_alg_icmp.c        Tue Jan 18 20:32:53 2011 +0000
+++ b/sys/net/npf/npf_alg_icmp.c        Tue Jan 18 20:33:45 2011 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: npf_alg_icmp.c,v 1.5 2010/12/18 01:07:25 rmind Exp $   */
+/*     $NetBSD: npf_alg_icmp.c,v 1.6 2011/01/18 20:33:45 rmind Exp $   */
 
 /*-
  * Copyright (c) 2010 The NetBSD Foundation, Inc.
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: npf_alg_icmp.c,v 1.5 2010/12/18 01:07:25 rmind Exp $");
+__KERNEL_RCSID(0, "$NetBSD: npf_alg_icmp.c,v 1.6 2011/01/18 20:33:45 rmind Exp $");
 
 #include <sys/param.h>
 #include <sys/kernel.h>
@@ -64,7 +64,7 @@
 #define        TR_PORT_RANGE   33484
 #define        TR_MAX_TTL      50
 
-static npf_alg_t *     alg_icmp;
+static npf_alg_t *     alg_icmp        __read_mostly;
 
 static bool            npfa_icmp_match(npf_cache_t *, nbuf_t *, void *);
 static bool            npfa_icmp_natin(npf_cache_t *, nbuf_t *, void *);
@@ -121,6 +121,11 @@
 
        KASSERT(npf_iscached(npc, NPC_IP46 | NPC_LAYER4));
 
+       /* Check for low TTL. */
+       if (ip->ip_ttl > TR_MAX_TTL) {
+               return false;
+       }
+
        if (proto == IPPROTO_TCP) {
                struct tcphdr *th = &npc->npc_l4.tcp;
                dport = ntohs(th->th_dport);
@@ -136,11 +141,6 @@
                return false;
        }
 
-       /* Check for low TTL. */
-       if (ip->ip_ttl > TR_MAX_TTL) {
-               return false;
-       }
-
        /* Associate ALG with translation entry. */
        npf_nat_t *nt = ntptr;
        npf_nat_setalg(nt, alg_icmp, 0);
@@ -205,21 +205,46 @@
        return false;
 }
 
+static void
+npfa_srcdst_invert(npf_cache_t *npc)
+{
+       const int proto = npf_cache_ipproto(npc);
+       npf_addr_t *tmp_ip;
+
+       if (proto == IPPROTO_TCP) {
+               struct tcphdr *th = &npc->npc_l4.tcp;
+               in_port_t tmp_sport = th->th_sport;
+               th->th_sport = th->th_dport;
+               th->th_dport = tmp_sport;
+
+       } else if (proto == IPPROTO_UDP) {
+               struct udphdr *uh = &npc->npc_l4.udp;
+               in_port_t tmp_sport = uh->uh_sport;
+               uh->uh_sport = uh->uh_dport;
+               uh->uh_dport = tmp_sport;
+       }
+       tmp_ip = npc->npc_srcip;
+       npc->npc_srcip = npc->npc_dstip;
+       npc->npc_dstip = tmp_ip;
+}
+
 /*
- * npfa_icmp_session: ALG session inspector, determines unique identifiers.
+ * npfa_icmp_session: ALG session inspector, returns unique identifiers.
  */
 static bool
 npfa_icmp_session(npf_cache_t *npc, nbuf_t *nbuf, void *keyptr)
 {
        npf_cache_t *key = keyptr;
+       KASSERT(key->npc_info == 0);
 
-       /* ICMP? Get unique identifiers from ICMP packet. */
+       /* IP + ICMP?  Get unique identifiers from ICMP packet. */
+       if (!npf_iscached(npc, NPC_IP4)) {
+               return false;
+       }
        if (npf_cache_ipproto(npc) != IPPROTO_ICMP) {
                return false;
        }
-       KASSERT(npf_iscached(npc, NPC_IP46));
        KASSERT(npf_iscached(npc, NPC_ICMP));
-       key->npc_info = NPC_ICMP;
 
        /* Advance to ICMP header. */
        struct ip *ip = &npc->npc_ip.v4;
@@ -242,7 +267,7 @@
                npc->npc_info |= NPC_ICMP_ID;
                ic->icmp_id = keyic->icmp_id;
 
-               /* Note: return 'false', since key is the original cache. */
+               /* Note: return False, since key is the original cache. */
                return false;
        }
 
@@ -252,6 +277,7 @@
         */
        KASSERT(npf_iscached(key, NPC_IP46));
        KASSERT(npf_iscached(key, NPC_LAYER4));
+       npfa_srcdst_invert(key);
        key->npc_ipsz = npc->npc_ipsz;
 
        return true;
@@ -264,47 +290,57 @@
 static bool
 npfa_icmp_natin(npf_cache_t *npc, nbuf_t *nbuf, void *ntptr)
 {
-       npf_cache_t enpc;
+       npf_cache_t enpc = { .npc_info = 0 };
 
-       /* XXX: Duplicated work. */
+       /* XXX: Duplicated work (done at session inspection). */
        if (!npfa_icmp_session(npc, nbuf, &enpc)) {
                return false;
        }
+       /* XXX: Restore inversion (inefficient). */
        KASSERT(npf_iscached(&enpc, NPC_IP46 | NPC_LAYER4));
-
-       const int proto = npf_cache_ipproto(&enpc);
-       void *n_ptr = nbuf_dataptr(nbuf);



Home | Main Index | Thread Index | Old Index