#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include "./swapfloat.c"
#include "./gethead.c"
#include "./qcksort.c"
#include "./getmedf2.c"
#include "./edithead.c"

/*
 badfillw.c 
 gcc -O2 -lm -o badfillw badfillw.c
*/

int main (int argc, char**argv)
{
 
  FILE   *fp;
  float  *data1,*data2,*data4,*mbox;
  float  med,stdev,med3,rms;
  float  lthresh;
  int    xynum,xynumw,i,j,k,datanum,iter;
  int    ix,iy,kx,ky,xbound,ybound;
  int    xsize=1024,ysize=1024;
  int    xsizew=1080,ysizew=1080;
  int    hfact,headsize;
  int    headunit=2880;
  char   fname[50],fname2[50];
  char   *header;

  if (argc < 2){
    fprintf(stderr, "usage : badfillw framename.fits out.fits\n");
    return 0;
  }

  sprintf(fname,"%s",argv[1]);
  sprintf(fname2,"%s",argv[2]);

  /*  size of header   */
  hfact = gethead(fname);
  headsize = hfact*headunit;

  xynum=xsize*ysize;
  xynumw=xsizew*ysizew;
  datanum = xynumw;  /* this is the case, when xynumw = 1080*1080 2013.4.30 */
  /*
  datanum=((int)(xynumw*sizeof(float)/2880)+1)*2880/sizeof(float);
  */

  data1=(float*)malloc(xynum*sizeof(float));
  data2=(float*)malloc(datanum*sizeof(float));
  header=(char*)malloc(headsize*sizeof(char));
  fp=fopen(fname,"rb");
  fread(header,sizeof(char),headsize,fp);
  fread(data1,sizeof(float),xynum,fp);
  fclose(fp);

  j=0;
  data4=(float*)malloc(xynum*sizeof(float));
  for(i=0; i<xynum; i++){
    swapfloat(&data1[i]);
    if (i%4==0){
      data4[j]=data1[i];
      j++;
    }
  }

  getmedf2(data4, j, &med, &stdev, -1000, 15000);
  lthresh=med-10*stdev;

  printf("%.1f %.1f\n", med, stdev);

  for(j=0; j<xynumw; j++){
    data2[j] = -9999;
  }

  for (iter=0; iter<3; iter++){
    for(i=0; i<xynum; i++){
      ix=i%xsize-1;
      iy=i/xsize-1;
      j = ix + 31 + xsizew * (iy + 31);
      if(data1[i]<lthresh){
	mbox=(float*)malloc(9*sizeof(float));    
	k=0;
	for(ky=0; ky<3; ky++){
	  for(kx=0; kx<3; kx++){
	    if(ix+kx>=0 && ix+kx<xsize && iy+ky>=0 && iy+ky<ysize){
	      mbox[k]=data1[ix+kx+(iy+ky)*xsize];
	    } else {
	      if(ix+kx<0) {
		xbound=0;
	      } else if(ix+kx>=xsize) {
		xbound=xsize-1;
	      } else {
		xbound=ix+kx;
	      }
	      
	      if(iy+ky<0) {
		ybound=0;
	      } else if(iy+ky>=ysize) {
		ybound=ysize-1;
	      } else {
		ybound=iy+ky;
	      }

	      mbox[k]=data1[xbound+ybound*xsize];
	    }
	    k++;
	  }
	}
	getmedf2(mbox, 9, &med3, &rms, lthresh, 15000);
	free(mbox);
	data2[j]=med3;
      } else {
	data2[j]=data1[i];
      }
      
    }

    for(i=0; i<xynum; i++){
      ix=i%xsize-1;
      iy=i/xsize-1;
      j = ix + 31 + xsizew * (iy + 31);
      data1[i]=data2[j];
    }
  }

  for(i=0; i<datanum; i++){
    swapfloat(&data2[i]);
  }

  edithead(header, xsizew, ysizew);

  if(NULL==(fp=fopen(fname2,"wb"))){
    printf("\n [%s] can not be opened \n", fname2);
    exit(1);
  }
  fwrite(header,sizeof(char),headsize,fp);
  fwrite(data2,sizeof(float),datanum,fp);
  fclose(fp);

  free(data1);
  free(data2);
  free(data4);
  free(header);

  return 0;

}

