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_IA32. | 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_IA32. |
6 #if defined(TARGET_ARCH_IA32) | 6 #if defined(TARGET_ARCH_IA32) |
7 | 7 |
8 #include "vm/flow_graph_compiler.h" | 8 #include "vm/flow_graph_compiler.h" |
9 | 9 |
10 #include "vm/ast_printer.h" | 10 #include "vm/ast_printer.h" |
(...skipping 600 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
611 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 611 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
612 __ pushl(EAX); // Push the instance. | 612 __ pushl(EAX); // Push the instance. |
613 __ PushObject(type); // Push the type. | 613 __ PushObject(type); // Push the type. |
614 __ pushl(ECX); // Instantiator. | 614 __ pushl(ECX); // Instantiator. |
615 __ pushl(EDX); // Instantiator type arguments. | 615 __ pushl(EDX); // Instantiator type arguments. |
616 __ LoadObject(EAX, test_cache); | 616 __ LoadObject(EAX, test_cache); |
617 __ pushl(EAX); | 617 __ pushl(EAX); |
618 GenerateCallRuntime(token_pos, | 618 GenerateCallRuntime(token_pos, |
619 deopt_id, | 619 deopt_id, |
620 kInstanceofRuntimeEntry, | 620 kInstanceofRuntimeEntry, |
| 621 5, |
621 locs); | 622 locs); |
622 // Pop the parameters supplied to the runtime entry. The result of the | 623 // Pop the parameters supplied to the runtime entry. The result of the |
623 // instanceof runtime call will be left as the result of the operation. | 624 // instanceof runtime call will be left as the result of the operation. |
624 __ Drop(5); | 625 __ Drop(5); |
625 if (negate_result) { | 626 if (negate_result) { |
626 __ popl(EDX); | 627 __ popl(EDX); |
627 __ LoadObject(EAX, Bool::True()); | 628 __ LoadObject(EAX, Bool::True()); |
628 __ cmpl(EDX, EAX); | 629 __ cmpl(EDX, EAX); |
629 __ j(NOT_EQUAL, &done, Assembler::kNearJump); | 630 __ j(NOT_EQUAL, &done, Assembler::kNearJump); |
630 __ LoadObject(EAX, Bool::False()); | 631 __ LoadObject(EAX, Bool::False()); |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
698 } | 699 } |
699 const String& error_message = String::ZoneHandle( | 700 const String& error_message = String::ZoneHandle( |
700 Symbols::New(error.ToErrorCString())); | 701 Symbols::New(error.ToErrorCString())); |
701 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 702 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
702 __ pushl(EAX); // Push the source object. | 703 __ pushl(EAX); // Push the source object. |
703 __ PushObject(dst_name); // Push the name of the destination. | 704 __ PushObject(dst_name); // Push the name of the destination. |
704 __ PushObject(error_message); | 705 __ PushObject(error_message); |
705 GenerateCallRuntime(token_pos, | 706 GenerateCallRuntime(token_pos, |
706 deopt_id, | 707 deopt_id, |
707 kMalformedTypeErrorRuntimeEntry, | 708 kMalformedTypeErrorRuntimeEntry, |
| 709 3, |
708 locs); | 710 locs); |
709 // We should never return here. | 711 // We should never return here. |
710 __ int3(); | 712 __ int3(); |
711 | 713 |
712 __ Bind(&is_assignable); // For a null object. | 714 __ Bind(&is_assignable); // For a null object. |
713 __ popl(EDX); // Remove pushed instantiator type arguments. | 715 __ popl(EDX); // Remove pushed instantiator type arguments. |
714 __ popl(ECX); // Remove pushed instantiator. | 716 __ popl(ECX); // Remove pushed instantiator. |
715 return; | 717 return; |
716 } | 718 } |
717 | 719 |
718 // Generate inline type check, linking to runtime call if not assignable. | 720 // Generate inline type check, linking to runtime call if not assignable. |
719 SubtypeTestCache& test_cache = SubtypeTestCache::ZoneHandle(); | 721 SubtypeTestCache& test_cache = SubtypeTestCache::ZoneHandle(); |
720 test_cache = GenerateInlineInstanceof(token_pos, dst_type, | 722 test_cache = GenerateInlineInstanceof(token_pos, dst_type, |
721 &is_assignable, &runtime_call); | 723 &is_assignable, &runtime_call); |
722 | 724 |
723 __ Bind(&runtime_call); | 725 __ Bind(&runtime_call); |
724 __ movl(EDX, Address(ESP, 0)); // Get instantiator type arguments. | 726 __ movl(EDX, Address(ESP, 0)); // Get instantiator type arguments. |
725 __ movl(ECX, Address(ESP, kWordSize)); // Get instantiator. | 727 __ movl(ECX, Address(ESP, kWordSize)); // Get instantiator. |
726 __ PushObject(Object::ZoneHandle()); // Make room for the result. | 728 __ PushObject(Object::ZoneHandle()); // Make room for the result. |
727 __ pushl(EAX); // Push the source object. | 729 __ pushl(EAX); // Push the source object. |
728 __ PushObject(dst_type); // Push the type of the destination. | 730 __ PushObject(dst_type); // Push the type of the destination. |
729 __ pushl(ECX); // Instantiator. | 731 __ pushl(ECX); // Instantiator. |
730 __ pushl(EDX); // Instantiator type arguments. | 732 __ pushl(EDX); // Instantiator type arguments. |
731 __ PushObject(dst_name); // Push the name of the destination. | 733 __ PushObject(dst_name); // Push the name of the destination. |
732 __ LoadObject(EAX, test_cache); | 734 __ LoadObject(EAX, test_cache); |
733 __ pushl(EAX); | 735 __ pushl(EAX); |
734 GenerateCallRuntime(token_pos, deopt_id, kTypeCheckRuntimeEntry, locs); | 736 GenerateCallRuntime(token_pos, deopt_id, kTypeCheckRuntimeEntry, 6, locs); |
735 // Pop the parameters supplied to the runtime entry. The result of the | 737 // Pop the parameters supplied to the runtime entry. The result of the |
736 // type check runtime call is the checked value. | 738 // type check runtime call is the checked value. |
737 __ Drop(6); | 739 __ Drop(6); |
738 __ popl(EAX); | 740 __ popl(EAX); |
739 | 741 |
740 __ Bind(&is_assignable); | 742 __ Bind(&is_assignable); |
741 __ popl(EDX); // Remove pushed instantiator type arguments. | 743 __ popl(EDX); // Remove pushed instantiator type arguments. |
742 __ popl(ECX); // Remove pushed instantiator. | 744 __ popl(ECX); // Remove pushed instantiator. |
743 } | 745 } |
744 | 746 |
(...skipping 511 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1256 // Add deoptimization continuation point after the call and before the | 1258 // Add deoptimization continuation point after the call and before the |
1257 // arguments are removed. | 1259 // arguments are removed. |
1258 AddCurrentDescriptor(PcDescriptors::kDeopt, deopt_id_after, token_pos); | 1260 AddCurrentDescriptor(PcDescriptors::kDeopt, deopt_id_after, token_pos); |
1259 } | 1261 } |
1260 } | 1262 } |
1261 | 1263 |
1262 | 1264 |
1263 void FlowGraphCompiler::GenerateCallRuntime(intptr_t token_pos, | 1265 void FlowGraphCompiler::GenerateCallRuntime(intptr_t token_pos, |
1264 intptr_t deopt_id, | 1266 intptr_t deopt_id, |
1265 const RuntimeEntry& entry, | 1267 const RuntimeEntry& entry, |
| 1268 intptr_t argument_count, |
1266 LocationSummary* locs) { | 1269 LocationSummary* locs) { |
1267 __ CallRuntime(entry); | 1270 __ CallRuntime(entry, argument_count); |
1268 AddCurrentDescriptor(PcDescriptors::kOther, deopt_id, token_pos); | 1271 AddCurrentDescriptor(PcDescriptors::kOther, deopt_id, token_pos); |
1269 RecordSafepoint(locs); | 1272 RecordSafepoint(locs); |
1270 if (deopt_id != Isolate::kNoDeoptId) { | 1273 if (deopt_id != Isolate::kNoDeoptId) { |
1271 // Marks either the continuation point in unoptimized code or the | 1274 // Marks either the continuation point in unoptimized code or the |
1272 // deoptimization point in optimized code, after call. | 1275 // deoptimization point in optimized code, after call. |
1273 const intptr_t deopt_id_after = Isolate::ToDeoptAfter(deopt_id); | 1276 const intptr_t deopt_id_after = Isolate::ToDeoptAfter(deopt_id); |
1274 if (is_optimizing()) { | 1277 if (is_optimizing()) { |
1275 AddDeoptIndexAtCall(deopt_id_after, token_pos); | 1278 AddDeoptIndexAtCall(deopt_id_after, token_pos); |
1276 } else { | 1279 } else { |
1277 // Add deoptimization continuation point after the call and before the | 1280 // Add deoptimization continuation point after the call and before the |
(...skipping 631 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1909 __ movups(reg, Address(ESP, 0)); | 1912 __ movups(reg, Address(ESP, 0)); |
1910 __ addl(ESP, Immediate(kFpuRegisterSize)); | 1913 __ addl(ESP, Immediate(kFpuRegisterSize)); |
1911 } | 1914 } |
1912 | 1915 |
1913 | 1916 |
1914 #undef __ | 1917 #undef __ |
1915 | 1918 |
1916 } // namespace dart | 1919 } // namespace dart |
1917 | 1920 |
1918 #endif // defined TARGET_ARCH_IA32 | 1921 #endif // defined TARGET_ARCH_IA32 |
OLD | NEW |