]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/tools/clang/include/clang/AST/NonTrivialTypeVisitor.h
Merge clang 7.0.1 and several follow-up changes
[FreeBSD/FreeBSD.git] / contrib / llvm / tools / clang / include / clang / AST / NonTrivialTypeVisitor.h
1 //===-- NonTrivialTypeVisitor.h - Visitor for non-trivial Types *- C++ --*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 //  This file defines the visitor classes that are used to traverse non-trivial
11 //  structs.
12 //
13 //===----------------------------------------------------------------------===//
14
15 #ifndef LLVM_CLANG_NON_TRIVIAL_TYPE_VISITOR_H
16 #define LLVM_CLANG_NON_TRIVIAL_TYPE_VISITOR_H
17
18 #include "clang/AST/Type.h"
19
20 namespace clang {
21
22 template <class Derived, class RetTy = void> struct DestructedTypeVisitor {
23   template <class... Ts> RetTy visit(QualType FT, Ts &&... Args) {
24     return asDerived().visitWithKind(FT.isDestructedType(), FT,
25                                      std::forward<Ts>(Args)...);
26   }
27
28   template <class... Ts>
29   RetTy visitWithKind(QualType::DestructionKind DK, QualType FT,
30                       Ts &&... Args) {
31     switch (DK) {
32     case QualType::DK_objc_strong_lifetime:
33       return asDerived().visitARCStrong(FT, std::forward<Ts>(Args)...);
34     case QualType::DK_nontrivial_c_struct:
35       return asDerived().visitStruct(FT, std::forward<Ts>(Args)...);
36     case QualType::DK_none:
37       return asDerived().visitTrivial(FT, std::forward<Ts>(Args)...);
38     case QualType::DK_cxx_destructor:
39       return asDerived().visitCXXDestructor(FT, std::forward<Ts>(Args)...);
40     case QualType::DK_objc_weak_lifetime:
41       return asDerived().visitARCWeak(FT, std::forward<Ts>(Args)...);
42     }
43
44     llvm_unreachable("unknown destruction kind");
45   }
46
47   Derived &asDerived() { return static_cast<Derived &>(*this); }
48 };
49
50 template <class Derived, class RetTy = void>
51 struct DefaultInitializedTypeVisitor {
52   template <class... Ts> RetTy visit(QualType FT, Ts &&... Args) {
53     return asDerived().visitWithKind(
54         FT.isNonTrivialToPrimitiveDefaultInitialize(), FT,
55         std::forward<Ts>(Args)...);
56   }
57
58   template <class... Ts>
59   RetTy visitWithKind(QualType::PrimitiveDefaultInitializeKind PDIK,
60                       QualType FT, Ts &&... Args) {
61     switch (PDIK) {
62     case QualType::PDIK_ARCStrong:
63       return asDerived().visitARCStrong(FT, std::forward<Ts>(Args)...);
64     case QualType::PDIK_ARCWeak:
65       return asDerived().visitARCWeak(FT, std::forward<Ts>(Args)...);
66     case QualType::PDIK_Struct:
67       return asDerived().visitStruct(FT, std::forward<Ts>(Args)...);
68     case QualType::PDIK_Trivial:
69       return asDerived().visitTrivial(FT, std::forward<Ts>(Args)...);
70     }
71
72     llvm_unreachable("unknown default-initialize kind");
73   }
74
75   Derived &asDerived() { return static_cast<Derived &>(*this); }
76 };
77
78 template <class Derived, bool IsMove, class RetTy = void>
79 struct CopiedTypeVisitor {
80   template <class... Ts> RetTy visit(QualType FT, Ts &&... Args) {
81     QualType::PrimitiveCopyKind PCK =
82         IsMove ? FT.isNonTrivialToPrimitiveDestructiveMove()
83                : FT.isNonTrivialToPrimitiveCopy();
84     return asDerived().visitWithKind(PCK, FT, std::forward<Ts>(Args)...);
85   }
86
87   template <class... Ts>
88   RetTy visitWithKind(QualType::PrimitiveCopyKind PCK, QualType FT,
89                       Ts &&... Args) {
90     asDerived().preVisit(PCK, FT, std::forward<Ts>(Args)...);
91
92     switch (PCK) {
93     case QualType::PCK_ARCStrong:
94       return asDerived().visitARCStrong(FT, std::forward<Ts>(Args)...);
95     case QualType::PCK_ARCWeak:
96       return asDerived().visitARCWeak(FT, std::forward<Ts>(Args)...);
97     case QualType::PCK_Struct:
98       return asDerived().visitStruct(FT, std::forward<Ts>(Args)...);
99     case QualType::PCK_Trivial:
100       return asDerived().visitTrivial(FT, std::forward<Ts>(Args)...);
101     case QualType::PCK_VolatileTrivial:
102       return asDerived().visitVolatileTrivial(FT, std::forward<Ts>(Args)...);
103     }
104
105     llvm_unreachable("unknown primitive copy kind");
106   }
107
108   Derived &asDerived() { return static_cast<Derived &>(*this); }
109 };
110
111 } // end namespace clang
112
113 #endif