Coverage Report

Created: 2024-01-17 10:31

/src/llvm-project/clang/lib/Basic/Targets/X86.cpp
Line
Count
Source (jump to first uncovered line)
1
//===--- X86.cpp - Implement X86 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 X86 TargetInfo objects.
10
//
11
//===----------------------------------------------------------------------===//
12
13
#include "X86.h"
14
#include "clang/Basic/Builtins.h"
15
#include "clang/Basic/Diagnostic.h"
16
#include "clang/Basic/TargetBuiltins.h"
17
#include "llvm/ADT/StringExtras.h"
18
#include "llvm/ADT/StringRef.h"
19
#include "llvm/ADT/StringSwitch.h"
20
#include "llvm/TargetParser/X86TargetParser.h"
21
#include <optional>
22
23
namespace clang {
24
namespace targets {
25
26
static constexpr Builtin::Info BuiltinInfoX86[] = {
27
#define BUILTIN(ID, TYPE, ATTRS)                                               \
28
  {#ID, TYPE, ATTRS, nullptr, HeaderDesc::NO_HEADER, ALL_LANGUAGES},
29
#define TARGET_BUILTIN(ID, TYPE, ATTRS, FEATURE)                               \
30
  {#ID, TYPE, ATTRS, FEATURE, HeaderDesc::NO_HEADER, ALL_LANGUAGES},
31
#define TARGET_HEADER_BUILTIN(ID, TYPE, ATTRS, HEADER, LANGS, FEATURE)         \
32
  {#ID, TYPE, ATTRS, FEATURE, HeaderDesc::HEADER, LANGS},
33
#include "clang/Basic/BuiltinsX86.def"
34
35
#define BUILTIN(ID, TYPE, ATTRS)                                               \
36
  {#ID, TYPE, ATTRS, nullptr, HeaderDesc::NO_HEADER, ALL_LANGUAGES},
37
#define TARGET_BUILTIN(ID, TYPE, ATTRS, FEATURE)                               \
38
  {#ID, TYPE, ATTRS, FEATURE, HeaderDesc::NO_HEADER, ALL_LANGUAGES},
39
#define TARGET_HEADER_BUILTIN(ID, TYPE, ATTRS, HEADER, LANGS, FEATURE)         \
40
  {#ID, TYPE, ATTRS, FEATURE, HeaderDesc::HEADER, LANGS},
41
#include "clang/Basic/BuiltinsX86_64.def"
42
};
43
44
static const char *const GCCRegNames[] = {
45
    "ax",    "dx",    "cx",    "bx",    "si",      "di",    "bp",    "sp",
46
    "st",    "st(1)", "st(2)", "st(3)", "st(4)",   "st(5)", "st(6)", "st(7)",
47
    "argp",  "flags", "fpcr",  "fpsr",  "dirflag", "frame", "xmm0",  "xmm1",
48
    "xmm2",  "xmm3",  "xmm4",  "xmm5",  "xmm6",    "xmm7",  "mm0",   "mm1",
49
    "mm2",   "mm3",   "mm4",   "mm5",   "mm6",     "mm7",   "r8",    "r9",
50
    "r10",   "r11",   "r12",   "r13",   "r14",     "r15",   "xmm8",  "xmm9",
51
    "xmm10", "xmm11", "xmm12", "xmm13", "xmm14",   "xmm15", "ymm0",  "ymm1",
52
    "ymm2",  "ymm3",  "ymm4",  "ymm5",  "ymm6",    "ymm7",  "ymm8",  "ymm9",
53
    "ymm10", "ymm11", "ymm12", "ymm13", "ymm14",   "ymm15", "xmm16", "xmm17",
54
    "xmm18", "xmm19", "xmm20", "xmm21", "xmm22",   "xmm23", "xmm24", "xmm25",
55
    "xmm26", "xmm27", "xmm28", "xmm29", "xmm30",   "xmm31", "ymm16", "ymm17",
56
    "ymm18", "ymm19", "ymm20", "ymm21", "ymm22",   "ymm23", "ymm24", "ymm25",
57
    "ymm26", "ymm27", "ymm28", "ymm29", "ymm30",   "ymm31", "zmm0",  "zmm1",
58
    "zmm2",  "zmm3",  "zmm4",  "zmm5",  "zmm6",    "zmm7",  "zmm8",  "zmm9",
59
    "zmm10", "zmm11", "zmm12", "zmm13", "zmm14",   "zmm15", "zmm16", "zmm17",
60
    "zmm18", "zmm19", "zmm20", "zmm21", "zmm22",   "zmm23", "zmm24", "zmm25",
61
    "zmm26", "zmm27", "zmm28", "zmm29", "zmm30",   "zmm31", "k0",    "k1",
62
    "k2",    "k3",    "k4",    "k5",    "k6",      "k7",
63
    "cr0",   "cr2",   "cr3",   "cr4",   "cr8",
64
    "dr0",   "dr1",   "dr2",   "dr3",   "dr6",     "dr7",
65
    "bnd0",  "bnd1",  "bnd2",  "bnd3",
66
    "tmm0",  "tmm1",  "tmm2",  "tmm3",  "tmm4",    "tmm5",  "tmm6",  "tmm7",
67
};
68
69
const TargetInfo::AddlRegName AddlRegNames[] = {
70
    {{"al", "ah", "eax", "rax"}, 0},
71
    {{"bl", "bh", "ebx", "rbx"}, 3},
72
    {{"cl", "ch", "ecx", "rcx"}, 2},
73
    {{"dl", "dh", "edx", "rdx"}, 1},
74
    {{"esi", "rsi"}, 4},
75
    {{"edi", "rdi"}, 5},
76
    {{"esp", "rsp"}, 7},
77
    {{"ebp", "rbp"}, 6},
78
    {{"r8d", "r8w", "r8b"}, 38},
79
    {{"r9d", "r9w", "r9b"}, 39},
80
    {{"r10d", "r10w", "r10b"}, 40},
81
    {{"r11d", "r11w", "r11b"}, 41},
82
    {{"r12d", "r12w", "r12b"}, 42},
83
    {{"r13d", "r13w", "r13b"}, 43},
84
    {{"r14d", "r14w", "r14b"}, 44},
85
    {{"r15d", "r15w", "r15b"}, 45},
86
};
87
88
} // namespace targets
89
} // namespace clang
90
91
using namespace clang;
92
using namespace clang::targets;
93
94
0
bool X86TargetInfo::setFPMath(StringRef Name) {
95
0
  if (Name == "387") {
96
0
    FPMath = FP_387;
97
0
    return true;
98
0
  }
99
0
  if (Name == "sse") {
100
0
    FPMath = FP_SSE;
101
0
    return true;
102
0
  }
103
0
  return false;
104
0
}
105
106
bool X86TargetInfo::initFeatureMap(
107
    llvm::StringMap<bool> &Features, DiagnosticsEngine &Diags, StringRef CPU,
108
46
    const std::vector<std::string> &FeaturesVec) const {
109
  // FIXME: This *really* should not be here.
110
  // X86_64 always has SSE2.
111
46
  if (getTriple().getArch() == llvm::Triple::x86_64)
112
46
    setFeatureEnabled(Features, "sse2", true);
113
114
46
  using namespace llvm::X86;
115
116
46
  SmallVector<StringRef, 16> CPUFeatures;
117
46
  getFeaturesForCPU(CPU, CPUFeatures);
118
46
  for (auto &F : CPUFeatures)
119
92
    setFeatureEnabled(Features, F, true);
120
121
46
  std::vector<std::string> UpdatedFeaturesVec;
122
46
  std::vector<std::string> UpdatedAVX10FeaturesVec;
123
46
  enum { FE_NOSET = -1, FE_FALSE, FE_TRUE };
124
46
  int HasEVEX512 = FE_NOSET;
125
46
  bool HasAVX512F = Features.lookup("avx512f");
126
46
  bool HasAVX10 = Features.lookup("avx10.1-256");
127
46
  bool HasAVX10_512 = Features.lookup("avx10.1-512");
128
46
  std::string LastAVX10;
129
46
  std::string LastAVX512;
130
46
  for (const auto &Feature : FeaturesVec) {
131
    // Expand general-regs-only to -x86, -mmx and -sse
132
0
    if (Feature == "+general-regs-only") {
133
0
      UpdatedFeaturesVec.push_back("-x87");
134
0
      UpdatedFeaturesVec.push_back("-mmx");
135
0
      UpdatedFeaturesVec.push_back("-sse");
136
0
      continue;
137
0
    }
138
139
0
    if (Feature.substr(1, 6) == "avx10.") {
140
0
      if (Feature[0] == '+') {
141
0
        HasAVX10 = true;
142
0
        if (Feature.substr(Feature.size() - 3, 3) == "512")
143
0
          HasAVX10_512 = true;
144
0
        LastAVX10 = Feature;
145
0
      } else if (HasAVX10 && Feature == "-avx10.1-256") {
146
0
        HasAVX10 = false;
147
0
        HasAVX10_512 = false;
148
0
      } else if (HasAVX10_512 && Feature == "-avx10.1-512") {
149
0
        HasAVX10_512 = false;
150
0
      }
151
      // Postpone AVX10 features handling after AVX512 settled.
152
0
      UpdatedAVX10FeaturesVec.push_back(Feature);
153
0
      continue;
154
0
    } else if (!HasAVX512F && Feature.substr(0, 7) == "+avx512") {
155
0
      HasAVX512F = true;
156
0
      LastAVX512 = Feature;
157
0
    } else if (HasAVX512F && Feature == "-avx512f") {
158
0
      HasAVX512F = false;
159
0
    } else if (HasEVEX512 != FE_TRUE && Feature == "+evex512") {
160
0
      HasEVEX512 = FE_TRUE;
161
0
      continue;
162
0
    } else if (HasEVEX512 != FE_FALSE && Feature == "-evex512") {
163
0
      HasEVEX512 = FE_FALSE;
164
0
      continue;
165
0
    }
166
167
0
    UpdatedFeaturesVec.push_back(Feature);
168
0
  }
169
46
  llvm::append_range(UpdatedFeaturesVec, UpdatedAVX10FeaturesVec);
170
  // HasEVEX512 is a three-states flag. We need to turn it into [+-]evex512
171
  // according to other features.
172
46
  if (HasAVX512F) {
173
0
    UpdatedFeaturesVec.push_back(HasEVEX512 == FE_FALSE ? "-evex512"
174
0
                                                        : "+evex512");
175
0
    if (HasAVX10 && !HasAVX10_512 && HasEVEX512 != FE_FALSE)
176
0
      Diags.Report(diag::warn_invalid_feature_combination)
177
0
          << LastAVX512 + " " + LastAVX10 + "; will be promoted to avx10.1-512";
178
46
  } else if (HasAVX10) {
179
0
    if (HasEVEX512 != FE_NOSET)
180
0
      Diags.Report(diag::warn_invalid_feature_combination)
181
0
          << LastAVX10 + (HasEVEX512 == FE_TRUE ? " +evex512" : " -evex512");
182
0
    UpdatedFeaturesVec.push_back(HasAVX10_512 ? "+evex512" : "-evex512");
183
0
  }
184
185
46
  if (!TargetInfo::initFeatureMap(Features, Diags, CPU, UpdatedFeaturesVec))
186
0
    return false;
187
188
  // Can't do this earlier because we need to be able to explicitly enable
189
  // or disable these features and the things that they depend upon.
190
191
  // Enable popcnt if sse4.2 is enabled and popcnt is not explicitly disabled.
192
46
  auto I = Features.find("sse4.2");
193
46
  if (I != Features.end() && I->getValue() &&
194
46
      !llvm::is_contained(UpdatedFeaturesVec, "-popcnt"))
195
0
    Features["popcnt"] = true;
196
197
  // Additionally, if SSE is enabled and mmx is not explicitly disabled,
198
  // then enable MMX.
199
46
  I = Features.find("sse");
200
46
  if (I != Features.end() && I->getValue() &&
201
46
      !llvm::is_contained(UpdatedFeaturesVec, "-mmx"))
202
46
    Features["mmx"] = true;
203
204
  // Enable xsave if avx is enabled and xsave is not explicitly disabled.
205
46
  I = Features.find("avx");
206
46
  if (I != Features.end() && I->getValue() &&
207
46
      !llvm::is_contained(UpdatedFeaturesVec, "-xsave"))
208
0
    Features["xsave"] = true;
209
210
  // Enable CRC32 if SSE4.2 is enabled and CRC32 is not explicitly disabled.
211
46
  I = Features.find("sse4.2");
212
46
  if (I != Features.end() && I->getValue() &&
213
46
      !llvm::is_contained(UpdatedFeaturesVec, "-crc32"))
214
0
    Features["crc32"] = true;
215
216
46
  return true;
217
46
}
218
219
void X86TargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features,
220
1.88k
                                      StringRef Name, bool Enabled) const {
221
1.88k
  if (Name == "sse4") {
222
    // We can get here via the __target__ attribute since that's not controlled
223
    // via the -msse4/-mno-sse4 command line alias. Handle this the same way
224
    // here - turn on the sse4.2 if enabled, turn off the sse4.1 level if
225
    // disabled.
226
0
    if (Enabled)
227
0
      Name = "sse4.2";
228
0
    else
229
0
      Name = "sse4.1";
230
0
  }
231
232
1.88k
  Features[Name] = Enabled;
233
1.88k
  llvm::X86::updateImpliedFeatures(Name, Enabled, Features);
234
1.88k
}
235
236
/// handleTargetFeatures - Perform initialization based on the user
237
/// configured set of features.
238
bool X86TargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
239
46
                                         DiagnosticsEngine &Diags) {
240
230
  for (const auto &Feature : Features) {
241
230
    if (Feature[0] != '+')
242
0
      continue;
243
244
230
    if (Feature == "+aes") {
245
0
      HasAES = true;
246
230
    } else if (Feature == "+vaes") {
247
0
      HasVAES = true;
248
230
    } else if (Feature == "+pclmul") {
249
0
      HasPCLMUL = true;
250
230
    } else if (Feature == "+vpclmulqdq") {
251
0
      HasVPCLMULQDQ = true;
252
230
    } else if (Feature == "+lzcnt") {
253
0
      HasLZCNT = true;
254
230
    } else if (Feature == "+rdrnd") {
255
0
      HasRDRND = true;
256
230
    } else if (Feature == "+fsgsbase") {
257
0
      HasFSGSBASE = true;
258
230
    } else if (Feature == "+bmi") {
259
0
      HasBMI = true;
260
230
    } else if (Feature == "+bmi2") {
261
0
      HasBMI2 = true;
262
230
    } else if (Feature == "+popcnt") {
263
0
      HasPOPCNT = true;
264
230
    } else if (Feature == "+rtm") {
265
0
      HasRTM = true;
266
230
    } else if (Feature == "+prfchw") {
267
0
      HasPRFCHW = true;
268
230
    } else if (Feature == "+rdseed") {
269
0
      HasRDSEED = true;
270
230
    } else if (Feature == "+adx") {
271
0
      HasADX = true;
272
230
    } else if (Feature == "+tbm") {
273
0
      HasTBM = true;
274
230
    } else if (Feature == "+lwp") {
275
0
      HasLWP = true;
276
230
    } else if (Feature == "+fma") {
277
0
      HasFMA = true;
278
230
    } else if (Feature == "+f16c") {
279
0
      HasF16C = true;
280
230
    } else if (Feature == "+gfni") {
281
0
      HasGFNI = true;
282
230
    } else if (Feature == "+evex512") {
283
0
      HasEVEX512 = true;
284
230
    } else if (Feature == "+avx10.1-256") {
285
0
      HasAVX10_1 = true;
286
230
    } else if (Feature == "+avx10.1-512") {
287
0
      HasAVX10_1_512 = true;
288
230
    } else if (Feature == "+avx512cd") {
289
0
      HasAVX512CD = true;
290
230
    } else if (Feature == "+avx512vpopcntdq") {
291
0
      HasAVX512VPOPCNTDQ = true;
292
230
    } else if (Feature == "+avx512vnni") {
293
0
      HasAVX512VNNI = true;
294
230
    } else if (Feature == "+avx512bf16") {
295
0
      HasAVX512BF16 = true;
296
230
    } else if (Feature == "+avx512er") {
297
0
      HasAVX512ER = true;
298
0
      Diags.Report(diag::warn_knl_knm_isa_support_removed);
299
230
    } else if (Feature == "+avx512fp16") {
300
0
      HasAVX512FP16 = true;
301
0
      HasLegalHalfType = true;
302
230
    } else if (Feature == "+avx512pf") {
303
0
      HasAVX512PF = true;
304
0
      Diags.Report(diag::warn_knl_knm_isa_support_removed);
305
230
    } else if (Feature == "+avx512dq") {
306
0
      HasAVX512DQ = true;
307
230
    } else if (Feature == "+avx512bitalg") {
308
0
      HasAVX512BITALG = true;
309
230
    } else if (Feature == "+avx512bw") {
310
0
      HasAVX512BW = true;
311
230
    } else if (Feature == "+avx512vl") {
312
0
      HasAVX512VL = true;
313
230
    } else if (Feature == "+avx512vbmi") {
314
0
      HasAVX512VBMI = true;
315
230
    } else if (Feature == "+avx512vbmi2") {
316
0
      HasAVX512VBMI2 = true;
317
230
    } else if (Feature == "+avx512ifma") {
318
0
      HasAVX512IFMA = true;
319
230
    } else if (Feature == "+avx512vp2intersect") {
320
0
      HasAVX512VP2INTERSECT = true;
321
230
    } else if (Feature == "+sha") {
322
0
      HasSHA = true;
323
230
    } else if (Feature == "+sha512") {
324
0
      HasSHA512 = true;
325
230
    } else if (Feature == "+shstk") {
326
0
      HasSHSTK = true;
327
230
    } else if (Feature == "+sm3") {
328
0
      HasSM3 = true;
329
230
    } else if (Feature == "+sm4") {
330
0
      HasSM4 = true;
331
230
    } else if (Feature == "+movbe") {
332
0
      HasMOVBE = true;
333
230
    } else if (Feature == "+sgx") {
334
0
      HasSGX = true;
335
230
    } else if (Feature == "+cx8") {
336
46
      HasCX8 = true;
337
184
    } else if (Feature == "+cx16") {
338
0
      HasCX16 = true;
339
184
    } else if (Feature == "+fxsr") {
340
0
      HasFXSR = true;
341
184
    } else if (Feature == "+xsave") {
342
0
      HasXSAVE = true;
343
184
    } else if (Feature == "+xsaveopt") {
344
0
      HasXSAVEOPT = true;
345
184
    } else if (Feature == "+xsavec") {
346
0
      HasXSAVEC = true;
347
184
    } else if (Feature == "+xsaves") {
348
0
      HasXSAVES = true;
349
184
    } else if (Feature == "+mwaitx") {
350
0
      HasMWAITX = true;
351
184
    } else if (Feature == "+pku") {
352
0
      HasPKU = true;
353
184
    } else if (Feature == "+clflushopt") {
354
0
      HasCLFLUSHOPT = true;
355
184
    } else if (Feature == "+clwb") {
356
0
      HasCLWB = true;
357
184
    } else if (Feature == "+wbnoinvd") {
358
0
      HasWBNOINVD = true;
359
184
    } else if (Feature == "+prefetchi") {
360
0
      HasPREFETCHI = true;
361
184
    } else if (Feature == "+prefetchwt1") {
362
0
      HasPREFETCHWT1 = true;
363
0
      Diags.Report(diag::warn_knl_knm_isa_support_removed);
364
184
    } else if (Feature == "+clzero") {
365
0
      HasCLZERO = true;
366
184
    } else if (Feature == "+cldemote") {
367
0
      HasCLDEMOTE = true;
368
184
    } else if (Feature == "+rdpid") {
369
0
      HasRDPID = true;
370
184
    } else if (Feature == "+rdpru") {
371
0
      HasRDPRU = true;
372
184
    } else if (Feature == "+kl") {
373
0
      HasKL = true;
374
184
    } else if (Feature == "+widekl") {
375
0
      HasWIDEKL = true;
376
184
    } else if (Feature == "+retpoline-external-thunk") {
377
0
      HasRetpolineExternalThunk = true;
378
184
    } else if (Feature == "+sahf") {
379
0
      HasLAHFSAHF = true;
380
184
    } else if (Feature == "+waitpkg") {
381
0
      HasWAITPKG = true;
382
184
    } else if (Feature == "+movdiri") {
383
0
      HasMOVDIRI = true;
384
184
    } else if (Feature == "+movdir64b") {
385
0
      HasMOVDIR64B = true;
386
184
    } else if (Feature == "+pconfig") {
387
0
      HasPCONFIG = true;
388
184
    } else if (Feature == "+ptwrite") {
389
0
      HasPTWRITE = true;
390
184
    } else if (Feature == "+invpcid") {
391
0
      HasINVPCID = true;
392
184
    } else if (Feature == "+enqcmd") {
393
0
      HasENQCMD = true;
394
184
    } else if (Feature == "+hreset") {
395
0
      HasHRESET = true;
396
184
    } else if (Feature == "+amx-bf16") {
397
0
      HasAMXBF16 = true;
398
184
    } else if (Feature == "+amx-fp16") {
399
0
      HasAMXFP16 = true;
400
184
    } else if (Feature == "+amx-int8") {
401
0
      HasAMXINT8 = true;
402
184
    } else if (Feature == "+amx-tile") {
403
0
      HasAMXTILE = true;
404
184
    } else if (Feature == "+amx-complex") {
405
0
      HasAMXCOMPLEX = true;
406
184
    } else if (Feature == "+cmpccxadd") {
407
0
      HasCMPCCXADD = true;
408
184
    } else if (Feature == "+raoint") {
409
0
      HasRAOINT = true;
410
184
    } else if (Feature == "+avxifma") {
411
0
      HasAVXIFMA = true;
412
184
    } else if (Feature == "+avxneconvert") {
413
0
      HasAVXNECONVERT= true;
414
184
    } else if (Feature == "+avxvnni") {
415
0
      HasAVXVNNI = true;
416
184
    } else if (Feature == "+avxvnniint16") {
417
0
      HasAVXVNNIINT16 = true;
418
184
    } else if (Feature == "+avxvnniint8") {
419
0
      HasAVXVNNIINT8 = true;
420
184
    } else if (Feature == "+serialize") {
421
0
      HasSERIALIZE = true;
422
184
    } else if (Feature == "+tsxldtrk") {
423
0
      HasTSXLDTRK = true;
424
184
    } else if (Feature == "+uintr") {
425
0
      HasUINTR = true;
426
184
    } else if (Feature == "+usermsr") {
427
0
      HasUSERMSR = true;
428
184
    } else if (Feature == "+crc32") {
429
0
      HasCRC32 = true;
430
184
    } else if (Feature == "+x87") {
431
46
      HasX87 = true;
432
138
    } else if (Feature == "+fullbf16") {
433
0
      HasFullBFloat16 = true;
434
138
    } else if (Feature == "+egpr") {
435
0
      HasEGPR = true;
436
138
    } else if (Feature == "+push2pop2") {
437
0
      HasPush2Pop2 = true;
438
138
    } else if (Feature == "+ppx") {
439
0
      HasPPX = true;
440
138
    } else if (Feature == "+ndd") {
441
0
      HasNDD = true;
442
138
    } else if (Feature == "+ccmp") {
443
0
      HasCCMP = true;
444
138
    } else if (Feature == "+cf") {
445
0
      HasCF = true;
446
0
    }
447
448
230
    X86SSEEnum Level = llvm::StringSwitch<X86SSEEnum>(Feature)
449
230
                           .Case("+avx512f", AVX512F)
450
230
                           .Case("+avx2", AVX2)
451
230
                           .Case("+avx", AVX)
452
230
                           .Case("+sse4.2", SSE42)
453
230
                           .Case("+sse4.1", SSE41)
454
230
                           .Case("+ssse3", SSSE3)
455
230
                           .Case("+sse3", SSE3)
456
230
                           .Case("+sse2", SSE2)
457
230
                           .Case("+sse", SSE1)
458
230
                           .Default(NoSSE);
459
230
    SSELevel = std::max(SSELevel, Level);
460
461
230
    HasFloat16 = SSELevel >= SSE2;
462
463
    // X86 target has bfloat16 emulation support in the backend, where
464
    // bfloat16 is treated as a 32-bit float, arithmetic operations are
465
    // performed in 32-bit, and the result is converted back to bfloat16.
466
    // Truncation and extension between bfloat16 and 32-bit float are supported
467
    // by the compiler-rt library. However, native bfloat16 support is currently
468
    // not available in the X86 target. Hence, HasFullBFloat16 will be false
469
    // until native bfloat16 support is available. HasFullBFloat16 is used to
470
    // determine whether to automatically use excess floating point precision
471
    // for bfloat16 arithmetic operations in the front-end.
472
230
    HasBFloat16 = SSELevel >= SSE2;
473
474
230
    MMX3DNowEnum ThreeDNowLevel = llvm::StringSwitch<MMX3DNowEnum>(Feature)
475
230
                                      .Case("+3dnowa", AMD3DNowAthlon)
476
230
                                      .Case("+3dnow", AMD3DNow)
477
230
                                      .Case("+mmx", MMX)
478
230
                                      .Default(NoMMX3DNow);
479
230
    MMX3DNowLevel = std::max(MMX3DNowLevel, ThreeDNowLevel);
480
481
230
    XOPEnum XLevel = llvm::StringSwitch<XOPEnum>(Feature)
482
230
                         .Case("+xop", XOP)
483
230
                         .Case("+fma4", FMA4)
484
230
                         .Case("+sse4a", SSE4A)
485
230
                         .Default(NoXOP);
486
230
    XOPLevel = std::max(XOPLevel, XLevel);
487
230
  }
488
489
  // LLVM doesn't have a separate switch for fpmath, so only accept it if it
490
  // matches the selected sse level.
491
46
  if ((FPMath == FP_SSE && SSELevel < SSE1) ||
492
46
      (FPMath == FP_387 && SSELevel >= SSE1)) {
493
0
    Diags.Report(diag::err_target_unsupported_fpmath)
494
0
        << (FPMath == FP_SSE ? "sse" : "387");
495
0
    return false;
496
0
  }
497
498
  // FIXME: We should allow long double type on 32-bits to match with GCC.
499
  // This requires backend to be able to lower f80 without x87 first.
500
46
  if (!HasX87 && LongDoubleFormat == &llvm::APFloat::x87DoubleExtended())
501
0
    HasLongDouble = false;
502
503
46
  return true;
504
46
}
505
506
/// X86TargetInfo::getTargetDefines - Return the set of the X86-specific macro
507
/// definitions for this particular subtarget.
508
void X86TargetInfo::getTargetDefines(const LangOptions &Opts,
509
46
                                     MacroBuilder &Builder) const {
510
  // Inline assembly supports X86 flag outputs.
511
46
  Builder.defineMacro("__GCC_ASM_FLAG_OUTPUTS__");
512
513
46
  std::string CodeModel = getTargetOpts().CodeModel;
514
46
  if (CodeModel == "default")
515
46
    CodeModel = "small";
516
46
  Builder.defineMacro("__code_model_" + CodeModel + "__");
517
518
  // Target identification.
519
46
  if (getTriple().getArch() == llvm::Triple::x86_64) {
520
46
    Builder.defineMacro("__amd64__");
521
46
    Builder.defineMacro("__amd64");
522
46
    Builder.defineMacro("__x86_64");
523
46
    Builder.defineMacro("__x86_64__");
524
46
    if (getTriple().getArchName() == "x86_64h") {
525
0
      Builder.defineMacro("__x86_64h");
526
0
      Builder.defineMacro("__x86_64h__");
527
0
    }
528
46
  } else {
529
0
    DefineStd(Builder, "i386", Opts);
530
0
  }
531
532
46
  Builder.defineMacro("__SEG_GS");
533
46
  Builder.defineMacro("__SEG_FS");
534
46
  Builder.defineMacro("__seg_gs", "__attribute__((address_space(256)))");
535
46
  Builder.defineMacro("__seg_fs", "__attribute__((address_space(257)))");
536
537
  // Subtarget options.
538
  // FIXME: We are hard-coding the tune parameters based on the CPU, but they
539
  // truly should be based on -mtune options.
540
46
  using namespace llvm::X86;
541
46
  switch (CPU) {
542
46
  case CK_None:
543
46
    break;
544
0
  case CK_i386:
545
    // The rest are coming from the i386 define above.
546
0
    Builder.defineMacro("__tune_i386__");
547
0
    break;
548
0
  case CK_i486:
549
0
  case CK_WinChipC6:
550
0
  case CK_WinChip2:
551
0
  case CK_C3:
552
0
    defineCPUMacros(Builder, "i486");
553
0
    break;
554
0
  case CK_PentiumMMX:
555
0
    Builder.defineMacro("__pentium_mmx__");
556
0
    Builder.defineMacro("__tune_pentium_mmx__");
557
0
    [[fallthrough]];
558
0
  case CK_i586:
559
0
  case CK_Pentium:
560
0
    defineCPUMacros(Builder, "i586");
561
0
    defineCPUMacros(Builder, "pentium");
562
0
    break;
563
0
  case CK_Pentium3:
564
0
  case CK_PentiumM:
565
0
    Builder.defineMacro("__tune_pentium3__");
566
0
    [[fallthrough]];
567
0
  case CK_Pentium2:
568
0
  case CK_C3_2:
569
0
    Builder.defineMacro("__tune_pentium2__");
570
0
    [[fallthrough]];
571
0
  case CK_PentiumPro:
572
0
  case CK_i686:
573
0
    defineCPUMacros(Builder, "i686");
574
0
    defineCPUMacros(Builder, "pentiumpro");
575
0
    break;
576
0
  case CK_Pentium4:
577
0
    defineCPUMacros(Builder, "pentium4");
578
0
    break;
579
0
  case CK_Yonah:
580
0
  case CK_Prescott:
581
0
  case CK_Nocona:
582
0
    defineCPUMacros(Builder, "nocona");
583
0
    break;
584
0
  case CK_Core2:
585
0
  case CK_Penryn:
586
0
    defineCPUMacros(Builder, "core2");
587
0
    break;
588
0
  case CK_Bonnell:
589
0
    defineCPUMacros(Builder, "atom");
590
0
    break;
591
0
  case CK_Silvermont:
592
0
    defineCPUMacros(Builder, "slm");
593
0
    break;
594
0
  case CK_Goldmont:
595
0
    defineCPUMacros(Builder, "goldmont");
596
0
    break;
597
0
  case CK_GoldmontPlus:
598
0
    defineCPUMacros(Builder, "goldmont_plus");
599
0
    break;
600
0
  case CK_Tremont:
601
0
    defineCPUMacros(Builder, "tremont");
602
0
    break;
603
  // Gracemont and later atom-cores use P-core cpu macros.
604
0
  case CK_Gracemont:
605
0
  case CK_Nehalem:
606
0
  case CK_Westmere:
607
0
  case CK_SandyBridge:
608
0
  case CK_IvyBridge:
609
0
  case CK_Haswell:
610
0
  case CK_Broadwell:
611
0
  case CK_SkylakeClient:
612
0
  case CK_SkylakeServer:
613
0
  case CK_Cascadelake:
614
0
  case CK_Cooperlake:
615
0
  case CK_Cannonlake:
616
0
  case CK_IcelakeClient:
617
0
  case CK_Rocketlake:
618
0
  case CK_IcelakeServer:
619
0
  case CK_Tigerlake:
620
0
  case CK_SapphireRapids:
621
0
  case CK_Alderlake:
622
0
  case CK_Raptorlake:
623
0
  case CK_Meteorlake:
624
0
  case CK_Arrowlake:
625
0
  case CK_ArrowlakeS:
626
0
  case CK_Lunarlake:
627
0
  case CK_Pantherlake:
628
0
  case CK_Sierraforest:
629
0
  case CK_Grandridge:
630
0
  case CK_Graniterapids:
631
0
  case CK_GraniterapidsD:
632
0
  case CK_Emeraldrapids:
633
0
  case CK_Clearwaterforest:
634
    // FIXME: Historically, we defined this legacy name, it would be nice to
635
    // remove it at some point. We've never exposed fine-grained names for
636
    // recent primary x86 CPUs, and we should keep it that way.
637
0
    defineCPUMacros(Builder, "corei7");
638
0
    break;
639
0
  case CK_KNL:
640
0
    defineCPUMacros(Builder, "knl");
641
0
    break;
642
0
  case CK_KNM:
643
0
    break;
644
0
  case CK_Lakemont:
645
0
    defineCPUMacros(Builder, "i586", /*Tuning*/false);
646
0
    defineCPUMacros(Builder, "pentium", /*Tuning*/false);
647
0
    Builder.defineMacro("__tune_lakemont__");
648
0
    break;
649
0
  case CK_K6_2:
650
0
    Builder.defineMacro("__k6_2__");
651
0
    Builder.defineMacro("__tune_k6_2__");
652
0
    [[fallthrough]];
653
0
  case CK_K6_3:
654
0
    if (CPU != CK_K6_2) { // In case of fallthrough
655
      // FIXME: GCC may be enabling these in cases where some other k6
656
      // architecture is specified but -m3dnow is explicitly provided. The
657
      // exact semantics need to be determined and emulated here.
658
0
      Builder.defineMacro("__k6_3__");
659
0
      Builder.defineMacro("__tune_k6_3__");
660
0
    }
661
0
    [[fallthrough]];
662
0
  case CK_K6:
663
0
    defineCPUMacros(Builder, "k6");
664
0
    break;
665
0
  case CK_Athlon:
666
0
  case CK_AthlonXP:
667
0
    defineCPUMacros(Builder, "athlon");
668
0
    if (SSELevel != NoSSE) {
669
0
      Builder.defineMacro("__athlon_sse__");
670
0
      Builder.defineMacro("__tune_athlon_sse__");
671
0
    }
672
0
    break;
673
0
  case CK_K8:
674
0
  case CK_K8SSE3:
675
0
  case CK_x86_64:
676
0
    defineCPUMacros(Builder, "k8");
677
0
    break;
678
0
  case CK_x86_64_v2:
679
0
  case CK_x86_64_v3:
680
0
  case CK_x86_64_v4:
681
0
    break;
682
0
  case CK_AMDFAM10:
683
0
    defineCPUMacros(Builder, "amdfam10");
684
0
    break;
685
0
  case CK_BTVER1:
686
0
    defineCPUMacros(Builder, "btver1");
687
0
    break;
688
0
  case CK_BTVER2:
689
0
    defineCPUMacros(Builder, "btver2");
690
0
    break;
691
0
  case CK_BDVER1:
692
0
    defineCPUMacros(Builder, "bdver1");
693
0
    break;
694
0
  case CK_BDVER2:
695
0
    defineCPUMacros(Builder, "bdver2");
696
0
    break;
697
0
  case CK_BDVER3:
698
0
    defineCPUMacros(Builder, "bdver3");
699
0
    break;
700
0
  case CK_BDVER4:
701
0
    defineCPUMacros(Builder, "bdver4");
702
0
    break;
703
0
  case CK_ZNVER1:
704
0
    defineCPUMacros(Builder, "znver1");
705
0
    break;
706
0
  case CK_ZNVER2:
707
0
    defineCPUMacros(Builder, "znver2");
708
0
    break;
709
0
  case CK_ZNVER3:
710
0
    defineCPUMacros(Builder, "znver3");
711
0
    break;
712
0
  case CK_ZNVER4:
713
0
    defineCPUMacros(Builder, "znver4");
714
0
    break;
715
0
  case CK_Geode:
716
0
    defineCPUMacros(Builder, "geode");
717
0
    break;
718
46
  }
719
720
  // Target properties.
721
46
  Builder.defineMacro("__REGISTER_PREFIX__", "");
722
723
  // Define __NO_MATH_INLINES on linux/x86 so that we don't get inline
724
  // functions in glibc header files that use FP Stack inline asm which the
725
  // backend can't deal with (PR879).
726
46
  Builder.defineMacro("__NO_MATH_INLINES");
727
728
46
  if (HasAES)
729
0
    Builder.defineMacro("__AES__");
730
731
46
  if (HasVAES)
732
0
    Builder.defineMacro("__VAES__");
733
734
46
  if (HasPCLMUL)
735
0
    Builder.defineMacro("__PCLMUL__");
736
737
46
  if (HasVPCLMULQDQ)
738
0
    Builder.defineMacro("__VPCLMULQDQ__");
739
740
  // Note, in 32-bit mode, GCC does not define the macro if -mno-sahf. In LLVM,
741
  // the feature flag only applies to 64-bit mode.
742
46
  if (HasLAHFSAHF || getTriple().getArch() == llvm::Triple::x86)
743
0
    Builder.defineMacro("__LAHF_SAHF__");
744
745
46
  if (HasLZCNT)
746
0
    Builder.defineMacro("__LZCNT__");
747
748
46
  if (HasRDRND)
749
0
    Builder.defineMacro("__RDRND__");
750
751
46
  if (HasFSGSBASE)
752
0
    Builder.defineMacro("__FSGSBASE__");
753
754
46
  if (HasBMI)
755
0
    Builder.defineMacro("__BMI__");
756
757
46
  if (HasBMI2)
758
0
    Builder.defineMacro("__BMI2__");
759
760
46
  if (HasPOPCNT)
761
0
    Builder.defineMacro("__POPCNT__");
762
763
46
  if (HasRTM)
764
0
    Builder.defineMacro("__RTM__");
765
766
46
  if (HasPRFCHW)
767
0
    Builder.defineMacro("__PRFCHW__");
768
769
46
  if (HasRDSEED)
770
0
    Builder.defineMacro("__RDSEED__");
771
772
46
  if (HasADX)
773
0
    Builder.defineMacro("__ADX__");
774
775
46
  if (HasTBM)
776
0
    Builder.defineMacro("__TBM__");
777
778
46
  if (HasLWP)
779
0
    Builder.defineMacro("__LWP__");
780
781
46
  if (HasMWAITX)
782
0
    Builder.defineMacro("__MWAITX__");
783
784
46
  if (HasMOVBE)
785
0
    Builder.defineMacro("__MOVBE__");
786
787
46
  switch (XOPLevel) {
788
0
  case XOP:
789
0
    Builder.defineMacro("__XOP__");
790
0
    [[fallthrough]];
791
0
  case FMA4:
792
0
    Builder.defineMacro("__FMA4__");
793
0
    [[fallthrough]];
794
0
  case SSE4A:
795
0
    Builder.defineMacro("__SSE4A__");
796
0
    [[fallthrough]];
797
46
  case NoXOP:
798
46
    break;
799
46
  }
800
801
46
  if (HasFMA)
802
0
    Builder.defineMacro("__FMA__");
803
804
46
  if (HasF16C)
805
0
    Builder.defineMacro("__F16C__");
806
807
46
  if (HasGFNI)
808
0
    Builder.defineMacro("__GFNI__");
809
810
46
  if (HasEVEX512)
811
0
    Builder.defineMacro("__EVEX512__");
812
46
  if (HasAVX10_1)
813
0
    Builder.defineMacro("__AVX10_1__");
814
46
  if (HasAVX10_1_512)
815
0
    Builder.defineMacro("__AVX10_1_512__");
816
46
  if (HasAVX512CD)
817
0
    Builder.defineMacro("__AVX512CD__");
818
46
  if (HasAVX512VPOPCNTDQ)
819
0
    Builder.defineMacro("__AVX512VPOPCNTDQ__");
820
46
  if (HasAVX512VNNI)
821
0
    Builder.defineMacro("__AVX512VNNI__");
822
46
  if (HasAVX512BF16)
823
0
    Builder.defineMacro("__AVX512BF16__");
824
46
  if (HasAVX512ER)
825
0
    Builder.defineMacro("__AVX512ER__");
826
46
  if (HasAVX512FP16)
827
0
    Builder.defineMacro("__AVX512FP16__");
828
46
  if (HasAVX512PF)
829
0
    Builder.defineMacro("__AVX512PF__");
830
46
  if (HasAVX512DQ)
831
0
    Builder.defineMacro("__AVX512DQ__");
832
46
  if (HasAVX512BITALG)
833
0
    Builder.defineMacro("__AVX512BITALG__");
834
46
  if (HasAVX512BW)
835
0
    Builder.defineMacro("__AVX512BW__");
836
46
  if (HasAVX512VL) {
837
0
    Builder.defineMacro("__AVX512VL__");
838
0
    Builder.defineMacro("__EVEX256__");
839
0
  }
840
46
  if (HasAVX512VBMI)
841
0
    Builder.defineMacro("__AVX512VBMI__");
842
46
  if (HasAVX512VBMI2)
843
0
    Builder.defineMacro("__AVX512VBMI2__");
844
46
  if (HasAVX512IFMA)
845
0
    Builder.defineMacro("__AVX512IFMA__");
846
46
  if (HasAVX512VP2INTERSECT)
847
0
    Builder.defineMacro("__AVX512VP2INTERSECT__");
848
46
  if (HasSHA)
849
0
    Builder.defineMacro("__SHA__");
850
46
  if (HasSHA512)
851
0
    Builder.defineMacro("__SHA512__");
852
853
46
  if (HasFXSR)
854
0
    Builder.defineMacro("__FXSR__");
855
46
  if (HasXSAVE)
856
0
    Builder.defineMacro("__XSAVE__");
857
46
  if (HasXSAVEOPT)
858
0
    Builder.defineMacro("__XSAVEOPT__");
859
46
  if (HasXSAVEC)
860
0
    Builder.defineMacro("__XSAVEC__");
861
46
  if (HasXSAVES)
862
0
    Builder.defineMacro("__XSAVES__");
863
46
  if (HasPKU)
864
0
    Builder.defineMacro("__PKU__");
865
46
  if (HasCLFLUSHOPT)
866
0
    Builder.defineMacro("__CLFLUSHOPT__");
867
46
  if (HasCLWB)
868
0
    Builder.defineMacro("__CLWB__");
869
46
  if (HasWBNOINVD)
870
0
    Builder.defineMacro("__WBNOINVD__");
871
46
  if (HasSHSTK)
872
0
    Builder.defineMacro("__SHSTK__");
873
46
  if (HasSGX)
874
0
    Builder.defineMacro("__SGX__");
875
46
  if (HasSM3)
876
0
    Builder.defineMacro("__SM3__");
877
46
  if (HasSM4)
878
0
    Builder.defineMacro("__SM4__");
879
46
  if (HasPREFETCHI)
880
0
    Builder.defineMacro("__PREFETCHI__");
881
46
  if (HasPREFETCHWT1)
882
0
    Builder.defineMacro("__PREFETCHWT1__");
883
46
  if (HasCLZERO)
884
0
    Builder.defineMacro("__CLZERO__");
885
46
  if (HasKL)
886
0
    Builder.defineMacro("__KL__");
887
46
  if (HasWIDEKL)
888
0
    Builder.defineMacro("__WIDEKL__");
889
46
  if (HasRDPID)
890
0
    Builder.defineMacro("__RDPID__");
891
46
  if (HasRDPRU)
892
0
    Builder.defineMacro("__RDPRU__");
893
46
  if (HasCLDEMOTE)
894
0
    Builder.defineMacro("__CLDEMOTE__");
895
46
  if (HasWAITPKG)
896
0
    Builder.defineMacro("__WAITPKG__");
897
46
  if (HasMOVDIRI)
898
0
    Builder.defineMacro("__MOVDIRI__");
899
46
  if (HasMOVDIR64B)
900
0
    Builder.defineMacro("__MOVDIR64B__");
901
46
  if (HasPCONFIG)
902
0
    Builder.defineMacro("__PCONFIG__");
903
46
  if (HasPTWRITE)
904
0
    Builder.defineMacro("__PTWRITE__");
905
46
  if (HasINVPCID)
906
0
    Builder.defineMacro("__INVPCID__");
907
46
  if (HasENQCMD)
908
0
    Builder.defineMacro("__ENQCMD__");
909
46
  if (HasHRESET)
910
0
    Builder.defineMacro("__HRESET__");
911
46
  if (HasAMXTILE)
912
0
    Builder.defineMacro("__AMX_TILE__");
913
46
  if (HasAMXINT8)
914
0
    Builder.defineMacro("__AMX_INT8__");
915
46
  if (HasAMXBF16)
916
0
    Builder.defineMacro("__AMX_BF16__");
917
46
  if (HasAMXFP16)
918
0
    Builder.defineMacro("__AMX_FP16__");
919
46
  if (HasAMXCOMPLEX)
920
0
    Builder.defineMacro("__AMX_COMPLEX__");
921
46
  if (HasCMPCCXADD)
922
0
    Builder.defineMacro("__CMPCCXADD__");
923
46
  if (HasRAOINT)
924
0
    Builder.defineMacro("__RAOINT__");
925
46
  if (HasAVXIFMA)
926
0
    Builder.defineMacro("__AVXIFMA__");
927
46
  if (HasAVXNECONVERT)
928
0
    Builder.defineMacro("__AVXNECONVERT__");
929
46
  if (HasAVXVNNI)
930
0
    Builder.defineMacro("__AVXVNNI__");
931
46
  if (HasAVXVNNIINT16)
932
0
    Builder.defineMacro("__AVXVNNIINT16__");
933
46
  if (HasAVXVNNIINT8)
934
0
    Builder.defineMacro("__AVXVNNIINT8__");
935
46
  if (HasSERIALIZE)
936
0
    Builder.defineMacro("__SERIALIZE__");
937
46
  if (HasTSXLDTRK)
938
0
    Builder.defineMacro("__TSXLDTRK__");
939
46
  if (HasUINTR)
940
0
    Builder.defineMacro("__UINTR__");
941
46
  if (HasUSERMSR)
942
0
    Builder.defineMacro("__USERMSR__");
943
46
  if (HasCRC32)
944
0
    Builder.defineMacro("__CRC32__");
945
46
  if (HasEGPR)
946
0
    Builder.defineMacro("__EGPR__");
947
46
  if (HasPush2Pop2)
948
0
    Builder.defineMacro("__PUSH2POP2__");
949
46
  if (HasPPX)
950
0
    Builder.defineMacro("__PPX__");
951
46
  if (HasNDD)
952
0
    Builder.defineMacro("__NDD__");
953
46
  if (HasCCMP)
954
0
    Builder.defineMacro("__CCMP__");
955
46
  if (HasCF)
956
0
    Builder.defineMacro("__CF__");
957
958
  // Each case falls through to the previous one here.
959
46
  switch (SSELevel) {
960
0
  case AVX512F:
961
0
    Builder.defineMacro("__AVX512F__");
962
0
    [[fallthrough]];
963
0
  case AVX2:
964
0
    Builder.defineMacro("__AVX2__");
965
0
    [[fallthrough]];
966
0
  case AVX:
967
0
    Builder.defineMacro("__AVX__");
968
0
    [[fallthrough]];
969
0
  case SSE42:
970
0
    Builder.defineMacro("__SSE4_2__");
971
0
    [[fallthrough]];
972
0
  case SSE41:
973
0
    Builder.defineMacro("__SSE4_1__");
974
0
    [[fallthrough]];
975
0
  case SSSE3:
976
0
    Builder.defineMacro("__SSSE3__");
977
0
    [[fallthrough]];
978
0
  case SSE3:
979
0
    Builder.defineMacro("__SSE3__");
980
0
    [[fallthrough]];
981
46
  case SSE2:
982
46
    Builder.defineMacro("__SSE2__");
983
46
    Builder.defineMacro("__SSE2_MATH__"); // -mfp-math=sse always implied.
984
46
    [[fallthrough]];
985
46
  case SSE1:
986
46
    Builder.defineMacro("__SSE__");
987
46
    Builder.defineMacro("__SSE_MATH__"); // -mfp-math=sse always implied.
988
46
    [[fallthrough]];
989
46
  case NoSSE:
990
46
    break;
991
46
  }
992
993
46
  if (Opts.MicrosoftExt && getTriple().getArch() == llvm::Triple::x86) {
994
0
    switch (SSELevel) {
995
0
    case AVX512F:
996
0
    case AVX2:
997
0
    case AVX:
998
0
    case SSE42:
999
0
    case SSE41:
1000
0
    case SSSE3:
1001
0
    case SSE3:
1002
0
    case SSE2:
1003
0
      Builder.defineMacro("_M_IX86_FP", Twine(2));
1004
0
      break;
1005
0
    case SSE1:
1006
0
      Builder.defineMacro("_M_IX86_FP", Twine(1));
1007
0
      break;
1008
0
    default:
1009
0
      Builder.defineMacro("_M_IX86_FP", Twine(0));
1010
0
      break;
1011
0
    }
1012
0
  }
1013
1014
  // Each case falls through to the previous one here.
1015
46
  switch (MMX3DNowLevel) {
1016
0
  case AMD3DNowAthlon:
1017
0
    Builder.defineMacro("__3dNOW_A__");
1018
0
    [[fallthrough]];
1019
0
  case AMD3DNow:
1020
0
    Builder.defineMacro("__3dNOW__");
1021
0
    [[fallthrough]];
1022
46
  case MMX:
1023
46
    Builder.defineMacro("__MMX__");
1024
46
    [[fallthrough]];
1025
46
  case NoMMX3DNow:
1026
46
    break;
1027
46
  }
1028
1029
46
  if (CPU >= CK_i486 || CPU == CK_None) {
1030
46
    Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_1");
1031
46
    Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_2");
1032
46
    Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4");
1033
46
  }
1034
46
  if (HasCX8)
1035
46
    Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8");
1036
46
  if (HasCX16 && getTriple().getArch() == llvm::Triple::x86_64)
1037
0
    Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_16");
1038
1039
46
  if (HasFloat128)
1040
46
    Builder.defineMacro("__SIZEOF_FLOAT128__", "16");
1041
46
}
1042
1043
0
bool X86TargetInfo::isValidFeatureName(StringRef Name) const {
1044
0
  return llvm::StringSwitch<bool>(Name)
1045
0
      .Case("3dnow", true)
1046
0
      .Case("3dnowa", true)
1047
0
      .Case("adx", true)
1048
0
      .Case("aes", true)
1049
0
      .Case("amx-bf16", true)
1050
0
      .Case("amx-complex", true)
1051
0
      .Case("amx-fp16", true)
1052
0
      .Case("amx-int8", true)
1053
0
      .Case("amx-tile", true)
1054
0
      .Case("avx", true)
1055
0
      .Case("avx10.1-256", true)
1056
0
      .Case("avx10.1-512", true)
1057
0
      .Case("avx2", true)
1058
0
      .Case("avx512f", true)
1059
0
      .Case("avx512cd", true)
1060
0
      .Case("avx512vpopcntdq", true)
1061
0
      .Case("avx512vnni", true)
1062
0
      .Case("avx512bf16", true)
1063
0
      .Case("avx512er", true)
1064
0
      .Case("avx512fp16", true)
1065
0
      .Case("avx512pf", true)
1066
0
      .Case("avx512dq", true)
1067
0
      .Case("avx512bitalg", true)
1068
0
      .Case("avx512bw", true)
1069
0
      .Case("avx512vl", true)
1070
0
      .Case("avx512vbmi", true)
1071
0
      .Case("avx512vbmi2", true)
1072
0
      .Case("avx512ifma", true)
1073
0
      .Case("avx512vp2intersect", true)
1074
0
      .Case("avxifma", true)
1075
0
      .Case("avxneconvert", true)
1076
0
      .Case("avxvnni", true)
1077
0
      .Case("avxvnniint16", true)
1078
0
      .Case("avxvnniint8", true)
1079
0
      .Case("bmi", true)
1080
0
      .Case("bmi2", true)
1081
0
      .Case("cldemote", true)
1082
0
      .Case("clflushopt", true)
1083
0
      .Case("clwb", true)
1084
0
      .Case("clzero", true)
1085
0
      .Case("cmpccxadd", true)
1086
0
      .Case("crc32", true)
1087
0
      .Case("cx16", true)
1088
0
      .Case("enqcmd", true)
1089
0
      .Case("evex512", true)
1090
0
      .Case("f16c", true)
1091
0
      .Case("fma", true)
1092
0
      .Case("fma4", true)
1093
0
      .Case("fsgsbase", true)
1094
0
      .Case("fxsr", true)
1095
0
      .Case("general-regs-only", true)
1096
0
      .Case("gfni", true)
1097
0
      .Case("hreset", true)
1098
0
      .Case("invpcid", true)
1099
0
      .Case("kl", true)
1100
0
      .Case("widekl", true)
1101
0
      .Case("lwp", true)
1102
0
      .Case("lzcnt", true)
1103
0
      .Case("mmx", true)
1104
0
      .Case("movbe", true)
1105
0
      .Case("movdiri", true)
1106
0
      .Case("movdir64b", true)
1107
0
      .Case("mwaitx", true)
1108
0
      .Case("pclmul", true)
1109
0
      .Case("pconfig", true)
1110
0
      .Case("pku", true)
1111
0
      .Case("popcnt", true)
1112
0
      .Case("prefetchi", true)
1113
0
      .Case("prefetchwt1", true)
1114
0
      .Case("prfchw", true)
1115
0
      .Case("ptwrite", true)
1116
0
      .Case("raoint", true)
1117
0
      .Case("rdpid", true)
1118
0
      .Case("rdpru", true)
1119
0
      .Case("rdrnd", true)
1120
0
      .Case("rdseed", true)
1121
0
      .Case("rtm", true)
1122
0
      .Case("sahf", true)
1123
0
      .Case("serialize", true)
1124
0
      .Case("sgx", true)
1125
0
      .Case("sha", true)
1126
0
      .Case("sha512", true)
1127
0
      .Case("shstk", true)
1128
0
      .Case("sm3", true)
1129
0
      .Case("sm4", true)
1130
0
      .Case("sse", true)
1131
0
      .Case("sse2", true)
1132
0
      .Case("sse3", true)
1133
0
      .Case("ssse3", true)
1134
0
      .Case("sse4", true)
1135
0
      .Case("sse4.1", true)
1136
0
      .Case("sse4.2", true)
1137
0
      .Case("sse4a", true)
1138
0
      .Case("tbm", true)
1139
0
      .Case("tsxldtrk", true)
1140
0
      .Case("uintr", true)
1141
0
      .Case("usermsr", true)
1142
0
      .Case("vaes", true)
1143
0
      .Case("vpclmulqdq", true)
1144
0
      .Case("wbnoinvd", true)
1145
0
      .Case("waitpkg", true)
1146
0
      .Case("x87", true)
1147
0
      .Case("xop", true)
1148
0
      .Case("xsave", true)
1149
0
      .Case("xsavec", true)
1150
0
      .Case("xsaves", true)
1151
0
      .Case("xsaveopt", true)
1152
0
      .Case("egpr", true)
1153
0
      .Case("push2pop2", true)
1154
0
      .Case("ppx", true)
1155
0
      .Case("ndd", true)
1156
0
      .Case("ccmp", true)
1157
0
      .Case("cf", true)
1158
0
      .Default(false);
1159
0
}
1160
1161
46
bool X86TargetInfo::hasFeature(StringRef Feature) const {
1162
46
  return llvm::StringSwitch<bool>(Feature)
1163
46
      .Case("adx", HasADX)
1164
46
      .Case("aes", HasAES)
1165
46
      .Case("amx-bf16", HasAMXBF16)
1166
46
      .Case("amx-complex", HasAMXCOMPLEX)
1167
46
      .Case("amx-fp16", HasAMXFP16)
1168
46
      .Case("amx-int8", HasAMXINT8)
1169
46
      .Case("amx-tile", HasAMXTILE)
1170
46
      .Case("avx", SSELevel >= AVX)
1171
46
      .Case("avx10.1-256", HasAVX10_1)
1172
46
      .Case("avx10.1-512", HasAVX10_1_512)
1173
46
      .Case("avx2", SSELevel >= AVX2)
1174
46
      .Case("avx512f", SSELevel >= AVX512F)
1175
46
      .Case("avx512cd", HasAVX512CD)
1176
46
      .Case("avx512vpopcntdq", HasAVX512VPOPCNTDQ)
1177
46
      .Case("avx512vnni", HasAVX512VNNI)
1178
46
      .Case("avx512bf16", HasAVX512BF16)
1179
46
      .Case("avx512er", HasAVX512ER)
1180
46
      .Case("avx512fp16", HasAVX512FP16)
1181
46
      .Case("avx512pf", HasAVX512PF)
1182
46
      .Case("avx512dq", HasAVX512DQ)
1183
46
      .Case("avx512bitalg", HasAVX512BITALG)
1184
46
      .Case("avx512bw", HasAVX512BW)
1185
46
      .Case("avx512vl", HasAVX512VL)
1186
46
      .Case("avx512vbmi", HasAVX512VBMI)
1187
46
      .Case("avx512vbmi2", HasAVX512VBMI2)
1188
46
      .Case("avx512ifma", HasAVX512IFMA)
1189
46
      .Case("avx512vp2intersect", HasAVX512VP2INTERSECT)
1190
46
      .Case("avxifma", HasAVXIFMA)
1191
46
      .Case("avxneconvert", HasAVXNECONVERT)
1192
46
      .Case("avxvnni", HasAVXVNNI)
1193
46
      .Case("avxvnniint16", HasAVXVNNIINT16)
1194
46
      .Case("avxvnniint8", HasAVXVNNIINT8)
1195
46
      .Case("bmi", HasBMI)
1196
46
      .Case("bmi2", HasBMI2)
1197
46
      .Case("cldemote", HasCLDEMOTE)
1198
46
      .Case("clflushopt", HasCLFLUSHOPT)
1199
46
      .Case("clwb", HasCLWB)
1200
46
      .Case("clzero", HasCLZERO)
1201
46
      .Case("cmpccxadd", HasCMPCCXADD)
1202
46
      .Case("crc32", HasCRC32)
1203
46
      .Case("cx8", HasCX8)
1204
46
      .Case("cx16", HasCX16)
1205
46
      .Case("enqcmd", HasENQCMD)
1206
46
      .Case("evex512", HasEVEX512)
1207
46
      .Case("f16c", HasF16C)
1208
46
      .Case("fma", HasFMA)
1209
46
      .Case("fma4", XOPLevel >= FMA4)
1210
46
      .Case("fsgsbase", HasFSGSBASE)
1211
46
      .Case("fxsr", HasFXSR)
1212
46
      .Case("gfni", HasGFNI)
1213
46
      .Case("hreset", HasHRESET)
1214
46
      .Case("invpcid", HasINVPCID)
1215
46
      .Case("kl", HasKL)
1216
46
      .Case("widekl", HasWIDEKL)
1217
46
      .Case("lwp", HasLWP)
1218
46
      .Case("lzcnt", HasLZCNT)
1219
46
      .Case("mm3dnow", MMX3DNowLevel >= AMD3DNow)
1220
46
      .Case("mm3dnowa", MMX3DNowLevel >= AMD3DNowAthlon)
1221
46
      .Case("mmx", MMX3DNowLevel >= MMX)
1222
46
      .Case("movbe", HasMOVBE)
1223
46
      .Case("movdiri", HasMOVDIRI)
1224
46
      .Case("movdir64b", HasMOVDIR64B)
1225
46
      .Case("mwaitx", HasMWAITX)
1226
46
      .Case("pclmul", HasPCLMUL)
1227
46
      .Case("pconfig", HasPCONFIG)
1228
46
      .Case("pku", HasPKU)
1229
46
      .Case("popcnt", HasPOPCNT)
1230
46
      .Case("prefetchi", HasPREFETCHI)
1231
46
      .Case("prefetchwt1", HasPREFETCHWT1)
1232
46
      .Case("prfchw", HasPRFCHW)
1233
46
      .Case("ptwrite", HasPTWRITE)
1234
46
      .Case("raoint", HasRAOINT)
1235
46
      .Case("rdpid", HasRDPID)
1236
46
      .Case("rdpru", HasRDPRU)
1237
46
      .Case("rdrnd", HasRDRND)
1238
46
      .Case("rdseed", HasRDSEED)
1239
46
      .Case("retpoline-external-thunk", HasRetpolineExternalThunk)
1240
46
      .Case("rtm", HasRTM)
1241
46
      .Case("sahf", HasLAHFSAHF)
1242
46
      .Case("serialize", HasSERIALIZE)
1243
46
      .Case("sgx", HasSGX)
1244
46
      .Case("sha", HasSHA)
1245
46
      .Case("sha512", HasSHA512)
1246
46
      .Case("shstk", HasSHSTK)
1247
46
      .Case("sm3", HasSM3)
1248
46
      .Case("sm4", HasSM4)
1249
46
      .Case("sse", SSELevel >= SSE1)
1250
46
      .Case("sse2", SSELevel >= SSE2)
1251
46
      .Case("sse3", SSELevel >= SSE3)
1252
46
      .Case("ssse3", SSELevel >= SSSE3)
1253
46
      .Case("sse4.1", SSELevel >= SSE41)
1254
46
      .Case("sse4.2", SSELevel >= SSE42)
1255
46
      .Case("sse4a", XOPLevel >= SSE4A)
1256
46
      .Case("tbm", HasTBM)
1257
46
      .Case("tsxldtrk", HasTSXLDTRK)
1258
46
      .Case("uintr", HasUINTR)
1259
46
      .Case("usermsr", HasUSERMSR)
1260
46
      .Case("vaes", HasVAES)
1261
46
      .Case("vpclmulqdq", HasVPCLMULQDQ)
1262
46
      .Case("wbnoinvd", HasWBNOINVD)
1263
46
      .Case("waitpkg", HasWAITPKG)
1264
46
      .Case("x86", true)
1265
46
      .Case("x86_32", getTriple().getArch() == llvm::Triple::x86)
1266
46
      .Case("x86_64", getTriple().getArch() == llvm::Triple::x86_64)
1267
46
      .Case("x87", HasX87)
1268
46
      .Case("xop", XOPLevel >= XOP)
1269
46
      .Case("xsave", HasXSAVE)
1270
46
      .Case("xsavec", HasXSAVEC)
1271
46
      .Case("xsaves", HasXSAVES)
1272
46
      .Case("xsaveopt", HasXSAVEOPT)
1273
46
      .Case("fullbf16", HasFullBFloat16)
1274
46
      .Case("egpr", HasEGPR)
1275
46
      .Case("push2pop2", HasPush2Pop2)
1276
46
      .Case("ppx", HasPPX)
1277
46
      .Case("ndd", HasNDD)
1278
46
      .Case("ccmp", HasCCMP)
1279
46
      .Case("cf", HasCF)
1280
46
      .Default(false);
1281
46
}
1282
1283
// We can't use a generic validation scheme for the features accepted here
1284
// versus subtarget features accepted in the target attribute because the
1285
// bitfield structure that's initialized in the runtime only supports the
1286
// below currently rather than the full range of subtarget features. (See
1287
// X86TargetInfo::hasFeature for a somewhat comprehensive list).
1288
0
bool X86TargetInfo::validateCpuSupports(StringRef FeatureStr) const {
1289
0
  return llvm::StringSwitch<bool>(FeatureStr)
1290
0
#define X86_FEATURE_COMPAT(ENUM, STR, PRIORITY) .Case(STR, true)
1291
0
#define X86_MICROARCH_LEVEL(ENUM, STR, PRIORITY) .Case(STR, true)
1292
0
#include "llvm/TargetParser/X86TargetParser.def"
1293
0
      .Default(false);
1294
0
}
1295
1296
0
static llvm::X86::ProcessorFeatures getFeature(StringRef Name) {
1297
0
  return llvm::StringSwitch<llvm::X86::ProcessorFeatures>(Name)
1298
0
#define X86_FEATURE_COMPAT(ENUM, STR, PRIORITY)                                \
1299
0
  .Case(STR, llvm::X86::FEATURE_##ENUM)
1300
1301
0
#include "llvm/TargetParser/X86TargetParser.def"
1302
0
      ;
1303
  // Note, this function should only be used after ensuring the value is
1304
  // correct, so it asserts if the value is out of range.
1305
0
}
1306
1307
0
unsigned X86TargetInfo::multiVersionSortPriority(StringRef Name) const {
1308
  // Valid CPUs have a 'key feature' that compares just better than its key
1309
  // feature.
1310
0
  using namespace llvm::X86;
1311
0
  CPUKind Kind = parseArchX86(Name);
1312
0
  if (Kind != CK_None) {
1313
0
    ProcessorFeatures KeyFeature = getKeyFeature(Kind);
1314
0
    return (getFeaturePriority(KeyFeature) << 1) + 1;
1315
0
  }
1316
1317
  // Now we know we have a feature, so get its priority and shift it a few so
1318
  // that we have sufficient room for the CPUs (above).
1319
0
  return getFeaturePriority(getFeature(Name)) << 1;
1320
0
}
1321
1322
0
bool X86TargetInfo::validateCPUSpecificCPUDispatch(StringRef Name) const {
1323
0
  return llvm::X86::validateCPUSpecificCPUDispatch(Name);
1324
0
}
1325
1326
0
char X86TargetInfo::CPUSpecificManglingCharacter(StringRef Name) const {
1327
0
  return llvm::X86::getCPUDispatchMangling(Name);
1328
0
}
1329
1330
void X86TargetInfo::getCPUSpecificCPUDispatchFeatures(
1331
0
    StringRef Name, llvm::SmallVectorImpl<StringRef> &Features) const {
1332
0
  SmallVector<StringRef, 32> TargetCPUFeatures;
1333
0
  llvm::X86::getFeaturesForCPU(Name, TargetCPUFeatures, true);
1334
0
  for (auto &F : TargetCPUFeatures)
1335
0
    Features.push_back(F);
1336
0
}
1337
1338
// We can't use a generic validation scheme for the cpus accepted here
1339
// versus subtarget cpus accepted in the target attribute because the
1340
// variables intitialized by the runtime only support the below currently
1341
// rather than the full range of cpus.
1342
0
bool X86TargetInfo::validateCpuIs(StringRef FeatureStr) const {
1343
0
  return llvm::StringSwitch<bool>(FeatureStr)
1344
0
#define X86_VENDOR(ENUM, STRING) .Case(STRING, true)
1345
0
#define X86_CPU_TYPE_ALIAS(ENUM, ALIAS) .Case(ALIAS, true)
1346
0
#define X86_CPU_TYPE(ENUM, STR) .Case(STR, true)
1347
0
#define X86_CPU_SUBTYPE_ALIAS(ENUM, ALIAS) .Case(ALIAS, true)
1348
0
#define X86_CPU_SUBTYPE(ENUM, STR) .Case(STR, true)
1349
0
#include "llvm/TargetParser/X86TargetParser.def"
1350
0
      .Default(false);
1351
0
}
1352
1353
0
static unsigned matchAsmCCConstraint(const char *Name) {
1354
0
  auto RV = llvm::StringSwitch<unsigned>(Name)
1355
0
                .Case("@cca", 4)
1356
0
                .Case("@ccae", 5)
1357
0
                .Case("@ccb", 4)
1358
0
                .Case("@ccbe", 5)
1359
0
                .Case("@ccc", 4)
1360
0
                .Case("@cce", 4)
1361
0
                .Case("@ccz", 4)
1362
0
                .Case("@ccg", 4)
1363
0
                .Case("@ccge", 5)
1364
0
                .Case("@ccl", 4)
1365
0
                .Case("@ccle", 5)
1366
0
                .Case("@ccna", 5)
1367
0
                .Case("@ccnae", 6)
1368
0
                .Case("@ccnb", 5)
1369
0
                .Case("@ccnbe", 6)
1370
0
                .Case("@ccnc", 5)
1371
0
                .Case("@ccne", 5)
1372
0
                .Case("@ccnz", 5)
1373
0
                .Case("@ccng", 5)
1374
0
                .Case("@ccnge", 6)
1375
0
                .Case("@ccnl", 5)
1376
0
                .Case("@ccnle", 6)
1377
0
                .Case("@ccno", 5)
1378
0
                .Case("@ccnp", 5)
1379
0
                .Case("@ccns", 5)
1380
0
                .Case("@cco", 4)
1381
0
                .Case("@ccp", 4)
1382
0
                .Case("@ccs", 4)
1383
0
                .Default(0);
1384
0
  return RV;
1385
0
}
1386
1387
bool X86TargetInfo::validateAsmConstraint(
1388
0
    const char *&Name, TargetInfo::ConstraintInfo &Info) const {
1389
0
  switch (*Name) {
1390
0
  default:
1391
0
    return false;
1392
  // Constant constraints.
1393
0
  case 'e': // 32-bit signed integer constant for use with sign-extending x86_64
1394
            // instructions.
1395
0
  case 'Z': // 32-bit unsigned integer constant for use with zero-extending
1396
            // x86_64 instructions.
1397
0
  case 's':
1398
0
    Info.setRequiresImmediate();
1399
0
    return true;
1400
0
  case 'I':
1401
0
    Info.setRequiresImmediate(0, 31);
1402
0
    return true;
1403
0
  case 'J':
1404
0
    Info.setRequiresImmediate(0, 63);
1405
0
    return true;
1406
0
  case 'K':
1407
0
    Info.setRequiresImmediate(-128, 127);
1408
0
    return true;
1409
0
  case 'L':
1410
0
    Info.setRequiresImmediate({int(0xff), int(0xffff), int(0xffffffff)});
1411
0
    return true;
1412
0
  case 'M':
1413
0
    Info.setRequiresImmediate(0, 3);
1414
0
    return true;
1415
0
  case 'N':
1416
0
    Info.setRequiresImmediate(0, 255);
1417
0
    return true;
1418
0
  case 'O':
1419
0
    Info.setRequiresImmediate(0, 127);
1420
0
    return true;
1421
  // Register constraints.
1422
0
  case 'Y': // 'Y' is the first character for several 2-character constraints.
1423
    // Shift the pointer to the second character of the constraint.
1424
0
    Name++;
1425
0
    switch (*Name) {
1426
0
    default:
1427
0
      return false;
1428
0
    case 'z': // First SSE register.
1429
0
    case '2':
1430
0
    case 't': // Any SSE register, when SSE2 is enabled.
1431
0
    case 'i': // Any SSE register, when SSE2 and inter-unit moves enabled.
1432
0
    case 'm': // Any MMX register, when inter-unit moves enabled.
1433
0
    case 'k': // AVX512 arch mask registers: k1-k7.
1434
0
      Info.setAllowsRegister();
1435
0
      return true;
1436
0
    }
1437
0
  case 'f': // Any x87 floating point stack register.
1438
    // Constraint 'f' cannot be used for output operands.
1439
0
    if (Info.ConstraintStr[0] == '=')
1440
0
      return false;
1441
0
    Info.setAllowsRegister();
1442
0
    return true;
1443
0
  case 'a': // eax.
1444
0
  case 'b': // ebx.
1445
0
  case 'c': // ecx.
1446
0
  case 'd': // edx.
1447
0
  case 'S': // esi.
1448
0
  case 'D': // edi.
1449
0
  case 'A': // edx:eax.
1450
0
  case 't': // Top of floating point stack.
1451
0
  case 'u': // Second from top of floating point stack.
1452
0
  case 'q': // Any register accessible as [r]l: a, b, c, and d.
1453
0
  case 'y': // Any MMX register.
1454
0
  case 'v': // Any {X,Y,Z}MM register (Arch & context dependent)
1455
0
  case 'x': // Any SSE register.
1456
0
  case 'k': // Any AVX512 mask register (same as Yk, additionally allows k0
1457
            // for intermideate k reg operations).
1458
0
  case 'Q': // Any register accessible as [r]h: a, b, c, and d.
1459
0
  case 'R': // "Legacy" registers: ax, bx, cx, dx, di, si, sp, bp.
1460
0
  case 'l': // "Index" registers: any general register that can be used as an
1461
            // index in a base+index memory access.
1462
0
    Info.setAllowsRegister();
1463
0
    return true;
1464
  // Floating point constant constraints.
1465
0
  case 'C': // SSE floating point constant.
1466
0
  case 'G': // x87 floating point constant.
1467
0
    return true;
1468
0
  case '@':
1469
    // CC condition changes.
1470
0
    if (auto Len = matchAsmCCConstraint(Name)) {
1471
0
      Name += Len - 1;
1472
0
      Info.setAllowsRegister();
1473
0
      return true;
1474
0
    }
1475
0
    return false;
1476
0
  }
1477
0
}
1478
1479
// Below is based on the following information:
1480
// +------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
1481
// |           Processor Name           | Cache Line Size (Bytes) |                                                                            Source                                                                            |
1482
// +------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
1483
// | i386                               |                      64 | https://www.intel.com/content/dam/www/public/us/en/documents/manuals/64-ia-32-architectures-optimization-manual.pdf                                          |
1484
// | i486                               |                      16 | "four doublewords" (doubleword = 32 bits, 4 bits * 32 bits = 16 bytes) https://en.wikichip.org/w/images/d/d3/i486_MICROPROCESSOR_HARDWARE_REFERENCE_MANUAL_%281990%29.pdf and http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.126.4216&rep=rep1&type=pdf (page 29) |
1485
// | i586/Pentium MMX                   |                      32 | https://www.7-cpu.com/cpu/P-MMX.html                                                                                                                         |
1486
// | i686/Pentium                       |                      32 | https://www.7-cpu.com/cpu/P6.html                                                                                                                            |
1487
// | Netburst/Pentium4                  |                      64 | https://www.7-cpu.com/cpu/P4-180.html                                                                                                                        |
1488
// | Atom                               |                      64 | https://www.7-cpu.com/cpu/Atom.html                                                                                                                          |
1489
// | Westmere                           |                      64 | https://en.wikichip.org/wiki/intel/microarchitectures/sandy_bridge_(client) "Cache Architecture"                                                             |
1490
// | Sandy Bridge                       |                      64 | https://en.wikipedia.org/wiki/Sandy_Bridge and https://www.7-cpu.com/cpu/SandyBridge.html                                                                    |
1491
// | Ivy Bridge                         |                      64 | https://blog.stuffedcow.net/2013/01/ivb-cache-replacement/ and https://www.7-cpu.com/cpu/IvyBridge.html                                                      |
1492
// | Haswell                            |                      64 | https://www.7-cpu.com/cpu/Haswell.html                                                                                                                       |
1493
// | Broadwell                          |                      64 | https://www.7-cpu.com/cpu/Broadwell.html                                                                                                                     |
1494
// | Skylake (including skylake-avx512) |                      64 | https://www.nas.nasa.gov/hecc/support/kb/skylake-processors_550.html "Cache Hierarchy"                                                                       |
1495
// | Cascade Lake                       |                      64 | https://www.nas.nasa.gov/hecc/support/kb/cascade-lake-processors_579.html "Cache Hierarchy"                                                                  |
1496
// | Skylake                            |                      64 | https://en.wikichip.org/wiki/intel/microarchitectures/kaby_lake "Memory Hierarchy"                                                                           |
1497
// | Ice Lake                           |                      64 | https://www.7-cpu.com/cpu/Ice_Lake.html                                                                                                                      |
1498
// | Knights Landing                    |                      64 | https://software.intel.com/en-us/articles/intel-xeon-phi-processor-7200-family-memory-management-optimizations "The Intel® Xeon Phi™ Processor Architecture" |
1499
// | Knights Mill                       |                      64 | https://software.intel.com/sites/default/files/managed/9e/bc/64-ia-32-architectures-optimization-manual.pdf?countrylabel=Colombia "2.5.5.2 L1 DCache "       |
1500
// +------------------------------------+-------------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------+
1501
0
std::optional<unsigned> X86TargetInfo::getCPUCacheLineSize() const {
1502
0
  using namespace llvm::X86;
1503
0
  switch (CPU) {
1504
    // i386
1505
0
    case CK_i386:
1506
    // i486
1507
0
    case CK_i486:
1508
0
    case CK_WinChipC6:
1509
0
    case CK_WinChip2:
1510
0
    case CK_C3:
1511
    // Lakemont
1512
0
    case CK_Lakemont:
1513
0
      return 16;
1514
1515
    // i586
1516
0
    case CK_i586:
1517
0
    case CK_Pentium:
1518
0
    case CK_PentiumMMX:
1519
    // i686
1520
0
    case CK_PentiumPro:
1521
0
    case CK_i686:
1522
0
    case CK_Pentium2:
1523
0
    case CK_Pentium3:
1524
0
    case CK_PentiumM:
1525
0
    case CK_C3_2:
1526
    // K6
1527
0
    case CK_K6:
1528
0
    case CK_K6_2:
1529
0
    case CK_K6_3:
1530
    // Geode
1531
0
    case CK_Geode:
1532
0
      return 32;
1533
1534
    // Netburst
1535
0
    case CK_Pentium4:
1536
0
    case CK_Prescott:
1537
0
    case CK_Nocona:
1538
    // Atom
1539
0
    case CK_Bonnell:
1540
0
    case CK_Silvermont:
1541
0
    case CK_Goldmont:
1542
0
    case CK_GoldmontPlus:
1543
0
    case CK_Tremont:
1544
0
    case CK_Gracemont:
1545
1546
0
    case CK_Westmere:
1547
0
    case CK_SandyBridge:
1548
0
    case CK_IvyBridge:
1549
0
    case CK_Haswell:
1550
0
    case CK_Broadwell:
1551
0
    case CK_SkylakeClient:
1552
0
    case CK_SkylakeServer:
1553
0
    case CK_Cascadelake:
1554
0
    case CK_Nehalem:
1555
0
    case CK_Cooperlake:
1556
0
    case CK_Cannonlake:
1557
0
    case CK_Tigerlake:
1558
0
    case CK_SapphireRapids:
1559
0
    case CK_IcelakeClient:
1560
0
    case CK_Rocketlake:
1561
0
    case CK_IcelakeServer:
1562
0
    case CK_Alderlake:
1563
0
    case CK_Raptorlake:
1564
0
    case CK_Meteorlake:
1565
0
    case CK_Arrowlake:
1566
0
    case CK_ArrowlakeS:
1567
0
    case CK_Lunarlake:
1568
0
    case CK_Pantherlake:
1569
0
    case CK_Sierraforest:
1570
0
    case CK_Grandridge:
1571
0
    case CK_Graniterapids:
1572
0
    case CK_GraniterapidsD:
1573
0
    case CK_Emeraldrapids:
1574
0
    case CK_Clearwaterforest:
1575
0
    case CK_KNL:
1576
0
    case CK_KNM:
1577
    // K7
1578
0
    case CK_Athlon:
1579
0
    case CK_AthlonXP:
1580
    // K8
1581
0
    case CK_K8:
1582
0
    case CK_K8SSE3:
1583
0
    case CK_AMDFAM10:
1584
    // Bobcat
1585
0
    case CK_BTVER1:
1586
0
    case CK_BTVER2:
1587
    // Bulldozer
1588
0
    case CK_BDVER1:
1589
0
    case CK_BDVER2:
1590
0
    case CK_BDVER3:
1591
0
    case CK_BDVER4:
1592
    // Zen
1593
0
    case CK_ZNVER1:
1594
0
    case CK_ZNVER2:
1595
0
    case CK_ZNVER3:
1596
0
    case CK_ZNVER4:
1597
    // Deprecated
1598
0
    case CK_x86_64:
1599
0
    case CK_x86_64_v2:
1600
0
    case CK_x86_64_v3:
1601
0
    case CK_x86_64_v4:
1602
0
    case CK_Yonah:
1603
0
    case CK_Penryn:
1604
0
    case CK_Core2:
1605
0
      return 64;
1606
1607
    // The following currently have unknown cache line sizes (but they are probably all 64):
1608
    // Core
1609
0
    case CK_None:
1610
0
      return std::nullopt;
1611
0
  }
1612
0
  llvm_unreachable("Unknown CPU kind");
1613
0
}
1614
1615
bool X86TargetInfo::validateOutputSize(const llvm::StringMap<bool> &FeatureMap,
1616
                                       StringRef Constraint,
1617
0
                                       unsigned Size) const {
1618
  // Strip off constraint modifiers.
1619
0
  Constraint = Constraint.ltrim("=+&");
1620
1621
0
  return validateOperandSize(FeatureMap, Constraint, Size);
1622
0
}
1623
1624
bool X86TargetInfo::validateInputSize(const llvm::StringMap<bool> &FeatureMap,
1625
                                      StringRef Constraint,
1626
0
                                      unsigned Size) const {
1627
0
  return validateOperandSize(FeatureMap, Constraint, Size);
1628
0
}
1629
1630
bool X86TargetInfo::validateOperandSize(const llvm::StringMap<bool> &FeatureMap,
1631
                                        StringRef Constraint,
1632
0
                                        unsigned Size) const {
1633
0
  switch (Constraint[0]) {
1634
0
  default:
1635
0
    break;
1636
0
  case 'k':
1637
  // Registers k0-k7 (AVX512) size limit is 64 bit.
1638
0
  case 'y':
1639
0
    return Size <= 64;
1640
0
  case 'f':
1641
0
  case 't':
1642
0
  case 'u':
1643
0
    return Size <= 128;
1644
0
  case 'Y':
1645
    // 'Y' is the first character for several 2-character constraints.
1646
0
    switch (Constraint[1]) {
1647
0
    default:
1648
0
      return false;
1649
0
    case 'm':
1650
      // 'Ym' is synonymous with 'y'.
1651
0
    case 'k':
1652
0
      return Size <= 64;
1653
0
    case 'z':
1654
      // XMM0/YMM/ZMM0
1655
0
      if (hasFeatureEnabled(FeatureMap, "avx512f") &&
1656
0
          hasFeatureEnabled(FeatureMap, "evex512"))
1657
        // ZMM0 can be used if target supports AVX512F and EVEX512 is set.
1658
0
        return Size <= 512U;
1659
0
      else if (hasFeatureEnabled(FeatureMap, "avx"))
1660
        // YMM0 can be used if target supports AVX.
1661
0
        return Size <= 256U;
1662
0
      else if (hasFeatureEnabled(FeatureMap, "sse"))
1663
0
        return Size <= 128U;
1664
0
      return false;
1665
0
    case 'i':
1666
0
    case 't':
1667
0
    case '2':
1668
      // 'Yi','Yt','Y2' are synonymous with 'x' when SSE2 is enabled.
1669
0
      if (SSELevel < SSE2)
1670
0
        return false;
1671
0
      break;
1672
0
    }
1673
0
    break;
1674
0
  case 'v':
1675
0
  case 'x':
1676
0
    if (hasFeatureEnabled(FeatureMap, "avx512f") &&
1677
0
        hasFeatureEnabled(FeatureMap, "evex512"))
1678
      // 512-bit zmm registers can be used if target supports AVX512F and
1679
      // EVEX512 is set.
1680
0
      return Size <= 512U;
1681
0
    else if (hasFeatureEnabled(FeatureMap, "avx"))
1682
      // 256-bit ymm registers can be used if target supports AVX.
1683
0
      return Size <= 256U;
1684
0
    return Size <= 128U;
1685
1686
0
  }
1687
1688
0
  return true;
1689
0
}
1690
1691
0
std::string X86TargetInfo::convertConstraint(const char *&Constraint) const {
1692
0
  switch (*Constraint) {
1693
0
  case '@':
1694
0
    if (auto Len = matchAsmCCConstraint(Constraint)) {
1695
0
      std::string Converted = "{" + std::string(Constraint, Len) + "}";
1696
0
      Constraint += Len - 1;
1697
0
      return Converted;
1698
0
    }
1699
0
    return std::string(1, *Constraint);
1700
0
  case 'a':
1701
0
    return std::string("{ax}");
1702
0
  case 'b':
1703
0
    return std::string("{bx}");
1704
0
  case 'c':
1705
0
    return std::string("{cx}");
1706
0
  case 'd':
1707
0
    return std::string("{dx}");
1708
0
  case 'S':
1709
0
    return std::string("{si}");
1710
0
  case 'D':
1711
0
    return std::string("{di}");
1712
0
  case 'p': // Keep 'p' constraint (address).
1713
0
    return std::string("p");
1714
0
  case 't': // top of floating point stack.
1715
0
    return std::string("{st}");
1716
0
  case 'u':                        // second from top of floating point stack.
1717
0
    return std::string("{st(1)}"); // second from top of floating point stack.
1718
0
  case 'Y':
1719
0
    switch (Constraint[1]) {
1720
0
    default:
1721
      // Break from inner switch and fall through (copy single char),
1722
      // continue parsing after copying the current constraint into
1723
      // the return string.
1724
0
      break;
1725
0
    case 'k':
1726
0
    case 'm':
1727
0
    case 'i':
1728
0
    case 't':
1729
0
    case 'z':
1730
0
    case '2':
1731
      // "^" hints llvm that this is a 2 letter constraint.
1732
      // "Constraint++" is used to promote the string iterator
1733
      // to the next constraint.
1734
0
      return std::string("^") + std::string(Constraint++, 2);
1735
0
    }
1736
0
    [[fallthrough]];
1737
0
  default:
1738
0
    return std::string(1, *Constraint);
1739
0
  }
1740
0
}
1741
1742
0
void X86TargetInfo::fillValidCPUList(SmallVectorImpl<StringRef> &Values) const {
1743
0
  bool Only64Bit = getTriple().getArch() != llvm::Triple::x86;
1744
0
  llvm::X86::fillValidCPUArchList(Values, Only64Bit);
1745
0
}
1746
1747
0
void X86TargetInfo::fillValidTuneCPUList(SmallVectorImpl<StringRef> &Values) const {
1748
0
  llvm::X86::fillValidTuneCPUList(Values);
1749
0
}
1750
1751
0
ArrayRef<const char *> X86TargetInfo::getGCCRegNames() const {
1752
0
  return llvm::ArrayRef(GCCRegNames);
1753
0
}
1754
1755
0
ArrayRef<TargetInfo::AddlRegName> X86TargetInfo::getGCCAddlRegNames() const {
1756
0
  return llvm::ArrayRef(AddlRegNames);
1757
0
}
1758
1759
0
ArrayRef<Builtin::Info> X86_32TargetInfo::getTargetBuiltins() const {
1760
0
  return llvm::ArrayRef(BuiltinInfoX86, clang::X86::LastX86CommonBuiltin -
1761
0
                                            Builtin::FirstTSBuiltin + 1);
1762
0
}
1763
1764
46
ArrayRef<Builtin::Info> X86_64TargetInfo::getTargetBuiltins() const {
1765
46
  return llvm::ArrayRef(BuiltinInfoX86,
1766
46
                        X86::LastTSBuiltin - Builtin::FirstTSBuiltin);
1767
46
}