> On Mar 12, 2025, at 12:40, Martin Uecker <uec...@tugraz.at> wrote: > > Am Mittwoch, dem 12.03.2025 um 16:20 +0000 schrieb Qing Zhao: >> >>> On Mar 10, 2025, at 15:34, Martin Uecker <uec...@tugraz.at> wrote: >>> >>> Am Montag, dem 10.03.2025 um 15:00 -0400 schrieb John McCall: >>>> >>> >>> ... >>> >>>> That said, my preference is still to just give preference to the field >>>> name, >>>> which sidesteps any need for disambiguation syntax and avoids this whole >>>> problem where structs can be broken by just adding a global variable that >>>> happens to collide with a field. >>> >>> I don't think it is a good idea when the 'n' in 'buf' refers to the >>> previous global 'n' coming before and the 'n' in attribute >>> refers to a member 'n' coming later in the following example. >>> >>> constexpr int n = 1; >>> >>> struct foo { >>> char *p [[gnu::counted_by(n)]]; >>> char buf[n]; >>> int n; >>> }; >>> >>> How are you going to explain this to anyone? >>> >>> >>> And neither global names nor struct members may always be under >>> the control of the programmer. Also that simply bringing >>> a new identifier into scope can break code elsewhere worries me. >>> >>> >>> Finally, the following does not even compile in C++. >>> >>> struct foo { >>> char buf[n]; >>> const static int n = 2; >>> }; >>> >>> While the next example is also ok in C++. >>> >>> constexpr int n = 2; >>> >>> struct foo { >>> char buf[n]; >>> }; >>> >>> With both declarations of 'n' the example has UB in C++. >>> So I am not convinced the proposed rules make a lot >>> of sense for C++ either. >>> >>> >>> Disambiguation with '__self__.' completely avoids all these issues >>> while keeping the door open for later improvements. >>> >>> I still think one could use designator syntax, i.e. '.n', which >>> would be clearer and intuitive for both C and C++ programmers. >> >> I think the major reason to use __self.n instead of .n is: >> >> The dot (.) operator, i.e., the member access operator in C, is used to >> access the member of an _instance_ of >> a structure/union. >> We should declare a variable with a structure type first, and then append >> this member access operator to this >> variable and followed by the member name to access the member, and then use >> it in the expressions. > > For a designator > > struct foo { int n; } a = { .n = 1 }; > > we also refer to a member 'n' of an instance 'a' of a structure type. > The instance is simply implied by the context. > > For > > struct foo { int n; char *x __counted_by(.n) }; > > is also refers to a member of an instance of the struct. The > instance is the 'a' which is later used in an expression 'a.x' > So the instance would again be implied by the context. > > So for me this makes perfect sense in both cases (and > for both C and C++)
Why does ‘.n' also make sense in C++? Qing > >> >> To me, this is clearer. But I am okay with the designator syntax. > > I am also okay with __self__ if people have concerns about > resuing the designator syntax. We could still always drop the > requirement for writing __self__ later. > > Martin > >> >> Qing >> >>> >>> >>> Martin >>> >>> >>> >>> >>> >> >