1 //===--- Targets.cpp - Implement target feature support -------------------===//
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 // This file implements construction of a TargetInfo object from a
10 // target triple.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #include "Targets.h"
15 
16 #include "Targets/AArch64.h"
17 #include "Targets/AMDGPU.h"
18 #include "Targets/ARC.h"
19 #include "Targets/ARM.h"
20 #include "Targets/AVR.h"
21 #include "Targets/BPF.h"
22 #include "Targets/Hexagon.h"
23 #include "Targets/Lanai.h"
24 #include "Targets/Le64.h"
25 #include "Targets/M68k.h"
26 #include "Targets/MSP430.h"
27 #include "Targets/Mips.h"
28 #include "Targets/NVPTX.h"
29 #include "Targets/OSTargets.h"
30 #include "Targets/PNaCl.h"
31 #include "Targets/PPC.h"
32 #include "Targets/RISCV.h"
33 #include "Targets/SPIR.h"
34 #include "Targets/Sparc.h"
35 #include "Targets/SystemZ.h"
36 #include "Targets/TCE.h"
37 #include "Targets/VE.h"
38 #include "Targets/WebAssembly.h"
39 #include "Targets/X86.h"
40 #include "Targets/XCore.h"
41 #include "clang/Basic/Diagnostic.h"
42 #include "llvm/ADT/StringExtras.h"
43 #include "llvm/ADT/Triple.h"
44 
45 using namespace clang;
46 
47 namespace clang {
48 namespace targets {
49 //===----------------------------------------------------------------------===//
50 //  Common code shared among targets.
51 //===----------------------------------------------------------------------===//
52 
53 /// DefineStd - Define a macro name and standard variants.  For example if
54 /// MacroName is "unix", then this will define "__unix", "__unix__", and "unix"
55 /// when in GNU mode.
DefineStd(MacroBuilder & Builder,StringRef MacroName,const LangOptions & Opts)56 void DefineStd(MacroBuilder &Builder, StringRef MacroName,
57                const LangOptions &Opts) {
58   assert(MacroName[0] != '_' && "Identifier should be in the user's namespace");
59 
60   // If in GNU mode (e.g. -std=gnu99 but not -std=c99) define the raw identifier
61   // in the user's namespace.
62   if (Opts.GNUMode)
63     Builder.defineMacro(MacroName);
64 
65   // Define __unix.
66   Builder.defineMacro("__" + MacroName);
67 
68   // Define __unix__.
69   Builder.defineMacro("__" + MacroName + "__");
70 }
71 
defineCPUMacros(MacroBuilder & Builder,StringRef CPUName,bool Tuning)72 void defineCPUMacros(MacroBuilder &Builder, StringRef CPUName, bool Tuning) {
73   Builder.defineMacro("__" + CPUName);
74   Builder.defineMacro("__" + CPUName + "__");
75   if (Tuning)
76     Builder.defineMacro("__tune_" + CPUName + "__");
77 }
78 
addCygMingDefines(const LangOptions & Opts,MacroBuilder & Builder)79 void addCygMingDefines(const LangOptions &Opts, MacroBuilder &Builder) {
80   // Mingw and cygwin define __declspec(a) to __attribute__((a)).  Clang
81   // supports __declspec natively under -fms-extensions, but we define a no-op
82   // __declspec macro anyway for pre-processor compatibility.
83   if (Opts.MicrosoftExt)
84     Builder.defineMacro("__declspec", "__declspec");
85   else
86     Builder.defineMacro("__declspec(a)", "__attribute__((a))");
87 
88   if (!Opts.MicrosoftExt) {
89     // Provide macros for all the calling convention keywords.  Provide both
90     // single and double underscore prefixed variants.  These are available on
91     // x64 as well as x86, even though they have no effect.
92     const char *CCs[] = {"cdecl", "stdcall", "fastcall", "thiscall", "pascal"};
93     for (const char *CC : CCs) {
94       std::string GCCSpelling = "__attribute__((__";
95       GCCSpelling += CC;
96       GCCSpelling += "__))";
97       Builder.defineMacro(Twine("_") + CC, GCCSpelling);
98       Builder.defineMacro(Twine("__") + CC, GCCSpelling);
99     }
100   }
101 }
102 
103 //===----------------------------------------------------------------------===//
104 // Driver code
105 //===----------------------------------------------------------------------===//
106 
AllocateTarget(const llvm::Triple & Triple,const TargetOptions & Opts)107 TargetInfo *AllocateTarget(const llvm::Triple &Triple,
108                            const TargetOptions &Opts) {
109   llvm::Triple::OSType os = Triple.getOS();
110 
111   switch (Triple.getArch()) {
112   default:
113     return nullptr;
114 
115   case llvm::Triple::arc:
116     return new ARCTargetInfo(Triple, Opts);
117 
118   case llvm::Triple::xcore:
119     return new XCoreTargetInfo(Triple, Opts);
120 
121   case llvm::Triple::hexagon:
122     if (os == llvm::Triple::Linux &&
123         Triple.getEnvironment() == llvm::Triple::Musl)
124       return new LinuxTargetInfo<HexagonTargetInfo>(Triple, Opts);
125     return new HexagonTargetInfo(Triple, Opts);
126 
127   case llvm::Triple::lanai:
128     return new LanaiTargetInfo(Triple, Opts);
129 
130   case llvm::Triple::aarch64_32:
131     if (Triple.isOSDarwin())
132       return new DarwinAArch64TargetInfo(Triple, Opts);
133 
134     return nullptr;
135   case llvm::Triple::aarch64:
136     if (Triple.isOSDarwin())
137       return new DarwinAArch64TargetInfo(Triple, Opts);
138 
139     switch (os) {
140     case llvm::Triple::CloudABI:
141       return new CloudABITargetInfo<AArch64leTargetInfo>(Triple, Opts);
142     case llvm::Triple::FreeBSD:
143       return new FreeBSDTargetInfo<AArch64leTargetInfo>(Triple, Opts);
144     case llvm::Triple::Fuchsia:
145       return new FuchsiaTargetInfo<AArch64leTargetInfo>(Triple, Opts);
146     case llvm::Triple::Linux:
147       return new LinuxTargetInfo<AArch64leTargetInfo>(Triple, Opts);
148     case llvm::Triple::NetBSD:
149       return new NetBSDTargetInfo<AArch64leTargetInfo>(Triple, Opts);
150     case llvm::Triple::OpenBSD:
151       return new OpenBSDTargetInfo<AArch64leTargetInfo>(Triple, Opts);
152     case llvm::Triple::Win32:
153       switch (Triple.getEnvironment()) {
154       case llvm::Triple::GNU:
155         return new MinGWARM64TargetInfo(Triple, Opts);
156       case llvm::Triple::MSVC:
157       default: // Assume MSVC for unknown environments
158         return new MicrosoftARM64TargetInfo(Triple, Opts);
159       }
160     default:
161       return new AArch64leTargetInfo(Triple, Opts);
162     }
163 
164   case llvm::Triple::aarch64_be:
165     switch (os) {
166     case llvm::Triple::FreeBSD:
167       return new FreeBSDTargetInfo<AArch64beTargetInfo>(Triple, Opts);
168     case llvm::Triple::Fuchsia:
169       return new FuchsiaTargetInfo<AArch64beTargetInfo>(Triple, Opts);
170     case llvm::Triple::Linux:
171       return new LinuxTargetInfo<AArch64beTargetInfo>(Triple, Opts);
172     case llvm::Triple::NetBSD:
173       return new NetBSDTargetInfo<AArch64beTargetInfo>(Triple, Opts);
174     default:
175       return new AArch64beTargetInfo(Triple, Opts);
176     }
177 
178   case llvm::Triple::arm:
179   case llvm::Triple::thumb:
180     if (Triple.isOSBinFormatMachO())
181       return new DarwinARMTargetInfo(Triple, Opts);
182 
183     switch (os) {
184     case llvm::Triple::CloudABI:
185       return new CloudABITargetInfo<ARMleTargetInfo>(Triple, Opts);
186     case llvm::Triple::Linux:
187       return new LinuxTargetInfo<ARMleTargetInfo>(Triple, Opts);
188     case llvm::Triple::FreeBSD:
189       return new FreeBSDTargetInfo<ARMleTargetInfo>(Triple, Opts);
190     case llvm::Triple::NetBSD:
191       return new NetBSDTargetInfo<ARMleTargetInfo>(Triple, Opts);
192     case llvm::Triple::OpenBSD:
193       return new OpenBSDTargetInfo<ARMleTargetInfo>(Triple, Opts);
194     case llvm::Triple::RTEMS:
195       return new RTEMSTargetInfo<ARMleTargetInfo>(Triple, Opts);
196     case llvm::Triple::NaCl:
197       return new NaClTargetInfo<ARMleTargetInfo>(Triple, Opts);
198     case llvm::Triple::Win32:
199       switch (Triple.getEnvironment()) {
200       case llvm::Triple::Cygnus:
201         return new CygwinARMTargetInfo(Triple, Opts);
202       case llvm::Triple::GNU:
203         return new MinGWARMTargetInfo(Triple, Opts);
204       case llvm::Triple::Itanium:
205         return new ItaniumWindowsARMleTargetInfo(Triple, Opts);
206       case llvm::Triple::MSVC:
207       default: // Assume MSVC for unknown environments
208         return new MicrosoftARMleTargetInfo(Triple, Opts);
209       }
210     default:
211       return new ARMleTargetInfo(Triple, Opts);
212     }
213 
214   case llvm::Triple::armeb:
215   case llvm::Triple::thumbeb:
216     if (Triple.isOSDarwin())
217       return new DarwinARMTargetInfo(Triple, Opts);
218 
219     switch (os) {
220     case llvm::Triple::Linux:
221       return new LinuxTargetInfo<ARMbeTargetInfo>(Triple, Opts);
222     case llvm::Triple::FreeBSD:
223       return new FreeBSDTargetInfo<ARMbeTargetInfo>(Triple, Opts);
224     case llvm::Triple::NetBSD:
225       return new NetBSDTargetInfo<ARMbeTargetInfo>(Triple, Opts);
226     case llvm::Triple::OpenBSD:
227       return new OpenBSDTargetInfo<ARMbeTargetInfo>(Triple, Opts);
228     case llvm::Triple::RTEMS:
229       return new RTEMSTargetInfo<ARMbeTargetInfo>(Triple, Opts);
230     case llvm::Triple::NaCl:
231       return new NaClTargetInfo<ARMbeTargetInfo>(Triple, Opts);
232     default:
233       return new ARMbeTargetInfo(Triple, Opts);
234     }
235 
236   case llvm::Triple::avr:
237     return new AVRTargetInfo(Triple, Opts);
238   case llvm::Triple::bpfeb:
239   case llvm::Triple::bpfel:
240     return new BPFTargetInfo(Triple, Opts);
241 
242   case llvm::Triple::msp430:
243     return new MSP430TargetInfo(Triple, Opts);
244 
245   case llvm::Triple::mips:
246     switch (os) {
247     case llvm::Triple::Linux:
248       return new LinuxTargetInfo<MipsTargetInfo>(Triple, Opts);
249     case llvm::Triple::RTEMS:
250       return new RTEMSTargetInfo<MipsTargetInfo>(Triple, Opts);
251     case llvm::Triple::FreeBSD:
252       return new FreeBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
253     case llvm::Triple::NetBSD:
254       return new NetBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
255     default:
256       return new MipsTargetInfo(Triple, Opts);
257     }
258 
259   case llvm::Triple::mipsel:
260     switch (os) {
261     case llvm::Triple::Linux:
262       return new LinuxTargetInfo<MipsTargetInfo>(Triple, Opts);
263     case llvm::Triple::RTEMS:
264       return new RTEMSTargetInfo<MipsTargetInfo>(Triple, Opts);
265     case llvm::Triple::FreeBSD:
266       return new FreeBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
267     case llvm::Triple::NetBSD:
268       return new NetBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
269     case llvm::Triple::NaCl:
270       return new NaClTargetInfo<NaClMips32TargetInfo>(Triple, Opts);
271     default:
272       return new MipsTargetInfo(Triple, Opts);
273     }
274 
275   case llvm::Triple::mips64:
276     switch (os) {
277     case llvm::Triple::Linux:
278       return new LinuxTargetInfo<MipsTargetInfo>(Triple, Opts);
279     case llvm::Triple::RTEMS:
280       return new RTEMSTargetInfo<MipsTargetInfo>(Triple, Opts);
281     case llvm::Triple::FreeBSD:
282       return new FreeBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
283     case llvm::Triple::NetBSD:
284       return new NetBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
285     case llvm::Triple::OpenBSD:
286       return new OpenBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
287     default:
288       return new MipsTargetInfo(Triple, Opts);
289     }
290 
291   case llvm::Triple::mips64el:
292     switch (os) {
293     case llvm::Triple::Linux:
294       return new LinuxTargetInfo<MipsTargetInfo>(Triple, Opts);
295     case llvm::Triple::RTEMS:
296       return new RTEMSTargetInfo<MipsTargetInfo>(Triple, Opts);
297     case llvm::Triple::FreeBSD:
298       return new FreeBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
299     case llvm::Triple::NetBSD:
300       return new NetBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
301     case llvm::Triple::OpenBSD:
302       return new OpenBSDTargetInfo<MipsTargetInfo>(Triple, Opts);
303     default:
304       return new MipsTargetInfo(Triple, Opts);
305     }
306 
307   case llvm::Triple::m68k:
308     switch (os) {
309     case llvm::Triple::Linux:
310       return new LinuxTargetInfo<M68kTargetInfo>(Triple, Opts);
311     case llvm::Triple::NetBSD:
312       return new NetBSDTargetInfo<M68kTargetInfo>(Triple, Opts);
313     default:
314       return new M68kTargetInfo(Triple, Opts);
315     }
316 
317   case llvm::Triple::le32:
318     switch (os) {
319     case llvm::Triple::NaCl:
320       return new NaClTargetInfo<PNaClTargetInfo>(Triple, Opts);
321     default:
322       return nullptr;
323     }
324 
325   case llvm::Triple::le64:
326     return new Le64TargetInfo(Triple, Opts);
327 
328   case llvm::Triple::ppc:
329     if (Triple.isOSDarwin())
330       return new DarwinPPC32TargetInfo(Triple, Opts);
331     switch (os) {
332     case llvm::Triple::Linux:
333       return new LinuxTargetInfo<PPC32TargetInfo>(Triple, Opts);
334     case llvm::Triple::FreeBSD:
335       return new FreeBSDTargetInfo<PPC32TargetInfo>(Triple, Opts);
336     case llvm::Triple::NetBSD:
337       return new NetBSDTargetInfo<PPC32TargetInfo>(Triple, Opts);
338     case llvm::Triple::OpenBSD:
339       return new OpenBSDTargetInfo<PPC32TargetInfo>(Triple, Opts);
340     case llvm::Triple::RTEMS:
341       return new RTEMSTargetInfo<PPC32TargetInfo>(Triple, Opts);
342     case llvm::Triple::AIX:
343       return new AIXPPC32TargetInfo(Triple, Opts);
344     default:
345       return new PPC32TargetInfo(Triple, Opts);
346     }
347 
348   case llvm::Triple::ppcle:
349     switch (os) {
350     case llvm::Triple::Linux:
351       return new LinuxTargetInfo<PPC32TargetInfo>(Triple, Opts);
352     case llvm::Triple::FreeBSD:
353       return new FreeBSDTargetInfo<PPC32TargetInfo>(Triple, Opts);
354     default:
355       return new PPC32TargetInfo(Triple, Opts);
356     }
357 
358   case llvm::Triple::ppc64:
359     if (Triple.isOSDarwin())
360       return new DarwinPPC64TargetInfo(Triple, Opts);
361     switch (os) {
362     case llvm::Triple::Linux:
363       return new LinuxTargetInfo<PPC64TargetInfo>(Triple, Opts);
364     case llvm::Triple::Lv2:
365       return new PS3PPUTargetInfo<PPC64TargetInfo>(Triple, Opts);
366     case llvm::Triple::FreeBSD:
367       return new FreeBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
368     case llvm::Triple::NetBSD:
369       return new NetBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
370     case llvm::Triple::OpenBSD:
371       return new OpenBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
372     case llvm::Triple::AIX:
373       return new AIXPPC64TargetInfo(Triple, Opts);
374     default:
375       return new PPC64TargetInfo(Triple, Opts);
376     }
377 
378   case llvm::Triple::ppc64le:
379     switch (os) {
380     case llvm::Triple::Linux:
381       return new LinuxTargetInfo<PPC64TargetInfo>(Triple, Opts);
382     case llvm::Triple::FreeBSD:
383       return new FreeBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
384     case llvm::Triple::NetBSD:
385       return new NetBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
386     case llvm::Triple::OpenBSD:
387       return new OpenBSDTargetInfo<PPC64TargetInfo>(Triple, Opts);
388     default:
389       return new PPC64TargetInfo(Triple, Opts);
390     }
391 
392   case llvm::Triple::nvptx:
393     return new NVPTXTargetInfo(Triple, Opts, /*TargetPointerWidth=*/32);
394   case llvm::Triple::nvptx64:
395     return new NVPTXTargetInfo(Triple, Opts, /*TargetPointerWidth=*/64);
396 
397   case llvm::Triple::amdgcn:
398   case llvm::Triple::r600:
399     return new AMDGPUTargetInfo(Triple, Opts);
400 
401   case llvm::Triple::riscv32:
402     // TODO: add cases for NetBSD, RTEMS once tested.
403     switch (os) {
404     case llvm::Triple::FreeBSD:
405       return new FreeBSDTargetInfo<RISCV32TargetInfo>(Triple, Opts);
406     case llvm::Triple::Linux:
407       return new LinuxTargetInfo<RISCV32TargetInfo>(Triple, Opts);
408     default:
409       return new RISCV32TargetInfo(Triple, Opts);
410     }
411 
412   case llvm::Triple::riscv64:
413     // TODO: add cases for NetBSD, RTEMS once tested.
414     switch (os) {
415     case llvm::Triple::FreeBSD:
416       return new FreeBSDTargetInfo<RISCV64TargetInfo>(Triple, Opts);
417     case llvm::Triple::OpenBSD:
418       return new OpenBSDTargetInfo<RISCV64TargetInfo>(Triple, Opts);
419     case llvm::Triple::Fuchsia:
420       return new FuchsiaTargetInfo<RISCV64TargetInfo>(Triple, Opts);
421     case llvm::Triple::Linux:
422       return new LinuxTargetInfo<RISCV64TargetInfo>(Triple, Opts);
423     default:
424       return new RISCV64TargetInfo(Triple, Opts);
425     }
426 
427   case llvm::Triple::sparc:
428     switch (os) {
429     case llvm::Triple::Linux:
430       return new LinuxTargetInfo<SparcV8TargetInfo>(Triple, Opts);
431     case llvm::Triple::Solaris:
432       return new SolarisTargetInfo<SparcV8TargetInfo>(Triple, Opts);
433     case llvm::Triple::NetBSD:
434       return new NetBSDTargetInfo<SparcV8TargetInfo>(Triple, Opts);
435     case llvm::Triple::RTEMS:
436       return new RTEMSTargetInfo<SparcV8TargetInfo>(Triple, Opts);
437     default:
438       return new SparcV8TargetInfo(Triple, Opts);
439     }
440 
441   // The 'sparcel' architecture copies all the above cases except for Solaris.
442   case llvm::Triple::sparcel:
443     switch (os) {
444     case llvm::Triple::Linux:
445       return new LinuxTargetInfo<SparcV8elTargetInfo>(Triple, Opts);
446     case llvm::Triple::NetBSD:
447       return new NetBSDTargetInfo<SparcV8elTargetInfo>(Triple, Opts);
448     case llvm::Triple::RTEMS:
449       return new RTEMSTargetInfo<SparcV8elTargetInfo>(Triple, Opts);
450     default:
451       return new SparcV8elTargetInfo(Triple, Opts);
452     }
453 
454   case llvm::Triple::sparcv9:
455     switch (os) {
456     case llvm::Triple::Linux:
457       return new LinuxTargetInfo<SparcV9TargetInfo>(Triple, Opts);
458     case llvm::Triple::Solaris:
459       return new SolarisTargetInfo<SparcV9TargetInfo>(Triple, Opts);
460     case llvm::Triple::NetBSD:
461       return new NetBSDTargetInfo<SparcV9TargetInfo>(Triple, Opts);
462     case llvm::Triple::OpenBSD:
463       return new OpenBSDTargetInfo<SparcV9TargetInfo>(Triple, Opts);
464     case llvm::Triple::FreeBSD:
465       return new FreeBSDTargetInfo<SparcV9TargetInfo>(Triple, Opts);
466     default:
467       return new SparcV9TargetInfo(Triple, Opts);
468     }
469 
470   case llvm::Triple::systemz:
471     switch (os) {
472     case llvm::Triple::Linux:
473       return new LinuxTargetInfo<SystemZTargetInfo>(Triple, Opts);
474     case llvm::Triple::ZOS:
475       return new ZOSTargetInfo<SystemZTargetInfo>(Triple, Opts);
476     default:
477       return new SystemZTargetInfo(Triple, Opts);
478     }
479 
480   case llvm::Triple::tce:
481     return new TCETargetInfo(Triple, Opts);
482 
483   case llvm::Triple::tcele:
484     return new TCELETargetInfo(Triple, Opts);
485 
486   case llvm::Triple::x86:
487     if (Triple.isOSDarwin())
488       return new DarwinI386TargetInfo(Triple, Opts);
489 
490     switch (os) {
491     case llvm::Triple::Ananas:
492       return new AnanasTargetInfo<X86_32TargetInfo>(Triple, Opts);
493     case llvm::Triple::CloudABI:
494       return new CloudABITargetInfo<X86_32TargetInfo>(Triple, Opts);
495     case llvm::Triple::Linux: {
496       switch (Triple.getEnvironment()) {
497       default:
498         return new LinuxTargetInfo<X86_32TargetInfo>(Triple, Opts);
499       case llvm::Triple::Android:
500         return new AndroidX86_32TargetInfo(Triple, Opts);
501       }
502     }
503     case llvm::Triple::DragonFly:
504       return new DragonFlyBSDTargetInfo<X86_32TargetInfo>(Triple, Opts);
505     case llvm::Triple::NetBSD:
506       return new NetBSDI386TargetInfo(Triple, Opts);
507     case llvm::Triple::OpenBSD:
508       return new OpenBSDI386TargetInfo(Triple, Opts);
509     case llvm::Triple::FreeBSD:
510       return new FreeBSDTargetInfo<X86_32TargetInfo>(Triple, Opts);
511     case llvm::Triple::Fuchsia:
512       return new FuchsiaTargetInfo<X86_32TargetInfo>(Triple, Opts);
513     case llvm::Triple::KFreeBSD:
514       return new KFreeBSDTargetInfo<X86_32TargetInfo>(Triple, Opts);
515     case llvm::Triple::Minix:
516       return new MinixTargetInfo<X86_32TargetInfo>(Triple, Opts);
517     case llvm::Triple::Solaris:
518       return new SolarisTargetInfo<X86_32TargetInfo>(Triple, Opts);
519     case llvm::Triple::Win32: {
520       switch (Triple.getEnvironment()) {
521       case llvm::Triple::Cygnus:
522         return new CygwinX86_32TargetInfo(Triple, Opts);
523       case llvm::Triple::GNU:
524         return new MinGWX86_32TargetInfo(Triple, Opts);
525       case llvm::Triple::Itanium:
526       case llvm::Triple::MSVC:
527       default: // Assume MSVC for unknown environments
528         return new MicrosoftX86_32TargetInfo(Triple, Opts);
529       }
530     }
531     case llvm::Triple::Haiku:
532       return new HaikuX86_32TargetInfo(Triple, Opts);
533     case llvm::Triple::RTEMS:
534       return new RTEMSX86_32TargetInfo(Triple, Opts);
535     case llvm::Triple::NaCl:
536       return new NaClTargetInfo<X86_32TargetInfo>(Triple, Opts);
537     case llvm::Triple::ELFIAMCU:
538       return new MCUX86_32TargetInfo(Triple, Opts);
539     case llvm::Triple::Hurd:
540       return new HurdTargetInfo<X86_32TargetInfo>(Triple, Opts);
541     default:
542       return new X86_32TargetInfo(Triple, Opts);
543     }
544 
545   case llvm::Triple::x86_64:
546     if (Triple.isOSDarwin() || Triple.isOSBinFormatMachO())
547       return new DarwinX86_64TargetInfo(Triple, Opts);
548 
549     switch (os) {
550     case llvm::Triple::Ananas:
551       return new AnanasTargetInfo<X86_64TargetInfo>(Triple, Opts);
552     case llvm::Triple::CloudABI:
553       return new CloudABITargetInfo<X86_64TargetInfo>(Triple, Opts);
554     case llvm::Triple::Linux: {
555       switch (Triple.getEnvironment()) {
556       default:
557         return new LinuxTargetInfo<X86_64TargetInfo>(Triple, Opts);
558       case llvm::Triple::Android:
559         return new AndroidX86_64TargetInfo(Triple, Opts);
560       }
561     }
562     case llvm::Triple::DragonFly:
563       return new DragonFlyBSDTargetInfo<X86_64TargetInfo>(Triple, Opts);
564     case llvm::Triple::NetBSD:
565       return new NetBSDTargetInfo<X86_64TargetInfo>(Triple, Opts);
566     case llvm::Triple::OpenBSD:
567       return new OpenBSDX86_64TargetInfo(Triple, Opts);
568     case llvm::Triple::FreeBSD:
569       return new FreeBSDTargetInfo<X86_64TargetInfo>(Triple, Opts);
570     case llvm::Triple::Fuchsia:
571       return new FuchsiaTargetInfo<X86_64TargetInfo>(Triple, Opts);
572     case llvm::Triple::KFreeBSD:
573       return new KFreeBSDTargetInfo<X86_64TargetInfo>(Triple, Opts);
574     case llvm::Triple::Solaris:
575       return new SolarisTargetInfo<X86_64TargetInfo>(Triple, Opts);
576     case llvm::Triple::Win32: {
577       switch (Triple.getEnvironment()) {
578       case llvm::Triple::Cygnus:
579         return new CygwinX86_64TargetInfo(Triple, Opts);
580       case llvm::Triple::GNU:
581         return new MinGWX86_64TargetInfo(Triple, Opts);
582       case llvm::Triple::MSVC:
583       default: // Assume MSVC for unknown environments
584         return new MicrosoftX86_64TargetInfo(Triple, Opts);
585       }
586     }
587     case llvm::Triple::Haiku:
588       return new HaikuTargetInfo<X86_64TargetInfo>(Triple, Opts);
589     case llvm::Triple::NaCl:
590       return new NaClTargetInfo<X86_64TargetInfo>(Triple, Opts);
591     case llvm::Triple::PS4:
592       return new PS4OSTargetInfo<X86_64TargetInfo>(Triple, Opts);
593     default:
594       return new X86_64TargetInfo(Triple, Opts);
595     }
596 
597   case llvm::Triple::spir: {
598     if (os != llvm::Triple::UnknownOS ||
599         Triple.getEnvironment() != llvm::Triple::UnknownEnvironment)
600       return nullptr;
601     return new SPIR32TargetInfo(Triple, Opts);
602   }
603   case llvm::Triple::spir64: {
604     if (os != llvm::Triple::UnknownOS ||
605         Triple.getEnvironment() != llvm::Triple::UnknownEnvironment)
606       return nullptr;
607     return new SPIR64TargetInfo(Triple, Opts);
608   }
609   case llvm::Triple::wasm32:
610     if (Triple.getSubArch() != llvm::Triple::NoSubArch ||
611         Triple.getVendor() != llvm::Triple::UnknownVendor ||
612         !Triple.isOSBinFormatWasm())
613       return nullptr;
614     switch (os) {
615       case llvm::Triple::WASI:
616         return new WASITargetInfo<WebAssembly32TargetInfo>(Triple, Opts);
617       case llvm::Triple::Emscripten:
618         return new EmscriptenTargetInfo<WebAssembly32TargetInfo>(Triple, Opts);
619       case llvm::Triple::UnknownOS:
620         return new WebAssemblyOSTargetInfo<WebAssembly32TargetInfo>(Triple, Opts);
621       default:
622         return nullptr;
623     }
624   case llvm::Triple::wasm64:
625     if (Triple.getSubArch() != llvm::Triple::NoSubArch ||
626         Triple.getVendor() != llvm::Triple::UnknownVendor ||
627         !Triple.isOSBinFormatWasm())
628       return nullptr;
629     switch (os) {
630       case llvm::Triple::WASI:
631         return new WASITargetInfo<WebAssembly64TargetInfo>(Triple, Opts);
632       case llvm::Triple::Emscripten:
633         return new EmscriptenTargetInfo<WebAssembly64TargetInfo>(Triple, Opts);
634       case llvm::Triple::UnknownOS:
635         return new WebAssemblyOSTargetInfo<WebAssembly64TargetInfo>(Triple, Opts);
636       default:
637         return nullptr;
638     }
639 
640   case llvm::Triple::renderscript32:
641     return new LinuxTargetInfo<RenderScript32TargetInfo>(Triple, Opts);
642   case llvm::Triple::renderscript64:
643     return new LinuxTargetInfo<RenderScript64TargetInfo>(Triple, Opts);
644 
645   case llvm::Triple::ve:
646     return new LinuxTargetInfo<VETargetInfo>(Triple, Opts);
647   }
648 }
649 } // namespace targets
650 } // namespace clang
651 
652 using namespace clang::targets;
653 /// CreateTargetInfo - Return the target info object for the specified target
654 /// options.
655 TargetInfo *
CreateTargetInfo(DiagnosticsEngine & Diags,const std::shared_ptr<TargetOptions> & Opts)656 TargetInfo::CreateTargetInfo(DiagnosticsEngine &Diags,
657                              const std::shared_ptr<TargetOptions> &Opts) {
658   llvm::Triple Triple(Opts->Triple);
659 
660   // Construct the target
661   std::unique_ptr<TargetInfo> Target(AllocateTarget(Triple, *Opts));
662   if (!Target) {
663     Diags.Report(diag::err_target_unknown_triple) << Triple.str();
664     return nullptr;
665   }
666   Target->TargetOpts = Opts;
667 
668   // Set the target CPU if specified.
669   if (!Opts->CPU.empty() && !Target->setCPU(Opts->CPU)) {
670     Diags.Report(diag::err_target_unknown_cpu) << Opts->CPU;
671     SmallVector<StringRef, 32> ValidList;
672     Target->fillValidCPUList(ValidList);
673     if (!ValidList.empty())
674       Diags.Report(diag::note_valid_options) << llvm::join(ValidList, ", ");
675     return nullptr;
676   }
677 
678   // Check the TuneCPU name if specified.
679   if (!Opts->TuneCPU.empty() &&
680       !Target->isValidTuneCPUName(Opts->TuneCPU)) {
681     Diags.Report(diag::err_target_unknown_cpu) << Opts->TuneCPU;
682     SmallVector<StringRef, 32> ValidList;
683     Target->fillValidTuneCPUList(ValidList);
684     if (!ValidList.empty())
685       Diags.Report(diag::note_valid_options) << llvm::join(ValidList, ", ");
686     return nullptr;
687   }
688 
689   // Set the target ABI if specified.
690   if (!Opts->ABI.empty() && !Target->setABI(Opts->ABI)) {
691     Diags.Report(diag::err_target_unknown_abi) << Opts->ABI;
692     return nullptr;
693   }
694 
695   // Set the fp math unit.
696   if (!Opts->FPMath.empty() && !Target->setFPMath(Opts->FPMath)) {
697     Diags.Report(diag::err_target_unknown_fpmath) << Opts->FPMath;
698     return nullptr;
699   }
700 
701   // Compute the default target features, we need the target to handle this
702   // because features may have dependencies on one another.
703   if (!Target->initFeatureMap(Opts->FeatureMap, Diags, Opts->CPU,
704                               Opts->FeaturesAsWritten))
705     return nullptr;
706 
707   // Add the features to the compile options.
708   Opts->Features.clear();
709   for (const auto &F : Opts->FeatureMap)
710     Opts->Features.push_back((F.getValue() ? "+" : "-") + F.getKey().str());
711   // Sort here, so we handle the features in a predictable order. (This matters
712   // when we're dealing with features that overlap.)
713   llvm::sort(Opts->Features);
714 
715   if (!Target->handleTargetFeatures(Opts->Features, Diags))
716     return nullptr;
717 
718   Target->setSupportedOpenCLOpts();
719   Target->setCommandLineOpenCLOpts();
720   Target->setMaxAtomicWidth();
721 
722   if (!Target->validateTarget(Diags))
723     return nullptr;
724 
725   Target->CheckFixedPointBits();
726 
727   return Target.release();
728 }
729 /// validateOpenCLTarget  - Check that OpenCL target has valid
730 /// options setting based on OpenCL version.
validateOpenCLTarget(const LangOptions & Opts,DiagnosticsEngine & Diags) const731 bool TargetInfo::validateOpenCLTarget(const LangOptions &Opts,
732                                       DiagnosticsEngine &Diags) const {
733   const llvm::StringMap<bool> &OpenCLFeaturesMap = getSupportedOpenCLOpts();
734 
735   auto diagnoseNotSupportedCore = [&](llvm::StringRef Name, auto... OptArgs) {
736     if (OpenCLOptions::isOpenCLOptionCoreIn(Opts, OptArgs...) &&
737         !hasFeatureEnabled(OpenCLFeaturesMap, Name))
738       Diags.Report(diag::warn_opencl_unsupported_core_feature)
739           << Name << Opts.OpenCLCPlusPlus
740           << Opts.getOpenCLVersionTuple().getAsString();
741   };
742 #define OPENCL_GENERIC_EXTENSION(Ext, ...)                                     \
743   diagnoseNotSupportedCore(#Ext, __VA_ARGS__);
744 #include "clang/Basic/OpenCLExtensions.def"
745 
746   // Validate that feature macros are set properly for OpenCL C 3.0.
747   // In other cases assume that target is always valid.
748   if (Opts.OpenCLCPlusPlus || Opts.OpenCLVersion < 300)
749     return true;
750 
751   return OpenCLOptions::diagnoseUnsupportedFeatureDependencies(*this, Diags) &&
752          OpenCLOptions::diagnoseFeatureExtensionDifferences(*this, Diags);
753 }
754