Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(290)

Side by Side Diff: runtime/vm/code_generator_ia32.cc

Issue 8508035: For instanceof inline check against right hand class id possible and interface String for OneByte... (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: '' Created 9 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« runtime/vm/code_generator.cc ('K') | « runtime/vm/code_generator.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, 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/code_generator.h" 8 #include "vm/code_generator.h"
9 9
10 #include "lib/error.h" 10 #include "lib/error.h"
(...skipping 1397 matching lines...) Expand 10 before | Expand all | Expand 10 after
1408 __ PushObject(negate_result ? bool_true : bool_false); 1408 __ PushObject(negate_result ? bool_true : bool_false);
1409 __ jmp(&done, Assembler::kNearJump); 1409 __ jmp(&done, Assembler::kNearJump);
1410 1410
1411 __ Bind(&non_null); 1411 __ Bind(&non_null);
1412 // If type is instantiated and non-parameterized, we can inline code 1412 // If type is instantiated and non-parameterized, we can inline code
1413 // checking whether the tested instance is a Smi. 1413 // checking whether the tested instance is a Smi.
1414 if (type.IsInstantiated()) { 1414 if (type.IsInstantiated()) {
1415 const Class& type_class = Class::ZoneHandle(type.type_class()); 1415 const Class& type_class = Class::ZoneHandle(type.type_class());
1416 const bool requires_type_arguments = type_class.HasTypeArguments(); 1416 const bool requires_type_arguments = type_class.HasTypeArguments();
1417 // A Smi object cannot be the instance of a parameterized class. 1417 // A Smi object cannot be the instance of a parameterized class.
1418 // A class equality check is only applicable to a non-parameterized class. 1418 // A class equality check is only applicable with a dst type of a
1419 // non-parameterized class or with a raw dst type of a parameterized class.
1419 // TODO(regis): Should we still inline a Smi type check when checking for a 1420 // TODO(regis): Should we still inline a Smi type check when checking for a
regis 2011/11/10 03:09:51 I think you can remove this TODO now.
srdjan 2011/11/10 17:24:41 Done.
1420 // parameterized type and return false for a Smi's without calling the 1421 // parameterized type and return false for a Smi's without calling the
1421 // runtime? 1422 // runtime?
1422 if (!requires_type_arguments) { 1423 if (requires_type_arguments) {
1424 const TypeArguments& type_arguments =
1425 TypeArguments::Handle(type.arguments());
1426 const bool is_raw_type = type_arguments.IsNull() ||
1427 type_arguments.IsDynamicTypes(type_arguments.Length());
1428 if (is_raw_type) {
1429 if (!type_class.is_interface()) {
1430 Label runtime_call;
1431 __ testl(EAX, Immediate(kSmiTagMask));
1432 __ j(ZERO, &runtime_call, Assembler::kNearJump);
regis 2011/11/10 03:09:51 Can't you perform this Smi check even if the type
srdjan 2011/11/10 17:24:41 Done.
1433 // Object not Smi.
1434 __ movl(ECX, FieldAddress(EAX, Object::class_offset()));
1435 __ CompareObject(ECX, type_class);
1436 __ j(NOT_EQUAL, &runtime_call, Assembler::kNearJump);
1437 __ PushObject(negate_result ? bool_false : bool_true);
1438 __ jmp(&done, Assembler::kNearJump);
1439 __ Bind(&runtime_call);
1440 // Fall through to runtime call.
1441 }
1442 }
1443 } else {
1423 Label compare_classes; 1444 Label compare_classes;
1424 __ testl(EAX, Immediate(kSmiTagMask)); 1445 __ testl(EAX, Immediate(kSmiTagMask));
1425 __ j(NOT_ZERO, &compare_classes, Assembler::kNearJump); 1446 __ j(NOT_ZERO, &compare_classes, Assembler::kNearJump);
1426 // Object is Smi. 1447 // Object is Smi.
1427 const Class& smi_class = Class::Handle(Smi::Class()); 1448 const Class& smi_class = Class::Handle(Smi::Class());
1428 // TODO(regis): We should introduce a SmiType. 1449 // TODO(regis): We should introduce a SmiType.
1429 if (smi_class.IsSubtypeOf(TypeArguments::Handle(), 1450 if (smi_class.IsSubtypeOf(TypeArguments::Handle(),
1430 type_class, 1451 type_class,
1431 TypeArguments::Handle())) { 1452 TypeArguments::Handle())) {
1432 __ PushObject(negate_result ? bool_false : bool_true); 1453 __ PushObject(negate_result ? bool_false : bool_true);
1433 } else { 1454 } else {
1434 __ PushObject(negate_result ? bool_true : bool_false); 1455 __ PushObject(negate_result ? bool_true : bool_false);
1435 } 1456 }
1436 __ jmp(&done, Assembler::kNearJump); 1457 __ jmp(&done, Assembler::kNearJump);
1437 1458
1438 // Compare if the classes are equal. 1459 // Compare if the classes are equal.
1439 __ Bind(&compare_classes); 1460 __ Bind(&compare_classes);
1440 // If type is an interface, we can skip the class equality check, 1461 if (type_class.is_interface()) {
1441 // because instances cannot be of an interface type. 1462 if (type.IsStringInterface()) {
1442 if (!type_class.is_interface()) { 1463 Label runtime_call;
1464 __ movl(ECX, FieldAddress(EAX, Object::class_offset()));
1465 const Class& one_byte_string_class = Class::ZoneHandle(
1466 Isolate::Current()->object_store()->one_byte_string_class());
1467 __ CompareObject(ECX, one_byte_string_class);
1468 __ j(NOT_EQUAL, &runtime_call, Assembler::kNearJump);
1469 __ PushObject(negate_result ? bool_false : bool_true);
1470 __ jmp(&done, Assembler::kNearJump);
1471 __ Bind(&runtime_call);
1472 }
1473 } else { // type_class is not an interface.
1443 Label runtime_call; 1474 Label runtime_call;
1444 __ movl(ECX, FieldAddress(EAX, Object::class_offset())); 1475 __ movl(ECX, FieldAddress(EAX, Object::class_offset()));
1445 __ CompareObject(ECX, type_class); 1476 __ CompareObject(ECX, type_class);
1446 __ j(NOT_EQUAL, &runtime_call, Assembler::kNearJump); 1477 __ j(NOT_EQUAL, &runtime_call, Assembler::kNearJump);
1447 __ PushObject(negate_result ? bool_false : bool_true); 1478 __ PushObject(negate_result ? bool_false : bool_true);
1448 __ jmp(&done, Assembler::kNearJump); 1479 __ jmp(&done, Assembler::kNearJump);
1449 __ Bind(&runtime_call); 1480 __ Bind(&runtime_call);
1450 } 1481 }
1451 } 1482 }
1452 } 1483 }
(...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after
1558 TestClassAndJump(*CoreClass("ObjectArray"), &done); 1589 TestClassAndJump(*CoreClass("ObjectArray"), &done);
1559 TestClassAndJump(*CoreClass("GrowableObjectArray"), &done); 1590 TestClassAndJump(*CoreClass("GrowableObjectArray"), &done);
1560 } else if (!dst_type_class.is_interface()) { 1591 } else if (!dst_type_class.is_interface()) {
1561 __ testl(EAX, Immediate(kSmiTagMask)); 1592 __ testl(EAX, Immediate(kSmiTagMask));
1562 __ j(ZERO, &runtime_call, Assembler::kNearJump); 1593 __ j(ZERO, &runtime_call, Assembler::kNearJump);
1563 __ movl(ECX, FieldAddress(EAX, Object::class_offset())); 1594 __ movl(ECX, FieldAddress(EAX, Object::class_offset()));
1564 TestClassAndJump(dst_type_class, &done); 1595 TestClassAndJump(dst_type_class, &done);
1565 } 1596 }
1566 // Fall through to runtime class. 1597 // Fall through to runtime class.
1567 } 1598 }
1568 } else { 1599 } else { // dst_type has NO type parameters.
regis 2011/11/10 03:09:51 Sorry to be picky, but "type parameters" is the wr
srdjan 2011/11/10 17:24:41 Done.
1569 Label compare_classes; 1600 Label compare_classes;
1570 __ testl(EAX, Immediate(kSmiTagMask)); 1601 __ testl(EAX, Immediate(kSmiTagMask));
1571 __ j(NOT_ZERO, &compare_classes, Assembler::kNearJump); 1602 __ j(NOT_ZERO, &compare_classes, Assembler::kNearJump);
1572 // Object is Smi. 1603 // Object is Smi.
1573 const Class& smi_class = Class::Handle(Smi::Class()); 1604 const Class& smi_class = Class::Handle(Smi::Class());
1574 // TODO(regis): We should introduce a SmiType. 1605 // TODO(regis): We should introduce a SmiType.
1575 if (smi_class.IsSubtypeOf(TypeArguments::Handle(), 1606 if (smi_class.IsSubtypeOf(TypeArguments::Handle(),
1576 dst_type_class, 1607 dst_type_class,
1577 TypeArguments::Handle())) { 1608 TypeArguments::Handle())) {
1578 // Successful assignable type check: return object in EAX. 1609 // Successful assignable type check: return object in EAX.
(...skipping 1129 matching lines...) Expand 10 before | Expand all | Expand 10 after
2708 const Class& cls = Class::Handle(parsed_function_.function().owner()); 2739 const Class& cls = Class::Handle(parsed_function_.function().owner());
2709 const Script& script = Script::Handle(cls.script()); 2740 const Script& script = Script::Handle(cls.script());
2710 Parser::ReportMsg(script, token_index, "Error", error_msg, format, args); 2741 Parser::ReportMsg(script, token_index, "Error", error_msg, format, args);
2711 Isolate::Current()->long_jump_base()->Jump(1, error_msg); 2742 Isolate::Current()->long_jump_base()->Jump(1, error_msg);
2712 UNREACHABLE(); 2743 UNREACHABLE();
2713 } 2744 }
2714 2745
2715 } // namespace dart 2746 } // namespace dart
2716 2747
2717 #endif // defined TARGET_ARCH_IA32 2748 #endif // defined TARGET_ARCH_IA32
OLDNEW
« runtime/vm/code_generator.cc ('K') | « runtime/vm/code_generator.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698