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

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

Issue 196133017: Experimental parser: merge r19949 (Closed) Base URL: https://v8.googlecode.com/svn/branches/experimental/parser
Patch Set: Created 6 years, 9 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 | Annotate | Revision Log
« no previous file with comments | « src/a64/regexp-macro-assembler-a64.cc ('k') | src/a64/simulator-a64.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 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 168 matching lines...) Expand 10 before | Expand all | Expand 10 after
179 ASSERT(size <= kSizeInBytes); 179 ASSERT(size <= kSizeInBytes);
180 T result; 180 T result;
181 memset(&result, 0, sizeof(result)); 181 memset(&result, 0, sizeof(result));
182 memcpy(&result, value_, size); 182 memcpy(&result, value_, size);
183 return result; 183 return result;
184 } 184 }
185 185
186 protected: 186 protected:
187 uint8_t value_[kSizeInBytes]; 187 uint8_t value_[kSizeInBytes];
188 }; 188 };
189 typedef SimRegisterBase<kXRegSizeInBytes> SimRegister; // r0-r31 189 typedef SimRegisterBase<kXRegSize> SimRegister; // r0-r31
190 typedef SimRegisterBase<kDRegSizeInBytes> SimFPRegister; // v0-v31 190 typedef SimRegisterBase<kDRegSize> SimFPRegister; // v0-v31
191 191
192 192
193 class Simulator : public DecoderVisitor { 193 class Simulator : public DecoderVisitor {
194 public: 194 public:
195 explicit Simulator(Decoder<DispatchingDecoderVisitor>* decoder, 195 explicit Simulator(Decoder<DispatchingDecoderVisitor>* decoder,
196 Isolate* isolate = NULL, 196 Isolate* isolate = NULL,
197 FILE* stream = stderr); 197 FILE* stream = stderr);
198 Simulator(); 198 Simulator();
199 ~Simulator(); 199 ~Simulator();
200 200
(...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after
351 // Declare all Visitor functions. 351 // Declare all Visitor functions.
352 #define DECLARE(A) void Visit##A(Instruction* instr); 352 #define DECLARE(A) void Visit##A(Instruction* instr);
353 VISITOR_LIST(DECLARE) 353 VISITOR_LIST(DECLARE)
354 #undef DECLARE 354 #undef DECLARE
355 355
356 // Register accessors. 356 // Register accessors.
357 357
358 // Return 'size' bits of the value of an integer register, as the specified 358 // Return 'size' bits of the value of an integer register, as the specified
359 // type. The value is zero-extended to fill the result. 359 // type. The value is zero-extended to fill the result.
360 // 360 //
361 // The only supported values of 'size' are kXRegSize and kWRegSize. 361 // The only supported values of 'size' are kXRegSizeInBits and
362 // kWRegSizeInBits.
362 template<typename T> 363 template<typename T>
363 T reg(unsigned size, unsigned code, 364 T reg(unsigned size, unsigned code,
364 Reg31Mode r31mode = Reg31IsZeroRegister) const { 365 Reg31Mode r31mode = Reg31IsZeroRegister) const {
365 unsigned size_in_bytes = size / 8; 366 unsigned size_in_bytes = size / 8;
366 ASSERT(size_in_bytes <= sizeof(T)); 367 ASSERT(size_in_bytes <= sizeof(T));
367 ASSERT((size == kXRegSize) || (size == kWRegSize)); 368 ASSERT((size == kXRegSizeInBits) || (size == kWRegSizeInBits));
368 ASSERT(code < kNumberOfRegisters); 369 ASSERT(code < kNumberOfRegisters);
369 370
370 if ((code == 31) && (r31mode == Reg31IsZeroRegister)) { 371 if ((code == 31) && (r31mode == Reg31IsZeroRegister)) {
371 T result; 372 T result;
372 memset(&result, 0, sizeof(result)); 373 memset(&result, 0, sizeof(result));
373 return result; 374 return result;
374 } 375 }
375 return registers_[code].Get<T>(size_in_bytes); 376 return registers_[code].Get<T>(size_in_bytes);
376 } 377 }
377 378
(...skipping 15 matching lines...) Expand all
393 } 394 }
394 395
395 int64_t reg(unsigned size, unsigned code, 396 int64_t reg(unsigned size, unsigned code,
396 Reg31Mode r31mode = Reg31IsZeroRegister) const { 397 Reg31Mode r31mode = Reg31IsZeroRegister) const {
397 return reg<int64_t>(size, code, r31mode); 398 return reg<int64_t>(size, code, r31mode);
398 } 399 }
399 400
400 // Write 'size' bits of 'value' into an integer register. The value is 401 // Write 'size' bits of 'value' into an integer register. The value is
401 // zero-extended. This behaviour matches AArch64 register writes. 402 // zero-extended. This behaviour matches AArch64 register writes.
402 // 403 //
403 // The only supported values of 'size' are kXRegSize and kWRegSize. 404 // The only supported values of 'size' are kXRegSizeInBits and
405 // kWRegSizeInBits.
404 template<typename T> 406 template<typename T>
405 void set_reg(unsigned size, unsigned code, T value, 407 void set_reg(unsigned size, unsigned code, T value,
406 Reg31Mode r31mode = Reg31IsZeroRegister) { 408 Reg31Mode r31mode = Reg31IsZeroRegister) {
407 unsigned size_in_bytes = size / 8; 409 unsigned size_in_bytes = size / 8;
408 ASSERT(size_in_bytes <= sizeof(T)); 410 ASSERT(size_in_bytes <= sizeof(T));
409 ASSERT((size == kXRegSize) || (size == kWRegSize)); 411 ASSERT((size == kXRegSizeInBits) || (size == kWRegSizeInBits));
410 ASSERT(code < kNumberOfRegisters); 412 ASSERT(code < kNumberOfRegisters);
411 413
412 if ((code == 31) && (r31mode == Reg31IsZeroRegister)) { 414 if ((code == 31) && (r31mode == Reg31IsZeroRegister)) {
413 return; 415 return;
414 } 416 }
415 return registers_[code].Set(value, size_in_bytes); 417 return registers_[code].Set(value, size_in_bytes);
416 } 418 }
417 419
418 // Like set_reg(), but infer the access size from the template type. 420 // Like set_reg(), but infer the access size from the template type.
419 template<typename T> 421 template<typename T>
420 void set_reg(unsigned code, T value, 422 void set_reg(unsigned code, T value,
421 Reg31Mode r31mode = Reg31IsZeroRegister) { 423 Reg31Mode r31mode = Reg31IsZeroRegister) {
422 set_reg(sizeof(value) * 8, code, value, r31mode); 424 set_reg(sizeof(value) * 8, code, value, r31mode);
423 } 425 }
424 426
425 // Common specialized accessors for the set_reg() template. 427 // Common specialized accessors for the set_reg() template.
426 void set_wreg(unsigned code, int32_t value, 428 void set_wreg(unsigned code, int32_t value,
427 Reg31Mode r31mode = Reg31IsZeroRegister) { 429 Reg31Mode r31mode = Reg31IsZeroRegister) {
428 set_reg(kWRegSize, code, value, r31mode); 430 set_reg(kWRegSizeInBits, code, value, r31mode);
429 } 431 }
430 432
431 void set_xreg(unsigned code, int64_t value, 433 void set_xreg(unsigned code, int64_t value,
432 Reg31Mode r31mode = Reg31IsZeroRegister) { 434 Reg31Mode r31mode = Reg31IsZeroRegister) {
433 set_reg(kXRegSize, code, value, r31mode); 435 set_reg(kXRegSizeInBits, code, value, r31mode);
434 } 436 }
435 437
436 // Commonly-used special cases. 438 // Commonly-used special cases.
437 template<typename T> 439 template<typename T>
438 void set_lr(T value) { 440 void set_lr(T value) {
439 ASSERT(sizeof(T) == kPointerSize); 441 ASSERT(sizeof(T) == kPointerSize);
440 set_reg(kLinkRegCode, value); 442 set_reg(kLinkRegCode, value);
441 } 443 }
442 444
443 template<typename T> 445 template<typename T>
444 void set_sp(T value) { 446 void set_sp(T value) {
445 ASSERT(sizeof(T) == kPointerSize); 447 ASSERT(sizeof(T) == kPointerSize);
446 set_reg(31, value, Reg31IsStackPointer); 448 set_reg(31, value, Reg31IsStackPointer);
447 } 449 }
448 450
449 int64_t sp() { return xreg(31, Reg31IsStackPointer); } 451 int64_t sp() { return xreg(31, Reg31IsStackPointer); }
450 int64_t jssp() { return xreg(kJSSPCode, Reg31IsStackPointer); } 452 int64_t jssp() { return xreg(kJSSPCode, Reg31IsStackPointer); }
451 int64_t fp() { 453 int64_t fp() {
452 return xreg(kFramePointerRegCode, Reg31IsStackPointer); 454 return xreg(kFramePointerRegCode, Reg31IsStackPointer);
453 } 455 }
454 Instruction* lr() { return reg<Instruction*>(kLinkRegCode); } 456 Instruction* lr() { return reg<Instruction*>(kLinkRegCode); }
455 457
456 Address get_sp() { return reg<Address>(31, Reg31IsStackPointer); } 458 Address get_sp() { return reg<Address>(31, Reg31IsStackPointer); }
457 459
458 // Return 'size' bits of the value of a floating-point register, as the 460 // Return 'size' bits of the value of a floating-point register, as the
459 // specified type. The value is zero-extended to fill the result. 461 // specified type. The value is zero-extended to fill the result.
460 // 462 //
461 // The only supported values of 'size' are kDRegSize and kSRegSize. 463 // The only supported values of 'size' are kDRegSizeInBits and
464 // kSRegSizeInBits.
462 template<typename T> 465 template<typename T>
463 T fpreg(unsigned size, unsigned code) const { 466 T fpreg(unsigned size, unsigned code) const {
464 unsigned size_in_bytes = size / 8; 467 unsigned size_in_bytes = size / 8;
465 ASSERT(size_in_bytes <= sizeof(T)); 468 ASSERT(size_in_bytes <= sizeof(T));
466 ASSERT((size == kDRegSize) || (size == kSRegSize)); 469 ASSERT((size == kDRegSizeInBits) || (size == kSRegSizeInBits));
467 ASSERT(code < kNumberOfFPRegisters); 470 ASSERT(code < kNumberOfFPRegisters);
468 return fpregisters_[code].Get<T>(size_in_bytes); 471 return fpregisters_[code].Get<T>(size_in_bytes);
469 } 472 }
470 473
471 // Like fpreg(), but infer the access size from the template type. 474 // Like fpreg(), but infer the access size from the template type.
472 template<typename T> 475 template<typename T>
473 T fpreg(unsigned code) const { 476 T fpreg(unsigned code) const {
474 return fpreg<T>(sizeof(T) * 8, code); 477 return fpreg<T>(sizeof(T) * 8, code);
475 } 478 }
476 479
477 // Common specialized accessors for the fpreg() template. 480 // Common specialized accessors for the fpreg() template.
478 float sreg(unsigned code) const { 481 float sreg(unsigned code) const {
479 return fpreg<float>(code); 482 return fpreg<float>(code);
480 } 483 }
481 484
482 uint32_t sreg_bits(unsigned code) const { 485 uint32_t sreg_bits(unsigned code) const {
483 return fpreg<uint32_t>(code); 486 return fpreg<uint32_t>(code);
484 } 487 }
485 488
486 double dreg(unsigned code) const { 489 double dreg(unsigned code) const {
487 return fpreg<double>(code); 490 return fpreg<double>(code);
488 } 491 }
489 492
490 uint64_t dreg_bits(unsigned code) const { 493 uint64_t dreg_bits(unsigned code) const {
491 return fpreg<uint64_t>(code); 494 return fpreg<uint64_t>(code);
492 } 495 }
493 496
494 double fpreg(unsigned size, unsigned code) const { 497 double fpreg(unsigned size, unsigned code) const {
495 switch (size) { 498 switch (size) {
496 case kSRegSize: return sreg(code); 499 case kSRegSizeInBits: return sreg(code);
497 case kDRegSize: return dreg(code); 500 case kDRegSizeInBits: return dreg(code);
498 default: 501 default:
499 UNREACHABLE(); 502 UNREACHABLE();
500 return 0.0; 503 return 0.0;
501 } 504 }
502 } 505 }
503 506
504 // Write 'value' into a floating-point register. The value is zero-extended. 507 // Write 'value' into a floating-point register. The value is zero-extended.
505 // This behaviour matches AArch64 register writes. 508 // This behaviour matches AArch64 register writes.
506 template<typename T> 509 template<typename T>
507 void set_fpreg(unsigned code, T value) { 510 void set_fpreg(unsigned code, T value) {
508 ASSERT((sizeof(value) == kDRegSizeInBytes) || 511 ASSERT((sizeof(value) == kDRegSize) || (sizeof(value) == kSRegSize));
509 (sizeof(value) == kSRegSizeInBytes));
510 ASSERT(code < kNumberOfFPRegisters); 512 ASSERT(code < kNumberOfFPRegisters);
511 fpregisters_[code].Set(value, sizeof(value)); 513 fpregisters_[code].Set(value, sizeof(value));
512 } 514 }
513 515
514 // Common specialized accessors for the set_fpreg() template. 516 // Common specialized accessors for the set_fpreg() template.
515 void set_sreg(unsigned code, float value) { 517 void set_sreg(unsigned code, float value) {
516 set_fpreg(code, value); 518 set_fpreg(code, value);
517 } 519 }
518 520
519 void set_sreg_bits(unsigned code, uint32_t value) { 521 void set_sreg_bits(unsigned code, uint32_t value) {
520 set_fpreg(code, value); 522 set_fpreg(code, value);
521 } 523 }
522 524
523 void set_dreg(unsigned code, double value) { 525 void set_dreg(unsigned code, double value) {
524 set_fpreg(code, value); 526 set_fpreg(code, value);
525 } 527 }
526 528
527 void set_dreg_bits(unsigned code, uint64_t value) { 529 void set_dreg_bits(unsigned code, uint64_t value) {
528 set_fpreg(code, value); 530 set_fpreg(code, value);
529 } 531 }
530 532
531 bool N() { return nzcv_.N() != 0; } 533 bool N() { return nzcv_.N() != 0; }
532 bool Z() { return nzcv_.Z() != 0; } 534 bool Z() { return nzcv_.Z() != 0; }
533 bool C() { return nzcv_.C() != 0; } 535 bool C() { return nzcv_.C() != 0; }
534 bool V() { return nzcv_.V() != 0; } 536 bool V() { return nzcv_.V() != 0; }
535 SimSystemRegister& nzcv() { return nzcv_; } 537 SimSystemRegister& nzcv() { return nzcv_; }
536 538
537 // TODO(jbramley): Find a way to make the fpcr_ members return the proper 539 // TODO(jbramley): Find a way to make the fpcr_ members return the proper
538 // types, so this accessor is not necessary. 540 // types, so these accessors are not necessary.
539 FPRounding RMode() { return static_cast<FPRounding>(fpcr_.RMode()); } 541 FPRounding RMode() { return static_cast<FPRounding>(fpcr_.RMode()); }
542 bool DN() { return fpcr_.DN() != 0; }
540 SimSystemRegister& fpcr() { return fpcr_; } 543 SimSystemRegister& fpcr() { return fpcr_; }
541 544
542 // Debug helpers 545 // Debug helpers
543 546
544 // Simulator breakpoints. 547 // Simulator breakpoints.
545 struct Breakpoint { 548 struct Breakpoint {
546 Instruction* location; 549 Instruction* location;
547 bool enabled; 550 bool enabled;
548 }; 551 };
549 std::vector<Breakpoint> breakpoints_; 552 std::vector<Breakpoint> breakpoints_;
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after
698 Shift shift_type, 701 Shift shift_type,
699 unsigned amount); 702 unsigned amount);
700 int64_t ExtendValue(unsigned reg_width, 703 int64_t ExtendValue(unsigned reg_width,
701 int64_t value, 704 int64_t value,
702 Extend extend_type, 705 Extend extend_type,
703 unsigned left_shift = 0); 706 unsigned left_shift = 0);
704 707
705 uint64_t ReverseBits(uint64_t value, unsigned num_bits); 708 uint64_t ReverseBits(uint64_t value, unsigned num_bits);
706 uint64_t ReverseBytes(uint64_t value, ReverseByteMode mode); 709 uint64_t ReverseBytes(uint64_t value, ReverseByteMode mode);
707 710
711 template <typename T>
712 T FPDefaultNaN() const;
713
708 void FPCompare(double val0, double val1); 714 void FPCompare(double val0, double val1);
709 double FPRoundInt(double value, FPRounding round_mode); 715 double FPRoundInt(double value, FPRounding round_mode);
710 double FPToDouble(float value); 716 double FPToDouble(float value);
711 float FPToFloat(double value, FPRounding round_mode); 717 float FPToFloat(double value, FPRounding round_mode);
712 double FixedToDouble(int64_t src, int fbits, FPRounding round_mode); 718 double FixedToDouble(int64_t src, int fbits, FPRounding round_mode);
713 double UFixedToDouble(uint64_t src, int fbits, FPRounding round_mode); 719 double UFixedToDouble(uint64_t src, int fbits, FPRounding round_mode);
714 float FixedToFloat(int64_t src, int fbits, FPRounding round_mode); 720 float FixedToFloat(int64_t src, int fbits, FPRounding round_mode);
715 float UFixedToFloat(uint64_t src, int fbits, FPRounding round_mode); 721 float UFixedToFloat(uint64_t src, int fbits, FPRounding round_mode);
716 int32_t FPToInt32(double value, FPRounding rmode); 722 int32_t FPToInt32(double value, FPRounding rmode);
717 int64_t FPToInt64(double value, FPRounding rmode); 723 int64_t FPToInt64(double value, FPRounding rmode);
718 uint32_t FPToUInt32(double value, FPRounding rmode); 724 uint32_t FPToUInt32(double value, FPRounding rmode);
719 uint64_t FPToUInt64(double value, FPRounding rmode); 725 uint64_t FPToUInt64(double value, FPRounding rmode);
720 726
721 template <typename T> 727 template <typename T>
728 T FPAdd(T op1, T op2);
729
730 template <typename T>
731 T FPDiv(T op1, T op2);
732
733 template <typename T>
722 T FPMax(T a, T b); 734 T FPMax(T a, T b);
723 735
724 template <typename T> 736 template <typename T>
725 T FPMin(T a, T b); 737 T FPMaxNM(T a, T b);
726 738
727 template <typename T> 739 template <typename T>
728 T FPMaxNM(T a, T b); 740 T FPMin(T a, T b);
729 741
730 template <typename T> 742 template <typename T>
731 T FPMinNM(T a, T b); 743 T FPMinNM(T a, T b);
732 744
745 template <typename T>
746 T FPMul(T op1, T op2);
747
748 template <typename T>
749 T FPMulAdd(T a, T op1, T op2);
750
751 template <typename T>
752 T FPSqrt(T op);
753
754 template <typename T>
755 T FPSub(T op1, T op2);
756
757 // Standard NaN processing.
758 template <typename T>
759 T FPProcessNaN(T op);
760
761 bool FPProcessNaNs(Instruction* instr);
762
763 template <typename T>
764 T FPProcessNaNs(T op1, T op2);
765
766 template <typename T>
767 T FPProcessNaNs3(T op1, T op2, T op3);
768
733 void CheckStackAlignment(); 769 void CheckStackAlignment();
734 770
735 inline void CheckPCSComplianceAndRun(); 771 inline void CheckPCSComplianceAndRun();
736 772
737 #ifdef DEBUG 773 #ifdef DEBUG
738 // Corruption values should have their least significant byte cleared to 774 // Corruption values should have their least significant byte cleared to
739 // allow the code of the register being corrupted to be inserted. 775 // allow the code of the register being corrupted to be inserted.
740 static const uint64_t kCallerSavedRegisterCorruptionValue = 776 static const uint64_t kCallerSavedRegisterCorruptionValue =
741 0xca11edc0de000000UL; 777 0xca11edc0de000000UL;
742 // This value is a NaN in both 32-bit and 64-bit FP. 778 // This value is a NaN in both 32-bit and 64-bit FP.
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
775 SimSystemRegister fpcr_; 811 SimSystemRegister fpcr_;
776 812
777 // Only a subset of FPCR features are supported by the simulator. This helper 813 // Only a subset of FPCR features are supported by the simulator. This helper
778 // checks that the FPCR settings are supported. 814 // checks that the FPCR settings are supported.
779 // 815 //
780 // This is checked when floating-point instructions are executed, not when 816 // This is checked when floating-point instructions are executed, not when
781 // FPCR is set. This allows generated code to modify FPCR for external 817 // FPCR is set. This allows generated code to modify FPCR for external
782 // functions, or to save and restore it when entering and leaving generated 818 // functions, or to save and restore it when entering and leaving generated
783 // code. 819 // code.
784 void AssertSupportedFPCR() { 820 void AssertSupportedFPCR() {
785 ASSERT(fpcr().DN() == 0); // No default-NaN support.
786 ASSERT(fpcr().FZ() == 0); // No flush-to-zero support. 821 ASSERT(fpcr().FZ() == 0); // No flush-to-zero support.
787 ASSERT(fpcr().RMode() == FPTieEven); // Ties-to-even rounding only. 822 ASSERT(fpcr().RMode() == FPTieEven); // Ties-to-even rounding only.
788 823
789 // The simulator does not support half-precision operations so fpcr().AHP() 824 // The simulator does not support half-precision operations so fpcr().AHP()
790 // is irrelevant, and is not checked here. 825 // is irrelevant, and is not checked here.
791 } 826 }
792 827
793 static int CalcNFlag(uint64_t result, unsigned reg_size) { 828 static int CalcNFlag(uint64_t result, unsigned reg_size) {
794 return (result >> (reg_size - 1)) & 1; 829 return (result >> (reg_size - 1)) & 1;
795 } 830 }
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after
872 static void UnregisterCTryCatch() { 907 static void UnregisterCTryCatch() {
873 Simulator::current(Isolate::Current())->PopAddress(); 908 Simulator::current(Isolate::Current())->PopAddress();
874 } 909 }
875 }; 910 };
876 911
877 #endif // !defined(USE_SIMULATOR) 912 #endif // !defined(USE_SIMULATOR)
878 913
879 } } // namespace v8::internal 914 } } // namespace v8::internal
880 915
881 #endif // V8_A64_SIMULATOR_A64_H_ 916 #endif // V8_A64_SIMULATOR_A64_H_
OLDNEW
« no previous file with comments | « src/a64/regexp-macro-assembler-a64.cc ('k') | src/a64/simulator-a64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698