Subversion Repositories HelenOS-historic

Rev

Rev 563 | Rev 652 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1.  
  2. /*
  3.  * Copyright (C) 2005 Josef Cejka
  4.  * All rights reserved.
  5.  *
  6.  * Redistribution and use in source and binary forms, with or without
  7.  * modification, are permitted provided that the following conditions
  8.  * are met:
  9.  *
  10.  * - Redistributions of source code must retain the above copyright
  11.  *   notice, this list of conditions and the following disclaimer.
  12.  * - Redistributions in binary form must reproduce the above copyright
  13.  *   notice, this list of conditions and the following disclaimer in the
  14.  *   documentation and/or other materials provided with the distribution.
  15.  * - The name of the author may not be used to endorse or promote products
  16.  *   derived from this software without specific prior written permission.
  17.  *
  18.  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  19.  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  20.  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
  21.  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
  22.  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  23.  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  24.  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  25.  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  26.  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  27.  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  28.  */
  29.  
  30. #include<softfloat.h>
  31.  
  32. float32 addFloat32(float32 a, float32 b);
  33. float32 subFloat32(float32 a, float32 b);
  34. inline int isFloat32NaN(float32 f);
  35. inline int isFloat32SigNaN(float32 f);
  36.  
  37. float __addsf3(float a, float b)
  38. {
  39.     float32 fa, fb;
  40.     fa.f=a;
  41.     fb.f=b;
  42.     if (fa.parts.sign!=fb.parts.sign) return subFloat32(fa,fb).f;
  43.     return addFloat32(fa,fb).f;
  44. };
  45.  
  46. float __subsf3(float a, float b)
  47. {
  48.     float32 fa, fb;
  49.     fa.f=a;
  50.     fb.f=b;
  51.     if (fa.parts.sign!=fb.parts.sign) return addFloat32(fa,fb).f;
  52.     return subFloat32(fa,fb).f;
  53. };
  54.  
  55. float __negsf2(float a)
  56. {
  57.     float32 fa;
  58.     fa.f=a;
  59.     fa.parts.sign=!fa.parts.sign;
  60.     return fa.f;
  61. };
  62.  
  63. double __negdf2(double a)
  64. {
  65.     float64 fa;
  66.     fa.d=a;
  67.     fa.parts.sign=!fa.parts.sign;
  68.     return fa.d;
  69. };
  70.  
  71. /** Add two Float32 numbers with same signs
  72.  */
  73. float32 addFloat32(float32 a, float32 b)
  74. {
  75.     int expdiff;
  76.     __u32 exp1,exp2,mant1,mant2;
  77.    
  78.     expdiff=a.parts.exp - b.parts.exp;
  79.     if (expdiff<0) {
  80.         if (isFloat32NaN(b)) {
  81.             //TODO: fix SigNaN
  82.             if (isFloat32SigNaN(b)) {
  83.             };
  84.             return b;
  85.         };
  86.        
  87.         if (b.parts.exp==0xFF) {
  88.             return b;
  89.         }
  90.        
  91.         mant1=b.parts.mantisa;
  92.         exp1=b.parts.exp;
  93.         mant2=a.parts.mantisa;
  94.         exp2=a.parts.exp;
  95.         expdiff*=-1;
  96.     } else {
  97.         if (isFloat32NaN(a)) {
  98.             //TODO: fix SigNaN
  99.             if ((isFloat32SigNaN(a))||(isFloat32SigNaN(b))) {
  100.             };
  101.             return a;
  102.         };
  103.        
  104.         if (a.parts.exp==0xFF) {
  105.             return a;
  106.         }
  107.        
  108.         mant1=a.parts.mantisa;
  109.         exp1=a.parts.exp;
  110.         mant2=b.parts.mantisa;
  111.         exp2=b.parts.exp;
  112.     };
  113.    
  114.     if (exp1==0) {
  115.         //both are denormalized
  116.         mant1+=mant2;
  117.         if (mant1&0xF00000) {
  118.             a.parts.exp=1;
  119.         };
  120.         a.parts.mantisa=mant1;
  121.         return a;
  122.     };
  123.    
  124.     // create some space for rounding
  125.     mant1<<=6;
  126.     mant2<<=6;
  127.    
  128.     mant1|=0x20000000; //add hidden bit
  129.    
  130.    
  131.     if (exp2==0) {
  132.         --expdiff; 
  133.     } else {
  134.         mant2|=0x20000000; //hidden bit
  135.     };
  136.    
  137.     if (expdiff>24) {
  138.          goto done;
  139.          };
  140.    
  141.     mant2>>=expdiff;
  142.     mant1+=mant2;
  143. done:
  144.     if (mant1&0x40000000) {
  145.         ++exp1;
  146.         mant1>>=1;
  147.     };
  148.    
  149.     //rounding - if first bit after mantisa is set then round up
  150.     mant1+=0x20;
  151.    
  152.     a.parts.exp=exp1;
  153.     a.parts.mantisa=mant1>>6;
  154.     return a;
  155. };
  156.  
  157. /** Substract two float32 numbers with same signs
  158.  */
  159. float32 subFloat32(float32 a, float32 b)
  160. {
  161.    
  162.    
  163. };
  164.  
  165. inline int isFloat32NaN(float32 f)
  166. {   /* NaN : exp = 0xff and nonzero mantisa */
  167.     return ((f.parts.exp==0xFF)&&(f.parts.mantisa));
  168. };
  169.  
  170. inline int isFloat32SigNaN(float32 f)
  171. {   /* SigNaN : exp = 0xff mantisa = 1xxxxx..x (binary), where at least one x is nonzero */
  172.     return ((f.parts.exp==0xFF)&&(f.parts.mantisa>0x400000));
  173. };
  174.  
  175.