[Bf-blender-cvs] [14f3b2cdad2] master: BLI_task: add TLS support to BLI_task_parallel_mempool

Campbell Barton noreply at git.blender.org
Wed Jun 9 17:23:08 CEST 2021


Commit: 14f3b2cdad2d7b00ce3ea27bf8eb0087ac2a6cbd
Author: Campbell Barton
Date:   Wed Jun 9 22:49:45 2021 +1000
Branches: master
https://developer.blender.org/rB14f3b2cdad2d7b00ce3ea27bf8eb0087ac2a6cbd

BLI_task: add TLS support to BLI_task_parallel_mempool

Support thread local storage for BLI_task_parallel_mempool,
as well as support for the reduce and free callbacks.

mempool_iter_threadsafe_* functions have been moved into a private
header thats only shared between task_iterator.c and BLI_mempool.c
so the TLS can be made part of the iterator array without having to
rely on passing in struct offsets.

Add test task.MempoolIterTLS that ensures reduce and free
are working as expected.

Reviewed By: mont29

Ref D11548

===================================================================

M	source/blender/blenkernel/intern/armature_deform.c
M	source/blender/blenkernel/intern/lattice_deform.c
M	source/blender/blenlib/BLI_mempool.h
M	source/blender/blenlib/BLI_task.h
M	source/blender/blenlib/CMakeLists.txt
M	source/blender/blenlib/intern/BLI_mempool.c
A	source/blender/blenlib/intern/BLI_mempool_private.h
M	source/blender/blenlib/intern/task_iterator.c
M	source/blender/blenlib/tests/BLI_task_test.cc
M	source/blender/bmesh/intern/bmesh_iterators_inline.h
M	source/blender/bmesh/intern/bmesh_mesh_normals.c

===================================================================

diff --git a/source/blender/blenkernel/intern/armature_deform.c b/source/blender/blenkernel/intern/armature_deform.c
index 8711a001e32..bca5503c8d2 100644
--- a/source/blender/blenkernel/intern/armature_deform.c
+++ b/source/blender/blenkernel/intern/armature_deform.c
@@ -444,7 +444,9 @@ static void armature_vert_task(void *__restrict userdata,
   armature_vert_task_with_dvert(data, i, dvert);
 }
 
-static void armature_vert_task_editmesh(void *__restrict userdata, MempoolIterData *iter)
+static void armature_vert_task_editmesh(void *__restrict userdata,
+                                        MempoolIterData *iter,
+                                        const TaskParallelTLS *__restrict UNUSED(tls))
 {
   const ArmatureUserdata *data = userdata;
   BMVert *v = (BMVert *)iter;
@@ -452,7 +454,9 @@ static void armature_vert_task_editmesh(void *__restrict userdata, MempoolIterDa
   armature_vert_task_with_dvert(data, BM_elem_index_get(v), dvert);
 }
 
-static void armature_vert_task_editmesh_no_dvert(void *__restrict userdata, MempoolIterData *iter)
+static void armature_vert_task_editmesh_no_dvert(void *__restrict userdata,
+                                                 MempoolIterData *iter,
+                                                 const TaskParallelTLS *__restrict UNUSED(tls))
 {
   const ArmatureUserdata *data = userdata;
   BMVert *v = (BMVert *)iter;
@@ -593,12 +597,16 @@ static void armature_deform_coords_impl(const Object *ob_arm,
      * have already been properly set. */
     BM_mesh_elem_index_ensure(em_target->bm, BM_VERT);
 
+    TaskParallelSettings settings;
+    BLI_parallel_mempool_settings_defaults(&settings);
+
     if (use_dverts) {
-      BLI_task_parallel_mempool(em_target->bm->vpool, &data, armature_vert_task_editmesh, true);
+      BLI_task_parallel_mempool(
+          em_target->bm->vpool, &data, armature_vert_task_editmesh, &settings);
     }
     else {
       BLI_task_parallel_mempool(
-          em_target->bm->vpool, &data, armature_vert_task_editmesh_no_dvert, true);
+          em_target->bm->vpool, &data, armature_vert_task_editmesh_no_dvert, &settings);
     }
   }
   else {
diff --git a/source/blender/blenkernel/intern/lattice_deform.c b/source/blender/blenkernel/intern/lattice_deform.c
index 4a926ee3d96..a8126cb5538 100644
--- a/source/blender/blenkernel/intern/lattice_deform.c
+++ b/source/blender/blenkernel/intern/lattice_deform.c
@@ -320,7 +320,9 @@ static void lattice_deform_vert_task(void *__restrict userdata,
   lattice_deform_vert_with_dvert(data, index, data->dvert ? &data->dvert[index] : NULL);
 }
 
-static void lattice_vert_task_editmesh(void *__restrict userdata, MempoolIterData *iter)
+static void lattice_vert_task_editmesh(void *__restrict userdata,
+                                       MempoolIterData *iter,
+                                       const TaskParallelTLS *__restrict UNUSED(tls))
 {
   const LatticeDeformUserdata *data = userdata;
   BMVert *v = (BMVert *)iter;
@@ -328,7 +330,9 @@ static void lattice_vert_task_editmesh(void *__restrict userdata, MempoolIterDat
   lattice_deform_vert_with_dvert(data, BM_elem_index_get(v), dvert);
 }
 
-static void lattice_vert_task_editmesh_no_dvert(void *__restrict userdata, MempoolIterData *iter)
+static void lattice_vert_task_editmesh_no_dvert(void *__restrict userdata,
+                                                MempoolIterData *iter,
+                                                const TaskParallelTLS *__restrict UNUSED(tls))
 {
   const LatticeDeformUserdata *data = userdata;
   BMVert *v = (BMVert *)iter;
@@ -397,12 +401,16 @@ static void lattice_deform_coords_impl(const Object *ob_lattice,
      * have already been properly set. */
     BM_mesh_elem_index_ensure(em_target->bm, BM_VERT);
 
+    TaskParallelSettings settings;
+    BLI_parallel_mempool_settings_defaults(&settings);
+
     if (cd_dvert_offset != -1) {
-      BLI_task_parallel_mempool(em_target->bm->vpool, &data, lattice_vert_task_editmesh, true);
+      BLI_task_parallel_mempool(
+          em_target->bm->vpool, &data, lattice_vert_task_editmesh, &settings);
     }
     else {
       BLI_task_parallel_mempool(
-          em_target->bm->vpool, &data, lattice_vert_task_editmesh_no_dvert, true);
+          em_target->bm->vpool, &data, lattice_vert_task_editmesh_no_dvert, &settings);
     }
   }
   else {
diff --git a/source/blender/blenlib/BLI_mempool.h b/source/blender/blenlib/BLI_mempool.h
index 3ee6f182593..29fb6a2e233 100644
--- a/source/blender/blenlib/BLI_mempool.h
+++ b/source/blender/blenlib/BLI_mempool.h
@@ -88,11 +88,6 @@ enum {
 void BLI_mempool_iternew(BLI_mempool *pool, BLI_mempool_iter *iter) ATTR_NONNULL();
 void *BLI_mempool_iterstep(BLI_mempool_iter *iter) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL();
 
-BLI_mempool_iter *BLI_mempool_iter_threadsafe_create(BLI_mempool *pool,
-                                                     const size_t num_iter) ATTR_WARN_UNUSED_RESULT
-    ATTR_NONNULL();
-void BLI_mempool_iter_threadsafe_free(BLI_mempool_iter *iter_arr) ATTR_NONNULL();
-
 #ifdef __cplusplus
 }
 #endif
diff --git a/source/blender/blenlib/BLI_task.h b/source/blender/blenlib/BLI_task.h
index 339bb256819..59020c9eb1e 100644
--- a/source/blender/blenlib/BLI_task.h
+++ b/source/blender/blenlib/BLI_task.h
@@ -261,11 +261,14 @@ void BLI_task_parallel_listbase(struct ListBase *listbase,
                                 const TaskParallelSettings *settings);
 
 typedef struct MempoolIterData MempoolIterData;
-typedef void (*TaskParallelMempoolFunc)(void *userdata, MempoolIterData *iter);
+
+typedef void (*TaskParallelMempoolFunc)(void *userdata,
+                                        MempoolIterData *iter,
+                                        const TaskParallelTLS *__restrict tls);
 void BLI_task_parallel_mempool(struct BLI_mempool *mempool,
                                void *userdata,
                                TaskParallelMempoolFunc func,
-                               const bool use_threading);
+                               const TaskParallelSettings *settings);
 
 /* TODO(sergey): Think of a better place for this. */
 BLI_INLINE void BLI_parallel_range_settings_defaults(TaskParallelSettings *settings)
@@ -276,6 +279,12 @@ BLI_INLINE void BLI_parallel_range_settings_defaults(TaskParallelSettings *setti
   settings->min_iter_per_thread = 0;
 }
 
+BLI_INLINE void BLI_parallel_mempool_settings_defaults(TaskParallelSettings *settings)
+{
+  memset(settings, 0, sizeof(*settings));
+  settings->use_threading = true;
+}
+
 /* Don't use this, store any thread specific data in tls->userdata_chunk instead.
  * Only here for code to be removed. */
 int BLI_task_parallel_thread_id(const TaskParallelTLS *tls);
diff --git a/source/blender/blenlib/CMakeLists.txt b/source/blender/blenlib/CMakeLists.txt
index f3dc343ee20..e04f3c1b19d 100644
--- a/source/blender/blenlib/CMakeLists.txt
+++ b/source/blender/blenlib/CMakeLists.txt
@@ -145,6 +145,9 @@ set(SRC
   intern/winstuff.c
   intern/winstuff_dir.c
 
+  # Private headers.
+  intern/BLI_mempool_private.h
+
   # Header as source (included in C files above).
   intern/kdtree_impl.h
   intern/list_sort_impl.h
diff --git a/source/blender/blenlib/intern/BLI_mempool.c b/source/blender/blenlib/intern/BLI_mempool.c
index 75f934c1fb8..cf0021609b5 100644
--- a/source/blender/blenlib/intern/BLI_mempool.c
+++ b/source/blender/blenlib/intern/BLI_mempool.c
@@ -36,7 +36,8 @@
 
 #include "BLI_utildefines.h"
 
-#include "BLI_mempool.h" /* own include */
+#include "BLI_mempool.h"         /* own include */
+#include "BLI_mempool_private.h" /* own include */
 
 #include "MEM_guardedalloc.h"
 
@@ -558,33 +559,31 @@ void BLI_mempool_iternew(BLI_mempool *pool, BLI_mempool_iter *iter)
  *
  * See BLI_task_parallel_mempool implementation for detailed usage example.
  */
-BLI_mempool_iter *BLI_mempool_iter_threadsafe_create(BLI_mempool *pool, const size_t num_iter)
+ParallelMempoolTaskData *mempool_iter_threadsafe_create(BLI_mempool *pool, const size_t num_iter)
 {
   BLI_assert(pool->flag & BLI_MEMPOOL_ALLOW_ITER);
 
-  BLI_mempool_iter *iter_arr = MEM_mallocN(sizeof(*iter_arr) * num_iter, __func__);
+  ParallelMempoolTaskData *iter_arr = MEM_mallocN(sizeof(*iter_arr) * num_iter, __func__);
   BLI_mempool_chunk **curchunk_threaded_shared = MEM_mallocN(sizeof(void *), __func__);
 
-  BLI_mempool_iternew(pool, iter_arr);
-
-  *curchunk_threaded_shared = iter_arr->curchunk;
-  iter_arr->curchunk_threaded_shared = curchunk_threaded_shared;
+  BLI_mempool_iternew(pool, &iter_arr->iter);
 
+  *curchunk_threaded_shared = iter_arr->iter.curchunk;
+  iter_arr->iter.curchunk_threaded_shared = curchunk_threaded_shared;
   for (size_t i = 1; i < num_iter; i++) {
-    iter_arr[i] = iter_arr[0];
-    *curchunk_threaded_shared = iter_arr[i].curchunk = ((*curchunk_threaded_shared) ?
-                                                            (*curchunk_threaded_shared)->next :
-                                                            NULL);
+    iter_arr[i].iter = iter_arr[0].iter;
+    *curchunk_threaded_shared = iter_arr[i].iter.curchunk =
+        ((*curchunk_threaded_shared) ? (*curchunk_threaded_shared)->next : NULL);
   }
 
   return iter_arr;
 }
 
-void BLI_mempool_iter_threadsafe_free(BLI_mempool_iter *iter_arr)
+void mempool_iter_threadsafe_destroy(ParallelMempoolTaskData *iter_arr)
 {
-  BLI_assert(iter_arr->curchunk_threaded_shared != NULL);
+  BLI_assert(iter_arr->iter.curchunk_threaded_shared != NULL);
 
-  MEM_freeN(iter_arr->curchunk_threaded_shared);
+  MEM_freeN(iter_arr->iter.curchunk_threaded_shared);
   MEM_freeN(iter_arr);
 }
 
diff --git a/source/blender/blenlib/intern/BLI_mempool_private.h b/source/blender/blenlib/intern/BLI_mempool_private.h
new file mode 100644
index 00000000000..60994624ecd
--- /dev/null
+++ b/source/blender/blenlib/intern/BLI_mempool_private.h
@@ -0,0 +1,45 @@
+/*
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but 

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list