/* common.h,v 1.4 1995/08/17 23:23:09 explorer Exp */

/*
 * Copyright (C) 1989, 1991, Craig E. Kolb
 * All rights reserved.
 *
 * This software may be freely copied, modified, and redistributed
 * provided that this copyright notice is preserved on all copies.
 *
 * You may not distribute this software, in whole or in part, as part of
 * any commercial product without the express consent of the authors.
 *
 * There is no warranty or other guarantee of fitness of this software
 * for any purpose.  It is provided solely "as is".
 *
 */

#ifndef COMMON_H 
#define COMMON_H

#include <stdio.h>
#include <math.h>

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif

#include <errno.h>

#ifdef STDC_HEADERS
#include <stdlib.h>
#include <string.h>
#else
#ifndef HAVE_STRCHR
#define strchr index
#define strrchr rindex
#endif
char *strchr(), *strrchr();
#ifdef HAVE_MEMCPY
#define memcpy(d, s, n) bcopy((s), (d), (n))
#define memmove(d, s, n) bcopy((s), (d), (n))
#endif
#endif

/*
 * If these is missing, put in a prototype for the replacment we'll
 * be using.
 */
#ifndef HAVE_STRERROR
char *strerror(int errornum);
#endif
#ifndef HAVE_STRDUP
char *strdup(char *s);
#endif

/*
 * Check to see if parallel processing support using TCP sockets is to be
 * compiled in.
 */
#ifdef HAVE_NETINET_IN_H
#define NSPARALLEL 1  /* Yep, we will try parallel processing */
#endif

typedef double Float;

typedef unsigned char uint8;
typedef unsigned short uint16;
#if SIZEOF_LONG == 4
typedef unsigned long uint32;
#else
#if SIZEOF_INT == 4
typedef unsigned int uint32;
#else
#error Error, cannot discover size of uint32!
#endif
#endif

/*
 * This is a hack -- better checking for void should be put here!
 * (just because the 4 machine types I tried this code on didn't
 * have a problem is no excuse :)
 */
#if 1
typedef void * voidstar;
typedef void const * voidconststar;
#else
typedef char * voidstar;
typedef char const * voidconststar;
#endif

#ifndef TRUE
#define TRUE		1
#endif

#ifndef FALSE
#define FALSE		0
#endif

/*
 * Various useful constants and macros.
 */

/*
 * Minimum vector length & fp value.
 * Modify depending upon Float typedef.
 */
#define EPSILON		(Float)0.00001

#ifndef PI
#define	PI		3.14159265358979323846
#endif
#define TWOPI		(2. * PI)
#define INV_TWOPI	(1. / TWOPI)
#define deg2rad(x)	(Float)(x * PI/180.)
#define LNHALF		(-.69314718)

#ifndef NULL
#define NULL 0
#endif

/*
 * Macro for prototypes of functions.
 */
#ifdef _PROTO
#undef _PROTO
#endif

#ifdef __STDC__
#define _PROTO(x) x
#else
#define _PROTO(x) ()
#endif

#define UNSET		-1

/*
 * Some systems, such as the RS6000, have fast fabs already defined.
 */
#ifndef fabs
extern Float RSabstmp;
#define fabs(x) 		((RSabstmp=x) < 0 ? -RSabstmp : RSabstmp)
#endif

#include "expr.h"
#include "vector.h"
#include "ray.h"
#include "color.h"
#include "transform.h"
#include "error.h"

#ifdef MULTIMAX
/*
 * On the multimax, allocate large pieces of memory as shared memory.
 */
extern voidstar share_malloc();
extern voidstar share_calloc();
#else
/*
 * Otherwise, malloc is malloc, etc.
 */
#define share_malloc(x)		Malloc(x)
#define share_calloc(x,y)	Calloc(x,y)
#endif

/*
 * Close enough for us.
 */
#define equal(a, b)		(fabs((a) - (b)) < EPSILON)
/*
 * Maximum/Minimum functions
 */
#define max(a, b)		((a) > (b) ? (a) : (b))
#define min(a, b)		((a) < (b) ? (a) : (b))
  
/* String comparison with more intuitive interface */
#ifndef	streq
#define	streq(a,b)	(strcmp((a), (b)) == 0)
#define	streql(a,b)	(strncmp((a), (b), strlen(b)) == 0)
#endif

extern voidstar Malloc _PROTO((size_t));
extern voidstar Calloc _PROTO((size_t, size_t));
extern char *strsave _PROTO((char *));
extern void PrintMemoryStats _PROTO((FILE *));

/*
 * in random.c
 * A spiffy (and hopefully correct) random number generator
 */
Float nrand _PROTO((void));
void seednrand _PROTO((uint32));

/*
 * in libobj/roots.c
 * this should go elsewhere, but where?
 */
int FindRoot _PROTO((Float *, int, Float, Float, Float *, int));

#endif /* COMMON_H */
