Skip to content

Conversation

tbaederr
Copy link
Contributor

@tbaederr tbaederr commented Aug 20, 2025

When initializing an anonymous struct via an IndirectFieldDecl, we create an APValue for the struct, but we leave the fields uninitialized. This would later cause the CXXConstructExpr that initializes the anonymous struct member to not do anything since its APValue already had a value (but the member didn't). Just remove the check for an APValue that already has a value from RecordExprEvaluator::VisitCXXConstructExpr().

Fixes #154567

@llvmbot llvmbot added clang Clang issues not falling into any other category clang:frontend Language frontend issues, e.g. anything involving "Sema" labels Aug 20, 2025
@tbaederr tbaederr marked this pull request as draft August 20, 2025 20:43
@llvmbot
Copy link
Member

llvmbot commented Aug 20, 2025

@llvm/pr-subscribers-clang

Author: Timm Baeder (tbaederr)

Changes

Let's see if this fixes #154567 without regressions.


Full diff: https://github.com/llvm/llvm-project/pull/154610.diff

1 Files Affected:

  • (modified) clang/lib/AST/ExprConstant.cpp (+2-2)
diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp
index 40c56501b0c14..c51f132614667 100644
--- a/clang/lib/AST/ExprConstant.cpp
+++ b/clang/lib/AST/ExprConstant.cpp
@@ -11046,8 +11046,8 @@ bool RecordExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E,
   bool ZeroInit = E->requiresZeroInitialization();
   if (CheckTrivialDefaultConstructor(Info, E->getExprLoc(), FD, ZeroInit)) {
     // If we've already performed zero-initialization, we're already done.
-    if (Result.hasValue())
-      return true;
+    if (Result.hasValue()) {
+    }
 
     if (ZeroInit)
       return ZeroInitialization(E, T);

@tbaederr tbaederr marked this pull request as ready for review August 21, 2025 06:08
@philnik777
Copy link
Contributor

Thanks for having a look so quickly!

Copy link
Collaborator

@AaronBallman AaronBallman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, thank you for checking the performance characteristics of the change! I think we need a release note, though.

@tbaederr
Copy link
Contributor Author

Does a release note make sense if the patch gets backported to the release branch anyway?

@AaronBallman
Copy link
Collaborator

Does a release note make sense if the patch gets backported to the release branch anyway?

Nope! I didn't realize this was heading for a backport

@tbaederr
Copy link
Contributor Author

@philnik777 Merge this whenever you need it, otherwise I'd leave it open for one of the other reviewers to look at.

@philnik777
Copy link
Contributor

@tbaederr Thanks! I'll merge it once the fix on our side is ready.

@philnik777 philnik777 merged commit 8b3d4bd into llvm:main Aug 23, 2025
9 checks passed
@github-project-automation github-project-automation bot moved this from Needs Triage to Done in LLVM Release Status Aug 23, 2025
@philnik777
Copy link
Contributor

/cherry-pick 8b3d4bd

@llvmbot
Copy link
Member

llvmbot commented Aug 23, 2025

Failed to cherry-pick: 8b3d4bd

https://github.com/llvm/llvm-project/actions/runs/17173100689

Please manually backport the fix and push it to your github fork. Once this is done, please create a pull request

@@ -11045,10 +11045,6 @@ bool RecordExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E,

bool ZeroInit = E->requiresZeroInitialization();
if (CheckTrivialDefaultConstructor(Info, E->getExprLoc(), FD, ZeroInit)) {
// If we've already performed zero-initialization, we're already done.
if (Result.hasValue())
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Was this code do nothing then? It looks like this check came in with e637cbe

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When it's working correctly, it allows skipping work zero-initializing something that's already zero-initialized, I think. But that assumes we maintain an invariant about exactly when values are absent, vs. uninitialized. We don't maintain that invariant for anonymous structs. (We probably could, but it's a little tricky to implement correctly for nested anonymous structs.)

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense, maybe worth a FIXME, probably not a huge win though.

philnik777 pushed a commit to philnik777/llvm-project that referenced this pull request Aug 25, 2025
…tructExpr()` (llvm#154610)

When initializing an anonymous struct via an `IndirectFieldDecl`, we
create an `APValue` for the struct, but we leave the fields
uninitialized. This would later cause the `CXXConstructExpr` that
initializes the anonymous struct member to not do anything since its
`APValue` already had a value (but the member didn't). Just remove the
check for an `APValue` that already has a value from
`RecordExprEvaluator::VisitCXXConstructExpr()`.

Fixes llvm#154567
tru pushed a commit to philnik777/llvm-project that referenced this pull request Aug 26, 2025
…tructExpr()` (llvm#154610)

When initializing an anonymous struct via an `IndirectFieldDecl`, we
create an `APValue` for the struct, but we leave the fields
uninitialized. This would later cause the `CXXConstructExpr` that
initializes the anonymous struct member to not do anything since its
`APValue` already had a value (but the member didn't). Just remove the
check for an `APValue` that already has a value from
`RecordExprEvaluator::VisitCXXConstructExpr()`.

Fixes llvm#154567
@h-vetinari
Copy link
Contributor

Failed to cherry-pick: 8b3d4bd

For completeness, this was done in 3263ad7

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
clang:frontend Language frontend issues, e.g. anything involving "Sema" clang Clang issues not falling into any other category release:cherry-pick-failed
Projects
Development

Successfully merging this pull request may close these issues.

[Clang] constant evaluator thinks that elements of an unnamed struct is not initialized
7 participants