/* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this file, * You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef mozmemory_wrap_h #define mozmemory_wrap_h /* * This header contains #defines which tweak the names of various memory * allocation functions. * * There are several types of functions related to memory allocation * that are meant to be used publicly by the Gecko codebase: * * - malloc implementation functions: * - malloc * - posix_memalign * - aligned_alloc * - calloc * - realloc * - free * - memalign * - valloc * - malloc_usable_size * - malloc_good_size * Some of these functions are specific to some systems, but for * convenience, they are treated as being cross-platform, and available * as such. * * - duplication functions: * - strndup * - strdup * - wcsdup (Windows only) * * - jemalloc specific functions: * - jemalloc_stats * - jemalloc_purge_freed_pages * - jemalloc_free_dirty_pages * (these functions are native to mozjemalloc, and have compatibility * implementations for jemalloc3) * * These functions are all exported as part of libmozglue (see * $(topsrcdir)/mozglue/build/Makefile.in), with a few implementation * peculiarities: * * - On Windows, the malloc implementation functions are all prefixed with * "je_", the duplication functions are prefixed with "wrap_", and jemalloc * specific functions are left unprefixed. All these functions are however * aliased when exporting them, such that the resulting mozglue.dll exports * them unprefixed (see $(topsrcdir)/mozglue/build/mozglue.def.in). The * prefixed malloc implementation and duplication functions are not * exported. * * - On MacOSX, the system libc has a zone allocator, which allows us to * hook custom malloc implementation functions without exporting them. * The malloc implementation functions are all prefixed with "je_" and used * this way from the custom zone allocator. They are not exported. * Duplication functions are not included, since they will call the custom * zone allocator anyways. Jemalloc-specific functions are also left * unprefixed. * * - On Android and Gonk, all functions are left unprefixed. Additionally, * C++ allocation functions (operator new/delete) are also exported and * unprefixed. * * - On other systems (mostly Linux), all functions are left unprefixed. * * Only Android and Gonk add C++ allocation functions. * * Proper exporting of the various functions is done with the MOZ_MEMORY_API * and MOZ_JEMALLOC_API macros. MOZ_MEMORY_API is meant to be used for malloc * implementation and duplication functions, while MOZ_JEMALLOC_API is * dedicated to jemalloc specific functions. * * * All these functions are meant to be called with no prefix from Gecko code. * In most cases, this is because that's how they are available at runtime. * However, on Android, this relies on faulty.lib (the custom dynamic linker) * resolving mozglue symbols before libc symbols, which is guaranteed by the * way faulty.lib works (it respects the DT_NEEDED order, and libc always * appears after mozglue ; which we double check when building anyways) * * * Within libmozglue (when MOZ_MEMORY_IMPL is defined), all the functions * should be suffixed with "_impl" both for declarations and use. * That is, the implementation declaration for e.g. strdup would look like: * char* strdup_impl(const char *) * That implementation would call malloc by using "malloc_impl". * * While mozjemalloc uses these "_impl" suffixed helpers, jemalloc3, being * third-party code, doesn't, but instead has an elaborate way to mangle * individual functions. See under "Run jemalloc configure script" in * $(topsrcdir)/configure.in. * * * When building with replace-malloc support, the above still holds, but * the malloc implementation and jemalloc specific functions are the * replace-malloc functions from replace_malloc.c. * * The actual jemalloc/mozjemalloc implementation is prefixed with "je_". * * Thus, when MOZ_REPLACE_MALLOC is defined, the "_impl" suffixed macros * expand to "je_" prefixed function when building mozjemalloc or * jemalloc3/mozjemalloc_compat, where MOZ_JEMALLOC_IMPL is defined. * * In other cases, the "_impl" suffixed macros follow the original scheme, * except on Windows and MacOSX, where they would expand to "je_" prefixed * functions. Instead, they are left unmodified (malloc_impl expands to * malloc_impl). */ #ifndef MOZ_MEMORY # error Should only include mozmemory_wrap.h when MOZ_MEMORY is set. #endif #if defined(MOZ_JEMALLOC_IMPL) && !defined(MOZ_MEMORY_IMPL) # define MOZ_MEMORY_IMPL #endif #if defined(MOZ_MEMORY_IMPL) && !defined(IMPL_MFBT) # ifdef MFBT_API /* mozilla/Types.h was already included */ # error mozmemory_wrap.h has to be included before mozilla/Types.h when MOZ_MEMORY_IMPL is set and IMPL_MFBT is not. # endif # define IMPL_MFBT #endif #include "mozilla/Types.h" #if !defined(MOZ_NATIVE_JEMALLOC) # ifdef MOZ_MEMORY_IMPL # if defined(MOZ_JEMALLOC_IMPL) && defined(MOZ_REPLACE_MALLOC) && !defined(MOZ_REPLACE_JEMALLOC) # define mozmem_malloc_impl(a) je_ ## a # define mozmem_jemalloc_impl(a) je_ ## a # else # define MOZ_JEMALLOC_API MFBT_API # ifdef MOZ_REPLACE_JEMALLOC # define MOZ_MEMORY_API MFBT_API # define mozmem_malloc_impl(a) replace_ ## a # define mozmem_jemalloc_impl(a) replace_ ## a # elif (defined(XP_WIN) || defined(XP_DARWIN)) # if defined(MOZ_REPLACE_MALLOC) # define mozmem_malloc_impl(a) a ## _impl # else # define mozmem_malloc_impl(a) je_ ## a # endif # else # define MOZ_MEMORY_API MFBT_API # if defined(MOZ_WIDGET_ANDROID) || defined(MOZ_WIDGET_GONK) # define MOZ_WRAP_NEW_DELETE # endif # endif # endif # ifdef XP_WIN # define mozmem_dup_impl(a) wrap_ ## a # endif # endif /* All other jemalloc3 functions are prefixed with "je_", except when * building against an unprefixed system jemalloc library */ # define je_(a) je_ ## a #else /* defined(MOZ_NATIVE_JEMALLOC) */ # define je_(a) a #endif #if !defined(MOZ_MEMORY_IMPL) || defined(MOZ_NATIVE_JEMALLOC) # define MOZ_MEMORY_API MFBT_API # define MOZ_JEMALLOC_API MFBT_API #endif #ifndef MOZ_MEMORY_API # define MOZ_MEMORY_API #endif #ifndef MOZ_JEMALLOC_API # define MOZ_JEMALLOC_API #endif #ifndef mozmem_malloc_impl # define mozmem_malloc_impl(a) a #endif #ifndef mozmem_dup_impl # define mozmem_dup_impl(a) a #endif #ifndef mozmem_jemalloc_impl # define mozmem_jemalloc_impl(a) a #endif /* Malloc implementation functions */ #define malloc_impl mozmem_malloc_impl(malloc) #define posix_memalign_impl mozmem_malloc_impl(posix_memalign) #define aligned_alloc_impl mozmem_malloc_impl(aligned_alloc) #define calloc_impl mozmem_malloc_impl(calloc) #define realloc_impl mozmem_malloc_impl(realloc) #define free_impl mozmem_malloc_impl(free) #define memalign_impl mozmem_malloc_impl(memalign) #define valloc_impl mozmem_malloc_impl(valloc) #define malloc_usable_size_impl mozmem_malloc_impl(malloc_usable_size) #define malloc_good_size_impl mozmem_malloc_impl(malloc_good_size) /* Duplication functions */ #define strndup_impl mozmem_dup_impl(strndup) #define strdup_impl mozmem_dup_impl(strdup) #ifdef XP_WIN # define wcsdup_impl mozmem_dup_impl(wcsdup) #endif /* String functions */ #ifdef ANDROID /* Bug 801571 and Bug 879668, libstagefright uses vasprintf, causing malloc()/ * free() to be mismatched between bionic and mozglue implementation. */ #define vasprintf_impl mozmem_dup_impl(vasprintf) #define asprintf_impl mozmem_dup_impl(asprintf) #endif /* Jemalloc specific function */ #define jemalloc_stats_impl mozmem_jemalloc_impl(jemalloc_stats) #define jemalloc_purge_freed_pages_impl mozmem_jemalloc_impl(jemalloc_purge_freed_pages) #define jemalloc_free_dirty_pages_impl mozmem_jemalloc_impl(jemalloc_free_dirty_pages) #endif /* mozmemory_wrap_h */