diff options
Diffstat (limited to 'src/vm_mips64.dasc')
-rw-r--r-- | src/vm_mips64.dasc | 68 |
1 files changed, 49 insertions, 19 deletions
diff --git a/src/vm_mips64.dasc b/src/vm_mips64.dasc index 4ae19b7d..dac143a4 100644 --- a/src/vm_mips64.dasc +++ b/src/vm_mips64.dasc | |||
@@ -1852,18 +1852,26 @@ static void build_subroutines(BuildCtx *ctx) | |||
1852 | |.if MIPSR6 | 1852 | |.if MIPSR6 |
1853 | | fpins FRET1, FRET1, FARG1 | 1853 | | fpins FRET1, FRET1, FARG1 |
1854 | |.else | 1854 | |.else |
1855 | |.if fpins // ismax | ||
1856 | | c.olt.d FARG1, FRET1 | ||
1857 | |.else | ||
1855 | | c.olt.d FRET1, FARG1 | 1858 | | c.olt.d FRET1, FARG1 |
1856 | | fpins FRET1, FARG1 | ||
1857 | |.endif | 1859 | |.endif |
1860 | | movf.d FRET1, FARG1 | ||
1861 | |.endif | ||
1862 | |.else | ||
1863 | |.if fpins // ismax | ||
1864 | | bal ->vm_sfcmpogt | ||
1858 | |.else | 1865 | |.else |
1859 | | bal ->vm_sfcmpolt | 1866 | | bal ->vm_sfcmpolt |
1867 | |.endif | ||
1860 | |. nop | 1868 | |. nop |
1861 | |.if MIPSR6 | 1869 | |.if MIPSR6 |
1862 | | intins AT, CARG2, CRET1 | 1870 | | seleqz AT, CARG2, CRET1 |
1863 | | intinsc CARG1, CARG1, CRET1 | 1871 | | selnez CARG1, CARG1, CRET1 |
1864 | | or CARG1, CARG1, AT | 1872 | | or CARG1, CARG1, AT |
1865 | |.else | 1873 | |.else |
1866 | | intins CARG1, CARG2, CRET1 | 1874 | | movz CARG1, CARG2, CRET1 |
1867 | |.endif | 1875 | |.endif |
1868 | |.endif | 1876 | |.endif |
1869 | | b <6 | 1877 | | b <6 |
@@ -1889,8 +1897,8 @@ static void build_subroutines(BuildCtx *ctx) | |||
1889 | | math_minmax math_min, seleqz, selnez, min.d | 1897 | | math_minmax math_min, seleqz, selnez, min.d |
1890 | | math_minmax math_max, selnez, seleqz, max.d | 1898 | | math_minmax math_max, selnez, seleqz, max.d |
1891 | |.else | 1899 | |.else |
1892 | | math_minmax math_min, movz, _, movf.d | 1900 | | math_minmax math_min, movz, _, 0 |
1893 | | math_minmax math_max, movn, _, movt.d | 1901 | | math_minmax math_max, movn, _, 1 |
1894 | |.endif | 1902 | |.endif |
1895 | | | 1903 | | |
1896 | |//-- String library ----------------------------------------------------- | 1904 | |//-- String library ----------------------------------------------------- |
@@ -2108,7 +2116,6 @@ static void build_subroutines(BuildCtx *ctx) | |||
2108 | | dsllv CRET2, CRET2, TMP0 // Integer check. | 2116 | | dsllv CRET2, CRET2, TMP0 // Integer check. |
2109 | | sextw AT, CRET1 | 2117 | | sextw AT, CRET1 |
2110 | | xor AT, CRET1, AT // Range check. | 2118 | | xor AT, CRET1, AT // Range check. |
2111 | | jr ra | ||
2112 | |.if MIPSR6 | 2119 | |.if MIPSR6 |
2113 | | seleqz AT, AT, CRET2 | 2120 | | seleqz AT, AT, CRET2 |
2114 | | selnez CRET2, CRET2, CRET2 | 2121 | | selnez CRET2, CRET2, CRET2 |
@@ -2809,6 +2816,34 @@ static void build_subroutines(BuildCtx *ctx) | |||
2809 | |. move CRET1, CRET2 | 2816 | |. move CRET1, CRET2 |
2810 | |.endif | 2817 | |.endif |
2811 | | | 2818 | | |
2819 | |->vm_sfcmpogt: | ||
2820 | |.if not FPU | ||
2821 | | dsll AT, CARG2, 1 | ||
2822 | | dsll TMP0, CARG1, 1 | ||
2823 | | or TMP1, AT, TMP0 | ||
2824 | | beqz TMP1, >8 // Both args +-0: return 0. | ||
2825 | |. lui TMP1, 0xffe0 | ||
2826 | | dsll TMP1, TMP1, 32 | ||
2827 | | sltu AT, TMP1, AT | ||
2828 | | sltu TMP0, TMP1, TMP0 | ||
2829 | | or TMP1, AT, TMP0 | ||
2830 | | bnez TMP1, >9 // Either arg is NaN: return 0 or 1; | ||
2831 | |. and AT, CARG2, CARG1 | ||
2832 | | bltz AT, >5 // Both args negative? | ||
2833 | |. nop | ||
2834 | | jr ra | ||
2835 | |. slt CRET1, CARG2, CARG1 | ||
2836 | |5: // Swap conditions if both operands are negative. | ||
2837 | | jr ra | ||
2838 | |. slt CRET1, CARG1, CARG2 | ||
2839 | |8: | ||
2840 | | jr ra | ||
2841 | |. li CRET1, 0 | ||
2842 | |9: | ||
2843 | | jr ra | ||
2844 | |. li CRET1, 0 | ||
2845 | |.endif | ||
2846 | | | ||
2812 | |// Soft-float comparison. Equivalent to c.ole.d a, b or c.ole.d b, a. | 2847 | |// Soft-float comparison. Equivalent to c.ole.d a, b or c.ole.d b, a. |
2813 | |// Input: CARG1, CARG2, TMP3. Output: CRET1. Temporaries: AT, TMP0, TMP1. | 2848 | |// Input: CARG1, CARG2, TMP3. Output: CRET1. Temporaries: AT, TMP0, TMP1. |
2814 | |->vm_sfcmpolex: | 2849 | |->vm_sfcmpolex: |
@@ -2840,34 +2875,29 @@ static void build_subroutines(BuildCtx *ctx) | |||
2840 | |. li CRET1, 0 | 2875 | |. li CRET1, 0 |
2841 | |.endif | 2876 | |.endif |
2842 | | | 2877 | | |
2843 | |.macro sfmin_max, name, intins, intinsc | 2878 | |.macro sfmin_max, name, fpcall |
2844 | |->vm_sf .. name: | 2879 | |->vm_sf .. name: |
2845 | |.if JIT and not FPU | 2880 | |.if JIT and not FPU |
2846 | | move TMP2, ra | 2881 | | move TMP2, ra |
2847 | | bal ->vm_sfcmpolt | 2882 | | bal ->fpcall |
2848 | |. nop | 2883 | |. nop |
2849 | | move ra, TMP2 | 2884 | | move ra, TMP2 |
2850 | | move TMP0, CRET1 | 2885 | | move TMP0, CRET1 |
2851 | | move CRET1, CARG1 | 2886 | | move CRET1, CARG1 |
2852 | |.if MIPSR6 | 2887 | |.if MIPSR6 |
2853 | | intins CRET1, CRET1, TMP0 | 2888 | | selnez CRET1, CRET1, TMP0 |
2854 | | intinsc TMP0, CARG2, TMP0 | 2889 | | seleqz TMP0, CARG2, TMP0 |
2855 | | jr ra | 2890 | | jr ra |
2856 | |. or CRET1, CRET1, TMP0 | 2891 | |. or CRET1, CRET1, TMP0 |
2857 | |.else | 2892 | |.else |
2858 | | jr ra | 2893 | | jr ra |
2859 | |. intins CRET1, CARG2, TMP0 | 2894 | |. movz CRET1, CARG2, TMP0 |
2860 | |.endif | 2895 | |.endif |
2861 | |.endif | 2896 | |.endif |
2862 | |.endmacro | 2897 | |.endmacro |
2863 | | | 2898 | | |
2864 | |.if MIPSR6 | 2899 | | sfmin_max min, vm_sfcmpolt |
2865 | | sfmin_max min, selnez, seleqz | 2900 | | sfmin_max max, vm_sfcmpogt |
2866 | | sfmin_max max, seleqz, selnez | ||
2867 | |.else | ||
2868 | | sfmin_max min, movz, _ | ||
2869 | | sfmin_max max, movn, _ | ||
2870 | |.endif | ||
2871 | | | 2901 | | |
2872 | |//----------------------------------------------------------------------- | 2902 | |//----------------------------------------------------------------------- |
2873 | |//-- Miscellaneous functions -------------------------------------------- | 2903 | |//-- Miscellaneous functions -------------------------------------------- |