Esempio n. 1
0
/*Filters the given float array to the low "keepSamples"
spectral components (low-pass filter).  If keepSamples
is small, the filter is strong (only lets the lowest
freqencies by)*/
void filter_lowPass(float *arr,int fftLen,int keepSamples)
{
	int i;
/*Init.*/
	complexFloat *fft=(complexFloat *)MALLOC(sizeof(complexFloat)*fftLen);
	cfft1d(fftLen,NULL,0);
/*Copy arr into fft buffer.*/
	for (i=0;i<fftLen;i++)
	{
		fft[i].real = arr[i];
		fft[i].imag = 0;
	}
	cfft1d(fftLen,fft,-1);/*Forward FFT.*/
/*Filter out high frequencies.*/
	for (i=1+keepSamples;i<fftLen-keepSamples;i++)
	{
		fft[i].real = 0;
		fft[i].imag = 0;
	}
	cfft1d(fftLen,fft,1);/*Reverse FFT.*/
/*Copy (smoothed) fft buffer back into arr.*/
	for (i=0;i<fftLen;i++)
		arr[i]=Cabs(fft[i]);
	FREE(fft);
}
Esempio n. 2
0
void cfft(int n, float ream[], double *comm, int *info)
{
    complex *xx, *com;
    com = (complex *) comm;
    xx = (complex *) ream;
    cfft1d(-1, n, xx, com, info);
}
Esempio n. 3
0
void fft_init(int n, float ream[], double *comm, int *info)
{
    complex *xx, *com;
    /* Allocate communication work array */
//  comm = (double *)malloc((5*n+100)*sizeof(double));
    com = (complex *) comm;
    xx = (complex *) ream;
    /* Initialize communication work array */
    cfft1d(0, n, xx, com, info);
}
Esempio n. 4
0
/*Return the average doppler centroid (in fractional PRF)
of inFile using fftLen lines starting at startLine*/
double fftEstDop(getRec *inFile,int startLine,int xStride,int fftLen)
{
	int x,y,i,wid=inFile->nSamples;
	float *power,peak;
	complexFloat *in,*fft;
/*Allocate arrays.*/
	in=(complexFloat *)MALLOC(sizeof(complexFloat)*fftLen*wid);
	fft=(complexFloat *)MALLOC(sizeof(complexFloat)*fftLen);
	power=(float *)MALLOC(sizeof(float)*fftLen);
/*Set power sum to zero.*/
	for (i=0;i<fftLen;i++)
		power[i]=0;
/*Read in fftLen lines of data.*/
	for (y=0;y<fftLen;y++)
		getSignalLine(inFile,startLine+y,&(in[y*wid]),0,wid);
/*FFT each column, add to power sum array.*/
	cfft1d(fftLen,NULL,0);
	for (x=0;x<wid;x+=xStride)
	{
		for (y=0;y<fftLen;y++)
			fft[y]=in[y*wid+x];
		cfft1d(fftLen,fft,-1);
		for (i=0;i<fftLen;i++)
			power[i] += fft[i].real*fft[i].real
                                    + fft[i].imag*fft[i].imag;
	}

/*Find peak of azimuth power array-- this is the center of the doppler.*/
	power[0]=0.0;/*Zero out DC component (misleading).*/
	filter_lowPass(power,fftLen,4);/*Do a low-pass on the power array.*/
	peak=findPeak(power,fftLen);

	if (!quietflag) printf("Peak at %f\n",peak);

	FREE(in);
	FREE(fft);
	FREE(power);
	return peak/fftLen;
}
Esempio n. 5
0
/*
  processPatch:
  Performs all processing necessary on the given patch.
  Expects a fully prepared patch.

  - read in & range compress the data (rciq).
  - fft the data along azimuth.
  - range migrate the data (rmpatch).
  - azimuth compress the data (acpatch).
  the data is returned in the patch's trans array.
*/
void processPatch(patch *p,const getRec *signalGetRec,const rangeRef *r,
          const satellite *s)
{
  int i;

  update_status("Range compressing");
  if (!quietflag) printf("   RANGE COMPRESSING CHANNELS...\n");
  elapse(0);
  rciq(p,signalGetRec,r);
  if (!quietflag) elapse(1);
  if (s->debugFlag & AZ_RAW_T) debugWritePatch(p,"az_raw_t");

  update_status("Starting azimuth compression");
  if (!quietflag) printf("   TRANSFORMING LINES...\n");
  elapse(0);
  cfft1d(p->n_az,NULL,0);
  for (i=0; i<p->n_range; i++) cfft1d(p->n_az,&p->trans[i*p->n_az],-1);
  if (!quietflag) elapse(1);
  if (s->debugFlag & AZ_RAW_F) debugWritePatch(p,"az_raw_f");
  if (!(s->debugFlag & NO_RCM))
    {
      update_status("Range cell migration");
      if (!quietflag) printf("   START RANGE MIGRATION CORRECTION...\n");
      elapse(0);
      rmpatch(p,s);
      if (!quietflag) elapse(1);
      if (s->debugFlag & AZ_MIG_F) debugWritePatch(p,"az_mig_f");
    }
  update_status("Finishing azimuth compression");
  if (!quietflag) printf("   INVERSE TRANSFORMING LINES...\n");
  elapse(0);
  acpatch(p,s);
  if (!quietflag) elapse(1);

  /*    if (!quietflag) printf("  Range-Doppler done...\n");*/
}
Esempio n. 6
0
void sgifftcall(fcomplex * indata, long nn, int isign)
{
   int expon;
   double fracpart;
   static complex *coeff[30];

   /* Determine the twoth power of the length of the data */

   fracpart = frexp((double) nn, &expon);
   expon--;

   /* If we are calling using an nn we haven't seen before */

   if (coeff[expon] == NULL) {

      /* Allocate coefficient array */

      coeff[expon] = cfft1di(nn, NULL);

   }
   /* Do the FFT */

   cfft1d(isign, nn, (complex *) indata, 1, coeff[expon]);
}
Esempio n. 7
0
int main(int argc,char **argv)
{
  int lines,samps;                   /* Number of image lines and samples     */
  int fftLen,start_line;             /* FFT length, & line to start processing at*/
  int x,y,i,k;                       /* Counters                              */
  int f_lo1,f_lo2,f_hi1,f_hi2;       /* Filter frequency indicies             */
  int chunk_size,chunk_int;          /* Size of current datablock, & temp value*/
  int last_chunk;                    /* Size of the last chunk                */
  int compensate_for_last_chunk=1;   /* If last chunk = 0 dont loop for last chunk*/
  char *inName, *parmName, *outName; /* Input filename                        */
  float filtStart[2], filtEnd[2];    /* Filter start and stop variables       */
  float df, stop;                    /* Delta and counter variables           */
  complexFloat *inBuf,*outBuf;       /* Input/Output Image Buffers            */
  complexFloat *fftBuf;              /* FFT Buffer for the image              */
  float *ampBuf,*phsBuf;             /* Amplitude and Phase Buffers           */
  float *time_vector,A,B,shift;      /* Time vector, & freq modulation shift vars*/
  float chunk_float;                 /* Temporary value                       */
  FILE *inF, *freqF, *outF1;         /* Input and Output file pointers        */
  float cur_time, f_s;               /* Current time to increment the time vector by */
  meta_parameters *inMeta, *outMeta; /* Meta info about the images            */

/* Usage is shown if the user doesn't give 3 arguements */
  if(argc!=4) { usage(argv[0]); }

  StartWatch();
  printf("Program cpx_filter\n");

/* Get the filename and filter start and end frequencies from the command line*/ 
  inName=argv[1];
  if(findExt(inName)==NULL)
          inName = appendExt(argv[1],".cpx");
  outName=argv[2];
  parmName=argv[3];

/* Get input metadata. Make sure data_type is complex */
  inMeta = meta_read(inName);
  if (inMeta->general->data_type < COMPLEX_BYTE) {
   switch (inMeta->general->data_type) {
     case ASF_BYTE:      inMeta->general->data_type=COMPLEX_BYTE;      break;
     case INTEGER16: inMeta->general->data_type=COMPLEX_INTEGER16; break;
     case INTEGER32: inMeta->general->data_type=COMPLEX_INTEGER32; break;
     case REAL32:    inMeta->general->data_type=COMPLEX_REAL32;    break;
     case REAL64:    inMeta->general->data_type=COMPLEX_REAL64;    break;
    }
    meta_write (inMeta, inName);
  }

/* Open the frequency parameter file and read the parameters */
  if((freqF=FOPEN(parmName,"r"))==NULL) {
    printf("Frequency Parameter File %s could not be Opened!\n",parmName);
    exit(EXIT_FAILURE);
  }
  fscanf(freqF,"%f\n",&f_s);
  fscanf(freqF,"%f\n",&shift);
  fscanf(freqF,"%f %f\n", &filtStart[0], &filtEnd[0]);
  fscanf(freqF,"%f %f\n", &filtStart[1], &filtEnd[1]);

  printf("\n");
  printf("Input file is %s\n",inName);
  printf("Output file is %s.cpx\n",outName);
  printf("Parameter file is %s\n",parmName);
  printf("Filtering from frequencies %.2f to %.2f Hz and %.2f to %.2f in Azimuth\n",filtStart[0],filtEnd[0],filtStart[1],filtEnd[1]);
  printf("The sampling frequency is %f Hz\n",f_s);
  printf("Shifting the spectrum by %.2f Hz\n",shift);

/* Get the number of lines and samples from the input meta file */
  lines = inMeta->general->line_count;
  samps = inMeta->general->sample_count;

  chunk_size  = BLOCK_SIZE;
  chunk_float = (float)lines/chunk_size;
  chunk_int   = lines/chunk_size;
  last_chunk  = (int)((chunk_float-(float)chunk_int) * (float)BLOCK_SIZE + 0.5);
  if( (2*TOSS_SIZE) > last_chunk)
    compensate_for_last_chunk=0;
  printf("Chunk Size is set to %d, the last chunk is %d lines\n",
         chunk_size, last_chunk);

/* Compute the FFT length based on the number of lines. Must be a power of 2 */
  i      = (log10(chunk_size)/log10(2)) + 1;
  fftLen = pow(2,i);
  printf("FFT Length is %d\n",fftLen);
  cfft1d(fftLen,NULL,0);

  printf("The Input Image has %d lines and %d samples\n",lines,samps);

/* Allocate the memory for all the buffers */
  inBuf  = (complexFloat *)MALLOC(sizeof(complexFloat)*samps*fftLen);
  outBuf = (complexFloat *)MALLOC(sizeof(complexFloat)*samps*fftLen);
  fftBuf = (complexFloat *)MALLOC(sizeof(complexFloat)*fftLen);
  ampBuf = (float *)MALLOC(sizeof(float)*fftLen);
  phsBuf = (float *)MALLOC(sizeof(float)*fftLen);
  time_vector = (float *)MALLOC(sizeof(float)*lines);

/* Open the Complex Image File */
  if((inF=FOPEN(inName,"rb"))==NULL) {        
    printf("Complex Image file %s could not be opened\n",inName);
    exit(EXIT_FAILURE);
  }

  strcat(outName,".cpx"); 
  if((outF1=FOPEN(outName,"wb"))==NULL) {
    printf("Unable to write output %s\n",outName);
    exit(EXIT_FAILURE);
  }

  outMeta = meta_copy(inMeta);
  outMeta->general->line_count = 
          chunk_int*(BLOCK_SIZE-2*TOSS_SIZE)+(last_chunk-2*TOSS_SIZE);
  outMeta->general->sample_count = samps; 
  meta_write(outMeta, outName);


/* Find the filter frequency index values */
  df   = f_s/fftLen;
  stop = 0;
  i    = 0;
  while(stop<filtStart[0]) {
    f_lo1 = i;
    stop  = df*i;
    i++;
  }

  stop = 0;
  i    = 0;
  while(stop<filtStart[1]) {
    f_lo2=i;
    stop=df*i;
    i++;
  }

  i    = fftLen;
  stop = df*i;  
  while(stop>filtEnd[0]) {
    f_hi1 = i;
    stop  = df*i;   
    i--;
  }

  i    = fftLen;
  stop = df*i;
  while(stop>filtEnd[1]) {
    f_hi2 = i;
    stop  = df*i;
    i--;
  }

/* Zero out all the arrays and begin processing data */
  cur_time = 0;
  for(i=0; i<fftLen; i++)
  {
    ampBuf[i] = 0;
    phsBuf[i] = 0;
  }

  for(k=0; k<chunk_int+compensate_for_last_chunk; k++)
  {
    printf("\nProcessing Chunk %d of %d\n",k,lines/chunk_size);

    start_line = (k==0) ? 0 : (k*chunk_size)-(2*TOSS_SIZE);

    if (k==chunk_int)
      chunk_size=last_chunk;

    cur_time=start_line*(1/f_s);

  /* Read in the data chunk & put in proper endian order */
    printf("Reading %d Lines Starting at Line %d\n",chunk_size,start_line);
    get_complexFloat_lines(inF, inMeta, start_line, chunk_size, inBuf);

  /* Process the each column */
    printf("Performing the FFT and Filtering Operations\n");
    for(x=0; x<samps; x++)
    {
      if(x%1000 == 0)  printf("Processing Column %d\n",x);

      for(y=0;y<fftLen;y++)
      {
        fftBuf[y].real = 0;
        fftBuf[y].imag = 0;
      }

      for(y=0;y<chunk_size;y++)
      {
        fftBuf[y].real = inBuf[y*samps+x].real;
        fftBuf[y].imag = inBuf[y*samps+x].imag;
      }

      cfft1d(fftLen,fftBuf,-1);

      for (i=0; i<fftLen; i++) 
      {
        ampBuf[i] = sqrt(fftBuf[i].real*fftBuf[i].real
                    + fftBuf[i].imag*fftBuf[i].imag);        

        if(fftBuf[i].imag!=0.0 || fftBuf[i].real!=0.0)
          phsBuf[i] = atan2(fftBuf[i].imag,fftBuf[i].real);
        else
          phsBuf[i] = 0;

        if(((i>f_lo1)&&(i<f_hi1)) || ((i>f_lo2) && (i<f_hi2)))
        {
          ampBuf[i] = 0;
          phsBuf[i] = 0;
        }

        fftBuf[i].real = ampBuf[i]*cos(phsBuf[i]);
        fftBuf[i].imag = ampBuf[i]*sin(phsBuf[i]);        
      }

      cfft1d(fftLen,fftBuf,1);

      for(i=0;i<chunk_size;i++)
      {        
        outBuf[i*samps+x].real = fftBuf[i].real;
        outBuf[i*samps+x].imag = fftBuf[i].imag;
      }        
    }
    printf("Finished the FFT and Filtering Operations\n");

  /* Perform the time-domain frequency shift */ 
    if(shift != 0.0)
    {
      for(i=0; i<chunk_size; i++)
        time_vector[i] = cur_time+(1/f_s)*i;

      printf("\nPerforming time-domain frequency shift of %.2f Hz\n",shift);
      for(y=0; y<chunk_size; y++)
      {
        for(x=0; x<samps; x++)
        {
          A = outBuf[y*samps+x].real;
          B = outBuf[y*samps+x].imag;
          outBuf[y*samps+x].real = A*cos(2*pi*shift*time_vector[y])
                                   - B*sin(2*pi*shift*time_vector[y]);
          outBuf[y*samps+x].imag = B*cos(2*pi*shift*time_vector[y])
                                   + A*sin(2*pi*shift*time_vector[y]);
        }
      }
    }

  /* Write out the data file in big endian format */
    printf("Writing the output lines %d to %d in file %s\n",
      start_line, start_line+chunk_size-TOSS_SIZE, outName);
    put_complexFloat_lines(outF1, outMeta, start_line,
      samps*(chunk_size-TOSS_SIZE), outBuf+(samps*TOSS_SIZE));
  }

  printf("\n");

  FCLOSE(outF1);
  StopWatch();
  return 0;
}
Esempio n. 8
0
int main(int argc,char **argv)
{
  int lines,samps,start_line;   /* Number of image lines and samples          */
  int x,y,ii;                   /* Counters and the filter frequency indicies */
  char *inName, *outName;       /* Input filename                             */
  char metaName[256];           /* Name of meta file                          */
  complexFloat *inBuf;          /* Input/Output Image Buffers                 */
  complexFloat *fftBuf;         /* FFT Buffer for the image                   */
  float *ampBuf,*phsBuf;        /* Amplitude and Phase Buffers                */
  float df, freq[FFT_LEN], f_s; /* Frequency Vector                           */
  FILE *inF,*outF1;             /* Input and Output file pointers             */
  meta_parameters *meta;        /* Meta-file data pointer                     */

/* Usage is shown if the user doesn't give correct number of arguments */
  if(argc!=4) { usage(argv[0]); }

  StartWatch();

/* Get the filename and filter start and end frequencies from the command line */ 
  inName  = argv[1];
  outName = argv[2];
  start_line = atoi(argv[3]);
  create_name(metaName, inName, ".meta");

/* Get the PRF and number of samples from the meta-file */
  meta = meta_read(metaName);
  lines = FFT_LEN;
  samps = meta->general->sample_count;
  f_s   = 1/(meta->sar->azimuth_time_per_pixel);
  printf("Sampling Frequency is %f\n",f_s);

/* Compute the FFT length based on the number of lines. Must be a power of 2 */
  printf("FFT Length is %d\n",FFT_LEN);
  cfft1d(FFT_LEN,NULL,0);

/* Allocate the memory for all the buffers */
  inBuf  = (complexFloat *)MALLOC(sizeof(complexFloat)*samps*FFT_LEN);
  fftBuf = (complexFloat *)MALLOC(sizeof(complexFloat)*FFT_LEN);
  ampBuf = (float *)MALLOC(sizeof(float)*FFT_LEN);
  phsBuf = (float *)MALLOC(sizeof(float)*FFT_LEN);

  df = f_s/FFT_LEN;
  for(ii=0; ii<FFT_LEN; ii++)   freq[ii] = df*ii;

/* Open the Complex Image File */
  if((inF=FOPEN(inName,"rb"))==NULL) {	
    printf("Complex Image file %s could not be opened\n",inName);
    exit(EXIT_FAILURE);
  }

/* Zero out all the arrays and begin processing data */
  for(ii=0; ii<FFT_LEN; ii++) {
    ampBuf[ii]=0;
    phsBuf[ii]=0;
  }

/* Read in the data chunk */
  printf("Reading Data Starting at Line %d\n",start_line);
  get_complexFloat_lines(inF, meta, start_line, FFT_LEN, inBuf);

/* Process the each column, take the average at the end */
  printf("Performing the FFT\n");
  for(x=0; x<samps; x++) {
    if(x%500 == 0)  printf("Processing Column %d\n",x);

    for(y=0; y<FFT_LEN; y++) {
      fftBuf[y].real=0;
      fftBuf[y].imag=0;
    }

    for(y=0; y<lines; y++) {
      fftBuf[y].real=inBuf[y*samps+x].real;
      fftBuf[y].imag=inBuf[y*samps+x].imag;
    }

    cfft1d(FFT_LEN,fftBuf,-1);

    for (ii=0; ii<FFT_LEN; ii++) {
      ampBuf[ii] += sqrt(fftBuf[ii].real*fftBuf[ii].real
                         + fftBuf[ii].imag*fftBuf[ii].imag);	
      if(fftBuf[ii].imag!=0.0 || fftBuf[ii].real!=0.0)
        phsBuf[ii] += atan2(fftBuf[ii].imag, fftBuf[ii].real);
    }
  }
  printf("Finished the FFT\n");

/* Open and write output file */
  strcat(outName,".spectra"); 
  if((outF1=FOPEN(outName,"w"))==NULL) {
    printf("Unable to write output %s\n",outName);
    exit(EXIT_FAILURE);
  }
  for (ii=0; ii<FFT_LEN; ii++) {
    ampBuf[ii] /= samps;
    phsBuf[ii] /= samps;
    fprintf(outF1,"%f %f %f\n",freq[ii],ampBuf[ii],phsBuf[ii]);
  }

/* Close up & leave */
  meta_free(meta);
  FCLOSE(outF1);
  StopWatch();
  return 0;
}
Esempio n. 9
0
/*******
amp_corr:
    Given two patches, p1 containing the echos from
ahead of beam center, p2 containing echos from behind beam
center; performs an amplitude cross-correlation in range
and returns the range offset, in pixels, between
these two images.
*/
double amp_corr(patch *p1,patch *p2,file *f)
{
    int clip=20;/*Remove this from the far-range end of the images*/
    int overlap=30;/*Overlap is the maximum shift we ever expect.*/
    FILE *fout;
    int x,y;
    int fftLen=smallestPow2(p1->n_range);
    float scale=1.0/fftLen;
    complexFloat *amp1,*amp2;
    float *corr;
        double ret;
    amp1=(complexFloat *)MALLOC(sizeof(complexFloat)*fftLen);
    amp2=(complexFloat *)MALLOC(sizeof(complexFloat)*fftLen);
    corr=(float *)MALLOC(sizeof(float)*(fftLen+overlap));
    if (!quietflag) printf("   Performing amplitude correlation.\n");
    for (x=0;x<fftLen+overlap;x++)
        corr[x]=0.0;
    cfft1d(fftLen,NULL,0);
    p1->n_range-=clip;
    p2->n_range-=clip;
    for (y=f->firstOutputLine;y<f->firstOutputLine+f->n_az_valid;y++)
    {
        for (x=0;x<overlap;x++)
        {
            amp1[x]=Czero();
            amp2[x].r=Cabs(p2->trans[x*p2->n_az+y])*scale;
            amp2[x].i=0.0;
        }
        for (;x<p1->n_range-overlap;x++)
        {
            amp1[x].r=Cabs(p1->trans[x*p1->n_az+y])*scale;
            amp1[x].i=0.0;
            amp2[x].r=Cabs(p2->trans[x*p2->n_az+y])*scale;
            amp2[x].i=0.0;
        }
        for (;x<p1->n_range;x++)
        {
            amp1[x]=Czero();
            amp2[x].r=Cabs(p2->trans[x*p2->n_az+y])*scale;
            amp2[x].i=0.0;
        }
        for (;x<fftLen;x++)
            amp1[x]=amp2[x]=Czero();
        cfft1d(fftLen,amp1,-1);
        cfft1d(fftLen,amp2,-1);
        for (x=0;x<fftLen;x++)
            amp2[x]=Cmul(amp2[x],Cconj(amp1[x]));
        cfft1d(fftLen,amp2,1);
        for (x=0;x<fftLen;x++)
            corr[x]+=Cabs(amp2[x]);
    }
    fout=FOPEN(f->out_cpx,"w");
    for (x=-overlap;x<overlap;x++)
    {
        corr[x+fftLen]=corr[(x+fftLen)%fftLen];
        if (corr[x+fftLen]<10000000000000000000000.0)
        /*Is a good value-- print it out*/
            fprintf(fout,"%d %f\n",x,corr[x+fftLen]);
        else/*Must be an infinity or NaN*/
        {
            fprintf(stderr, "   WARNING!! Found infinity at offset %d!\n",x);
            if (logflag) {
              sprintf(logbuf,"   WARNING!! Found infinity at offset %d!\n",x);
              printLog(logbuf);
            }
            corr[x+fftLen]=0.0;
        }
    }
    FCLOSE(fout);
        FREE(amp1);
        FREE(amp2);
    ret = dop_findPeak(corr,fftLen-overlap,2*overlap)-fftLen;
        FREE(corr);
        return ret;
}