1 /*
2 * Copyright (c) 2000, 2020, Oracle and/or its affiliates. All rights reserved.
3 * Copyright (c) 2014, 2020, Red Hat Inc. All rights reserved.
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 *
6 * This code is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License version 2 only, as
8 * published by the Free Software Foundation.
9 *
10 * This code is distributed in the hope that it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
13 * version 2 for more details (a copy is included in the LICENSE file that
14 * accompanied this code).
15 *
16 * You should have received a copy of the GNU General Public License version
17 * 2 along with this work; if not, write to the Free Software Foundation,
18 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
19 *
20 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
21 * or visit www.oracle.com if you need additional information or have any
22 * questions.
23 *
24 */
25
26 #ifndef CPU_AARCH64_REGISTER_AARCH64_HPP
27 #define CPU_AARCH64_REGISTER_AARCH64_HPP
28
29 #include "asm/register.hpp"
30 #include "utilities/powerOfTwo.hpp"
31
32 class VMRegImpl;
33 typedef VMRegImpl* VMReg;
34
35 // Use Register as shortcut
36 class RegisterImpl;
37 typedef RegisterImpl* Register;
38
as_Register(int encoding)39 inline Register as_Register(int encoding) {
40 return (Register)(intptr_t) encoding;
41 }
42
43 class RegisterImpl: public AbstractRegisterImpl {
44 public:
45 enum {
46 number_of_registers = 32,
47 number_of_byte_registers = 32,
48 number_of_registers_for_jvmci = 34, // Including SP and ZR.
49 max_slots_per_register = 2
50 };
51
52 // derived registers, offsets, and addresses
successor() const53 Register successor() const { return as_Register(encoding() + 1); }
54
55 // construction
56 inline friend Register as_Register(int encoding);
57
58 VMReg as_VMReg();
59
60 // accessors
encoding() const61 int encoding() const { assert(is_valid(), "invalid register"); return (intptr_t)this; }
is_valid() const62 bool is_valid() const { return 0 <= (intptr_t)this && (intptr_t)this < number_of_registers; }
has_byte_register() const63 bool has_byte_register() const { return 0 <= (intptr_t)this && (intptr_t)this < number_of_byte_registers; }
64 const char* name() const;
encoding_nocheck() const65 int encoding_nocheck() const { return (intptr_t)this; }
66
67 // Return the bit which represents this register. This is intended
68 // to be ORed into a bitmask: for usage see class RegSet below.
bit(bool should_set=true) const69 uint64_t bit(bool should_set = true) const { return should_set ? 1 << encoding() : 0; }
70 };
71
72 // The integer registers of the aarch64 architecture
73
74 CONSTANT_REGISTER_DECLARATION(Register, noreg, (-1));
75
76
77 CONSTANT_REGISTER_DECLARATION(Register, r0, (0));
78 CONSTANT_REGISTER_DECLARATION(Register, r1, (1));
79 CONSTANT_REGISTER_DECLARATION(Register, r2, (2));
80 CONSTANT_REGISTER_DECLARATION(Register, r3, (3));
81 CONSTANT_REGISTER_DECLARATION(Register, r4, (4));
82 CONSTANT_REGISTER_DECLARATION(Register, r5, (5));
83 CONSTANT_REGISTER_DECLARATION(Register, r6, (6));
84 CONSTANT_REGISTER_DECLARATION(Register, r7, (7));
85 CONSTANT_REGISTER_DECLARATION(Register, r8, (8));
86 CONSTANT_REGISTER_DECLARATION(Register, r9, (9));
87 CONSTANT_REGISTER_DECLARATION(Register, r10, (10));
88 CONSTANT_REGISTER_DECLARATION(Register, r11, (11));
89 CONSTANT_REGISTER_DECLARATION(Register, r12, (12));
90 CONSTANT_REGISTER_DECLARATION(Register, r13, (13));
91 CONSTANT_REGISTER_DECLARATION(Register, r14, (14));
92 CONSTANT_REGISTER_DECLARATION(Register, r15, (15));
93 CONSTANT_REGISTER_DECLARATION(Register, r16, (16));
94 CONSTANT_REGISTER_DECLARATION(Register, r17, (17));
95
96 // In the ABI for Windows+AArch64 the register r18 is used to store the pointer
97 // to the current thread's TEB (where TLS variables are stored). We could
98 // carefully save and restore r18 at key places, however Win32 Structured
99 // Exception Handling (SEH) is using TLS to unwind the stack. If r18 is used
100 // for any other purpose at the time of an exception happening, SEH would not
101 // be able to unwind the stack properly and most likely crash.
102 //
103 // It's easier to avoid allocating r18 altogether.
104 //
105 // See https://docs.microsoft.com/en-us/cpp/build/arm64-windows-abi-conventions?view=vs-2019#integer-registers
106 CONSTANT_REGISTER_DECLARATION(Register, r18_tls, (18));
107 CONSTANT_REGISTER_DECLARATION(Register, r19, (19));
108 CONSTANT_REGISTER_DECLARATION(Register, r20, (20));
109 CONSTANT_REGISTER_DECLARATION(Register, r21, (21));
110 CONSTANT_REGISTER_DECLARATION(Register, r22, (22));
111 CONSTANT_REGISTER_DECLARATION(Register, r23, (23));
112 CONSTANT_REGISTER_DECLARATION(Register, r24, (24));
113 CONSTANT_REGISTER_DECLARATION(Register, r25, (25));
114 CONSTANT_REGISTER_DECLARATION(Register, r26, (26));
115 CONSTANT_REGISTER_DECLARATION(Register, r27, (27));
116 CONSTANT_REGISTER_DECLARATION(Register, r28, (28));
117 CONSTANT_REGISTER_DECLARATION(Register, r29, (29));
118 CONSTANT_REGISTER_DECLARATION(Register, r30, (30));
119
120
121 // r31 is not a general purpose register, but represents either the
122 // stack pointer or the zero/discard register depending on the
123 // instruction.
124 CONSTANT_REGISTER_DECLARATION(Register, r31_sp, (31));
125 CONSTANT_REGISTER_DECLARATION(Register, zr, (32));
126 CONSTANT_REGISTER_DECLARATION(Register, sp, (33));
127
128 // Used as a filler in instructions where a register field is unused.
129 const Register dummy_reg = r31_sp;
130
131 // Use FloatRegister as shortcut
132 class FloatRegisterImpl;
133 typedef FloatRegisterImpl* FloatRegister;
134
as_FloatRegister(int encoding)135 inline FloatRegister as_FloatRegister(int encoding) {
136 return (FloatRegister)(intptr_t) encoding;
137 }
138
139 // The implementation of floating point registers for the architecture
140 class FloatRegisterImpl: public AbstractRegisterImpl {
141 public:
142 enum {
143 number_of_registers = 32,
144 max_slots_per_register = 8,
145 save_slots_per_register = 2,
146 slots_per_neon_register = 4,
147 extra_save_slots_per_neon_register = slots_per_neon_register - save_slots_per_register
148 };
149
150 // construction
151 inline friend FloatRegister as_FloatRegister(int encoding);
152
153 VMReg as_VMReg();
154
155 // derived registers, offsets, and addresses
successor() const156 FloatRegister successor() const { return as_FloatRegister((encoding() + 1) % 32); }
157
158 // accessors
encoding() const159 int encoding() const { assert(is_valid(), "invalid register"); return (intptr_t)this; }
encoding_nocheck() const160 int encoding_nocheck() const { return (intptr_t)this; }
is_valid() const161 bool is_valid() const { return 0 <= (intptr_t)this && (intptr_t)this < number_of_registers; }
162 const char* name() const;
163
164 };
165
166 // The float registers of the AARCH64 architecture
167
168 CONSTANT_REGISTER_DECLARATION(FloatRegister, fnoreg , (-1));
169
170 CONSTANT_REGISTER_DECLARATION(FloatRegister, v0 , ( 0));
171 CONSTANT_REGISTER_DECLARATION(FloatRegister, v1 , ( 1));
172 CONSTANT_REGISTER_DECLARATION(FloatRegister, v2 , ( 2));
173 CONSTANT_REGISTER_DECLARATION(FloatRegister, v3 , ( 3));
174 CONSTANT_REGISTER_DECLARATION(FloatRegister, v4 , ( 4));
175 CONSTANT_REGISTER_DECLARATION(FloatRegister, v5 , ( 5));
176 CONSTANT_REGISTER_DECLARATION(FloatRegister, v6 , ( 6));
177 CONSTANT_REGISTER_DECLARATION(FloatRegister, v7 , ( 7));
178 CONSTANT_REGISTER_DECLARATION(FloatRegister, v8 , ( 8));
179 CONSTANT_REGISTER_DECLARATION(FloatRegister, v9 , ( 9));
180 CONSTANT_REGISTER_DECLARATION(FloatRegister, v10 , (10));
181 CONSTANT_REGISTER_DECLARATION(FloatRegister, v11 , (11));
182 CONSTANT_REGISTER_DECLARATION(FloatRegister, v12 , (12));
183 CONSTANT_REGISTER_DECLARATION(FloatRegister, v13 , (13));
184 CONSTANT_REGISTER_DECLARATION(FloatRegister, v14 , (14));
185 CONSTANT_REGISTER_DECLARATION(FloatRegister, v15 , (15));
186 CONSTANT_REGISTER_DECLARATION(FloatRegister, v16 , (16));
187 CONSTANT_REGISTER_DECLARATION(FloatRegister, v17 , (17));
188 CONSTANT_REGISTER_DECLARATION(FloatRegister, v18 , (18));
189 CONSTANT_REGISTER_DECLARATION(FloatRegister, v19 , (19));
190 CONSTANT_REGISTER_DECLARATION(FloatRegister, v20 , (20));
191 CONSTANT_REGISTER_DECLARATION(FloatRegister, v21 , (21));
192 CONSTANT_REGISTER_DECLARATION(FloatRegister, v22 , (22));
193 CONSTANT_REGISTER_DECLARATION(FloatRegister, v23 , (23));
194 CONSTANT_REGISTER_DECLARATION(FloatRegister, v24 , (24));
195 CONSTANT_REGISTER_DECLARATION(FloatRegister, v25 , (25));
196 CONSTANT_REGISTER_DECLARATION(FloatRegister, v26 , (26));
197 CONSTANT_REGISTER_DECLARATION(FloatRegister, v27 , (27));
198 CONSTANT_REGISTER_DECLARATION(FloatRegister, v28 , (28));
199 CONSTANT_REGISTER_DECLARATION(FloatRegister, v29 , (29));
200 CONSTANT_REGISTER_DECLARATION(FloatRegister, v30 , (30));
201 CONSTANT_REGISTER_DECLARATION(FloatRegister, v31 , (31));
202
203 // SVE vector registers, shared with the SIMD&FP v0-v31. Vn maps to Zn[127:0].
204 CONSTANT_REGISTER_DECLARATION(FloatRegister, z0 , ( 0));
205 CONSTANT_REGISTER_DECLARATION(FloatRegister, z1 , ( 1));
206 CONSTANT_REGISTER_DECLARATION(FloatRegister, z2 , ( 2));
207 CONSTANT_REGISTER_DECLARATION(FloatRegister, z3 , ( 3));
208 CONSTANT_REGISTER_DECLARATION(FloatRegister, z4 , ( 4));
209 CONSTANT_REGISTER_DECLARATION(FloatRegister, z5 , ( 5));
210 CONSTANT_REGISTER_DECLARATION(FloatRegister, z6 , ( 6));
211 CONSTANT_REGISTER_DECLARATION(FloatRegister, z7 , ( 7));
212 CONSTANT_REGISTER_DECLARATION(FloatRegister, z8 , ( 8));
213 CONSTANT_REGISTER_DECLARATION(FloatRegister, z9 , ( 9));
214 CONSTANT_REGISTER_DECLARATION(FloatRegister, z10 , (10));
215 CONSTANT_REGISTER_DECLARATION(FloatRegister, z11 , (11));
216 CONSTANT_REGISTER_DECLARATION(FloatRegister, z12 , (12));
217 CONSTANT_REGISTER_DECLARATION(FloatRegister, z13 , (13));
218 CONSTANT_REGISTER_DECLARATION(FloatRegister, z14 , (14));
219 CONSTANT_REGISTER_DECLARATION(FloatRegister, z15 , (15));
220 CONSTANT_REGISTER_DECLARATION(FloatRegister, z16 , (16));
221 CONSTANT_REGISTER_DECLARATION(FloatRegister, z17 , (17));
222 CONSTANT_REGISTER_DECLARATION(FloatRegister, z18 , (18));
223 CONSTANT_REGISTER_DECLARATION(FloatRegister, z19 , (19));
224 CONSTANT_REGISTER_DECLARATION(FloatRegister, z20 , (20));
225 CONSTANT_REGISTER_DECLARATION(FloatRegister, z21 , (21));
226 CONSTANT_REGISTER_DECLARATION(FloatRegister, z22 , (22));
227 CONSTANT_REGISTER_DECLARATION(FloatRegister, z23 , (23));
228 CONSTANT_REGISTER_DECLARATION(FloatRegister, z24 , (24));
229 CONSTANT_REGISTER_DECLARATION(FloatRegister, z25 , (25));
230 CONSTANT_REGISTER_DECLARATION(FloatRegister, z26 , (26));
231 CONSTANT_REGISTER_DECLARATION(FloatRegister, z27 , (27));
232 CONSTANT_REGISTER_DECLARATION(FloatRegister, z28 , (28));
233 CONSTANT_REGISTER_DECLARATION(FloatRegister, z29 , (29));
234 CONSTANT_REGISTER_DECLARATION(FloatRegister, z30 , (30));
235 CONSTANT_REGISTER_DECLARATION(FloatRegister, z31 , (31));
236
237
238 class PRegisterImpl;
239 typedef PRegisterImpl* PRegister;
as_PRegister(int encoding)240 inline PRegister as_PRegister(int encoding) {
241 return (PRegister)(intptr_t)encoding;
242 }
243
244 // The implementation of predicate registers for the architecture
245 class PRegisterImpl: public AbstractRegisterImpl {
246 public:
247 enum {
248 number_of_registers = 16,
249 max_slots_per_register = 1
250 };
251
252 // construction
253 inline friend PRegister as_PRegister(int encoding);
254
255 VMReg as_VMReg();
256
257 // derived registers, offsets, and addresses
successor() const258 PRegister successor() const { return as_PRegister(encoding() + 1); }
259
260 // accessors
encoding() const261 int encoding() const { assert(is_valid(), "invalid register"); return (intptr_t)this; }
encoding_nocheck() const262 int encoding_nocheck() const { return (intptr_t)this; }
is_valid() const263 bool is_valid() const { return 0 <= (intptr_t)this && (intptr_t)this < number_of_registers; }
264 const char* name() const;
265 };
266
267 // The predicate registers of SVE.
268 CONSTANT_REGISTER_DECLARATION(PRegister, p0, ( 0));
269 CONSTANT_REGISTER_DECLARATION(PRegister, p1, ( 1));
270 CONSTANT_REGISTER_DECLARATION(PRegister, p2, ( 2));
271 CONSTANT_REGISTER_DECLARATION(PRegister, p3, ( 3));
272 CONSTANT_REGISTER_DECLARATION(PRegister, p4, ( 4));
273 CONSTANT_REGISTER_DECLARATION(PRegister, p5, ( 5));
274 CONSTANT_REGISTER_DECLARATION(PRegister, p6, ( 6));
275 CONSTANT_REGISTER_DECLARATION(PRegister, p7, ( 7));
276 CONSTANT_REGISTER_DECLARATION(PRegister, p8, ( 8));
277 CONSTANT_REGISTER_DECLARATION(PRegister, p9, ( 9));
278 CONSTANT_REGISTER_DECLARATION(PRegister, p10, (10));
279 CONSTANT_REGISTER_DECLARATION(PRegister, p11, (11));
280 CONSTANT_REGISTER_DECLARATION(PRegister, p12, (12));
281 CONSTANT_REGISTER_DECLARATION(PRegister, p13, (13));
282 CONSTANT_REGISTER_DECLARATION(PRegister, p14, (14));
283 CONSTANT_REGISTER_DECLARATION(PRegister, p15, (15));
284
285 // Need to know the total number of registers of all sorts for SharedInfo.
286 // Define a class that exports it.
287 class ConcreteRegisterImpl : public AbstractRegisterImpl {
288 public:
289 enum {
290 // A big enough number for C2: all the registers plus flags
291 // This number must be large enough to cover REG_COUNT (defined by c2) registers.
292 // There is no requirement that any ordering here matches any ordering c2 gives
293 // it's optoregs.
294
295 number_of_registers = (RegisterImpl::max_slots_per_register * RegisterImpl::number_of_registers +
296 FloatRegisterImpl::max_slots_per_register * FloatRegisterImpl::number_of_registers +
297 PRegisterImpl::max_slots_per_register * PRegisterImpl::number_of_registers +
298 1) // flags
299 };
300
301 // added to make it compile
302 static const int max_gpr;
303 static const int max_fpr;
304 static const int max_pr;
305 };
306
307 class RegSetIterator;
308
309 // A set of registers
310 class RegSet {
311 uint32_t _bitset;
312
RegSet(uint32_t bitset)313 RegSet(uint32_t bitset) : _bitset(bitset) { }
314
315 public:
316
RegSet()317 RegSet() : _bitset(0) { }
318
RegSet(Register r1)319 RegSet(Register r1) : _bitset(r1->bit()) { }
320
operator +(const RegSet aSet) const321 RegSet operator+(const RegSet aSet) const {
322 RegSet result(_bitset | aSet._bitset);
323 return result;
324 }
325
operator -(const RegSet aSet) const326 RegSet operator-(const RegSet aSet) const {
327 RegSet result(_bitset & ~aSet._bitset);
328 return result;
329 }
330
operator +=(const RegSet aSet)331 RegSet &operator+=(const RegSet aSet) {
332 *this = *this + aSet;
333 return *this;
334 }
335
operator -=(const RegSet aSet)336 RegSet &operator-=(const RegSet aSet) {
337 *this = *this - aSet;
338 return *this;
339 }
340
of(Register r1)341 static RegSet of(Register r1) {
342 return RegSet(r1);
343 }
344
of(Register r1,Register r2)345 static RegSet of(Register r1, Register r2) {
346 return of(r1) + r2;
347 }
348
of(Register r1,Register r2,Register r3)349 static RegSet of(Register r1, Register r2, Register r3) {
350 return of(r1, r2) + r3;
351 }
352
of(Register r1,Register r2,Register r3,Register r4)353 static RegSet of(Register r1, Register r2, Register r3, Register r4) {
354 return of(r1, r2, r3) + r4;
355 }
356
range(Register start,Register end)357 static RegSet range(Register start, Register end) {
358 uint32_t bits = ~0;
359 bits <<= start->encoding();
360 bits <<= 31 - end->encoding();
361 bits >>= 31 - end->encoding();
362
363 return RegSet(bits);
364 }
365
bits() const366 uint32_t bits() const { return _bitset; }
367
368 private:
369
first()370 Register first() {
371 uint32_t first = _bitset & -_bitset;
372 return first ? as_Register(exact_log2(first)) : noreg;
373 }
374
375 public:
376
377 friend class RegSetIterator;
378
379 RegSetIterator begin();
380 };
381
382 class RegSetIterator {
383 RegSet _regs;
384
385 public:
RegSetIterator(RegSet x)386 RegSetIterator(RegSet x): _regs(x) {}
RegSetIterator(const RegSetIterator & mit)387 RegSetIterator(const RegSetIterator& mit) : _regs(mit._regs) {}
388
operator ++()389 RegSetIterator& operator++() {
390 Register r = _regs.first();
391 if (r != noreg)
392 _regs -= r;
393 return *this;
394 }
395
operator ==(const RegSetIterator & rhs) const396 bool operator==(const RegSetIterator& rhs) const {
397 return _regs.bits() == rhs._regs.bits();
398 }
operator !=(const RegSetIterator & rhs) const399 bool operator!=(const RegSetIterator& rhs) const {
400 return ! (rhs == *this);
401 }
402
operator *()403 Register operator*() {
404 return _regs.first();
405 }
406 };
407
begin()408 inline RegSetIterator RegSet::begin() {
409 return RegSetIterator(*this);
410 }
411
412 #endif // CPU_AARCH64_REGISTER_AARCH64_HPP
413