LLVM  4.0.0
AArch64LegalizerInfo.cpp
Go to the documentation of this file.
1 //===- AArch64LegalizerInfo.cpp ----------------------------------*- C++ -*-==//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 /// \file
10 /// This file implements the targeting of the Machinelegalizer class for
11 /// AArch64.
12 /// \todo This should be generated by TableGen.
13 //===----------------------------------------------------------------------===//
14 
15 #include "AArch64LegalizerInfo.h"
17 #include "llvm/IR/Type.h"
18 #include "llvm/IR/DerivedTypes.h"
20 
21 using namespace llvm;
22 
23 #ifndef LLVM_BUILD_GLOBAL_ISEL
24 #error "You shouldn't build this"
25 #endif
26 
28  using namespace TargetOpcode;
29  const LLT p0 = LLT::pointer(0, 64);
30  const LLT s1 = LLT::scalar(1);
31  const LLT s8 = LLT::scalar(8);
32  const LLT s16 = LLT::scalar(16);
33  const LLT s32 = LLT::scalar(32);
34  const LLT s64 = LLT::scalar(64);
35  const LLT v2s32 = LLT::vector(2, 32);
36  const LLT v4s32 = LLT::vector(4, 32);
37  const LLT v2s64 = LLT::vector(2, 64);
38 
39  for (auto BinOp : {G_ADD, G_SUB, G_MUL, G_AND, G_OR, G_XOR, G_SHL}) {
40  // These operations naturally get the right answer when used on
41  // GPR32, even if the actual type is narrower.
42  for (auto Ty : {s1, s8, s16, s32, s64, v2s32, v4s32, v2s64})
43  setAction({BinOp, Ty}, Legal);
44  }
45 
46  setAction({G_GEP, p0}, Legal);
47  setAction({G_GEP, 1, s64}, Legal);
48 
49  for (auto Ty : {s1, s8, s16, s32})
50  setAction({G_GEP, 1, Ty}, WidenScalar);
51 
52  for (auto BinOp : {G_LSHR, G_ASHR, G_SDIV, G_UDIV}) {
53  for (auto Ty : {s32, s64})
54  setAction({BinOp, Ty}, Legal);
55 
56  for (auto Ty : {s1, s8, s16})
57  setAction({BinOp, Ty}, WidenScalar);
58  }
59 
60  for (auto BinOp : { G_SREM, G_UREM })
61  for (auto Ty : { s1, s8, s16, s32, s64 })
62  setAction({BinOp, Ty}, Lower);
63 
64  for (auto Op : { G_UADDE, G_USUBE, G_SADDO, G_SSUBO, G_SMULO, G_UMULO }) {
65  for (auto Ty : { s32, s64 })
66  setAction({Op, Ty}, Legal);
67 
68  setAction({Op, 1, s1}, Legal);
69  }
70 
71  for (auto BinOp : {G_FADD, G_FSUB, G_FMUL, G_FDIV})
72  for (auto Ty : {s32, s64})
73  setAction({BinOp, Ty}, Legal);
74 
75  setAction({G_FREM, s32}, Libcall);
76  setAction({G_FREM, s64}, Libcall);
77 
78  for (auto MemOp : {G_LOAD, G_STORE}) {
79  for (auto Ty : {s8, s16, s32, s64, p0, v2s32})
80  setAction({MemOp, Ty}, Legal);
81 
82  setAction({MemOp, s1}, WidenScalar);
83 
84  // And everything's fine in addrspace 0.
85  setAction({MemOp, 1, p0}, Legal);
86  }
87 
88  // Constants
89  for (auto Ty : {s32, s64}) {
90  setAction({TargetOpcode::G_CONSTANT, Ty}, Legal);
91  setAction({TargetOpcode::G_FCONSTANT, Ty}, Legal);
92  }
93 
94  setAction({G_CONSTANT, p0}, Legal);
95 
96  for (auto Ty : {s1, s8, s16})
97  setAction({TargetOpcode::G_CONSTANT, Ty}, WidenScalar);
98 
99  setAction({TargetOpcode::G_FCONSTANT, s16}, WidenScalar);
100 
101  setAction({G_ICMP, s1}, Legal);
102  setAction({G_ICMP, 1, s32}, Legal);
103  setAction({G_ICMP, 1, s64}, Legal);
104  setAction({G_ICMP, 1, p0}, Legal);
105 
106  for (auto Ty : {s1, s8, s16}) {
107  setAction({G_ICMP, 1, Ty}, WidenScalar);
108  }
109 
110  setAction({G_FCMP, s1}, Legal);
111  setAction({G_FCMP, 1, s32}, Legal);
112  setAction({G_FCMP, 1, s64}, Legal);
113 
114  // Extensions
115  for (auto Ty : { s1, s8, s16, s32, s64 }) {
116  setAction({G_ZEXT, Ty}, Legal);
117  setAction({G_SEXT, Ty}, Legal);
118  setAction({G_ANYEXT, Ty}, Legal);
119  }
120 
121  for (auto Ty : { s1, s8, s16, s32 }) {
122  setAction({G_ZEXT, 1, Ty}, Legal);
123  setAction({G_SEXT, 1, Ty}, Legal);
124  setAction({G_ANYEXT, 1, Ty}, Legal);
125  }
126 
127  setAction({G_FPEXT, s64}, Legal);
128  setAction({G_FPEXT, 1, s32}, Legal);
129 
130  // Truncations
131  for (auto Ty : { s16, s32 })
132  setAction({G_FPTRUNC, Ty}, Legal);
133 
134  for (auto Ty : { s32, s64 })
135  setAction({G_FPTRUNC, 1, Ty}, Legal);
136 
137  for (auto Ty : { s1, s8, s16, s32 })
138  setAction({G_TRUNC, Ty}, Legal);
139 
140  for (auto Ty : { s8, s16, s32, s64 })
141  setAction({G_TRUNC, 1, Ty}, Legal);
142 
143  // Conversions
144  for (auto Ty : { s1, s8, s16, s32, s64 }) {
145  setAction({G_FPTOSI, 0, Ty}, Legal);
146  setAction({G_FPTOUI, 0, Ty}, Legal);
147  setAction({G_SITOFP, 1, Ty}, Legal);
148  setAction({G_UITOFP, 1, Ty}, Legal);
149  }
150 
151  for (auto Ty : { s32, s64 }) {
152  setAction({G_FPTOSI, 1, Ty}, Legal);
153  setAction({G_FPTOUI, 1, Ty}, Legal);
154  setAction({G_SITOFP, 0, Ty}, Legal);
155  setAction({G_UITOFP, 0, Ty}, Legal);
156  }
157 
158  // Control-flow
159  for (auto Ty : {s1, s8, s16, s32})
160  setAction({G_BRCOND, Ty}, Legal);
161 
162  // Select
163  for (auto Ty : {s1, s8, s16, s32, s64})
164  setAction({G_SELECT, Ty}, Legal);
165 
166  setAction({G_SELECT, 1, s1}, Legal);
167 
168  // Pointer-handling
169  setAction({G_FRAME_INDEX, p0}, Legal);
170  setAction({G_GLOBAL_VALUE, p0}, Legal);
171 
172  for (auto Ty : {s1, s8, s16, s32, s64})
173  setAction({G_PTRTOINT, 0, Ty}, Legal);
174 
175  setAction({G_PTRTOINT, 1, p0}, Legal);
176 
177  setAction({G_INTTOPTR, 0, p0}, Legal);
178  setAction({G_INTTOPTR, 1, s64}, Legal);
179 
180  // Casts for 32 and 64-bit width type are just copies.
181  for (auto Ty : {s1, s8, s16, s32, s64}) {
182  setAction({G_BITCAST, 0, Ty}, Legal);
183  setAction({G_BITCAST, 1, Ty}, Legal);
184  }
185 
186  // For the sake of copying bits around, the type does not really
187  // matter as long as it fits a register.
188  for (int EltSize = 8; EltSize <= 64; EltSize *= 2) {
189  setAction({G_BITCAST, 0, LLT::vector(128/EltSize, EltSize)}, Legal);
190  setAction({G_BITCAST, 1, LLT::vector(128/EltSize, EltSize)}, Legal);
191  if (EltSize >= 64)
192  continue;
193 
194  setAction({G_BITCAST, 0, LLT::vector(64/EltSize, EltSize)}, Legal);
195  setAction({G_BITCAST, 1, LLT::vector(64/EltSize, EltSize)}, Legal);
196  if (EltSize >= 32)
197  continue;
198 
199  setAction({G_BITCAST, 0, LLT::vector(32/EltSize, EltSize)}, Legal);
200  setAction({G_BITCAST, 1, LLT::vector(32/EltSize, EltSize)}, Legal);
201  }
202 
203  computeTables();
204 }
This file declares the targeting of the Machinelegalizer class for AArch64.
void computeTables()
Compute any ancillary tables needed to quickly decide how an operation should be handled.
static LLT scalar(unsigned SizeInBits)
Get a low-level scalar or aggregate "bag of bits".
Definition: LowLevelType.h:51
The operation should be implemented as a call to some kind of runtime support library.
Definition: LegalizerInfo.h:84
The operation should be implemented in terms of a wider scalar base-type.
Definition: LegalizerInfo.h:64
The operation itself must be expressed in terms of simpler actions on this target.
Definition: LegalizerInfo.h:79
The operation is expected to be selectable directly by the target, and no transformation is necessary...
Definition: LegalizerInfo.h:54
static LLT pointer(uint16_t AddressSpace, unsigned SizeInBits)
Get a low-level pointer in the given address space (defaulting to 0).
Definition: LowLevelType.h:57
static LLT vector(uint16_t NumElements, unsigned ScalarSizeInBits)
Get a low-level vector of some number of elements and element width.
Definition: LowLevelType.h:63
void setAction(const InstrAspect &Aspect, LegalizeAction Action)
More friendly way to set an action for common types that have an LLT representation.