| Index: src/arm/ic-arm.cc
|
| ===================================================================
|
| --- src/arm/ic-arm.cc (revision 7619)
|
| +++ src/arm/ic-arm.cc (working copy)
|
| @@ -926,218 +926,7 @@
|
| __ TailCallExternalReference(ref, 2, 1);
|
| }
|
|
|
| -// Returns the code marker, or the 0 if the code is not marked.
|
| -static inline int InlinedICSiteMarker(Address address,
|
| - Address* inline_end_address) {
|
| - if (V8::UseCrankshaft()) return false;
|
|
|
| - // If the instruction after the call site is not the pseudo instruction nop1
|
| - // then this is not related to an inlined in-object property load. The nop1
|
| - // instruction is located just after the call to the IC in the deferred code
|
| - // handling the miss in the inlined code. After the nop1 instruction there is
|
| - // a branch instruction for jumping back from the deferred code.
|
| - Address address_after_call = address + Assembler::kCallTargetAddressOffset;
|
| - Instr instr_after_call = Assembler::instr_at(address_after_call);
|
| - int code_marker = MacroAssembler::GetCodeMarker(instr_after_call);
|
| -
|
| - // A negative result means the code is not marked.
|
| - if (code_marker <= 0) return 0;
|
| -
|
| - Address address_after_nop = address_after_call + Assembler::kInstrSize;
|
| - Instr instr_after_nop = Assembler::instr_at(address_after_nop);
|
| - // There may be some reg-reg move and frame merging code to skip over before
|
| - // the branch back from the DeferredReferenceGetKeyedValue code to the inlined
|
| - // code.
|
| - while (!Assembler::IsBranch(instr_after_nop)) {
|
| - address_after_nop += Assembler::kInstrSize;
|
| - instr_after_nop = Assembler::instr_at(address_after_nop);
|
| - }
|
| -
|
| - // Find the end of the inlined code for handling the load.
|
| - int b_offset =
|
| - Assembler::GetBranchOffset(instr_after_nop) + Assembler::kPcLoadDelta;
|
| - ASSERT(b_offset < 0); // Jumping back from deferred code.
|
| - *inline_end_address = address_after_nop + b_offset;
|
| -
|
| - return code_marker;
|
| -}
|
| -
|
| -
|
| -bool LoadIC::PatchInlinedLoad(Address address, Object* map, int offset) {
|
| - if (V8::UseCrankshaft()) return false;
|
| -
|
| - // Find the end of the inlined code for handling the load if this is an
|
| - // inlined IC call site.
|
| - Address inline_end_address = 0;
|
| - if (InlinedICSiteMarker(address, &inline_end_address)
|
| - != Assembler::PROPERTY_ACCESS_INLINED) {
|
| - return false;
|
| - }
|
| -
|
| - // Patch the offset of the property load instruction (ldr r0, [r1, #+XXX]).
|
| - // The immediate must be representable in 12 bits.
|
| - ASSERT((JSObject::kMaxInstanceSize - JSObject::kHeaderSize) < (1 << 12));
|
| - Address ldr_property_instr_address =
|
| - inline_end_address - Assembler::kInstrSize;
|
| - ASSERT(Assembler::IsLdrRegisterImmediate(
|
| - Assembler::instr_at(ldr_property_instr_address)));
|
| - Instr ldr_property_instr = Assembler::instr_at(ldr_property_instr_address);
|
| - ldr_property_instr = Assembler::SetLdrRegisterImmediateOffset(
|
| - ldr_property_instr, offset - kHeapObjectTag);
|
| - Assembler::instr_at_put(ldr_property_instr_address, ldr_property_instr);
|
| -
|
| - // Indicate that code has changed.
|
| - CPU::FlushICache(ldr_property_instr_address, 1 * Assembler::kInstrSize);
|
| -
|
| - // Patch the map check.
|
| - // For PROPERTY_ACCESS_INLINED, the load map instruction is generated
|
| - // 4 instructions before the end of the inlined code.
|
| - // See codgen-arm.cc CodeGenerator::EmitNamedLoad.
|
| - int ldr_map_offset = -4;
|
| - Address ldr_map_instr_address =
|
| - inline_end_address + ldr_map_offset * Assembler::kInstrSize;
|
| - Assembler::set_target_address_at(ldr_map_instr_address,
|
| - reinterpret_cast<Address>(map));
|
| - return true;
|
| -}
|
| -
|
| -
|
| -bool LoadIC::PatchInlinedContextualLoad(Address address,
|
| - Object* map,
|
| - Object* cell,
|
| - bool is_dont_delete) {
|
| - // Find the end of the inlined code for handling the contextual load if
|
| - // this is inlined IC call site.
|
| - Address inline_end_address = 0;
|
| - int marker = InlinedICSiteMarker(address, &inline_end_address);
|
| - if (!((marker == Assembler::PROPERTY_ACCESS_INLINED_CONTEXT) ||
|
| - (marker == Assembler::PROPERTY_ACCESS_INLINED_CONTEXT_DONT_DELETE))) {
|
| - return false;
|
| - }
|
| - // On ARM we don't rely on the is_dont_delete argument as the hint is already
|
| - // embedded in the code marker.
|
| - bool marker_is_dont_delete =
|
| - marker == Assembler::PROPERTY_ACCESS_INLINED_CONTEXT_DONT_DELETE;
|
| -
|
| - // These are the offsets from the end of the inlined code.
|
| - // See codgen-arm.cc CodeGenerator::EmitNamedLoad.
|
| - int ldr_map_offset = marker_is_dont_delete ? -5: -8;
|
| - int ldr_cell_offset = marker_is_dont_delete ? -2: -5;
|
| - if (FLAG_debug_code && marker_is_dont_delete) {
|
| - // Three extra instructions were generated to check for the_hole_value.
|
| - ldr_map_offset -= 3;
|
| - ldr_cell_offset -= 3;
|
| - }
|
| - Address ldr_map_instr_address =
|
| - inline_end_address + ldr_map_offset * Assembler::kInstrSize;
|
| - Address ldr_cell_instr_address =
|
| - inline_end_address + ldr_cell_offset * Assembler::kInstrSize;
|
| -
|
| - // Patch the map check.
|
| - Assembler::set_target_address_at(ldr_map_instr_address,
|
| - reinterpret_cast<Address>(map));
|
| - // Patch the cell address.
|
| - Assembler::set_target_address_at(ldr_cell_instr_address,
|
| - reinterpret_cast<Address>(cell));
|
| -
|
| - return true;
|
| -}
|
| -
|
| -
|
| -bool StoreIC::PatchInlinedStore(Address address, Object* map, int offset) {
|
| - if (V8::UseCrankshaft()) return false;
|
| -
|
| - // Find the end of the inlined code for the store if there is an
|
| - // inlined version of the store.
|
| - Address inline_end_address = 0;
|
| - if (InlinedICSiteMarker(address, &inline_end_address)
|
| - != Assembler::PROPERTY_ACCESS_INLINED) {
|
| - return false;
|
| - }
|
| -
|
| - // Compute the address of the map load instruction.
|
| - Address ldr_map_instr_address =
|
| - inline_end_address -
|
| - (CodeGenerator::GetInlinedNamedStoreInstructionsAfterPatch() *
|
| - Assembler::kInstrSize);
|
| -
|
| - // Update the offsets if initializing the inlined store. No reason
|
| - // to update the offsets when clearing the inlined version because
|
| - // it will bail out in the map check.
|
| - if (map != HEAP->null_value()) {
|
| - // Patch the offset in the actual store instruction.
|
| - Address str_property_instr_address =
|
| - ldr_map_instr_address + 3 * Assembler::kInstrSize;
|
| - Instr str_property_instr = Assembler::instr_at(str_property_instr_address);
|
| - ASSERT(Assembler::IsStrRegisterImmediate(str_property_instr));
|
| - str_property_instr = Assembler::SetStrRegisterImmediateOffset(
|
| - str_property_instr, offset - kHeapObjectTag);
|
| - Assembler::instr_at_put(str_property_instr_address, str_property_instr);
|
| -
|
| - // Patch the offset in the add instruction that is part of the
|
| - // write barrier.
|
| - Address add_offset_instr_address =
|
| - str_property_instr_address + Assembler::kInstrSize;
|
| - Instr add_offset_instr = Assembler::instr_at(add_offset_instr_address);
|
| - ASSERT(Assembler::IsAddRegisterImmediate(add_offset_instr));
|
| - add_offset_instr = Assembler::SetAddRegisterImmediateOffset(
|
| - add_offset_instr, offset - kHeapObjectTag);
|
| - Assembler::instr_at_put(add_offset_instr_address, add_offset_instr);
|
| -
|
| - // Indicate that code has changed.
|
| - CPU::FlushICache(str_property_instr_address, 2 * Assembler::kInstrSize);
|
| - }
|
| -
|
| - // Patch the map check.
|
| - Assembler::set_target_address_at(ldr_map_instr_address,
|
| - reinterpret_cast<Address>(map));
|
| -
|
| - return true;
|
| -}
|
| -
|
| -
|
| -bool KeyedLoadIC::PatchInlinedLoad(Address address, Object* map) {
|
| - if (V8::UseCrankshaft()) return false;
|
| -
|
| - Address inline_end_address = 0;
|
| - if (InlinedICSiteMarker(address, &inline_end_address)
|
| - != Assembler::PROPERTY_ACCESS_INLINED) {
|
| - return false;
|
| - }
|
| -
|
| - // Patch the map check.
|
| - Address ldr_map_instr_address =
|
| - inline_end_address -
|
| - (CodeGenerator::GetInlinedKeyedLoadInstructionsAfterPatch() *
|
| - Assembler::kInstrSize);
|
| - Assembler::set_target_address_at(ldr_map_instr_address,
|
| - reinterpret_cast<Address>(map));
|
| - return true;
|
| -}
|
| -
|
| -
|
| -bool KeyedStoreIC::PatchInlinedStore(Address address, Object* map) {
|
| - if (V8::UseCrankshaft()) return false;
|
| -
|
| - // Find the end of the inlined code for handling the store if this is an
|
| - // inlined IC call site.
|
| - Address inline_end_address = 0;
|
| - if (InlinedICSiteMarker(address, &inline_end_address)
|
| - != Assembler::PROPERTY_ACCESS_INLINED) {
|
| - return false;
|
| - }
|
| -
|
| - // Patch the map check.
|
| - Address ldr_map_instr_address =
|
| - inline_end_address -
|
| - (CodeGenerator::kInlinedKeyedStoreInstructionsAfterPatch *
|
| - Assembler::kInstrSize);
|
| - Assembler::set_target_address_at(ldr_map_instr_address,
|
| - reinterpret_cast<Address>(map));
|
| - return true;
|
| -}
|
| -
|
| -
|
| Object* KeyedLoadIC_Miss(Arguments args);
|
|
|
|
|
|
|