Thread overview
union alignment
May 18, 2016
tsbockman
May 21, 2016
Iain Buclaw
May 21, 2016
tsbockman
May 18, 2016
Is this a bug?
---
module app;

union Foo(A, B) {
    A a;
    B b;
}

void main() {
    alias F = Foo!(double, ulong);

    import std.stdio, std.algorithm;
    writefln("sizeof:  (%s >= %s) == %s",
        F.sizeof, max(double.sizeof, ulong.sizeof),
        F.sizeof >= max(double.sizeof, ulong.sizeof));
    writefln("alignof: (%s >= %s) == %s",
        F.alignof, max(double.alignof, ulong.alignof),
        F.alignof >= max(double.alignof, ulong.alignof));
}
---
Shouldn't a union type always have an `alignof` at least as great as the `alignof` for its largest member?

DMD 64:
sizeof:  (8 >= 8) == true
alignof: (8 >= 8) == true

DMD 32:
sizeof:  (8 >= 8) == true
alignof: (4 >= 4) == true

GDC 64:
sizeof:  (8 >= 8) == true
alignof: (8 >= 8) == true

GDC 32:
sizeof:  (8 >= 8) == true
alignof: (4 >= 8) == false  <<===== Bug?

LDC 64:
sizeof:  (8 >= 8) == true
alignof: (8 >= 8) == true

LDC 32:
sizeof:  (8 >= 8) == true
alignof: (4 >= 4) == true

May 21, 2016
On Wednesday, 18 May 2016 at 01:46:37 UTC, tsbockman wrote:
> Shouldn't a union type always have an `alignof` at least as great as the `alignof` for its largest member?
>

On x86, there's a difference between the type alignment and the field alignment.

The type align of ulong and double are 8 bytes on both x86 and x86_64.
The field align is worked out differently, something to the effect of:

uint fieldalignof(T)()
{
  version (X86_64)
    return T.alignof;
  else version (X86)
  {
    static if (isIntegral!T || is(T == double) || is(T == cdouble))
      return min(4, T.alignof);
    else
      return T.alignof;
  }
}

static assert(ulong.alignof == 8);
static assert(double.alignof == 8);
static assert(fieldalignof!ulong == 4);
static assert(fieldalignof!double == 4);


> DMD 32:
> sizeof:  (8 >= 8) == true
> alignof: (4 >= 4) == true
>
> GDC 32:
> sizeof:  (8 >= 8) == true
> alignof: (4 >= 8) == false  <<===== Bug?
>
> LDC 32:
> sizeof:  (8 >= 8) == true
> alignof: (4 >= 4) == true

GDC is in the right, it's all other compilers that are wrong.  :-)

Iain.
May 21, 2016
On Wednesday, 18 May 2016 at 01:46:37 UTC, tsbockman wrote:
> Shouldn't a union type always have an `alignof` at least as great as the `alignof` for its largest member?

Apparently not; it's actually DMD and LDC that are wrong here:
    http://bugzilla.gdcproject.org/show_bug.cgi?id=226