Constructing objects from dataspaces
norman.feske at ...1...
Mon Jul 5 14:59:05 CEST 2010
you have a compelling use case for a placement 'new' operator but there
is no such operator provided by the Genode framework for good reasons:
- A placement new operator is very simple. Indeed, its only one line of
code, which does not relate in any way with rest of the Genode
framework. It is completely independent. If you like, you are free
to implement one in a custom header file of your's and use it from
- Having to use of a placement new operator is (and should be) rare.
If it cannot be avoided, it is the best to provide it local to where
it is used to document the reason of why it is needed in the
particular case. If not used with caution, a placement new operator
is easy to misuse (in particular if overloads exist - see below).
- You already found that our only "official" new operator takes an
'Allocator' as argument. This argument allows you to specify the
memory pool from where to allocate. For the motivation, see the "heap
partitioning concept" of Genode:
Because the 'Allocator' interface is abstract, it further enables the
use of customized allocation strategies by supplying different
'Allocator' arguments to different sub systems. This way, allocation
strategies can be optimized (e.g., using slabs or a list-based
implementation) without changing the code that uses 'new'.
If we provided a general placement new operator, this would overload
our standard new operator, which could lead to really bad errors.
For example, assume that your code included 'placement_new.h' but
not 'allocator.h', and you try passing a real allocator interface as
argument to 'new'. In this case, the placement new operator would
be used w/o any compiler warning and the new object would corrupt
the 'Allocator' object.
If you like to stick with the classes provided with the Genode
framework, there is a clean way to solve your placement-new problem by
introducing a new 'Allocator' implementation - quite similar to the
'Sliced_heap' allocator. But your special allocator would allow for only
one allocation. A 'Single_allocator' object would hold the dataspace
capability ('ds_cap'). When 'alloc' called and the 'ds_cap' is not
already initialized, a dataspace is allocated and locally mapped. The
local address is then returned. The destructor could automatically unmap
and free the dataspace. This way, the lifetime of the dataspace gets
implicitly taken care of. For allocating an instance of your 'Object',
you will need a dedicated 'Single_allocator' instance (hosted outside
the shared-memory of course), which you supply as argument for 'new'.
> And worse, its implementation tries to effectively allocate the object’s
Honestly, I do not know why you are using the word 'worse'. Which part
of our interfaces is unreasonable from your point of view?
More information about the users