OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/v8.h" | 5 #include "src/v8.h" |
6 | 6 |
7 #include "src/arm/lithium-codegen-arm.h" | 7 #include "src/arm/lithium-codegen-arm.h" |
8 #include "src/arm/lithium-gap-resolver-arm.h" | 8 #include "src/arm/lithium-gap-resolver-arm.h" |
9 #include "src/base/bits.h" | 9 #include "src/base/bits.h" |
10 #include "src/code-factory.h" | 10 #include "src/code-factory.h" |
(...skipping 2969 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2980 | 2980 |
2981 if (no_frame_start != -1) { | 2981 if (no_frame_start != -1) { |
2982 info_->AddNoFrameRange(no_frame_start, masm_->pc_offset()); | 2982 info_->AddNoFrameRange(no_frame_start, masm_->pc_offset()); |
2983 } | 2983 } |
2984 } | 2984 } |
2985 } | 2985 } |
2986 | 2986 |
2987 | 2987 |
2988 template <class T> | 2988 template <class T> |
2989 void LCodeGen::EmitVectorLoadICRegisters(T* instr) { | 2989 void LCodeGen::EmitVectorLoadICRegisters(T* instr) { |
2990 DCHECK(FLAG_vector_ics); | |
2991 Register vector_register = ToRegister(instr->temp_vector()); | 2990 Register vector_register = ToRegister(instr->temp_vector()); |
2992 Register slot_register = VectorLoadICDescriptor::SlotRegister(); | 2991 Register slot_register = VectorLoadICDescriptor::SlotRegister(); |
2993 DCHECK(vector_register.is(VectorLoadICDescriptor::VectorRegister())); | 2992 DCHECK(vector_register.is(VectorLoadICDescriptor::VectorRegister())); |
2994 DCHECK(slot_register.is(r0)); | 2993 DCHECK(slot_register.is(r0)); |
2995 | 2994 |
2996 AllowDeferredHandleDereference vector_structure_check; | 2995 AllowDeferredHandleDereference vector_structure_check; |
2997 Handle<TypeFeedbackVector> vector = instr->hydrogen()->feedback_vector(); | 2996 Handle<TypeFeedbackVector> vector = instr->hydrogen()->feedback_vector(); |
2998 __ Move(vector_register, vector); | 2997 __ Move(vector_register, vector); |
2999 // No need to allocate this register. | 2998 // No need to allocate this register. |
3000 FeedbackVectorICSlot slot = instr->hydrogen()->slot(); | 2999 FeedbackVectorICSlot slot = instr->hydrogen()->slot(); |
3001 int index = vector->GetIndex(slot); | 3000 int index = vector->GetIndex(slot); |
3002 __ mov(slot_register, Operand(Smi::FromInt(index))); | 3001 __ mov(slot_register, Operand(Smi::FromInt(index))); |
3003 } | 3002 } |
3004 | 3003 |
3005 | 3004 |
3006 void LCodeGen::DoLoadGlobalGeneric(LLoadGlobalGeneric* instr) { | 3005 void LCodeGen::DoLoadGlobalGeneric(LLoadGlobalGeneric* instr) { |
3007 DCHECK(ToRegister(instr->context()).is(cp)); | 3006 DCHECK(ToRegister(instr->context()).is(cp)); |
3008 DCHECK(ToRegister(instr->global_object()) | 3007 DCHECK(ToRegister(instr->global_object()) |
3009 .is(LoadDescriptor::ReceiverRegister())); | 3008 .is(LoadDescriptor::ReceiverRegister())); |
3010 DCHECK(ToRegister(instr->result()).is(r0)); | 3009 DCHECK(ToRegister(instr->result()).is(r0)); |
3011 | 3010 |
3012 __ mov(LoadDescriptor::NameRegister(), Operand(instr->name())); | 3011 __ mov(LoadDescriptor::NameRegister(), Operand(instr->name())); |
3013 if (FLAG_vector_ics) { | 3012 EmitVectorLoadICRegisters<LLoadGlobalGeneric>(instr); |
3014 EmitVectorLoadICRegisters<LLoadGlobalGeneric>(instr); | |
3015 } | |
3016 ContextualMode mode = instr->for_typeof() ? NOT_CONTEXTUAL : CONTEXTUAL; | 3013 ContextualMode mode = instr->for_typeof() ? NOT_CONTEXTUAL : CONTEXTUAL; |
3017 Handle<Code> ic = CodeFactory::LoadICInOptimizedCode(isolate(), mode, | 3014 Handle<Code> ic = CodeFactory::LoadICInOptimizedCode(isolate(), mode, |
3018 PREMONOMORPHIC).code(); | 3015 PREMONOMORPHIC).code(); |
3019 CallCode(ic, RelocInfo::CODE_TARGET, instr); | 3016 CallCode(ic, RelocInfo::CODE_TARGET, instr); |
3020 } | 3017 } |
3021 | 3018 |
3022 | 3019 |
3023 void LCodeGen::DoLoadContextSlot(LLoadContextSlot* instr) { | 3020 void LCodeGen::DoLoadContextSlot(LLoadContextSlot* instr) { |
3024 Register context = ToRegister(instr->context()); | 3021 Register context = ToRegister(instr->context()); |
3025 Register result = ToRegister(instr->result()); | 3022 Register result = ToRegister(instr->result()); |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3102 } | 3099 } |
3103 | 3100 |
3104 | 3101 |
3105 void LCodeGen::DoLoadNamedGeneric(LLoadNamedGeneric* instr) { | 3102 void LCodeGen::DoLoadNamedGeneric(LLoadNamedGeneric* instr) { |
3106 DCHECK(ToRegister(instr->context()).is(cp)); | 3103 DCHECK(ToRegister(instr->context()).is(cp)); |
3107 DCHECK(ToRegister(instr->object()).is(LoadDescriptor::ReceiverRegister())); | 3104 DCHECK(ToRegister(instr->object()).is(LoadDescriptor::ReceiverRegister())); |
3108 DCHECK(ToRegister(instr->result()).is(r0)); | 3105 DCHECK(ToRegister(instr->result()).is(r0)); |
3109 | 3106 |
3110 // Name is always in r2. | 3107 // Name is always in r2. |
3111 __ mov(LoadDescriptor::NameRegister(), Operand(instr->name())); | 3108 __ mov(LoadDescriptor::NameRegister(), Operand(instr->name())); |
3112 if (FLAG_vector_ics) { | 3109 EmitVectorLoadICRegisters<LLoadNamedGeneric>(instr); |
3113 EmitVectorLoadICRegisters<LLoadNamedGeneric>(instr); | |
3114 } | |
3115 Handle<Code> ic = CodeFactory::LoadICInOptimizedCode( | 3110 Handle<Code> ic = CodeFactory::LoadICInOptimizedCode( |
3116 isolate(), NOT_CONTEXTUAL, | 3111 isolate(), NOT_CONTEXTUAL, |
3117 instr->hydrogen()->initialization_state()).code(); | 3112 instr->hydrogen()->initialization_state()).code(); |
3118 CallCode(ic, RelocInfo::CODE_TARGET, instr, NEVER_INLINE_TARGET_ADDRESS); | 3113 CallCode(ic, RelocInfo::CODE_TARGET, instr, NEVER_INLINE_TARGET_ADDRESS); |
3119 } | 3114 } |
3120 | 3115 |
3121 | 3116 |
3122 void LCodeGen::DoLoadFunctionPrototype(LLoadFunctionPrototype* instr) { | 3117 void LCodeGen::DoLoadFunctionPrototype(LLoadFunctionPrototype* instr) { |
3123 Register scratch = scratch0(); | 3118 Register scratch = scratch0(); |
3124 Register function = ToRegister(instr->function()); | 3119 Register function = ToRegister(instr->function()); |
(...skipping 830 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3955 ParameterCount count(instr->arity()); | 3950 ParameterCount count(instr->arity()); |
3956 __ InvokeFunction(r1, count, CALL_FUNCTION, generator); | 3951 __ InvokeFunction(r1, count, CALL_FUNCTION, generator); |
3957 } else { | 3952 } else { |
3958 CallKnownFunction(known_function, | 3953 CallKnownFunction(known_function, |
3959 instr->hydrogen()->formal_parameter_count(), | 3954 instr->hydrogen()->formal_parameter_count(), |
3960 instr->arity(), instr); | 3955 instr->arity(), instr); |
3961 } | 3956 } |
3962 } | 3957 } |
3963 | 3958 |
3964 | 3959 |
3965 void LCodeGen::DoTailCallThroughMegamorphicCache( | |
3966 LTailCallThroughMegamorphicCache* instr) { | |
3967 Register receiver = ToRegister(instr->receiver()); | |
3968 Register name = ToRegister(instr->name()); | |
3969 DCHECK(receiver.is(LoadDescriptor::ReceiverRegister())); | |
3970 DCHECK(name.is(LoadDescriptor::NameRegister())); | |
3971 DCHECK(receiver.is(r1)); | |
3972 DCHECK(name.is(r2)); | |
3973 Register scratch = r4; | |
3974 Register extra = r5; | |
3975 Register extra2 = r6; | |
3976 Register extra3 = r9; | |
3977 | |
3978 // The probe will tail call to a handler if found. | |
3979 isolate()->stub_cache()->GenerateProbe( | |
3980 masm(), Code::LOAD_IC, instr->hydrogen()->flags(), false, receiver, name, | |
3981 scratch, extra, extra2, extra3); | |
3982 | |
3983 // Tail call to miss if we ended up here. | |
3984 LoadIC::GenerateMiss(masm()); | |
3985 } | |
3986 | |
3987 | |
3988 void LCodeGen::DoCallWithDescriptor(LCallWithDescriptor* instr) { | 3960 void LCodeGen::DoCallWithDescriptor(LCallWithDescriptor* instr) { |
3989 DCHECK(ToRegister(instr->result()).is(r0)); | 3961 DCHECK(ToRegister(instr->result()).is(r0)); |
3990 | 3962 |
3991 if (instr->hydrogen()->IsTailCall()) { | 3963 if (instr->hydrogen()->IsTailCall()) { |
3992 if (NeedsEagerFrame()) __ LeaveFrame(StackFrame::INTERNAL); | 3964 if (NeedsEagerFrame()) __ LeaveFrame(StackFrame::INTERNAL); |
3993 | 3965 |
3994 if (instr->target()->IsConstantOperand()) { | 3966 if (instr->target()->IsConstantOperand()) { |
3995 LConstantOperand* target = LConstantOperand::cast(instr->target()); | 3967 LConstantOperand* target = LConstantOperand::cast(instr->target()); |
3996 Handle<Code> code = Handle<Code>::cast(ToHandle(target)); | 3968 Handle<Code> code = Handle<Code>::cast(ToHandle(target)); |
3997 __ Jump(code, RelocInfo::CODE_TARGET); | 3969 __ Jump(code, RelocInfo::CODE_TARGET); |
(...skipping 2048 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6046 __ Push(scope_info); | 6018 __ Push(scope_info); |
6047 __ push(ToRegister(instr->function())); | 6019 __ push(ToRegister(instr->function())); |
6048 CallRuntime(Runtime::kPushBlockContext, 2, instr); | 6020 CallRuntime(Runtime::kPushBlockContext, 2, instr); |
6049 RecordSafepoint(Safepoint::kNoLazyDeopt); | 6021 RecordSafepoint(Safepoint::kNoLazyDeopt); |
6050 } | 6022 } |
6051 | 6023 |
6052 | 6024 |
6053 #undef __ | 6025 #undef __ |
6054 | 6026 |
6055 } } // namespace v8::internal | 6027 } } // namespace v8::internal |
OLD | NEW |