Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/source
diff options
context:
space:
mode:
authorJacques Lucke <jacques@blender.org>2020-07-20 17:00:20 +0300
committerJacques Lucke <jacques@blender.org>2020-07-20 17:03:14 +0300
commitccc2a7996b836cd255fbb7d7f693f5b958442043 (patch)
tree0ce38fb1d1d0980dc73fa6d8816f7f4e82ba46df /source
parented184050b6e787bbfb218e8ad2a0108172a1b68c (diff)
BLI: add typedefs for containers that use raw allocators
Those are useful when you have to create containers with static storage duration. If those would use Blender's guarded allocator, it would report memory leaks, that are not actually leaks.
Diffstat (limited to 'source')
-rw-r--r--source/blender/blenlib/BLI_array.hh12
-rw-r--r--source/blender/blenlib/BLI_map.hh20
-rw-r--r--source/blender/blenlib/BLI_memory_utils.hh9
-rw-r--r--source/blender/blenlib/BLI_set.hh17
-rw-r--r--source/blender/blenlib/BLI_stack.hh12
-rw-r--r--source/blender/blenlib/BLI_vector.hh9
-rw-r--r--source/blender/blenlib/BLI_vector_set.hh11
-rw-r--r--source/blender/blenlib/intern/BLI_index_range.cc4
-rw-r--r--source/blender/depsgraph/intern/depsgraph_registry.cc8
-rw-r--r--source/blender/functions/FN_multi_function_signature.hh6
10 files changed, 81 insertions, 27 deletions
diff --git a/source/blender/blenlib/BLI_array.hh b/source/blender/blenlib/BLI_array.hh
index 871038d7d85..c7b4bdc977f 100644
--- a/source/blender/blenlib/BLI_array.hh
+++ b/source/blender/blenlib/BLI_array.hh
@@ -53,11 +53,8 @@ template<
typename T,
/**
* The number of values that can be stored in the array, without doing a heap allocation.
- *
- * When T is large, the small buffer optimization is disabled by default to avoid large
- * unexpected allocations on the stack. It can still be enabled explicitly though.
*/
- int64_t InlineBufferCapacity = (sizeof(T) < 100) ? 4 : 0,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T)),
/**
* The allocator used by this array. Should rarely be changed, except when you don't want that
* MEM_* functions are used internally.
@@ -364,6 +361,13 @@ class Array {
}
};
+/**
+ * Same as a normal Array, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename T, int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T))>
+using RawArray = Array<T, InlineBufferCapacity, RawAllocator>;
+
} // namespace blender
#endif /* __BLI_ARRAY_HH__ */
diff --git a/source/blender/blenlib/BLI_map.hh b/source/blender/blenlib/BLI_map.hh
index 2abaf814ec9..dd375272fdb 100644
--- a/source/blender/blenlib/BLI_map.hh
+++ b/source/blender/blenlib/BLI_map.hh
@@ -92,11 +92,8 @@ template<
* The minimum number of elements that can be stored in this Map without doing a heap
* allocation. This is useful when you expect to have many small maps. However, keep in mind
* that (unlike vector) initializing a map has a O(n) cost in the number of slots.
- *
- * When Key or Value are large, the small buffer optimization is disabled by default to avoid
- * large unexpected allocations on the stack. It can still be enabled explicitly though.
*/
- int64_t InlineBufferCapacity = (sizeof(Key) + sizeof(Value) < 100) ? 4 : 0,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(Key) + sizeof(Value)),
/**
* The strategy used to deal with collisions. They are defined in BLI_probing_strategies.hh.
*/
@@ -1163,6 +1160,21 @@ class Map {
};
/**
+ * Same as a normal Map, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename Key,
+ typename Value,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(Key) +
+ sizeof(Value)),
+ typename ProbingStrategy = DefaultProbingStrategy,
+ typename Hash = DefaultHash<Key>,
+ typename IsEqual = DefaultEquality,
+ typename Slot = typename DefaultMapSlot<Key, Value>::type>
+using RawMap =
+ Map<Key, Value, InlineBufferCapacity, ProbingStrategy, Hash, IsEqual, Slot, RawAllocator>;
+
+/**
* A wrapper for std::unordered_map with the API of blender::Map. This can be used for
* benchmarking.
*/
diff --git a/source/blender/blenlib/BLI_memory_utils.hh b/source/blender/blenlib/BLI_memory_utils.hh
index 5c692850017..9f65fe0742e 100644
--- a/source/blender/blenlib/BLI_memory_utils.hh
+++ b/source/blender/blenlib/BLI_memory_utils.hh
@@ -419,6 +419,15 @@ template<typename From, typename To>
inline constexpr bool is_convertible_pointer_v =
std::is_convertible_v<From, To> &&std::is_pointer_v<From> &&std::is_pointer_v<To>;
+/**
+ * Inline buffers for small-object-optimization should be disable by default. Otherwise we might
+ * get large unexpected allocations on the stack.
+ */
+inline constexpr int64_t default_inline_buffer_capacity(size_t element_size)
+{
+ return ((int64_t)element_size < 100) ? 4 : 0;
+}
+
} // namespace blender
#endif /* __BLI_MEMORY_UTILS_HH__ */
diff --git a/source/blender/blenlib/BLI_set.hh b/source/blender/blenlib/BLI_set.hh
index 80e4858bbb9..90adea69e06 100644
--- a/source/blender/blenlib/BLI_set.hh
+++ b/source/blender/blenlib/BLI_set.hh
@@ -89,11 +89,8 @@ template<
* The minimum number of elements that can be stored in this Set without doing a heap
* allocation. This is useful when you expect to have many small sets. However, keep in mind
* that (unlike vector) initializing a set has a O(n) cost in the number of slots.
- *
- * When Key is large, the small buffer optimization is disabled by default to avoid large
- * unexpected allocations on the stack. It can still be enabled explicitly though.
*/
- int64_t InlineBufferCapacity = (sizeof(Key) < 100) ? 4 : 0,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(Key)),
/**
* The strategy used to deal with collisions. They are defined in BLI_probing_strategies.hh.
*/
@@ -821,6 +818,18 @@ template<typename Key> class StdUnorderedSetWrapper {
}
};
+/**
+ * Same as a normal Set, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename Key,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(Key)),
+ typename ProbingStrategy = DefaultProbingStrategy,
+ typename Hash = DefaultHash<Key>,
+ typename IsEqual = DefaultEquality,
+ typename Slot = typename DefaultSetSlot<Key>::type>
+using RawSet = Set<Key, InlineBufferCapacity, ProbingStrategy, Hash, IsEqual, Slot, RawAllocator>;
+
} // namespace blender
#endif /* __BLI_SET_HH__ */
diff --git a/source/blender/blenlib/BLI_stack.hh b/source/blender/blenlib/BLI_stack.hh
index 422931862a8..75ae9df79a4 100644
--- a/source/blender/blenlib/BLI_stack.hh
+++ b/source/blender/blenlib/BLI_stack.hh
@@ -73,11 +73,8 @@ template<
* The number of values that can be stored in this stack, without doing a heap allocation.
* Sometimes it can make sense to increase this value a lot. The memory in the inline buffer is
* not initialized when it is not needed.
- *
- * When T is large, the small buffer optimization is disabled by default to avoid large
- * unexpected allocations on the stack. It can still be enabled explicitly though.
*/
- int64_t InlineBufferCapacity = (sizeof(T) < 100) ? 4 : 0,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T)),
/**
* The allocator used by this stack. Should rarely be changed, except when you don't want that
* MEM_* is used internally.
@@ -381,6 +378,13 @@ class Stack {
}
};
+/**
+ * Same as a normal Stack, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename T, int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T))>
+using RawStack = Stack<T, InlineBufferCapacity, RawAllocator>;
+
} /* namespace blender */
#endif /* __BLI_STACK_HH__ */
diff --git a/source/blender/blenlib/BLI_vector.hh b/source/blender/blenlib/BLI_vector.hh
index 11bb00c3f8d..1bb674093bb 100644
--- a/source/blender/blenlib/BLI_vector.hh
+++ b/source/blender/blenlib/BLI_vector.hh
@@ -70,7 +70,7 @@ template<
* When T is large, the small buffer optimization is disabled by default to avoid large
* unexpected allocations on the stack. It can still be enabled explicitly though.
*/
- int64_t InlineBufferCapacity = (sizeof(T) < 100) ? 4 : 0,
+ int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T)),
/**
* The allocator used by this vector. Should rarely be changed, except when you don't want that
* MEM_* is used internally.
@@ -824,6 +824,13 @@ class Vector {
#undef UPDATE_VECTOR_SIZE
+/**
+ * Same as a normal Vector, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename T, int64_t InlineBufferCapacity = default_inline_buffer_capacity(sizeof(T))>
+using RawVector = Vector<T, InlineBufferCapacity, RawAllocator>;
+
} /* namespace blender */
#endif /* __BLI_VECTOR_HH__ */
diff --git a/source/blender/blenlib/BLI_vector_set.hh b/source/blender/blenlib/BLI_vector_set.hh
index 7573b77cdf7..f007d41118f 100644
--- a/source/blender/blenlib/BLI_vector_set.hh
+++ b/source/blender/blenlib/BLI_vector_set.hh
@@ -732,6 +732,17 @@ class VectorSet {
}
};
+/**
+ * Same as a normal VectorSet, but does not use Blender's guarded allocator. This is useful when
+ * allocating memory with static storage duration.
+ */
+template<typename Key,
+ typename ProbingStrategy = DefaultProbingStrategy,
+ typename Hash = DefaultHash<Key>,
+ typename IsEqual = DefaultEquality,
+ typename Slot = typename DefaultVectorSetSlot<Key>::type>
+using RawVectorSet = VectorSet<Key, ProbingStrategy, Hash, IsEqual, Slot, RawAllocator>;
+
} // namespace blender
#endif /* __BLI_VECTOR_SET_HH__ */
diff --git a/source/blender/blenlib/intern/BLI_index_range.cc b/source/blender/blenlib/intern/BLI_index_range.cc
index a906416b491..43c6265a17d 100644
--- a/source/blender/blenlib/intern/BLI_index_range.cc
+++ b/source/blender/blenlib/intern/BLI_index_range.cc
@@ -24,7 +24,7 @@
namespace blender {
-static Vector<Array<int64_t, 0, RawAllocator>, 1, RawAllocator> arrays;
+static RawVector<RawArray<int64_t, 0>> arrays;
static int64_t current_array_size = 0;
static int64_t *current_array = nullptr;
static std::mutex current_array_mutex;
@@ -44,7 +44,7 @@ Span<int64_t> IndexRange::as_span() const
}
int64_t new_size = std::max<int64_t>(1000, power_of_2_max_u(min_required_size));
- Array<int64_t, 0, RawAllocator> new_array(new_size);
+ RawArray<int64_t, 0> new_array(new_size);
for (int64_t i = 0; i < new_size; i++) {
new_array[i] = i;
}
diff --git a/source/blender/depsgraph/intern/depsgraph_registry.cc b/source/blender/depsgraph/intern/depsgraph_registry.cc
index bc3b85f9be5..c9d03e47ded 100644
--- a/source/blender/depsgraph/intern/depsgraph_registry.cc
+++ b/source/blender/depsgraph/intern/depsgraph_registry.cc
@@ -30,9 +30,7 @@
namespace blender {
namespace deg {
-/* TODO: Static variables should use RawAllocator to avoid false positives of Blender's memory leak
- * detector. */
-static Map<Main *, VectorSet<Depsgraph *>> g_graph_registry;
+static RawMap<Main *, RawVectorSet<Depsgraph *>> g_graph_registry;
void register_graph(Depsgraph *depsgraph)
{
@@ -43,7 +41,7 @@ void register_graph(Depsgraph *depsgraph)
void unregister_graph(Depsgraph *depsgraph)
{
Main *bmain = depsgraph->bmain;
- VectorSet<Depsgraph *> &graphs = g_graph_registry.lookup(bmain);
+ RawVectorSet<Depsgraph *> &graphs = g_graph_registry.lookup(bmain);
graphs.remove(depsgraph);
// If this was the last depsgraph associated with the main, remove the main entry as well.
@@ -54,7 +52,7 @@ void unregister_graph(Depsgraph *depsgraph)
Span<Depsgraph *> get_all_registered_graphs(Main *bmain)
{
- VectorSet<Depsgraph *> *graphs = g_graph_registry.lookup_ptr(bmain);
+ RawVectorSet<Depsgraph *> *graphs = g_graph_registry.lookup_ptr(bmain);
if (graphs != nullptr) {
return *graphs;
}
diff --git a/source/blender/functions/FN_multi_function_signature.hh b/source/blender/functions/FN_multi_function_signature.hh
index 4ccceb39503..af5f61fe2ee 100644
--- a/source/blender/functions/FN_multi_function_signature.hh
+++ b/source/blender/functions/FN_multi_function_signature.hh
@@ -33,9 +33,9 @@ namespace blender::fn {
struct MFSignature {
std::string function_name;
/* Use RawAllocator so that a MultiFunction can have static storage duration. */
- Vector<std::string, 4, RawAllocator> param_names;
- Vector<MFParamType, 4, RawAllocator> param_types;
- Vector<int, 4, RawAllocator> param_data_indices;
+ RawVector<std::string> param_names;
+ RawVector<MFParamType> param_types;
+ RawVector<int> param_data_indices;
int data_index(int param_index) const
{