Reputation: 2196
For some specialised allocator-like thing I'm implementing, I would like to require that all objects that are going to be stored share a common base class as their first subobject. This allows me to keep a single pointer the common base class as both an indicator of the start of the object as well as to regain access to the original object using static_cast
, assuming I have some way to know the type of the original object.
Specifically, I would like the following equality to always hold for any pointer ptr
to a type Base
, assuming no virtual inheritance between Derived
and Base
.
reinterpret_cast<char *>(static_cast<Derived*>(ptr)) == reinterpret_cast<char *>(ptr)
I assume that this equation holds either for all valid pointers of a given class hierarchy, or it doesn't hold for any valid pointer of a given class hierarchy. Is that correct?
Therefore, that check should be possible to be made at compile-time, without even knowing the runtime value of ptr
. So is there a constexpr
method to check if a static_cast
between two related types changes the pointer value? The above equality seems not acceptable, as I found no constexpr way to create test pointer.
Upvotes: 1
Views: 518
Reputation: 7428
You are asking about is pointer interconvertibility. There is a related trait std::is_pointer_interconvertible_base_of
which isn't implemented yet in gcc and clang. See also the paper and issue. Pointer interconvertible types have the same address and their pointers can be casted between with reinterpret_cast
.
I assume that this equation holds either for all valid pointers of a given class hierarchy, or it doesn't hold for any valid pointer of a given class hierarchy. Is that correct?
As you already noted, virtual inheritance foils this, but so does failure of the standard layout criteria. If Derived
has multiple base classes, and Base
isn't the first, it fails.
The question fails to motivate the requirement for having the same address. If that is not a requirement, static_cast
to upcast from Derived
to Base
and to downcast from Base
to Derived
will just work so long as the inheritance relationship is not virtual, unambiguous, and public.
Upvotes: 3