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

Side by Side Diff: runtime/vm/intermediate_language_ia32.cc

Issue 19482023: Fix math min/max for -0.0 case. Enable min_max_test to run in optimizing compiler as well. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 7 years, 5 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 #include "vm/globals.h" // Needed here to get TARGET_ARCH_IA32. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_IA32.
6 #if defined(TARGET_ARCH_IA32) 6 #if defined(TARGET_ARCH_IA32)
7 7
8 #include "vm/intermediate_language.h" 8 #include "vm/intermediate_language.h"
9 9
10 #include "lib/error.h" 10 #include "lib/error.h"
(...skipping 3619 matching lines...) Expand 10 before | Expand all | Expand 10 after
3630 3630
3631 3631
3632 void MathSqrtInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 3632 void MathSqrtInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
3633 __ sqrtsd(locs()->out().fpu_reg(), locs()->in(0).fpu_reg()); 3633 __ sqrtsd(locs()->out().fpu_reg(), locs()->in(0).fpu_reg());
3634 } 3634 }
3635 3635
3636 3636
3637 LocationSummary* MathMinMaxInstr::MakeLocationSummary() const { 3637 LocationSummary* MathMinMaxInstr::MakeLocationSummary() const {
3638 if (result_cid() == kDoubleCid) { 3638 if (result_cid() == kDoubleCid) {
3639 const intptr_t kNumInputs = 2; 3639 const intptr_t kNumInputs = 2;
3640 const intptr_t kNumTemps = 0; 3640 const intptr_t kNumTemps = 1;
3641 LocationSummary* summary = 3641 LocationSummary* summary =
3642 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kNoCall); 3642 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kNoCall);
3643 summary->set_in(0, Location::RequiresFpuRegister()); 3643 summary->set_in(0, Location::RequiresFpuRegister());
3644 summary->set_in(1, Location::RequiresFpuRegister()); 3644 summary->set_in(1, Location::RequiresFpuRegister());
3645 summary->set_out(Location::RequiresFpuRegister()); 3645 summary->set_out(Location::RequiresFpuRegister());
3646 summary->set_temp(0, Location::RequiresRegister());
3646 return summary; 3647 return summary;
3647 } 3648 }
3648 ASSERT(result_cid() == kSmiCid); 3649 ASSERT(result_cid() == kSmiCid);
3649 UNIMPLEMENTED(); 3650 UNIMPLEMENTED();
3650 return NULL; 3651 return NULL;
3651 } 3652 }
3652 3653
3653 3654
3654 void MathMinMaxInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 3655 void MathMinMaxInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
3656 ASSERT((op_kind() == MethodRecognizer::kMathMin) ||
3657 (op_kind() == MethodRecognizer::kMathMax));
3655 if (result_cid() == kDoubleCid) { 3658 if (result_cid() == kDoubleCid) {
3656 Label done, is_left, is_nan; 3659 Label done, returns_left, returns_nan, are_equal;
3657 XmmRegister left = locs()->in(0).fpu_reg(); 3660 XmmRegister left = locs()->in(0).fpu_reg();
3658 XmmRegister right = locs()->in(1).fpu_reg(); 3661 XmmRegister right = locs()->in(1).fpu_reg();
3659 XmmRegister result = locs()->out().fpu_reg(); 3662 XmmRegister result = locs()->out().fpu_reg();
3663 Register temp = locs()->temp(0).reg();
3660 __ comisd(left, right); 3664 __ comisd(left, right);
3661 __ j(PARITY_EVEN, &is_nan, Assembler::kNearJump); 3665 __ j(PARITY_EVEN, &returns_nan, Assembler::kNearJump);
3662 Condition double_condition; 3666 __ j(EQUAL, &are_equal, Assembler::kNearJump);
3663 if (op_kind() == MethodRecognizer::kMathMin) { 3667 const intptr_t is_min = (op_kind() == MethodRecognizer::kMathMin);
3664 double_condition = TokenKindToDoubleCondition(Token::kLT); 3668 const Condition double_condition =
3665 } else { 3669 is_min ? TokenKindToDoubleCondition(Token::kLT)
3666 ASSERT(op_kind() == MethodRecognizer::kMathMax); 3670 : TokenKindToDoubleCondition(Token::kGT);
3667 double_condition = TokenKindToDoubleCondition(Token::kGT); 3671 __ j(double_condition, &returns_left, Assembler::kNearJump);
3668 }
3669 __ j(double_condition, &is_left, Assembler::kNearJump);
3670 __ movsd(result, right); 3672 __ movsd(result, right);
3671 __ jmp(&done, Assembler::kNearJump); 3673 __ jmp(&done, Assembler::kNearJump);
3672 __ Bind(&is_left); 3674
3675 __ Bind(&returns_left);
3673 __ movsd(result, left); 3676 __ movsd(result, left);
3674 __ jmp(&done); 3677 __ jmp(&done, Assembler::kNearJump);
3675 __ Bind(&is_nan); 3678
3679 __ Bind(&returns_nan);
3676 static double kNaN = NAN; 3680 static double kNaN = NAN;
3677 __ movsd(result, Address::Absolute(reinterpret_cast<uword>(&kNaN))); 3681 __ movsd(result, Address::Absolute(reinterpret_cast<uword>(&kNaN)));
3682 __ jmp(&done, Assembler::kNearJump);
3683
3684 __ Bind(&are_equal);
3685 Label left_is_negative;
3686 // Check for negative zero: -0.0 is equal 0.0 but min or max must return
3687 // -0.0 or 0.0 respectively.
3688 // Check for negative left value (get the sign bit):
3689 // - min -> left is negative ? left : right.
3690 // - max -> left is negative ? right : left
3691 // Check the sign bit.
3692 __ movmskpd(temp, left);
3693 __ testl(temp, Immediate(1));
3694 __ j(NOT_ZERO, &left_is_negative, Assembler::kNearJump);
3695 // Left is positive.
3696 __ movsd(result, (is_min ? right : left));
3697 __ jmp(&done, Assembler::kNearJump);
3698
3699 __ Bind(&left_is_negative);
3700 __ movsd(result, (is_min ? left : right));
3678 __ Bind(&done); 3701 __ Bind(&done);
3679 return; 3702 return;
3680 } 3703 }
3681 ASSERT(result_cid() == kSmiCid); 3704 ASSERT(result_cid() == kSmiCid);
3682 UNIMPLEMENTED(); 3705 UNIMPLEMENTED();
3683 } 3706 }
3684 3707
3685 3708
3686 LocationSummary* UnarySmiOpInstr::MakeLocationSummary() const { 3709 LocationSummary* UnarySmiOpInstr::MakeLocationSummary() const {
3687 const intptr_t kNumInputs = 1; 3710 const intptr_t kNumInputs = 1;
(...skipping 1110 matching lines...) Expand 10 before | Expand all | Expand 10 after
4798 PcDescriptors::kOther, 4821 PcDescriptors::kOther,
4799 locs()); 4822 locs());
4800 __ Drop(2); // Discard type arguments and receiver. 4823 __ Drop(2); // Discard type arguments and receiver.
4801 } 4824 }
4802 4825
4803 } // namespace dart 4826 } // namespace dart
4804 4827
4805 #undef __ 4828 #undef __
4806 4829
4807 #endif // defined TARGET_ARCH_IA32 4830 #endif // defined TARGET_ARCH_IA32
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698