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

Side by Side Diff: sdk/lib/_internal/compiler/implementation/ssa/invoke_dynamic_specializers.dart

Issue 12042003: Move relational operators to the new interceptors. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 7 years, 11 months 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
OLDNEW
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 part of ssa; 5 part of ssa;
6 6
7 /** 7 /**
8 * [InvokeDynamicSpecializer] and its subclasses are helpers to 8 * [InvokeDynamicSpecializer] and its subclasses are helpers to
9 * optimize intercepted dynamic calls. It knows what input types 9 * optimize intercepted dynamic calls. It knows what input types
10 * would be beneficial for performance, and how to change a invoke 10 * would be beneficial for performance, and how to change a invoke
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
58 } else if (selector.name == const SourceString('>>')) { 58 } else if (selector.name == const SourceString('>>')) {
59 return const ShiftRightSpecializer(); 59 return const ShiftRightSpecializer();
60 } else if (selector.name == const SourceString('<<')) { 60 } else if (selector.name == const SourceString('<<')) {
61 return const ShiftLeftSpecializer(); 61 return const ShiftLeftSpecializer();
62 } else if (selector.name == const SourceString('&')) { 62 } else if (selector.name == const SourceString('&')) {
63 return const BitAndSpecializer(); 63 return const BitAndSpecializer();
64 } else if (selector.name == const SourceString('|')) { 64 } else if (selector.name == const SourceString('|')) {
65 return const BitOrSpecializer(); 65 return const BitOrSpecializer();
66 } else if (selector.name == const SourceString('^')) { 66 } else if (selector.name == const SourceString('^')) {
67 return const BitXorSpecializer(); 67 return const BitXorSpecializer();
68 } else if (selector.name == const SourceString('==')) {
69 return const EqualsSpecializer();
70 } else if (selector.name == const SourceString('<')) {
71 return const LessSpecializer();
72 } else if (selector.name == const SourceString('<=')) {
73 return const LessEqualSpecializer();
74 } else if (selector.name == const SourceString('>')) {
75 return const GreaterSpecializer();
76 } else if (selector.name == const SourceString('>=')) {
77 return const GreaterEqualSpecializer();
68 } 78 }
69 } 79 }
70 return const InvokeDynamicSpecializer(); 80 return const InvokeDynamicSpecializer();
71 } 81 }
72 } 82 }
73 83
74 class IndexAssignSpecializer extends InvokeDynamicSpecializer { 84 class IndexAssignSpecializer extends InvokeDynamicSpecializer {
75 const IndexAssignSpecializer(); 85 const IndexAssignSpecializer();
76 86
77 HType computeDesiredTypeForInput(HInvokeDynamicMethod instruction, 87 HType computeDesiredTypeForInput(HInvokeDynamicMethod instruction,
(...skipping 391 matching lines...) Expand 10 before | Expand all | Expand 10 after
469 const BitXorSpecializer(); 479 const BitXorSpecializer();
470 480
471 BinaryOperation operation(ConstantSystem constantSystem) { 481 BinaryOperation operation(ConstantSystem constantSystem) {
472 return constantSystem.bitXor; 482 return constantSystem.bitXor;
473 } 483 }
474 484
475 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) { 485 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
476 return new HBitXor(left, right); 486 return new HBitXor(left, right);
477 } 487 }
478 } 488 }
489
490 class RelationalSpecializer extends InvokeDynamicSpecializer {
491 const RelationalSpecializer();
492
493 HType computeTypeFromInputTypes(HInvokeDynamicMethod instruction,
494 HTypeMap types,
495 Compiler compiler) {
496 if (types[instruction.inputs[1]].isPrimitiveOrNull()) return HType.BOOLEAN;
497 return HType.UNKNOWN;
498 }
499
500 HType computeDesiredTypeForInput(HInvokeDynamicMethod instruction,
501 HInstruction input,
502 HTypeMap types,
503 Compiler compiler) {
504 if (input == instruction.inputs[0]) return HType.UNKNOWN;
505 HType propagatedType = types[instruction];
506 // For all relational operations except HIdentity, we expect to get numbers
507 // only. With numbers the outgoing type is a boolean. If something else
508 // is desired, then numbers are incorrect, though.
509 if (propagatedType.isUnknown() || propagatedType.isBoolean()) {
510 HInstruction left = instruction.inputs[1];
511 if (left.isTypeUnknown(types) || left.isNumber(types)) {
512 return HType.NUMBER;
513 }
514 }
515 return HType.UNKNOWN;
516 }
517
518 HInstruction tryConvertToBuiltin(HInvokeDynamicMethod instruction,
519 HTypeMap types) {
520 HInstruction left = instruction.inputs[1];
521 HInstruction right = instruction.inputs[2];
522 if (left.isNumber(types) && right.isNumber(types)) {
523 return newBuiltinVariant(left, right);
524 }
525 return null;
526 }
527
528 HInstruction newBuiltinVariant(HInstruction left, HInstruction right);
529 }
530
531 class EqualsSpecializer extends RelationalSpecializer {
532 const EqualsSpecializer();
533
534 HType computeDesiredTypeForInput(HInvokeDynamicMethod instruction,
535 HInstruction input,
536 HTypeMap types,
537 Compiler compiler) {
538 HInstruction left = instruction.inputs[1];
539 HInstruction right = instruction.inputs[2];
540 HType propagatedType = types[instruction];
541 if (input == left && types[right].isUseful()) {
542 // All our useful types have 'identical' semantics. But we don't want to
543 // speculatively test for all possible types. Therefore we try to match
544 // the two types. That is, if we see x == 3, then we speculatively test
545 // if x is a number and bailout if it isn't.
546 // If right is a number we don't need more than a number (no need to match
547 // the exact type of right).
548 if (right.isNumber(types)) return HType.NUMBER;
549 return types[right];
550 }
551 // String equality testing is much more common than array equality testing.
552 if (input == left && left.isIndexablePrimitive(types)) {
553 return HType.READABLE_ARRAY;
554 }
555 // String equality testing is much more common than array equality testing.
556 if (input == right && right.isIndexablePrimitive(types)) {
557 return HType.STRING;
558 }
559 return HType.UNKNOWN;
560 }
561
562 HInstruction tryConvertToBuiltin(HInvokeDynamicMethod instruction,
563 HTypeMap types) {
564 HInstruction left = instruction.inputs[1];
565 HInstruction right = instruction.inputs[2];
566 if (types[left].isPrimitiveOrNull() || right.isConstantNull()) {
567 return newBuiltinVariant(left, right);
568 }
569 return null;
570 }
571
572 BinaryOperation operation(ConstantSystem constantSystem) {
573 return constantSystem.equal;
574 }
575
576 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
577 return new HIdentity(left, right);
578 }
579 }
580
581 class LessSpecializer extends RelationalSpecializer {
582 const LessSpecializer();
583
584 BinaryOperation operation(ConstantSystem constantSystem) {
585 return constantSystem.less;
586 }
587
588 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
589 return new HLess(left, right);
590 }
591 }
592
593 class GreaterSpecializer extends RelationalSpecializer {
594 const GreaterSpecializer();
595
596 BinaryOperation operation(ConstantSystem constantSystem) {
597 return constantSystem.greater;
598 }
599
600 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
601 return new HGreater(left, right);
602 }
603 }
604
605 class GreaterEqualSpecializer extends RelationalSpecializer {
606 const GreaterEqualSpecializer();
607
608 BinaryOperation operation(ConstantSystem constantSystem) {
609 return constantSystem.greaterEqual;
610 }
611
612 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
613 return new HGreaterEqual(left, right);
614 }
615 }
616
617 class LessEqualSpecializer extends RelationalSpecializer {
618 const LessEqualSpecializer();
619
620 BinaryOperation operation(ConstantSystem constantSystem) {
621 return constantSystem.lessEqual;
622 }
623
624 HInstruction newBuiltinVariant(HInstruction left, HInstruction right) {
625 return new HLessEqual(left, right);
626 }
627 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698