Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(8)

Side by Side Diff: src/arm64/simulator-arm64.h

Issue 2622643005: ARM64: Add NEON support (Closed)
Patch Set: Created 3 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #ifndef V8_ARM64_SIMULATOR_ARM64_H_ 5 #ifndef V8_ARM64_SIMULATOR_ARM64_H_
6 #define V8_ARM64_SIMULATOR_ARM64_H_ 6 #define V8_ARM64_SIMULATOR_ARM64_H_
7 7
8 #include <stdarg.h> 8 #include <stdarg.h>
9 #include <vector> 9 #include <vector>
10 10
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
63 return try_catch_address; 63 return try_catch_address;
64 } 64 }
65 65
66 static void UnregisterCTryCatch(v8::internal::Isolate* isolate) { 66 static void UnregisterCTryCatch(v8::internal::Isolate* isolate) {
67 USE(isolate); 67 USE(isolate);
68 } 68 }
69 }; 69 };
70 70
71 #else // !defined(USE_SIMULATOR) 71 #else // !defined(USE_SIMULATOR)
72 72
73 // Assemble the specified IEEE-754 components into the target type and apply
74 // appropriate rounding.
75 // sign: 0 = positive, 1 = negative
76 // exponent: Unbiased IEEE-754 exponent.
77 // mantissa: The mantissa of the input. The top bit (which is not encoded for
78 // normal IEEE-754 values) must not be omitted. This bit has the
79 // value 'pow(2, exponent)'.
80 //
81 // The input value is assumed to be a normalized value. That is, the input may
82 // not be infinity or NaN. If the source value is subnormal, it must be
83 // normalized before calling this function such that the highest set bit in the
84 // mantissa has the value 'pow(2, exponent)'.
85 //
86 // Callers should use FPRoundToFloat or FPRoundToDouble directly, rather than
87 // calling a templated FPRound.
88 template <class T, int ebits, int mbits>
89 T FPRound(int64_t sign, int64_t exponent, uint64_t mantissa,
90 FPRounding round_mode) {
91 static_assert((sizeof(T) * 8) >= (1 + ebits + mbits),
92 "destination type T not large enough");
93 static_assert(sizeof(T) <= sizeof(uint64_t),
94 "maximum size of destination type T is 64 bits");
95 static_assert(std::is_unsigned<T>::value,
96 "destination type T must be unsigned");
97
98 DCHECK((sign == 0) || (sign == 1));
99
100 // Only FPTieEven and FPRoundOdd rounding modes are implemented.
101 DCHECK((round_mode == FPTieEven) || (round_mode == FPRoundOdd));
102
103 // Rounding can promote subnormals to normals, and normals to infinities. For
104 // example, a double with exponent 127 (FLT_MAX_EXP) would appear to be
105 // encodable as a float, but rounding based on the low-order mantissa bits
106 // could make it overflow. With ties-to-even rounding, this value would become
107 // an infinity.
108
109 // ---- Rounding Method ----
110 //
111 // The exponent is irrelevant in the rounding operation, so we treat the
112 // lowest-order bit that will fit into the result ('onebit') as having
113 // the value '1'. Similarly, the highest-order bit that won't fit into
114 // the result ('halfbit') has the value '0.5'. The 'point' sits between
115 // 'onebit' and 'halfbit':
116 //
117 // These bits fit into the result.
118 // |---------------------|
119 // mantissa = 0bxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
120 // ||
121 // / |
122 // / halfbit
123 // onebit
124 //
125 // For subnormal outputs, the range of representable bits is smaller and
126 // the position of onebit and halfbit depends on the exponent of the
127 // input, but the method is otherwise similar.
128 //
129 // onebit(frac)
130 // |
131 // | halfbit(frac) halfbit(adjusted)
132 // | / /
133 // | | |
134 // 0b00.0 (exact) -> 0b00.0 (exact) -> 0b00
135 // 0b00.0... -> 0b00.0... -> 0b00
136 // 0b00.1 (exact) -> 0b00.0111..111 -> 0b00
137 // 0b00.1... -> 0b00.1... -> 0b01
138 // 0b01.0 (exact) -> 0b01.0 (exact) -> 0b01
139 // 0b01.0... -> 0b01.0... -> 0b01
140 // 0b01.1 (exact) -> 0b01.1 (exact) -> 0b10
141 // 0b01.1... -> 0b01.1... -> 0b10
142 // 0b10.0 (exact) -> 0b10.0 (exact) -> 0b10
143 // 0b10.0... -> 0b10.0... -> 0b10
144 // 0b10.1 (exact) -> 0b10.0111..111 -> 0b10
145 // 0b10.1... -> 0b10.1... -> 0b11
146 // 0b11.0 (exact) -> 0b11.0 (exact) -> 0b11
147 // ... / | / |
148 // / | / |
149 // / |
150 // adjusted = frac - (halfbit(mantissa) & ~onebit(frac)); / |
151 //
152 // mantissa = (mantissa >> shift) + halfbit(adjusted);
153
154 const int mantissa_offset = 0;
155 const int exponent_offset = mantissa_offset + mbits;
156 const int sign_offset = exponent_offset + ebits;
157 DCHECK_EQ(sign_offset, static_cast<int>(sizeof(T) * 8 - 1));
158
159 // Bail out early for zero inputs.
160 if (mantissa == 0) {
161 return static_cast<T>(sign << sign_offset);
162 }
163
164 // If all bits in the exponent are set, the value is infinite or NaN.
165 // This is true for all binary IEEE-754 formats.
166 const int infinite_exponent = (1 << ebits) - 1;
167 const int max_normal_exponent = infinite_exponent - 1;
168
169 // Apply the exponent bias to encode it for the result. Doing this early makes
170 // it easy to detect values that will be infinite or subnormal.
171 exponent += max_normal_exponent >> 1;
172
173 if (exponent > max_normal_exponent) {
174 // Overflow: the input is too large for the result type to represent.
175 if (round_mode == FPTieEven) {
176 // FPTieEven rounding mode handles overflows using infinities.
177 exponent = infinite_exponent;
178 mantissa = 0;
179 } else {
180 DCHECK_EQ(round_mode, FPRoundOdd);
181 // FPRoundOdd rounding mode handles overflows using the largest magnitude
182 // normal number.
183 exponent = max_normal_exponent;
184 mantissa = (UINT64_C(1) << exponent_offset) - 1;
185 }
186 return static_cast<T>((sign << sign_offset) |
187 (exponent << exponent_offset) |
188 (mantissa << mantissa_offset));
189 }
190
191 // Calculate the shift required to move the top mantissa bit to the proper
192 // place in the destination type.
193 const int highest_significant_bit = 63 - CountLeadingZeros(mantissa, 64);
194 int shift = highest_significant_bit - mbits;
195
196 if (exponent <= 0) {
197 // The output will be subnormal (before rounding).
198 // For subnormal outputs, the shift must be adjusted by the exponent. The +1
199 // is necessary because the exponent of a subnormal value (encoded as 0) is
200 // the same as the exponent of the smallest normal value (encoded as 1).
201 shift += -exponent + 1;
202
203 // Handle inputs that would produce a zero output.
204 //
205 // Shifts higher than highest_significant_bit+1 will always produce a zero
206 // result. A shift of exactly highest_significant_bit+1 might produce a
207 // non-zero result after rounding.
208 if (shift > (highest_significant_bit + 1)) {
209 if (round_mode == FPTieEven) {
210 // The result will always be +/-0.0.
211 return static_cast<T>(sign << sign_offset);
212 } else {
213 DCHECK_EQ(round_mode, FPRoundOdd);
214 DCHECK_NE(mantissa, 0U);
215 // For FPRoundOdd, if the mantissa is too small to represent and
216 // non-zero return the next "odd" value.
217 return static_cast<T>((sign << sign_offset) | 1);
218 }
219 }
220
221 // Properly encode the exponent for a subnormal output.
222 exponent = 0;
223 } else {
224 // Clear the topmost mantissa bit, since this is not encoded in IEEE-754
225 // normal values.
226 mantissa &= ~(UINT64_C(1) << highest_significant_bit);
227 }
228
229 if (shift > 0) {
230 if (round_mode == FPTieEven) {
231 // We have to shift the mantissa to the right. Some precision is lost, so
232 // we need to apply rounding.
233 uint64_t onebit_mantissa = (mantissa >> (shift)) & 1;
234 uint64_t halfbit_mantissa = (mantissa >> (shift - 1)) & 1;
235 uint64_t adjustment = (halfbit_mantissa & ~onebit_mantissa);
236 uint64_t adjusted = mantissa - adjustment;
237 T halfbit_adjusted = (adjusted >> (shift - 1)) & 1;
238
239 T result =
240 static_cast<T>((sign << sign_offset) | (exponent << exponent_offset) |
241 ((mantissa >> shift) << mantissa_offset));
242
243 // A very large mantissa can overflow during rounding. If this happens,
244 // the exponent should be incremented and the mantissa set to 1.0
245 // (encoded as 0). Applying halfbit_adjusted after assembling the float
246 // has the nice side-effect that this case is handled for free.
247 //
248 // This also handles cases where a very large finite value overflows to
249 // infinity, or where a very large subnormal value overflows to become
250 // normal.
251 return result + halfbit_adjusted;
252 } else {
253 DCHECK_EQ(round_mode, FPRoundOdd);
254 // If any bits at position halfbit or below are set, onebit (ie. the
255 // bottom bit of the resulting mantissa) must be set.
256 uint64_t fractional_bits = mantissa & ((UINT64_C(1) << shift) - 1);
257 if (fractional_bits != 0) {
258 mantissa |= UINT64_C(1) << shift;
259 }
260
261 return static_cast<T>((sign << sign_offset) |
262 (exponent << exponent_offset) |
263 ((mantissa >> shift) << mantissa_offset));
264 }
265 } else {
266 // We have to shift the mantissa to the left (or not at all). The input
267 // mantissa is exactly representable in the output mantissa, so apply no
268 // rounding correction.
269 return static_cast<T>((sign << sign_offset) |
270 (exponent << exponent_offset) |
271 ((mantissa << -shift) << mantissa_offset));
272 }
273 }
274
275 // Representation of memory, with typed getters and setters for access.
276 class SimMemory {
277 public:
278 template <typename T>
279 static T AddressUntag(T address) {
280 // Cast the address using a C-style cast. A reinterpret_cast would be
281 // appropriate, but it can't cast one integral type to another.
282 uint64_t bits = (uint64_t)address;
283 return (T)(bits & ~kAddressTagMask);
284 }
285
286 template <typename T, typename A>
287 static T Read(A address) {
288 T value;
289 address = AddressUntag(address);
290 DCHECK((sizeof(value) == 1) || (sizeof(value) == 2) ||
291 (sizeof(value) == 4) || (sizeof(value) == 8) ||
292 (sizeof(value) == 16));
293 memcpy(&value, reinterpret_cast<const char*>(address), sizeof(value));
294 return value;
295 }
296
297 template <typename T, typename A>
298 static void Write(A address, T value) {
299 address = AddressUntag(address);
300 DCHECK((sizeof(value) == 1) || (sizeof(value) == 2) ||
301 (sizeof(value) == 4) || (sizeof(value) == 8) ||
302 (sizeof(value) == 16));
303 memcpy(reinterpret_cast<char*>(address), &value, sizeof(value));
304 }
305 };
73 306
74 // The proper way to initialize a simulated system register (such as NZCV) is as 307 // The proper way to initialize a simulated system register (such as NZCV) is as
75 // follows: 308 // follows:
76 // SimSystemRegister nzcv = SimSystemRegister::DefaultValueFor(NZCV); 309 // SimSystemRegister nzcv = SimSystemRegister::DefaultValueFor(NZCV);
77 class SimSystemRegister { 310 class SimSystemRegister {
78 public: 311 public:
79 // The default constructor represents a register which has no writable bits. 312 // The default constructor represents a register which has no writable bits.
80 // It is not possible to set its value to anything other than 0. 313 // It is not possible to set its value to anything other than 0.
81 SimSystemRegister() : value_(0), write_ignore_mask_(0xffffffff) { } 314 SimSystemRegister() : value_(0), write_ignore_mask_(0xffffffff) { }
82 315
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
118 // describes the bits which are not modifiable. 351 // describes the bits which are not modifiable.
119 SimSystemRegister(uint32_t value, uint32_t write_ignore_mask) 352 SimSystemRegister(uint32_t value, uint32_t write_ignore_mask)
120 : value_(value), write_ignore_mask_(write_ignore_mask) { } 353 : value_(value), write_ignore_mask_(write_ignore_mask) { }
121 354
122 uint32_t value_; 355 uint32_t value_;
123 uint32_t write_ignore_mask_; 356 uint32_t write_ignore_mask_;
124 }; 357 };
125 358
126 359
127 // Represent a register (r0-r31, v0-v31). 360 // Represent a register (r0-r31, v0-v31).
361 template <int kSizeInBytes>
128 class SimRegisterBase { 362 class SimRegisterBase {
129 public: 363 public:
130 template<typename T> 364 template<typename T>
131 void Set(T new_value) { 365 void Set(T new_value) {
132 value_ = 0; 366 static_assert(sizeof(new_value) <= kSizeInBytes,
367 "Size of new_value must be <= size of template type.");
368 if (sizeof(new_value) < kSizeInBytes) {
369 // All AArch64 registers are zero-extending.
370 memset(value_ + sizeof(new_value), 0, kSizeInBytes - sizeof(new_value));
371 }
133 memcpy(&value_, &new_value, sizeof(T)); 372 memcpy(&value_, &new_value, sizeof(T));
134 } 373 NotifyRegisterWrite();
135 374 }
136 template<typename T> 375
137 T Get() const { 376 // Insert a typed value into a register, leaving the rest of the register
377 // unchanged. The lane parameter indicates where in the register the value
378 // should be inserted, in the range [ 0, sizeof(value_) / sizeof(T) ), where
379 // 0 represents the least significant bits.
380 template <typename T>
381 void Insert(int lane, T new_value) {
382 DCHECK_GE(lane, 0);
383 DCHECK_LE(sizeof(new_value) + (lane * sizeof(new_value)),
384 static_cast<unsigned>(kSizeInBytes));
385 memcpy(&value_[lane * sizeof(new_value)], &new_value, sizeof(new_value));
386 NotifyRegisterWrite();
387 }
388
389 template <typename T>
390 T Get(int lane = 0) const {
138 T result; 391 T result;
139 memcpy(&result, &value_, sizeof(T)); 392 DCHECK_GE(lane, 0);
393 DCHECK_LE(sizeof(result) + (lane * sizeof(result)),
394 static_cast<unsigned>(kSizeInBytes));
395 memcpy(&result, &value_[lane * sizeof(result)], sizeof(result));
140 return result; 396 return result;
141 } 397 }
142 398
399 // TODO(all): Make this return a map of updated bytes, so that we can
400 // highlight updated lanes for load-and-insert. (That never happens for scalar
401 // code, but NEON has some instructions that can update individual lanes.)
402 bool WrittenSinceLastLog() const { return written_since_last_log_; }
403
404 void NotifyRegisterLogged() { written_since_last_log_ = false; }
405
143 protected: 406 protected:
144 int64_t value_; 407 uint8_t value_[kSizeInBytes];
408
409 // Helpers to aid with register tracing.
410 bool written_since_last_log_;
411
412 void NotifyRegisterWrite() { written_since_last_log_ = true; }
145 }; 413 };
146 414 typedef SimRegisterBase<kXRegSize> SimRegister; // r0-r31
147 415 typedef SimRegisterBase<kQRegSize> SimVRegister; // v0-v31
148 typedef SimRegisterBase SimRegister; // r0-r31 416
149 typedef SimRegisterBase SimFPRegister; // v0-v31 417 // Representation of a vector register, with typed getters and setters for lanes
150 418 // and additional information to represent lane state.
419 class LogicVRegister {
420 public:
421 inline LogicVRegister(SimVRegister& other) // NOLINT
422 : register_(other) {
423 for (unsigned i = 0; i < sizeof(saturated_) / sizeof(saturated_[0]); i++) {
424 saturated_[i] = kNotSaturated;
425 }
426 for (unsigned i = 0; i < sizeof(round_) / sizeof(round_[0]); i++) {
427 round_[i] = 0;
428 }
429 }
430
431 int64_t Int(VectorFormat vform, int index) const {
432 int64_t element;
433 switch (LaneSizeInBitsFromFormat(vform)) {
434 case 8:
435 element = register_.Get<int8_t>(index);
436 break;
437 case 16:
438 element = register_.Get<int16_t>(index);
439 break;
440 case 32:
441 element = register_.Get<int32_t>(index);
442 break;
443 case 64:
444 element = register_.Get<int64_t>(index);
445 break;
446 default:
447 UNREACHABLE();
448 return 0;
449 }
450 return element;
451 }
452
453 uint64_t Uint(VectorFormat vform, int index) const {
454 uint64_t element;
455 switch (LaneSizeInBitsFromFormat(vform)) {
456 case 8:
457 element = register_.Get<uint8_t>(index);
458 break;
459 case 16:
460 element = register_.Get<uint16_t>(index);
461 break;
462 case 32:
463 element = register_.Get<uint32_t>(index);
464 break;
465 case 64:
466 element = register_.Get<uint64_t>(index);
467 break;
468 default:
469 UNREACHABLE();
470 return 0;
471 }
472 return element;
473 }
474
475 uint64_t UintLeftJustified(VectorFormat vform, int index) const {
476 return Uint(vform, index) << (64 - LaneSizeInBitsFromFormat(vform));
477 }
478
479 int64_t IntLeftJustified(VectorFormat vform, int index) const {
480 uint64_t value = UintLeftJustified(vform, index);
481 int64_t result;
482 memcpy(&result, &value, sizeof(result));
483 return result;
484 }
485
486 void SetInt(VectorFormat vform, int index, int64_t value) const {
487 switch (LaneSizeInBitsFromFormat(vform)) {
488 case 8:
489 register_.Insert(index, static_cast<int8_t>(value));
490 break;
491 case 16:
492 register_.Insert(index, static_cast<int16_t>(value));
493 break;
494 case 32:
495 register_.Insert(index, static_cast<int32_t>(value));
496 break;
497 case 64:
498 register_.Insert(index, static_cast<int64_t>(value));
499 break;
500 default:
501 UNREACHABLE();
502 return;
503 }
504 }
505
506 void SetIntArray(VectorFormat vform, const int64_t* src) const {
507 ClearForWrite(vform);
508 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
509 SetInt(vform, i, src[i]);
510 }
511 }
512
513 void SetUint(VectorFormat vform, int index, uint64_t value) const {
514 switch (LaneSizeInBitsFromFormat(vform)) {
515 case 8:
516 register_.Insert(index, static_cast<uint8_t>(value));
517 break;
518 case 16:
519 register_.Insert(index, static_cast<uint16_t>(value));
520 break;
521 case 32:
522 register_.Insert(index, static_cast<uint32_t>(value));
523 break;
524 case 64:
525 register_.Insert(index, static_cast<uint64_t>(value));
526 break;
527 default:
528 UNREACHABLE();
529 return;
530 }
531 }
532
533 void SetUintArray(VectorFormat vform, const uint64_t* src) const {
534 ClearForWrite(vform);
535 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
536 SetUint(vform, i, src[i]);
537 }
538 }
539
540 void ReadUintFromMem(VectorFormat vform, int index, uint64_t addr) const;
541
542 void WriteUintToMem(VectorFormat vform, int index, uint64_t addr) const;
543
544 template <typename T>
545 T Float(int index) const {
546 return register_.Get<T>(index);
547 }
548
549 template <typename T>
550 void SetFloat(int index, T value) const {
551 register_.Insert(index, value);
552 }
553
554 // When setting a result in a register of size less than Q, the top bits of
555 // the Q register must be cleared.
556 void ClearForWrite(VectorFormat vform) const {
557 unsigned size = RegisterSizeInBytesFromFormat(vform);
558 for (unsigned i = size; i < kQRegSize; i++) {
559 SetUint(kFormat16B, i, 0);
560 }
561 }
562
563 // Saturation state for each lane of a vector.
564 enum Saturation {
565 kNotSaturated = 0,
566 kSignedSatPositive = 1 << 0,
567 kSignedSatNegative = 1 << 1,
568 kSignedSatMask = kSignedSatPositive | kSignedSatNegative,
569 kSignedSatUndefined = kSignedSatMask,
570 kUnsignedSatPositive = 1 << 2,
571 kUnsignedSatNegative = 1 << 3,
572 kUnsignedSatMask = kUnsignedSatPositive | kUnsignedSatNegative,
573 kUnsignedSatUndefined = kUnsignedSatMask
574 };
575
576 // Getters for saturation state.
577 Saturation GetSignedSaturation(int index) {
578 return static_cast<Saturation>(saturated_[index] & kSignedSatMask);
579 }
580
581 Saturation GetUnsignedSaturation(int index) {
582 return static_cast<Saturation>(saturated_[index] & kUnsignedSatMask);
583 }
584
585 // Setters for saturation state.
586 void ClearSat(int index) { saturated_[index] = kNotSaturated; }
587
588 void SetSignedSat(int index, bool positive) {
589 SetSatFlag(index, positive ? kSignedSatPositive : kSignedSatNegative);
590 }
591
592 void SetUnsignedSat(int index, bool positive) {
593 SetSatFlag(index, positive ? kUnsignedSatPositive : kUnsignedSatNegative);
594 }
595
596 void SetSatFlag(int index, Saturation sat) {
597 saturated_[index] = static_cast<Saturation>(saturated_[index] | sat);
598 DCHECK_NE(sat & kUnsignedSatMask, kUnsignedSatUndefined);
599 DCHECK_NE(sat & kSignedSatMask, kSignedSatUndefined);
600 }
601
602 // Saturate lanes of a vector based on saturation state.
603 LogicVRegister& SignedSaturate(VectorFormat vform) {
604 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
605 Saturation sat = GetSignedSaturation(i);
606 if (sat == kSignedSatPositive) {
607 SetInt(vform, i, MaxIntFromFormat(vform));
608 } else if (sat == kSignedSatNegative) {
609 SetInt(vform, i, MinIntFromFormat(vform));
610 }
611 }
612 return *this;
613 }
614
615 LogicVRegister& UnsignedSaturate(VectorFormat vform) {
616 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
617 Saturation sat = GetUnsignedSaturation(i);
618 if (sat == kUnsignedSatPositive) {
619 SetUint(vform, i, MaxUintFromFormat(vform));
620 } else if (sat == kUnsignedSatNegative) {
621 SetUint(vform, i, 0);
622 }
623 }
624 return *this;
625 }
626
627 // Getter for rounding state.
628 bool GetRounding(int index) { return round_[index]; }
629
630 // Setter for rounding state.
631 void SetRounding(int index, bool round) { round_[index] = round; }
632
633 // Round lanes of a vector based on rounding state.
634 LogicVRegister& Round(VectorFormat vform) {
635 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
636 SetUint(vform, i, Uint(vform, i) + (GetRounding(i) ? 1 : 0));
637 }
638 return *this;
639 }
640
641 // Unsigned halve lanes of a vector, and use the saturation state to set the
642 // top bit.
643 LogicVRegister& Uhalve(VectorFormat vform) {
644 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
645 uint64_t val = Uint(vform, i);
646 SetRounding(i, (val & 1) == 1);
647 val >>= 1;
648 if (GetUnsignedSaturation(i) != kNotSaturated) {
649 // If the operation causes unsigned saturation, the bit shifted into the
650 // most significant bit must be set.
651 val |= (MaxUintFromFormat(vform) >> 1) + 1;
652 }
653 SetInt(vform, i, val);
654 }
655 return *this;
656 }
657
658 // Signed halve lanes of a vector, and use the carry state to set the top bit.
659 LogicVRegister& Halve(VectorFormat vform) {
660 for (int i = 0; i < LaneCountFromFormat(vform); i++) {
661 int64_t val = Int(vform, i);
662 SetRounding(i, (val & 1) == 1);
663 val >>= 1;
664 if (GetSignedSaturation(i) != kNotSaturated) {
665 // If the operation causes signed saturation, the sign bit must be
666 // inverted.
667 val ^= (MaxUintFromFormat(vform) >> 1) + 1;
668 }
669 SetInt(vform, i, val);
670 }
671 return *this;
672 }
673
674 private:
675 SimVRegister& register_;
676
677 // Allocate one saturation state entry per lane; largest register is type Q,
678 // and lanes can be a minimum of one byte wide.
679 Saturation saturated_[kQRegSize];
680
681 // Allocate one rounding state entry per lane.
682 bool round_[kQRegSize];
683 };
151 684
152 class Simulator : public DecoderVisitor { 685 class Simulator : public DecoderVisitor {
153 public: 686 public:
154 static void FlushICache(base::CustomMatcherHashMap* i_cache, void* start, 687 static void FlushICache(base::CustomMatcherHashMap* i_cache, void* start,
155 size_t size) { 688 size_t size) {
156 USE(i_cache); 689 USE(i_cache);
157 USE(start); 690 USE(start);
158 USE(size); 691 USE(size);
159 } 692 }
160 693
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after
308 841
309 virtual void Decode(Instruction* instr) { 842 virtual void Decode(Instruction* instr) {
310 decoder_->Decode(instr); 843 decoder_->Decode(instr);
311 } 844 }
312 845
313 void ExecuteInstruction() { 846 void ExecuteInstruction() {
314 DCHECK(IsAligned(reinterpret_cast<uintptr_t>(pc_), kInstructionSize)); 847 DCHECK(IsAligned(reinterpret_cast<uintptr_t>(pc_), kInstructionSize));
315 CheckBreakNext(); 848 CheckBreakNext();
316 Decode(pc_); 849 Decode(pc_);
317 increment_pc(); 850 increment_pc();
851 LogAllWrittenRegisters();
318 CheckBreakpoints(); 852 CheckBreakpoints();
319 } 853 }
320 854
321 // Declare all Visitor functions. 855 // Declare all Visitor functions.
322 #define DECLARE(A) void Visit##A(Instruction* instr); 856 #define DECLARE(A) void Visit##A(Instruction* instr);
323 VISITOR_LIST(DECLARE) 857 VISITOR_LIST(DECLARE)
324 #undef DECLARE 858 #undef DECLARE
325 859
326 bool IsZeroRegister(unsigned code, Reg31Mode r31mode) const { 860 bool IsZeroRegister(unsigned code, Reg31Mode r31mode) const {
327 return ((code == 31) && (r31mode == Reg31IsZeroRegister)); 861 return ((code == 31) && (r31mode == Reg31IsZeroRegister));
328 } 862 }
329 863
330 // Register accessors. 864 // Register accessors.
331 // Return 'size' bits of the value of an integer register, as the specified 865 // Return 'size' bits of the value of an integer register, as the specified
332 // type. The value is zero-extended to fill the result. 866 // type. The value is zero-extended to fill the result.
333 // 867 //
334 template<typename T> 868 template<typename T>
335 T reg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const { 869 T reg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const {
336 DCHECK(code < kNumberOfRegisters); 870 DCHECK_LT(code, static_cast<unsigned>(kNumberOfRegisters));
337 if (IsZeroRegister(code, r31mode)) { 871 if (IsZeroRegister(code, r31mode)) {
338 return 0; 872 return 0;
339 } 873 }
340 return registers_[code].Get<T>(); 874 return registers_[code].Get<T>();
341 } 875 }
342 876
343 // Common specialized accessors for the reg() template. 877 // Common specialized accessors for the reg() template.
344 int32_t wreg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const { 878 int32_t wreg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const {
345 return reg<int32_t>(code, r31mode); 879 return reg<int32_t>(code, r31mode);
346 } 880 }
347 881
348 int64_t xreg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const { 882 int64_t xreg(unsigned code, Reg31Mode r31mode = Reg31IsZeroRegister) const {
349 return reg<int64_t>(code, r31mode); 883 return reg<int64_t>(code, r31mode);
350 } 884 }
351 885
886 enum RegLogMode { LogRegWrites, NoRegLog };
887
352 // Write 'value' into an integer register. The value is zero-extended. This 888 // Write 'value' into an integer register. The value is zero-extended. This
353 // behaviour matches AArch64 register writes. 889 // behaviour matches AArch64 register writes.
354 template<typename T> 890 template<typename T>
355 void set_reg(unsigned code, T value, 891 void set_reg(unsigned code, T value,
356 Reg31Mode r31mode = Reg31IsZeroRegister) { 892 Reg31Mode r31mode = Reg31IsZeroRegister) {
357 set_reg_no_log(code, value, r31mode); 893 set_reg_no_log(code, value, r31mode);
358 LogRegister(code, r31mode); 894 LogRegister(code, r31mode);
359 } 895 }
360 896
361 // Common specialized accessors for the set_reg() template. 897 // Common specialized accessors for the set_reg() template.
362 void set_wreg(unsigned code, int32_t value, 898 void set_wreg(unsigned code, int32_t value,
363 Reg31Mode r31mode = Reg31IsZeroRegister) { 899 Reg31Mode r31mode = Reg31IsZeroRegister) {
364 set_reg(code, value, r31mode); 900 set_reg(code, value, r31mode);
365 } 901 }
366 902
367 void set_xreg(unsigned code, int64_t value, 903 void set_xreg(unsigned code, int64_t value,
368 Reg31Mode r31mode = Reg31IsZeroRegister) { 904 Reg31Mode r31mode = Reg31IsZeroRegister) {
369 set_reg(code, value, r31mode); 905 set_reg(code, value, r31mode);
370 } 906 }
371 907
372 // As above, but don't automatically log the register update. 908 // As above, but don't automatically log the register update.
373 template <typename T> 909 template <typename T>
374 void set_reg_no_log(unsigned code, T value, 910 void set_reg_no_log(unsigned code, T value,
375 Reg31Mode r31mode = Reg31IsZeroRegister) { 911 Reg31Mode r31mode = Reg31IsZeroRegister) {
376 DCHECK(code < kNumberOfRegisters); 912 DCHECK_LT(code, static_cast<unsigned>(kNumberOfRegisters));
377 if (!IsZeroRegister(code, r31mode)) { 913 if (!IsZeroRegister(code, r31mode)) {
378 registers_[code].Set(value); 914 registers_[code].Set(value);
379 } 915 }
380 } 916 }
381 917
382 void set_wreg_no_log(unsigned code, int32_t value, 918 void set_wreg_no_log(unsigned code, int32_t value,
383 Reg31Mode r31mode = Reg31IsZeroRegister) { 919 Reg31Mode r31mode = Reg31IsZeroRegister) {
384 set_reg_no_log(code, value, r31mode); 920 set_reg_no_log(code, value, r31mode);
385 } 921 }
386 922
387 void set_xreg_no_log(unsigned code, int64_t value, 923 void set_xreg_no_log(unsigned code, int64_t value,
388 Reg31Mode r31mode = Reg31IsZeroRegister) { 924 Reg31Mode r31mode = Reg31IsZeroRegister) {
389 set_reg_no_log(code, value, r31mode); 925 set_reg_no_log(code, value, r31mode);
390 } 926 }
391 927
392 // Commonly-used special cases. 928 // Commonly-used special cases.
393 template<typename T> 929 template<typename T>
394 void set_lr(T value) { 930 void set_lr(T value) {
395 DCHECK(sizeof(T) == kPointerSize); 931 DCHECK_EQ(sizeof(T), static_cast<unsigned>(kPointerSize));
396 set_reg(kLinkRegCode, value); 932 set_reg(kLinkRegCode, value);
397 } 933 }
398 934
399 template<typename T> 935 template<typename T>
400 void set_sp(T value) { 936 void set_sp(T value) {
401 DCHECK(sizeof(T) == kPointerSize); 937 DCHECK_EQ(sizeof(T), static_cast<unsigned>(kPointerSize));
402 set_reg(31, value, Reg31IsStackPointer); 938 set_reg(31, value, Reg31IsStackPointer);
403 } 939 }
404 940
941 // Vector register accessors.
942 // These are equivalent to the integer register accessors, but for vector
943 // registers.
944
945 // A structure for representing a 128-bit Q register.
946 struct qreg_t {
947 uint8_t val[kQRegSize];
948 };
949
950 // Basic accessor: read the register as the specified type.
951 template <typename T>
952 T vreg(unsigned code) const {
953 static_assert((sizeof(T) == kBRegSize) || (sizeof(T) == kHRegSize) ||
954 (sizeof(T) == kSRegSize) || (sizeof(T) == kDRegSize) ||
955 (sizeof(T) == kQRegSize),
956 "Template type must match size of register.");
957 DCHECK_LT(code, static_cast<unsigned>(kNumberOfVRegisters));
958
959 return vregisters_[code].Get<T>();
960 }
961
962 inline SimVRegister& vreg(unsigned code) { return vregisters_[code]; }
963
405 int64_t sp() { return xreg(31, Reg31IsStackPointer); } 964 int64_t sp() { return xreg(31, Reg31IsStackPointer); }
406 int64_t jssp() { return xreg(kJSSPCode, Reg31IsStackPointer); } 965 int64_t jssp() { return xreg(kJSSPCode, Reg31IsStackPointer); }
407 int64_t fp() { 966 int64_t fp() {
408 return xreg(kFramePointerRegCode, Reg31IsStackPointer); 967 return xreg(kFramePointerRegCode, Reg31IsStackPointer);
409 } 968 }
410 Instruction* lr() { return reg<Instruction*>(kLinkRegCode); } 969 Instruction* lr() { return reg<Instruction*>(kLinkRegCode); }
411 970
412 Address get_sp() const { return reg<Address>(31, Reg31IsStackPointer); } 971 Address get_sp() const { return reg<Address>(31, Reg31IsStackPointer); }
413 972
414 template<typename T> 973 // Common specialized accessors for the vreg() template.
415 T fpreg(unsigned code) const { 974 uint8_t breg(unsigned code) const { return vreg<uint8_t>(code); }
416 DCHECK(code < kNumberOfRegisters);
417 return fpregisters_[code].Get<T>();
418 }
419 975
420 // Common specialized accessors for the fpreg() template. 976 float hreg(unsigned code) const { return vreg<uint16_t>(code); }
421 float sreg(unsigned code) const {
422 return fpreg<float>(code);
423 }
424 977
425 uint32_t sreg_bits(unsigned code) const { 978 float sreg(unsigned code) const { return vreg<float>(code); }
426 return fpreg<uint32_t>(code);
427 }
428 979
429 double dreg(unsigned code) const { 980 uint32_t sreg_bits(unsigned code) const { return vreg<uint32_t>(code); }
430 return fpreg<double>(code);
431 }
432 981
433 uint64_t dreg_bits(unsigned code) const { 982 double dreg(unsigned code) const { return vreg<double>(code); }
434 return fpreg<uint64_t>(code);
435 }
436 983
437 double fpreg(unsigned size, unsigned code) const { 984 uint64_t dreg_bits(unsigned code) const { return vreg<uint64_t>(code); }
985
986 qreg_t qreg(unsigned code) const { return vreg<qreg_t>(code); }
987
988 // As above, with parameterized size and return type. The value is
989 // either zero-extended or truncated to fit, as required.
990 template <typename T>
991 T vreg(unsigned size, unsigned code) const {
992 uint64_t raw = 0;
993 T result;
994
438 switch (size) { 995 switch (size) {
439 case kSRegSizeInBits: return sreg(code); 996 case kSRegSize:
440 case kDRegSizeInBits: return dreg(code); 997 raw = vreg<uint32_t>(code);
998 break;
999 case kDRegSize:
1000 raw = vreg<uint64_t>(code);
1001 break;
441 default: 1002 default:
442 UNREACHABLE(); 1003 UNREACHABLE();
443 return 0.0; 1004 break;
444 } 1005 }
1006
1007 static_assert(sizeof(result) <= sizeof(raw),
1008 "Template type must be <= 64 bits.");
1009 // Copy the result and truncate to fit. This assumes a little-endian host.
1010 memcpy(&result, &raw, sizeof(result));
1011 return result;
445 } 1012 }
446 1013
447 // Write 'value' into a floating-point register. The value is zero-extended. 1014 // Write 'value' into a floating-point register. The value is zero-extended.
448 // This behaviour matches AArch64 register writes. 1015 // This behaviour matches AArch64 register writes.
449 template<typename T> 1016 template <typename T>
450 void set_fpreg(unsigned code, T value) { 1017 void set_vreg(unsigned code, T value, RegLogMode log_mode = LogRegWrites) {
451 set_fpreg_no_log(code, value); 1018 static_assert(
1019 (sizeof(value) == kBRegSize) || (sizeof(value) == kHRegSize) ||
1020 (sizeof(value) == kSRegSize) || (sizeof(value) == kDRegSize) ||
1021 (sizeof(value) == kQRegSize),
1022 "Template type must match size of register.");
1023 DCHECK_LT(code, static_cast<unsigned>(kNumberOfVRegisters));
1024 vregisters_[code].Set(value);
452 1025
453 if (sizeof(value) <= kSRegSize) { 1026 if (log_mode == LogRegWrites) {
454 LogFPRegister(code, kPrintSRegValue); 1027 LogVRegister(code, GetPrintRegisterFormat(value));
455 } else {
456 LogFPRegister(code, kPrintDRegValue);
457 } 1028 }
458 } 1029 }
459 1030
460 // Common specialized accessors for the set_fpreg() template. 1031 // Common specialized accessors for the set_vreg() template.
461 void set_sreg(unsigned code, float value) { 1032 void set_breg(unsigned code, int8_t value,
462 set_fpreg(code, value); 1033 RegLogMode log_mode = LogRegWrites) {
1034 set_vreg(code, value, log_mode);
463 } 1035 }
464 1036
465 void set_sreg_bits(unsigned code, uint32_t value) { 1037 void set_hreg(unsigned code, int16_t value,
466 set_fpreg(code, value); 1038 RegLogMode log_mode = LogRegWrites) {
1039 set_vreg(code, value, log_mode);
467 } 1040 }
468 1041
469 void set_dreg(unsigned code, double value) { 1042 void set_sreg(unsigned code, float value,
470 set_fpreg(code, value); 1043 RegLogMode log_mode = LogRegWrites) {
1044 set_vreg(code, value, log_mode);
471 } 1045 }
472 1046
473 void set_dreg_bits(unsigned code, uint64_t value) { 1047 void set_sreg_bits(unsigned code, uint32_t value,
474 set_fpreg(code, value); 1048 RegLogMode log_mode = LogRegWrites) {
1049 set_vreg(code, value, log_mode);
1050 }
1051
1052 void set_dreg(unsigned code, double value,
1053 RegLogMode log_mode = LogRegWrites) {
1054 set_vreg(code, value, log_mode);
1055 }
1056
1057 void set_dreg_bits(unsigned code, uint64_t value,
1058 RegLogMode log_mode = LogRegWrites) {
1059 set_vreg(code, value, log_mode);
1060 }
1061
1062 void set_qreg(unsigned code, qreg_t value,
1063 RegLogMode log_mode = LogRegWrites) {
1064 set_vreg(code, value, log_mode);
475 } 1065 }
476 1066
477 // As above, but don't automatically log the register update. 1067 // As above, but don't automatically log the register update.
478 template <typename T> 1068 template <typename T>
479 void set_fpreg_no_log(unsigned code, T value) { 1069 void set_vreg_no_log(unsigned code, T value) {
480 DCHECK((sizeof(value) == kDRegSize) || (sizeof(value) == kSRegSize)); 1070 STATIC_ASSERT((sizeof(value) == kBRegSize) ||
481 DCHECK(code < kNumberOfFPRegisters); 1071 (sizeof(value) == kHRegSize) ||
482 fpregisters_[code].Set(value); 1072 (sizeof(value) == kSRegSize) ||
1073 (sizeof(value) == kDRegSize) || (sizeof(value) == kQRegSize));
1074 DCHECK_LT(code, static_cast<unsigned>(kNumberOfVRegisters));
1075 vregisters_[code].Set(value);
1076 }
1077
1078 void set_breg_no_log(unsigned code, uint8_t value) {
1079 set_vreg_no_log(code, value);
1080 }
1081
1082 void set_hreg_no_log(unsigned code, uint16_t value) {
1083 set_vreg_no_log(code, value);
483 } 1084 }
484 1085
485 void set_sreg_no_log(unsigned code, float value) { 1086 void set_sreg_no_log(unsigned code, float value) {
486 set_fpreg_no_log(code, value); 1087 set_vreg_no_log(code, value);
487 } 1088 }
488 1089
489 void set_dreg_no_log(unsigned code, double value) { 1090 void set_dreg_no_log(unsigned code, double value) {
490 set_fpreg_no_log(code, value); 1091 set_vreg_no_log(code, value);
1092 }
1093
1094 void set_qreg_no_log(unsigned code, qreg_t value) {
1095 set_vreg_no_log(code, value);
491 } 1096 }
492 1097
493 SimSystemRegister& nzcv() { return nzcv_; } 1098 SimSystemRegister& nzcv() { return nzcv_; }
494 SimSystemRegister& fpcr() { return fpcr_; } 1099 SimSystemRegister& fpcr() { return fpcr_; }
1100 FPRounding RMode() { return static_cast<FPRounding>(fpcr_.RMode()); }
1101 bool DN() { return fpcr_.DN() != 0; }
495 1102
496 // Debug helpers 1103 // Debug helpers
497 1104
498 // Simulator breakpoints. 1105 // Simulator breakpoints.
499 struct Breakpoint { 1106 struct Breakpoint {
500 Instruction* location; 1107 Instruction* location;
501 bool enabled; 1108 bool enabled;
502 }; 1109 };
503 std::vector<Breakpoint> breakpoints_; 1110 std::vector<Breakpoint> breakpoints_;
504 void SetBreakpoint(Instruction* breakpoint); 1111 void SetBreakpoint(Instruction* breakpoint);
505 void ListBreakpoints(); 1112 void ListBreakpoints();
506 void CheckBreakpoints(); 1113 void CheckBreakpoints();
507 1114
508 // Helpers for the 'next' command. 1115 // Helpers for the 'next' command.
509 // When this is set, the Simulator will insert a breakpoint after the next BL 1116 // When this is set, the Simulator will insert a breakpoint after the next BL
510 // instruction it meets. 1117 // instruction it meets.
511 bool break_on_next_; 1118 bool break_on_next_;
512 // Check if the Simulator should insert a break after the current instruction 1119 // Check if the Simulator should insert a break after the current instruction
513 // for the 'next' command. 1120 // for the 'next' command.
514 void CheckBreakNext(); 1121 void CheckBreakNext();
515 1122
516 // Disassemble instruction at the given address. 1123 // Disassemble instruction at the given address.
517 void PrintInstructionsAt(Instruction* pc, uint64_t count); 1124 void PrintInstructionsAt(Instruction* pc, uint64_t count);
518 1125
519 // Print all registers of the specified types. 1126 // Print all registers of the specified types.
520 void PrintRegisters(); 1127 void PrintRegisters();
521 void PrintFPRegisters(); 1128 void PrintVRegisters();
522 void PrintSystemRegisters(); 1129 void PrintSystemRegisters();
523 1130
524 // Like Print* (above), but respect log_parameters(). 1131 // As above, but only print the registers that have been updated.
525 void LogSystemRegisters() { 1132 void PrintWrittenRegisters();
526 if (log_parameters() & LOG_SYS_REGS) PrintSystemRegisters(); 1133 void PrintWrittenVRegisters();
1134
1135 // As above, but respect LOG_REG and LOG_VREG.
1136 void LogWrittenRegisters() {
1137 if (log_parameters() & LOG_REGS) PrintWrittenRegisters();
527 } 1138 }
528 void LogRegisters() { 1139 void LogWrittenVRegisters() {
529 if (log_parameters() & LOG_REGS) PrintRegisters(); 1140 if (log_parameters() & LOG_VREGS) PrintWrittenVRegisters();
530 } 1141 }
531 void LogFPRegisters() { 1142 void LogAllWrittenRegisters() {
532 if (log_parameters() & LOG_FP_REGS) PrintFPRegisters(); 1143 LogWrittenRegisters();
1144 LogWrittenVRegisters();
533 } 1145 }
534 1146
535 // Specify relevant register sizes, for PrintFPRegister. 1147 // Specify relevant register formats for Print(V)Register and related helpers.
536 // 1148 enum PrintRegisterFormat {
537 // These values are bit masks; they can be combined in case multiple views of 1149 // The lane size.
538 // a machine register are interesting. 1150 kPrintRegLaneSizeB = 0 << 0,
539 enum PrintFPRegisterSizes { 1151 kPrintRegLaneSizeH = 1 << 0,
540 kPrintDRegValue = 1 << kDRegSize, 1152 kPrintRegLaneSizeS = 2 << 0,
541 kPrintSRegValue = 1 << kSRegSize, 1153 kPrintRegLaneSizeW = kPrintRegLaneSizeS,
542 kPrintAllFPRegValues = kPrintDRegValue | kPrintSRegValue 1154 kPrintRegLaneSizeD = 3 << 0,
1155 kPrintRegLaneSizeX = kPrintRegLaneSizeD,
1156 kPrintRegLaneSizeQ = 4 << 0,
1157
1158 kPrintRegLaneSizeOffset = 0,
1159 kPrintRegLaneSizeMask = 7 << 0,
1160
1161 // The lane count.
1162 kPrintRegAsScalar = 0,
1163 kPrintRegAsDVector = 1 << 3,
1164 kPrintRegAsQVector = 2 << 3,
1165
1166 kPrintRegAsVectorMask = 3 << 3,
1167
1168 // Indicate floating-point format lanes. (This flag is only supported for S-
1169 // and D-sized lanes.)
1170 kPrintRegAsFP = 1 << 5,
1171
1172 // Supported combinations.
1173
1174 kPrintXReg = kPrintRegLaneSizeX | kPrintRegAsScalar,
1175 kPrintWReg = kPrintRegLaneSizeW | kPrintRegAsScalar,
1176 kPrintSReg = kPrintRegLaneSizeS | kPrintRegAsScalar | kPrintRegAsFP,
1177 kPrintDReg = kPrintRegLaneSizeD | kPrintRegAsScalar | kPrintRegAsFP,
1178
1179 kPrintReg1B = kPrintRegLaneSizeB | kPrintRegAsScalar,
1180 kPrintReg8B = kPrintRegLaneSizeB | kPrintRegAsDVector,
1181 kPrintReg16B = kPrintRegLaneSizeB | kPrintRegAsQVector,
1182 kPrintReg1H = kPrintRegLaneSizeH | kPrintRegAsScalar,
1183 kPrintReg4H = kPrintRegLaneSizeH | kPrintRegAsDVector,
1184 kPrintReg8H = kPrintRegLaneSizeH | kPrintRegAsQVector,
1185 kPrintReg1S = kPrintRegLaneSizeS | kPrintRegAsScalar,
1186 kPrintReg2S = kPrintRegLaneSizeS | kPrintRegAsDVector,
1187 kPrintReg4S = kPrintRegLaneSizeS | kPrintRegAsQVector,
1188 kPrintReg1SFP = kPrintRegLaneSizeS | kPrintRegAsScalar | kPrintRegAsFP,
1189 kPrintReg2SFP = kPrintRegLaneSizeS | kPrintRegAsDVector | kPrintRegAsFP,
1190 kPrintReg4SFP = kPrintRegLaneSizeS | kPrintRegAsQVector | kPrintRegAsFP,
1191 kPrintReg1D = kPrintRegLaneSizeD | kPrintRegAsScalar,
1192 kPrintReg2D = kPrintRegLaneSizeD | kPrintRegAsQVector,
1193 kPrintReg1DFP = kPrintRegLaneSizeD | kPrintRegAsScalar | kPrintRegAsFP,
1194 kPrintReg2DFP = kPrintRegLaneSizeD | kPrintRegAsQVector | kPrintRegAsFP,
1195 kPrintReg1Q = kPrintRegLaneSizeQ | kPrintRegAsScalar
543 }; 1196 };
544 1197
1198 unsigned GetPrintRegLaneSizeInBytesLog2(PrintRegisterFormat format) {
1199 return (format & kPrintRegLaneSizeMask) >> kPrintRegLaneSizeOffset;
1200 }
1201
1202 unsigned GetPrintRegLaneSizeInBytes(PrintRegisterFormat format) {
1203 return 1 << GetPrintRegLaneSizeInBytesLog2(format);
1204 }
1205
1206 unsigned GetPrintRegSizeInBytesLog2(PrintRegisterFormat format) {
1207 if (format & kPrintRegAsDVector) return kDRegSizeLog2;
1208 if (format & kPrintRegAsQVector) return kQRegSizeLog2;
1209
1210 // Scalar types.
1211 return GetPrintRegLaneSizeInBytesLog2(format);
1212 }
1213
1214 unsigned GetPrintRegSizeInBytes(PrintRegisterFormat format) {
1215 return 1 << GetPrintRegSizeInBytesLog2(format);
1216 }
1217
1218 unsigned GetPrintRegLaneCount(PrintRegisterFormat format) {
1219 unsigned reg_size_log2 = GetPrintRegSizeInBytesLog2(format);
1220 unsigned lane_size_log2 = GetPrintRegLaneSizeInBytesLog2(format);
1221 DCHECK_GE(reg_size_log2, lane_size_log2);
1222 return 1 << (reg_size_log2 - lane_size_log2);
1223 }
1224
1225 template <typename T>
1226 PrintRegisterFormat GetPrintRegisterFormat(T value) {
1227 return GetPrintRegisterFormatForSize(sizeof(value));
1228 }
1229
1230 PrintRegisterFormat GetPrintRegisterFormat(double value) {
1231 static_assert(sizeof(value) == kDRegSize,
1232 "D register must be size of double.");
1233 return GetPrintRegisterFormatForSizeFP(sizeof(value));
1234 }
1235
1236 PrintRegisterFormat GetPrintRegisterFormat(float value) {
1237 static_assert(sizeof(value) == kSRegSize,
1238 "S register must be size of float.");
1239 return GetPrintRegisterFormatForSizeFP(sizeof(value));
1240 }
1241
1242 PrintRegisterFormat GetPrintRegisterFormat(VectorFormat vform);
1243 PrintRegisterFormat GetPrintRegisterFormatFP(VectorFormat vform);
1244
1245 PrintRegisterFormat GetPrintRegisterFormatForSize(size_t reg_size,
1246 size_t lane_size);
1247
1248 PrintRegisterFormat GetPrintRegisterFormatForSize(size_t size) {
1249 return GetPrintRegisterFormatForSize(size, size);
1250 }
1251
1252 PrintRegisterFormat GetPrintRegisterFormatForSizeFP(size_t size) {
1253 switch (size) {
1254 default:
1255 UNREACHABLE();
1256 case kDRegSize:
1257 return kPrintDReg;
1258 case kSRegSize:
1259 return kPrintSReg;
1260 }
1261 }
1262
1263 PrintRegisterFormat GetPrintRegisterFormatTryFP(PrintRegisterFormat format) {
1264 if ((GetPrintRegLaneSizeInBytes(format) == kSRegSize) ||
1265 (GetPrintRegLaneSizeInBytes(format) == kDRegSize)) {
1266 return static_cast<PrintRegisterFormat>(format | kPrintRegAsFP);
1267 }
1268 return format;
1269 }
1270
545 // Print individual register values (after update). 1271 // Print individual register values (after update).
546 void PrintRegister(unsigned code, Reg31Mode r31mode = Reg31IsStackPointer); 1272 void PrintRegister(unsigned code, Reg31Mode r31mode = Reg31IsStackPointer);
547 void PrintFPRegister(unsigned code, 1273 void PrintVRegister(unsigned code, PrintRegisterFormat sizes);
548 PrintFPRegisterSizes sizes = kPrintAllFPRegValues);
549 void PrintSystemRegister(SystemRegister id); 1274 void PrintSystemRegister(SystemRegister id);
550 1275
551 // Like Print* (above), but respect log_parameters(). 1276 // Like Print* (above), but respect log_parameters().
552 void LogRegister(unsigned code, Reg31Mode r31mode = Reg31IsStackPointer) { 1277 void LogRegister(unsigned code, Reg31Mode r31mode = Reg31IsStackPointer) {
553 if (log_parameters() & LOG_REGS) PrintRegister(code, r31mode); 1278 if (log_parameters() & LOG_REGS) PrintRegister(code, r31mode);
554 } 1279 }
555 void LogFPRegister(unsigned code, 1280 void LogVRegister(unsigned code, PrintRegisterFormat format) {
556 PrintFPRegisterSizes sizes = kPrintAllFPRegValues) { 1281 if (log_parameters() & LOG_VREGS) PrintVRegister(code, format);
557 if (log_parameters() & LOG_FP_REGS) PrintFPRegister(code, sizes);
558 } 1282 }
559 void LogSystemRegister(SystemRegister id) { 1283 void LogSystemRegister(SystemRegister id) {
560 if (log_parameters() & LOG_SYS_REGS) PrintSystemRegister(id); 1284 if (log_parameters() & LOG_SYS_REGS) PrintSystemRegister(id);
561 } 1285 }
562 1286
563 // Print memory accesses. 1287 // Print memory accesses.
564 void PrintRead(uintptr_t address, size_t size, unsigned reg_code); 1288 void PrintRead(uintptr_t address, unsigned reg_code,
565 void PrintReadFP(uintptr_t address, size_t size, unsigned reg_code); 1289 PrintRegisterFormat format);
566 void PrintWrite(uintptr_t address, size_t size, unsigned reg_code); 1290 void PrintWrite(uintptr_t address, unsigned reg_code,
567 void PrintWriteFP(uintptr_t address, size_t size, unsigned reg_code); 1291 PrintRegisterFormat format);
1292 void PrintVRead(uintptr_t address, unsigned reg_code,
1293 PrintRegisterFormat format, unsigned lane);
1294 void PrintVWrite(uintptr_t address, unsigned reg_code,
1295 PrintRegisterFormat format, unsigned lane);
568 1296
569 // Like Print* (above), but respect log_parameters(). 1297 // Like Print* (above), but respect log_parameters().
570 void LogRead(uintptr_t address, size_t size, unsigned reg_code) { 1298 void LogRead(uintptr_t address, unsigned reg_code,
571 if (log_parameters() & LOG_REGS) PrintRead(address, size, reg_code); 1299 PrintRegisterFormat format) {
1300 if (log_parameters() & LOG_REGS) PrintRead(address, reg_code, format);
572 } 1301 }
573 void LogReadFP(uintptr_t address, size_t size, unsigned reg_code) { 1302 void LogWrite(uintptr_t address, unsigned reg_code,
574 if (log_parameters() & LOG_FP_REGS) PrintReadFP(address, size, reg_code); 1303 PrintRegisterFormat format) {
1304 if (log_parameters() & LOG_WRITE) PrintWrite(address, reg_code, format);
575 } 1305 }
576 void LogWrite(uintptr_t address, size_t size, unsigned reg_code) { 1306 void LogVRead(uintptr_t address, unsigned reg_code,
577 if (log_parameters() & LOG_WRITE) PrintWrite(address, size, reg_code); 1307 PrintRegisterFormat format, unsigned lane = 0) {
1308 if (log_parameters() & LOG_VREGS) {
1309 PrintVRead(address, reg_code, format, lane);
1310 }
578 } 1311 }
579 void LogWriteFP(uintptr_t address, size_t size, unsigned reg_code) { 1312 void LogVWrite(uintptr_t address, unsigned reg_code,
580 if (log_parameters() & LOG_WRITE) PrintWriteFP(address, size, reg_code); 1313 PrintRegisterFormat format, unsigned lane = 0) {
1314 if (log_parameters() & LOG_WRITE) {
1315 PrintVWrite(address, reg_code, format, lane);
1316 }
581 } 1317 }
582 1318
583 int log_parameters() { return log_parameters_; } 1319 int log_parameters() { return log_parameters_; }
584 void set_log_parameters(int new_parameters) { 1320 void set_log_parameters(int new_parameters) {
585 log_parameters_ = new_parameters; 1321 log_parameters_ = new_parameters;
586 if (!decoder_) { 1322 if (!decoder_) {
587 if (new_parameters & LOG_DISASM) { 1323 if (new_parameters & LOG_DISASM) {
588 PrintF("Run --debug-sim to dynamically turn on disassembler\n"); 1324 PrintF("Run --debug-sim to dynamically turn on disassembler\n");
589 } 1325 }
590 return; 1326 return;
591 } 1327 }
592 if (new_parameters & LOG_DISASM) { 1328 if (new_parameters & LOG_DISASM) {
593 decoder_->InsertVisitorBefore(print_disasm_, this); 1329 decoder_->InsertVisitorBefore(print_disasm_, this);
594 } else { 1330 } else {
595 decoder_->RemoveVisitor(print_disasm_); 1331 decoder_->RemoveVisitor(print_disasm_);
596 } 1332 }
597 } 1333 }
598 1334
1335 // Helper functions for register tracing.
1336 void PrintRegisterRawHelper(unsigned code, Reg31Mode r31mode,
1337 int size_in_bytes = kXRegSize);
1338 void PrintVRegisterRawHelper(unsigned code, int bytes = kQRegSize,
1339 int lsb = 0);
1340 void PrintVRegisterFPHelper(unsigned code, unsigned lane_size_in_bytes,
1341 int lane_count = 1, int rightmost_lane = 0);
1342
599 static inline const char* WRegNameForCode(unsigned code, 1343 static inline const char* WRegNameForCode(unsigned code,
600 Reg31Mode mode = Reg31IsZeroRegister); 1344 Reg31Mode mode = Reg31IsZeroRegister);
601 static inline const char* XRegNameForCode(unsigned code, 1345 static inline const char* XRegNameForCode(unsigned code,
602 Reg31Mode mode = Reg31IsZeroRegister); 1346 Reg31Mode mode = Reg31IsZeroRegister);
603 static inline const char* SRegNameForCode(unsigned code); 1347 static inline const char* SRegNameForCode(unsigned code);
604 static inline const char* DRegNameForCode(unsigned code); 1348 static inline const char* DRegNameForCode(unsigned code);
605 static inline const char* VRegNameForCode(unsigned code); 1349 static inline const char* VRegNameForCode(unsigned code);
606 static inline int CodeFromName(const char* name); 1350 static inline int CodeFromName(const char* name);
607 1351
608 protected: 1352 protected:
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
663 void ConditionalCompareHelper(Instruction* instr, T op2); 1407 void ConditionalCompareHelper(Instruction* instr, T op2);
664 void LoadStoreHelper(Instruction* instr, 1408 void LoadStoreHelper(Instruction* instr,
665 int64_t offset, 1409 int64_t offset,
666 AddrMode addrmode); 1410 AddrMode addrmode);
667 void LoadStorePairHelper(Instruction* instr, AddrMode addrmode); 1411 void LoadStorePairHelper(Instruction* instr, AddrMode addrmode);
668 uintptr_t LoadStoreAddress(unsigned addr_reg, int64_t offset, 1412 uintptr_t LoadStoreAddress(unsigned addr_reg, int64_t offset,
669 AddrMode addrmode); 1413 AddrMode addrmode);
670 void LoadStoreWriteBack(unsigned addr_reg, 1414 void LoadStoreWriteBack(unsigned addr_reg,
671 int64_t offset, 1415 int64_t offset,
672 AddrMode addrmode); 1416 AddrMode addrmode);
1417 void NEONLoadStoreMultiStructHelper(const Instruction* instr,
1418 AddrMode addr_mode);
1419 void NEONLoadStoreSingleStructHelper(const Instruction* instr,
1420 AddrMode addr_mode);
673 void CheckMemoryAccess(uintptr_t address, uintptr_t stack); 1421 void CheckMemoryAccess(uintptr_t address, uintptr_t stack);
674 1422
675 // Memory read helpers. 1423 // Memory read helpers.
676 template <typename T, typename A> 1424 template <typename T, typename A>
677 T MemoryRead(A address) { 1425 T MemoryRead(A address) {
678 T value; 1426 T value;
679 STATIC_ASSERT((sizeof(value) == 1) || (sizeof(value) == 2) || 1427 STATIC_ASSERT((sizeof(value) == 1) || (sizeof(value) == 2) ||
680 (sizeof(value) == 4) || (sizeof(value) == 8)); 1428 (sizeof(value) == 4) || (sizeof(value) == 8) ||
1429 (sizeof(value) == 16));
681 memcpy(&value, reinterpret_cast<const void*>(address), sizeof(value)); 1430 memcpy(&value, reinterpret_cast<const void*>(address), sizeof(value));
682 return value; 1431 return value;
683 } 1432 }
684 1433
685 // Memory write helpers. 1434 // Memory write helpers.
686 template <typename T, typename A> 1435 template <typename T, typename A>
687 void MemoryWrite(A address, T value) { 1436 void MemoryWrite(A address, T value) {
688 STATIC_ASSERT((sizeof(value) == 1) || (sizeof(value) == 2) || 1437 STATIC_ASSERT((sizeof(value) == 1) || (sizeof(value) == 2) ||
689 (sizeof(value) == 4) || (sizeof(value) == 8)); 1438 (sizeof(value) == 4) || (sizeof(value) == 8) ||
1439 (sizeof(value) == 16));
690 memcpy(reinterpret_cast<void*>(address), &value, sizeof(value)); 1440 memcpy(reinterpret_cast<void*>(address), &value, sizeof(value));
691 } 1441 }
692 1442
693 template <typename T> 1443 template <typename T>
694 T ShiftOperand(T value, 1444 T ShiftOperand(T value,
695 Shift shift_type, 1445 Shift shift_type,
696 unsigned amount); 1446 unsigned amount);
697 template <typename T> 1447 template <typename T>
698 T ExtendValue(T value, 1448 T ExtendValue(T value,
699 Extend extend_type, 1449 Extend extend_type,
700 unsigned left_shift = 0); 1450 unsigned left_shift = 0);
701 template <typename T> 1451 template <typename T>
702 void Extract(Instruction* instr); 1452 void Extract(Instruction* instr);
703 template <typename T> 1453 template <typename T>
704 void DataProcessing2Source(Instruction* instr); 1454 void DataProcessing2Source(Instruction* instr);
705 template <typename T> 1455 template <typename T>
706 void BitfieldHelper(Instruction* instr); 1456 void BitfieldHelper(Instruction* instr);
707 1457 uint16_t PolynomialMult(uint8_t op1, uint8_t op2);
708 template <typename T> 1458
709 T FPDefaultNaN() const; 1459 void ld1(VectorFormat vform, LogicVRegister dst, uint64_t addr);
1460 void ld1(VectorFormat vform, LogicVRegister dst, int index, uint64_t addr);
1461 void ld1r(VectorFormat vform, LogicVRegister dst, uint64_t addr);
1462 void ld2(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1463 uint64_t addr);
1464 void ld2(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1465 int index, uint64_t addr);
1466 void ld2r(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1467 uint64_t addr);
1468 void ld3(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1469 LogicVRegister dst3, uint64_t addr);
1470 void ld3(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1471 LogicVRegister dst3, int index, uint64_t addr);
1472 void ld3r(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1473 LogicVRegister dst3, uint64_t addr);
1474 void ld4(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1475 LogicVRegister dst3, LogicVRegister dst4, uint64_t addr);
1476 void ld4(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1477 LogicVRegister dst3, LogicVRegister dst4, int index, uint64_t addr);
1478 void ld4r(VectorFormat vform, LogicVRegister dst1, LogicVRegister dst2,
1479 LogicVRegister dst3, LogicVRegister dst4, uint64_t addr);
1480 void st1(VectorFormat vform, LogicVRegister src, uint64_t addr);
1481 void st1(VectorFormat vform, LogicVRegister src, int index, uint64_t addr);
1482 void st2(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1483 uint64_t addr);
1484 void st2(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1485 int index, uint64_t addr);
1486 void st3(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1487 LogicVRegister src3, uint64_t addr);
1488 void st3(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1489 LogicVRegister src3, int index, uint64_t addr);
1490 void st4(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1491 LogicVRegister src3, LogicVRegister src4, uint64_t addr);
1492 void st4(VectorFormat vform, LogicVRegister src, LogicVRegister src2,
1493 LogicVRegister src3, LogicVRegister src4, int index, uint64_t addr);
1494 LogicVRegister cmp(VectorFormat vform, LogicVRegister dst,
1495 const LogicVRegister& src1, const LogicVRegister& src2,
1496 Condition cond);
1497 LogicVRegister cmp(VectorFormat vform, LogicVRegister dst,
1498 const LogicVRegister& src1, int imm, Condition cond);
1499 LogicVRegister cmptst(VectorFormat vform, LogicVRegister dst,
1500 const LogicVRegister& src1, const LogicVRegister& src2);
1501 LogicVRegister add(VectorFormat vform, LogicVRegister dst,
1502 const LogicVRegister& src1, const LogicVRegister& src2);
1503 LogicVRegister addp(VectorFormat vform, LogicVRegister dst,
1504 const LogicVRegister& src1, const LogicVRegister& src2);
1505 LogicVRegister mla(VectorFormat vform, LogicVRegister dst,
1506 const LogicVRegister& src1, const LogicVRegister& src2);
1507 LogicVRegister mls(VectorFormat vform, LogicVRegister dst,
1508 const LogicVRegister& src1, const LogicVRegister& src2);
1509 LogicVRegister mul(VectorFormat vform, LogicVRegister dst,
1510 const LogicVRegister& src1, const LogicVRegister& src2);
1511 LogicVRegister mul(VectorFormat vform, LogicVRegister dst,
1512 const LogicVRegister& src1, const LogicVRegister& src2,
1513 int index);
1514 LogicVRegister mla(VectorFormat vform, LogicVRegister dst,
1515 const LogicVRegister& src1, const LogicVRegister& src2,
1516 int index);
1517 LogicVRegister mls(VectorFormat vform, LogicVRegister dst,
1518 const LogicVRegister& src1, const LogicVRegister& src2,
1519 int index);
1520 LogicVRegister pmul(VectorFormat vform, LogicVRegister dst,
1521 const LogicVRegister& src1, const LogicVRegister& src2);
1522
1523 typedef LogicVRegister (Simulator::*ByElementOp)(VectorFormat vform,
1524 LogicVRegister dst,
1525 const LogicVRegister& src1,
1526 const LogicVRegister& src2,
1527 int index);
1528 LogicVRegister fmul(VectorFormat vform, LogicVRegister dst,
1529 const LogicVRegister& src1, const LogicVRegister& src2,
1530 int index);
1531 LogicVRegister fmla(VectorFormat vform, LogicVRegister dst,
1532 const LogicVRegister& src1, const LogicVRegister& src2,
1533 int index);
1534 LogicVRegister fmls(VectorFormat vform, LogicVRegister dst,
1535 const LogicVRegister& src1, const LogicVRegister& src2,
1536 int index);
1537 LogicVRegister fmulx(VectorFormat vform, LogicVRegister dst,
1538 const LogicVRegister& src1, const LogicVRegister& src2,
1539 int index);
1540 LogicVRegister smull(VectorFormat vform, LogicVRegister dst,
1541 const LogicVRegister& src1, const LogicVRegister& src2,
1542 int index);
1543 LogicVRegister smull2(VectorFormat vform, LogicVRegister dst,
1544 const LogicVRegister& src1, const LogicVRegister& src2,
1545 int index);
1546 LogicVRegister umull(VectorFormat vform, LogicVRegister dst,
1547 const LogicVRegister& src1, const LogicVRegister& src2,
1548 int index);
1549 LogicVRegister umull2(VectorFormat vform, LogicVRegister dst,
1550 const LogicVRegister& src1, const LogicVRegister& src2,
1551 int index);
1552 LogicVRegister smlal(VectorFormat vform, LogicVRegister dst,
1553 const LogicVRegister& src1, const LogicVRegister& src2,
1554 int index);
1555 LogicVRegister smlal2(VectorFormat vform, LogicVRegister dst,
1556 const LogicVRegister& src1, const LogicVRegister& src2,
1557 int index);
1558 LogicVRegister umlal(VectorFormat vform, LogicVRegister dst,
1559 const LogicVRegister& src1, const LogicVRegister& src2,
1560 int index);
1561 LogicVRegister umlal2(VectorFormat vform, LogicVRegister dst,
1562 const LogicVRegister& src1, const LogicVRegister& src2,
1563 int index);
1564 LogicVRegister smlsl(VectorFormat vform, LogicVRegister dst,
1565 const LogicVRegister& src1, const LogicVRegister& src2,
1566 int index);
1567 LogicVRegister smlsl2(VectorFormat vform, LogicVRegister dst,
1568 const LogicVRegister& src1, const LogicVRegister& src2,
1569 int index);
1570 LogicVRegister umlsl(VectorFormat vform, LogicVRegister dst,
1571 const LogicVRegister& src1, const LogicVRegister& src2,
1572 int index);
1573 LogicVRegister umlsl2(VectorFormat vform, LogicVRegister dst,
1574 const LogicVRegister& src1, const LogicVRegister& src2,
1575 int index);
1576 LogicVRegister sqdmull(VectorFormat vform, LogicVRegister dst,
1577 const LogicVRegister& src1, const LogicVRegister& src2,
1578 int index);
1579 LogicVRegister sqdmull2(VectorFormat vform, LogicVRegister dst,
1580 const LogicVRegister& src1,
1581 const LogicVRegister& src2, int index);
1582 LogicVRegister sqdmlal(VectorFormat vform, LogicVRegister dst,
1583 const LogicVRegister& src1, const LogicVRegister& src2,
1584 int index);
1585 LogicVRegister sqdmlal2(VectorFormat vform, LogicVRegister dst,
1586 const LogicVRegister& src1,
1587 const LogicVRegister& src2, int index);
1588 LogicVRegister sqdmlsl(VectorFormat vform, LogicVRegister dst,
1589 const LogicVRegister& src1, const LogicVRegister& src2,
1590 int index);
1591 LogicVRegister sqdmlsl2(VectorFormat vform, LogicVRegister dst,
1592 const LogicVRegister& src1,
1593 const LogicVRegister& src2, int index);
1594 LogicVRegister sqdmulh(VectorFormat vform, LogicVRegister dst,
1595 const LogicVRegister& src1, const LogicVRegister& src2,
1596 int index);
1597 LogicVRegister sqrdmulh(VectorFormat vform, LogicVRegister dst,
1598 const LogicVRegister& src1,
1599 const LogicVRegister& src2, int index);
1600 LogicVRegister sub(VectorFormat vform, LogicVRegister dst,
1601 const LogicVRegister& src1, const LogicVRegister& src2);
1602 LogicVRegister and_(VectorFormat vform, LogicVRegister dst,
1603 const LogicVRegister& src1, const LogicVRegister& src2);
1604 LogicVRegister orr(VectorFormat vform, LogicVRegister dst,
1605 const LogicVRegister& src1, const LogicVRegister& src2);
1606 LogicVRegister orn(VectorFormat vform, LogicVRegister dst,
1607 const LogicVRegister& src1, const LogicVRegister& src2);
1608 LogicVRegister eor(VectorFormat vform, LogicVRegister dst,
1609 const LogicVRegister& src1, const LogicVRegister& src2);
1610 LogicVRegister bic(VectorFormat vform, LogicVRegister dst,
1611 const LogicVRegister& src1, const LogicVRegister& src2);
1612 LogicVRegister bic(VectorFormat vform, LogicVRegister dst,
1613 const LogicVRegister& src, uint64_t imm);
1614 LogicVRegister bif(VectorFormat vform, LogicVRegister dst,
1615 const LogicVRegister& src1, const LogicVRegister& src2);
1616 LogicVRegister bit(VectorFormat vform, LogicVRegister dst,
1617 const LogicVRegister& src1, const LogicVRegister& src2);
1618 LogicVRegister bsl(VectorFormat vform, LogicVRegister dst,
1619 const LogicVRegister& src1, const LogicVRegister& src2);
1620 LogicVRegister cls(VectorFormat vform, LogicVRegister dst,
1621 const LogicVRegister& src);
1622 LogicVRegister clz(VectorFormat vform, LogicVRegister dst,
1623 const LogicVRegister& src);
1624 LogicVRegister cnt(VectorFormat vform, LogicVRegister dst,
1625 const LogicVRegister& src);
1626 LogicVRegister not_(VectorFormat vform, LogicVRegister dst,
1627 const LogicVRegister& src);
1628 LogicVRegister rbit(VectorFormat vform, LogicVRegister dst,
1629 const LogicVRegister& src);
1630 LogicVRegister rev(VectorFormat vform, LogicVRegister dst,
1631 const LogicVRegister& src, int revSize);
1632 LogicVRegister rev16(VectorFormat vform, LogicVRegister dst,
1633 const LogicVRegister& src);
1634 LogicVRegister rev32(VectorFormat vform, LogicVRegister dst,
1635 const LogicVRegister& src);
1636 LogicVRegister rev64(VectorFormat vform, LogicVRegister dst,
1637 const LogicVRegister& src);
1638 LogicVRegister addlp(VectorFormat vform, LogicVRegister dst,
1639 const LogicVRegister& src, bool is_signed,
1640 bool do_accumulate);
1641 LogicVRegister saddlp(VectorFormat vform, LogicVRegister dst,
1642 const LogicVRegister& src);
1643 LogicVRegister uaddlp(VectorFormat vform, LogicVRegister dst,
1644 const LogicVRegister& src);
1645 LogicVRegister sadalp(VectorFormat vform, LogicVRegister dst,
1646 const LogicVRegister& src);
1647 LogicVRegister uadalp(VectorFormat vform, LogicVRegister dst,
1648 const LogicVRegister& src);
1649 LogicVRegister ext(VectorFormat vform, LogicVRegister dst,
1650 const LogicVRegister& src1, const LogicVRegister& src2,
1651 int index);
1652 LogicVRegister ins_element(VectorFormat vform, LogicVRegister dst,
1653 int dst_index, const LogicVRegister& src,
1654 int src_index);
1655 LogicVRegister ins_immediate(VectorFormat vform, LogicVRegister dst,
1656 int dst_index, uint64_t imm);
1657 LogicVRegister dup_element(VectorFormat vform, LogicVRegister dst,
1658 const LogicVRegister& src, int src_index);
1659 LogicVRegister dup_immediate(VectorFormat vform, LogicVRegister dst,
1660 uint64_t imm);
1661 LogicVRegister movi(VectorFormat vform, LogicVRegister dst, uint64_t imm);
1662 LogicVRegister mvni(VectorFormat vform, LogicVRegister dst, uint64_t imm);
1663 LogicVRegister orr(VectorFormat vform, LogicVRegister dst,
1664 const LogicVRegister& src, uint64_t imm);
1665 LogicVRegister sshl(VectorFormat vform, LogicVRegister dst,
1666 const LogicVRegister& src1, const LogicVRegister& src2);
1667 LogicVRegister ushl(VectorFormat vform, LogicVRegister dst,
1668 const LogicVRegister& src1, const LogicVRegister& src2);
1669 LogicVRegister SMinMax(VectorFormat vform, LogicVRegister dst,
1670 const LogicVRegister& src1, const LogicVRegister& src2,
1671 bool max);
1672 LogicVRegister smax(VectorFormat vform, LogicVRegister dst,
1673 const LogicVRegister& src1, const LogicVRegister& src2);
1674 LogicVRegister smin(VectorFormat vform, LogicVRegister dst,
1675 const LogicVRegister& src1, const LogicVRegister& src2);
1676 LogicVRegister SMinMaxP(VectorFormat vform, LogicVRegister dst,
1677 const LogicVRegister& src1,
1678 const LogicVRegister& src2, bool max);
1679 LogicVRegister smaxp(VectorFormat vform, LogicVRegister dst,
1680 const LogicVRegister& src1, const LogicVRegister& src2);
1681 LogicVRegister sminp(VectorFormat vform, LogicVRegister dst,
1682 const LogicVRegister& src1, const LogicVRegister& src2);
1683 LogicVRegister addp(VectorFormat vform, LogicVRegister dst,
1684 const LogicVRegister& src);
1685 LogicVRegister addv(VectorFormat vform, LogicVRegister dst,
1686 const LogicVRegister& src);
1687 LogicVRegister uaddlv(VectorFormat vform, LogicVRegister dst,
1688 const LogicVRegister& src);
1689 LogicVRegister saddlv(VectorFormat vform, LogicVRegister dst,
1690 const LogicVRegister& src);
1691 LogicVRegister SMinMaxV(VectorFormat vform, LogicVRegister dst,
1692 const LogicVRegister& src, bool max);
1693 LogicVRegister smaxv(VectorFormat vform, LogicVRegister dst,
1694 const LogicVRegister& src);
1695 LogicVRegister sminv(VectorFormat vform, LogicVRegister dst,
1696 const LogicVRegister& src);
1697 LogicVRegister uxtl(VectorFormat vform, LogicVRegister dst,
1698 const LogicVRegister& src);
1699 LogicVRegister uxtl2(VectorFormat vform, LogicVRegister dst,
1700 const LogicVRegister& src);
1701 LogicVRegister sxtl(VectorFormat vform, LogicVRegister dst,
1702 const LogicVRegister& src);
1703 LogicVRegister sxtl2(VectorFormat vform, LogicVRegister dst,
1704 const LogicVRegister& src);
1705 LogicVRegister Table(VectorFormat vform, LogicVRegister dst,
1706 const LogicVRegister& ind, bool zero_out_of_bounds,
1707 const LogicVRegister* tab1,
1708 const LogicVRegister* tab2 = NULL,
1709 const LogicVRegister* tab3 = NULL,
1710 const LogicVRegister* tab4 = NULL);
1711 LogicVRegister tbl(VectorFormat vform, LogicVRegister dst,
1712 const LogicVRegister& tab, const LogicVRegister& ind);
1713 LogicVRegister tbl(VectorFormat vform, LogicVRegister dst,
1714 const LogicVRegister& tab, const LogicVRegister& tab2,
1715 const LogicVRegister& ind);
1716 LogicVRegister tbl(VectorFormat vform, LogicVRegister dst,
1717 const LogicVRegister& tab, const LogicVRegister& tab2,
1718 const LogicVRegister& tab3, const LogicVRegister& ind);
1719 LogicVRegister tbl(VectorFormat vform, LogicVRegister dst,
1720 const LogicVRegister& tab, const LogicVRegister& tab2,
1721 const LogicVRegister& tab3, const LogicVRegister& tab4,
1722 const LogicVRegister& ind);
1723 LogicVRegister tbx(VectorFormat vform, LogicVRegister dst,
1724 const LogicVRegister& tab, const LogicVRegister& ind);
1725 LogicVRegister tbx(VectorFormat vform, LogicVRegister dst,
1726 const LogicVRegister& tab, const LogicVRegister& tab2,
1727 const LogicVRegister& ind);
1728 LogicVRegister tbx(VectorFormat vform, LogicVRegister dst,
1729 const LogicVRegister& tab, const LogicVRegister& tab2,
1730 const LogicVRegister& tab3, const LogicVRegister& ind);
1731 LogicVRegister tbx(VectorFormat vform, LogicVRegister dst,
1732 const LogicVRegister& tab, const LogicVRegister& tab2,
1733 const LogicVRegister& tab3, const LogicVRegister& tab4,
1734 const LogicVRegister& ind);
1735 LogicVRegister uaddl(VectorFormat vform, LogicVRegister dst,
1736 const LogicVRegister& src1, const LogicVRegister& src2);
1737 LogicVRegister uaddl2(VectorFormat vform, LogicVRegister dst,
1738 const LogicVRegister& src1, const LogicVRegister& src2);
1739 LogicVRegister uaddw(VectorFormat vform, LogicVRegister dst,
1740 const LogicVRegister& src1, const LogicVRegister& src2);
1741 LogicVRegister uaddw2(VectorFormat vform, LogicVRegister dst,
1742 const LogicVRegister& src1, const LogicVRegister& src2);
1743 LogicVRegister saddl(VectorFormat vform, LogicVRegister dst,
1744 const LogicVRegister& src1, const LogicVRegister& src2);
1745 LogicVRegister saddl2(VectorFormat vform, LogicVRegister dst,
1746 const LogicVRegister& src1, const LogicVRegister& src2);
1747 LogicVRegister saddw(VectorFormat vform, LogicVRegister dst,
1748 const LogicVRegister& src1, const LogicVRegister& src2);
1749 LogicVRegister saddw2(VectorFormat vform, LogicVRegister dst,
1750 const LogicVRegister& src1, const LogicVRegister& src2);
1751 LogicVRegister usubl(VectorFormat vform, LogicVRegister dst,
1752 const LogicVRegister& src1, const LogicVRegister& src2);
1753 LogicVRegister usubl2(VectorFormat vform, LogicVRegister dst,
1754 const LogicVRegister& src1, const LogicVRegister& src2);
1755 LogicVRegister usubw(VectorFormat vform, LogicVRegister dst,
1756 const LogicVRegister& src1, const LogicVRegister& src2);
1757 LogicVRegister usubw2(VectorFormat vform, LogicVRegister dst,
1758 const LogicVRegister& src1, const LogicVRegister& src2);
1759 LogicVRegister ssubl(VectorFormat vform, LogicVRegister dst,
1760 const LogicVRegister& src1, const LogicVRegister& src2);
1761 LogicVRegister ssubl2(VectorFormat vform, LogicVRegister dst,
1762 const LogicVRegister& src1, const LogicVRegister& src2);
1763 LogicVRegister ssubw(VectorFormat vform, LogicVRegister dst,
1764 const LogicVRegister& src1, const LogicVRegister& src2);
1765 LogicVRegister ssubw2(VectorFormat vform, LogicVRegister dst,
1766 const LogicVRegister& src1, const LogicVRegister& src2);
1767 LogicVRegister UMinMax(VectorFormat vform, LogicVRegister dst,
1768 const LogicVRegister& src1, const LogicVRegister& src2,
1769 bool max);
1770 LogicVRegister umax(VectorFormat vform, LogicVRegister dst,
1771 const LogicVRegister& src1, const LogicVRegister& src2);
1772 LogicVRegister umin(VectorFormat vform, LogicVRegister dst,
1773 const LogicVRegister& src1, const LogicVRegister& src2);
1774 LogicVRegister UMinMaxP(VectorFormat vform, LogicVRegister dst,
1775 const LogicVRegister& src1,
1776 const LogicVRegister& src2, bool max);
1777 LogicVRegister umaxp(VectorFormat vform, LogicVRegister dst,
1778 const LogicVRegister& src1, const LogicVRegister& src2);
1779 LogicVRegister uminp(VectorFormat vform, LogicVRegister dst,
1780 const LogicVRegister& src1, const LogicVRegister& src2);
1781 LogicVRegister UMinMaxV(VectorFormat vform, LogicVRegister dst,
1782 const LogicVRegister& src, bool max);
1783 LogicVRegister umaxv(VectorFormat vform, LogicVRegister dst,
1784 const LogicVRegister& src);
1785 LogicVRegister uminv(VectorFormat vform, LogicVRegister dst,
1786 const LogicVRegister& src);
1787 LogicVRegister trn1(VectorFormat vform, LogicVRegister dst,
1788 const LogicVRegister& src1, const LogicVRegister& src2);
1789 LogicVRegister trn2(VectorFormat vform, LogicVRegister dst,
1790 const LogicVRegister& src1, const LogicVRegister& src2);
1791 LogicVRegister zip1(VectorFormat vform, LogicVRegister dst,
1792 const LogicVRegister& src1, const LogicVRegister& src2);
1793 LogicVRegister zip2(VectorFormat vform, LogicVRegister dst,
1794 const LogicVRegister& src1, const LogicVRegister& src2);
1795 LogicVRegister uzp1(VectorFormat vform, LogicVRegister dst,
1796 const LogicVRegister& src1, const LogicVRegister& src2);
1797 LogicVRegister uzp2(VectorFormat vform, LogicVRegister dst,
1798 const LogicVRegister& src1, const LogicVRegister& src2);
1799 LogicVRegister shl(VectorFormat vform, LogicVRegister dst,
1800 const LogicVRegister& src, int shift);
1801 LogicVRegister scvtf(VectorFormat vform, LogicVRegister dst,
1802 const LogicVRegister& src, int fbits,
1803 FPRounding rounding_mode);
1804 LogicVRegister ucvtf(VectorFormat vform, LogicVRegister dst,
1805 const LogicVRegister& src, int fbits,
1806 FPRounding rounding_mode);
1807 LogicVRegister sshll(VectorFormat vform, LogicVRegister dst,
1808 const LogicVRegister& src, int shift);
1809 LogicVRegister sshll2(VectorFormat vform, LogicVRegister dst,
1810 const LogicVRegister& src, int shift);
1811 LogicVRegister shll(VectorFormat vform, LogicVRegister dst,
1812 const LogicVRegister& src);
1813 LogicVRegister shll2(VectorFormat vform, LogicVRegister dst,
1814 const LogicVRegister& src);
1815 LogicVRegister ushll(VectorFormat vform, LogicVRegister dst,
1816 const LogicVRegister& src, int shift);
1817 LogicVRegister ushll2(VectorFormat vform, LogicVRegister dst,
1818 const LogicVRegister& src, int shift);
1819 LogicVRegister sli(VectorFormat vform, LogicVRegister dst,
1820 const LogicVRegister& src, int shift);
1821 LogicVRegister sri(VectorFormat vform, LogicVRegister dst,
1822 const LogicVRegister& src, int shift);
1823 LogicVRegister sshr(VectorFormat vform, LogicVRegister dst,
1824 const LogicVRegister& src, int shift);
1825 LogicVRegister ushr(VectorFormat vform, LogicVRegister dst,
1826 const LogicVRegister& src, int shift);
1827 LogicVRegister ssra(VectorFormat vform, LogicVRegister dst,
1828 const LogicVRegister& src, int shift);
1829 LogicVRegister usra(VectorFormat vform, LogicVRegister dst,
1830 const LogicVRegister& src, int shift);
1831 LogicVRegister srsra(VectorFormat vform, LogicVRegister dst,
1832 const LogicVRegister& src, int shift);
1833 LogicVRegister ursra(VectorFormat vform, LogicVRegister dst,
1834 const LogicVRegister& src, int shift);
1835 LogicVRegister suqadd(VectorFormat vform, LogicVRegister dst,
1836 const LogicVRegister& src);
1837 LogicVRegister usqadd(VectorFormat vform, LogicVRegister dst,
1838 const LogicVRegister& src);
1839 LogicVRegister sqshl(VectorFormat vform, LogicVRegister dst,
1840 const LogicVRegister& src, int shift);
1841 LogicVRegister uqshl(VectorFormat vform, LogicVRegister dst,
1842 const LogicVRegister& src, int shift);
1843 LogicVRegister sqshlu(VectorFormat vform, LogicVRegister dst,
1844 const LogicVRegister& src, int shift);
1845 LogicVRegister abs(VectorFormat vform, LogicVRegister dst,
1846 const LogicVRegister& src);
1847 LogicVRegister neg(VectorFormat vform, LogicVRegister dst,
1848 const LogicVRegister& src);
1849 LogicVRegister ExtractNarrow(VectorFormat vform, LogicVRegister dst,
1850 bool dstIsSigned, const LogicVRegister& src,
1851 bool srcIsSigned);
1852 LogicVRegister xtn(VectorFormat vform, LogicVRegister dst,
1853 const LogicVRegister& src);
1854 LogicVRegister sqxtn(VectorFormat vform, LogicVRegister dst,
1855 const LogicVRegister& src);
1856 LogicVRegister uqxtn(VectorFormat vform, LogicVRegister dst,
1857 const LogicVRegister& src);
1858 LogicVRegister sqxtun(VectorFormat vform, LogicVRegister dst,
1859 const LogicVRegister& src);
1860 LogicVRegister AbsDiff(VectorFormat vform, LogicVRegister dst,
1861 const LogicVRegister& src1, const LogicVRegister& src2,
1862 bool issigned);
1863 LogicVRegister saba(VectorFormat vform, LogicVRegister dst,
1864 const LogicVRegister& src1, const LogicVRegister& src2);
1865 LogicVRegister uaba(VectorFormat vform, LogicVRegister dst,
1866 const LogicVRegister& src1, const LogicVRegister& src2);
1867 LogicVRegister shrn(VectorFormat vform, LogicVRegister dst,
1868 const LogicVRegister& src, int shift);
1869 LogicVRegister shrn2(VectorFormat vform, LogicVRegister dst,
1870 const LogicVRegister& src, int shift);
1871 LogicVRegister rshrn(VectorFormat vform, LogicVRegister dst,
1872 const LogicVRegister& src, int shift);
1873 LogicVRegister rshrn2(VectorFormat vform, LogicVRegister dst,
1874 const LogicVRegister& src, int shift);
1875 LogicVRegister uqshrn(VectorFormat vform, LogicVRegister dst,
1876 const LogicVRegister& src, int shift);
1877 LogicVRegister uqshrn2(VectorFormat vform, LogicVRegister dst,
1878 const LogicVRegister& src, int shift);
1879 LogicVRegister uqrshrn(VectorFormat vform, LogicVRegister dst,
1880 const LogicVRegister& src, int shift);
1881 LogicVRegister uqrshrn2(VectorFormat vform, LogicVRegister dst,
1882 const LogicVRegister& src, int shift);
1883 LogicVRegister sqshrn(VectorFormat vform, LogicVRegister dst,
1884 const LogicVRegister& src, int shift);
1885 LogicVRegister sqshrn2(VectorFormat vform, LogicVRegister dst,
1886 const LogicVRegister& src, int shift);
1887 LogicVRegister sqrshrn(VectorFormat vform, LogicVRegister dst,
1888 const LogicVRegister& src, int shift);
1889 LogicVRegister sqrshrn2(VectorFormat vform, LogicVRegister dst,
1890 const LogicVRegister& src, int shift);
1891 LogicVRegister sqshrun(VectorFormat vform, LogicVRegister dst,
1892 const LogicVRegister& src, int shift);
1893 LogicVRegister sqshrun2(VectorFormat vform, LogicVRegister dst,
1894 const LogicVRegister& src, int shift);
1895 LogicVRegister sqrshrun(VectorFormat vform, LogicVRegister dst,
1896 const LogicVRegister& src, int shift);
1897 LogicVRegister sqrshrun2(VectorFormat vform, LogicVRegister dst,
1898 const LogicVRegister& src, int shift);
1899 LogicVRegister sqrdmulh(VectorFormat vform, LogicVRegister dst,
1900 const LogicVRegister& src1,
1901 const LogicVRegister& src2, bool round = true);
1902 LogicVRegister sqdmulh(VectorFormat vform, LogicVRegister dst,
1903 const LogicVRegister& src1,
1904 const LogicVRegister& src2);
1905 #define NEON_3VREG_LOGIC_LIST(V) \
1906 V(addhn) \
1907 V(addhn2) \
1908 V(raddhn) \
1909 V(raddhn2) \
1910 V(subhn) \
1911 V(subhn2) \
1912 V(rsubhn) \
1913 V(rsubhn2) \
1914 V(pmull) \
1915 V(pmull2) \
1916 V(sabal) \
1917 V(sabal2) \
1918 V(uabal) \
1919 V(uabal2) \
1920 V(sabdl) \
1921 V(sabdl2) \
1922 V(uabdl) \
1923 V(uabdl2) \
1924 V(smull) \
1925 V(smull2) \
1926 V(umull) \
1927 V(umull2) \
1928 V(smlal) \
1929 V(smlal2) \
1930 V(umlal) \
1931 V(umlal2) \
1932 V(smlsl) \
1933 V(smlsl2) \
1934 V(umlsl) \
1935 V(umlsl2) \
1936 V(sqdmlal) \
1937 V(sqdmlal2) \
1938 V(sqdmlsl) \
1939 V(sqdmlsl2) \
1940 V(sqdmull) \
1941 V(sqdmull2)
1942
1943 #define DEFINE_LOGIC_FUNC(FXN) \
1944 LogicVRegister FXN(VectorFormat vform, LogicVRegister dst, \
1945 const LogicVRegister& src1, const LogicVRegister& src2);
1946 NEON_3VREG_LOGIC_LIST(DEFINE_LOGIC_FUNC)
1947 #undef DEFINE_LOGIC_FUNC
1948
1949 #define NEON_FP3SAME_LIST(V) \
1950 V(fadd, FPAdd, false) \
1951 V(fsub, FPSub, true) \
1952 V(fmul, FPMul, true) \
1953 V(fmulx, FPMulx, true) \
1954 V(fdiv, FPDiv, true) \
1955 V(fmax, FPMax, false) \
1956 V(fmin, FPMin, false) \
1957 V(fmaxnm, FPMaxNM, false) \
1958 V(fminnm, FPMinNM, false)
1959
1960 #define DECLARE_NEON_FP_VECTOR_OP(FN, OP, PROCNAN) \
1961 template <typename T> \
1962 LogicVRegister FN(VectorFormat vform, LogicVRegister dst, \
1963 const LogicVRegister& src1, const LogicVRegister& src2); \
1964 LogicVRegister FN(VectorFormat vform, LogicVRegister dst, \
1965 const LogicVRegister& src1, const LogicVRegister& src2);
1966 NEON_FP3SAME_LIST(DECLARE_NEON_FP_VECTOR_OP)
1967 #undef DECLARE_NEON_FP_VECTOR_OP
1968
1969 #define NEON_FPPAIRWISE_LIST(V) \
1970 V(faddp, fadd, FPAdd) \
1971 V(fmaxp, fmax, FPMax) \
1972 V(fmaxnmp, fmaxnm, FPMaxNM) \
1973 V(fminp, fmin, FPMin) \
1974 V(fminnmp, fminnm, FPMinNM)
1975
1976 #define DECLARE_NEON_FP_PAIR_OP(FNP, FN, OP) \
1977 LogicVRegister FNP(VectorFormat vform, LogicVRegister dst, \
1978 const LogicVRegister& src1, const LogicVRegister& src2); \
1979 LogicVRegister FNP(VectorFormat vform, LogicVRegister dst, \
1980 const LogicVRegister& src);
1981 NEON_FPPAIRWISE_LIST(DECLARE_NEON_FP_PAIR_OP)
1982 #undef DECLARE_NEON_FP_PAIR_OP
1983
1984 template <typename T>
1985 LogicVRegister frecps(VectorFormat vform, LogicVRegister dst,
1986 const LogicVRegister& src1, const LogicVRegister& src2);
1987 LogicVRegister frecps(VectorFormat vform, LogicVRegister dst,
1988 const LogicVRegister& src1, const LogicVRegister& src2);
1989 template <typename T>
1990 LogicVRegister frsqrts(VectorFormat vform, LogicVRegister dst,
1991 const LogicVRegister& src1,
1992 const LogicVRegister& src2);
1993 LogicVRegister frsqrts(VectorFormat vform, LogicVRegister dst,
1994 const LogicVRegister& src1,
1995 const LogicVRegister& src2);
1996 template <typename T>
1997 LogicVRegister fmla(VectorFormat vform, LogicVRegister dst,
1998 const LogicVRegister& src1, const LogicVRegister& src2);
1999 LogicVRegister fmla(VectorFormat vform, LogicVRegister dst,
2000 const LogicVRegister& src1, const LogicVRegister& src2);
2001 template <typename T>
2002 LogicVRegister fmls(VectorFormat vform, LogicVRegister dst,
2003 const LogicVRegister& src1, const LogicVRegister& src2);
2004 LogicVRegister fmls(VectorFormat vform, LogicVRegister dst,
2005 const LogicVRegister& src1, const LogicVRegister& src2);
2006 LogicVRegister fnmul(VectorFormat vform, LogicVRegister dst,
2007 const LogicVRegister& src1, const LogicVRegister& src2);
2008
2009 template <typename T>
2010 LogicVRegister fcmp(VectorFormat vform, LogicVRegister dst,
2011 const LogicVRegister& src1, const LogicVRegister& src2,
2012 Condition cond);
2013 LogicVRegister fcmp(VectorFormat vform, LogicVRegister dst,
2014 const LogicVRegister& src1, const LogicVRegister& src2,
2015 Condition cond);
2016 LogicVRegister fabscmp(VectorFormat vform, LogicVRegister dst,
2017 const LogicVRegister& src1, const LogicVRegister& src2,
2018 Condition cond);
2019 LogicVRegister fcmp_zero(VectorFormat vform, LogicVRegister dst,
2020 const LogicVRegister& src, Condition cond);
2021
2022 template <typename T>
2023 LogicVRegister fneg(VectorFormat vform, LogicVRegister dst,
2024 const LogicVRegister& src);
2025 LogicVRegister fneg(VectorFormat vform, LogicVRegister dst,
2026 const LogicVRegister& src);
2027 template <typename T>
2028 LogicVRegister frecpx(VectorFormat vform, LogicVRegister dst,
2029 const LogicVRegister& src);
2030 LogicVRegister frecpx(VectorFormat vform, LogicVRegister dst,
2031 const LogicVRegister& src);
2032 template <typename T>
2033 LogicVRegister fabs_(VectorFormat vform, LogicVRegister dst,
2034 const LogicVRegister& src);
2035 LogicVRegister fabs_(VectorFormat vform, LogicVRegister dst,
2036 const LogicVRegister& src);
2037 LogicVRegister fabd(VectorFormat vform, LogicVRegister dst,
2038 const LogicVRegister& src1, const LogicVRegister& src2);
2039 LogicVRegister frint(VectorFormat vform, LogicVRegister dst,
2040 const LogicVRegister& src, FPRounding rounding_mode,
2041 bool inexact_exception = false);
2042 LogicVRegister fcvts(VectorFormat vform, LogicVRegister dst,
2043 const LogicVRegister& src, FPRounding rounding_mode,
2044 int fbits = 0);
2045 LogicVRegister fcvtu(VectorFormat vform, LogicVRegister dst,
2046 const LogicVRegister& src, FPRounding rounding_mode,
2047 int fbits = 0);
2048 LogicVRegister fcvtl(VectorFormat vform, LogicVRegister dst,
2049 const LogicVRegister& src);
2050 LogicVRegister fcvtl2(VectorFormat vform, LogicVRegister dst,
2051 const LogicVRegister& src);
2052 LogicVRegister fcvtn(VectorFormat vform, LogicVRegister dst,
2053 const LogicVRegister& src);
2054 LogicVRegister fcvtn2(VectorFormat vform, LogicVRegister dst,
2055 const LogicVRegister& src);
2056 LogicVRegister fcvtxn(VectorFormat vform, LogicVRegister dst,
2057 const LogicVRegister& src);
2058 LogicVRegister fcvtxn2(VectorFormat vform, LogicVRegister dst,
2059 const LogicVRegister& src);
2060 LogicVRegister fsqrt(VectorFormat vform, LogicVRegister dst,
2061 const LogicVRegister& src);
2062 LogicVRegister frsqrte(VectorFormat vform, LogicVRegister dst,
2063 const LogicVRegister& src);
2064 LogicVRegister frecpe(VectorFormat vform, LogicVRegister dst,
2065 const LogicVRegister& src, FPRounding rounding);
2066 LogicVRegister ursqrte(VectorFormat vform, LogicVRegister dst,
2067 const LogicVRegister& src);
2068 LogicVRegister urecpe(VectorFormat vform, LogicVRegister dst,
2069 const LogicVRegister& src);
2070
2071 typedef float (Simulator::*FPMinMaxOp)(float a, float b);
2072
2073 LogicVRegister FMinMaxV(VectorFormat vform, LogicVRegister dst,
2074 const LogicVRegister& src, FPMinMaxOp Op);
2075
2076 LogicVRegister fminv(VectorFormat vform, LogicVRegister dst,
2077 const LogicVRegister& src);
2078 LogicVRegister fmaxv(VectorFormat vform, LogicVRegister dst,
2079 const LogicVRegister& src);
2080 LogicVRegister fminnmv(VectorFormat vform, LogicVRegister dst,
2081 const LogicVRegister& src);
2082 LogicVRegister fmaxnmv(VectorFormat vform, LogicVRegister dst,
2083 const LogicVRegister& src);
2084
2085 template <typename T>
2086 T FPRecipSqrtEstimate(T op);
2087 template <typename T>
2088 T FPRecipEstimate(T op, FPRounding rounding);
2089 template <typename T, typename R>
2090 R FPToFixed(T op, int fbits, bool is_signed, FPRounding rounding);
710 2091
711 void FPCompare(double val0, double val1); 2092 void FPCompare(double val0, double val1);
712 double FPRoundInt(double value, FPRounding round_mode); 2093 double FPRoundInt(double value, FPRounding round_mode);
713 double FPToDouble(float value); 2094 double FPToDouble(float value);
714 float FPToFloat(double value, FPRounding round_mode); 2095 float FPToFloat(double value, FPRounding round_mode);
2096 float FPToFloat(float16 value);
2097 float16 FPToFloat16(float value, FPRounding round_mode);
2098 float16 FPToFloat16(double value, FPRounding round_mode);
2099 double recip_sqrt_estimate(double a);
2100 double recip_estimate(double a);
2101 double FPRecipSqrtEstimate(double a);
2102 double FPRecipEstimate(double a);
715 double FixedToDouble(int64_t src, int fbits, FPRounding round_mode); 2103 double FixedToDouble(int64_t src, int fbits, FPRounding round_mode);
716 double UFixedToDouble(uint64_t src, int fbits, FPRounding round_mode); 2104 double UFixedToDouble(uint64_t src, int fbits, FPRounding round_mode);
717 float FixedToFloat(int64_t src, int fbits, FPRounding round_mode); 2105 float FixedToFloat(int64_t src, int fbits, FPRounding round_mode);
718 float UFixedToFloat(uint64_t src, int fbits, FPRounding round_mode); 2106 float UFixedToFloat(uint64_t src, int fbits, FPRounding round_mode);
719 int32_t FPToInt32(double value, FPRounding rmode); 2107 int32_t FPToInt32(double value, FPRounding rmode);
720 int64_t FPToInt64(double value, FPRounding rmode); 2108 int64_t FPToInt64(double value, FPRounding rmode);
721 uint32_t FPToUInt32(double value, FPRounding rmode); 2109 uint32_t FPToUInt32(double value, FPRounding rmode);
722 uint64_t FPToUInt64(double value, FPRounding rmode); 2110 uint64_t FPToUInt64(double value, FPRounding rmode);
723 2111
724 template <typename T> 2112 template <typename T>
(...skipping 11 matching lines...) Expand all
736 template <typename T> 2124 template <typename T>
737 T FPMin(T a, T b); 2125 T FPMin(T a, T b);
738 2126
739 template <typename T> 2127 template <typename T>
740 T FPMinNM(T a, T b); 2128 T FPMinNM(T a, T b);
741 2129
742 template <typename T> 2130 template <typename T>
743 T FPMul(T op1, T op2); 2131 T FPMul(T op1, T op2);
744 2132
745 template <typename T> 2133 template <typename T>
2134 T FPMulx(T op1, T op2);
2135
2136 template <typename T>
746 T FPMulAdd(T a, T op1, T op2); 2137 T FPMulAdd(T a, T op1, T op2);
747 2138
748 template <typename T> 2139 template <typename T>
749 T FPSqrt(T op); 2140 T FPSqrt(T op);
750 2141
751 template <typename T> 2142 template <typename T>
752 T FPSub(T op1, T op2); 2143 T FPSub(T op1, T op2);
753 2144
754 // Standard NaN processing.
755 template <typename T> 2145 template <typename T>
756 T FPProcessNaN(T op); 2146 T FPRecipStepFused(T op1, T op2);
757
758 bool FPProcessNaNs(Instruction* instr);
759 2147
760 template <typename T> 2148 template <typename T>
761 T FPProcessNaNs(T op1, T op2); 2149 T FPRSqrtStepFused(T op1, T op2);
762 2150
763 template <typename T> 2151 // This doesn't do anything at the moment. We'll need it if we want support
764 T FPProcessNaNs3(T op1, T op2, T op3); 2152 // for cumulative exception bits or floating-point exceptions.
2153 void FPProcessException() {}
2154
2155 // Standard NaN processing.
2156 bool FPProcessNaNs(Instruction* instr);
765 2157
766 void CheckStackAlignment(); 2158 void CheckStackAlignment();
767 2159
768 inline void CheckPCSComplianceAndRun(); 2160 inline void CheckPCSComplianceAndRun();
769 2161
770 #ifdef DEBUG 2162 #ifdef DEBUG
771 // Corruption values should have their least significant byte cleared to 2163 // Corruption values should have their least significant byte cleared to
772 // allow the code of the register being corrupted to be inserted. 2164 // allow the code of the register being corrupted to be inserted.
773 static const uint64_t kCallerSavedRegisterCorruptionValue = 2165 static const uint64_t kCallerSavedRegisterCorruptionValue =
774 0xca11edc0de000000UL; 2166 0xca11edc0de000000UL;
775 // This value is a NaN in both 32-bit and 64-bit FP. 2167 // This value is a NaN in both 32-bit and 64-bit FP.
776 static const uint64_t kCallerSavedFPRegisterCorruptionValue = 2168 static const uint64_t kCallerSavedVRegisterCorruptionValue =
777 0x7ff000007f801000UL; 2169 0x7ff000007f801000UL;
778 // This value is a mix of 32/64-bits NaN and "verbose" immediate. 2170 // This value is a mix of 32/64-bits NaN and "verbose" immediate.
779 static const uint64_t kDefaultCPURegisterCorruptionValue = 2171 static const uint64_t kDefaultCPURegisterCorruptionValue =
780 0x7ffbad007f8bad00UL; 2172 0x7ffbad007f8bad00UL;
781 2173
782 void CorruptRegisters(CPURegList* list, 2174 void CorruptRegisters(CPURegList* list,
783 uint64_t value = kDefaultCPURegisterCorruptionValue); 2175 uint64_t value = kDefaultCPURegisterCorruptionValue);
784 void CorruptAllCallerSavedCPURegisters(); 2176 void CorruptAllCallerSavedCPURegisters();
785 #endif 2177 #endif
786 2178
787 // Pseudo Printf instruction 2179 // Pseudo Printf instruction
788 void DoPrintf(Instruction* instr); 2180 void DoPrintf(Instruction* instr);
789 2181
790 // Processor state --------------------------------------- 2182 // Processor state ---------------------------------------
791 2183
792 // Output stream. 2184 // Output stream.
793 FILE* stream_; 2185 FILE* stream_;
794 PrintDisassembler* print_disasm_; 2186 PrintDisassembler* print_disasm_;
795 void PRINTF_FORMAT(2, 3) TraceSim(const char* format, ...); 2187 void PRINTF_FORMAT(2, 3) TraceSim(const char* format, ...);
796 2188
797 // Instrumentation. 2189 // Instrumentation.
798 Instrument* instrument_; 2190 Instrument* instrument_;
799 2191
800 // General purpose registers. Register 31 is the stack pointer. 2192 // General purpose registers. Register 31 is the stack pointer.
801 SimRegister registers_[kNumberOfRegisters]; 2193 SimRegister registers_[kNumberOfRegisters];
802 2194
803 // Floating point registers 2195 // Floating point registers
804 SimFPRegister fpregisters_[kNumberOfFPRegisters]; 2196 SimVRegister vregisters_[kNumberOfVRegisters];
805 2197
806 // Processor state 2198 // Processor state
807 // bits[31, 27]: Condition flags N, Z, C, and V. 2199 // bits[31, 27]: Condition flags N, Z, C, and V.
808 // (Negative, Zero, Carry, Overflow) 2200 // (Negative, Zero, Carry, Overflow)
809 SimSystemRegister nzcv_; 2201 SimSystemRegister nzcv_;
810 2202
811 // Floating-Point Control Register 2203 // Floating-Point Control Register
812 SimSystemRegister fpcr_; 2204 SimSystemRegister fpcr_;
813 2205
814 // Only a subset of FPCR features are supported by the simulator. This helper 2206 // Only a subset of FPCR features are supported by the simulator. This helper
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
861 void set_last_debugger_input(char* input) { 2253 void set_last_debugger_input(char* input) {
862 DeleteArray(last_debugger_input_); 2254 DeleteArray(last_debugger_input_);
863 last_debugger_input_ = input; 2255 last_debugger_input_ = input;
864 } 2256 }
865 char* last_debugger_input() { return last_debugger_input_; } 2257 char* last_debugger_input() { return last_debugger_input_; }
866 char* last_debugger_input_; 2258 char* last_debugger_input_;
867 2259
868 private: 2260 private:
869 void Init(FILE* stream); 2261 void Init(FILE* stream);
870 2262
2263 template <typename T>
2264 static T FPDefaultNaN();
2265
2266 template <typename T>
2267 T FPProcessNaN(T op) {
2268 DCHECK(std::isnan(op));
2269 return fpcr().DN() ? FPDefaultNaN<T>() : ToQuietNaN(op);
2270 }
2271
2272 template <typename T>
2273 T FPProcessNaNs(T op1, T op2) {
2274 if (IsSignallingNaN(op1)) {
2275 return FPProcessNaN(op1);
2276 } else if (IsSignallingNaN(op2)) {
2277 return FPProcessNaN(op2);
2278 } else if (std::isnan(op1)) {
2279 DCHECK(IsQuietNaN(op1));
2280 return FPProcessNaN(op1);
2281 } else if (std::isnan(op2)) {
2282 DCHECK(IsQuietNaN(op2));
2283 return FPProcessNaN(op2);
2284 } else {
2285 return 0.0;
2286 }
2287 }
2288
2289 template <typename T>
2290 T FPProcessNaNs3(T op1, T op2, T op3) {
2291 if (IsSignallingNaN(op1)) {
2292 return FPProcessNaN(op1);
2293 } else if (IsSignallingNaN(op2)) {
2294 return FPProcessNaN(op2);
2295 } else if (IsSignallingNaN(op3)) {
2296 return FPProcessNaN(op3);
2297 } else if (std::isnan(op1)) {
2298 DCHECK(IsQuietNaN(op1));
2299 return FPProcessNaN(op1);
2300 } else if (std::isnan(op2)) {
2301 DCHECK(IsQuietNaN(op2));
2302 return FPProcessNaN(op2);
2303 } else if (std::isnan(op3)) {
2304 DCHECK(IsQuietNaN(op3));
2305 return FPProcessNaN(op3);
2306 } else {
2307 return 0.0;
2308 }
2309 }
2310
871 int log_parameters_; 2311 int log_parameters_;
872 Isolate* isolate_; 2312 Isolate* isolate_;
873 }; 2313 };
874 2314
875 2315
876 // When running with the simulator transition into simulated execution at this 2316 // When running with the simulator transition into simulated execution at this
877 // point. 2317 // point.
878 #define CALL_GENERATED_CODE(isolate, entry, p0, p1, p2, p3, p4) \ 2318 #define CALL_GENERATED_CODE(isolate, entry, p0, p1, p2, p3, p4) \
879 reinterpret_cast<Object*>(Simulator::current(isolate)->CallJS( \ 2319 reinterpret_cast<Object*>(Simulator::current(isolate)->CallJS( \
880 FUNCTION_ADDR(entry), p0, p1, p2, p3, p4)) 2320 FUNCTION_ADDR(entry), p0, p1, p2, p3, p4))
(...skipping 25 matching lines...) Expand all
906 Simulator::current(isolate)->PopAddress(); 2346 Simulator::current(isolate)->PopAddress();
907 } 2347 }
908 }; 2348 };
909 2349
910 #endif // !defined(USE_SIMULATOR) 2350 #endif // !defined(USE_SIMULATOR)
911 2351
912 } // namespace internal 2352 } // namespace internal
913 } // namespace v8 2353 } // namespace v8
914 2354
915 #endif // V8_ARM64_SIMULATOR_ARM64_H_ 2355 #endif // V8_ARM64_SIMULATOR_ARM64_H_
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698