108 lines
2.5 KiB
C++
108 lines
2.5 KiB
C++
#pragma once
|
|
|
|
#include "../backend/backend.h"
|
|
#include "../mem/chunkallocator.h"
|
|
#include "../mem/corealloc.h"
|
|
#include "../mem/pool.h"
|
|
#include "commonconfig.h"
|
|
|
|
#ifdef SNMALLOC_TRACING
|
|
# include <iostream>
|
|
#endif
|
|
namespace snmalloc
|
|
{
|
|
// Forward reference to thread local cleanup.
|
|
void register_clean_up();
|
|
|
|
#ifdef USE_SNMALLOC_STATS
|
|
inline static void print_stats()
|
|
{
|
|
printf("No Stats yet!");
|
|
// Stats s;
|
|
// current_alloc_pool()->aggregate_stats(s);
|
|
// s.print<Alloc>(std::cout);
|
|
}
|
|
#endif
|
|
|
|
/**
|
|
* The default configuration for a global snmalloc. This allocates memory
|
|
* from the operating system and expects to manage memory anywhere in the
|
|
* address space.
|
|
*/
|
|
class Globals final : public BackendAllocator<Pal, false>
|
|
{
|
|
public:
|
|
using GlobalPoolState = PoolState<CoreAllocator<Globals>>;
|
|
|
|
private:
|
|
using Backend = BackendAllocator<Pal, false>;
|
|
SNMALLOC_REQUIRE_CONSTINIT
|
|
inline static ChunkAllocatorState chunk_allocator_state;
|
|
|
|
SNMALLOC_REQUIRE_CONSTINIT
|
|
inline static GlobalPoolState alloc_pool;
|
|
|
|
SNMALLOC_REQUIRE_CONSTINIT
|
|
inline static std::atomic<bool> initialised{false};
|
|
|
|
SNMALLOC_REQUIRE_CONSTINIT
|
|
inline static std::atomic_flag initialisation_lock{};
|
|
|
|
public:
|
|
static ChunkAllocatorState&
|
|
get_chunk_allocator_state(Backend::LocalState* = nullptr)
|
|
{
|
|
return chunk_allocator_state;
|
|
}
|
|
|
|
static GlobalPoolState& pool()
|
|
{
|
|
return alloc_pool;
|
|
}
|
|
|
|
static constexpr Flags Options{};
|
|
|
|
// Performs initialisation for this configuration
|
|
// of allocators. Needs to be idempotent,
|
|
// and concurrency safe.
|
|
static void ensure_init()
|
|
{
|
|
FlagLock lock{initialisation_lock};
|
|
#ifdef SNMALLOC_TRACING
|
|
std::cout << "Run init_impl" << std::endl;
|
|
#endif
|
|
|
|
if (initialised)
|
|
return;
|
|
|
|
LocalEntropy entropy;
|
|
entropy.init<Pal>();
|
|
// Initialise key for remote deallocation lists
|
|
key_global = FreeListKey(entropy.get_free_list_key());
|
|
|
|
// Need to initialise pagemap.
|
|
Backend::init();
|
|
|
|
#ifdef USE_SNMALLOC_STATS
|
|
atexit(snmalloc::print_stats);
|
|
#endif
|
|
|
|
initialised = true;
|
|
}
|
|
|
|
static bool is_initialised()
|
|
{
|
|
return initialised;
|
|
}
|
|
|
|
// This needs to be a forward reference as the
|
|
// thread local state will need to know about this.
|
|
// This may allocate, so should only be called once
|
|
// a thread local allocator is available.
|
|
static void register_clean_up()
|
|
{
|
|
snmalloc::register_clean_up();
|
|
}
|
|
};
|
|
} // namespace snmalloc
|