Date: Thu, 16 Jan 2014 14:53:00 -0800
On Thu, Jan 16, 2014 at 2:06 PM, Jens Maurer <Jens.Maurer_at_[hidden]> wrote:
> On 01/16/2014 10:10 PM, Herb Sutter wrote:
>> And dare I ask: Um, what about using part of the same allocated
>> buffer to hold a T and another part to hold a U, such as malloc(1000)
>> and read/write an int at offset 10 and read/write a short at offset
>> 314 -- they're the same allocation, so do we even have any way to
>> talk about that?
>
> They're the same allocation, but different regions of storage, so
> you're fine, in my opinion. (Implementing your own sub-allocators
> with a malloc backend probably depends on this to work.)
Mhmm; that matches my understanding. For some more litmus tests, how
about an object like:
struct S {
int x;
std::aligned_union<1, float>::type y;
};
If I write:
S* s = (S*)malloc(sizeof(S));
float* y = (float*)(&s->y);
*y = 5.0f;
Do I have defined behavior? Can I use *y as an object of type float,
or does it stay an object of type std::aligned_union<float>::type? (Am
I using "object" in the right way here?)
If I change that to:
S* s = new S;
float* y = (float*)(&s->y);
*y = 5.0f;
does anything change?
What if I use
S s;
float* y = (float*)(&s.y);
*y = 5.0f;
instead? My reading of C suggests that moving the object on to the
stack makes a difference because the object now has a "declared type",
but what do we want in C++?
Or, finally
S s;
new (&s.y) float();
float* y = (float*)(&s.y);
Types like llvm::SmallVector
(http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ADT/SmallVector.h?revision=190708&view=markup#l112)
do this one.
If some part of the answer is that std::aligned_union is "magic", does
that make the possible implementation at
http://en.cppreference.com/w/cpp/types/aligned_storage#Possible_implementation
incorrect?
Thanks,
Jeffrey
> On 01/16/2014 10:10 PM, Herb Sutter wrote:
>> And dare I ask: Um, what about using part of the same allocated
>> buffer to hold a T and another part to hold a U, such as malloc(1000)
>> and read/write an int at offset 10 and read/write a short at offset
>> 314 -- they're the same allocation, so do we even have any way to
>> talk about that?
>
> They're the same allocation, but different regions of storage, so
> you're fine, in my opinion. (Implementing your own sub-allocators
> with a malloc backend probably depends on this to work.)
Mhmm; that matches my understanding. For some more litmus tests, how
about an object like:
struct S {
int x;
std::aligned_union<1, float>::type y;
};
If I write:
S* s = (S*)malloc(sizeof(S));
float* y = (float*)(&s->y);
*y = 5.0f;
Do I have defined behavior? Can I use *y as an object of type float,
or does it stay an object of type std::aligned_union<float>::type? (Am
I using "object" in the right way here?)
If I change that to:
S* s = new S;
float* y = (float*)(&s->y);
*y = 5.0f;
does anything change?
What if I use
S s;
float* y = (float*)(&s.y);
*y = 5.0f;
instead? My reading of C suggests that moving the object on to the
stack makes a difference because the object now has a "declared type",
but what do we want in C++?
Or, finally
S s;
new (&s.y) float();
float* y = (float*)(&s.y);
Types like llvm::SmallVector
(http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ADT/SmallVector.h?revision=190708&view=markup#l112)
do this one.
If some part of the answer is that std::aligned_union is "magic", does
that make the possible implementation at
http://en.cppreference.com/w/cpp/types/aligned_storage#Possible_implementation
incorrect?
Thanks,
Jeffrey
Received on 2014-01-16 23:53:21