--- ray/src/common/calfunc.c 1991/07/16 14:26:18 1.8
+++ ray/src/common/calfunc.c 2003/02/22 02:07:21 2.8
@@ -1,25 +1,78 @@
-/* Copyright (c) 1991 Regents of the University of California */
-
#ifndef lint
-static char SCCSid[] = "$SunId$ LBL";
+static const char RCSid[] = "$Id: calfunc.c,v 2.8 2003/02/22 02:07:21 greg Exp $";
#endif
-
/*
* calfunc.c - routines for calcomp using functions.
*
- * The define BIGLIB pulls in a large number of the
- * available math routines.
- *
- * If VARIABLE is not defined, only library functions
+ * If VARIABLE is not set, only library functions
* can be accessed.
*
- * 4/2/86
+ * 2/19/03 Eliminated conditional compiles in favor of esupport extern.
*/
+/* ====================================================================
+ * The Radiance Software License, Version 1.0
+ *
+ * Copyright (c) 1990 - 2002 The Regents of the University of California,
+ * through Lawrence Berkeley National Laboratory. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * 3. The end-user documentation included with the redistribution,
+ * if any, must include the following acknowledgment:
+ * "This product includes Radiance software
+ * (http://radsite.lbl.gov/)
+ * developed by the Lawrence Berkeley National Laboratory
+ * (http://www.lbl.gov/)."
+ * Alternately, this acknowledgment may appear in the software itself,
+ * if and wherever such third-party acknowledgments normally appear.
+ *
+ * 4. The names "Radiance," "Lawrence Berkeley National Laboratory"
+ * and "The Regents of the University of California" must
+ * not be used to endorse or promote products derived from this
+ * software without prior written permission. For written
+ * permission, please contact radiance@radsite.lbl.gov.
+ *
+ * 5. Products derived from this software may not be called "Radiance",
+ * nor may "Radiance" appear in their name, without prior written
+ * permission of Lawrence Berkeley National Laboratory.
+ *
+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL Lawrence Berkeley National Laboratory OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
+ * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This software consists of voluntary contributions made by many
+ * individuals on behalf of Lawrence Berkeley National Laboratory. For more
+ * information on Lawrence Berkeley National Laboratory, please see
+ * .
+ */
+
#include
#include
+#include
+
#include "calcomp.h"
/* bits in argument flag (better be right!) */
@@ -38,18 +91,17 @@ static ACTIVATION *curact = NULL;
static double libfunc();
+#ifndef MAXLIB
#define MAXLIB 64 /* maximum number of library functions */
+#endif
static double l_if(), l_select(), l_rand();
static double l_floor(), l_ceil();
-#ifdef BIGLIB
static double l_sqrt();
static double l_sin(), l_cos(), l_tan();
static double l_asin(), l_acos(), l_atan(), l_atan2();
static double l_exp(), l_log(), l_log10();
-#endif
-#ifdef BIGLIB
/* functions must be listed alphabetically */
static LIBR library[MAXLIB] = {
{ "acos", 1, ':', l_acos },
@@ -72,49 +124,23 @@ static LIBR library[MAXLIB] = {
static int libsize = 16;
-#else
- /* functions must be listed alphabetically */
-static LIBR library[MAXLIB] = {
- { "ceil", 1, ':', l_ceil },
- { "floor", 1, ':', l_floor },
- { "if", 3, ':', l_if },
- { "rand", 1, ':', l_rand },
- { "select", 1, ':', l_select },
-};
-
-static int libsize = 5;
-
-#endif
-
-extern char *savestr(), *emalloc();
-
-extern LIBR *liblookup();
-
-extern VARDEF *argf();
-
-#ifdef VARIABLE
#define resolve(ep) ((ep)->type==VAR?(ep)->v.ln:argf((ep)->v.chan))
-#else
-#define resolve(ep) ((ep)->v.ln)
-#define varlookup(name) NULL
-#endif
int
fundefined(fname) /* return # of arguments for function */
char *fname;
{
- LIBR *lp;
+ register LIBR *lp;
register VARDEF *vp;
- if ((vp = varlookup(fname)) == NULL || vp->def == NULL
- || vp->def->v.kid->type != FUNC)
- if ((lp = liblookup(fname)) == NULL)
- return(0);
- else
- return(lp->nargs);
- else
+ if ((vp = varlookup(fname)) != NULL && vp->def != NULL
+ && vp->def->v.kid->type == FUNC)
return(nekids(vp->def->v.kid) - 1);
+ lp = vp != NULL ? vp->lib : liblookup(fname);
+ if (lp == NULL)
+ return(0);
+ return(lp->nargs);
}
@@ -149,15 +175,24 @@ double *a;
}
+void
funset(fname, nargs, assign, fptr) /* set a library function */
char *fname;
int nargs;
int assign;
double (*fptr)();
{
+ int oldlibsize = libsize;
+ char *cp;
register LIBR *lp;
-
- if ((lp = liblookup(fname)) == NULL) {
+ /* check for context */
+ for (cp = fname; *cp; cp++)
+ ;
+ if (cp == fname)
+ return;
+ if (cp[-1] == CNTXMARK)
+ *--cp = '\0';
+ if ((lp = liblookup(fname)) == NULL) { /* insert */
if (libsize >= MAXLIB) {
eputs("Too many library functons!\n");
quit(1);
@@ -172,10 +207,23 @@ double (*fptr)();
break;
libsize++;
}
- lp[0].fname = fname; /* must be static! */
- lp[0].nargs = nargs;
- lp[0].atyp = assign;
- lp[0].f = fptr;
+ if (fptr == NULL) { /* delete */
+ while (lp < &library[libsize-1]) {
+ lp[0].fname = lp[1].fname;
+ lp[0].nargs = lp[1].nargs;
+ lp[0].atyp = lp[1].atyp;
+ lp[0].f = lp[1].f;
+ lp++;
+ }
+ libsize--;
+ } else { /* or assign */
+ lp[0].fname = fname; /* string must be static! */
+ lp[0].nargs = nargs;
+ lp[0].atyp = assign;
+ lp[0].f = fptr;
+ }
+ if (libsize != oldlibsize)
+ libupdate(fname); /* relink library */
}
@@ -227,7 +275,6 @@ register int n;
}
-#ifdef VARIABLE
VARDEF *
argf(n) /* return function def for nth argument */
int n;
@@ -272,7 +319,6 @@ int n;
{
return(argf(n)->name);
}
-#endif
double
@@ -326,33 +372,6 @@ char *fname;
}
-#ifndef VARIABLE
-VARDEF *
-varinsert(vname) /* dummy variable insert */
-char *vname;
-{
- register VARDEF *vp;
-
- vp = (VARDEF *)emalloc(sizeof(VARDEF));
- vp->name = savestr(vname);
- vp->nlinks = 1;
- vp->def = NULL;
- vp->lib = NULL;
- vp->next = NULL;
- return(vp);
-}
-
-
-varfree(vp) /* free dummy variable */
-register VARDEF *vp;
-{
- freestr(vp->name);
- efree((char *)vp);
-}
-#endif
-
-
-
/*
* The following routines are for internal use:
*/
@@ -361,29 +380,30 @@ register VARDEF *vp;
static double
libfunc(fname, vp) /* execute library function */
char *fname;
-register VARDEF *vp;
+VARDEF *vp;
{
- VARDEF dumdef;
+ register LIBR *lp;
double d;
int lasterrno;
- if (vp == NULL) {
- vp = &dumdef;
- vp->lib = NULL;
- }
- if (((vp->lib == NULL || strcmp(fname, vp->lib->fname)) &&
- (vp->lib = liblookup(fname)) == NULL) ||
- vp->lib->f == NULL) {
+ if (vp != NULL)
+ lp = vp->lib;
+ else
+ lp = liblookup(fname);
+ if (lp == NULL) {
eputs(fname);
eputs(": undefined function\n");
quit(1);
}
lasterrno = errno;
errno = 0;
- d = (*vp->lib->f)(vp->lib->fname);
+ d = (*lp->f)(lp->fname);
#ifdef IEEE
- if (!finite(d))
- errno = EDOM;
+ if (errno == 0)
+ if (isnan(d))
+ errno = EDOM;
+ else if (isinf(d))
+ errno = ERANGE;
#endif
if (errno) {
wputs(fname);
@@ -435,7 +455,6 @@ l_select() /* return argument #(A1+1) */
static double
l_rand() /* random function between 0 and 1 */
{
- extern double floor();
double x;
x = argument(1);
@@ -449,8 +468,6 @@ l_rand() /* random function between 0 and 1 */
static double
l_floor() /* return largest integer not greater than arg1 */
{
- extern double floor();
-
return(floor(argument(1)));
}
@@ -458,18 +475,13 @@ l_floor() /* return largest integer not greater than
static double
l_ceil() /* return smallest integer not less than arg1 */
{
- extern double ceil();
-
return(ceil(argument(1)));
}
-#ifdef BIGLIB
static double
l_sqrt()
{
- extern double sqrt();
-
return(sqrt(argument(1)));
}
@@ -477,8 +489,6 @@ l_sqrt()
static double
l_sin()
{
- extern double sin();
-
return(sin(argument(1)));
}
@@ -486,8 +496,6 @@ l_sin()
static double
l_cos()
{
- extern double cos();
-
return(cos(argument(1)));
}
@@ -495,8 +503,6 @@ l_cos()
static double
l_tan()
{
- extern double tan();
-
return(tan(argument(1)));
}
@@ -504,8 +510,6 @@ l_tan()
static double
l_asin()
{
- extern double asin();
-
return(asin(argument(1)));
}
@@ -513,8 +517,6 @@ l_asin()
static double
l_acos()
{
- extern double acos();
-
return(acos(argument(1)));
}
@@ -522,8 +524,6 @@ l_acos()
static double
l_atan()
{
- extern double atan();
-
return(atan(argument(1)));
}
@@ -531,8 +531,6 @@ l_atan()
static double
l_atan2()
{
- extern double atan2();
-
return(atan2(argument(1), argument(2)));
}
@@ -540,8 +538,6 @@ l_atan2()
static double
l_exp()
{
- extern double exp();
-
return(exp(argument(1)));
}
@@ -549,8 +545,6 @@ l_exp()
static double
l_log()
{
- extern double log();
-
return(log(argument(1)));
}
@@ -558,8 +552,5 @@ l_log()
static double
l_log10()
{
- extern double log10();
-
return(log10(argument(1)));
}
-#endif