Issue |
136764
|
Summary |
[[no_unique_address]] Zero sized subobjects don't overlap with any preceding sub-objects
|
Labels |
new issue
|
Assignees |
|
Reporter |
Ext3h
|
Consider the following example:
```c++
#include <cstddef>
#include <cstdint>
struct S1 {};
struct ST1 {
[[no_unique_address]] S1 s1;
[[no_unique_address]] S1 s2;
[[no_unique_address]] S1 s3;
[[no_unique_address]] S1 s4;
[[no_unique_address]] S1 s5;
[[no_unique_address]] S1 s6;
uint16_t i1;
uint16_t i2;
uint16_t i3;
};
struct ST2 {
uint16_t i1;
uint16_t i2;
uint16_t i3;
[[no_unique_address]] S1 s1;
[[no_unique_address]] S1 s2;
[[no_unique_address]] S1 s3;
[[no_unique_address]] S1 s4;
[[no_unique_address]] S1 s5;
[[no_unique_address]] S1 s6;
};
size_t size_st1() {
return sizeof(ST1);
}
size_t offset_st1() {
return offsetof(ST1, s2);
}
size_t size_st2() {
return sizeof(ST2);
}
size_t offset_st2_i3() {
return offsetof(ST2, i3);
}
size_t offset_st2_s1() {
return offsetof(ST2, s1);
}
size_t offset_st2_s2() {
return offsetof(ST2, s2);
}
size_t offset_st2_s3() {
return offsetof(ST2, s3);
}
size_t offset_st2_s4() {
return offsetof(ST2, s4);
}
```
With the following output: https://godbolt.org/z/TzTWb8xxc
The case `ST1` behaves as expected, all the zero-sized sub-objects are placed at contiguous memory addresses starting from offset 0. Finally `ST1::i1` to `ST1::i3` are also placed at contiguous memory addresses starting from 0, overlapping all of `ST1::s1` to `ST1::s6`. As a result `sizeof(ST1) == 6` holds as expected.
For `ST2` however the behavior is weird - `ST2::s1` has an offset of `0` as expected, but `ST2::s2` is the placed at the first address ***after*** `ST1::i3`. Resulting at the perfectly legal offsets 1-5 remaining unused, and `ST2` becomes much larger than expected: `sizeof(ST2) == 12`
It appears that if a struct already has any members that are not partially overlapping sub-objects, then Clang is unexpectedly not re-assigning addresses from this memory range despite being allowed to do so.
_______________________________________________
llvm-bugs mailing list
llvm-bugs@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-bugs