clang  10.0.0git
RISCV.cpp
Go to the documentation of this file.
1 //===--- RISCV.cpp - Implement RISCV 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 RISCV TargetInfo objects.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "RISCV.h"
15 #include "llvm/ADT/StringSwitch.h"
16 
17 using namespace clang;
18 using namespace clang::targets;
19 
21  static const char *const GCCRegNames[] = {
22  // Integer registers
23  "x0", "x1", "x2", "x3", "x4", "x5", "x6", "x7",
24  "x8", "x9", "x10", "x11", "x12", "x13", "x14", "x15",
25  "x16", "x17", "x18", "x19", "x20", "x21", "x22", "x23",
26  "x24", "x25", "x26", "x27", "x28", "x29", "x30", "x31",
27 
28  // Floating point registers
29  "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7",
30  "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15",
31  "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
32  "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31"};
33  return llvm::makeArrayRef(GCCRegNames);
34 }
35 
37  static const TargetInfo::GCCRegAlias GCCRegAliases[] = {
38  {{"zero"}, "x0"}, {{"ra"}, "x1"}, {{"sp"}, "x2"}, {{"gp"}, "x3"},
39  {{"tp"}, "x4"}, {{"t0"}, "x5"}, {{"t1"}, "x6"}, {{"t2"}, "x7"},
40  {{"s0"}, "x8"}, {{"s1"}, "x9"}, {{"a0"}, "x10"}, {{"a1"}, "x11"},
41  {{"a2"}, "x12"}, {{"a3"}, "x13"}, {{"a4"}, "x14"}, {{"a5"}, "x15"},
42  {{"a6"}, "x16"}, {{"a7"}, "x17"}, {{"s2"}, "x18"}, {{"s3"}, "x19"},
43  {{"s4"}, "x20"}, {{"s5"}, "x21"}, {{"s6"}, "x22"}, {{"s7"}, "x23"},
44  {{"s8"}, "x24"}, {{"s9"}, "x25"}, {{"s10"}, "x26"}, {{"s11"}, "x27"},
45  {{"t3"}, "x28"}, {{"t4"}, "x29"}, {{"t5"}, "x30"}, {{"t6"}, "x31"},
46  {{"ft0"}, "f0"}, {{"ft1"}, "f1"}, {{"ft2"}, "f2"}, {{"ft3"}, "f3"},
47  {{"ft4"}, "f4"}, {{"ft5"}, "f5"}, {{"ft6"}, "f6"}, {{"ft7"}, "f7"},
48  {{"fs0"}, "f8"}, {{"fs1"}, "f9"}, {{"fa0"}, "f10"}, {{"fa1"}, "f11"},
49  {{"fa2"}, "f12"}, {{"fa3"}, "f13"}, {{"fa4"}, "f14"}, {{"fa5"}, "f15"},
50  {{"fa6"}, "f16"}, {{"fa7"}, "f17"}, {{"fs2"}, "f18"}, {{"fs3"}, "f19"},
51  {{"fs4"}, "f20"}, {{"fs5"}, "f21"}, {{"fs6"}, "f22"}, {{"fs7"}, "f23"},
52  {{"fs8"}, "f24"}, {{"fs9"}, "f25"}, {{"fs10"}, "f26"}, {{"fs11"}, "f27"},
53  {{"ft8"}, "f28"}, {{"ft9"}, "f29"}, {{"ft10"}, "f30"}, {{"ft11"}, "f31"}};
54  return llvm::makeArrayRef(GCCRegAliases);
55 }
56 
58  const char *&Name, TargetInfo::ConstraintInfo &Info) const {
59  switch (*Name) {
60  default:
61  return false;
62  case 'I':
63  // A 12-bit signed immediate.
64  Info.setRequiresImmediate(-2048, 2047);
65  return true;
66  case 'J':
67  // Integer zero.
68  Info.setRequiresImmediate(0);
69  return true;
70  case 'K':
71  // A 5-bit unsigned immediate for CSR access instructions.
72  Info.setRequiresImmediate(0, 31);
73  return true;
74  case 'f':
75  // A floating-point register.
76  Info.setAllowsRegister();
77  return true;
78  case 'A':
79  // An address that is held in a general-purpose register.
80  Info.setAllowsMemory();
81  return true;
82  }
83 }
84 
86  MacroBuilder &Builder) const {
87  Builder.defineMacro("__ELF__");
88  Builder.defineMacro("__riscv");
89  bool Is64Bit = getTriple().getArch() == llvm::Triple::riscv64;
90  Builder.defineMacro("__riscv_xlen", Is64Bit ? "64" : "32");
91  StringRef CodeModel = getTargetOpts().CodeModel;
92  if (CodeModel == "default")
93  CodeModel = "small";
94 
95  if (CodeModel == "small")
96  Builder.defineMacro("__riscv_cmodel_medlow");
97  else if (CodeModel == "medium")
98  Builder.defineMacro("__riscv_cmodel_medany");
99 
100  StringRef ABIName = getABI();
101  if (ABIName == "ilp32f" || ABIName == "lp64f")
102  Builder.defineMacro("__riscv_float_abi_single");
103  else if (ABIName == "ilp32d" || ABIName == "lp64d")
104  Builder.defineMacro("__riscv_float_abi_double");
105  else
106  Builder.defineMacro("__riscv_float_abi_soft");
107 
108  if (ABIName == "ilp32e")
109  Builder.defineMacro("__riscv_abi_rve");
110 
111  if (HasM) {
112  Builder.defineMacro("__riscv_mul");
113  Builder.defineMacro("__riscv_div");
114  Builder.defineMacro("__riscv_muldiv");
115  }
116 
117  if (HasA)
118  Builder.defineMacro("__riscv_atomic");
119 
120  if (HasF || HasD) {
121  Builder.defineMacro("__riscv_flen", HasD ? "64" : "32");
122  Builder.defineMacro("__riscv_fdiv");
123  Builder.defineMacro("__riscv_fsqrt");
124  }
125 
126  if (HasC)
127  Builder.defineMacro("__riscv_compressed");
128 }
129 
130 /// Return true if has this feature, need to sync with handleTargetFeatures.
131 bool RISCVTargetInfo::hasFeature(StringRef Feature) const {
132  bool Is64Bit = getTriple().getArch() == llvm::Triple::riscv64;
133  return llvm::StringSwitch<bool>(Feature)
134  .Case("riscv", true)
135  .Case("riscv32", !Is64Bit)
136  .Case("riscv64", Is64Bit)
137  .Case("m", HasM)
138  .Case("a", HasA)
139  .Case("f", HasF)
140  .Case("d", HasD)
141  .Case("c", HasC)
142  .Default(false);
143 }
144 
145 /// Perform initialization based on the user configured set of features.
146 bool RISCVTargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
147  DiagnosticsEngine &Diags) {
148  for (const auto &Feature : Features) {
149  if (Feature == "+m")
150  HasM = true;
151  else if (Feature == "+a")
152  HasA = true;
153  else if (Feature == "+f")
154  HasF = true;
155  else if (Feature == "+d")
156  HasD = true;
157  else if (Feature == "+c")
158  HasC = true;
159  }
160 
161  return true;
162 }
TargetOptions & getTargetOpts() const
Retrieve the target options.
Definition: TargetInfo.h:219
Defines the clang::MacroBuilder utility class.
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
Definition: TargetInfo.h:994
void setRequiresImmediate(int Min, int Max)
Definition: TargetInfo.h:897
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:53
bool validateAsmConstraint(const char *&Name, TargetInfo::ConstraintInfo &Info) const override
Definition: RISCV.cpp:57
Concrete class used by the front-end to report problems and issues.
Definition: Diagnostic.h:149
bool handleTargetFeatures(std::vector< std::string > &Features, DiagnosticsEngine &Diags) override
Perform initialization based on the user configured set of features.
Definition: RISCV.cpp:146
static const char *const GCCRegNames[]
Definition: X86.cpp:43
StringRef getABI() const override
Get the ABI currently in use.
Definition: RISCV.h:46
ArrayRef< const char * > getGCCRegNames() const override
Definition: RISCV.cpp:20
bool hasFeature(StringRef Feature) const override
Return true if has this feature, need to sync with handleTargetFeatures.
Definition: RISCV.cpp:131
Dataflow Directional Tag Classes.
void getTargetDefines(const LangOptions &Opts, MacroBuilder &Builder) const override
===-— Other target property query methods --------------------——===//
Definition: RISCV.cpp:85
std::string CodeModel
Definition: TargetOptions.h:75
void defineMacro(const Twine &Name, const Twine &Value="1")
Append a #define line for macro of the form "\#define Name Value\n".
Definition: MacroBuilder.h:29
ArrayRef< TargetInfo::GCCRegAlias > getGCCRegAliases() const override
Definition: RISCV.cpp:36