arena.h

#include <google/protobuf/arena.h>
namespace google::protobuf

This file defines an Arena allocator for better allocation performance.

Classes in this file

ArenaOptions provides optional additional parameters to arena construction that control its block-allocation behavior.
Arena allocator.
Helper typetrait that indicates support for arenas in a type T at compile time.
Helper typetrait that indicates whether the desctructor of type T should be called when arena is destroyed at compile time.

struct ArenaOptions

#include <google/protobuf/arena.h>
namespace google::protobuf

ArenaOptions provides optional additional parameters to arena construction that control its block-allocation behavior.

Members

size_t
start_block_size
This defines the size of the first block requested from the system malloc. more...
size_t
max_block_size
This defines the maximum block size requested from system malloc (unless an individual arena allocation request occurs with a size larger than this maximum). more...
char *
initial_block
An initial block of memory for the arena to use, or NULL for none. more...
size_t
initial_block_size
The size of the initial block, if provided.
void *(*
block_alloc
A function pointer to an alloc method that returns memory blocks of size requested. more...
void(*
block_dealloc
A function pointer to a dealloc method that takes ownership of the blocks from the arena. more...
void *(*
on_arena_init
Hooks for adding external functionality such as user-specific metrics collection, specific debugging abilities, etc. more...
void(*
on_arena_reset
void(*
on_arena_destruction
void(*
on_arena_allocation
type_info is promised to be static - its lifetime extends to match program's lifetime (It is given by typeid operator). more...
ArenaOptions()

size_tArenaOptions::start_block_size

This defines the size of the first block requested from the system malloc.

Subsequent block sizes will increase in a geometric series up to a maximum.


size_tArenaOptions::max_block_size

This defines the maximum block size requested from system malloc (unless an individual arena allocation request occurs with a size larger than this maximum).

Requested block sizes increase up to this value, then remain here.


char *ArenaOptions::initial_block

An initial block of memory for the arena to use, or NULL for none.

If provided, the block must live at least as long as the arena itself. The creator of the Arena retains ownership of the block after the Arena is destroyed.


void *(*ArenaOptions::block_alloc

A function pointer to an alloc method that returns memory blocks of size requested.

By default, it contains a ptr to the malloc function.

NOTE: block_alloc and dealloc functions are expected to behave like malloc and free, including Asan poisoning.


void(*ArenaOptions::block_dealloc

A function pointer to a dealloc method that takes ownership of the blocks from the arena.

By default, it contains a ptr to a wrapper function that calls free.


void *(*ArenaOptions::on_arena_init

Hooks for adding external functionality such as user-specific metrics collection, specific debugging abilities, etc.

Init hook may return a pointer to a cookie to be stored in the arena. reset and destruction hooks will then be called with the same cookie pointer. This allows us to save an external object per arena instance and use it on the other hooks (Note: It is just as legal for init to return NULL and not use the cookie feature). on_arena_reset and on_arena_destruction also receive the space used in the arena just before the reset.


void(*ArenaOptions::on_arena_allocation

type_info is promised to be static - its lifetime extends to match program's lifetime (It is given by typeid operator).

Note: typeid(void) will be passed as allocated_type every time we intentionally want to avoid monitoring an allocation. (i.e. internal allocations for managing the arena)

class Arena

#include <google/protobuf/arena.h>
namespace google::protobuf

Arena allocator.

Arena allocation replaces ordinary (heap-based) allocation with new/delete, and improves performance by aggregating allocations into larger blocks and freeing allocations all at once. Protocol messages are allocated on an arena by using Arena::CreateMessage<T>(Arena*), below, and are automatically freed when the arena is destroyed.

This is a thread-safe implementation: multiple threads may allocate from the arena concurrently. Destruction is not thread-safe and the destructing thread must synchronize with users of the arena first.

An arena provides two allocation interfaces: CreateMessage<T>, which works for arena-enabled proto2 message types as well as other types that satisfy the appropriate protocol (described below), and Create<T>, which works for any arbitrary type T. CreateMessage<T> is better when the type T supports it, because this interface (i) passes the arena pointer to the created object so that its sub-objects and internal allocations can use the arena too, and (ii) elides the object's destructor call when possible. Create<T> does not place any special requirements on the type T, and will invoke the object's destructor when the arena is destroyed.

The arena message allocation protocol, required by CreateMessage<T>, is as follows:

  • The type T must have (at least) two constructors: a constructor with no arguments, called when a T is allocated on the heap; and a constructor with a google::protobuf::Arena* argument, called when a T is allocated on an arena. If the second constructor is called with a NULL arena pointer, it must be equivalent to invoking the first (no-argument) constructor.
  • The type T must have a particular type trait: a nested type |InternalArenaConstructable_|. This is usually a typedef to |void|. If no such type trait exists, then the instantiation CreateMessage<T> will fail to compile.
  • The type T may have the type trait |DestructorSkippable_|. If this type trait is present in the type, then its destructor will not be called if and only if it was passed a non-NULL arena pointer. If this type trait is not present on the type, then its destructor is always called when the containing arena is destroyed.
  • One- and two-user-argument forms of CreateMessage<T>() also exist that forward these constructor arguments to T's constructor: for example, CreateMessage<T>(Arena*, arg1, arg2) forwards to a constructor T(Arena*, arg1, arg2).

This protocol is implemented by all arena-enabled proto2 message classes as well as RepeatedPtrField.

Do NOT subclass Arena. This class will be marked as final when C++11 is enabled.

Members

explicit
Arena(const ArenaOptions & options)
Arena constructor taking custom options. more...
Arena()
Default constructor with sensible default options, tuned for average use-cases.
~Arena()
Destructor deletes all owned heap allocated objects, and destructs objects that have non-trivial destructors, except for proto2 message objects whose destructors can be skipped. more...
GOOGLE_ATTRIBUTE_NOINLINE uint64
SpaceAllocated() const
Returns the total space used by the arena, which is the sums of the sizes of the underlying blocks. more...
GOOGLE_ATTRIBUTE_NOINLINE uint64
SpaceUsed() const
As above, but does not include any free space in underlying blocks.
GOOGLE_ATTRIBUTE_NOINLINE std::pair< uint64, uint64 >
SpaceAllocatedAndUsed() const
Combines SpaceAllocated and SpaceUsed. more...
GOOGLE_ATTRIBUTE_NOINLINE uint64
Reset()
Frees all storage allocated by this arena after calling destructors registered with OwnDestructor() and freeing objects registered with Own(). more...
template GOOGLE_ATTRIBUTE_NOINLINE void
Own(T * object)
Adds |object| to a list of heap-allocated objects to be freed with |delete| when the arena is destroyed or reset.
template GOOGLE_ATTRIBUTE_NOINLINE void
OwnDestructor(T * object)
Adds |object| to a list of objects whose destructors will be manually called when the arena is destroyed or reset. more...
GOOGLE_ATTRIBUTE_NOINLINE void
OwnCustomDestructor(void * object, void(*)(void *) destruct)
Adds a custom member function on an object to the list of destructors that will be manually called when the arena is destroyed or reset. more...
template static T *
CreateMessage(Arena * arena)
API to create proto2 message objects on the arena. more...
template static T *
CreateMessage(Arena * arena, const Arg & arg)
One-argument form of CreateMessage. more...
template static T *
CreateMessage(Arena * arena, const Arg1 & arg1, const Arg2 & arg2)
Two-argument form of CreateMessage. more...
template static T *
Create(Arena * arena)
API to create any objects on the arena. more...
template static T *
Create(Arena * arena, const Arg & arg)
Version of the above with one constructor argument for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2)
Version of the above with two constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3)
Version of the above with three constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3, const Arg4 & arg4)
Version of the above with four constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3, const Arg4 & arg4, const Arg5 & arg5)
Version of the above with five constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3, const Arg4 & arg4, const Arg5 & arg5, const Arg6 & arg6)
Version of the above with six constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3, const Arg4 & arg4, const Arg5 & arg5, const Arg6 & arg6, const Arg7 & arg7)
Version of the above with seven constructor arguments for the created object.
template static T *
Create(Arena * arena, const Arg1 & arg1, const Arg2 & arg2, const Arg3 & arg3, const Arg4 & arg4, const Arg5 & arg5, const Arg6 & arg6, const Arg7 & arg7, const Arg8 & arg8)
Version of the above with eight constructor arguments for the created object.
template static T *
CreateArray(Arena * arena, size_t num_elements)
Create an array of object type T on the arena without invoking the constructor of T. more...
template static Arena *
GetArena(const T * value)
Retrieves the arena associated with |value| if |value| is an arena-capable message, or NULL otherwise. more...

explicit Arena::Arena(
        const ArenaOptions & options)

Arena constructor taking custom options.

See ArenaOptions below for descriptions of the options available.


Arena::~Arena()

Destructor deletes all owned heap allocated objects, and destructs objects that have non-trivial destructors, except for proto2 message objects whose destructors can be skipped.

Also, frees all blocks except the initial block if it was passed in.


GOOGLE_ATTRIBUTE_NOINLINE uint64
    Arena::SpaceAllocated() const

Returns the total space used by the arena, which is the sums of the sizes of the underlying blocks.

The total space used may not include the new blocks that are allocated by this arena from other threads concurrently with the call to this method.


GOOGLE_ATTRIBUTE_NOINLINE std::pair< uint64, uint64 >
    Arena::SpaceAllocatedAndUsed() const

Combines SpaceAllocated and SpaceUsed.

Returns a pair of <space_allocated, space_used>.


GOOGLE_ATTRIBUTE_NOINLINE uint64
    Arena::Reset()

Frees all storage allocated by this arena after calling destructors registered with OwnDestructor() and freeing objects registered with Own().

Any objects allocated on this arena are unusable after this call. It also returns the total space used by the arena which is the sums of the sizes of the allocated blocks. This method is not thread-safe.


template GOOGLE_ATTRIBUTE_NOINLINE void
    Arena::OwnDestructor(
        T * object)

Adds |object| to a list of objects whose destructors will be manually called when the arena is destroyed or reset.

This differs from Own() in that it does not free the underlying memory with |delete|; hence, it is normally only used for objects that are placement-newed into arena-allocated memory.


GOOGLE_ATTRIBUTE_NOINLINE void
    Arena::OwnCustomDestructor(
        void * object,
        void(*)(void *) destruct)

Adds a custom member function on an object to the list of destructors that will be manually called when the arena is destroyed or reset.

This differs from OwnDestructor() in that any member function may be specified, not only the class destructor.


template static T * Arena::CreateMessage(
        Arena * arena)

API to create proto2 message objects on the arena.

If the arena passed in is NULL, then a heap allocated object is returned. Type T must be a message defined in a .proto file with cc_enable_arenas set to true, otherwise a compilation error will occur.

RepeatedField and RepeatedPtrField may also be instantiated directly on an arena with this method.

This function also accepts any type T that satisfies the arena message allocation protocol, documented above.


template static T * Arena::CreateMessage(
        Arena * arena,
        const Arg & arg)

One-argument form of CreateMessage.

This is useful for constructing objects that implement the arena message construction protocol described above but take additional constructor arguments.


template static T * Arena::CreateMessage(
        Arena * arena,
        const Arg1 & arg1,
        const Arg2 & arg2)

Two-argument form of CreateMessage.

This is useful for constructing objects that implement the arena message construction protocol described above but take additional constructor arguments.


template static T * Arena::Create(
        Arena * arena)

API to create any objects on the arena.

Note that only the object will be created on the arena; the underlying ptrs (in case of a proto2 message) will be still heap allocated. Proto messages should usually be allocated with CreateMessage<T>() instead.

Note that even if T satisfies the arena message construction protocol (InternalArenaConstructable_ trait and optional DestructorSkippable_ trait), as described above, this function does not follow the protocol; instead, it treats T as a black-box type, just as if it did not have these traits. Specifically, T's constructor arguments will always be only those passed to Create<T>() – no additional arena pointer is implicitly added. Furthermore, the destructor will always be called at arena destruction time (unless the destructor is trivial). Hence, from T's point of view, it is as if the object were allocated on the heap (except that the underlying memory is obtained from the arena).


template static T * Arena::CreateArray(
        Arena * arena,
        size_t num_elements)

Create an array of object type T on the arena without invoking the constructor of T.

If arena is null, then the return value should be freed with delete[[]] x; (or ::operator delete[[]](x);). To ensure safe uses, this function checks at compile time (when compiled as C++11) that T is trivially default-constructible and trivially destructible.


template static Arena * Arena::GetArena(
        const T * value)

Retrieves the arena associated with |value| if |value| is an arena-capable message, or NULL otherwise.

This differs from value->GetArena() in that the latter is a virtual call, while this method is a templated call that resolves at compile-time.

template struct Arena::is_arena_constructable

#include <google/protobuf/arena.h>
namespace google::protobuf

template <typename >

Helper typetrait that indicates support for arenas in a type T at compile time.

This is public only to allow construction of higher-level templated utilities. is_arena_constructable<T>::value is true if the message type T has arena support enabled, and false otherwise.

This is inside Arena because only Arena has the friend relationships necessary to see the underlying generated code traits.

Members

template struct Arena::is_destructor_skippable

#include <google/protobuf/arena.h>
namespace google::protobuf

template <typename >

Helper typetrait that indicates whether the desctructor of type T should be called when arena is destroyed at compile time.

This is only to allow construction of higher-level templated utilities. is_destructor_skippable<T>::value is true if the destructor of the message type T should not be called when arena is destroyed or false otherwise. This is inside Arena because only Arena has the friend relationships necessary to see the underlying generated code traits.

Members