115613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org// Copyright 2012 the V8 project authors. All rights reserved. 23484964a86451e86dcf04be9bd8c0d76ee04f081rossberg@chromium.org// Use of this source code is governed by a BSD-style license that can be 33484964a86451e86dcf04be9bd8c0d76ee04f081rossberg@chromium.org// found in the LICENSE file. 443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// Declares a Simulator for ARM instructions if we are not generating a native 743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// ARM binary. This Simulator allows us to run and debug ARM code generation on 843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// regular desktop machines. 943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// V8 calls into generated code by "calling" the CALL_GENERATED_CODE macro, 1043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// which will start execution in the Simulator or forwards to the real entry 1143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// on a ARM HW platform. 1243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 135ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org#ifndef V8_ARM_SIMULATOR_ARM_H_ 145ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org#define V8_ARM_SIMULATOR_ARM_H_ 1543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 16196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/allocation.h" 17c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org 18303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org#if !defined(USE_SIMULATOR) 19303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org// Running without a simulator on a native arm platform. 20303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 21303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.orgnamespace v8 { 22303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.orgnamespace internal { 2343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen// When running without a simulator we call the entry directly. 2543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen#define CALL_GENERATED_CODE(entry, p0, p1, p2, p3, p4) \ 2618ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org (entry(p0, p1, p2, p3, p4)) 2743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2849edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.orgtypedef int (*arm_regexp_matcher)(String*, int, const byte*, const byte*, 2915613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org void*, int*, int, Address, int, Isolate*); 3049edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 3149edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 3249edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org// Call the generated regexp code directly. The code at the entry address 3349edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org// should act as a function matching the type arm_regexp_matcher. 3449edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org// The fifth argument is a dummy that reserves the space used for 3549edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org// the return address added by the ExitFrame in native calls. 3615613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org#define CALL_GENERATED_REGEXP_CODE(entry, p0, p1, p2, p3, p4, p5, p6, p7, p8) \ 37ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org (FUNCTION_CAST<arm_regexp_matcher>(entry)( \ 3815613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org p0, p1, p2, p3, NULL, p4, p5, p6, p7, p8)) 39303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 40c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// The stack limit beyond which we will throw stack overflow errors in 41c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// generated code. Because generated code on arm uses the C stack, we 42c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// just use the C stack limit. 43c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.orgclass SimulatorStack : public v8::internal::AllStatic { 44c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org public: 451c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org static inline uintptr_t JsLimitFromCLimit(v8::internal::Isolate* isolate, 461c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org uintptr_t c_limit) { 471c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org USE(isolate); 48c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org return c_limit; 49c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org } 50c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 51c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org static inline uintptr_t RegisterCTryCatch(uintptr_t try_catch_address) { 52c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org return try_catch_address; 53c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org } 54c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 55c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org static inline void UnregisterCTryCatch() { } 56c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org}; 5743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 58303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org} } // namespace v8::internal 5918ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 60303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org#else // !defined(USE_SIMULATOR) 61303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org// Running with a simulator. 62c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 63196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/arm/constants-arm.h" 64196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/hashmap.h" 65196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/assembler.h" 6643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 67378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.orgnamespace v8 { 68378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.orgnamespace internal { 6943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 70013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.orgclass CachePage { 71013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org public: 72013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int LINE_VALID = 0; 73013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int LINE_INVALID = 1; 74013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 75013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kPageShift = 12; 76013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kPageSize = 1 << kPageShift; 77013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kPageMask = kPageSize - 1; 78013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kLineShift = 2; // The cache line is only 4 bytes right now. 79013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kLineLength = 1 << kLineShift; 80013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kLineMask = kLineLength - 1; 81013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 82013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org CachePage() { 83013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org memset(&validity_map_, LINE_INVALID, sizeof(validity_map_)); 84013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org } 85013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 86013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org char* ValidityByte(int offset) { 87013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org return &validity_map_[offset >> kLineShift]; 88013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org } 89013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 90013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org char* CachedData(int offset) { 91013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org return &data_[offset]; 92013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org } 93013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 94013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org private: 95013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org char data_[kPageSize]; // The cached data. 96013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org static const int kValidityMapSize = kPageSize >> kLineShift; 97013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org char validity_map_[kValidityMapSize]; // One byte per line. 98013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org}; 99013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 100013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 10143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansenclass Simulator { 10243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen public: 103ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org friend class ArmDebugger; 10443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen enum Register { 10543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen no_reg = -1, 10643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen r0 = 0, r1, r2, r3, r4, r5, r6, r7, 10743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen r8, r9, r10, r11, r12, r13, r14, r15, 10843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen num_registers, 10943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen sp = 13, 11043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen lr = 14, 111c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org pc = 15, 112c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org s0 = 0, s1, s2, s3, s4, s5, s6, s7, 113c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org s8, s9, s10, s11, s12, s13, s14, s15, 114c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org s16, s17, s18, s19, s20, s21, s22, s23, 115c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org s24, s25, s26, s27, s28, s29, s30, s31, 116c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org num_s_registers = 32, 117c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org d0 = 0, d1, d2, d3, d4, d5, d6, d7, 118c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org d8, d9, d10, d11, d12, d13, d14, d15, 119003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org d16, d17, d18, d19, d20, d21, d22, d23, 120003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org d24, d25, d26, d27, d28, d29, d30, d31, 121169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org num_d_registers = 32, 122169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org q0 = 0, q1, q2, q3, q4, q5, q6, q7, 123169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org q8, q9, q10, q11, q12, q13, q14, q15, 124169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org num_q_registers = 16 12543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen }; 12643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1271c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org explicit Simulator(Isolate* isolate); 12843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen ~Simulator(); 12943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 13043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // The currently executing Simulator instance. Potentially there can be one 13143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // for each native thread. 132ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org static Simulator* current(v8::internal::Isolate* isolate); 13343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 13443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Accessors for register state. Reading the pc value adheres to the ARM 13543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // architecture specification and is off by a 8 from the currently executing 13643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // instruction. 13743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen void set_register(int reg, int32_t value); 13843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int32_t get_register(int reg) const; 139160a7b0747492f3f735353d9582521f3314bf4dfdanno@chromium.org double get_double_from_register_pair(int reg); 140528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org void set_register_pair_from_double(int reg, double* value); 141720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org void set_dw_register(int dreg, const int* dbl); 14243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 143c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Support for VFP. 144169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void get_d_register(int dreg, uint64_t* value); 145169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void set_d_register(int dreg, const uint64_t* value); 146169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void get_d_register(int dreg, uint32_t* value); 147169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void set_d_register(int dreg, const uint32_t* value); 148169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void get_q_register(int qreg, uint64_t* value); 149169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void set_q_register(int qreg, const uint64_t* value); 150169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void get_q_register(int qreg, uint32_t* value); 151169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void set_q_register(int qreg, const uint32_t* value); 152169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org 153c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org void set_s_register(int reg, unsigned int value); 154c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org unsigned int get_s_register(int reg) const; 155471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 156471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org void set_d_register_from_double(int dreg, const double& dbl) { 157471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org SetVFPRegister<double, 2>(dreg, dbl); 158471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 159471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 160471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org double get_double_from_d_register(int dreg) { 161471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org return GetFromVFPRegister<double, 2>(dreg); 162471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 163471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 164471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org void set_s_register_from_float(int sreg, const float flt) { 165471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org SetVFPRegister<float, 1>(sreg, flt); 166471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 167471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 168471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org float get_float_from_s_register(int sreg) { 169471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org return GetFromVFPRegister<float, 1>(sreg); 170471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 171471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 172471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org void set_s_register_from_sinteger(int sreg, const int sint) { 173471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org SetVFPRegister<int, 1>(sreg, sint); 174471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 175471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 176471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org int get_sinteger_from_s_register(int sreg) { 177471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org return GetFromVFPRegister<int, 1>(sreg); 178471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 179c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 18043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Special case of set_register and get_register to access the raw PC value. 18143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen void set_pc(int32_t value); 18243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int32_t get_pc() const; 18343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 184f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org Address get_sp() { 185f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org return reinterpret_cast<Address>(static_cast<intptr_t>(get_register(sp))); 186f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org } 187f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org 18843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Accessor to the internal simulator stack area. 18943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen uintptr_t StackLimit() const; 19043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 19143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Executes ARM instructions until the PC reaches end_sim_pc. 1923bf7b91c90e9bff46f53eec55055d2d1a1949215ager@chromium.org void Execute(); 19343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 194eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Call on program start. 1951c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org static void Initialize(Isolate* isolate); 196eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 19718ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org // V8 generally calls into generated JS code with 5 parameters and into 19818ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org // generated RegExp code with 7 parameters. This is a convenience function, 19918ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org // which sets up the simulator state and grabs the result on return. 20018ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org int32_t Call(byte* entry, int argument_count, ...); 2011f34ad3eadf9b0e6b8ed415817d276f54dd6d06bdanno@chromium.org // Alternative: call a 2-argument double function. 202528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org void CallFP(byte* entry, double d0, double d1); 203528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org int32_t CallFPReturnsInt(byte* entry, double d0, double d1); 204528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org double CallFPReturnsDouble(byte* entry, double d0, double d1); 20543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 206c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Push an address onto the JS stack. 207c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org uintptr_t PushAddress(uintptr_t address); 208c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 209c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Pop an address from the JS stack. 210c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org uintptr_t PopAddress(); 211c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 212c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org // Debugger input. 213c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org void set_last_debugger_input(char* input); 214c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org char* last_debugger_input() { return last_debugger_input_; } 215c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org 216013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org // ICache checking. 217ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org static void FlushICache(v8::internal::HashMap* i_cache, void* start, 218ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org size_t size); 219013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 220a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Returns true if pc register contains one of the 'special_values' defined 221a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // below (bad_lr, end_sim_pc). 222a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org bool has_bad_pc() const; 223a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 2248e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org // EABI variant for double arguments in use. 2258e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org bool use_eabi_hardfloat() { 2268e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org#if USE_EABI_HARDFLOAT 2278e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org return true; 2288e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org#else 2298e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org return false; 2308e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org#endif 2318e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 2328e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 23343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen private: 23443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen enum special_values { 23543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Known bad pc value to ensure that the simulator does not execute 23643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // without being properly setup. 23743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bad_lr = -1, 23843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // A pc value used to signal the simulator to stop execution. Generally 23943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // the lr is set to this value on transition from native C code to 24043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // simulated execution, so that the simulator can "return" to the native 24143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // C code. 24243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen end_sim_pc = -2 24343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen }; 24443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 24543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Unsupported instructions use Format to print an error and stop execution. 246378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void Format(Instruction* instr, const char* format); 24743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 24843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Checks if the current instruction should be executed based on its 24943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // condition bits. 25037be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org inline bool ConditionallyExecute(Instruction* instr); 25143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 25243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Helper functions to set the conditional flags in the architecture state. 25343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen void SetNZFlags(int32_t val); 25443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen void SetCFlag(bool val); 25543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen void SetVFlag(bool val); 256dcebac0f4c6c0da579b7cc91a0cbba8f3c820c8dricow@chromium.org bool CarryFrom(int32_t left, int32_t right, int32_t carry = 0); 25743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool BorrowFrom(int32_t left, int32_t right); 25843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool OverflowFrom(int32_t alu_out, 25943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int32_t left, 26043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int32_t right, 26143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool addition); 26243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 263dcebac0f4c6c0da579b7cc91a0cbba8f3c820c8dricow@chromium.org inline int GetCarry() { 264dcebac0f4c6c0da579b7cc91a0cbba8f3c820c8dricow@chromium.org return c_flag_ ? 1 : 0; 2653c3c8d733702cb2b41471efa5eead1faf5b5711bmachenbach@chromium.org } 266dcebac0f4c6c0da579b7cc91a0cbba8f3c820c8dricow@chromium.org 267c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Support for VFP. 268c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org void Compute_FPSCR_Flags(double val1, double val2); 269c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org void Copy_FPSCR_to_APSR(); 270e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org inline double canonicalizeNaN(double value); 271c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 27243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Helper functions to decode common "addressing" modes 273378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org int32_t GetShiftRm(Instruction* instr, bool* carry_out); 274378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org int32_t GetImm(Instruction* instr, bool* carry_out); 27510480471c0db59c51c15e57d2a3489551d61b273jkummerow@chromium.org int32_t ProcessPU(Instruction* instr, 27610480471c0db59c51c15e57d2a3489551d61b273jkummerow@chromium.org int num_regs, 27710480471c0db59c51c15e57d2a3489551d61b273jkummerow@chromium.org int operand_size, 27810480471c0db59c51c15e57d2a3489551d61b273jkummerow@chromium.org intptr_t* start_address, 27910480471c0db59c51c15e57d2a3489551d61b273jkummerow@chromium.org intptr_t* end_address); 280378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void HandleRList(Instruction* instr, bool load); 28174f333bce721daf6b1f9d7d3d3faa623f77658d7vegorov@chromium.org void HandleVList(Instruction* inst); 282378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void SoftwareInterrupt(Instruction* instr); 28343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 284e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // Stop helper functions. 285378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline bool isStopInstruction(Instruction* instr); 286e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org inline bool isWatchedStop(uint32_t bkpt_code); 287e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org inline bool isEnabledStop(uint32_t bkpt_code); 288e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org inline void EnableStop(uint32_t bkpt_code); 289e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org inline void DisableStop(uint32_t bkpt_code); 290e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org inline void IncreaseStopCounter(uint32_t bkpt_code); 291e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org void PrintStopInfo(uint32_t code); 292e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org 2939bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org // Read and write memory. 2949bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org inline uint8_t ReadBU(int32_t addr); 2959bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org inline int8_t ReadB(int32_t addr); 2969bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org inline void WriteB(int32_t addr, uint8_t value); 2979bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org inline void WriteB(int32_t addr, int8_t value); 2989bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org 299378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline uint16_t ReadHU(int32_t addr, Instruction* instr); 300378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline int16_t ReadH(int32_t addr, Instruction* instr); 3019bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org // Note: Overloaded on the sign of the value. 302378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline void WriteH(int32_t addr, uint16_t value, Instruction* instr); 303378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline void WriteH(int32_t addr, int16_t value, Instruction* instr); 3049bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org 305378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline int ReadW(int32_t addr, Instruction* instr); 306378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org inline void WriteW(int32_t addr, int value, Instruction* instr); 3079bbf968a649030335309265ba2c98fcc36aeb762kasperl@chromium.org 308720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org int32_t* ReadDW(int32_t addr); 309720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org void WriteDW(int32_t addr, int32_t value1, int32_t value2); 310720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org 31143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Executing is handled based on the instruction type. 312378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org // Both type 0 and type 1 rolled into one. 313378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType01(Instruction* instr); 314378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType2(Instruction* instr); 315378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType3(Instruction* instr); 316378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType4(Instruction* instr); 317378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType5(Instruction* instr); 318378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType6(Instruction* instr); 319378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType7(Instruction* instr); 32043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 321c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Support for VFP. 322378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeTypeVFP(Instruction* instr); 323378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeType6CoprocessorIns(Instruction* instr); 324169691d93a961c8b511f8ac8fd8ee33d081ca10fdanno@chromium.org void DecodeSpecialCondition(Instruction* instr); 325c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 326378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeVMOVBetweenCoreAndSinglePrecisionRegisters(Instruction* instr); 327378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeVCMP(Instruction* instr); 328378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeVCVTBetweenDoubleAndSingle(Instruction* instr); 329378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void DecodeVCVTBetweenFloatingPointAndInteger(Instruction* instr); 3305d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org 33143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Executes one instruction. 332378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org void InstructionDecode(Instruction* instr); 33343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 334013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org // ICache. 335ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org static void CheckICache(v8::internal::HashMap* i_cache, Instruction* instr); 336ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org static void FlushOnePage(v8::internal::HashMap* i_cache, intptr_t start, 337ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org int size); 338ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org static CachePage* GetCachePage(v8::internal::HashMap* i_cache, void* page); 339013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 340eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Runtime call support. 34183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org static void* RedirectExternalReference( 34283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org void* external_function, 34383aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org v8::internal::ExternalReference::Type type); 344eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 345f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org // Handle arguments and return value for runtime FP functions. 346f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org void GetFpArgs(double* x, double* y, int32_t* z); 34765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org void SetFpResult(const double& result); 34865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org void TrashCallerSaveRegisters(); 34965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org 350471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org template<class ReturnType, int register_size> 351471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org ReturnType GetFromVFPRegister(int reg_index); 352471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 353471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org template<class InputType, int register_size> 354471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org void SetVFPRegister(int reg_index, const InputType& value); 355471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 3561f34ad3eadf9b0e6b8ed415817d276f54dd6d06bdanno@chromium.org void CallInternal(byte* entry); 3571f34ad3eadf9b0e6b8ed415817d276f54dd6d06bdanno@chromium.org 358c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Architecture state. 359ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org // Saturating instructions require a Q flag to indicate saturation. 360ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org // There is currently no way to read the CPSR directly, and thus read the Q 361ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org // flag, so this is left unimplemented. 36243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int32_t registers_[16]; 36343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool n_flag_; 36443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool z_flag_; 36543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool c_flag_; 36643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool v_flag_; 36743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 368c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // VFP architecture state. 369e3b8d0fe80e858c990832db1233c069f8b8cd5c9mstarzinger@chromium.org unsigned int vfp_registers_[num_d_registers * 2]; 370c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool n_flag_FPSCR_; 371c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool z_flag_FPSCR_; 372c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool c_flag_FPSCR_; 373c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool v_flag_FPSCR_; 374c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 37501fe7df37ce9858e3d0069ec6a2d7c667256b95aager@chromium.org // VFP rounding mode. See ARM DDI 0406B Page A2-29. 37683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org VFPRoundingMode FPSCR_rounding_mode_; 377e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org bool FPSCR_default_NaN_mode_; 37801fe7df37ce9858e3d0069ec6a2d7c667256b95aager@chromium.org 379c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // VFP FP exception flags architecture state. 380c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool inv_op_vfp_flag_; 381c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool div_zero_vfp_flag_; 382c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool overflow_vfp_flag_; 383c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool underflow_vfp_flag_; 384c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org bool inexact_vfp_flag_; 385c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 386c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Simulator support. 38743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen char* stack_; 38843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bool pc_modified_; 38943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen int icount_; 39043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 391c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org // Debugger input. 392c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org char* last_debugger_input_; 393c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org 394013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org // Icache simulation 395ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org v8::internal::HashMap* i_cache_; 396013f3e12d3af426bf5545b5f457aa08ee98bdca2fschneider@chromium.org 397c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org // Registered breakpoints. 398378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Instruction* break_pc_; 399378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Instr break_instr_; 400e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org 401ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org v8::internal::Isolate* isolate_; 402ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org 403e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // A stop is watched if its code is less than kNumOfWatchedStops. 404e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // Only watched stops support enabling/disabling and the counter feature. 405e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org static const uint32_t kNumOfWatchedStops = 256; 406e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org 407e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // Breakpoint is disabled if bit 31 is set. 408e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org static const uint32_t kStopDisabledBit = 1 << 31; 409e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org 410e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // A stop is enabled, meaning the simulator will stop when meeting the 411f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org // instruction, if bit 31 of watched_stops_[code].count is unset. 412f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org // The value watched_stops_[code].count & ~(1 << 31) indicates how many times 413e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org // the breakpoint was hit or gone through. 414378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org struct StopCountAndDesc { 415e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org uint32_t count; 416e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org char* desc; 417e03fb64ef23331755b7986d2560bc4c00ba3e67bfschneider@chromium.org }; 418f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org StopCountAndDesc watched_stops_[kNumOfWatchedStops]; 41943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen}; 42043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 421303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 422303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org// When running with the simulator transition into simulated execution at this 423303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org// point. 424303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org#define CALL_GENERATED_CODE(entry, p0, p1, p2, p3, p4) \ 425ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org reinterpret_cast<Object*>(Simulator::current(Isolate::Current())->Call( \ 426303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org FUNCTION_ADDR(entry), 5, p0, p1, p2, p3, p4)) 427303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 428528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org#define CALL_GENERATED_FP_INT(entry, p0, p1) \ 429528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Simulator::current(Isolate::Current())->CallFPReturnsInt( \ 430528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org FUNCTION_ADDR(entry), p0, p1) 431528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 43215613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org#define CALL_GENERATED_REGEXP_CODE(entry, p0, p1, p2, p3, p4, p5, p6, p7, p8) \ 433ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Simulator::current(Isolate::Current())->Call( \ 43415613d0b07bac19e341905ff374c930420b3b9c8mstarzinger@chromium.org entry, 10, p0, p1, p2, p3, NULL, p4, p5, p6, p7, p8) 435303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 436303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 437c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// The simulator has its own stack. Thus it has a different stack limit from 438c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// the C-based native code. Setting the c_limit to indicate a very small 439c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// stack cause stack overflow errors, since the simulator ignores the input. 440c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// This is unlikely to be an issue in practice, though it might cause testing 441c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org// trouble down the line. 442c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.orgclass SimulatorStack : public v8::internal::AllStatic { 443c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org public: 4441c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org static inline uintptr_t JsLimitFromCLimit(v8::internal::Isolate* isolate, 4451c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org uintptr_t c_limit) { 4461c09276ce2ac5214e81ca554360b9f101187893blrn@chromium.org return Simulator::current(isolate)->StackLimit(); 447c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org } 448c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 449c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org static inline uintptr_t RegisterCTryCatch(uintptr_t try_catch_address) { 450ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Simulator* sim = Simulator::current(Isolate::Current()); 451c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org return sim->PushAddress(try_catch_address); 452c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org } 453c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org 454c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org static inline void UnregisterCTryCatch() { 455ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Simulator::current(Isolate::Current())->PopAddress(); 456c4c927273ae2b690c4a015b4640a2a469c9a1a69ager@chromium.org } 457c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org}; 458c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org 459303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org} } // namespace v8::internal 460c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org 461303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org#endif // !defined(USE_SIMULATOR) 4625ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org#endif // V8_ARM_SIMULATOR_ARM_H_ 463