c++: Treat unnamed bitfields as padding for __has_unique_object_representations [PR109096]
Checks
Commit Message
Hi!
As reported in the PR, for __has_unique_object_representations we
were treating unnamed bitfields as named ones, which is wrong, they
are actually padding.
THe following patch fixes that. Ok for trunk (and what about release
branches later?)?
2023-03-14 Jakub Jelinek <jakub@redhat.com>
PR c++/109096
* tree.cc (record_has_unique_obj_representations): Ignore unnamed
bitfields.
* g++.dg/cpp1z/has-unique-obj-representations3.C: New test.
Jakub
Comments
On 3/14/23 03:58, Jakub Jelinek wrote:
> Hi!
>
> As reported in the PR, for __has_unique_object_representations we
> were treating unnamed bitfields as named ones, which is wrong, they
> are actually padding.
>
> THe following patch fixes that. Ok for trunk (and what about release
> branches later?)?
OK.
> 2023-03-14 Jakub Jelinek <jakub@redhat.com>
>
> PR c++/109096
> * tree.cc (record_has_unique_obj_representations): Ignore unnamed
> bitfields.
>
> * g++.dg/cpp1z/has-unique-obj-representations3.C: New test.
>
> --- gcc/cp/tree.cc.jj 2023-03-10 10:06:40.247560614 +0100
> +++ gcc/cp/tree.cc 2023-03-13 10:38:03.394836926 +0100
> @@ -4851,7 +4851,7 @@ record_has_unique_obj_representations (c
> DECL_SIZE (field)))
> return false;
> }
> - else if (DECL_C_BIT_FIELD (field))
> + else if (DECL_C_BIT_FIELD (field) && !DECL_UNNAMED_BIT_FIELD (field))
> {
> tree btype = DECL_BIT_FIELD_TYPE (field);
> if (!type_has_unique_obj_representations (btype))
> @@ -4862,7 +4862,7 @@ record_has_unique_obj_representations (c
>
> offset_int cur = 0;
> for (tree field = TYPE_FIELDS (t); field; field = DECL_CHAIN (field))
> - if (TREE_CODE (field) == FIELD_DECL)
> + if (TREE_CODE (field) == FIELD_DECL && !DECL_UNNAMED_BIT_FIELD (field))
> {
> offset_int fld = wi::to_offset (DECL_FIELD_OFFSET (field));
> offset_int bitpos = wi::to_offset (DECL_FIELD_BIT_OFFSET (field));
> --- gcc/testsuite/g++.dg/cpp1z/has-unique-obj-representations3.C.jj 2023-03-13 10:50:21.705127719 +0100
> +++ gcc/testsuite/g++.dg/cpp1z/has-unique-obj-representations3.C 2023-03-13 10:50:17.751185067 +0100
> @@ -0,0 +1,10 @@
> +// PR c++/109096
> +// { dg-do compile { target c++11 } }
> +
> +#define INTB (__SIZEOF_INT__ * __CHAR_BIT__)
> +struct U { int i : INTB * 3 / 4; int : INTB / 4; };
> +struct V { int : INTB * 3 / 4; int j : INTB / 4; };
> +struct W { int i; int : 0; int j; };
> +static_assert (__has_unique_object_representations (U) == false, "");
> +static_assert (__has_unique_object_representations (V) == false, "");
> +static_assert (sizeof (W) != 2 * sizeof (int) || __has_unique_object_representations (W) == true, "");
>
> Jakub
>
@@ -4851,7 +4851,7 @@ record_has_unique_obj_representations (c
DECL_SIZE (field)))
return false;
}
- else if (DECL_C_BIT_FIELD (field))
+ else if (DECL_C_BIT_FIELD (field) && !DECL_UNNAMED_BIT_FIELD (field))
{
tree btype = DECL_BIT_FIELD_TYPE (field);
if (!type_has_unique_obj_representations (btype))
@@ -4862,7 +4862,7 @@ record_has_unique_obj_representations (c
offset_int cur = 0;
for (tree field = TYPE_FIELDS (t); field; field = DECL_CHAIN (field))
- if (TREE_CODE (field) == FIELD_DECL)
+ if (TREE_CODE (field) == FIELD_DECL && !DECL_UNNAMED_BIT_FIELD (field))
{
offset_int fld = wi::to_offset (DECL_FIELD_OFFSET (field));
offset_int bitpos = wi::to_offset (DECL_FIELD_BIT_OFFSET (field));
@@ -0,0 +1,10 @@
+// PR c++/109096
+// { dg-do compile { target c++11 } }
+
+#define INTB (__SIZEOF_INT__ * __CHAR_BIT__)
+struct U { int i : INTB * 3 / 4; int : INTB / 4; };
+struct V { int : INTB * 3 / 4; int j : INTB / 4; };
+struct W { int i; int : 0; int j; };
+static_assert (__has_unique_object_representations (U) == false, "");
+static_assert (__has_unique_object_representations (V) == false, "");
+static_assert (sizeof (W) != 2 * sizeof (int) || __has_unique_object_representations (W) == true, "");