Branch data Line data Source code
1 : : #ifndef __LINUX_NETFILTER_H
2 : : #define __LINUX_NETFILTER_H
3 : :
4 : : #include <linux/init.h>
5 : : #include <linux/skbuff.h>
6 : : #include <linux/net.h>
7 : : #include <linux/if.h>
8 : : #include <linux/in.h>
9 : : #include <linux/in6.h>
10 : : #include <linux/wait.h>
11 : : #include <linux/list.h>
12 : : #include <uapi/linux/netfilter.h>
13 : : #ifdef CONFIG_NETFILTER
14 : : static inline int NF_DROP_GETERR(int verdict)
15 : : {
16 : 0 : return -(verdict >> NF_VERDICT_QBITS);
17 : : }
18 : :
19 : : static inline int nf_inet_addr_cmp(const union nf_inet_addr *a1,
20 : : const union nf_inet_addr *a2)
21 : : {
22 : : return a1->all[0] == a2->all[0] &&
23 : : a1->all[1] == a2->all[1] &&
24 : : a1->all[2] == a2->all[2] &&
25 : : a1->all[3] == a2->all[3];
26 : : }
27 : :
28 : : static inline void nf_inet_addr_mask(const union nf_inet_addr *a1,
29 : : union nf_inet_addr *result,
30 : : const union nf_inet_addr *mask)
31 : : {
32 : : result->all[0] = a1->all[0] & mask->all[0];
33 : : result->all[1] = a1->all[1] & mask->all[1];
34 : : result->all[2] = a1->all[2] & mask->all[2];
35 : : result->all[3] = a1->all[3] & mask->all[3];
36 : : }
37 : :
38 : : int netfilter_init(void);
39 : :
40 : : /* Largest hook number + 1 */
41 : : #define NF_MAX_HOOKS 8
42 : :
43 : : struct sk_buff;
44 : :
45 : : struct nf_hook_ops;
46 : : typedef unsigned int nf_hookfn(const struct nf_hook_ops *ops,
47 : : struct sk_buff *skb,
48 : : const struct net_device *in,
49 : : const struct net_device *out,
50 : : int (*okfn)(struct sk_buff *));
51 : :
52 : : struct nf_hook_ops {
53 : : struct list_head list;
54 : :
55 : : /* User fills in from here down. */
56 : : nf_hookfn *hook;
57 : : struct module *owner;
58 : : void *priv;
59 : : u_int8_t pf;
60 : : unsigned int hooknum;
61 : : /* Hooks are ordered in ascending priority. */
62 : : int priority;
63 : : };
64 : :
65 : : struct nf_sockopt_ops {
66 : : struct list_head list;
67 : :
68 : : u_int8_t pf;
69 : :
70 : : /* Non-inclusive ranges: use 0/0/NULL to never get called. */
71 : : int set_optmin;
72 : : int set_optmax;
73 : : int (*set)(struct sock *sk, int optval, void __user *user, unsigned int len);
74 : : #ifdef CONFIG_COMPAT
75 : : int (*compat_set)(struct sock *sk, int optval,
76 : : void __user *user, unsigned int len);
77 : : #endif
78 : : int get_optmin;
79 : : int get_optmax;
80 : : int (*get)(struct sock *sk, int optval, void __user *user, int *len);
81 : : #ifdef CONFIG_COMPAT
82 : : int (*compat_get)(struct sock *sk, int optval,
83 : : void __user *user, int *len);
84 : : #endif
85 : : /* Use the module struct to lock set/get code in place */
86 : : struct module *owner;
87 : : };
88 : :
89 : : /* Function to register/unregister hook points. */
90 : : int nf_register_hook(struct nf_hook_ops *reg);
91 : : void nf_unregister_hook(struct nf_hook_ops *reg);
92 : : int nf_register_hooks(struct nf_hook_ops *reg, unsigned int n);
93 : : void nf_unregister_hooks(struct nf_hook_ops *reg, unsigned int n);
94 : :
95 : : /* Functions to register get/setsockopt ranges (non-inclusive). You
96 : : need to check permissions yourself! */
97 : : int nf_register_sockopt(struct nf_sockopt_ops *reg);
98 : : void nf_unregister_sockopt(struct nf_sockopt_ops *reg);
99 : :
100 : : extern struct list_head nf_hooks[NFPROTO_NUMPROTO][NF_MAX_HOOKS];
101 : :
102 : : #if defined(CONFIG_JUMP_LABEL)
103 : : #include <linux/static_key.h>
104 : : extern struct static_key nf_hooks_needed[NFPROTO_NUMPROTO][NF_MAX_HOOKS];
105 : : static inline bool nf_hooks_active(u_int8_t pf, unsigned int hook)
106 : : {
107 : : if (__builtin_constant_p(pf) &&
108 : : __builtin_constant_p(hook))
109 : : return static_key_false(&nf_hooks_needed[pf][hook]);
110 : :
111 : : return !list_empty(&nf_hooks[pf][hook]);
112 : : }
113 : : #else
114 : : static inline bool nf_hooks_active(u_int8_t pf, unsigned int hook)
115 : : {
116 : 0 : return !list_empty(&nf_hooks[pf][hook]);
117 : : }
118 : : #endif
119 : :
120 : : int nf_hook_slow(u_int8_t pf, unsigned int hook, struct sk_buff *skb,
121 : : struct net_device *indev, struct net_device *outdev,
122 : : int (*okfn)(struct sk_buff *), int thresh);
123 : :
124 : : /**
125 : : * nf_hook_thresh - call a netfilter hook
126 : : *
127 : : * Returns 1 if the hook has allowed the packet to pass. The function
128 : : * okfn must be invoked by the caller in this case. Any other return
129 : : * value indicates the packet has been consumed by the hook.
130 : : */
131 : : static inline int nf_hook_thresh(u_int8_t pf, unsigned int hook,
132 : : struct sk_buff *skb,
133 : : struct net_device *indev,
134 : : struct net_device *outdev,
135 : : int (*okfn)(struct sk_buff *), int thresh)
136 : : {
137 [ - + ][ - + ]: 113246 : if (nf_hooks_active(pf, hook))
[ # # ]
[ # # - + ]
[ - + ][ - + ]
[ # # ][ # # ]
[ # # ]
138 : 0 : return nf_hook_slow(pf, hook, skb, indev, outdev, okfn, thresh);
139 : : return 1;
140 : : }
141 : :
142 : : static inline int nf_hook(u_int8_t pf, unsigned int hook, struct sk_buff *skb,
143 : : struct net_device *indev, struct net_device *outdev,
144 : : int (*okfn)(struct sk_buff *))
145 : : {
146 : : return nf_hook_thresh(pf, hook, skb, indev, outdev, okfn, INT_MIN);
147 : : }
148 : :
149 : : /* Activate hook; either okfn or kfree_skb called, unless a hook
150 : : returns NF_STOLEN (in which case, it's up to the hook to deal with
151 : : the consequences).
152 : :
153 : : Returns -ERRNO if packet dropped. Zero means queued, stolen or
154 : : accepted.
155 : : */
156 : :
157 : : /* RR:
158 : : > I don't want nf_hook to return anything because people might forget
159 : : > about async and trust the return value to mean "packet was ok".
160 : :
161 : : AK:
162 : : Just document it clearly, then you can expect some sense from kernel
163 : : coders :)
164 : : */
165 : :
166 : : static inline int
167 : : NF_HOOK_THRESH(uint8_t pf, unsigned int hook, struct sk_buff *skb,
168 : : struct net_device *in, struct net_device *out,
169 : : int (*okfn)(struct sk_buff *), int thresh)
170 : : {
171 : : int ret = nf_hook_thresh(pf, hook, skb, in, out, okfn, thresh);
172 [ + - ][ + - ]: 44057 : if (ret == 1)
[ # # ]
173 : 44057 : ret = okfn(skb);
174 : : return ret;
175 : : }
176 : :
177 : : static inline int
178 : : NF_HOOK_COND(uint8_t pf, unsigned int hook, struct sk_buff *skb,
179 : : struct net_device *in, struct net_device *out,
180 : : int (*okfn)(struct sk_buff *), bool cond)
181 : : {
182 : : int ret;
183 : :
184 [ + - ][ + - ]: 47360 : if (!cond ||
[ # # ][ # # ]
[ # # ][ # # ]
185 : : ((ret = nf_hook_thresh(pf, hook, skb, in, out, okfn, INT_MIN)) == 1))
186 : 23680 : ret = okfn(skb);
187 : : return ret;
188 : : }
189 : :
190 : : static inline int
191 : : NF_HOOK(uint8_t pf, unsigned int hook, struct sk_buff *skb,
192 : : struct net_device *in, struct net_device *out,
193 : : int (*okfn)(struct sk_buff *))
194 : : {
195 : : return NF_HOOK_THRESH(pf, hook, skb, in, out, okfn, INT_MIN);
196 : : }
197 : :
198 : : /* Call setsockopt() */
199 : : int nf_setsockopt(struct sock *sk, u_int8_t pf, int optval, char __user *opt,
200 : : unsigned int len);
201 : : int nf_getsockopt(struct sock *sk, u_int8_t pf, int optval, char __user *opt,
202 : : int *len);
203 : : #ifdef CONFIG_COMPAT
204 : : int compat_nf_setsockopt(struct sock *sk, u_int8_t pf, int optval,
205 : : char __user *opt, unsigned int len);
206 : : int compat_nf_getsockopt(struct sock *sk, u_int8_t pf, int optval,
207 : : char __user *opt, int *len);
208 : : #endif
209 : :
210 : : /* Call this before modifying an existing packet: ensures it is
211 : : modifiable and linear to the point you care about (writable_len).
212 : : Returns true or false. */
213 : : int skb_make_writable(struct sk_buff *skb, unsigned int writable_len);
214 : :
215 : : struct flowi;
216 : : struct nf_queue_entry;
217 : :
218 : : struct nf_afinfo {
219 : : unsigned short family;
220 : : __sum16 (*checksum)(struct sk_buff *skb, unsigned int hook,
221 : : unsigned int dataoff, u_int8_t protocol);
222 : : __sum16 (*checksum_partial)(struct sk_buff *skb,
223 : : unsigned int hook,
224 : : unsigned int dataoff,
225 : : unsigned int len,
226 : : u_int8_t protocol);
227 : : int (*route)(struct net *net, struct dst_entry **dst,
228 : : struct flowi *fl, bool strict);
229 : : void (*saveroute)(const struct sk_buff *skb,
230 : : struct nf_queue_entry *entry);
231 : : int (*reroute)(struct sk_buff *skb,
232 : : const struct nf_queue_entry *entry);
233 : : int route_key_size;
234 : : };
235 : :
236 : : extern const struct nf_afinfo __rcu *nf_afinfo[NFPROTO_NUMPROTO];
237 : : static inline const struct nf_afinfo *nf_get_afinfo(unsigned short family)
238 : : {
239 : 0 : return rcu_dereference(nf_afinfo[family]);
240 : : }
241 : :
242 : : static inline __sum16
243 : : nf_checksum(struct sk_buff *skb, unsigned int hook, unsigned int dataoff,
244 : : u_int8_t protocol, unsigned short family)
245 : : {
246 : : const struct nf_afinfo *afinfo;
247 : : __sum16 csum = 0;
248 : :
249 : : rcu_read_lock();
250 : : afinfo = nf_get_afinfo(family);
251 : : if (afinfo)
252 : : csum = afinfo->checksum(skb, hook, dataoff, protocol);
253 : : rcu_read_unlock();
254 : : return csum;
255 : : }
256 : :
257 : : static inline __sum16
258 : : nf_checksum_partial(struct sk_buff *skb, unsigned int hook,
259 : : unsigned int dataoff, unsigned int len,
260 : : u_int8_t protocol, unsigned short family)
261 : : {
262 : : const struct nf_afinfo *afinfo;
263 : : __sum16 csum = 0;
264 : :
265 : : rcu_read_lock();
266 : : afinfo = nf_get_afinfo(family);
267 : : if (afinfo)
268 : : csum = afinfo->checksum_partial(skb, hook, dataoff, len,
269 : : protocol);
270 : : rcu_read_unlock();
271 : : return csum;
272 : : }
273 : :
274 : : int nf_register_afinfo(const struct nf_afinfo *afinfo);
275 : : void nf_unregister_afinfo(const struct nf_afinfo *afinfo);
276 : :
277 : : #include <net/flow.h>
278 : : extern void (*nf_nat_decode_session_hook)(struct sk_buff *, struct flowi *);
279 : :
280 : : static inline void
281 : : nf_nat_decode_session(struct sk_buff *skb, struct flowi *fl, u_int8_t family)
282 : : {
283 : : #ifdef CONFIG_NF_NAT_NEEDED
284 : : void (*decodefn)(struct sk_buff *, struct flowi *);
285 : :
286 : : rcu_read_lock();
287 : 0 : decodefn = rcu_dereference(nf_nat_decode_session_hook);
288 [ # # ]: 0 : if (decodefn)
289 : 0 : decodefn(skb, fl);
290 : : rcu_read_unlock();
291 : : #endif
292 : : }
293 : :
294 : : #else /* !CONFIG_NETFILTER */
295 : : #define NF_HOOK(pf, hook, skb, indev, outdev, okfn) (okfn)(skb)
296 : : #define NF_HOOK_COND(pf, hook, skb, indev, outdev, okfn, cond) (okfn)(skb)
297 : : static inline int nf_hook_thresh(u_int8_t pf, unsigned int hook,
298 : : struct sk_buff *skb,
299 : : struct net_device *indev,
300 : : struct net_device *outdev,
301 : : int (*okfn)(struct sk_buff *), int thresh)
302 : : {
303 : : return okfn(skb);
304 : : }
305 : : static inline int nf_hook(u_int8_t pf, unsigned int hook, struct sk_buff *skb,
306 : : struct net_device *indev, struct net_device *outdev,
307 : : int (*okfn)(struct sk_buff *))
308 : : {
309 : : return 1;
310 : : }
311 : : struct flowi;
312 : : static inline void
313 : : nf_nat_decode_session(struct sk_buff *skb, struct flowi *fl, u_int8_t family)
314 : : {
315 : : }
316 : : #endif /*CONFIG_NETFILTER*/
317 : :
318 : : #if defined(CONFIG_NF_CONNTRACK) || defined(CONFIG_NF_CONNTRACK_MODULE)
319 : : extern void (*ip_ct_attach)(struct sk_buff *, const struct sk_buff *) __rcu;
320 : : void nf_ct_attach(struct sk_buff *, const struct sk_buff *);
321 : : extern void (*nf_ct_destroy)(struct nf_conntrack *) __rcu;
322 : :
323 : : struct nf_conn;
324 : : enum ip_conntrack_info;
325 : : struct nlattr;
326 : :
327 : : struct nfq_ct_hook {
328 : : size_t (*build_size)(const struct nf_conn *ct);
329 : : int (*build)(struct sk_buff *skb, struct nf_conn *ct);
330 : : int (*parse)(const struct nlattr *attr, struct nf_conn *ct);
331 : : int (*attach_expect)(const struct nlattr *attr, struct nf_conn *ct,
332 : : u32 portid, u32 report);
333 : : void (*seq_adjust)(struct sk_buff *skb, struct nf_conn *ct,
334 : : enum ip_conntrack_info ctinfo, s32 off);
335 : : };
336 : : extern struct nfq_ct_hook __rcu *nfq_ct_hook;
337 : : #else
338 : : static inline void nf_ct_attach(struct sk_buff *new, struct sk_buff *skb) {}
339 : : #endif
340 : :
341 : : #endif /*__LINUX_NETFILTER_H*/
|