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 #if V8_TARGET_ARCH_ARM | 9 #if V8_TARGET_ARCH_ARM |
10 | 10 |
(...skipping 1023 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1034 if (register_size == 2) DCHECK(reg_index < DwVfpRegister::NumRegisters()); | 1034 if (register_size == 2) DCHECK(reg_index < DwVfpRegister::NumRegisters()); |
1035 | 1035 |
1036 ReturnType value = 0; | 1036 ReturnType value = 0; |
1037 char buffer[register_size * sizeof(vfp_registers_[0])]; | 1037 char buffer[register_size * sizeof(vfp_registers_[0])]; |
1038 memcpy(buffer, &vfp_registers_[register_size * reg_index], | 1038 memcpy(buffer, &vfp_registers_[register_size * reg_index], |
1039 register_size * sizeof(vfp_registers_[0])); | 1039 register_size * sizeof(vfp_registers_[0])); |
1040 memcpy(&value, buffer, register_size * sizeof(vfp_registers_[0])); | 1040 memcpy(&value, buffer, register_size * sizeof(vfp_registers_[0])); |
1041 return value; | 1041 return value; |
1042 } | 1042 } |
1043 | 1043 |
| 1044 void Simulator::SetSpecialRegister(SRegisterFieldMask reg_and_mask, |
| 1045 uint32_t value) { |
| 1046 // Only CPSR_f is implemented. Of that, only N, Z, C and V are implemented. |
| 1047 if ((reg_and_mask == CPSR_f) && ((value & ~kSpecialCondition) == 0)) { |
| 1048 n_flag_ = ((value & (1 << 31)) != 0); |
| 1049 z_flag_ = ((value & (1 << 30)) != 0); |
| 1050 c_flag_ = ((value & (1 << 29)) != 0); |
| 1051 v_flag_ = ((value & (1 << 28)) != 0); |
| 1052 } else { |
| 1053 UNIMPLEMENTED(); |
| 1054 } |
| 1055 } |
| 1056 |
| 1057 uint32_t Simulator::GetFromSpecialRegister(SRegister reg) { |
| 1058 uint32_t result = 0; |
| 1059 // Only CPSR_f is implemented. |
| 1060 if (reg == CPSR) { |
| 1061 if (n_flag_) result |= (1 << 31); |
| 1062 if (z_flag_) result |= (1 << 30); |
| 1063 if (c_flag_) result |= (1 << 29); |
| 1064 if (v_flag_) result |= (1 << 28); |
| 1065 } else { |
| 1066 UNIMPLEMENTED(); |
| 1067 } |
| 1068 return result; |
| 1069 } |
1044 | 1070 |
1045 // Runtime FP routines take: | 1071 // Runtime FP routines take: |
1046 // - two double arguments | 1072 // - two double arguments |
1047 // - one double argument and zero or one integer arguments. | 1073 // - one double argument and zero or one integer arguments. |
1048 // All are consructed here from r0-r3 or d0, d1 and r0. | 1074 // All are consructed here from r0-r3 or d0, d1 and r0. |
1049 void Simulator::GetFpArgs(double* x, double* y, int32_t* z) { | 1075 void Simulator::GetFpArgs(double* x, double* y, int32_t* z) { |
1050 if (use_eabi_hardfloat()) { | 1076 if (use_eabi_hardfloat()) { |
1051 *x = get_double_from_d_register(0); | 1077 *x = get_double_from_d_register(0); |
1052 *y = get_double_from_d_register(1); | 1078 *y = get_double_from_d_register(1); |
1053 *z = get_register(0); | 1079 *z = get_register(0); |
(...skipping 1251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2305 } else { | 2331 } else { |
2306 // signed byte loads | 2332 // signed byte loads |
2307 DCHECK(instr->HasSign()); | 2333 DCHECK(instr->HasSign()); |
2308 DCHECK(instr->HasL()); | 2334 DCHECK(instr->HasL()); |
2309 int8_t val = ReadB(addr); | 2335 int8_t val = ReadB(addr); |
2310 set_register(rd, val); | 2336 set_register(rd, val); |
2311 } | 2337 } |
2312 return; | 2338 return; |
2313 } | 2339 } |
2314 } else if ((type == 0) && instr->IsMiscType0()) { | 2340 } else if ((type == 0) && instr->IsMiscType0()) { |
2315 if (instr->Bits(22, 21) == 1) { | 2341 if ((instr->Bits(27, 23) == 2) && (instr->Bits(21, 20) == 2) && |
| 2342 (instr->Bits(15, 4) == 0xf00)) { |
| 2343 // MSR |
| 2344 int rm = instr->RmValue(); |
| 2345 DCHECK_NE(pc, rm); // UNPREDICTABLE |
| 2346 SRegisterFieldMask sreg_and_mask = |
| 2347 instr->BitField(22, 22) | instr->BitField(19, 16); |
| 2348 SetSpecialRegister(sreg_and_mask, get_register(rm)); |
| 2349 } else if ((instr->Bits(27, 23) == 2) && (instr->Bits(21, 20) == 0) && |
| 2350 (instr->Bits(11, 0) == 0)) { |
| 2351 // MRS |
| 2352 int rd = instr->RdValue(); |
| 2353 DCHECK_NE(pc, rd); // UNPREDICTABLE |
| 2354 SRegister sreg = static_cast<SRegister>(instr->BitField(22, 22)); |
| 2355 set_register(rd, GetFromSpecialRegister(sreg)); |
| 2356 } else if (instr->Bits(22, 21) == 1) { |
2316 int rm = instr->RmValue(); | 2357 int rm = instr->RmValue(); |
2317 switch (instr->BitField(7, 4)) { | 2358 switch (instr->BitField(7, 4)) { |
2318 case BX: | 2359 case BX: |
2319 set_pc(get_register(rm)); | 2360 set_pc(get_register(rm)); |
2320 break; | 2361 break; |
2321 case BLX: { | 2362 case BLX: { |
2322 uint32_t old_pc = get_pc(); | 2363 uint32_t old_pc = get_pc(); |
2323 set_pc(get_register(rm)); | 2364 set_pc(get_register(rm)); |
2324 set_register(lr, old_pc + Instruction::kInstrSize); | 2365 set_register(lr, old_pc + Instruction::kInstrSize); |
2325 break; | 2366 break; |
(...skipping 1900 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4226 set_register(sp, current_sp + sizeof(uintptr_t)); | 4267 set_register(sp, current_sp + sizeof(uintptr_t)); |
4227 return address; | 4268 return address; |
4228 } | 4269 } |
4229 | 4270 |
4230 } // namespace internal | 4271 } // namespace internal |
4231 } // namespace v8 | 4272 } // namespace v8 |
4232 | 4273 |
4233 #endif // USE_SIMULATOR | 4274 #endif // USE_SIMULATOR |
4234 | 4275 |
4235 #endif // V8_TARGET_ARCH_ARM | 4276 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |