diff --git a/doc/mimalloc-doc.h b/doc/mimalloc-doc.h index e4f8590f..5ad5a1e6 100644 --- a/doc/mimalloc-doc.h +++ b/doc/mimalloc-doc.h @@ -48,20 +48,23 @@ Notable aspects of the design include: - __first-class heaps__: efficiently create and use multiple heaps to allocate across different regions. A heap can be destroyed at once instead of deallocating each object separately. - __bounded__: it does not suffer from _blowup_ \[1\], has bounded worst-case allocation - times (_wcat_), bounded space overhead (~0.2% meta-data, with at most 16.7% waste in allocation sizes), + times (_wcat_), bounded space overhead (~0.2% meta-data, with at most 12.5% waste in allocation sizes), and has no internal points of contention using only atomic operations. - __fast__: In our benchmarks (see [below](#performance)), _mimalloc_ always outperforms all other leading allocators (_jemalloc_, _tcmalloc_, _Hoard_, etc), and usually uses less memory (up to 25% more in the worst case). A nice property is that it does consistently well over a wide range of benchmarks. -You can read more on the design of _mimalloc_ in the upcoming technical report +You can read more on the design of _mimalloc_ in the +[technical report](https://www.microsoft.com/en-us/research/publication/mimalloc-free-list-sharding-in-action) which also has detailed benchmark results. + Further information: - \ref build - \ref using +- \ref environment - \ref overrides - \ref bench - \ref malloc @@ -293,31 +296,34 @@ size_t mi_good_size(size_t size); /// resource usage by calling this every once in a while. void mi_collect(bool force); -/// Print statistics. -/// @param out Output file. Use \a NULL for \a stderr. +/// Print the main statistics. +/// @param out Output function. Use \a NULL for outputting to \a stderr. /// /// Most detailed when using a debug build. -void mi_stats_print(FILE* out); +void mi_stats_print(mi_output_fun* out); /// Reset statistics. -void mi_stats_reset(); +void mi_stats_reset(void); + +/// Merge thread local statistics with the main statistics and reset. +void mi_stats_merge(void); /// Initialize mimalloc on a thread. /// Should not be used as on most systems (pthreads, windows) this is done /// automatically. -void mi_thread_init(); +void mi_thread_init(void); /// Uninitialize mimalloc on a thread. /// Should not be used as on most systems (pthreads, windows) this is done /// automatically. Ensures that any memory that is not freed yet (but will /// be freed by other threads in the future) is properly handled. -void mi_thread_done(); +void mi_thread_done(void); /// Print out heap statistics for this thread. -/// @param out Output file. Use \a NULL for \a stderr. +/// @param out Output function. Use \a NULL for outputting to \a stderr. /// /// Most detailed when using a debug build. -void mi_thread_stats_print(FILE* out); +void mi_thread_stats_print(mi_output_fun* out); /// Type of deferred free functions. /// @param force If \a true all outstanding items should be freed. @@ -342,6 +348,45 @@ typedef void (mi_deferred_free_fun)(bool force, unsigned long long heartbeat); /// At most one \a deferred_free function can be active. void mi_register_deferred_free(mi_deferred_free_fun* deferred_free); +/// Type of output functions. +/// @param msg Message to output. +/// +/// @see mi_register_output() +typedef void (mi_output_fun)(const char* msg); + +/// Register an output function. +/// @param out The output function, use `NULL` to output to stdout. +/// +/// The `out` function is called to output any information from mimalloc, +/// like verbose or warning messages. +void mi_register_output(mi_output_fun* out) mi_attr_noexcept; + +/// Is a pointer part of our heap? +/// @param p The pointer to check. +/// @returns \a true if this is a pointer into our heap. +/// This function is relatively fast. +bool mi_is_in_heap_region(const void* p); + +/// Reserve \a pages of huge OS pages (1GiB) but stops after at most `max_secs` seconds. +/// @param pages The number of 1GiB pages to reserve. +/// @param max_secs Maximum number of seconds to try reserving. +/// @param pages_reserved If not \a NULL, it is set to the actual number of pages that were reserved. +/// @returns 0 if successfull, \a ENOMEM if running out of memory, or \a ETIMEDOUT if timed out. +/// +/// The reserved memory is used by mimalloc to satisfy allocations. +/// May quit before \a max_secs are expired if it estimates it will take more than +/// 1.5 times \a max_secs. The time limit is needed because on some operating systems +/// it can take a long time to reserve contiguous memory if the physical memory is +/// fragmented. +int mi_reserve_huge_os_pages(size_t pages, double max_secs, size_t* pages_reserved); + +/// Is the C runtime \a malloc API redirected? +/// @returns \a true if all malloc API calls are redirected to mimalloc. +/// +/// Currenty only used on Windows. +bool mi_is_redirected(); + + /// \} // ------------------------------------------------------ @@ -443,10 +488,18 @@ mi_heap_t* mi_heap_get_default(); /// except by exiting the thread. mi_heap_t* mi_heap_get_backing(); +/// Release outstanding resources in a specific heap. +void mi_heap_collect(mi_heap_t* heap, bool force); + /// Allocate in a specific heap. /// @see mi_malloc() void* mi_heap_malloc(mi_heap_t* heap, size_t size); +/// Allocate a small object in a specific heap. +/// \a size must be smaller or equal to MI_SMALL_SIZE_MAX(). +/// @see mi_malloc() +void* mi_heap_malloc_small(mi_heap_t* heap, size_t size); + /// Allocate zero-initialized in a specific heap. /// @see mi_zalloc() void* mi_heap_zalloc(mi_heap_t* heap, size_t size); @@ -486,6 +539,34 @@ void* mi_heap_realloc_aligned_at(mi_heap_t* heap, void* p, size_t newsize, size_ /// \} + +/// \defgroup zeroinit Zero initialized re-allocation +/// +/// The zero-initialized re-allocations are only valid on memory that was +/// originally allocated with zero initialization too. +/// e.g. `mi_calloc`, `mi_zalloc`, `mi_zalloc_aligned` etc. +/// see +/// +/// \{ + +void* mi_rezalloc(void* p, size_t newsize); +void* mi_recalloc(void* p, size_t newcount, size_t size) ; + +void* mi_rezalloc_aligned(void* p, size_t newsize, size_t alignment); +void* mi_rezalloc_aligned_at(void* p, size_t newsize, size_t alignment, size_t offset); +void* mi_recalloc_aligned(void* p, size_t newcount, size_t size, size_t alignment); +void* mi_recalloc_aligned_at(void* p, size_t newcount, size_t size, size_t alignment, size_t offset); + +void* mi_heap_rezalloc(mi_heap_t* heap, void* p, size_t newsize); +void* mi_heap_recalloc(mi_heap_t* heap, void* p, size_t newcount, size_t size); + +void* mi_heap_rezalloc_aligned(mi_heap_t* heap, void* p, size_t newsize, size_t alignment); +void* mi_heap_rezalloc_aligned_at(mi_heap_t* heap, void* p, size_t newsize, size_t alignment, size_t offset); +void* mi_heap_recalloc_aligned(mi_heap_t* heap, void* p, size_t newcount, size_t size, size_t alignment); +void* mi_heap_recalloc_aligned_at(mi_heap_t* heap, void* p, size_t newcount, size_t size, size_t alignment, size_t offset); + +/// \} + /// \defgroup typed Typed Macros /// /// Typed allocation macros @@ -532,6 +613,9 @@ void* mi_heap_realloc_aligned_at(mi_heap_t* heap, void* p, size_t newsize, size_ /// Re-allocate to \a count blocks of type \a tp in a heap \a hp. #define mi_heap_reallocn_tp(hp,p,tp,count) ((tp*)mi_heap_reallocn(p,count,sizeof(tp))) +/// Re-allocate to \a count zero initialized blocks of type \a tp in a heap \a hp. +#define mi_heap_recalloc_tp(hp,p,tp,count) ((tp*)mi_heap_recalloc(p,count,sizeof(tp))) + /// \} /// \defgroup analysis Heap Introspection @@ -614,14 +698,17 @@ typedef enum mi_option_e { mi_option_show_errors, ///< Print error messages to `stderr`. mi_option_verbose, ///< Print verbose messages to `stderr`. // the following options are experimental - mi_option_secure, ///< Experimental mi_option_eager_commit, ///< Eagerly commit segments (4MiB) (enabled by default). - mi_option_eager_region_commit, ///< Eagerly commit large (256MiB) memory regions (enabled by default except on Windows) - mi_option_large_os_pages, ///< Use large OS pages if possible + mi_option_eager_region_commit, ///< Eagerly commit large (256MiB) memory regions (enabled by default, except on Windows) + mi_option_large_os_pages, ///< Use large OS pages (2MiB in size) if possible + mi_option_reserve_huge_os_pages, ///< The number of huge OS pages (1GiB in size) to reserve at the start of the program. + mi_option_segment_cache, ///< The number of segments per thread to keep cached. mi_option_page_reset, ///< Reset page memory when it becomes free. mi_option_cache_reset, ///< Reset segment memory when a segment is cached. mi_option_reset_decommits, ///< Experimental - mi_option_reset_discards, ///< Experimental + mi_option_eager_commit_delay, ///< Experimental + mi_option_segment_reset, ///< Experimental + mi_option_os_tag, ///< OS tag to assign to mimalloc'd memory _mi_option_last } mi_option_t; @@ -647,6 +734,8 @@ void mi_option_set_default(mi_option_t option, long value); void* mi_recalloc(void* p, size_t count, size_t size); size_t mi_malloc_size(const void* p); size_t mi_malloc_usable_size(const void *p); + +/// Just as `free` but also checks if the pointer `p` belongs to our heap. void mi_cfree(void* p); int mi_posix_memalign(void** p, size_t alignment, size_t size); @@ -804,9 +893,12 @@ completely and redirect all calls to the _mimalloc_ library instead. See \ref overrides for more info. -## Environment Options +*/ -You can set further options either programmatically (using [`mi_option_set`](https://microsoft.github.io/mimalloc/group__options.html)), +/*! \page environment Environment Options + +You can set further options either programmatically +(using [`mi_option_set`](https://microsoft.github.io/mimalloc/group__options.html)), or via environment variables. - `MIMALLOC_SHOW_STATS=1`: show statistics when the program terminates. @@ -869,19 +961,23 @@ Note: unfortunately, at this time, dynamic overriding on macOS seems broken but ### Windows On Windows you need to link your program explicitly with the mimalloc -DLL, and use the C-runtime library as a DLL (the `/MD` or `/MDd` switch). -To ensure the mimalloc DLL gets loaded it is easiest to insert some +DLL and use the C-runtime library as a DLL (using the `/MD` or `/MDd` switch). +Moreover, you need to ensure the `mimalloc-redirect.dll` (or `mimalloc-redirect32.dll`) is available +in the same folder as the mimalloc DLL at runtime (as it as referred to by the mimalloc DLL). +The redirection DLL's ensure all calls to the C runtime malloc API get redirected to mimalloc. + +To ensure the mimalloc DLL is loaded at run-time it is easiest to insert some call to the mimalloc API in the `main` function, like `mi_version()` -(or use the `/INCLUDE:mi_version` switch on the linker) +(or use the `/INCLUDE:mi_version` switch on the linker). See the `mimalloc-override-test` project +for an example on how to use this. -Due to the way mimalloc intercepts the standard malloc at runtime, it is best -to link to the mimalloc import library first on the command line so it gets -loaded right after the universal C runtime DLL (`ucrtbase`). See -the `mimalloc-override-test` project for an example. +The environment variable `MIMALLOC_DISABLE_REDIRECT=1` can be used to disable dynamic +overriding at run-time. Use `MIMALLOC_VERBOSE=1` to check if mimalloc successfully redirected. -Note: the current overriding on Windows works for most programs but some programs still have -trouble -- the `dev-exp` branch contains a newer way of overriding that is more -robust; try this out if you experience troubles. +(Note: in principle, it should be possible to patch existing executables +that are linked with the dynamic C runtime (`ucrtbase.dll`) by just putting the mimalloc DLL into +the import table (and putting `mimalloc-redirect.dll` in the same folder) +Such patching can be done for example with [CFF Explorer](https://ntcore.com/?page_id=388)). ## Static override @@ -897,8 +993,6 @@ object file. For example: gcc -o myprogram mimalloc-override.o myfile1.c ... ``` - - ## List of Overrides: The specific functions that get redirected to the _mimalloc_ library are: diff --git a/docs/group__extended.html b/docs/group__extended.html index 8ab087e1..4d07f38d 100644 --- a/docs/group__extended.html +++ b/docs/group__extended.html @@ -121,6 +121,9 @@ Typedefs typedef void() mi_deferred_free_fun(bool force, unsigned long long heartbeat)  Type of deferred free functions. More...
  +typedef void() mi_output_fun(const char *msg) + Type of output functions. More...
+  @@ -139,24 +142,39 @@ Functions - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Functions

void mi_collect (bool force)
 Eagerly free memory. More...
 
void mi_stats_print (FILE *out)
 Print statistics. More...
 
void mi_stats_reset ()
 Reset statistics. More...
 
void mi_thread_init ()
 Initialize mimalloc on a thread. More...
 
void mi_thread_done ()
 Uninitialize mimalloc on a thread. More...
 
void mi_thread_stats_print (FILE *out)
 Print out heap statistics for this thread. More...
 
void mi_stats_print (mi_output_fun *out)
 Print the main statistics. More...
 
void mi_stats_reset (void)
 Reset statistics. More...
 
void mi_stats_merge (void)
 Merge thread local statistics with the main statistics and reset. More...
 
void mi_thread_init (void)
 Initialize mimalloc on a thread. More...
 
void mi_thread_done (void)
 Uninitialize mimalloc on a thread. More...
 
void mi_thread_stats_print (mi_output_fun *out)
 Print out heap statistics for this thread. More...
 
void mi_register_deferred_free (mi_deferred_free_fun *deferred_free)
 Register a deferred free function. More...
 
void mi_register_output (mi_output_fun *out) mi_attr_noexcept
 Register an output function. More...
 
bool mi_is_in_heap_region (const void *p)
 Is a pointer part of our heap? More...
 
int mi_reserve_huge_os_pages (size_t pages, double max_secs, size_t *pages_reserved)
 Reserve pages of huge OS pages (1GiB) but stops after at most max_secs seconds. More...
 
bool mi_is_redirected ()
 Is the C runtime malloc API redirected? More...
 

Detailed Description

Extended functionality.

@@ -200,6 +218,29 @@ Functions
See also
mi_register_deferred_free
+ + + +

◆ mi_output_fun

+ +
+
+ + + + +
typedef void() mi_output_fun(const char *msg)
+
+ +

Type of output functions.

+
Parameters
+ + +
msgMessage to output.
+
+
+
See also
mi_register_output()
+

Function Documentation

@@ -257,6 +298,54 @@ Functions

Generally, mi_usable_size(mi_malloc(size)) == mi_good_size(size). This can be used to reduce internal wasted space when allocating buffers for example.

See also
mi_usable_size()
+ + + +

◆ mi_is_in_heap_region()

+ +
+
+ + + + + + + + +
bool mi_is_in_heap_region (const void * p)
+
+ +

Is a pointer part of our heap?

+
Parameters
+ + +
pThe pointer to check.
+
+
+
Returns
true if this is a pointer into our heap. This function is relatively fast.
+ +
+
+ +

◆ mi_is_redirected()

+ +
+
+ + + + + + + +
bool mi_is_redirected ()
+
+ +

Is the C runtime malloc API redirected?

+
Returns
true if all malloc API calls are redirected to mimalloc.
+

Currenty only used on Windows.

+
@@ -313,8 +402,101 @@ Functions - -

◆ mi_stats_print()

+ +

◆ mi_register_output()

+ +
+
+ + + + + + + + +
void mi_register_output (mi_output_funout)
+
+ +

Register an output function.

+
Parameters
+ + +
outThe output function, use NULL to output to stdout.
+
+
+

The out function is called to output any information from mimalloc, like verbose or warning messages.

+ +
+
+ +

◆ mi_reserve_huge_os_pages()

+ +
+
+ + + + + + + + + + + + + + + + + + + + + + + + +
int mi_reserve_huge_os_pages (size_t pages,
double max_secs,
size_t * pages_reserved 
)
+
+ +

Reserve pages of huge OS pages (1GiB) but stops after at most max_secs seconds.

+
Parameters
+ + + + +
pagesThe number of 1GiB pages to reserve.
max_secsMaximum number of seconds to try reserving.
pages_reservedIf not NULL, it is set to the actual number of pages that were reserved.
+
+
+
Returns
0 if successfull, ENOMEM if running out of memory, or ETIMEDOUT if timed out.
+

The reserved memory is used by mimalloc to satisfy allocations. May quit before max_secs are expired if it estimates it will take more than 1.5 times max_secs. The time limit is needed because on some operating systems it can take a long time to reserve contiguous memory if the physical memory is fragmented.

+ +
+
+ +

◆ mi_stats_merge()

+ +
+
+ + + + + + + + +
void mi_stats_merge (void )
+
+ +

Merge thread local statistics with the main statistics and reset.

+ +
+
+ +

◆ mi_stats_print()

@@ -322,17 +504,17 @@ Functions void mi_stats_print ( - FILE *  + mi_output_funout)
-

Print statistics.

+

Print the main statistics.

Parameters
- +
outOutput file. Use NULL for stderr.
outOutput function. Use NULL for outputting to stderr.
@@ -340,8 +522,8 @@ Functions
- -

◆ mi_stats_reset()

+ +

◆ mi_stats_reset()

@@ -349,6 +531,7 @@ Functions void mi_stats_reset ( + void  ) @@ -359,8 +542,8 @@ Functions
- -

◆ mi_thread_done()

+ +

◆ mi_thread_done()

@@ -368,6 +551,7 @@ Functions void mi_thread_done ( + void  ) @@ -379,8 +563,8 @@ Functions
- -

◆ mi_thread_init()

+ +

◆ mi_thread_init()

@@ -388,6 +572,7 @@ Functions void mi_thread_init ( + void  ) @@ -399,8 +584,8 @@ Functions
- -

◆ mi_thread_stats_print()

+ +

◆ mi_thread_stats_print()

@@ -408,7 +593,7 @@ Functions void mi_thread_stats_print ( - FILE *  + mi_output_funout) @@ -418,7 +603,7 @@ Functions

Print out heap statistics for this thread.

Parameters
- +
outOutput file. Use NULL for stderr.
outOutput function. Use NULL for outputting to stderr.
diff --git a/docs/group__extended.js b/docs/group__extended.js index fd2ce8a5..00c73614 100644 --- a/docs/group__extended.js +++ b/docs/group__extended.js @@ -2,15 +2,21 @@ var group__extended = [ [ "MI_SMALL_SIZE_MAX", "group__extended.html#ga1ea64283508718d9d645c38efc2f4305", null ], [ "mi_deferred_free_fun", "group__extended.html#ga22213691c3ce5ab4d91b24aff1023529", null ], + [ "mi_output_fun", "group__extended.html#ga2bed6d40b74591a67f81daea4b4a246f", null ], [ "mi_collect", "group__extended.html#ga421430e2226d7d468529cec457396756", null ], [ "mi_good_size", "group__extended.html#gac057927cd06c854b45fe7847e921bd47", null ], + [ "mi_is_in_heap_region", "group__extended.html#ga5f071b10d4df1c3658e04e7fd67a94e6", null ], + [ "mi_is_redirected", "group__extended.html#gaad25050b19f30cd79397b227e0157a3f", null ], [ "mi_malloc_small", "group__extended.html#ga7136c2e55cb22c98ecf95d08d6debb99", null ], [ "mi_register_deferred_free", "group__extended.html#ga24dc9cc6fca8daa2aa30aa8025467ce2", null ], - [ "mi_stats_print", "group__extended.html#ga6bb821ca1b664b452112c0e17b15fcf1", null ], - [ "mi_stats_reset", "group__extended.html#ga9883b8a059aed7eb0888a01ec1461161", null ], - [ "mi_thread_done", "group__extended.html#gac0f4849256aaf677f334690952c6ebbd", null ], - [ "mi_thread_init", "group__extended.html#ga9398517f01a1ec971244aa0db084ea46", null ], - [ "mi_thread_stats_print", "group__extended.html#ga490826cbd7c494acc9fe69be23f018ac", null ], + [ "mi_register_output", "group__extended.html#ga84a0c8b401e42eb5b1bce156852f44c5", null ], + [ "mi_reserve_huge_os_pages", "group__extended.html#ga2664f36a2dd557741c429cb799f04641", null ], + [ "mi_stats_merge", "group__extended.html#ga854b1de8cb067c7316286c28b2fcd3d1", null ], + [ "mi_stats_print", "group__extended.html#ga8ca07ccff283956d71f48272f4fd5c01", null ], + [ "mi_stats_reset", "group__extended.html#ga3bb8468b8cfcc6e2a61d98aee85c5f99", null ], + [ "mi_thread_done", "group__extended.html#ga0ae4581e85453456a0d658b2b98bf7bf", null ], + [ "mi_thread_init", "group__extended.html#gaf8e73efc2cbca9ebfdfb166983a04c17", null ], + [ "mi_thread_stats_print", "group__extended.html#ga489670a15d1a257ab4639e645ee4612a", null ], [ "mi_usable_size", "group__extended.html#ga089c859d9eddc5f9b4bd946cd53cebee", null ], [ "mi_zalloc_small", "group__extended.html#ga220f29f40a44404b0061c15bc1c31152", null ] ]; \ No newline at end of file diff --git a/docs/group__heap.html b/docs/group__heap.html index cc970c7a..753aaba3 100644 --- a/docs/group__heap.html +++ b/docs/group__heap.html @@ -135,9 +135,15 @@ Functions mi_heap_tmi_heap_get_backing ()  Get the backing heap. More...
  +void mi_heap_collect (mi_heap_t *heap, bool force) + Release outstanding resources in a specific heap. More...
+  void * mi_heap_malloc (mi_heap_t *heap, size_t size)  Allocate in a specific heap. More...
  +void * mi_heap_malloc_small (mi_heap_t *heap, size_t size) + Allocate a small object in a specific heap. More...
+  void * mi_heap_zalloc (mi_heap_t *heap, size_t size)  Allocate zero-initialized in a specific heap. More...
  @@ -321,6 +327,36 @@ Functions
+
+
+ +

◆ mi_heap_collect()

+ +
+
+ + + + + + + + + + + + + + + + + + +
void mi_heap_collect (mi_heap_theap,
bool force 
)
+
+ +

Release outstanding resources in a specific heap.

+
@@ -510,6 +546,37 @@ Functions
+
+ + +

◆ mi_heap_malloc_small()

+ +
+
+ + + + + + + + + + + + + + + + + + +
void* mi_heap_malloc_small (mi_heap_theap,
size_t size 
)
+
+ +

Allocate a small object in a specific heap.

+

size must be smaller or equal to MI_SMALL_SIZE_MAX().

See also
mi_malloc()
+
diff --git a/docs/group__heap.js b/docs/group__heap.js index 7e908c04..13d13778 100644 --- a/docs/group__heap.js +++ b/docs/group__heap.js @@ -4,6 +4,7 @@ var group__heap = [ "mi_heap_calloc", "group__heap.html#gaa6702b3c48e9e53e50e81b36f5011d55", null ], [ "mi_heap_calloc_aligned", "group__heap.html#ga4af03a6e2b93fae77424d93f889705c3", null ], [ "mi_heap_calloc_aligned_at", "group__heap.html#ga08ca6419a5c057a4d965868998eef487", null ], + [ "mi_heap_collect", "group__heap.html#ga7922f7495cde30b1984d0e6072419298", null ], [ "mi_heap_delete", "group__heap.html#ga2ab1af8d438819b55319c7ef51d1e409", null ], [ "mi_heap_destroy", "group__heap.html#ga9f9c0844edb9717f4feacd79116b8e0d", null ], [ "mi_heap_get_backing", "group__heap.html#ga5d03fbe062ffcf38f0f417fd968357fc", null ], @@ -11,6 +12,7 @@ var group__heap = [ "mi_heap_malloc", "group__heap.html#ga9cbed01e42c0647907295de92c3fa296", null ], [ "mi_heap_malloc_aligned", "group__heap.html#gab5b87e1805306f70df38789fcfcf6653", null ], [ "mi_heap_malloc_aligned_at", "group__heap.html#ga23acd7680fb0976dde3783254c6c874b", null ], + [ "mi_heap_malloc_small", "group__heap.html#gaa1a1c7a1f4da6826b5a25b70ef878368", null ], [ "mi_heap_mallocn", "group__heap.html#ga851da6c43fe0b71c1376cee8aef90db0", null ], [ "mi_heap_new", "group__heap.html#ga766f672ba56f2fbfeb9d9dbb0b7f6b11", null ], [ "mi_heap_realloc", "group__heap.html#gaaef3395f66be48f37bdc8322509c5d81", null ], diff --git a/docs/group__options.html b/docs/group__options.html index e8a0bbd6..a34a9307 100644 --- a/docs/group__options.html +++ b/docs/group__options.html @@ -115,16 +115,20 @@ Enumerations   mi_option_show_stats, mi_option_show_errors, mi_option_verbose, -mi_option_secure, +mi_option_eager_commit,
-  mi_option_eager_commit, -mi_option_eager_region_commit, +  mi_option_eager_region_commit, mi_option_large_os_pages, -mi_option_page_reset, +mi_option_reserve_huge_os_pages, +mi_option_segment_cache,
-  mi_option_cache_reset, +  mi_option_page_reset, +mi_option_cache_reset, mi_option_reset_decommits, -mi_option_reset_discards, +mi_option_eager_commit_delay, +
+  mi_option_segment_reset, +mi_option_os_tag, _mi_option_last
} @@ -169,13 +173,15 @@ Functions mi_option_verbose 

Print verbose messages to stderr.

-mi_option_secure 

Experimental.

- mi_option_eager_commit 

Eagerly commit segments (4MiB) (enabled by default).

-mi_option_eager_region_commit 

Eagerly commit large (256MiB) memory regions (enabled by default except on Windows)

+mi_option_eager_region_commit 

Eagerly commit large (256MiB) memory regions (enabled by default, except on Windows)

-mi_option_large_os_pages 

Use large OS pages if possible.

+mi_option_large_os_pages 

Use large OS pages (2MiB in size) if possible.

+ +mi_option_reserve_huge_os_pages 

The number of huge OS pages (1GiB in size) to reserve at the start of the program.

+ +mi_option_segment_cache 

The number of segments per thread to keep cached.

mi_option_page_reset 

Reset page memory when it becomes free.

@@ -183,7 +189,11 @@ Functions mi_option_reset_decommits 

Experimental.

-mi_option_reset_discards 

Experimental.

+mi_option_eager_commit_delay 

Experimental.

+ +mi_option_segment_reset 

Experimental.

+ +mi_option_os_tag 

OS tag to assign to mimalloc'd memory.

_mi_option_last  diff --git a/docs/group__options.js b/docs/group__options.js index 485dc83d..4bf52d54 100644 --- a/docs/group__options.js +++ b/docs/group__options.js @@ -4,14 +4,17 @@ var group__options = [ "mi_option_show_stats", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca0957ef73b2550764b4840edf48422fda", null ], [ "mi_option_show_errors", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cafbf4822e5c00732c5984b32a032837f0", null ], [ "mi_option_verbose", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca7c8b7bf5281c581bad64f5daa6442777", null ], - [ "mi_option_secure", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca083ee20765063fc6d727e11d33cf378f", null ], [ "mi_option_eager_commit", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca1e8de72c93da7ff22d91e1e27b52ac2b", null ], [ "mi_option_eager_region_commit", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca32ce97ece29f69e82579679cf8a307ad", null ], [ "mi_option_large_os_pages", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca4192d491200d0055df0554d4cf65054e", null ], + [ "mi_option_reserve_huge_os_pages", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884caca7ed041be3b0b9d0b82432c7bf41af2", null ], + [ "mi_option_segment_cache", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca2ecbe7ef32f5c84de3739aa4f0b805a1", null ], [ "mi_option_page_reset", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cada854dd272c66342f18a93ee254a2968", null ], [ "mi_option_cache_reset", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cac2157a0cb79cd996c1db7d9f6a090c07", null ], [ "mi_option_reset_decommits", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cac81ee965b130fa81238913a3c239d536", null ], - [ "mi_option_reset_discards", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cab3a837b5ceee250e14e051dbee2a441b", null ], + [ "mi_option_eager_commit_delay", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca17a190c25be381142d87e0468c4c068c", null ], + [ "mi_option_segment_reset", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884cafb121d30d87591850d5410ccc3a95c6d", null ], + [ "mi_option_os_tag", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca4b74ae2a69e445de6c2361b73c1d14bf", null ], [ "_mi_option_last", "group__options.html#ggafebf7ed116adb38ae5218bc3ce06884ca5b4357b74be0d87568036c32eb1a2e4a", null ] ] ], [ "mi_option_enable", "group__options.html#ga6d45a20a3131f18bc351b69763b38ce4", null ], diff --git a/docs/group__posix.html b/docs/group__posix.html index 6d0ca57c..b9cf0b52 100644 --- a/docs/group__posix.html +++ b/docs/group__posix.html @@ -115,6 +115,7 @@ Functions size_t mi_malloc_usable_size (const void *p)   void mi_cfree (void *p) + Just as free but also checks if the pointer p belongs to our heap. More...
  int mi_posix_memalign (void **p, size_t alignment, size_t size)   @@ -231,6 +232,8 @@ Functions
