Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 41964
b: refs/heads/master
c: 22b440b
h: refs/heads/master
v: v3
  • Loading branch information
Al Viro authored and David S. Miller committed Dec 3, 2006
1 parent ebe5288 commit 0e62ca3
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 25 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 14197d5447afc41fce6b11a91592278cad1a09eb
refs/heads/master: 22b440bf9e717226d0fbaf4f29357cbdd5279de5
73 changes: 49 additions & 24 deletions trunk/net/bridge/netfilter/ebtables.c
Original file line number Diff line number Diff line change
Expand Up @@ -393,15 +393,11 @@ ebt_check_watcher(struct ebt_entry_watcher *w, struct ebt_entry *e,
return 0;
}

/*
* this one is very careful, as it is the first function
* to parse the userspace data
*/
static inline int
ebt_check_entry_size_and_hooks(struct ebt_entry *e,
__ebt_verify_pointers(struct ebt_entry *e,
struct ebt_table_info *newinfo, char *base, char *limit,
struct ebt_entries **hook_entries, unsigned int *n, unsigned int *cnt,
unsigned int *totalcnt, unsigned int *udc_cnt, unsigned int valid_hooks)
struct ebt_entries **hook_entries,
unsigned int valid_hooks)
{
unsigned int offset = (char *)e - newinfo->entries;
size_t left = (limit - base) - offset;
Expand All @@ -416,8 +412,6 @@ ebt_check_entry_size_and_hooks(struct ebt_entry *e,
if ((char *)hook_entries[i] == base + offset)
break;
}
/* beginning of a new chain
if i == NF_BR_NUMHOOKS it must be a user defined chain */
if (i != NF_BR_NUMHOOKS || !(e->bitmask & EBT_ENTRY_OR_ENTRIES)) {
if (e->bitmask != 0) {
/* we make userspace set this right,
Expand All @@ -426,16 +420,52 @@ ebt_check_entry_size_and_hooks(struct ebt_entry *e,
"in distinguisher\n");
return -EINVAL;
}
if (left < sizeof(struct ebt_entries))
goto Esmall;
if (i != NF_BR_NUMHOOKS)
newinfo->hook_entry[i] = (struct ebt_entries *)e;
return 0;
}
if (left < sizeof(struct ebt_entry))
goto Esmall;
if (left < e->next_offset)
goto Esmall;
return 0;

Esmall:
BUGPRINT("entries_size too small\n");
return -EINVAL;
}

/*
* this one is very careful, as it is the first function
* to parse the userspace data
*/
static inline int
ebt_check_entry_size_and_hooks(struct ebt_entry *e,
struct ebt_table_info *newinfo, char *base,
struct ebt_entries **hook_entries, unsigned int *n, unsigned int *cnt,
unsigned int *totalcnt, unsigned int *udc_cnt, unsigned int valid_hooks)
{
unsigned int offset = (char *)e - newinfo->entries;
int i;

for (i = 0; i < NF_BR_NUMHOOKS; i++) {
if ((valid_hooks & (1 << i)) == 0)
continue;
if ((char *)hook_entries[i] == base + offset)
break;
}
/* beginning of a new chain
if i == NF_BR_NUMHOOKS it must be a user defined chain */
if (i != NF_BR_NUMHOOKS || !e->bitmask) {
/* this checks if the previous chain has as many entries
as it said it has */
if (*n != *cnt) {
BUGPRINT("nentries does not equal the nr of entries "
"in the chain\n");
return -EINVAL;
}
/* before we look at the struct, be sure it is not too big */
if (left < sizeof(struct ebt_entries))
goto Esmall;
if (((struct ebt_entries *)e)->policy != EBT_DROP &&
((struct ebt_entries *)e)->policy != EBT_ACCEPT) {
/* only RETURN from udc */
Expand All @@ -447,8 +477,6 @@ ebt_check_entry_size_and_hooks(struct ebt_entry *e,
}
if (i == NF_BR_NUMHOOKS) /* it's a user defined chain */
(*udc_cnt)++;
else
newinfo->hook_entry[i] = (struct ebt_entries *)e;
if (((struct ebt_entries *)e)->counter_offset != *totalcnt) {
BUGPRINT("counter_offset != totalcnt");
return -EINVAL;
Expand All @@ -458,8 +486,6 @@ ebt_check_entry_size_and_hooks(struct ebt_entry *e,
return 0;
}
/* a plain old entry, heh */
if (left < sizeof(struct ebt_entry))
goto Esmall;
if (sizeof(struct ebt_entry) > e->watchers_offset ||
e->watchers_offset > e->target_offset ||
e->target_offset >= e->next_offset) {
Expand All @@ -471,16 +497,9 @@ ebt_check_entry_size_and_hooks(struct ebt_entry *e,
BUGPRINT("target size too small\n");
return -EINVAL;
}
if (left < e->next_offset)
goto Esmall;

(*cnt)++;
(*totalcnt)++;
return 0;

Esmall:
BUGPRINT("entries_size too small\n");
return -EINVAL;
}

struct ebt_cl_stack
Expand Down Expand Up @@ -776,6 +795,12 @@ static int translate_table(struct ebt_replace *repl,
newinfo->entries_size = repl->entries_size;
newinfo->nentries = repl->nentries;

ret = EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
__ebt_verify_pointers, newinfo, repl->entries,
repl->entries + repl->entries_size, repl->hook_entry, repl->valid_hooks);
if (ret != 0)
return ret;

/* do some early checkings and initialize some things */
i = 0; /* holds the expected nr. of entries for the chain */
j = 0; /* holds the up to now counted entries for the chain */
Expand All @@ -784,7 +809,7 @@ static int translate_table(struct ebt_replace *repl,
udc_cnt = 0; /* will hold the nr. of user defined chains (udc) */
ret = EBT_ENTRY_ITERATE(newinfo->entries, newinfo->entries_size,
ebt_check_entry_size_and_hooks, newinfo, repl->entries,
repl->entries + repl->entries_size, repl->hook_entry, &i, &j, &k,
repl->hook_entry, &i, &j, &k,
&udc_cnt, repl->valid_hooks);

if (ret != 0)
Expand Down

0 comments on commit 0e62ca3

Please sign in to comment.