netfilter: x_tables: do not fail xt_alloc_table_info too easilly
eacd86ca3b
("net/netfilter/x_tables.c: use kvmalloc() in xt_alloc_table_info()") has unintentionally fortified xt_alloc_table_info allocation when __GFP_RETRY has been dropped from the vmalloc fallback. Later on there was a syzbot report that this can lead to OOM killer invocations when tables are too large and0537250fdc
("netfilter: x_tables: make allocation less aggressive") has been merged to restore the original behavior. Georgi Nikolov however noticed that he is not able to install his iptables anymore so this can be seen as a regression. The primary argument for0537250fdc
was that this allocation path shouldn't really trigger the OOM killer and kill innocent tasks. On the other hand the interface requires root and as such should allow what the admin asks for. Root inside a namespaces makes this more complicated because those might be not trusted in general. If they are not then such namespaces should be restricted anyway. Therefore drop the __GFP_NORETRY and replace it by __GFP_ACCOUNT to enfore memcg constrains on it. Fixes:0537250fdc
("netfilter: x_tables: make allocation less aggressive") Reported-by: Georgi Nikolov <gnikolov@icdsoft.com> Suggested-by: Vlastimil Babka <vbabka@suse.cz> Acked-by: Florian Westphal <fw@strlen.de> Signed-off-by: Michal Hocko <mhocko@suse.com> Acked-by: Vlastimil Babka <vbabka@suse.cz> Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
This commit is contained in:
Родитель
1c117d3b72
Коммит
a148ce1537
|
@ -1178,12 +1178,7 @@ struct xt_table_info *xt_alloc_table_info(unsigned int size)
|
|||
if (sz < sizeof(*info) || sz >= XT_MAX_TABLE_SIZE)
|
||||
return NULL;
|
||||
|
||||
/* __GFP_NORETRY is not fully supported by kvmalloc but it should
|
||||
* work reasonably well if sz is too large and bail out rather
|
||||
* than shoot all processes down before realizing there is nothing
|
||||
* more to reclaim.
|
||||
*/
|
||||
info = kvmalloc(sz, GFP_KERNEL | __GFP_NORETRY);
|
||||
info = kvmalloc(sz, GFP_KERNEL_ACCOUNT);
|
||||
if (!info)
|
||||
return NULL;
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче