October 28, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to Peter Alexander Attachments:
| On 28 October 2013 06:46, Peter Alexander <peter.alexander.au@gmail.com>wrote: > On Sunday, 27 October 2013 at 20:30:05 UTC, Andrei Alexandrescu wrote: > >> Yah, something like that. I found align(NNN) underspecified and underpowered for my work with allocators. As a simple matter, NNN must be a literal, not a compile-time expression. You can't even write e.g. align(size_t.alignof), which is fairly basic. >> > > Yeah I noticed the literal requirement as well and thought it was quite odd... > I reported that as a deficiency over a year ago, I recall discussion, and thought it was to be fixed. Guess it didn't eventuate. |
October 28, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to monarch_dodra Attachments:
| On 28 October 2013 06:50, monarch_dodra <monarchdodra@gmail.com> wrote:
> On Sunday, 27 October 2013 at 20:30:05 UTC, Andrei Alexandrescu wrote:
>
>> Yah, something like that. I found align(NNN) underspecified and underpowered for my work with allocators. As a simple matter, NNN must be a literal, not a compile-time expression. You can't even write e.g. align(size_t.alignof), which is fairly basic.
>>
>>
>> Andrei
>>
>
> In that case, we also need to specify how alignOf works. For example:
>
> struct S
> {
> align(128) int i;
> }
>
> static assert(S.alignOf == 128);
>
> If "align(N)" is supposed to only mean "alignement relative to the start of the struct", why the heck is S's "alignOf" 128?
>
> Also, (but I can't double check it right now), I seem to remember that
> there are odd things, like "ulong.alignOf == 8", yet if you declare one on
> the stack, you notice it's only 4 aligned (at least, on my win32 (I think)
> it is...)
>
I had a lot of informal conversations with Walter trying to get my head
around the details here.
To my recollection, the intent was that it should behave like C, and that
S.alignof must certainly == 128 in that case. It can't work otherwise.
Alignment must be inherited by parent structures.
I also recall commenting on that case with ulong. On most architectures it only needs to be 4 byte aligned, but that one is arch specific.
|
October 28, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to Manu | On Monday, 28 October 2013 at 02:44:54 UTC, Manu wrote: > I had a lot of informal conversations with Walter trying to get my head > around the details here. > To my recollection, the intent was that it should behave like C, and that > S.alignof must certainly == 128 in that case. It can't work otherwise. > Alignment must be inherited by parent structures. But is that really what it means though? From the above conversation, it would instead appear to mean that: struct S { int i; align(128) int j; } in this case, the *padding* needed until we reach j is 128 bytes. It doesn't mean that S itself need to be 128 aligned. > I also recall commenting on that case with ulong. On most architectures it > only needs to be 4 byte aligned, but that one is arch specific. Does it make sense (and should it be illegal) in that case to have anything with alignment > 8 ? I just don't see how something like "malloc" would be able to deal with them otherwise... ? |
October 28, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to monarch_dodra | On Monday, 28 October 2013 at 18:33:49 UTC, monarch_dodra wrote: > But is that really what it means though? From the above conversation, it would instead appear to mean that: > struct S > { > int i; > align(128) int j; > } > in this case, the *padding* needed until we reach j is 128 bytes. Like Manu, I think the only sane way for align() to behave is like GCC's/Clang's "aligned" attribute, which would both add padding such that j is at offset 128, and ensure that any variables of type S are aligned to 128 bytes as well. > I just don't see how something like "malloc" would be able to deal with them otherwise... ? Raw system malloc(), without knowing anything about the type, obviously cannot honor any special alignment requests. Thus, usually special primitives exist which accept an additional parameter to specify the target alignment (cf. the std.allocator discussion). If you really want to use C malloc() for your 256-byte-aligned objects, you have to handle things yourself, e.g. by over-allocating and then adjusting the base pointer or similar strategies. David |
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to monarch_dodra Attachments:
| On 29 October 2013 04:33, monarch_dodra <monarchdodra@gmail.com> wrote: > On Monday, 28 October 2013 at 02:44:54 UTC, Manu wrote: > >> I had a lot of informal conversations with Walter trying to get my head >> around the details here. >> To my recollection, the intent was that it should behave like C, and that >> S.alignof must certainly == 128 in that case. It can't work otherwise. >> Alignment must be inherited by parent structures. >> > > But is that really what it means though? From the above conversation, it > would instead appear to mean that: > struct S > { > int i; > align(128) int j; > } > in this case, the *padding* needed until we reach j is 128 bytes. > > It doesn't mean that S itself need to be 128 aligned. Both should be true, if it's not, it's a bug. I also recall commenting on that case with ulong. On most architectures it >> only needs to be 4 byte aligned, but that one is arch specific. >> > > Does it make sense (and should it be illegal) in that case to have anything with alignment > 8 ? I just don't see how something like "malloc" would be able to deal with them otherwise... ? Well SIMD vector's require at least 16 byte alignment, so say goodbye to a major subsection of your CPU ;) I've never seen a malloc implementation that returns memory that is less than 16 byte aligned. If you expect higher alignment, typically you use OS provided AliognedAlloc primitives, or you use tricks like overallocating and offseting. |
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to Manu | On Tuesday, 29 October 2013 at 00:45:59 UTC, Manu wrote: > On 29 October 2013 04:33, monarch_dodra <monarchdodra@gmail.com> wrote: > >> On Monday, 28 October 2013 at 02:44:54 UTC, Manu wrote: >> >>> I had a lot of informal conversations with Walter trying to get my head >>> around the details here. >>> To my recollection, the intent was that it should behave like C, and that >>> S.alignof must certainly == 128 in that case. It can't work otherwise. >>> Alignment must be inherited by parent structures. >>> >> >> But is that really what it means though? From the above conversation, it >> would instead appear to mean that: >> struct S >> { >> int i; >> align(128) int j; >> } >> in this case, the *padding* needed until we reach j is 128 bytes. >> >> It doesn't mean that S itself need to be 128 aligned. > > > Both should be true, if it's not, it's a bug. > http://dlang.org/attribute.html#align --- The alignment for the fields of an aggregate does not affect the alignment of the aggregate itself - that is affected by the alignment setting outside of the aggregate. align (2) struct S { align (1): byte a; // placed at offset 0 int b; // placed at offset 1 long c; // placed at offset 5 } auto sz = S.sizeof; // 14 --- My understanding of that is S is not affected by the alignment of its fields. |
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to growler | > My understanding of that is S is not affected by the alignment of its fields.
To clarify, I mean the *alignment* of S is not affected by the alignment of its fields.
|
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to growler Attachments:
| On 29 October 2013 13:47, growler <growlercab@gmail.com> wrote:
> On Tuesday, 29 October 2013 at 00:45:59 UTC, Manu wrote:
>
>> On 29 October 2013 04:33, monarch_dodra <monarchdodra@gmail.com> wrote:
>>
>> On Monday, 28 October 2013 at 02:44:54 UTC, Manu wrote:
>>>
>>> I had a lot of informal conversations with Walter trying to get my head
>>>> around the details here.
>>>> To my recollection, the intent was that it should behave like C, and
>>>> that
>>>> S.alignof must certainly == 128 in that case. It can't work otherwise.
>>>> Alignment must be inherited by parent structures.
>>>>
>>>>
>>> But is that really what it means though? From the above conversation, it
>>> would instead appear to mean that:
>>> struct S
>>> {
>>> int i;
>>> align(128) int j;
>>> }
>>> in this case, the *padding* needed until we reach j is 128 bytes.
>>>
>>> It doesn't mean that S itself need to be 128 aligned.
>>>
>>
>>
>> Both should be true, if it's not, it's a bug.
>>
>>
> http://dlang.org/attribute.**html#align<http://dlang.org/attribute.html#align>
> ---
> The alignment for the fields of an aggregate does not affect the alignment of the aggregate itself - that is affected by the alignment setting outside of the aggregate.
>
> align (2) struct S {
> align (1):
> byte a; // placed at offset 0
> int b; // placed at offset 1
> long c; // placed at offset 5
> }
>
> auto sz = S.sizeof; // 14
> ---
>
> My understanding of that is S is not affected by the alignment of its fields.
>
This is a strange test.
It looks like your align(1) is intended to mean pack(1), and if that is the
case, then the observed sizeof is correct.
with pack(1), the size would be 8+4+1 = 13, but then the struct marked
align(2) must be padded to a multiple of it's alignment, so 14.
What you observe is probably correct, except I don't think the use of
align(1) to mean pack(1) is right. That should raise discussion...
|
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to growler | On 10/29/13 06:36, growler wrote:
>> My understanding of that is S is not affected by the alignment of its fields.
>
> To clarify, I mean the *alignment* of S is not affected by the alignment of its fields.
The alignment of an object must be at least as large as the max of the alignment of all fields that it contains, obviously. The object layout never changes; using a smaller alignment for the parent object would make it impossible to guarantee the specified field alignment.
artur
|
October 29, 2013 Re: core.runtime.GC memory alignment | ||||
---|---|---|---|---|
| ||||
Posted in reply to Artur Skawina | On Tuesday, 29 October 2013 at 12:31:00 UTC, Artur Skawina wrote:
> On 10/29/13 06:36, growler wrote:
>>> My understanding of that is S is not affected by the alignment of its fields.
>>
>> To clarify, I mean the *alignment* of S is not affected by the alignment of its fields.
>
> The alignment of an object must be at least as large as the max of the alignment
> of all fields that it contains, obviously. The object layout never changes; using
> a smaller alignment for the parent object would make it impossible to guarantee the
> specified field alignment.
>
> artur
You're right, it would be nonsensical otherwise.
|
Copyright © 1999-2021 by the D Language Foundation