summaryrefslogtreecommitdiffstats
path: root/compiler/optimizing/code_generator_x86_64.cc
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/optimizing/code_generator_x86_64.cc')
-rw-r--r--compiler/optimizing/code_generator_x86_64.cc28
1 files changed, 17 insertions, 11 deletions
diff --git a/compiler/optimizing/code_generator_x86_64.cc b/compiler/optimizing/code_generator_x86_64.cc
index 393eb1a2d4..d37ef06687 100644
--- a/compiler/optimizing/code_generator_x86_64.cc
+++ b/compiler/optimizing/code_generator_x86_64.cc
@@ -482,10 +482,13 @@ void LocationsBuilderX86_64::VisitIf(HIf* if_instr) {
void InstructionCodeGeneratorX86_64::VisitIf(HIf* if_instr) {
HInstruction* cond = if_instr->InputAt(0);
- if (!cond->IsCondition() || cond->AsCondition()->NeedsMaterialization()) {
- // Moves do not affect the eflags register, so if the condition is evaluated
- // just before the if, we don't need to evaluate it again.
- if (!cond->IsCondition() || !cond->AsCondition()->IsBeforeWhenDisregardMoves(if_instr)) {
+ bool materialized = !cond->IsCondition() || cond->AsCondition()->NeedsMaterialization();
+ // Moves do not affect the eflags register, so if the condition is evaluated
+ // just before the if, we don't need to evaluate it again.
+ bool eflags_set = cond->IsCondition()
+ && cond->AsCondition()->IsBeforeWhenDisregardMoves(if_instr);
+ if (materialized) {
+ if (!eflags_set) {
// Materialized condition, compare against 0.
Location lhs = if_instr->GetLocations()->InAt(0);
if (lhs.IsRegister()) {
@@ -493,8 +496,11 @@ void InstructionCodeGeneratorX86_64::VisitIf(HIf* if_instr) {
} else {
__ cmpl(Address(CpuRegister(RSP), lhs.GetStackIndex()), Immediate(0));
}
+ __ j(kNotEqual, codegen_->GetLabelOf(if_instr->IfTrueSuccessor()));
+ } else {
+ __ j(X86_64Condition(cond->AsCondition()->GetCondition()),
+ codegen_->GetLabelOf(if_instr->IfTrueSuccessor()));
}
- __ j(kNotEqual, codegen_->GetLabelOf(if_instr->IfTrueSuccessor()));
} else {
Location lhs = cond->GetLocations()->InAt(0);
Location rhs = cond->GetLocations()->InAt(1);
@@ -574,13 +580,13 @@ void InstructionCodeGeneratorX86_64::VisitCondition(HCondition* comp) {
// Clear register: setcc only sets the low byte.
__ xorq(reg, reg);
if (locations->InAt(1).IsRegister()) {
- __ cmpq(locations->InAt(0).As<CpuRegister>(),
+ __ cmpl(locations->InAt(0).As<CpuRegister>(),
locations->InAt(1).As<CpuRegister>());
} else if (locations->InAt(1).IsConstant()) {
- __ cmpq(locations->InAt(0).As<CpuRegister>(),
+ __ cmpl(locations->InAt(0).As<CpuRegister>(),
Immediate(locations->InAt(1).GetConstant()->AsIntConstant()->GetValue()));
} else {
- __ cmpq(locations->InAt(0).As<CpuRegister>(),
+ __ cmpl(locations->InAt(0).As<CpuRegister>(),
Address(CpuRegister(RSP), locations->InAt(1).GetStackIndex()));
}
__ setcc(X86_64Condition(comp->GetCondition()), reg);
@@ -879,10 +885,10 @@ void InstructionCodeGeneratorX86_64::VisitInvokeVirtual(HInvokeVirtual* invoke)
size_t class_offset = mirror::Object::ClassOffset().SizeValue();
// temp = object->GetClass();
if (receiver.IsStackSlot()) {
- __ movq(temp, Address(CpuRegister(RSP), receiver.GetStackIndex()));
- __ movq(temp, Address(temp, class_offset));
+ __ movl(temp, Address(CpuRegister(RSP), receiver.GetStackIndex()));
+ __ movl(temp, Address(temp, class_offset));
} else {
- __ movq(temp, Address(receiver.As<CpuRegister>(), class_offset));
+ __ movl(temp, Address(receiver.As<CpuRegister>(), class_offset));
}
// temp = temp->GetMethodAt(method_offset);
__ movl(temp, Address(temp, method_offset));