Coverage Report

Created: 2021-08-24 07:12

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/include/clang/AST/GlobalDecl.h
Line
Count
Source (jump to first uncovered line)
1
//===- GlobalDecl.h - Global declaration holder -----------------*- C++ -*-===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
//
9
// A GlobalDecl can hold either a regular variable/function or a C++ ctor/dtor
10
// together with its type.
11
//
12
//===----------------------------------------------------------------------===//
13
14
#ifndef LLVM_CLANG_AST_GLOBALDECL_H
15
#define LLVM_CLANG_AST_GLOBALDECL_H
16
17
#include "clang/AST/Attr.h"
18
#include "clang/AST/DeclCXX.h"
19
#include "clang/AST/DeclObjC.h"
20
#include "clang/AST/DeclOpenMP.h"
21
#include "clang/Basic/ABI.h"
22
#include "clang/Basic/LLVM.h"
23
#include "llvm/ADT/DenseMapInfo.h"
24
#include "llvm/ADT/PointerIntPair.h"
25
#include "llvm/Support/Casting.h"
26
#include "llvm/Support/type_traits.h"
27
#include <cassert>
28
29
namespace clang {
30
31
enum class DynamicInitKind : unsigned {
32
  NoStub = 0,
33
  Initializer,
34
  AtExit,
35
  GlobalArrayDestructor
36
};
37
38
enum class KernelReferenceKind : unsigned {
39
  Kernel = 0,
40
  Stub = 1,
41
};
42
43
/// GlobalDecl - represents a global declaration. This can either be a
44
/// CXXConstructorDecl and the constructor type (Base, Complete).
45
/// a CXXDestructorDecl and the destructor type (Base, Complete),
46
/// a FunctionDecl and the kernel reference type (Kernel, Stub), or
47
/// a VarDecl, a FunctionDecl or a BlockDecl.
48
///
49
/// When a new type of GlobalDecl is added, the following places should
50
/// be updated to convert a Decl* to a GlobalDecl:
51
/// PredefinedExpr::ComputeName() in lib/AST/Expr.cpp.
52
/// getParentOfLocalEntity() in lib/AST/ItaniumMangle.cpp
53
/// ASTNameGenerator::Implementation::writeFuncOrVarName in lib/AST/Mangle.cpp
54
///
55
class GlobalDecl {
56
  llvm::PointerIntPair<const Decl *, 3> Value;
57
  unsigned MultiVersionIndex = 0;
58
59
33.6M
  void Init(const Decl *D) {
60
33.6M
    assert(!isa<CXXConstructorDecl>(D) && "Use other ctor with ctor decls!");
61
0
    assert(!isa<CXXDestructorDecl>(D) && "Use other ctor with dtor decls!");
62
0
    assert(!D->hasAttr<CUDAGlobalAttr>() && "Use other ctor with GPU kernels!");
63
64
0
    Value.setPointer(D);
65
33.6M
  }
66
67
public:
68
36.1M
  GlobalDecl() = default;
69
1.83M
  GlobalDecl(const VarDecl *D) { Init(D);}
70
  GlobalDecl(const FunctionDecl *D, unsigned MVIndex = 0)
71
27.0M
      : MultiVersionIndex(MVIndex) {
72
27.0M
    if (!D->hasAttr<CUDAGlobalAttr>()) {
73
27.0M
      Init(D);
74
27.0M
      return;
75
27.0M
    }
76
264
    Value.setPointerAndInt(D, unsigned(getDefaultKernelReference(D)));
77
264
  }
78
  GlobalDecl(const FunctionDecl *D, KernelReferenceKind Kind)
79
156
      : Value(D, unsigned(Kind)) {
80
156
    assert(D->hasAttr<CUDAGlobalAttr>() && "Decl is not a GPU kernel!");
81
156
  }
82
4.65M
  GlobalDecl(const NamedDecl *D) { Init(D); }
83
4.31k
  GlobalDecl(const BlockDecl *D) { Init(D); }
84
74.3k
  GlobalDecl(const CapturedDecl *D) { Init(D); }
85
21.4k
  GlobalDecl(const ObjCMethodDecl *D) { Init(D); }
86
10
  GlobalDecl(const OMPDeclareReductionDecl *D) { Init(D); }
87
0
  GlobalDecl(const OMPDeclareMapperDecl *D) { Init(D); }
88
466k
  GlobalDecl(const CXXConstructorDecl *D, CXXCtorType Type) : Value(D, Type) {}
89
122k
  GlobalDecl(const CXXDestructorDecl *D, CXXDtorType Type) : Value(D, Type) {}
90
  GlobalDecl(const VarDecl *D, DynamicInitKind StubKind)
91
6.36k
      : Value(D, unsigned(StubKind)) {}
92
93
4.67M
  GlobalDecl getCanonicalDecl() const {
94
4.67M
    GlobalDecl CanonGD;
95
4.67M
    CanonGD.Value.setPointer(Value.getPointer()->getCanonicalDecl());
96
4.67M
    CanonGD.Value.setInt(Value.getInt());
97
4.67M
    CanonGD.MultiVersionIndex = MultiVersionIndex;
98
99
4.67M
    return CanonGD;
100
4.67M
  }
101
102
83.7M
  const Decl *getDecl() const { return Value.getPointer(); }
103
104
404k
  CXXCtorType getCtorType() const {
105
404k
    assert(isa<CXXConstructorDecl>(getDecl()) && "Decl is not a ctor!");
106
0
    return static_cast<CXXCtorType>(Value.getInt());
107
404k
  }
108
109
286k
  CXXDtorType getDtorType() const {
110
286k
    assert(isa<CXXDestructorDecl>(getDecl()) && "Decl is not a dtor!");
111
0
    return static_cast<CXXDtorType>(Value.getInt());
112
286k
  }
113
114
1.54k
  DynamicInitKind getDynamicInitKind() const {
115
1.54k
    assert(isa<VarDecl>(getDecl()) &&
116
1.54k
           cast<VarDecl>(getDecl())->hasGlobalStorage() &&
117
1.54k
           "Decl is not a global variable!");
118
0
    return static_cast<DynamicInitKind>(Value.getInt());
119
1.54k
  }
120
121
132
  unsigned getMultiVersionIndex() const {
122
132
    assert(isa<FunctionDecl>(
123
132
               getDecl()) &&
124
132
               !cast<FunctionDecl>(getDecl())->hasAttr<CUDAGlobalAttr>() &&
125
132
           !isa<CXXConstructorDecl>(getDecl()) &&
126
132
           !isa<CXXDestructorDecl>(getDecl()) &&
127
132
           "Decl is not a plain FunctionDecl!");
128
0
    return MultiVersionIndex;
129
132
  }
130
131
484
  KernelReferenceKind getKernelReferenceKind() const {
132
484
    assert(isa<FunctionDecl>(getDecl()) &&
133
484
           cast<FunctionDecl>(getDecl())->hasAttr<CUDAGlobalAttr>() &&
134
484
           "Decl is not a GPU kernel!");
135
0
    return static_cast<KernelReferenceKind>(Value.getInt());
136
484
  }
137
138
96.9M
  friend bool operator==(const GlobalDecl &LHS, const GlobalDecl &RHS) {
139
96.9M
    return LHS.Value == RHS.Value &&
140
96.9M
           
LHS.MultiVersionIndex == RHS.MultiVersionIndex20.6M
;
141
96.9M
  }
142
143
15.7M
  void *getAsOpaquePtr() const { return Value.getOpaqueValue(); }
144
145
4.60M
  explicit operator bool() const { return getAsOpaquePtr(); }
146
147
11.2M
  static GlobalDecl getFromOpaquePtr(void *P) {
148
11.2M
    GlobalDecl GD;
149
11.2M
    GD.Value.setFromOpaqueValue(P);
150
11.2M
    return GD;
151
11.2M
  }
152
153
264
  static KernelReferenceKind getDefaultKernelReference(const FunctionDecl *D) {
154
264
    return D->getLangOpts().CUDAIsDevice ? 
KernelReferenceKind::Kernel150
155
264
                                         : 
KernelReferenceKind::Stub114
;
156
264
  }
157
158
4.73M
  GlobalDecl getWithDecl(const Decl *D) {
159
4.73M
    GlobalDecl Result(*this);
160
4.73M
    Result.Value.setPointer(D);
161
4.73M
    return Result;
162
4.73M
  }
163
164
17.8k
  GlobalDecl getWithCtorType(CXXCtorType Type) {
165
17.8k
    assert(isa<CXXConstructorDecl>(getDecl()));
166
0
    GlobalDecl Result(*this);
167
17.8k
    Result.Value.setInt(Type);
168
17.8k
    return Result;
169
17.8k
  }
170
171
7.69k
  GlobalDecl getWithDtorType(CXXDtorType Type) {
172
7.69k
    assert(isa<CXXDestructorDecl>(getDecl()));
173
0
    GlobalDecl Result(*this);
174
7.69k
    Result.Value.setInt(Type);
175
7.69k
    return Result;
176
7.69k
  }
177
178
82
  GlobalDecl getWithMultiVersionIndex(unsigned Index) {
179
82
    assert(isa<FunctionDecl>(getDecl()) &&
180
82
           !cast<FunctionDecl>(getDecl())->hasAttr<CUDAGlobalAttr>() &&
181
82
           !isa<CXXConstructorDecl>(getDecl()) &&
182
82
           !isa<CXXDestructorDecl>(getDecl()) &&
183
82
           "Decl is not a plain FunctionDecl!");
184
0
    GlobalDecl Result(*this);
185
82
    Result.MultiVersionIndex = Index;
186
82
    return Result;
187
82
  }
188
189
146
  GlobalDecl getWithKernelReferenceKind(KernelReferenceKind Kind) {
190
146
    assert(isa<FunctionDecl>(getDecl()) &&
191
146
           cast<FunctionDecl>(getDecl())->hasAttr<CUDAGlobalAttr>() &&
192
146
           "Decl is not a GPU kernel!");
193
0
    GlobalDecl Result(*this);
194
146
    Result.Value.setInt(unsigned(Kind));
195
146
    return Result;
196
146
  }
197
};
198
199
} // namespace clang
200
201
namespace llvm {
202
203
  template<> struct DenseMapInfo<clang::GlobalDecl> {
204
14.2M
    static inline clang::GlobalDecl getEmptyKey() {
205
14.2M
      return clang::GlobalDecl();
206
14.2M
    }
207
208
11.2M
    static inline clang::GlobalDecl getTombstoneKey() {
209
11.2M
      return clang::GlobalDecl::
210
11.2M
        getFromOpaquePtr(reinterpret_cast<void*>(-1));
211
11.2M
    }
212
213
11.1M
    static unsigned getHashValue(clang::GlobalDecl GD) {
214
11.1M
      return DenseMapInfo<void*>::getHashValue(GD.getAsOpaquePtr());
215
11.1M
    }
216
217
    static bool isEqual(clang::GlobalDecl LHS,
218
96.9M
                        clang::GlobalDecl RHS) {
219
96.9M
      return LHS == RHS;
220
96.9M
    }
221
  };
222
223
} // namespace llvm
224
225
#endif // LLVM_CLANG_AST_GLOBALDECL_H