+

Just as free but also checks if the pointer p belongs to our heap.

+
diff --git a/docs/group__typed.html b/docs/group__typed.html index c0a52c4b..8ea0f095 100644 --- a/docs/group__typed.html +++ b/docs/group__typed.html @@ -140,6 +140,9 @@ Macros #define mi_heap_reallocn_tp(hp, p, tp, count)  Re-allocate to count blocks of type tp in a heap hp. More...
  +#define mi_heap_recalloc_tp(hp, p, tp, count) + Re-allocate to count zero initialized blocks of type tp in a heap hp. More...

Detailed Description

Typed allocation macros.

@@ -316,6 +319,48 @@ Macros

Re-allocate to count blocks of type tp in a heap hp.

+ + + +

◆ mi_heap_recalloc_tp

+ +
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
#define mi_heap_recalloc_tp( hp,
 p,
 tp,
 count 
)
+
+ +

Re-allocate to count zero initialized blocks of type tp in a heap hp.

+
diff --git a/docs/group__typed.js b/docs/group__typed.js index 095a5b4a..c6be55d8 100644 --- a/docs/group__typed.js +++ b/docs/group__typed.js @@ -5,6 +5,7 @@ var group__typed = [ "mi_heap_malloc_tp", "group__typed.html#ga653bcb24ac495bc19940ecd6898f9cd7", null ], [ "mi_heap_mallocn_tp", "group__typed.html#ga6b75cb9c4b9c647661d0924552dc6e83", null ], [ "mi_heap_reallocn_tp", "group__typed.html#gaf213d5422ec35e7f6caad827c79bc948", null ], + [ "mi_heap_recalloc_tp", "group__typed.html#ga3e50a1600958fcaf1a7f3560c9174f9e", null ], [ "mi_heap_zalloc_tp", "group__typed.html#gad6e87e86e994aa14416ae9b5d4c188fe", null ], [ "mi_malloc_tp", "group__typed.html#ga0619a62c5fd886f1016030abe91f0557", null ], [ "mi_mallocn_tp", "group__typed.html#gae5cb6e0fafc9f23169c5622e077afe8b", null ], diff --git a/docs/index.html b/docs/index.html index 68127d24..bf758c3c 100644 --- a/docs/index.html +++ b/docs/index.html @@ -110,14 +110,15 @@ $(document).ready(function(){initNavTree('index.html','');});
  • eager page reset: when a "page" becomes empty (with increased chance due to free list sharding) the memory is marked to the OS as unused ("reset" or "purged") reducing (real) memory pressure and fragmentation, especially in long running programs.
  • secure: mimalloc can be build in secure mode, adding guard pages, randomized allocation, encrypted free lists, etc. to protect against various heap vulnerabilities. The performance penalty is only around 3% on average over our benchmarks.
  • first-class heaps: efficiently create and use multiple heaps to allocate across different regions. A heap can be destroyed at once instead of deallocating each object separately.
  • -
  • bounded: it does not suffer from blowup [1], has bounded worst-case allocation times (wcat), bounded space overhead (~0.2% meta-data, with at most 16.7% waste in allocation sizes), and has no internal points of contention using only atomic operations.
  • +
  • bounded: it does not suffer from blowup [1], has bounded worst-case allocation times (wcat), bounded space overhead (~0.2% meta-data, with at most 12.5% waste in allocation sizes), and has no internal points of contention using only atomic operations.
  • fast: In our benchmarks (see below), mimalloc always outperforms all other leading allocators (jemalloc, tcmalloc, Hoard, etc), and usually uses less memory (up to 25% more in the worst case). A nice property is that it does consistently well over a wide range of benchmarks.
  • -

    You can read more on the design of mimalloc in the upcoming technical report which also has detailed benchmark results.

    +

    You can read more on the design of mimalloc in the technical report which also has detailed benchmark results.

    Further information: