Index: src/compiler/x64/instruction-selector-x64.cc |
diff --git a/src/compiler/x64/instruction-selector-x64.cc b/src/compiler/x64/instruction-selector-x64.cc |
index cfc1841bac507e11b23295d393814faa12151491..44103971680c17ea1132070df9eb1cbe73aaf65b 100644 |
--- a/src/compiler/x64/instruction-selector-x64.cc |
+++ b/src/compiler/x64/instruction-selector-x64.cc |
@@ -58,10 +58,20 @@ class X64OperandGenerator final : public OperandGenerator { |
MachineRepresentation rep = |
LoadRepresentationOf(input->op()).representation(); |
switch (opcode) { |
+ case kX64And: |
+ case kX64Or: |
+ case kX64Xor: |
+ case kX64Add: |
+ case kX64Sub: |
case kX64Push: |
case kX64Cmp: |
case kX64Test: |
return rep == MachineRepresentation::kWord64 || IsAnyTagged(rep); |
+ case kX64And32: |
+ case kX64Or32: |
+ case kX64Xor32: |
+ case kX64Add32: |
+ case kX64Sub32: |
case kX64Cmp32: |
case kX64Test32: |
return rep == MachineRepresentation::kWord32; |
@@ -507,7 +517,7 @@ static void VisitBinop(InstructionSelector* selector, Node* node, |
Int32BinopMatcher m(node); |
Node* left = m.left().node(); |
Node* right = m.right().node(); |
- InstructionOperand inputs[4]; |
+ InstructionOperand inputs[6]; |
size_t input_count = 0; |
InstructionOperand outputs[2]; |
size_t output_count = 0; |
@@ -528,12 +538,26 @@ static void VisitBinop(InstructionSelector* selector, Node* node, |
inputs[input_count++] = g.UseRegister(left); |
inputs[input_count++] = g.UseImmediate(right); |
} else { |
+ int effect_level = selector->GetEffectLevel(node); |
+ if (cont->IsBranch()) { |
+ effect_level = selector->GetEffectLevel( |
+ cont->true_block()->PredecessorAt(0)->control_input()); |
+ } |
if (node->op()->HasProperty(Operator::kCommutative) && |
- g.CanBeBetterLeftOperand(right)) { |
+ g.CanBeBetterLeftOperand(right) && |
+ (!g.CanBeBetterLeftOperand(left) || |
+ !g.CanBeMemoryOperand(opcode, node, right, effect_level))) { |
std::swap(left, right); |
} |
- inputs[input_count++] = g.UseRegister(left); |
- inputs[input_count++] = g.Use(right); |
+ if (g.CanBeMemoryOperand(opcode, node, right, effect_level)) { |
+ inputs[input_count++] = g.UseRegister(left); |
+ AddressingMode addressing_mode = |
+ g.GetEffectiveAddressMemoryOperand(right, inputs, &input_count); |
+ opcode |= AddressingModeField::encode(addressing_mode); |
+ } else { |
+ inputs[input_count++] = g.UseRegister(left); |
+ inputs[input_count++] = g.Use(right); |
+ } |
} |
if (cont->IsBranch()) { |