1//===--- ARM.cpp - ARM (not AArch64) Helpers for Tools ----------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "ARM.h"
10#include "clang/Driver/Driver.h"
11#include "clang/Driver/DriverDiagnostic.h"
12#include "clang/Driver/Options.h"
13#include "llvm/ADT/StringSwitch.h"
14#include "llvm/Option/ArgList.h"
15#include "llvm/Support/TargetParser.h"
16#include "llvm/Support/Host.h"
17
18using namespace clang::driver;
19using namespace clang::driver::tools;
20using namespace clang;
21using namespace llvm::opt;
22
23// Get SubArch (vN).
24int arm::getARMSubArchVersionNumber(const llvm::Triple &Triple) {
25  llvm::StringRef Arch = Triple.getArchName();
26  return llvm::ARM::parseArchVersion(Arch);
27}
28
29// True if M-profile.
30bool arm::isARMMProfile(const llvm::Triple &Triple) {
31  llvm::StringRef Arch = Triple.getArchName();
32  return llvm::ARM::parseArchProfile(Arch) == llvm::ARM::ProfileKind::M;
33}
34
35// Get Arch/CPU from args.
36void arm::getARMArchCPUFromArgs(const ArgList &Args, llvm::StringRef &Arch,
37                                llvm::StringRef &CPU, bool FromAs) {
38  if (const Arg *A = Args.getLastArg(clang::driver::options::OPT_mcpu_EQ))
39    CPU = A->getValue();
40  if (const Arg *A = Args.getLastArg(options::OPT_march_EQ))
41    Arch = A->getValue();
42  if (!FromAs)
43    return;
44
45  for (const Arg *A :
46       Args.filtered(options::OPT_Wa_COMMA, options::OPT_Xassembler)) {
47    StringRef Value = A->getValue();
48    if (Value.startswith("-mcpu="))
49      CPU = Value.substr(6);
50    if (Value.startswith("-march="))
51      Arch = Value.substr(7);
52  }
53}
54
55// Handle -mhwdiv=.
56// FIXME: Use ARMTargetParser.
57static void getARMHWDivFeatures(const Driver &D, const Arg *A,
58                                const ArgList &Args, StringRef HWDiv,
59                                std::vector<StringRef> &Features) {
60  unsigned HWDivID = llvm::ARM::parseHWDiv(HWDiv);
61  if (!llvm::ARM::getHWDivFeatures(HWDivID, Features))
62    D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args);
63}
64
65// Handle -mfpu=.
66static unsigned getARMFPUFeatures(const Driver &D, const Arg *A,
67                                  const ArgList &Args, StringRef FPU,
68                                  std::vector<StringRef> &Features) {
69  unsigned FPUID = llvm::ARM::parseFPU(FPU);
70  if (!llvm::ARM::getFPUFeatures(FPUID, Features))
71    D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args);
72  return FPUID;
73}
74
75// Decode ARM features from string like +[no]featureA+[no]featureB+...
76static bool DecodeARMFeatures(const Driver &D, StringRef text,
77                              StringRef CPU, llvm::ARM::ArchKind ArchKind,
78                              std::vector<StringRef> &Features) {
79  SmallVector<StringRef, 8> Split;
80  text.split(Split, StringRef("+"), -1, false);
81
82  for (StringRef Feature : Split) {
83    if (!appendArchExtFeatures(CPU, ArchKind, Feature, Features))
84      return false;
85  }
86  return true;
87}
88
89static void DecodeARMFeaturesFromCPU(const Driver &D, StringRef CPU,
90                                     std::vector<StringRef> &Features) {
91  CPU = CPU.split("+").first;
92  if (CPU != "generic") {
93    llvm::ARM::ArchKind ArchKind = llvm::ARM::parseCPUArch(CPU);
94    unsigned Extension = llvm::ARM::getDefaultExtensions(CPU, ArchKind);
95    llvm::ARM::getExtensionFeatures(Extension, Features);
96  }
97}
98
99// Check if -march is valid by checking if it can be canonicalised and parsed.
100// getARMArch is used here instead of just checking the -march value in order
101// to handle -march=native correctly.
102static void checkARMArchName(const Driver &D, const Arg *A, const ArgList &Args,
103                             llvm::StringRef ArchName, llvm::StringRef CPUName,
104                             std::vector<StringRef> &Features,
105                             const llvm::Triple &Triple) {
106  std::pair<StringRef, StringRef> Split = ArchName.split("+");
107
108  std::string MArch = arm::getARMArch(ArchName, Triple);
109  llvm::ARM::ArchKind ArchKind = llvm::ARM::parseArch(MArch);
110  if (ArchKind == llvm::ARM::ArchKind::INVALID ||
111      (Split.second.size() && !DecodeARMFeatures(
112        D, Split.second, CPUName, ArchKind, Features)))
113    D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args);
114}
115
116// Check -mcpu=. Needs ArchName to handle -mcpu=generic.
117static void checkARMCPUName(const Driver &D, const Arg *A, const ArgList &Args,
118                            llvm::StringRef CPUName, llvm::StringRef ArchName,
119                            std::vector<StringRef> &Features,
120                            const llvm::Triple &Triple) {
121  std::pair<StringRef, StringRef> Split = CPUName.split("+");
122
123  std::string CPU = arm::getARMTargetCPU(CPUName, ArchName, Triple);
124  llvm::ARM::ArchKind ArchKind =
125    arm::getLLVMArchKindForARM(CPU, ArchName, Triple);
126  if (ArchKind == llvm::ARM::ArchKind::INVALID ||
127      (Split.second.size() && !DecodeARMFeatures(
128        D, Split.second, CPU, ArchKind, Features)))
129    D.Diag(clang::diag::err_drv_clang_unsupported) << A->getAsString(Args);
130}
131
132bool arm::useAAPCSForMachO(const llvm::Triple &T) {
133  // The backend is hardwired to assume AAPCS for M-class processors, ensure
134  // the frontend matches that.
135  return T.getEnvironment() == llvm::Triple::EABI ||
136         T.getOS() == llvm::Triple::UnknownOS || isARMMProfile(T);
137}
138
139// Select mode for reading thread pointer (-mtp=soft/cp15).
140arm::ReadTPMode arm::getReadTPMode(const ToolChain &TC, const ArgList &Args) {
141  if (Arg *A = Args.getLastArg(options::OPT_mtp_mode_EQ)) {
142    const Driver &D = TC.getDriver();
143    arm::ReadTPMode ThreadPointer =
144        llvm::StringSwitch<arm::ReadTPMode>(A->getValue())
145            .Case("cp15", ReadTPMode::Cp15)
146            .Case("soft", ReadTPMode::Soft)
147            .Default(ReadTPMode::Invalid);
148    if (ThreadPointer != ReadTPMode::Invalid)
149      return ThreadPointer;
150    if (StringRef(A->getValue()).empty())
151      D.Diag(diag::err_drv_missing_arg_mtp) << A->getAsString(Args);
152    else
153      D.Diag(diag::err_drv_invalid_mtp) << A->getAsString(Args);
154    return ReadTPMode::Invalid;
155  }
156  return ReadTPMode::Soft;
157}
158
159// Select the float ABI as determined by -msoft-float, -mhard-float, and
160// -mfloat-abi=.
161arm::FloatABI arm::getARMFloatABI(const ToolChain &TC, const ArgList &Args) {
162  const Driver &D = TC.getDriver();
163  const llvm::Triple &Triple = TC.getEffectiveTriple();
164  auto SubArch = getARMSubArchVersionNumber(Triple);
165  arm::FloatABI ABI = FloatABI::Invalid;
166  if (Arg *A =
167          Args.getLastArg(options::OPT_msoft_float, options::OPT_mhard_float,
168                          options::OPT_mfloat_abi_EQ)) {
169    if (A->getOption().matches(options::OPT_msoft_float)) {
170      ABI = FloatABI::Soft;
171    } else if (A->getOption().matches(options::OPT_mhard_float)) {
172      ABI = FloatABI::Hard;
173    } else {
174      ABI = llvm::StringSwitch<arm::FloatABI>(A->getValue())
175                .Case("soft", FloatABI::Soft)
176                .Case("softfp", FloatABI::SoftFP)
177                .Case("hard", FloatABI::Hard)
178                .Default(FloatABI::Invalid);
179      if (ABI == FloatABI::Invalid && !StringRef(A->getValue()).empty()) {
180        D.Diag(diag::err_drv_invalid_mfloat_abi) << A->getAsString(Args);
181        ABI = FloatABI::Soft;
182      }
183    }
184
185    // It is incorrect to select hard float ABI on MachO platforms if the ABI is
186    // "apcs-gnu".
187    if (Triple.isOSBinFormatMachO() && !useAAPCSForMachO(Triple) &&
188        ABI == FloatABI::Hard) {
189      D.Diag(diag::err_drv_unsupported_opt_for_target) << A->getAsString(Args)
190                                                       << Triple.getArchName();
191    }
192  }
193
194  // If unspecified, choose the default based on the platform.
195  if (ABI == FloatABI::Invalid) {
196    switch (Triple.getOS()) {
197    case llvm::Triple::Darwin:
198    case llvm::Triple::MacOSX:
199    case llvm::Triple::IOS:
200    case llvm::Triple::TvOS: {
201      // Darwin defaults to "softfp" for v6 and v7.
202      ABI = (SubArch == 6 || SubArch == 7) ? FloatABI::SoftFP : FloatABI::Soft;
203      ABI = Triple.isWatchABI() ? FloatABI::Hard : ABI;
204      break;
205    }
206    case llvm::Triple::WatchOS:
207      ABI = FloatABI::Hard;
208      break;
209
210    // FIXME: this is invalid for WindowsCE
211    case llvm::Triple::Win32:
212      ABI = FloatABI::Hard;
213      break;
214
215    case llvm::Triple::NetBSD:
216      switch (Triple.getEnvironment()) {
217      case llvm::Triple::EABIHF:
218      case llvm::Triple::GNUEABIHF:
219        ABI = FloatABI::Hard;
220        break;
221      default:
222        ABI = FloatABI::Soft;
223        break;
224      }
225      break;
226
227    case llvm::Triple::FreeBSD:
228      switch (Triple.getEnvironment()) {
229      case llvm::Triple::GNUEABIHF:
230        ABI = FloatABI::Hard;
231        break;
232      default:
233        // FreeBSD defaults to soft float
234        ABI = FloatABI::Soft;
235        break;
236      }
237      break;
238
239    case llvm::Triple::OpenBSD:
240      ABI = FloatABI::SoftFP;
241      break;
242
243    default:
244      switch (Triple.getEnvironment()) {
245      case llvm::Triple::GNUEABIHF:
246      case llvm::Triple::MuslEABIHF:
247      case llvm::Triple::EABIHF:
248        ABI = FloatABI::Hard;
249        break;
250      case llvm::Triple::GNUEABI:
251      case llvm::Triple::MuslEABI:
252      case llvm::Triple::EABI:
253        // EABI is always AAPCS, and if it was not marked 'hard', it's softfp
254        ABI = FloatABI::SoftFP;
255        break;
256      case llvm::Triple::Android:
257        ABI = (SubArch >= 7) ? FloatABI::SoftFP : FloatABI::Soft;
258        break;
259      default:
260        // Assume "soft", but warn the user we are guessing.
261        if (Triple.isOSBinFormatMachO() &&
262            Triple.getSubArch() == llvm::Triple::ARMSubArch_v7em)
263          ABI = FloatABI::Hard;
264        else
265          ABI = FloatABI::Soft;
266
267        if (Triple.getOS() != llvm::Triple::UnknownOS ||
268            !Triple.isOSBinFormatMachO())
269          D.Diag(diag::warn_drv_assuming_mfloat_abi_is) << "soft";
270        break;
271      }
272    }
273  }
274
275  assert(ABI != FloatABI::Invalid && "must select an ABI");
276  return ABI;
277}
278
279void arm::getARMTargetFeatures(const ToolChain &TC,
280                               const llvm::Triple &Triple,
281                               const ArgList &Args,
282                               ArgStringList &CmdArgs,
283                               std::vector<StringRef> &Features,
284                               bool ForAS) {
285  const Driver &D = TC.getDriver();
286
287  bool KernelOrKext =
288      Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext);
289  arm::FloatABI ABI = arm::getARMFloatABI(TC, Args);
290  arm::ReadTPMode ThreadPointer = arm::getReadTPMode(TC, Args);
291  const Arg *WaCPU = nullptr, *WaFPU = nullptr;
292  const Arg *WaHDiv = nullptr, *WaArch = nullptr;
293
294  // This vector will accumulate features from the architecture
295  // extension suffixes on -mcpu and -march (e.g. the 'bar' in
296  // -mcpu=foo+bar). We want to apply those after the features derived
297  // from the FPU, in case -mfpu generates a negative feature which
298  // the +bar is supposed to override.
299  std::vector<StringRef> ExtensionFeatures;
300
301  if (!ForAS) {
302    // FIXME: Note, this is a hack, the LLVM backend doesn't actually use these
303    // yet (it uses the -mfloat-abi and -msoft-float options), and it is
304    // stripped out by the ARM target. We should probably pass this a new
305    // -target-option, which is handled by the -cc1/-cc1as invocation.
306    //
307    // FIXME2:  For consistency, it would be ideal if we set up the target
308    // machine state the same when using the frontend or the assembler. We don't
309    // currently do that for the assembler, we pass the options directly to the
310    // backend and never even instantiate the frontend TargetInfo. If we did,
311    // and used its handleTargetFeatures hook, then we could ensure the
312    // assembler and the frontend behave the same.
313
314    // Use software floating point operations?
315    if (ABI == arm::FloatABI::Soft)
316      Features.push_back("+soft-float");
317
318    // Use software floating point argument passing?
319    if (ABI != arm::FloatABI::Hard)
320      Features.push_back("+soft-float-abi");
321  } else {
322    // Here, we make sure that -Wa,-mfpu/cpu/arch/hwdiv will be passed down
323    // to the assembler correctly.
324    for (const Arg *A :
325         Args.filtered(options::OPT_Wa_COMMA, options::OPT_Xassembler)) {
326      StringRef Value = A->getValue();
327      if (Value.startswith("-mfpu=")) {
328        WaFPU = A;
329      } else if (Value.startswith("-mcpu=")) {
330        WaCPU = A;
331      } else if (Value.startswith("-mhwdiv=")) {
332        WaHDiv = A;
333      } else if (Value.startswith("-march=")) {
334        WaArch = A;
335      }
336    }
337  }
338
339  if (ThreadPointer == arm::ReadTPMode::Cp15)
340    Features.push_back("+read-tp-hard");
341
342  const Arg *ArchArg = Args.getLastArg(options::OPT_march_EQ);
343  const Arg *CPUArg = Args.getLastArg(options::OPT_mcpu_EQ);
344  StringRef ArchName;
345  StringRef CPUName;
346
347  // Check -mcpu. ClangAs gives preference to -Wa,-mcpu=.
348  if (WaCPU) {
349    if (CPUArg)
350      D.Diag(clang::diag::warn_drv_unused_argument)
351          << CPUArg->getAsString(Args);
352    CPUName = StringRef(WaCPU->getValue()).substr(6);
353    CPUArg = WaCPU;
354  } else if (CPUArg)
355    CPUName = CPUArg->getValue();
356
357  // Check -march. ClangAs gives preference to -Wa,-march=.
358  if (WaArch) {
359    if (ArchArg)
360      D.Diag(clang::diag::warn_drv_unused_argument)
361          << ArchArg->getAsString(Args);
362    ArchName = StringRef(WaArch->getValue()).substr(7);
363    checkARMArchName(D, WaArch, Args, ArchName, CPUName,
364                     ExtensionFeatures, Triple);
365    // FIXME: Set Arch.
366    D.Diag(clang::diag::warn_drv_unused_argument) << WaArch->getAsString(Args);
367  } else if (ArchArg) {
368    ArchName = ArchArg->getValue();
369    checkARMArchName(D, ArchArg, Args, ArchName, CPUName,
370                     ExtensionFeatures, Triple);
371  }
372
373  // Add CPU features for generic CPUs
374  if (CPUName == "native") {
375    llvm::StringMap<bool> HostFeatures;
376    if (llvm::sys::getHostCPUFeatures(HostFeatures))
377      for (auto &F : HostFeatures)
378        Features.push_back(
379            Args.MakeArgString((F.second ? "+" : "-") + F.first()));
380  } else if (!CPUName.empty()) {
381    // This sets the default features for the specified CPU. We certainly don't
382    // want to override the features that have been explicitly specified on the
383    // command line. Therefore, process them directly instead of appending them
384    // at the end later.
385    DecodeARMFeaturesFromCPU(D, CPUName, Features);
386  }
387
388  if (CPUArg)
389    checkARMCPUName(D, CPUArg, Args, CPUName, ArchName,
390                    ExtensionFeatures, Triple);
391  // Honor -mfpu=. ClangAs gives preference to -Wa,-mfpu=.
392  unsigned FPUID = llvm::ARM::FK_INVALID;
393  const Arg *FPUArg = Args.getLastArg(options::OPT_mfpu_EQ);
394  if (WaFPU) {
395    if (FPUArg)
396      D.Diag(clang::diag::warn_drv_unused_argument)
397          << FPUArg->getAsString(Args);
398    (void)getARMFPUFeatures(D, WaFPU, Args, StringRef(WaFPU->getValue()).substr(6),
399                            Features);
400  } else if (FPUArg) {
401    FPUID = getARMFPUFeatures(D, FPUArg, Args, FPUArg->getValue(), Features);
402  } else if (Triple.isAndroid() && getARMSubArchVersionNumber(Triple) >= 7) {
403    const char *AndroidFPU = "neon";
404    FPUID = llvm::ARM::parseFPU(AndroidFPU);
405    if (!llvm::ARM::getFPUFeatures(FPUID, Features))
406      D.Diag(clang::diag::err_drv_clang_unsupported)
407          << std::string("-mfpu=") + AndroidFPU;
408  }
409
410  // Now we've finished accumulating features from arch, cpu and fpu,
411  // we can append the ones for architecture extensions that we
412  // collected separately.
413  Features.insert(std::end(Features),
414                  std::begin(ExtensionFeatures), std::end(ExtensionFeatures));
415
416  // Honor -mhwdiv=. ClangAs gives preference to -Wa,-mhwdiv=.
417  const Arg *HDivArg = Args.getLastArg(options::OPT_mhwdiv_EQ);
418  if (WaHDiv) {
419    if (HDivArg)
420      D.Diag(clang::diag::warn_drv_unused_argument)
421          << HDivArg->getAsString(Args);
422    getARMHWDivFeatures(D, WaHDiv, Args,
423                        StringRef(WaHDiv->getValue()).substr(8), Features);
424  } else if (HDivArg)
425    getARMHWDivFeatures(D, HDivArg, Args, HDivArg->getValue(), Features);
426
427  // Handle (arch-dependent) fp16fml/fullfp16 relationship.
428  // Must happen before any features are disabled due to soft-float.
429  // FIXME: this fp16fml option handling will be reimplemented after the
430  // TargetParser rewrite.
431  const auto ItRNoFullFP16 = std::find(Features.rbegin(), Features.rend(), "-fullfp16");
432  const auto ItRFP16FML = std::find(Features.rbegin(), Features.rend(), "+fp16fml");
433  if (Triple.getSubArch() == llvm::Triple::SubArchType::ARMSubArch_v8_4a) {
434    const auto ItRFullFP16  = std::find(Features.rbegin(), Features.rend(), "+fullfp16");
435    if (ItRFullFP16 < ItRNoFullFP16 && ItRFullFP16 < ItRFP16FML) {
436      // Only entangled feature that can be to the right of this +fullfp16 is -fp16fml.
437      // Only append the +fp16fml if there is no -fp16fml after the +fullfp16.
438      if (std::find(Features.rbegin(), ItRFullFP16, "-fp16fml") == ItRFullFP16)
439        Features.push_back("+fp16fml");
440    }
441    else
442      goto fp16_fml_fallthrough;
443  }
444  else {
445fp16_fml_fallthrough:
446    // In both of these cases, putting the 'other' feature on the end of the vector will
447    // result in the same effect as placing it immediately after the current feature.
448    if (ItRNoFullFP16 < ItRFP16FML)
449      Features.push_back("-fp16fml");
450    else if (ItRNoFullFP16 > ItRFP16FML)
451      Features.push_back("+fullfp16");
452  }
453
454  // Setting -msoft-float/-mfloat-abi=soft effectively disables the FPU (GCC
455  // ignores the -mfpu options in this case).
456  // Note that the ABI can also be set implicitly by the target selected.
457  if (ABI == arm::FloatABI::Soft) {
458    llvm::ARM::getFPUFeatures(llvm::ARM::FK_NONE, Features);
459
460    // Disable all features relating to hardware FP, not already disabled by the
461    // above call.
462    Features.insert(Features.end(), {"-neon", "-crypto", "-dotprod", "-fp16fml",
463                                     "-mve", "-mve.fp", "-fpregs"});
464  } else if (FPUID == llvm::ARM::FK_NONE) {
465    // -mfpu=none is *very* similar to -mfloat-abi=soft, only that it should not
466    // disable MVE-I.
467    Features.insert(Features.end(),
468                    {"-neon", "-crypto", "-dotprod", "-fp16fml", "-mve.fp"});
469    // Even though we remove MVE-FP, we still need to check if it was originally
470    // present among the requested extensions, because it implies MVE-I, which
471    // should not be disabled by -mfpu-none.
472    if (!llvm::is_contained(Features, "+mve") &&
473        !llvm::is_contained(Features, "+mve.fp"))
474      Features.emplace_back("-fpregs");
475  }
476
477  // En/disable crc code generation.
478  if (Arg *A = Args.getLastArg(options::OPT_mcrc, options::OPT_mnocrc)) {
479    if (A->getOption().matches(options::OPT_mcrc))
480      Features.push_back("+crc");
481    else
482      Features.push_back("-crc");
483  }
484
485  // For Arch >= ARMv8.0 && A profile:  crypto = sha2 + aes
486  // FIXME: this needs reimplementation after the TargetParser rewrite
487  auto CryptoIt = llvm::find_if(llvm::reverse(Features), [](const StringRef F) {
488    return F.contains("crypto");
489  });
490  if (CryptoIt != Features.rend()) {
491    if (CryptoIt->take_front() == "+") {
492      StringRef ArchSuffix = arm::getLLVMArchSuffixForARM(
493          arm::getARMTargetCPU(CPUName, ArchName, Triple), ArchName, Triple);
494      if (llvm::ARM::parseArchVersion(ArchSuffix) >= 8 &&
495          llvm::ARM::parseArchProfile(ArchSuffix) ==
496              llvm::ARM::ProfileKind::A) {
497        if (ArchName.find_lower("+nosha2") == StringRef::npos &&
498            CPUName.find_lower("+nosha2") == StringRef::npos)
499          Features.push_back("+sha2");
500        if (ArchName.find_lower("+noaes") == StringRef::npos &&
501            CPUName.find_lower("+noaes") == StringRef::npos)
502          Features.push_back("+aes");
503      } else {
504        D.Diag(clang::diag::warn_target_unsupported_extension)
505            << "crypto"
506            << llvm::ARM::getArchName(llvm::ARM::parseArch(ArchSuffix));
507        // With -fno-integrated-as -mfpu=crypto-neon-fp-armv8 some assemblers such as the GNU assembler
508        // will permit the use of crypto instructions as the fpu will override the architecture.
509        // We keep the crypto feature in this case to preserve compatibility.
510        // In all other cases we remove the crypto feature.
511        if (!Args.hasArg(options::OPT_fno_integrated_as))
512          Features.push_back("-crypto");
513      }
514    }
515  }
516
517  // CMSE: Check for target 8M (for -mcmse to be applicable) is performed later.
518  if (Args.getLastArg(options::OPT_mcmse))
519    Features.push_back("+8msecext");
520
521  // Look for the last occurrence of -mlong-calls or -mno-long-calls. If
522  // neither options are specified, see if we are compiling for kernel/kext and
523  // decide whether to pass "+long-calls" based on the OS and its version.
524  if (Arg *A = Args.getLastArg(options::OPT_mlong_calls,
525                               options::OPT_mno_long_calls)) {
526    if (A->getOption().matches(options::OPT_mlong_calls))
527      Features.push_back("+long-calls");
528  } else if (KernelOrKext && (!Triple.isiOS() || Triple.isOSVersionLT(6)) &&
529             !Triple.isWatchOS()) {
530      Features.push_back("+long-calls");
531  }
532
533  // Generate execute-only output (no data access to code sections).
534  // This only makes sense for the compiler, not for the assembler.
535  if (!ForAS) {
536    // Supported only on ARMv6T2 and ARMv7 and above.
537    // Cannot be combined with -mno-movt or -mlong-calls
538    if (Arg *A = Args.getLastArg(options::OPT_mexecute_only, options::OPT_mno_execute_only)) {
539      if (A->getOption().matches(options::OPT_mexecute_only)) {
540        if (getARMSubArchVersionNumber(Triple) < 7 &&
541            llvm::ARM::parseArch(Triple.getArchName()) != llvm::ARM::ArchKind::ARMV6T2)
542              D.Diag(diag::err_target_unsupported_execute_only) << Triple.getArchName();
543        else if (Arg *B = Args.getLastArg(options::OPT_mno_movt))
544          D.Diag(diag::err_opt_not_valid_with_opt) << A->getAsString(Args) << B->getAsString(Args);
545        // Long calls create constant pool entries and have not yet been fixed up
546        // to play nicely with execute-only. Hence, they cannot be used in
547        // execute-only code for now
548        else if (Arg *B = Args.getLastArg(options::OPT_mlong_calls, options::OPT_mno_long_calls)) {
549          if (B->getOption().matches(options::OPT_mlong_calls))
550            D.Diag(diag::err_opt_not_valid_with_opt) << A->getAsString(Args) << B->getAsString(Args);
551        }
552        Features.push_back("+execute-only");
553      }
554    }
555  }
556
557  // Kernel code has more strict alignment requirements.
558  if (KernelOrKext)
559    Features.push_back("+strict-align");
560  else if (Arg *A = Args.getLastArg(options::OPT_mno_unaligned_access,
561                                    options::OPT_munaligned_access)) {
562    if (A->getOption().matches(options::OPT_munaligned_access)) {
563      // No v6M core supports unaligned memory access (v6M ARM ARM A3.2).
564      if (Triple.getSubArch() == llvm::Triple::SubArchType::ARMSubArch_v6m)
565        D.Diag(diag::err_target_unsupported_unaligned) << "v6m";
566      // v8M Baseline follows on from v6M, so doesn't support unaligned memory
567      // access either.
568      else if (Triple.getSubArch() == llvm::Triple::SubArchType::ARMSubArch_v8m_baseline)
569        D.Diag(diag::err_target_unsupported_unaligned) << "v8m.base";
570    } else
571      Features.push_back("+strict-align");
572  } else {
573    // Assume pre-ARMv6 doesn't support unaligned accesses.
574    //
575    // ARMv6 may or may not support unaligned accesses depending on the
576    // SCTLR.U bit, which is architecture-specific. We assume ARMv6
577    // Darwin and NetBSD targets support unaligned accesses, and others don't.
578    //
579    // ARMv7 always has SCTLR.U set to 1, but it has a new SCTLR.A bit
580    // which raises an alignment fault on unaligned accesses. Linux
581    // defaults this bit to 0 and handles it as a system-wide (not
582    // per-process) setting. It is therefore safe to assume that ARMv7+
583    // Linux targets support unaligned accesses. The same goes for NaCl.
584    //
585    // The above behavior is consistent with GCC.
586    int VersionNum = getARMSubArchVersionNumber(Triple);
587    if (Triple.isOSDarwin() || Triple.isOSNetBSD()) {
588      if (VersionNum < 6 ||
589          Triple.getSubArch() == llvm::Triple::SubArchType::ARMSubArch_v6m)
590        Features.push_back("+strict-align");
591    } else if (Triple.isOSLinux() || Triple.isOSNaCl()) {
592      if (VersionNum < 7)
593        Features.push_back("+strict-align");
594    } else
595      Features.push_back("+strict-align");
596  }
597
598  // llvm does not support reserving registers in general. There is support
599  // for reserving r9 on ARM though (defined as a platform-specific register
600  // in ARM EABI).
601  if (Args.hasArg(options::OPT_ffixed_r9))
602    Features.push_back("+reserve-r9");
603
604  // The kext linker doesn't know how to deal with movw/movt.
605  if (KernelOrKext || Args.hasArg(options::OPT_mno_movt))
606    Features.push_back("+no-movt");
607
608  if (Args.hasArg(options::OPT_mno_neg_immediates))
609    Features.push_back("+no-neg-immediates");
610}
611
612const std::string arm::getARMArch(StringRef Arch, const llvm::Triple &Triple) {
613  std::string MArch;
614  if (!Arch.empty())
615    MArch = Arch;
616  else
617    MArch = Triple.getArchName();
618  MArch = StringRef(MArch).split("+").first.lower();
619
620  // Handle -march=native.
621  if (MArch == "native") {
622    std::string CPU = llvm::sys::getHostCPUName();
623    if (CPU != "generic") {
624      // Translate the native cpu into the architecture suffix for that CPU.
625      StringRef Suffix = arm::getLLVMArchSuffixForARM(CPU, MArch, Triple);
626      // If there is no valid architecture suffix for this CPU we don't know how
627      // to handle it, so return no architecture.
628      if (Suffix.empty())
629        MArch = "";
630      else
631        MArch = std::string("arm") + Suffix.str();
632    }
633  }
634
635  return MArch;
636}
637
638/// Get the (LLVM) name of the minimum ARM CPU for the arch we are targeting.
639StringRef arm::getARMCPUForMArch(StringRef Arch, const llvm::Triple &Triple) {
640  std::string MArch = getARMArch(Arch, Triple);
641  // getARMCPUForArch defaults to the triple if MArch is empty, but empty MArch
642  // here means an -march=native that we can't handle, so instead return no CPU.
643  if (MArch.empty())
644    return StringRef();
645
646  // We need to return an empty string here on invalid MArch values as the
647  // various places that call this function can't cope with a null result.
648  return Triple.getARMCPUForArch(MArch);
649}
650
651/// getARMTargetCPU - Get the (LLVM) name of the ARM cpu we are targeting.
652std::string arm::getARMTargetCPU(StringRef CPU, StringRef Arch,
653                                 const llvm::Triple &Triple) {
654  // FIXME: Warn on inconsistent use of -mcpu and -march.
655  // If we have -mcpu=, use that.
656  if (!CPU.empty()) {
657    std::string MCPU = StringRef(CPU).split("+").first.lower();
658    // Handle -mcpu=native.
659    if (MCPU == "native")
660      return llvm::sys::getHostCPUName();
661    else
662      return MCPU;
663  }
664
665  return getARMCPUForMArch(Arch, Triple);
666}
667
668/// getLLVMArchSuffixForARM - Get the LLVM ArchKind value to use for a
669/// particular CPU (or Arch, if CPU is generic). This is needed to
670/// pass to functions like llvm::ARM::getDefaultFPU which need an
671/// ArchKind as well as a CPU name.
672llvm::ARM::ArchKind arm::getLLVMArchKindForARM(StringRef CPU, StringRef Arch,
673                                               const llvm::Triple &Triple) {
674  llvm::ARM::ArchKind ArchKind;
675  if (CPU == "generic" || CPU.empty()) {
676    std::string ARMArch = tools::arm::getARMArch(Arch, Triple);
677    ArchKind = llvm::ARM::parseArch(ARMArch);
678    if (ArchKind == llvm::ARM::ArchKind::INVALID)
679      // In case of generic Arch, i.e. "arm",
680      // extract arch from default cpu of the Triple
681      ArchKind = llvm::ARM::parseCPUArch(Triple.getARMCPUForArch(ARMArch));
682  } else {
683    // FIXME: horrible hack to get around the fact that Cortex-A7 is only an
684    // armv7k triple if it's actually been specified via "-arch armv7k".
685    ArchKind = (Arch == "armv7k" || Arch == "thumbv7k")
686                          ? llvm::ARM::ArchKind::ARMV7K
687                          : llvm::ARM::parseCPUArch(CPU);
688  }
689  return ArchKind;
690}
691
692/// getLLVMArchSuffixForARM - Get the LLVM arch name to use for a particular
693/// CPU  (or Arch, if CPU is generic).
694// FIXME: This is redundant with -mcpu, why does LLVM use this.
695StringRef arm::getLLVMArchSuffixForARM(StringRef CPU, StringRef Arch,
696                                       const llvm::Triple &Triple) {
697  llvm::ARM::ArchKind ArchKind = getLLVMArchKindForARM(CPU, Arch, Triple);
698  if (ArchKind == llvm::ARM::ArchKind::INVALID)
699    return "";
700  return llvm::ARM::getSubArch(ArchKind);
701}
702
703void arm::appendBE8LinkFlag(const ArgList &Args, ArgStringList &CmdArgs,
704                            const llvm::Triple &Triple) {
705  if (Args.hasArg(options::OPT_r))
706    return;
707
708  // ARMv7 (and later) and ARMv6-M do not support BE-32, so instruct the linker
709  // to generate BE-8 executables.
710  if (arm::getARMSubArchVersionNumber(Triple) >= 7 || arm::isARMMProfile(Triple))
711    CmdArgs.push_back("--be8");
712}
713