Merge branch 'master' of git://1984.lsi.us.es/nf

Pablo Neira Ayuso says:

====================
The following batch contains Netfilter fixes for 3.8-rc2, they are:

* Fix IPv6 stateless network/port translation (NPT) checksum
calculation, from Ulrich Weber.

* Fix for xt_recent to avoid memory allocation failures if large
hashtables are used, from Eric Dumazet.

* Fix missing dependencies in Kconfig for the deprecated NOTRACK,
from myself.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>

+28 -31
+7 -26
net/ipv6/netfilter/ip6t_NPT.c
··· 14 #include <linux/netfilter_ipv6/ip6t_NPT.h> 15 #include <linux/netfilter/x_tables.h> 16 17 - static __sum16 csum16_complement(__sum16 a) 18 - { 19 - return (__force __sum16)(0xffff - (__force u16)a); 20 - } 21 - 22 - static __sum16 csum16_add(__sum16 a, __sum16 b) 23 - { 24 - u16 sum; 25 - 26 - sum = (__force u16)a + (__force u16)b; 27 - sum += (__force u16)a < (__force u16)b; 28 - return (__force __sum16)sum; 29 - } 30 - 31 - static __sum16 csum16_sub(__sum16 a, __sum16 b) 32 - { 33 - return csum16_add(a, csum16_complement(b)); 34 - } 35 - 36 static int ip6t_npt_checkentry(const struct xt_tgchk_param *par) 37 { 38 struct ip6t_npt_tginfo *npt = par->targinfo; 39 - __sum16 src_sum = 0, dst_sum = 0; 40 unsigned int i; 41 42 if (npt->src_pfx_len > 64 || npt->dst_pfx_len > 64) 43 return -EINVAL; 44 45 for (i = 0; i < ARRAY_SIZE(npt->src_pfx.in6.s6_addr16); i++) { 46 - src_sum = csum16_add(src_sum, 47 - (__force __sum16)npt->src_pfx.in6.s6_addr16[i]); 48 - dst_sum = csum16_add(dst_sum, 49 - (__force __sum16)npt->dst_pfx.in6.s6_addr16[i]); 50 } 51 52 - npt->adjustment = csum16_sub(src_sum, dst_sum); 53 return 0; 54 } 55 ··· 66 return false; 67 } 68 69 - sum = csum16_add((__force __sum16)addr->s6_addr16[idx], 70 npt->adjustment); 71 if (sum == CSUM_MANGLED_0) 72 sum = 0;
··· 14 #include <linux/netfilter_ipv6/ip6t_NPT.h> 15 #include <linux/netfilter/x_tables.h> 16 17 static int ip6t_npt_checkentry(const struct xt_tgchk_param *par) 18 { 19 struct ip6t_npt_tginfo *npt = par->targinfo; 20 + __wsum src_sum = 0, dst_sum = 0; 21 unsigned int i; 22 23 if (npt->src_pfx_len > 64 || npt->dst_pfx_len > 64) 24 return -EINVAL; 25 26 for (i = 0; i < ARRAY_SIZE(npt->src_pfx.in6.s6_addr16); i++) { 27 + src_sum = csum_add(src_sum, 28 + (__force __wsum)npt->src_pfx.in6.s6_addr16[i]); 29 + dst_sum = csum_add(dst_sum, 30 + (__force __wsum)npt->dst_pfx.in6.s6_addr16[i]); 31 } 32 33 + npt->adjustment = (__force __sum16) csum_sub(src_sum, dst_sum); 34 return 0; 35 } 36 ··· 85 return false; 86 } 87 88 + sum = (__force __sum16) csum_add((__force __wsum)addr->s6_addr16[idx], 89 npt->adjustment); 90 if (sum == CSUM_MANGLED_0) 91 sum = 0;
+3
net/netfilter/Kconfig
··· 682 683 config NETFILTER_XT_TARGET_NOTRACK 684 tristate '"NOTRACK" target support (DEPRECATED)' 685 select NETFILTER_XT_TARGET_CT 686 687 config NETFILTER_XT_TARGET_RATEEST
··· 682 683 config NETFILTER_XT_TARGET_NOTRACK 684 tristate '"NOTRACK" target support (DEPRECATED)' 685 + depends on NF_CONNTRACK 686 + depends on IP_NF_RAW || IP6_NF_RAW 687 + depends on NETFILTER_ADVANCED 688 select NETFILTER_XT_TARGET_CT 689 690 config NETFILTER_XT_TARGET_RATEEST
+18 -5
net/netfilter/xt_recent.c
··· 29 #include <linux/skbuff.h> 30 #include <linux/inet.h> 31 #include <linux/slab.h> 32 #include <net/net_namespace.h> 33 #include <net/netns/generic.h> 34 ··· 311 return ret; 312 } 313 314 static int recent_mt_check(const struct xt_mtchk_param *par, 315 const struct xt_recent_mtinfo_v1 *info) 316 { ··· 331 #endif 332 unsigned int i; 333 int ret = -EINVAL; 334 335 if (unlikely(!hash_rnd_inited)) { 336 get_random_bytes(&hash_rnd, sizeof(hash_rnd)); ··· 370 goto out; 371 } 372 373 - t = kzalloc(sizeof(*t) + sizeof(t->iphash[0]) * ip_list_hash_size, 374 - GFP_KERNEL); 375 if (t == NULL) { 376 ret = -ENOMEM; 377 goto out; ··· 390 uid = make_kuid(&init_user_ns, ip_list_uid); 391 gid = make_kgid(&init_user_ns, ip_list_gid); 392 if (!uid_valid(uid) || !gid_valid(gid)) { 393 - kfree(t); 394 ret = -EINVAL; 395 goto out; 396 } 397 pde = proc_create_data(t->name, ip_list_perms, recent_net->xt_recent, 398 &recent_mt_fops, t); 399 if (pde == NULL) { 400 - kfree(t); 401 ret = -ENOMEM; 402 goto out; 403 } ··· 448 remove_proc_entry(t->name, recent_net->xt_recent); 449 #endif 450 recent_table_flush(t); 451 - kfree(t); 452 } 453 mutex_unlock(&recent_mutex); 454 }
··· 29 #include <linux/skbuff.h> 30 #include <linux/inet.h> 31 #include <linux/slab.h> 32 + #include <linux/vmalloc.h> 33 #include <net/net_namespace.h> 34 #include <net/netns/generic.h> 35 ··· 310 return ret; 311 } 312 313 + static void recent_table_free(void *addr) 314 + { 315 + if (is_vmalloc_addr(addr)) 316 + vfree(addr); 317 + else 318 + kfree(addr); 319 + } 320 + 321 static int recent_mt_check(const struct xt_mtchk_param *par, 322 const struct xt_recent_mtinfo_v1 *info) 323 { ··· 322 #endif 323 unsigned int i; 324 int ret = -EINVAL; 325 + size_t sz; 326 327 if (unlikely(!hash_rnd_inited)) { 328 get_random_bytes(&hash_rnd, sizeof(hash_rnd)); ··· 360 goto out; 361 } 362 363 + sz = sizeof(*t) + sizeof(t->iphash[0]) * ip_list_hash_size; 364 + if (sz <= PAGE_SIZE) 365 + t = kzalloc(sz, GFP_KERNEL); 366 + else 367 + t = vzalloc(sz); 368 if (t == NULL) { 369 ret = -ENOMEM; 370 goto out; ··· 377 uid = make_kuid(&init_user_ns, ip_list_uid); 378 gid = make_kgid(&init_user_ns, ip_list_gid); 379 if (!uid_valid(uid) || !gid_valid(gid)) { 380 + recent_table_free(t); 381 ret = -EINVAL; 382 goto out; 383 } 384 pde = proc_create_data(t->name, ip_list_perms, recent_net->xt_recent, 385 &recent_mt_fops, t); 386 if (pde == NULL) { 387 + recent_table_free(t); 388 ret = -ENOMEM; 389 goto out; 390 } ··· 435 remove_proc_entry(t->name, recent_net->xt_recent); 436 #endif 437 recent_table_flush(t); 438 + recent_table_free(t); 439 } 440 mutex_unlock(&recent_mutex); 441 }