function.c

00001 /* File:      function.c
00002 ** Author(s): Jiyang Xu
00003 ** Contact:   xsb-contact@cs.sunysb.edu
00004 ** 
00005 ** Copyright (C) The Research Foundation of SUNY, 1986, 1993-1998
00006 ** 
00007 ** XSB is free software; you can redistribute it and/or modify it under the
00008 ** terms of the GNU Library General Public License as published by the Free
00009 ** Software Foundation; either version 2 of the License, or (at your option)
00010 ** any later version.
00011 ** 
00012 ** XSB is distributed in the hope that it will be useful, but WITHOUT ANY
00013 ** WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
00014 ** FOR A PARTICULAR PURPOSE.  See the GNU Library General Public License for
00015 ** more details.
00016 ** 
00017 ** You should have received a copy of the GNU Library General Public License
00018 ** along with XSB; if not, write to the Free Software Foundation,
00019 ** Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00020 **
00021 ** $Id: function.c,v 1.18 2005/08/03 20:09:16 dwarren Exp $
00022 ** 
00023 */
00024 
00025 
00026 #include "xsb_config.h"
00027 #include "xsb_debug.h"
00028 
00029 #include <math.h>
00030 
00031 #include "auxlry.h"
00032 #include "cell_xsb.h"
00033 #include "register.h"
00034 #include "memory_xsb.h"
00035 #include "deref.h"
00036 #include "heap_xsb.h"
00037 #include "binding.h"
00038 #include "context.h"
00039 
00040 #define FUN_PLUS   1
00041 #define FUN_MINUS  2
00042 #define FUN_TIMES  3
00043 #define FUN_DIVIDE 4
00044 #define FUN_AND    5
00045 #define FUN_OR     6
00046 #define FUN_sin    9
00047 #define FUN_cos   10
00048 #define FUN_tan   11
00049 
00050 #define FUN_float 13
00051 #define FUN_floor 14
00052 #define FUN_exp   15
00053 #define FUN_log   16
00054 #define FUN_log10 17
00055 #define FUN_sqrt  18
00056 #define FUN_asin  19
00057 #define FUN_acos  20
00058 #define FUN_atan  21
00059 #define FUN_abs  22
00060 #define FUN_truncate  23
00061 #define FUN_round  24
00062 #define FUN_ceiling  25
00063 #define FUN_max  26
00064 #define FUN_min  27
00065 
00066 /* --- returns 1 when succeeds, and returns 0 when there is an error -- */
00067 
00068 #define set_fvalue_from_value  \
00069     if (isinteger(value)) fvalue = (Float) int_val(value); \
00070     else if (isofloat(value)) fvalue = ofloat_val(value);   \
00071     else if (isboxedinteger(value)) fvalue = (Float) boxedint_val(value); \
00072     else return 0
00073 
00074 extern inline void bld_boxedfloat(CTXTdeclc CPtr, Float);
00075 
00076 int  unifunc_call(CTXTdeclc int funcnum, CPtr regaddr)
00077 {
00078   Cell value;
00079   Float fvalue; 
00080   prolog_int ivalue;
00081 
00082   value = cell(regaddr);
00083   XSB_Deref(value);
00084   switch (funcnum) {
00085   case FUN_float:
00086     set_fvalue_from_value;
00087     bld_boxedfloat(CTXTc regaddr, fvalue);
00088     break;
00089   case FUN_floor:
00090     set_fvalue_from_value;
00091     ivalue = (prolog_int) floor(fvalue);
00092     bld_oint(regaddr, ivalue);
00093     break;
00094   case FUN_PLUS:
00095   case FUN_MINUS:
00096   case FUN_TIMES:
00097   case FUN_DIVIDE:
00098   case FUN_AND:
00099   case FUN_OR:
00100     return 0;           /* should not come here */
00101   case FUN_sin:
00102       set_fvalue_from_value;
00103       fvalue = sin(fvalue);
00104       bld_boxedfloat(CTXTc regaddr, fvalue);
00105   break;
00106   case FUN_cos:
00107       set_fvalue_from_value;
00108       fvalue = cos(fvalue);
00109       bld_boxedfloat(CTXTc regaddr, fvalue);
00110   break;
00111   case FUN_tan:
00112       set_fvalue_from_value;
00113       fvalue = tan(fvalue);
00114       bld_boxedfloat(CTXTc regaddr, fvalue);
00115   break;
00116   case FUN_exp:
00117       set_fvalue_from_value;
00118       fvalue = exp(fvalue);
00119       bld_boxedfloat(CTXTc regaddr, fvalue);
00120       break;
00121   case FUN_log:
00122       set_fvalue_from_value;
00123       fvalue = log(fvalue);
00124   bld_boxedfloat(CTXTc regaddr, fvalue);
00125   break;
00126   case FUN_log10:
00127       set_fvalue_from_value;
00128       fvalue = log10(fvalue);
00129   bld_boxedfloat(CTXTc regaddr, fvalue);
00130   break;
00131   case FUN_sqrt:
00132       set_fvalue_from_value;
00133       fvalue = sqrt(fvalue);
00134   bld_boxedfloat(CTXTc regaddr, fvalue);
00135   break;
00136   case FUN_asin:
00137       set_fvalue_from_value;
00138       fvalue = asin(fvalue);
00139       bld_boxedfloat(CTXTc regaddr, fvalue);
00140   break;
00141   case FUN_acos:
00142     set_fvalue_from_value;
00143     fvalue = acos(fvalue);
00144     bld_boxedfloat(CTXTc regaddr, fvalue);
00145     break;
00146   case FUN_atan:
00147     set_fvalue_from_value;
00148     fvalue = atan(fvalue);
00149     bld_boxedfloat(CTXTc regaddr, fvalue);
00150     break;
00151   case FUN_abs:
00152     if (isinteger(value)) {
00153       ivalue = int_val(value);
00154       if (ivalue > 0) 
00155         bld_int(regaddr,ivalue);
00156       else bld_int(regaddr,-ivalue);
00157     } 
00158     else if (isboxedinteger(value)) {
00159       ivalue = boxedint_val(value);
00160       if (ivalue > 0) 
00161         {bld_oint(regaddr,ivalue)}
00162       else bld_oint(regaddr,-ivalue);
00163     } 
00164     else if (isofloat(value) ) {
00165       fvalue = ofloat_val(value);
00166       if (fvalue > 0)
00167       {
00168           bld_boxedfloat(CTXTc regaddr,fvalue);
00169       }
00170       else 
00171       {
00172           fvalue = -fvalue;
00173           bld_boxedfloat(CTXTc regaddr,fvalue);
00174       }
00175     } else return 0;
00176     break;
00177   case FUN_truncate:
00178     if (isinteger(value)) { 
00179       ivalue = int_val(value);
00180       bld_int(regaddr,ivalue);
00181     }
00182     else if (isboxedinteger(value)) { 
00183       ivalue = boxedint_val(value);
00184       bld_oint(regaddr,ivalue);
00185     }
00186     else if (isofloat(value)) {
00187       fvalue = ofloat_val(value);
00188       if (fvalue > 0) 
00189       {
00190           ivalue = (prolog_int) floor(fvalue);
00191           bld_oint(regaddr,ivalue);
00192       }
00193       else 
00194       {
00195           ivalue = (prolog_int) -floor(-fvalue);
00196           bld_oint(regaddr,ivalue);
00197       }
00198     } else return 0;
00199     break;
00200   case FUN_round:
00201     if (isinteger(value)) { 
00202       ivalue = int_val(value);
00203       bld_int(regaddr,ivalue);
00204     }
00205     else if (isboxedinteger(value)) { 
00206       ivalue = boxedint_val(value);
00207       bld_oint(regaddr,ivalue);
00208     }
00209     else if (isofloat(value)) {
00210       fvalue = ofloat_val(value);
00211       ivalue = (prolog_int) floor(fvalue+0.5);
00212       bld_oint(regaddr, ivalue);
00213     } else return 0;
00214     break;
00215   case FUN_ceiling:
00216     if (isinteger(value)) { 
00217       ivalue = int_val(value);
00218       bld_int(regaddr,ivalue);
00219     }
00220     else if (isboxedinteger(value)) { 
00221       ivalue = boxedint_val(value);
00222       bld_oint(regaddr,ivalue);
00223     }
00224     else if (isofloat(value)) {
00225       fvalue = ofloat_val(value);
00226       ivalue = (prolog_int) -floor(-fvalue);
00227       bld_oint(regaddr,ivalue);
00228     } else return 0;
00229     break;
00230   default:  return 0;
00231   }
00232   return 1;
00233 }

Generated on Wed Jul 26 13:30:40 2006 for XSB by  doxygen 1.4.5