summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--net/netfilter/x_tables.c23
1 files changed, 23 insertions, 0 deletions
diff --git a/net/netfilter/x_tables.c b/net/netfilter/x_tables.c
index 2e4d423..f045bb4 100644
--- a/net/netfilter/x_tables.c
+++ b/net/netfilter/x_tables.c
@@ -654,6 +654,11 @@ struct compat_xt_standard_target {
compat_uint_t verdict;
};
+struct compat_xt_error_target {
+ struct compat_xt_entry_target t;
+ char errorname[XT_FUNCTION_MAXNAMELEN];
+};
+
static bool verdict_ok(int verdict)
{
if (verdict > 0)
@@ -679,6 +684,12 @@ static bool verdict_ok(int verdict)
return false;
}
+static bool error_tg_ok(unsigned int usersize, unsigned int kernsize,
+ const char *msg, unsigned int msglen)
+{
+ return usersize == kernsize && strnlen(msg, msglen) < msglen;
+}
+
int xt_compat_check_entry_offsets(const void *base, const char *elems,
unsigned int target_offset,
unsigned int next_offset)
@@ -708,6 +719,12 @@ int xt_compat_check_entry_offsets(const void *base, const char *elems,
if (!verdict_ok(st->verdict))
return -EINVAL;
+ } else if (strcmp(t->u.user.name, XT_ERROR_TARGET) == 0) {
+ const struct compat_xt_error_target *et = (const void *)t;
+
+ if (!error_tg_ok(t->u.target_size, sizeof(*et),
+ et->errorname, sizeof(et->errorname)))
+ return -EINVAL;
}
/* compat_xt_entry match has less strict alignment requirements,
@@ -796,6 +813,12 @@ int xt_check_entry_offsets(const void *base,
if (!verdict_ok(st->verdict))
return -EINVAL;
+ } else if (strcmp(t->u.user.name, XT_ERROR_TARGET) == 0) {
+ const struct xt_error_target *et = (const void *)t;
+
+ if (!error_tg_ok(t->u.target_size, sizeof(*et),
+ et->errorname, sizeof(et->errorname)))
+ return -EINVAL;
}
return xt_check_entry_match(elems, base + target_offset,
OpenPOWER on IntegriCloud