netdev
[Top] [All Lists]

[PATCH] Baby Bear: Netfilter merge patch I vs. vger

To: davem@xxxxxxxxxx
Subject: [PATCH] Baby Bear: Netfilter merge patch I vs. vger
From: Rusty Russell <rusty@xxxxxxxxxxxxxxxx>
Date: Wed, 01 Mar 2000 14:55:32 +1100
Cc: netdev@xxxxxxxxxxx
Sender: owner-netdev@xxxxxxxxxxx
This is JamesM's netfilter queing registration changes.

Working on patches II (ct pointer in skb) and III (all the netfilter
modules in official tree).

Index: include/linux/netfilter.h
===================================================================
RCS file: /cvs/linux/linux/include/linux/netfilter.h,v
retrieving revision 1.5
diff -u -r1.5 netfilter.h
--- include/linux/netfilter.h   1999/12/21 04:00:16     1.5
+++ include/linux/netfilter.h   2000/03/01 03:51:15
@@ -6,6 +6,7 @@
 #include <linux/types.h>
 #include <linux/skbuff.h>
 #include <linux/net.h>
+#include <linux/if.h>
 #include <linux/wait.h>
 #include <linux/list.h>
 #endif
@@ -39,19 +40,12 @@
                               const struct net_device *out,
                               int (*okfn)(struct sk_buff *));
 
-typedef unsigned int nf_cacheflushfn(const void *packet,
-                                    const struct net_device *in,
-                                    const struct net_device *out,
-                                    u_int32_t packetcount,
-                                    u_int32_t bytecount);
-
 struct nf_hook_ops
 {
        struct list_head list;
 
        /* User fills in from here down. */
        nf_hookfn *hook;
-       nf_cacheflushfn *flush;
        int pf;
        int hooknum;
        /* Hooks are ordered in ascending priority. */
@@ -74,6 +68,19 @@
        int (*get)(struct sock *sk, int optval, void *user, int *len);
 };
 
+/* Each queued (to userspace) skbuff has one of these. */
+struct nf_info
+{
+       /* The ops struct which sent us to userspace. */
+       struct nf_hook_ops *elem;
+       
+       /* If we're sent to userspace, this keeps housekeeping info */
+       int pf;
+       unsigned int hook;
+       struct net_device *indev, *outdev;
+       int (*okfn)(struct sk_buff *);
+};
+                                                                               
 
 /* Function to register/unregister hook points. */
 int nf_register_hook(struct nf_hook_ops *reg);
 void nf_unregister_hook(struct nf_hook_ops *reg);
@@ -85,7 +92,7 @@
 
 extern struct list_head nf_hooks[NPROTO][NF_MAX_HOOKS];
 
-/* Activate hook/flush; either okfn or kfree_skb called, unless a hook
+/* Activate hook; either okfn or kfree_skb called, unless a hook
    returns NF_STOLEN (in which case, it's up to the hook to deal with
    the consequences).
 
@@ -117,47 +124,20 @@
                 struct net_device *indev, struct net_device *outdev,
                 int (*okfn)(struct sk_buff *));
 
-void nf_cacheflush(int pf, unsigned int hook, const void *packet,
-                  const struct net_device *indev, const struct net_device 
*outdev,
-                  __u32 packetcount, __u32 bytecount);
-
 /* Call setsockopt() */
 int nf_setsockopt(struct sock *sk, int pf, int optval, char *opt, 
                  int len);
 int nf_getsockopt(struct sock *sk, int pf, int optval, char *opt,
                  int *len);
-
-struct nf_wakeme
-{
-       wait_queue_head_t sleep;
-       struct sk_buff_head skbq;
-};
-
-/* For netfilter device. */
-struct nf_interest
-{
-       struct list_head list;
-
-       int pf;
-       /* Bitmask of hook numbers to match (1 << hooknum). */
-       unsigned int hookmask;
-       /* If non-zero, only catch packets with this mark. */
-       unsigned int mark;
-       /* If non-zero, only catch packets of this reason. */
-       unsigned int reason;
-
-       struct nf_wakeme *wake;
-};
 
-/* For asynchronous packet handling. */
-extern void nf_register_interest(struct nf_interest *interest);
-extern void nf_unregister_interest(struct nf_interest *interest);
-extern void nf_getinfo(const struct sk_buff *skb,
-                      struct net_device **indev,
-                      struct net_device **outdev,
-                      unsigned long *mark);
+/* Packet queuing */
+typedef int (*nf_queue_outfn_t)(struct sk_buff *skb, 
+                                struct nf_info *info, void *data);
+extern int nf_register_queue_handler(int pf, 
+                                     nf_queue_outfn_t outfn, void *data);
+extern int nf_unregister_queue_handler(int pf);
 extern void nf_reinject(struct sk_buff *skb,
-                       unsigned long mark,
+                       struct nf_info *info,
                        unsigned int verdict);
 
 #ifdef CONFIG_NETFILTER_DEBUG
Index: include/linux/netfilter_ipv4.h
===================================================================
RCS file: /cvs/linux/linux/include/linux/netfilter_ipv4.h,v
retrieving revision 1.4
diff -u -r1.4 netfilter_ipv4.h
--- include/linux/netfilter_ipv4.h      1999/11/23 05:44:08     1.4
+++ include/linux/netfilter_ipv4.h      2000/03/01 03:51:16
@@ -51,7 +51,6 @@
 
 #ifdef CONFIG_NETFILTER_DEBUG
 #ifdef __KERNEL__
-void debug_print_hooks_ip(unsigned int nf_debug);
 void nf_debug_ip_local_deliver(struct sk_buff *skb);
 void nf_debug_ip_loopback_xmit(struct sk_buff *newskb);
 void nf_debug_ip_finish_output2(struct sk_buff *skb);
Index: net/netsyms.c
===================================================================
RCS file: /cvs/linux/linux/net/netsyms.c,v
retrieving revision 1.139
diff -u -r1.139 netsyms.c
--- net/netsyms.c       2000/02/27 19:41:08     1.139
+++ net/netsyms.c       2000/03/01 03:51:17
@@ -581,10 +581,9 @@
 EXPORT_SYMBOL(nf_unregister_hook);
 EXPORT_SYMBOL(nf_register_sockopt);
 EXPORT_SYMBOL(nf_unregister_sockopt);
-EXPORT_SYMBOL(nf_getinfo);
 EXPORT_SYMBOL(nf_reinject);
-EXPORT_SYMBOL(nf_register_interest);
-EXPORT_SYMBOL(nf_unregister_interest);
+EXPORT_SYMBOL(nf_register_queue_handler);
+EXPORT_SYMBOL(nf_unregister_queue_handler);
 EXPORT_SYMBOL(nf_hook_slow);
 EXPORT_SYMBOL(nf_hooks);
 #endif
Index: net/core/netfilter.c
===================================================================
RCS file: /cvs/linux/linux/net/core/netfilter.c,v
retrieving revision 1.7
diff -u -r1.7 netfilter.c
--- net/core/netfilter.c        1999/12/21 04:04:58     1.7
+++ net/core/netfilter.c        2000/03/01 03:51:17
@@ -5,6 +5,8 @@
  * way.
  *
  * Rusty Russell (C)1998 -- This code is GPL.
+ *
+ * February 2000: Modified by James Morris to have 1 queue per protocol.
  */
 #include <linux/config.h>
 #include <linux/netfilter.h>
@@ -16,7 +18,7 @@
 #include <linux/interrupt.h>
 #include <linux/if.h>
 #include <linux/netdevice.h>
-#include <linux/spinlock.h>
+#include <linux/brlock.h>
 
 #define __KERNEL_SYSCALLS__
 #include <linux/unistd.h>
@@ -32,41 +34,31 @@
 #define NFDEBUG(format, args...)
 #endif
 
-/* Each queued (to userspace) skbuff has one of these. */
-struct nf_info
-{
-       /* The ops struct which sent us to userspace. */
-       struct nf_hook_ops *elem;
-
-       /* If we're sent to userspace, this keeps housekeeping info */
-       int pf;
-       unsigned long mark;
-       unsigned int hook;
-       struct net_device *indev, *outdev;
-       int (*okfn)(struct sk_buff *);
-};
-
-static rwlock_t nf_lock = RW_LOCK_UNLOCKED;
+/* Sockopts only registered and called from user context, so
+   BR_NETPROTO_LOCK would be overkill.  Also, [gs]etsockopt calls may
+   sleep. */
 static DECLARE_MUTEX(nf_sockopt_mutex);
 
 struct list_head nf_hooks[NPROTO][NF_MAX_HOOKS];
 static LIST_HEAD(nf_sockopts);
-static LIST_HEAD(nf_interested);
+
+/* 
+ * A queue handler may be registered for each protocol.  Each is protected by
+ * long term mutex.  The handler must provide an an outfn() to accept packets
+ * for queueing and must reinject all packets it receives, no matter what.
+ */
+static struct nf_queue_handler_t {
+       nf_queue_outfn_t outfn;
+       void *data;
+} queue_handler[NPROTO];
 
 int nf_register_hook(struct nf_hook_ops *reg)
 {
        struct list_head *i;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-       if (reg->pf<0 || reg->pf>=NPROTO || reg->hooknum >= NF_MAX_HOOKS) {
-               NFDEBUG("nf_register_hook: bad vals: pf=%i, hooknum=%u.\n",
-                       reg->pf, reg->hooknum);
-               return -EINVAL;
-       }
-#endif
        NFDEBUG("nf_register_hook: pf=%i hook=%u.\n", reg->pf, reg->hooknum);
-       
-       write_lock_bh(&nf_lock);
+
+       br_write_lock_bh(BR_NETPROTO_LOCK);
        for (i = nf_hooks[reg->pf][reg->hooknum].next; 
             i != &nf_hooks[reg->pf][reg->hooknum]; 
             i = i->next) {
@@ -74,22 +66,15 @@
                        break;
        }
        list_add(&reg->list, i->prev);
-       write_unlock_bh(&nf_lock);
+       br_write_unlock_bh(BR_NETPROTO_LOCK);
        return 0;
 }
 
 void nf_unregister_hook(struct nf_hook_ops *reg)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-       if (reg->pf<0 || reg->pf>=NPROTO || reg->hooknum >= NF_MAX_HOOKS) {
-               NFDEBUG("nf_unregister_hook: bad vals: pf=%i, hooknum=%u.\n",
-                       reg->pf, reg->hooknum);
-               return;
-       }
-#endif
-       write_lock_bh(&nf_lock);
+       br_write_lock_bh(BR_NETPROTO_LOCK);
        list_del(&reg->list);
-       write_unlock_bh(&nf_lock);
+       br_write_unlock_bh(BR_NETPROTO_LOCK);
 }
 
 /* Do exclusive ranges overlap? */
@@ -105,22 +90,6 @@
        struct list_head *i;
        int ret = 0;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-       if (reg->pf<0 || reg->pf>=NPROTO) {
-               NFDEBUG("nf_register_sockopt: bad val: pf=%i.\n", reg->pf);
-               return -EINVAL;
-       }
-       if (reg->set_optmin > reg->set_optmax) {
-               NFDEBUG("nf_register_sockopt: bad set val: min=%i max=%i.\n", 
-                       reg->set_optmin, reg->set_optmax);
-               return -EINVAL;
-       }
-       if (reg->get_optmin > reg->get_optmax) {
-               NFDEBUG("nf_register_sockopt: bad get val: min=%i max=%i.\n", 
-                       reg->get_optmin, reg->get_optmax);
-               return -EINVAL;
-       }
-#endif
        if (down_interruptible(&nf_sockopt_mutex) != 0)
                return -EINTR;
 
