rhashtable: use cond_resched()
authorEric Dumazet <edumazet@google.com>
Thu, 26 Feb 2015 15:20:34 +0000 (07:20 -0800)
committerDavid S. Miller <davem@davemloft.net>
Fri, 27 Feb 2015 22:55:14 +0000 (17:55 -0500)
If a hash table has 128 slots and 16384 elems, expand to 256 slots
takes more than one second. For larger sets, a soft lockup is detected.

Holding cpu for that long, even in a work queue is a show stopper
for non preemptable kernels.

cond_resched() at strategic points to allow process scheduler
to reschedule us.

Signed-off-by: Eric Dumazet <edumazet@google.com>
Acked-by: Daniel Borkmann <daniel@iogearbox.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
lib/rhashtable.c

index 090641d..b5344ef 100644 (file)
@@ -17,6 +17,7 @@
 #include <linux/kernel.h>
 #include <linux/init.h>
 #include <linux/log2.h>
+#include <linux/sched.h>
 #include <linux/slab.h>
 #include <linux/vmalloc.h>
 #include <linux/mm.h>
@@ -412,6 +413,7 @@ int rhashtable_expand(struct rhashtable *ht)
                        }
                }
                unlock_buckets(new_tbl, old_tbl, new_hash);
+               cond_resched();
        }
 
        /* Unzip interleaved hash chains */
@@ -435,6 +437,7 @@ int rhashtable_expand(struct rhashtable *ht)
                                complete = false;
 
                        unlock_buckets(new_tbl, old_tbl, old_hash);
+                       cond_resched();
                }
        }
 
@@ -493,6 +496,7 @@ int rhashtable_shrink(struct rhashtable *ht)
                                   tbl->buckets[new_hash + new_tbl->size]);
 
                unlock_buckets(new_tbl, tbl, new_hash);
+               cond_resched();
        }
 
        /* Publish the new, valid hash table */