Commit | Line | Data |
---|---|---|
1da177e4 LT |
1 | /* IPv6-specific defines for netfilter. |
2 | * (C)1998 Rusty Russell -- This code is GPL. | |
3 | * (C)1999 David Jeffery | |
b0edba2a | 4 | * this header was blatantly ripped from netfilter_ipv4.h |
1da177e4 LT |
5 | * it's amazing what adding a bunch of 6s can do =8^) |
6 | */ | |
607ca46e DH |
7 | #ifndef __LINUX_IP6_NETFILTER_H |
8 | #define __LINUX_IP6_NETFILTER_H | |
1da177e4 | 9 | |
607ca46e | 10 | #include <uapi/linux/netfilter_ipv6.h> |
3006a522 | 11 | #include <net/tcp.h> |
1da177e4 | 12 | |
44dde236 JS |
13 | /* Check for an extension */ |
14 | static inline int | |
15 | nf_ip6_ext_hdr(u8 nexthdr) | |
16 | { return (nexthdr == IPPROTO_HOPOPTS) || | |
17 | (nexthdr == IPPROTO_ROUTING) || | |
18 | (nexthdr == IPPROTO_FRAGMENT) || | |
19 | (nexthdr == IPPROTO_ESP) || | |
20 | (nexthdr == IPPROTO_AH) || | |
21 | (nexthdr == IPPROTO_NONE) || | |
22 | (nexthdr == IPPROTO_DSTOPTS); | |
23 | } | |
24 | ||
7db9a51e PNA |
25 | /* Extra routing may needed on local out, as the QUEUE target never returns |
26 | * control to the table. | |
27 | */ | |
28 | struct ip6_rt_info { | |
29 | struct in6_addr daddr; | |
30 | struct in6_addr saddr; | |
31 | u_int32_t mark; | |
32 | }; | |
33 | ||
ce388f45 | 34 | struct nf_queue_entry; |
46705b07 | 35 | struct nf_bridge_frag_data; |
ce388f45 | 36 | |
2a7851bf FW |
37 | /* |
38 | * Hook functions for ipv6 to allow xt_* modules to be built-in even | |
39 | * if IPv6 is a module. | |
40 | */ | |
41 | struct nf_ipv6_ops { | |
ac02bcf9 | 42 | #if IS_MODULE(CONFIG_IPV6) |
2a7851bf FW |
43 | int (*chk_addr)(struct net *net, const struct in6_addr *addr, |
44 | const struct net_device *dev, int strict); | |
46d6c5ae | 45 | int (*route_me_harder)(struct net *net, struct sock *sk, struct sk_buff *skb); |
96058728 FW |
46 | int (*dev_get_saddr)(struct net *net, const struct net_device *dev, |
47 | const struct in6_addr *daddr, unsigned int srcprefs, | |
48 | struct in6_addr *saddr); | |
ac02bcf9 FW |
49 | int (*route)(struct net *net, struct dst_entry **dst, struct flowi *fl, |
50 | bool strict); | |
3006a522 FFM |
51 | u32 (*cookie_init_sequence)(const struct ipv6hdr *iph, |
52 | const struct tcphdr *th, u16 *mssp); | |
53 | int (*cookie_v6_check)(const struct ipv6hdr *iph, | |
54 | const struct tcphdr *th, __u32 cookie); | |
96058728 | 55 | #endif |
ac02bcf9 FW |
56 | void (*route_input)(struct sk_buff *skb); |
57 | int (*fragment)(struct net *net, struct sock *sk, struct sk_buff *skb, | |
58 | int (*output)(struct net *, struct sock *, struct sk_buff *)); | |
59 | int (*reroute)(struct sk_buff *skb, const struct nf_queue_entry *entry); | |
764dd163 | 60 | #if IS_MODULE(CONFIG_IPV6) |
764dd163 PNA |
61 | int (*br_fragment)(struct net *net, struct sock *sk, |
62 | struct sk_buff *skb, | |
46705b07 | 63 | struct nf_bridge_frag_data *data, |
764dd163 | 64 | int (*output)(struct net *, struct sock *sk, |
46705b07 | 65 | const struct nf_bridge_frag_data *data, |
764dd163 PNA |
66 | struct sk_buff *)); |
67 | #endif | |
2a7851bf FW |
68 | }; |
69 | ||
2e4cfae2 | 70 | #ifdef CONFIG_NETFILTER |
ac02bcf9 | 71 | #include <net/addrconf.h> |
2e4cfae2 | 72 | |
2a7851bf FW |
73 | extern const struct nf_ipv6_ops __rcu *nf_ipv6_ops; |
74 | static inline const struct nf_ipv6_ops *nf_get_ipv6_ops(void) | |
75 | { | |
76 | return rcu_dereference(nf_ipv6_ops); | |
77 | } | |
78 | ||
ac02bcf9 FW |
79 | static inline int nf_ipv6_chk_addr(struct net *net, const struct in6_addr *addr, |
80 | const struct net_device *dev, int strict) | |
81 | { | |
82 | #if IS_MODULE(CONFIG_IPV6) | |
83 | const struct nf_ipv6_ops *v6_ops = nf_get_ipv6_ops(); | |
84 | ||
85 | if (!v6_ops) | |
86 | return 1; | |
87 | ||
88 | return v6_ops->chk_addr(net, addr, dev, strict); | |
43a38c3f | 89 | #elif IS_BUILTIN(CONFIG_IPV6) |
ac02bcf9 | 90 | return ipv6_chk_addr(net, addr, dev, strict); |
43a38c3f AB |
91 | #else |
92 | return 1; | |
ac02bcf9 FW |
93 | #endif |
94 | } | |
95 | ||
96 | int __nf_ip6_route(struct net *net, struct dst_entry **dst, | |
97 | struct flowi *fl, bool strict); | |
98 | ||
99 | static inline int nf_ip6_route(struct net *net, struct dst_entry **dst, | |
100 | struct flowi *fl, bool strict) | |
101 | { | |
102 | #if IS_MODULE(CONFIG_IPV6) | |
103 | const struct nf_ipv6_ops *v6ops = nf_get_ipv6_ops(); | |
104 | ||
105 | if (v6ops) | |
106 | return v6ops->route(net, dst, fl, strict); | |
107 | ||
108 | return -EHOSTUNREACH; | |
109 | #endif | |
110 | #if IS_BUILTIN(CONFIG_IPV6) | |
111 | return __nf_ip6_route(net, dst, fl, strict); | |
112 | #else | |
113 | return -EHOSTUNREACH; | |
114 | #endif | |
115 | } | |
116 | ||
c9bb6165 PNA |
117 | #include <net/netfilter/ipv6/nf_defrag_ipv6.h> |
118 | ||
764dd163 | 119 | int br_ip6_fragment(struct net *net, struct sock *sk, struct sk_buff *skb, |
46705b07 | 120 | struct nf_bridge_frag_data *data, |
764dd163 | 121 | int (*output)(struct net *, struct sock *sk, |
46705b07 | 122 | const struct nf_bridge_frag_data *data, |
764dd163 PNA |
123 | struct sk_buff *)); |
124 | ||
125 | static inline int nf_br_ip6_fragment(struct net *net, struct sock *sk, | |
126 | struct sk_buff *skb, | |
46705b07 | 127 | struct nf_bridge_frag_data *data, |
764dd163 | 128 | int (*output)(struct net *, struct sock *sk, |
46705b07 | 129 | const struct nf_bridge_frag_data *data, |
764dd163 PNA |
130 | struct sk_buff *)) |
131 | { | |
132 | #if IS_MODULE(CONFIG_IPV6) | |
133 | const struct nf_ipv6_ops *v6_ops = nf_get_ipv6_ops(); | |
134 | ||
135 | if (!v6_ops) | |
136 | return 1; | |
137 | ||
138 | return v6_ops->br_fragment(net, sk, skb, data, output); | |
43a38c3f | 139 | #elif IS_BUILTIN(CONFIG_IPV6) |
764dd163 | 140 | return br_ip6_fragment(net, sk, skb, data, output); |
43a38c3f AB |
141 | #else |
142 | return 1; | |
764dd163 PNA |
143 | #endif |
144 | } | |
145 | ||
46d6c5ae | 146 | int ip6_route_me_harder(struct net *net, struct sock *sk, struct sk_buff *skb); |
c1deb065 | 147 | |
46d6c5ae | 148 | static inline int nf_ip6_route_me_harder(struct net *net, struct sock *sk, struct sk_buff *skb) |
c1deb065 FW |
149 | { |
150 | #if IS_MODULE(CONFIG_IPV6) | |
151 | const struct nf_ipv6_ops *v6_ops = nf_get_ipv6_ops(); | |
152 | ||
153 | if (!v6_ops) | |
154 | return -EHOSTUNREACH; | |
155 | ||
46d6c5ae | 156 | return v6_ops->route_me_harder(net, sk, skb); |
43a38c3f | 157 | #elif IS_BUILTIN(CONFIG_IPV6) |
46d6c5ae | 158 | return ip6_route_me_harder(net, sk, skb); |
43a38c3f AB |
159 | #else |
160 | return -EHOSTUNREACH; | |
c1deb065 FW |
161 | #endif |
162 | } | |
163 | ||
3006a522 FFM |
164 | static inline u32 nf_ipv6_cookie_init_sequence(const struct ipv6hdr *iph, |
165 | const struct tcphdr *th, | |
166 | u16 *mssp) | |
167 | { | |
8527fa6c | 168 | #if IS_ENABLED(CONFIG_SYN_COOKIES) |
3006a522 FFM |
169 | #if IS_MODULE(CONFIG_IPV6) |
170 | const struct nf_ipv6_ops *v6_ops = nf_get_ipv6_ops(); | |
171 | ||
172 | if (v6_ops) | |
173 | return v6_ops->cookie_init_sequence(iph, th, mssp); | |
8527fa6c | 174 | #elif IS_BUILTIN(CONFIG_IPV6) |
3006a522 FFM |
175 | return __cookie_v6_init_sequence(iph, th, mssp); |
176 | #endif | |
8527fa6c AB |
177 | #endif |
178 | return 0; | |
3006a522 FFM |
179 | } |
180 | ||
181 | static inline int nf_cookie_v6_check(const struct ipv6hdr *iph, | |
182 | const struct tcphdr *th, __u32 cookie) | |
183 | { | |
8527fa6c | 184 | #if IS_ENABLED(CONFIG_SYN_COOKIES) |
3006a522 FFM |
185 | #if IS_MODULE(CONFIG_IPV6) |
186 | const struct nf_ipv6_ops *v6_ops = nf_get_ipv6_ops(); | |
187 | ||
188 | if (v6_ops) | |
189 | return v6_ops->cookie_v6_check(iph, th, cookie); | |
8527fa6c | 190 | #elif IS_BUILTIN(CONFIG_IPV6) |
3006a522 FFM |
191 | return __cookie_v6_check(iph, th, cookie); |
192 | #endif | |
8527fa6c AB |
193 | #endif |
194 | return 0; | |
3006a522 FFM |
195 | } |
196 | ||
ac02bcf9 FW |
197 | __sum16 nf_ip6_checksum(struct sk_buff *skb, unsigned int hook, |
198 | unsigned int dataoff, u_int8_t protocol); | |
199 | ||
28e144cf XL |
200 | int nf_ip6_check_hbh_len(struct sk_buff *skb, u32 *plen); |
201 | ||
ac02bcf9 FW |
202 | int ipv6_netfilter_init(void); |
203 | void ipv6_netfilter_fini(void); | |
204 | ||
bb94aa16 PM |
205 | #else /* CONFIG_NETFILTER */ |
206 | static inline int ipv6_netfilter_init(void) { return 0; } | |
207 | static inline void ipv6_netfilter_fini(void) { return; } | |
2e4cfae2 | 208 | static inline const struct nf_ipv6_ops *nf_get_ipv6_ops(void) { return NULL; } |
bb94aa16 | 209 | #endif /* CONFIG_NETFILTER */ |
2cc7d573 | 210 | |
1da177e4 | 211 | #endif /*__LINUX_IP6_NETFILTER_H*/ |