Index: src/full-codegen.cc |
=================================================================== |
--- src/full-codegen.cc (revision 5348) |
+++ src/full-codegen.cc (working copy) |
@@ -516,18 +516,21 @@ |
void FullCodeGenerator::VisitBinaryOperation(BinaryOperation* expr) { |
Comment cmnt(masm_, "[ BinaryOperation"); |
+ Token::Value op = expr->op(); |
+ Expression* left = expr->left(); |
+ Expression* right = expr->right(); |
- OverwriteMode overwrite_mode = NO_OVERWRITE; |
- if (expr->left()->ResultOverwriteAllowed()) { |
- overwrite_mode = OVERWRITE_LEFT; |
- } else if (expr->right()->ResultOverwriteAllowed()) { |
- overwrite_mode = OVERWRITE_RIGHT; |
+ OverwriteMode mode = NO_OVERWRITE; |
+ if (left->ResultOverwriteAllowed()) { |
+ mode = OVERWRITE_LEFT; |
+ } else if (right->ResultOverwriteAllowed()) { |
+ mode = OVERWRITE_RIGHT; |
} |
- switch (expr->op()) { |
+ switch (op) { |
case Token::COMMA: |
- VisitForEffect(expr->left()); |
- Visit(expr->right()); |
+ VisitForEffect(left); |
+ Visit(right); |
break; |
case Token::OR: |
@@ -545,12 +548,31 @@ |
case Token::BIT_XOR: |
case Token::SHL: |
case Token::SHR: |
- case Token::SAR: |
- VisitForValue(expr->left(), kStack); |
- VisitForValue(expr->right(), kAccumulator); |
+ case Token::SAR: { |
+ // Figure out if either of the operands is a constant. |
+ ConstantOperand constant = ShouldInlineSmiCase(op) |
+ ? GetConstantOperand(op, left, right) |
+ : kNoConstants; |
+ |
+ // Load only the operands that we need to materialize. |
+ if (constant == kNoConstants) { |
+ VisitForValue(left, kStack); |
+ VisitForValue(right, kAccumulator); |
+ } else if (constant == kRightConstant) { |
+ VisitForValue(left, kAccumulator); |
+ } else { |
+ ASSERT(constant == kLeftConstant); |
+ VisitForValue(right, kAccumulator); |
+ } |
+ |
SetSourcePosition(expr->position()); |
- EmitBinaryOp(expr->op(), context_, overwrite_mode); |
+ if (ShouldInlineSmiCase(op)) { |
+ EmitInlineSmiBinaryOp(expr, op, context_, mode, left, right, constant); |
+ } else { |
+ EmitBinaryOp(op, context_, mode); |
+ } |
break; |
+ } |
default: |
UNREACHABLE(); |