File Index
Files and directories
Sign in
FILE

nf_flow_table_inet.c

File preview with syntax highlighting.

linux-6.19.14/net/netfilter/nf_flow_table_inet.c C
  1// SPDX-License-Identifier: GPL-2.0-only
  2#include <linux/kernel.h>
  3#include <linux/init.h>
  4#include <linux/module.h>
  5#include <linux/netfilter.h>
  6#include <linux/rhashtable.h>
  7#include <net/netfilter/nf_flow_table.h>
  8#include <net/netfilter/nf_tables.h>
  9#include <linux/if_vlan.h>
 10
 11static unsigned int
 12nf_flow_offload_inet_hook(void *priv, struct sk_buff *skb,
 13			  const struct nf_hook_state *state)
 14{
 15	struct vlan_ethhdr *veth;
 16	__be16 proto;
 17
 18	switch (skb->protocol) {
 19	case htons(ETH_P_8021Q):
 20		if (!pskb_may_pull(skb, skb_mac_offset(skb) + sizeof(*veth)))
 21			return NF_ACCEPT;
 22
 23		veth = (struct vlan_ethhdr *)skb_mac_header(skb);
 24		proto = veth->h_vlan_encapsulated_proto;
 25		break;
 26	case htons(ETH_P_PPP_SES):
 27		if (!nf_flow_pppoe_proto(skb, &proto))
 28			return NF_ACCEPT;
 29		break;
 30	default:
 31		proto = skb->protocol;
 32		break;
 33	}
 34
 35	switch (proto) {
 36	case htons(ETH_P_IP):
 37		return nf_flow_offload_ip_hook(priv, skb, state);
 38	case htons(ETH_P_IPV6):
 39		return nf_flow_offload_ipv6_hook(priv, skb, state);
 40	}
 41
 42	return NF_ACCEPT;
 43}
 44
 45static int nf_flow_rule_route_inet(struct net *net,
 46				   struct flow_offload *flow,
 47				   enum flow_offload_tuple_dir dir,
 48				   struct nf_flow_rule *flow_rule)
 49{
 50	const struct flow_offload_tuple *flow_tuple = &flow->tuplehash[dir].tuple;
 51	int err;
 52
 53	switch (flow_tuple->l3proto) {
 54	case NFPROTO_IPV4:
 55		err = nf_flow_rule_route_ipv4(net, flow, dir, flow_rule);
 56		break;
 57	case NFPROTO_IPV6:
 58		err = nf_flow_rule_route_ipv6(net, flow, dir, flow_rule);
 59		break;
 60	default:
 61		err = -1;
 62		break;
 63	}
 64
 65	return err;
 66}
 67
 68static struct nf_flowtable_type flowtable_inet = {
 69	.family		= NFPROTO_INET,
 70	.init		= nf_flow_table_init,
 71	.setup		= nf_flow_table_offload_setup,
 72	.action		= nf_flow_rule_route_inet,
 73	.free		= nf_flow_table_free,
 74	.hook		= nf_flow_offload_inet_hook,
 75	.owner		= THIS_MODULE,
 76};
 77
 78static struct nf_flowtable_type flowtable_ipv4 = {
 79	.family		= NFPROTO_IPV4,
 80	.init		= nf_flow_table_init,
 81	.setup		= nf_flow_table_offload_setup,
 82	.action		= nf_flow_rule_route_ipv4,
 83	.free		= nf_flow_table_free,
 84	.hook		= nf_flow_offload_ip_hook,
 85	.owner		= THIS_MODULE,
 86};
 87
 88static struct nf_flowtable_type flowtable_ipv6 = {
 89	.family		= NFPROTO_IPV6,
 90	.init		= nf_flow_table_init,
 91	.setup		= nf_flow_table_offload_setup,
 92	.action		= nf_flow_rule_route_ipv6,
 93	.free		= nf_flow_table_free,
 94	.hook		= nf_flow_offload_ipv6_hook,
 95	.owner		= THIS_MODULE,
 96};
 97
 98static int __init nf_flow_inet_module_init(void)
 99{
100	nft_register_flowtable_type(&flowtable_ipv4);
101	nft_register_flowtable_type(&flowtable_ipv6);
102	nft_register_flowtable_type(&flowtable_inet);
103
104	return 0;
105}
106
107static void __exit nf_flow_inet_module_exit(void)
108{
109	nft_unregister_flowtable_type(&flowtable_inet);
110	nft_unregister_flowtable_type(&flowtable_ipv6);
111	nft_unregister_flowtable_type(&flowtable_ipv4);
112}
113
114module_init(nf_flow_inet_module_init);
115module_exit(nf_flow_inet_module_exit);
116
117MODULE_LICENSE("GPL");
118MODULE_AUTHOR("Pablo Neira Ayuso <pablo@netfilter.org>");
119MODULE_ALIAS_NF_FLOWTABLE(AF_INET);
120MODULE_ALIAS_NF_FLOWTABLE(AF_INET6);
121MODULE_ALIAS_NF_FLOWTABLE(1); /* NFPROTO_INET */
122MODULE_DESCRIPTION("Netfilter flow table mixed IPv4/IPv6 module");
~/ Read-only file preview.