Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[class.bit] p2 The wording about the affect of unnamed bit-field with a width zero is unclear #650

Open
xmh0511 opened this issue Dec 5, 2024 · 9 comments

Comments

@xmh0511
Copy link

xmh0511 commented Dec 5, 2024

Full name of submitter (unless configured in github; will be published with the issue): Jim X

[class.bit] p2 says:

As a special case, an unnamed bit-field with a width of zero specifies alignment of the next bit-field at an allocation unit boundary.

The intent expressed by this wording is unclear. The wording allocation unit boundary is not defined, as well as allocation unit. The C standard has the following wording:

As a special case, a bit-field structure member with a width of zero indicates that no further bit-field is to be packed into the unit in which the previous bit-field, if any, was placed.

For this code:

struct S1 {
    unsigned char b1 : 1;
    unsigned int :0; 
    unsigned char b2 : 2;
    unsigned char b3 : 5;
};

GCC and Clang have this layout for S1

struct S1 size(5)
| b1 |  size(1)
alignment member 3 
|b3 | b2 |   size(1)

whereas in msvc

1>class S1	size(8):
1>	+---
1> 0.	| b1 (bitstart=0,nbits=1)
1>  	| <alignment member> (size=3)
1> 4.	| b2 (bitstart=0,nbits=2)
1> 4.	| b3 (bitstart=2,nbits=5)
1>  	| <alignment member> (size=3)
1>	+---

In any implementation, the unnamed bit-field with a width of zero just has the same effect that places the next bit-field in a new unit.

Suggested Resolution

The intent is not clearly expressed by the current wording. The proposed wording might be:

As a special case, an unnamed bit-field with a width of zero specifies that the next bit-field is packed into an allocation unit where the previous bit-fields(if any) were not packed into.

@jensmaurer
Copy link
Member

If you believe "allocation unit boundary" is not defined, why is "allocation unit" any better? And why do you believe the C wording of an undefined "unit" is anywhere near good?

@xmh0511
Copy link
Author

xmh0511 commented Dec 5, 2024

Hmmm, "allocation unit" is another unclear part. This wording just tries to state the effect of unnamed bit-field with a width of zero, that the next bit-field is packed into a new X, and the X is something that needs further definition.

@jensmaurer
Copy link
Member

I think "aligned at an allocation unit boundary" is synonymous with "not packed into the same unit as the previous one".

And, of course, what's the net effect of this rule, anyway, in terms of the abstract machine? None, it feels. The definition of "memory location" already takes care of unnamed bit-fields separately.

@xmh0511
Copy link
Author

xmh0511 commented Dec 6, 2024

I think "aligned at an allocation unit boundary" is synonymous with "not packed into the same unit as the previous one".

How are they associated? Is there any extra meaning to allocation unit boundary? Using packed might be closer to that meaning. Like the first paragraph phrase that

Bit-fields are packed into some addressable allocation unit.

The corresponding wording could be

As a special case, an unnamed bit-field with a width of zero specifies that the next bit-field is packed into an allocation unit boundary.

The remaining thing is to clarify what the allocation unit boundary means. Specifically, the boundary might mean a new unit.

@jensmaurer
Copy link
Member

"boundary" means "border". It seems clear from the context that an allocation unit cannot span such a boundary.

@frederick-vs-ja
Copy link

The sentence seemingly misuses the term "alignment".

Would it be better to say "a maximal sequence of adjacent bit-fields all having nonzero width are packed into adjacent bytes; an unnamed bit-field with a width of zero specifies the next bit-field, if any, is not packed into previous bytes"?

@jensmaurer
Copy link
Member

The "alignment" used here certainly is unrelated to the alignment specified in [basic.align].

@hubert-reinterpretcast
Copy link

While revising this wording, it may be helpful to have a note that the type of the zero-width bit-field can affect layout compatibility. It may also be helpful to note that the presence of a zero-width bit-field can affect layout compatibility even if the next non-static data member is not a bit-field.

Additionally, depending on what wording we use, we might want to say "any immediately following bit-field" instead of "next bit-field".

@xmh0511
Copy link
Author

xmh0511 commented Dec 9, 2024

The "alignment" used here certainly is unrelated to the alignment specified in [basic.align].

This is also the issue here: the "alignment" is not that alignment in [basic.align], which makes the whole wording confusing. It is hard to know what the sentence intends to mean.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants