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

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

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

Powered by Google App Engine
This is Rietveld 408576698