OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 #include <stdarg.h> | 5 #include <stdarg.h> |
6 #include <stdlib.h> | 6 #include <stdlib.h> |
7 #include <cmath> | 7 #include <cmath> |
8 | 8 |
9 #include "src/v8.h" | 9 #include "src/v8.h" |
10 | 10 |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
80 } | 80 } |
81 | 81 |
82 | 82 |
83 void ArmDebugger::Stop(Instruction* instr) { | 83 void ArmDebugger::Stop(Instruction* instr) { |
84 // Get the stop code. | 84 // Get the stop code. |
85 uint32_t code = instr->SvcValue() & kStopCodeMask; | 85 uint32_t code = instr->SvcValue() & kStopCodeMask; |
86 // Retrieve the encoded address, which comes just after this stop. | 86 // Retrieve the encoded address, which comes just after this stop. |
87 char** msg_address = | 87 char** msg_address = |
88 reinterpret_cast<char**>(sim_->get_pc() + Instruction::kInstrSize); | 88 reinterpret_cast<char**>(sim_->get_pc() + Instruction::kInstrSize); |
89 char* msg = *msg_address; | 89 char* msg = *msg_address; |
90 ASSERT(msg != NULL); | 90 DCHECK(msg != NULL); |
91 | 91 |
92 // Update this stop description. | 92 // Update this stop description. |
93 if (isWatchedStop(code) && !watched_stops_[code].desc) { | 93 if (isWatchedStop(code) && !watched_stops_[code].desc) { |
94 watched_stops_[code].desc = msg; | 94 watched_stops_[code].desc = msg; |
95 } | 95 } |
96 | 96 |
97 if (strlen(msg) > 0) { | 97 if (strlen(msg) > 0) { |
98 if (coverage_log != NULL) { | 98 if (coverage_log != NULL) { |
99 fprintf(coverage_log, "%s\n", msg); | 99 fprintf(coverage_log, "%s\n", msg); |
100 fflush(coverage_log); | 100 fflush(coverage_log); |
(...skipping 500 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
601 | 601 |
602 #undef COMMAND_SIZE | 602 #undef COMMAND_SIZE |
603 #undef ARG_SIZE | 603 #undef ARG_SIZE |
604 | 604 |
605 #undef STR | 605 #undef STR |
606 #undef XSTR | 606 #undef XSTR |
607 } | 607 } |
608 | 608 |
609 | 609 |
610 static bool ICacheMatch(void* one, void* two) { | 610 static bool ICacheMatch(void* one, void* two) { |
611 ASSERT((reinterpret_cast<intptr_t>(one) & CachePage::kPageMask) == 0); | 611 DCHECK((reinterpret_cast<intptr_t>(one) & CachePage::kPageMask) == 0); |
612 ASSERT((reinterpret_cast<intptr_t>(two) & CachePage::kPageMask) == 0); | 612 DCHECK((reinterpret_cast<intptr_t>(two) & CachePage::kPageMask) == 0); |
613 return one == two; | 613 return one == two; |
614 } | 614 } |
615 | 615 |
616 | 616 |
617 static uint32_t ICacheHash(void* key) { | 617 static uint32_t ICacheHash(void* key) { |
618 return static_cast<uint32_t>(reinterpret_cast<uintptr_t>(key)) >> 2; | 618 return static_cast<uint32_t>(reinterpret_cast<uintptr_t>(key)) >> 2; |
619 } | 619 } |
620 | 620 |
621 | 621 |
622 static bool AllOnOnePage(uintptr_t start, int size) { | 622 static bool AllOnOnePage(uintptr_t start, int size) { |
(...skipping 16 matching lines...) Expand all Loading... |
639 int intra_line = (start & CachePage::kLineMask); | 639 int intra_line = (start & CachePage::kLineMask); |
640 start -= intra_line; | 640 start -= intra_line; |
641 size += intra_line; | 641 size += intra_line; |
642 size = ((size - 1) | CachePage::kLineMask) + 1; | 642 size = ((size - 1) | CachePage::kLineMask) + 1; |
643 int offset = (start & CachePage::kPageMask); | 643 int offset = (start & CachePage::kPageMask); |
644 while (!AllOnOnePage(start, size - 1)) { | 644 while (!AllOnOnePage(start, size - 1)) { |
645 int bytes_to_flush = CachePage::kPageSize - offset; | 645 int bytes_to_flush = CachePage::kPageSize - offset; |
646 FlushOnePage(i_cache, start, bytes_to_flush); | 646 FlushOnePage(i_cache, start, bytes_to_flush); |
647 start += bytes_to_flush; | 647 start += bytes_to_flush; |
648 size -= bytes_to_flush; | 648 size -= bytes_to_flush; |
649 ASSERT_EQ(0, start & CachePage::kPageMask); | 649 DCHECK_EQ(0, start & CachePage::kPageMask); |
650 offset = 0; | 650 offset = 0; |
651 } | 651 } |
652 if (size != 0) { | 652 if (size != 0) { |
653 FlushOnePage(i_cache, start, size); | 653 FlushOnePage(i_cache, start, size); |
654 } | 654 } |
655 } | 655 } |
656 | 656 |
657 | 657 |
658 CachePage* Simulator::GetCachePage(v8::internal::HashMap* i_cache, void* page) { | 658 CachePage* Simulator::GetCachePage(v8::internal::HashMap* i_cache, void* page) { |
659 v8::internal::HashMap::Entry* entry = i_cache->Lookup(page, | 659 v8::internal::HashMap::Entry* entry = i_cache->Lookup(page, |
660 ICacheHash(page), | 660 ICacheHash(page), |
661 true); | 661 true); |
662 if (entry->value == NULL) { | 662 if (entry->value == NULL) { |
663 CachePage* new_page = new CachePage(); | 663 CachePage* new_page = new CachePage(); |
664 entry->value = new_page; | 664 entry->value = new_page; |
665 } | 665 } |
666 return reinterpret_cast<CachePage*>(entry->value); | 666 return reinterpret_cast<CachePage*>(entry->value); |
667 } | 667 } |
668 | 668 |
669 | 669 |
670 // Flush from start up to and not including start + size. | 670 // Flush from start up to and not including start + size. |
671 void Simulator::FlushOnePage(v8::internal::HashMap* i_cache, | 671 void Simulator::FlushOnePage(v8::internal::HashMap* i_cache, |
672 intptr_t start, | 672 intptr_t start, |
673 int size) { | 673 int size) { |
674 ASSERT(size <= CachePage::kPageSize); | 674 DCHECK(size <= CachePage::kPageSize); |
675 ASSERT(AllOnOnePage(start, size - 1)); | 675 DCHECK(AllOnOnePage(start, size - 1)); |
676 ASSERT((start & CachePage::kLineMask) == 0); | 676 DCHECK((start & CachePage::kLineMask) == 0); |
677 ASSERT((size & CachePage::kLineMask) == 0); | 677 DCHECK((size & CachePage::kLineMask) == 0); |
678 void* page = reinterpret_cast<void*>(start & (~CachePage::kPageMask)); | 678 void* page = reinterpret_cast<void*>(start & (~CachePage::kPageMask)); |
679 int offset = (start & CachePage::kPageMask); | 679 int offset = (start & CachePage::kPageMask); |
680 CachePage* cache_page = GetCachePage(i_cache, page); | 680 CachePage* cache_page = GetCachePage(i_cache, page); |
681 char* valid_bytemap = cache_page->ValidityByte(offset); | 681 char* valid_bytemap = cache_page->ValidityByte(offset); |
682 memset(valid_bytemap, CachePage::LINE_INVALID, size >> CachePage::kLineShift); | 682 memset(valid_bytemap, CachePage::LINE_INVALID, size >> CachePage::kLineShift); |
683 } | 683 } |
684 | 684 |
685 | 685 |
686 void Simulator::CheckICache(v8::internal::HashMap* i_cache, | 686 void Simulator::CheckICache(v8::internal::HashMap* i_cache, |
687 Instruction* instr) { | 687 Instruction* instr) { |
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
807 | 807 |
808 void* external_function() { return external_function_; } | 808 void* external_function() { return external_function_; } |
809 ExternalReference::Type type() { return type_; } | 809 ExternalReference::Type type() { return type_; } |
810 | 810 |
811 static Redirection* Get(void* external_function, | 811 static Redirection* Get(void* external_function, |
812 ExternalReference::Type type) { | 812 ExternalReference::Type type) { |
813 Isolate* isolate = Isolate::Current(); | 813 Isolate* isolate = Isolate::Current(); |
814 Redirection* current = isolate->simulator_redirection(); | 814 Redirection* current = isolate->simulator_redirection(); |
815 for (; current != NULL; current = current->next_) { | 815 for (; current != NULL; current = current->next_) { |
816 if (current->external_function_ == external_function) { | 816 if (current->external_function_ == external_function) { |
817 ASSERT_EQ(current->type(), type); | 817 DCHECK_EQ(current->type(), type); |
818 return current; | 818 return current; |
819 } | 819 } |
820 } | 820 } |
821 return new Redirection(external_function, type); | 821 return new Redirection(external_function, type); |
822 } | 822 } |
823 | 823 |
824 static Redirection* FromSwiInstruction(Instruction* swi_instruction) { | 824 static Redirection* FromSwiInstruction(Instruction* swi_instruction) { |
825 char* addr_of_swi = reinterpret_cast<char*>(swi_instruction); | 825 char* addr_of_swi = reinterpret_cast<char*>(swi_instruction); |
826 char* addr_of_redirection = | 826 char* addr_of_redirection = |
827 addr_of_swi - OFFSET_OF(Redirection, swi_instruction_); | 827 addr_of_swi - OFFSET_OF(Redirection, swi_instruction_); |
(...skipping 18 matching lines...) Expand all Loading... |
846 ExternalReference::Type type) { | 846 ExternalReference::Type type) { |
847 Redirection* redirection = Redirection::Get(external_function, type); | 847 Redirection* redirection = Redirection::Get(external_function, type); |
848 return redirection->address_of_swi_instruction(); | 848 return redirection->address_of_swi_instruction(); |
849 } | 849 } |
850 | 850 |
851 | 851 |
852 // Get the active Simulator for the current thread. | 852 // Get the active Simulator for the current thread. |
853 Simulator* Simulator::current(Isolate* isolate) { | 853 Simulator* Simulator::current(Isolate* isolate) { |
854 v8::internal::Isolate::PerIsolateThreadData* isolate_data = | 854 v8::internal::Isolate::PerIsolateThreadData* isolate_data = |
855 isolate->FindOrAllocatePerThreadDataForThisThread(); | 855 isolate->FindOrAllocatePerThreadDataForThisThread(); |
856 ASSERT(isolate_data != NULL); | 856 DCHECK(isolate_data != NULL); |
857 | 857 |
858 Simulator* sim = isolate_data->simulator(); | 858 Simulator* sim = isolate_data->simulator(); |
859 if (sim == NULL) { | 859 if (sim == NULL) { |
860 // TODO(146): delete the simulator object when a thread/isolate goes away. | 860 // TODO(146): delete the simulator object when a thread/isolate goes away. |
861 sim = new Simulator(isolate); | 861 sim = new Simulator(isolate); |
862 isolate_data->set_simulator(sim); | 862 isolate_data->set_simulator(sim); |
863 } | 863 } |
864 return sim; | 864 return sim; |
865 } | 865 } |
866 | 866 |
867 | 867 |
868 // Sets the register in the architecture state. It will also deal with updating | 868 // Sets the register in the architecture state. It will also deal with updating |
869 // Simulator internal state for special registers such as PC. | 869 // Simulator internal state for special registers such as PC. |
870 void Simulator::set_register(int reg, int32_t value) { | 870 void Simulator::set_register(int reg, int32_t value) { |
871 ASSERT((reg >= 0) && (reg < num_registers)); | 871 DCHECK((reg >= 0) && (reg < num_registers)); |
872 if (reg == pc) { | 872 if (reg == pc) { |
873 pc_modified_ = true; | 873 pc_modified_ = true; |
874 } | 874 } |
875 registers_[reg] = value; | 875 registers_[reg] = value; |
876 } | 876 } |
877 | 877 |
878 | 878 |
879 // Get the register from the architecture state. This function does handle | 879 // Get the register from the architecture state. This function does handle |
880 // the special case of accessing the PC register. | 880 // the special case of accessing the PC register. |
881 int32_t Simulator::get_register(int reg) const { | 881 int32_t Simulator::get_register(int reg) const { |
882 ASSERT((reg >= 0) && (reg < num_registers)); | 882 DCHECK((reg >= 0) && (reg < num_registers)); |
883 // Stupid code added to avoid bug in GCC. | 883 // Stupid code added to avoid bug in GCC. |
884 // See: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=43949 | 884 // See: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=43949 |
885 if (reg >= num_registers) return 0; | 885 if (reg >= num_registers) return 0; |
886 // End stupid code. | 886 // End stupid code. |
887 return registers_[reg] + ((reg == pc) ? Instruction::kPCReadOffset : 0); | 887 return registers_[reg] + ((reg == pc) ? Instruction::kPCReadOffset : 0); |
888 } | 888 } |
889 | 889 |
890 | 890 |
891 double Simulator::get_double_from_register_pair(int reg) { | 891 double Simulator::get_double_from_register_pair(int reg) { |
892 ASSERT((reg >= 0) && (reg < num_registers) && ((reg % 2) == 0)); | 892 DCHECK((reg >= 0) && (reg < num_registers) && ((reg % 2) == 0)); |
893 | 893 |
894 double dm_val = 0.0; | 894 double dm_val = 0.0; |
895 // Read the bits from the unsigned integer register_[] array | 895 // Read the bits from the unsigned integer register_[] array |
896 // into the double precision floating point value and return it. | 896 // into the double precision floating point value and return it. |
897 char buffer[2 * sizeof(vfp_registers_[0])]; | 897 char buffer[2 * sizeof(vfp_registers_[0])]; |
898 memcpy(buffer, ®isters_[reg], 2 * sizeof(registers_[0])); | 898 memcpy(buffer, ®isters_[reg], 2 * sizeof(registers_[0])); |
899 memcpy(&dm_val, buffer, 2 * sizeof(registers_[0])); | 899 memcpy(&dm_val, buffer, 2 * sizeof(registers_[0])); |
900 return(dm_val); | 900 return(dm_val); |
901 } | 901 } |
902 | 902 |
903 | 903 |
904 void Simulator::set_register_pair_from_double(int reg, double* value) { | 904 void Simulator::set_register_pair_from_double(int reg, double* value) { |
905 ASSERT((reg >= 0) && (reg < num_registers) && ((reg % 2) == 0)); | 905 DCHECK((reg >= 0) && (reg < num_registers) && ((reg % 2) == 0)); |
906 memcpy(registers_ + reg, value, sizeof(*value)); | 906 memcpy(registers_ + reg, value, sizeof(*value)); |
907 } | 907 } |
908 | 908 |
909 | 909 |
910 void Simulator::set_dw_register(int dreg, const int* dbl) { | 910 void Simulator::set_dw_register(int dreg, const int* dbl) { |
911 ASSERT((dreg >= 0) && (dreg < num_d_registers)); | 911 DCHECK((dreg >= 0) && (dreg < num_d_registers)); |
912 registers_[dreg] = dbl[0]; | 912 registers_[dreg] = dbl[0]; |
913 registers_[dreg + 1] = dbl[1]; | 913 registers_[dreg + 1] = dbl[1]; |
914 } | 914 } |
915 | 915 |
916 | 916 |
917 void Simulator::get_d_register(int dreg, uint64_t* value) { | 917 void Simulator::get_d_register(int dreg, uint64_t* value) { |
918 ASSERT((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); | 918 DCHECK((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); |
919 memcpy(value, vfp_registers_ + dreg * 2, sizeof(*value)); | 919 memcpy(value, vfp_registers_ + dreg * 2, sizeof(*value)); |
920 } | 920 } |
921 | 921 |
922 | 922 |
923 void Simulator::set_d_register(int dreg, const uint64_t* value) { | 923 void Simulator::set_d_register(int dreg, const uint64_t* value) { |
924 ASSERT((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); | 924 DCHECK((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); |
925 memcpy(vfp_registers_ + dreg * 2, value, sizeof(*value)); | 925 memcpy(vfp_registers_ + dreg * 2, value, sizeof(*value)); |
926 } | 926 } |
927 | 927 |
928 | 928 |
929 void Simulator::get_d_register(int dreg, uint32_t* value) { | 929 void Simulator::get_d_register(int dreg, uint32_t* value) { |
930 ASSERT((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); | 930 DCHECK((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); |
931 memcpy(value, vfp_registers_ + dreg * 2, sizeof(*value) * 2); | 931 memcpy(value, vfp_registers_ + dreg * 2, sizeof(*value) * 2); |
932 } | 932 } |
933 | 933 |
934 | 934 |
935 void Simulator::set_d_register(int dreg, const uint32_t* value) { | 935 void Simulator::set_d_register(int dreg, const uint32_t* value) { |
936 ASSERT((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); | 936 DCHECK((dreg >= 0) && (dreg < DwVfpRegister::NumRegisters())); |
937 memcpy(vfp_registers_ + dreg * 2, value, sizeof(*value) * 2); | 937 memcpy(vfp_registers_ + dreg * 2, value, sizeof(*value) * 2); |
938 } | 938 } |
939 | 939 |
940 | 940 |
941 void Simulator::get_q_register(int qreg, uint64_t* value) { | 941 void Simulator::get_q_register(int qreg, uint64_t* value) { |
942 ASSERT((qreg >= 0) && (qreg < num_q_registers)); | 942 DCHECK((qreg >= 0) && (qreg < num_q_registers)); |
943 memcpy(value, vfp_registers_ + qreg * 4, sizeof(*value) * 2); | 943 memcpy(value, vfp_registers_ + qreg * 4, sizeof(*value) * 2); |
944 } | 944 } |
945 | 945 |
946 | 946 |
947 void Simulator::set_q_register(int qreg, const uint64_t* value) { | 947 void Simulator::set_q_register(int qreg, const uint64_t* value) { |
948 ASSERT((qreg >= 0) && (qreg < num_q_registers)); | 948 DCHECK((qreg >= 0) && (qreg < num_q_registers)); |
949 memcpy(vfp_registers_ + qreg * 4, value, sizeof(*value) * 2); | 949 memcpy(vfp_registers_ + qreg * 4, value, sizeof(*value) * 2); |
950 } | 950 } |
951 | 951 |
952 | 952 |
953 void Simulator::get_q_register(int qreg, uint32_t* value) { | 953 void Simulator::get_q_register(int qreg, uint32_t* value) { |
954 ASSERT((qreg >= 0) && (qreg < num_q_registers)); | 954 DCHECK((qreg >= 0) && (qreg < num_q_registers)); |
955 memcpy(value, vfp_registers_ + qreg * 4, sizeof(*value) * 4); | 955 memcpy(value, vfp_registers_ + qreg * 4, sizeof(*value) * 4); |
956 } | 956 } |
957 | 957 |
958 | 958 |
959 void Simulator::set_q_register(int qreg, const uint32_t* value) { | 959 void Simulator::set_q_register(int qreg, const uint32_t* value) { |
960 ASSERT((qreg >= 0) && (qreg < num_q_registers)); | 960 DCHECK((qreg >= 0) && (qreg < num_q_registers)); |
961 memcpy(vfp_registers_ + qreg * 4, value, sizeof(*value) * 4); | 961 memcpy(vfp_registers_ + qreg * 4, value, sizeof(*value) * 4); |
962 } | 962 } |
963 | 963 |
964 | 964 |
965 // Raw access to the PC register. | 965 // Raw access to the PC register. |
966 void Simulator::set_pc(int32_t value) { | 966 void Simulator::set_pc(int32_t value) { |
967 pc_modified_ = true; | 967 pc_modified_ = true; |
968 registers_[pc] = value; | 968 registers_[pc] = value; |
969 } | 969 } |
970 | 970 |
971 | 971 |
972 bool Simulator::has_bad_pc() const { | 972 bool Simulator::has_bad_pc() const { |
973 return ((registers_[pc] == bad_lr) || (registers_[pc] == end_sim_pc)); | 973 return ((registers_[pc] == bad_lr) || (registers_[pc] == end_sim_pc)); |
974 } | 974 } |
975 | 975 |
976 | 976 |
977 // Raw access to the PC register without the special adjustment when reading. | 977 // Raw access to the PC register without the special adjustment when reading. |
978 int32_t Simulator::get_pc() const { | 978 int32_t Simulator::get_pc() const { |
979 return registers_[pc]; | 979 return registers_[pc]; |
980 } | 980 } |
981 | 981 |
982 | 982 |
983 // Getting from and setting into VFP registers. | 983 // Getting from and setting into VFP registers. |
984 void Simulator::set_s_register(int sreg, unsigned int value) { | 984 void Simulator::set_s_register(int sreg, unsigned int value) { |
985 ASSERT((sreg >= 0) && (sreg < num_s_registers)); | 985 DCHECK((sreg >= 0) && (sreg < num_s_registers)); |
986 vfp_registers_[sreg] = value; | 986 vfp_registers_[sreg] = value; |
987 } | 987 } |
988 | 988 |
989 | 989 |
990 unsigned int Simulator::get_s_register(int sreg) const { | 990 unsigned int Simulator::get_s_register(int sreg) const { |
991 ASSERT((sreg >= 0) && (sreg < num_s_registers)); | 991 DCHECK((sreg >= 0) && (sreg < num_s_registers)); |
992 return vfp_registers_[sreg]; | 992 return vfp_registers_[sreg]; |
993 } | 993 } |
994 | 994 |
995 | 995 |
996 template<class InputType, int register_size> | 996 template<class InputType, int register_size> |
997 void Simulator::SetVFPRegister(int reg_index, const InputType& value) { | 997 void Simulator::SetVFPRegister(int reg_index, const InputType& value) { |
998 ASSERT(reg_index >= 0); | 998 DCHECK(reg_index >= 0); |
999 if (register_size == 1) ASSERT(reg_index < num_s_registers); | 999 if (register_size == 1) DCHECK(reg_index < num_s_registers); |
1000 if (register_size == 2) ASSERT(reg_index < DwVfpRegister::NumRegisters()); | 1000 if (register_size == 2) DCHECK(reg_index < DwVfpRegister::NumRegisters()); |
1001 | 1001 |
1002 char buffer[register_size * sizeof(vfp_registers_[0])]; | 1002 char buffer[register_size * sizeof(vfp_registers_[0])]; |
1003 memcpy(buffer, &value, register_size * sizeof(vfp_registers_[0])); | 1003 memcpy(buffer, &value, register_size * sizeof(vfp_registers_[0])); |
1004 memcpy(&vfp_registers_[reg_index * register_size], buffer, | 1004 memcpy(&vfp_registers_[reg_index * register_size], buffer, |
1005 register_size * sizeof(vfp_registers_[0])); | 1005 register_size * sizeof(vfp_registers_[0])); |
1006 } | 1006 } |
1007 | 1007 |
1008 | 1008 |
1009 template<class ReturnType, int register_size> | 1009 template<class ReturnType, int register_size> |
1010 ReturnType Simulator::GetFromVFPRegister(int reg_index) { | 1010 ReturnType Simulator::GetFromVFPRegister(int reg_index) { |
1011 ASSERT(reg_index >= 0); | 1011 DCHECK(reg_index >= 0); |
1012 if (register_size == 1) ASSERT(reg_index < num_s_registers); | 1012 if (register_size == 1) DCHECK(reg_index < num_s_registers); |
1013 if (register_size == 2) ASSERT(reg_index < DwVfpRegister::NumRegisters()); | 1013 if (register_size == 2) DCHECK(reg_index < DwVfpRegister::NumRegisters()); |
1014 | 1014 |
1015 ReturnType value = 0; | 1015 ReturnType value = 0; |
1016 char buffer[register_size * sizeof(vfp_registers_[0])]; | 1016 char buffer[register_size * sizeof(vfp_registers_[0])]; |
1017 memcpy(buffer, &vfp_registers_[register_size * reg_index], | 1017 memcpy(buffer, &vfp_registers_[register_size * reg_index], |
1018 register_size * sizeof(vfp_registers_[0])); | 1018 register_size * sizeof(vfp_registers_[0])); |
1019 memcpy(&value, buffer, register_size * sizeof(vfp_registers_[0])); | 1019 memcpy(&value, buffer, register_size * sizeof(vfp_registers_[0])); |
1020 return value; | 1020 return value; |
1021 } | 1021 } |
1022 | 1022 |
1023 | 1023 |
(...skipping 399 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1423 shift_amount = get_register(rs) &0xff; | 1423 shift_amount = get_register(rs) &0xff; |
1424 switch (shift) { | 1424 switch (shift) { |
1425 case ASR: { | 1425 case ASR: { |
1426 if (shift_amount == 0) { | 1426 if (shift_amount == 0) { |
1427 *carry_out = c_flag_; | 1427 *carry_out = c_flag_; |
1428 } else if (shift_amount < 32) { | 1428 } else if (shift_amount < 32) { |
1429 result >>= (shift_amount - 1); | 1429 result >>= (shift_amount - 1); |
1430 *carry_out = (result & 1) == 1; | 1430 *carry_out = (result & 1) == 1; |
1431 result >>= 1; | 1431 result >>= 1; |
1432 } else { | 1432 } else { |
1433 ASSERT(shift_amount >= 32); | 1433 DCHECK(shift_amount >= 32); |
1434 if (result < 0) { | 1434 if (result < 0) { |
1435 *carry_out = true; | 1435 *carry_out = true; |
1436 result = 0xffffffff; | 1436 result = 0xffffffff; |
1437 } else { | 1437 } else { |
1438 *carry_out = false; | 1438 *carry_out = false; |
1439 result = 0; | 1439 result = 0; |
1440 } | 1440 } |
1441 } | 1441 } |
1442 break; | 1442 break; |
1443 } | 1443 } |
1444 | 1444 |
1445 case LSL: { | 1445 case LSL: { |
1446 if (shift_amount == 0) { | 1446 if (shift_amount == 0) { |
1447 *carry_out = c_flag_; | 1447 *carry_out = c_flag_; |
1448 } else if (shift_amount < 32) { | 1448 } else if (shift_amount < 32) { |
1449 result <<= (shift_amount - 1); | 1449 result <<= (shift_amount - 1); |
1450 *carry_out = (result < 0); | 1450 *carry_out = (result < 0); |
1451 result <<= 1; | 1451 result <<= 1; |
1452 } else if (shift_amount == 32) { | 1452 } else if (shift_amount == 32) { |
1453 *carry_out = (result & 1) == 1; | 1453 *carry_out = (result & 1) == 1; |
1454 result = 0; | 1454 result = 0; |
1455 } else { | 1455 } else { |
1456 ASSERT(shift_amount > 32); | 1456 DCHECK(shift_amount > 32); |
1457 *carry_out = false; | 1457 *carry_out = false; |
1458 result = 0; | 1458 result = 0; |
1459 } | 1459 } |
1460 break; | 1460 break; |
1461 } | 1461 } |
1462 | 1462 |
1463 case LSR: { | 1463 case LSR: { |
1464 if (shift_amount == 0) { | 1464 if (shift_amount == 0) { |
1465 *carry_out = c_flag_; | 1465 *carry_out = c_flag_; |
1466 } else if (shift_amount < 32) { | 1466 } else if (shift_amount < 32) { |
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1568 int rlist = instr->RlistValue(); | 1568 int rlist = instr->RlistValue(); |
1569 int num_regs = count_bits(rlist); | 1569 int num_regs = count_bits(rlist); |
1570 | 1570 |
1571 intptr_t start_address = 0; | 1571 intptr_t start_address = 0; |
1572 intptr_t end_address = 0; | 1572 intptr_t end_address = 0; |
1573 int32_t rn_val = | 1573 int32_t rn_val = |
1574 ProcessPU(instr, num_regs, kPointerSize, &start_address, &end_address); | 1574 ProcessPU(instr, num_regs, kPointerSize, &start_address, &end_address); |
1575 | 1575 |
1576 intptr_t* address = reinterpret_cast<intptr_t*>(start_address); | 1576 intptr_t* address = reinterpret_cast<intptr_t*>(start_address); |
1577 // Catch null pointers a little earlier. | 1577 // Catch null pointers a little earlier. |
1578 ASSERT(start_address > 8191 || start_address < 0); | 1578 DCHECK(start_address > 8191 || start_address < 0); |
1579 int reg = 0; | 1579 int reg = 0; |
1580 while (rlist != 0) { | 1580 while (rlist != 0) { |
1581 if ((rlist & 1) != 0) { | 1581 if ((rlist & 1) != 0) { |
1582 if (load) { | 1582 if (load) { |
1583 set_register(reg, *address); | 1583 set_register(reg, *address); |
1584 } else { | 1584 } else { |
1585 *address = get_register(reg); | 1585 *address = get_register(reg); |
1586 } | 1586 } |
1587 address += 1; | 1587 address += 1; |
1588 } | 1588 } |
1589 reg++; | 1589 reg++; |
1590 rlist >>= 1; | 1590 rlist >>= 1; |
1591 } | 1591 } |
1592 ASSERT(end_address == ((intptr_t)address) - 4); | 1592 DCHECK(end_address == ((intptr_t)address) - 4); |
1593 if (instr->HasW()) { | 1593 if (instr->HasW()) { |
1594 set_register(instr->RnValue(), rn_val); | 1594 set_register(instr->RnValue(), rn_val); |
1595 } | 1595 } |
1596 } | 1596 } |
1597 | 1597 |
1598 | 1598 |
1599 // Addressing Mode 6 - Load and Store Multiple Coprocessor registers. | 1599 // Addressing Mode 6 - Load and Store Multiple Coprocessor registers. |
1600 void Simulator::HandleVList(Instruction* instr) { | 1600 void Simulator::HandleVList(Instruction* instr) { |
1601 VFPRegPrecision precision = | 1601 VFPRegPrecision precision = |
1602 (instr->SzValue() == 0) ? kSinglePrecision : kDoublePrecision; | 1602 (instr->SzValue() == 0) ? kSinglePrecision : kDoublePrecision; |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1641 } else { | 1641 } else { |
1642 int32_t data[2]; | 1642 int32_t data[2]; |
1643 double d = get_double_from_d_register(reg); | 1643 double d = get_double_from_d_register(reg); |
1644 memcpy(data, &d, 8); | 1644 memcpy(data, &d, 8); |
1645 WriteW(reinterpret_cast<int32_t>(address), data[0], instr); | 1645 WriteW(reinterpret_cast<int32_t>(address), data[0], instr); |
1646 WriteW(reinterpret_cast<int32_t>(address + 1), data[1], instr); | 1646 WriteW(reinterpret_cast<int32_t>(address + 1), data[1], instr); |
1647 } | 1647 } |
1648 address += 2; | 1648 address += 2; |
1649 } | 1649 } |
1650 } | 1650 } |
1651 ASSERT(reinterpret_cast<intptr_t>(address) - operand_size == end_address); | 1651 DCHECK(reinterpret_cast<intptr_t>(address) - operand_size == end_address); |
1652 if (instr->HasW()) { | 1652 if (instr->HasW()) { |
1653 set_register(instr->RnValue(), rn_val); | 1653 set_register(instr->RnValue(), rn_val); |
1654 } | 1654 } |
1655 } | 1655 } |
1656 | 1656 |
1657 | 1657 |
1658 // Calls into the V8 runtime are based on this very simple interface. | 1658 // Calls into the V8 runtime are based on this very simple interface. |
1659 // Note: To be able to return two values from some calls the code in runtime.cc | 1659 // Note: To be able to return two values from some calls the code in runtime.cc |
1660 // uses the ObjectPair which is essentially two 32-bit values stuffed into a | 1660 // uses the ObjectPair which is essentially two 32-bit values stuffed into a |
1661 // 64-bit value. With the code below we assume that all runtime calls return | 1661 // 64-bit value. With the code below we assume that all runtime calls return |
(...skipping 184 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1846 } | 1846 } |
1847 PrintF("\n"); | 1847 PrintF("\n"); |
1848 } | 1848 } |
1849 CHECK(stack_aligned); | 1849 CHECK(stack_aligned); |
1850 SimulatorRuntimeProfilingGetterCall target = | 1850 SimulatorRuntimeProfilingGetterCall target = |
1851 reinterpret_cast<SimulatorRuntimeProfilingGetterCall>( | 1851 reinterpret_cast<SimulatorRuntimeProfilingGetterCall>( |
1852 external); | 1852 external); |
1853 target(arg0, arg1, Redirection::ReverseRedirection(arg2)); | 1853 target(arg0, arg1, Redirection::ReverseRedirection(arg2)); |
1854 } else { | 1854 } else { |
1855 // builtin call. | 1855 // builtin call. |
1856 ASSERT(redirection->type() == ExternalReference::BUILTIN_CALL); | 1856 DCHECK(redirection->type() == ExternalReference::BUILTIN_CALL); |
1857 SimulatorRuntimeCall target = | 1857 SimulatorRuntimeCall target = |
1858 reinterpret_cast<SimulatorRuntimeCall>(external); | 1858 reinterpret_cast<SimulatorRuntimeCall>(external); |
1859 if (::v8::internal::FLAG_trace_sim || !stack_aligned) { | 1859 if (::v8::internal::FLAG_trace_sim || !stack_aligned) { |
1860 PrintF( | 1860 PrintF( |
1861 "Call to host function at %p " | 1861 "Call to host function at %p " |
1862 "args %08x, %08x, %08x, %08x, %08x, %08x", | 1862 "args %08x, %08x, %08x, %08x, %08x, %08x", |
1863 FUNCTION_ADDR(target), | 1863 FUNCTION_ADDR(target), |
1864 arg0, | 1864 arg0, |
1865 arg1, | 1865 arg1, |
1866 arg2, | 1866 arg2, |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1922 } | 1922 } |
1923 | 1923 |
1924 | 1924 |
1925 // Stop helper functions. | 1925 // Stop helper functions. |
1926 bool Simulator::isStopInstruction(Instruction* instr) { | 1926 bool Simulator::isStopInstruction(Instruction* instr) { |
1927 return (instr->Bits(27, 24) == 0xF) && (instr->SvcValue() >= kStopCode); | 1927 return (instr->Bits(27, 24) == 0xF) && (instr->SvcValue() >= kStopCode); |
1928 } | 1928 } |
1929 | 1929 |
1930 | 1930 |
1931 bool Simulator::isWatchedStop(uint32_t code) { | 1931 bool Simulator::isWatchedStop(uint32_t code) { |
1932 ASSERT(code <= kMaxStopCode); | 1932 DCHECK(code <= kMaxStopCode); |
1933 return code < kNumOfWatchedStops; | 1933 return code < kNumOfWatchedStops; |
1934 } | 1934 } |
1935 | 1935 |
1936 | 1936 |
1937 bool Simulator::isEnabledStop(uint32_t code) { | 1937 bool Simulator::isEnabledStop(uint32_t code) { |
1938 ASSERT(code <= kMaxStopCode); | 1938 DCHECK(code <= kMaxStopCode); |
1939 // Unwatched stops are always enabled. | 1939 // Unwatched stops are always enabled. |
1940 return !isWatchedStop(code) || | 1940 return !isWatchedStop(code) || |
1941 !(watched_stops_[code].count & kStopDisabledBit); | 1941 !(watched_stops_[code].count & kStopDisabledBit); |
1942 } | 1942 } |
1943 | 1943 |
1944 | 1944 |
1945 void Simulator::EnableStop(uint32_t code) { | 1945 void Simulator::EnableStop(uint32_t code) { |
1946 ASSERT(isWatchedStop(code)); | 1946 DCHECK(isWatchedStop(code)); |
1947 if (!isEnabledStop(code)) { | 1947 if (!isEnabledStop(code)) { |
1948 watched_stops_[code].count &= ~kStopDisabledBit; | 1948 watched_stops_[code].count &= ~kStopDisabledBit; |
1949 } | 1949 } |
1950 } | 1950 } |
1951 | 1951 |
1952 | 1952 |
1953 void Simulator::DisableStop(uint32_t code) { | 1953 void Simulator::DisableStop(uint32_t code) { |
1954 ASSERT(isWatchedStop(code)); | 1954 DCHECK(isWatchedStop(code)); |
1955 if (isEnabledStop(code)) { | 1955 if (isEnabledStop(code)) { |
1956 watched_stops_[code].count |= kStopDisabledBit; | 1956 watched_stops_[code].count |= kStopDisabledBit; |
1957 } | 1957 } |
1958 } | 1958 } |
1959 | 1959 |
1960 | 1960 |
1961 void Simulator::IncreaseStopCounter(uint32_t code) { | 1961 void Simulator::IncreaseStopCounter(uint32_t code) { |
1962 ASSERT(code <= kMaxStopCode); | 1962 DCHECK(code <= kMaxStopCode); |
1963 ASSERT(isWatchedStop(code)); | 1963 DCHECK(isWatchedStop(code)); |
1964 if ((watched_stops_[code].count & ~(1 << 31)) == 0x7fffffff) { | 1964 if ((watched_stops_[code].count & ~(1 << 31)) == 0x7fffffff) { |
1965 PrintF("Stop counter for code %i has overflowed.\n" | 1965 PrintF("Stop counter for code %i has overflowed.\n" |
1966 "Enabling this code and reseting the counter to 0.\n", code); | 1966 "Enabling this code and reseting the counter to 0.\n", code); |
1967 watched_stops_[code].count = 0; | 1967 watched_stops_[code].count = 0; |
1968 EnableStop(code); | 1968 EnableStop(code); |
1969 } else { | 1969 } else { |
1970 watched_stops_[code].count++; | 1970 watched_stops_[code].count++; |
1971 } | 1971 } |
1972 } | 1972 } |
1973 | 1973 |
1974 | 1974 |
1975 // Print a stop status. | 1975 // Print a stop status. |
1976 void Simulator::PrintStopInfo(uint32_t code) { | 1976 void Simulator::PrintStopInfo(uint32_t code) { |
1977 ASSERT(code <= kMaxStopCode); | 1977 DCHECK(code <= kMaxStopCode); |
1978 if (!isWatchedStop(code)) { | 1978 if (!isWatchedStop(code)) { |
1979 PrintF("Stop not watched."); | 1979 PrintF("Stop not watched."); |
1980 } else { | 1980 } else { |
1981 const char* state = isEnabledStop(code) ? "Enabled" : "Disabled"; | 1981 const char* state = isEnabledStop(code) ? "Enabled" : "Disabled"; |
1982 int32_t count = watched_stops_[code].count & ~kStopDisabledBit; | 1982 int32_t count = watched_stops_[code].count & ~kStopDisabledBit; |
1983 // Don't print the state of unused breakpoints. | 1983 // Don't print the state of unused breakpoints. |
1984 if (count != 0) { | 1984 if (count != 0) { |
1985 if (watched_stops_[code].desc) { | 1985 if (watched_stops_[code].desc) { |
1986 PrintF("stop %i - 0x%x: \t%s, \tcounter = %i, \t%s\n", | 1986 PrintF("stop %i - 0x%x: \t%s, \tcounter = %i, \t%s\n", |
1987 code, code, state, count, watched_stops_[code].desc); | 1987 code, code, state, count, watched_stops_[code].desc); |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2085 int rd = instr->RdValue(); | 2085 int rd = instr->RdValue(); |
2086 int rn = instr->RnValue(); | 2086 int rn = instr->RnValue(); |
2087 int32_t rn_val = get_register(rn); | 2087 int32_t rn_val = get_register(rn); |
2088 int32_t addr = 0; | 2088 int32_t addr = 0; |
2089 if (instr->Bit(22) == 0) { | 2089 if (instr->Bit(22) == 0) { |
2090 int rm = instr->RmValue(); | 2090 int rm = instr->RmValue(); |
2091 int32_t rm_val = get_register(rm); | 2091 int32_t rm_val = get_register(rm); |
2092 switch (instr->PUField()) { | 2092 switch (instr->PUField()) { |
2093 case da_x: { | 2093 case da_x: { |
2094 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], -'rm"); | 2094 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], -'rm"); |
2095 ASSERT(!instr->HasW()); | 2095 DCHECK(!instr->HasW()); |
2096 addr = rn_val; | 2096 addr = rn_val; |
2097 rn_val -= rm_val; | 2097 rn_val -= rm_val; |
2098 set_register(rn, rn_val); | 2098 set_register(rn, rn_val); |
2099 break; | 2099 break; |
2100 } | 2100 } |
2101 case ia_x: { | 2101 case ia_x: { |
2102 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], +'rm"); | 2102 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], +'rm"); |
2103 ASSERT(!instr->HasW()); | 2103 DCHECK(!instr->HasW()); |
2104 addr = rn_val; | 2104 addr = rn_val; |
2105 rn_val += rm_val; | 2105 rn_val += rm_val; |
2106 set_register(rn, rn_val); | 2106 set_register(rn, rn_val); |
2107 break; | 2107 break; |
2108 } | 2108 } |
2109 case db_x: { | 2109 case db_x: { |
2110 // Format(instr, "'memop'cond'sign'h 'rd, ['rn, -'rm]'w"); | 2110 // Format(instr, "'memop'cond'sign'h 'rd, ['rn, -'rm]'w"); |
2111 rn_val -= rm_val; | 2111 rn_val -= rm_val; |
2112 addr = rn_val; | 2112 addr = rn_val; |
2113 if (instr->HasW()) { | 2113 if (instr->HasW()) { |
(...skipping 14 matching lines...) Expand all Loading... |
2128 // The PU field is a 2-bit field. | 2128 // The PU field is a 2-bit field. |
2129 UNREACHABLE(); | 2129 UNREACHABLE(); |
2130 break; | 2130 break; |
2131 } | 2131 } |
2132 } | 2132 } |
2133 } else { | 2133 } else { |
2134 int32_t imm_val = (instr->ImmedHValue() << 4) | instr->ImmedLValue(); | 2134 int32_t imm_val = (instr->ImmedHValue() << 4) | instr->ImmedLValue(); |
2135 switch (instr->PUField()) { | 2135 switch (instr->PUField()) { |
2136 case da_x: { | 2136 case da_x: { |
2137 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], #-'off8"); | 2137 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], #-'off8"); |
2138 ASSERT(!instr->HasW()); | 2138 DCHECK(!instr->HasW()); |
2139 addr = rn_val; | 2139 addr = rn_val; |
2140 rn_val -= imm_val; | 2140 rn_val -= imm_val; |
2141 set_register(rn, rn_val); | 2141 set_register(rn, rn_val); |
2142 break; | 2142 break; |
2143 } | 2143 } |
2144 case ia_x: { | 2144 case ia_x: { |
2145 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], #+'off8"); | 2145 // Format(instr, "'memop'cond'sign'h 'rd, ['rn], #+'off8"); |
2146 ASSERT(!instr->HasW()); | 2146 DCHECK(!instr->HasW()); |
2147 addr = rn_val; | 2147 addr = rn_val; |
2148 rn_val += imm_val; | 2148 rn_val += imm_val; |
2149 set_register(rn, rn_val); | 2149 set_register(rn, rn_val); |
2150 break; | 2150 break; |
2151 } | 2151 } |
2152 case db_x: { | 2152 case db_x: { |
2153 // Format(instr, "'memop'cond'sign'h 'rd, ['rn, #-'off8]'w"); | 2153 // Format(instr, "'memop'cond'sign'h 'rd, ['rn, #-'off8]'w"); |
2154 rn_val -= imm_val; | 2154 rn_val -= imm_val; |
2155 addr = rn_val; | 2155 addr = rn_val; |
2156 if (instr->HasW()) { | 2156 if (instr->HasW()) { |
(...skipping 11 matching lines...) Expand all Loading... |
2168 break; | 2168 break; |
2169 } | 2169 } |
2170 default: { | 2170 default: { |
2171 // The PU field is a 2-bit field. | 2171 // The PU field is a 2-bit field. |
2172 UNREACHABLE(); | 2172 UNREACHABLE(); |
2173 break; | 2173 break; |
2174 } | 2174 } |
2175 } | 2175 } |
2176 } | 2176 } |
2177 if (((instr->Bits(7, 4) & 0xd) == 0xd) && (instr->Bit(20) == 0)) { | 2177 if (((instr->Bits(7, 4) & 0xd) == 0xd) && (instr->Bit(20) == 0)) { |
2178 ASSERT((rd % 2) == 0); | 2178 DCHECK((rd % 2) == 0); |
2179 if (instr->HasH()) { | 2179 if (instr->HasH()) { |
2180 // The strd instruction. | 2180 // The strd instruction. |
2181 int32_t value1 = get_register(rd); | 2181 int32_t value1 = get_register(rd); |
2182 int32_t value2 = get_register(rd+1); | 2182 int32_t value2 = get_register(rd+1); |
2183 WriteDW(addr, value1, value2); | 2183 WriteDW(addr, value1, value2); |
2184 } else { | 2184 } else { |
2185 // The ldrd instruction. | 2185 // The ldrd instruction. |
2186 int* rn_data = ReadDW(addr); | 2186 int* rn_data = ReadDW(addr); |
2187 set_dw_register(rd, rn_data); | 2187 set_dw_register(rd, rn_data); |
2188 } | 2188 } |
(...skipping 10 matching lines...) Expand all Loading... |
2199 if (instr->HasL()) { | 2199 if (instr->HasL()) { |
2200 uint16_t val = ReadHU(addr, instr); | 2200 uint16_t val = ReadHU(addr, instr); |
2201 set_register(rd, val); | 2201 set_register(rd, val); |
2202 } else { | 2202 } else { |
2203 uint16_t val = get_register(rd); | 2203 uint16_t val = get_register(rd); |
2204 WriteH(addr, val, instr); | 2204 WriteH(addr, val, instr); |
2205 } | 2205 } |
2206 } | 2206 } |
2207 } else { | 2207 } else { |
2208 // signed byte loads | 2208 // signed byte loads |
2209 ASSERT(instr->HasSign()); | 2209 DCHECK(instr->HasSign()); |
2210 ASSERT(instr->HasL()); | 2210 DCHECK(instr->HasL()); |
2211 int8_t val = ReadB(addr); | 2211 int8_t val = ReadB(addr); |
2212 set_register(rd, val); | 2212 set_register(rd, val); |
2213 } | 2213 } |
2214 return; | 2214 return; |
2215 } | 2215 } |
2216 } else if ((type == 0) && instr->IsMiscType0()) { | 2216 } else if ((type == 0) && instr->IsMiscType0()) { |
2217 if (instr->Bits(22, 21) == 1) { | 2217 if (instr->Bits(22, 21) == 1) { |
2218 int rm = instr->RmValue(); | 2218 int rm = instr->RmValue(); |
2219 switch (instr->BitField(7, 4)) { | 2219 switch (instr->BitField(7, 4)) { |
2220 case BX: | 2220 case BX: |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2264 // NOP. | 2264 // NOP. |
2265 } else { | 2265 } else { |
2266 int rd = instr->RdValue(); | 2266 int rd = instr->RdValue(); |
2267 int rn = instr->RnValue(); | 2267 int rn = instr->RnValue(); |
2268 int32_t rn_val = get_register(rn); | 2268 int32_t rn_val = get_register(rn); |
2269 int32_t shifter_operand = 0; | 2269 int32_t shifter_operand = 0; |
2270 bool shifter_carry_out = 0; | 2270 bool shifter_carry_out = 0; |
2271 if (type == 0) { | 2271 if (type == 0) { |
2272 shifter_operand = GetShiftRm(instr, &shifter_carry_out); | 2272 shifter_operand = GetShiftRm(instr, &shifter_carry_out); |
2273 } else { | 2273 } else { |
2274 ASSERT(instr->TypeValue() == 1); | 2274 DCHECK(instr->TypeValue() == 1); |
2275 shifter_operand = GetImm(instr, &shifter_carry_out); | 2275 shifter_operand = GetImm(instr, &shifter_carry_out); |
2276 } | 2276 } |
2277 int32_t alu_out; | 2277 int32_t alu_out; |
2278 | 2278 |
2279 switch (instr->OpcodeField()) { | 2279 switch (instr->OpcodeField()) { |
2280 case AND: { | 2280 case AND: { |
2281 // Format(instr, "and'cond's 'rd, 'rn, 'shift_rm"); | 2281 // Format(instr, "and'cond's 'rd, 'rn, 'shift_rm"); |
2282 // Format(instr, "and'cond's 'rd, 'rn, 'imm"); | 2282 // Format(instr, "and'cond's 'rd, 'rn, 'imm"); |
2283 alu_out = rn_val & shifter_operand; | 2283 alu_out = rn_val & shifter_operand; |
2284 set_register(rd, alu_out); | 2284 set_register(rd, alu_out); |
(...skipping 202 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2487 | 2487 |
2488 void Simulator::DecodeType2(Instruction* instr) { | 2488 void Simulator::DecodeType2(Instruction* instr) { |
2489 int rd = instr->RdValue(); | 2489 int rd = instr->RdValue(); |
2490 int rn = instr->RnValue(); | 2490 int rn = instr->RnValue(); |
2491 int32_t rn_val = get_register(rn); | 2491 int32_t rn_val = get_register(rn); |
2492 int32_t im_val = instr->Offset12Value(); | 2492 int32_t im_val = instr->Offset12Value(); |
2493 int32_t addr = 0; | 2493 int32_t addr = 0; |
2494 switch (instr->PUField()) { | 2494 switch (instr->PUField()) { |
2495 case da_x: { | 2495 case da_x: { |
2496 // Format(instr, "'memop'cond'b 'rd, ['rn], #-'off12"); | 2496 // Format(instr, "'memop'cond'b 'rd, ['rn], #-'off12"); |
2497 ASSERT(!instr->HasW()); | 2497 DCHECK(!instr->HasW()); |
2498 addr = rn_val; | 2498 addr = rn_val; |
2499 rn_val -= im_val; | 2499 rn_val -= im_val; |
2500 set_register(rn, rn_val); | 2500 set_register(rn, rn_val); |
2501 break; | 2501 break; |
2502 } | 2502 } |
2503 case ia_x: { | 2503 case ia_x: { |
2504 // Format(instr, "'memop'cond'b 'rd, ['rn], #+'off12"); | 2504 // Format(instr, "'memop'cond'b 'rd, ['rn], #+'off12"); |
2505 ASSERT(!instr->HasW()); | 2505 DCHECK(!instr->HasW()); |
2506 addr = rn_val; | 2506 addr = rn_val; |
2507 rn_val += im_val; | 2507 rn_val += im_val; |
2508 set_register(rn, rn_val); | 2508 set_register(rn, rn_val); |
2509 break; | 2509 break; |
2510 } | 2510 } |
2511 case db_x: { | 2511 case db_x: { |
2512 // Format(instr, "'memop'cond'b 'rd, ['rn, #-'off12]'w"); | 2512 // Format(instr, "'memop'cond'b 'rd, ['rn, #-'off12]'w"); |
2513 rn_val -= im_val; | 2513 rn_val -= im_val; |
2514 addr = rn_val; | 2514 addr = rn_val; |
2515 if (instr->HasW()) { | 2515 if (instr->HasW()) { |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2551 | 2551 |
2552 void Simulator::DecodeType3(Instruction* instr) { | 2552 void Simulator::DecodeType3(Instruction* instr) { |
2553 int rd = instr->RdValue(); | 2553 int rd = instr->RdValue(); |
2554 int rn = instr->RnValue(); | 2554 int rn = instr->RnValue(); |
2555 int32_t rn_val = get_register(rn); | 2555 int32_t rn_val = get_register(rn); |
2556 bool shifter_carry_out = 0; | 2556 bool shifter_carry_out = 0; |
2557 int32_t shifter_operand = GetShiftRm(instr, &shifter_carry_out); | 2557 int32_t shifter_operand = GetShiftRm(instr, &shifter_carry_out); |
2558 int32_t addr = 0; | 2558 int32_t addr = 0; |
2559 switch (instr->PUField()) { | 2559 switch (instr->PUField()) { |
2560 case da_x: { | 2560 case da_x: { |
2561 ASSERT(!instr->HasW()); | 2561 DCHECK(!instr->HasW()); |
2562 Format(instr, "'memop'cond'b 'rd, ['rn], -'shift_rm"); | 2562 Format(instr, "'memop'cond'b 'rd, ['rn], -'shift_rm"); |
2563 UNIMPLEMENTED(); | 2563 UNIMPLEMENTED(); |
2564 break; | 2564 break; |
2565 } | 2565 } |
2566 case ia_x: { | 2566 case ia_x: { |
2567 if (instr->Bit(4) == 0) { | 2567 if (instr->Bit(4) == 0) { |
2568 // Memop. | 2568 // Memop. |
2569 } else { | 2569 } else { |
2570 if (instr->Bit(5) == 0) { | 2570 if (instr->Bit(5) == 0) { |
2571 switch (instr->Bits(22, 21)) { | 2571 switch (instr->Bits(22, 21)) { |
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2713 if (FLAG_enable_sudiv) { | 2713 if (FLAG_enable_sudiv) { |
2714 if (instr->Bits(5, 4) == 0x1) { | 2714 if (instr->Bits(5, 4) == 0x1) { |
2715 if ((instr->Bit(22) == 0x0) && (instr->Bit(20) == 0x1)) { | 2715 if ((instr->Bit(22) == 0x0) && (instr->Bit(20) == 0x1)) { |
2716 // (s/u)div (in V8 notation matching ARM ISA format) rn = rm/rs | 2716 // (s/u)div (in V8 notation matching ARM ISA format) rn = rm/rs |
2717 // Format(instr, "'(s/u)div'cond'b 'rn, 'rm, 'rs); | 2717 // Format(instr, "'(s/u)div'cond'b 'rn, 'rm, 'rs); |
2718 int rm = instr->RmValue(); | 2718 int rm = instr->RmValue(); |
2719 int32_t rm_val = get_register(rm); | 2719 int32_t rm_val = get_register(rm); |
2720 int rs = instr->RsValue(); | 2720 int rs = instr->RsValue(); |
2721 int32_t rs_val = get_register(rs); | 2721 int32_t rs_val = get_register(rs); |
2722 int32_t ret_val = 0; | 2722 int32_t ret_val = 0; |
2723 ASSERT(rs_val != 0); | 2723 DCHECK(rs_val != 0); |
2724 // udiv | 2724 // udiv |
2725 if (instr->Bit(21) == 0x1) { | 2725 if (instr->Bit(21) == 0x1) { |
2726 ret_val = static_cast<int32_t>(static_cast<uint32_t>(rm_val) / | 2726 ret_val = static_cast<int32_t>(static_cast<uint32_t>(rm_val) / |
2727 static_cast<uint32_t>(rs_val)); | 2727 static_cast<uint32_t>(rs_val)); |
2728 } else if ((rm_val == kMinInt) && (rs_val == -1)) { | 2728 } else if ((rm_val == kMinInt) && (rs_val == -1)) { |
2729 ret_val = kMinInt; | 2729 ret_val = kMinInt; |
2730 } else { | 2730 } else { |
2731 ret_val = rm_val / rs_val; | 2731 ret_val = rm_val / rs_val; |
2732 } | 2732 } |
2733 set_register(rn, ret_val); | 2733 set_register(rn, ret_val); |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2814 if (instr->HasL()) { | 2814 if (instr->HasL()) { |
2815 set_register(rd, ReadW(addr, instr)); | 2815 set_register(rd, ReadW(addr, instr)); |
2816 } else { | 2816 } else { |
2817 WriteW(addr, get_register(rd), instr); | 2817 WriteW(addr, get_register(rd), instr); |
2818 } | 2818 } |
2819 } | 2819 } |
2820 } | 2820 } |
2821 | 2821 |
2822 | 2822 |
2823 void Simulator::DecodeType4(Instruction* instr) { | 2823 void Simulator::DecodeType4(Instruction* instr) { |
2824 ASSERT(instr->Bit(22) == 0); // only allowed to be set in privileged mode | 2824 DCHECK(instr->Bit(22) == 0); // only allowed to be set in privileged mode |
2825 if (instr->HasL()) { | 2825 if (instr->HasL()) { |
2826 // Format(instr, "ldm'cond'pu 'rn'w, 'rlist"); | 2826 // Format(instr, "ldm'cond'pu 'rn'w, 'rlist"); |
2827 HandleRList(instr, true); | 2827 HandleRList(instr, true); |
2828 } else { | 2828 } else { |
2829 // Format(instr, "stm'cond'pu 'rn'w, 'rlist"); | 2829 // Format(instr, "stm'cond'pu 'rn'w, 'rlist"); |
2830 HandleRList(instr, false); | 2830 HandleRList(instr, false); |
2831 } | 2831 } |
2832 } | 2832 } |
2833 | 2833 |
2834 | 2834 |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2868 // Dd = vabs(Dm) | 2868 // Dd = vabs(Dm) |
2869 // Dd = vneg(Dm) | 2869 // Dd = vneg(Dm) |
2870 // Dd = vadd(Dn, Dm) | 2870 // Dd = vadd(Dn, Dm) |
2871 // Dd = vsub(Dn, Dm) | 2871 // Dd = vsub(Dn, Dm) |
2872 // Dd = vmul(Dn, Dm) | 2872 // Dd = vmul(Dn, Dm) |
2873 // Dd = vdiv(Dn, Dm) | 2873 // Dd = vdiv(Dn, Dm) |
2874 // vcmp(Dd, Dm) | 2874 // vcmp(Dd, Dm) |
2875 // vmrs | 2875 // vmrs |
2876 // Dd = vsqrt(Dm) | 2876 // Dd = vsqrt(Dm) |
2877 void Simulator::DecodeTypeVFP(Instruction* instr) { | 2877 void Simulator::DecodeTypeVFP(Instruction* instr) { |
2878 ASSERT((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0) ); | 2878 DCHECK((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0) ); |
2879 ASSERT(instr->Bits(11, 9) == 0x5); | 2879 DCHECK(instr->Bits(11, 9) == 0x5); |
2880 | 2880 |
2881 // Obtain double precision register codes. | 2881 // Obtain double precision register codes. |
2882 int vm = instr->VFPMRegValue(kDoublePrecision); | 2882 int vm = instr->VFPMRegValue(kDoublePrecision); |
2883 int vd = instr->VFPDRegValue(kDoublePrecision); | 2883 int vd = instr->VFPDRegValue(kDoublePrecision); |
2884 int vn = instr->VFPNRegValue(kDoublePrecision); | 2884 int vn = instr->VFPNRegValue(kDoublePrecision); |
2885 | 2885 |
2886 if (instr->Bit(4) == 0) { | 2886 if (instr->Bit(4) == 0) { |
2887 if (instr->Opc1Value() == 0x7) { | 2887 if (instr->Opc1Value() == 0x7) { |
2888 // Other data processing instructions | 2888 // Other data processing instructions |
2889 if ((instr->Opc2Value() == 0x0) && (instr->Opc3Value() == 0x1)) { | 2889 if ((instr->Opc2Value() == 0x0) && (instr->Opc3Value() == 0x1)) { |
(...skipping 194 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3084 } | 3084 } |
3085 } else { | 3085 } else { |
3086 UNIMPLEMENTED(); // Not used by V8. | 3086 UNIMPLEMENTED(); // Not used by V8. |
3087 } | 3087 } |
3088 } | 3088 } |
3089 } | 3089 } |
3090 | 3090 |
3091 | 3091 |
3092 void Simulator::DecodeVMOVBetweenCoreAndSinglePrecisionRegisters( | 3092 void Simulator::DecodeVMOVBetweenCoreAndSinglePrecisionRegisters( |
3093 Instruction* instr) { | 3093 Instruction* instr) { |
3094 ASSERT((instr->Bit(4) == 1) && (instr->VCValue() == 0x0) && | 3094 DCHECK((instr->Bit(4) == 1) && (instr->VCValue() == 0x0) && |
3095 (instr->VAValue() == 0x0)); | 3095 (instr->VAValue() == 0x0)); |
3096 | 3096 |
3097 int t = instr->RtValue(); | 3097 int t = instr->RtValue(); |
3098 int n = instr->VFPNRegValue(kSinglePrecision); | 3098 int n = instr->VFPNRegValue(kSinglePrecision); |
3099 bool to_arm_register = (instr->VLValue() == 0x1); | 3099 bool to_arm_register = (instr->VLValue() == 0x1); |
3100 | 3100 |
3101 if (to_arm_register) { | 3101 if (to_arm_register) { |
3102 int32_t int_value = get_sinteger_from_s_register(n); | 3102 int32_t int_value = get_sinteger_from_s_register(n); |
3103 set_register(t, int_value); | 3103 set_register(t, int_value); |
3104 } else { | 3104 } else { |
3105 int32_t rs_val = get_register(t); | 3105 int32_t rs_val = get_register(t); |
3106 set_s_register_from_sinteger(n, rs_val); | 3106 set_s_register_from_sinteger(n, rs_val); |
3107 } | 3107 } |
3108 } | 3108 } |
3109 | 3109 |
3110 | 3110 |
3111 void Simulator::DecodeVCMP(Instruction* instr) { | 3111 void Simulator::DecodeVCMP(Instruction* instr) { |
3112 ASSERT((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7)); | 3112 DCHECK((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7)); |
3113 ASSERT(((instr->Opc2Value() == 0x4) || (instr->Opc2Value() == 0x5)) && | 3113 DCHECK(((instr->Opc2Value() == 0x4) || (instr->Opc2Value() == 0x5)) && |
3114 (instr->Opc3Value() & 0x1)); | 3114 (instr->Opc3Value() & 0x1)); |
3115 // Comparison. | 3115 // Comparison. |
3116 | 3116 |
3117 VFPRegPrecision precision = kSinglePrecision; | 3117 VFPRegPrecision precision = kSinglePrecision; |
3118 if (instr->SzValue() == 1) { | 3118 if (instr->SzValue() == 1) { |
3119 precision = kDoublePrecision; | 3119 precision = kDoublePrecision; |
3120 } | 3120 } |
3121 | 3121 |
3122 int d = instr->VFPDRegValue(precision); | 3122 int d = instr->VFPDRegValue(precision); |
3123 int m = 0; | 3123 int m = 0; |
(...skipping 16 matching lines...) Expand all Loading... |
3140 } | 3140 } |
3141 | 3141 |
3142 Compute_FPSCR_Flags(dd_value, dm_value); | 3142 Compute_FPSCR_Flags(dd_value, dm_value); |
3143 } else { | 3143 } else { |
3144 UNIMPLEMENTED(); // Not used by V8. | 3144 UNIMPLEMENTED(); // Not used by V8. |
3145 } | 3145 } |
3146 } | 3146 } |
3147 | 3147 |
3148 | 3148 |
3149 void Simulator::DecodeVCVTBetweenDoubleAndSingle(Instruction* instr) { | 3149 void Simulator::DecodeVCVTBetweenDoubleAndSingle(Instruction* instr) { |
3150 ASSERT((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7)); | 3150 DCHECK((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7)); |
3151 ASSERT((instr->Opc2Value() == 0x7) && (instr->Opc3Value() == 0x3)); | 3151 DCHECK((instr->Opc2Value() == 0x7) && (instr->Opc3Value() == 0x3)); |
3152 | 3152 |
3153 VFPRegPrecision dst_precision = kDoublePrecision; | 3153 VFPRegPrecision dst_precision = kDoublePrecision; |
3154 VFPRegPrecision src_precision = kSinglePrecision; | 3154 VFPRegPrecision src_precision = kSinglePrecision; |
3155 if (instr->SzValue() == 1) { | 3155 if (instr->SzValue() == 1) { |
3156 dst_precision = kSinglePrecision; | 3156 dst_precision = kSinglePrecision; |
3157 src_precision = kDoublePrecision; | 3157 src_precision = kDoublePrecision; |
3158 } | 3158 } |
3159 | 3159 |
3160 int dst = instr->VFPDRegValue(dst_precision); | 3160 int dst = instr->VFPDRegValue(dst_precision); |
3161 int src = instr->VFPMRegValue(src_precision); | 3161 int src = instr->VFPMRegValue(src_precision); |
3162 | 3162 |
3163 if (dst_precision == kSinglePrecision) { | 3163 if (dst_precision == kSinglePrecision) { |
3164 double val = get_double_from_d_register(src); | 3164 double val = get_double_from_d_register(src); |
3165 set_s_register_from_float(dst, static_cast<float>(val)); | 3165 set_s_register_from_float(dst, static_cast<float>(val)); |
3166 } else { | 3166 } else { |
3167 float val = get_float_from_s_register(src); | 3167 float val = get_float_from_s_register(src); |
3168 set_d_register_from_double(dst, static_cast<double>(val)); | 3168 set_d_register_from_double(dst, static_cast<double>(val)); |
3169 } | 3169 } |
3170 } | 3170 } |
3171 | 3171 |
3172 bool get_inv_op_vfp_flag(VFPRoundingMode mode, | 3172 bool get_inv_op_vfp_flag(VFPRoundingMode mode, |
3173 double val, | 3173 double val, |
3174 bool unsigned_) { | 3174 bool unsigned_) { |
3175 ASSERT((mode == RN) || (mode == RM) || (mode == RZ)); | 3175 DCHECK((mode == RN) || (mode == RM) || (mode == RZ)); |
3176 double max_uint = static_cast<double>(0xffffffffu); | 3176 double max_uint = static_cast<double>(0xffffffffu); |
3177 double max_int = static_cast<double>(kMaxInt); | 3177 double max_int = static_cast<double>(kMaxInt); |
3178 double min_int = static_cast<double>(kMinInt); | 3178 double min_int = static_cast<double>(kMinInt); |
3179 | 3179 |
3180 // Check for NaN. | 3180 // Check for NaN. |
3181 if (val != val) { | 3181 if (val != val) { |
3182 return true; | 3182 return true; |
3183 } | 3183 } |
3184 | 3184 |
3185 // Check for overflow. This code works because 32bit integers can be | 3185 // Check for overflow. This code works because 32bit integers can be |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3218 if (unsigned_res) { | 3218 if (unsigned_res) { |
3219 return (val < 0) ? 0 : 0xffffffffu; | 3219 return (val < 0) ? 0 : 0xffffffffu; |
3220 } else { | 3220 } else { |
3221 return (val < 0) ? kMinInt : kMaxInt; | 3221 return (val < 0) ? kMinInt : kMaxInt; |
3222 } | 3222 } |
3223 } | 3223 } |
3224 } | 3224 } |
3225 | 3225 |
3226 | 3226 |
3227 void Simulator::DecodeVCVTBetweenFloatingPointAndInteger(Instruction* instr) { | 3227 void Simulator::DecodeVCVTBetweenFloatingPointAndInteger(Instruction* instr) { |
3228 ASSERT((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7) && | 3228 DCHECK((instr->Bit(4) == 0) && (instr->Opc1Value() == 0x7) && |
3229 (instr->Bits(27, 23) == 0x1D)); | 3229 (instr->Bits(27, 23) == 0x1D)); |
3230 ASSERT(((instr->Opc2Value() == 0x8) && (instr->Opc3Value() & 0x1)) || | 3230 DCHECK(((instr->Opc2Value() == 0x8) && (instr->Opc3Value() & 0x1)) || |
3231 (((instr->Opc2Value() >> 1) == 0x6) && (instr->Opc3Value() & 0x1))); | 3231 (((instr->Opc2Value() >> 1) == 0x6) && (instr->Opc3Value() & 0x1))); |
3232 | 3232 |
3233 // Conversion between floating-point and integer. | 3233 // Conversion between floating-point and integer. |
3234 bool to_integer = (instr->Bit(18) == 1); | 3234 bool to_integer = (instr->Bit(18) == 1); |
3235 | 3235 |
3236 VFPRegPrecision src_precision = (instr->SzValue() == 1) ? kDoublePrecision | 3236 VFPRegPrecision src_precision = (instr->SzValue() == 1) ? kDoublePrecision |
3237 : kSinglePrecision; | 3237 : kSinglePrecision; |
3238 | 3238 |
3239 if (to_integer) { | 3239 if (to_integer) { |
3240 // We are playing with code close to the C++ standard's limits below, | 3240 // We are playing with code close to the C++ standard's limits below, |
3241 // hence the very simple code and heavy checks. | 3241 // hence the very simple code and heavy checks. |
3242 // | 3242 // |
3243 // Note: | 3243 // Note: |
3244 // C++ defines default type casting from floating point to integer as | 3244 // C++ defines default type casting from floating point to integer as |
3245 // (close to) rounding toward zero ("fractional part discarded"). | 3245 // (close to) rounding toward zero ("fractional part discarded"). |
3246 | 3246 |
3247 int dst = instr->VFPDRegValue(kSinglePrecision); | 3247 int dst = instr->VFPDRegValue(kSinglePrecision); |
3248 int src = instr->VFPMRegValue(src_precision); | 3248 int src = instr->VFPMRegValue(src_precision); |
3249 | 3249 |
3250 // Bit 7 in vcvt instructions indicates if we should use the FPSCR rounding | 3250 // Bit 7 in vcvt instructions indicates if we should use the FPSCR rounding |
3251 // mode or the default Round to Zero mode. | 3251 // mode or the default Round to Zero mode. |
3252 VFPRoundingMode mode = (instr->Bit(7) != 1) ? FPSCR_rounding_mode_ | 3252 VFPRoundingMode mode = (instr->Bit(7) != 1) ? FPSCR_rounding_mode_ |
3253 : RZ; | 3253 : RZ; |
3254 ASSERT((mode == RM) || (mode == RZ) || (mode == RN)); | 3254 DCHECK((mode == RM) || (mode == RZ) || (mode == RN)); |
3255 | 3255 |
3256 bool unsigned_integer = (instr->Bit(16) == 0); | 3256 bool unsigned_integer = (instr->Bit(16) == 0); |
3257 bool double_precision = (src_precision == kDoublePrecision); | 3257 bool double_precision = (src_precision == kDoublePrecision); |
3258 | 3258 |
3259 double val = double_precision ? get_double_from_d_register(src) | 3259 double val = double_precision ? get_double_from_d_register(src) |
3260 : get_float_from_s_register(src); | 3260 : get_float_from_s_register(src); |
3261 | 3261 |
3262 int temp = unsigned_integer ? static_cast<uint32_t>(val) | 3262 int temp = unsigned_integer ? static_cast<uint32_t>(val) |
3263 : static_cast<int32_t>(val); | 3263 : static_cast<int32_t>(val); |
3264 | 3264 |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3328 } | 3328 } |
3329 | 3329 |
3330 | 3330 |
3331 // void Simulator::DecodeType6CoprocessorIns(Instruction* instr) | 3331 // void Simulator::DecodeType6CoprocessorIns(Instruction* instr) |
3332 // Decode Type 6 coprocessor instructions. | 3332 // Decode Type 6 coprocessor instructions. |
3333 // Dm = vmov(Rt, Rt2) | 3333 // Dm = vmov(Rt, Rt2) |
3334 // <Rt, Rt2> = vmov(Dm) | 3334 // <Rt, Rt2> = vmov(Dm) |
3335 // Ddst = MEM(Rbase + 4*offset). | 3335 // Ddst = MEM(Rbase + 4*offset). |
3336 // MEM(Rbase + 4*offset) = Dsrc. | 3336 // MEM(Rbase + 4*offset) = Dsrc. |
3337 void Simulator::DecodeType6CoprocessorIns(Instruction* instr) { | 3337 void Simulator::DecodeType6CoprocessorIns(Instruction* instr) { |
3338 ASSERT((instr->TypeValue() == 6)); | 3338 DCHECK((instr->TypeValue() == 6)); |
3339 | 3339 |
3340 if (instr->CoprocessorValue() == 0xA) { | 3340 if (instr->CoprocessorValue() == 0xA) { |
3341 switch (instr->OpcodeValue()) { | 3341 switch (instr->OpcodeValue()) { |
3342 case 0x8: | 3342 case 0x8: |
3343 case 0xA: | 3343 case 0xA: |
3344 case 0xC: | 3344 case 0xC: |
3345 case 0xE: { // Load and store single precision float to memory. | 3345 case 0xE: { // Load and store single precision float to memory. |
3346 int rn = instr->RnValue(); | 3346 int rn = instr->RnValue(); |
3347 int vd = instr->VFPDRegValue(kSinglePrecision); | 3347 int vd = instr->VFPDRegValue(kSinglePrecision); |
3348 int offset = instr->Immed8Value(); | 3348 int offset = instr->Immed8Value(); |
(...skipping 400 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3749 set_register(r11, r11_val); | 3749 set_register(r11, r11_val); |
3750 } | 3750 } |
3751 | 3751 |
3752 | 3752 |
3753 int32_t Simulator::Call(byte* entry, int argument_count, ...) { | 3753 int32_t Simulator::Call(byte* entry, int argument_count, ...) { |
3754 va_list parameters; | 3754 va_list parameters; |
3755 va_start(parameters, argument_count); | 3755 va_start(parameters, argument_count); |
3756 // Set up arguments | 3756 // Set up arguments |
3757 | 3757 |
3758 // First four arguments passed in registers. | 3758 // First four arguments passed in registers. |
3759 ASSERT(argument_count >= 4); | 3759 DCHECK(argument_count >= 4); |
3760 set_register(r0, va_arg(parameters, int32_t)); | 3760 set_register(r0, va_arg(parameters, int32_t)); |
3761 set_register(r1, va_arg(parameters, int32_t)); | 3761 set_register(r1, va_arg(parameters, int32_t)); |
3762 set_register(r2, va_arg(parameters, int32_t)); | 3762 set_register(r2, va_arg(parameters, int32_t)); |
3763 set_register(r3, va_arg(parameters, int32_t)); | 3763 set_register(r3, va_arg(parameters, int32_t)); |
3764 | 3764 |
3765 // Remaining arguments passed on stack. | 3765 // Remaining arguments passed on stack. |
3766 int original_stack = get_register(sp); | 3766 int original_stack = get_register(sp); |
3767 // Compute position of stack on entry to generated code. | 3767 // Compute position of stack on entry to generated code. |
3768 int entry_stack = (original_stack - (argument_count - 4) * sizeof(int32_t)); | 3768 int entry_stack = (original_stack - (argument_count - 4) * sizeof(int32_t)); |
3769 if (base::OS::ActivationFrameAlignment() != 0) { | 3769 if (base::OS::ActivationFrameAlignment() != 0) { |
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3832 uintptr_t address = *stack_slot; | 3832 uintptr_t address = *stack_slot; |
3833 set_register(sp, current_sp + sizeof(uintptr_t)); | 3833 set_register(sp, current_sp + sizeof(uintptr_t)); |
3834 return address; | 3834 return address; |
3835 } | 3835 } |
3836 | 3836 |
3837 } } // namespace v8::internal | 3837 } } // namespace v8::internal |
3838 | 3838 |
3839 #endif // USE_SIMULATOR | 3839 #endif // USE_SIMULATOR |
3840 | 3840 |
3841 #endif // V8_TARGET_ARCH_ARM | 3841 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |