bridge: ebtables: fix reception of frames DNAT-ed to bridge device/port
When trying to redirect bridged frames to the bridge device itself or a bridge port (brouting) via the dnat target then this currently fails: The ethernet destination of the frame is dnat'ed to the MAC address of the bridge device or port just fine. However, the IP code drops it in the beginning of ip_input.c/ip_rcv() as the dnat target left the skb->pkt_type as PACKET_OTHERHOST. Fixing this by resetting skb->pkt_type to an appropriate type after dnat'ing. Signed-off-by: Linus Lüssing <linus.luessing@c0d3.blue> Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
This commit is contained in:
Родитель
6bd3d19292
Коммит
cf3cb246e2
|
@ -9,6 +9,7 @@
|
|||
*/
|
||||
#include <linux/module.h>
|
||||
#include <net/sock.h>
|
||||
#include "../br_private.h"
|
||||
#include <linux/netfilter.h>
|
||||
#include <linux/netfilter/x_tables.h>
|
||||
#include <linux/netfilter_bridge/ebtables.h>
|
||||
|
@ -18,11 +19,30 @@ static unsigned int
|
|||
ebt_dnat_tg(struct sk_buff *skb, const struct xt_action_param *par)
|
||||
{
|
||||
const struct ebt_nat_info *info = par->targinfo;
|
||||
struct net_device *dev;
|
||||
|
||||
if (!skb_make_writable(skb, 0))
|
||||
return EBT_DROP;
|
||||
|
||||
ether_addr_copy(eth_hdr(skb)->h_dest, info->mac);
|
||||
|
||||
if (is_multicast_ether_addr(info->mac)) {
|
||||
if (is_broadcast_ether_addr(info->mac))
|
||||
skb->pkt_type = PACKET_BROADCAST;
|
||||
else
|
||||
skb->pkt_type = PACKET_MULTICAST;
|
||||
} else {
|
||||
if (xt_hooknum(par) != NF_BR_BROUTING)
|
||||
dev = br_port_get_rcu(xt_in(par))->br->dev;
|
||||
else
|
||||
dev = xt_in(par);
|
||||
|
||||
if (ether_addr_equal(info->mac, dev->dev_addr))
|
||||
skb->pkt_type = PACKET_HOST;
|
||||
else
|
||||
skb->pkt_type = PACKET_OTHERHOST;
|
||||
}
|
||||
|
||||
return info->target;
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче