]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/tools/clang/lib/Driver/ToolChains/Darwin.h
Merge llvm, clang, lld, lldb, compiler-rt and libc++ r303197, and update
[FreeBSD/FreeBSD.git] / contrib / llvm / tools / clang / lib / Driver / ToolChains / Darwin.h
1 //===--- Darwin.h - Darwin ToolChain Implementations ------------*- 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 #ifndef LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_DARWIN_H
11 #define LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_DARWIN_H
12
13 #include "Cuda.h"
14 #include "clang/Driver/Tool.h"
15 #include "clang/Driver/ToolChain.h"
16
17 namespace clang {
18 namespace driver {
19
20 namespace toolchains {
21 class MachO;
22 } // end namespace toolchains
23
24 namespace tools {
25
26 namespace darwin {
27 llvm::Triple::ArchType getArchTypeForMachOArchName(StringRef Str);
28 void setTripleTypeForMachOArchName(llvm::Triple &T, StringRef Str);
29
30 class LLVM_LIBRARY_VISIBILITY MachOTool : public Tool {
31   virtual void anchor();
32
33 protected:
34   void AddMachOArch(const llvm::opt::ArgList &Args,
35                     llvm::opt::ArgStringList &CmdArgs) const;
36
37   const toolchains::MachO &getMachOToolChain() const {
38     return reinterpret_cast<const toolchains::MachO &>(getToolChain());
39   }
40
41 public:
42   MachOTool(
43       const char *Name, const char *ShortName, const ToolChain &TC,
44       ResponseFileSupport ResponseSupport = RF_None,
45       llvm::sys::WindowsEncodingMethod ResponseEncoding = llvm::sys::WEM_UTF8,
46       const char *ResponseFlag = "@")
47       : Tool(Name, ShortName, TC, ResponseSupport, ResponseEncoding,
48              ResponseFlag) {}
49 };
50
51 class LLVM_LIBRARY_VISIBILITY Assembler : public MachOTool {
52 public:
53   Assembler(const ToolChain &TC)
54       : MachOTool("darwin::Assembler", "assembler", TC) {}
55
56   bool hasIntegratedCPP() const override { return false; }
57
58   void ConstructJob(Compilation &C, const JobAction &JA,
59                     const InputInfo &Output, const InputInfoList &Inputs,
60                     const llvm::opt::ArgList &TCArgs,
61                     const char *LinkingOutput) const override;
62 };
63
64 class LLVM_LIBRARY_VISIBILITY Linker : public MachOTool {
65   bool NeedsTempPath(const InputInfoList &Inputs) const;
66   void AddLinkArgs(Compilation &C, const llvm::opt::ArgList &Args,
67                    llvm::opt::ArgStringList &CmdArgs,
68                    const InputInfoList &Inputs) const;
69
70 public:
71   Linker(const ToolChain &TC)
72       : MachOTool("darwin::Linker", "linker", TC, RF_FileList,
73                   llvm::sys::WEM_UTF8, "-filelist") {}
74
75   bool hasIntegratedCPP() const override { return false; }
76   bool isLinkJob() const override { return true; }
77
78   void ConstructJob(Compilation &C, const JobAction &JA,
79                     const InputInfo &Output, const InputInfoList &Inputs,
80                     const llvm::opt::ArgList &TCArgs,
81                     const char *LinkingOutput) const override;
82 };
83
84 class LLVM_LIBRARY_VISIBILITY Lipo : public MachOTool {
85 public:
86   Lipo(const ToolChain &TC) : MachOTool("darwin::Lipo", "lipo", TC) {}
87
88   bool hasIntegratedCPP() const override { return false; }
89
90   void ConstructJob(Compilation &C, const JobAction &JA,
91                     const InputInfo &Output, const InputInfoList &Inputs,
92                     const llvm::opt::ArgList &TCArgs,
93                     const char *LinkingOutput) const override;
94 };
95
96 class LLVM_LIBRARY_VISIBILITY Dsymutil : public MachOTool {
97 public:
98   Dsymutil(const ToolChain &TC)
99       : MachOTool("darwin::Dsymutil", "dsymutil", TC) {}
100
101   bool hasIntegratedCPP() const override { return false; }
102   bool isDsymutilJob() const override { return true; }
103
104   void ConstructJob(Compilation &C, const JobAction &JA,
105                     const InputInfo &Output, const InputInfoList &Inputs,
106                     const llvm::opt::ArgList &TCArgs,
107                     const char *LinkingOutput) const override;
108 };
109
110 class LLVM_LIBRARY_VISIBILITY VerifyDebug : public MachOTool {
111 public:
112   VerifyDebug(const ToolChain &TC)
113       : MachOTool("darwin::VerifyDebug", "dwarfdump", TC) {}
114
115   bool hasIntegratedCPP() const override { return false; }
116
117   void ConstructJob(Compilation &C, const JobAction &JA,
118                     const InputInfo &Output, const InputInfoList &Inputs,
119                     const llvm::opt::ArgList &TCArgs,
120                     const char *LinkingOutput) const override;
121 };
122 } // end namespace darwin
123 } // end namespace tools
124
125 namespace toolchains {
126
127 class LLVM_LIBRARY_VISIBILITY MachO : public ToolChain {
128 protected:
129   Tool *buildAssembler() const override;
130   Tool *buildLinker() const override;
131   Tool *getTool(Action::ActionClass AC) const override;
132
133 private:
134   mutable std::unique_ptr<tools::darwin::Lipo> Lipo;
135   mutable std::unique_ptr<tools::darwin::Dsymutil> Dsymutil;
136   mutable std::unique_ptr<tools::darwin::VerifyDebug> VerifyDebug;
137
138 public:
139   MachO(const Driver &D, const llvm::Triple &Triple,
140         const llvm::opt::ArgList &Args);
141   ~MachO() override;
142
143   /// @name MachO specific toolchain API
144   /// {
145
146   /// Get the "MachO" arch name for a particular compiler invocation. For
147   /// example, Apple treats different ARM variations as distinct architectures.
148   StringRef getMachOArchName(const llvm::opt::ArgList &Args) const;
149
150   /// Add the linker arguments to link the ARC runtime library.
151   virtual void AddLinkARCArgs(const llvm::opt::ArgList &Args,
152                               llvm::opt::ArgStringList &CmdArgs) const {}
153
154   /// Add the linker arguments to link the compiler runtime library.
155   virtual void AddLinkRuntimeLibArgs(const llvm::opt::ArgList &Args,
156                                      llvm::opt::ArgStringList &CmdArgs) const;
157   virtual void AddFuzzerLinkArgs(const llvm::opt::ArgList &Args,
158                                llvm::opt::ArgStringList &CmdArgs) const;
159
160   virtual void addStartObjectFileArgs(const llvm::opt::ArgList &Args,
161                                       llvm::opt::ArgStringList &CmdArgs) const {
162   }
163
164   virtual void addMinVersionArgs(const llvm::opt::ArgList &Args,
165                                  llvm::opt::ArgStringList &CmdArgs) const {}
166
167   /// On some iOS platforms, kernel and kernel modules were built statically. Is
168   /// this such a target?
169   virtual bool isKernelStatic() const { return false; }
170
171   /// Is the target either iOS or an iOS simulator?
172   bool isTargetIOSBased() const { return false; }
173
174   void AddLinkRuntimeLib(const llvm::opt::ArgList &Args,
175                          llvm::opt::ArgStringList &CmdArgs,
176                          StringRef DarwinLibName, bool AlwaysLink = false,
177                          bool IsEmbedded = false, bool AddRPath = false) const;
178
179   /// Add any profiling runtime libraries that are needed. This is essentially a
180   /// MachO specific version of addProfileRT in Tools.cpp.
181   void addProfileRTLibs(const llvm::opt::ArgList &Args,
182                         llvm::opt::ArgStringList &CmdArgs) const override {
183     // There aren't any profiling libs for embedded targets currently.
184   }
185
186   /// }
187   /// @name ToolChain Implementation
188   /// {
189
190   types::ID LookupTypeForExtension(StringRef Ext) const override;
191
192   bool HasNativeLLVMSupport() const override;
193
194   llvm::opt::DerivedArgList *
195   TranslateArgs(const llvm::opt::DerivedArgList &Args, StringRef BoundArch,
196                 Action::OffloadKind DeviceOffloadKind) const override;
197
198   bool IsBlocksDefault() const override {
199     // Always allow blocks on Apple; users interested in versioning are
200     // expected to use /usr/include/Block.h.
201     return true;
202   }
203   bool IsIntegratedAssemblerDefault() const override {
204     // Default integrated assembler to on for Apple's MachO targets.
205     return true;
206   }
207
208   bool IsMathErrnoDefault() const override { return false; }
209
210   bool IsEncodeExtendedBlockSignatureDefault() const override { return true; }
211
212   bool IsObjCNonFragileABIDefault() const override {
213     // Non-fragile ABI is default for everything but i386.
214     return getTriple().getArch() != llvm::Triple::x86;
215   }
216
217   bool UseObjCMixedDispatch() const override { return true; }
218
219   bool IsUnwindTablesDefault() const override;
220
221   RuntimeLibType GetDefaultRuntimeLibType() const override {
222     return ToolChain::RLT_CompilerRT;
223   }
224
225   bool isPICDefault() const override;
226   bool isPIEDefault() const override;
227   bool isPICDefaultForced() const override;
228
229   bool SupportsProfiling() const override;
230
231   bool SupportsObjCGC() const override { return false; }
232
233   bool UseDwarfDebugFlags() const override;
234
235   bool UseSjLjExceptions(const llvm::opt::ArgList &Args) const override {
236     return false;
237   }
238
239   /// }
240 };
241
242 /// Darwin - The base Darwin tool chain.
243 class LLVM_LIBRARY_VISIBILITY Darwin : public MachO {
244 public:
245   /// Whether the information on the target has been initialized.
246   //
247   // FIXME: This should be eliminated. What we want to do is make this part of
248   // the "default target for arguments" selection process, once we get out of
249   // the argument translation business.
250   mutable bool TargetInitialized;
251
252   enum DarwinPlatformKind {
253     MacOS,
254     IPhoneOS,
255     IPhoneOSSimulator,
256     TvOS,
257     TvOSSimulator,
258     WatchOS,
259     WatchOSSimulator
260   };
261
262   mutable DarwinPlatformKind TargetPlatform;
263
264   /// The OS version we are targeting.
265   mutable VersionTuple TargetVersion;
266
267   CudaInstallationDetector CudaInstallation;
268
269 private:
270   void AddDeploymentTarget(llvm::opt::DerivedArgList &Args) const;
271
272 public:
273   Darwin(const Driver &D, const llvm::Triple &Triple,
274          const llvm::opt::ArgList &Args);
275   ~Darwin() override;
276
277   std::string ComputeEffectiveClangTriple(const llvm::opt::ArgList &Args,
278                                           types::ID InputType) const override;
279
280   /// @name Apple Specific Toolchain Implementation
281   /// {
282
283   void addMinVersionArgs(const llvm::opt::ArgList &Args,
284                          llvm::opt::ArgStringList &CmdArgs) const override;
285
286   void addStartObjectFileArgs(const llvm::opt::ArgList &Args,
287                               llvm::opt::ArgStringList &CmdArgs) const override;
288
289   bool isKernelStatic() const override {
290     return (!(isTargetIPhoneOS() && !isIPhoneOSVersionLT(6, 0)) &&
291             !isTargetWatchOS());
292   }
293
294   void addProfileRTLibs(const llvm::opt::ArgList &Args,
295                         llvm::opt::ArgStringList &CmdArgs) const override;
296
297 protected:
298   /// }
299   /// @name Darwin specific Toolchain functions
300   /// {
301
302   // FIXME: Eliminate these ...Target functions and derive separate tool chains
303   // for these targets and put version in constructor.
304   void setTarget(DarwinPlatformKind Platform, unsigned Major, unsigned Minor,
305                  unsigned Micro) const {
306     // FIXME: For now, allow reinitialization as long as values don't
307     // change. This will go away when we move away from argument translation.
308     if (TargetInitialized && TargetPlatform == Platform &&
309         TargetVersion == VersionTuple(Major, Minor, Micro))
310       return;
311
312     assert(!TargetInitialized && "Target already initialized!");
313     TargetInitialized = true;
314     TargetPlatform = Platform;
315     TargetVersion = VersionTuple(Major, Minor, Micro);
316   }
317
318   bool isTargetIPhoneOS() const {
319     assert(TargetInitialized && "Target not initialized!");
320     return TargetPlatform == IPhoneOS || TargetPlatform == TvOS;
321   }
322
323   bool isTargetIOSSimulator() const {
324     assert(TargetInitialized && "Target not initialized!");
325     return TargetPlatform == IPhoneOSSimulator ||
326            TargetPlatform == TvOSSimulator;
327   }
328
329   bool isTargetIOSBased() const {
330     assert(TargetInitialized && "Target not initialized!");
331     return isTargetIPhoneOS() || isTargetIOSSimulator();
332   }
333
334   bool isTargetTvOS() const {
335     assert(TargetInitialized && "Target not initialized!");
336     return TargetPlatform == TvOS;
337   }
338
339   bool isTargetTvOSSimulator() const {
340     assert(TargetInitialized && "Target not initialized!");
341     return TargetPlatform == TvOSSimulator;
342   }
343
344   bool isTargetTvOSBased() const {
345     assert(TargetInitialized && "Target not initialized!");
346     return TargetPlatform == TvOS || TargetPlatform == TvOSSimulator;
347   }
348
349   bool isTargetWatchOS() const {
350     assert(TargetInitialized && "Target not initialized!");
351     return TargetPlatform == WatchOS;
352   }
353
354   bool isTargetWatchOSSimulator() const {
355     assert(TargetInitialized && "Target not initialized!");
356     return TargetPlatform == WatchOSSimulator;
357   }
358
359   bool isTargetWatchOSBased() const {
360     assert(TargetInitialized && "Target not initialized!");
361     return TargetPlatform == WatchOS || TargetPlatform == WatchOSSimulator;
362   }
363
364   bool isTargetMacOS() const {
365     assert(TargetInitialized && "Target not initialized!");
366     return TargetPlatform == MacOS;
367   }
368
369   bool isTargetInitialized() const { return TargetInitialized; }
370
371   VersionTuple getTargetVersion() const {
372     assert(TargetInitialized && "Target not initialized!");
373     return TargetVersion;
374   }
375
376   bool isIPhoneOSVersionLT(unsigned V0, unsigned V1 = 0,
377                            unsigned V2 = 0) const {
378     assert(isTargetIOSBased() && "Unexpected call for non iOS target!");
379     return TargetVersion < VersionTuple(V0, V1, V2);
380   }
381
382   bool isMacosxVersionLT(unsigned V0, unsigned V1 = 0, unsigned V2 = 0) const {
383     assert(isTargetMacOS() && "Unexpected call for non OS X target!");
384     return TargetVersion < VersionTuple(V0, V1, V2);
385   }
386
387   StringRef getPlatformFamily() const;
388   static StringRef getSDKName(StringRef isysroot);
389   StringRef getOSLibraryNameSuffix() const;
390
391 public:
392   /// }
393   /// @name ToolChain Implementation
394   /// {
395
396   // Darwin tools support multiple architecture (e.g., i386 and x86_64) and
397   // most development is done against SDKs, so compiling for a different
398   // architecture should not get any special treatment.
399   bool isCrossCompiling() const override { return false; }
400
401   llvm::opt::DerivedArgList *
402   TranslateArgs(const llvm::opt::DerivedArgList &Args, StringRef BoundArch,
403                 Action::OffloadKind DeviceOffloadKind) const override;
404
405   CXXStdlibType GetDefaultCXXStdlibType() const override;
406   ObjCRuntime getDefaultObjCRuntime(bool isNonFragile) const override;
407   bool hasBlocksRuntime() const override;
408
409   void AddCudaIncludeArgs(const llvm::opt::ArgList &DriverArgs,
410                           llvm::opt::ArgStringList &CC1Args) const override;
411
412   bool UseObjCMixedDispatch() const override {
413     // This is only used with the non-fragile ABI and non-legacy dispatch.
414
415     // Mixed dispatch is used everywhere except OS X before 10.6.
416     return !(isTargetMacOS() && isMacosxVersionLT(10, 6));
417   }
418
419   unsigned GetDefaultStackProtectorLevel(bool KernelOrKext) const override {
420     // Stack protectors default to on for user code on 10.5,
421     // and for everything in 10.6 and beyond
422     if (isTargetIOSBased() || isTargetWatchOSBased())
423       return 1;
424     else if (isTargetMacOS() && !isMacosxVersionLT(10, 6))
425       return 1;
426     else if (isTargetMacOS() && !isMacosxVersionLT(10, 5) && !KernelOrKext)
427       return 1;
428
429     return 0;
430   }
431
432   bool SupportsObjCGC() const override;
433
434   void CheckObjCARC() const override;
435
436   bool UseSjLjExceptions(const llvm::opt::ArgList &Args) const override;
437
438   bool SupportsEmbeddedBitcode() const override;
439
440   SanitizerMask getSupportedSanitizers() const override;
441
442   void printVerboseInfo(raw_ostream &OS) const override;
443 };
444
445 /// DarwinClang - The Darwin toolchain used by Clang.
446 class LLVM_LIBRARY_VISIBILITY DarwinClang : public Darwin {
447 public:
448   DarwinClang(const Driver &D, const llvm::Triple &Triple,
449               const llvm::opt::ArgList &Args);
450
451   /// @name Apple ToolChain Implementation
452   /// {
453
454   RuntimeLibType GetRuntimeLibType(const llvm::opt::ArgList &Args) const override;
455
456   void AddLinkRuntimeLibArgs(const llvm::opt::ArgList &Args,
457                              llvm::opt::ArgStringList &CmdArgs) const override;
458
459   void AddCXXStdlibLibArgs(const llvm::opt::ArgList &Args,
460                            llvm::opt::ArgStringList &CmdArgs) const override;
461
462   void AddCCKextLibArgs(const llvm::opt::ArgList &Args,
463                         llvm::opt::ArgStringList &CmdArgs) const override;
464
465   void addClangWarningOptions(llvm::opt::ArgStringList &CC1Args) const override;
466
467   void AddLinkARCArgs(const llvm::opt::ArgList &Args,
468                       llvm::opt::ArgStringList &CmdArgs) const override;
469
470   unsigned GetDefaultDwarfVersion() const override;
471   // Until dtrace (via CTF) and LLDB can deal with distributed debug info,
472   // Darwin defaults to standalone/full debug info.
473   bool GetDefaultStandaloneDebug() const override { return true; }
474   llvm::DebuggerKind getDefaultDebuggerTuning() const override {
475     return llvm::DebuggerKind::LLDB;
476   }
477
478   /// }
479
480 private:
481   void AddLinkSanitizerLibArgs(const llvm::opt::ArgList &Args,
482                                llvm::opt::ArgStringList &CmdArgs,
483                                StringRef Sanitizer) const;
484 };
485
486 } // end namespace toolchains
487 } // end namespace driver
488 } // end namespace clang
489
490 #endif // LLVM_CLANG_LIB_DRIVER_TOOLCHAINS_DARWIN_H