diff options
author | Akira Hatanaka <ahatanaka@apple.com> | 2019-07-13 01:47:15 +0000 |
---|---|---|
committer | Akira Hatanaka <ahatanaka@apple.com> | 2019-07-13 01:47:15 +0000 |
commit | 657b099cc209b4c70658e8cbc1e29e40b7dbffe7 (patch) | |
tree | 1c79967bb90719a1d22e9b8ee2b957570bc15364 /lib/Sema/Sema.cpp | |
parent | dd578bb497322855a0116d2ed3b6ccff7f8ad7db (diff) | |
download | clang-657b099cc209b4c70658e8cbc1e29e40b7dbffe7.tar.gz |
[Sema] Diagnose default-initialization, destruction, and copying of
non-trivial C union types
This patch diagnoses uses of non-trivial C unions and structs/unions
containing non-trivial C unions in the following contexts, which require
default-initialization, destruction, or copying of the union objects,
instead of disallowing fields of non-trivial types in C unions, which is
what we currently do:
- function parameters.
- function returns.
- assignments.
- compound literals.
- block captures except capturing of `__block` variables by non-escaping
blocks.
- local and global variable definitions.
- lvalue-to-rvalue conversions of volatile types.
See the discussion in https://reviews.llvm.org/D62988 for more background.
rdar://problem/50679094
Differential Revision: https://reviews.llvm.org/D63753
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@365985 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/Sema.cpp')
-rw-r--r-- | lib/Sema/Sema.cpp | 18 |
1 files changed, 15 insertions, 3 deletions
diff --git a/lib/Sema/Sema.cpp b/lib/Sema/Sema.cpp index 3941643893..11fed28b52 100644 --- a/lib/Sema/Sema.cpp +++ b/lib/Sema/Sema.cpp @@ -1658,12 +1658,24 @@ static void markEscapingByrefs(const FunctionScopeInfo &FSI, Sema &S) { // Set the EscapingByref flag of __block variables captured by // escaping blocks. for (const BlockDecl *BD : FSI.Blocks) { - if (BD->doesNotEscape()) - continue; for (const BlockDecl::Capture &BC : BD->captures()) { VarDecl *VD = BC.getVariable(); - if (VD->hasAttr<BlocksAttr>()) + if (VD->hasAttr<BlocksAttr>()) { + // Nothing to do if this is a __block variable captured by a + // non-escaping block. + if (BD->doesNotEscape()) + continue; VD->setEscapingByref(); + } + // Check whether the captured variable is or contains an object of + // non-trivial C union type. + QualType CapType = BC.getVariable()->getType(); + if (CapType.hasNonTrivialToPrimitiveDestructCUnion() || + CapType.hasNonTrivialToPrimitiveCopyCUnion()) + S.checkNonTrivialCUnion(BC.getVariable()->getType(), + BD->getCaretLocation(), + Sema::NTCUC_BlockCapture, + Sema::NTCUK_Destruct|Sema::NTCUK_Copy); } } |