1f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com// 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 53cdd9e13bac71e7c5b63da6962f8d30f6622db14kmillikin@chromium.org#include <limits.h> // For LONG_MIN, LONG_MAX. 63cdd9e13bac71e7c5b63da6962f8d30f6622db14kmillikin@chromium.org 7196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/v8.h" 843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 993a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org#if V8_TARGET_ARCH_ARM 109dfbea4c7d423c7bc1db94425cb78e7f7cf41f78erik.corry@gmail.com 11196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/bootstrapper.h" 12196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/codegen.h" 13196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/cpu-profiler.h" 14196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/debug.h" 15196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/isolate-inl.h" 16196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org#include "src/runtime.h" 1743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1871affb54842da76b24f0bb3184e9f0960523f89dkasperl@chromium.orgnamespace v8 { 1971affb54842da76b24f0bb3184e9f0960523f89dkasperl@chromium.orgnamespace internal { 2043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 21c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.orgMacroAssembler::MacroAssembler(Isolate* arg_isolate, void* buffer, int size) 22c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org : Assembler(arg_isolate, buffer, size), 237276f14ca716596e0a0d17539516370c1f453847kasper.lund generating_stub_(false), 24c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com has_frame_(false) { 25c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org if (isolate() != NULL) { 26c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org code_object_ = Handle<Object>(isolate()->heap()->undefined_value(), 27c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org isolate()); 28c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org } 2943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 3043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 3143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 3243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansenvoid MacroAssembler::Jump(Register target, Condition cond) { 3343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bx(target, cond); 3443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 3543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 3643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 37236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.orgvoid MacroAssembler::Jump(intptr_t target, RelocInfo::Mode rmode, 38236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org Condition cond) { 399ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ASSERT(RelocInfo::IsCodeTarget(rmode)); 409ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org mov(pc, Operand(target, rmode), LeaveCC, cond); 4143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 4243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 4343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 444f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.orgvoid MacroAssembler::Jump(Address target, RelocInfo::Mode rmode, 45236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org Condition cond) { 46236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org ASSERT(!RelocInfo::IsCodeTarget(rmode)); 4743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen Jump(reinterpret_cast<intptr_t>(target), rmode, cond); 4843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 4943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 5043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 51236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.orgvoid MacroAssembler::Jump(Handle<Code> code, RelocInfo::Mode rmode, 52236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org Condition cond) { 53236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org ASSERT(RelocInfo::IsCodeTarget(rmode)); 5443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // 'code' is always generated ARM code, never THUMB code 5579e7902fa5f94747b5383dd40f3002dd8b62303arossberg@chromium.org AllowDeferredHandleDereference embedding_raw_address; 5643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen Jump(reinterpret_cast<intptr_t>(code.location()), rmode, cond); 5743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 5843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 5943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 60b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.orgint MacroAssembler::CallSize(Register target, Condition cond) { 61b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org return kInstrSize; 62b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org} 63b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org 64b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org 6543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansenvoid MacroAssembler::Call(Register target, Condition cond) { 66b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // Block constant pool for the call instruction sequence. 67b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org BlockConstPoolScope block_const_pool(this); 684f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Label start; 694f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org bind(&start); 7043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen blx(target, cond); 714f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org ASSERT_EQ(CallSize(target, cond), SizeOfCodeGeneratedSince(&start)); 7243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 7343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 7443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 75b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.orgint MacroAssembler::CallSize( 764f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Address target, RelocInfo::Mode rmode, Condition cond) { 77b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org int size = 2 * kInstrSize; 78b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org Instr mov_instr = cond | MOV | LeaveCC; 794f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org intptr_t immediate = reinterpret_cast<intptr_t>(target); 80874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org if (!Operand(immediate, rmode).is_single_instruction(this, mov_instr)) { 81471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org size += kInstrSize; 82471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org } 83471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org return size; 84471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org} 85471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 86471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org 879e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.orgint MacroAssembler::CallStubSize( 889e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org CodeStub* stub, TypeFeedbackId ast_id, Condition cond) { 89f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org return CallSize(stub->GetCode(), RelocInfo::CODE_TARGET, ast_id, cond); 909e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org} 919e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org 929e41f9ecf5042292a9efcb36e264b37621199553machenbach@chromium.org 93a86d416fb652b1936026eee315eccd4f17ca1002machenbach@chromium.orgint MacroAssembler::CallSizeNotPredictableCodeSize(Isolate* isolate, 94a86d416fb652b1936026eee315eccd4f17ca1002machenbach@chromium.org Address target, 95a86d416fb652b1936026eee315eccd4f17ca1002machenbach@chromium.org RelocInfo::Mode rmode, 96a86d416fb652b1936026eee315eccd4f17ca1002machenbach@chromium.org Condition cond) { 97471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org int size = 2 * kInstrSize; 98471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org Instr mov_instr = cond | MOV | LeaveCC; 99471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org intptr_t immediate = reinterpret_cast<intptr_t>(target); 100874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org if (!Operand(immediate, rmode).is_single_instruction(NULL, mov_instr)) { 101b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org size += kInstrSize; 102b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org } 103b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org return size; 104b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org} 105b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org 106b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org 1074f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.orgvoid MacroAssembler::Call(Address target, 1088e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org RelocInfo::Mode rmode, 10989e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org Condition cond, 11089e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org TargetAddressStorageMode mode) { 111b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // Block constant pool for the call instruction sequence. 112b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org BlockConstPoolScope block_const_pool(this); 1134f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Label start; 1144f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org bind(&start); 11589e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org 11689e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org bool old_predictable_code_size = predictable_code_size(); 11789e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org if (mode == NEVER_INLINE_TARGET_ADDRESS) { 11889e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org set_predictable_code_size(true); 11989e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org } 12089e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org 121763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org#ifdef DEBUG 122763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org // Check the expected size before generating code to ensure we assume the same 123763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org // constant pool availability (e.g., whether constant pool is full or not). 124763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org int expected_size = CallSize(target, rmode, cond); 125763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org#endif 126763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org 12789e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // Call sequence on V7 or later may be : 12889e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // movw ip, #... @ call address low 16 12989e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // movt ip, #... @ call address high 16 13089e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // blx ip 13189e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // @ return address 13289e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // Or for pre-V7 or values that may be back-patched 13389e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // to avoid ICache flushes: 13489e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // ldr ip, [pc, #...] @ call address 13589e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // blx ip 13689e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org // @ return address 137cec079d8ed1f0920a0ea3dc9a3e81966013287c1whesse@chromium.org 138b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // Statement positions are expected to be recorded when the target 139b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // address is loaded. The mov method will automatically record 140b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // positions when pc is the target, since this is not the case here 141b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org // we have to do it explicitly. 142b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org positions_recorder()->WriteRecordedPositions(); 143b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org 1444f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org mov(ip, Operand(reinterpret_cast<int32_t>(target), rmode)); 145b08986cb66c3f6687247cb6da186c1e73057e399whesse@chromium.org blx(ip, cond); 146cec079d8ed1f0920a0ea3dc9a3e81966013287c1whesse@chromium.org 147763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org ASSERT_EQ(expected_size, SizeOfCodeGeneratedSince(&start)); 14889e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org if (mode == NEVER_INLINE_TARGET_ADDRESS) { 14989e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org set_predictable_code_size(old_predictable_code_size); 15089e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org } 15143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 15243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 15343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1544f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.orgint MacroAssembler::CallSize(Handle<Code> code, 1554f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org RelocInfo::Mode rmode, 156471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org TypeFeedbackId ast_id, 1574f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Condition cond) { 15879e7902fa5f94747b5383dd40f3002dd8b62303arossberg@chromium.org AllowDeferredHandleDereference using_raw_address; 1594f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org return CallSize(reinterpret_cast<Address>(code.location()), rmode, cond); 1608e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 1618e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 1628e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 1638e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgvoid MacroAssembler::Call(Handle<Code> code, 1648e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org RelocInfo::Mode rmode, 165471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org TypeFeedbackId ast_id, 16689e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org Condition cond, 16789e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org TargetAddressStorageMode mode) { 1684f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Label start; 1694f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org bind(&start); 170236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org ASSERT(RelocInfo::IsCodeTarget(rmode)); 171471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (rmode == RelocInfo::CODE_TARGET && !ast_id.IsNone()) { 172717967fd64e99e759ff094df6f069440cc866266rossberg@chromium.org SetRecordedAstId(ast_id); 1734f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org rmode = RelocInfo::CODE_TARGET_WITH_ID; 1744f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org } 17543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // 'code' is always generated ARM code, never THUMB code 17679e7902fa5f94747b5383dd40f3002dd8b62303arossberg@chromium.org AllowDeferredHandleDereference embedding_raw_address; 17789e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org Call(reinterpret_cast<Address>(code.location()), rmode, cond, mode); 17843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 17943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 18043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 18165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgvoid MacroAssembler::Ret(Condition cond) { 18265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org bx(lr, cond); 18343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 18443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 18543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1860c20e676f8a0209982ff89e5a9c707771748a585fschneider@chromium.orgvoid MacroAssembler::Drop(int count, Condition cond) { 1870c20e676f8a0209982ff89e5a9c707771748a585fschneider@chromium.org if (count > 0) { 1880c20e676f8a0209982ff89e5a9c707771748a585fschneider@chromium.org add(sp, sp, Operand(count * kPointerSize), LeaveCC, cond); 18913bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org } 19013bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org} 19113bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 19213bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 193023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.orgvoid MacroAssembler::Ret(int drop, Condition cond) { 194023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Drop(drop, cond); 195023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Ret(cond); 196023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org} 197023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 198023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 19930ce411529579186181838984710b0b0980857aaricow@chromium.orgvoid MacroAssembler::Swap(Register reg1, 20030ce411529579186181838984710b0b0980857aaricow@chromium.org Register reg2, 20130ce411529579186181838984710b0b0980857aaricow@chromium.org Register scratch, 20230ce411529579186181838984710b0b0980857aaricow@chromium.org Condition cond) { 203357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org if (scratch.is(no_reg)) { 20430ce411529579186181838984710b0b0980857aaricow@chromium.org eor(reg1, reg1, Operand(reg2), LeaveCC, cond); 20530ce411529579186181838984710b0b0980857aaricow@chromium.org eor(reg2, reg2, Operand(reg1), LeaveCC, cond); 20630ce411529579186181838984710b0b0980857aaricow@chromium.org eor(reg1, reg1, Operand(reg2), LeaveCC, cond); 207357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } else { 20830ce411529579186181838984710b0b0980857aaricow@chromium.org mov(scratch, reg1, LeaveCC, cond); 20930ce411529579186181838984710b0b0980857aaricow@chromium.org mov(reg1, reg2, LeaveCC, cond); 21030ce411529579186181838984710b0b0980857aaricow@chromium.org mov(reg2, scratch, LeaveCC, cond); 211357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } 212357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org} 213357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 214357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 21513bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.orgvoid MacroAssembler::Call(Label* target) { 21613bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org bl(target); 21713bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org} 21813bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 21913bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 2206d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.orgvoid MacroAssembler::Push(Handle<Object> handle) { 2216d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org mov(ip, Operand(handle)); 2226d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org push(ip); 2236d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org} 2246d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org 2256d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org 22613bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.orgvoid MacroAssembler::Move(Register dst, Handle<Object> value) { 227e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org AllowDeferredHandleDereference smi_check; 228e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org if (value->IsSmi()) { 229e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org mov(dst, Operand(value)); 230e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org } else { 231e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org ASSERT(value->IsHeapObject()); 232e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org if (isolate()->heap()->InNewSpace(*value)) { 233e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org Handle<Cell> cell = isolate()->factory()->NewCell(value); 234e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org mov(dst, Operand(cell)); 235e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org ldr(dst, FieldMemOperand(dst, Cell::kValueOffset)); 236e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org } else { 237e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org mov(dst, Operand(value)); 238e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org } 239e94b5ff1e1e95fb2c8ef6bce66ce8533786d9792bmeurer@chromium.org } 24013bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org} 241ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 242ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 2433cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.orgvoid MacroAssembler::Move(Register dst, Register src, Condition cond) { 244357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org if (!dst.is(src)) { 2453cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org mov(dst, src, LeaveCC, cond); 246357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } 247357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org} 248357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 249357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 250a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.orgvoid MacroAssembler::Move(DwVfpRegister dst, DwVfpRegister src) { 2518e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org if (!dst.is(src)) { 2528e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org vmov(dst, src); 2538e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 2548e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 2558e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 2568e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 25770d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.orgvoid MacroAssembler::Mls(Register dst, Register src1, Register src2, 25870d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org Register srcA, Condition cond) { 25970d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org if (CpuFeatures::IsSupported(MLS)) { 26070d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org CpuFeatureScope scope(this, MLS); 26170d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org mls(dst, src1, src2, srcA, cond); 26270d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org } else { 26370d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org ASSERT(!dst.is(srcA)); 26470d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org mul(ip, src1, src2, LeaveCC, cond); 26570d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org sub(dst, srcA, ip, LeaveCC, cond); 26670d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org } 26770d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org} 26870d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org 26970d11c79c7833b9ab1ee185625fcf707b9480a40machenbach@chromium.org 2702c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.orgvoid MacroAssembler::And(Register dst, Register src1, const Operand& src2, 2712c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org Condition cond) { 272f0ac72dfa39ec827de605aafc57d4834237aa7f3whesse@chromium.org if (!src2.is_reg() && 273874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org !src2.must_output_reloc_info(this) && 274f0ac72dfa39ec827de605aafc57d4834237aa7f3whesse@chromium.org src2.immediate() == 0) { 27559297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(dst, Operand::Zero(), LeaveCC, cond); 276874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org } else if (!src2.is_single_instruction(this) && 277874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org !src2.must_output_reloc_info(this) && 278c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org CpuFeatures::IsSupported(ARMv7) && 279f0ac72dfa39ec827de605aafc57d4834237aa7f3whesse@chromium.org IsPowerOf2(src2.immediate() + 1)) { 280d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com ubfx(dst, src1, 0, 281d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com WhichPowerOf2(static_cast<uint32_t>(src2.immediate()) + 1), cond); 282f0ac72dfa39ec827de605aafc57d4834237aa7f3whesse@chromium.org } else { 283f0ac72dfa39ec827de605aafc57d4834237aa7f3whesse@chromium.org and_(dst, src1, src2, LeaveCC, cond); 2842c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 2852c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org} 2862c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 2872c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 2882c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.orgvoid MacroAssembler::Ubfx(Register dst, Register src1, int lsb, int width, 2892c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org Condition cond) { 2902c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org ASSERT(lsb < 32); 291471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (!CpuFeatures::IsSupported(ARMv7) || predictable_code_size()) { 2922c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org int mask = (1 << (width + lsb)) - 1 - ((1 << lsb) - 1); 2932c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org and_(dst, src1, Operand(mask), LeaveCC, cond); 2942c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org if (lsb != 0) { 2952c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org mov(dst, Operand(dst, LSR, lsb), LeaveCC, cond); 2962c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 2972c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } else { 2982c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org ubfx(dst, src1, lsb, width, cond); 2992c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 3002c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org} 3012c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 3022c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 3032c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.orgvoid MacroAssembler::Sbfx(Register dst, Register src1, int lsb, int width, 3042c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org Condition cond) { 3052c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org ASSERT(lsb < 32); 306471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (!CpuFeatures::IsSupported(ARMv7) || predictable_code_size()) { 3072c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org int mask = (1 << (width + lsb)) - 1 - ((1 << lsb) - 1); 3082c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org and_(dst, src1, Operand(mask), LeaveCC, cond); 3092c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org int shift_up = 32 - lsb - width; 3102c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org int shift_down = lsb + shift_up; 3112c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org if (shift_up != 0) { 3122c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org mov(dst, Operand(dst, LSL, shift_up), LeaveCC, cond); 3132c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 3142c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org if (shift_down != 0) { 3152c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org mov(dst, Operand(dst, ASR, shift_down), LeaveCC, cond); 3162c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 3172c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } else { 3182c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org sbfx(dst, src1, lsb, width, cond); 3192c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org } 3202c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org} 3212c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 3222c186ca6690a1cb19ec7584e71f167234587c87cwhesse@chromium.org 3239ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.orgvoid MacroAssembler::Bfi(Register dst, 3249ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Register src, 3259ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Register scratch, 3269ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org int lsb, 3279ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org int width, 3289ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Condition cond) { 3299ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ASSERT(0 <= lsb && lsb < 32); 3309ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ASSERT(0 <= width && width < 32); 3319ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ASSERT(lsb + width < 32); 3329ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ASSERT(!scratch.is(dst)); 3339ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org if (width == 0) return; 334471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (!CpuFeatures::IsSupported(ARMv7) || predictable_code_size()) { 3359ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org int mask = (1 << (width + lsb)) - 1 - ((1 << lsb) - 1); 3369ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bic(dst, dst, Operand(mask)); 3379ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org and_(scratch, src, Operand((1 << width) - 1)); 3389ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org mov(scratch, Operand(scratch, LSL, lsb)); 3399ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org orr(dst, dst, scratch); 3409ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org } else { 3419ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bfi(dst, src, lsb, width, cond); 3429ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org } 3439ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org} 3449ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 3459ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 34633e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.orgvoid MacroAssembler::Bfc(Register dst, Register src, int lsb, int width, 34733e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org Condition cond) { 3485ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org ASSERT(lsb < 32); 349471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (!CpuFeatures::IsSupported(ARMv7) || predictable_code_size()) { 3505ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org int mask = (1 << (width + lsb)) - 1 - ((1 << lsb) - 1); 35133e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org bic(dst, src, Operand(mask)); 3525ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org } else { 35333e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org Move(dst, src, cond); 3545ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org bfc(dst, lsb, width, cond); 3555ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org } 3565ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org} 3575ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org 3585ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org 359ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.orgvoid MacroAssembler::Usat(Register dst, int satpos, const Operand& src, 360ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org Condition cond) { 361471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (!CpuFeatures::IsSupported(ARMv7) || predictable_code_size()) { 362ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org ASSERT(!dst.is(pc) && !src.rm().is(pc)); 363ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org ASSERT((satpos >= 0) && (satpos <= 31)); 364ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org 365ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org // These asserts are required to ensure compatibility with the ARMv7 366ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org // implementation. 367ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org ASSERT((src.shift_op() == ASR) || (src.shift_op() == LSL)); 368ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org ASSERT(src.rs().is(no_reg)); 369ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org 370ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org Label done; 371ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org int satval = (1 << satpos) - 1; 372ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org 373ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org if (cond != al) { 374ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org b(NegateCondition(cond), &done); // Skip saturate if !condition. 375ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org } 376ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org if (!(src.is_reg() && dst.is(src.rm()))) { 377ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org mov(dst, src); 378ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org } 379ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org tst(dst, Operand(~satval)); 380ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org b(eq, &done); 38159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(dst, Operand::Zero(), LeaveCC, mi); // 0 if negative. 382ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org mov(dst, Operand(satval), LeaveCC, pl); // satval if positive. 383ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org bind(&done); 384ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org } else { 385ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org usat(dst, satpos, src, cond); 386ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org } 387ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org} 388ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org 389ed78ffdee6ea4f4f94420b464e7377b610fdac2ffschneider@chromium.org 390935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.orgvoid MacroAssembler::Load(Register dst, 391935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org const MemOperand& src, 392935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org Representation r) { 393935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ASSERT(!r.IsDouble()); 394935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org if (r.IsInteger8()) { 395935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ldrsb(dst, src); 396935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else if (r.IsUInteger8()) { 397935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ldrb(dst, src); 398935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else if (r.IsInteger16()) { 399935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ldrsh(dst, src); 400935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else if (r.IsUInteger16()) { 401935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ldrh(dst, src); 402935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else { 403935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ldr(dst, src); 404935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } 405935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org} 406935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org 407935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org 408935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.orgvoid MacroAssembler::Store(Register src, 409935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org const MemOperand& dst, 410935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org Representation r) { 411935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org ASSERT(!r.IsDouble()); 412935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org if (r.IsInteger8() || r.IsUInteger8()) { 413935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org strb(src, dst); 414935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else if (r.IsInteger16() || r.IsUInteger16()) { 415935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org strh(src, dst); 416935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } else { 417d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org if (r.IsHeapObject()) { 418d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org AssertNotSmi(src); 419d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org } else if (r.IsSmi()) { 420d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org AssertSmi(src); 421d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org } 422935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org str(src, dst); 423935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org } 424935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org} 425935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org 426935a7790c70d49e252069bc2d34eaa72f8c6677fmachenbach@chromium.org 427ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.orgvoid MacroAssembler::LoadRoot(Register destination, 428ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org Heap::RootListIndex index, 429ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org Condition cond) { 430e4ac3ef2f6fa9300bc78c5a4cb7d4cb66ac6e83dmvstanton@chromium.org if (CpuFeatures::IsSupported(MOVW_MOVT_IMMEDIATE_LOADS) && 431594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org isolate()->heap()->RootCanBeTreatedAsConstant(index) && 432fae3da58258d606d4832dc69aca191cfc006a3d6ulan@chromium.org !predictable_code_size()) { 433594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org // The CPU supports fast immediate values, and this root will never 434594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org // change. We will load it as a relocatable immediate value. 435594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Handle<Object> root(&isolate()->heap()->roots_array_start()[index]); 436594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org mov(destination, Operand(root), LeaveCC, cond); 437594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org return; 438e4ac3ef2f6fa9300bc78c5a4cb7d4cb66ac6e83dmvstanton@chromium.org } 439f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com ldr(destination, MemOperand(kRootRegister, index << kPointerSizeLog2), cond); 440ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org} 441ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org 442ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org 443720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.orgvoid MacroAssembler::StoreRoot(Register source, 444720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org Heap::RootListIndex index, 445720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org Condition cond) { 446f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com str(source, MemOperand(kRootRegister, index << kPointerSizeLog2), cond); 447720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org} 448720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org 449720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org 450ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.orgvoid MacroAssembler::InNewSpace(Register object, 451ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Register scratch, 452378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Condition cond, 453ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Label* branch) { 454378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org ASSERT(cond == eq || cond == ne); 455ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org and_(scratch, object, Operand(ExternalReference::new_space_mask(isolate()))); 456ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org cmp(scratch, Operand(ExternalReference::new_space_start(isolate()))); 457378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org b(cond, branch); 458ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org} 459ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 460ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 461c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::RecordWriteField( 462c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register object, 463c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int offset, 464c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register value, 465c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register dst, 466c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com LinkRegisterStatus lr_status, 467c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com SaveFPRegsMode save_fp, 468c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com RememberedSetAction remembered_set_action, 469196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org SmiCheck smi_check, 470196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org PointersToHereCheck pointers_to_here_check_for_value) { 471c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // First, check if a write barrier is even needed. The tests below 472c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // catch stores of Smis. 473ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Label done; 474ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 475c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Skip barrier if writing a smi. 476c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (smi_check == INLINE_SMI_CHECK) { 477c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com JumpIfSmi(value, &done); 478c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 479ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 480c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Although the object register is tagged, the offset is relative to the start 481c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // of the object, so so offset must be a multiple of kPointerSize. 482c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(IsAligned(offset, kPointerSize)); 48369ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 484c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com add(dst, object, Operand(offset - kHeapObjectTag)); 485c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (emit_debug_code()) { 486c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label ok; 487c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(dst, Operand((1 << kPointerSizeLog2) - 1)); 488c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &ok); 489c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com stop("Unaligned cell in write barrier"); 490c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&ok); 491c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 492c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 493c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com RecordWrite(object, 494c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com dst, 495c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com value, 496c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com lr_status, 497c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com save_fp, 498c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com remembered_set_action, 499196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org OMIT_SMI_CHECK, 500196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org pointers_to_here_check_for_value); 50143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 50243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bind(&done); 503b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org 504c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Clobber clobbered input registers when running with the debug-code flag 505b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // turned on to provoke errors. 506badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 507c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(value, Operand(BitCast<int32_t>(kZapValue + 4))); 508c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(dst, Operand(BitCast<int32_t>(kZapValue + 8))); 509b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org } 51043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 51143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 51243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 513196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org// Will clobber 4 registers: object, map, dst, ip. The 514196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org// register 'object' contains a heap object pointer. 515196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.orgvoid MacroAssembler::RecordWriteForMap(Register object, 516196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Register map, 517196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Register dst, 518196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org LinkRegisterStatus lr_status, 519196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org SaveFPRegsMode fp_mode) { 520196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (emit_debug_code()) { 521196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org ldr(dst, FieldMemOperand(map, HeapObject::kMapOffset)); 522196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org cmp(dst, Operand(isolate()->factory()->meta_map())); 523196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Check(eq, kWrongAddressOrValuePassedToRecordWrite); 524196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 525196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 526196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (!FLAG_incremental_marking) { 527196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org return; 528196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 529196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 530196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // Count number of write barriers in generated code. 531196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org isolate()->counters()->write_barriers_static()->Increment(); 532196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // TODO(mstarzinger): Dynamic counter missing. 533196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 534196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (emit_debug_code()) { 535196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org ldr(ip, FieldMemOperand(object, HeapObject::kMapOffset)); 536196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org cmp(ip, map); 537196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Check(eq, kWrongAddressOrValuePassedToRecordWrite); 538196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 539196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 540196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Label done; 541196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 542196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // A single check of the map's pages interesting flag suffices, since it is 543196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // only set during incremental collection, and then it's also guaranteed that 544196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // the from object's page's interesting flag is also set. This optimization 545196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // relies on the fact that maps can never be in new space. 546196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org CheckPageFlag(map, 547196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org map, // Used as scratch. 548196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org MemoryChunk::kPointersToHereAreInterestingMask, 549196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org eq, 550196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org &done); 551196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 552196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org add(dst, object, Operand(HeapObject::kMapOffset - kHeapObjectTag)); 553196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (emit_debug_code()) { 554196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Label ok; 555196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org tst(dst, Operand((1 << kPointerSizeLog2) - 1)); 556196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org b(eq, &ok); 557196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org stop("Unaligned cell in write barrier"); 558196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org bind(&ok); 559196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 560196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 561196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // Record the actual write. 562196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (lr_status == kLRHasNotBeenSaved) { 563196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org push(lr); 564196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 565196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org RecordWriteStub stub(isolate(), object, map, dst, OMIT_REMEMBERED_SET, 566196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org fp_mode); 567196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org CallStub(&stub); 568196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (lr_status == kLRHasNotBeenSaved) { 569196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org pop(lr); 570196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 571196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 572196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org bind(&done); 573196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 574196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // Clobber clobbered registers when running with the debug-code flag 575196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org // turned on to provoke errors. 576196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (emit_debug_code()) { 577196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org mov(dst, Operand(BitCast<int32_t>(kZapValue + 12))); 578196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org mov(map, Operand(BitCast<int32_t>(kZapValue + 16))); 579196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 580196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org} 581196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 582196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 58369ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org// Will clobber 4 registers: object, address, scratch, ip. The 58469ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org// register 'object' contains a heap object pointer. The heap object 58569ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org// tag is shifted away. 586196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.orgvoid MacroAssembler::RecordWrite( 587196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Register object, 588196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Register address, 589196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org Register value, 590196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org LinkRegisterStatus lr_status, 591196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org SaveFPRegsMode fp_mode, 592196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org RememberedSetAction remembered_set_action, 593196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org SmiCheck smi_check, 594196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org PointersToHereCheck pointers_to_here_check_for_value) { 5958297530cd2b71ba1a2fe6f27ba1c030a20468306machenbach@chromium.org ASSERT(!object.is(value)); 596f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com if (emit_debug_code()) { 5972c4567981e65b51f161283f8635e110a73629c9ddanno@chromium.org ldr(ip, MemOperand(address)); 5982c4567981e65b51f161283f8635e110a73629c9ddanno@chromium.org cmp(ip, value); 599594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kWrongAddressOrValuePassedToRecordWrite); 6002c4567981e65b51f161283f8635e110a73629c9ddanno@chromium.org } 6012c4567981e65b51f161283f8635e110a73629c9ddanno@chromium.org 602196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (remembered_set_action == OMIT_REMEMBERED_SET && 603196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org !FLAG_incremental_marking) { 604196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org return; 605196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 606196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org 607f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org // Count number of write barriers in generated code. 608f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org isolate()->counters()->write_barriers_static()->Increment(); 609f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org // TODO(mstarzinger): Dynamic counter missing. 610f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org 611f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org // First, check if a write barrier is even needed. The tests below 612f9841897146bc10dbb3c45f0632bb79254602c75machenbach@chromium.org // catch stores of smis and stores into the young generation. 61369ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org Label done; 61469ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 615c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (smi_check == INLINE_SMI_CHECK) { 616bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org JumpIfSmi(value, &done); 617c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 618c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 619196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org if (pointers_to_here_check_for_value != kPointersToHereAreAlwaysInteresting) { 620196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org CheckPageFlag(value, 621196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org value, // Used as scratch. 622196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org MemoryChunk::kPointersToHereAreInterestingMask, 623196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org eq, 624196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org &done); 625196eb601290dc49c3754da728dc58700dff2de1bmachenbach@chromium.org } 626c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CheckPageFlag(object, 627c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com value, // Used as scratch. 628c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com MemoryChunk::kPointersFromHereAreInterestingMask, 629c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com eq, 630c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com &done); 63169ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 63269ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org // Record the actual write. 633c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (lr_status == kLRHasNotBeenSaved) { 634c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com push(lr); 635c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 636f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org RecordWriteStub stub(isolate(), object, value, address, remembered_set_action, 637f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org fp_mode); 638c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CallStub(&stub); 639c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (lr_status == kLRHasNotBeenSaved) { 640c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com pop(lr); 641c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 64269ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 64369ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org bind(&done); 64469ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 645c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Clobber clobbered registers when running with the debug-code flag 64669ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org // turned on to provoke errors. 647badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 648c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(address, Operand(BitCast<int32_t>(kZapValue + 12))); 649c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(value, Operand(BitCast<int32_t>(kZapValue + 16))); 650c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 651c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 652c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 653c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 654c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::RememberedSetHelper(Register object, // For debug tests. 655c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register address, 656c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch, 657c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com SaveFPRegsMode fp_mode, 658c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com RememberedSetFinalAction and_then) { 659c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label done; 660f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com if (emit_debug_code()) { 661c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label ok; 662c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com JumpIfNotInNewSpace(object, scratch, &ok); 663c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com stop("Remembered set pointer is in new space"); 664c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&ok); 665c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 666c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Load store buffer top. 667c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ExternalReference store_buffer = 668c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ExternalReference::store_buffer_top(isolate()); 669c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(ip, Operand(store_buffer)); 670c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(scratch, MemOperand(ip)); 671c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Store pointer to buffer and increment buffer top. 672c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com str(address, MemOperand(scratch, kPointerSize, PostIndex)); 673c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Write back new top of buffer. 674c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com str(scratch, MemOperand(ip)); 675c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Call stub on end of buffer. 676c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Check for end of buffer. 677c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(scratch, Operand(StoreBuffer::kStoreBufferOverflowBit)); 678c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (and_then == kFallThroughAtEnd) { 679c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &done); 680c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } else { 681c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(and_then == kReturnAtEnd); 682b4b2aa69a9f12525fca190287f47a66d7bdcb3aerossberg@chromium.org Ret(eq); 683c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 684c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com push(lr); 685c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com StoreBufferOverflowStub store_buffer_overflow = 686f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org StoreBufferOverflowStub(isolate(), fp_mode); 687c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CallStub(&store_buffer_overflow); 688c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com pop(lr); 689c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&done); 690c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (and_then == kReturnAtEnd) { 691c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Ret(); 69269ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org } 69369ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org} 69469ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 69569ea3965ef6e0d3f020a402cf7e6b96b9cb651aekmillikin@chromium.org 6969ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.orgvoid MacroAssembler::PushFixedFrame(Register marker_reg) { 6979ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ASSERT(!marker_reg.is_valid() || marker_reg.code() < cp.code()); 6989ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org stm(db_w, sp, (marker_reg.is_valid() ? marker_reg.bit() : 0) | 6999ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org cp.bit() | 7009ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org (FLAG_enable_ool_constant_pool ? pp.bit() : 0) | 7019ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org fp.bit() | 7029ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org lr.bit()); 7039ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org} 7049ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 7059ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 7069ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.orgvoid MacroAssembler::PopFixedFrame(Register marker_reg) { 7079ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ASSERT(!marker_reg.is_valid() || marker_reg.code() < cp.code()); 7089ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ldm(ia_w, sp, (marker_reg.is_valid() ? marker_reg.bit() : 0) | 7099ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org cp.bit() | 7109ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org (FLAG_enable_ool_constant_pool ? pp.bit() : 0) | 7119ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org fp.bit() | 7129ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org lr.bit()); 7139ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org} 7149ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 7159ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 716a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org// Push and pop all registers that can hold pointers. 717a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.orgvoid MacroAssembler::PushSafepointRegisters() { 718a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Safepoints expect a block of contiguous register values starting with r0: 719a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(((1 << kNumSafepointSavedRegisters) - 1) == kSafepointSavedRegisters); 720a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Safepoints expect a block of kNumSafepointRegisters values on the 721a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // stack, so adjust the stack for unsaved registers. 722a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org const int num_unsaved = kNumSafepointRegisters - kNumSafepointSavedRegisters; 723a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(num_unsaved >= 0); 724a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org sub(sp, sp, Operand(num_unsaved * kPointerSize)); 725a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org stm(db_w, sp, kSafepointSavedRegisters); 726a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org} 727a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 728a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 729a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.orgvoid MacroAssembler::PopSafepointRegisters() { 730a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org const int num_unsaved = kNumSafepointRegisters - kNumSafepointSavedRegisters; 731a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldm(ia_w, sp, kSafepointSavedRegisters); 732a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org add(sp, sp, Operand(num_unsaved * kPointerSize)); 733a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org} 734a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 735a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 736c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::PushSafepointRegistersAndDoubles() { 737003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org // Number of d-regs not known at snapshot time. 738874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org ASSERT(!serializer_enabled()); 739c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org PushSafepointRegisters(); 740af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org // Only save allocatable registers. 741af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org ASSERT(kScratchDoubleReg.is(d15) && kDoubleRegZero.is(d14)); 742af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org ASSERT(DwVfpRegister::NumReservedRegisters() == 2); 743af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org if (CpuFeatures::IsSupported(VFP32DREGS)) { 744af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org vstm(db_w, sp, d16, d31); 745c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org } 746af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org vstm(db_w, sp, d0, d13); 747c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org} 748c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 749c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 750c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::PopSafepointRegistersAndDoubles() { 751003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org // Number of d-regs not known at snapshot time. 752874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org ASSERT(!serializer_enabled()); 753af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org // Only save allocatable registers. 754af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org ASSERT(kScratchDoubleReg.is(d15) && kDoubleRegZero.is(d14)); 755af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org ASSERT(DwVfpRegister::NumReservedRegisters() == 2); 756af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org vldm(ia_w, sp, d0, d13); 757af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org if (CpuFeatures::IsSupported(VFP32DREGS)) { 758af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org vldm(ia_w, sp, d16, d31); 759c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org } 760c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org PopSafepointRegisters(); 761c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org} 762c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 7633a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.orgvoid MacroAssembler::StoreToSafepointRegistersAndDoublesSlot(Register src, 7643a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org Register dst) { 7653a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org str(src, SafepointRegistersAndDoublesSlot(dst)); 7667a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org} 7677a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 7687a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 7693a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.orgvoid MacroAssembler::StoreToSafepointRegisterSlot(Register src, Register dst) { 7703a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org str(src, SafepointRegisterSlot(dst)); 7710a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org} 7720a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 7730a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 7743a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.orgvoid MacroAssembler::LoadFromSafepointRegisterSlot(Register dst, Register src) { 7753a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org ldr(dst, SafepointRegisterSlot(src)); 7767a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org} 7777a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 7787a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 779a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.orgint MacroAssembler::SafepointRegisterStackIndex(int reg_code) { 780a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // The registers are pushed starting with the highest encoding, 781a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // which means that lowest encodings are closest to the stack pointer. 782a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(reg_code >= 0 && reg_code < kNumSafepointRegisters); 783a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org return reg_code; 784a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org} 785a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 786a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 7870a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.orgMemOperand MacroAssembler::SafepointRegisterSlot(Register reg) { 7880a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org return MemOperand(sp, SafepointRegisterStackIndex(reg.code()) * kPointerSize); 7890a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org} 7900a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 7910a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 7927a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.orgMemOperand MacroAssembler::SafepointRegistersAndDoublesSlot(Register reg) { 793003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org // Number of d-regs not known at snapshot time. 794874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org ASSERT(!serializer_enabled()); 7957a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org // General purpose registers are pushed last on the stack. 796a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.org int doubles_size = DwVfpRegister::NumAllocatableRegisters() * kDoubleSize; 7977a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org int register_offset = SafepointRegisterStackIndex(reg.code()) * kPointerSize; 7987a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org return MemOperand(sp, doubles_size + register_offset); 7997a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org} 8007a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 8017a392b3bfb39dbbc1ff22f0b53109aa5763fde57whesse@chromium.org 8029155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.orgvoid MacroAssembler::Ldrd(Register dst1, Register dst2, 8039155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org const MemOperand& src, Condition cond) { 8049155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org ASSERT(src.rm().is(no_reg)); 8059155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org ASSERT(!dst1.is(lr)); // r14. 8069155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 80704921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org // V8 does not use this addressing mode, so the fallback code 80804921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org // below doesn't support it yet. 80904921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ASSERT((src.am() != PreIndex) && (src.am() != NegPreIndex)); 81004921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org 8119155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org // Generate two ldr instructions if ldrd is not available. 812f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org if (CpuFeatures::IsSupported(ARMv7) && !predictable_code_size() && 813f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org (dst1.code() % 2 == 0) && (dst1.code() + 1 == dst2.code())) { 814750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org CpuFeatureScope scope(this, ARMv7); 8159155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org ldrd(dst1, dst2, src, cond); 8169155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org } else { 81704921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org if ((src.am() == Offset) || (src.am() == NegOffset)) { 81804921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org MemOperand src2(src); 81904921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org src2.set_offset(src2.offset() + 4); 82004921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org if (dst1.is(src.rn())) { 82104921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst2, src2, cond); 82204921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst1, src, cond); 82304921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } else { 82404921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst1, src, cond); 82504921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst2, src2, cond); 82604921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } 82704921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } else { // PostIndex or NegPostIndex. 82804921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ASSERT((src.am() == PostIndex) || (src.am() == NegPostIndex)); 82904921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org if (dst1.is(src.rn())) { 83004921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst2, MemOperand(src.rn(), 4, Offset), cond); 83104921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst1, src, cond); 83204921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } else { 83304921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org MemOperand src2(src); 83404921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org src2.set_offset(src2.offset() - 4); 83504921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst1, MemOperand(src.rn(), 4, PostIndex), cond); 83604921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ldr(dst2, src2, cond); 83704921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } 8389155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org } 8399155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org } 8409155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org} 8419155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 8429155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 8439155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.orgvoid MacroAssembler::Strd(Register src1, Register src2, 8449155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org const MemOperand& dst, Condition cond) { 8459155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org ASSERT(dst.rm().is(no_reg)); 8469155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org ASSERT(!src1.is(lr)); // r14. 8479155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 84804921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org // V8 does not use this addressing mode, so the fallback code 84904921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org // below doesn't support it yet. 85004921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ASSERT((dst.am() != PreIndex) && (dst.am() != NegPreIndex)); 85104921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org 8529155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org // Generate two str instructions if strd is not available. 853f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org if (CpuFeatures::IsSupported(ARMv7) && !predictable_code_size() && 854f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org (src1.code() % 2 == 0) && (src1.code() + 1 == src2.code())) { 855750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org CpuFeatureScope scope(this, ARMv7); 8569155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org strd(src1, src2, dst, cond); 8579155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org } else { 8589155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org MemOperand dst2(dst); 85904921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org if ((dst.am() == Offset) || (dst.am() == NegOffset)) { 86004921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org dst2.set_offset(dst2.offset() + 4); 86104921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org str(src1, dst, cond); 86204921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org str(src2, dst2, cond); 86304921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } else { // PostIndex or NegPostIndex. 86404921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org ASSERT((dst.am() == PostIndex) || (dst.am() == NegPostIndex)); 86504921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org dst2.set_offset(dst2.offset() - 4); 86604921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org str(src1, MemOperand(dst.rn(), 4, PostIndex), cond); 86704921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org str(src2, dst2, cond); 86804921a8093ce8bbec34084bd742b7aa3d299be15ager@chromium.org } 8699155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org } 8709155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org} 8719155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 8729155e252524a2bf92aecd27493feafed86702312kmillikin@chromium.org 873e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.orgvoid MacroAssembler::VFPEnsureFPSCRState(Register scratch) { 874e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org // If needed, restore wanted bits of FPSCR. 875e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org Label fpscr_done; 876e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org vmrs(scratch); 877e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org if (emit_debug_code()) { 878e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org Label rounding_mode_correct; 879e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org tst(scratch, Operand(kVFPRoundingModeMask)); 880e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org b(eq, &rounding_mode_correct); 881e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org // Don't call Assert here, since Runtime_Abort could re-enter here. 882e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org stop("Default rounding mode not set"); 883e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org bind(&rounding_mode_correct); 884e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org } 885e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org tst(scratch, Operand(kVFPDefaultNaNModeControlBit)); 886e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org b(ne, &fpscr_done); 887e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org orr(scratch, scratch, Operand(kVFPDefaultNaNModeControlBit)); 888e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org vmsr(scratch); 889e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org bind(&fpscr_done); 890e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org} 891e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org 892528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 893528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.orgvoid MacroAssembler::VFPCanonicalizeNaN(const DwVfpRegister dst, 894528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org const DwVfpRegister src, 895e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org const Condition cond) { 896528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org vsub(dst, src, kDoubleRegZero, cond); 897e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org} 898e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org 899e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org 900c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::VFPCompareAndSetFlags(const DwVfpRegister src1, 901c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const DwVfpRegister src2, 902c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Condition cond) { 903c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org // Compare and move FPSCR flags to the normal condition flags. 904c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org VFPCompareAndLoadFlags(src1, src2, pc, cond); 905c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org} 906c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 907c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::VFPCompareAndSetFlags(const DwVfpRegister src1, 908c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const double src2, 909c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Condition cond) { 910c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org // Compare and move FPSCR flags to the normal condition flags. 911c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org VFPCompareAndLoadFlags(src1, src2, pc, cond); 912c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org} 913c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 914c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 915c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::VFPCompareAndLoadFlags(const DwVfpRegister src1, 916c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const DwVfpRegister src2, 917c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Register fpscr_flags, 918c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Condition cond) { 919c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org // Compare and load FPSCR. 920c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org vcmp(src1, src2, cond); 921c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org vmrs(fpscr_flags, cond); 922c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org} 923c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org 924c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.orgvoid MacroAssembler::VFPCompareAndLoadFlags(const DwVfpRegister src1, 925c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const double src2, 926c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Register fpscr_flags, 927c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org const Condition cond) { 928c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org // Compare and load FPSCR. 929c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org vcmp(src1, src2, cond); 930c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org vmrs(fpscr_flags, cond); 931d2c22f0121ebc55ee26a9e742f0fd7c0b8397730kmillikin@chromium.org} 932d2c22f0121ebc55ee26a9e742f0fd7c0b8397730kmillikin@chromium.org 9333cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.orgvoid MacroAssembler::Vmov(const DwVfpRegister dst, 9343cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org const double imm, 93571fc3467b5396c27d0b701d88e196e88c78d8864mstarzinger@chromium.org const Register scratch) { 9363cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org static const DoubleRepresentation minus_zero(-0.0); 9373cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org static const DoubleRepresentation zero(0.0); 938ea9b8ba58955b7efcc3e1550dd33a44fb4530136hpayer@chromium.org DoubleRepresentation value_rep(imm); 9393cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org // Handle special values first. 940ea9b8ba58955b7efcc3e1550dd33a44fb4530136hpayer@chromium.org if (value_rep == zero) { 94171fc3467b5396c27d0b701d88e196e88c78d8864mstarzinger@chromium.org vmov(dst, kDoubleRegZero); 942ea9b8ba58955b7efcc3e1550dd33a44fb4530136hpayer@chromium.org } else if (value_rep == minus_zero) { 94371fc3467b5396c27d0b701d88e196e88c78d8864mstarzinger@chromium.org vneg(dst, kDoubleRegZero); 9443cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org } else { 94571fc3467b5396c27d0b701d88e196e88c78d8864mstarzinger@chromium.org vmov(dst, imm, scratch); 9463cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org } 9473cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org} 9483cf47318da216c319ecf1f7a59de23455f117197vegorov@chromium.org 949d2c22f0121ebc55ee26a9e742f0fd7c0b8397730kmillikin@chromium.org 950fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::VmovHigh(Register dst, DwVfpRegister src) { 951fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org if (src.code() < 16) { 952fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org const LowDwVfpRegister loc = LowDwVfpRegister::from_code(src.code()); 953fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, loc.high()); 954fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } else { 955fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, VmovIndexHi, src); 956fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } 957fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org} 958fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 959fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 960fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::VmovHigh(DwVfpRegister dst, Register src) { 961fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org if (dst.code() < 16) { 962fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org const LowDwVfpRegister loc = LowDwVfpRegister::from_code(dst.code()); 963fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(loc.high(), src); 964fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } else { 965fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, VmovIndexHi, src); 966fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } 967fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org} 968fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 969fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 970fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::VmovLow(Register dst, DwVfpRegister src) { 971fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org if (src.code() < 16) { 972fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org const LowDwVfpRegister loc = LowDwVfpRegister::from_code(src.code()); 973fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, loc.low()); 974fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } else { 975fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, VmovIndexLo, src); 976fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } 977fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org} 978fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 979fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 980fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::VmovLow(DwVfpRegister dst, Register src) { 981fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org if (dst.code() < 16) { 982fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org const LowDwVfpRegister loc = LowDwVfpRegister::from_code(dst.code()); 983fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(loc.low(), src); 984fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } else { 985fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(dst, VmovIndexLo, src); 986fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org } 987fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org} 988fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 989fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 99097b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.orgvoid MacroAssembler::LoadConstantPoolPointerRegister() { 99197b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org if (FLAG_enable_ool_constant_pool) { 99297b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org int constant_pool_offset = Code::kConstantPoolOffset - Code::kHeaderSize - 99397b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org pc_offset() - Instruction::kPCReadOffset; 99497b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org ASSERT(ImmediateFitsAddrMode2Instruction(constant_pool_offset)); 99597b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org ldr(pp, MemOperand(pc, constant_pool_offset)); 99697b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org } 99797b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org} 99897b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org 99997b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org 1000285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.orgvoid MacroAssembler::StubPrologue() { 1001285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org PushFixedFrame(); 1002285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org Push(Smi::FromInt(StackFrame::STUB)); 1003285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org // Adjust FP to point to saved FP. 1004285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org add(fp, sp, Operand(StandardFrameConstants::kFixedFrameSizeFromFp)); 1005285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org if (FLAG_enable_ool_constant_pool) { 1006285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org LoadConstantPoolPointerRegister(); 1007285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org set_constant_pool_available(true); 1008285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org } 1009285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org} 1010285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org 1011285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.org 1012285f85a5a149f36516a20200a76899651dd95fb6machenbach@chromium.orgvoid MacroAssembler::Prologue(bool code_pre_aging) { 1013874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org { PredictableCodeSizeScope predictible_code_size_scope( 1014874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org this, kNoCodeAgeSequenceLength); 1015874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org // The following three instructions must remain together and unmodified 1016874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org // for code aging to work properly. 1017874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org if (code_pre_aging) { 1018874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org // Pre-age the code. 1019874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org Code* stub = Code::GetPreAgedCodeAgeStub(isolate()); 1020874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org add(r0, pc, Operand(-8)); 1021874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org ldr(pc, MemOperand(pc, -4)); 1022874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org emit_code_stub_address(stub); 1023874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org } else { 1024874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org PushFixedFrame(r1); 1025874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org nop(ip.code()); 1026874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org // Adjust FP to point to saved FP. 1027874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org add(fp, sp, Operand(StandardFrameConstants::kFixedFrameSizeFromFp)); 1028874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org } 1029c9913f099d68d3604e53b19d0fc5abe309143bdcbmeurer@chromium.org } 10309ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org if (FLAG_enable_ool_constant_pool) { 103197b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org LoadConstantPoolPointerRegister(); 103297b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org set_constant_pool_available(true); 10339ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org } 10349ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org} 10359ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 10369ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org 103797b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.orgvoid MacroAssembler::EnterFrame(StackFrame::Type type, 103897b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org bool load_constant_pool) { 1039b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r0-r3: preserved 10409ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org PushFixedFrame(); 104197b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org if (FLAG_enable_ool_constant_pool && load_constant_pool) { 104297b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org LoadConstantPoolPointerRegister(); 104397b98c9169c85693801d4d59089450695ad82e2dmachenbach@chromium.org } 1044b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org mov(ip, Operand(Smi::FromInt(type))); 1045b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org push(ip); 1046061ef74c9b8acd038edf4b4355c50d097c8a9683kasperl@chromium.org mov(ip, Operand(CodeObject())); 1047061ef74c9b8acd038edf4b4355c50d097c8a9683kasperl@chromium.org push(ip); 10487ff7607c2315ea91e4d13330ce14125e4bb4851amachenbach@chromium.org // Adjust FP to point to saved FP. 10497ff7607c2315ea91e4d13330ce14125e4bb4851amachenbach@chromium.org add(fp, sp, 10507ff7607c2315ea91e4d13330ce14125e4bb4851amachenbach@chromium.org Operand(StandardFrameConstants::kFixedFrameSizeFromFp + kPointerSize)); 105143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 105243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 105343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 10549ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.orgint MacroAssembler::LeaveFrame(StackFrame::Type type) { 1055b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r0: preserved 1056b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r1: preserved 1057b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r2: preserved 105843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 10597c537e2abe09729ed6cb827b4dd206470d8c4a42ager@chromium.org // Drop the execution stack down to the frame pointer and restore 10609ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org // the caller frame pointer, return address and constant pool pointer 10619ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org // (if FLAG_enable_ool_constant_pool). 10629ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org int frame_ends; 10639ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org if (FLAG_enable_ool_constant_pool) { 10649ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org add(sp, fp, Operand(StandardFrameConstants::kConstantPoolOffset)); 10659ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org frame_ends = pc_offset(); 10669ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ldm(ia_w, sp, pp.bit() | fp.bit() | lr.bit()); 10679ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org } else { 10689ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org mov(sp, fp); 10699ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org frame_ends = pc_offset(); 10709ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org ldm(ia_w, sp, fp.bit() | lr.bit()); 10719ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org } 10729ca3017c616a778baff6d57c68d6d4746a130036ulan@chromium.org return frame_ends; 107343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 107443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 107543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 107683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.orgvoid MacroAssembler::EnterExitFrame(bool save_doubles, int stack_space) { 1077f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // Set up the frame structure on the stack. 10780ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org ASSERT_EQ(2 * kPointerSize, ExitFrameConstants::kCallerSPDisplacement); 10790ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org ASSERT_EQ(1 * kPointerSize, ExitFrameConstants::kCallerPCOffset); 10800ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org ASSERT_EQ(0 * kPointerSize, ExitFrameConstants::kCallerFPOffset); 10810ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org Push(lr, fp); 1082f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com mov(fp, Operand(sp)); // Set up new frame pointer. 10830ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org // Reserve room for saved entry sp and code object. 10849cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org sub(sp, sp, Operand(ExitFrameConstants::kFrameSize)); 1085badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 108659297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(ip, Operand::Zero()); 10870ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org str(ip, MemOperand(fp, ExitFrameConstants::kSPOffset)); 10880ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org } 10899cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org if (FLAG_enable_ool_constant_pool) { 10909cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org str(pp, MemOperand(fp, ExitFrameConstants::kConstantPoolOffset)); 10919cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org } 10925c838251403b0be9a882540f1922577abba4c872ager@chromium.org mov(ip, Operand(CodeObject())); 10930ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org str(ip, MemOperand(fp, ExitFrameConstants::kCodeOffset)); 1094236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1095236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org // Save the frame pointer and the context in top. 109683e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org mov(ip, Operand(ExternalReference(Isolate::kCEntryFPAddress, isolate()))); 1097236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org str(fp, MemOperand(ip)); 109883e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org mov(ip, Operand(ExternalReference(Isolate::kContextAddress, isolate()))); 1099236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org str(cp, MemOperand(ip)); 1100236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1101a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Optionally save all double registers. 1102a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org if (save_doubles) { 110377ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org SaveFPRegs(sp, ip); 11040ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org // Note that d0 will be accessible at 11059cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org // fp - ExitFrameConstants::kFrameSize - 11069cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org // DwVfpRegister::kMaxNumRegisters * kDoubleSize, 11079cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org // since the sp slot, code slot and constant pool slot (if 11089cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org // FLAG_enable_ool_constant_pool) were pushed after the fp. 1109a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } 11100ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org 111183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // Reserve place for the return address and stack space and align the frame 111283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // preparing for calling the runtime function. 11130ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org const int frame_alignment = MacroAssembler::ActivationFrameAlignment(); 111483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org sub(sp, sp, Operand((stack_space + 1) * kPointerSize)); 11150ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org if (frame_alignment > 0) { 11160ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org ASSERT(IsPowerOf2(frame_alignment)); 11170ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org and_(sp, sp, Operand(-frame_alignment)); 11180ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org } 11190ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org 11200ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org // Set the exit frame sp value to point just before the return address 11210ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org // location. 11220ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org add(ip, sp, Operand(kPointerSize)); 11230ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org str(ip, MemOperand(fp, ExitFrameConstants::kSPOffset)); 1124236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org} 1125236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1126236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1127ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.orgvoid MacroAssembler::InitializeNewString(Register string, 1128ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Register length, 1129ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Heap::RootListIndex map_index, 1130ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Register scratch1, 1131ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Register scratch2) { 1132bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiTag(scratch1, length); 1133ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org LoadRoot(scratch2, map_index); 1134ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org str(scratch1, FieldMemOperand(string, String::kLengthOffset)); 1135ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org mov(scratch1, Operand(String::kEmptyHashField)); 1136ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org str(scratch2, FieldMemOperand(string, HeapObject::kMapOffset)); 1137ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org str(scratch1, FieldMemOperand(string, String::kHashFieldOffset)); 1138ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org} 1139ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 1140ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 1141c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.orgint MacroAssembler::ActivationFrameAlignment() { 114293a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org#if V8_HOST_ARCH_ARM 1143c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // Running on the real platform. Use the alignment as mandated by the local 1144c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // environment. 1145c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // Note: This will break if we ever start generating snapshots on one ARM 1146c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // platform for another ARM platform with a different alignment. 1147c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org return OS::ActivationFrameAlignment(); 114893a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org#else // V8_HOST_ARCH_ARM 1149c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // If we are using the simulator then we should always align to the expected 1150c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org // alignment. As the simulator is used to generate snapshots we do not know 1151c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // if the target platform will need alignment, so this is controlled from a 1152c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // flag. 1153c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org return FLAG_sim_stack_alignment; 115493a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org#endif // V8_HOST_ARCH_ARM 1155c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org} 1156c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org 1157c514574143c1bf74d4fb6e7dccb175fe9ff2f5d3sgjesse@chromium.org 115849edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.orgvoid MacroAssembler::LeaveExitFrame(bool save_doubles, 1159528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register argument_count, 1160528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org bool restore_context) { 1161763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org ConstantPoolUnavailableScope constant_pool_unavailable(this); 1162763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org 1163a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Optionally restore all double registers. 1164a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org if (save_doubles) { 116574f333bce721daf6b1f9d7d3d3faa623f77658d7vegorov@chromium.org // Calculate the stack location of the saved doubles and restore them. 11669cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org const int offset = ExitFrameConstants::kFrameSize; 116794b0d6fcb08a2f01ba52c6edb712068f482366f1danno@chromium.org sub(r3, fp, 116894b0d6fcb08a2f01ba52c6edb712068f482366f1danno@chromium.org Operand(offset + DwVfpRegister::kMaxNumRegisters * kDoubleSize)); 116977ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org RestoreFPRegs(r3, ip); 1170a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } 1171a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 1172236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org // Clear top frame. 117359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(r3, Operand::Zero()); 117483e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org mov(ip, Operand(ExternalReference(Isolate::kCEntryFPAddress, isolate()))); 1175236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org str(r3, MemOperand(ip)); 1176236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1177236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org // Restore current context from top and clear it in debug mode. 1178528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org if (restore_context) { 1179528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org mov(ip, Operand(ExternalReference(Isolate::kContextAddress, isolate()))); 1180528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(cp, MemOperand(ip)); 1181528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org } 11822f877ace3ac6432b1ce44abd553cd3ff97321680hpayer@chromium.org#ifdef DEBUG 1183528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org mov(ip, Operand(ExternalReference(Isolate::kContextAddress, isolate()))); 118465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org str(r3, MemOperand(ip)); 118565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org#endif 1186236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 118749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org // Tear down the exit frame, pop the arguments, and return. 11889cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org if (FLAG_enable_ool_constant_pool) { 11899cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org ldr(pp, MemOperand(fp, ExitFrameConstants::kConstantPoolOffset)); 11909cbaabda8b4daeb06759ace10c926ab55bb69d7bulan@chromium.org } 11910ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org mov(sp, Operand(fp)); 11920ee099beef2c2b38743d657b84a30b626d9178ecager@chromium.org ldm(ia_w, sp, fp.bit() | lr.bit()); 119349edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org if (argument_count.is_valid()) { 119449edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org add(sp, sp, Operand(argument_count, LSL, kPointerSizeLog2)); 119549edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org } 1196236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org} 1197236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 1198e0e1b0d3e70c933d36ed381d511e9fda39f2a751mstarzinger@chromium.org 11994ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.orgvoid MacroAssembler::MovFromFloatResult(const DwVfpRegister dst) { 12008e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org if (use_eabi_hardfloat()) { 12018e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org Move(dst, d0); 12028e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } else { 12038e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org vmov(dst, r0, r1); 12048e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 12053a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org} 12063a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org 1207236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org 12084ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org// On ARM this is just a synonym to make the purpose clear. 12094ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.orgvoid MacroAssembler::MovFromFloatParameter(DwVfpRegister dst) { 12104ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org MovFromFloatResult(dst); 12114ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org} 12124ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org 12134ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org 1214769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.comvoid MacroAssembler::InvokePrologue(const ParameterCount& expected, 1215769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com const ParameterCount& actual, 1216769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com Handle<Code> code_constant, 1217769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com Register code_reg, 1218769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com Label* done, 12192efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org bool* definitely_mismatches, 1220c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org InvokeFlag flag, 1221e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org const CallWrapper& call_wrapper) { 1222b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org bool definitely_matches = false; 12232efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org *definitely_mismatches = false; 1224b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org Label regular_invoke; 1225b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 1226b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // Check whether the expected and actual arguments count match. If not, 1227b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // setup registers according to contract with ArgumentsAdaptorTrampoline: 1228b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r0: actual arguments count 1229b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r1: function (passed through to callee) 1230b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // r2: expected arguments count 1231b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 1232b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // The code below is made a lot easier because the calling code already sets 1233b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // up actual and expected registers according to the contract if values are 1234b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // passed in registers. 1235b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org ASSERT(actual.is_immediate() || actual.reg().is(r0)); 1236b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org ASSERT(expected.is_immediate() || expected.reg().is(r2)); 1237b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org ASSERT((!code_constant.is_null() && code_reg.is(no_reg)) || code_reg.is(r3)); 1238b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 1239b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (expected.is_immediate()) { 1240b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org ASSERT(actual.is_immediate()); 1241b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (expected.immediate() == actual.immediate()) { 1242b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org definitely_matches = true; 1243b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } else { 1244b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org mov(r0, Operand(actual.immediate())); 1245b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org const int sentinel = SharedFunctionInfo::kDontAdaptArgumentsSentinel; 1246b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (expected.immediate() == sentinel) { 1247b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // Don't worry about adapting arguments for builtins that 1248b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // don't want that done. Skip adaption code by making it look 1249b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // like we have a match between expected and actual number of 1250b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org // arguments. 1251b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org definitely_matches = true; 1252b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } else { 12532efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org *definitely_mismatches = true; 1254b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org mov(r2, Operand(expected.immediate())); 1255b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 1256b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 1257769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com } else { 1258b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (actual.is_immediate()) { 1259b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org cmp(expected.reg(), Operand(actual.immediate())); 1260b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org b(eq, ®ular_invoke); 1261b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org mov(r0, Operand(actual.immediate())); 1262b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } else { 1263b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org cmp(expected.reg(), Operand(actual.reg())); 1264b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org b(eq, ®ular_invoke); 1265b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 1266b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 1267b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 1268b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (!definitely_matches) { 1269b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (!code_constant.is_null()) { 1270b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org mov(r3, Operand(code_constant)); 1271b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org add(r3, r3, Operand(Code::kHeaderSize - kHeapObjectTag)); 1272769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com } 1273b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 1274b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org Handle<Code> adaptor = 12757979bbb1df2eaff193e85d44c8da1ffa1525b7fcfschneider@chromium.org isolate()->builtins()->ArgumentsAdaptorTrampoline(); 1276b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org if (flag == CALL_FUNCTION) { 12774f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org call_wrapper.BeforeCall(CallSize(adaptor)); 12784f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org Call(adaptor); 1279fb144a0716afe7ab8bf245f2391a9e53b3db3c89fschneider@chromium.org call_wrapper.AfterCall(); 12802efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org if (!*definitely_mismatches) { 12812efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org b(done); 12822efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org } 1283b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } else { 1284236ad9617a7359a463144a6ebeb5431a70f769cfager@chromium.org Jump(adaptor, RelocInfo::CODE_TARGET); 1285b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 1286b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org bind(®ular_invoke); 1287769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com } 1288769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com} 1289769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1290769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1291769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.comvoid MacroAssembler::InvokeCode(Register code, 1292769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com const ParameterCount& expected, 1293769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com const ParameterCount& actual, 1294c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org InvokeFlag flag, 1295e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org const CallWrapper& call_wrapper) { 1296c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // You can't call a function without a valid frame. 1297c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(flag == JUMP_FUNCTION || has_frame()); 1298c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 1299769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com Label done; 13002efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org bool definitely_mismatches = false; 13012efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org InvokePrologue(expected, actual, Handle<Code>::null(), code, 13022efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org &done, &definitely_mismatches, flag, 1303e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org call_wrapper); 13042efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org if (!definitely_mismatches) { 13052efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org if (flag == CALL_FUNCTION) { 13062efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org call_wrapper.BeforeCall(CallSize(code)); 13072efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org Call(code); 13082efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org call_wrapper.AfterCall(); 13092efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org } else { 13102efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org ASSERT(flag == JUMP_FUNCTION); 13112efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org Jump(code); 13122efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org } 1313769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 13142efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org // Continue here if InvokePrologue does handle the invocation due to 13152efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org // mismatched parameter counts. 13162efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org bind(&done); 13172efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org } 1318769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com} 1319769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1320769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1321769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.comvoid MacroAssembler::InvokeFunction(Register fun, 1322769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com const ParameterCount& actual, 1323c6c5718277d4047fad1e034396228ce15571b5a4sgjesse@chromium.org InvokeFlag flag, 1324e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org const CallWrapper& call_wrapper) { 1325c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // You can't call a function without a valid frame. 1326c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(flag == JUMP_FUNCTION || has_frame()); 1327c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 1328769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com // Contract with called JS functions requires that function is passed in r1. 1329769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ASSERT(fun.is(r1)); 1330769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1331769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com Register expected_reg = r2; 1332b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org Register code_reg = r3; 1333769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1334769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ldr(code_reg, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); 1335769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ldr(cp, FieldMemOperand(r1, JSFunction::kContextOffset)); 1336769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ldr(expected_reg, 1337769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com FieldMemOperand(code_reg, 1338769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com SharedFunctionInfo::kFormalParameterCountOffset)); 1339bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(expected_reg); 1340769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ldr(code_reg, 1341145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); 1342769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1343769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com ParameterCount expected(expected_reg); 1344e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org InvokeCode(code_reg, expected, actual, flag, call_wrapper); 1345769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com} 1346769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 1347769cc962a043dd8d92cc010dd2c50bc26f652c94mads.s.ager@gmail.com 13488a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.orgvoid MacroAssembler::InvokeFunction(Register function, 134932d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org const ParameterCount& expected, 13505c838251403b0be9a882540f1922577abba4c872ager@chromium.org const ParameterCount& actual, 1351d2be901879306d8ff27e78e37783028d581d46fcricow@chromium.org InvokeFlag flag, 1352e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org const CallWrapper& call_wrapper) { 1353c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // You can't call a function without a valid frame. 1354c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(flag == JUMP_FUNCTION || has_frame()); 1355c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 13568a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org // Contract with called JS functions requires that function is passed in r1. 13578a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org ASSERT(function.is(r1)); 13588a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org 13595c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Get the function and setup the context. 13605c838251403b0be9a882540f1922577abba4c872ager@chromium.org ldr(cp, FieldMemOperand(r1, JSFunction::kContextOffset)); 13615c838251403b0be9a882540f1922577abba4c872ager@chromium.org 1362394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com // We call indirectly through the code field in the function to 1363394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com // allow recompilation to take effect without changing any of the 1364394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com // call sites. 1365394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com ldr(r3, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); 1366e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org InvokeCode(r3, expected, actual, flag, call_wrapper); 13675c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 13685c838251403b0be9a882540f1922577abba4c872ager@chromium.org 13695c838251403b0be9a882540f1922577abba4c872ager@chromium.org 13708a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.orgvoid MacroAssembler::InvokeFunction(Handle<JSFunction> function, 13718a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org const ParameterCount& expected, 13728a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org const ParameterCount& actual, 13738a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org InvokeFlag flag, 1374e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org const CallWrapper& call_wrapper) { 13758a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org Move(r1, function); 1376e31286d471eb2e656a1809383fa16b76053dd673machenbach@chromium.org InvokeFunction(r1, expected, actual, flag, call_wrapper); 13778a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org} 13788a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org 13798a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org 1380023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.orgvoid MacroAssembler::IsObjectJSObjectType(Register heap_object, 1381023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Register map, 1382023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Register scratch, 1383023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Label* fail) { 1384023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org ldr(map, FieldMemOperand(heap_object, HeapObject::kMapOffset)); 1385023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org IsInstanceJSObjectType(map, scratch, fail); 1386023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org} 1387023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1388023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1389023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.orgvoid MacroAssembler::IsInstanceJSObjectType(Register map, 1390023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Register scratch, 1391023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org Label* fail) { 1392023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org ldrb(scratch, FieldMemOperand(map, Map::kInstanceTypeOffset)); 1393d2be901879306d8ff27e78e37783028d581d46fcricow@chromium.org cmp(scratch, Operand(FIRST_NONCALLABLE_SPEC_OBJECT_TYPE)); 1394023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org b(lt, fail); 1395d2be901879306d8ff27e78e37783028d581d46fcricow@chromium.org cmp(scratch, Operand(LAST_NONCALLABLE_SPEC_OBJECT_TYPE)); 1396023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org b(gt, fail); 1397023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org} 1398023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1399023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1400023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.orgvoid MacroAssembler::IsObjectJSStringType(Register object, 140149edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org Register scratch, 140249edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org Label* fail) { 1403023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org ASSERT(kNotStringTag != 0); 1404023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1405023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org ldr(scratch, FieldMemOperand(object, HeapObject::kMapOffset)); 1406023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org ldrb(scratch, FieldMemOperand(scratch, Map::kInstanceTypeOffset)); 1407023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org tst(scratch, Operand(kIsNotStringMask)); 1408378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org b(ne, fail); 1409023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org} 1410023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1411023421e6892b2ba6dcd2bbee117e0bfb24545cf7whesse@chromium.org 1412750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.orgvoid MacroAssembler::IsObjectNameType(Register object, 1413750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Register scratch, 1414750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Label* fail) { 1415750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org ldr(scratch, FieldMemOperand(object, HeapObject::kMapOffset)); 1416750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org ldrb(scratch, FieldMemOperand(scratch, Map::kInstanceTypeOffset)); 1417750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org cmp(scratch, Operand(LAST_NAME_TYPE)); 1418750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(hi, fail); 1419750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org} 1420750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 1421750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 14225c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::DebugBreak() { 142359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(r0, Operand::Zero()); 1424ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org mov(r1, Operand(ExternalReference(Runtime::kDebugBreak, isolate()))); 1425f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org CEntryStub ces(isolate(), 1); 1426c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(AllowThisStubCall(&ces)); 1427f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org Call(ces.GetCode(), RelocInfo::DEBUG_BREAK); 14285c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 142943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1430eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 143178d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.orgvoid MacroAssembler::PushTryHandler(StackHandler::Kind kind, 143204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org int handler_index) { 1433eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Adjust this code if not the case. 14344acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kSize == 5 * kPointerSize); 14354acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kNextOffset == 0 * kPointerSize); 143604e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kCodeOffset == 1 * kPointerSize); 143704e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kStateOffset == 2 * kPointerSize); 143804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kContextOffset == 3 * kPointerSize); 143904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kFPOffset == 4 * kPointerSize); 144004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 14413d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org // For the JSEntry handler, we must preserve r0-r4, r5-r6 are available. 144204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // We will build up the handler from the bottom by pushing on the stack. 144304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Set up the code object (r5) and the state (r6) for pushing. 144478d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org unsigned state = 144578d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org StackHandler::IndexField::encode(handler_index) | 144678d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org StackHandler::KindField::encode(kind); 144704e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org mov(r5, Operand(CodeObject())); 144804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org mov(r6, Operand(state)); 144904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 145004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Push the frame pointer, context, state, and code object. 145178d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org if (kind == StackHandler::JS_ENTRY) { 14523d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org mov(cp, Operand(Smi::FromInt(0))); // Indicates no context. 145359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org mov(ip, Operand::Zero()); // NULL frame pointer. 14543d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org stm(db_w, sp, r5.bit() | r6.bit() | cp.bit() | ip.bit()); 145578d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org } else { 145678d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org stm(db_w, sp, r5.bit() | r6.bit() | cp.bit() | fp.bit()); 145743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen } 145804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 145904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Link the current handler as the next handler. 146004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org mov(r6, Operand(ExternalReference(Isolate::kHandlerAddress, isolate()))); 146104e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org ldr(r5, MemOperand(r6)); 146204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org push(r5); 146304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Set this new handler as the current one. 146404e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org str(sp, MemOperand(r6)); 146543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 146643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 146743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 146813bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.orgvoid MacroAssembler::PopTryHandler() { 14694acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kNextOffset == 0); 147013bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org pop(r1); 147183e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org mov(ip, Operand(ExternalReference(Isolate::kHandlerAddress, isolate()))); 147213bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org add(sp, sp, Operand(StackHandlerConstants::kSize - kPointerSize)); 147313bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org str(r1, MemOperand(ip)); 147413bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org} 147513bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 147613bd294acf56c7f824d92d4941a2aeb3cec58e0ckmillikin@chromium.org 147704e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.orgvoid MacroAssembler::JumpToHandlerEntry() { 147804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Compute the handler entry address and jump to it. The handler table is 147904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // a fixed array of (smi-tagged) code offsets. 148004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // r0 = exception, r1 = code object, r2 = state. 1481763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org 1482763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org ConstantPoolUnavailableScope constant_pool_unavailable(this); 1483763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org if (FLAG_enable_ool_constant_pool) { 1484763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org ldr(pp, FieldMemOperand(r1, Code::kConstantPoolOffset)); // Constant pool. 1485763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org } 148604e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org ldr(r3, FieldMemOperand(r1, Code::kHandlerTableOffset)); // Handler table. 148704e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org add(r3, r3, Operand(FixedArray::kHeaderSize - kHeapObjectTag)); 148804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org mov(r2, Operand(r2, LSR, StackHandler::kKindWidth)); // Handler index. 148904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org ldr(r2, MemOperand(r3, r2, LSL, kPointerSizeLog2)); // Smi-tagged offset. 149004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org add(r1, r1, Operand(Code::kHeaderSize - kHeapObjectTag)); // Code start. 1491bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org add(pc, r1, Operand::SmiUntag(r2)); // Jump 149204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org} 149304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 149404e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 149549edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.orgvoid MacroAssembler::Throw(Register value) { 14964acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org // Adjust this code if not the case. 14974acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kSize == 5 * kPointerSize); 149804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kNextOffset == 0); 149904e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kCodeOffset == 1 * kPointerSize); 150004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kStateOffset == 2 * kPointerSize); 150104e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kContextOffset == 3 * kPointerSize); 150204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kFPOffset == 4 * kPointerSize); 150304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org 150404e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // The exception is expected in r0. 150549edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org if (!value.is(r0)) { 150649edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org mov(r0, value); 150749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org } 150804e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Drop the stack pointer to the top of the top handler. 150983e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org mov(r3, Operand(ExternalReference(Isolate::kHandlerAddress, isolate()))); 151049edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org ldr(sp, MemOperand(r3)); 15114acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org // Restore the next handler. 151249edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org pop(r2); 151349edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org str(r2, MemOperand(r3)); 15144acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org 151504e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Get the code object (r1) and state (r2). Restore the context and frame 151604e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // pointer. 151704e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org ldm(ia_w, sp, r1.bit() | r2.bit() | cp.bit() | fp.bit()); 15184acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org 15194acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org // If the handler is a JS frame, restore the context to the frame. 152004e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // (kind == ENTRY) == (fp == 0) == (cp == 0), so we could test either fp 152104e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // or cp. 152204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org tst(cp, cp); 15234acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org str(cp, MemOperand(fp, StandardFrameConstants::kContextOffset), ne); 15244acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org 152504e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org JumpToHandlerEntry(); 152649edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org} 152749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 152849edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 152965a89c29ac6da09f5726f48f68eae9587b0e562aulan@chromium.orgvoid MacroAssembler::ThrowUncatchable(Register value) { 153049edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org // Adjust this code if not the case. 15314acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kSize == 5 * kPointerSize); 15324acdc2c8d4caecf7606db8af710366c1d6e28fe5whesse@chromium.org STATIC_ASSERT(StackHandlerConstants::kNextOffset == 0 * kPointerSize); 153304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kCodeOffset == 1 * kPointerSize); 153404e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kStateOffset == 2 * kPointerSize); 153504e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kContextOffset == 3 * kPointerSize); 153604e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org STATIC_ASSERT(StackHandlerConstants::kFPOffset == 4 * kPointerSize); 153749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 1538c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org // The exception is expected in r0. 153965a89c29ac6da09f5726f48f68eae9587b0e562aulan@chromium.org if (!value.is(r0)) { 1540c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org mov(r0, value); 154149edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org } 1542c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org // Drop the stack pointer to the top of the top stack handler. 1543c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org mov(r3, Operand(ExternalReference(Isolate::kHandlerAddress, isolate()))); 1544c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org ldr(sp, MemOperand(r3)); 1545c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org 154604e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Unwind the handlers until the ENTRY handler is found. 1547c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org Label fetch_next, check_kind; 1548c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org jmp(&check_kind); 1549c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org bind(&fetch_next); 1550c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org ldr(sp, MemOperand(sp, StackHandlerConstants::kNextOffset)); 1551c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org 1552c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org bind(&check_kind); 155378d1ad443658709d6c27809001a0e71efd8b898fyangguo@chromium.org STATIC_ASSERT(StackHandler::JS_ENTRY == 0); 1554c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org ldr(r2, MemOperand(sp, StackHandlerConstants::kStateOffset)); 155504e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org tst(r2, Operand(StackHandler::KindField::kMask)); 1556c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org b(ne, &fetch_next); 1557c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org 1558c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org // Set the top handler address to next handler past the top ENTRY handler. 1559c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org pop(r2); 1560c612e0211bdb8821cbd7886e15b0273ed82d2e9edanno@chromium.org str(r2, MemOperand(r3)); 156104e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // Get the code object (r1) and state (r2). Clear the context and frame 156204e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org // pointer (0 was saved in the handler). 156304e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org ldm(ia_w, sp, r1.bit() | r2.bit() | cp.bit() | fp.bit()); 156449edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 156504e4f1e9e1291ac270e1cb7d8384b2af2fd2d685jkummerow@chromium.org JumpToHandlerEntry(); 156649edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org} 156749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 156849edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 15695a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.orgvoid MacroAssembler::CheckAccessGlobalProxy(Register holder_reg, 15705a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org Register scratch, 15715a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org Label* miss) { 15725a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org Label same_contexts; 15735a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 157443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen ASSERT(!holder_reg.is(scratch)); 15755a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ASSERT(!holder_reg.is(ip)); 15765a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ASSERT(!scratch.is(ip)); 157743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 15785a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Load current lexical context from the stack frame. 15795a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ldr(scratch, MemOperand(fp, StandardFrameConstants::kContextOffset)); 15805a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // In debug mode, make sure the lexical context is set. 158165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org#ifdef DEBUG 158259297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org cmp(scratch, Operand::Zero()); 1583594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(ne, kWeShouldNotHaveAnEmptyLexicalContext); 158465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org#endif 158543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 158646839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Load the native context of the current context. 158746839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org int offset = 158846839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org Context::kHeaderSize + Context::GLOBAL_OBJECT_INDEX * kPointerSize; 158943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen ldr(scratch, FieldMemOperand(scratch, offset)); 159046839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(scratch, FieldMemOperand(scratch, GlobalObject::kNativeContextOffset)); 15915a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 159246839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Check the context is a native context. 1593badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 15945a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Cannot use ip as a temporary in this verification code. Due to the fact 15955a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // that ip is clobbered as part of cmp with an object Operand. 15965a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org push(holder_reg); // Temporarily save holder on the stack. 159746839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Read the first word and compare to the native_context_map. 15985a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ldr(holder_reg, FieldMemOperand(scratch, HeapObject::kMapOffset)); 159946839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org LoadRoot(ip, Heap::kNativeContextMapRootIndex); 1600ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org cmp(holder_reg, ip); 1601594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kJSGlobalObjectNativeContextShouldBeANativeContext); 16025a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org pop(holder_reg); // Restore holder. 16035a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org } 16045a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 16055a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Check if both contexts are the same. 160646839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(ip, FieldMemOperand(holder_reg, JSGlobalProxy::kNativeContextOffset)); 16075a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org cmp(scratch, Operand(ip)); 16085a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org b(eq, &same_contexts); 16095a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 161046839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Check the context is a native context. 1611badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 16125a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Cannot use ip as a temporary in this verification code. Due to the fact 16135a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // that ip is clobbered as part of cmp with an object Operand. 16145a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org push(holder_reg); // Temporarily save holder on the stack. 16155a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org mov(holder_reg, ip); // Move ip to its holding place. 1616ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org LoadRoot(ip, Heap::kNullValueRootIndex); 1617ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org cmp(holder_reg, ip); 1618594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(ne, kJSGlobalProxyContextShouldNotBeNull); 16195a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 16205a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ldr(holder_reg, FieldMemOperand(holder_reg, HeapObject::kMapOffset)); 162146839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org LoadRoot(ip, Heap::kNativeContextMapRootIndex); 1622ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org cmp(holder_reg, ip); 1623594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kJSGlobalObjectNativeContextShouldBeANativeContext); 16245a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Restore ip is not needed. ip is reloaded below. 16255a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org pop(holder_reg); // Restore holder. 16265a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org // Restore ip to holder's context. 162746839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(ip, FieldMemOperand(holder_reg, JSGlobalProxy::kNativeContextOffset)); 16285a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org } 16295a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 163043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Check that the security token in the calling global object is 163143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // compatible with the security token in the receiving global 163243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // object. 16335a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org int token_offset = Context::kHeaderSize + 16345a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org Context::SECURITY_TOKEN_INDEX * kPointerSize; 16355a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 16365a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ldr(scratch, FieldMemOperand(scratch, token_offset)); 16375a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org ldr(ip, FieldMemOperand(ip, token_offset)); 163843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen cmp(scratch, Operand(ip)); 163943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen b(ne, miss); 16405a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org 16415a8ca6c70c6fc9716f18f6223c98d1fef5752cf6kasperl@chromium.org bind(&same_contexts); 164243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 164343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 164443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 1645ea468886ebe54afda9c81df0e85eea04bbb4f0f2machenbach@chromium.org// Compute the hash code from the untagged key. This must be kept in sync with 1646ea468886ebe54afda9c81df0e85eea04bbb4f0f2machenbach@chromium.org// ComputeIntegerHash in utils.h and KeyedLoadGenericElementStub in 1647ea468886ebe54afda9c81df0e85eea04bbb4f0f2machenbach@chromium.org// code-stub-hydrogen.cc 1648f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.comvoid MacroAssembler::GetNumberHash(Register t0, Register scratch) { 1649f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // First of all we assign the hash seed to scratch. 1650f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com LoadRoot(scratch, Heap::kHashSeedRootIndex); 1651f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com SmiUntag(scratch); 1652f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 1653f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // Xor original key with a seed. 1654f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com eor(t0, t0, Operand(scratch)); 1655f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 1656f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // Compute the hash code from the untagged key. This must be kept in sync 1657f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // with ComputeIntegerHash in utils.h. 1658f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // 1659f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = ~hash + (hash << 15); 1660f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com mvn(scratch, Operand(t0)); 1661f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com add(t0, scratch, Operand(t0, LSL, 15)); 1662f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = hash ^ (hash >> 12); 1663f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com eor(t0, t0, Operand(t0, LSR, 12)); 1664f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = hash + (hash << 2); 1665f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com add(t0, t0, Operand(t0, LSL, 2)); 1666f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = hash ^ (hash >> 4); 1667f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com eor(t0, t0, Operand(t0, LSR, 4)); 1668f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = hash * 2057; 1669f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com mov(scratch, Operand(t0, LSL, 11)); 1670f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com add(t0, t0, Operand(t0, LSL, 3)); 1671f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com add(t0, t0, scratch); 1672f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com // hash = hash ^ (hash >> 16); 1673f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com eor(t0, t0, Operand(t0, LSR, 16)); 1674f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com} 1675f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 1676f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 16776db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.orgvoid MacroAssembler::LoadFromNumberDictionary(Label* miss, 16786db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register elements, 16796db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register key, 16806db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register result, 16816db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register t0, 16826db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register t1, 16836db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Register t2) { 16846db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Register use: 16856db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 16866db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // elements - holds the slow-case elements of the receiver on entry. 16876db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Unchanged unless 'result' is the same register. 16886db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 16896db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // key - holds the smi key on entry. 16906db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Unchanged unless 'result' is the same register. 16916db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 16926db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // result - holds the result on exit if the load succeeded. 16936db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Allowed to be the same as 'key' or 'result'. 16946db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Unchanged on bailout so 'key' or 'result' can be used 16956db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // in further computation. 16966db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 16976db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Scratch registers: 16986db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 16996db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // t0 - holds the untagged key on entry and holds the hash once computed. 17006db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 17016db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // t1 - used to hold the capacity mask of the dictionary 17026db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // 17036db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // t2 - used for the index into the dictionary. 17046db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org Label done; 17056db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 1706f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com GetNumberHash(t0, t1); 17076db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17086db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Compute the capacity mask. 1709f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com ldr(t1, FieldMemOperand(elements, SeededNumberDictionary::kCapacityOffset)); 1710bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(t1); 17116db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org sub(t1, t1, Operand(1)); 17126db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17136db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Generate an unrolled loop that performs a few probes before giving up. 1714ea468886ebe54afda9c81df0e85eea04bbb4f0f2machenbach@chromium.org for (int i = 0; i < kNumberDictionaryProbes; i++) { 17156db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Use t2 for index calculations and keep the hash intact in t0. 17166db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org mov(t2, t0); 17176db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Compute the masked index: (hash + i + i * i) & mask. 17186db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org if (i > 0) { 1719f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com add(t2, t2, Operand(SeededNumberDictionary::GetProbeOffset(i))); 17206db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org } 17216db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org and_(t2, t2, Operand(t1)); 17226db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17236db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Scale the index by multiplying by the element size. 1724f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com ASSERT(SeededNumberDictionary::kEntrySize == 3); 17256db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org add(t2, t2, Operand(t2, LSL, 1)); // t2 = t2 * 3 17266db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17276db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Check if the key is identical to the name. 17286db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org add(t2, elements, Operand(t2, LSL, kPointerSizeLog2)); 1729f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com ldr(ip, FieldMemOperand(t2, SeededNumberDictionary::kElementsStartOffset)); 17306db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org cmp(key, Operand(ip)); 1731ea468886ebe54afda9c81df0e85eea04bbb4f0f2machenbach@chromium.org if (i != kNumberDictionaryProbes - 1) { 17326db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org b(eq, &done); 17336db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org } else { 17346db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org b(ne, miss); 17356db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org } 17366db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org } 17376db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17386db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org bind(&done); 17396db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Check that the value is a normal property. 17406db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // t2: elements + (index * kPointerSize) 17416db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org const int kDetailsOffset = 1742f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com SeededNumberDictionary::kElementsStartOffset + 2 * kPointerSize; 17436db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org ldr(t1, FieldMemOperand(t2, kDetailsOffset)); 174483e168294456ca2f02db421a635f7d5f5d023966kmillikin@chromium.org tst(t1, Operand(Smi::FromInt(PropertyDetails::TypeField::kMask))); 17456db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org b(ne, miss); 17466db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17476db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org // Get the value at the masked, scaled index and return. 17486db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org const int kValueOffset = 1749f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com SeededNumberDictionary::kElementsStartOffset + kPointerSize; 17506db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org ldr(result, FieldMemOperand(t2, kValueOffset)); 17516db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org} 17526db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17536db8871df97e7137d11f956af3c772f4f8370761sgjesse@chromium.org 17542bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.orgvoid MacroAssembler::Allocate(int object_size, 17552bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Register result, 17562bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Register scratch1, 17572bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Register scratch2, 17582bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Label* gc_required, 17592bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org AllocationFlags flags) { 1760ef9a2b9208396fda21c01fdff922975fe35d9c4amachenbach@chromium.org ASSERT(object_size <= Page::kMaxRegularHeapObjectSize); 1761303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org if (!FLAG_inline_new) { 1762badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 1763303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org // Trash the registers to simulate an allocation failure. 1764303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(result, Operand(0x7091)); 1765303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(scratch1, Operand(0x7191)); 1766303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(scratch2, Operand(0x7291)); 1767303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org } 1768303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org jmp(gc_required); 1769303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org return; 1770303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org } 1771303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 177218ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org ASSERT(!result.is(scratch1)); 1773a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(!result.is(scratch2)); 177418ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org ASSERT(!scratch1.is(scratch2)); 17758f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org ASSERT(!scratch1.is(ip)); 17768f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org ASSERT(!scratch2.is(ip)); 177718ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 1778720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org // Make object size into bytes. 1779720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org if ((flags & SIZE_IN_WORDS) != 0) { 1780720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org object_size *= kPointerSize; 1781720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org } 1782720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org ASSERT_EQ(0, object_size & kObjectAlignmentMask); 1783720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org 1784a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Check relative positions of allocation top and limit addresses. 1785a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // The values must be adjacent in memory to allow the use of LDM. 1786a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Also, assert that the registers are numbered such that the values 1787a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // are loaded in the correct order. 17882bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org ExternalReference allocation_top = 17892bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org AllocationUtils::GetAllocationTopReference(isolate(), flags); 17902bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org ExternalReference allocation_limit = 17912bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org AllocationUtils::GetAllocationLimitReference(isolate(), flags); 17922bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org 1793a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org intptr_t top = 17942bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org reinterpret_cast<intptr_t>(allocation_top.address()); 1795a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org intptr_t limit = 17962bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org reinterpret_cast<intptr_t>(allocation_limit.address()); 1797a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT((limit - top) == kPointerSize); 1798a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(result.code() < ip.code()); 1799a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 180032cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org // Set up allocation top address register. 1801a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org Register topaddr = scratch1; 18022bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org mov(topaddr, Operand(allocation_top)); 1803a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 1804a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // This code stores a temporary value in ip. This is OK, as the code below 1805a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // does not need ip for implicit literal generation. 1806a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org if ((flags & RESULT_CONTAINS_TOP) == 0) { 1807a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Load allocation top into result and allocation limit into ip. 1808a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldm(ia, topaddr, result.bit() | ip.bit()); 1809a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } else { 1810badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 1811a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Assert that result actually contains top on entry. ip is used 1812a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // immediately below so this use of ip does not cause difference with 1813a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // respect to register content between debug and release mode. 1814a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldr(ip, MemOperand(topaddr)); 1815a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org cmp(result, ip); 1816594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kUnexpectedAllocationTop); 1817a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } 1818a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Load allocation limit into ip. Result already contains allocation top. 1819a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldr(ip, MemOperand(topaddr, limit - top)); 1820a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org } 182118ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 18224cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org if ((flags & DOUBLE_ALIGNMENT) != 0) { 18234cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org // Align the next allocation. Storing the filler map without checking top is 1824f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org // safe in new-space because the limit of the heap is aligned there. 18252bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org ASSERT((flags & PRETENURE_OLD_POINTER_SPACE) == 0); 182632cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org STATIC_ASSERT(kPointerAlignment * 2 == kDoubleAlignment); 18274cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org and_(scratch2, result, Operand(kDoubleAlignmentMask), SetCC); 18284cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org Label aligned; 18294cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org b(eq, &aligned); 1830f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org if ((flags & PRETENURE_OLD_DATA_SPACE) != 0) { 1831f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org cmp(result, Operand(ip)); 1832f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org b(hs, gc_required); 1833f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org } 18344cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org mov(scratch2, Operand(isolate()->factory()->one_pointer_filler_map())); 18354cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org str(scratch2, MemOperand(result, kDoubleSize / 2, PostIndex)); 18364cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org bind(&aligned); 18374cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org } 18384cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org 183918ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org // Calculate new top and bail out if new space is exhausted. Use result 184032cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org // to calculate the new top. We must preserve the ip register at this 184132cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org // point, so we cannot just use add(). 184232cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org ASSERT(object_size > 0); 184332cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org Register source = result; 184432cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org Condition cond = al; 184532cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org int shift = 0; 184632cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org while (object_size != 0) { 184732cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org if (((object_size >> shift) & 0x03) == 0) { 184832cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org shift += 2; 184932cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org } else { 185032cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org int bits = object_size & (0xff << shift); 185132cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org object_size -= bits; 185232cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org shift += 8; 185332cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org Operand bits_operand(bits); 1854874aad37f2a832804012c6f56739f4fc6c9283cdmachenbach@chromium.org ASSERT(bits_operand.is_single_instruction(this)); 185532cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org add(scratch2, source, bits_operand, SetCC, cond); 185632cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org source = scratch2; 185732cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org cond = cc; 185832cb9b2c195baa85d4c04f4c7b22b9aa04e97d3fverwaest@chromium.org } 1859c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 1860d91075f76b836c2cfa4f4e4cc0fb31170df864ccerik.corry@gmail.com b(cs, gc_required); 1861a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org cmp(scratch2, Operand(ip)); 186218ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org b(hi, gc_required); 1863a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org str(scratch2, MemOperand(topaddr)); 186418ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 1865a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Tag object if requested. 1866a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org if ((flags & TAG_OBJECT) != 0) { 1867a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org add(result, result, Operand(kHeapObjectTag)); 1868a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org } 1869a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org} 1870a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1871a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1872f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.orgvoid MacroAssembler::Allocate(Register object_size, 1873f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Register result, 1874f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Register scratch1, 1875f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Register scratch2, 1876f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Label* gc_required, 1877f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org AllocationFlags flags) { 1878303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org if (!FLAG_inline_new) { 1879badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 1880303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org // Trash the registers to simulate an allocation failure. 1881303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(result, Operand(0x7091)); 1882303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(scratch1, Operand(0x7191)); 1883303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org mov(scratch2, Operand(0x7291)); 1884303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org } 1885303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org jmp(gc_required); 1886303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org return; 1887303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org } 1888303ada708275d2d425b846fb237f1ba7598ee239lrn@chromium.org 18895f0c45f2cacb31d36a8f80c31f17bda7751a3644ager@chromium.org // Assert that the register arguments are different and that none of 18905f0c45f2cacb31d36a8f80c31f17bda7751a3644ager@chromium.org // them are ip. ip is used explicitly in the code generated below. 1891a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org ASSERT(!result.is(scratch1)); 1892a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(!result.is(scratch2)); 1893a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org ASSERT(!scratch1.is(scratch2)); 1894394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com ASSERT(!object_size.is(ip)); 18955f0c45f2cacb31d36a8f80c31f17bda7751a3644ager@chromium.org ASSERT(!result.is(ip)); 18965f0c45f2cacb31d36a8f80c31f17bda7751a3644ager@chromium.org ASSERT(!scratch1.is(ip)); 18975f0c45f2cacb31d36a8f80c31f17bda7751a3644ager@chromium.org ASSERT(!scratch2.is(ip)); 1898a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1899a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Check relative positions of allocation top and limit addresses. 1900a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // The values must be adjacent in memory to allow the use of LDM. 1901a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Also, assert that the registers are numbered such that the values 1902a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // are loaded in the correct order. 1903f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org ExternalReference allocation_top = 1904f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org AllocationUtils::GetAllocationTopReference(isolate(), flags); 1905f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org ExternalReference allocation_limit = 1906f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org AllocationUtils::GetAllocationLimitReference(isolate(), flags); 1907a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org intptr_t top = 1908f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org reinterpret_cast<intptr_t>(allocation_top.address()); 1909a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org intptr_t limit = 1910f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org reinterpret_cast<intptr_t>(allocation_limit.address()); 1911a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT((limit - top) == kPointerSize); 1912a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ASSERT(result.code() < ip.code()); 1913a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 1914a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Set up allocation top address. 1915a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org Register topaddr = scratch1; 1916f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org mov(topaddr, Operand(allocation_top)); 1917a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 1918a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // This code stores a temporary value in ip. This is OK, as the code below 1919a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // does not need ip for implicit literal generation. 1920a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org if ((flags & RESULT_CONTAINS_TOP) == 0) { 1921a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Load allocation top into result and allocation limit into ip. 1922a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldm(ia, topaddr, result.bit() | ip.bit()); 1923a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } else { 1924badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 1925a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Assert that result actually contains top on entry. ip is used 1926a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // immediately below so this use of ip does not cause difference with 1927a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // respect to register content between debug and release mode. 1928a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldr(ip, MemOperand(topaddr)); 1929a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org cmp(result, ip); 1930594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kUnexpectedAllocationTop); 1931a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org } 1932a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // Load allocation limit into ip. Result already contains allocation top. 1933a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org ldr(ip, MemOperand(topaddr, limit - top)); 1934a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org } 1935a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 19364cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org if ((flags & DOUBLE_ALIGNMENT) != 0) { 19374cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org // Align the next allocation. Storing the filler map without checking top is 1938f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org // safe in new-space because the limit of the heap is aligned there. 1939f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org ASSERT((flags & PRETENURE_OLD_POINTER_SPACE) == 0); 19404cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org ASSERT(kPointerAlignment * 2 == kDoubleAlignment); 19414cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org and_(scratch2, result, Operand(kDoubleAlignmentMask), SetCC); 19424cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org Label aligned; 19434cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org b(eq, &aligned); 1944f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org if ((flags & PRETENURE_OLD_DATA_SPACE) != 0) { 1945f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org cmp(result, Operand(ip)); 1946f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org b(hs, gc_required); 1947f6fe1183c2663bdae2b8e265d4ec3d9e925568e7mstarzinger@chromium.org } 19484cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org mov(scratch2, Operand(isolate()->factory()->one_pointer_filler_map())); 19494cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org str(scratch2, MemOperand(result, kDoubleSize / 2, PostIndex)); 19504cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org bind(&aligned); 19514cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org } 19524cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org 1953a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org // Calculate new top and bail out if new space is exhausted. Use result 1954a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // to calculate the new top. Object size may be in words so a shift is 1955a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org // required to get the number of bytes. 1956720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org if ((flags & SIZE_IN_WORDS) != 0) { 1957d91075f76b836c2cfa4f4e4cc0fb31170df864ccerik.corry@gmail.com add(scratch2, result, Operand(object_size, LSL, kPointerSizeLog2), SetCC); 1958720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org } else { 1959d91075f76b836c2cfa4f4e4cc0fb31170df864ccerik.corry@gmail.com add(scratch2, result, Operand(object_size), SetCC); 1960720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org } 1961d91075f76b836c2cfa4f4e4cc0fb31170df864ccerik.corry@gmail.com b(cs, gc_required); 1962a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org cmp(scratch2, Operand(ip)); 1963a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org b(hi, gc_required); 1964a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1965ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org // Update allocation top. result temporarily holds the new top. 1966badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 1967a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org tst(scratch2, Operand(kObjectAlignmentMask)); 1968594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kUnalignedAllocationInNewSpace); 1969ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org } 1970a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org str(scratch2, MemOperand(topaddr)); 1971a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1972a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org // Tag object if requested. 1973a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org if ((flags & TAG_OBJECT) != 0) { 1974a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org add(result, result, Operand(kHeapObjectTag)); 197518ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org } 197618ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org} 197718ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 197818ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 1979a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.orgvoid MacroAssembler::UndoAllocationInNewSpace(Register object, 1980a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org Register scratch) { 1981a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org ExternalReference new_space_allocation_top = 1982ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org ExternalReference::new_space_allocation_top_address(isolate()); 1983a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1984a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org // Make sure the object has no tag before resetting top. 1985a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org and_(object, object, Operand(~kHeapObjectTagMask)); 1986a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org#ifdef DEBUG 1987a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org // Check that the object un-allocated is below the current top. 1988a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org mov(scratch, Operand(new_space_allocation_top)); 1989a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org ldr(scratch, MemOperand(scratch)); 1990a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org cmp(object, scratch); 1991594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(lt, kUndoAllocationOfNonAllocatedMemory); 1992a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org#endif 1993a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org // Write the address of the object to un-allocate as the current top. 1994a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org mov(scratch, Operand(new_space_allocation_top)); 1995a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org str(object, MemOperand(scratch)); 1996a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org} 1997a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 1998a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 19995c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::AllocateTwoByteString(Register result, 20005c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register length, 20015c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch1, 20025c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch2, 20035c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch3, 20045c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* gc_required) { 20055c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Calculate the number of bytes needed for the characters in the string while 20065c838251403b0be9a882540f1922577abba4c872ager@chromium.org // observing object alignment. 20075c838251403b0be9a882540f1922577abba4c872ager@chromium.org ASSERT((SeqTwoByteString::kHeaderSize & kObjectAlignmentMask) == 0); 20085c838251403b0be9a882540f1922577abba4c872ager@chromium.org mov(scratch1, Operand(length, LSL, 1)); // Length in bytes, not chars. 20095c838251403b0be9a882540f1922577abba4c872ager@chromium.org add(scratch1, scratch1, 20105c838251403b0be9a882540f1922577abba4c872ager@chromium.org Operand(kObjectAlignmentMask + SeqTwoByteString::kHeaderSize)); 2011720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org and_(scratch1, scratch1, Operand(~kObjectAlignmentMask)); 20125c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20135c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Allocate two-byte string in new space. 2014f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Allocate(scratch1, 2015f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org result, 2016f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org scratch2, 2017f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org scratch3, 2018f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org gc_required, 2019f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org TAG_OBJECT); 20205c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20215c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Set the map, length and hash field. 2022ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org InitializeNewString(result, 2023ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org length, 2024ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Heap::kStringMapRootIndex, 2025ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch1, 2026ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch2); 20275c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 20285c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20295c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20305c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::AllocateAsciiString(Register result, 20315c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register length, 20325c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch1, 20335c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch2, 20345c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch3, 20355c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* gc_required) { 20365c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Calculate the number of bytes needed for the characters in the string while 20375c838251403b0be9a882540f1922577abba4c872ager@chromium.org // observing object alignment. 2038fb37721ea34922d8758d5cb26ae465aaf241e6b6yangguo@chromium.org ASSERT((SeqOneByteString::kHeaderSize & kObjectAlignmentMask) == 0); 20395c838251403b0be9a882540f1922577abba4c872ager@chromium.org ASSERT(kCharSize == 1); 20405c838251403b0be9a882540f1922577abba4c872ager@chromium.org add(scratch1, length, 2041fb37721ea34922d8758d5cb26ae465aaf241e6b6yangguo@chromium.org Operand(kObjectAlignmentMask + SeqOneByteString::kHeaderSize)); 2042720dc0bc17114e33b9b2177fcb6726bda9cabd62sgjesse@chromium.org and_(scratch1, scratch1, Operand(~kObjectAlignmentMask)); 20435c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20445c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Allocate ASCII string in new space. 2045f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org Allocate(scratch1, 2046f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org result, 2047f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org scratch2, 2048f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org scratch3, 2049f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org gc_required, 2050f705b5034dc5bc422ac1019b591469a7d0534772mstarzinger@chromium.org TAG_OBJECT); 20515c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20525c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Set the map, length and hash field. 2053ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org InitializeNewString(result, 2054ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org length, 2055ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Heap::kAsciiStringMapRootIndex, 2056ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch1, 2057ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch2); 20585c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 20595c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20605c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20615c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::AllocateTwoByteConsString(Register result, 20625c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register length, 20635c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch1, 20645c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch2, 20655c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* gc_required) { 20662bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Allocate(ConsString::kSize, result, scratch1, scratch2, gc_required, 20672bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org TAG_OBJECT); 2068ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 2069ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org InitializeNewString(result, 2070ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org length, 2071ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Heap::kConsStringMapRootIndex, 2072ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch1, 2073ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch2); 20745c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 20755c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20765c838251403b0be9a882540f1922577abba4c872ager@chromium.org 20775c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::AllocateAsciiConsString(Register result, 20785c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register length, 20795c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch1, 20805c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch2, 20815c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* gc_required) { 208257ff881caeb2e15b46ac9e4dfc00e378f7c5f929ulan@chromium.org Allocate(ConsString::kSize, 208357ff881caeb2e15b46ac9e4dfc00e378f7c5f929ulan@chromium.org result, 208457ff881caeb2e15b46ac9e4dfc00e378f7c5f929ulan@chromium.org scratch1, 208557ff881caeb2e15b46ac9e4dfc00e378f7c5f929ulan@chromium.org scratch2, 208657ff881caeb2e15b46ac9e4dfc00e378f7c5f929ulan@chromium.org gc_required, 20877e6132b924829c353864933f29124419916db550machenbach@chromium.org TAG_OBJECT); 2088ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org 2089ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org InitializeNewString(result, 2090ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org length, 2091ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org Heap::kConsAsciiStringMapRootIndex, 2092ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch1, 20931805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org scratch2); 20941805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org} 20951805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 20961805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 20971805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.orgvoid MacroAssembler::AllocateTwoByteSlicedString(Register result, 20981805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register length, 20991805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register scratch1, 21001805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register scratch2, 21011805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Label* gc_required) { 21022bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, 21032bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org TAG_OBJECT); 21041805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 21051805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org InitializeNewString(result, 21061805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org length, 21071805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Heap::kSlicedStringMapRootIndex, 21081805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org scratch1, 21091805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org scratch2); 21101805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org} 21111805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 21121805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 21131805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.orgvoid MacroAssembler::AllocateAsciiSlicedString(Register result, 21141805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register length, 21151805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register scratch1, 21161805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Register scratch2, 21171805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Label* gc_required) { 21182bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, 21192bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org TAG_OBJECT); 21201805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org 21211805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org InitializeNewString(result, 21221805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org length, 21231805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org Heap::kSlicedAsciiStringMapRootIndex, 21241805e21b0aece8c05f4960a5c0751c4463557891fschneider@chromium.org scratch1, 2125ac091b7d178f1853ede4a5cba58e767e6adf7d96ager@chromium.org scratch2); 21265c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 21275c838251403b0be9a882540f1922577abba4c872ager@chromium.org 21285c838251403b0be9a882540f1922577abba4c872ager@chromium.org 2129c34f5802a37a9fa2ce8f3929d1d5159ddcf04ff3lrn@chromium.orgvoid MacroAssembler::CompareObjectType(Register object, 2130eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Register map, 2131eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Register type_reg, 2132eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org InstanceType type) { 213337be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org const Register temp = type_reg.is(no_reg) ? ip : type_reg; 213437be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org 213537be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org ldr(map, FieldMemOperand(object, HeapObject::kMapOffset)); 213637be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org CompareInstanceType(map, temp, type); 213737be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org} 213837be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org 213937be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org 214037be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.orgvoid MacroAssembler::CheckObjectTypeRange(Register object, 214137be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org Register map, 214237be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org InstanceType min_type, 214337be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org InstanceType max_type, 214437be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org Label* false_label) { 214537be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org STATIC_ASSERT(Map::kInstanceTypeOffset < 4096); 214637be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org STATIC_ASSERT(LAST_TYPE < 256); 2147c34f5802a37a9fa2ce8f3929d1d5159ddcf04ff3lrn@chromium.org ldr(map, FieldMemOperand(object, HeapObject::kMapOffset)); 214837be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org ldrb(ip, FieldMemOperand(map, Map::kInstanceTypeOffset)); 214937be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org sub(ip, ip, Operand(min_type)); 215037be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org cmp(ip, Operand(max_type - min_type)); 215137be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org b(hi, false_label); 2152a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org} 2153a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 2154a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org 2155a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.orgvoid MacroAssembler::CompareInstanceType(Register map, 2156a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org Register type_reg, 2157a1645e29968e70a41226edda2c49788fcea48b74ager@chromium.org InstanceType type) { 215837be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org // Registers map and type_reg can be ip. These two lines assert 215937be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org // that ip can be used with the two instructions (the constants 216037be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org // will never need ip). 216137be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org STATIC_ASSERT(Map::kInstanceTypeOffset < 4096); 216237be408adf363bbe682921a4a690752fa0ec33femachenbach@chromium.org STATIC_ASSERT(LAST_TYPE < 256); 2163eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org ldrb(type_reg, FieldMemOperand(map, Map::kInstanceTypeOffset)); 2164eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org cmp(type_reg, Operand(type)); 2165eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org} 2166eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2167eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 21688f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.orgvoid MacroAssembler::CompareRoot(Register obj, 21698f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org Heap::RootListIndex index) { 21708f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org ASSERT(!obj.is(ip)); 21718f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org LoadRoot(ip, index); 21728f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org cmp(obj, ip); 21738f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org} 21748f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org 21758f806e8b8f108ca2c8899c5d31861ef1273dcd4akarlklose@chromium.org 2176d6076d96a1411932548838e5960b594564264010erik.corry@gmail.comvoid MacroAssembler::CheckFastElements(Register map, 2177d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com Register scratch, 2178d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com Label* fail) { 2179830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_SMI_ELEMENTS == 0); 2180830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_HOLEY_SMI_ELEMENTS == 1); 2181830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_ELEMENTS == 2); 2182830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_HOLEY_ELEMENTS == 3); 2183c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldrb(scratch, FieldMemOperand(map, Map::kBitField2Offset)); 2184830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org cmp(scratch, Operand(Map::kMaximumBitField2FastHoleyElementValue)); 2185c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(hi, fail); 2186c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 2187c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2188c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2189c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::CheckFastObjectElements(Register map, 2190c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch, 2191c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* fail) { 2192830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_SMI_ELEMENTS == 0); 2193830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_HOLEY_SMI_ELEMENTS == 1); 2194830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_ELEMENTS == 2); 2195830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_HOLEY_ELEMENTS == 3); 21964f693d6b99ffdbc05e5e211e08ed5039e13279d2ricow@chromium.org ldrb(scratch, FieldMemOperand(map, Map::kBitField2Offset)); 2197830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org cmp(scratch, Operand(Map::kMaximumBitField2FastHoleySmiElementValue)); 2198c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(ls, fail); 2199830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org cmp(scratch, Operand(Map::kMaximumBitField2FastHoleyElementValue)); 2200d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com b(hi, fail); 2201d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com} 2202d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com 2203d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com 2204830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.orgvoid MacroAssembler::CheckFastSmiElements(Register map, 2205830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org Register scratch, 2206830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org Label* fail) { 2207830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_SMI_ELEMENTS == 0); 2208830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org STATIC_ASSERT(FAST_HOLEY_SMI_ELEMENTS == 1); 2209c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldrb(scratch, FieldMemOperand(map, Map::kBitField2Offset)); 2210830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org cmp(scratch, Operand(Map::kMaximumBitField2FastHoleySmiElementValue)); 2211c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(hi, fail); 2212c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 2213c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2214c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2215fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::StoreNumberToDoubleElements( 2216fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Register value_reg, 2217fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Register key_reg, 2218fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Register elements_reg, 2219fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Register scratch1, 2220fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch, 2221fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Label* fail, 2222fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org int elements_offset) { 2223e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org Label smi_value, store; 2224a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2225a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org // Handle smi values specially. 2226a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org JumpIfSmi(value_reg, &smi_value); 2227a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2228a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org // Ensure that the object is a heap number 2229a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org CheckMap(value_reg, 2230a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org scratch1, 2231a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org isolate()->factory()->heap_number_map(), 2232a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org fail, 2233a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org DONT_DO_SMI_CHECK); 2234a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2235fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vldr(double_scratch, FieldMemOperand(value_reg, HeapNumber::kValueOffset)); 2236e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org // Force a canonical NaN. 2237e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org if (emit_debug_code()) { 2238e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org vmrs(ip); 2239e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org tst(ip, Operand(kVFPDefaultNaNModeControlBit)); 2240594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Assert(ne, kDefaultNaNModeNotSet); 2241e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org } 2242fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org VFPCanonicalizeNaN(double_scratch); 2243e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org b(&store); 2244a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2245a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org bind(&smi_value); 2246fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org SmiToDouble(double_scratch, value_reg); 2247e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org 2248e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org bind(&store); 2249bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org add(scratch1, elements_reg, Operand::DoubleOffsetFromSmiKey(key_reg)); 2250fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vstr(double_scratch, 2251fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org FieldMemOperand(scratch1, 2252fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org FixedDoubleArray::kHeaderSize - elements_offset)); 2253a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org} 2254a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2255a8bb4d938869bdcdf759625ee868775ff24826d9svenpanne@chromium.org 2256f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.comvoid MacroAssembler::CompareMap(Register obj, 2257f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com Register scratch, 2258f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com Handle<Map> map, 2259a53e8e03bcb23716d1025de362626f90f00da892svenpanne@chromium.org Label* early_success) { 2260f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com ldr(scratch, FieldMemOperand(obj, HeapObject::kMapOffset)); 2261a53e8e03bcb23716d1025de362626f90f00da892svenpanne@chromium.org CompareMap(scratch, map, early_success); 22627028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org} 22637028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org 22647028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org 22657028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.orgvoid MacroAssembler::CompareMap(Register obj_map, 22667028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org Handle<Map> map, 2267a53e8e03bcb23716d1025de362626f90f00da892svenpanne@chromium.org Label* early_success) { 22687028c05c1c71b9d5c5fe1bca01f2461d17a2dda7mmassi@chromium.org cmp(obj_map, Operand(map)); 2269f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com} 2270f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 2271f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 22725c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::CheckMap(Register obj, 22735c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register scratch, 22745c838251403b0be9a882540f1922577abba4c872ager@chromium.org Handle<Map> map, 22755c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* fail, 2276a53e8e03bcb23716d1025de362626f90f00da892svenpanne@chromium.org SmiCheckType smi_check_type) { 2277c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org if (smi_check_type == DO_SMI_CHECK) { 2278378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org JumpIfSmi(obj, fail); 22795c838251403b0be9a882540f1922577abba4c872ager@chromium.org } 2280f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com 2281f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com Label success; 2282a53e8e03bcb23716d1025de362626f90f00da892svenpanne@chromium.org CompareMap(obj, scratch, map, &success); 22835c838251403b0be9a882540f1922577abba4c872ager@chromium.org b(ne, fail); 2284f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com bind(&success); 22855c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 22865c838251403b0be9a882540f1922577abba4c872ager@chromium.org 22875c838251403b0be9a882540f1922577abba4c872ager@chromium.org 22882cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.orgvoid MacroAssembler::CheckMap(Register obj, 22892cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org Register scratch, 22902cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org Heap::RootListIndex index, 22912cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org Label* fail, 2292c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org SmiCheckType smi_check_type) { 2293c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org if (smi_check_type == DO_SMI_CHECK) { 2294378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org JumpIfSmi(obj, fail); 22952cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org } 22962cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org ldr(scratch, FieldMemOperand(obj, HeapObject::kMapOffset)); 22972cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org LoadRoot(ip, index); 22982cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org cmp(scratch, ip); 22992cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org b(ne, fail); 23002cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org} 23012cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org 23022cc82ae439960d1adaf4374e093730dc23945d59ager@chromium.org 2303ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.orgvoid MacroAssembler::DispatchMap(Register obj, 2304ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org Register scratch, 2305ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org Handle<Map> map, 2306ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org Handle<Code> success, 2307ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org SmiCheckType smi_check_type) { 2308ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org Label fail; 2309ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org if (smi_check_type == DO_SMI_CHECK) { 2310ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org JumpIfSmi(obj, &fail); 2311ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org } 2312ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org ldr(scratch, FieldMemOperand(obj, HeapObject::kMapOffset)); 2313ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org mov(ip, Operand(map)); 2314ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org cmp(scratch, ip); 2315ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org Jump(success, RelocInfo::CODE_TARGET, eq); 2316ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org bind(&fail); 2317ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org} 2318ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org 2319ea91cc579ade536e3a08498a8157921dd4f533d1ager@chromium.org 2320eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.orgvoid MacroAssembler::TryGetFunctionPrototype(Register function, 2321eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Register result, 2322eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Register scratch, 2323394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com Label* miss, 2324394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com bool miss_on_bound_function) { 2325eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Check that the receiver isn't a smi. 2326378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org JumpIfSmi(function, miss); 2327eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2328eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Check that the function really is a function. Load map into result reg. 2329eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org CompareObjectType(function, result, scratch, JS_FUNCTION_TYPE); 2330eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org b(ne, miss); 2331eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2332394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com if (miss_on_bound_function) { 2333394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com ldr(scratch, 2334394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com FieldMemOperand(function, JSFunction::kSharedFunctionInfoOffset)); 2335394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com ldr(scratch, 2336394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com FieldMemOperand(scratch, SharedFunctionInfo::kCompilerHintsOffset)); 2337394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com tst(scratch, 2338394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com Operand(Smi::FromInt(1 << SharedFunctionInfo::kBoundFunction))); 2339394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com b(ne, miss); 2340394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com } 2341394dbcf9009cf5203b6d85e8b515fcff072040f3erik.corry@gmail.com 2342eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Make sure that the function has an instance prototype. 2343eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Label non_instance; 2344eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org ldrb(scratch, FieldMemOperand(result, Map::kBitFieldOffset)); 2345eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org tst(scratch, Operand(1 << Map::kHasNonInstancePrototype)); 2346eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org b(ne, &non_instance); 2347eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2348eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Get the prototype or initial map from the function. 2349eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org ldr(result, 2350eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org FieldMemOperand(function, JSFunction::kPrototypeOrInitialMapOffset)); 2351eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2352eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // If the prototype or initial map is the hole, don't return it and 2353eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // simply miss the cache instead. This will allow us to allocate a 2354eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // prototype object on-demand in the runtime system. 2355ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org LoadRoot(ip, Heap::kTheHoleValueRootIndex); 2356ab99eea3d9d0cc20698ebb39bf0fb80e3e66bffcager@chromium.org cmp(result, ip); 2357eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org b(eq, miss); 2358eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2359eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // If the function does not have an initial map, we're done. 2360eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org Label done; 2361eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org CompareObjectType(result, scratch, scratch, MAP_TYPE); 2362eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org b(ne, &done); 2363eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2364eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Get the prototype from the initial map. 2365eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org ldr(result, FieldMemOperand(result, Map::kPrototypeOffset)); 2366eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org jmp(&done); 2367eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2368eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // Non-instance prototype: Fetch prototype from constructor field 2369eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // in initial map. 2370eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org bind(&non_instance); 2371eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org ldr(result, FieldMemOperand(result, Map::kConstructorOffset)); 2372eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2373eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org // All done. 2374eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org bind(&done); 2375eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org} 2376eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 2377eadaf2282ee421d7a63a21d71369b029105341ccager@chromium.org 23784cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.orgvoid MacroAssembler::CallStub(CodeStub* stub, 23794cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org TypeFeedbackId ast_id, 23804cd70b470729dd5850dd4120a350f01363d16837yangguo@chromium.org Condition cond) { 2381c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(AllowThisStubCall(stub)); // Stub calls are not allowed in some stubs. 2382f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org Call(stub->GetCode(), RelocInfo::CODE_TARGET, ast_id, cond); 238343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 238443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 238543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 23865c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::TailCallStub(CodeStub* stub, Condition cond) { 2387f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org Jump(stub->GetCode(), RelocInfo::CODE_TARGET, cond); 238883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org} 238983aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 239083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 239183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.orgstatic int AddressOffset(ExternalReference ref0, ExternalReference ref1) { 239283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org return ref0.address() - ref1.address(); 239383aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org} 239483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 239583aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 2396528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.orgvoid MacroAssembler::CallApiFunctionAndReturn( 2397e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org Register function_address, 2398528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ExternalReference thunk_ref, 2399528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org int stack_space, 2400528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org MemOperand return_value_operand, 2401528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org MemOperand* context_restore_operand) { 240283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org ExternalReference next_address = 240309d7ab5aba54ebac170eac755664c45eefb0be7dulan@chromium.org ExternalReference::handle_scope_next_address(isolate()); 240483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org const int kNextOffset = 0; 240583aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org const int kLimitOffset = AddressOffset( 240609d7ab5aba54ebac170eac755664c45eefb0be7dulan@chromium.org ExternalReference::handle_scope_limit_address(isolate()), 240783aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org next_address); 240883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org const int kLevelOffset = AddressOffset( 240909d7ab5aba54ebac170eac755664c45eefb0be7dulan@chromium.org ExternalReference::handle_scope_level_address(isolate()), 241083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org next_address); 241183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 241257a54ace4b6b45d5d6a7ff38d88ee9990d47f5e2machenbach@chromium.org ASSERT(function_address.is(r1) || function_address.is(r2)); 2413e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org 2414e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org Label profiler_disabled; 2415e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org Label end_profiler_check; 2416a70700b91bc28abeed6373b856017f7f9cc8273bmachenbach@chromium.org mov(r9, Operand(ExternalReference::is_profiling_address(isolate()))); 2417e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org ldrb(r9, MemOperand(r9, 0)); 2418e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org cmp(r9, Operand(0)); 2419e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org b(eq, &profiler_disabled); 2420e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org 2421e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org // Additional parameter is the address of the actual callback. 2422e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org mov(r3, Operand(thunk_ref)); 2423e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org jmp(&end_profiler_check); 2424e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org 2425e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org bind(&profiler_disabled); 2426e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org Move(r3, function_address); 2427e014e5bf9ccd6a759add3b35ba610f3a0c752a90machenbach@chromium.org bind(&end_profiler_check); 24283d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org 242983aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // Allocate HandleScope in callee-save registers. 24303d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org mov(r9, Operand(next_address)); 24313d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org ldr(r4, MemOperand(r9, kNextOffset)); 24323d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org ldr(r5, MemOperand(r9, kLimitOffset)); 24333d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org ldr(r6, MemOperand(r9, kLevelOffset)); 243483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org add(r6, r6, Operand(1)); 24353d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org str(r6, MemOperand(r9, kLevelOffset)); 243683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 243783130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org if (FLAG_log_timer_events) { 243883130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org FrameScope frame(this, StackFrame::MANUAL); 243983130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org PushSafepointRegisters(); 2440ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org PrepareCallCFunction(1, r0); 2441ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org mov(r0, Operand(ExternalReference::isolate_address(isolate()))); 2442ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org CallCFunction(ExternalReference::log_enter_external_function(isolate()), 1); 244383130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org PopSafepointRegisters(); 244483130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org } 244583130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org 244683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // Native call returns to the DirectCEntry stub which redirects to the 244783aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // return address pushed on stack (could have moved after GC). 244883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // DirectCEntry stub itself is generated early and never moves. 2449f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org DirectCEntryStub stub(isolate()); 2450b752d4061aaeb7d6a6ec368607871789d54b0207dslomov@chromium.org stub.GenerateCall(this, r3); 245183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 245283130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org if (FLAG_log_timer_events) { 245383130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org FrameScope frame(this, StackFrame::MANUAL); 245483130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org PushSafepointRegisters(); 2455ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org PrepareCallCFunction(1, r0); 2456ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org mov(r0, Operand(ExternalReference::isolate_address(isolate()))); 2457ca29dd85fa02449d17188f5a6ff9a7cdf2ad9680danno@chromium.org CallCFunction(ExternalReference::log_leave_external_function(isolate()), 1); 245883130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org PopSafepointRegisters(); 245983130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org } 246083130cfc204d3ffed6832a7ef149b19328a58b33svenpanne@chromium.org 246183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org Label promote_scheduled_exception; 2462528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Label exception_handled; 246383aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org Label delete_allocated_handles; 246483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org Label leave_exit_frame; 2465bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org Label return_value_loaded; 2466bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org 2467bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org // load value from ReturnValue 2468528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(r0, return_value_operand); 2469bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org bind(&return_value_loaded); 247083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // No more valid handles (the result handle was the last one). Restore 247183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // previous handle scope. 24723d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org str(r4, MemOperand(r9, kNextOffset)); 2473badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 24743d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org ldr(r1, MemOperand(r9, kLevelOffset)); 247583aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org cmp(r1, r6); 2476594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kUnexpectedLevelAfterReturnFromApiCall); 247783aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org } 247883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org sub(r6, r6, Operand(1)); 24793d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org str(r6, MemOperand(r9, kLevelOffset)); 24803d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org ldr(ip, MemOperand(r9, kLimitOffset)); 248183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org cmp(r5, ip); 248283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org b(ne, &delete_allocated_handles); 248383aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 248483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // Check if the function scheduled an exception. 248583aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org bind(&leave_exit_frame); 248683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org LoadRoot(r4, Heap::kTheHoleValueRootIndex); 2487ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org mov(ip, Operand(ExternalReference::scheduled_exception_address(isolate()))); 248883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org ldr(r5, MemOperand(ip)); 248983aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org cmp(r4, r5); 249083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org b(ne, &promote_scheduled_exception); 2491528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org bind(&exception_handled); 249283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 2493528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org bool restore_context = context_restore_operand != NULL; 2494528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org if (restore_context) { 2495528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(cp, *context_restore_operand); 2496528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org } 249749edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org // LeaveExitFrame expects unwind space to be in a register. 249883aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org mov(r4, Operand(stack_space)); 2499528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org LeaveExitFrame(false, r4, !restore_context); 250049edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org mov(pc, lr); 250183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 250283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org bind(&promote_scheduled_exception); 2503528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org { 2504528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org FrameScope frame(this, StackFrame::INTERNAL); 2505528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org CallExternalReference( 2506895f00d1d8c5a7a7209c36d690688e3552de3df4machenbach@chromium.org ExternalReference(Runtime::kHiddenPromoteScheduledException, isolate()), 2507528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 0); 2508528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org } 2509528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org jmp(&exception_handled); 251083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 251183aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org // HandleScope limit has changed. Delete allocated extensions. 251283aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org bind(&delete_allocated_handles); 25133d079fe881245e49c7ba803b54b4fe6d4b46113cmachenbach@chromium.org str(r5, MemOperand(r9, kLimitOffset)); 251483aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org mov(r4, r0); 2515c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org PrepareCallCFunction(1, r5); 251632d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org mov(r0, Operand(ExternalReference::isolate_address(isolate()))); 2517ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org CallCFunction( 2518c36ce6e8979bbbd43539f0a0effc87ea20dd65cckmillikin@chromium.org ExternalReference::delete_handle_scope_extensions(isolate()), 1); 251983aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org mov(r0, r4); 252083aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org jmp(&leave_exit_frame); 25215c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 25225c838251403b0be9a882540f1922577abba4c872ager@chromium.org 25235c838251403b0be9a882540f1922577abba4c872ager@chromium.org 2524c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.combool MacroAssembler::AllowThisStubCall(CodeStub* stub) { 25258a58f6420f995bb19fff9babb261458d49d90cb1machenbach@chromium.org return has_frame_ || !stub->SometimesSetsUpAFrame(); 2526c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 2527c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2528c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 2529d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.orgvoid MacroAssembler::IndexFromHash(Register hash, Register index) { 2530d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org // If the hash field contains an array index pick it out. The assert checks 2531d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org // that the constants for the maximum number of digits for an array index 2532d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org // cached in the hash field and the number of bits reserved for it does not 2533d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org // conflict. 2534d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org ASSERT(TenToThe(String::kMaxCachedArrayIndexLength) < 2535d236f4d96b5dd21acc5ec57f4e50fa97cdd97bb6ricow@chromium.org (1 << String::kArrayIndexValueBits)); 2536d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org DecodeFieldToSmi<String::ArrayIndexValueBits>(index, hash); 253732d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org} 253832d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 253932d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 2540fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.orgvoid MacroAssembler::SmiToDouble(LowDwVfpRegister value, Register smi) { 2541bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org if (CpuFeatures::IsSupported(VFP3)) { 2542bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org vmov(value.low(), smi); 2543bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org vcvt_f64_s32(value, 1); 2544bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org } else { 2545bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(ip, smi); 2546bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org vmov(value.low(), ip); 2547bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org vcvt_f64_s32(value, value.low()); 2548bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org } 254932d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org} 255032d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 255132d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 2552750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.orgvoid MacroAssembler::TestDoubleIsInt32(DwVfpRegister double_input, 2553fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch) { 2554cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org ASSERT(!double_input.is(double_scratch)); 2555cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org vcvt_s32_f64(double_scratch.low(), double_input); 2556cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org vcvt_f64_s32(double_scratch, double_scratch.low()); 2557cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org VFPCompareAndSetFlags(double_input, double_scratch); 2558cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org} 2559cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org 2560cddc71f18a46e6117cc765b1c53ca122e7aaa318rossberg@chromium.org 2561750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.orgvoid MacroAssembler::TryDoubleToInt32Exact(Register result, 2562750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org DwVfpRegister double_input, 2563fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch) { 256433e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org ASSERT(!double_input.is(double_scratch)); 2565750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org vcvt_s32_f64(double_scratch.low(), double_input); 256633e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org vmov(result, double_scratch.low()); 2567750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org vcvt_f64_s32(double_scratch, double_scratch.low()); 2568750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org VFPCompareAndSetFlags(double_input, double_scratch); 2569750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org} 257033e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org 2571750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 2572750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.orgvoid MacroAssembler::TryInt32Floor(Register result, 2573750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org DwVfpRegister double_input, 2574750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Register input_high, 2575fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch, 2576750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Label* done, 2577750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Label* exact) { 2578750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org ASSERT(!result.is(input_high)); 2579750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org ASSERT(!double_input.is(double_scratch)); 2580750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Label negative, exception; 2581750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 2582fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org VmovHigh(input_high, double_input); 2583fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org 2584750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // Test for NaN and infinities. 2585750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org Sbfx(result, input_high, 2586750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org HeapNumber::kExponentShift, HeapNumber::kExponentBits); 2587750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org cmp(result, Operand(-1)); 2588750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(eq, &exception); 2589750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // Test for values that can be exactly represented as a 2590750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // signed 32-bit integer. 2591750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org TryDoubleToInt32Exact(result, double_input, double_scratch); 2592750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // If exact, return (result already fetched). 2593750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(eq, exact); 2594750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org cmp(input_high, Operand::Zero()); 2595750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(mi, &negative); 2596750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 2597750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // Input is in ]+0, +inf[. 2598750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // If result equals 0x7fffffff input was out of range or 2599750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // in ]0x7fffffff, 0x80000000[. We ignore this last case which 2600750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // could fits into an int32, that means we always think input was 2601750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // out of range and always go to exception. 2602750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // If result < 0x7fffffff, go to done, result fetched. 2603750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org cmn(result, Operand(1)); 2604750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(mi, &exception); 2605750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(done); 2606750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 2607750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // Input is in ]-inf, -0[. 2608750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // If x is a non integer negative number, 2609750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // floor(x) <=> round_to_zero(x) - 1. 2610750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org bind(&negative); 2611750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org sub(result, result, Operand(1), SetCC); 2612750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // If result is still negative, go to done, result fetched. 2613750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org // Else, we had an overflow and we fall through exception. 2614750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org b(mi, done); 2615750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org bind(&exception); 26169ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org} 26179ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 26181e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.orgvoid MacroAssembler::TryInlineTruncateDoubleToI(Register result, 26191e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org DwVfpRegister double_input, 26201e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Label* done) { 26211e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org LowDwVfpRegister double_scratch = kScratchDoubleReg; 26222bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org vcvt_s32_f64(double_scratch.low(), double_input); 26232bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org vmov(result, double_scratch.low()); 26242bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org 26252bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org // If result is not saturated (0x7fffffff or 0x80000000), we are done. 26261e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org sub(ip, result, Operand(1)); 26271e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org cmp(ip, Operand(0x7ffffffe)); 26281e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org b(lt, done); 26291e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org} 2630badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org 26316e196bfaf0e555d0c835390bb6ebc0a74484491dulan@chromium.org 26321e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.orgvoid MacroAssembler::TruncateDoubleToI(Register result, 26331e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org DwVfpRegister double_input) { 26341e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Label done; 26351e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26361e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org TryInlineTruncateDoubleToI(result, double_input, &done); 26371e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26381e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org // If we fell through then inline version didn't succeed - call stub instead. 26391e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org push(lr); 26401e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org sub(sp, sp, Operand(kDoubleSize)); // Put input on stack. 26411e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org vstr(double_input, MemOperand(sp, 0)); 26421e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 2643f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org DoubleToIStub stub(isolate(), sp, result, 0, true, true); 26441e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org CallStub(&stub); 26451e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26461e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org add(sp, sp, Operand(kDoubleSize)); 26471e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org pop(lr); 26481e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26491e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org bind(&done); 26501e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org} 26511e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26521e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26531e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.orgvoid MacroAssembler::TruncateHeapNumberToI(Register result, 26541e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register object) { 26551e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Label done; 26561e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org LowDwVfpRegister double_scratch = kScratchDoubleReg; 26571e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org ASSERT(!result.is(object)); 26581e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26591e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org vldr(double_scratch, 26601e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org MemOperand(object, HeapNumber::kValueOffset - kHeapObjectTag)); 26611e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org TryInlineTruncateDoubleToI(result, double_scratch, &done); 26621e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26631e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org // If we fell through then inline version didn't succeed - call stub instead. 26641e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org push(lr); 2665f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org DoubleToIStub stub(isolate(), 2666f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org object, 26671e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org result, 26681e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org HeapNumber::kValueOffset - kHeapObjectTag, 26691e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org true, 26701e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org true); 26711e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org CallStub(&stub); 26721e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org pop(lr); 26731e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26741e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org bind(&done); 26751e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org} 26761e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26771e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26781e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.orgvoid MacroAssembler::TruncateNumberToI(Register object, 26791e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register result, 26801e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register heap_number_map, 26811e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register scratch1, 26821e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Label* not_number) { 26831e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Label done; 26841e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org ASSERT(!result.is(object)); 26851e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 26861e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org UntagAndJumpIfSmi(result, object, &done); 26871e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org JumpIfNotHeapNumber(object, heap_number_map, scratch1, not_number); 26881e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org TruncateHeapNumberToI(result, object); 26896e196bfaf0e555d0c835390bb6ebc0a74484491dulan@chromium.org 269032d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org bind(&done); 2691badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org} 2692badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org 2693badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org 26945c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::GetLeastBitsFromSmi(Register dst, 26955c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register src, 26965c838251403b0be9a882540f1922577abba4c872ager@chromium.org int num_least_bits) { 2697471f2f1d24adb4bad1edc3bf0ee35092486de187mstarzinger@chromium.org if (CpuFeatures::IsSupported(ARMv7) && !predictable_code_size()) { 269830ce411529579186181838984710b0b0980857aaricow@chromium.org ubfx(dst, src, kSmiTagSize, num_least_bits); 26995c838251403b0be9a882540f1922577abba4c872ager@chromium.org } else { 2700bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(dst, src); 27015c838251403b0be9a882540f1922577abba4c872ager@chromium.org and_(dst, dst, Operand((1 << num_least_bits) - 1)); 27025c838251403b0be9a882540f1922577abba4c872ager@chromium.org } 27035c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 27045c838251403b0be9a882540f1922577abba4c872ager@chromium.org 27055c838251403b0be9a882540f1922577abba4c872ager@chromium.org 2706496c03a64f12710e837204e261ef155601247895sgjesse@chromium.orgvoid MacroAssembler::GetLeastBitsFromInt32(Register dst, 2707496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org Register src, 2708496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org int num_least_bits) { 2709496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org and_(dst, src, Operand((1 << num_least_bits) - 1)); 2710496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org} 2711496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org 2712496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org 2713ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgvoid MacroAssembler::CallRuntime(const Runtime::Function* f, 2714fb7a7c4ffde9a4d060f5f989371e2ce964ee5831jkummerow@chromium.org int num_arguments, 2715fb7a7c4ffde9a4d060f5f989371e2ce964ee5831jkummerow@chromium.org SaveFPRegsMode save_doubles) { 271631e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager // All parameters are on the stack. r0 has the return value after call. 271743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 271841044eb0969b0d7d5c041a077519a36efa6aff27kasperl@chromium.org // If the expected number of arguments of the runtime function is 271941044eb0969b0d7d5c041a077519a36efa6aff27kasperl@chromium.org // constant, we check that the actual number of arguments match the 272041044eb0969b0d7d5c041a077519a36efa6aff27kasperl@chromium.org // expectation. 272129699e37f62a9aa96c100f29bc8ea3668acff099machenbach@chromium.org CHECK(f->nargs < 0 || f->nargs == num_arguments); 272243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2723b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // TODO(1236192): Most runtime routines don't need the number of 2724b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // arguments passed in because it is constant. At some point we 2725b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // should remove this need and make the runtime routine entry code 2726b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // smarter. 2727b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org mov(r0, Operand(num_arguments)); 2728ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org mov(r1, Operand(ExternalReference(f, isolate()))); 2729f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org CEntryStub stub(isolate(), 1, save_doubles); 2730a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org CallStub(&stub); 2731a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org} 2732a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 2733a55512615f5adc085d23bc8589d155c4b579fb7bkasperl@chromium.org 27345c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::CallExternalReference(const ExternalReference& ext, 27355c838251403b0be9a882540f1922577abba4c872ager@chromium.org int num_arguments) { 27365c838251403b0be9a882540f1922577abba4c872ager@chromium.org mov(r0, Operand(num_arguments)); 27375c838251403b0be9a882540f1922577abba4c872ager@chromium.org mov(r1, Operand(ext)); 27385c838251403b0be9a882540f1922577abba4c872ager@chromium.org 2739f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org CEntryStub stub(isolate(), 1); 27405c838251403b0be9a882540f1922577abba4c872ager@chromium.org CallStub(&stub); 27415c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 27425c838251403b0be9a882540f1922577abba4c872ager@chromium.org 27435c838251403b0be9a882540f1922577abba4c872ager@chromium.org 2744ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.orgvoid MacroAssembler::TailCallExternalReference(const ExternalReference& ext, 2745ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org int num_arguments, 2746ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org int result_size) { 274731e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager // TODO(1236192): Most runtime routines don't need the number of 274831e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager // arguments passed in because it is constant. At some point we 274931e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager // should remove this need and make the runtime routine entry code 275031e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager // smarter. 275131e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager mov(r0, Operand(num_arguments)); 2752ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org JumpToExternalReference(ext); 2753ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org} 2754ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 2755ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 2756ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.orgvoid MacroAssembler::TailCallRuntime(Runtime::FunctionId fid, 2757ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org int num_arguments, 2758ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org int result_size) { 2759ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org TailCallExternalReference(ExternalReference(fid, isolate()), 2760ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org num_arguments, 2761ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org result_size); 276243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 276343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 276443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2765ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.orgvoid MacroAssembler::JumpToExternalReference(const ExternalReference& builtin) { 276643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen#if defined(__thumb__) 276743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // Thumb mode builtin. 276843d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen ASSERT((reinterpret_cast<intptr_t>(builtin.address()) & 1) == 1); 276943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen#endif 277043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen mov(r1, Operand(builtin)); 2771f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org CEntryStub stub(isolate(), 1); 2772f2f0489407bbb5e50d16ae791442df29513b53b5machenbach@chromium.org Jump(stub.GetCode(), RelocInfo::CODE_TARGET); 277343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 277443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 277543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2776b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.orgvoid MacroAssembler::InvokeBuiltin(Builtins::JavaScript id, 27778e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org InvokeFlag flag, 2778fb144a0716afe7ab8bf245f2391a9e53b3db3c89fschneider@chromium.org const CallWrapper& call_wrapper) { 2779c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // You can't call a builtin without a valid frame. 2780c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(flag == JUMP_FUNCTION || has_frame()); 2781c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 27825c838251403b0be9a882540f1922577abba4c872ager@chromium.org GetBuiltinEntry(r2, id); 27838e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org if (flag == CALL_FUNCTION) { 2784fb144a0716afe7ab8bf245f2391a9e53b3db3c89fschneider@chromium.org call_wrapper.BeforeCall(CallSize(r2)); 27855c838251403b0be9a882540f1922577abba4c872ager@chromium.org Call(r2); 2786fb144a0716afe7ab8bf245f2391a9e53b3db3c89fschneider@chromium.org call_wrapper.AfterCall(); 278743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen } else { 27888e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org ASSERT(flag == JUMP_FUNCTION); 27895c838251403b0be9a882540f1922577abba4c872ager@chromium.org Jump(r2); 2790b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org } 2791b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org} 2792b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 2793b912362e2b2e704d09faac4290e027fd744bf587kasperl@chromium.org 2794145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.comvoid MacroAssembler::GetBuiltinFunction(Register target, 2795145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com Builtins::JavaScript id) { 2796c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // Load the builtins object into target register. 279746839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(target, 279846839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org MemOperand(cp, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); 2799c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org ldr(target, FieldMemOperand(target, GlobalObject::kBuiltinsOffset)); 28005c838251403b0be9a882540f1922577abba4c872ager@chromium.org // Load the JavaScript builtin function from the builtins object. 2801145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com ldr(target, FieldMemOperand(target, 2802c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org JSBuiltinsObject::OffsetOfFunctionWithId(id))); 2803145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com} 2804145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com 2805c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org 2806145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.comvoid MacroAssembler::GetBuiltinEntry(Register target, Builtins::JavaScript id) { 2807145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com ASSERT(!target.is(r1)); 2808145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com GetBuiltinFunction(r1, id); 2809c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // Load the code entry point from the builtins object. 2810145eff58d4f6ac0dcc53abb556dbf3cac6c3280aerik.corry@gmail.com ldr(target, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); 281143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 281243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 281343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2814a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.orgvoid MacroAssembler::SetCounter(StatsCounter* counter, int value, 2815a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org Register scratch1, Register scratch2) { 2816a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org if (FLAG_native_code_counters && counter->Enabled()) { 2817a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org mov(scratch1, Operand(value)); 2818a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org mov(scratch2, Operand(ExternalReference(counter))); 2819a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org str(scratch1, MemOperand(scratch2)); 2820a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org } 2821a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org} 2822a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2823a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2824a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.orgvoid MacroAssembler::IncrementCounter(StatsCounter* counter, int value, 2825a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org Register scratch1, Register scratch2) { 2826a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org ASSERT(value > 0); 2827a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org if (FLAG_native_code_counters && counter->Enabled()) { 2828a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org mov(scratch2, Operand(ExternalReference(counter))); 2829a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org ldr(scratch1, MemOperand(scratch2)); 2830a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org add(scratch1, scratch1, Operand(value)); 2831a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org str(scratch1, MemOperand(scratch2)); 2832a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org } 2833a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org} 2834a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2835a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2836a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.orgvoid MacroAssembler::DecrementCounter(StatsCounter* counter, int value, 2837a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org Register scratch1, Register scratch2) { 2838a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org ASSERT(value > 0); 2839a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org if (FLAG_native_code_counters && counter->Enabled()) { 2840a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org mov(scratch2, Operand(ExternalReference(counter))); 2841a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org ldr(scratch1, MemOperand(scratch2)); 2842a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org sub(scratch1, scratch1, Operand(value)); 2843a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org str(scratch1, MemOperand(scratch2)); 2844a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org } 2845a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org} 2846a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2847a74f0daeb278665869b4b6a3bc2739e88fed93b1ager@chromium.org 2848594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.orgvoid MacroAssembler::Assert(Condition cond, BailoutReason reason) { 2849badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) 2850594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(cond, reason); 285143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 285243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 285343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 28540b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.orgvoid MacroAssembler::AssertFastElements(Register elements) { 2855badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 28560b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org ASSERT(!elements.is(ip)); 28570b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org Label ok; 28580b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org push(elements); 28590b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org ldr(elements, FieldMemOperand(elements, HeapObject::kMapOffset)); 28600b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org LoadRoot(ip, Heap::kFixedArrayMapRootIndex); 28610b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org cmp(elements, ip); 28620b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org b(eq, &ok); 286384bcc559ac20fb04f806e97d28a314b20b58fd60svenpanne@chromium.org LoadRoot(ip, Heap::kFixedDoubleArrayMapRootIndex); 286484bcc559ac20fb04f806e97d28a314b20b58fd60svenpanne@chromium.org cmp(elements, ip); 286584bcc559ac20fb04f806e97d28a314b20b58fd60svenpanne@chromium.org b(eq, &ok); 28660b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org LoadRoot(ip, Heap::kFixedCOWArrayMapRootIndex); 28670b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org cmp(elements, ip); 28680b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org b(eq, &ok); 2869594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Abort(kJSObjectWithFastElementsMapHasSlowElements); 28700b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org bind(&ok); 28710b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org pop(elements); 28720b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org } 28730b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org} 28740b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org 28750b9f850f0e9dc624b9e0c5254393112ecc7f8bc9ricow@chromium.org 2876594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.orgvoid MacroAssembler::Check(Condition cond, BailoutReason reason) { 287743d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen Label L; 2878378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org b(cond, &L); 2879594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Abort(reason); 288043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // will not return here 288143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen bind(&L); 288243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 288343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 288443d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 2885594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.orgvoid MacroAssembler::Abort(BailoutReason reason) { 288640b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org Label abort_start; 288740b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org bind(&abort_start); 2888052c9560e8a41c723726ebe914a93747d8f13285hpayer@chromium.org#ifdef DEBUG 2889f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org const char* msg = GetBailoutReason(reason); 289043d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen if (msg != NULL) { 289143d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen RecordComment("Abort message: "); 289243d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen RecordComment(msg); 289343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen } 28941e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 28951e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (FLAG_trap_on_abort) { 28961e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org stop(msg); 28971e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org return; 28981e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org } 289943d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen#endif 2900ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 2901f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org mov(r0, Operand(Smi::FromInt(reason))); 290231e7138e1a05e29ceefa8919ae12cb621a48ca7fmads.s.ager push(r0); 2903f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org 2904c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Disable stub call restrictions to always allow calls to abort. 2905c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com if (!has_frame_) { 2906c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // We don't actually want to generate a pile of code for this, so just 2907c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // claim there is a stack frame, without generating one. 2908c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com FrameScope scope(this, StackFrame::NONE); 2909f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org CallRuntime(Runtime::kAbort, 1); 2910c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } else { 2911f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org CallRuntime(Runtime::kAbort, 1); 2912c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 291343d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen // will not return here 291440b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org if (is_const_pool_blocked()) { 291540b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org // If the calling code cares about the exact number of 291640b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org // instructions generated, we insert padding here to keep the size 291740b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org // of the Abort macro constant. 2918f5a24546072ecdbbd6372c85c42157e01e913561titzer@chromium.org static const int kExpectedAbortInstructions = 7; 291940b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org int abort_instructions = InstructionsGeneratedSince(&abort_start); 292040b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org ASSERT(abort_instructions <= kExpectedAbortInstructions); 292140b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org while (abort_instructions++ < kExpectedAbortInstructions) { 292240b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org nop(); 292340b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org } 292440b9da37a45dabf86bd82a39e885f2921f47fc08fschneider@chromium.org } 292543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} 292643d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen 292718ad94b919217ffbcd2d3159eeb5f8c588761c47ager@chromium.org 2928ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.orgvoid MacroAssembler::LoadContext(Register dst, int context_chain_length) { 2929ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org if (context_chain_length > 0) { 2930ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org // Move up the chain of contexts to the context containing the slot. 29316d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org ldr(dst, MemOperand(cp, Context::SlotOffset(Context::PREVIOUS_INDEX))); 2932ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org for (int i = 1; i < context_chain_length; i++) { 29336d786c9805481bd13ecb29c3155540f2f32950e1svenpanne@chromium.org ldr(dst, MemOperand(dst, Context::SlotOffset(Context::PREVIOUS_INDEX))); 2934ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org } 29353a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org } else { 29363a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org // Slot is in the current function context. Move it into the 29373a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org // destination register in case we store into it (the write barrier 29383a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org // cannot be allowed to destroy the context in esi). 29393a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org mov(dst, cp); 29403a5fd78f0ca6c2827bb05f69a373d152a9ce6ff3fschneider@chromium.org } 2941ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org} 2942ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 2943ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 29441145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.orgvoid MacroAssembler::LoadTransitionedArrayMapConditional( 29451145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org ElementsKind expected_kind, 29461145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org ElementsKind transitioned_kind, 29471145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org Register map_in_out, 29481145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org Register scratch, 29491145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org Label* no_map_match) { 29501145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org // Load the global or builtins object from the current context. 295146839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(scratch, 295246839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org MemOperand(cp, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); 295346839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(scratch, FieldMemOperand(scratch, GlobalObject::kNativeContextOffset)); 29541145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org 29551145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org // Check that the function's map is the same as the expected cached map. 2956830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org ldr(scratch, 2957830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org MemOperand(scratch, 2958830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org Context::SlotOffset(Context::JS_ARRAY_MAPS_INDEX))); 2959830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org size_t offset = expected_kind * kPointerSize + 2960830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org FixedArrayBase::kHeaderSize; 2961c31a3c079281b7da0df2e33c1fd972dd110ca71bdanno@chromium.org ldr(ip, FieldMemOperand(scratch, offset)); 2962c31a3c079281b7da0df2e33c1fd972dd110ca71bdanno@chromium.org cmp(map_in_out, ip); 29631145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org b(ne, no_map_match); 29641145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org 29651145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org // Use the transitioned cached map. 2966830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org offset = transitioned_kind * kPointerSize + 2967830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org FixedArrayBase::kHeaderSize; 2968830d30c478be03b0ac560f4002833ab141e41effsvenpanne@chromium.org ldr(map_in_out, FieldMemOperand(scratch, offset)); 29691145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org} 29701145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org 29711145ef852a4e230e1f642eecd8de155f2b26bc53jkummerow@chromium.org 2972beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.orgvoid MacroAssembler::LoadGlobalFunction(int index, Register function) { 2973beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org // Load the global or builtins object from the current context. 297446839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org ldr(function, 297546839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org MemOperand(cp, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); 297646839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Load the native context from the global or builtins object. 2977beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org ldr(function, FieldMemOperand(function, 297846839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org GlobalObject::kNativeContextOffset)); 297946839fbbdee40a3d2d924e8b5b13c4139b0b24f2yangguo@chromium.org // Load the function from the native context. 2980beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org ldr(function, MemOperand(function, Context::SlotOffset(index))); 2981beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org} 2982beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org 2983beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org 2984beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.orgvoid MacroAssembler::LoadGlobalFunctionInitialMap(Register function, 2985beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org Register map, 2986beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org Register scratch) { 2987beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org // Load the initial map. The global functions all have initial maps. 2988beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org ldr(map, FieldMemOperand(function, JSFunction::kPrototypeOrInitialMapOffset)); 2989badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 2990beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org Label ok, fail; 2991c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org CheckMap(map, scratch, Heap::kMetaMapRootIndex, &fail, DO_SMI_CHECK); 2992beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org b(&ok); 2993beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org bind(&fail); 2994594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Abort(kGlobalFunctionsMustHaveInitialMap); 2995beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org bind(&ok); 2996beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org } 2997beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org} 2998beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org 2999beb2571dca14508fbbbb47a2f606327d5968ee92ager@chromium.org 300031b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.orgvoid MacroAssembler::JumpIfNotPowerOfTwoOrZero( 300131b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org Register reg, 300231b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org Register scratch, 300331b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org Label* not_power_of_two_or_zero) { 300431b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org sub(scratch, reg, Operand(1), SetCC); 300531b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org b(mi, not_power_of_two_or_zero); 300631b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org tst(scratch, reg); 300731b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org b(ne, not_power_of_two_or_zero); 300831b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org} 300931b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org 301031b1277ec3b8cd17acb01c66d85a456159072157kmillikin@chromium.org 3011ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgvoid MacroAssembler::JumpIfNotPowerOfTwoOrZeroAndNeg( 3012ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Register reg, 3013ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Register scratch, 3014ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Label* zero_and_neg, 3015ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org Label* not_power_of_two) { 3016ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org sub(scratch, reg, Operand(1), SetCC); 3017ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org b(mi, zero_and_neg); 3018ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org tst(scratch, reg); 3019ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org b(ne, not_power_of_two); 3020ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org} 3021ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org 3022ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org 30235c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::JumpIfNotBothSmi(Register reg1, 30245c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register reg2, 30255c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* on_not_both_smi) { 3026378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org STATIC_ASSERT(kSmiTag == 0); 30275c838251403b0be9a882540f1922577abba4c872ager@chromium.org tst(reg1, Operand(kSmiTagMask)); 30285c838251403b0be9a882540f1922577abba4c872ager@chromium.org tst(reg2, Operand(kSmiTagMask), eq); 30295c838251403b0be9a882540f1922577abba4c872ager@chromium.org b(ne, on_not_both_smi); 30305c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 30315c838251403b0be9a882540f1922577abba4c872ager@chromium.org 30325c838251403b0be9a882540f1922577abba4c872ager@chromium.org 3033fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.orgvoid MacroAssembler::UntagAndJumpIfSmi( 3034fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org Register dst, Register src, Label* smi_case) { 3035fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org STATIC_ASSERT(kSmiTag == 0); 3036bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(dst, src, SetCC); 3037fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org b(cc, smi_case); // Shifter carry is not set for a smi. 3038fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org} 3039fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org 3040fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org 3041fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.orgvoid MacroAssembler::UntagAndJumpIfNotSmi( 3042fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org Register dst, Register src, Label* non_smi_case) { 3043fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org STATIC_ASSERT(kSmiTag == 0); 3044bf9432e3965b385e2e8df3701b710c105f5b3eb7ulan@chromium.org SmiUntag(dst, src, SetCC); 3045fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org b(cs, non_smi_case); // Shifter carry is set for a non-smi. 3046fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org} 3047fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org 3048fa458e413c3e5b8d479e49258d060b7bb4567c57danno@chromium.org 30495c838251403b0be9a882540f1922577abba4c872ager@chromium.orgvoid MacroAssembler::JumpIfEitherSmi(Register reg1, 30505c838251403b0be9a882540f1922577abba4c872ager@chromium.org Register reg2, 30515c838251403b0be9a882540f1922577abba4c872ager@chromium.org Label* on_either_smi) { 3052378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org STATIC_ASSERT(kSmiTag == 0); 30535c838251403b0be9a882540f1922577abba4c872ager@chromium.org tst(reg1, Operand(kSmiTagMask)); 30545c838251403b0be9a882540f1922577abba4c872ager@chromium.org tst(reg2, Operand(kSmiTagMask), ne); 30555c838251403b0be9a882540f1922577abba4c872ager@chromium.org b(eq, on_either_smi); 30565c838251403b0be9a882540f1922577abba4c872ager@chromium.org} 30575c838251403b0be9a882540f1922577abba4c872ager@chromium.org 30585c838251403b0be9a882540f1922577abba4c872ager@chromium.org 3059c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.orgvoid MacroAssembler::AssertNotSmi(Register object) { 3060c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org if (emit_debug_code()) { 3061c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org STATIC_ASSERT(kSmiTag == 0); 3062c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org tst(object, Operand(kSmiTagMask)); 3063594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(ne, kOperandIsASmi); 3064c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 3065ea4f62e1df22417fc8dc2c2425485dca98b13d07ager@chromium.org} 3066ea4f62e1df22417fc8dc2c2425485dca98b13d07ager@chromium.org 3067ea4f62e1df22417fc8dc2c2425485dca98b13d07ager@chromium.org 3068c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.orgvoid MacroAssembler::AssertSmi(Register object) { 3069c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org if (emit_debug_code()) { 3070c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org STATIC_ASSERT(kSmiTag == 0); 3071c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org tst(object, Operand(kSmiTagMask)); 3072594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kOperandIsNotSmi); 3073c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 30740a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org} 30750a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 30760a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 3077c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.orgvoid MacroAssembler::AssertString(Register object) { 3078c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org if (emit_debug_code()) { 3079c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org STATIC_ASSERT(kSmiTag == 0); 3080c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org tst(object, Operand(kSmiTagMask)); 3081594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(ne, kOperandIsASmiAndNotAString); 3082c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org push(object); 3083c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org ldr(object, FieldMemOperand(object, HeapObject::kMapOffset)); 3084c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org CompareInstanceType(object, object, FIRST_NONSTRING_TYPE); 3085c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org pop(object); 3086594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(lo, kOperandIsNotAString); 3087c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 308849edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org} 308949edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 309049edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 3091750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.orgvoid MacroAssembler::AssertName(Register object) { 3092750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org if (emit_debug_code()) { 3093750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org STATIC_ASSERT(kSmiTag == 0); 3094750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org tst(object, Operand(kSmiTagMask)); 3095594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(ne, kOperandIsASmiAndNotAName); 3096750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org push(object); 3097750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org ldr(object, FieldMemOperand(object, HeapObject::kMapOffset)); 3098750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org CompareInstanceType(object, object, LAST_NAME_TYPE); 3099750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org pop(object); 3100594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(le, kOperandIsNotAName); 3101750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org } 3102750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org} 3103750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 3104750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org 31052904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.orgvoid MacroAssembler::AssertUndefinedOrAllocationSite(Register object, 31062904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org Register scratch) { 31072904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org if (emit_debug_code()) { 31082904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org Label done_checking; 31092904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org AssertNotSmi(object); 31102904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org CompareRoot(object, Heap::kUndefinedValueRootIndex); 31112904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org b(eq, &done_checking); 31122904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org ldr(scratch, FieldMemOperand(object, HeapObject::kMapOffset)); 31132904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org CompareRoot(scratch, Heap::kAllocationSiteMapRootIndex); 31142904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org Assert(eq, kExpectedUndefinedOrCell); 31152904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org bind(&done_checking); 31162904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org } 31172904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org} 31182904d1a42292be3056c2dd3f98822f8e1470fa72machenbach@chromium.org 311949edbdf52640c88918f8e6638ab4965819eb1dfekmillikin@chromium.org 312032d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.orgvoid MacroAssembler::AssertIsRoot(Register reg, Heap::RootListIndex index) { 3121c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org if (emit_debug_code()) { 312232d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org CompareRoot(reg, index); 3123594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Check(eq, kHeapNumberMapRegisterClobbered); 3124c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 312583aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org} 312683aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 312783aa54905e559090bea7771b83f188762cfcf082ricow@chromium.org 3128378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.orgvoid MacroAssembler::JumpIfNotHeapNumber(Register object, 3129378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Register heap_number_map, 3130378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Register scratch, 3131378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org Label* on_not_heap_number) { 3132378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org ldr(scratch, FieldMemOperand(object, HeapObject::kMapOffset)); 313332d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org AssertIsRoot(heap_number_map, Heap::kHeapNumberMapRootIndex); 3134378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org cmp(scratch, heap_number_map); 3135378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org b(ne, on_not_heap_number); 3136378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org} 3137378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org 3138378b34e3f8852e94739bb77a528278fe0e2bb532ager@chromium.org 3139528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.orgvoid MacroAssembler::LookupNumberStringCache(Register object, 3140528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register result, 3141528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register scratch1, 3142528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register scratch2, 3143528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register scratch3, 3144528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Label* not_found) { 3145528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Use of registers. Register result is used as a temporary. 3146528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register number_string_cache = result; 3147528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register mask = scratch3; 3148528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3149528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Load the number string cache. 3150528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org LoadRoot(number_string_cache, Heap::kNumberStringCacheRootIndex); 3151528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3152528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Make the hash mask from the length of the number string cache. It 3153528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // contains two elements (number and string) for each cache entry. 3154528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(mask, FieldMemOperand(number_string_cache, FixedArray::kLengthOffset)); 3155528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Divide length by two (length is a smi). 3156528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org mov(mask, Operand(mask, ASR, kSmiTagSize + 1)); 3157528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org sub(mask, mask, Operand(1)); // Make mask. 3158528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3159528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Calculate the entry in the number string cache. The hash value in the 3160528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // number string cache for smis is just the smi value, and the hash for 3161528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // doubles is the xor of the upper and lower words. See 3162528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Heap::GetNumberStringCache. 3163528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Label is_smi; 3164528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Label load_result_from_cache; 3165528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org JumpIfSmi(object, &is_smi); 3166528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org CheckMap(object, 3167528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org scratch1, 3168528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Heap::kHeapNumberMapRootIndex, 3169528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org not_found, 3170528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org DONT_DO_SMI_CHECK); 3171528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3172528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org STATIC_ASSERT(8 == kDoubleSize); 3173528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org add(scratch1, 3174528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org object, 3175528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Operand(HeapNumber::kValueOffset - kHeapObjectTag)); 3176528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldm(ia, scratch1, scratch1.bit() | scratch2.bit()); 3177528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org eor(scratch1, scratch1, Operand(scratch2)); 3178528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org and_(scratch1, scratch1, Operand(mask)); 3179528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3180528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Calculate address of entry in string cache: each entry consists 3181528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // of two pointer sized fields. 3182528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org add(scratch1, 3183528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org number_string_cache, 3184528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Operand(scratch1, LSL, kPointerSizeLog2 + 1)); 3185528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3186528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register probe = mask; 3187528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(probe, FieldMemOperand(scratch1, FixedArray::kHeaderSize)); 3188528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org JumpIfSmi(probe, not_found); 3189528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org sub(scratch2, object, Operand(kHeapObjectTag)); 3190528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org vldr(d0, scratch2, HeapNumber::kValueOffset); 3191528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org sub(probe, probe, Operand(kHeapObjectTag)); 3192528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org vldr(d1, probe, HeapNumber::kValueOffset); 3193528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org VFPCompareAndSetFlags(d0, d1); 3194528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org b(ne, not_found); // The cache did not contain this value. 3195528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org b(&load_result_from_cache); 3196528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3197528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org bind(&is_smi); 3198528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Register scratch = scratch1; 3199528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org and_(scratch, mask, Operand(object, ASR, 1)); 3200528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Calculate address of entry in string cache: each entry consists 3201528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // of two pointer sized fields. 3202528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org add(scratch, 3203528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org number_string_cache, 3204528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Operand(scratch, LSL, kPointerSizeLog2 + 1)); 3205528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3206528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Check if the entry is the smi we are looking for. 3207528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(probe, FieldMemOperand(scratch, FixedArray::kHeaderSize)); 3208528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org cmp(object, probe); 3209528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org b(ne, not_found); 3210528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3211528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org // Get the result from the cache. 3212528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org bind(&load_result_from_cache); 3213528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org ldr(result, FieldMemOperand(scratch, FixedArray::kHeaderSize + kPointerSize)); 3214528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org IncrementCounter(isolate()->counters()->number_to_string_native(), 3215528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 1, 3216528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org scratch1, 3217528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org scratch2); 3218528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org} 3219528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3220528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 3221b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.orgvoid MacroAssembler::JumpIfNonSmisNotBothSequentialAsciiStrings( 3222b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register first, 3223b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register second, 3224b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register scratch1, 3225b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register scratch2, 3226b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Label* failure) { 3227b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // Test that both first and second are sequential ASCII strings. 3228b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // Assume that they are non-smis. 3229b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org ldr(scratch1, FieldMemOperand(first, HeapObject::kMapOffset)); 3230b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org ldr(scratch2, FieldMemOperand(second, HeapObject::kMapOffset)); 3231b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org ldrb(scratch1, FieldMemOperand(scratch1, Map::kInstanceTypeOffset)); 3232b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org ldrb(scratch2, FieldMemOperand(scratch2, Map::kInstanceTypeOffset)); 3233ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 3234ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org JumpIfBothInstanceTypesAreNotSequentialAscii(scratch1, 3235ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org scratch2, 3236ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org scratch1, 3237ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org scratch2, 3238ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org failure); 3239b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org} 3240b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org 3241b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.orgvoid MacroAssembler::JumpIfNotBothSequentialAsciiStrings(Register first, 3242b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register second, 3243b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register scratch1, 3244b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Register scratch2, 3245b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org Label* failure) { 3246b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org // Check that neither is a smi. 3247b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org and_(scratch1, first, Operand(second)); 32487b26015ac58e54e88f4214e248f772ad4f055477whesse@chromium.org JumpIfSmi(scratch1, failure); 3249b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org JumpIfNonSmisNotBothSequentialAsciiStrings(first, 3250b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org second, 3251b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org scratch1, 3252b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org scratch2, 3253b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org failure); 3254b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org} 3255b302e56e5b70c4504faa2adf4ec3efb64a9d3e38sgjesse@chromium.org 3256ac6aa175ab59d65cfb7a88dbb621e1d7f1a80b8fsgjesse@chromium.org 32571510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.orgvoid MacroAssembler::JumpIfNotUniqueName(Register reg, 32581510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.org Label* not_unique_name) { 3259ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0); 3260ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org Label succeed; 3261ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org tst(reg, Operand(kIsNotStringMask | kIsNotInternalizedMask)); 3262ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org b(eq, &succeed); 32631510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.org cmp(reg, Operand(SYMBOL_TYPE)); 3264ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org b(ne, not_unique_name); 3265ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org 3266ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org bind(&succeed); 32671510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.org} 32681510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.org 32691510d58cbcf57c82a10e7d390bfe21a7ae68ba43mstarzinger@chromium.org 32705d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org// Allocates a heap number or jumps to the need_gc label if the young space 32715d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org// is full and a scavenge is needed. 32725d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.orgvoid MacroAssembler::AllocateHeapNumber(Register result, 32735d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org Register scratch1, 32745d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org Register scratch2, 32755ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org Register heap_number_map, 3276c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org Label* gc_required, 3277c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org TaggingMode tagging_mode) { 32785d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org // Allocate an object in the heap for the heap number and tag it as a heap 32795d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org // object. 32802bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org Allocate(HeapNumber::kSize, result, scratch1, scratch2, gc_required, 32812bda543d75374afd8d7e98f56ca99a57ae1b7bd1svenpanne@chromium.org tagging_mode == TAG_RESULT ? TAG_OBJECT : NO_ALLOCATION_FLAGS); 32825d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org 32835ad5acef6bd4ebc785f946d8bcc2a88b1e031827ricow@chromium.org // Store heap number map in the allocated object. 328432d7dbafe29be06cec1edd36c31fbe2865c799f4ulan@chromium.org AssertIsRoot(heap_number_map, Heap::kHeapNumberMapRootIndex); 3285c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org if (tagging_mode == TAG_RESULT) { 3286c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org str(heap_number_map, FieldMemOperand(result, HeapObject::kMapOffset)); 3287c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } else { 3288c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org str(heap_number_map, MemOperand(result, HeapObject::kMapOffset)); 3289c859c4f83f6ec3e010213dbbe447cc1f927d01c5svenpanne@chromium.org } 32905d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org} 32915d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org 32925d8f0e6e7b477f422e3064bdf0dd5f2a23f75544kmillikin@chromium.org 329332d961d4454609ab4251a760fc46b19f661da90clrn@chromium.orgvoid MacroAssembler::AllocateHeapNumberWithValue(Register result, 329432d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org DwVfpRegister value, 329532d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org Register scratch1, 329632d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org Register scratch2, 329732d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org Register heap_number_map, 329832d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org Label* gc_required) { 329932d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org AllocateHeapNumber(result, scratch1, scratch2, heap_number_map, gc_required); 330032d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org sub(scratch1, result, Operand(kHeapObjectTag)); 330132d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org vstr(value, scratch1, HeapNumber::kValueOffset); 330232d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org} 330332d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 330432d961d4454609ab4251a760fc46b19f661da90clrn@chromium.org 3305c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org// Copies a fixed number of fields of heap objects from src to dst. 3306c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.orgvoid MacroAssembler::CopyFields(Register dst, 3307c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org Register src, 3308fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch, 3309c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org int field_count) { 3310e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org int double_count = field_count / (DwVfpRegister::kSizeInBytes / kPointerSize); 3311e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org for (int i = 0; i < double_count; i++) { 3312e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org vldr(double_scratch, FieldMemOperand(src, i * DwVfpRegister::kSizeInBytes)); 3313e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org vstr(double_scratch, FieldMemOperand(dst, i * DwVfpRegister::kSizeInBytes)); 3314c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org } 3315c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org 3316e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org STATIC_ASSERT(SwVfpRegister::kSizeInBytes == kPointerSize); 3317e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org STATIC_ASSERT(2 * SwVfpRegister::kSizeInBytes == DwVfpRegister::kSizeInBytes); 3318e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org 3319e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org int remain = field_count % (DwVfpRegister::kSizeInBytes / kPointerSize); 3320e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org if (remain != 0) { 3321fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vldr(double_scratch.low(), 3322e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org FieldMemOperand(src, (field_count - 1) * kPointerSize)); 3323fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vstr(double_scratch.low(), 3324e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org FieldMemOperand(dst, (field_count - 1) * kPointerSize)); 3325c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org } 3326c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org} 3327c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org 3328c4e51ac6d26b42753a57a4a9e4a419243b50151clrn@chromium.org 33299ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.orgvoid MacroAssembler::CopyBytes(Register src, 33309ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Register dst, 33319ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Register length, 33329ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org Register scratch) { 3333528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Label align_loop_1, word_loop, byte_loop, byte_loop_1, done; 33349ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 33359ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org // Align src before copying in word size chunks. 3336528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org cmp(length, Operand(kPointerSize)); 3337528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org b(le, &byte_loop); 3338528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org 33399ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bind(&align_loop_1); 33409ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org tst(src, Operand(kPointerSize - 1)); 33419ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org b(eq, &word_loop); 33429ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ldrb(scratch, MemOperand(src, 1, PostIndex)); 33439ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 33449ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org sub(length, length, Operand(1), SetCC); 3345528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org b(&align_loop_1); 33469ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org // Copy bytes in word size chunks. 33479ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bind(&word_loop); 3348badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 33499ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org tst(src, Operand(kPointerSize - 1)); 3350594006017e46d82ed7146611dc12c20e3c509c7ddanno@chromium.org Assert(eq, kExpectingAlignmentForCopyBytes); 33519ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org } 33529ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org cmp(length, Operand(kPointerSize)); 33539ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org b(lt, &byte_loop); 33549ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ldr(scratch, MemOperand(src, kPointerSize, PostIndex)); 335589e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org if (CpuFeatures::IsSupported(UNALIGNED_ACCESSES)) { 335689e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org str(scratch, MemOperand(dst, kPointerSize, PostIndex)); 335789e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org } else { 335889e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 335989e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org mov(scratch, Operand(scratch, LSR, 8)); 336089e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 336189e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org mov(scratch, Operand(scratch, LSR, 8)); 336289e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 336389e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org mov(scratch, Operand(scratch, LSR, 8)); 336489e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 336589e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org } 33669ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org sub(length, length, Operand(kPointerSize)); 33679ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org b(&word_loop); 33689ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 33699ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org // Copy the last bytes if any left. 33709ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bind(&byte_loop); 337159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org cmp(length, Operand::Zero()); 33729ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org b(eq, &done); 33739ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bind(&byte_loop_1); 33749ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org ldrb(scratch, MemOperand(src, 1, PostIndex)); 33759ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org strb(scratch, MemOperand(dst, 1, PostIndex)); 33769ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org sub(length, length, Operand(1), SetCC); 33779ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org b(ne, &byte_loop_1); 33789ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org bind(&done); 33799ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org} 33809ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 33819ee27ae43ab88e9bb6417ff9e27af64e0cf13729ager@chromium.org 3382c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::InitializeFieldsWithFiller(Register start_offset, 3383c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register end_offset, 3384c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register filler) { 3385c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label loop, entry; 3386c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(&entry); 3387c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&loop); 3388c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com str(filler, MemOperand(start_offset, kPointerSize, PostIndex)); 3389c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&entry); 3390c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com cmp(start_offset, end_offset); 3391c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(lt, &loop); 3392c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3393c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3394c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3395003650ee766f5e92756d470a37973fd371757485yangguo@chromium.orgvoid MacroAssembler::CheckFor32DRegs(Register scratch) { 3396003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org mov(scratch, Operand(ExternalReference::cpu_features())); 3397003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org ldr(scratch, MemOperand(scratch)); 3398003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org tst(scratch, Operand(1u << VFP32DREGS)); 3399003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org} 3400003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org 3401003650ee766f5e92756d470a37973fd371757485yangguo@chromium.org 340277ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.orgvoid MacroAssembler::SaveFPRegs(Register location, Register scratch) { 340377ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org CheckFor32DRegs(scratch); 340477ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org vstm(db_w, location, d16, d31, ne); 340577ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org sub(location, location, Operand(16 * kDoubleSize), LeaveCC, eq); 340677ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org vstm(db_w, location, d0, d15); 340777ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org} 340877ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org 340977ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org 341077ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.orgvoid MacroAssembler::RestoreFPRegs(Register location, Register scratch) { 341177ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org CheckFor32DRegs(scratch); 341277ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org vldm(ia_w, location, d0, d15); 341377ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org vldm(ia_w, location, d16, d31, ne); 341477ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org add(location, location, Operand(16 * kDoubleSize), LeaveCC, eq); 341577ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org} 341677ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org 341777ca49ac05d25684c89442029c22f5b2bce94395ulan@chromium.org 3418ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.orgvoid MacroAssembler::JumpIfBothInstanceTypesAreNotSequentialAscii( 3419ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Register first, 3420ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Register second, 3421ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Register scratch1, 3422ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Register scratch2, 3423ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Label* failure) { 3424c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org const int kFlatAsciiStringMask = 342546a2a51ad190697e0f62c3060ce02a9de5820a07yangguo@chromium.org kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; 3426c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org const int kFlatAsciiStringTag = 3427c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org kStringTag | kOneByteStringTag | kSeqStringTag; 3428ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org and_(scratch1, first, Operand(kFlatAsciiStringMask)); 3429ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org and_(scratch2, second, Operand(kFlatAsciiStringMask)); 3430ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org cmp(scratch1, Operand(kFlatAsciiStringTag)); 3431ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org // Ignore second test if first test failed. 3432ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org cmp(scratch2, Operand(kFlatAsciiStringTag), eq); 3433ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org b(ne, failure); 3434ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org} 3435ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 3436ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 3437ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.orgvoid MacroAssembler::JumpIfInstanceTypeIsNotSequentialAscii(Register type, 3438ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Register scratch, 3439ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org Label* failure) { 3440c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org const int kFlatAsciiStringMask = 344146a2a51ad190697e0f62c3060ce02a9de5820a07yangguo@chromium.org kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; 3442c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org const int kFlatAsciiStringTag = 3443c73d55b355913690124f3ee70c344035431cdd3ayangguo@chromium.org kStringTag | kOneByteStringTag | kSeqStringTag; 3444ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org and_(scratch, type, Operand(kFlatAsciiStringMask)); 3445ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org cmp(scratch, Operand(kFlatAsciiStringTag)); 3446ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org b(ne, failure); 3447ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org} 3448ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 3449ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgstatic const int kRegisterPassedArguments = 4; 3450ce5e87bd905d592a8bd612b3dedf7a994177c13aager@chromium.org 3451ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org 34528e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgint MacroAssembler::CalculateStackPassedWords(int num_reg_arguments, 34538e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_double_arguments) { 34548e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int stack_passed_words = 0; 34558e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org if (use_eabi_hardfloat()) { 34568e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org // In the hard floating point calling convention, we can use 34578e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org // all double registers to pass doubles. 3458a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.org if (num_double_arguments > DoubleRegister::NumRegisters()) { 34598e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org stack_passed_words += 3460a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.org 2 * (num_double_arguments - DoubleRegister::NumRegisters()); 34618e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 34628e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } else { 34638e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org // In the soft floating point calling convention, every double 34648e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org // argument is passed using two registers. 34658e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org num_reg_arguments += 2 * num_double_arguments; 34668e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 3467357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // Up to four simple arguments are passed in registers r0..r3. 34688e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org if (num_reg_arguments > kRegisterPassedArguments) { 34698e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org stack_passed_words += num_reg_arguments - kRegisterPassedArguments; 34708e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 34718e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org return stack_passed_words; 34728e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 34738e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 34748e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 34759af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.orgvoid MacroAssembler::EmitSeqStringSetCharCheck(Register string, 34769af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org Register index, 34779af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org Register value, 34789af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org uint32_t encoding_mask) { 34799af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org Label is_object; 34809af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org SmiTst(string); 348105150ab746caefd8e734c394ecc7863200ca04cfmachenbach@chromium.org Check(ne, kNonObject); 34829af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 34839af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org ldr(ip, FieldMemOperand(string, HeapObject::kMapOffset)); 34849af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org ldrb(ip, FieldMemOperand(ip, Map::kInstanceTypeOffset)); 34859af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 34869af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org and_(ip, ip, Operand(kStringRepresentationMask | kStringEncodingMask)); 34879af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org cmp(ip, Operand(encoding_mask)); 348805150ab746caefd8e734c394ecc7863200ca04cfmachenbach@chromium.org Check(eq, kUnexpectedStringType); 34899af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 34909af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org // The index is assumed to be untagged coming in, tag it to compare with the 34919af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org // string length without using a temp register, it is restored at the end of 34929af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org // this function. 34939af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org Label index_tag_ok, index_tag_bad; 34949af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org TrySmiTag(index, index, &index_tag_bad); 34959af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org b(&index_tag_ok); 34969af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org bind(&index_tag_bad); 349705150ab746caefd8e734c394ecc7863200ca04cfmachenbach@chromium.org Abort(kIndexIsTooLarge); 34989af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org bind(&index_tag_ok); 34999af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 35009af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org ldr(ip, FieldMemOperand(string, String::kLengthOffset)); 35019af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org cmp(index, ip); 350205150ab746caefd8e734c394ecc7863200ca04cfmachenbach@chromium.org Check(lt, kIndexIsTooLarge); 35039af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 35049af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org cmp(index, Operand(Smi::FromInt(0))); 350505150ab746caefd8e734c394ecc7863200ca04cfmachenbach@chromium.org Check(ge, kIndexIsNegative); 35069af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 35079af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org SmiUntag(index, index); 35089af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org} 35099af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 35109af454f6b1c6a921ac79ba0b9a979c73adb2ca1emachenbach@chromium.org 35118e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgvoid MacroAssembler::PrepareCallCFunction(int num_reg_arguments, 35128e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_double_arguments, 35138e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org Register scratch) { 35148e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int frame_alignment = ActivationFrameAlignment(); 35158e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int stack_passed_arguments = CalculateStackPassedWords( 35168e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org num_reg_arguments, num_double_arguments); 3517c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org if (frame_alignment > kPointerSize) { 3518357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // Make stack end at alignment and make room for num_arguments - 4 words 3519357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // and the original value of sp. 3520357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org mov(scratch, sp); 3521357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org sub(sp, sp, Operand((stack_passed_arguments + 1) * kPointerSize)); 3522c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org ASSERT(IsPowerOf2(frame_alignment)); 3523c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org and_(sp, sp, Operand(-frame_alignment)); 3524357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org str(scratch, MemOperand(sp, stack_passed_arguments * kPointerSize)); 3525357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } else { 3526357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org sub(sp, sp, Operand(stack_passed_arguments * kPointerSize)); 3527357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } 3528357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org} 3529357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 3530357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 35318e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgvoid MacroAssembler::PrepareCallCFunction(int num_reg_arguments, 35328e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org Register scratch) { 35338e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org PrepareCallCFunction(num_reg_arguments, 0, scratch); 35348e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35358e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35368e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35374ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.orgvoid MacroAssembler::MovToFloatParameter(DwVfpRegister src) { 35384ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org ASSERT(src.is(d0)); 35399f18d9111f676f2899d9aa2444130c985eb75395machenbach@chromium.org if (!use_eabi_hardfloat()) { 35404ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org vmov(r0, r1, src); 35418e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 35428e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35438e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35448e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35454ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org// On ARM this is just a synonym to make the purpose clear. 35464ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.orgvoid MacroAssembler::MovToFloatResult(DwVfpRegister src) { 35474ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org MovToFloatParameter(src); 35488e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35498e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35508e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35514ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.orgvoid MacroAssembler::MovToFloatParameters(DwVfpRegister src1, 35524ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org DwVfpRegister src2) { 35534ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org ASSERT(src1.is(d0)); 35544ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org ASSERT(src2.is(d1)); 35554ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org if (!use_eabi_hardfloat()) { 35564ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org vmov(r0, r1, src1); 35574ddd2f1981d343a2efe6609a3e0ce6b9c80b6ed9machenbach@chromium.org vmov(r2, r3, src2); 35588e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org } 35598e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35608e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35618e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 3562357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.orgvoid MacroAssembler::CallCFunction(ExternalReference function, 35638e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_reg_arguments, 35648e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_double_arguments) { 3565c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(ip, Operand(function)); 3566c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CallCFunctionHelper(ip, num_reg_arguments, num_double_arguments); 3567ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org} 3568ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.org 35698e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 3570ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgvoid MacroAssembler::CallCFunction(Register function, 3571c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int num_reg_arguments, 3572c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int num_double_arguments) { 3573c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CallCFunctionHelper(function, num_reg_arguments, num_double_arguments); 35748e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35758e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35768e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35778e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgvoid MacroAssembler::CallCFunction(ExternalReference function, 35788e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_arguments) { 35798e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org CallCFunction(function, num_arguments, 0); 35808e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org} 35818e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35828e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org 35838e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.orgvoid MacroAssembler::CallCFunction(Register function, 35848e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_arguments) { 3585c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CallCFunction(function, num_arguments, 0); 3586357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org} 3587357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 3588357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 3589ea88ce93dcb41a9200ec8747ae7642a5db1f4ce7sgjesse@chromium.orgvoid MacroAssembler::CallCFunctionHelper(Register function, 35908e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_reg_arguments, 35918e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int num_double_arguments) { 3592c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(has_frame()); 3593c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // Make sure that the stack is aligned before calling a C function unless 3594c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // running in the simulator. The simulator has its own alignment check which 3595c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // provides more information. 359693a47f4837f2137c8d8349250fd8e91da3108126jkummerow@chromium.org#if V8_HOST_ARCH_ARM 3597badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 3598c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org int frame_alignment = OS::ActivationFrameAlignment(); 3599c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org int frame_alignment_mask = frame_alignment - 1; 3600c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org if (frame_alignment > kPointerSize) { 3601c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org ASSERT(IsPowerOf2(frame_alignment)); 3602c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org Label alignment_as_expected; 3603c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org tst(sp, Operand(frame_alignment_mask)); 3604c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org b(eq, &alignment_as_expected); 3605c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // Don't use Check here, as it will call Runtime_Abort possibly 3606c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org // re-entering here. 3607c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org stop("Unexpected alignment"); 3608c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org bind(&alignment_as_expected); 3609c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org } 3610c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org } 3611c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org#endif 3612c9c80823e038328f2e1060d7feef0762a50adf06ricow@chromium.org 3613357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // Just call directly. The function called cannot cause a GC, or 3614357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // allow preemption, so the return address in the link register 3615357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org // stays correct. 3616357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org Call(function); 36178e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org int stack_passed_arguments = CalculateStackPassedWords( 36188e8294a88dc7d58f579aee0ba08c19fc8a616e2dsgjesse@chromium.org num_reg_arguments, num_double_arguments); 3619dcebac0f4c6c0da579b7cc91a0cbba8f3c820c8dricow@chromium.org if (ActivationFrameAlignment() > kPointerSize) { 3620357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org ldr(sp, MemOperand(sp, stack_passed_arguments * kPointerSize)); 3621357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } else { 3622357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org add(sp, sp, Operand(stack_passed_arguments * sizeof(kPointerSize))); 3623357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org } 3624357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org} 3625357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 3626357bf65ed5309ac3a2c4bf20b6ce7770488787c2ager@chromium.org 36270a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.orgvoid MacroAssembler::GetRelocatedValueLocation(Register ldr_location, 3628763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org Register result) { 36290a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org const uint32_t kLdrOffsetMask = (1 << 12) - 1; 36300a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org ldr(result, MemOperand(ldr_location)); 3631badaffc570baec00166b0ad3bdc96995751a7e13ricow@chromium.org if (emit_debug_code()) { 3632763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org // Check that the instruction is a ldr reg, [<pc or pp> + offset] . 3633763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org if (FLAG_enable_ool_constant_pool) { 3634763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org and_(result, result, Operand(kLdrPpPattern)); 3635763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org cmp(result, Operand(kLdrPpPattern)); 3636763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org Check(eq, kTheInstructionToPatchShouldBeALoadFromPp); 3637763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org } else { 3638763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org and_(result, result, Operand(kLdrPCPattern)); 3639763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org cmp(result, Operand(kLdrPCPattern)); 3640763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org Check(eq, kTheInstructionToPatchShouldBeALoadFromPc); 3641763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org } 36420a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org // Result was clobbered. Restore it. 36430a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org ldr(result, MemOperand(ldr_location)); 36440a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org } 36450a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org // Get the address of the constant. 36460a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org and_(result, result, Operand(kLdrOffsetMask)); 3647763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org if (FLAG_enable_ool_constant_pool) { 3648763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org add(result, pp, Operand(result)); 3649763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org } else { 3650763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org add(result, ldr_location, Operand(result)); 3651763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org add(result, result, Operand(Instruction::kPCReadOffset)); 3652763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org } 36530a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org} 36540a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 36550a4e901cdfb5505a896d30aa8c2e04fce0fbe069vegorov@chromium.org 3656c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::CheckPageFlag( 3657c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register object, 3658c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch, 3659c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int mask, 3660c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Condition cc, 3661c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* condition_met) { 366233e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org Bfc(scratch, object, 0, kPageSizeBits); 3663c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(scratch, MemOperand(scratch, MemoryChunk::kFlagsOffset)); 3664c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(scratch, Operand(mask)); 3665c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(cc, condition_met); 3666c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3667c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3668c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3669f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.orgvoid MacroAssembler::CheckMapDeprecated(Handle<Map> map, 3670f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org Register scratch, 3671f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org Label* if_deprecated) { 3672f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org if (map->CanBeDeprecated()) { 3673f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org mov(scratch, Operand(map)); 3674f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org ldr(scratch, FieldMemOperand(scratch, Map::kBitField3Offset)); 36753c3c8d733702cb2b41471efa5eead1faf5b5711bmachenbach@chromium.org tst(scratch, Operand(Map::Deprecated::kMask)); 3676f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org b(ne, if_deprecated); 3677f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org } 3678f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org} 3679f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org 3680f005df6c3232e65028420519fbab7284bc9b33aedanno@chromium.org 3681c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::JumpIfBlack(Register object, 3682c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch0, 3683c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch1, 3684c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* on_black) { 3685c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern. 3686c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(strcmp(Marking::kBlackBitPattern, "10") == 0); 3687c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3688c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3689c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3690c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::HasColor(Register object, 3691c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register bitmap_scratch, 3692c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register mask_scratch, 3693c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* has_color, 3694c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int first_bit, 3695c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com int second_bit) { 3696c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(!AreAliased(object, bitmap_scratch, mask_scratch, no_reg)); 3697c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3698c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com GetMarkBits(object, bitmap_scratch, mask_scratch); 3699c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3700c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label other_color, word_boundary; 3701c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(ip, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize)); 3702c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(ip, Operand(mask_scratch)); 3703c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(first_bit == 1 ? eq : ne, &other_color); 3704c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Shift left 1 by adding. 3705c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com add(mask_scratch, mask_scratch, Operand(mask_scratch), SetCC); 3706c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &word_boundary); 3707c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(ip, Operand(mask_scratch)); 3708c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(second_bit == 1 ? ne : eq, has_color); 3709c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com jmp(&other_color); 3710c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3711c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&word_boundary); 3712c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(ip, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize + kPointerSize)); 3713c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(ip, Operand(1)); 3714c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(second_bit == 1 ? ne : eq, has_color); 3715c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&other_color); 3716c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3717c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3718c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3719c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com// Detect some, but not all, common pointer-free objects. This is used by the 3720c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com// incremental write barrier which doesn't care about oddballs (they are always 3721c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com// marked black immediately so this code is not hit). 3722c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::JumpIfDataObject(Register value, 3723c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register scratch, 3724c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* not_data_object) { 3725c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label is_data_object; 3726c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(scratch, FieldMemOperand(value, HeapObject::kMapOffset)); 3727c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CompareRoot(scratch, Heap::kHeapNumberMapRootIndex); 3728c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &is_data_object); 3729c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(kIsIndirectStringTag == 1 && kIsIndirectStringMask == 1); 3730c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(kNotStringTag == 0x80 && kIsNotStringMask == 0x80); 3731c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // If it's a string and it's not a cons string then it's an object containing 3732c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // no GC pointers. 3733c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldrb(scratch, FieldMemOperand(scratch, Map::kInstanceTypeOffset)); 3734c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(scratch, Operand(kIsIndirectStringMask | kIsNotStringMask)); 3735c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(ne, not_data_object); 3736c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&is_data_object); 3737c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3738c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3739c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3740c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::GetMarkBits(Register addr_reg, 3741c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register bitmap_reg, 3742c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register mask_reg) { 3743c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(!AreAliased(addr_reg, bitmap_reg, mask_reg, no_reg)); 3744c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com and_(bitmap_reg, addr_reg, Operand(~Page::kPageAlignmentMask)); 3745c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Ubfx(mask_reg, addr_reg, kPointerSizeLog2, Bitmap::kBitsPerCellLog2); 3746c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com const int kLowBits = kPointerSizeLog2 + Bitmap::kBitsPerCellLog2; 3747c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Ubfx(ip, addr_reg, kLowBits, kPageSizeBits - kLowBits); 3748c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com add(bitmap_reg, bitmap_reg, Operand(ip, LSL, kPointerSizeLog2)); 3749c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(ip, Operand(1)); 3750c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(mask_reg, Operand(ip, LSL, mask_reg)); 3751c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3752c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3753c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3754c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.comvoid MacroAssembler::EnsureNotWhite( 3755c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register value, 3756c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register bitmap_scratch, 3757c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register mask_scratch, 3758c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register load_scratch, 3759c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label* value_is_white_and_not_data) { 3760c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(!AreAliased(value, bitmap_scratch, mask_scratch, ip)); 3761c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com GetMarkBits(value, bitmap_scratch, mask_scratch); 3762c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3763c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // If the value is black or grey we don't need to do anything. 3764c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(strcmp(Marking::kWhiteBitPattern, "00") == 0); 3765c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(strcmp(Marking::kBlackBitPattern, "10") == 0); 3766c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(strcmp(Marking::kGreyBitPattern, "11") == 0); 3767c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(strcmp(Marking::kImpossibleBitPattern, "01") == 0); 3768c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3769c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label done; 3770c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3771c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Since both black and grey have a 1 in the first position and white does 3772c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // not have a 1 there we only need to check one bit. 3773c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(load_scratch, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize)); 3774c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(mask_scratch, load_scratch); 3775c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(ne, &done); 3776c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3777f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com if (emit_debug_code()) { 3778c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Check for impossible bit pattern. 3779c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label ok; 3780c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // LSL may overflow, making the check conservative. 3781c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(load_scratch, Operand(mask_scratch, LSL, 1)); 3782c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &ok); 3783c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com stop("Impossible marking bit pattern"); 3784c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&ok); 3785c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com } 3786c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3787c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Value is white. We check whether it is data that doesn't need scanning. 3788c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Currently only checks for HeapNumber and non-cons strings. 3789c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register map = load_scratch; // Holds map while checking type. 3790c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register length = load_scratch; // Holds length of object after testing type. 3791c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Label is_data_object; 3792c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3793c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Check for heap-number 3794c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(map, FieldMemOperand(value, HeapObject::kMapOffset)); 3795c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com CompareRoot(map, Heap::kHeapNumberMapRootIndex); 3796c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(length, Operand(HeapNumber::kSize), LeaveCC, eq); 3797c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(eq, &is_data_object); 3798c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3799c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Check for strings. 3800c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(kIsIndirectStringTag == 1 && kIsIndirectStringMask == 1); 3801c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(kNotStringTag == 0x80 && kIsNotStringMask == 0x80); 3802c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // If it's a string and it's not a cons string then it's an object containing 3803c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // no GC pointers. 3804c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com Register instance_type = load_scratch; 3805c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldrb(instance_type, FieldMemOperand(map, Map::kInstanceTypeOffset)); 3806c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(instance_type, Operand(kIsIndirectStringMask | kIsNotStringMask)); 3807c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(ne, value_is_white_and_not_data); 3808c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // It's a non-indirect (non-cons and non-slice) string. 3809c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // If it's external, the length is just ExternalString::kSize. 3810c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Otherwise it's String::kHeaderSize + string->length() * (1 or 2). 3811c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // External strings are the only ones with the kExternalStringTag bit 3812c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // set. 3813c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT_EQ(0, kSeqStringTag & kExternalStringTag); 3814c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT_EQ(0, kConsStringTag & kExternalStringTag); 3815c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(instance_type, Operand(kExternalStringTag)); 3816c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(length, Operand(ExternalString::kSize), LeaveCC, ne); 3817c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com b(ne, &is_data_object); 3818c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3819c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Sequential string, either ASCII or UC16. 3820c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // For ASCII (char-size of 1) we shift the smi tag away to get the length. 3821c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // For UC16 (char-size of 2) we just leave the smi tag in place, thereby 3822c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // getting the length multiplied by 2. 3823e4ac3ef2f6fa9300bc78c5a4cb7d4cb66ac6e83dmvstanton@chromium.org ASSERT(kOneByteStringTag == 4 && kStringEncodingMask == 4); 3824c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ASSERT(kSmiTag == 0 && kSmiTagSize == 1); 3825c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(ip, FieldMemOperand(value, String::kLengthOffset)); 3826c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com tst(instance_type, Operand(kStringEncodingMask)); 3827c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com mov(ip, Operand(ip, LSR, 1), LeaveCC, ne); 3828c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com add(length, ip, Operand(SeqString::kHeaderSize + kObjectAlignmentMask)); 3829c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com and_(length, length, Operand(~kObjectAlignmentMask)); 3830c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3831c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&is_data_object); 3832c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // Value is a data object, and it is white. Mark it black. Since we know 3833c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com // that the object is white we can make it black by flipping one bit. 3834c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(ip, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize)); 3835c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com orr(ip, ip, Operand(mask_scratch)); 3836c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com str(ip, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize)); 3837c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3838c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com and_(bitmap_scratch, bitmap_scratch, Operand(~Page::kPageAlignmentMask)); 3839c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com ldr(ip, MemOperand(bitmap_scratch, MemoryChunk::kLiveBytesOffset)); 3840c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com add(ip, ip, Operand(length)); 3841c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com str(ip, MemOperand(bitmap_scratch, MemoryChunk::kLiveBytesOffset)); 3842c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3843c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com bind(&done); 3844c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 3845c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3846c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 3847c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.orgvoid MacroAssembler::ClampUint8(Register output_reg, Register input_reg) { 3848c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org Usat(output_reg, 8, Operand(input_reg)); 3849c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org} 3850c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org 3851c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org 3852c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.orgvoid MacroAssembler::ClampDoubleToUint8(Register result_reg, 3853a6bbcc801f63c451f814d6da77a1a48fba3d36c6yangguo@chromium.org DwVfpRegister input_reg, 3854fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org LowDwVfpRegister double_scratch) { 3855c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org Label done; 3856c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org 3857e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org // Handle inputs >= 255 (including +infinity). 3858fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org Vmov(double_scratch, 255.0, result_reg); 3859c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org mov(result_reg, Operand(255)); 3860e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org VFPCompareAndSetFlags(input_reg, double_scratch); 3861e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org b(ge, &done); 3862e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org 3863e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org // For inputs < 255 (including negative) vcvt_u32_f64 with round-to-nearest 3864e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org // rounding mode will provide the correct result. 3865e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org vcvt_u32_f64(double_scratch.low(), input_reg, kFPSCRRounding); 3866fb732b17922ea75830be4db6b80534c4827d8a55jkummerow@chromium.org vmov(result_reg, double_scratch.low()); 3867e9fd6580f52407c94d77bfcb4be04207f2ebb2f1machenbach@chromium.org 3868c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org bind(&done); 3869c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org} 3870c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org 3871c53e10d01c5495df3896b9d318910b58688c6929kmillikin@chromium.org 387240cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.orgvoid MacroAssembler::LoadInstanceDescriptors(Register map, 387389e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org Register descriptors) { 387489e18f5599cb4cd462cb1ed324addd7388fb4d60rossberg@chromium.org ldr(descriptors, FieldMemOperand(map, Map::kDescriptorsOffset)); 387540cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org} 387640cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org 387740cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org 387806ab2ec756e44eeaf7500b9794f9d2abc79dc8cfverwaest@chromium.orgvoid MacroAssembler::NumberOfOwnDescriptors(Register dst, Register map) { 387933e09c8efd078308de3c77a88301566f65c07befverwaest@chromium.org ldr(dst, FieldMemOperand(map, Map::kBitField3Offset)); 388006ab2ec756e44eeaf7500b9794f9d2abc79dc8cfverwaest@chromium.org DecodeField<Map::NumberOfOwnDescriptorsBits>(dst); 388106ab2ec756e44eeaf7500b9794f9d2abc79dc8cfverwaest@chromium.org} 388206ab2ec756e44eeaf7500b9794f9d2abc79dc8cfverwaest@chromium.org 388306ab2ec756e44eeaf7500b9794f9d2abc79dc8cfverwaest@chromium.org 3884355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.orgvoid MacroAssembler::EnumLength(Register dst, Register map) { 3885355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org STATIC_ASSERT(Map::EnumLengthBits::kShift == 0); 3886355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org ldr(dst, FieldMemOperand(map, Map::kBitField3Offset)); 38873c3c8d733702cb2b41471efa5eead1faf5b5711bmachenbach@chromium.org and_(dst, dst, Operand(Map::EnumLengthBits::kMask)); 38883c3c8d733702cb2b41471efa5eead1faf5b5711bmachenbach@chromium.org SmiTag(dst); 3889355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org} 3890355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org 3891355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org 3892be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.orgvoid MacroAssembler::CheckEnumCache(Register null_value, Label* call_runtime) { 3893be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org Register empty_fixed_array_value = r6; 3894be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org LoadRoot(empty_fixed_array_value, Heap::kEmptyFixedArrayRootIndex); 3895355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org Label next, start; 3896355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org mov(r2, r0); 3897be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org 3898355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org // Check if the enum length field is properly initialized, indicating that 3899355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org // there is an enum cache. 3900355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org ldr(r1, FieldMemOperand(r2, HeapObject::kMapOffset)); 3901657d53b99cb4d261f8245bcb4248c39eb0a2b10frossberg@chromium.org 3902355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org EnumLength(r3, r1); 3903af9cfcbed5daf6e636e189bce451c6fafdbb127dmachenbach@chromium.org cmp(r3, Operand(Smi::FromInt(kInvalidEnumCacheSentinel))); 3904de64f721c489207a7b9018406d39c7fb04bb9424verwaest@chromium.org b(eq, call_runtime); 3905de64f721c489207a7b9018406d39c7fb04bb9424verwaest@chromium.org 3906355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org jmp(&start); 3907355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org 3908355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org bind(&next); 3909355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org ldr(r1, FieldMemOperand(r2, HeapObject::kMapOffset)); 3910be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org 3911be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org // For all objects but the receiver, check that the cache is empty. 3912355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org EnumLength(r3, r1); 3913355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org cmp(r3, Operand(Smi::FromInt(0))); 3914355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org b(ne, call_runtime); 3915355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org 3916355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org bind(&start); 3917355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org 3918355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org // Check that there are no elements. Register r2 contains the current JS 3919355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org // object we've reached through the prototype chain. 39206d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org Label no_elements; 3921355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org ldr(r2, FieldMemOperand(r2, JSObject::kElementsOffset)); 3922355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org cmp(r2, empty_fixed_array_value); 39236d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org b(eq, &no_elements); 39246d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org 39256d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org // Second chance, the object may be using the empty slow element dictionary. 39266d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org CompareRoot(r2, Heap::kEmptySlowElementDictionaryRootIndex); 3927be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org b(ne, call_runtime); 3928be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org 39296d26cbb00b8ff12ecf86400c59f4a18d3850f22dmachenbach@chromium.org bind(&no_elements); 3930355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org ldr(r2, FieldMemOperand(r1, Map::kPrototypeOffset)); 3931355cfd19c23ac613f2738a40e356ea48297f7d5eyangguo@chromium.org cmp(r2, null_value); 3932be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org b(ne, &next); 3933be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org} 3934be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org 3935be6bd10d8264b7a05e0a04407eb98b253bc0f152kmillikin@chromium.org 3936ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.orgvoid MacroAssembler::TestJSArrayForAllocationMemento( 393759297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org Register receiver_reg, 3938b4968bea48ba224f54110f626278e2c04649dd5bmstarzinger@chromium.org Register scratch_reg, 3939b4968bea48ba224f54110f626278e2c04649dd5bmstarzinger@chromium.org Label* no_memento_found) { 394059297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org ExternalReference new_space_start = 394159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org ExternalReference::new_space_start(isolate()); 394259297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org ExternalReference new_space_allocation_top = 394359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org ExternalReference::new_space_allocation_top_address(isolate()); 39446bec0093ef661b53a1e338a233d7aafb9536a307mvstanton@chromium.org add(scratch_reg, receiver_reg, 3945ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org Operand(JSArray::kSize + AllocationMemento::kSize - kHeapObjectTag)); 394659297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org cmp(scratch_reg, Operand(new_space_start)); 3947b4968bea48ba224f54110f626278e2c04649dd5bmstarzinger@chromium.org b(lt, no_memento_found); 39486bec0093ef661b53a1e338a233d7aafb9536a307mvstanton@chromium.org mov(ip, Operand(new_space_allocation_top)); 39496bec0093ef661b53a1e338a233d7aafb9536a307mvstanton@chromium.org ldr(ip, MemOperand(ip)); 39506bec0093ef661b53a1e338a233d7aafb9536a307mvstanton@chromium.org cmp(scratch_reg, ip); 3951b4968bea48ba224f54110f626278e2c04649dd5bmstarzinger@chromium.org b(gt, no_memento_found); 3952ba72ec861b69b67139c93fc6dd56f4a73c9b3135jkummerow@chromium.org ldr(scratch_reg, MemOperand(scratch_reg, -AllocationMemento::kSize)); 395359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org cmp(scratch_reg, 3954528ce02b8680a3ab6d75c7079f180a4016c69b7amachenbach@chromium.org Operand(isolate()->factory()->allocation_memento_map())); 395559297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org} 395659297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org 395759297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org 39581e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.orgRegister GetRegisterThatIsNotOneOf(Register reg1, 39591e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register reg2, 39601e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register reg3, 39611e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register reg4, 39621e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register reg5, 39631e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register reg6) { 39641e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org RegList regs = 0; 39651e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg1.is_valid()) regs |= reg1.bit(); 39661e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg2.is_valid()) regs |= reg2.bit(); 39671e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg3.is_valid()) regs |= reg3.bit(); 39681e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg4.is_valid()) regs |= reg4.bit(); 39691e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg5.is_valid()) regs |= reg5.bit(); 39701e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (reg6.is_valid()) regs |= reg6.bit(); 39711e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 39721e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org for (int i = 0; i < Register::NumAllocatableRegisters(); i++) { 39731e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org Register candidate = Register::FromAllocationIndex(i); 39741e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org if (regs & candidate.bit()) continue; 39751e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org return candidate; 39761e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org } 39771e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org UNREACHABLE(); 39781e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org return no_reg; 39791e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org} 39801e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 39811e8da746019f818a22dfdc6f691dbc0447048cadjkummerow@chromium.org 3982e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.orgvoid MacroAssembler::JumpIfDictionaryInPrototypeChain( 3983e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Register object, 3984e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Register scratch0, 3985e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Register scratch1, 3986e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Label* found) { 3987e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org ASSERT(!scratch1.is(scratch0)); 3988e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Factory* factory = isolate()->factory(); 3989e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Register current = scratch0; 3990e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org Label loop_again; 3991e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org 3992e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org // scratch contained elements pointer. 3993e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org mov(current, object); 3994e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org 3995e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org // Loop based on the map going up the prototype chain. 3996e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org bind(&loop_again); 3997e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org ldr(current, FieldMemOperand(current, HeapObject::kMapOffset)); 3998e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org ldr(scratch1, FieldMemOperand(current, Map::kBitField2Offset)); 3999d06b9264b1c886fc80a100e9915cf8ae07fdb4e5machenbach@chromium.org DecodeField<Map::ElementsKindBits>(scratch1); 4000e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org cmp(scratch1, Operand(DICTIONARY_ELEMENTS)); 4001e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org b(eq, found); 4002e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org ldr(current, FieldMemOperand(current, Map::kPrototypeOffset)); 4003e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org cmp(current, Operand(factory->null_value())); 4004e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org b(ne, &loop_again); 4005e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org} 4006e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org 4007e8412be858dc48afaec4959e42c5932f71a7f29bmachenbach@chromium.org 4008efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org#ifdef DEBUG 4009efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.orgbool AreAliased(Register reg1, 4010efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org Register reg2, 4011efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org Register reg3, 4012efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org Register reg4, 4013efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org Register reg5, 4014efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org Register reg6) { 4015efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org int n_of_valid_regs = reg1.is_valid() + reg2.is_valid() + 4016efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org reg3.is_valid() + reg4.is_valid() + reg5.is_valid() + reg6.is_valid(); 4017efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org 4018efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org RegList regs = 0; 4019efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg1.is_valid()) regs |= reg1.bit(); 4020efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg2.is_valid()) regs |= reg2.bit(); 4021efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg3.is_valid()) regs |= reg3.bit(); 4022efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg4.is_valid()) regs |= reg4.bit(); 4023efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg5.is_valid()) regs |= reg5.bit(); 4024efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org if (reg6.is_valid()) regs |= reg6.bit(); 4025efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org int n_of_non_aliasing_regs = NumRegs(regs); 4026efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org 4027efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org return n_of_valid_regs != n_of_non_aliasing_regs; 4028c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com} 4029efdb9d70bddd496ceb6a281dadcc065efbce37a1yangguo@chromium.org#endif 4030c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 4031c3b670ff19220959730d7886892bc4beb95d2ebaerik.corry@gmail.com 40324a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.orgCodePatcher::CodePatcher(byte* address, 40334a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org int instructions, 40344a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org FlushICache flush_cache) 40354af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org : address_(address), 40364af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org size_(instructions * Assembler::kInstrSize), 40374a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org masm_(NULL, address, size_ + Assembler::kGap), 40384a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org flush_cache_(flush_cache) { 40394af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org // Create a new macro assembler pointing to the address of the code to patch. 40404af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org // The size is adjusted with kGap on order for the assembler to generate size 40414af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org // bytes of instructions without failing with buffer size constraints. 40424af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org ASSERT(masm_.reloc_info_writer.pos() == address_ + size_ + Assembler::kGap); 40434af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org} 40444af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40454af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40464af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.orgCodePatcher::~CodePatcher() { 40474af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org // Indicate that code has changed. 40484a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org if (flush_cache_ == FLUSH) { 40494a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org CPU::FlushICache(address_, size_); 40504a35c5a501e5b966f895ddea8e19c3ca232cb23fdslomov@chromium.org } 40514af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40524af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org // Check that the code was patched as expected. 40534af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org ASSERT(masm_.pc_ == address_ + size_); 40544af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org ASSERT(masm_.reloc_info_writer.pos() == address_ + size_ + Assembler::kGap); 40554af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org} 40564af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40574af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 4058496c03a64f12710e837204e261ef155601247895sgjesse@chromium.orgvoid CodePatcher::Emit(Instr instr) { 4059496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org masm()->emit(instr); 40604af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org} 40614af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40624af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40634af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.orgvoid CodePatcher::Emit(Address addr) { 40644af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org masm()->emit(reinterpret_cast<Instr>(addr)); 40654af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org} 4066496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org 4067496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org 4068496c03a64f12710e837204e261ef155601247895sgjesse@chromium.orgvoid CodePatcher::EmitCondition(Condition cond) { 4069496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org Instr instr = Assembler::instr_at(masm_.pc_); 4070496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org instr = (instr & ~kCondMask) | cond; 4071496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org masm_.emit(instr); 4072496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org} 40734af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 40744af710e493dc8583f3b7b7ce65127ad4e7c3f8a1ager@chromium.org 4075763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.orgvoid MacroAssembler::TruncatingDiv(Register result, 4076763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org Register dividend, 4077763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org int32_t divisor) { 4078bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org ASSERT(!dividend.is(result)); 4079bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org ASSERT(!dividend.is(ip)); 4080bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org ASSERT(!result.is(ip)); 4081bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org MultiplierAndShift ms(divisor); 4082bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org mov(ip, Operand(ms.multiplier())); 4083bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org smull(ip, result, dividend, ip); 4084bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org if (divisor > 0 && ms.multiplier() < 0) { 4085bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org add(result, result, Operand(dividend)); 4086bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org } 4087bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org if (divisor < 0 && ms.multiplier() > 0) { 4088bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org sub(result, result, Operand(dividend)); 4089bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org } 4090bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org if (ms.shift() > 0) mov(result, Operand(result, ASR, ms.shift())); 4091763da4c1a1bd42dfafe0844b4c18f4882cc66352machenbach@chromium.org add(result, result, Operand(dividend, LSR, 31)); 4092bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org} 4093bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org 4094bcc36723a2ace28fa3b0d7dd0d1de926d313fff9machenbach@chromium.org 409543d26ecc3563a46f62a0224030667c8f8f3f6cebchristian.plesner.hansen} } // namespace v8::internal 40969dfbea4c7d423c7bc1db94425cb78e7f7cf41f78erik.corry@gmail.com 40979dfbea4c7d423c7bc1db94425cb78e7f7cf41f78erik.corry@gmail.com#endif // V8_TARGET_ARCH_ARM 4098