Example #1
0
/*{{{  recode(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
recode(transform_info_ptr tinfo) {
 struct recode_storage *local_arg=(struct recode_storage *)tinfo->methods->local_storage;
 transform_info_ptr const tinfoptr=tinfo;
 array myarray;

  int itempart;
  int shift, nrofshifts=1;
  DATATYPE *save_tsdata;

  tinfo_array(tinfoptr, &myarray);	/* The channels are the vectors */
  save_tsdata=myarray.start;

  if (tinfoptr->data_type==FREQ_DATA) {
   nrofshifts=tinfoptr->nrofshifts;
  }
  for (shift=0; shift<nrofshifts; shift++) {
   myarray.start=save_tsdata+shift*tinfo->nroffreq*tinfo->nr_of_channels*tinfo->itemsize;
   array_setreadwrite(&myarray);
   for (itempart=local_arg->fromitem; itempart<=local_arg->toitem; itempart++) {
    array_use_item(&myarray, itempart);
    do {
     if (local_arg->have_channel_list && !is_in_channellist(myarray.current_vector+1, local_arg->channel_list)) {
      array_nextvector(&myarray);
      continue;
     }
     do {
      DATATYPE hold=READ_ELEMENT(&myarray);
      struct blockdef *inblocks=local_arg->blockdefs;
      while (inblocks!=NULL) {
       if (isnan(inblocks->fromstart) && isnan(hold)) {
	/* Recode NaN values */
	hold=inblocks->tostart;
       } else
       if (hold>=inblocks->fromstart && hold<=inblocks->fromend) {
	if (inblocks->fromend==inblocks->fromstart || inblocks->toend==inblocks->tostart) {
	 hold=inblocks->tostart;
	} else {
	 hold=((hold-inblocks->fromstart)/(inblocks->fromend-inblocks->fromstart))*(inblocks->toend-inblocks->tostart)+inblocks->tostart;
	}
	break;
       }
       if (inblocks->last_block) break;
       inblocks++;
      }
      array_write(&myarray, hold);
     } while (myarray.message==ARRAY_CONTINUE);
    } while (myarray.message==ARRAY_ENDOFVECTOR);
   }
  }

 return tinfo->tsdata;
}
Example #2
0
/*{{{  export_point(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
export_point(transform_info_ptr tinfo) {
 struct export_point_info *exp_info=(struct export_point_info *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 array_dump_format format=(args[ARGS_MATLAB].is_set ? ARRAY_MATLAB : ARRAY_ASCII);
 int channel, itempart, i;
 double *channelpos;
 array myarray, newarray;

 if (exp_info->pointno<0 || exp_info->pointno>=tinfo->nr_of_points) {
  ERREXIT1(tinfo->emethods, "export_point: Point number %d is out of range.\n", MSGPARM(exp_info->pointno));
 }
 TRACEMS2(tinfo->emethods, 1, "export_point: Exporting point number %d to file %s\n", MSGPARM(exp_info->pointno), MSGPARM(args[ARGS_OFILE].arg.s));
 if (args[ARGS_CLOSE].is_set) export_file_open(tinfo);
 tinfo_array(tinfo, &myarray);
 myarray.current_element=exp_info->pointno;
 if (exp_info->channelcoords_to_display==0 && tinfo->itemsize==1) {
  /*{{{  Don't need to build new array, just access tinfo*/
  newarray=myarray;
  array_transpose(&newarray);
  array_setto_vector(&newarray);	/* Select only one element */
  array_transpose(&newarray);
  /*}}}  */
 } else {
  /*{{{  Build new array containing the data*/
  newarray.nr_of_vectors=myarray.nr_of_vectors;
  newarray.nr_of_elements=exp_info->channelcoords_to_display+tinfo->itemsize;
  newarray.element_skip=1;
  if (array_allocate(&newarray)==NULL) {
   ERREXIT(tinfo->emethods, "export_point: Can't allocate output array\n");
  }
  for (channel=0; channel<tinfo->nr_of_channels; channel++) {
   channelpos=tinfo->probepos+3*channel;
   for (i=0; i<exp_info->channelcoords_to_display; i++) {
    array_write(&newarray, channelpos[i]);
   }
   myarray.current_vector=channel;
   for (itempart=0; itempart<tinfo->itemsize; itempart++) {
    array_use_item(&myarray, itempart);
    array_write(&newarray, READ_ELEMENT(&myarray));
   }
  }
  /*}}}  */
 }
 array_dump(exp_info->file, &newarray, format);
 if (newarray.nr_of_elements>1) array_free(&newarray);

 if (args[ARGS_CLOSE].is_set) export_file_close(tinfo);

 return tinfo->tsdata;
}
Example #3
0
/*{{{  write_rec(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
write_rec(transform_info_ptr tinfo) {
 struct write_rec_storage *local_arg=(struct write_rec_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 FILE *outfptr=local_arg->outfptr;
 short *inbuf;
 array myarray;

 if (tinfo->itemsize!=1) {
  ERREXIT(tinfo->emethods, "write_rec: Only itemsize=1 is supported.\n");
 }
 if (args[ARGS_CLOSE].is_set) {
  write_rec_open_file(tinfo);
  outfptr=local_arg->outfptr;
 }
 /*{{{  Write epoch*/
 tinfo_array(tinfo, &myarray);
 /* We read the data point by point, i.e. channels fastest */
 array_transpose(&myarray);
 /* Within the record, writing is non-interlaced, ie points fastest */
 do {
  do {
   inbuf=local_arg->outbuf+local_arg->samples_per_record*myarray.current_element+local_arg->current_sample;
   *inbuf= (short int)rint(array_scan(&myarray)/local_arg->resolution);
   if (!local_arg->overflow_has_occurred && (*inbuf<local_arg->digmin || *inbuf>local_arg->digmax)) {
    TRACEMS(tinfo->emethods, 0, "write_rec: Some output values exceed digitization bits!\n");
    local_arg->overflow_has_occurred=TRUE;
   }
#ifndef LITTLE_ENDIAN
   Intel_int16(inbuf);
#endif
  } while (myarray.message==ARRAY_CONTINUE);
  if (++local_arg->current_sample>=local_arg->samples_per_record) {
   if ((int)fwrite(local_arg->outbuf, sizeof(short), tinfo->nr_of_channels*local_arg->samples_per_record, outfptr)!=tinfo->nr_of_channels*local_arg->samples_per_record) {
    ERREXIT(tinfo->emethods, "write_rec: Write error on data file.\n");
   }
   /* If nr_of_records was -1 (can only happen while appending),
    * leave it that way */
   if (local_arg->nr_of_records>=0) local_arg->nr_of_records++;
   local_arg->current_sample=0L;
  }
 } while (myarray.message!=ARRAY_ENDOFSCAN);
 /*}}}  */
 if (args[ARGS_CLOSE].is_set) write_rec_close_file(tinfo);
 return tinfo->tsdata;	/* Simply to return something `useful' */
}
Example #4
0
/*{{{  write_vitaport(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
write_vitaport(transform_info_ptr tinfo) {
    struct write_vitaport_storage *local_arg=(struct write_vitaport_storage *)tinfo->methods->local_storage;
    array myarray;
    int channel;

    /*{{{  Assert that epoch size didn't change & itemsize==1*/
    if (tinfo->itemsize!=1) {
        ERREXIT(tinfo->emethods, "write_vitaport: Only itemsize=1 is supported.\n");
    }
    if (local_arg->fileheader.knum!=tinfo->nr_of_channels) {
        ERREXIT2(tinfo->emethods, "write_vitaport: nr_of_channels was %d, now %d\n", MSGPARM(local_arg->fileheader.knum), MSGPARM(tinfo->nr_of_channels));
    }
    /*}}}  */

    if (tinfo->data_type==FREQ_DATA) tinfo->nr_of_points=tinfo->nroffreq;

    tinfo_array(tinfo, &myarray);
    array_transpose(&myarray); /* channels are the elements: Temp file is interlaced */
    do {
        channel=0;
        do {
            DATATYPE dat=array_scan(&myarray);
            if (fwrite(&dat, sizeof(DATATYPE), 1, local_arg->channelfile)!=1) {
                ERREXIT(tinfo->emethods, "write_vitaport: Error writing temp file.\n");
            }
            /* Keep track of the scaling... */
            if (dat>local_arg->channelmax[channel]) local_arg->channelmax[channel]=dat;
            if (dat<local_arg->channelmin[channel]) local_arg->channelmin[channel]=dat;
            channel++;
        } while (myarray.message==ARRAY_CONTINUE);
    } while (myarray.message!=ARRAY_ENDOFSCAN);

    if (tinfo->triggers.buffer_start!=NULL) {
        struct trigger *intrig=(struct trigger *)tinfo->triggers.buffer_start+1;
        while (intrig->code!=0) {
            push_trigger(&local_arg->triggers,local_arg->total_points+intrig->position,intrig->code,intrig->description);
            intrig++;
        }
    }

    local_arg->total_points+=tinfo->nr_of_points;

    return tinfo->tsdata;	/* Simply to return something `useful' */
}
Example #5
0
/*{{{  raw_fft(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
raw_fft(transform_info_ptr tinfo) {
 int i;
 array myarray, fftarray;
 long datasize, fftsize;

 if (tinfo->itemsize==2) {
  /*{{{  Do the inverse transform*/
  if (tinfo->data_type==TIME_DATA) {
   tinfo->nroffreq=tinfo->nr_of_points;
   tinfo->nrofshifts=1;
  }
  datasize=tinfo->nroffreq;
  fftsize=datasize-3;
  for (i=0; fftsize>>=1; i++);
  fftsize=1<<(i+2);
  if (datasize!=fftsize/2+1 || tinfo->nrofshifts!=1) {
   ERREXIT(tinfo->emethods, "raw_fft: Input spectra must have 2^n+1 frequencies, 2 items and 1 shift\n");
  }

  fftarray.nr_of_elements=fftsize;
  fftarray.element_skip=1;
  fftarray.nr_of_vectors=tinfo->nr_of_channels;
  if (array_allocate(&fftarray)==NULL) {
   ERREXIT(tinfo->emethods, "raw_fft: Error allocating memory\n");
  }

  /* We access tsdata as 1-item data already now (this makes copying easier) */
  tinfo->itemsize=1;
  tinfo->nr_of_points*=2;
  tinfo->data_type=TIME_DATA;
  tinfo_array(tinfo, &myarray);
  do {
   myarray.current_element=0;
   myarray.current_vector=fftarray.current_vector;
   realfft(ARRAY_ELEMENT(&myarray), fftsize, -1);
   do {
    array_write(&fftarray, array_scan(&myarray));
   } while (fftarray.message==ARRAY_CONTINUE);
  } while (fftarray.message==ARRAY_ENDOFVECTOR);
  tinfo->nr_of_points=fftarray.nr_of_elements;
  /*}}}  */
 } else {
Example #6
0
/*{{{  rereference(transform_info_ptr tinfo)*/
METHODDEF DATATYPE *
rereference(transform_info_ptr tinfo) {
 struct rereference_args_struct *rereference_args=(struct rereference_args_struct *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int itempart;
 transform_info_ptr const tinfoptr=tinfo;
 array indata;

  tinfo_array(tinfoptr, &indata);
  array_transpose(&indata);	/* Vector=map */
  for (itempart=0; itempart<tinfoptr->itemsize-tinfoptr->leaveright; itempart++) {
   array_use_item(&indata, itempart);
   do {
    DATATYPE mean=0;
    int n=0;

    do {
     if (is_in_channellist(indata.current_element+1, rereference_args->refchannel_numbers)) {
      mean+=array_scan(&indata);
      n++;
     } else {
      array_advance(&indata);
     }
    } while (indata.message==ARRAY_CONTINUE);
    mean/=n;
    array_previousvector(&indata);
    do {
     if ((args[ARGS_EXCLUDEOTHER].is_set && !is_in_channellist(indata.current_element+1, rereference_args->refchannel_numbers)) 
      || is_in_channellist(indata.current_element+1, rereference_args->excludechannel_numbers)) {
      array_advance(&indata);
     } else {
      array_write(&indata, READ_ELEMENT(&indata)-mean);
     }
    } while (indata.message==ARRAY_CONTINUE);
   } while (indata.message!=ARRAY_ENDOFSCAN);
  }

 return tinfo->tsdata;
}
Example #7
0
File: trim.c Project: berndf/avg_q
/*{{{  trim(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
trim(transform_info_ptr tinfo) {
 struct trim_storage *local_arg=(struct trim_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int item, shift, nrofshifts=1;
 long nr_of_input_ranges,nr_of_ranges;
 long output_points;
 long rangeno, current_output_point=0;
 const Bool collapse=args[ARGS_COLLAPSE].is_set || args[ARGS_COLLAPSE_Q].is_set;
 const DATATYPE collapse_quantile=(args[ARGS_COLLAPSE].is_set&&args[ARGS_COLLAPSE].arg.i==COLLAPSE_BY_MEDIAN ? 0.5 : (args[ARGS_COLLAPSE_Q].is_set ? args[ARGS_COLLAPSE_Q].arg.d/100.0 : 0.0));
 array myarray, newarray;
 DATATYPE *oldtsdata;
 DATATYPE *new_xdata=NULL;
 growing_buf ranges, tokenbuf;
 growing_buf triggers;

 growing_buf_init(&ranges);
 growing_buf_init(&tokenbuf);
 growing_buf_init(&triggers);

 if (tinfo->data_type==FREQ_DATA) {
  tinfo->nr_of_points=tinfo->nroffreq;
  nrofshifts=tinfo->nrofshifts;
 }

 /*{{{  Parse the ranges argument */
 nr_of_input_ranges=growing_buf_count_tokens(&local_arg->rangearg);
 if (nr_of_input_ranges<=0 || nr_of_input_ranges%2!=0) {
  ERREXIT(tinfo->emethods, "trim: Need an even number of arguments >=2\n");
 }
 nr_of_input_ranges/=2;
 output_points=0;
 growing_buf_allocate(&ranges, 0);
 growing_buf_allocate(&tokenbuf, 0);
 growing_buf_get_firsttoken(&local_arg->rangearg,&tokenbuf);
 while (tokenbuf.current_length>0) {
  struct range thisrange;
  if (args[ARGS_USE_CHANNEL].is_set) {
   int const channel=find_channel_number(tinfo,args[ARGS_USE_CHANNEL].arg.s);
   if (channel>=0) {
    DATATYPE const minval=get_value(tokenbuf.buffer_start, NULL);
    growing_buf_get_nexttoken(&local_arg->rangearg,&tokenbuf);
    DATATYPE const maxval=get_value(tokenbuf.buffer_start, NULL);
    array indata;
    tinfo_array(tinfo, &indata);
    indata.current_vector=channel;
    thisrange.offset= -1; /* Marks no start recorded yet */
    do {
     DATATYPE const currval=indata.read_element(&indata);
     if (currval>=minval && currval<=maxval) {
      if (thisrange.offset== -1) {
       thisrange.offset=indata.current_element;
       thisrange.length= 1;
      } else {
       thisrange.length++;
      }
     } else {
      if (thisrange.offset!= -1) {
       growing_buf_append(&ranges, (char *)&thisrange, sizeof(struct range));
       output_points+=(collapse ? 1 : thisrange.length);
       thisrange.offset= -1;
      }
     }
     array_advance(&indata);
    } while (indata.message==ARRAY_CONTINUE);
    if (thisrange.offset!= -1) {
     growing_buf_append(&ranges, (char *)&thisrange, sizeof(struct range));
     output_points+=(collapse ? 1 : thisrange.length);
    }
   } else {
    ERREXIT1(tinfo->emethods, "set xdata_from_channel: Unknown channel name >%s<\n", MSGPARM(args[ARGS_USE_CHANNEL].arg.s));
   }
  } else {
   if (args[ARGS_USE_XVALUES].is_set) {
    if (tinfo->xdata==NULL) create_xaxis(tinfo, NULL);
    thisrange.offset=decode_xpoint(tinfo, tokenbuf.buffer_start);
    growing_buf_get_nexttoken(&local_arg->rangearg,&tokenbuf);
    thisrange.length=decode_xpoint(tinfo, tokenbuf.buffer_start)-thisrange.offset+1;
   } else {
    thisrange.offset=gettimeslice(tinfo, tokenbuf.buffer_start);
    growing_buf_get_nexttoken(&local_arg->rangearg,&tokenbuf);
    thisrange.length=gettimeslice(tinfo, tokenbuf.buffer_start);
    if (thisrange.length==0) {
     thisrange.length=tinfo->nr_of_points-thisrange.offset;
    }
   }
   if (thisrange.length<=0) {
    ERREXIT1(tinfo->emethods, "trim: length is %d but must be >0.\n", MSGPARM(thisrange.length));
   }
   growing_buf_append(&ranges, (char *)&thisrange, sizeof(struct range));
   output_points+=(collapse ? 1 : thisrange.length);
  }
  growing_buf_get_nexttoken(&local_arg->rangearg,&tokenbuf);
 }
 /*}}}  */

 nr_of_ranges=ranges.current_length/sizeof(struct range);
 if (nr_of_ranges==0) {
  TRACEMS(tinfo->emethods, 0, "trim: No valid ranges selected, rejecting epoch.\n");
  return NULL;
 }
 TRACEMS2(tinfo->emethods, 1, "trim: nr_of_ranges=%ld, output_points=%ld\n", MSGPARM(nr_of_ranges), MSGPARM(output_points));

 newarray.nr_of_vectors=tinfo->nr_of_channels*nrofshifts;
 newarray.nr_of_elements=output_points;
 newarray.element_skip=tinfo->itemsize;
 if (array_allocate(&newarray)==NULL) {
  ERREXIT(tinfo->emethods, "trim: Error allocating memory.\n");
 }
 oldtsdata=tinfo->tsdata;

 if (tinfo->xdata!=NULL) {
  /* Store xchannelname at the end of xdata, as in create_xaxis(); otherwise we'll have 
   * a problem after free()'ing xdata... */
  new_xdata=(DATATYPE *)malloc(output_points*sizeof(DATATYPE)+strlen(tinfo->xchannelname)+1);
  if (new_xdata==NULL) {
   ERREXIT(tinfo->emethods, "trim: Error allocating xdata memory.\n");
  }
 }

 if (tinfo->triggers.buffer_start!=NULL) {
  struct trigger trig= *(struct trigger *)tinfo->triggers.buffer_start;
  growing_buf_allocate(&triggers, 0);
  /* Record the file position... */
  if (collapse) {
   /* Make triggers in subsequent append() work as expected at least with
    * continuous reading */
   trig.position=local_arg->current_epoch*nr_of_ranges;
   trig.code= -1;
  }
  growing_buf_append(&triggers, (char *)&trig, sizeof(struct trigger));
 }
 
 for (rangeno=0; rangeno<nr_of_ranges; rangeno++) {
  struct range *rangep=((struct range *)(ranges.buffer_start))+rangeno;
  long const old_startpoint=(rangep->offset>0 ?  rangep->offset : 0);
  long const new_startpoint=(rangep->offset<0 ? -rangep->offset : 0);

 /*{{{  Transfer the data*/
 if (old_startpoint<tinfo->nr_of_points 
  /* Skip this explicitly if no "real" point needs copying (length confined within negative offset)
   * since otherwise an endless loop can result as the stop conditions below look at the array 
   * states and no array is touched... */
  && new_startpoint<rangep->length)
 for (item=0; item<tinfo->itemsize; item++) {
  array_use_item(&newarray, item);
  for (shift=0; shift<nrofshifts; shift++) {
   tinfo_array(tinfo, &myarray);
   array_use_item(&myarray, item);
  do {
   DATATYPE sum=0.0;
   long reached_length=new_startpoint;
   myarray.current_element= old_startpoint;
   if (collapse) {
    newarray.current_element=current_output_point;
    newarray.message=ARRAY_CONTINUE;	/* Otherwise the loop below may finish promptly... */
    if (args[ARGS_COLLAPSE].is_set)
    switch (args[ARGS_COLLAPSE].arg.i) {
     case COLLAPSE_BY_HIGHEST:
      sum= -FLT_MAX;
      break;
     case COLLAPSE_BY_LOWEST:
      sum=  FLT_MAX;
      break;
     default:
      break;
    }
   } else {
    newarray.current_element=current_output_point+new_startpoint;
   }
   if (collapse && collapse_quantile>0.0) {
    array helparray=myarray;
    helparray.ringstart=ARRAY_ELEMENT(&myarray);
    helparray.current_element=helparray.current_vector=0;
    helparray.nr_of_vectors=1;
    helparray.nr_of_elements=rangep->length;
    sum=array_quantile(&helparray,collapse_quantile);
    myarray.message=ARRAY_CONTINUE;
   } else
   do {
    if (reached_length>=rangep->length) break;
    if (args[ARGS_COLLAPSE].is_set) {
     DATATYPE const hold=array_scan(&myarray);
     switch (args[ARGS_COLLAPSE].arg.i) {
      case COLLAPSE_BY_SUMMATION:
      case COLLAPSE_BY_AVERAGING:
       sum+=hold;
       break;
      case COLLAPSE_BY_HIGHEST:
       if (hold>sum) sum=hold;
       break;
      case COLLAPSE_BY_LOWEST:
       if (hold<sum) sum=hold;
       break;
      default:
       break;
     }
    } else {
     array_write(&newarray, array_scan(&myarray));
    }
    reached_length++;
   } while (newarray.message==ARRAY_CONTINUE && myarray.message==ARRAY_CONTINUE);
   if (collapse) {
    if (args[ARGS_COLLAPSE].is_set && args[ARGS_COLLAPSE].arg.i==COLLAPSE_BY_AVERAGING && item<tinfo->itemsize-tinfo->leaveright) sum/=reached_length;
    array_write(&newarray, sum);
   }
   if (newarray.message==ARRAY_CONTINUE) {
    array_nextvector(&newarray);
   }
   if (myarray.message==ARRAY_CONTINUE) {
    array_nextvector(&myarray);
   }
  } while (myarray.message==ARRAY_ENDOFVECTOR);
   tinfo->tsdata+=myarray.nr_of_vectors*myarray.nr_of_elements*myarray.element_skip;
  }
  tinfo->tsdata=oldtsdata;
 }
 /*}}}  */

 if (new_xdata!=NULL) {
  /*{{{  Transfer xdata*/
  DATATYPE sum=0.0;
  long reached_length=new_startpoint;
  long point, newpoint;
  if (collapse) {
   newpoint=current_output_point;
  } else {
   newpoint=current_output_point+new_startpoint;
  }
  for (point=old_startpoint;
    point<tinfo->nr_of_points && reached_length<rangep->length;
    point++) {
   if (collapse) {
    sum+=tinfo->xdata[point];
   } else {
    new_xdata[newpoint]=tinfo->xdata[point];
    newpoint++;
   }
   reached_length++;
  }
  if (collapse) {
   /* Summation of x axis values does not appear to make sense, so we always average: */
   new_xdata[newpoint]=sum/reached_length;
  }
  /*}}}  */
  /* Save xchannelname to the end of new_xdata */
  strcpy((char *)(new_xdata+output_points),tinfo->xchannelname);
 }

  if (tinfo->triggers.buffer_start!=NULL) {
   /* Collect triggers... */
   struct trigger *intrig=(struct trigger *)tinfo->triggers.buffer_start+1;
   while (intrig->code!=0) {
    if (intrig->position>=old_startpoint && intrig->position<old_startpoint+rangep->length) {
     struct trigger trig= *intrig;
     if (collapse) {
      trig.position=current_output_point;
     } else {
      trig.position=intrig->position-old_startpoint+current_output_point;
     }
     growing_buf_append(&triggers, (char *)&trig, sizeof(struct trigger));
    }
    intrig++;
   }
  }
  current_output_point+=(collapse ? 1 : rangep->length);
 }

 if (new_xdata!=NULL) {
  free(tinfo->xdata);
  tinfo->xdata=new_xdata;
  tinfo->xchannelname=(char *)(new_xdata+output_points);
 }
 if (tinfo->triggers.buffer_start!=NULL) {
  struct trigger trig;
  /* Write end marker */
  trig.position=0;
  trig.code=0;
  growing_buf_append(&triggers, (char *)&trig, sizeof(struct trigger));
  growing_buf_free(&tinfo->triggers);
  tinfo->triggers=triggers;
 }

 tinfo->multiplexed=FALSE;
 tinfo->nr_of_points=output_points;
 if (tinfo->data_type==FREQ_DATA) {
  tinfo->nroffreq=tinfo->nr_of_points;
 } else {
  tinfo->beforetrig-=((struct range *)(ranges.buffer_start))->offset;
  tinfo->aftertrig=output_points-tinfo->beforetrig;
 }
 tinfo->length_of_output_region=tinfo->nr_of_points*tinfo->nr_of_channels*tinfo->itemsize*nrofshifts;
 local_arg->current_epoch++;

 growing_buf_free(&tokenbuf);
 growing_buf_free(&ranges);

 return newarray.start;
}
Example #8
0
/*{{{  write_synamps(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
write_synamps(transform_info_ptr calltinfo) {
 struct write_synamps_storage *local_arg=(struct write_synamps_storage *)calltinfo->methods->local_storage;
 transform_argument *args=calltinfo->methods->arguments;
 NEUROSCAN_EPOCHED_SWEEP_HEAD sweephead;
 long tsdata_step, tsdata_steps, tsdata_stepwidth;
 array myarray;
 /* Note that 'tinfo' instead of 'tinfoptr' is used here so that we don't have to modify 
  * all of the older code which stored only one epoch */
 transform_info_ptr tinfo=calltinfo;

 if (args[ARGS_LINKED].is_set) {
  /* Go to the start: */
  for (; tinfo->previous!=NULL; tinfo=tinfo->previous);
 }
 for (; tinfo!=NULL; tinfo=tinfo->next) {
  DATATYPE * const orig_tsdata=tinfo->tsdata;
 /*{{{  Assert that epoch size didn't change & itemsize==1*/
 if (tinfo->itemsize!=1) {
  ERREXIT(tinfo->emethods, "write_synamps: Only itemsize=1 is supported.\n");
 }
 if (local_arg->EEG.nchannels!=tinfo->nr_of_channels) {
  ERREXIT2(tinfo->emethods, "write_synamps: nr_of_channels was %d, now %d\n", MSGPARM(local_arg->EEG.nchannels), MSGPARM(tinfo->nr_of_channels));
 }
 /*}}}  */

 if (tinfo->data_type==FREQ_DATA) {
  tinfo->nr_of_points=tinfo->nroffreq;
  tsdata_steps=tinfo->nrofshifts;
  tsdata_stepwidth=tinfo->nr_of_channels*tinfo->nroffreq*tinfo->itemsize;
 } else {
  tsdata_steps=1;
  tsdata_stepwidth=0;
 }
 for (tsdata_step=0; tsdata_step<tsdata_steps; tinfo->tsdata+=tsdata_stepwidth, tsdata_step++) {
 switch (local_arg->output_format) {
  case FORMAT_EEGFILE:
 if (local_arg->EEG.pnts!=tinfo->nr_of_points) {
  ERREXIT2(tinfo->emethods, "write_synamps: nr_of_points was %d, now %d\n", MSGPARM(local_arg->EEG.pnts), MSGPARM(tinfo->nr_of_points));
 }
 /*{{{  Set sweephead values*/
 sweephead.accept=1;
 sweephead.type=254;
 sweephead.correct=0;
 sweephead.rt=0;
 sweephead.response=0;
 if (tinfo->condition>0) {
  sweephead.type=tinfo->condition&0xff;
 } else if (tinfo->condition<0 && (-tinfo->condition)<=0xf) {
  sweephead.type=0;
  sweephead.response= -tinfo->condition;
 } else {
  /* KeyBoard event: Do it the same way 'Edit' does when epoching,
   * mapping F1 to type=1 and so on (overlap with stim codes, but they
   * should know how they want it...) */
  sweephead.type= (-tinfo->condition)>>4;
 }
 /*}}}  */
 /*{{{  Write sweephead struct*/
# ifndef LITTLE_ENDIAN
 change_byteorder((char *)&sweephead, sm_NEUROSCAN_EPOCHED_SWEEP_HEAD);
# endif
 write_struct((char *)&sweephead, sm_NEUROSCAN_EPOCHED_SWEEP_HEAD, local_arg->SCAN);
# ifndef LITTLE_ENDIAN
 change_byteorder((char *)&sweephead, sm_NEUROSCAN_EPOCHED_SWEEP_HEAD);
# endif
 /*}}}  */
 local_arg->EEG.nsweeps++;	/* This gets patched into the header by write_synamps_exit */
 local_arg->EEG.compsweeps++;
 local_arg->EEG.acceptcnt++;
   break;
  case FORMAT_AVGFILE:
   if (local_arg->EEG.NumSamples!=0) {
    ERREXIT(tinfo->emethods, "write_synamps: Only a single epoch may be written to an .AVG file!\n");
   }
  case FORMAT_CNTFILE:
   if (tinfo->triggers.buffer_start!=NULL) {
    struct trigger *intrig=(struct trigger *)tinfo->triggers.buffer_start+1;
    while (intrig->code!=0) {
     push_trigger(&local_arg->triggers,local_arg->EEG.NumSamples+intrig->position,intrig->code,intrig->description);
     intrig++;
    }
   }
   local_arg->EEG.NumSamples+=tinfo->nr_of_points;
   break;
 }

 tinfo_array(tinfo, &myarray);
 if (local_arg->output_format==FORMAT_AVGFILE) {
  /* points are the elements */
  float *pdata, * const buffer=(float *)malloc(myarray.nr_of_elements*sizeof(float));
  const char *fill="\0\0\0\0\0";
  if (buffer==NULL) {
   ERREXIT(tinfo->emethods, "write_synamps: Error allocating AVGFILE buffer\n");
  }
  do {
   int const channel=myarray.current_vector;
   /* Write the `5-byte channel header that is no longer used' */
   fwrite(fill, 1, 5, local_arg->SCAN);
   pdata=buffer;
   do {
    *pdata=NEUROSCAN_FLOATCONV(&local_arg->Channels[channel], array_scan(&myarray));
# ifndef LITTLE_ENDIAN
    Intel_float(pdata);
# endif
    pdata++;
   } while (myarray.message==ARRAY_CONTINUE);
   if ((int)fwrite(buffer,sizeof(float),myarray.nr_of_elements,local_arg->SCAN)!=myarray.nr_of_elements) {
    ERREXIT(tinfo->emethods, "write_synamps: Error writing data point\n");
   }
  } while (myarray.message!=ARRAY_ENDOFSCAN);
  free(buffer);
 } else {
 int16_t * const buffer=(int16_t *)malloc(myarray.nr_of_vectors*sizeof(int16_t));
 if (buffer==NULL) {
  ERREXIT(tinfo->emethods, "write_synamps: Error allocating buffer\n");
 }
 array_transpose(&myarray);	/* channels are the elements */
 do {
  int channel=0;
  do {
   DATATYPE hold=array_scan(&myarray), hold2;
   /* Code anything exceeding the representable range, including +-Inf, as min/max representable value. */
   hold2=NEUROSCAN_SHORTCONV(&local_arg->Channels[channel], hold);
   if (hold2< -32768) hold2= -32768;
   else if (hold2> 32767) hold2= 32767;
   buffer[channel]=(int16_t)hold2;
# ifndef LITTLE_ENDIAN
   Intel_int16(&buffer[channel]);
# endif
   channel++;
  } while (myarray.message==ARRAY_CONTINUE);
  if ((int)fwrite(buffer,sizeof(int16_t),myarray.nr_of_elements,local_arg->SCAN)!=myarray.nr_of_elements) {
   ERREXIT(tinfo->emethods, "write_synamps: Error writing data point\n");
  }
 } while (myarray.message!=ARRAY_ENDOFSCAN);
 free(buffer);
 }
 } /* FREQ_DATA shifts loop */
 tinfo->tsdata=orig_tsdata;
  if (!args[ARGS_LINKED].is_set) {
   break;
  }
 } /* Linked epochs loop */

 return calltinfo->tsdata;	/* Simply to return something `useful' */
}
Example #9
0
/*{{{  scale_by(transform_info_ptr tinfo)*/
METHODDEF DATATYPE *
scale_by(transform_info_ptr tinfo) {
 struct scale_by_storage *local_arg=(struct scale_by_storage *)tinfo->methods->local_storage;
 DATATYPE factor;
 int itempart;
 array indata;

 tinfo_array(tinfo, &indata);
 switch (local_arg->type) {
  /* Operations which are done on maps */
  case SCALE_BY_XDATA:
  case SCALE_BY_INVXDATA:
   if (tinfo->xdata==NULL) create_xaxis(tinfo, NULL);
  case SCALE_BY_NORMALIZE:
  case SCALE_BY_INVNORM:
  case SCALE_BY_INVSQUARENORM:
  case SCALE_BY_INVSUM:
  case SCALE_BY_INVMAX:
  case SCALE_BY_INVMAXABS:
  case SCALE_BY_INVQUANTILE:
   array_transpose(&indata);	/* Vectors are maps */
   if (local_arg->have_channel_list) {
    ERREXIT(tinfo->emethods, "scale_by: Channel subsets are not supported for map operations.\n");
   }
   break;

  /* Operations which are done on channels */
  case SCALE_BY_INVPOINTNORM:
  case SCALE_BY_INVPOINTSQUARENORM:
  case SCALE_BY_INVPOINTSUM:
  case SCALE_BY_INVPOINTMAX:
  case SCALE_BY_INVPOINTMAXABS:
  case SCALE_BY_INVPOINTQUANTILE:
  case SCALE_BY_FACTOR:
   break;

  /* Operations which involve a special but constant factor */
  case SCALE_BY_PI:
   local_arg->factor= M_PI;
   break;
  case SCALE_BY_INVPI:
   local_arg->factor= 1.0/M_PI;
   break;
  case SCALE_BY_SFREQ:
   local_arg->factor= tinfo->sfreq;
   break;
  case SCALE_BY_INVSFREQ:
   local_arg->factor= 1.0/tinfo->sfreq;
   break;
  case SCALE_BY_NR_OF_POINTS:
   local_arg->factor= (tinfo->data_type==FREQ_DATA ? tinfo->nroffreq : tinfo->nr_of_points);
   break;
  case SCALE_BY_INVNR_OF_POINTS:
   local_arg->factor= 1.0/(tinfo->data_type==FREQ_DATA ? tinfo->nroffreq : tinfo->nr_of_points);
   break;
  case SCALE_BY_NR_OF_CHANNELS:
   local_arg->factor= tinfo->nr_of_channels;
   break;
  case SCALE_BY_INVNR_OF_CHANNELS:
   local_arg->factor= 1.0/tinfo->nr_of_channels;
   break;
  case SCALE_BY_NROFAVERAGES:
   local_arg->factor= tinfo->nrofaverages;
   break;
  case SCALE_BY_INVNROFAVERAGES:
   local_arg->factor= 1.0/tinfo->nrofaverages;
   break;
  case SCALE_BY_SQRTNROFAVERAGES:
   local_arg->factor= sqrt(tinfo->nrofaverages);
   break;
  case SCALE_BY_INVSQRTNROFAVERAGES:
   local_arg->factor= 1.0/sqrt(tinfo->nrofaverages);
   break;
 }

 for (itempart=local_arg->fromitem; itempart<=local_arg->toitem; itempart++) {
  array_use_item(&indata, itempart);
  do {
   if (local_arg->have_channel_list && !is_in_channellist(indata.current_vector+1, local_arg->channel_list)) {
    array_nextvector(&indata);
    continue;
   }
   switch (local_arg->type) {
    case SCALE_BY_NORMALIZE:
    case SCALE_BY_INVNORM:
    case SCALE_BY_INVPOINTNORM:
     factor=array_abs(&indata);
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     array_previousvector(&indata);
     break;
    case SCALE_BY_INVSQUARENORM:
    case SCALE_BY_INVPOINTSQUARENORM:
     factor=array_square(&indata);
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     array_previousvector(&indata);
     break;
    case SCALE_BY_INVSUM:
    case SCALE_BY_INVPOINTSUM:
     factor=array_sum(&indata);
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     array_previousvector(&indata);
     break;
    case SCALE_BY_INVMAX:
    case SCALE_BY_INVPOINTMAX:
     factor=array_max(&indata);
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     array_previousvector(&indata);
     break;
    case SCALE_BY_INVMAXABS:
    case SCALE_BY_INVPOINTMAXABS: {
     DATATYPE amax=fabs(array_scan(&indata)), hold;
     while (indata.message==ARRAY_CONTINUE) {
      hold=fabs(array_scan(&indata));
      if (hold>amax) amax=hold;
     }
     factor=amax;
     }
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     array_previousvector(&indata);
     break;
    case SCALE_BY_INVQUANTILE:
    case SCALE_BY_INVPOINTQUANTILE:
     factor=array_quantile(&indata,local_arg->factor);
     if (factor==0.0) factor=1.0;
     factor=1.0/factor;
     break;
    case SCALE_BY_XDATA:
     factor=tinfo->xdata[indata.current_vector];
     break;
    case SCALE_BY_INVXDATA:
     factor=1.0/tinfo->xdata[indata.current_vector];
     break;
    case SCALE_BY_PI:
    case SCALE_BY_INVPI:
    case SCALE_BY_SFREQ:
    case SCALE_BY_INVSFREQ:
    case SCALE_BY_NR_OF_POINTS:
    case SCALE_BY_INVNR_OF_POINTS:
    case SCALE_BY_NR_OF_CHANNELS:
    case SCALE_BY_INVNR_OF_CHANNELS:
    case SCALE_BY_NROFAVERAGES:
    case SCALE_BY_INVNROFAVERAGES:
    case SCALE_BY_SQRTNROFAVERAGES:
    case SCALE_BY_INVSQRTNROFAVERAGES:
    case SCALE_BY_FACTOR:
     factor=local_arg->factor;
     break;
    default:
     continue;
   }
   array_scale(&indata, factor);
  } while (indata.message!=ARRAY_ENDOFSCAN);
 }

 return tinfo->tsdata;
}
Example #10
0
int main(int argc, char *argv[]) {
 int i=1, start=0, end=0, freqno;
 DATATYPE *new_tsdata, hold;
 array D;
 OPT_DTYPE ax, bx, cx, fa, fb, fc, xmin, sumsq, weight, sumweight, ave, min_power, optimize_arg, *points;
 optimize_struct ostruct;
 struct minfunc_struct mfs;
 struct transform_info_struct firsttinfo;
 transform_info_ptr tinfo, tinfo_next;
 struct transform_methods_struct methods[2];
 struct external_methods_struct emethod;


 tinfo= &firsttinfo;
 /*{{{  Process command line*/
 while (*argv[1]=='-') {
  switch (argv[1][1]) {
  }
  argv++; argc--;
 }
 if (argc!=3) {
  fprintf(stderr, "Usage: %s ascdatafile outfile\n"
    , argv[0]);
  return 1;
 }

 if (start<0) start=0;
 if (end<=0) end=start;
 /*}}}  */

 clear_external_methods(&emethod);
 firsttinfo.methods= methods;
 firsttinfo.emethods= &emethod;

 /*{{{  Read all data sets*/
 select_readasc(tinfo);
 (*tinfo->methods->transform_defaults)(tinfo);
 firsttinfo.filename=argv[1];
 firsttinfo.epochs= -1; firsttinfo.fromepoch=1;
 (*tinfo->methods->transform_init)(tinfo);
 if (start!=0) {
  while (i<start) {
   (*tinfo->methods->transform)(tinfo);
   i++;
  }
 }
 while ((end==0 || i<=end) && (*tinfo->methods->transform)(tinfo)!=NULL) {
  if ((tinfo_next=malloc(sizeof(struct transform_info_struct)))==NULL) {
   ERREXIT(&emethod, "similarity: Error malloc'ing tinfo struct\n");
  }
  *(tinfo_next)=firsttinfo;
  tinfo_next->previous=tinfo;
  tinfo_next->next=NULL;
  tinfo->next=tinfo_next;
  tinfo=tinfo_next;
  i++;
 }
 /* The last tinfo structure was allocated in vein, throw away */
 tinfo=tinfo->previous;
 free(tinfo->next);
 tinfo->next=NULL;
 (*firsttinfo.methods->transform_exit)(&firsttinfo);
 /*}}}  */

 points=malloc(2*firsttinfo.nr_of_channels*sizeof(OPT_DTYPE));
 for (freqno=0; freqno<firsttinfo.nr_of_channels; freqno++) {
  /*{{{  Construct symmetrical function*/
  sumweight=ave=0.0;
  min_power=1e10;
  for (i=0, tinfo= &firsttinfo; tinfo!=NULL; tinfo=tinfo->next, i++) {
   tinfo_array(tinfo, &D);
   array_transpose(&D);
   array_reset(&D);

   D.current_vector=freqno;
   D.current_element=i;
   hold=array_readelement(&D);
   D.current_element=0;
   do {
    points[D.current_element*2]=100*channel_distance(tinfo, i, D.current_element);
    points[D.current_element*2+1]=array_scan(&D)/hold;
   } while (D.message==ARRAY_CONTINUE);
   ostruct.function= &minfunc;
   mfs.nr_of_points=firsttinfo.nr_of_channels;
   mfs.points=points;
   ostruct.fixed_args=(void *)&mfs;
   ostruct.num_opt_args=1;
   ostruct.opt_args=(void *)&optimize_arg;
   ax=0.1; bx=12;
   opt_mnbrak(&ostruct, &ax, &bx, &cx, &fa, &fb, &fc);
   sumsq=opt_brent(&ostruct, ax, bx, cx, 1e-4, &xmin);
#   ifdef VERBOSE
   printf("%d %g %g %g\n", i, xmin, sumsq, hold);
#   endif
   weight= 1.0/sumsq;
   sumweight+=weight;
   ave+=weight*xmin;
   if (hold<min_power) min_power=hold;
  }
  ave/=sumweight;
#  ifdef VERBOSE
  printf("Consensus: %g %g\n", ave, min_power);
#  endif
  /*}}}  */
  /*{{{  Subtract symmetrical function*/
  for (i=0, tinfo= &firsttinfo; tinfo!=NULL; tinfo=tinfo->next, i++) {
   tinfo_array(tinfo, &D);
   array_transpose(&D);
   array_reset(&D);
   D.current_vector=freqno;
   D.current_element=0;
   do {
    hold= min_power*distfun(100*channel_distance(tinfo, i, D.current_element), ave);
    array_write(&D, array_readelement(&D)-hold);
   } while (D.message==ARRAY_CONTINUE);
  }
  /*}}}  */
 }
 free(points);

 /*{{{  Write all data sets*/
 tinfo= &firsttinfo;

 select_extract_item(tinfo);	/* Output real part only */
 (*tinfo->methods->transform_defaults)(tinfo);
 tinfo->methods->local_storage=(void *)0;
 (*tinfo->methods->transform_init)(tinfo);
 tinfo->methods++;

 select_writeasc(tinfo);
 (*tinfo->methods->transform_defaults)(tinfo);
 tinfo->outfname=argv[2];
 tinfo->methods->local_storage=(void *)1;
 (*tinfo->methods->transform_init)(tinfo);

 for (; tinfo!=NULL; tinfo=tinfo->next) {
  tinfo->outfptr=firsttinfo.outfptr;
  tinfo->methods=methods;
  if ((new_tsdata=(*tinfo->methods->transform)(tinfo))==NULL) {
   ERREXIT(tinfo->emethods, "extract_item failed !\n");
  }
  free(tinfo->tsdata);
  tinfo->tsdata=new_tsdata;
  tinfo->methods++;
  (*tinfo->methods->transform)(tinfo);
 }

 tinfo= &firsttinfo;
 tinfo->methods=methods;
 (*tinfo->methods->transform_exit)(tinfo);
 tinfo->methods++;
 (*tinfo->methods->transform_exit)(tinfo);
 /*}}}  */

 return 0;
}
Example #11
0
/*{{{  project_init(transform_info_ptr tinfo)*/
METHODDEF void
project_init(transform_info_ptr tinfo) {
 struct project_args_struct *project_args=(struct project_args_struct *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 transform_info_ptr side_tinfo= &project_args->side_tinfo;
 array *vectors= &project_args->vectors;
 growing_buf buf;
#define BUFFER_SIZE 80
 char buffer[BUFFER_SIZE];

 side_tinfo->methods= &project_args->methods;
 side_tinfo->emethods=tinfo->emethods;
 select_readasc(side_tinfo);
 growing_buf_init(&buf);
 growing_buf_allocate(&buf, 0);
 if (args[ARGS_FROMEPOCH].is_set) {
  snprintf(buffer, BUFFER_SIZE, "-f %ld ", args[ARGS_FROMEPOCH].arg.i);
  growing_buf_appendstring(&buf, buffer);
 }
 if (args[ARGS_EPOCHS].is_set) {
  project_args->epochs=args[ARGS_EPOCHS].arg.i;
  if (project_args->epochs<=0) {
   ERREXIT(tinfo->emethods, "project_init: The number of epochs must be positive.\n");
  }
 } else {
  project_args->epochs=1;
 }
 snprintf(buffer, BUFFER_SIZE, "-e %d ", project_args->epochs);
 growing_buf_appendstring(&buf, buffer);
 growing_buf_appendstring(&buf, args[ARGS_PROJECTFILE].arg.s);
 if (!buf.can_be_freed || !setup_method(side_tinfo, &buf)) {
  ERREXIT(tinfo->emethods, "project_init: Error setting readasc arguments.\n");
 }

 project_args->points=(args[ARGS_POINTS].is_set ? args[ARGS_POINTS].arg.i : 1);
 project_args->nr_of_item=(args[ARGS_NROFITEM].is_set ? args[ARGS_NROFITEM].arg.i : 0);
 project_args->orthogonalize_vectors_first=args[ARGS_ORTHOGONALIZE].is_set;
 if (args[ARGS_SUBSPACE].is_set) {
  project_args->project_mode=PROJECT_MODE_SSP;
 } else if (args[ARGS_SUBTRACT_SUBSPACE].is_set) {
  project_args->project_mode=PROJECT_MODE_SSPS;
 } else if (args[ARGS_MULTIPLY].is_set) {
  project_args->project_mode=PROJECT_MODE_MULTIPLY;
 } else {
  project_args->project_mode=PROJECT_MODE_SCALAR;
 }
 if (args[ARGS_CHANNELNAMES].is_set) {
  project_args->channel_list=expand_channel_list(tinfo, args[ARGS_CHANNELNAMES].arg.s);
  if (project_args->channel_list==NULL) {
   ERREXIT(tinfo->emethods, "project_init: Zero channels were selected by -N!\n");
  }
 } else {
  project_args->channel_list=NULL;
 }

 (*side_tinfo->methods->transform_init)(side_tinfo);

 /*{{{  Read first project_file epoch and allocate vectors array accordingly*/
 if ((side_tinfo->tsdata=(*side_tinfo->methods->transform)(side_tinfo))==NULL) {
  ERREXIT(tinfo->emethods, "project_init: Can't get the first project epoch.\n");
 }
 if (project_args->project_mode==PROJECT_MODE_MULTIPLY) {
  /* Save channel names and positions for later */
  project_args->save_side_tinfo.nr_of_channels=side_tinfo->nr_of_channels;
  copy_channelinfo(&project_args->save_side_tinfo, side_tinfo->channelnames, side_tinfo->probepos);
 }
 if (project_args->points==0) project_args->points=side_tinfo->nr_of_points;
 if (project_args->points>side_tinfo->nr_of_points) {
  ERREXIT1(tinfo->emethods, "project_init: There are only %d points in the project_file epoch.\n", MSGPARM(side_tinfo->nr_of_points));
 }
 if (args[ARGS_AT_XVALUE].is_set) {
  project_args->nr_of_point=find_pointnearx(side_tinfo, (DATATYPE)atof(args[ARGS_NROFPOINT].arg.s));
 } else {
 project_args->nr_of_point=gettimeslice(side_tinfo, args[ARGS_NROFPOINT].arg.s);
 }
 vectors->nr_of_vectors=project_args->epochs*project_args->points;
 vectors->nr_of_elements=side_tinfo->nr_of_channels;
 vectors->element_skip=1;
 if (array_allocate(vectors)==NULL) {
  ERREXIT(tinfo->emethods, "project_init: Error allocating vectors memory\n");
 }
 /*}}}  */

 do {
  /*{{{  Copy [points] vectors from project_file to vectors array*/
  array indata;
  int point;

  if (vectors->nr_of_elements!=side_tinfo->nr_of_channels) {
   ERREXIT(side_tinfo->emethods, "project_init: Varying channel numbers in project file!\n");
  }
  if (project_args->nr_of_point>=side_tinfo->nr_of_points) {
   ERREXIT2(side_tinfo->emethods, "project_init: nr_of_point=%d, nr_of_points=%d\n", MSGPARM(project_args->nr_of_point), MSGPARM(side_tinfo->nr_of_points));
  }
  if (project_args->nr_of_item>=side_tinfo->itemsize) {
   ERREXIT2(side_tinfo->emethods, "project_init: nr_of_item=%d, itemsize=%d\n", MSGPARM(project_args->nr_of_item), MSGPARM(side_tinfo->itemsize));
  }

  for (point=0; point<project_args->points; point++) {
   tinfo_array(side_tinfo, &indata);
   array_transpose(&indata);	/* Vector = map */
   if (vectors->nr_of_elements!=indata.nr_of_elements) {
    ERREXIT(side_tinfo->emethods, "project_init: vector size doesn't match\n");
   }
   indata.current_vector=project_args->nr_of_point+point;
   array_setto_vector(&indata);
   array_use_item(&indata, project_args->nr_of_item);
   array_copy(&indata, vectors);
  }
  /*}}}  */
  free_tinfo(side_tinfo);
 } while ((side_tinfo->tsdata=(*side_tinfo->methods->transform)(side_tinfo))!=NULL);

 if (vectors->message!=ARRAY_ENDOFSCAN) {
  ERREXIT1(tinfo->emethods, "project_init: Less than %d epochs in project file\n", MSGPARM(vectors->nr_of_vectors));
 }
 
 /*{{{  Set unused channels to zero if requested*/
 if (args[ARGS_ZERO_UNUSEDCOEFFICIENTS].is_set) {
  if (project_args->channel_list!=NULL) {
   do {
    do {
     if (is_in_channellist(vectors->current_element+1, project_args->channel_list)) {
      array_advance(vectors);
     } else {
      array_write(vectors, 0.0);
     }
    } while (vectors->message==ARRAY_CONTINUE);
   } while (vectors->message!=ARRAY_ENDOFSCAN);
  } else {
   ERREXIT(tinfo->emethods, "project_init: Option -z only makes sense in combination with -N!\n");
  }
 }
 /*}}}  */
 /*{{{  De-mean vectors if requested*/
 if (args[ARGS_CORRELATION].is_set) {
  do {
   DATATYPE mean=0.0;
   int nrofaverages=0;
   do {
    if (project_args->channel_list!=NULL && !is_in_channellist(vectors->current_element+1, project_args->channel_list)) {
     array_advance(vectors);
    } else {
     mean+=array_scan(vectors);
     nrofaverages++;
    }
   } while (vectors->message==ARRAY_CONTINUE);
   mean/=nrofaverages;
   array_previousvector(vectors);
   do {
    array_write(vectors, READ_ELEMENT(vectors)-mean);
   } while (vectors->message==ARRAY_CONTINUE);
  } while (vectors->message!=ARRAY_ENDOFSCAN);
 }
 /*}}}  */
 /*{{{  Orthogonalize vectors if requested*/
 if (project_args->orthogonalize_vectors_first) {
  array_make_orthogonal(vectors);
  if (vectors->message==ARRAY_ERROR) {
   ERREXIT(tinfo->emethods, "project_init: Error orthogonalizing projection vectors\n");
  }
 }
 /*}}}  */
 if (!args[ARGS_NONORMALIZATION].is_set) {
 /*{{{  Normalize vectors*/
 do {
  DATATYPE length=0.0;
  do {
   if (project_args->channel_list!=NULL && !is_in_channellist(vectors->current_element+1, project_args->channel_list)) {
    array_advance(vectors);
   } else {
    const DATATYPE hold=array_scan(vectors);
    length+=hold*hold;
   }
  } while (vectors->message==ARRAY_CONTINUE);
  length=sqrt(length);

  array_previousvector(vectors);
  if (length==0.0) {
   ERREXIT1(tinfo->emethods, "project_init: Vector %d has zero length !\n", MSGPARM(vectors->current_vector));
  }
  array_scale(vectors, 1.0/length);
 } while (vectors->message!=ARRAY_ENDOFSCAN);
 /*}}}  */
 }
 /*{{{  Dump vectors if requested*/
 if (args[ARGS_DUMPVECTORS].is_set) {
  FILE * const fp=fopen(args[ARGS_DUMPVECTORS].arg.s, "w");
  if (fp==NULL) {
   ERREXIT1(tinfo->emethods, "project_init: Error opening output file >%s<.\n", MSGPARM(args[ARGS_DUMPVECTORS].arg.s));
  }
  array_transpose(vectors); /* We want one vector to be one column */ 
  array_dump(fp, vectors, ARRAY_MATLAB);
  array_transpose(vectors);
  fclose(fp);
 }
 /*}}}  */

 (*side_tinfo->methods->transform_exit)(side_tinfo);
 free_methodmem(side_tinfo);
 growing_buf_free(&buf);

 tinfo->methods->init_done=TRUE;
}
Example #12
0
/*{{{  project(transform_info_ptr tinfo)*/
METHODDEF DATATYPE *
project(transform_info_ptr tinfo) {
 struct project_args_struct *project_args=(struct project_args_struct *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 DATATYPE *retvalue=tinfo->tsdata;
 array indata, scalars, *vectors= &project_args->vectors;
 int itempart, itemparts=tinfo->itemsize-tinfo->leaveright;

 if (project_args->project_mode==PROJECT_MODE_MULTIPLY) {
  if (!(tinfo->nr_of_channels==vectors->nr_of_vectors
      ||(tinfo->nr_of_channels==1 && tinfo->itemsize==vectors->nr_of_vectors))) {
   ERREXIT(tinfo->emethods, "project: Number of scalars and maps doesn't match!\n");
  }
 } else {
 if (vectors->nr_of_elements!=tinfo->nr_of_channels) {
  ERREXIT2(tinfo->emethods, "project: %d channels in epoch, but %d channels in project file.\n", MSGPARM(tinfo->nr_of_channels), MSGPARM(vectors->nr_of_elements));
 }
 }

 array_reset(vectors);

 tinfo_array(tinfo, &indata);
 array_transpose(&indata);	/* Vectors are maps */

 /* Be sure that different output items are adjacent... */
 scalars.nr_of_elements=vectors->nr_of_vectors;
 switch (project_args->project_mode) {
  case PROJECT_MODE_SCALAR:
   scalars.nr_of_vectors=tinfo->nr_of_points;
   scalars.element_skip=itemparts;
   break;
  case PROJECT_MODE_SSP:
  case PROJECT_MODE_SSPS:
   scalars.nr_of_vectors=1;
   scalars.element_skip=1;
   break;
  case PROJECT_MODE_MULTIPLY:
   scalars=indata;
   if (tinfo->nr_of_channels!=vectors->nr_of_vectors) {
    /* Ie, one channel and weights in the items: Convert from 1 element to
     * itemsize elements */
    scalars.element_skip=1;
    scalars.nr_of_elements=tinfo->itemsize;
    itemparts=1;
   }
   indata.element_skip=itemparts;
   indata.nr_of_elements=vectors->nr_of_elements; /* New number of channels */
   indata.nr_of_vectors=scalars.nr_of_vectors; /* New number of points */
   if (array_allocate(&indata)==NULL) {
    ERREXIT(tinfo->emethods, "project: Can't allocate new indata array\n");
   }
   break;
 }

 if (project_args->project_mode==PROJECT_MODE_MULTIPLY) {
  array_transpose(vectors); /* Now the elements are the subspace dimensions */
  for (itempart=0; itempart<itemparts; itempart++) {
   array_use_item(&indata, itempart);
   array_use_item(&scalars, itempart);
   do {
    /*{{{  Build the signal subspace vector*/
    do {
     array_write(&indata, array_multiply(vectors, &scalars, MULT_SAMESIZE));
    } while (indata.message==ARRAY_CONTINUE);
    /*}}}  */
   } while (indata.message!=ARRAY_ENDOFSCAN);
  }
  array_transpose(vectors);
 } else {

 if (array_allocate(&scalars)==NULL) {
  ERREXIT(tinfo->emethods, "project: Can't allocate scalars array\n");
 }

 for (itempart=0; itempart<itemparts; itempart++) {
  array_use_item(&indata, itempart);
  if (project_args->project_mode==PROJECT_MODE_SCALAR) {
   array_use_item(&scalars, itempart);
  }

  do {
   /*{{{  Calculate the projection scalars*/
   do {
    /* With all vectors in turn: */
    DATATYPE product=0.0;
    do {
     if (project_args->channel_list!=NULL && !is_in_channellist(vectors->current_element+1, project_args->channel_list)) {
      array_advance(vectors);
      array_advance(&indata);
     } else {
      product+=array_scan(&indata)*array_scan(vectors);
     }
    } while (vectors->message==ARRAY_CONTINUE);

    array_write(&scalars, product);
    if (scalars.message==ARRAY_CONTINUE) array_previousvector(&indata);
   } while (scalars.message==ARRAY_CONTINUE);
   /*}}}  */
   
   switch (project_args->project_mode) {
    case PROJECT_MODE_SCALAR:
     break;
    case PROJECT_MODE_SSP:
     /*{{{  Build the signal subspace vector*/
     array_transpose(vectors); /* Now the elements are the subspace dimensions */
     array_previousvector(&indata);
     do {
      array_write(&indata, array_multiply(vectors, &scalars, MULT_VECTOR));
     } while (indata.message==ARRAY_CONTINUE);
     array_transpose(vectors);
     /*}}}  */
     break;
    case PROJECT_MODE_SSPS:
     /*{{{  Subtract the signal subspace vector*/
     array_transpose(vectors); /* Now the elements are the subspace dimensions */
     array_previousvector(&indata);
     do {
      array_write(&indata, READ_ELEMENT(&indata)-array_multiply(vectors, &scalars, MULT_VECTOR));
     } while (indata.message==ARRAY_CONTINUE);
     array_transpose(vectors);
     /*}}}  */
     break;
    default:
     /* Can't happen, just to keep the compiler happy... */
     ERREXIT(tinfo->emethods, "project: This cannot happen!\n");
     break;
   }
  } while (indata.message!=ARRAY_ENDOFSCAN);
 }
 }

 /*{{{  Prepare tinfo to reflect the data structure returned*/
 switch (project_args->project_mode) {
  case PROJECT_MODE_SCALAR:
   if (args[ARGS_USE_CHANNELS].is_set) {
    tinfo->nr_of_channels=vectors->nr_of_vectors;
    tinfo->itemsize=itemparts;
   } else {
    tinfo->nr_of_channels=1;
    tinfo->itemsize=itemparts*vectors->nr_of_vectors;
   }
   tinfo->length_of_output_region=scalars.nr_of_elements*scalars.element_skip*scalars.nr_of_vectors;
   tinfo->leaveright=0;
   tinfo->multiplexed=TRUE;
   if (tinfo->channelnames!=NULL) {
    free_pointer((void **)&tinfo->channelnames[0]);
    free_pointer((void **)&tinfo->channelnames);
   }
   free_pointer((void **)&tinfo->probepos);
   create_channelgrid(tinfo);
   retvalue=scalars.start;
   break;
  case PROJECT_MODE_SSP:
  case PROJECT_MODE_SSPS:
   array_free(&scalars);
   retvalue=tinfo->tsdata;
   break;
  case PROJECT_MODE_MULTIPLY:
   /* Note that we don't free `scalars' because it just points to the original tsdata! */
   /* Have to set this correctly so that copy_channelinfo works... */
   tinfo->nr_of_channels=indata.nr_of_elements;
   copy_channelinfo(tinfo, project_args->save_side_tinfo.channelnames, project_args->save_side_tinfo.probepos);
   tinfo->nr_of_points=indata.nr_of_vectors;
   tinfo->itemsize=indata.element_skip;
   tinfo->length_of_output_region=tinfo->nr_of_channels*tinfo->nr_of_points*tinfo->itemsize;
   retvalue=indata.start;
   tinfo->multiplexed=TRUE;
   break;
 }
 /*}}}  */

 return retvalue;
}
Example #13
0
/*{{{  writeasc(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
writeasc(transform_info_ptr calltinfo) {
    struct writeasc_storage *local_arg=(struct writeasc_storage *)calltinfo->methods->local_storage;
    transform_argument *args=calltinfo->methods->arguments;
    int i, channel, itempart;
    long tsdata_step, tsdata_steps, tsdata_stepwidth;
    FILE *outfptr=local_arg->outfptr;
    /* Note that 'tinfo' instead of 'tinfoptr' is used here so that we don't have to modify
     * all of the older code which stored only one epoch */
    transform_info_ptr tinfo=calltinfo;

    if (args[ARGS_CLOSE].is_set) {
        writeasc_open_file(calltinfo);
        outfptr=local_arg->outfptr;
    }
    if (args[ARGS_LINKED].is_set) {
        /* Go to the start: */
        for (; tinfo->previous!=NULL; tinfo=tinfo->previous);
    }
    for (; tinfo!=NULL; tinfo=tinfo->next) {
        DATATYPE * const orig_tsdata=tinfo->tsdata;
        if (tinfo->xdata==NULL) create_xaxis(tinfo,NULL);
        if (tinfo->data_type==FREQ_DATA) {
            tinfo->nr_of_points=tinfo->nroffreq;
            tsdata_steps=tinfo->nrofshifts;
            tsdata_stepwidth=tinfo->nr_of_channels*tinfo->nroffreq*tinfo->itemsize;
        } else {
            tsdata_steps=1;
            tsdata_stepwidth=0;
        }
        for (tsdata_step=0; tsdata_step<tsdata_steps; tinfo->tsdata+=tsdata_stepwidth, tsdata_step++) {
            if (tinfo->data_type==FREQ_DATA && tsdata_steps>1) {
                /* Multiple data sets to be written: Construct a different z_value for each. */
                if (tinfo->basetime==0.0) {
                    /* Assigning the same latency to all shifts would not be optimal... */
                    tinfo->z_label="Nr";
                    tinfo->z_value=tsdata_step+1;
                } else {
                    tinfo->z_label="Lat[ms]";
                    tinfo->z_value=(tsdata_step*tinfo->basetime+(tinfo->windowsize-tinfo->beforetrig)/tinfo->sfreq)*1000;
                }
            }
            if (args[ARGS_BINARY].is_set) {
                /*{{{  Write binary*/
                char outbuf[OUTBUFSIZE], *inoutbuf;
                int len;

                fwrite((void *)&tinfo->nr_of_channels, sizeof(int), 1, outfptr);
                fwrite((void *)&tinfo->nr_of_points, sizeof(int), 1, outfptr);
                if (tinfo->itemsize<=0) tinfo->itemsize=1;
                fwrite((void *)&tinfo->itemsize, sizeof(int), 1, outfptr);
                fwrite((void *)&tinfo->multiplexed, sizeof(int), 1, outfptr);

                *outbuf='\0';
                inoutbuf=outbuf;
                if (tinfo->nrofaverages>0) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Nr_of_averages=%d;", tinfo->nrofaverages);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->sfreq!=local_arg->sfreq) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Sfreq=%f;", (float)tinfo->sfreq);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->beforetrig!=local_arg->beforetrig) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "BeforeTrig=%d;", tinfo->beforetrig);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->leaveright!=local_arg->leaveright) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Leaveright=%d;", tinfo->leaveright);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->condition!=0) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Condition=%d;", tinfo->condition);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->triggers.buffer_start!=NULL) {
                    struct trigger *intrig=(struct trigger *)tinfo->triggers.buffer_start;
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Triggers=%ld", intrig->position);
                    inoutbuf+=strlen(inoutbuf);
                    intrig++;
                    while (intrig->code!=0) {
                        snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), ",%ld:%d", intrig->position, intrig->code);
                        inoutbuf+=strlen(inoutbuf);
                        intrig++;
                    }
                    *inoutbuf++=';';
                }
                if (tinfo->comment!=NULL) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "%s", tinfo->comment);
                    inoutbuf+=strlen(inoutbuf);
                }
                if (tinfo->z_label!=NULL) {
                    snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "%s%s=%g", ZAXIS_DELIMITER, tinfo->z_label, tinfo->z_value);
                    inoutbuf+=strlen(inoutbuf);
                }
                len=inoutbuf-outbuf+1;
                len+=strlen(tinfo->xchannelname)+1;
                for (channel=0; channel<tinfo->nr_of_channels; channel++) {
                    len+=strlen(tinfo->channelnames[channel])+1;
                }
                fwrite((void *)&len, sizeof(int), 1, outfptr);

                fwrite((void *)outbuf, strlen(outbuf)+1, 1, outfptr);
                fwrite((void *)tinfo->xchannelname, strlen(tinfo->xchannelname)+1, 1, outfptr);
                for (channel=0; channel<tinfo->nr_of_channels; channel++) {
                    fwrite((void *)tinfo->channelnames[channel], strlen(tinfo->channelnames[channel])+1, 1, outfptr);
                }
                fwrite((void *)tinfo->probepos, sizeof(double), 3*tinfo->nr_of_channels, outfptr);
                fwrite((void *)tinfo->xdata, sizeof(DATATYPE), tinfo->nr_of_points, outfptr);

                fwrite((void *)tinfo->tsdata, sizeof(DATATYPE), tinfo->nr_of_channels*tinfo->nr_of_points*tinfo->itemsize, outfptr);
                /* 6 ints: channels/points/items/multiplexed/len_of_string_section/skipback */
                len+=6*sizeof(int)+3*tinfo->nr_of_channels*sizeof(double)+tinfo->nr_of_points*(1+tinfo->nr_of_channels*tinfo->itemsize)*sizeof(DATATYPE);
                fwrite((void *)&len, sizeof(int), 1, outfptr);
                /*}}}  */
            } else {
                /*{{{  Write ascii*/
                array myarray;

                if (tinfo->nrofaverages>0) fprintf(outfptr, "Nr_of_averages=%d;", tinfo->nrofaverages);
                if (tinfo->sfreq!=local_arg->sfreq) fprintf(outfptr, "Sfreq=%f;", (float)tinfo->sfreq);
                if (tinfo->beforetrig!=local_arg->beforetrig) fprintf(outfptr, "BeforeTrig=%d;", tinfo->beforetrig);
                if (tinfo->leaveright!=local_arg->leaveright) fprintf(outfptr, "Leaveright=%d;", tinfo->leaveright);
                if (tinfo->condition!=0) fprintf(outfptr, "Condition=%d;", tinfo->condition);
                if (tinfo->triggers.buffer_start!=NULL) {
                    struct trigger *intrig=(struct trigger *)tinfo->triggers.buffer_start;
                    fprintf(outfptr, "Triggers=%ld", intrig->position);
                    intrig++;
                    while (intrig->code!=0) {
                        fprintf(outfptr, ",%ld:%d", intrig->position, intrig->code);
                        intrig++;
                    }
                    fprintf(outfptr, ";");
                }
                if (tinfo->comment!=NULL) fprintf(outfptr, "%s", tinfo->comment);
                if (tinfo->z_label!=NULL) fprintf(outfptr, "%s%s=%g", ZAXIS_DELIMITER, tinfo->z_label, tinfo->z_value);
                fprintf(outfptr,"\nchannels=%d, points=%d", tinfo->nr_of_channels, tinfo->nr_of_points);
                if (tinfo->itemsize<=1) {
                    tinfo->itemsize=1;	/* Make sure the itemsize is at least 1 */
                } else {
                    fprintf(outfptr, ", itemsize=%d", tinfo->itemsize);
                }
                fprintf(outfptr, "\n%s", tinfo->xchannelname);
                for (channel=0; channel<tinfo->nr_of_channels; channel++) {
                    char buffer[MAX_CHANNEL_LEN+1], *inbuf;
                    strncpy(buffer, tinfo->channelnames[channel], MAX_CHANNEL_LEN);
                    buffer[MAX_CHANNEL_LEN]='\0';
                    /* Some characters can become hazardous, so we change them... */
                    for (inbuf=buffer; *inbuf!='\0'; inbuf++) {
                        if (strchr(" \t\n", *inbuf)!=NULL) *inbuf='_';
                    }
                    fprintf(outfptr, "\t%s", buffer);
                }
                for (i=0; i<3; i++) {
                    fprintf(outfptr, "\n-");
                    for (channel=0; channel<tinfo->nr_of_channels; channel++) {
                        fprintf(outfptr, "\t%g", tinfo->probepos[channel*3+i]);
                    }
                }
                fprintf(outfptr, "\n");

                tinfo_array(tinfo, &myarray);
                array_transpose(&myarray); /* Outer loop is for points */
                i=0;
                do {
                    fprintf(outfptr, "%g", tinfo->xdata[i]);
                    do {
                        if (tinfo->itemsize==1) {
                            fprintf(outfptr, "\t%g", array_scan(&myarray));
                        } else {
                            DATATYPE *itemptr=ARRAY_ELEMENT(&myarray);
                            fprintf(outfptr, "\t(%g", *itemptr++);
                            for (itempart=1; itempart<tinfo->itemsize; itempart++) {
                                fprintf(outfptr, "\t%g", *itemptr++);
                            }
                            fprintf(outfptr, ")");
                            array_advance(&myarray);
                        }
                    } while (myarray.message==ARRAY_CONTINUE);
                    fprintf(outfptr, "\n");
                    i++;
                } while (myarray.message!=ARRAY_ENDOFSCAN);
                /*}}}  */
            }
        } /* FREQ_DATA shifts loop */
        tinfo->tsdata=orig_tsdata;
        if (!args[ARGS_LINKED].is_set) {
            break;
        }
    } /* Linked epochs loop */
    if (args[ARGS_CLOSE].is_set) writeasc_close_file(tinfo);
    return calltinfo->tsdata;	/* Simply to return something `useful' */
}