netfilter: x_tables: move hook entry checks into core
authorFlorian Westphal <fw@strlen.de>
Tue, 27 Feb 2018 18:42:29 +0000 (19:42 +0100)
committerPablo Neira Ayuso <pablo@netfilter.org>
Mon, 5 Mar 2018 22:15:43 +0000 (23:15 +0100)
Allow followup patch to change on location instead of three.

Signed-off-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
include/linux/netfilter/x_tables.h
net/ipv4/netfilter/arp_tables.c
net/ipv4/netfilter/ip_tables.c
net/ipv6/netfilter/ip6_tables.c
net/netfilter/x_tables.c

index 1313b35c3ab7914a26c463aa9113756dd4e4ceae..fa0c19c328f1de701512c746d1862849d90a2ac7 100644 (file)
@@ -281,6 +281,8 @@ int xt_check_entry_offsets(const void *base, const char *elems,
                           unsigned int target_offset,
                           unsigned int next_offset);
 
+int xt_check_table_hooks(const struct xt_table_info *info, unsigned int valid_hooks);
+
 unsigned int *xt_alloc_entry_offsets(unsigned int size);
 bool xt_find_jump_offset(const unsigned int *offsets,
                         unsigned int target, unsigned int size);
index c9ffa884a4eef79e58721584777dc2226532bf38..be5821215ea0e9cde7eb5a94e794365b36b2b07b 100644 (file)
@@ -555,16 +555,9 @@ static int translate_table(struct xt_table_info *newinfo, void *entry0,
        if (i != repl->num_entries)
                goto out_free;
 
-       /* Check hooks all assigned */
-       for (i = 0; i < NF_ARP_NUMHOOKS; i++) {
-               /* Only hooks which are valid */
-               if (!(repl->valid_hooks & (1 << i)))
-                       continue;
-               if (newinfo->hook_entry[i] == 0xFFFFFFFF)
-                       goto out_free;
-               if (newinfo->underflow[i] == 0xFFFFFFFF)
-                       goto out_free;
-       }
+       ret = xt_check_table_hooks(newinfo, repl->valid_hooks);
+       if (ret)
+               goto out_free;
 
        if (!mark_source_chains(newinfo, repl->valid_hooks, entry0, offsets)) {
                ret = -ELOOP;
index c9b57a6bf96a745fce221184d9b88e4dca6752c2..29bda9484a33282a5aee0ba1c0d3bc79d6591f56 100644 (file)
@@ -702,16 +702,9 @@ translate_table(struct net *net, struct xt_table_info *newinfo, void *entry0,
        if (i != repl->num_entries)
                goto out_free;
 
-       /* Check hooks all assigned */
-       for (i = 0; i < NF_INET_NUMHOOKS; i++) {
-               /* Only hooks which are valid */
-               if (!(repl->valid_hooks & (1 << i)))
-                       continue;
-               if (newinfo->hook_entry[i] == 0xFFFFFFFF)
-                       goto out_free;
-               if (newinfo->underflow[i] == 0xFFFFFFFF)
-                       goto out_free;
-       }
+       ret = xt_check_table_hooks(newinfo, repl->valid_hooks);
+       if (ret)
+               goto out_free;
 
        if (!mark_source_chains(newinfo, repl->valid_hooks, entry0, offsets)) {
                ret = -ELOOP;
index f46954221933420c4b1f8304dea5358051a258d0..ba3776a4d30553f52db644d4c3bcb3c6c6cf7bef 100644 (file)
@@ -720,16 +720,9 @@ translate_table(struct net *net, struct xt_table_info *newinfo, void *entry0,
        if (i != repl->num_entries)
                goto out_free;
 
-       /* Check hooks all assigned */
-       for (i = 0; i < NF_INET_NUMHOOKS; i++) {
-               /* Only hooks which are valid */
-               if (!(repl->valid_hooks & (1 << i)))
-                       continue;
-               if (newinfo->hook_entry[i] == 0xFFFFFFFF)
-                       goto out_free;
-               if (newinfo->underflow[i] == 0xFFFFFFFF)
-                       goto out_free;
-       }
+       ret = xt_check_table_hooks(newinfo, repl->valid_hooks);
+       if (ret)
+               goto out_free;
 
        if (!mark_source_chains(newinfo, repl->valid_hooks, entry0, offsets)) {
                ret = -ELOOP;
index f045bb4f706391fb2ae85846f28c9dd168aea9e5..5d8ba89a8da84099f2be7a2a1dc1e7d76bd75ec7 100644 (file)
@@ -518,6 +518,35 @@ static int xt_check_entry_match(const char *match, const char *target,
        return 0;
 }
 
+/** xt_check_table_hooks - check hook entry points are sane
+ *
+ * @info xt_table_info to check
+ * @valid_hooks - hook entry points that we can enter from
+ *
+ * Validates that the hook entry and underflows points are set up.
+ *
+ * Return: 0 on success, negative errno on failure.
+ */
+int xt_check_table_hooks(const struct xt_table_info *info, unsigned int valid_hooks)
+{
+       unsigned int i;
+
+       BUILD_BUG_ON(ARRAY_SIZE(info->hook_entry) != ARRAY_SIZE(info->underflow));
+
+       for (i = 0; i < ARRAY_SIZE(info->hook_entry); i++) {
+               if (!(valid_hooks & (1 << i)))
+                       continue;
+
+               if (info->hook_entry[i] == 0xFFFFFFFF)
+                       return -EINVAL;
+               if (info->underflow[i] == 0xFFFFFFFF)
+                       return -EINVAL;
+       }
+
+       return 0;
+}
+EXPORT_SYMBOL(xt_check_table_hooks);
+
 #ifdef CONFIG_COMPAT
 int xt_compat_add_offset(u_int8_t af, unsigned int offset, int delta)
 {