blob: aa3aca359cb8deab9e6fe74516caad663f288c15 [file] [log] [blame]
Inna Palantff3f07a2019-07-11 16:15:26 -07001//===-- ARMBaseInfo.h - Top level definitions for ARM ---*- C++ -*-===//
2//
Chih-Hung Hsieh43f06942019-12-19 15:01:08 -08003// 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
Inna Palantff3f07a2019-07-11 16:15:26 -07006//
7//===----------------------------------------------------------------------===//
8//
9// This file contains small standalone helper functions and enum definitions for
10// the ARM target useful for the compiler back-end and the MC libraries.
11// As such, it deliberately does not include references to LLVM core
12// code gen types, passes, etc..
13//
14//===----------------------------------------------------------------------===//
15
16#ifndef LLVM_LIB_TARGET_ARM_UTILS_ARMBASEINFO_H
17#define LLVM_LIB_TARGET_ARM_UTILS_ARMBASEINFO_H
18
19#include "llvm/ADT/StringSwitch.h"
20#include "llvm/Support/ErrorHandling.h"
21#include "llvm/MC/SubtargetFeature.h"
22#include "MCTargetDesc/ARMMCTargetDesc.h"
23
24namespace llvm {
25
26// Enums corresponding to ARM condition codes
27namespace ARMCC {
28// The CondCodes constants map directly to the 4-bit encoding of the
29// condition field for predicated instructions.
30enum CondCodes { // Meaning (integer) Meaning (floating-point)
31 EQ, // Equal Equal
32 NE, // Not equal Not equal, or unordered
33 HS, // Carry set >, ==, or unordered
34 LO, // Carry clear Less than
35 MI, // Minus, negative Less than
36 PL, // Plus, positive or zero >, ==, or unordered
37 VS, // Overflow Unordered
38 VC, // No overflow Not unordered
39 HI, // Unsigned higher Greater than, or unordered
40 LS, // Unsigned lower or same Less than or equal
41 GE, // Greater than or equal Greater than or equal
42 LT, // Less than Less than, or unordered
43 GT, // Greater than Greater than
44 LE, // Less than or equal <, ==, or unordered
45 AL // Always (unconditional) Always (unconditional)
46};
47
48inline static CondCodes getOppositeCondition(CondCodes CC) {
49 switch (CC) {
50 default: llvm_unreachable("Unknown condition code");
51 case EQ: return NE;
52 case NE: return EQ;
53 case HS: return LO;
54 case LO: return HS;
55 case MI: return PL;
56 case PL: return MI;
57 case VS: return VC;
58 case VC: return VS;
59 case HI: return LS;
60 case LS: return HI;
61 case GE: return LT;
62 case LT: return GE;
63 case GT: return LE;
64 case LE: return GT;
65 }
66}
67} // end namespace ARMCC
68
Chih-Hung Hsieh43f06942019-12-19 15:01:08 -080069namespace ARMVCC {
70 enum VPTCodes {
71 None = 0,
72 Then,
73 Else
74 };
75}
76
77inline static const char *ARMVPTPredToString(ARMVCC::VPTCodes CC) {
78 switch (CC) {
79 case ARMVCC::None: return "none";
80 case ARMVCC::Then: return "t";
81 case ARMVCC::Else: return "e";
82 }
83 llvm_unreachable("Unknown VPT code");
84}
85
86inline static unsigned ARMVectorCondCodeFromString(StringRef CC) {
87 return StringSwitch<unsigned>(CC.lower())
88 .Case("t", ARMVCC::Then)
89 .Case("e", ARMVCC::Else)
90 .Default(~0U);
91}
92
Inna Palantff3f07a2019-07-11 16:15:26 -070093inline static const char *ARMCondCodeToString(ARMCC::CondCodes CC) {
94 switch (CC) {
95 case ARMCC::EQ: return "eq";
96 case ARMCC::NE: return "ne";
97 case ARMCC::HS: return "hs";
98 case ARMCC::LO: return "lo";
99 case ARMCC::MI: return "mi";
100 case ARMCC::PL: return "pl";
101 case ARMCC::VS: return "vs";
102 case ARMCC::VC: return "vc";
103 case ARMCC::HI: return "hi";
104 case ARMCC::LS: return "ls";
105 case ARMCC::GE: return "ge";
106 case ARMCC::LT: return "lt";
107 case ARMCC::GT: return "gt";
108 case ARMCC::LE: return "le";
109 case ARMCC::AL: return "al";
110 }
111 llvm_unreachable("Unknown condition code");
112}
113
114inline static unsigned ARMCondCodeFromString(StringRef CC) {
115 return StringSwitch<unsigned>(CC.lower())
116 .Case("eq", ARMCC::EQ)
117 .Case("ne", ARMCC::NE)
118 .Case("hs", ARMCC::HS)
119 .Case("cs", ARMCC::HS)
120 .Case("lo", ARMCC::LO)
121 .Case("cc", ARMCC::LO)
122 .Case("mi", ARMCC::MI)
123 .Case("pl", ARMCC::PL)
124 .Case("vs", ARMCC::VS)
125 .Case("vc", ARMCC::VC)
126 .Case("hi", ARMCC::HI)
127 .Case("ls", ARMCC::LS)
128 .Case("ge", ARMCC::GE)
129 .Case("lt", ARMCC::LT)
130 .Case("gt", ARMCC::GT)
131 .Case("le", ARMCC::LE)
132 .Case("al", ARMCC::AL)
133 .Default(~0U);
134}
135
136// System Registers
137namespace ARMSysReg {
138 struct MClassSysReg {
139 const char *Name;
140 uint16_t M1Encoding12;
141 uint16_t M2M3Encoding8;
142 uint16_t Encoding;
143 FeatureBitset FeaturesRequired;
144
145 // return true if FeaturesRequired are all present in ActiveFeatures
146 bool hasRequiredFeatures(FeatureBitset ActiveFeatures) const {
147 return (FeaturesRequired & ActiveFeatures) == FeaturesRequired;
148 }
149
150 // returns true if TestFeatures are all present in FeaturesRequired
151 bool isInRequiredFeatures(FeatureBitset TestFeatures) const {
152 return (FeaturesRequired & TestFeatures) == TestFeatures;
153 }
154 };
155
156 #define GET_MCLASSSYSREG_DECL
157 #include "ARMGenSystemRegister.inc"
158
159 // lookup system register using 12-bit SYSm value.
160 // Note: the search is uniqued using M1 mask
161 const MClassSysReg *lookupMClassSysRegBy12bitSYSmValue(unsigned SYSm);
162
163 // returns APSR with _<bits> qualifier.
164 // Note: ARMv7-M deprecates using MSR APSR without a _<bits> qualifier
165 const MClassSysReg *lookupMClassSysRegAPSRNonDeprecated(unsigned SYSm);
166
167 // lookup system registers using 8-bit SYSm value
168 const MClassSysReg *lookupMClassSysRegBy8bitSYSmValue(unsigned SYSm);
169
170} // end namespace ARMSysReg
171
172// Banked Registers
173namespace ARMBankedReg {
174 struct BankedReg {
175 const char *Name;
176 uint16_t Encoding;
177 };
178 #define GET_BANKEDREG_DECL
179 #include "ARMGenSystemRegister.inc"
180} // end namespace ARMBankedReg
181
182} // end namespace llvm
183
184#endif // LLVM_LIB_TARGET_ARM_UTILS_ARMBASEINFO_H