-
Notifications
You must be signed in to change notification settings - Fork 13.6k
[Clang] Require base element type of __has_unique_object_representations
to be complete
#95432
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
[Clang] Require base element type of __has_unique_object_representations
to be complete
#95432
Conversation
…ons to be complete
@llvm/pr-subscribers-clang Author: Mital Ashok (MitalAshok) ChangesFixes #95311 Previous behaviour was that Full diff: https://github.com/llvm/llvm-project/pull/95432.diff 4 Files Affected:
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 8c2f737836a9d..4359213286fa0 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -660,6 +660,9 @@ Bug Fixes in This Version
- Correctly reject declarations where a statement is required in C.
Fixes #GH92775
+- ``__has_unique_object_representations`` correctly handles arrays of unknown bounds of
+ types by ensuring they are complete and instantiating them if needed. Fixes (#GH95311).
+
Bug Fixes to Compiler Builtins
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp
index aa22825602a40..f3b698b3f0c59 100644
--- a/clang/lib/AST/ASTContext.cpp
+++ b/clang/lib/AST/ASTContext.cpp
@@ -2791,6 +2791,12 @@ bool ASTContext::hasUniqueObjectRepresentations(
return hasUniqueObjectRepresentations(getBaseElementType(Ty),
CheckIfTriviallyCopyable);
+ if (Ty->isVoidType())
+ return false;
+
+ assert(!Ty->isIncompleteType() && "hasUniqueObjectRepresentations should not "
+ "be called with an incomplete type");
+
// (9.1) - T is trivially copyable...
if (CheckIfTriviallyCopyable && !Ty.isTriviallyCopyableType(*this))
return false;
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index f3af8dee6b090..127621a31470d 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -5149,6 +5149,10 @@ static bool CheckUnaryTypeTraitTypeCompleteness(Sema &S, TypeTrait UTT,
case UTT_HasTrivialCopy:
case UTT_HasTrivialDestructor:
case UTT_HasVirtualDestructor:
+ // has_unique_object_representations<T> when T is an array is defined in terms
+ // of has_unique_object_representations<remove_all_extents_t<T>>, so the base
+ // type needs to be complete even if the type is an incomplete array type.
+ case UTT_HasUniqueObjectRepresentations:
ArgTy = QualType(ArgTy->getBaseElementTypeUnsafe(), 0);
[[fallthrough]];
@@ -5157,7 +5161,6 @@ static bool CheckUnaryTypeTraitTypeCompleteness(Sema &S, TypeTrait UTT,
case UTT_IsDestructible:
case UTT_IsNothrowDestructible:
case UTT_IsTriviallyDestructible:
- case UTT_HasUniqueObjectRepresentations:
if (ArgTy->isIncompleteArrayType() || ArgTy->isVoidType())
return true;
diff --git a/clang/test/SemaCXX/type-traits.cpp b/clang/test/SemaCXX/type-traits.cpp
index d40605f56f1ed..b5cefb18fa13e 100644
--- a/clang/test/SemaCXX/type-traits.cpp
+++ b/clang/test/SemaCXX/type-traits.cpp
@@ -3505,6 +3505,17 @@ static_assert(__has_unique_object_representations(_BitInt(8)), "BitInt:");
static_assert(!__has_unique_object_representations(_BitInt(127)), "BitInt:");
static_assert(__has_unique_object_representations(_BitInt(128)), "BitInt:");
+namespace GH95311 {
+
+template <int>
+class Foo {
+ int x;
+};
+static_assert(__has_unique_object_representations(Foo<0>[]));
+class Bar; // expected-note {{forward declaration of 'GH95311::Bar'}}
+static_assert(__has_unique_object_representations(Bar[])); // expected-error {{incomplete type}}
+
+}
namespace PR46209 {
// Foo has both a trivial assignment operator and a non-trivial one.
|
clang/lib/AST/ASTContext.cpp
Outdated
@@ -2791,6 +2791,12 @@ bool ASTContext::hasUniqueObjectRepresentations( | |||
return hasUniqueObjectRepresentations(getBaseElementType(Ty), | |||
CheckIfTriviallyCopyable); | |||
|
|||
if (Ty->isVoidType()) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is not clear why we need this change as well.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For the new !Ty->isIncompleteType()
assertion below. Before void
would go to the !isTriviallyCopyable
path, this is just a more explicit way of handling __has_unique_object_representations(void)
. The assertion could also be assert(Ty->isVoidType() || !Ty->isIncompleteType())
to follow the spec better?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd prefer that, I think
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
…antiated-unbounded-array
…ions` to be complete (#95432) Summary: Fixes #95311 Previous behaviour was that `false` was silently returned, templated classes were not instantiated and incomplete classes did not issue an error. --------- Co-authored-by: cor3ntin <[email protected]> Test Plan: Reviewers: Subscribers: Tasks: Tags: Differential Revision: https://phabricator.intern.facebook.com/D60250880
Fixes #95311
Previous behaviour was that
false
was silently returned, templated classes were not instantiated and incomplete classes did not issue an error.