Skip to content

Commit

Permalink
netfilter: nft_meta: add pkttype support
Browse files Browse the repository at this point in the history
Add pkttype support for ip, ipv6 and inet families of tables.

This allows you to fetch the meta packet type based on the link layer
information. The loopback traffic is a special case, the packet type
is guessed from the network layer header.

No special handling for bridge and arp since we're not going to see
such traffic in the loopback interface.

Joint work with Alvaro Neira Ayuso <alvaroneay@gmail.com>

Signed-off-by: Alvaro Neira Ayuso <alvaroneay@gmail.com>
Signed-off-by: Ana Rey <anarey@gmail.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
  • Loading branch information
Ana Rey authored and Pablo Neira Ayuso committed Aug 24, 2014
1 parent e91ded8 commit e2a093f
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 0 deletions.
2 changes: 2 additions & 0 deletions include/uapi/linux/netfilter/nf_tables.h
Original file line number Diff line number Diff line change
Expand Up @@ -571,6 +571,7 @@ enum nft_exthdr_attributes {
* @NFT_META_L4PROTO: layer 4 protocol number
* @NFT_META_BRI_IIFNAME: packet input bridge interface name
* @NFT_META_BRI_OIFNAME: packet output bridge interface name
* @NFT_META_PKTTYPE: packet type (skb->pkt_type), special handling for loopback
*/
enum nft_meta_keys {
NFT_META_LEN,
Expand All @@ -592,6 +593,7 @@ enum nft_meta_keys {
NFT_META_L4PROTO,
NFT_META_BRI_IIFNAME,
NFT_META_BRI_OIFNAME,
NFT_META_PKTTYPE,
};

/**
Expand Down
28 changes: 28 additions & 0 deletions net/netfilter/nft_meta.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@
#include <linux/netlink.h>
#include <linux/netfilter.h>
#include <linux/netfilter/nf_tables.h>
#include <linux/in.h>
#include <linux/ip.h>
#include <linux/ipv6.h>
#include <net/dst.h>
#include <net/sock.h>
#include <net/tcp_states.h> /* for TCP_TIME_WAIT */
Expand Down Expand Up @@ -124,6 +127,30 @@ void nft_meta_get_eval(const struct nft_expr *expr,
dest->data[0] = skb->secmark;
break;
#endif
case NFT_META_PKTTYPE:
if (skb->pkt_type != PACKET_LOOPBACK) {
dest->data[0] = skb->pkt_type;
break;
}

switch (pkt->ops->pf) {
case NFPROTO_IPV4:
if (ipv4_is_multicast(ip_hdr(skb)->daddr))
dest->data[0] = PACKET_MULTICAST;
else
dest->data[0] = PACKET_BROADCAST;
break;
case NFPROTO_IPV6:
if (ipv6_hdr(skb)->daddr.s6_addr[0] == 0xFF)
dest->data[0] = PACKET_MULTICAST;
else
dest->data[0] = PACKET_BROADCAST;
break;
default:
WARN_ON(1);
goto err;
}
break;
default:
WARN_ON(1);
goto err;
Expand Down Expand Up @@ -195,6 +222,7 @@ int nft_meta_get_init(const struct nft_ctx *ctx,
#ifdef CONFIG_NETWORK_SECMARK
case NFT_META_SECMARK:
#endif
case NFT_META_PKTTYPE:
break;
default:
return -EOPNOTSUPP;
Expand Down

0 comments on commit e2a093f

Please sign in to comment.