On Mon, Jan 07, 2002 at 04:45:59PM -0500, Lennert Buytenhek wrote:
> > > > Any function that attaches to a netfilter hook after the passthrough
> > > > function might as well attach before the passthrough function:
> > > > - if the function does stuff for ip packets it gets useless if it
> > attaches
> > > > after the passthrough function because passthrough steals those packets.
> > >
> > > *That* is the bug. We should definitely call NF_HOOK_THRESH after the
> > > passthrough functions.
> >
> > Isn't NF_HOOK_THRESH called _inside_ the br_nf_local_out() function of
> > 'passthrough'? I don't think that's a bug.
>
> No, it isn't. I'm afraid I failed to make myself clear here. The bug is
> that we don't give the packet back to the PF_BRIDGE/* hooks, causing the
> oddity that prio>0 causes your hook not to be called. Just handing
> the packet to okfn() is wrong.
How does this look?
diff -u -r1.31 br_netfilter.c
--- br_netfilter.c 2002/01/08 12:51:33 1.31
+++ br_netfilter.c 2002/01/08 13:09:46
@@ -118,7 +118,8 @@
}
skb->dev = skb->physindev;
- br_handle_frame_finish(skb);
+ NF_HOOK_THRESH(PF_BRIDGE, NF_BR_PRE_ROUTING, skb, skb->dev, NULL,
+ br_handle_frame_finish, 1);
return 0;
}
@@ -194,6 +195,14 @@
/* PF_BRIDGE/FORWARD *************************************************/
+static int br_nf_forward_finish(struct sk_buff *skb)
+{
+ NF_HOOK_THRESH(PF_BRIDGE, NF_BR_FORWARD, skb, skb->physindev,
+ skb->dev, br_forward_finish, 1);
+
+ return 0;
+}
+
static unsigned int br_nf_forward(unsigned int hook, struct sk_buff **pskb, const
struct net_device *in, const struct net_device *out, int (*okfn)(struct sk_buff *))
{
struct sk_buff *skb = *pskb;
@@ -203,18 +212,35 @@
skb->physoutdev = skb->dev;
NF_HOOK(PF_INET, NF_IP_FORWARD, skb, bridge_parent(skb->physindev),
- bridge_parent(skb->dev), br_forward_finish);
+ bridge_parent(skb->dev), br_nf_forward_finish);
return NF_STOLEN;
}
/* PF_BRIDGE/LOCAL_OUT ***********************************************/
+static int br_nf_local_out_finish_forward(struct sk_buff *skb)
+{
+ NF_HOOK_THRESH(PF_BRIDGE, NF_BR_FORWARD, skb, skb->physindev,
+ skb->dev, br_forward_finish, 1);
+
+ return 0;
+}
+
+static int br_nf_local_out_finish(struct sk_buff *skb)
+{
+ NF_HOOK_THRESH(PF_BRIDGE, NF_BR_LOCAL_OUT, skb, NULL, skb->dev,
+ br_forward_finish, 1);
+
+ return 0;
+}
+
static unsigned int br_nf_local_out(unsigned int hook, struct sk_buff **pskb, const
struct net_device *in, const struct net_device *out, int (*okfn)(struct sk_buff *))
{
int hookno;
struct net_device *realindev;
struct sk_buff *skb = *pskb;
+ void (*okfn)(struct sk_buff *);
if (skb->mac.ethernet->h_proto != __constant_htons(ETH_P_IP))
return NF_ACCEPT;
@@ -228,14 +254,16 @@
skb->physoutdev = skb->dev;
hookno = NF_IP_LOCAL_OUT;
+ okfn = br_nf_local_out_finish;
if ((realindev = skb->physindev) != NULL) {
hookno = NF_IP_FORWARD;
+ okfn = br_nf_local_out_finish_forward;
if (has_bridge_parent(realindev))
realindev = bridge_parent(realindev);
}
NF_HOOK_THRESH(PF_INET, hookno, skb, realindev,
- bridge_parent(skb->dev), br_forward_finish,
+ bridge_parent(skb->dev), okfn,
NF_IP_PRI_BRIDGE_SABOTAGE + 1);
return NF_STOLEN;
@@ -246,7 +274,8 @@
static int br_nf_post_routing_finish(struct sk_buff *skb)
{
__maybe_fixup_src_address(skb);
- br_dev_queue_push_xmit(skb);
+ NF_HOOK_THRESH(PF_BRIDGE, NF_BR_POST_ROUTING, skb, NULL,
+ bridge_parent(skb->dev), br_dev_queue_push_xmit, 1);
return 0;
}
_______________________________________________
Bridge mailing list
[EMAIL PROTECTED]
http://www.math.leidenuniv.nl/mailman/listinfo/bridge