rculfhash: handle pthread_create failures
authorEric Wong <normalperson@yhbt.net>
Tue, 24 Jun 2014 01:20:31 +0000 (01:20 +0000)
committerMathieu Desnoyers <mathieu.desnoyers@efficios.com>
Thu, 31 Jul 2014 20:54:36 +0000 (16:54 -0400)
Like calloc, pthread_create may fail with EAGAIN due to a lack
of resources.  Account for that and gracefully continue.

Signed-off-by: Eric Wong <normalperson@yhbt.net>
Signed-off-by: Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
rculfhash.c

index 2a450459f5cfa50e94bce03e00be0ad1be7b2b4f..8a8ede7a6cadd1027a2c55c450ac3016f696fa6c 100644 (file)
@@ -1171,7 +1171,7 @@ void partition_resize_helper(struct cds_lfht *ht, unsigned long i,
                void (*fct)(struct cds_lfht *ht, unsigned long i,
                        unsigned long start, unsigned long len))
 {
-       unsigned long partition_len;
+       unsigned long partition_len, start = 0;
        struct partition_resize_work *work;
        int thread, ret;
        unsigned long nr_threads;
@@ -1201,6 +1201,17 @@ void partition_resize_helper(struct cds_lfht *ht, unsigned long i,
                work[thread].fct = fct;
                ret = pthread_create(&(work[thread].thread_id), ht->resize_attr,
                        partition_resize_thread, &work[thread]);
+               if (ret == EAGAIN) {
+                       /*
+                        * Out of resources: wait and join the threads
+                        * we've created, then handle leftovers.
+                        */
+                       dbg_printf("error spawning for resize, single-threading\n");
+                       start = work[thread].start;
+                       len -= start;
+                       nr_threads = thread;
+                       break;
+               }
                assert(!ret);
        }
        for (thread = 0; thread < nr_threads; thread++) {
@@ -1208,10 +1219,17 @@ void partition_resize_helper(struct cds_lfht *ht, unsigned long i,
                assert(!ret);
        }
        free(work);
-       return;
+
+       /*
+        * A pthread_create failure above will either lead in us having
+        * no threads to join or starting at a non-zero offset,
+        * fallback to single thread processing of leftovers.
+        */
+       if (start == 0 && nr_threads > 0)
+               return;
 fallback:
        ht->flavor->thread_online();
-       fct(ht, i, 0, len);
+       fct(ht, i, start, len);
        ht->flavor->thread_offline();
 }
 
This page took 0.0346 seconds and 4 git commands to generate.