/src/llvm-project/clang/lib/Basic/Targets/X86.h
Line | Count | Source (jump to first uncovered line) |
1 | | //===--- X86.h - Declare X86 target feature support -------------*- 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 | | // This file declares X86 TargetInfo objects. |
10 | | // |
11 | | //===----------------------------------------------------------------------===// |
12 | | |
13 | | #ifndef LLVM_CLANG_LIB_BASIC_TARGETS_X86_H |
14 | | #define LLVM_CLANG_LIB_BASIC_TARGETS_X86_H |
15 | | |
16 | | #include "OSTargets.h" |
17 | | #include "clang/Basic/BitmaskEnum.h" |
18 | | #include "clang/Basic/TargetInfo.h" |
19 | | #include "clang/Basic/TargetOptions.h" |
20 | | #include "llvm/Support/Compiler.h" |
21 | | #include "llvm/TargetParser/Triple.h" |
22 | | #include "llvm/TargetParser/X86TargetParser.h" |
23 | | #include <optional> |
24 | | |
25 | | namespace clang { |
26 | | namespace targets { |
27 | | |
28 | | static const unsigned X86AddrSpaceMap[] = { |
29 | | 0, // Default |
30 | | 0, // opencl_global |
31 | | 0, // opencl_local |
32 | | 0, // opencl_constant |
33 | | 0, // opencl_private |
34 | | 0, // opencl_generic |
35 | | 0, // opencl_global_device |
36 | | 0, // opencl_global_host |
37 | | 0, // cuda_device |
38 | | 0, // cuda_constant |
39 | | 0, // cuda_shared |
40 | | 0, // sycl_global |
41 | | 0, // sycl_global_device |
42 | | 0, // sycl_global_host |
43 | | 0, // sycl_local |
44 | | 0, // sycl_private |
45 | | 270, // ptr32_sptr |
46 | | 271, // ptr32_uptr |
47 | | 272, // ptr64 |
48 | | 0, // hlsl_groupshared |
49 | | // Wasm address space values for this target are dummy values, |
50 | | // as it is only enabled for Wasm targets. |
51 | | 20, // wasm_funcref |
52 | | }; |
53 | | |
54 | | // X86 target abstract base class; x86-32 and x86-64 are very close, so |
55 | | // most of the implementation can be shared. |
56 | | class LLVM_LIBRARY_VISIBILITY X86TargetInfo : public TargetInfo { |
57 | | |
58 | | enum X86SSEEnum { |
59 | | NoSSE, |
60 | | SSE1, |
61 | | SSE2, |
62 | | SSE3, |
63 | | SSSE3, |
64 | | SSE41, |
65 | | SSE42, |
66 | | AVX, |
67 | | AVX2, |
68 | | AVX512F |
69 | | } SSELevel = NoSSE; |
70 | | enum MMX3DNowEnum { |
71 | | NoMMX3DNow, |
72 | | MMX, |
73 | | AMD3DNow, |
74 | | AMD3DNowAthlon |
75 | | } MMX3DNowLevel = NoMMX3DNow; |
76 | | enum XOPEnum { NoXOP, SSE4A, FMA4, XOP } XOPLevel = NoXOP; |
77 | | enum AddrSpace { ptr32_sptr = 270, ptr32_uptr = 271, ptr64 = 272 }; |
78 | | |
79 | | bool HasAES = false; |
80 | | bool HasVAES = false; |
81 | | bool HasPCLMUL = false; |
82 | | bool HasVPCLMULQDQ = false; |
83 | | bool HasGFNI = false; |
84 | | bool HasLZCNT = false; |
85 | | bool HasRDRND = false; |
86 | | bool HasFSGSBASE = false; |
87 | | bool HasBMI = false; |
88 | | bool HasBMI2 = false; |
89 | | bool HasPOPCNT = false; |
90 | | bool HasRTM = false; |
91 | | bool HasPRFCHW = false; |
92 | | bool HasRDSEED = false; |
93 | | bool HasADX = false; |
94 | | bool HasTBM = false; |
95 | | bool HasLWP = false; |
96 | | bool HasFMA = false; |
97 | | bool HasF16C = false; |
98 | | bool HasAVX10_1 = false; |
99 | | bool HasAVX10_1_512 = false; |
100 | | bool HasEVEX512 = false; |
101 | | bool HasAVX512CD = false; |
102 | | bool HasAVX512VPOPCNTDQ = false; |
103 | | bool HasAVX512VNNI = false; |
104 | | bool HasAVX512FP16 = false; |
105 | | bool HasAVX512BF16 = false; |
106 | | bool HasAVX512ER = false; |
107 | | bool HasAVX512PF = false; |
108 | | bool HasAVX512DQ = false; |
109 | | bool HasAVX512BITALG = false; |
110 | | bool HasAVX512BW = false; |
111 | | bool HasAVX512VL = false; |
112 | | bool HasAVX512VBMI = false; |
113 | | bool HasAVX512VBMI2 = false; |
114 | | bool HasAVXIFMA = false; |
115 | | bool HasAVX512IFMA = false; |
116 | | bool HasAVX512VP2INTERSECT = false; |
117 | | bool HasSHA = false; |
118 | | bool HasSHA512 = false; |
119 | | bool HasSHSTK = false; |
120 | | bool HasSM3 = false; |
121 | | bool HasSGX = false; |
122 | | bool HasSM4 = false; |
123 | | bool HasCX8 = false; |
124 | | bool HasCX16 = false; |
125 | | bool HasFXSR = false; |
126 | | bool HasXSAVE = false; |
127 | | bool HasXSAVEOPT = false; |
128 | | bool HasXSAVEC = false; |
129 | | bool HasXSAVES = false; |
130 | | bool HasMWAITX = false; |
131 | | bool HasCLZERO = false; |
132 | | bool HasCLDEMOTE = false; |
133 | | bool HasPCONFIG = false; |
134 | | bool HasPKU = false; |
135 | | bool HasCLFLUSHOPT = false; |
136 | | bool HasCLWB = false; |
137 | | bool HasMOVBE = false; |
138 | | bool HasPREFETCHI = false; |
139 | | bool HasPREFETCHWT1 = false; |
140 | | bool HasRDPID = false; |
141 | | bool HasRDPRU = false; |
142 | | bool HasRetpolineExternalThunk = false; |
143 | | bool HasLAHFSAHF = false; |
144 | | bool HasWBNOINVD = false; |
145 | | bool HasWAITPKG = false; |
146 | | bool HasMOVDIRI = false; |
147 | | bool HasMOVDIR64B = false; |
148 | | bool HasPTWRITE = false; |
149 | | bool HasINVPCID = false; |
150 | | bool HasENQCMD = false; |
151 | | bool HasAVXVNNIINT16 = false; |
152 | | bool HasAMXFP16 = false; |
153 | | bool HasCMPCCXADD = false; |
154 | | bool HasRAOINT = false; |
155 | | bool HasAVXVNNIINT8 = false; |
156 | | bool HasAVXNECONVERT = false; |
157 | | bool HasKL = false; // For key locker |
158 | | bool HasWIDEKL = false; // For wide key locker |
159 | | bool HasHRESET = false; |
160 | | bool HasAVXVNNI = false; |
161 | | bool HasAMXTILE = false; |
162 | | bool HasAMXINT8 = false; |
163 | | bool HasAMXBF16 = false; |
164 | | bool HasAMXCOMPLEX = false; |
165 | | bool HasSERIALIZE = false; |
166 | | bool HasTSXLDTRK = false; |
167 | | bool HasUSERMSR = false; |
168 | | bool HasUINTR = false; |
169 | | bool HasCRC32 = false; |
170 | | bool HasX87 = false; |
171 | | bool HasEGPR = false; |
172 | | bool HasPush2Pop2 = false; |
173 | | bool HasPPX = false; |
174 | | bool HasNDD = false; |
175 | | bool HasCCMP = false; |
176 | | bool HasCF = false; |
177 | | |
178 | | protected: |
179 | | llvm::X86::CPUKind CPU = llvm::X86::CK_None; |
180 | | |
181 | | enum FPMathKind { FP_Default, FP_SSE, FP_387 } FPMath = FP_Default; |
182 | | |
183 | | public: |
184 | | X86TargetInfo(const llvm::Triple &Triple, const TargetOptions &) |
185 | 46 | : TargetInfo(Triple) { |
186 | 46 | BFloat16Width = BFloat16Align = 16; |
187 | 46 | BFloat16Format = &llvm::APFloat::BFloat(); |
188 | 46 | LongDoubleFormat = &llvm::APFloat::x87DoubleExtended(); |
189 | 46 | AddrSpaceMap = &X86AddrSpaceMap; |
190 | 46 | HasStrictFP = true; |
191 | | |
192 | 46 | bool IsWinCOFF = |
193 | 46 | getTriple().isOSWindows() && getTriple().isOSBinFormatCOFF(); |
194 | 46 | if (IsWinCOFF) |
195 | 0 | MaxVectorAlign = MaxTLSAlign = 8192u * getCharWidth(); |
196 | 46 | } |
197 | | |
198 | 0 | const char *getLongDoubleMangling() const override { |
199 | 0 | return LongDoubleFormat == &llvm::APFloat::IEEEquad() ? "g" : "e"; |
200 | 0 | } |
201 | | |
202 | 92 | LangOptions::FPEvalMethodKind getFPEvalMethod() const override { |
203 | | // X87 evaluates with 80 bits "long double" precision. |
204 | 92 | return SSELevel == NoSSE ? LangOptions::FPEvalMethodKind::FEM_Extended |
205 | 92 | : LangOptions::FPEvalMethodKind::FEM_Source; |
206 | 92 | } |
207 | | |
208 | | // EvalMethod `source` is not supported for targets with `NoSSE` feature. |
209 | 1 | bool supportSourceEvalMethod() const override { return SSELevel > NoSSE; } |
210 | | |
211 | | ArrayRef<const char *> getGCCRegNames() const override; |
212 | | |
213 | 0 | ArrayRef<TargetInfo::GCCRegAlias> getGCCRegAliases() const override { |
214 | 0 | return std::nullopt; |
215 | 0 | } |
216 | | |
217 | | ArrayRef<TargetInfo::AddlRegName> getGCCAddlRegNames() const override; |
218 | | |
219 | 0 | bool isSPRegName(StringRef RegName) const override { |
220 | 0 | return RegName.equals("esp") || RegName.equals("rsp"); |
221 | 0 | } |
222 | | |
223 | | bool validateCpuSupports(StringRef FeatureStr) const override; |
224 | | |
225 | | bool validateCpuIs(StringRef FeatureStr) const override; |
226 | | |
227 | | bool validateCPUSpecificCPUDispatch(StringRef Name) const override; |
228 | | |
229 | | char CPUSpecificManglingCharacter(StringRef Name) const override; |
230 | | |
231 | | void getCPUSpecificCPUDispatchFeatures( |
232 | | StringRef Name, |
233 | | llvm::SmallVectorImpl<StringRef> &Features) const override; |
234 | | |
235 | | std::optional<unsigned> getCPUCacheLineSize() const override; |
236 | | |
237 | | bool validateAsmConstraint(const char *&Name, |
238 | | TargetInfo::ConstraintInfo &info) const override; |
239 | | |
240 | | bool validateGlobalRegisterVariable(StringRef RegName, unsigned RegSize, |
241 | 0 | bool &HasSizeMismatch) const override { |
242 | | // esp and ebp are the only 32-bit registers the x86 backend can currently |
243 | | // handle. |
244 | 0 | if (RegName.equals("esp") || RegName.equals("ebp")) { |
245 | | // Check that the register size is 32-bit. |
246 | 0 | HasSizeMismatch = RegSize != 32; |
247 | 0 | return true; |
248 | 0 | } |
249 | | |
250 | 0 | return false; |
251 | 0 | } |
252 | | |
253 | | bool validateOutputSize(const llvm::StringMap<bool> &FeatureMap, |
254 | | StringRef Constraint, unsigned Size) const override; |
255 | | |
256 | | bool validateInputSize(const llvm::StringMap<bool> &FeatureMap, |
257 | | StringRef Constraint, unsigned Size) const override; |
258 | | |
259 | | bool |
260 | 0 | checkCFProtectionReturnSupported(DiagnosticsEngine &Diags) const override { |
261 | 0 | if (CPU == llvm::X86::CK_None || CPU >= llvm::X86::CK_PentiumPro) |
262 | 0 | return true; |
263 | 0 | return TargetInfo::checkCFProtectionReturnSupported(Diags); |
264 | 0 | }; |
265 | | |
266 | | bool |
267 | 0 | checkCFProtectionBranchSupported(DiagnosticsEngine &Diags) const override { |
268 | 0 | if (CPU == llvm::X86::CK_None || CPU >= llvm::X86::CK_PentiumPro) |
269 | 0 | return true; |
270 | 0 | return TargetInfo::checkCFProtectionBranchSupported(Diags); |
271 | 0 | }; |
272 | | |
273 | | virtual bool validateOperandSize(const llvm::StringMap<bool> &FeatureMap, |
274 | | StringRef Constraint, unsigned Size) const; |
275 | | |
276 | | std::string convertConstraint(const char *&Constraint) const override; |
277 | 0 | std::string_view getClobbers() const override { |
278 | 0 | return "~{dirflag},~{fpsr},~{flags}"; |
279 | 0 | } |
280 | | |
281 | | StringRef getConstraintRegister(StringRef Constraint, |
282 | 0 | StringRef Expression) const override { |
283 | 0 | StringRef::iterator I, E; |
284 | 0 | for (I = Constraint.begin(), E = Constraint.end(); I != E; ++I) { |
285 | 0 | if (isalpha(*I) || *I == '@') |
286 | 0 | break; |
287 | 0 | } |
288 | 0 | if (I == E) |
289 | 0 | return ""; |
290 | 0 | switch (*I) { |
291 | | // For the register constraints, return the matching register name |
292 | 0 | case 'a': |
293 | 0 | return "ax"; |
294 | 0 | case 'b': |
295 | 0 | return "bx"; |
296 | 0 | case 'c': |
297 | 0 | return "cx"; |
298 | 0 | case 'd': |
299 | 0 | return "dx"; |
300 | 0 | case 'S': |
301 | 0 | return "si"; |
302 | 0 | case 'D': |
303 | 0 | return "di"; |
304 | | // In case the constraint is 'r' we need to return Expression |
305 | 0 | case 'r': |
306 | 0 | return Expression; |
307 | | // Double letters Y<x> constraints |
308 | 0 | case 'Y': |
309 | 0 | if ((++I != E) && ((*I == '0') || (*I == 'z'))) |
310 | 0 | return "xmm0"; |
311 | 0 | break; |
312 | 0 | default: |
313 | 0 | break; |
314 | 0 | } |
315 | 0 | return ""; |
316 | 0 | } |
317 | | |
318 | 2 | bool useFP16ConversionIntrinsics() const override { |
319 | 2 | return false; |
320 | 2 | } |
321 | | |
322 | | void getTargetDefines(const LangOptions &Opts, |
323 | | MacroBuilder &Builder) const override; |
324 | | |
325 | | void setFeatureEnabled(llvm::StringMap<bool> &Features, StringRef Name, |
326 | | bool Enabled) const final; |
327 | | |
328 | | bool |
329 | | initFeatureMap(llvm::StringMap<bool> &Features, DiagnosticsEngine &Diags, |
330 | | StringRef CPU, |
331 | | const std::vector<std::string> &FeaturesVec) const override; |
332 | | |
333 | | bool isValidFeatureName(StringRef Name) const override; |
334 | | |
335 | | bool hasFeature(StringRef Feature) const final; |
336 | | |
337 | | bool handleTargetFeatures(std::vector<std::string> &Features, |
338 | | DiagnosticsEngine &Diags) override; |
339 | | |
340 | 92 | StringRef getABI() const override { |
341 | 92 | if (getTriple().getArch() == llvm::Triple::x86_64 && SSELevel >= AVX512F) |
342 | 0 | return "avx512"; |
343 | 92 | if (getTriple().getArch() == llvm::Triple::x86_64 && SSELevel >= AVX) |
344 | 0 | return "avx"; |
345 | 92 | if (getTriple().getArch() == llvm::Triple::x86 && |
346 | 92 | MMX3DNowLevel == NoMMX3DNow) |
347 | 0 | return "no-mmx"; |
348 | 92 | return ""; |
349 | 92 | } |
350 | | |
351 | 0 | bool supportsTargetAttributeTune() const override { |
352 | 0 | return true; |
353 | 0 | } |
354 | | |
355 | 0 | bool isValidCPUName(StringRef Name) const override { |
356 | 0 | bool Only64Bit = getTriple().getArch() != llvm::Triple::x86; |
357 | 0 | return llvm::X86::parseArchX86(Name, Only64Bit) != llvm::X86::CK_None; |
358 | 0 | } |
359 | | |
360 | 0 | bool isValidTuneCPUName(StringRef Name) const override { |
361 | 0 | if (Name == "generic") |
362 | 0 | return true; |
363 | | |
364 | | // Allow 32-bit only CPUs regardless of 64-bit mode unlike isValidCPUName. |
365 | | // NOTE: gcc rejects 32-bit mtune CPUs in 64-bit mode. But being lenient |
366 | | // since mtune was ignored by clang for so long. |
367 | 0 | return llvm::X86::parseTuneCPU(Name) != llvm::X86::CK_None; |
368 | 0 | } |
369 | | |
370 | | void fillValidCPUList(SmallVectorImpl<StringRef> &Values) const override; |
371 | | void fillValidTuneCPUList(SmallVectorImpl<StringRef> &Values) const override; |
372 | | |
373 | 0 | bool setCPU(const std::string &Name) override { |
374 | 0 | bool Only64Bit = getTriple().getArch() != llvm::Triple::x86; |
375 | 0 | CPU = llvm::X86::parseArchX86(Name, Only64Bit); |
376 | 0 | return CPU != llvm::X86::CK_None; |
377 | 0 | } |
378 | | |
379 | | unsigned multiVersionSortPriority(StringRef Name) const override; |
380 | | |
381 | | bool setFPMath(StringRef Name) override; |
382 | | |
383 | 0 | bool supportsExtendIntArgs() const override { |
384 | 0 | return getTriple().getArch() != llvm::Triple::x86; |
385 | 0 | } |
386 | | |
387 | 0 | CallingConvCheckResult checkCallingConvention(CallingConv CC) const override { |
388 | | // Most of the non-ARM calling conventions are i386 conventions. |
389 | 0 | switch (CC) { |
390 | 0 | case CC_X86ThisCall: |
391 | 0 | case CC_X86FastCall: |
392 | 0 | case CC_X86StdCall: |
393 | 0 | case CC_X86VectorCall: |
394 | 0 | case CC_X86RegCall: |
395 | 0 | case CC_C: |
396 | 0 | case CC_PreserveMost: |
397 | 0 | case CC_Swift: |
398 | 0 | case CC_X86Pascal: |
399 | 0 | case CC_IntelOclBicc: |
400 | 0 | case CC_OpenCLKernel: |
401 | 0 | return CCCR_OK; |
402 | 0 | case CC_SwiftAsync: |
403 | 0 | return CCCR_Error; |
404 | 0 | default: |
405 | 0 | return CCCR_Warning; |
406 | 0 | } |
407 | 0 | } |
408 | | |
409 | 0 | bool checkArithmeticFenceSupported() const override { return true; } |
410 | | |
411 | 0 | CallingConv getDefaultCallingConv() const override { |
412 | 0 | return CC_C; |
413 | 0 | } |
414 | | |
415 | 0 | bool hasSjLjLowering() const override { return true; } |
416 | | |
417 | 46 | void setSupportedOpenCLOpts() override { supportAllOpenCLOpts(); } |
418 | | |
419 | 0 | uint64_t getPointerWidthV(LangAS AS) const override { |
420 | 0 | unsigned TargetAddrSpace = getTargetAddressSpace(AS); |
421 | 0 | if (TargetAddrSpace == ptr32_sptr || TargetAddrSpace == ptr32_uptr) |
422 | 0 | return 32; |
423 | 0 | if (TargetAddrSpace == ptr64) |
424 | 0 | return 64; |
425 | 0 | return PointerWidth; |
426 | 0 | } |
427 | | |
428 | 0 | uint64_t getPointerAlignV(LangAS AddrSpace) const override { |
429 | 0 | return getPointerWidthV(AddrSpace); |
430 | 0 | } |
431 | | |
432 | | }; |
433 | | |
434 | | // X86-32 generic target |
435 | | class LLVM_LIBRARY_VISIBILITY X86_32TargetInfo : public X86TargetInfo { |
436 | | public: |
437 | | X86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
438 | 0 | : X86TargetInfo(Triple, Opts) { |
439 | 0 | DoubleAlign = LongLongAlign = 32; |
440 | 0 | LongDoubleWidth = 96; |
441 | 0 | LongDoubleAlign = 32; |
442 | 0 | SuitableAlign = 128; |
443 | 0 | resetDataLayout(Triple.isOSBinFormatMachO() |
444 | 0 | ? "e-m:o-p:32:32-p270:32:32-p271:32:32-p272:64:64-i128:" |
445 | 0 | "128-f64:32:64-f80:32-n8:16:32-S128" |
446 | 0 | : "e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-i128:" |
447 | 0 | "128-f64:32:64-f80:32-n8:16:32-S128", |
448 | 0 | Triple.isOSBinFormatMachO() ? "_" : ""); |
449 | 0 | SizeType = UnsignedInt; |
450 | 0 | PtrDiffType = SignedInt; |
451 | 0 | IntPtrType = SignedInt; |
452 | 0 | RegParmMax = 3; |
453 | | |
454 | | // Use fpret for all types. |
455 | 0 | RealTypeUsesObjCFPRetMask = |
456 | 0 | (unsigned)(FloatModeKind::Float | FloatModeKind::Double | |
457 | 0 | FloatModeKind::LongDouble); |
458 | | |
459 | | // x86-32 has atomics up to 8 bytes |
460 | 0 | MaxAtomicPromoteWidth = 64; |
461 | 0 | MaxAtomicInlineWidth = 32; |
462 | 0 | } |
463 | | |
464 | 0 | BuiltinVaListKind getBuiltinVaListKind() const override { |
465 | 0 | return TargetInfo::CharPtrBuiltinVaList; |
466 | 0 | } |
467 | | |
468 | 0 | int getEHDataRegisterNumber(unsigned RegNo) const override { |
469 | 0 | if (RegNo == 0) |
470 | 0 | return 0; |
471 | 0 | if (RegNo == 1) |
472 | 0 | return 2; |
473 | 0 | return -1; |
474 | 0 | } |
475 | | |
476 | | bool validateOperandSize(const llvm::StringMap<bool> &FeatureMap, |
477 | 0 | StringRef Constraint, unsigned Size) const override { |
478 | 0 | switch (Constraint[0]) { |
479 | 0 | default: |
480 | 0 | break; |
481 | 0 | case 'R': |
482 | 0 | case 'q': |
483 | 0 | case 'Q': |
484 | 0 | case 'a': |
485 | 0 | case 'b': |
486 | 0 | case 'c': |
487 | 0 | case 'd': |
488 | 0 | case 'S': |
489 | 0 | case 'D': |
490 | 0 | return Size <= 32; |
491 | 0 | case 'A': |
492 | 0 | return Size <= 64; |
493 | 0 | } |
494 | | |
495 | 0 | return X86TargetInfo::validateOperandSize(FeatureMap, Constraint, Size); |
496 | 0 | } |
497 | | |
498 | 0 | void setMaxAtomicWidth() override { |
499 | 0 | if (hasFeature("cx8")) |
500 | 0 | MaxAtomicInlineWidth = 64; |
501 | 0 | } |
502 | | |
503 | | ArrayRef<Builtin::Info> getTargetBuiltins() const override; |
504 | | |
505 | 0 | bool hasBitIntType() const override { return true; } |
506 | 0 | size_t getMaxBitIntWidth() const override { |
507 | 0 | return llvm::IntegerType::MAX_INT_BITS; |
508 | 0 | } |
509 | | }; |
510 | | |
511 | | class LLVM_LIBRARY_VISIBILITY NetBSDI386TargetInfo |
512 | | : public NetBSDTargetInfo<X86_32TargetInfo> { |
513 | | public: |
514 | | NetBSDI386TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
515 | 0 | : NetBSDTargetInfo<X86_32TargetInfo>(Triple, Opts) {} |
516 | | |
517 | 0 | LangOptions::FPEvalMethodKind getFPEvalMethod() const override { |
518 | 0 | VersionTuple OsVersion = getTriple().getOSVersion(); |
519 | | // New NetBSD uses the default rounding mode. |
520 | 0 | if (OsVersion >= VersionTuple(6, 99, 26) || OsVersion.getMajor() == 0) |
521 | 0 | return X86_32TargetInfo::getFPEvalMethod(); |
522 | | // NetBSD before 6.99.26 defaults to "double" rounding. |
523 | 0 | return LangOptions::FPEvalMethodKind::FEM_Double; |
524 | 0 | } |
525 | | }; |
526 | | |
527 | | class LLVM_LIBRARY_VISIBILITY OpenBSDI386TargetInfo |
528 | | : public OpenBSDTargetInfo<X86_32TargetInfo> { |
529 | | public: |
530 | | OpenBSDI386TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
531 | 0 | : OpenBSDTargetInfo<X86_32TargetInfo>(Triple, Opts) { |
532 | 0 | SizeType = UnsignedLong; |
533 | 0 | IntPtrType = SignedLong; |
534 | 0 | PtrDiffType = SignedLong; |
535 | 0 | } |
536 | | }; |
537 | | |
538 | | class LLVM_LIBRARY_VISIBILITY DarwinI386TargetInfo |
539 | | : public DarwinTargetInfo<X86_32TargetInfo> { |
540 | | public: |
541 | | DarwinI386TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
542 | 0 | : DarwinTargetInfo<X86_32TargetInfo>(Triple, Opts) { |
543 | 0 | LongDoubleWidth = 128; |
544 | 0 | LongDoubleAlign = 128; |
545 | 0 | SuitableAlign = 128; |
546 | 0 | MaxVectorAlign = 256; |
547 | | // The watchOS simulator uses the builtin bool type for Objective-C. |
548 | 0 | llvm::Triple T = llvm::Triple(Triple); |
549 | 0 | if (T.isWatchOS()) |
550 | 0 | UseSignedCharForObjCBool = false; |
551 | 0 | SizeType = UnsignedLong; |
552 | 0 | IntPtrType = SignedLong; |
553 | 0 | resetDataLayout("e-m:o-p:32:32-p270:32:32-p271:32:32-p272:64:64-i128:128-" |
554 | 0 | "f64:32:64-f80:128-n8:16:32-S128", |
555 | 0 | "_"); |
556 | 0 | HasAlignMac68kSupport = true; |
557 | 0 | } |
558 | | |
559 | | bool handleTargetFeatures(std::vector<std::string> &Features, |
560 | 0 | DiagnosticsEngine &Diags) override { |
561 | 0 | if (!DarwinTargetInfo<X86_32TargetInfo>::handleTargetFeatures(Features, |
562 | 0 | Diags)) |
563 | 0 | return false; |
564 | | // We now know the features we have: we can decide how to align vectors. |
565 | 0 | MaxVectorAlign = |
566 | 0 | hasFeature("avx512f") ? 512 : hasFeature("avx") ? 256 : 128; |
567 | 0 | return true; |
568 | 0 | } |
569 | | }; |
570 | | |
571 | | // x86-32 Windows target |
572 | | class LLVM_LIBRARY_VISIBILITY WindowsX86_32TargetInfo |
573 | | : public WindowsTargetInfo<X86_32TargetInfo> { |
574 | | public: |
575 | | WindowsX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
576 | 0 | : WindowsTargetInfo<X86_32TargetInfo>(Triple, Opts) { |
577 | 0 | DoubleAlign = LongLongAlign = 64; |
578 | 0 | bool IsWinCOFF = |
579 | 0 | getTriple().isOSWindows() && getTriple().isOSBinFormatCOFF(); |
580 | 0 | bool IsMSVC = getTriple().isWindowsMSVCEnvironment(); |
581 | 0 | std::string Layout = IsWinCOFF ? "e-m:x" : "e-m:e"; |
582 | 0 | Layout += "-p:32:32-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-"; |
583 | 0 | Layout += IsMSVC ? "f80:128" : "f80:32"; |
584 | 0 | Layout += "-n8:16:32-a:0:32-S32"; |
585 | 0 | resetDataLayout(Layout, IsWinCOFF ? "_" : ""); |
586 | 0 | } |
587 | | }; |
588 | | |
589 | | // x86-32 Windows Visual Studio target |
590 | | class LLVM_LIBRARY_VISIBILITY MicrosoftX86_32TargetInfo |
591 | | : public WindowsX86_32TargetInfo { |
592 | | public: |
593 | | MicrosoftX86_32TargetInfo(const llvm::Triple &Triple, |
594 | | const TargetOptions &Opts) |
595 | 0 | : WindowsX86_32TargetInfo(Triple, Opts) { |
596 | 0 | LongDoubleWidth = LongDoubleAlign = 64; |
597 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEdouble(); |
598 | 0 | } |
599 | | |
600 | | void getTargetDefines(const LangOptions &Opts, |
601 | 0 | MacroBuilder &Builder) const override { |
602 | 0 | WindowsX86_32TargetInfo::getTargetDefines(Opts, Builder); |
603 | | // The value of the following reflects processor type. |
604 | | // 300=386, 400=486, 500=Pentium, 600=Blend (default) |
605 | | // We lost the original triple, so we use the default. |
606 | 0 | Builder.defineMacro("_M_IX86", "600"); |
607 | 0 | } |
608 | | }; |
609 | | |
610 | | // x86-32 MinGW target |
611 | | class LLVM_LIBRARY_VISIBILITY MinGWX86_32TargetInfo |
612 | | : public WindowsX86_32TargetInfo { |
613 | | public: |
614 | | MinGWX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
615 | 0 | : WindowsX86_32TargetInfo(Triple, Opts) { |
616 | 0 | HasFloat128 = true; |
617 | 0 | } |
618 | | |
619 | | void getTargetDefines(const LangOptions &Opts, |
620 | 0 | MacroBuilder &Builder) const override { |
621 | 0 | WindowsX86_32TargetInfo::getTargetDefines(Opts, Builder); |
622 | 0 | Builder.defineMacro("_X86_"); |
623 | 0 | } |
624 | | }; |
625 | | |
626 | | // x86-32 Cygwin target |
627 | | class LLVM_LIBRARY_VISIBILITY CygwinX86_32TargetInfo : public X86_32TargetInfo { |
628 | | public: |
629 | | CygwinX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
630 | 0 | : X86_32TargetInfo(Triple, Opts) { |
631 | 0 | this->WCharType = TargetInfo::UnsignedShort; |
632 | 0 | DoubleAlign = LongLongAlign = 64; |
633 | 0 | resetDataLayout("e-m:x-p:32:32-p270:32:32-p271:32:32-p272:64:64-i64:64-" |
634 | 0 | "i128:128-f80:32-n8:16:32-a:0:32-S32", |
635 | 0 | "_"); |
636 | 0 | } |
637 | | |
638 | | void getTargetDefines(const LangOptions &Opts, |
639 | 0 | MacroBuilder &Builder) const override { |
640 | 0 | X86_32TargetInfo::getTargetDefines(Opts, Builder); |
641 | 0 | Builder.defineMacro("_X86_"); |
642 | 0 | Builder.defineMacro("__CYGWIN__"); |
643 | 0 | Builder.defineMacro("__CYGWIN32__"); |
644 | 0 | addCygMingDefines(Opts, Builder); |
645 | 0 | DefineStd(Builder, "unix", Opts); |
646 | 0 | if (Opts.CPlusPlus) |
647 | 0 | Builder.defineMacro("_GNU_SOURCE"); |
648 | 0 | } |
649 | | }; |
650 | | |
651 | | // x86-32 Haiku target |
652 | | class LLVM_LIBRARY_VISIBILITY HaikuX86_32TargetInfo |
653 | | : public HaikuTargetInfo<X86_32TargetInfo> { |
654 | | public: |
655 | | HaikuX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
656 | 0 | : HaikuTargetInfo<X86_32TargetInfo>(Triple, Opts) {} |
657 | | |
658 | | void getTargetDefines(const LangOptions &Opts, |
659 | 0 | MacroBuilder &Builder) const override { |
660 | 0 | HaikuTargetInfo<X86_32TargetInfo>::getTargetDefines(Opts, Builder); |
661 | 0 | Builder.defineMacro("__INTEL__"); |
662 | 0 | } |
663 | | }; |
664 | | |
665 | | // X86-32 MCU target |
666 | | class LLVM_LIBRARY_VISIBILITY MCUX86_32TargetInfo : public X86_32TargetInfo { |
667 | | public: |
668 | | MCUX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
669 | 0 | : X86_32TargetInfo(Triple, Opts) { |
670 | 0 | LongDoubleWidth = 64; |
671 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEdouble(); |
672 | 0 | resetDataLayout("e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-i64:32-" |
673 | 0 | "f64:32-f128:32-n8:16:32-a:0:32-S32"); |
674 | 0 | WIntType = UnsignedInt; |
675 | 0 | } |
676 | | |
677 | 0 | CallingConvCheckResult checkCallingConvention(CallingConv CC) const override { |
678 | | // On MCU we support only C calling convention. |
679 | 0 | return CC == CC_C ? CCCR_OK : CCCR_Warning; |
680 | 0 | } |
681 | | |
682 | | void getTargetDefines(const LangOptions &Opts, |
683 | 0 | MacroBuilder &Builder) const override { |
684 | 0 | X86_32TargetInfo::getTargetDefines(Opts, Builder); |
685 | 0 | Builder.defineMacro("__iamcu"); |
686 | 0 | Builder.defineMacro("__iamcu__"); |
687 | 0 | } |
688 | | |
689 | 0 | bool allowsLargerPreferedTypeAlignment() const override { return false; } |
690 | | }; |
691 | | |
692 | | // x86-32 RTEMS target |
693 | | class LLVM_LIBRARY_VISIBILITY RTEMSX86_32TargetInfo : public X86_32TargetInfo { |
694 | | public: |
695 | | RTEMSX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
696 | 0 | : X86_32TargetInfo(Triple, Opts) { |
697 | 0 | SizeType = UnsignedLong; |
698 | 0 | IntPtrType = SignedLong; |
699 | 0 | PtrDiffType = SignedLong; |
700 | 0 | } |
701 | | |
702 | | void getTargetDefines(const LangOptions &Opts, |
703 | 0 | MacroBuilder &Builder) const override { |
704 | 0 | X86_32TargetInfo::getTargetDefines(Opts, Builder); |
705 | 0 | Builder.defineMacro("__INTEL__"); |
706 | 0 | Builder.defineMacro("__rtems__"); |
707 | 0 | } |
708 | | }; |
709 | | |
710 | | // x86-64 generic target |
711 | | class LLVM_LIBRARY_VISIBILITY X86_64TargetInfo : public X86TargetInfo { |
712 | | public: |
713 | | X86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
714 | 46 | : X86TargetInfo(Triple, Opts) { |
715 | 46 | const bool IsX32 = getTriple().isX32(); |
716 | 46 | bool IsWinCOFF = |
717 | 46 | getTriple().isOSWindows() && getTriple().isOSBinFormatCOFF(); |
718 | 46 | LongWidth = LongAlign = PointerWidth = PointerAlign = IsX32 ? 32 : 64; |
719 | 46 | LongDoubleWidth = 128; |
720 | 46 | LongDoubleAlign = 128; |
721 | 46 | LargeArrayMinWidth = 128; |
722 | 46 | LargeArrayAlign = 128; |
723 | 46 | SuitableAlign = 128; |
724 | 46 | SizeType = IsX32 ? UnsignedInt : UnsignedLong; |
725 | 46 | PtrDiffType = IsX32 ? SignedInt : SignedLong; |
726 | 46 | IntPtrType = IsX32 ? SignedInt : SignedLong; |
727 | 46 | IntMaxType = IsX32 ? SignedLongLong : SignedLong; |
728 | 46 | Int64Type = IsX32 ? SignedLongLong : SignedLong; |
729 | 46 | RegParmMax = 6; |
730 | | |
731 | | // Pointers are 32-bit in x32. |
732 | 46 | resetDataLayout(IsX32 ? "e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-" |
733 | 0 | "i64:64-i128:128-f80:128-n8:16:32:64-S128" |
734 | 46 | : IsWinCOFF ? "e-m:w-p270:32:32-p271:32:32-p272:64:64-i64:" |
735 | 0 | "64-i128:128-f80:128-n8:16:32:64-S128" |
736 | 46 | : "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:" |
737 | 46 | "64-i128:128-f80:128-n8:16:32:64-S128"); |
738 | | |
739 | | // Use fpret only for long double. |
740 | 46 | RealTypeUsesObjCFPRetMask = (unsigned)FloatModeKind::LongDouble; |
741 | | |
742 | | // Use fp2ret for _Complex long double. |
743 | 46 | ComplexLongDoubleUsesFP2Ret = true; |
744 | | |
745 | | // Make __builtin_ms_va_list available. |
746 | 46 | HasBuiltinMSVaList = true; |
747 | | |
748 | | // x86-64 has atomics up to 16 bytes. |
749 | 46 | MaxAtomicPromoteWidth = 128; |
750 | 46 | MaxAtomicInlineWidth = 64; |
751 | 46 | } |
752 | | |
753 | 46 | BuiltinVaListKind getBuiltinVaListKind() const override { |
754 | 46 | return TargetInfo::X86_64ABIBuiltinVaList; |
755 | 46 | } |
756 | | |
757 | 0 | int getEHDataRegisterNumber(unsigned RegNo) const override { |
758 | 0 | if (RegNo == 0) |
759 | 0 | return 0; |
760 | 0 | if (RegNo == 1) |
761 | 0 | return 1; |
762 | 0 | return -1; |
763 | 0 | } |
764 | | |
765 | 0 | CallingConvCheckResult checkCallingConvention(CallingConv CC) const override { |
766 | 0 | switch (CC) { |
767 | 0 | case CC_C: |
768 | 0 | case CC_Swift: |
769 | 0 | case CC_SwiftAsync: |
770 | 0 | case CC_X86VectorCall: |
771 | 0 | case CC_IntelOclBicc: |
772 | 0 | case CC_Win64: |
773 | 0 | case CC_PreserveMost: |
774 | 0 | case CC_PreserveAll: |
775 | 0 | case CC_X86RegCall: |
776 | 0 | case CC_OpenCLKernel: |
777 | 0 | return CCCR_OK; |
778 | 0 | default: |
779 | 0 | return CCCR_Warning; |
780 | 0 | } |
781 | 0 | } |
782 | | |
783 | 24 | CallingConv getDefaultCallingConv() const override { |
784 | 24 | return CC_C; |
785 | 24 | } |
786 | | |
787 | | // for x32 we need it here explicitly |
788 | 138 | bool hasInt128Type() const override { return true; } |
789 | | |
790 | 0 | unsigned getUnwindWordWidth() const override { return 64; } |
791 | | |
792 | 0 | unsigned getRegisterWidth() const override { return 64; } |
793 | | |
794 | | bool validateGlobalRegisterVariable(StringRef RegName, unsigned RegSize, |
795 | 0 | bool &HasSizeMismatch) const override { |
796 | | // rsp and rbp are the only 64-bit registers the x86 backend can currently |
797 | | // handle. |
798 | 0 | if (RegName.equals("rsp") || RegName.equals("rbp")) { |
799 | | // Check that the register size is 64-bit. |
800 | 0 | HasSizeMismatch = RegSize != 64; |
801 | 0 | return true; |
802 | 0 | } |
803 | | |
804 | | // Check if the register is a 32-bit register the backend can handle. |
805 | 0 | return X86TargetInfo::validateGlobalRegisterVariable(RegName, RegSize, |
806 | 0 | HasSizeMismatch); |
807 | 0 | } |
808 | | |
809 | 46 | void setMaxAtomicWidth() override { |
810 | 46 | if (hasFeature("cx16")) |
811 | 0 | MaxAtomicInlineWidth = 128; |
812 | 46 | } |
813 | | |
814 | | ArrayRef<Builtin::Info> getTargetBuiltins() const override; |
815 | | |
816 | 0 | bool hasBitIntType() const override { return true; } |
817 | 46 | size_t getMaxBitIntWidth() const override { |
818 | 46 | return llvm::IntegerType::MAX_INT_BITS; |
819 | 46 | } |
820 | | }; |
821 | | |
822 | | // x86-64 Windows target |
823 | | class LLVM_LIBRARY_VISIBILITY WindowsX86_64TargetInfo |
824 | | : public WindowsTargetInfo<X86_64TargetInfo> { |
825 | | public: |
826 | | WindowsX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
827 | 0 | : WindowsTargetInfo<X86_64TargetInfo>(Triple, Opts) { |
828 | 0 | LongWidth = LongAlign = 32; |
829 | 0 | DoubleAlign = LongLongAlign = 64; |
830 | 0 | IntMaxType = SignedLongLong; |
831 | 0 | Int64Type = SignedLongLong; |
832 | 0 | SizeType = UnsignedLongLong; |
833 | 0 | PtrDiffType = SignedLongLong; |
834 | 0 | IntPtrType = SignedLongLong; |
835 | 0 | } |
836 | | |
837 | 0 | BuiltinVaListKind getBuiltinVaListKind() const override { |
838 | 0 | return TargetInfo::CharPtrBuiltinVaList; |
839 | 0 | } |
840 | | |
841 | 0 | CallingConvCheckResult checkCallingConvention(CallingConv CC) const override { |
842 | 0 | switch (CC) { |
843 | 0 | case CC_X86StdCall: |
844 | 0 | case CC_X86ThisCall: |
845 | 0 | case CC_X86FastCall: |
846 | 0 | return CCCR_Ignore; |
847 | 0 | case CC_C: |
848 | 0 | case CC_X86VectorCall: |
849 | 0 | case CC_IntelOclBicc: |
850 | 0 | case CC_PreserveMost: |
851 | 0 | case CC_PreserveAll: |
852 | 0 | case CC_X86_64SysV: |
853 | 0 | case CC_Swift: |
854 | 0 | case CC_SwiftAsync: |
855 | 0 | case CC_X86RegCall: |
856 | 0 | case CC_OpenCLKernel: |
857 | 0 | return CCCR_OK; |
858 | 0 | default: |
859 | 0 | return CCCR_Warning; |
860 | 0 | } |
861 | 0 | } |
862 | | }; |
863 | | |
864 | | // x86-64 Windows Visual Studio target |
865 | | class LLVM_LIBRARY_VISIBILITY MicrosoftX86_64TargetInfo |
866 | | : public WindowsX86_64TargetInfo { |
867 | | public: |
868 | | MicrosoftX86_64TargetInfo(const llvm::Triple &Triple, |
869 | | const TargetOptions &Opts) |
870 | 0 | : WindowsX86_64TargetInfo(Triple, Opts) { |
871 | 0 | LongDoubleWidth = LongDoubleAlign = 64; |
872 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEdouble(); |
873 | 0 | } |
874 | | |
875 | | void getTargetDefines(const LangOptions &Opts, |
876 | 0 | MacroBuilder &Builder) const override { |
877 | 0 | WindowsX86_64TargetInfo::getTargetDefines(Opts, Builder); |
878 | 0 | Builder.defineMacro("_M_X64", "100"); |
879 | 0 | Builder.defineMacro("_M_AMD64", "100"); |
880 | 0 | } |
881 | | |
882 | | TargetInfo::CallingConvKind |
883 | 0 | getCallingConvKind(bool ClangABICompat4) const override { |
884 | 0 | return CCK_MicrosoftWin64; |
885 | 0 | } |
886 | | }; |
887 | | |
888 | | // x86-64 MinGW target |
889 | | class LLVM_LIBRARY_VISIBILITY MinGWX86_64TargetInfo |
890 | | : public WindowsX86_64TargetInfo { |
891 | | public: |
892 | | MinGWX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
893 | 0 | : WindowsX86_64TargetInfo(Triple, Opts) { |
894 | | // Mingw64 rounds long double size and alignment up to 16 bytes, but sticks |
895 | | // with x86 FP ops. Weird. |
896 | 0 | LongDoubleWidth = LongDoubleAlign = 128; |
897 | 0 | LongDoubleFormat = &llvm::APFloat::x87DoubleExtended(); |
898 | 0 | HasFloat128 = true; |
899 | 0 | } |
900 | | }; |
901 | | |
902 | | // x86-64 Cygwin target |
903 | | class LLVM_LIBRARY_VISIBILITY CygwinX86_64TargetInfo : public X86_64TargetInfo { |
904 | | public: |
905 | | CygwinX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
906 | 0 | : X86_64TargetInfo(Triple, Opts) { |
907 | 0 | this->WCharType = TargetInfo::UnsignedShort; |
908 | 0 | TLSSupported = false; |
909 | 0 | } |
910 | | |
911 | | void getTargetDefines(const LangOptions &Opts, |
912 | 0 | MacroBuilder &Builder) const override { |
913 | 0 | X86_64TargetInfo::getTargetDefines(Opts, Builder); |
914 | 0 | Builder.defineMacro("__x86_64__"); |
915 | 0 | Builder.defineMacro("__CYGWIN__"); |
916 | 0 | Builder.defineMacro("__CYGWIN64__"); |
917 | 0 | addCygMingDefines(Opts, Builder); |
918 | 0 | DefineStd(Builder, "unix", Opts); |
919 | 0 | if (Opts.CPlusPlus) |
920 | 0 | Builder.defineMacro("_GNU_SOURCE"); |
921 | 0 | } |
922 | | }; |
923 | | |
924 | | class LLVM_LIBRARY_VISIBILITY DarwinX86_64TargetInfo |
925 | | : public DarwinTargetInfo<X86_64TargetInfo> { |
926 | | public: |
927 | | DarwinX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
928 | 0 | : DarwinTargetInfo<X86_64TargetInfo>(Triple, Opts) { |
929 | 0 | Int64Type = SignedLongLong; |
930 | | // The 64-bit iOS simulator uses the builtin bool type for Objective-C. |
931 | 0 | llvm::Triple T = llvm::Triple(Triple); |
932 | 0 | if (T.isiOS()) |
933 | 0 | UseSignedCharForObjCBool = false; |
934 | 0 | resetDataLayout("e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-" |
935 | 0 | "f80:128-n8:16:32:64-S128", |
936 | 0 | "_"); |
937 | 0 | } |
938 | | |
939 | | bool handleTargetFeatures(std::vector<std::string> &Features, |
940 | 0 | DiagnosticsEngine &Diags) override { |
941 | 0 | if (!DarwinTargetInfo<X86_64TargetInfo>::handleTargetFeatures(Features, |
942 | 0 | Diags)) |
943 | 0 | return false; |
944 | | // We now know the features we have: we can decide how to align vectors. |
945 | 0 | MaxVectorAlign = |
946 | 0 | hasFeature("avx512f") ? 512 : hasFeature("avx") ? 256 : 128; |
947 | 0 | return true; |
948 | 0 | } |
949 | | }; |
950 | | |
951 | | class LLVM_LIBRARY_VISIBILITY OpenBSDX86_64TargetInfo |
952 | | : public OpenBSDTargetInfo<X86_64TargetInfo> { |
953 | | public: |
954 | | OpenBSDX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
955 | 0 | : OpenBSDTargetInfo<X86_64TargetInfo>(Triple, Opts) { |
956 | 0 | IntMaxType = SignedLongLong; |
957 | 0 | Int64Type = SignedLongLong; |
958 | 0 | } |
959 | | }; |
960 | | |
961 | | // x86_32 Android target |
962 | | class LLVM_LIBRARY_VISIBILITY AndroidX86_32TargetInfo |
963 | | : public LinuxTargetInfo<X86_32TargetInfo> { |
964 | | public: |
965 | | AndroidX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
966 | 0 | : LinuxTargetInfo<X86_32TargetInfo>(Triple, Opts) { |
967 | 0 | SuitableAlign = 32; |
968 | 0 | LongDoubleWidth = 64; |
969 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEdouble(); |
970 | 0 | } |
971 | | }; |
972 | | |
973 | | // x86_64 Android target |
974 | | class LLVM_LIBRARY_VISIBILITY AndroidX86_64TargetInfo |
975 | | : public LinuxTargetInfo<X86_64TargetInfo> { |
976 | | public: |
977 | | AndroidX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
978 | 0 | : LinuxTargetInfo<X86_64TargetInfo>(Triple, Opts) { |
979 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEquad(); |
980 | 0 | } |
981 | | }; |
982 | | |
983 | | // x86_32 OHOS target |
984 | | class LLVM_LIBRARY_VISIBILITY OHOSX86_32TargetInfo |
985 | | : public OHOSTargetInfo<X86_32TargetInfo> { |
986 | | public: |
987 | | OHOSX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
988 | 0 | : OHOSTargetInfo<X86_32TargetInfo>(Triple, Opts) { |
989 | 0 | SuitableAlign = 32; |
990 | 0 | LongDoubleWidth = 64; |
991 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEdouble(); |
992 | 0 | } |
993 | | }; |
994 | | |
995 | | // x86_64 OHOS target |
996 | | class LLVM_LIBRARY_VISIBILITY OHOSX86_64TargetInfo |
997 | | : public OHOSTargetInfo<X86_64TargetInfo> { |
998 | | public: |
999 | | OHOSX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) |
1000 | 0 | : OHOSTargetInfo<X86_64TargetInfo>(Triple, Opts) { |
1001 | 0 | LongDoubleFormat = &llvm::APFloat::IEEEquad(); |
1002 | 0 | } |
1003 | | }; |
1004 | | } // namespace targets |
1005 | | } // namespace clang |
1006 | | #endif // LLVM_CLANG_LIB_BASIC_TARGETS_X86_H |