https://gcc.gnu.org/bugzilla/show_bug.cgi?id=121376
--- Comment #3 from Halalaluyafail3 <luigighiron at gmail dot com> --- (In reply to Joseph S. Myers from comment #2) > C23 says "Any attempt to modify an object with temporary lifetime results in > undefined behavior.", so this test does not demonstrate a bug. It also says > "Such an object may not have a unique address.", and the Proposed Committee > Response in issue 0452, as linked from that LLVM issue, says 'To the > question "Should the expression (O, o2).ca == o2.ca yield zero, non-zero, or > should it be implementation defined?" the answer is "implementation > defined".', which appears to indicate an intent that it's not unique with > respect to objects with non-temporary lifetime, not just with respect to > other objects with temporary lifetime (although it looks "unspecified" not > "implementation-defined" to me). So even if there were a test based on > comparing addresses rather than modifying an object with temporary lifetime, > I don't think it would demonstrate a bug, If this interpretation is correct, then can't the temporary object share addresses with any object? For example: #include<errno.h> int main(){ struct{int x[1];}x={}; int*p; return p=(0,x).x,errno=1,*p; } Could this be UB because errno=1 modifies the temporary object? Here is another example: #include<string.h> int main(){ int a=0; struct{int x[1];}x={}; int*p; return p=(0,x).x,memcpy(&a,p,sizeof(int)),*p; } Could this be UB because the temporary object and a share the same address violating the aliasing restriction of memcpy? Furthermore, what if the temporary object isn't even read from: int main(){ struct{int x[1];}x={}; int*p; return p=(0,x).x,*x.x=1,0; } Further reduced: int main(){ struct{int x[1];}x={}; return(0,x).x,*x.x=1,0; } Does the mere existence of a temporary object create undefined behavior if another object exists with sufficient alignment and the same bit pattern (so the addresses can be shared) and gets modified during the existence of the temporary object? Here is another example: struct foo{char str[4];}; struct foo bar(){ return(struct foo){"abc"}; } int baz(const char*p){ int x=0; return x; } int main(){ return baz(bar().str); } bar().str doesn't have a unique address, and at the start of the call of baz x has an indeterminate value. So if the implementation chooses the correct bit pattern of x and the alignment of the temporary object is sufficient for int then p and &x can share the same address. If that happens, then the initialization of x will modify the temporary object causing undefined behavior. As far as a I understand, if the interpretation in DR452 is correct then even simple uses such as: #include<stdio.h> struct X{char x[32];}; struct X get(){ return(struct X){"a string"}; } int main(){ puts(get().x); } Would be undefined behavior.