aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorThomas Graf <tgraf@suug.ch>2015-04-22 03:41:46 -0400
committerDavid S. Miller <davem@davemloft.net>2015-04-22 14:17:22 -0400
commita87b9ebf1709687ff213091d0fdb4254b1564803 (patch)
treea28503490179133baff9275d428a3c0c31f35e4e /lib
parente2307ed6cbe71c74e291681aaa7e92ab98bc3177 (diff)
rhashtable: Do not schedule more than one rehash if we can't grow further
The current code currently only stops inserting rehashes into the chain when no resizes are currently scheduled. As long as resizes are scheduled and while inserting above the utilization watermark, more and more rehashes will be scheduled. This lead to a perfect DoS storm with thousands of rehashes scheduled which lead to thousands of spinlocks to be taken sequentially. Instead, only allow either a series of resizes or a single rehash. Drop any further rehashes and return -EBUSY. Fixes: ccd57b1bd324 ("rhashtable: Add immediate rehash during insertion") Signed-off-by: Thomas Graf <tgraf@suug.ch> Acked-by: Herbert Xu <herbert@gondor.apana.org.au> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'lib')
-rw-r--r--lib/rhashtable.c4
1 files changed, 2 insertions, 2 deletions
diff --git a/lib/rhashtable.c b/lib/rhashtable.c
index f648cfde8520..b28df4019ade 100644
--- a/lib/rhashtable.c
+++ b/lib/rhashtable.c
@@ -405,8 +405,8 @@ int rhashtable_insert_rehash(struct rhashtable *ht)
405 405
406 if (rht_grow_above_75(ht, tbl)) 406 if (rht_grow_above_75(ht, tbl))
407 size *= 2; 407 size *= 2;
408 /* More than two rehashes (not resizes) detected. */ 408 /* Do not schedule more than one rehash */
409 else if (WARN_ON(old_tbl != tbl && old_tbl->size == size)) 409 else if (old_tbl != tbl)
410 return -EBUSY; 410 return -EBUSY;
411 411
412 new_tbl = bucket_table_alloc(ht, size, GFP_ATOMIC); 412 new_tbl = bucket_table_alloc(ht, size, GFP_ATOMIC);