Files
tubestation/memory/build/mozjemalloc.h
Serban Stanca 72ddd15355 Revert "Bug 1928254 - pt 8. Improve the idle purge markers r=jstutte" for causing multiple failures.
This reverts commit 1de23dc2a6.

This reverts commit dc7de1e170.

This reverts commit 0891965b10.

This reverts commit 52c855715a.

This reverts commit fcdc85d6b4.

This reverts commit 1fa61503c2.

This reverts commit df279eb40e.

This reverts commit dd4278a7d5.
2025-05-16 08:52:29 +00:00

191 lines
5.5 KiB
C++

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* 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 mozjemalloc_h
#define mozjemalloc_h
#include <errno.h>
#include "mozjemalloc_types.h"
#include "malloc_decls.h"
#include "mozilla/MacroArgs.h"
// Macro helpers
#define MACRO_CALL(a, b) a b
// Can't use macros recursively, so we need another one doing the same as above.
#define MACRO_CALL2(a, b) a b
#define ARGS_HELPER(name, ...) \
MACRO_CALL2(MOZ_PASTE_PREFIX_AND_ARG_COUNT(name, ##__VA_ARGS__), \
(__VA_ARGS__))
#define TYPED_ARGS0()
#define TYPED_ARGS1(t1) t1 arg1
#define TYPED_ARGS2(t1, t2) TYPED_ARGS1(t1), t2 arg2
#define TYPED_ARGS3(t1, t2, t3) TYPED_ARGS2(t1, t2), t3 arg3
#define ARGS0()
#define ARGS1(t1) arg1
#define ARGS2(t1, t2) ARGS1(t1), arg2
#define ARGS3(t1, t2, t3) ARGS2(t1, t2), arg3
#ifdef MOZ_MEMORY
size_t GetKernelPageSize();
// Implement the set of alignment functions in terms of memalign.
template <void* (*memalign)(size_t, size_t)>
struct AlignedAllocator {
static inline int posix_memalign(void** aMemPtr, size_t aAlignment,
size_t aSize) {
void* result;
// alignment must be a power of two and a multiple of sizeof(void*)
if (((aAlignment - 1) & aAlignment) != 0 || aAlignment < sizeof(void*)) {
return EINVAL;
}
// The 0-->1 size promotion is done in the memalign() call below
result = memalign(aAlignment, aSize);
if (!result) {
return ENOMEM;
}
*aMemPtr = result;
return 0;
}
static inline void* aligned_alloc(size_t aAlignment, size_t aSize) {
if (aSize % aAlignment) {
return nullptr;
}
return memalign(aAlignment, aSize);
}
static inline void* valloc(size_t aSize) {
return memalign(GetKernelPageSize(), aSize);
}
};
// These classes each implement the same interface. Writing out the
// interface for each one rather than using inheritance makes things more
// explicit.
//
// Note: compilers are expected to be able to optimize out `this`.
// The MozJemalloc allocator
struct MozJemalloc {
# define MALLOC_DECL(name, return_type, ...) \
static inline return_type name(__VA_ARGS__);
# include "malloc_decls.h"
};
# ifdef MOZ_PHC
struct MozJemallocPHC : public MozJemalloc {
# define MALLOC_DECL(name, return_type, ...) \
static return_type name(__VA_ARGS__);
# define MALLOC_FUNCS MALLOC_FUNCS_MALLOC_BASE
# include "malloc_decls.h"
static inline int posix_memalign(void** aMemPtr, size_t aAlignment,
size_t aSize) {
return AlignedAllocator<memalign>::posix_memalign(aMemPtr, aAlignment,
aSize);
}
static inline void* aligned_alloc(size_t aAlignment, size_t aSize) {
return AlignedAllocator<memalign>::aligned_alloc(aAlignment, aSize);
}
static inline void* valloc(size_t aSize) {
return AlignedAllocator<memalign>::valloc(aSize);
}
static size_t malloc_usable_size(usable_ptr_t);
static void jemalloc_stats_internal(jemalloc_stats_t*, jemalloc_bin_stats_t*);
static void jemalloc_stats_lite(jemalloc_stats_lite_t*);
static void jemalloc_ptr_info(const void*, jemalloc_ptr_info_t*);
# define MALLOC_DECL(name, return_type, ...) \
static return_type name(__VA_ARGS__);
# define MALLOC_FUNCS MALLOC_FUNCS_ARENA_ALLOC
# include "malloc_decls.h"
};
# endif
# ifdef MOZ_REPLACE_MALLOC
// The replace-malloc allocator
struct ReplaceMalloc {
# define MALLOC_DECL(name, return_type, ...) \
static return_type name(__VA_ARGS__);
# include "malloc_decls.h"
};
# endif
# ifdef MOZ_PHC
using CanonicalMalloc = MozJemallocPHC;
# else
using CanonicalMalloc = MozJemalloc;
# endif
# ifdef MOZ_REPLACE_MALLOC
using DefaultMalloc = ReplaceMalloc;
# else
using DefaultMalloc = CanonicalMalloc;
# endif
// Poison - write "poison" to cells upon deallocation.
constexpr uint8_t kAllocPoison = 0xe5;
// Junk - write this junk value to freshly allocated cells.
constexpr uint8_t kAllocJunk = 0xe4;
// Maximum size of L1 cache line. This is used to avoid cache line aliasing,
// so over-estimates are okay (up to a point), but under-estimates will
// negatively affect performance.
constexpr size_t kCacheLineSize =
# if defined(XP_DARWIN) && defined(__aarch64__)
128
# else
64
# endif
;
#endif // MOZ_MEMORY
// Dummy implementation of the moz_arena_* API, falling back to a given
// implementation of the base allocator.
template <typename T>
struct DummyArenaAllocator {
static arena_id_t moz_create_arena_with_params(arena_params_t*) { return 0; }
static void moz_dispose_arena(arena_id_t) {}
static void moz_set_max_dirty_page_modifier(int32_t) {}
static bool moz_enable_deferred_purge(bool aEnable) { return false; }
static purge_result_t moz_may_purge_now(
bool aPeekOnly, uint32_t aReuseGraceMS,
const mozilla::Maybe<std::function<bool()>>& aKeepGoing) {
return purge_result_t::Done;
}
#define MALLOC_DECL(name, return_type, ...) \
static return_type moz_arena_##name( \
arena_id_t, ARGS_HELPER(TYPED_ARGS, ##__VA_ARGS__)) { \
return T::name(ARGS_HELPER(ARGS, ##__VA_ARGS__)); \
}
#define MALLOC_FUNCS MALLOC_FUNCS_MALLOC_BASE
#include "malloc_decls.h"
};
#endif