diff options
author | Shafik Yaghmour <shafik.yaghmour@intel.com> | 2023-05-08 11:13:08 -0700 |
---|---|---|
committer | Shafik Yaghmour <shafik.yaghmour@intel.com> | 2023-05-08 11:14:33 -0700 |
commit | 96bc78631f16fe5ce2e7e6000b74d790b32f7a16 (patch) | |
tree | 5bac08570586a9f015b5cd383adc7bca44c5f8fa /clang/lib/Sema/SemaInit.cpp | |
parent | 0dec49cb3466c7fe116030a568be423c6aa5bdf3 (diff) | |
download | llvm-96bc78631f16fe5ce2e7e6000b74d790b32f7a16.zip llvm-96bc78631f16fe5ce2e7e6000b74d790b32f7a16.tar.gz llvm-96bc78631f16fe5ce2e7e6000b74d790b32f7a16.tar.bz2 |
[Clang] Update warning on some designator initializer cases involving unions
Currently when using designated initializers in C++ we have a few
extension. Two extension which are dangerous involved assigning to
multiple members of union which will likely be a mistake since unions
can only have one active member. I have updated to be a warning by
default.
The second case if when we assign to multiple union members and one of
the previous members had a non-trivial destructor, which could lead to
leaking resources. This one is now an error by default.
Fixes: https://github.com/llvm/llvm-project/issues/62156
Differential Revision: https://reviews.llvm.org/D149694
Diffstat (limited to 'clang/lib/Sema/SemaInit.cpp')
-rw-r--r-- | clang/lib/Sema/SemaInit.cpp | 15 |
1 files changed, 11 insertions, 4 deletions
diff --git a/clang/lib/Sema/SemaInit.cpp b/clang/lib/Sema/SemaInit.cpp index d27cd6b..3db7022 100644 --- a/clang/lib/Sema/SemaInit.cpp +++ b/clang/lib/Sema/SemaInit.cpp @@ -394,12 +394,15 @@ class InitListChecker { /// Diagnose that OldInit (or part thereof) has been overridden by NewInit. void diagnoseInitOverride(Expr *OldInit, SourceRange NewInitRange, + bool UnionOverride = false, bool FullyOverwritten = true) { // Overriding an initializer via a designator is valid with C99 designated // initializers, but ill-formed with C++20 designated initializers. - unsigned DiagID = SemaRef.getLangOpts().CPlusPlus - ? diag::ext_initializer_overrides - : diag::warn_initializer_overrides; + unsigned DiagID = + SemaRef.getLangOpts().CPlusPlus + ? (UnionOverride ? diag::ext_initializer_union_overrides + : diag::ext_initializer_overrides) + : diag::warn_initializer_overrides; if (InOverloadResolution && SemaRef.getLangOpts().CPlusPlus) { // In overload resolution, we have to strictly enforce the rules, and so @@ -2546,6 +2549,7 @@ InitListChecker::CheckDesignatedInitializer(const InitializedEntity &Entity, // subobject [0].b. diagnoseInitOverride(ExistingInit, SourceRange(D->getBeginLoc(), DIE->getEndLoc()), + /*UnionOverride=*/false, /*FullyOverwritten=*/false); if (!VerifyOnly) { @@ -2691,7 +2695,10 @@ InitListChecker::CheckDesignatedInitializer(const InitializedEntity &Entity, if (ExistingInit) { // We're about to throw away an initializer, emit warning. diagnoseInitOverride( - ExistingInit, SourceRange(D->getBeginLoc(), DIE->getEndLoc())); + ExistingInit, SourceRange(D->getBeginLoc(), DIE->getEndLoc()), + /*UnionOverride=*/true, + /*FullyOverwritten=*/SemaRef.getLangOpts().CPlusPlus ? false + : true); } // remove existing initializer |