@@ -149,12 +118,6 @@
 
 void nf_unregister_sockopt(struct nf_sockopt_ops *reg)
 {
-#ifdef CONFIG_NETFILTER_DEBUG
-       if (reg->pf<0 || reg->pf>=NPROTO) {
-               NFDEBUG("nf_register_sockopt: bad val: pf=%i.\n", reg->pf);
-               return;
-       }
-#endif
        /* No point being interruptible: we're probably in cleanup_module() */
        down(&nf_sockopt_mutex);
        list_del(&reg->list);
@@ -167,6 +130,33 @@
 #include <net/tcp.h>
 #include <linux/netfilter_ipv4.h>
 
+static void debug_print_hooks_ip(unsigned int nf_debug)
+{
+       if (nf_debug & (1 << NF_IP_PRE_ROUTING)) {
+               printk("PRE_ROUTING ");
+               nf_debug ^= (1 << NF_IP_PRE_ROUTING);
+       }
+       if (nf_debug & (1 << NF_IP_LOCAL_IN)) {
+               printk("LOCAL_IN ");
+               nf_debug ^= (1 << NF_IP_LOCAL_IN);
+       }
+       if (nf_debug & (1 << NF_IP_FORWARD)) {
+               printk("FORWARD ");
+               nf_debug ^= (1 << NF_IP_FORWARD);
+       }
+       if (nf_debug & (1 << NF_IP_LOCAL_OUT)) {
+               printk("LOCAL_OUT ");
+               nf_debug ^= (1 << NF_IP_LOCAL_OUT);
+       }
+       if (nf_debug & (1 << NF_IP_POST_ROUTING)) {
+               printk("POST_ROUTING ");
+               nf_debug ^= (1 << NF_IP_POST_ROUTING);
+       }
+       if (nf_debug)
+               printk("Crap bits: 0x%04X", nf_debug);
+       printk("\n");
+}
+
 void nf_dump_skb(int pf, struct sk_buff *skb)
 {
        printk("skb: pf=%i %s dev=%s len=%u\n", 
@@ -257,7 +247,7 @@
 {
        /* If it's owned, it must have gone through the
         * NF_IP_LOCAL_OUT and NF_IP_POST_ROUTING.
-        * Otherwise, must have gone through NF_IP_RAW_INPUT,
+        * Otherwise, must have gone through
         * NF_IP_PRE_ROUTING, NF_IP_FORWARD and NF_IP_POST_ROUTING.
         */
        if (skb->sk) {
@@ -269,9 +259,6 @@
                }
        } else {
                if (skb->nf_debug != ((1 << NF_IP_PRE_ROUTING)
-#ifdef CONFIG_IP_NETFILTER_RAW_INPUT
-                                     | (1 << NF_IP_RAW_INPUT)
-#endif
                                      | (1 << NF_IP_FORWARD)
                                      | (1 << NF_IP_POST_ROUTING))) {
                        printk("ip_finish_output: bad unowned skb = %p: ",skb);
@@ -280,29 +267,8 @@
                }
        }
 }
-
-
 #endif /*CONFIG_NETFILTER_DEBUG*/
 
-void nf_cacheflush(int pf, unsigned int hook, const void *packet,
-                  const struct net_device *indev, const struct net_device 
*outdev,
-                  __u32 packetcount, __u32 bytecount)
-{
-       struct list_head *i;
-
-       read_lock_bh(&nf_lock);
-       for (i = nf_hooks[pf][hook].next; 
-            i != &nf_hooks[pf][hook]; 
-            i = i->next) {
-               if (((struct nf_hook_ops *)i)->flush)
-                       ((struct nf_hook_ops *)i)->flush(packet, indev,
-                                                        outdev,
-                                                        packetcount,
-                                                        bytecount);
-       }
-       read_unlock_bh(&nf_lock);
-}
-
 /* Call get/setsockopt() */
 static int nf_sockopt(struct sock *sk, int pf, int val, 
                      char *opt, int *len, int get)
@@ -360,15 +326,12 @@
                struct nf_hook_ops *elem = (struct nf_hook_ops *)*i;
                switch (elem->hook(hook, skb, indev, outdev, okfn)) {
                case NF_QUEUE:
-                       NFDEBUG("nf_iterate: NF_QUEUE for %p.\n", *skb);
                        return NF_QUEUE;
 
                case NF_STOLEN:
-                       NFDEBUG("nf_iterate: NF_STOLEN for %p.\n", *skb);
                        return NF_STOLEN;
 
                case NF_DROP:
-                       NFDEBUG("nf_iterate: NF_DROP for %p.\n", *skb);
                        return NF_DROP;
 
 #ifdef CONFIG_NETFILTER_DEBUG
@@ -384,6 +347,38 @@
        return NF_ACCEPT;
 }
 
+int nf_register_queue_handler(int pf, nf_queue_outfn_t outfn, void *data)
+{      
+       int ret;
+
+       br_write_lock_bh(BR_NETPROTO_LOCK);
+       if (queue_handler[pf].outfn)
+               ret = -EBUSY;
+       else {
+               queue_handler[pf].outfn = outfn;
+               queue_handler[pf].data = data;
+               ret = 0;
+       }
+       br_write_unlock_bh(BR_NETPROTO_LOCK);
+
+       return ret;
+}
+
+/* The caller must flush their queue before this */
+int nf_unregister_queue_handler(int pf)
+{
+       NFDEBUG("Unregistering Netfilter queue handler for pf=%d\n", pf);
+       br_write_lock_bh(BR_NETPROTO_LOCK);
+       queue_handler[pf].outfn = NULL;
+       queue_handler[pf].data = NULL;
+       br_write_unlock_bh(BR_NETPROTO_LOCK);
+       return 0;
+}
+
+/* 
+ * Any packet that leaves via this function must come back 
+ * through nf_reinject().
+ */
 static void nf_queue(struct sk_buff *skb, 
                     struct list_head *elem, 
                     int pf, unsigned int hook,
@@ -391,61 +386,43 @@
                     struct net_device *outdev,
                     int (*okfn)(struct sk_buff *))
 {
-       struct list_head *i;
+       int status;
+       struct nf_info *info;
 
-       struct nf_info *info = kmalloc(sizeof(*info), GFP_ATOMIC);
+       if (!queue_handler[pf].outfn) {
+               NFDEBUG("nf_queue: noone wants the packet, dropping it.\n");
+               kfree_skb(skb);
+               return;
+       }
+
+       info = kmalloc(sizeof(*info), GFP_ATOMIC);
        if (!info) {
-               NFDEBUG("nf_hook: OOM.\n");
+               if (net_ratelimit())
+                       printk(KERN_ERR "OOM queueing packet %p\n",
+                              skb);
                kfree_skb(skb);
                return;
        }
 
-       /* Can't do struct assignments with arrays in them.  Damn. */
-       info->elem = (struct nf_hook_ops *)elem;
-       info->mark = skb->nfmark;
-       info->pf = pf;
-       info->hook = hook;
-       info->okfn = okfn;
-       info->indev = indev;
-       info->outdev = outdev;
-       skb->nfmark = (unsigned long)info;
+       *info = (struct nf_info) { 
+               (struct nf_hook_ops *)elem, pf, hook, indev, outdev, okfn };
 
        /* Bump dev refs so they don't vanish while packet is out */
        if (indev) dev_hold(indev);
        if (outdev) dev_hold(outdev);
-
-       for (i = nf_interested.next; i != &nf_interested; i = i->next) {
-               struct nf_interest *recip = (struct nf_interest *)i;
 
-               if ((recip->hookmask & (1 << info->hook))
-                   && info->pf == recip->pf
-                   && (!recip->mark || info->mark == recip->mark)
-                   && (!recip->reason || skb->nfreason == recip->reason)) {
-                       /* FIXME: Andi says: use netlink.  Hmmm... --RR */
-                       if (skb_queue_len(&recip->wake->skbq) >= 100) {
-                               NFDEBUG("nf_hook: queue to long.\n");
-                               goto free_discard;
-                       }
-                       /* Hand it to userspace for collection */
-                       skb_queue_tail(&recip->wake->skbq, skb);
-                       NFDEBUG("Waking up pf=%i hook=%u mark=%lu reason=%u\n",
-                               pf, hook, skb->nfmark, skb->nfreason);
-                       wake_up_interruptible(&recip->wake->sleep);
-
-                       return;
-               }
+       status = queue_handler[pf].outfn(skb, info, queue_handler[pf].data);
+       if (status < 0) {
+               /* James M doesn't say fuck enough. */
+               if (indev) dev_put(indev);
+               if (outdev) dev_put(outdev);
+               kfree_s(info, sizeof(*info));
+               kfree_skb(skb);
+               return;
        }
-       NFDEBUG("nf_hook: noone wants the packet.\n");
-
- free_discard: 
-       if (indev) dev_put(indev);
-       if (outdev) dev_put(outdev);
-
-       kfree_s(info, sizeof(*info));
-       kfree_skb(skb);
 }
 
-/* nf_hook() doesn't have lock, so may give false positive. */
+/* We have BR_NETPROTO_LOCK here */
 int nf_hook_slow(int pf, unsigned int hook, struct sk_buff *skb,
                 struct net_device *indev,
                 struct net_device *outdev,
@@ -455,21 +432,6 @@
        unsigned int verdict;
        int ret = 0;
 
-#ifdef CONFIG_NETFILTER_DEBUG
-       if (pf < 0 || pf >= NPROTO || hook >= NF_MAX_HOOKS) {
-               NFDEBUG("nf_hook: bad vals: pf=%i, hook=%u.\n",
-                       pf, hook);
-               kfree_skb(skb);
-               return -EINVAL; /* -ECODERFUCKEDUP ?*/
-       }
-
-       if (skb->nf_debug & (1 << hook)) {
-               NFDEBUG("nf_hook: hook %i already set.\n", hook);
-               nf_dump_skb(pf, skb);
-       }
-       skb->nf_debug |= (1 << hook);
-#endif
-       read_lock_bh(&nf_lock);
        elem = &nf_hooks[pf][hook];
        verdict = nf_iterate(&nf_hooks[pf][hook], &skb, hook, indev,
                             outdev, &elem, okfn);
@@ -477,7 +439,6 @@
                NFDEBUG("nf_hook: Verdict = QUEUE.\n");
                nf_queue(skb, elem, pf, hook, indev, outdev, okfn);
        }
-       read_unlock_bh(&nf_lock);
 
        switch (verdict) {
        case NF_ACCEPT:
@@ -492,85 +453,42 @@
 
        return ret;
 }
-
-struct nf_waitinfo {
-       unsigned int verdict;
-       struct task_struct *owner;
-};
 
-/* For netfilter device. */
-void nf_register_interest(struct nf_interest *interest)
+void nf_reinject(struct sk_buff *skb, struct nf_info *info,
+                unsigned int verdict)
 {
-       /* First in, best dressed. */
-       write_lock_bh(&nf_lock);
-       list_add(&interest->list, &nf_interested);
-       write_unlock_bh(&nf_lock);
-}
-
-void nf_unregister_interest(struct nf_interest *interest)
-{
-       struct sk_buff *skb;
-
-       write_lock_bh(&nf_lock);
-       list_del(&interest->list);
-       write_unlock_bh(&nf_lock);
-
-       /* Blow away any queued skbs; this is overzealous. */
-       while ((skb = skb_dequeue(&interest->wake->skbq)) != NULL)
-               nf_reinject(skb, 0, NF_DROP);
-}
-
-void nf_getinfo(const struct sk_buff *skb, 
-               struct net_device **indev,
-               struct net_device **outdev,
-               unsigned long *mark)
-{
-       const struct nf_info *info = (const struct nf_info *)skb->nfmark;
-
-       *indev = info->indev;
-       *outdev = info->outdev;
-       *mark = info->mark;
-}
-
-void nf_reinject(struct sk_buff *skb, unsigned long mark, unsigned int verdict)
-{
-       struct nf_info *info = (struct nf_info *)skb->nfmark;
        struct list_head *elem = &info->elem->list;
        struct list_head *i;
-
-       read_lock_bh(&nf_lock);
 
+       /* We don't have BR_NETPROTO_LOCK here */
+       br_read_lock_bh(BR_NETPROTO_LOCK);
        for (i = nf_hooks[info->pf][info->hook].next; i != elem; i = i->next) {
                if (i == &nf_hooks[info->pf][info->hook]) {
                        /* The module which sent it to userspace is gone. */
+                       NFDEBUG("%s: module disappeared, dropping packet.\n",
+                                __FUNCTION__);
                        verdict = NF_DROP;
                        break;
                }
        }
 
-       /* Continue traversal iff userspace said ok, and devices still
-           exist... */
+       /* Continue traversal iff userspace said ok... */
        if (verdict == NF_ACCEPT) {
-               skb->nfmark = mark;
                verdict = nf_iterate(&nf_hooks[info->pf][info->hook],
                                     &skb, info->hook, 
                                     info->indev, info->outdev, &elem,
                                     info->okfn);
        }
 
-       if (verdict == NF_QUEUE) {
-               nf_queue(skb, elem, info->pf, info->hook, 
-                        info->indev, info->outdev, info->okfn);
-       }
-       read_unlock_bh(&nf_lock);
-
        switch (verdict) {
        case NF_ACCEPT:
-               local_bh_disable();
                info->okfn(skb);
-               local_bh_enable();
                break;
 
+       case NF_QUEUE:
+               nf_queue(skb, elem, info->pf, info->hook, 
+                        info->indev, info->outdev, info->okfn);
+
        case NF_DROP:
                kfree_skb(skb);
                break;
@@ -579,51 +497,17 @@
        /* Release those devices we held, or Alexey will kill me. */
        if (info->indev) dev_put(info->indev);
        if (info->outdev) dev_put(info->outdev);
-
+       
        kfree_s(info, sizeof(*info));
        return;
 }
 
-/* FIXME: Before cache is ever used, this must be implemented for real. */
-void nf_invalidate_cache(int pf)
-{
-}
-
-#ifdef CONFIG_NETFILTER_DEBUG
-
-void debug_print_hooks_ip(unsigned int nf_debug)
-{
-       if (nf_debug & (1 << NF_IP_PRE_ROUTING)) {
-               printk("PRE_ROUTING ");
-               nf_debug ^= (1 << NF_IP_PRE_ROUTING);
-       }
-       if (nf_debug & (1 << NF_IP_LOCAL_IN)) {
-               printk("LOCAL_IN ");
-               nf_debug ^= (1 << NF_IP_LOCAL_IN);
-       }
-       if (nf_debug & (1 << NF_IP_FORWARD)) {
-               printk("FORWARD ");
-               nf_debug ^= (1 << NF_IP_FORWARD);
-       }
-       if (nf_debug & (1 << NF_IP_LOCAL_OUT)) {
-               printk("LOCAL_OUT ");
-               nf_debug ^= (1 << NF_IP_LOCAL_OUT);
-       }
-       if (nf_debug & (1 << NF_IP_POST_ROUTING)) {
-               printk("POST_ROUTING ");
-               nf_debug ^= (1 << NF_IP_POST_ROUTING);
-       }
-       if (nf_debug)
-               printk("Crap bits: 0x%04X", nf_debug);
-       printk("\n");
-}
-#endif /* CONFIG_NETFILTER_DEBUG */
-
 void __init netfilter_init(void)
 {
        int i, h;
 
-       for (i = 0; i < NPROTO; i++)
+       for (i = 0; i < NPROTO; i++) {
                for (h = 0; h < NF_MAX_HOOKS; h++)
                        INIT_LIST_HEAD(&nf_hooks[i][h]);
+       }
 }

--
Hacking time.

<Prev in Thread] Current Thread [Next in Thread>
  • [PATCH] Baby Bear: Netfilter merge patch I vs. vger, Rusty Russell <=