#define f_amr_begin F77NAME(amr_begin_,amr_begin,AMR_BEGIN)
#define f_amr_end F77NAME(amr_end_,amr_end,AMR_END)
#define f_amr_settype F77NAME(amr_settype_,amr_settype,AMR_SETTYPE)
#define f_amr_settopparms F77NAME(amr_settopparams_,amr_settopparams,AMR_SETTOPPARAMS)
#define f_amr_setrefine F77NAME(amr_setrefine_,amr_setrefine,AMR_SETREFINE);
#define f_amr_setlevrefine F77NAME(amr_setlevrefine_,amr_setlevrefine,AMR_SETLEVREFINE)
#define f_amr_setdims F77NAME(amr_setdims_,amr_setdims,AMR_SETDIMS)
#define f_amr_setlevel F77NAME(amr_setlevel_,amr_setlevel,AMR_SETLEVEL)
#define f_amr_settime F77NAME(amr_settime_,amr_settime,AMR_SETTIME)
#define f_amr_incrtime F77NAME(amr_incrtime_,amr_incrtime,AMR_INCRTIME)
#define f_amr_write F77NAME(amr_write_,amr_write,AMR_WRITE)

extern "C" {
#include "AMRwriter.h" 
Long8 f_amr_begin (Long8 *descriptor);
void f_amr_end (Long8 *afile);
void f_amr_settype (Long8 *afile,int *numbertype);
void f_amr_settopparms (Long8 *afile,int *rank,double *origin,
				   double *delta, double *timestep);
void f_amr_setrefine (Long8 *afile,int *maxdepth,int veclen,
		      int *timerefinement,
		      int *spatialrefinement,int *gridplacementrefinement);
void f_amr_setlevrefine (Long8 *afile,int *level,int *veclen,
			 int *timerefinement,
			 int *spatialrefinement,int *gridplacementrefinement);
void f_amr_setlevel (Long8 *afile,int *level);
void f_amr_settime (Long8 *afile,int *timestep);
void f_amr_incrtime (Long8 *afile);
void f_amr_write (Long8 *afile,int *origin,int *dims,void *data);
}


//===========F77/F90 Interface==================================
// should have an RTTI interface and inherit everything from
// IOobject which contains the RTTI isOfType() information.
// isOfType() should propagate recursively to determin type info
// match.  must grab typeID from floating point pool.  And then
// we need a static initializer for everything.

// How does performer/inventor do this?

Long8 *f_amr_beginFile(Long8 *descriptor){
  IObase *io = (IObase*)descriptor;
  return (AMRFile)(new AMRwriter(*io));
}

int f_amr_endFile(Long8 *afile){
  AMRwriter *w = (AMRwriter*)afile;
  delete w;
  return 1;
}

int f_amr_settype(Long8 *afile,int *numbertype){
  AMRwriter *w = (AMRwriter*)afile;
  w->setType(IObase::Int2DataType(*numbertype));
  return 1;
}

int f_amr_settopparams(Long8 *afile,int *rank,double *origin,
			      double *delta, double *timestep){
  AMRwriter *w = (AMRwriter*)afile;
  w->setToplevelParameters(*rank,origin,delta,timestep);
  return 1;
}

int f_amr_setlevrefine(Long8 *afile,int *maxdepth,int *veclen,
			   int *timerefinement,
			   int *spatialrefinement,
			   int *gridplacementrefinement){
  AMRwriter *w = (AMRwriter*)afile;
  if(*veclen==1)
    w->setRefinement(*maxdepth,*timerefinement,
			  *spatialrefinement,*gridplacementrefinement);
  else
    w->setRefinement(*maxdepth,*timerefinement,
			  spatialrefinement,gridplacementrefinement);
  return 1;
}

int f_amr_setlevrefine(Long8 *afile,int *level,int *veclen,
			   int *timerefinement,
			   int *spatialrefinement,
			   int *gridplacementrefinement){
  AMRwriter *w = (AMRwriter*)afile;
  if(*veclen==1)
    w->setLevelRefinement(*level,*timerefinement,
			  *spatialrefinement,*gridplacementrefinement);
  else
    w->setLevelRefinement(*level,*timerefinement,
			  spatialrefinement,gridplacementrefinement);
  return 1;
}

void f_amr_setlevel (Long8 *afile,int *level){
  AMRwriter *w = (AMRwriter*)afile;
  w->setLevel(*level);
  return 1;
}

void f_amr_settime (Long8 *afile,int *timestep){
  AMRwriter *w = (AMRwriter*)afile;
  w->setTime(*timestep);
  return 1;
}

void f_amr_incrttime(Long8 *afile){
  AMRwriter *w = (AMRwriter*)afile;
  w->incrementTime();
  return 1;
}

int f_amr_write(Long8 *afile,int *origin, int *dims, void *data){
  AMRwriter *w = (AMRwriter*)afile;
  w->write(origin,dims,data);
  return 1;
}