Coverage Report

Created: 2021-08-24 07:12

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/Basic/Targets/Hexagon.cpp
Line
Count
Source (jump to first uncovered line)
1
//===--- Hexagon.cpp - Implement Hexagon 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 Hexagon TargetInfo objects.
10
//
11
//===----------------------------------------------------------------------===//
12
13
#include "Hexagon.h"
14
#include "Targets.h"
15
#include "clang/Basic/MacroBuilder.h"
16
#include "clang/Basic/TargetBuiltins.h"
17
#include "llvm/ADT/StringSwitch.h"
18
19
using namespace clang;
20
using namespace clang::targets;
21
22
void HexagonTargetInfo::getTargetDefines(const LangOptions &Opts,
23
73
                                         MacroBuilder &Builder) const {
24
73
  Builder.defineMacro("__qdsp6__", "1");
25
73
  Builder.defineMacro("__hexagon__", "1");
26
27
73
  Builder.defineMacro("__ELF__");
28
29
  // The macro __HVXDBL__ is deprecated.
30
73
  bool DefineHvxDbl = false;
31
32
73
  if (CPU == "hexagonv5") {
33
1
    Builder.defineMacro("__HEXAGON_V5__");
34
1
    Builder.defineMacro("__HEXAGON_ARCH__", "5");
35
1
    if (Opts.HexagonQdsp6Compat) {
36
0
      Builder.defineMacro("__QDSP6_V5__");
37
0
      Builder.defineMacro("__QDSP6_ARCH__", "5");
38
0
    }
39
72
  } else if (CPU == "hexagonv55") {
40
4
    Builder.defineMacro("__HEXAGON_V55__");
41
4
    Builder.defineMacro("__HEXAGON_ARCH__", "55");
42
4
    Builder.defineMacro("__QDSP6_V55__");
43
4
    Builder.defineMacro("__QDSP6_ARCH__", "55");
44
68
  } else if (CPU == "hexagonv60") {
45
15
    DefineHvxDbl = true;
46
15
    Builder.defineMacro("__HEXAGON_V60__");
47
15
    Builder.defineMacro("__HEXAGON_ARCH__", "60");
48
15
    Builder.defineMacro("__QDSP6_V60__");
49
15
    Builder.defineMacro("__QDSP6_ARCH__", "60");
50
53
  } else if (CPU == "hexagonv62") {
51
7
    DefineHvxDbl = true;
52
7
    Builder.defineMacro("__HEXAGON_V62__");
53
7
    Builder.defineMacro("__HEXAGON_ARCH__", "62");
54
46
  } else if (CPU == "hexagonv65") {
55
6
    DefineHvxDbl = true;
56
6
    Builder.defineMacro("__HEXAGON_V65__");
57
6
    Builder.defineMacro("__HEXAGON_ARCH__", "65");
58
40
  } else if (CPU == "hexagonv66") {
59
7
    DefineHvxDbl = true;
60
7
    Builder.defineMacro("__HEXAGON_V66__");
61
7
    Builder.defineMacro("__HEXAGON_ARCH__", "66");
62
33
  } else if (CPU == "hexagonv67") {
63
6
    Builder.defineMacro("__HEXAGON_V67__");
64
6
    Builder.defineMacro("__HEXAGON_ARCH__", "67");
65
27
  } else if (CPU == "hexagonv67t") {
66
3
    Builder.defineMacro("__HEXAGON_V67T__");
67
3
    Builder.defineMacro("__HEXAGON_ARCH__", "67");
68
24
  } else if (CPU == "hexagonv68") {
69
10
    Builder.defineMacro("__HEXAGON_V68__");
70
10
    Builder.defineMacro("__HEXAGON_ARCH__", "68");
71
10
  }
72
73
73
  if (hasFeature("hvx-length64b")) {
74
7
    Builder.defineMacro("__HVX__");
75
7
    Builder.defineMacro("__HVX_ARCH__", HVXVersion);
76
7
    Builder.defineMacro("__HVX_LENGTH__", "64");
77
7
  }
78
79
73
  if (hasFeature("hvx-length128b")) {
80
22
    Builder.defineMacro("__HVX__");
81
22
    Builder.defineMacro("__HVX_ARCH__", HVXVersion);
82
22
    Builder.defineMacro("__HVX_LENGTH__", "128");
83
22
    if (DefineHvxDbl)
84
12
      Builder.defineMacro("__HVXDBL__");
85
22
  }
86
87
73
  if (hasFeature("audio")) {
88
4
    Builder.defineMacro("__HEXAGON_AUDIO__");
89
4
  }
90
91
73
  std::string NumPhySlots = isTinyCore() ? 
"3"3
:
"4"70
;
92
73
  Builder.defineMacro("__HEXAGON_PHYSICAL_SLOTS__", NumPhySlots);
93
73
}
94
95
bool HexagonTargetInfo::initFeatureMap(
96
    llvm::StringMap<bool> &Features, DiagnosticsEngine &Diags, StringRef CPU,
97
73
    const std::vector<std::string> &FeaturesVec) const {
98
73
  if (isTinyCore())
99
3
    Features["audio"] = true;
100
101
73
  StringRef CPUFeature = CPU;
102
73
  CPUFeature.consume_front("hexagon");
103
73
  CPUFeature.consume_back("t");
104
73
  if (!CPUFeature.empty())
105
59
    Features[CPUFeature] = true;
106
107
73
  Features["long-calls"] = false;
108
109
73
  return TargetInfo::initFeatureMap(Features, Diags, CPU, FeaturesVec);
110
73
}
111
112
bool HexagonTargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
113
73
                                             DiagnosticsEngine &Diags) {
114
195
  for (auto &F : Features) {
115
195
    if (F == "+hvx-length64b")
116
7
      HasHVX = HasHVX64B = true;
117
188
    else if (F == "+hvx-length128b")
118
22
      HasHVX = HasHVX128B = true;
119
166
    else if (F.find("+hvxv") != std::string::npos) {
120
28
      HasHVX = true;
121
28
      HVXVersion = F.substr(std::string("+hvxv").length());
122
138
    } else if (F == "-hvx")
123
0
      HasHVX = HasHVX64B = HasHVX128B = false;
124
138
    else if (F == "+long-calls")
125
0
      UseLongCalls = true;
126
138
    else if (F == "-long-calls")
127
73
      UseLongCalls = false;
128
65
    else if (F == "+audio")
129
4
      HasAudio = true;
130
195
  }
131
73
  return true;
132
73
}
133
134
const char *const HexagonTargetInfo::GCCRegNames[] = {
135
    // Scalar registers:
136
    "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11",
137
    "r12", "r13", "r14", "r15", "r16", "r17", "r18", "r19", "r20", "r21",
138
    "r22", "r23", "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
139
    "r1:0", "r3:2", "r5:4", "r7:6", "r9:8", "r11:10", "r13:12", "r15:14",
140
    "r17:16", "r19:18", "r21:20", "r23:22", "r25:24", "r27:26", "r29:28",
141
    "r31:30",
142
    // Predicate registers:
143
    "p0", "p1", "p2", "p3",
144
    // Control registers:
145
    "c0", "c1", "c2", "c3", "c4", "c5", "c6", "c7", "c8", "c9", "c10", "c11",
146
    "c12", "c13", "c14", "c15", "c16", "c17", "c18", "c19", "c20", "c21",
147
    "c22", "c23", "c24", "c25", "c26", "c27", "c28", "c29", "c30", "c31",
148
    "c1:0", "c3:2", "c5:4", "c7:6", "c9:8", "c11:10", "c13:12", "c15:14",
149
    "c17:16", "c19:18", "c21:20", "c23:22", "c25:24", "c27:26", "c29:28",
150
    "c31:30",
151
    // Control register aliases:
152
    "sa0", "lc0", "sa1", "lc1", "p3:0", "m0",  "m1",  "usr", "pc", "ugp",
153
    "gp", "cs0", "cs1", "upcyclelo", "upcyclehi", "framelimit", "framekey",
154
    "pktcountlo", "pktcounthi", "utimerlo", "utimerhi",
155
    "upcycle", "pktcount", "utimer",
156
    // HVX vector registers:
157
    "v0", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "v9", "v10", "v11",
158
    "v12", "v13", "v14", "v15", "v16", "v17", "v18", "v19", "v20", "v21",
159
    "v22", "v23", "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31",
160
    "v1:0", "v3:2", "v5:4", "v7:6", "v9:8", "v11:10", "v13:12", "v15:14",
161
    "v17:16", "v19:18", "v21:20", "v23:22", "v25:24", "v27:26", "v29:28",
162
    "v31:30",
163
    "v3:0", "v7:4", "v11:8", "v15:12", "v19:16", "v23:20", "v27:24", "v31:28",
164
    // HVX vector predicates:
165
    "q0", "q1", "q2", "q3",
166
};
167
168
921
ArrayRef<const char *> HexagonTargetInfo::getGCCRegNames() const {
169
921
  return llvm::makeArrayRef(GCCRegNames);
170
921
}
171
172
const TargetInfo::GCCRegAlias HexagonTargetInfo::GCCRegAliases[] = {
173
    {{"sp"}, "r29"},
174
    {{"fp"}, "r30"},
175
    {{"lr"}, "r31"},
176
};
177
178
369
ArrayRef<TargetInfo::GCCRegAlias> HexagonTargetInfo::getGCCRegAliases() const {
179
369
  return llvm::makeArrayRef(GCCRegAliases);
180
369
}
181
182
const Builtin::Info HexagonTargetInfo::BuiltinInfo[] = {
183
#define BUILTIN(ID, TYPE, ATTRS)                                               \
184
  {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, nullptr},
185
#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER)                                    \
186
  {#ID, TYPE, ATTRS, HEADER, ALL_LANGUAGES, nullptr},
187
#define TARGET_BUILTIN(ID, TYPE, ATTRS, FEATURE)                               \
188
  {#ID, TYPE, ATTRS, nullptr, ALL_LANGUAGES, FEATURE},
189
#include "clang/Basic/BuiltinsHexagon.def"
190
};
191
192
282
bool HexagonTargetInfo::hasFeature(StringRef Feature) const {
193
282
  std::string VS = "hvxv" + HVXVersion;
194
282
  if (Feature == VS)
195
0
    return true;
196
197
282
  return llvm::StringSwitch<bool>(Feature)
198
282
      .Case("hexagon", true)
199
282
      .Case("hvx", HasHVX)
200
282
      .Case("hvx-length64b", HasHVX64B)
201
282
      .Case("hvx-length128b", HasHVX128B)
202
282
      .Case("long-calls", UseLongCalls)
203
282
      .Case("audio", HasAudio)
204
282
      .Default(false);
205
282
}
206
207
struct CPUSuffix {
208
  llvm::StringLiteral Name;
209
  llvm::StringLiteral Suffix;
210
};
211
212
static constexpr CPUSuffix Suffixes[] = {
213
    {{"hexagonv5"},  {"5"}},  {{"hexagonv55"},  {"55"}},
214
    {{"hexagonv60"}, {"60"}}, {{"hexagonv62"},  {"62"}},
215
    {{"hexagonv65"}, {"65"}}, {{"hexagonv66"},  {"66"}},
216
    {{"hexagonv67"}, {"67"}}, {{"hexagonv67t"}, {"67t"}},
217
    {{"hexagonv68"}, {"68"}},
218
};
219
220
60
const char *HexagonTargetInfo::getHexagonCPUSuffix(StringRef Name) {
221
60
  const CPUSuffix *Item = llvm::find_if(
222
319
      Suffixes, [Name](const CPUSuffix &S) { return S.Name == Name; });
223
60
  if (Item == std::end(Suffixes))
224
1
    return nullptr;
225
59
  return Item->Suffix.data();
226
60
}
227
228
void HexagonTargetInfo::fillValidCPUList(
229
1
    SmallVectorImpl<StringRef> &Values) const {
230
1
  for (const CPUSuffix &Suffix : Suffixes)
231
9
    Values.push_back(Suffix.Name);
232
1
}
233
234
73
ArrayRef<Builtin::Info> HexagonTargetInfo::getTargetBuiltins() const {
235
73
  return llvm::makeArrayRef(BuiltinInfo, clang::Hexagon::LastTSBuiltin -
236
73
                                             Builtin::FirstTSBuiltin);
237
73
}