• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  ebtables
3  *
4  *  Author:
5  *  Bart De Schuymer		<bdschuym@pandora.be>
6  *
7  *  ebtables.c,v 2.0, July, 2002
8  *
9  *  This code is stongly inspired on the iptables code which is
10  *  Copyright (C) 1999 Paul `Rusty' Russell & Michael J. Neuling
11  *
12  *  This program is free software; you can redistribute it and/or
13  *  modify it under the terms of the GNU General Public License
14  *  as published by the Free Software Foundation; either version
15  *  2 of the License, or (at your option) any later version.
16  */
17 
18 
19 #include <linux/kmod.h>
20 #include <linux/module.h>
21 #include <linux/vmalloc.h>
22 #include <linux/netfilter/x_tables.h>
23 #include <linux/netfilter_bridge/ebtables.h>
24 #include <linux/spinlock.h>
25 #include <linux/mutex.h>
26 #include <asm/uaccess.h>
27 #include <linux/smp.h>
28 #include <linux/cpumask.h>
29 #include <net/sock.h>
30 /* needed for logical [in,out]-dev filtering */
31 #include "../br_private.h"
32 
33 #define BUGPRINT(format, args...) printk("kernel msg: ebtables bug: please "\
34 					 "report to author: "format, ## args)
35 /* #define BUGPRINT(format, args...) */
36 #define MEMPRINT(format, args...) printk("kernel msg: ebtables "\
37 					 ": out of memory: "format, ## args)
38 /* #define MEMPRINT(format, args...) */
39 
40 
41 
42 /*
43  * Each cpu has its own set of counters, so there is no need for write_lock in
44  * the softirq
45  * For reading or updating the counters, the user context needs to
46  * get a write_lock
47  */
48 
49 /* The size of each set of counters is altered to get cache alignment */
50 #define SMP_ALIGN(x) (((x) + SMP_CACHE_BYTES-1) & ~(SMP_CACHE_BYTES-1))
51 #define COUNTER_OFFSET(n) (SMP_ALIGN(n * sizeof(struct ebt_counter)))
52 #define COUNTER_BASE(c, n, cpu) ((struct ebt_counter *)(((char *)c) + \
53    COUNTER_OFFSET(n) * cpu))
54 
55 
56 
57 static DEFINE_MUTEX(ebt_mutex);
58 
59 static struct xt_target ebt_standard_target = {
60 	.name       = "standard",
61 	.revision   = 0,
62 	.family     = NFPROTO_BRIDGE,
63 	.targetsize = sizeof(int),
64 };
65 
66 static inline int
ebt_do_watcher(const struct ebt_entry_watcher * w,struct sk_buff * skb,struct xt_target_param * par)67 ebt_do_watcher(const struct ebt_entry_watcher *w, struct sk_buff *skb,
68 	       struct xt_target_param *par)
69 {
70 	par->target   = w->u.watcher;
71 	par->targinfo = w->data;
72 	w->u.watcher->target(skb, par);
73 	/* watchers don't give a verdict */
74 	return 0;
75 }
76 
ebt_do_match(struct ebt_entry_match * m,const struct sk_buff * skb,struct xt_match_param * par)77 static inline int ebt_do_match (struct ebt_entry_match *m,
78    const struct sk_buff *skb, struct xt_match_param *par)
79 {
80 	par->match     = m->u.match;
81 	par->matchinfo = m->data;
82 	return m->u.match->match(skb, par) ? EBT_MATCH : EBT_NOMATCH;
83 }
84 
ebt_dev_check(char * entry,const struct net_device * device)85 static inline int ebt_dev_check(char *entry, const struct net_device *device)
86 {
87 	int i = 0;
88 	const char *devname;
89 
90 	if (*entry == '\0')
91 		return 0;
92 	if (!device)
93 		return 1;
94 	devname = device->name;
95 	/* 1 is the wildcard token */
96 	while (entry[i] != '\0' && entry[i] != 1 && entry[i] == devname[i])
97 		i++;
98 	return (devname[i] != entry[i] && entry[i] != 1);
99 }
100 
101 #define FWINV2(bool,invflg) ((bool) ^ !!(e->invflags & invflg))
102 /* process standard matches */
ebt_basic_match(struct ebt_entry * e,struct ethhdr * h,const struct net_device * in,const struct net_device * out)103 static inline int ebt_basic_match(struct ebt_entry *e, struct ethhdr *h,
104    const struct net_device *in, const struct net_device *out)
105 {
106 	int verdict, i;
107 
108 	if (e->bitmask & EBT_802_3) {
109 		if (FWINV2(ntohs(h->h_proto) >= 1536, EBT_IPROTO))
110 			return 1;
111 	} else if (!(e->bitmask & EBT_NOPROTO) &&
112 	   FWINV2(e->ethproto != h->h_proto, EBT_IPROTO))
113 		return 1;
114 
115 	if (FWINV2(ebt_dev_check(e->in, in), EBT_IIN))
116 		return 1;
117 	if (FWINV2(ebt_dev_check(e->out, out), EBT_IOUT))
118 		return 1;
119 	if ((!in || !in->br_port) ? 0 : FWINV2(ebt_dev_check(
120 	   e->logical_in, in->br_port->br->dev), EBT_ILOGICALIN))
121 		return 1;
122 	if ((!out || !out->br_port) ? 0 : FWINV2(ebt_dev_check(
123 	   e->logical_out, out->br_port->br->dev), EBT_ILOGICALOUT))
124 		return 1;
125 
126 	if (e->bitmask & EBT_SOURCEMAC) {
127 		verdict = 0;
128 		for (i = 0; i < 6; i++)
129 			verdict |= (h->h_source[i] ^ e->sourcemac[i]) &
130 			   e->sourcemsk[i];
131 		if (FWINV2(verdict != 0, EBT_ISOURCE) )
132 			return 1;
133 	}
134 	if (e->bitmask & EBT_DESTMAC) {
135 		verdict = 0;
136 		for (i = 0; i < 6; i++)
137 			verdict |= (h->h_dest[i] ^ e->destmac[i]) &
138 			   e->destmsk[i];
139 		if (FWINV2(verdict != 0, EBT_IDEST) )
140 			return 1;
141 	}
142 	return 0;
143 }
144 
145 /* Do some firewalling */
ebt_do_table(unsigned int hook,struct sk_buff * skb,const struct net_device * in,const struct net_device * out,struct ebt_table * table)146 unsigned int ebt_do_table (unsigned int hook, struct sk_buff *skb,
147    const struct net_device *in, const struct net_device *out,
148    struct ebt_table *table)
149 {
150 	int i, nentries;
151 	struct ebt_entry *point;
152 	struct ebt_counter *counter_base, *cb_base;
153 	struct ebt_entry_target *t;
154 	int verdict, sp = 0;
155 	struct ebt_chainstack *cs;
156 	struct ebt_entries *chaininfo;
157 	char *base;
158 	struct ebt_table_info *private;
159 	bool hotdrop = false;
160 	struct xt_match_param mtpar;
161 	struct xt_target_param tgpar;
162 
163 	mtpar.family  = tgpar.family = NFPROTO_BRIDGE;
164 	mtpar.in      = tgpar.in  = in;
165 	mtpar.out     = tgpar.out = out;
166 	mtpar.hotdrop = &hotdrop;
167 	tgpar.hooknum = hook;
168 
169 	read_lock_bh(&table->lock);
170 	private = table->private;
171 	cb_base = COUNTER_BASE(private->counters, private->nentries,
172 	   smp_processor_id());
173 	if (private->chainstack)
174 		cs = private->chainstack[smp_processor_id()];
175 	else
176 		cs = NULL;
177 	chaininfo = private->hook_entry[hook];
178 	nentries = private->hook_entry[hook]->nentries;
179 	point = (struct ebt_entry *)(private->hook_entry[hook]->data);
180 	counter_base = cb_base + private->hook_entry[hook]->counter_offset;
181 	/* base for chain jumps */
182 	base = private->entries;
183 	i = 0;
184 	while (i < nentries) {
185 		if (ebt_basic_match(point, eth_hdr(skb), in, out))
186 			goto letscontinue;
187 
188 		if (EBT_MATCH_ITERATE(point, ebt_do_match, skb, &mtpar) != 0)
189 			goto letscontinue;
190 		if (hotdrop) {
191 			read_unlock_bh(&table->lock);
192 			return NF_DROP;
193 		}
194 
195 		/* increase counter */
196 		(*(counter_base + i)).pcnt++;
197 		(*(counter_base + i)).bcnt += skb->len;
198 
199 		/* these should only watch: not modify, nor tell us
200 		   what to do with the packet */
201 		EBT_WATCHER_ITERATE(point, ebt_do_watcher, skb, &tgpar);
202 
203 		t = (struct ebt_entry_target *)
204 		   (((char *)point) + point->target_offset);
205 		/* standard target */
206 		if (!t->u.target->target)
207 			verdict = ((struct ebt_standard_target *)t)->verdict;
208 		else {
209 			tgpar.target   = t->u.target;
210 			tgpar.targinfo = t->data;
211 			verdict = t->u.target->target(skb, &tgpar);
212 		}
213 		if (verdict == EBT_ACCEPT) {
214 			read_unlock_bh(&table->lock);
215 			return NF_ACCEPT;
216 		}
217 		if (verdict == EBT_DROP) {
218 			read_unlock_bh(&table->lock);
219 			return NF_DROP;
220 		}
221 		if (verdict == EBT_RETURN) {
222 letsreturn:
223 #ifdef CONFIG_NETFILTER_DEBUG
224 			if (sp == 0) {
225 				BUGPRINT("RETURN on base chain");
226 				/* act like this is EBT_CONTINUE */
227 				goto letscontinue;
228 			}
229 #endif
230 			sp--;
231 			/* put all the local variables right */
232 			i = cs[sp].n;
233 			chaininfo = cs[sp].chaininfo;
234 			nentries = chaininfo->nentries;
235 			point = cs[sp].e;
236 			counter_base = cb_base +
237 			   chaininfo->counter_offset;
238 			continue;
239 		}
240 		if (verdict == EBT_CONTINUE)
241 			goto letscontinue;
242 #ifdef CONFIG_NETFILTER_DEBUG
243 		if (verdict < 0) {
244 			BUGPRINT("bogus standard verdict\n");
245 			read_unlock_bh(&table->lock);
246 			return NF_DROP;
247 		}
248 #endif
249 		/* jump to a udc */
250 		cs[sp].n = i + 1;
251 		cs[sp].chaininfo = chaininfo;
252 		cs[sp].e = (struct ebt_entry *)
253 		   (((char *)point) + point->next_offset);
254 		i = 0;
255 		chaininfo = (struct ebt_entries *) (base + verdict);
256 #ifdef CONFIG_NETFILTER_DEBUG
257 		if (chaininfo->distinguisher) {
258 			BUGPRINT("jump to non-chain\n");
259 			read_unlock_bh(&table->lock);
260 			return NF_DROP;
261 		}
262 #endif
263 		nentries = chaininfo->nentries;
264 		point = (struct ebt_entry *)chaininfo->data;
265 		counter_base = cb_base + chaininfo->counter_offset;
266 		sp++;
267 		continue;
268 letscontinue:
269 		point = (struct ebt_entry *)
270 		   (((char *)point) + point->next_offset);
271 		i++;
272 	}
273 
274 	/* I actually like this :) */
275 	if (chaininfo->policy == EBT_RETURN)
276 		goto letsreturn;
277 	if (chaininfo->policy == EBT_ACCEPT) {
278 		read_unlock_bh(&table->lock);
279 		return NF_ACCEPT;
280 	}
281 	read_unlock_bh(&table->lock);
282 	return NF_DROP;
283 }
284 
285 /* If it succeeds, returns element and locks mutex */
286 static inline void *
find_inlist_lock_noload(struct list_head * head,const char * name,int * error,struct mutex * mutex)287 find_inlist_lock_noload(struct list_head *head, const char *name, int *error,
288    struct mutex *mutex)
289 {
290 	struct {
291 		struct list_head list;
292 		char name[EBT_FUNCTION_MAXNAMELEN];
293 	} *e;
294 
295 	*error = mutex_lock_interruptible(mutex);
296 	if (*error != 0)
297 		return NULL;
298 
299 	list_for_each_entry(e, head, list) {
300 		if (strcmp(e->name, name) == 0)
301 			return e;
302 	}
303 	*error = -ENOENT;
304 	mutex_unlock(mutex);
305 	return NULL;
306 }
307 
308 static void *
find_inlist_lock(struct list_head * head,const char * name,const char * prefix,int * error,struct mutex * mutex)309 find_inlist_lock(struct list_head *head, const char *name, const char *prefix,
310    int *error, struct mutex *mutex)
311 {
312 	return try_then_request_module(
313 			find_inlist_lock_noload(head, name, error, mutex),
314 			"%s%s", prefix, name);
315 }
316 
317 static inline struct ebt_table *
find_table_lock(struct net * net,const char * name,int * error,struct mutex * mutex)318 find_table_lock(struct net *net, const char *name, int *error,
319 		struct mutex *mutex)
320 {
321 	return find_inlist_lock(&net->xt.tables[NFPROTO_BRIDGE], name,
322 				"ebtable_", error, mutex);
323 }
324 
325 static inline int
ebt_check_match(struct ebt_entry_match * m,struct xt_mtchk_param * par,unsigned int * cnt)326 ebt_check_match(struct ebt_entry_match *m, struct xt_mtchk_param *par,
327 		unsigned int *cnt)
328 {
329 	const struct ebt_entry *e = par->entryinfo;
330 	struct xt_match *match;
331 	size_t left = ((char *)e + e->watchers_offset) - (char *)m;
332 	int ret;
333 
334 	if (left < sizeof(struct ebt_entry_match) ||
335 	    left - sizeof(struct ebt_entry_match) < m->match_size)
336 		return -EINVAL;
337 
338 	match = try_then_request_module(xt_find_match(NFPROTO_BRIDGE,
339 		m->u.name, 0), "ebt_%s", m->u.name);
340 	if (IS_ERR(match))
341 		return PTR_ERR(match);
342 	if (match == NULL)
343 		return -ENOENT;
344 	m->u.match = match;
345 
346 	par->match     = match;
347 	par->matchinfo = m->data;
348 	ret = xt_check_match(par, m->match_size,
349 	      e->ethproto, e->invflags & EBT_IPROTO);
350 	if (ret < 0) {
351 		module_put(match->me);
352 		return ret;
353 	}
354 
355 	(*cnt)++;
356 	return 0;
357 }
358 
359 static inline int
ebt_check_watcher(struct ebt_entry_watcher * w,struct xt_tgchk_param * par,unsigned int * cnt)360 ebt_check_watcher(struct ebt_entry_watcher *w, struct xt_tgchk_param *par,
361 		  unsigned int *cnt)
362 {
363 	const struct ebt_entry *e = par->entryinfo;
364 	struct xt_target *watcher;
365 	size_t left = ((char *)e + e->target_offset) - (char *)w;
366 	int ret;
367 
368 	if (left < sizeof(struct ebt_entry_watcher) ||
369 	   left - sizeof(struct ebt_entry_watcher) < w->watcher_size)
370 		return -EINVAL;
371 
372 	watcher = try_then_request_module(
373 		  xt_find_target(NFPROTO_BRIDGE, w->u.name, 0),
374 		  "ebt_%s", w->u.name);
375 	if (IS_ERR(watcher))
376 		return PTR_ERR(watcher);
377 	if (watcher == NULL)
378 		return -ENOENT;
379 	w->u.watcher = watcher;
380 
381 	par->target   = watcher;
382 	par->targinfo = w->data;
383 	ret = xt_check_target(par, w->watcher_size,
384 	      e->ethproto, e->invflags & EBT_IPROTO);
385 	if (ret < 0) {
386 		module_put(watcher->me);
387 		return ret;
388 	}
389 
390 	(*cnt)++;
391 	return 0;
392 }
393 
ebt_verify_pointers(struct ebt_replace * repl,struct ebt_table_info * newinfo)394 static int ebt_verify_pointers(struct ebt_replace *repl,
395 			       struct ebt_table_info *newinfo)
396 {
397 	unsigned int limit = repl->entries_size;
398 	unsigned int valid_hooks = repl->valid_hooks;
399 	unsigned int offset = 0;
400 	int i;
401 
402 	for (i = 0; i < NF_BR_NUMHOOKS; i++)
403 		newinfo->hook_entry[i] = NULL;
404 
405 	newinfo->entries_size = repl->entries_size;
406 	newinfo->nentries = repl->nentries;
407 
408 	while (offset < limit) {
409 		size_t left = limit - offset;
410 		struct ebt_entry *e = (void *)newinfo->entries + offset;
411 
412 		if (left < sizeof(unsigned int))
413 			break;
414 
415 		for (i = 0; i < NF_BR_NUMHOOKS; i++) {
416 			if ((valid_hooks & (1 << i)) == 0)
417 				continue;
418 			if ((char __user *)repl->hook_entry[i] ==
419 			     repl->entries + offset)
420 				break;
421 		}
422 
423 		if (i != NF_BR_NUMHOOKS || !(e->bitmask & EBT_ENTRY_OR_ENTRIES)) {
424 			if (e->bitmask != 0) {
425 				/* we make userspace set this right,
426 				   so there is no misunderstanding */
427 				BUGPRINT("EBT_ENTRY_OR_ENTRIES shouldn't be set "
428 					 "in distinguisher\n");
429 				return -EINVAL;
430 			}
431 			if (i != NF_BR_NUMHOOKS)
432 				newinfo->hook_entry[i] = (struct ebt_entries *)e;
433 			if (left < sizeof(struct ebt_entries))
434 				break;
435 			offset += sizeof(struct ebt_entries);
436 		} else {
437 			if (left < sizeof(struct ebt_entry))
438 				break;
439 			if (left < e->next_offset)
440 				break;
441 			offset += e->next_offset;
442 		}
443 	}
444 	if (offset != limit) {
445 		BUGPRINT("entries_size too small\n");
446 		return -EINVAL;
447 	}
448 
449 	/* check if all valid hooks have a chain */
450 	for (i = 0; i < NF_BR_NUMHOOKS; i++) {
451 		if (!newinfo->hook_entry[i] &&
452 		   (valid_hooks & (1 << i))) {
453 			BUGPRINT("Valid hook without chain\n");
454 			return -EINVAL;
455 		}
456 	}
457 	return 0;
458 }
459 
460 /*
461  * this one is very careful, as it is the first function
462  * to parse the userspace data
463  */
464 static inline int
ebt_check_entry_size_and_hooks(struct ebt_entry * e,struct ebt_table_info * newinfo,unsigned int * n,unsigned int * cnt,unsigned int * totalcnt,unsigned int * udc_cnt)465 ebt_check_entry_size_and_hooks(struct ebt_entry *e,
466    struct ebt_table_info *newinfo,
467    unsigned int *n, unsigned int *cnt,
468    unsigned int *totalcnt, unsigned int *udc_cnt)
469 {
470 	int i;
471 
472 	for (i = 0; i < NF_BR_NUMHOOKS; i++) {
473 		if ((void *)e == (void *)newinfo->hook_entry[i])
474 			break;
475 	}
476 	/* beginning of a new chain
477 	   if i == NF_BR_NUMHOOKS it must be a user defined chain */
478 	if (i != NF_BR_NUMHOOKS || !e->bitmask) {
479 		/* this checks if the previous chain has as many entries
480 		   as it said it has */
481 		if (*n != *cnt) {
482 			BUGPRINT("nentries does not equal the nr of entries "
483 				 "in the chain\n");
484 			return -EINVAL;
485 		}
486 		if (((struct ebt_entries *)e)->policy != EBT_DROP &&
487 		   ((struct ebt_entries *)e)->policy != EBT_ACCEPT) {
488 			/* only RETURN from udc */
489 			if (i != NF_BR_NUMHOOKS ||
490 			   ((struct ebt_entries *)e)->policy != EBT_RETURN) {
491 				BUGPRINT("bad policy\n");
492 				return -EINVAL;
493 			}
494 		}
495 		if (i == NF_BR_NUMHOOKS) /* it's a user defined chain */
496 			(*udc_cnt)++;
497 		if (((struct ebt_entries *)e)->counter_offset != *totalcnt) {
498 			BUGPRINT("counter_offset != totalcnt");
499 			return -EINVAL;
500 		}
501 		*n = ((struct ebt_entries *)e)->nentries;
502 		*cnt = 0;
503 		return 0;
504 	}
505 	/* a plain old entry, heh */
506 	if (sizeof(struct ebt_entry) > e->watchers_offset ||
507 	   e->watchers_offset > e->target_offset ||
508 	   e->target_offset >= e->next_offset) {
509 		BUGPRINT("entry offsets not in right order\n");
510 		return -EINVAL;
511 	}
512 	/* this is not checked anywhere else */
513 	if (e->next_offset - e->target_offset < sizeof(struct ebt_entry_target)) {
514 		BUGPRINT("target size too small\n");
515 		return -EINVAL;
516 	}
517 	(*cnt)++;
518 	(*totalcnt)++;
519 	return 0;
520 }
521 
522 struct ebt_cl_stack
523 {
524 	struct ebt_chainstack cs;
525 	int from;
526 	unsigned int hookmask;
527 };
528 
529 /*
530  * we need these positions to check that the jumps to a different part of the
531  * entries is a jump to the beginning of a new chain.
532  */
533 static inline int
ebt_get_udc_positions(struct ebt_entry * e,struct ebt_table_info * newinfo,unsigned int * n,struct ebt_cl_stack * udc)534 ebt_get_udc_positions(struct ebt_entry *e, struct ebt_table_info *newinfo,
535    unsigned int *n, struct ebt_cl_stack *udc)
536 {
537 	int i;
538 
539 	/* we're only interested in chain starts */
540 	if (e->bitmask)
541 		return 0;
542 	for (i = 0; i < NF_BR_NUMHOOKS; i++) {
543 		if (newinfo->hook_entry[i] == (struct ebt_entries *)e)
544 			break;
545 	}
546 	/* only care about udc */
547 	if (i != NF_BR_NUMHOOKS)
548 		return 0;
549 
550 	udc[*n].cs.chaininfo = (struct ebt_entries *)e;
551 	/* these initialisations are depended on later in check_chainloops() */
552 	udc[*n].cs.n = 0;
553 	udc[*n].hookmask = 0;
554 
555 	(*n)++;
556 	return 0;
557 }
558 
559 static inline int
ebt_cleanup_match(struct ebt_entry_match * m,unsigned int * i)560 ebt_cleanup_match(struct ebt_entry_match *m, unsigned int *i)
561 {
562 	struct xt_mtdtor_param par;
563 
564 	if (i && (*i)-- == 0)
565 		return 1;
566 
567 	par.match     = m->u.match;
568 	par.matchinfo = m->data;
569 	par.family    = NFPROTO_BRIDGE;
570 	if (par.match->destroy != NULL)
571 		par.match->destroy(&par);
572 	module_put(par.match->me);
573 	return 0;
574 }
575 
576 static inline int
ebt_cleanup_watcher(struct ebt_entry_watcher * w,unsigned int * i)577 ebt_cleanup_watcher(struct ebt_entry_watcher *w, unsigned int *i)
578 {
579 	struct xt_tgdtor_param par;
580 
581 	if (i && (*i)-- == 0)
582 		return 1;
583 
584 	par.target   = w->u.watcher;
585 	par.targinfo = w->data;
586 	par.family   = NFPROTO_BRIDGE;
587 	if (par.target->destroy != NULL)
588 		par.target->destroy(&par);
589 	module_put(par.target->me);
590 	return 0;
591 }
592 
593 static inline int
ebt_cleanup_entry(struct ebt_entry * e,unsigned int * cnt)594 ebt_cleanup_entry(struct ebt_entry *e, unsigned int *cnt)
595 {
596 	struct xt_tgdtor_param par;
597 	struct ebt_entry_target *t;
598 
599 	if (e->bitmask == 0)
600 		return 0;
601 	/* we're done */
602 	if (cnt && (*cnt)-- == 0)
603 		return 1;
604 	EBT_WATCHER_ITERATE(e, ebt_cleanup_watcher, NULL);
605 	EBT_MATCH_ITERATE(e, ebt_cleanup_match, NULL);
606 	t = (struct ebt_entry_target *)(((char *)e) + e->target_offset);
607 
608 	par.target   = t->u.target;
609 	par.targinfo = t->data;
610 	par.family   = NFPROTO_BRIDGE;
611 	if (par.target->destroy != NULL)
612 		par.target->destroy(&par);
613 	module_put(par.target->me);
614 	return 0;
615 }
616 
617 static inline int
ebt_check_entry(struct ebt_entry * e,struct ebt_table_info * newinfo,const char * name,unsigned int * cnt,struct ebt_cl_stack * cl_s,unsigned int udc_cnt)618 ebt_check_entry(struct ebt_entry *e, struct ebt_table_info *newinfo,
619    const char *name, unsigned int *cnt,
620    struct ebt_cl_stack *cl_s, unsigned int udc_cnt)
621 {
622 	struct ebt_entry_target *t;
623 	struct xt_target *target;
624 	unsigned int i, j, hook = 0, hookmask = 0;
625 	size_t gap;
626 	int ret;
627 	struct xt_mtchk_param mtpar;
628 	struct xt_tgchk_param tgpar;
629 
630 	/* don't mess with the struct ebt_entries */
631 	if (e->bitmask == 0)
632 		return 0;
633 
634 	if (e->bitmask & ~EBT_F_MASK) {
635 		BUGPRINT("Unknown flag for bitmask\n");
636 		return -EINVAL;
637 	}
638 	if (e->invflags & ~EBT_INV_MASK) {
639 		BUGPRINT("Unknown flag for inv bitmask\n");
640 		return -EINVAL;
641 	}
642 	if ( (e->bitmask & EBT_NOPROTO) && (e->bitmask & EBT_802_3) ) {
643 		BUGPRINT("NOPROTO & 802_3 not allowed\n");
644 		return -EINVAL;
645 	}
646 	/* what hook do we belong to? */
647 	for (i = 0; i < NF_BR_NUMHOOKS; i++) {
648 		if (!newinfo->hook_entry[i])
649 			continue;
650 		if ((char *)newinfo->hook_entry[i] < (char *)e)
651 			hook = i;
652 		else
653 			break;
654 	}
655 	/* (1 << NF_BR_NUMHOOKS) tells the check functions the rule is on
656 	   a base chain */
657 	if (i < NF_BR_NUMHOOKS)
658 		hookmask = (1 << hook) | (1 << NF_BR_NUMHOOKS);
659 	else {
660 		for (i = 0; i < udc_cnt; i++)
661 			if ((char *)(cl_s[i].cs.chaininfo) > (char *)e)
662 				break;
663 		if (i == 0)
664 			hookmask = (1 << hook) | (1 << NF_BR_NUMHOOKS);
665 		else
666 			hookmask = cl_s[i - 1].hookmask;
667 	}
668 	i = 0;
669 
670 	mtpar.table     = tgpar.table     = name;
671 	mtpar.entryinfo = tgpar.entryinfo = e;
672 	mtpar.hook_mask = tgpar.hook_mask = hookmask;
673 	mtpar.family    = tgpar.family    = NFPROTO_BRIDGE;
674 	ret = EBT_MATCH_ITERATE(e, ebt_check_match, &mtpar, &i);
675 	if (ret != 0)
676 		goto cleanup_matches;
677 	j = 0;
678 	ret = EBT_WATCHER_ITERATE(e, ebt_check_watcher, &tgpar, &j);
679 	if (ret != 0)
680 		goto cleanup_watchers;
681 	t = (struct ebt_entry_target *)(((char *)e) + e->target_offset);
682 	gap = e->next_offset - e->target_offset;
683 
684 	target = try_then_request_module(
685 		 xt_find_target(NFPROTO_BRIDGE, t->u.name, 0),
686 		 "ebt_%s", t->u.name);
687 	if (IS_ERR(target)) {
688 		ret = PTR_ERR(target);
689 		goto cleanup_watchers;
690 	} else if (target == NULL) {
691 		ret = -ENOENT;
692 		goto cleanup_watchers;
693 	}
694 
695 	t->u.target = target;
696 	if (t->u.target == &ebt_standard_target) {
697 		if (gap < sizeof(struct ebt_standard_target)) {
698 			BUGPRINT("Standard target size too big\n");
699 			ret = -EFAULT;
700 			goto cleanup_watchers;
701 		}
702 		if (((struct ebt_standard_target *)t)->verdict <
703 		   -NUM_STANDARD_TARGETS) {
704 			BUGPRINT("Invalid standard target\n");
705 			ret = -EFAULT;
706 			goto cleanup_watchers;
707 		}
708 	} else if (t->target_size > gap - sizeof(struct ebt_entry_target)) {
709 		module_put(t->u.target->me);
710 		ret = -EFAULT;
711 		goto cleanup_watchers;
712 	}
713 
714 	tgpar.target   = target;
715 	tgpar.targinfo = t->data;
716 	ret = xt_check_target(&tgpar, t->target_size,
717 	      e->ethproto, e->invflags & EBT_IPROTO);
718 	if (ret < 0) {
719 		module_put(target->me);
720 		goto cleanup_watchers;
721 	}
722 	(*cnt)++;
723 	return 0;
724 cleanup_watchers:
725 	EBT_WATCHER_ITERATE(e, ebt_cleanup_watcher, &j);
726 cleanup_matches:
727 	EBT_MATCH_ITERATE(e, ebt_cleanup_match, &i);
728 	return ret;
729 }
730 
731 /*
732  * checks for loops and sets the hook mask for udc
733  * the hook mask for udc tells us from which base chains the udc can be
734  * accessed. This mask is a parameter to the check() functions of the extensions
735  */
check_chainloops(struct ebt_entries * chain,struct ebt_cl_stack * cl_s,unsigned int udc_cnt,unsigned int hooknr,char * base)736 static int check_chainloops(struct ebt_entries *chain, struct ebt_cl_stack *cl_s,
737    unsigned int udc_cnt, unsigned int hooknr, char *base)
738 {
739 	int i, chain_nr = -1, pos = 0, nentries = chain->nentries, verdict;
740 	struct ebt_entry *e = (struct ebt_entry *)chain->data;
741 	struct ebt_entry_target *t;
742 
743 	while (pos < nentries || chain_nr != -1) {
744 		/* end of udc, go back one 'recursion' step */
745 		if (pos == nentries) {
746 			/* put back values of the time when this chain was called */
747 			e = cl_s[chain_nr].cs.e;
748 			if (cl_s[chain_nr].from != -1)
749 				nentries =
750 				cl_s[cl_s[chain_nr].from].cs.chaininfo->nentries;
751 			else
752 				nentries = chain->nentries;
753 			pos = cl_s[chain_nr].cs.n;
754 			/* make sure we won't see a loop that isn't one */
755 			cl_s[chain_nr].cs.n = 0;
756 			chain_nr = cl_s[chain_nr].from;
757 			if (pos == nentries)
758 				continue;
759 		}
760 		t = (struct ebt_entry_target *)
761 		   (((char *)e) + e->target_offset);
762 		if (strcmp(t->u.name, EBT_STANDARD_TARGET))
763 			goto letscontinue;
764 		if (e->target_offset + sizeof(struct ebt_standard_target) >
765 		   e->next_offset) {
766 			BUGPRINT("Standard target size too big\n");
767 			return -1;
768 		}
769 		verdict = ((struct ebt_standard_target *)t)->verdict;
770 		if (verdict >= 0) { /* jump to another chain */
771 			struct ebt_entries *hlp2 =
772 			   (struct ebt_entries *)(base + verdict);
773 			for (i = 0; i < udc_cnt; i++)
774 				if (hlp2 == cl_s[i].cs.chaininfo)
775 					break;
776 			/* bad destination or loop */
777 			if (i == udc_cnt) {
778 				BUGPRINT("bad destination\n");
779 				return -1;
780 			}
781 			if (cl_s[i].cs.n) {
782 				BUGPRINT("loop\n");
783 				return -1;
784 			}
785 			if (cl_s[i].hookmask & (1 << hooknr))
786 				goto letscontinue;
787 			/* this can't be 0, so the loop test is correct */
788 			cl_s[i].cs.n = pos + 1;
789 			pos = 0;
790 			cl_s[i].cs.e = ((void *)e + e->next_offset);
791 			e = (struct ebt_entry *)(hlp2->data);
792 			nentries = hlp2->nentries;
793 			cl_s[i].from = chain_nr;
794 			chain_nr = i;
795 			/* this udc is accessible from the base chain for hooknr */
796 			cl_s[i].hookmask |= (1 << hooknr);
797 			continue;
798 		}
799 letscontinue:
800 		e = (void *)e + e->next_offset;
801 		pos++;
802 	}
803 	return 0;
804 }
805 
806 /* do the parsing of the table/chains/entries/matches/watchers/targets, heh */
translate_table(char * name,struct ebt_table_info * newinfo)807 static int translate_table(char *name, struct ebt_table_info *newinfo)
808 {
809 	unsigned int i, j, k, udc_cnt;
810 	int ret;
811 	struct ebt_cl_stack *cl_s = NULL; /* used in the checking for chain loops */
812 
813 	i = 0;
814 	while (i < NF_BR_NUMHOOKS && !newinfo->hook_entry[i])
815 		i++;
816 	if (i == NF_BR_NUMHOOKS) {
817 		BUGPRINT("No valid hooks specified\n");
818 		return -EINVAL;
819 	}
820 	if (newinfo->hook_entry[i] != (struct ebt_entries *)newinfo->entries) {
821 		BUGPRINT("Chains don't start at beginning\n");
822 		return -EINVAL;
823 	}
824 	/* make sure chains are ordered after each other in same order
825 	   as their corresponding hooks */
826 	for (j = i + 1; j < NF_BR_NUMHOOKS; j++) {
827 		if (!newinfo->hook_entry[j])
828 			continue;
829 		if (newinfo->hook_entry[j] <= newinfo->hook_entry[i]) {
830 			BUGPRINT("Hook order must be followed\n");
831 			return -EINVAL;
832 		}
833 		i = j;
834 	}
835 
836 	/* do some early checkings and initialize some things */
837 	i = 0; /* holds the expected nr. of entries for the chain */
838 	j = 0; /* holds the up to now counted entries for the chain */
839 	k = 0; /* holds the total nr. of entries, should equal
840 		  newinfo->nentries afterwards */
841 	udc_cnt = 0; /* will hold the nr. of user defined chains (udc) */
842 	ret = EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
843 	   ebt_check_entry_size_and_hooks, newinfo,
844 	   &i, &j, &k, &udc_cnt);
845 
846 	if (ret != 0)
847 		return ret;
848 
849 	if (i != j) {
850 		BUGPRINT("nentries does not equal the nr of entries in the "
851 			 "(last) chain\n");
852 		return -EINVAL;
853 	}
854 	if (k != newinfo->nentries) {
855 		BUGPRINT("Total nentries is wrong\n");
856 		return -EINVAL;
857 	}
858 
859 	/* get the location of the udc, put them in an array
860 	   while we're at it, allocate the chainstack */
861 	if (udc_cnt) {
862 		/* this will get free'd in do_replace()/ebt_register_table()
863 		   if an error occurs */
864 		newinfo->chainstack =
865 			vmalloc(nr_cpu_ids * sizeof(*(newinfo->chainstack)));
866 		if (!newinfo->chainstack)
867 			return -ENOMEM;
868 		for_each_possible_cpu(i) {
869 			newinfo->chainstack[i] =
870 			  vmalloc(udc_cnt * sizeof(*(newinfo->chainstack[0])));
871 			if (!newinfo->chainstack[i]) {
872 				while (i)
873 					vfree(newinfo->chainstack[--i]);
874 				vfree(newinfo->chainstack);
875 				newinfo->chainstack = NULL;
876 				return -ENOMEM;
877 			}
878 		}
879 
880 		cl_s = vmalloc(udc_cnt * sizeof(*cl_s));
881 		if (!cl_s)
882 			return -ENOMEM;
883 		i = 0; /* the i'th udc */
884 		EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
885 		   ebt_get_udc_positions, newinfo, &i, cl_s);
886 		/* sanity check */
887 		if (i != udc_cnt) {
888 			BUGPRINT("i != udc_cnt\n");
889 			vfree(cl_s);
890 			return -EFAULT;
891 		}
892 	}
893 
894 	/* Check for loops */
895 	for (i = 0; i < NF_BR_NUMHOOKS; i++)
896 		if (newinfo->hook_entry[i])
897 			if (check_chainloops(newinfo->hook_entry[i],
898 			   cl_s, udc_cnt, i, newinfo->entries)) {
899 				vfree(cl_s);
900 				return -EINVAL;
901 			}
902 
903 	/* we now know the following (along with E=mc²):
904 	   - the nr of entries in each chain is right
905 	   - the size of the allocated space is right
906 	   - all valid hooks have a corresponding chain
907 	   - there are no loops
908 	   - wrong data can still be on the level of a single entry
909 	   - could be there are jumps to places that are not the
910 	     beginning of a chain. This can only occur in chains that
911 	     are not accessible from any base chains, so we don't care. */
912 
913 	/* used to know what we need to clean up if something goes wrong */
914 	i = 0;
915 	ret = EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
916 	   ebt_check_entry, newinfo, name, &i, cl_s, udc_cnt);
917 	if (ret != 0) {
918 		EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
919 		   ebt_cleanup_entry, &i);
920 	}
921 	vfree(cl_s);
922 	return ret;
923 }
924 
925 /* called under write_lock */
get_counters(struct ebt_counter * oldcounters,struct ebt_counter * counters,unsigned int nentries)926 static void get_counters(struct ebt_counter *oldcounters,
927    struct ebt_counter *counters, unsigned int nentries)
928 {
929 	int i, cpu;
930 	struct ebt_counter *counter_base;
931 
932 	/* counters of cpu 0 */
933 	memcpy(counters, oldcounters,
934 	       sizeof(struct ebt_counter) * nentries);
935 
936 	/* add other counters to those of cpu 0 */
937 	for_each_possible_cpu(cpu) {
938 		if (cpu == 0)
939 			continue;
940 		counter_base = COUNTER_BASE(oldcounters, nentries, cpu);
941 		for (i = 0; i < nentries; i++) {
942 			counters[i].pcnt += counter_base[i].pcnt;
943 			counters[i].bcnt += counter_base[i].bcnt;
944 		}
945 	}
946 }
947 
948 /* replace the table */
do_replace(struct net * net,void __user * user,unsigned int len)949 static int do_replace(struct net *net, void __user *user, unsigned int len)
950 {
951 	int ret, i, countersize;
952 	struct ebt_table_info *newinfo;
953 	struct ebt_replace tmp;
954 	struct ebt_table *t;
955 	struct ebt_counter *counterstmp = NULL;
956 	/* used to be able to unlock earlier */
957 	struct ebt_table_info *table;
958 
959 	if (copy_from_user(&tmp, user, sizeof(tmp)) != 0)
960 		return -EFAULT;
961 
962 	if (len != sizeof(tmp) + tmp.entries_size) {
963 		BUGPRINT("Wrong len argument\n");
964 		return -EINVAL;
965 	}
966 
967 	if (tmp.entries_size == 0) {
968 		BUGPRINT("Entries_size never zero\n");
969 		return -EINVAL;
970 	}
971 	/* overflow check */
972 	if (tmp.nentries >= ((INT_MAX - sizeof(struct ebt_table_info)) / NR_CPUS -
973 			SMP_CACHE_BYTES) / sizeof(struct ebt_counter))
974 		return -ENOMEM;
975 	if (tmp.num_counters >= INT_MAX / sizeof(struct ebt_counter))
976 		return -ENOMEM;
977 
978 	countersize = COUNTER_OFFSET(tmp.nentries) * nr_cpu_ids;
979 	newinfo = vmalloc(sizeof(*newinfo) + countersize);
980 	if (!newinfo)
981 		return -ENOMEM;
982 
983 	if (countersize)
984 		memset(newinfo->counters, 0, countersize);
985 
986 	newinfo->entries = vmalloc(tmp.entries_size);
987 	if (!newinfo->entries) {
988 		ret = -ENOMEM;
989 		goto free_newinfo;
990 	}
991 	if (copy_from_user(
992 	   newinfo->entries, tmp.entries, tmp.entries_size) != 0) {
993 		BUGPRINT("Couldn't copy entries from userspace\n");
994 		ret = -EFAULT;
995 		goto free_entries;
996 	}
997 
998 	/* the user wants counters back
999 	   the check on the size is done later, when we have the lock */
1000 	if (tmp.num_counters) {
1001 		counterstmp = vmalloc(tmp.num_counters * sizeof(*counterstmp));
1002 		if (!counterstmp) {
1003 			ret = -ENOMEM;
1004 			goto free_entries;
1005 		}
1006 	}
1007 	else
1008 		counterstmp = NULL;
1009 
1010 	/* this can get initialized by translate_table() */
1011 	newinfo->chainstack = NULL;
1012 	ret = ebt_verify_pointers(&tmp, newinfo);
1013 	if (ret != 0)
1014 		goto free_counterstmp;
1015 
1016 	ret = translate_table(tmp.name, newinfo);
1017 
1018 	if (ret != 0)
1019 		goto free_counterstmp;
1020 
1021 	t = find_table_lock(net, tmp.name, &ret, &ebt_mutex);
1022 	if (!t) {
1023 		ret = -ENOENT;
1024 		goto free_iterate;
1025 	}
1026 
1027 	/* the table doesn't like it */
1028 	if (t->check && (ret = t->check(newinfo, tmp.valid_hooks)))
1029 		goto free_unlock;
1030 
1031 	if (tmp.num_counters && tmp.num_counters != t->private->nentries) {
1032 		BUGPRINT("Wrong nr. of counters requested\n");
1033 		ret = -EINVAL;
1034 		goto free_unlock;
1035 	}
1036 
1037 	/* we have the mutex lock, so no danger in reading this pointer */
1038 	table = t->private;
1039 	/* make sure the table can only be rmmod'ed if it contains no rules */
1040 	if (!table->nentries && newinfo->nentries && !try_module_get(t->me)) {
1041 		ret = -ENOENT;
1042 		goto free_unlock;
1043 	} else if (table->nentries && !newinfo->nentries)
1044 		module_put(t->me);
1045 	/* we need an atomic snapshot of the counters */
1046 	write_lock_bh(&t->lock);
1047 	if (tmp.num_counters)
1048 		get_counters(t->private->counters, counterstmp,
1049 		   t->private->nentries);
1050 
1051 	t->private = newinfo;
1052 	write_unlock_bh(&t->lock);
1053 	mutex_unlock(&ebt_mutex);
1054 	/* so, a user can change the chains while having messed up her counter
1055 	   allocation. Only reason why this is done is because this way the lock
1056 	   is held only once, while this doesn't bring the kernel into a
1057 	   dangerous state. */
1058 	if (tmp.num_counters &&
1059 	   copy_to_user(tmp.counters, counterstmp,
1060 	   tmp.num_counters * sizeof(struct ebt_counter))) {
1061 		BUGPRINT("Couldn't copy counters to userspace\n");
1062 		ret = -EFAULT;
1063 	}
1064 	else
1065 		ret = 0;
1066 
1067 	/* decrease module count and free resources */
1068 	EBT_ENTRY_ITERATE(table->entries, table->entries_size,
1069 	   ebt_cleanup_entry, NULL);
1070 
1071 	vfree(table->entries);
1072 	if (table->chainstack) {
1073 		for_each_possible_cpu(i)
1074 			vfree(table->chainstack[i]);
1075 		vfree(table->chainstack);
1076 	}
1077 	vfree(table);
1078 
1079 	vfree(counterstmp);
1080 	return ret;
1081 
1082 free_unlock:
1083 	mutex_unlock(&ebt_mutex);
1084 free_iterate:
1085 	EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
1086 	   ebt_cleanup_entry, NULL);
1087 free_counterstmp:
1088 	vfree(counterstmp);
1089 	/* can be initialized in translate_table() */
1090 	if (newinfo->chainstack) {
1091 		for_each_possible_cpu(i)
1092 			vfree(newinfo->chainstack[i]);
1093 		vfree(newinfo->chainstack);
1094 	}
1095 free_entries:
1096 	vfree(newinfo->entries);
1097 free_newinfo:
1098 	vfree(newinfo);
1099 	return ret;
1100 }
1101 
ebt_register_table(struct net * net,struct ebt_table * table)1102 struct ebt_table *ebt_register_table(struct net *net, struct ebt_table *table)
1103 {
1104 	struct ebt_table_info *newinfo;
1105 	struct ebt_table *t;
1106 	struct ebt_replace_kernel *repl;
1107 	int ret, i, countersize;
1108 	void *p;
1109 
1110 	if (!table || !(repl = table->table) || !repl->entries ||
1111 	    repl->entries_size == 0 ||
1112 	    repl->counters || table->private) {
1113 		BUGPRINT("Bad table data for ebt_register_table!!!\n");
1114 		return ERR_PTR(-EINVAL);
1115 	}
1116 
1117 	/* Don't add one table to multiple lists. */
1118 	table = kmemdup(table, sizeof(struct ebt_table), GFP_KERNEL);
1119 	if (!table) {
1120 		ret = -ENOMEM;
1121 		goto out;
1122 	}
1123 
1124 	countersize = COUNTER_OFFSET(repl->nentries) * nr_cpu_ids;
1125 	newinfo = vmalloc(sizeof(*newinfo) + countersize);
1126 	ret = -ENOMEM;
1127 	if (!newinfo)
1128 		goto free_table;
1129 
1130 	p = vmalloc(repl->entries_size);
1131 	if (!p)
1132 		goto free_newinfo;
1133 
1134 	memcpy(p, repl->entries, repl->entries_size);
1135 	newinfo->entries = p;
1136 
1137 	newinfo->entries_size = repl->entries_size;
1138 	newinfo->nentries = repl->nentries;
1139 
1140 	if (countersize)
1141 		memset(newinfo->counters, 0, countersize);
1142 
1143 	/* fill in newinfo and parse the entries */
1144 	newinfo->chainstack = NULL;
1145 	for (i = 0; i < NF_BR_NUMHOOKS; i++) {
1146 		if ((repl->valid_hooks & (1 << i)) == 0)
1147 			newinfo->hook_entry[i] = NULL;
1148 		else
1149 			newinfo->hook_entry[i] = p +
1150 				((char *)repl->hook_entry[i] - repl->entries);
1151 	}
1152 	ret = translate_table(repl->name, newinfo);
1153 	if (ret != 0) {
1154 		BUGPRINT("Translate_table failed\n");
1155 		goto free_chainstack;
1156 	}
1157 
1158 	if (table->check && table->check(newinfo, table->valid_hooks)) {
1159 		BUGPRINT("The table doesn't like its own initial data, lol\n");
1160 		return ERR_PTR(-EINVAL);
1161 	}
1162 
1163 	table->private = newinfo;
1164 	rwlock_init(&table->lock);
1165 	ret = mutex_lock_interruptible(&ebt_mutex);
1166 	if (ret != 0)
1167 		goto free_chainstack;
1168 
1169 	list_for_each_entry(t, &net->xt.tables[NFPROTO_BRIDGE], list) {
1170 		if (strcmp(t->name, table->name) == 0) {
1171 			ret = -EEXIST;
1172 			BUGPRINT("Table name already exists\n");
1173 			goto free_unlock;
1174 		}
1175 	}
1176 
1177 	/* Hold a reference count if the chains aren't empty */
1178 	if (newinfo->nentries && !try_module_get(table->me)) {
1179 		ret = -ENOENT;
1180 		goto free_unlock;
1181 	}
1182 	list_add(&table->list, &net->xt.tables[NFPROTO_BRIDGE]);
1183 	mutex_unlock(&ebt_mutex);
1184 	return table;
1185 free_unlock:
1186 	mutex_unlock(&ebt_mutex);
1187 free_chainstack:
1188 	if (newinfo->chainstack) {
1189 		for_each_possible_cpu(i)
1190 			vfree(newinfo->chainstack[i]);
1191 		vfree(newinfo->chainstack);
1192 	}
1193 	vfree(newinfo->entries);
1194 free_newinfo:
1195 	vfree(newinfo);
1196 free_table:
1197 	kfree(table);
1198 out:
1199 	return ERR_PTR(ret);
1200 }
1201 
ebt_unregister_table(struct ebt_table * table)1202 void ebt_unregister_table(struct ebt_table *table)
1203 {
1204 	int i;
1205 
1206 	if (!table) {
1207 		BUGPRINT("Request to unregister NULL table!!!\n");
1208 		return;
1209 	}
1210 	mutex_lock(&ebt_mutex);
1211 	list_del(&table->list);
1212 	mutex_unlock(&ebt_mutex);
1213 	EBT_ENTRY_ITERATE(table->private->entries, table->private->entries_size,
1214 			  ebt_cleanup_entry, NULL);
1215 	if (table->private->nentries)
1216 		module_put(table->me);
1217 	vfree(table->private->entries);
1218 	if (table->private->chainstack) {
1219 		for_each_possible_cpu(i)
1220 			vfree(table->private->chainstack[i]);
1221 		vfree(table->private->chainstack);
1222 	}
1223 	vfree(table->private);
1224 	kfree(table);
1225 }
1226 
1227 /* userspace just supplied us with counters */
update_counters(struct net * net,void __user * user,unsigned int len)1228 static int update_counters(struct net *net, void __user *user, unsigned int len)
1229 {
1230 	int i, ret;
1231 	struct ebt_counter *tmp;
1232 	struct ebt_replace hlp;
1233 	struct ebt_table *t;
1234 
1235 	if (copy_from_user(&hlp, user, sizeof(hlp)))
1236 		return -EFAULT;
1237 
1238 	if (len != sizeof(hlp) + hlp.num_counters * sizeof(struct ebt_counter))
1239 		return -EINVAL;
1240 	if (hlp.num_counters == 0)
1241 		return -EINVAL;
1242 
1243 	if (!(tmp = vmalloc(hlp.num_counters * sizeof(*tmp)))) {
1244 		MEMPRINT("Update_counters && nomemory\n");
1245 		return -ENOMEM;
1246 	}
1247 
1248 	t = find_table_lock(net, hlp.name, &ret, &ebt_mutex);
1249 	if (!t)
1250 		goto free_tmp;
1251 
1252 	if (hlp.num_counters != t->private->nentries) {
1253 		BUGPRINT("Wrong nr of counters\n");
1254 		ret = -EINVAL;
1255 		goto unlock_mutex;
1256 	}
1257 
1258 	if ( copy_from_user(tmp, hlp.counters,
1259 	   hlp.num_counters * sizeof(struct ebt_counter)) ) {
1260 		BUGPRINT("Updata_counters && !cfu\n");
1261 		ret = -EFAULT;
1262 		goto unlock_mutex;
1263 	}
1264 
1265 	/* we want an atomic add of the counters */
1266 	write_lock_bh(&t->lock);
1267 
1268 	/* we add to the counters of the first cpu */
1269 	for (i = 0; i < hlp.num_counters; i++) {
1270 		t->private->counters[i].pcnt += tmp[i].pcnt;
1271 		t->private->counters[i].bcnt += tmp[i].bcnt;
1272 	}
1273 
1274 	write_unlock_bh(&t->lock);
1275 	ret = 0;
1276 unlock_mutex:
1277 	mutex_unlock(&ebt_mutex);
1278 free_tmp:
1279 	vfree(tmp);
1280 	return ret;
1281 }
1282 
ebt_make_matchname(struct ebt_entry_match * m,char * base,char __user * ubase)1283 static inline int ebt_make_matchname(struct ebt_entry_match *m,
1284    char *base, char __user *ubase)
1285 {
1286 	char __user *hlp = ubase + ((char *)m - base);
1287 	if (copy_to_user(hlp, m->u.match->name, EBT_FUNCTION_MAXNAMELEN))
1288 		return -EFAULT;
1289 	return 0;
1290 }
1291 
ebt_make_watchername(struct ebt_entry_watcher * w,char * base,char __user * ubase)1292 static inline int ebt_make_watchername(struct ebt_entry_watcher *w,
1293    char *base, char __user *ubase)
1294 {
1295 	char __user *hlp = ubase + ((char *)w - base);
1296 	if (copy_to_user(hlp , w->u.watcher->name, EBT_FUNCTION_MAXNAMELEN))
1297 		return -EFAULT;
1298 	return 0;
1299 }
1300 
ebt_make_names(struct ebt_entry * e,char * base,char __user * ubase)1301 static inline int ebt_make_names(struct ebt_entry *e, char *base, char __user *ubase)
1302 {
1303 	int ret;
1304 	char __user *hlp;
1305 	struct ebt_entry_target *t;
1306 
1307 	if (e->bitmask == 0)
1308 		return 0;
1309 
1310 	hlp = ubase + (((char *)e + e->target_offset) - base);
1311 	t = (struct ebt_entry_target *)(((char *)e) + e->target_offset);
1312 
1313 	ret = EBT_MATCH_ITERATE(e, ebt_make_matchname, base, ubase);
1314 	if (ret != 0)
1315 		return ret;
1316 	ret = EBT_WATCHER_ITERATE(e, ebt_make_watchername, base, ubase);
1317 	if (ret != 0)
1318 		return ret;
1319 	if (copy_to_user(hlp, t->u.target->name, EBT_FUNCTION_MAXNAMELEN))
1320 		return -EFAULT;
1321 	return 0;
1322 }
1323 
1324 /* called with ebt_mutex locked */
copy_everything_to_user(struct ebt_table * t,void __user * user,int * len,int cmd)1325 static int copy_everything_to_user(struct ebt_table *t, void __user *user,
1326    int *len, int cmd)
1327 {
1328 	struct ebt_replace tmp;
1329 	struct ebt_counter *counterstmp, *oldcounters;
1330 	unsigned int entries_size, nentries;
1331 	char *entries;
1332 
1333 	if (cmd == EBT_SO_GET_ENTRIES) {
1334 		entries_size = t->private->entries_size;
1335 		nentries = t->private->nentries;
1336 		entries = t->private->entries;
1337 		oldcounters = t->private->counters;
1338 	} else {
1339 		entries_size = t->table->entries_size;
1340 		nentries = t->table->nentries;
1341 		entries = t->table->entries;
1342 		oldcounters = t->table->counters;
1343 	}
1344 
1345 	if (copy_from_user(&tmp, user, sizeof(tmp))) {
1346 		BUGPRINT("Cfu didn't work\n");
1347 		return -EFAULT;
1348 	}
1349 
1350 	if (*len != sizeof(struct ebt_replace) + entries_size +
1351 	   (tmp.num_counters? nentries * sizeof(struct ebt_counter): 0)) {
1352 		BUGPRINT("Wrong size\n");
1353 		return -EINVAL;
1354 	}
1355 
1356 	if (tmp.nentries != nentries) {
1357 		BUGPRINT("Nentries wrong\n");
1358 		return -EINVAL;
1359 	}
1360 
1361 	if (tmp.entries_size != entries_size) {
1362 		BUGPRINT("Wrong size\n");
1363 		return -EINVAL;
1364 	}
1365 
1366 	/* userspace might not need the counters */
1367 	if (tmp.num_counters) {
1368 		if (tmp.num_counters != nentries) {
1369 			BUGPRINT("Num_counters wrong\n");
1370 			return -EINVAL;
1371 		}
1372 		counterstmp = vmalloc(nentries * sizeof(*counterstmp));
1373 		if (!counterstmp) {
1374 			MEMPRINT("Couldn't copy counters, out of memory\n");
1375 			return -ENOMEM;
1376 		}
1377 		write_lock_bh(&t->lock);
1378 		get_counters(oldcounters, counterstmp, nentries);
1379 		write_unlock_bh(&t->lock);
1380 
1381 		if (copy_to_user(tmp.counters, counterstmp,
1382 		   nentries * sizeof(struct ebt_counter))) {
1383 			BUGPRINT("Couldn't copy counters to userspace\n");
1384 			vfree(counterstmp);
1385 			return -EFAULT;
1386 		}
1387 		vfree(counterstmp);
1388 	}
1389 
1390 	if (copy_to_user(tmp.entries, entries, entries_size)) {
1391 		BUGPRINT("Couldn't copy entries to userspace\n");
1392 		return -EFAULT;
1393 	}
1394 	/* set the match/watcher/target names right */
1395 	return EBT_ENTRY_ITERATE(entries, entries_size,
1396 	   ebt_make_names, entries, tmp.entries);
1397 }
1398 
do_ebt_set_ctl(struct sock * sk,int cmd,void __user * user,unsigned int len)1399 static int do_ebt_set_ctl(struct sock *sk,
1400 	int cmd, void __user *user, unsigned int len)
1401 {
1402 	int ret;
1403 
1404 	switch(cmd) {
1405 	case EBT_SO_SET_ENTRIES:
1406 		ret = do_replace(sock_net(sk), user, len);
1407 		break;
1408 	case EBT_SO_SET_COUNTERS:
1409 		ret = update_counters(sock_net(sk), user, len);
1410 		break;
1411 	default:
1412 		ret = -EINVAL;
1413   }
1414 	return ret;
1415 }
1416 
do_ebt_get_ctl(struct sock * sk,int cmd,void __user * user,int * len)1417 static int do_ebt_get_ctl(struct sock *sk, int cmd, void __user *user, int *len)
1418 {
1419 	int ret;
1420 	struct ebt_replace tmp;
1421 	struct ebt_table *t;
1422 
1423 	if (copy_from_user(&tmp, user, sizeof(tmp)))
1424 		return -EFAULT;
1425 
1426 	t = find_table_lock(sock_net(sk), tmp.name, &ret, &ebt_mutex);
1427 	if (!t)
1428 		return ret;
1429 
1430 	switch(cmd) {
1431 	case EBT_SO_GET_INFO:
1432 	case EBT_SO_GET_INIT_INFO:
1433 		if (*len != sizeof(struct ebt_replace)){
1434 			ret = -EINVAL;
1435 			mutex_unlock(&ebt_mutex);
1436 			break;
1437 		}
1438 		if (cmd == EBT_SO_GET_INFO) {
1439 			tmp.nentries = t->private->nentries;
1440 			tmp.entries_size = t->private->entries_size;
1441 			tmp.valid_hooks = t->valid_hooks;
1442 		} else {
1443 			tmp.nentries = t->table->nentries;
1444 			tmp.entries_size = t->table->entries_size;
1445 			tmp.valid_hooks = t->table->valid_hooks;
1446 		}
1447 		mutex_unlock(&ebt_mutex);
1448 		if (copy_to_user(user, &tmp, *len) != 0){
1449 			BUGPRINT("c2u Didn't work\n");
1450 			ret = -EFAULT;
1451 			break;
1452 		}
1453 		ret = 0;
1454 		break;
1455 
1456 	case EBT_SO_GET_ENTRIES:
1457 	case EBT_SO_GET_INIT_ENTRIES:
1458 		ret = copy_everything_to_user(t, user, len, cmd);
1459 		mutex_unlock(&ebt_mutex);
1460 		break;
1461 
1462 	default:
1463 		mutex_unlock(&ebt_mutex);
1464 		ret = -EINVAL;
1465 	}
1466 
1467 	return ret;
1468 }
1469 
1470 static struct nf_sockopt_ops ebt_sockopts =
1471 {
1472 	.pf		= PF_INET,
1473 	.set_optmin	= EBT_BASE_CTL,
1474 	.set_optmax	= EBT_SO_SET_MAX + 1,
1475 	.set		= do_ebt_set_ctl,
1476 	.get_optmin	= EBT_BASE_CTL,
1477 	.get_optmax	= EBT_SO_GET_MAX + 1,
1478 	.get		= do_ebt_get_ctl,
1479 	.owner		= THIS_MODULE,
1480 };
1481 
ebtables_init(void)1482 static int __init ebtables_init(void)
1483 {
1484 	int ret;
1485 
1486 	ret = xt_register_target(&ebt_standard_target);
1487 	if (ret < 0)
1488 		return ret;
1489 	ret = nf_register_sockopt(&ebt_sockopts);
1490 	if (ret < 0) {
1491 		xt_unregister_target(&ebt_standard_target);
1492 		return ret;
1493 	}
1494 
1495 	printk(KERN_INFO "Ebtables v2.0 registered\n");
1496 	return 0;
1497 }
1498 
ebtables_fini(void)1499 static void __exit ebtables_fini(void)
1500 {
1501 	nf_unregister_sockopt(&ebt_sockopts);
1502 	xt_unregister_target(&ebt_standard_target);
1503 	printk(KERN_INFO "Ebtables v2.0 unregistered\n");
1504 }
1505 
1506 EXPORT_SYMBOL(ebt_register_table);
1507 EXPORT_SYMBOL(ebt_unregister_table);
1508 EXPORT_SYMBOL(ebt_do_table);
1509 module_init(ebtables_init);
1510 module_exit(ebtables_fini);
1511 MODULE_LICENSE("GPL");
1512