| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. | 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. |
| 6 #if defined(TARGET_ARCH_X64) | 6 #if defined(TARGET_ARCH_X64) |
| 7 | 7 |
| 8 #include "vm/intermediate_language.h" | 8 #include "vm/intermediate_language.h" |
| 9 | 9 |
| 10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
| (...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 355 Label done; | 355 Label done; |
| 356 __ CompareObject(reg, Bool::True()); | 356 __ CompareObject(reg, Bool::True()); |
| 357 __ j(EQUAL, &done, Assembler::kNearJump); | 357 __ j(EQUAL, &done, Assembler::kNearJump); |
| 358 __ CompareObject(reg, Bool::False()); | 358 __ CompareObject(reg, Bool::False()); |
| 359 __ j(EQUAL, &done, Assembler::kNearJump); | 359 __ j(EQUAL, &done, Assembler::kNearJump); |
| 360 | 360 |
| 361 __ pushq(reg); // Push the source object. | 361 __ pushq(reg); // Push the source object. |
| 362 compiler->GenerateCallRuntime(token_pos, | 362 compiler->GenerateCallRuntime(token_pos, |
| 363 deopt_id, | 363 deopt_id, |
| 364 kConditionTypeErrorRuntimeEntry, | 364 kConditionTypeErrorRuntimeEntry, |
| 365 1, |
| 365 locs); | 366 locs); |
| 366 // We should never return here. | 367 // We should never return here. |
| 367 __ int3(); | 368 __ int3(); |
| 368 __ Bind(&done); | 369 __ Bind(&done); |
| 369 } | 370 } |
| 370 | 371 |
| 371 | 372 |
| 372 void AssertBooleanInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 373 void AssertBooleanInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 373 Register obj = locs()->in(0).reg(); | 374 Register obj = locs()->in(0).reg(); |
| 374 Register result = locs()->out().reg(); | 375 Register result = locs()->out().reg(); |
| (...skipping 1450 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1825 if (deopt == NULL) { | 1826 if (deopt == NULL) { |
| 1826 ASSERT(!compiler->is_optimizing()); | 1827 ASSERT(!compiler->is_optimizing()); |
| 1827 __ Bind(fail); | 1828 __ Bind(fail); |
| 1828 | 1829 |
| 1829 __ cmpq(FieldAddress(field_reg, Field::guarded_cid_offset()), | 1830 __ cmpq(FieldAddress(field_reg, Field::guarded_cid_offset()), |
| 1830 Immediate(kDynamicCid)); | 1831 Immediate(kDynamicCid)); |
| 1831 __ j(EQUAL, &ok); | 1832 __ j(EQUAL, &ok); |
| 1832 | 1833 |
| 1833 __ pushq(field_reg); | 1834 __ pushq(field_reg); |
| 1834 __ pushq(value_reg); | 1835 __ pushq(value_reg); |
| 1835 __ CallRuntime(kUpdateFieldCidRuntimeEntry); | 1836 __ CallRuntime(kUpdateFieldCidRuntimeEntry, 2); |
| 1836 __ Drop(2); // Drop the field and the value. | 1837 __ Drop(2); // Drop the field and the value. |
| 1837 } | 1838 } |
| 1838 | 1839 |
| 1839 __ Bind(&ok); | 1840 __ Bind(&ok); |
| 1840 } | 1841 } |
| 1841 | 1842 |
| 1842 | 1843 |
| 1843 LocationSummary* StoreInstanceFieldInstr::MakeLocationSummary() const { | 1844 LocationSummary* StoreInstanceFieldInstr::MakeLocationSummary() const { |
| 1844 const intptr_t kNumInputs = 2; | 1845 const intptr_t kNumInputs = 2; |
| 1845 const intptr_t kNumTemps = 0; | 1846 const intptr_t kNumTemps = 0; |
| (...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1975 AllocateObjectWithBoundsCheckInstr::MakeLocationSummary() const { | 1976 AllocateObjectWithBoundsCheckInstr::MakeLocationSummary() const { |
| 1976 return MakeCallSummary(); | 1977 return MakeCallSummary(); |
| 1977 } | 1978 } |
| 1978 | 1979 |
| 1979 | 1980 |
| 1980 void AllocateObjectWithBoundsCheckInstr::EmitNativeCode( | 1981 void AllocateObjectWithBoundsCheckInstr::EmitNativeCode( |
| 1981 FlowGraphCompiler* compiler) { | 1982 FlowGraphCompiler* compiler) { |
| 1982 compiler->GenerateCallRuntime(token_pos(), | 1983 compiler->GenerateCallRuntime(token_pos(), |
| 1983 deopt_id(), | 1984 deopt_id(), |
| 1984 kAllocateObjectWithBoundsCheckRuntimeEntry, | 1985 kAllocateObjectWithBoundsCheckRuntimeEntry, |
| 1986 3, |
| 1985 locs()); | 1987 locs()); |
| 1986 __ Drop(3); | 1988 __ Drop(3); |
| 1987 ASSERT(locs()->out().reg() == RAX); | 1989 ASSERT(locs()->out().reg() == RAX); |
| 1988 __ popq(RAX); // Pop new instance. | 1990 __ popq(RAX); // Pop new instance. |
| 1989 } | 1991 } |
| 1990 | 1992 |
| 1991 | 1993 |
| 1992 LocationSummary* LoadFieldInstr::MakeLocationSummary() const { | 1994 LocationSummary* LoadFieldInstr::MakeLocationSummary() const { |
| 1993 return LocationSummary::Make(1, | 1995 return LocationSummary::Make(1, |
| 1994 Location::RequiresRegister(), | 1996 Location::RequiresRegister(), |
| (...skipping 26 matching lines...) Expand all Loading... |
| 2021 | 2023 |
| 2022 // 'instantiator_reg' is the instantiator AbstractTypeArguments object | 2024 // 'instantiator_reg' is the instantiator AbstractTypeArguments object |
| 2023 // (or null). | 2025 // (or null). |
| 2024 // A runtime call to instantiate the type is required. | 2026 // A runtime call to instantiate the type is required. |
| 2025 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 2027 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
| 2026 __ PushObject(type()); | 2028 __ PushObject(type()); |
| 2027 __ pushq(instantiator_reg); // Push instantiator type arguments. | 2029 __ pushq(instantiator_reg); // Push instantiator type arguments. |
| 2028 compiler->GenerateCallRuntime(token_pos(), | 2030 compiler->GenerateCallRuntime(token_pos(), |
| 2029 deopt_id(), | 2031 deopt_id(), |
| 2030 kInstantiateTypeRuntimeEntry, | 2032 kInstantiateTypeRuntimeEntry, |
| 2033 2, |
| 2031 locs()); | 2034 locs()); |
| 2032 __ Drop(2); // Drop instantiator and uninstantiated type. | 2035 __ Drop(2); // Drop instantiator and uninstantiated type. |
| 2033 __ popq(result_reg); // Pop instantiated type. | 2036 __ popq(result_reg); // Pop instantiated type. |
| 2034 ASSERT(instantiator_reg == result_reg); | 2037 ASSERT(instantiator_reg == result_reg); |
| 2035 } | 2038 } |
| 2036 | 2039 |
| 2037 | 2040 |
| 2038 LocationSummary* InstantiateTypeArgumentsInstr::MakeLocationSummary() const { | 2041 LocationSummary* InstantiateTypeArgumentsInstr::MakeLocationSummary() const { |
| 2039 const intptr_t kNumInputs = 1; | 2042 const intptr_t kNumInputs = 1; |
| 2040 const intptr_t kNumTemps = 0; | 2043 const intptr_t kNumTemps = 0; |
| (...skipping 27 matching lines...) Expand all Loading... |
| 2068 __ j(EQUAL, &type_arguments_instantiated, Assembler::kNearJump); | 2071 __ j(EQUAL, &type_arguments_instantiated, Assembler::kNearJump); |
| 2069 } | 2072 } |
| 2070 // Instantiate non-null type arguments. | 2073 // Instantiate non-null type arguments. |
| 2071 // A runtime call to instantiate the type arguments is required. | 2074 // A runtime call to instantiate the type arguments is required. |
| 2072 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 2075 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
| 2073 __ PushObject(type_arguments()); | 2076 __ PushObject(type_arguments()); |
| 2074 __ pushq(instantiator_reg); // Push instantiator type arguments. | 2077 __ pushq(instantiator_reg); // Push instantiator type arguments. |
| 2075 compiler->GenerateCallRuntime(token_pos(), | 2078 compiler->GenerateCallRuntime(token_pos(), |
| 2076 deopt_id(), | 2079 deopt_id(), |
| 2077 kInstantiateTypeArgumentsRuntimeEntry, | 2080 kInstantiateTypeArgumentsRuntimeEntry, |
| 2081 2, |
| 2078 locs()); | 2082 locs()); |
| 2079 __ Drop(2); // Drop instantiator and uninstantiated type arguments. | 2083 __ Drop(2); // Drop instantiator and uninstantiated type arguments. |
| 2080 __ popq(result_reg); // Pop instantiated type arguments. | 2084 __ popq(result_reg); // Pop instantiated type arguments. |
| 2081 __ Bind(&type_arguments_instantiated); | 2085 __ Bind(&type_arguments_instantiated); |
| 2082 ASSERT(instantiator_reg == result_reg); | 2086 ASSERT(instantiator_reg == result_reg); |
| 2083 } | 2087 } |
| 2084 | 2088 |
| 2085 | 2089 |
| 2086 LocationSummary* | 2090 LocationSummary* |
| 2087 ExtractConstructorTypeArgumentsInstr::MakeLocationSummary() const { | 2091 ExtractConstructorTypeArgumentsInstr::MakeLocationSummary() const { |
| (...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2205 | 2209 |
| 2206 void CloneContextInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 2210 void CloneContextInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 2207 Register context_value = locs()->in(0).reg(); | 2211 Register context_value = locs()->in(0).reg(); |
| 2208 Register result = locs()->out().reg(); | 2212 Register result = locs()->out().reg(); |
| 2209 | 2213 |
| 2210 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 2214 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
| 2211 __ pushq(context_value); | 2215 __ pushq(context_value); |
| 2212 compiler->GenerateCallRuntime(token_pos(), | 2216 compiler->GenerateCallRuntime(token_pos(), |
| 2213 deopt_id(), | 2217 deopt_id(), |
| 2214 kCloneContextRuntimeEntry, | 2218 kCloneContextRuntimeEntry, |
| 2219 1, |
| 2215 locs()); | 2220 locs()); |
| 2216 __ popq(result); // Remove argument. | 2221 __ popq(result); // Remove argument. |
| 2217 __ popq(result); // Get result (cloned context). | 2222 __ popq(result); // Get result (cloned context). |
| 2218 } | 2223 } |
| 2219 | 2224 |
| 2220 | 2225 |
| 2221 LocationSummary* CatchBlockEntryInstr::MakeLocationSummary() const { | 2226 LocationSummary* CatchBlockEntryInstr::MakeLocationSummary() const { |
| 2222 UNREACHABLE(); | 2227 UNREACHABLE(); |
| 2223 return NULL; | 2228 return NULL; |
| 2224 } | 2229 } |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2272 __ Comment("CheckStackOverflowSlowPath"); | 2277 __ Comment("CheckStackOverflowSlowPath"); |
| 2273 __ Bind(entry_label()); | 2278 __ Bind(entry_label()); |
| 2274 compiler->SaveLiveRegisters(instruction_->locs()); | 2279 compiler->SaveLiveRegisters(instruction_->locs()); |
| 2275 // pending_deoptimization_env_ is needed to generate a runtime call that | 2280 // pending_deoptimization_env_ is needed to generate a runtime call that |
| 2276 // may throw an exception. | 2281 // may throw an exception. |
| 2277 ASSERT(compiler->pending_deoptimization_env_ == NULL); | 2282 ASSERT(compiler->pending_deoptimization_env_ == NULL); |
| 2278 compiler->pending_deoptimization_env_ = instruction_->env(); | 2283 compiler->pending_deoptimization_env_ = instruction_->env(); |
| 2279 compiler->GenerateCallRuntime(instruction_->token_pos(), | 2284 compiler->GenerateCallRuntime(instruction_->token_pos(), |
| 2280 instruction_->deopt_id(), | 2285 instruction_->deopt_id(), |
| 2281 kStackOverflowRuntimeEntry, | 2286 kStackOverflowRuntimeEntry, |
| 2287 0, |
| 2282 instruction_->locs()); | 2288 instruction_->locs()); |
| 2283 | 2289 |
| 2284 if (FLAG_use_osr && !compiler->is_optimizing() && instruction_->in_loop()) { | 2290 if (FLAG_use_osr && !compiler->is_optimizing() && instruction_->in_loop()) { |
| 2285 // In unoptimized code, record loop stack checks as possible OSR entries. | 2291 // In unoptimized code, record loop stack checks as possible OSR entries. |
| 2286 compiler->AddCurrentDescriptor(PcDescriptors::kOsrEntry, | 2292 compiler->AddCurrentDescriptor(PcDescriptors::kOsrEntry, |
| 2287 instruction_->deopt_id(), | 2293 instruction_->deopt_id(), |
| 2288 0); // No token position. | 2294 0); // No token position. |
| 2289 } | 2295 } |
| 2290 compiler->pending_deoptimization_env_ = NULL; | 2296 compiler->pending_deoptimization_env_ = NULL; |
| 2291 compiler->RestoreLiveRegisters(instruction_->locs()); | 2297 compiler->RestoreLiveRegisters(instruction_->locs()); |
| (...skipping 1999 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4291 __ j(EQUAL, &skip_call, Assembler::kNearJump); // base and result are 1.0 | 4297 __ j(EQUAL, &skip_call, Assembler::kNearJump); // base and result are 1.0 |
| 4292 __ jmp(&do_call, Assembler::kNearJump); | 4298 __ jmp(&do_call, Assembler::kNearJump); |
| 4293 | 4299 |
| 4294 __ Bind(&base_is_nan); | 4300 __ Bind(&base_is_nan); |
| 4295 // Returns NaN. | 4301 // Returns NaN. |
| 4296 __ movsd(result, base); | 4302 __ movsd(result, base); |
| 4297 __ jmp(&skip_call, Assembler::kNearJump); | 4303 __ jmp(&skip_call, Assembler::kNearJump); |
| 4298 // exp is Nan case is handled correctly in the C-library. | 4304 // exp is Nan case is handled correctly in the C-library. |
| 4299 } | 4305 } |
| 4300 __ Bind(&do_call); | 4306 __ Bind(&do_call); |
| 4301 __ CallRuntime(TargetFunction()); | 4307 __ CallRuntime(TargetFunction(), InputCount()); |
| 4302 __ movaps(locs()->out().fpu_reg(), XMM0); | 4308 __ movaps(locs()->out().fpu_reg(), XMM0); |
| 4303 __ Bind(&skip_call); | 4309 __ Bind(&skip_call); |
| 4304 __ leave(); | 4310 __ leave(); |
| 4305 } | 4311 } |
| 4306 | 4312 |
| 4307 | 4313 |
| 4308 LocationSummary* PolymorphicInstanceCallInstr::MakeLocationSummary() const { | 4314 LocationSummary* PolymorphicInstanceCallInstr::MakeLocationSummary() const { |
| 4309 return MakeCallSummary(); | 4315 return MakeCallSummary(); |
| 4310 } | 4316 } |
| 4311 | 4317 |
| (...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4546 | 4552 |
| 4547 LocationSummary* ThrowInstr::MakeLocationSummary() const { | 4553 LocationSummary* ThrowInstr::MakeLocationSummary() const { |
| 4548 return new LocationSummary(0, 0, LocationSummary::kCall); | 4554 return new LocationSummary(0, 0, LocationSummary::kCall); |
| 4549 } | 4555 } |
| 4550 | 4556 |
| 4551 | 4557 |
| 4552 void ThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 4558 void ThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 4553 compiler->GenerateCallRuntime(token_pos(), | 4559 compiler->GenerateCallRuntime(token_pos(), |
| 4554 deopt_id(), | 4560 deopt_id(), |
| 4555 kThrowRuntimeEntry, | 4561 kThrowRuntimeEntry, |
| 4562 1, |
| 4556 locs()); | 4563 locs()); |
| 4557 __ int3(); | 4564 __ int3(); |
| 4558 } | 4565 } |
| 4559 | 4566 |
| 4560 | 4567 |
| 4561 LocationSummary* ReThrowInstr::MakeLocationSummary() const { | 4568 LocationSummary* ReThrowInstr::MakeLocationSummary() const { |
| 4562 return new LocationSummary(0, 0, LocationSummary::kCall); | 4569 return new LocationSummary(0, 0, LocationSummary::kCall); |
| 4563 } | 4570 } |
| 4564 | 4571 |
| 4565 | 4572 |
| 4566 void ReThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 4573 void ReThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 4567 compiler->GenerateCallRuntime(token_pos(), | 4574 compiler->GenerateCallRuntime(token_pos(), |
| 4568 deopt_id(), | 4575 deopt_id(), |
| 4569 kReThrowRuntimeEntry, | 4576 kReThrowRuntimeEntry, |
| 4577 2, |
| 4570 locs()); | 4578 locs()); |
| 4571 __ int3(); | 4579 __ int3(); |
| 4572 } | 4580 } |
| 4573 | 4581 |
| 4574 | 4582 |
| 4575 void TargetEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 4583 void TargetEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 4576 __ Bind(compiler->GetJumpLabel(this)); | 4584 __ Bind(compiler->GetJumpLabel(this)); |
| 4577 if (!compiler->is_optimizing()) { | 4585 if (!compiler->is_optimizing()) { |
| 4578 compiler->AddCurrentDescriptor(PcDescriptors::kDeopt, | 4586 compiler->AddCurrentDescriptor(PcDescriptors::kDeopt, |
| 4579 deopt_id_, | 4587 deopt_id_, |
| (...skipping 292 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4872 PcDescriptors::kOther, | 4880 PcDescriptors::kOther, |
| 4873 locs()); | 4881 locs()); |
| 4874 __ Drop(2); // Discard type arguments and receiver. | 4882 __ Drop(2); // Discard type arguments and receiver. |
| 4875 } | 4883 } |
| 4876 | 4884 |
| 4877 } // namespace dart | 4885 } // namespace dart |
| 4878 | 4886 |
| 4879 #undef __ | 4887 #undef __ |
| 4880 | 4888 |
| 4881 #endif // defined TARGET_ARCH_X64 | 4889 #endif // defined TARGET_ARCH_X64 |
| OLD | NEW |