| OLD | NEW |
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <assert.h> // For assert | 5 #include <assert.h> // For assert |
| 6 #include <limits.h> // For LONG_MIN, LONG_MAX. | 6 #include <limits.h> // For LONG_MIN, LONG_MAX. |
| 7 | 7 |
| 8 #if V8_TARGET_ARCH_S390 | 8 #if V8_TARGET_ARCH_S390 |
| 9 | 9 |
| 10 #include "src/base/bits.h" | 10 #include "src/base/bits.h" |
| (...skipping 619 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 630 } | 630 } |
| 631 | 631 |
| 632 void MacroAssembler::CanonicalizeNaN(const DoubleRegister dst, | 632 void MacroAssembler::CanonicalizeNaN(const DoubleRegister dst, |
| 633 const DoubleRegister src) { | 633 const DoubleRegister src) { |
| 634 // Turn potential sNaN into qNaN | 634 // Turn potential sNaN into qNaN |
| 635 if (!dst.is(src)) ldr(dst, src); | 635 if (!dst.is(src)) ldr(dst, src); |
| 636 lzdr(kDoubleRegZero); | 636 lzdr(kDoubleRegZero); |
| 637 sdbr(dst, kDoubleRegZero); | 637 sdbr(dst, kDoubleRegZero); |
| 638 } | 638 } |
| 639 | 639 |
| 640 void MacroAssembler::ConvertIntToDouble(Register src, DoubleRegister dst) { | 640 void MacroAssembler::ConvertIntToDouble(DoubleRegister dst, Register src) { |
| 641 cdfbr(dst, src); | 641 cdfbr(dst, src); |
| 642 } | 642 } |
| 643 | 643 |
| 644 void MacroAssembler::ConvertUnsignedIntToDouble(Register src, | 644 void MacroAssembler::ConvertUnsignedIntToDouble(DoubleRegister dst, |
| 645 DoubleRegister dst) { | 645 Register src) { |
| 646 if (CpuFeatures::IsSupported(FLOATING_POINT_EXT)) { | 646 if (CpuFeatures::IsSupported(FLOATING_POINT_EXT)) { |
| 647 cdlfbr(Condition(5), Condition(0), dst, src); | 647 cdlfbr(Condition(5), Condition(0), dst, src); |
| 648 } else { | 648 } else { |
| 649 // zero-extend src | 649 // zero-extend src |
| 650 llgfr(src, src); | 650 llgfr(src, src); |
| 651 // convert to double | 651 // convert to double |
| 652 cdgbr(dst, src); | 652 cdgbr(dst, src); |
| 653 } | 653 } |
| 654 } | 654 } |
| 655 | 655 |
| 656 void MacroAssembler::ConvertIntToFloat(Register src, DoubleRegister dst) { | 656 void MacroAssembler::ConvertIntToFloat(DoubleRegister dst, Register src) { |
| 657 cefbr(Condition(4), dst, src); | 657 cefbr(Condition(4), dst, src); |
| 658 } | 658 } |
| 659 | 659 |
| 660 void MacroAssembler::ConvertUnsignedIntToFloat(Register src, | 660 void MacroAssembler::ConvertUnsignedIntToFloat(DoubleRegister dst, |
| 661 DoubleRegister dst) { | 661 Register src) { |
| 662 celfbr(Condition(4), Condition(0), dst, src); | 662 celfbr(Condition(4), Condition(0), dst, src); |
| 663 } | 663 } |
| 664 | 664 |
| 665 #if V8_TARGET_ARCH_S390X | 665 void MacroAssembler::ConvertInt64ToFloat(DoubleRegister double_dst, |
| 666 void MacroAssembler::ConvertInt64ToDouble(Register src, | 666 Register src) { |
| 667 DoubleRegister double_dst) { | 667 cegbr(double_dst, src); |
| 668 } |
| 669 |
| 670 void MacroAssembler::ConvertInt64ToDouble(DoubleRegister double_dst, |
| 671 Register src) { |
| 668 cdgbr(double_dst, src); | 672 cdgbr(double_dst, src); |
| 669 } | 673 } |
| 670 | 674 |
| 671 void MacroAssembler::ConvertUnsignedInt64ToFloat(Register src, | 675 void MacroAssembler::ConvertUnsignedInt64ToFloat(DoubleRegister double_dst, |
| 672 DoubleRegister double_dst) { | 676 Register src) { |
| 673 celgbr(Condition(0), Condition(0), double_dst, src); | 677 celgbr(Condition(0), Condition(0), double_dst, src); |
| 674 } | 678 } |
| 675 | 679 |
| 676 void MacroAssembler::ConvertUnsignedInt64ToDouble(Register src, | 680 void MacroAssembler::ConvertUnsignedInt64ToDouble(DoubleRegister double_dst, |
| 677 DoubleRegister double_dst) { | 681 Register src) { |
| 678 cdlgbr(Condition(0), Condition(0), double_dst, src); | 682 cdlgbr(Condition(0), Condition(0), double_dst, src); |
| 679 } | 683 } |
| 680 | 684 |
| 681 void MacroAssembler::ConvertInt64ToFloat(Register src, | 685 void MacroAssembler::ConvertFloat32ToInt64(const Register dst, |
| 682 DoubleRegister double_dst) { | 686 const DoubleRegister double_input, |
| 683 cegbr(double_dst, src); | |
| 684 } | |
| 685 #endif | |
| 686 | |
| 687 void MacroAssembler::ConvertFloat32ToInt64(const DoubleRegister double_input, | |
| 688 #if !V8_TARGET_ARCH_S390X | |
| 689 const Register dst_hi, | |
| 690 #endif | |
| 691 const Register dst, | |
| 692 const DoubleRegister double_dst, | |
| 693 FPRoundingMode rounding_mode) { | 687 FPRoundingMode rounding_mode) { |
| 694 Condition m = Condition(0); | 688 Condition m = Condition(0); |
| 695 switch (rounding_mode) { | 689 switch (rounding_mode) { |
| 696 case kRoundToZero: | 690 case kRoundToZero: |
| 697 m = Condition(5); | 691 m = Condition(5); |
| 698 break; | 692 break; |
| 699 case kRoundToNearest: | 693 case kRoundToNearest: |
| 700 UNIMPLEMENTED(); | 694 UNIMPLEMENTED(); |
| 701 break; | 695 break; |
| 702 case kRoundToPlusInf: | 696 case kRoundToPlusInf: |
| 703 m = Condition(6); | 697 m = Condition(6); |
| 704 break; | 698 break; |
| 705 case kRoundToMinusInf: | 699 case kRoundToMinusInf: |
| 706 m = Condition(7); | 700 m = Condition(7); |
| 707 break; | 701 break; |
| 708 default: | 702 default: |
| 709 UNIMPLEMENTED(); | 703 UNIMPLEMENTED(); |
| 710 break; | 704 break; |
| 711 } | 705 } |
| 712 cgebr(m, dst, double_input); | 706 cgebr(m, dst, double_input); |
| 713 ldgr(double_dst, dst); | |
| 714 #if !V8_TARGET_ARCH_S390X | |
| 715 srlg(dst_hi, dst, Operand(32)); | |
| 716 #endif | |
| 717 } | 707 } |
| 718 | 708 |
| 719 void MacroAssembler::ConvertDoubleToInt64(const DoubleRegister double_input, | 709 void MacroAssembler::ConvertDoubleToInt64(const Register dst, |
| 720 #if !V8_TARGET_ARCH_S390X | 710 const DoubleRegister double_input, |
| 721 const Register dst_hi, | |
| 722 #endif | |
| 723 const Register dst, | |
| 724 const DoubleRegister double_dst, | |
| 725 FPRoundingMode rounding_mode) { | 711 FPRoundingMode rounding_mode) { |
| 726 Condition m = Condition(0); | 712 Condition m = Condition(0); |
| 727 switch (rounding_mode) { | 713 switch (rounding_mode) { |
| 728 case kRoundToZero: | 714 case kRoundToZero: |
| 729 m = Condition(5); | 715 m = Condition(5); |
| 730 break; | 716 break; |
| 731 case kRoundToNearest: | 717 case kRoundToNearest: |
| 732 UNIMPLEMENTED(); | 718 UNIMPLEMENTED(); |
| 733 break; | 719 break; |
| 734 case kRoundToPlusInf: | 720 case kRoundToPlusInf: |
| 735 m = Condition(6); | 721 m = Condition(6); |
| 736 break; | 722 break; |
| 737 case kRoundToMinusInf: | 723 case kRoundToMinusInf: |
| 738 m = Condition(7); | 724 m = Condition(7); |
| 739 break; | 725 break; |
| 740 default: | 726 default: |
| 741 UNIMPLEMENTED(); | 727 UNIMPLEMENTED(); |
| 742 break; | 728 break; |
| 743 } | 729 } |
| 744 cgdbr(m, dst, double_input); | 730 cgdbr(m, dst, double_input); |
| 745 ldgr(double_dst, dst); | |
| 746 #if !V8_TARGET_ARCH_S390X | |
| 747 srlg(dst_hi, dst, Operand(32)); | |
| 748 #endif | |
| 749 } | 731 } |
| 750 | 732 |
| 751 void MacroAssembler::ConvertFloat32ToInt32(const DoubleRegister double_input, | 733 void MacroAssembler::ConvertDoubleToInt32(const Register dst, |
| 752 const Register dst, | 734 const DoubleRegister double_input, |
| 753 const DoubleRegister double_dst, | 735 FPRoundingMode rounding_mode) { |
| 736 Condition m = Condition(0); |
| 737 switch (rounding_mode) { |
| 738 case kRoundToZero: |
| 739 m = Condition(5); |
| 740 break; |
| 741 case kRoundToNearest: |
| 742 m = Condition(4); |
| 743 break; |
| 744 case kRoundToPlusInf: |
| 745 m = Condition(6); |
| 746 break; |
| 747 case kRoundToMinusInf: |
| 748 m = Condition(7); |
| 749 break; |
| 750 default: |
| 751 UNIMPLEMENTED(); |
| 752 break; |
| 753 } |
| 754 cfdbr(m, dst, double_input); |
| 755 } |
| 756 |
| 757 void MacroAssembler::ConvertFloat32ToInt32(const Register result, |
| 758 const DoubleRegister double_input, |
| 754 FPRoundingMode rounding_mode) { | 759 FPRoundingMode rounding_mode) { |
| 755 Condition m = Condition(0); | 760 Condition m = Condition(0); |
| 756 switch (rounding_mode) { | 761 switch (rounding_mode) { |
| 757 case kRoundToZero: | 762 case kRoundToZero: |
| 758 m = Condition(5); | 763 m = Condition(5); |
| 759 break; | 764 break; |
| 760 case kRoundToNearest: | 765 case kRoundToNearest: |
| 761 m = Condition(4); | 766 m = Condition(4); |
| 762 break; | 767 break; |
| 763 case kRoundToPlusInf: | 768 case kRoundToPlusInf: |
| 764 m = Condition(6); | 769 m = Condition(6); |
| 765 break; | 770 break; |
| 766 case kRoundToMinusInf: | 771 case kRoundToMinusInf: |
| 767 m = Condition(7); | 772 m = Condition(7); |
| 768 break; | 773 break; |
| 769 default: | 774 default: |
| 770 UNIMPLEMENTED(); | 775 UNIMPLEMENTED(); |
| 771 break; | 776 break; |
| 772 } | 777 } |
| 773 cfebr(m, dst, double_input); | 778 cfebr(m, result, double_input); |
| 774 Label done; | |
| 775 b(Condition(0xe), &done, Label::kNear); // special case | |
| 776 LoadImmP(dst, Operand::Zero()); | |
| 777 bind(&done); | |
| 778 ldgr(double_dst, dst); | |
| 779 } | 779 } |
| 780 | 780 |
| 781 void MacroAssembler::ConvertFloat32ToUnsignedInt32( | 781 void MacroAssembler::ConvertFloat32ToUnsignedInt32( |
| 782 const DoubleRegister double_input, const Register dst, | 782 const Register result, const DoubleRegister double_input, |
| 783 const DoubleRegister double_dst, FPRoundingMode rounding_mode) { | 783 FPRoundingMode rounding_mode) { |
| 784 Condition m = Condition(0); | 784 Condition m = Condition(0); |
| 785 switch (rounding_mode) { | 785 switch (rounding_mode) { |
| 786 case kRoundToZero: | 786 case kRoundToZero: |
| 787 m = Condition(5); | 787 m = Condition(5); |
| 788 break; | 788 break; |
| 789 case kRoundToNearest: | 789 case kRoundToNearest: |
| 790 UNIMPLEMENTED(); | 790 UNIMPLEMENTED(); |
| 791 break; | 791 break; |
| 792 case kRoundToPlusInf: | 792 case kRoundToPlusInf: |
| 793 m = Condition(6); | 793 m = Condition(6); |
| 794 break; | 794 break; |
| 795 case kRoundToMinusInf: | 795 case kRoundToMinusInf: |
| 796 m = Condition(7); | 796 m = Condition(7); |
| 797 break; | 797 break; |
| 798 default: | 798 default: |
| 799 UNIMPLEMENTED(); | 799 UNIMPLEMENTED(); |
| 800 break; | 800 break; |
| 801 } | 801 } |
| 802 clfebr(m, Condition(0), dst, double_input); | 802 clfebr(m, Condition(0), result, double_input); |
| 803 Label done; | |
| 804 b(Condition(0xe), &done, Label::kNear); // special case | |
| 805 LoadImmP(dst, Operand::Zero()); | |
| 806 bind(&done); | |
| 807 ldgr(double_dst, dst); | |
| 808 } | 803 } |
| 809 | 804 |
| 810 #if V8_TARGET_ARCH_S390X | |
| 811 void MacroAssembler::ConvertFloat32ToUnsignedInt64( | 805 void MacroAssembler::ConvertFloat32ToUnsignedInt64( |
| 812 const DoubleRegister double_input, const Register dst, | 806 const Register result, const DoubleRegister double_input, |
| 813 const DoubleRegister double_dst, FPRoundingMode rounding_mode) { | 807 FPRoundingMode rounding_mode) { |
| 814 Condition m = Condition(0); | 808 Condition m = Condition(0); |
| 815 switch (rounding_mode) { | 809 switch (rounding_mode) { |
| 816 case kRoundToZero: | 810 case kRoundToZero: |
| 817 m = Condition(5); | 811 m = Condition(5); |
| 818 break; | 812 break; |
| 819 case kRoundToNearest: | 813 case kRoundToNearest: |
| 820 UNIMPLEMENTED(); | 814 UNIMPLEMENTED(); |
| 821 break; | 815 break; |
| 822 case kRoundToPlusInf: | 816 case kRoundToPlusInf: |
| 823 m = Condition(6); | 817 m = Condition(6); |
| 824 break; | 818 break; |
| 825 case kRoundToMinusInf: | 819 case kRoundToMinusInf: |
| 826 m = Condition(7); | 820 m = Condition(7); |
| 827 break; | 821 break; |
| 828 default: | 822 default: |
| 829 UNIMPLEMENTED(); | 823 UNIMPLEMENTED(); |
| 830 break; | 824 break; |
| 831 } | 825 } |
| 832 clgebr(m, Condition(0), dst, double_input); | 826 clgebr(m, Condition(0), result, double_input); |
| 833 ldgr(double_dst, dst); | |
| 834 } | 827 } |
| 835 | 828 |
| 836 void MacroAssembler::ConvertDoubleToUnsignedInt64( | 829 void MacroAssembler::ConvertDoubleToUnsignedInt64( |
| 837 const DoubleRegister double_input, const Register dst, | 830 const Register dst, const DoubleRegister double_input, |
| 838 const DoubleRegister double_dst, FPRoundingMode rounding_mode) { | 831 FPRoundingMode rounding_mode) { |
| 839 Condition m = Condition(0); | 832 Condition m = Condition(0); |
| 840 switch (rounding_mode) { | 833 switch (rounding_mode) { |
| 841 case kRoundToZero: | 834 case kRoundToZero: |
| 842 m = Condition(5); | 835 m = Condition(5); |
| 843 break; | 836 break; |
| 844 case kRoundToNearest: | 837 case kRoundToNearest: |
| 845 UNIMPLEMENTED(); | 838 UNIMPLEMENTED(); |
| 846 break; | 839 break; |
| 847 case kRoundToPlusInf: | 840 case kRoundToPlusInf: |
| 848 m = Condition(6); | 841 m = Condition(6); |
| 849 break; | 842 break; |
| 850 case kRoundToMinusInf: | 843 case kRoundToMinusInf: |
| 851 m = Condition(7); | 844 m = Condition(7); |
| 852 break; | 845 break; |
| 853 default: | 846 default: |
| 854 UNIMPLEMENTED(); | 847 UNIMPLEMENTED(); |
| 855 break; | 848 break; |
| 856 } | 849 } |
| 857 clgdbr(m, Condition(0), dst, double_input); | 850 clgdbr(m, Condition(0), dst, double_input); |
| 858 ldgr(double_dst, dst); | |
| 859 } | 851 } |
| 860 | 852 |
| 861 #endif | 853 void MacroAssembler::ConvertDoubleToUnsignedInt32( |
| 854 const Register dst, const DoubleRegister double_input, |
| 855 FPRoundingMode rounding_mode) { |
| 856 Condition m = Condition(0); |
| 857 switch (rounding_mode) { |
| 858 case kRoundToZero: |
| 859 m = Condition(5); |
| 860 break; |
| 861 case kRoundToNearest: |
| 862 UNIMPLEMENTED(); |
| 863 break; |
| 864 case kRoundToPlusInf: |
| 865 m = Condition(6); |
| 866 break; |
| 867 case kRoundToMinusInf: |
| 868 m = Condition(7); |
| 869 break; |
| 870 default: |
| 871 UNIMPLEMENTED(); |
| 872 break; |
| 873 } |
| 874 clfdbr(m, Condition(0), dst, double_input); |
| 875 } |
| 862 | 876 |
| 863 #if !V8_TARGET_ARCH_S390X | 877 #if !V8_TARGET_ARCH_S390X |
| 864 void MacroAssembler::ShiftLeftPair(Register dst_low, Register dst_high, | 878 void MacroAssembler::ShiftLeftPair(Register dst_low, Register dst_high, |
| 865 Register src_low, Register src_high, | 879 Register src_low, Register src_high, |
| 866 Register scratch, Register shift) { | 880 Register scratch, Register shift) { |
| 867 LoadRR(r0, src_high); | 881 LoadRR(r0, src_high); |
| 868 LoadRR(r1, src_low); | 882 LoadRR(r1, src_low); |
| 869 sldl(r0, shift, Operand::Zero()); | 883 sldl(r0, shift, Operand::Zero()); |
| 870 LoadRR(dst_high, r0); | 884 LoadRR(dst_high, r0); |
| 871 LoadRR(dst_low, r1); | 885 LoadRR(dst_low, r1); |
| (...skipping 997 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1869 LoadlB(type_reg, FieldMemOperand(map, Map::kInstanceTypeOffset)); | 1883 LoadlB(type_reg, FieldMemOperand(map, Map::kInstanceTypeOffset)); |
| 1870 CmpP(type_reg, Operand(type)); | 1884 CmpP(type_reg, Operand(type)); |
| 1871 } | 1885 } |
| 1872 | 1886 |
| 1873 void MacroAssembler::CompareRoot(Register obj, Heap::RootListIndex index) { | 1887 void MacroAssembler::CompareRoot(Register obj, Heap::RootListIndex index) { |
| 1874 CmpP(obj, MemOperand(kRootRegister, index << kPointerSizeLog2)); | 1888 CmpP(obj, MemOperand(kRootRegister, index << kPointerSizeLog2)); |
| 1875 } | 1889 } |
| 1876 | 1890 |
| 1877 void MacroAssembler::SmiToDouble(DoubleRegister value, Register smi) { | 1891 void MacroAssembler::SmiToDouble(DoubleRegister value, Register smi) { |
| 1878 SmiUntag(ip, smi); | 1892 SmiUntag(ip, smi); |
| 1879 ConvertIntToDouble(ip, value); | 1893 ConvertIntToDouble(value, ip); |
| 1880 } | 1894 } |
| 1881 | 1895 |
| 1882 void MacroAssembler::CompareMap(Register obj, Register scratch, Handle<Map> map, | 1896 void MacroAssembler::CompareMap(Register obj, Register scratch, Handle<Map> map, |
| 1883 Label* early_success) { | 1897 Label* early_success) { |
| 1884 LoadP(scratch, FieldMemOperand(obj, HeapObject::kMapOffset)); | 1898 LoadP(scratch, FieldMemOperand(obj, HeapObject::kMapOffset)); |
| 1885 CompareMap(obj, map, early_success); | 1899 CompareMap(obj, map, early_success); |
| 1886 } | 1900 } |
| 1887 | 1901 |
| 1888 void MacroAssembler::CompareMap(Register obj_map, Handle<Map> map, | 1902 void MacroAssembler::CompareMap(Register obj_map, Handle<Map> map, |
| 1889 Label* early_success) { | 1903 Label* early_success) { |
| (...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1994 Cmp32(scratch, Operand::Zero()); | 2008 Cmp32(scratch, Operand::Zero()); |
| 1995 } | 2009 } |
| 1996 | 2010 |
| 1997 void MacroAssembler::TryDoubleToInt32Exact(Register result, | 2011 void MacroAssembler::TryDoubleToInt32Exact(Register result, |
| 1998 DoubleRegister double_input, | 2012 DoubleRegister double_input, |
| 1999 Register scratch, | 2013 Register scratch, |
| 2000 DoubleRegister double_scratch) { | 2014 DoubleRegister double_scratch) { |
| 2001 Label done; | 2015 Label done; |
| 2002 DCHECK(!double_input.is(double_scratch)); | 2016 DCHECK(!double_input.is(double_scratch)); |
| 2003 | 2017 |
| 2004 ConvertDoubleToInt64(double_input, | 2018 ConvertDoubleToInt64(result, double_input); |
| 2005 #if !V8_TARGET_ARCH_S390X | |
| 2006 scratch, | |
| 2007 #endif | |
| 2008 result, double_scratch); | |
| 2009 | 2019 |
| 2010 #if V8_TARGET_ARCH_S390X | 2020 TestIfInt32(result); |
| 2011 TestIfInt32(result, r0); | |
| 2012 #else | |
| 2013 TestIfInt32(scratch, result, r0); | |
| 2014 #endif | |
| 2015 bne(&done); | 2021 bne(&done); |
| 2016 | 2022 |
| 2017 // convert back and compare | 2023 // convert back and compare |
| 2018 lgdr(scratch, double_scratch); | 2024 cdfbr(double_scratch, result); |
| 2019 cdfbr(double_scratch, scratch); | |
| 2020 cdbr(double_scratch, double_input); | 2025 cdbr(double_scratch, double_input); |
| 2021 bind(&done); | 2026 bind(&done); |
| 2022 } | 2027 } |
| 2023 | 2028 |
| 2024 void MacroAssembler::TryInt32Floor(Register result, DoubleRegister double_input, | 2029 void MacroAssembler::TryInt32Floor(Register result, DoubleRegister double_input, |
| 2025 Register input_high, Register scratch, | 2030 Register input_high, Register scratch, |
| 2026 DoubleRegister double_scratch, Label* done, | 2031 DoubleRegister double_scratch, Label* done, |
| 2027 Label* exact) { | 2032 Label* exact) { |
| 2028 DCHECK(!result.is(input_high)); | 2033 DCHECK(!result.is(input_high)); |
| 2029 DCHECK(!double_input.is(double_scratch)); | 2034 DCHECK(!double_input.is(double_scratch)); |
| 2030 Label exception; | 2035 Label exception; |
| 2031 | 2036 |
| 2032 // Move high word into input_high | 2037 // Move high word into input_high |
| 2033 lay(sp, MemOperand(sp, -kDoubleSize)); | 2038 lay(sp, MemOperand(sp, -kDoubleSize)); |
| 2034 StoreDouble(double_input, MemOperand(sp)); | 2039 StoreDouble(double_input, MemOperand(sp)); |
| 2035 LoadlW(input_high, MemOperand(sp, Register::kExponentOffset)); | 2040 LoadlW(input_high, MemOperand(sp, Register::kExponentOffset)); |
| 2036 la(sp, MemOperand(sp, kDoubleSize)); | 2041 la(sp, MemOperand(sp, kDoubleSize)); |
| 2037 | 2042 |
| 2038 // Test for NaN/Inf | 2043 // Test for NaN/Inf |
| 2039 ExtractBitMask(result, input_high, HeapNumber::kExponentMask); | 2044 ExtractBitMask(result, input_high, HeapNumber::kExponentMask); |
| 2040 CmpLogicalP(result, Operand(0x7ff)); | 2045 CmpLogicalP(result, Operand(0x7ff)); |
| 2041 beq(&exception); | 2046 beq(&exception); |
| 2042 | 2047 |
| 2043 // Convert (rounding to -Inf) | 2048 // Convert (rounding to -Inf) |
| 2044 ConvertDoubleToInt64(double_input, | 2049 ConvertDoubleToInt64(result, double_input, kRoundToMinusInf); |
| 2045 #if !V8_TARGET_ARCH_S390X | |
| 2046 scratch, | |
| 2047 #endif | |
| 2048 result, double_scratch, kRoundToMinusInf); | |
| 2049 | 2050 |
| 2050 // Test for overflow | 2051 // Test for overflow |
| 2051 #if V8_TARGET_ARCH_S390X | 2052 TestIfInt32(result); |
| 2052 TestIfInt32(result, r0); | |
| 2053 #else | |
| 2054 TestIfInt32(scratch, result, r0); | |
| 2055 #endif | |
| 2056 bne(&exception); | 2053 bne(&exception); |
| 2057 | 2054 |
| 2058 // Test for exactness | 2055 // Test for exactness |
| 2059 lgdr(scratch, double_scratch); | 2056 cdfbr(double_scratch, result); |
| 2060 cdfbr(double_scratch, scratch); | |
| 2061 cdbr(double_scratch, double_input); | 2057 cdbr(double_scratch, double_input); |
| 2062 beq(exact); | 2058 beq(exact); |
| 2063 b(done); | 2059 b(done); |
| 2064 | 2060 |
| 2065 bind(&exception); | 2061 bind(&exception); |
| 2066 } | 2062 } |
| 2067 | 2063 |
| 2068 void MacroAssembler::TryInlineTruncateDoubleToI(Register result, | 2064 void MacroAssembler::TryInlineTruncateDoubleToI(Register result, |
| 2069 DoubleRegister double_input, | 2065 DoubleRegister double_input, |
| 2070 Label* done) { | 2066 Label* done) { |
| 2071 DoubleRegister double_scratch = kScratchDoubleReg; | 2067 ConvertDoubleToInt64(result, double_input); |
| 2072 #if !V8_TARGET_ARCH_S390X | |
| 2073 Register scratch = ip; | |
| 2074 #endif | |
| 2075 | 2068 |
| 2076 ConvertDoubleToInt64(double_input, | 2069 // Test for overflow |
| 2077 #if !V8_TARGET_ARCH_S390X | 2070 TestIfInt32(result); |
| 2078 scratch, | |
| 2079 #endif | |
| 2080 result, double_scratch); | |
| 2081 | |
| 2082 // Test for overflow | |
| 2083 #if V8_TARGET_ARCH_S390X | |
| 2084 TestIfInt32(result, r0); | |
| 2085 #else | |
| 2086 TestIfInt32(scratch, result, r0); | |
| 2087 #endif | |
| 2088 beq(done); | 2071 beq(done); |
| 2089 } | 2072 } |
| 2090 | 2073 |
| 2091 void MacroAssembler::TruncateDoubleToI(Register result, | 2074 void MacroAssembler::TruncateDoubleToI(Register result, |
| 2092 DoubleRegister double_input) { | 2075 DoubleRegister double_input) { |
| 2093 Label done; | 2076 Label done; |
| 2094 | 2077 |
| 2095 TryInlineTruncateDoubleToI(result, double_input, &done); | 2078 TryInlineTruncateDoubleToI(result, double_input, &done); |
| 2096 | 2079 |
| 2097 // If we fell through then inline version didn't succeed - call stub instead. | 2080 // If we fell through then inline version didn't succeed - call stub instead. |
| (...skipping 3363 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5461 } | 5444 } |
| 5462 if (mag.shift > 0) ShiftRightArith(result, result, Operand(mag.shift)); | 5445 if (mag.shift > 0) ShiftRightArith(result, result, Operand(mag.shift)); |
| 5463 ExtractBit(r0, dividend, 31); | 5446 ExtractBit(r0, dividend, 31); |
| 5464 AddP(result, r0); | 5447 AddP(result, r0); |
| 5465 } | 5448 } |
| 5466 | 5449 |
| 5467 } // namespace internal | 5450 } // namespace internal |
| 5468 } // namespace v8 | 5451 } // namespace v8 |
| 5469 | 5452 |
| 5470 #endif // V8_TARGET_ARCH_S390 | 5453 #endif // V8_TARGET_ARCH_S390 |
| OLD | NEW |