1 /* Functions needed for soft-float on riscv-linux. Based on 2 rs6000/ppc64-fp.c with TF types removed. 3 4 Copyright (C) 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 5 2000, 2001, 2002, 2003, 2004, 2006, 2009 Free Software Foundation, 6 Inc. 7 8 This file is part of GCC. 9 10 GCC is free software; you can redistribute it and/or modify it under 11 the terms of the GNU General Public License as published by the Free 12 Software Foundation; either version 3, or (at your option) any later 13 version. 14 15 GCC is distributed in the hope that it will be useful, but WITHOUT ANY 16 WARRANTY; without even the implied warranty of MERCHANTABILITY or 17 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 18 for more details. 19 20 Under Section 7 of GPL version 3, you are granted additional 21 permissions described in the GCC Runtime Library Exception, version 22 3.1, as published by the Free Software Foundation. 23 24 You should have received a copy of the GNU General Public License and 25 a copy of the GCC Runtime Library Exception along with this program; 26 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 27 <http://www.gnu.org/licenses/>. */ 28 29 #if defined(__riscv64) 30 #include "fp-bit.h" 31 32 extern DItype __fixdfdi (DFtype); 33 extern DItype __fixsfdi (SFtype); 34 extern USItype __fixunsdfsi (DFtype); 35 extern USItype __fixunssfsi (SFtype); 36 extern DFtype __floatdidf (DItype); 37 extern DFtype __floatundidf (UDItype); 38 extern SFtype __floatdisf (DItype); 39 extern SFtype __floatundisf (UDItype); 40 41 static DItype local_fixunssfdi (SFtype); 42 static DItype local_fixunsdfdi (DFtype); 43 44 DItype 45 __fixdfdi (DFtype a) 46 { 47 if (a < 0) 48 return - local_fixunsdfdi (-a); 49 return local_fixunsdfdi (a); 50 } 51 52 DItype 53 __fixsfdi (SFtype a) 54 { 55 if (a < 0) 56 return - local_fixunssfdi (-a); 57 return local_fixunssfdi (a); 58 } 59 60 USItype 61 __fixunsdfsi (DFtype a) 62 { 63 if (a >= - (DFtype) (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1)) 64 return (SItype) (a + (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1)) 65 - (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1); 66 return (SItype) a; 67 } 68 69 USItype 70 __fixunssfsi (SFtype a) 71 { 72 if (a >= - (SFtype) (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1)) 73 return (SItype) (a + (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1)) 74 - (- ((SItype)(((USItype)1 << ((4 * 8) - 1)) - 1)) - 1); 75 return (SItype) a; 76 } 77 78 DFtype 79 __floatdidf (DItype u) 80 { 81 DFtype d; 82 83 d = (SItype) (u >> (sizeof (SItype) * 8)); 84 d *= 2.0 * (((UDItype) 1) << ((sizeof (SItype) * 8) - 1)); 85 d += (USItype) (u & ((((UDItype) 1) << (sizeof (SItype) * 8)) - 1)); 86 87 return d; 88 } 89 90 DFtype 91 __floatundidf (UDItype u) 92 { 93 DFtype d; 94 95 d = (USItype) (u >> (sizeof (SItype) * 8)); 96 d *= 2.0 * (((UDItype) 1) << ((sizeof (SItype) * 8) - 1)); 97 d += (USItype) (u & ((((UDItype) 1) << (sizeof (SItype) * 8)) - 1)); 98 99 return d; 100 } 101 102 SFtype 103 __floatdisf (DItype u) 104 { 105 DFtype f; 106 107 if (53 < (sizeof (DItype) * 8) 108 && 53 > ((sizeof (DItype) * 8) - 53 + 24)) 109 { 110 if (! (- ((DItype) 1 << 53) < u 111 && u < ((DItype) 1 << 53))) 112 { 113 if ((UDItype) u & (((UDItype) 1 << ((sizeof (DItype) * 8) - 53)) - 1)) 114 { 115 u &= ~ (((UDItype) 1 << ((sizeof (DItype) * 8) - 53)) - 1); 116 u |= ((UDItype) 1 << ((sizeof (DItype) * 8) - 53)); 117 } 118 } 119 } 120 f = (SItype) (u >> (sizeof (SItype) * 8)); 121 f *= 2.0 * (((UDItype) 1) << ((sizeof (SItype) * 8) - 1)); 122 f += (USItype) (u & ((((UDItype) 1) << (sizeof (SItype) * 8)) - 1)); 123 124 return (SFtype) f; 125 } 126 127 SFtype 128 __floatundisf (UDItype u) 129 { 130 DFtype f; 131 132 if (53 < (sizeof (DItype) * 8) 133 && 53 > ((sizeof (DItype) * 8) - 53 + 24)) 134 { 135 if (u >= ((UDItype) 1 << 53)) 136 { 137 if ((UDItype) u & (((UDItype) 1 << ((sizeof (DItype) * 8) - 53)) - 1)) 138 { 139 u &= ~ (((UDItype) 1 << ((sizeof (DItype) * 8) - 53)) - 1); 140 u |= ((UDItype) 1 << ((sizeof (DItype) * 8) - 53)); 141 } 142 } 143 } 144 f = (USItype) (u >> (sizeof (SItype) * 8)); 145 f *= 2.0 * (((UDItype) 1) << ((sizeof (SItype) * 8) - 1)); 146 f += (USItype) (u & ((((UDItype) 1) << (sizeof (SItype) * 8)) - 1)); 147 148 return (SFtype) f; 149 } 150 151 /* This version is needed to prevent recursion; fixunsdfdi in libgcc 152 calls fixdfdi, which in turn calls calls fixunsdfdi. */ 153 154 static DItype 155 local_fixunsdfdi (DFtype a) 156 { 157 USItype hi, lo; 158 159 hi = a / (((UDItype) 1) << (sizeof (SItype) * 8)); 160 lo = (a - ((DFtype) hi) * (((UDItype) 1) << (sizeof (SItype) * 8))); 161 return ((UDItype) hi << (sizeof (SItype) * 8)) | lo; 162 } 163 164 /* This version is needed to prevent recursion; fixunssfdi in libgcc 165 calls fixsfdi, which in turn calls calls fixunssfdi. */ 166 167 static DItype 168 local_fixunssfdi (SFtype original_a) 169 { 170 DFtype a = original_a; 171 USItype hi, lo; 172 173 hi = a / (((UDItype) 1) << (sizeof (SItype) * 8)); 174 lo = (a - ((DFtype) hi) * (((UDItype) 1) << (sizeof (SItype) * 8))); 175 return ((UDItype) hi << (sizeof (SItype) * 8)) | lo; 176 } 177 178 #endif 179