493 {
496 const BinaryFeedback& binary_feedback =
call->BinaryFeedback();
497 switch (op_kind) {
498 case Token::kADD:
499 case Token::kSUB:
500 case Token::kMUL:
501 if (binary_feedback.OperandsAre(kSmiCid)) {
502
503
504 operands_type =
505 call->ic_data()->HasDeoptReason(ICData::kDeoptBinarySmiOp)
506 ? kMintCid
507 : kSmiCid;
508 } else if (binary_feedback.OperandsAreSmiOrMint()) {
509
510
511 if (
call->ic_data()->HasDeoptReason(ICData::kDeoptBinaryInt64Op))
512 return false;
513 operands_type = kMintCid;
515 operands_type = kDoubleCid;
516 } else if (binary_feedback.OperandsAre(kFloat32x4Cid)) {
517 operands_type = kFloat32x4Cid;
518 } else if (binary_feedback.OperandsAre(kInt32x4Cid)) {
519 ASSERT(op_kind != Token::kMUL);
520 operands_type = kInt32x4Cid;
521 } else if (binary_feedback.OperandsAre(kFloat64x2Cid)) {
522 operands_type = kFloat64x2Cid;
523 } else {
524 return false;
525 }
526 break;
527 case Token::kDIV:
529 binary_feedback.OperandsAre(kSmiCid)) {
530 operands_type = kDoubleCid;
531 } else if (binary_feedback.OperandsAre(kFloat32x4Cid)) {
532 operands_type = kFloat32x4Cid;
533 } else if (binary_feedback.OperandsAre(kFloat64x2Cid)) {
534 operands_type = kFloat64x2Cid;
535 } else {
536 return false;
537 }
538 break;
539 case Token::kBIT_AND:
540 case Token::kBIT_OR:
541 case Token::kBIT_XOR:
542 if (binary_feedback.OperandsAre(kSmiCid)) {
543 operands_type = kSmiCid;
544 } else if (binary_feedback.OperandsAreSmiOrMint()) {
545 operands_type = kMintCid;
546 } else if (binary_feedback.OperandsAre(kInt32x4Cid)) {
547 operands_type = kInt32x4Cid;
548 } else {
549 return false;
550 }
551 break;
552 case Token::kSHL:
553 case Token::kSHR:
554 case Token::kUSHR:
555 if (binary_feedback.OperandsAre(kSmiCid)) {
556
557
558
559 if (
call->ic_data()->HasDeoptReason(ICData::kDeoptBinaryInt64Op)) {
560 return false;
561 }
562 operands_type =
563 call->ic_data()->HasDeoptReason(ICData::kDeoptBinarySmiOp)
564 ? kMintCid
565 : kSmiCid;
566 } else if (binary_feedback.OperandsAreSmiOrMint() &&
567 binary_feedback.ArgumentIs(kSmiCid)) {
568
569
570 if (
call->ic_data()->HasDeoptReason(ICData::kDeoptBinaryInt64Op)) {
571 return false;
572 }
573
574 operands_type = kMintCid;
575 } else {
576 return false;
577 }
578 break;
579 case Token::kMOD:
580 case Token::kTRUNCDIV:
581 if (binary_feedback.OperandsAre(kSmiCid)) {
582 if (
call->ic_data()->HasDeoptReason(ICData::kDeoptBinarySmiOp)) {
583 return false;
584 }
585 operands_type = kSmiCid;
586 } else {
587 return false;
588 }
589 break;
590 default:
592 }
593
596 Definition*
left =
call->ArgumentAt(0);
598 if (operands_type == kDoubleCid) {
599
600
601
602 if (op_kind != Token::kDIV) {
605 new (
Z) CheckEitherNonSmiInstr(
608 }
609
610 BinaryDoubleOpInstr* double_bin_op =
new (
Z)
611 BinaryDoubleOpInstr(op_kind,
new (
Z)
Value(left),
new (
Z)
Value(right),
614 } else if (operands_type == kMintCid) {
615 if ((op_kind == Token::kSHL) || (op_kind == Token::kSHR) ||
616 (op_kind == Token::kUSHR)) {
617 SpeculativeShiftInt64OpInstr* shift_op =
new (
Z)
618 SpeculativeShiftInt64OpInstr(op_kind,
new (
Z)
Value(left),
621 } else {
622 BinaryInt64OpInstr* bin_op =
new (
Z) BinaryInt64OpInstr(
625 }
626 } else if ((operands_type == kFloat32x4Cid) ||
627 (operands_type == kInt32x4Cid) ||
628 (operands_type == kFloat64x2Cid)) {
629 return InlineSimdBinaryOp(
call, operands_type, op_kind);
630 } else if (op_kind == Token::kMOD) {
631 ASSERT(operands_type == kSmiCid);
632 if (
right->IsConstant()) {
633 const Object& obj =
right->AsConstant()->value();
635
636
638 new (
Z) CheckSmiInstr(
new (
Z)
Value(left),
643 BinarySmiOpInstr* bin_op =
644 new (
Z) BinarySmiOpInstr(Token::kBIT_AND,
new (
Z)
Value(left),
647 return true;
648 }
649 }
650
651
653 AddCheckSmi(right,
call->deopt_id(),
call->env(),
call);
654 BinarySmiOpInstr* bin_op =
new (
Z) BinarySmiOpInstr(
657 } else {
658 ASSERT(operands_type == kSmiCid);
659
660
662 AddCheckSmi(right,
call->deopt_id(),
call->env(),
call);
663 if (
left->IsConstant() &&
664 ((op_kind == Token::kADD) || (op_kind == Token::kMUL))) {
665
666 Definition* temp =
left;
669 }
670 BinarySmiOpInstr* bin_op =
new (
Z) BinarySmiOpInstr(
673 }
674 return true;
675}
static constexpr bool IsPowerOfTwo(T x)
static bool ShouldSpecializeForDouble(const BinaryFeedback &binary_feedback)