Another corner case: struct foo6_1 { char x; short p:8; short :0; short :0; short p2:8; char y; }; In MS layout the second anon :0 bit-field does _not_ adjust size or alignment of the struct again. The first one does, though.
Unified · Split
| @@ -3266,7 +3266,7 @@ static void struct_add_offset (Sym *s, int offset) · 3265 unmodified lines | |||
| 3266 | 3266 | ||
| 3267 | static void struct_layout(CType *type, AttributeDef *ad) | 3267 | static void struct_layout(CType *type, AttributeDef *ad) |
| 3268 | { | 3268 | { |
| 3269 | int align, maxalign, offset, c, bit_pos, bt, prevbt; | 3269 | int align, maxalign, offset, c, bit_pos, bt, prevbt, prev_bit_size; |
| 3270 | int pcc = !tcc_state->ms_bitfields; | 3270 | int pcc = !tcc_state->ms_bitfields; |
| 3271 | Sym *f; | 3271 | Sym *f; |
| 3272 | if (ad->a.aligned) | 3272 | if (ad->a.aligned) |
| @@ -3277,6 +3277,7 @@ static void struct_layout(CType *type, AttributeDef *ad) · 4 unmodified lines | |||
| 3277 | c = 0; | 3277 | c = 0; |
| 3278 | bit_pos = 0; | 3278 | bit_pos = 0; |
| 3279 | prevbt = VT_STRUCT; /* make it never match */ | 3279 | prevbt = VT_STRUCT; /* make it never match */ |
| 3280 | prev_bit_size = 0; | ||
| 3280 | for (f = type->ref->next; f; f = f->next) { | 3281 | for (f = type->ref->next; f; f = f->next) { |
| 3281 | int extra_bytes = 0; | 3282 | int extra_bytes = 0; |
| 3282 | int typealign, bit_size; | 3283 | int typealign, bit_size; |
| @@ -3314,6 +3315,7 @@ static void struct_layout(CType *type, AttributeDef *ad) · 31 unmodified lines | |||
| 3314 | if (extra_bytes) c += extra_bytes; | 3315 | if (extra_bytes) c += extra_bytes; |
| 3315 | else if (bit_size < 0) { | 3316 | else if (bit_size < 0) { |
| 3316 | prevbt = VT_STRUCT; | 3317 | prevbt = VT_STRUCT; |
| 3318 | prev_bit_size = 0; | ||
| 3317 | if (type->ref->type.t == TOK_STRUCT) { | 3319 | if (type->ref->type.t == TOK_STRUCT) { |
| 3318 | int addbytes = pcc ? (bit_pos + 7) >> 3 : 0; | 3320 | int addbytes = pcc ? (bit_pos + 7) >> 3 : 0; |
| 3319 | c = (c + addbytes + align - 1) & -align; | 3321 | c = (c + addbytes + align - 1) & -align; |
| @@ -3355,14 +3357,15 @@ static void struct_layout(CType *type, AttributeDef *ad) · 35 unmodified lines | |||
| 3355 | (bit_pos + bit_size > size * 8) | 3357 | (bit_pos + bit_size > size * 8) |
| 3356 | ) {*/ | 3358 | ) {*/ |
| 3357 | if (bit_size == 0 || | 3359 | if (bit_size == 0 || |
| 3358 | (typealign != 1 && (ofs2 / (typealign * 8)) > ((size*8)/(typealign*8)))) { | 3360 | (typealign != 1 && (ofs2 / (typealign * 8)) > (size/typealign))) { |
| 3359 | c = (c + ((bit_pos + 7) >> 3) + typealign - 1) & -typealign; | 3361 | c = (c + ((bit_pos + 7) >> 3) + typealign - 1) & -typealign; |
| 3360 | bit_pos = 0; | 3362 | bit_pos = 0; |
| 3361 | } | 3363 | } |
| 3362 | offset = c; | 3364 | offset = c; |
| 3363 | /* In PCC layout named bit-fields influence the alignment | 3365 | /* In PCC layout named bit-fields influence the alignment |
| 3364 | of the containing struct using the base types alignment, | 3366 | of the containing struct using the base types alignment, |
| 3365 | except for packed fields or zero-width fields. */ | 3367 | except for packed fields (which here have correct |
| 3368 | align/typealign). */ | ||
| 3366 | if (!(f->v & SYM_FIRST_ANOM)) { | 3369 | if (!(f->v & SYM_FIRST_ANOM)) { |
| 3367 | if (align > maxalign) | 3370 | if (align > maxalign) |
| 3368 | maxalign = align; | 3371 | maxalign = align; |
| @@ -3381,7 +3384,8 @@ static void struct_layout(CType *type, AttributeDef *ad) · 12 unmodified lines | |||
| 3381 | bit_pos = 0; | 3384 | bit_pos = 0; |
| 3382 | /* In MS bitfield mode a bit-field run always uses | 3385 | /* In MS bitfield mode a bit-field run always uses |
| 3383 | at least as many bits as the underlying type. */ | 3386 | at least as many bits as the underlying type. */ |
| 3384 | c += size; | 3387 | if (bit_size || prev_bit_size) |
| 3388 | c += size; | ||
| 3385 | } | 3389 | } |
| 3386 | if (bit_size > 0 || prevbt == bt) { | 3390 | if (bit_size > 0 || prevbt == bt) { |
| 3387 | if (align > maxalign) | 3391 | if (align > maxalign) |
| @@ -3390,6 +3394,7 @@ static void struct_layout(CType *type, AttributeDef *ad) · 2 unmodified lines | |||
| 3390 | maxalign = typealign; | 3394 | maxalign = typealign; |
| 3391 | } | 3395 | } |
| 3392 | prevbt = bt; | 3396 | prevbt = bt; |
| 3397 | prev_bit_size = bit_size; | ||
| 3393 | } | 3398 | } |
| 3394 | f->type.t = (f->type.t & ~(0x3f << VT_STRUCT_SHIFT)) | 3399 | f->type.t = (f->type.t & ~(0x3f << VT_STRUCT_SHIFT)) |
| 3395 | | (bit_pos << VT_STRUCT_SHIFT); | 3400 | | (bit_pos << VT_STRUCT_SHIFT); |