Coverage Report

Created: 2020-02-25 14:32

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/Basic/Targets/AArch64.cpp
Line
Count
Source (jump to first uncovered line)
1
//===--- AArch64.cpp - Implement AArch64 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 AArch64 TargetInfo objects.
10
//
11
//===----------------------------------------------------------------------===//
12
13
#include "AArch64.h"
14
#include "clang/Basic/TargetBuiltins.h"
15
#include "clang/Basic/TargetInfo.h"
16
#include "llvm/ADT/ArrayRef.h"
17
#include "llvm/ADT/StringExtras.h"
18
#include "llvm/ADT/StringSwitch.h"
19
#include "llvm/Support/AArch64TargetParser.h"
20
21
using namespace clang;
22
using namespace clang::targets;
23
24
const Builtin::Info AArch64TargetInfo::BuiltinInfo[] = {
25
#define BUILTIN(ID, TYPE, ATTRS)                                               \
26
   {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr},
27
#include "clang/Basic/BuiltinsNEON.def"
28
29
#define BUILTIN(ID, TYPE, ATTRS)                                               \
30
   {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr},
31
#define LANGBUILTIN(ID, TYPE, ATTRS, LANG)                                     \
32
  {#ID, TYPE, ATTRS, nullptr, LANG, nullptr},
33
#define TARGET_HEADER_BUILTIN(ID, TYPE, ATTRS, HEADER, LANGS, FEATURE)         \
34
  {#ID, TYPE, ATTRS, HEADER, LANGS, FEATURE},
35
#include "clang/Basic/BuiltinsAArch64.def"
36
};
37
38
AArch64TargetInfo::AArch64TargetInfo(const llvm::Triple &Triple,
39
                                     const TargetOptions &Opts)
40
532
    : TargetInfo(Triple), ABI("aapcs") {
41
532
  if (getTriple().isOSOpenBSD()) {
42
4
    Int64Type = SignedLongLong;
43
4
    IntMaxType = SignedLongLong;
44
528
  } else {
45
528
    if (!getTriple().isOSDarwin() && 
!getTriple().isOSNetBSD()386
)
46
378
      WCharType = UnsignedInt;
47
528
48
528
    Int64Type = SignedLong;
49
528
    IntMaxType = SignedLong;
50
528
  }
51
532
52
532
  // All AArch64 implementations support ARMv8 FP, which makes half a legal type.
53
532
  HasLegalHalfType = true;
54
532
  HasFloat16 = true;
55
532
56
532
  if (Triple.isArch64Bit())
57
521
    LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
58
11
  else
59
11
    LongWidth = LongAlign = PointerWidth = PointerAlign = 32;
60
532
61
532
  MaxVectorAlign = 128;
62
532
  MaxAtomicInlineWidth = 128;
63
532
  MaxAtomicPromoteWidth = 128;
64
532
65
532
  LongDoubleWidth = LongDoubleAlign = SuitableAlign = 128;
66
532
  LongDoubleFormat = &llvm::APFloat::IEEEquad();
67
532
68
532
  // Make __builtin_ms_va_list available.
69
532
  HasBuiltinMSVaList = true;
70
532
71
532
  // Make the SVE types available.  Note that this deliberately doesn't
72
532
  // depend on SveMode, since in principle it should be possible to turn
73
532
  // SVE on and off within a translation unit.  It should also be possible
74
532
  // to compile the global declaration:
75
532
  //
76
532
  // __SVInt8_t *ptr;
77
532
  //
78
532
  // even without SVE.
79
532
  HasAArch64SVETypes = true;
80
532
81
532
  // {} in inline assembly are neon specifiers, not assembly variant
82
532
  // specifiers.
83
532
  NoAsmVariants = true;
84
532
85
532
  // AAPCS gives rules for bitfields. 7.1.7 says: "The container type
86
532
  // contributes to the alignment of the containing aggregate in the same way
87
532
  // a plain (non bit-field) member of that type would, without exception for
88
532
  // zero-sized or anonymous bit-fields."
89
532
  assert(UseBitFieldTypeAlignment && "bitfields affect type alignment");
90
532
  UseZeroLengthBitfieldAlignment = true;
91
532
92
532
  // AArch64 targets default to using the ARM C++ ABI.
93
532
  TheCXXABI.set(TargetCXXABI::GenericAArch64);
94
532
95
532
  if (Triple.getOS() == llvm::Triple::Linux)
96
205
    this->MCountName = "\01_mcount";
97
327
  else if (Triple.getOS() == llvm::Triple::UnknownOS)
98
123
    this->MCountName =
99
123
        Opts.EABIVersion == llvm::EABI::GNU ? 
"\01_mcount"1
:
"mcount"122
;
100
532
}
101
102
295
StringRef AArch64TargetInfo::getABI() const { return ABI; }
103
104
154
bool AArch64TargetInfo::setABI(const std::string &Name) {
105
154
  if (Name != "aapcs" && 
Name != "darwinpcs"19
)
106
0
    return false;
107
154
108
154
  ABI = Name;
109
154
  return true;
110
154
}
111
112
bool AArch64TargetInfo::validateBranchProtection(StringRef Spec,
113
                                                 BranchProtectionInfo &BPI,
114
73
                                                 StringRef &Err) const {
115
73
  llvm::AArch64::ParsedBranchProtection PBP;
116
73
  if (!llvm::AArch64::parseBranchProtection(Spec, PBP, Err))
117
7
    return false;
118
66
119
66
  BPI.SignReturnAddr =
120
66
      llvm::StringSwitch<CodeGenOptions::SignReturnAddressScope>(PBP.Scope)
121
66
          .Case("non-leaf", CodeGenOptions::SignReturnAddressScope::NonLeaf)
122
66
          .Case("all", CodeGenOptions::SignReturnAddressScope::All)
123
66
          .Default(CodeGenOptions::SignReturnAddressScope::None);
124
66
125
66
  if (PBP.Key == "a_key")
126
48
    BPI.SignKey = CodeGenOptions::SignReturnAddressKeyValue::AKey;
127
18
  else
128
18
    BPI.SignKey = CodeGenOptions::SignReturnAddressKeyValue::BKey;
129
66
130
66
  BPI.BranchTargetEnforcement = PBP.BranchTargetEnforcement;
131
66
  return true;
132
66
}
133
134
163
bool AArch64TargetInfo::isValidCPUName(StringRef Name) const {
135
163
  return Name == "generic" ||
136
163
         
llvm::AArch64::parseCPUArch(Name) != llvm::AArch64::ArchKind::INVALID26
;
137
163
}
138
139
163
bool AArch64TargetInfo::setCPU(const std::string &Name) {
140
163
  return isValidCPUName(Name);
141
163
}
142
143
void AArch64TargetInfo::fillValidCPUList(
144
1
    SmallVectorImpl<StringRef> &Values) const {
145
1
  llvm::AArch64::fillValidCPUArchList(Values);
146
1
}
147
148
void AArch64TargetInfo::getTargetDefinesARMV81A(const LangOptions &Opts,
149
68
                                                MacroBuilder &Builder) const {
150
68
  Builder.defineMacro("__ARM_FEATURE_QRDMX", "1");
151
68
}
152
153
void AArch64TargetInfo::getTargetDefinesARMV82A(const LangOptions &Opts,
154
65
                                                MacroBuilder &Builder) const {
155
65
  // Also include the ARMv8.1 defines
156
65
  getTargetDefinesARMV81A(Opts, Builder);
157
65
}
158
159
void AArch64TargetInfo::getTargetDefinesARMV83A(const LangOptions &Opts,
160
23
                                                MacroBuilder &Builder) const {
161
23
  Builder.defineMacro("__ARM_FEATURE_COMPLEX", "1");
162
23
  Builder.defineMacro("__ARM_FEATURE_JCVT", "1");
163
23
  // Also include the Armv8.2 defines
164
23
  getTargetDefinesARMV82A(Opts, Builder);
165
23
}
166
167
void AArch64TargetInfo::getTargetDefinesARMV84A(const LangOptions &Opts,
168
15
                                                MacroBuilder &Builder) const {
169
15
  // Also include the Armv8.3 defines
170
15
  // FIXME: Armv8.4 makes some extensions mandatory. Handle them here.
171
15
  getTargetDefinesARMV83A(Opts, Builder);
172
15
}
173
174
void AArch64TargetInfo::getTargetDefinesARMV85A(const LangOptions &Opts,
175
3
                                                MacroBuilder &Builder) const {
176
3
  // Also include the Armv8.4 defines
177
3
  // FIXME: Armv8.5 makes some extensions mandatory. Handle them here.
178
3
  getTargetDefinesARMV84A(Opts, Builder);
179
3
}
180
181
182
void AArch64TargetInfo::getTargetDefines(const LangOptions &Opts,
183
527
                                         MacroBuilder &Builder) const {
184
527
  // Target identification.
185
527
  Builder.defineMacro("__aarch64__");
186
527
  // For bare-metal.
187
527
  if (getTriple().getOS() == llvm::Triple::UnknownOS &&
188
527
      
getTriple().isOSBinFormatELF()122
)
189
121
    Builder.defineMacro("__ELF__");
190
527
191
527
  // Target properties.
192
527
  if (!getTriple().isOSWindows() && 
getTriple().isArch64Bit()484
) {
193
473
    Builder.defineMacro("_LP64");
194
473
    Builder.defineMacro("__LP64__");
195
473
  }
196
527
197
527
  std::string CodeModel = getTargetOpts().CodeModel;
198
527
  if (CodeModel == "default")
199
523
    CodeModel = "small";
200
527
  for (char &c : CodeModel)
201
2.63k
    c = toupper(c);
202
527
  Builder.defineMacro("__AARCH64_CMODEL_" + CodeModel + "__");
203
527
204
527
  // ACLE predefines. Many can only have one possible value on v8 AArch64.
205
527
  Builder.defineMacro("__ARM_ACLE", "200");
206
527
  Builder.defineMacro("__ARM_ARCH", "8");
207
527
  Builder.defineMacro("__ARM_ARCH_PROFILE", "'A'");
208
527
209
527
  Builder.defineMacro("__ARM_64BIT_STATE", "1");
210
527
  Builder.defineMacro("__ARM_PCS_AAPCS64", "1");
211
527
  Builder.defineMacro("__ARM_ARCH_ISA_A64", "1");
212
527
213
527
  Builder.defineMacro("__ARM_FEATURE_CLZ", "1");
214
527
  Builder.defineMacro("__ARM_FEATURE_FMA", "1");
215
527
  Builder.defineMacro("__ARM_FEATURE_LDREX", "0xF");
216
527
  Builder.defineMacro("__ARM_FEATURE_IDIV", "1"); // As specified in ACLE
217
527
  Builder.defineMacro("__ARM_FEATURE_DIV");       // For backwards compatibility
218
527
  Builder.defineMacro("__ARM_FEATURE_NUMERIC_MAXMIN", "1");
219
527
  Builder.defineMacro("__ARM_FEATURE_DIRECTED_ROUNDING", "1");
220
527
221
527
  Builder.defineMacro("__ARM_ALIGN_MAX_STACK_PWR", "4");
222
527
223
527
  // 0xe implies support for half, single and double precision operations.
224
527
  Builder.defineMacro("__ARM_FP", "0xE");
225
527
226
527
  // PCS specifies this for SysV variants, which is all we support. Other ABIs
227
527
  // may choose __ARM_FP16_FORMAT_ALTERNATIVE.
228
527
  Builder.defineMacro("__ARM_FP16_FORMAT_IEEE", "1");
229
527
  Builder.defineMacro("__ARM_FP16_ARGS", "1");
230
527
231
527
  if (Opts.UnsafeFPMath)
232
3
    Builder.defineMacro("__ARM_FP_FAST", "1");
233
527
234
527
  Builder.defineMacro("__ARM_SIZEOF_WCHAR_T",
235
527
                      Twine(Opts.WCharSize ? 
Opts.WCharSize5
:
4522
));
236
527
237
527
  Builder.defineMacro("__ARM_SIZEOF_MINIMAL_ENUM", Opts.ShortEnums ? 
"1"2
:
"4"525
);
238
527
239
527
  if (FPU & NeonMode) {
240
215
    Builder.defineMacro("__ARM_NEON", "1");
241
215
    // 64-bit NEON supports half, single and double precision operations.
242
215
    Builder.defineMacro("__ARM_NEON_FP", "0xE");
243
215
  }
244
527
245
527
  if (HasCRC)
246
4
    Builder.defineMacro("__ARM_FEATURE_CRC32", "1");
247
527
248
527
  if (HasCrypto)
249
16
    Builder.defineMacro("__ARM_FEATURE_CRYPTO", "1");
250
527
251
527
  if (HasUnaligned)
252
527
    Builder.defineMacro("__ARM_FEATURE_UNALIGNED", "1");
253
527
254
527
  if ((FPU & NeonMode) && 
HasFullFP16215
)
255
44
    Builder.defineMacro("__ARM_FEATURE_FP16_VECTOR_ARITHMETIC", "1");
256
527
  if (HasFullFP16)
257
49
   Builder.defineMacro("__ARM_FEATURE_FP16_SCALAR_ARITHMETIC", "1");
258
527
259
527
  if (HasDotProd)
260
4
    Builder.defineMacro("__ARM_FEATURE_DOTPROD", "1");
261
527
262
527
  if (HasMTE)
263
4
    Builder.defineMacro("__ARM_FEATURE_MEMORY_TAGGING", "1");
264
527
265
527
  if (HasTME)
266
4
    Builder.defineMacro("__ARM_FEATURE_TME", "1");
267
527
268
527
  if ((FPU & NeonMode) && 
HasFP16FML215
)
269
9
    Builder.defineMacro("__ARM_FEATURE_FP16FML", "1");
270
527
271
527
  switch (ArchKind) {
272
459
  default:
273
459
    break;
274
3
  case llvm::AArch64::ArchKind::ARMV8_1A:
275
3
    getTargetDefinesARMV81A(Opts, Builder);
276
3
    break;
277
42
  case llvm::AArch64::ArchKind::ARMV8_2A:
278
42
    getTargetDefinesARMV82A(Opts, Builder);
279
42
    break;
280
8
  case llvm::AArch64::ArchKind::ARMV8_3A:
281
8
    getTargetDefinesARMV83A(Opts, Builder);
282
8
    break;
283
12
  case llvm::AArch64::ArchKind::ARMV8_4A:
284
12
    getTargetDefinesARMV84A(Opts, Builder);
285
12
    break;
286
3
  case llvm::AArch64::ArchKind::ARMV8_5A:
287
3
    getTargetDefinesARMV85A(Opts, Builder);
288
3
    break;
289
527
  }
290
527
291
527
  // All of the __sync_(bool|val)_compare_and_swap_(1|2|4|8) builtins work.
292
527
  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_1");
293
527
  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_2");
294
527
  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_4");
295
527
  Builder.defineMacro("__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8");
296
527
}
297
298
527
ArrayRef<Builtin::Info> AArch64TargetInfo::getTargetBuiltins() const {
299
527
  return llvm::makeArrayRef(BuiltinInfo, clang::AArch64::LastTSBuiltin -
300
527
                                             Builtin::FirstTSBuiltin);
301
527
}
302
303
2.54k
bool AArch64TargetInfo::hasFeature(StringRef Feature) const {
304
2.54k
  return Feature == "aarch64" || 
Feature == "arm64"2.54k
||
Feature == "arm"2.54k
||
305
2.54k
         
(2.53k
Feature == "neon"2.53k
&&
(FPU & NeonMode)2.32k
) ||
306
2.54k
         
(236
Feature == "sve"236
&&
(FPU & SveMode)104
);
307
2.54k
}
308
309
bool AArch64TargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
310
531
                                             DiagnosticsEngine &Diags) {
311
531
  FPU = FPUMode;
312
531
  HasCRC = false;
313
531
  HasCrypto = false;
314
531
  HasUnaligned = true;
315
531
  HasFullFP16 = false;
316
531
  HasDotProd = false;
317
531
  HasFP16FML = false;
318
531
  HasMTE = false;
319
531
  HasTME = false;
320
531
  ArchKind = llvm::AArch64::ArchKind::ARMV8A;
321
531
322
531
  for (const auto &Feature : Features) {
323
469
    if (Feature == "+neon")
324
215
      FPU |= NeonMode;
325
469
    if (Feature == "+sve")
326
16
      FPU |= SveMode;
327
469
    if (Feature == "+crc")
328
4
      HasCRC = true;
329
469
    if (Feature == "+crypto")
330
16
      HasCrypto = true;
331
469
    if (Feature == "+strict-align")
332
0
      HasUnaligned = false;
333
469
    if (Feature == "+v8.1a")
334
3
      ArchKind = llvm::AArch64::ArchKind::ARMV8_1A;
335
469
    if (Feature == "+v8.2a")
336
42
      ArchKind = llvm::AArch64::ArchKind::ARMV8_2A;
337
469
    if (Feature == "+v8.3a")
338
8
      ArchKind = llvm::AArch64::ArchKind::ARMV8_3A;
339
469
    if (Feature == "+v8.4a")
340
12
      ArchKind = llvm::AArch64::ArchKind::ARMV8_4A;
341
469
    if (Feature == "+v8.5a")
342
3
      ArchKind = llvm::AArch64::ArchKind::ARMV8_5A;
343
469
    if (Feature == "+fullfp16")
344
49
      HasFullFP16 = true;
345
469
    if (Feature == "+dotprod")
346
4
      HasDotProd = true;
347
469
    if (Feature == "+fp16fml")
348
12
      HasFP16FML = true;
349
469
    if (Feature == "+mte")
350
4
      HasMTE = true;
351
469
    if (Feature == "+tme")
352
4
      HasTME = true;
353
469
  }
354
531
355
531
  setDataLayout();
356
531
357
531
  return true;
358
531
}
359
360
TargetInfo::CallingConvCheckResult
361
339
AArch64TargetInfo::checkCallingConvention(CallingConv CC) const {
362
339
  switch (CC) {
363
339
  case CC_C:
364
339
  case CC_Swift:
365
339
  case CC_PreserveMost:
366
339
  case CC_PreserveAll:
367
339
  case CC_OpenCLKernel:
368
339
  case CC_AArch64VectorCall:
369
339
  case CC_Win64:
370
339
    return CCCR_OK;
371
339
  default:
372
0
    return CCCR_Warning;
373
339
  }
374
339
}
375
376
24
bool AArch64TargetInfo::isCLZForZeroUndef() const { return false; }
377
378
354
TargetInfo::BuiltinVaListKind AArch64TargetInfo::getBuiltinVaListKind() const {
379
354
  return TargetInfo::AArch64ABIBuiltinVaList;
380
354
}
381
382
const char *const AArch64TargetInfo::GCCRegNames[] = {
383
    // 32-bit Integer registers
384
    "w0", "w1", "w2", "w3", "w4", "w5", "w6", "w7", "w8", "w9", "w10", "w11",
385
    "w12", "w13", "w14", "w15", "w16", "w17", "w18", "w19", "w20", "w21", "w22",
386
    "w23", "w24", "w25", "w26", "w27", "w28", "w29", "w30", "wsp",
387
388
    // 64-bit Integer registers
389
    "x0", "x1", "x2", "x3", "x4", "x5", "x6", "x7", "x8", "x9", "x10", "x11",
390
    "x12", "x13", "x14", "x15", "x16", "x17", "x18", "x19", "x20", "x21", "x22",
391
    "x23", "x24", "x25", "x26", "x27", "x28", "fp", "lr", "sp",
392
393
    // 32-bit floating point regsisters
394
    "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "s10", "s11",
395
    "s12", "s13", "s14", "s15", "s16", "s17", "s18", "s19", "s20", "s21", "s22",
396
    "s23", "s24", "s25", "s26", "s27", "s28", "s29", "s30", "s31",
397
398
    // 64-bit floating point regsisters
399
    "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d8", "d9", "d10", "d11",
400
    "d12", "d13", "d14", "d15", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
401
    "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31",
402
403
    // Neon vector registers
404
    "v0", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "v9", "v10", "v11",
405
    "v12", "v13", "v14", "v15", "v16", "v17", "v18", "v19", "v20", "v21", "v22",
406
    "v23", "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31",
407
408
    // SVE vector registers
409
    "z0",  "z1",  "z2",  "z3",  "z4",  "z5",  "z6",  "z7",  "z8",  "z9",  "z10",
410
    "z11", "z12", "z13", "z14", "z15", "z16", "z17", "z18", "z19", "z20", "z21",
411
    "z22", "z23", "z24", "z25", "z26", "z27", "z28", "z29", "z30", "z31",
412
413
    // SVE predicate registers
414
    "p0",  "p1",  "p2",  "p3",  "p4",  "p5",  "p6",  "p7",  "p8",  "p9",  "p10",
415
    "p11", "p12", "p13", "p14", "p15"
416
};
417
418
1.70k
ArrayRef<const char *> AArch64TargetInfo::getGCCRegNames() const {
419
1.70k
  return llvm::makeArrayRef(GCCRegNames);
420
1.70k
}
421
422
const TargetInfo::GCCRegAlias AArch64TargetInfo::GCCRegAliases[] = {
423
    {{"w31"}, "wsp"},
424
    {{"x31"}, "sp"},
425
    // GCC rN registers are aliases of xN registers.
426
    {{"r0"}, "x0"},
427
    {{"r1"}, "x1"},
428
    {{"r2"}, "x2"},
429
    {{"r3"}, "x3"},
430
    {{"r4"}, "x4"},
431
    {{"r5"}, "x5"},
432
    {{"r6"}, "x6"},
433
    {{"r7"}, "x7"},
434
    {{"r8"}, "x8"},
435
    {{"r9"}, "x9"},
436
    {{"r10"}, "x10"},
437
    {{"r11"}, "x11"},
438
    {{"r12"}, "x12"},
439
    {{"r13"}, "x13"},
440
    {{"r14"}, "x14"},
441
    {{"r15"}, "x15"},
442
    {{"r16"}, "x16"},
443
    {{"r17"}, "x17"},
444
    {{"r18"}, "x18"},
445
    {{"r19"}, "x19"},
446
    {{"r20"}, "x20"},
447
    {{"r21"}, "x21"},
448
    {{"r22"}, "x22"},
449
    {{"r23"}, "x23"},
450
    {{"r24"}, "x24"},
451
    {{"r25"}, "x25"},
452
    {{"r26"}, "x26"},
453
    {{"r27"}, "x27"},
454
    {{"r28"}, "x28"},
455
    {{"r29", "x29"}, "fp"},
456
    {{"r30", "x30"}, "lr"},
457
    // The S/D/Q and W/X registers overlap, but aren't really aliases; we
458
    // don't want to substitute one of these for a different-sized one.
459
};
460
461
707
ArrayRef<TargetInfo::GCCRegAlias> AArch64TargetInfo::getGCCRegAliases() const {
462
707
  return llvm::makeArrayRef(GCCRegAliases);
463
707
}
464
465
bool AArch64TargetInfo::validateAsmConstraint(
466
26
    const char *&Name, TargetInfo::ConstraintInfo &Info) const {
467
26
  switch (*Name) {
468
0
  default:
469
0
    return false;
470
10
  case 'w': // Floating point and SIMD registers (V0-V31)
471
10
    Info.setAllowsRegister();
472
10
    return true;
473
6
  case 'I': // Constant that can be used with an ADD instruction
474
6
  case 'J': // Constant that can be used with a SUB instruction
475
6
  case 'K': // Constant that can be used with a 32-bit logical instruction
476
6
  case 'L': // Constant that can be used with a 64-bit logical instruction
477
6
  case 'M': // Constant that can be used as a 32-bit MOV immediate
478
6
  case 'N': // Constant that can be used as a 64-bit MOV immediate
479
6
  case 'Y': // Floating point constant zero
480
6
  case 'Z': // Integer constant zero
481
6
    return true;
482
6
  case 'Q': // A memory reference with base register and no offset
483
4
    Info.setAllowsMemory();
484
4
    return true;
485
6
  case 'S': // A symbolic address
486
2
    Info.setAllowsRegister();
487
2
    return true;
488
6
  case 'U':
489
0
    // Ump: A memory address suitable for ldp/stp in SI, DI, SF and DF modes.
490
0
    // Utf: A memory address suitable for ldp/stp in TF mode.
491
0
    // Usa: An absolute symbolic address.
492
0
    // Ush: The high part (bits 32:12) of a pc-relative symbolic address.
493
0
    llvm_unreachable("FIXME: Unimplemented support for U* constraints.");
494
6
  case 'z': // Zero register, wzr or xzr
495
4
    Info.setAllowsRegister();
496
4
    return true;
497
6
  case 'x': // Floating point and SIMD registers (V0-V15)
498
0
    Info.setAllowsRegister();
499
0
    return true;
500
0
  }
501
0
  return false;
502
0
}
503
504
bool AArch64TargetInfo::validateConstraintModifier(
505
    StringRef Constraint, char Modifier, unsigned Size,
506
63
    std::string &SuggestedModifier) const {
507
63
  // Strip off constraint modifiers.
508
94
  while (Constraint[0] == '=' || 
Constraint[0] == '+'71
||
Constraint[0] == '&'64
)
509
31
    Constraint = Constraint.substr(1);
510
63
511
63
  switch (Constraint[0]) {
512
22
  default:
513
22
    return true;
514
41
  case 'z':
515
41
  case 'r': {
516
41
    switch (Modifier) {
517
7
    case 'x':
518
7
    case 'w':
519
7
      // For now assume that the person knows what they're
520
7
      // doing with the modifier.
521
7
      return true;
522
34
    default:
523
34
      // By default an 'r' constraint will be in the 'x'
524
34
      // registers.
525
34
      if (Size == 64)
526
18
        return true;
527
16
528
16
      SuggestedModifier = "w";
529
16
      return false;
530
41
    }
531
41
  }
532
63
  }
533
63
}
534
535
27
const char *AArch64TargetInfo::getClobbers() const { return ""; }
536
537
0
int AArch64TargetInfo::getEHDataRegisterNumber(unsigned RegNo) const {
538
0
  if (RegNo == 0)
539
0
    return 0;
540
0
  if (RegNo == 1)
541
0
    return 1;
542
0
  return -1;
543
0
}
544
545
1.54k
bool AArch64TargetInfo::hasInt128Type() const { return true; }
546
547
AArch64leTargetInfo::AArch64leTargetInfo(const llvm::Triple &Triple,
548
                                         const TargetOptions &Opts)
549
507
    : AArch64TargetInfo(Triple, Opts) {}
clang::targets::AArch64leTargetInfo::AArch64leTargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
549
399
    : AArch64TargetInfo(Triple, Opts) {}
clang::targets::AArch64leTargetInfo::AArch64leTargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
549
108
    : AArch64TargetInfo(Triple, Opts) {}
550
551
463
void AArch64leTargetInfo::setDataLayout() {
552
463
  if (getTriple().isOSBinFormatMachO()) {
553
143
    if(getTriple().isArch32Bit())
554
11
      resetDataLayout("e-m:o-p:32:32-i64:64-i128:128-n32:64-S128");
555
132
    else
556
132
      resetDataLayout("e-m:o-i64:64-i128:128-n32:64-S128");
557
143
  } else
558
320
    resetDataLayout("e-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128");
559
463
}
560
561
void AArch64leTargetInfo::getTargetDefines(const LangOptions &Opts,
562
502
                                           MacroBuilder &Builder) const {
563
502
  Builder.defineMacro("__AARCH64EL__");
564
502
  AArch64TargetInfo::getTargetDefines(Opts, Builder);
565
502
}
566
567
AArch64beTargetInfo::AArch64beTargetInfo(const llvm::Triple &Triple,
568
                                         const TargetOptions &Opts)
569
25
    : AArch64TargetInfo(Triple, Opts) {}
clang::targets::AArch64beTargetInfo::AArch64beTargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
569
8
    : AArch64TargetInfo(Triple, Opts) {}
clang::targets::AArch64beTargetInfo::AArch64beTargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
569
17
    : AArch64TargetInfo(Triple, Opts) {}
570
571
void AArch64beTargetInfo::getTargetDefines(const LangOptions &Opts,
572
25
                                           MacroBuilder &Builder) const {
573
25
  Builder.defineMacro("__AARCH64EB__");
574
25
  Builder.defineMacro("__AARCH_BIG_ENDIAN");
575
25
  Builder.defineMacro("__ARM_BIG_ENDIAN");
576
25
  AArch64TargetInfo::getTargetDefines(Opts, Builder);
577
25
}
578
579
25
void AArch64beTargetInfo::setDataLayout() {
580
25
  assert(!getTriple().isOSBinFormatMachO());
581
25
  resetDataLayout("E-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128");
582
25
}
583
584
WindowsARM64TargetInfo::WindowsARM64TargetInfo(const llvm::Triple &Triple,
585
                                               const TargetOptions &Opts)
586
43
    : WindowsTargetInfo<AArch64leTargetInfo>(Triple, Opts), Triple(Triple) {
587
43
588
43
  // This is an LLP64 platform.
589
43
  // int:4, long:4, long long:8, long double:8.
590
43
  IntWidth = IntAlign = 32;
591
43
  LongWidth = LongAlign = 32;
592
43
  DoubleAlign = LongLongAlign = 64;
593
43
  LongDoubleWidth = LongDoubleAlign = 64;
594
43
  LongDoubleFormat = &llvm::APFloat::IEEEdouble();
595
43
  IntMaxType = SignedLongLong;
596
43
  Int64Type = SignedLongLong;
597
43
  SizeType = UnsignedLongLong;
598
43
  PtrDiffType = SignedLongLong;
599
43
  IntPtrType = SignedLongLong;
600
43
}
clang::targets::WindowsARM64TargetInfo::WindowsARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
586
43
    : WindowsTargetInfo<AArch64leTargetInfo>(Triple, Opts), Triple(Triple) {
587
43
588
43
  // This is an LLP64 platform.
589
43
  // int:4, long:4, long long:8, long double:8.
590
43
  IntWidth = IntAlign = 32;
591
43
  LongWidth = LongAlign = 32;
592
43
  DoubleAlign = LongLongAlign = 64;
593
43
  LongDoubleWidth = LongDoubleAlign = 64;
594
43
  LongDoubleFormat = &llvm::APFloat::IEEEdouble();
595
43
  IntMaxType = SignedLongLong;
596
43
  Int64Type = SignedLongLong;
597
43
  SizeType = UnsignedLongLong;
598
43
  PtrDiffType = SignedLongLong;
599
43
  IntPtrType = SignedLongLong;
600
43
}
Unexecuted instantiation: clang::targets::WindowsARM64TargetInfo::WindowsARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
601
602
43
void WindowsARM64TargetInfo::setDataLayout() {
603
43
  resetDataLayout("e-m:w-p:64:64-i32:32-i64:64-i128:128-n32:64-S128");
604
43
}
605
606
TargetInfo::BuiltinVaListKind
607
42
WindowsARM64TargetInfo::getBuiltinVaListKind() const {
608
42
  return TargetInfo::CharPtrBuiltinVaList;
609
42
}
610
611
TargetInfo::CallingConvCheckResult
612
53
WindowsARM64TargetInfo::checkCallingConvention(CallingConv CC) const {
613
53
  switch (CC) {
614
7
  case CC_X86StdCall:
615
7
  case CC_X86ThisCall:
616
7
  case CC_X86FastCall:
617
7
  case CC_X86VectorCall:
618
7
    return CCCR_Ignore;
619
46
  case CC_C:
620
46
  case CC_OpenCLKernel:
621
46
  case CC_PreserveMost:
622
46
  case CC_PreserveAll:
623
46
  case CC_Swift:
624
46
  case CC_Win64:
625
46
    return CCCR_OK;
626
46
  default:
627
0
    return CCCR_Warning;
628
53
  }
629
53
}
630
631
MicrosoftARM64TargetInfo::MicrosoftARM64TargetInfo(const llvm::Triple &Triple,
632
                                                   const TargetOptions &Opts)
633
40
    : WindowsARM64TargetInfo(Triple, Opts) {
634
40
  TheCXXABI.set(TargetCXXABI::Microsoft);
635
40
}
Unexecuted instantiation: clang::targets::MicrosoftARM64TargetInfo::MicrosoftARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
clang::targets::MicrosoftARM64TargetInfo::MicrosoftARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
633
40
    : WindowsARM64TargetInfo(Triple, Opts) {
634
40
  TheCXXABI.set(TargetCXXABI::Microsoft);
635
40
}
636
637
void MicrosoftARM64TargetInfo::getTargetDefines(const LangOptions &Opts,
638
40
                                                MacroBuilder &Builder) const {
639
40
  WindowsARM64TargetInfo::getTargetDefines(Opts, Builder);
640
40
  Builder.defineMacro("_M_ARM64", "1");
641
40
}
642
643
TargetInfo::CallingConvKind
644
77
MicrosoftARM64TargetInfo::getCallingConvKind(bool ClangABICompat4) const {
645
77
  return CCK_MicrosoftWin64;
646
77
}
647
648
163
unsigned MicrosoftARM64TargetInfo::getMinGlobalAlign(uint64_t TypeSize) const {
649
163
  unsigned Align = WindowsARM64TargetInfo::getMinGlobalAlign(TypeSize);
650
163
651
163
  // MSVC does size based alignment for arm64 based on alignment section in
652
163
  // below document, replicate that to keep alignment consistent with object
653
163
  // files compiled by MSVC.
654
163
  // https://docs.microsoft.com/en-us/cpp/build/arm64-windows-abi-conventions
655
163
  if (TypeSize >= 512) {              // TypeSize >= 64 bytes
656
10
    Align = std::max(Align, 128u);    // align type at least 16 bytes
657
153
  } else if (TypeSize >= 64) {        // TypeSize >= 8 bytes
658
57
    Align = std::max(Align, 64u);     // align type at least 8 butes
659
96
  } else if (TypeSize >= 16) {        // TypeSize >= 2 bytes
660
45
    Align = std::max(Align, 32u);     // align type at least 4 bytes
661
45
  }
662
163
  return Align;
663
163
}
664
665
MinGWARM64TargetInfo::MinGWARM64TargetInfo(const llvm::Triple &Triple,
666
                                           const TargetOptions &Opts)
667
3
    : WindowsARM64TargetInfo(Triple, Opts) {
668
3
  TheCXXABI.set(TargetCXXABI::GenericAArch64);
669
3
}
Unexecuted instantiation: clang::targets::MinGWARM64TargetInfo::MinGWARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
clang::targets::MinGWARM64TargetInfo::MinGWARM64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
667
3
    : WindowsARM64TargetInfo(Triple, Opts) {
668
3
  TheCXXABI.set(TargetCXXABI::GenericAArch64);
669
3
}
670
671
DarwinAArch64TargetInfo::DarwinAArch64TargetInfo(const llvm::Triple &Triple,
672
                                                 const TargetOptions &Opts)
673
142
    : DarwinTargetInfo<AArch64leTargetInfo>(Triple, Opts) {
674
142
  Int64Type = SignedLongLong;
675
142
  if (getTriple().isArch32Bit())
676
11
    IntMaxType = SignedLongLong;
677
142
678
142
  WCharType = SignedInt;
679
142
  UseSignedCharForObjCBool = false;
680
142
681
142
  LongDoubleWidth = LongDoubleAlign = SuitableAlign = 64;
682
142
  LongDoubleFormat = &llvm::APFloat::IEEEdouble();
683
142
684
142
  UseZeroLengthBitfieldAlignment = false;
685
142
686
142
  if (getTriple().isArch32Bit()) {
687
11
    UseBitFieldTypeAlignment = false;
688
11
    ZeroLengthBitfieldBoundary = 32;
689
11
    UseZeroLengthBitfieldAlignment = true;
690
11
    TheCXXABI.set(TargetCXXABI::WatchOS);
691
11
  } else
692
131
    TheCXXABI.set(TargetCXXABI::iOS64);
693
142
}
Unexecuted instantiation: clang::targets::DarwinAArch64TargetInfo::DarwinAArch64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
clang::targets::DarwinAArch64TargetInfo::DarwinAArch64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
673
142
    : DarwinTargetInfo<AArch64leTargetInfo>(Triple, Opts) {
674
142
  Int64Type = SignedLongLong;
675
142
  if (getTriple().isArch32Bit())
676
11
    IntMaxType = SignedLongLong;
677
142
678
142
  WCharType = SignedInt;
679
142
  UseSignedCharForObjCBool = false;
680
142
681
142
  LongDoubleWidth = LongDoubleAlign = SuitableAlign = 64;
682
142
  LongDoubleFormat = &llvm::APFloat::IEEEdouble();
683
142
684
142
  UseZeroLengthBitfieldAlignment = false;
685
142
686
142
  if (getTriple().isArch32Bit()) {
687
11
    UseBitFieldTypeAlignment = false;
688
11
    ZeroLengthBitfieldBoundary = 32;
689
11
    UseZeroLengthBitfieldAlignment = true;
690
11
    TheCXXABI.set(TargetCXXABI::WatchOS);
691
11
  } else
692
131
    TheCXXABI.set(TargetCXXABI::iOS64);
693
142
}
694
695
void DarwinAArch64TargetInfo::getOSDefines(const LangOptions &Opts,
696
                                           const llvm::Triple &Triple,
697
142
                                           MacroBuilder &Builder) const {
698
142
  Builder.defineMacro("__AARCH64_SIMD__");
699
142
  if (Triple.isArch32Bit())
700
11
    Builder.defineMacro("__ARM64_ARCH_8_32__");
701
131
  else
702
131
    Builder.defineMacro("__ARM64_ARCH_8__");
703
142
  Builder.defineMacro("__ARM_NEON__");
704
142
  Builder.defineMacro("__LITTLE_ENDIAN__");
705
142
  Builder.defineMacro("__REGISTER_PREFIX__", "");
706
142
  Builder.defineMacro("__arm64", "1");
707
142
  Builder.defineMacro("__arm64__", "1");
708
142
709
142
  getDarwinDefines(Builder, Opts, Triple, PlatformName, PlatformMinVersion);
710
142
}
711
712
TargetInfo::BuiltinVaListKind
713
158
DarwinAArch64TargetInfo::getBuiltinVaListKind() const {
714
158
  return TargetInfo::CharPtrBuiltinVaList;
715
158
}
716
717
// 64-bit RenderScript is aarch64
718
RenderScript64TargetInfo::RenderScript64TargetInfo(const llvm::Triple &Triple,
719
                                                   const TargetOptions &Opts)
720
    : AArch64leTargetInfo(llvm::Triple("aarch64", Triple.getVendorName(),
721
                                       Triple.getOSName(),
722
                                       Triple.getEnvironmentName()),
723
1
                          Opts) {
724
1
  IsRenderScriptTarget = true;
725
1
}
clang::targets::RenderScript64TargetInfo::RenderScript64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
Line
Count
Source
723
1
                          Opts) {
724
1
  IsRenderScriptTarget = true;
725
1
}
Unexecuted instantiation: clang::targets::RenderScript64TargetInfo::RenderScript64TargetInfo(llvm::Triple const&, clang::TargetOptions const&)
726
727
void RenderScript64TargetInfo::getTargetDefines(const LangOptions &Opts,
728
1
                                                MacroBuilder &Builder) const {
729
1
  Builder.defineMacro("__RENDERSCRIPT__");
730
1
  AArch64leTargetInfo::getTargetDefines(Opts, Builder);
731
1
}