Skip to content

Commit 9251caa

Browse files
committed
flag non-portable bitfields
1 parent 2489ab7 commit 9251caa

File tree

1 file changed

+25
-17
lines changed

1 file changed

+25
-17
lines changed

compiler/src/dmd/dsymbolsem.d

+25-17
Original file line numberDiff line numberDiff line change
@@ -7114,8 +7114,8 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71147114

71157115
const sz = t.size(vd.loc);
71167116
assert(sz != SIZE_INVALID && sz < uint.max);
7117-
uint memsize = cast(uint)sz; // size of member
7118-
uint memalignsize = target.fieldalign(t); // size of member for alignment purposes
7117+
const memsize = cast(uint)sz; // size of member
7118+
const memalignsize = target.fieldalign(t); // size of member for alignment purposes
71197119
vd.offset = placeField(vd.loc,
71207120
fieldState.offset,
71217121
memsize, memalignsize, vd.alignment,
@@ -7153,8 +7153,8 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71537153

71547154
const sz = t.size(bfd.loc);
71557155
assert(sz != SIZE_INVALID && sz < uint.max);
7156-
uint memsize = cast(uint)sz; // size of member
7157-
uint memalignsize = target.fieldalign(t); // size of member for alignment purposes
7156+
const uint memsize = cast(uint)sz; // size of member
7157+
const uint memalignsize = target.fieldalign(t); // size of member for alignment purposes
71587158
if (log) printf(" memsize: %u memalignsize: %u\n", memsize, memalignsize);
71597159

71607160
if (bfd.fieldWidth == 0 && !anon)
@@ -7169,6 +7169,12 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71697169
const isMicrosoftStyle = style == TargetC.BitFieldStyle.MS;
71707170
const contributesToAggregateAlignment = target.c.contributesToAggregateAlignment(bfd);
71717171

7172+
/* Flag bitfield non-portable layouts that differ between MicrosoftStyle and non-MicrosoftStyle
7173+
* unless it's C semantics.
7174+
*/
7175+
const checkPortable = false; //!sc.inCfile && sc.linkage == LINK.d;
7176+
bool isPortable = true; // start out assuming portable
7177+
71727178
void startNewField()
71737179
{
71747180
if (log) printf("startNewField()\n");
@@ -7208,19 +7214,16 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72087214

72097215
if (bfd.fieldWidth == 0)
72107216
{
7211-
if (!isMicrosoftStyle && !isunion)
7217+
if (!isunion)
72127218
{
7213-
// Use type of zero width field to align to next field
7214-
fieldState.offset = (fieldState.offset + memalignsize - 1) & ~(memalignsize - 1);
7215-
ad.structsize = fieldState.offset;
7216-
}
7217-
else if (isMicrosoftStyle && fieldState.inFlight && !isunion)
7218-
{
7219-
// documentation says align to next int
7220-
//const alsz = cast(uint)Type.tint32.size();
7221-
const alsz = memsize; // but it really does this
7222-
fieldState.offset = (fieldState.offset + alsz - 1) & ~(alsz - 1);
7223-
ad.structsize = fieldState.offset;
7219+
if (!isMicrosoftStyle || fieldState.inFlight)
7220+
{
7221+
const alsz = isMicrosoftStyle
7222+
? memsize // documentation says align to next int but memsize is actually used
7223+
: memalignsize; // use type of zero width field to align to next field
7224+
fieldState.offset = (fieldState.offset + alsz - 1) & ~(alsz - 1);
7225+
ad.structsize = fieldState.offset;
7226+
}
72247227
}
72257228

72267229
fieldState.inFlight = false;
@@ -7229,7 +7232,7 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72297232

72307233
if (!fieldState.inFlight)
72317234
{
7232-
//printf("not in flight\n");
7235+
if (log) printf("not in flight\n");
72337236
startNewField();
72347237
}
72357238
else if (!isMicrosoftStyle)
@@ -7296,6 +7299,11 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72967299
fieldState.bitOffset = pastField;
72977300
}
72987301

7302+
if (checkPortable && !isPortable)
7303+
{
7304+
error(bfd.loc, "bitfield layout not portable among supported C compilers, wrap with `extern (C)` or `extern (C++)`");
7305+
}
7306+
72997307
//printf("\t%s: offset = %d bitOffset = %d fieldWidth = %d memsize = %d\n", toChars(), offset, bitOffset, fieldWidth, memsize);
73007308
//printf("\t%s: memalignsize = %d\n", toChars(), memalignsize);
73017309
//printf(" addField '%s' to '%s' at offset %d, size = %d\n", toChars(), ad.toChars(), offset, memsize);

0 commit comments

Comments
 (0)