/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/Driver/Types.cpp
Line | Count | Source (jump to first uncovered line) |
1 | | //===--- Types.cpp - Driver input & temporary type information ------------===// |
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 | | #include "clang/Driver/Types.h" |
10 | | #include "clang/Driver/Driver.h" |
11 | | #include "clang/Driver/DriverDiagnostic.h" |
12 | | #include "clang/Driver/Options.h" |
13 | | #include "llvm/ADT/STLExtras.h" |
14 | | #include "llvm/ADT/SmallVector.h" |
15 | | #include "llvm/ADT/StringSwitch.h" |
16 | | #include "llvm/Option/Arg.h" |
17 | | #include <cassert> |
18 | | #include <cstring> |
19 | | |
20 | | using namespace clang::driver; |
21 | | using namespace clang::driver::types; |
22 | | |
23 | | struct TypeInfo { |
24 | | const char *Name; |
25 | | const char *TempSuffix; |
26 | | ID PreprocessedType; |
27 | | class PhasesBitSet { |
28 | | unsigned Bits = 0; |
29 | | |
30 | | public: |
31 | 0 | constexpr PhasesBitSet(std::initializer_list<phases::ID> Phases) { |
32 | 0 | for (auto Id : Phases) |
33 | 0 | Bits |= 1 << Id; |
34 | 0 | } |
35 | 1.13M | bool contains(phases::ID Id) const { return Bits & (1 << Id); } |
36 | | } Phases; |
37 | | }; |
38 | | |
39 | | static constexpr TypeInfo TypeInfos[] = { |
40 | | #define TYPE(NAME, ID, PP_TYPE, TEMP_SUFFIX, ...) \ |
41 | | { NAME, TEMP_SUFFIX, TY_##PP_TYPE, { __VA_ARGS__ }, }, |
42 | | #include "clang/Driver/Types.def" |
43 | | #undef TYPE |
44 | | }; |
45 | | static const unsigned numTypes = std::size(TypeInfos); |
46 | | |
47 | 513k | static const TypeInfo &getInfo(unsigned id) { |
48 | 513k | assert(id > 0 && id - 1 < numTypes && "Invalid Type ID."); |
49 | 513k | return TypeInfos[id - 1]; |
50 | 513k | } |
51 | | |
52 | 48.9k | const char *types::getTypeName(ID Id) { |
53 | 48.9k | return getInfo(Id).Name; |
54 | 48.9k | } |
55 | | |
56 | 122k | types::ID types::getPreprocessedType(ID Id) { |
57 | 122k | ID PPT = getInfo(Id).PreprocessedType; |
58 | 122k | assert((getInfo(Id).Phases.contains(phases::Preprocess) != |
59 | 122k | (PPT == TY_INVALID)) && |
60 | 122k | "Unexpected Preprocess Type."); |
61 | 122k | return PPT; |
62 | 122k | } |
63 | | |
64 | 198 | static bool isPreprocessedModuleType(ID Id) { |
65 | 198 | return Id == TY_CXXModule || Id == TY_PP_CXXModule; |
66 | 198 | } |
67 | | |
68 | 84 | static bool isPreprocessedHeaderUnitType(ID Id) { |
69 | 84 | return Id == TY_CXXSHeader || Id == TY_CXXUHeader || Id == TY_CXXHUHeader || |
70 | 84 | Id == TY_PP_CXXHeaderUnit; |
71 | 84 | } |
72 | | |
73 | 115 | types::ID types::getPrecompiledType(ID Id) { |
74 | 115 | if (isPreprocessedModuleType(Id)) |
75 | 31 | return TY_ModuleFile; |
76 | 84 | if (isPreprocessedHeaderUnitType(Id)) |
77 | 9 | return TY_HeaderUnit; |
78 | 75 | if (onlyPrecompileType(Id)) |
79 | 75 | return TY_PCH; |
80 | 0 | return TY_INVALID; |
81 | 75 | } |
82 | | |
83 | 12.1k | const char *types::getTypeTempSuffix(ID Id, bool CLStyle) { |
84 | 12.1k | if (CLStyle) { |
85 | 961 | switch (Id) { |
86 | 553 | case TY_Object: |
87 | 560 | case TY_LTO_BC: |
88 | 560 | return "obj"; |
89 | 347 | case TY_Image: |
90 | 347 | return "exe"; |
91 | 38 | case TY_PP_Asm: |
92 | 38 | return "asm"; |
93 | 16 | default: |
94 | 16 | break; |
95 | 961 | } |
96 | 961 | } |
97 | 11.1k | return getInfo(Id).TempSuffix; |
98 | 12.1k | } |
99 | | |
100 | 83 | bool types::onlyPrecompileType(ID Id) { |
101 | 83 | return getInfo(Id).Phases.contains(phases::Precompile) && |
102 | 83 | !isPreprocessedModuleType(Id); |
103 | 83 | } |
104 | | |
105 | 43.3k | bool types::canTypeBeUserSpecified(ID Id) { |
106 | 43.3k | static const clang::driver::types::ID kStaticLangageTypes[] = { |
107 | 43.3k | TY_CUDA_DEVICE, TY_HIP_DEVICE, TY_PP_CHeader, |
108 | 43.3k | TY_PP_ObjCHeader, TY_PP_CXXHeader, TY_PP_ObjCXXHeader, |
109 | 43.3k | TY_PP_CXXModule, TY_LTO_IR, TY_LTO_BC, |
110 | 43.3k | TY_Plist, TY_RewrittenObjC, TY_RewrittenLegacyObjC, |
111 | 43.3k | TY_Remap, TY_PCH, TY_Object, |
112 | 43.3k | TY_Image, TY_dSYM, TY_Dependencies, |
113 | 43.3k | TY_CUDA_FATBIN, TY_HIP_FATBIN}; |
114 | 43.3k | return !llvm::is_contained(kStaticLangageTypes, Id); |
115 | 43.3k | } |
116 | | |
117 | 5.43k | bool types::appendSuffixForType(ID Id) { |
118 | 5.43k | return Id == TY_PCH || Id == TY_dSYM5.43k || Id == TY_CUDA_FATBIN5.36k || |
119 | 5.43k | Id == TY_HIP_FATBIN5.36k ; |
120 | 5.43k | } |
121 | | |
122 | 30 | bool types::canLipoType(ID Id) { |
123 | 30 | return (Id == TY_Nothing || |
124 | 30 | Id == TY_Image29 || |
125 | 30 | Id == TY_Object10 || |
126 | 30 | Id == TY_LTO_BC0 ); |
127 | 30 | } |
128 | | |
129 | 53.9k | bool types::isAcceptedByClang(ID Id) { |
130 | 53.9k | switch (Id) { |
131 | 6.03k | default: |
132 | 6.03k | return false; |
133 | | |
134 | 74 | case TY_Asm: |
135 | 14.1k | case TY_C: 1.62k case TY_PP_C: |
136 | 14.2k | case TY_CL: case TY_CLCXX: |
137 | 14.3k | case TY_CUDA: 14.2k case TY_PP_CUDA: |
138 | 14.3k | case TY_CUDA_DEVICE: |
139 | 14.4k | case TY_HIP: |
140 | 15.0k | case TY_PP_HIP: |
141 | 15.1k | case TY_HIP_DEVICE: |
142 | 16.8k | case TY_ObjC: 15.1k case TY_PP_ObjC: 16.8k case TY_PP_ObjC_Alias: |
143 | 46.2k | case TY_CXX: 17.0k case TY_PP_CXX: |
144 | 47.4k | case TY_ObjCXX: 46.2k case TY_PP_ObjCXX: 47.4k case TY_PP_ObjCXX_Alias: |
145 | 47.5k | case TY_CHeader: 47.5k case TY_PP_CHeader: |
146 | 47.5k | case TY_CLHeader: |
147 | 47.5k | case TY_ObjCHeader: 47.5k case TY_PP_ObjCHeader: |
148 | 47.5k | case TY_CXXHeader: 47.5k case TY_PP_CXXHeader: |
149 | 47.5k | case TY_CXXSHeader: |
150 | 47.5k | case TY_CXXUHeader: |
151 | 47.5k | case TY_CXXHUHeader: |
152 | 47.6k | case TY_PP_CXXHeaderUnit: |
153 | 47.6k | case TY_ObjCXXHeader: case TY_PP_ObjCXXHeader: |
154 | 47.6k | case TY_CXXModule: 47.6k case TY_PP_CXXModule: |
155 | 47.6k | case TY_AST: 47.6k case TY_ModuleFile: 47.6k case TY_PCH: |
156 | 47.9k | case TY_LLVM_IR: 47.7k case TY_LLVM_BC: |
157 | 47.9k | case TY_API_INFO: |
158 | 47.9k | return true; |
159 | 53.9k | } |
160 | 53.9k | } |
161 | | |
162 | 20 | bool types::isAcceptedByFlang(ID Id) { |
163 | 20 | switch (Id) { |
164 | 3 | default: |
165 | 3 | return false; |
166 | | |
167 | 2 | case TY_Fortran: |
168 | 15 | case TY_PP_Fortran: |
169 | 15 | return true; |
170 | 0 | case TY_LLVM_IR: |
171 | 2 | case TY_LLVM_BC: |
172 | 2 | return true; |
173 | 20 | } |
174 | 20 | } |
175 | | |
176 | 2 | bool types::isDerivedFromC(ID Id) { |
177 | 2 | switch (Id) { |
178 | 1 | default: |
179 | 1 | return false; |
180 | | |
181 | 0 | case TY_PP_C: |
182 | 1 | case TY_C: |
183 | 1 | case TY_CL: |
184 | 1 | case TY_CLCXX: |
185 | 1 | case TY_PP_CUDA: |
186 | 1 | case TY_CUDA: |
187 | 1 | case TY_CUDA_DEVICE: |
188 | 1 | case TY_PP_HIP: |
189 | 1 | case TY_HIP: |
190 | 1 | case TY_HIP_DEVICE: |
191 | 1 | case TY_PP_ObjC: |
192 | 1 | case TY_PP_ObjC_Alias: |
193 | 1 | case TY_ObjC: |
194 | 1 | case TY_PP_CXX: |
195 | 1 | case TY_CXX: |
196 | 1 | case TY_PP_ObjCXX: |
197 | 1 | case TY_PP_ObjCXX_Alias: |
198 | 1 | case TY_ObjCXX: |
199 | 1 | case TY_RenderScript: |
200 | 1 | case TY_PP_CHeader: |
201 | 1 | case TY_CHeader: |
202 | 1 | case TY_CLHeader: |
203 | 1 | case TY_PP_ObjCHeader: |
204 | 1 | case TY_ObjCHeader: |
205 | 1 | case TY_PP_CXXHeader: |
206 | 1 | case TY_CXXHeader: |
207 | 1 | case TY_PP_ObjCXXHeader: |
208 | 1 | case TY_ObjCXXHeader: |
209 | 1 | case TY_CXXModule: |
210 | 1 | case TY_PP_CXXModule: |
211 | 1 | return true; |
212 | 2 | } |
213 | 2 | } |
214 | | |
215 | 239k | bool types::isObjC(ID Id) { |
216 | 239k | switch (Id) { |
217 | 223k | default: |
218 | 223k | return false; |
219 | | |
220 | 8.83k | case TY_ObjC: 8.81k case TY_PP_ObjC: 8.83k case TY_PP_ObjC_Alias: |
221 | 16.1k | case TY_ObjCXX: 16.1k case TY_PP_ObjCXX: |
222 | 16.2k | case TY_ObjCHeader: case TY_PP_ObjCHeader: |
223 | 16.2k | case TY_ObjCXXHeader: 16.2k case TY_PP_ObjCXXHeader: 16.2k case TY_PP_ObjCXX_Alias: |
224 | 16.2k | return true; |
225 | 239k | } |
226 | 239k | } |
227 | | |
228 | 95.5k | bool types::isOpenCL(ID Id) { return Id == TY_CL || Id == TY_CLCXX94.8k ; } |
229 | | |
230 | 356k | bool types::isCXX(ID Id) { |
231 | 356k | switch (Id) { |
232 | 128k | default: |
233 | 128k | return false; |
234 | | |
235 | 209k | case TY_CXX: 209k case TY_PP_CXX: |
236 | 221k | case TY_ObjCXX: 221k case TY_PP_ObjCXX: 221k case TY_PP_ObjCXX_Alias: |
237 | 221k | case TY_CXXHeader: case TY_PP_CXXHeader: |
238 | 221k | case TY_CXXSHeader: |
239 | 221k | case TY_CXXUHeader: |
240 | 221k | case TY_CXXHUHeader: |
241 | 221k | case TY_PP_CXXHeaderUnit: |
242 | 221k | case TY_ObjCXXHeader: case TY_PP_ObjCXXHeader: |
243 | 221k | case TY_CXXModule: case TY_PP_CXXModule: |
244 | 222k | case TY_CUDA: 222k case TY_PP_CUDA: 222k case TY_CUDA_DEVICE: |
245 | 224k | case TY_HIP: |
246 | 225k | case TY_PP_HIP: |
247 | 228k | case TY_HIP_DEVICE: |
248 | 228k | return true; |
249 | 356k | } |
250 | 356k | } |
251 | | |
252 | 62.3k | bool types::isLLVMIR(ID Id) { |
253 | 62.3k | switch (Id) { |
254 | 61.0k | default: |
255 | 61.0k | return false; |
256 | | |
257 | 726 | case TY_LLVM_IR: |
258 | 970 | case TY_LLVM_BC: |
259 | 1.01k | case TY_LTO_IR: |
260 | 1.25k | case TY_LTO_BC: |
261 | 1.25k | return true; |
262 | 62.3k | } |
263 | 62.3k | } |
264 | | |
265 | 56.5k | bool types::isCuda(ID Id) { |
266 | 56.5k | switch (Id) { |
267 | 56.4k | default: |
268 | 56.4k | return false; |
269 | | |
270 | 97 | case TY_CUDA: |
271 | 98 | case TY_PP_CUDA: |
272 | 98 | case TY_CUDA_DEVICE: |
273 | 98 | return true; |
274 | 56.5k | } |
275 | 56.5k | } |
276 | | |
277 | 56.5k | bool types::isHIP(ID Id) { |
278 | 56.5k | switch (Id) { |
279 | 56.1k | default: |
280 | 56.1k | return false; |
281 | | |
282 | 367 | case TY_HIP: |
283 | 371 | case TY_PP_HIP: |
284 | 371 | case TY_HIP_DEVICE: |
285 | 371 | return true; |
286 | 56.5k | } |
287 | 56.5k | } |
288 | | |
289 | 47.7k | bool types::isHLSL(ID Id) { return Id == TY_HLSL; } |
290 | | |
291 | 27.0k | bool types::isSrcFile(ID Id) { |
292 | 27.0k | return Id != TY_Object && getPreprocessedType(Id) != TY_INVALID26.9k ; |
293 | 27.0k | } |
294 | | |
295 | 66.7k | types::ID types::lookupTypeForExtension(llvm::StringRef Ext) { |
296 | 66.7k | return llvm::StringSwitch<types::ID>(Ext) |
297 | 66.7k | .Case("c", TY_C) |
298 | 66.7k | .Case("C", TY_CXX) |
299 | 66.7k | .Case("F", TY_Fortran) |
300 | 66.7k | .Case("f", TY_PP_Fortran) |
301 | 66.7k | .Case("h", TY_CHeader) |
302 | 66.7k | .Case("H", TY_CXXHeader) |
303 | 66.7k | .Case("i", TY_PP_C) |
304 | 66.7k | .Case("m", TY_ObjC) |
305 | 66.7k | .Case("M", TY_ObjCXX) |
306 | 66.7k | .Case("o", TY_Object) |
307 | 66.7k | .Case("S", TY_Asm) |
308 | 66.7k | .Case("s", TY_PP_Asm) |
309 | 66.7k | .Case("bc", TY_LLVM_BC) |
310 | 66.7k | .Case("cc", TY_CXX) |
311 | 66.7k | .Case("CC", TY_CXX) |
312 | 66.7k | .Case("cl", TY_CL) |
313 | 66.7k | .Case("clcpp", TY_CLCXX) |
314 | 66.7k | .Case("cp", TY_CXX) |
315 | 66.7k | .Case("cu", TY_CUDA) |
316 | 66.7k | .Case("hh", TY_CXXHeader) |
317 | 66.7k | .Case("ii", TY_PP_CXX) |
318 | 66.7k | .Case("ll", TY_LLVM_IR) |
319 | 66.7k | .Case("mi", TY_PP_ObjC) |
320 | 66.7k | .Case("mm", TY_ObjCXX) |
321 | 66.7k | .Case("rs", TY_RenderScript) |
322 | 66.7k | .Case("adb", TY_Ada) |
323 | 66.7k | .Case("ads", TY_Ada) |
324 | 66.7k | .Case("asm", TY_PP_Asm) |
325 | 66.7k | .Case("ast", TY_AST) |
326 | 66.7k | .Case("ccm", TY_CXXModule) |
327 | 66.7k | .Case("cpp", TY_CXX) |
328 | 66.7k | .Case("CPP", TY_CXX) |
329 | 66.7k | .Case("c++", TY_CXX) |
330 | 66.7k | .Case("C++", TY_CXX) |
331 | 66.7k | .Case("cui", TY_PP_CUDA) |
332 | 66.7k | .Case("cxx", TY_CXX) |
333 | 66.7k | .Case("CXX", TY_CXX) |
334 | 66.7k | .Case("F03", TY_Fortran) |
335 | 66.7k | .Case("f03", TY_PP_Fortran) |
336 | 66.7k | .Case("F08", TY_Fortran) |
337 | 66.7k | .Case("f08", TY_PP_Fortran) |
338 | 66.7k | .Case("F90", TY_Fortran) |
339 | 66.7k | .Case("f90", TY_PP_Fortran) |
340 | 66.7k | .Case("F95", TY_Fortran) |
341 | 66.7k | .Case("f95", TY_PP_Fortran) |
342 | 66.7k | .Case("for", TY_PP_Fortran) |
343 | 66.7k | .Case("FOR", TY_PP_Fortran) |
344 | 66.7k | .Case("fpp", TY_Fortran) |
345 | 66.7k | .Case("FPP", TY_Fortran) |
346 | 66.7k | .Case("gch", TY_PCH) |
347 | 66.7k | .Case("hip", TY_HIP) |
348 | 66.7k | .Case("hipi", TY_PP_HIP) |
349 | 66.7k | .Case("hpp", TY_CXXHeader) |
350 | 66.7k | .Case("hxx", TY_CXXHeader) |
351 | 66.7k | .Case("iim", TY_PP_CXXModule) |
352 | 66.7k | .Case("iih", TY_PP_CXXHeaderUnit) |
353 | 66.7k | .Case("lib", TY_Object) |
354 | 66.7k | .Case("mii", TY_PP_ObjCXX) |
355 | 66.7k | .Case("obj", TY_Object) |
356 | 66.7k | .Case("ifs", TY_IFS) |
357 | 66.7k | .Case("pch", TY_PCH) |
358 | 66.7k | .Case("pcm", TY_ModuleFile) |
359 | 66.7k | .Case("c++m", TY_CXXModule) |
360 | 66.7k | .Case("cppm", TY_CXXModule) |
361 | 66.7k | .Case("cxxm", TY_CXXModule) |
362 | 66.7k | .Case("hlsl", TY_HLSL) |
363 | 66.7k | .Default(TY_INVALID); |
364 | 66.7k | } |
365 | | |
366 | 5.41k | types::ID types::lookupTypeForTypeSpecifier(const char *Name) { |
367 | 42.8k | for (unsigned i=0; i<numTypes; ++i37.4k ) { |
368 | 42.8k | types::ID Id = (types::ID) (i + 1); |
369 | 42.8k | if (canTypeBeUserSpecified(Id) && |
370 | 42.8k | strcmp(Name, getInfo(Id).Name) == 038.2k ) |
371 | 5.41k | return Id; |
372 | 42.8k | } |
373 | | // Accept "cu" as an alias for "cuda" for NVCC compatibility |
374 | 0 | if (strcmp(Name, "cu") == 0) { |
375 | 0 | return types::TY_CUDA; |
376 | 0 | } |
377 | 0 | return TY_INVALID; |
378 | 0 | } |
379 | | |
380 | | llvm::SmallVector<phases::ID, phases::MaxNumberOfPhases> |
381 | 169k | types::getCompilationPhases(ID Id, phases::ID LastPhase) { |
382 | 169k | llvm::SmallVector<phases::ID, phases::MaxNumberOfPhases> P; |
383 | 169k | const auto &Info = getInfo(Id); |
384 | 1.18M | for (int I = 0; I <= LastPhase; ++I1.01M ) |
385 | 1.01M | if (Info.Phases.contains(static_cast<phases::ID>(I))) |
386 | 622k | P.push_back(static_cast<phases::ID>(I)); |
387 | 169k | assert(P.size() <= phases::MaxNumberOfPhases && "Too many phases in list"); |
388 | 169k | return P; |
389 | 169k | } |
390 | | |
391 | | llvm::SmallVector<phases::ID, phases::MaxNumberOfPhases> |
392 | | types::getCompilationPhases(const clang::driver::Driver &Driver, |
393 | 56.6k | llvm::opt::DerivedArgList &DAL, ID Id) { |
394 | 56.6k | return types::getCompilationPhases(Id, Driver.getFinalPhase(DAL)); |
395 | 56.6k | } |
396 | | |
397 | 4.74k | ID types::lookupCXXTypeForCType(ID Id) { |
398 | 4.74k | switch (Id) { |
399 | 4.66k | default: |
400 | 4.66k | return Id; |
401 | | |
402 | 71 | case types::TY_C: |
403 | 71 | return types::TY_CXX; |
404 | 0 | case types::TY_PP_C: |
405 | 0 | return types::TY_PP_CXX; |
406 | 0 | case types::TY_CHeader: |
407 | 0 | return types::TY_CXXHeader; |
408 | 0 | case types::TY_PP_CHeader: |
409 | 0 | return types::TY_PP_CXXHeader; |
410 | 4.74k | } |
411 | 4.74k | } |
412 | | |
413 | 30 | ID types::lookupHeaderTypeForSourceType(ID Id) { |
414 | 30 | switch (Id) { |
415 | 0 | default: |
416 | 0 | return Id; |
417 | | |
418 | | // FIXME: Handle preprocessed input types. |
419 | 5 | case types::TY_C: |
420 | 5 | return types::TY_CHeader; |
421 | 24 | case types::TY_CXX: |
422 | 24 | case types::TY_CXXModule: |
423 | 24 | return types::TY_CXXHeader; |
424 | 0 | case types::TY_ObjC: |
425 | 0 | return types::TY_ObjCHeader; |
426 | 1 | case types::TY_ObjCXX: |
427 | 1 | return types::TY_ObjCXXHeader; |
428 | 0 | case types::TY_CL: |
429 | 0 | case types::TY_CLCXX: |
430 | 0 | return types::TY_CLHeader; |
431 | 30 | } |
432 | 30 | } |