示例#1
0
文件: write_rec.c 项目: berndf/avg_q
/*{{{  write_rec_init(transform_info_ptr tinfo) {*/
METHODDEF void
write_rec_init(transform_info_ptr tinfo) {
 struct write_rec_storage *local_arg=(struct write_rec_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int bits=(args[ARGS_BITS].is_set ? args[ARGS_BITS].arg.i : DEFAULT_BITS);
 local_arg->resolution=(args[ARGS_RESOLUTION].is_set ? args[ARGS_RESOLUTION].arg.d : 1.0);

 local_arg->samples_per_record=args[ARGS_SAMPLES_PER_RECORD].is_set ? gettimeslice(tinfo, args[ARGS_SAMPLES_PER_RECORD].arg.s) : (tinfo->data_type==FREQ_DATA ? tinfo->nroffreq : tinfo->nr_of_points);
 local_arg->current_sample=0L;
 if ((local_arg->outbuf=(short *)malloc(tinfo->nr_of_channels*local_arg->samples_per_record*sizeof(short)))==NULL) {
  ERREXIT(tinfo->emethods, "write_rec_init: Error allocating buffer memory.\n");
 }
 if (bits<1) {
  ERREXIT1(tinfo->emethods, "write_rec_init: Invalid number of bits %d\n", MSGPARM(bits));
 }
 if (local_arg->resolution<=0.0) {
  ERREXIT1(tinfo->emethods, "write_rec_init: A resolution<=0.0 is not allowed\n", MSGPARM(bits));
 }
 local_arg->digmin=(-1L<<(bits-1));
 local_arg->digmax=(~local_arg->digmin);
 local_arg->overflow_has_occurred=FALSE;

 if (args[ARGS_CLOSE].is_set==FALSE) write_rec_open_file(tinfo);

 tinfo->methods->init_done=TRUE;
}
示例#2
0
文件: write_mfx.c 项目: berndf/avg_q
/*{{{  write_mfx_init(transform_info_ptr tinfo) {*/
METHODDEF void
write_mfx_init(transform_info_ptr tinfo) {
 struct write_mfx_storage *local_arg=(struct write_mfx_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int NoOfChannels=tinfo->nr_of_channels;
 int channel;

 local_arg->mfxfile=mfx_open(args[ARGS_OFILE].arg.s, "r+b", MFX_DATATYPE);
 if (!args[ARGS_APPEND].is_set || local_arg->mfxfile==NULL) {   /* target does not exist*/
  /*{{{  Create file*/
  if (local_arg->mfxfile!=NULL) mfx_close(local_arg->mfxfile);
  if ((local_arg->mfxfile=mfx_create(args[ARGS_OFILE].arg.s, (args[ARGS_CREATE_TRIGGERCHANNEL].is_set ? NoOfChannels+1 : NoOfChannels), MFX_DATATYPE))==NULL) {
   ERREXIT1(tinfo->emethods, "write_mfx_init: Can't open file >%s<\n", MSGPARM(args[ARGS_OFILE].arg.s));
  }
  if (mfx_describefile(local_arg->mfxfile, tinfo->comment, 1.0/tinfo->sfreq, (args[ARGS_CONTINUOUS].is_set ? 0 : tinfo->nr_of_points), -tinfo->beforetrig/tinfo->sfreq)!=MFX_NOERR) {
   ERREXIT1(tinfo->emethods, "write_mfx_init: mfx_describefile error %s\n", MSGPARM(mfx_errors[mfx_lasterr]));
  }
  for (channel=0; channel<NoOfChannels; channel++) {
   double * const pos_mfx=local_arg->mfxfile->channelheaders[channel].position;
   double * const pos_tinfo=tinfo->probepos+3*channel;
   int i;
   const Bool is_electric=(*tinfo->channelnames[channel]!='M');
   if (mfx_describechannel(local_arg->mfxfile, channel+1, tinfo->channelnames[channel], (is_electric ? "uV" : "fT"),
    (is_electric ? DT_EEGTYPE : DT_MEGTYPE), SHRT_MIN/args[ARGS_CONVFACTOR].arg.d, SHRT_MAX/args[ARGS_CONVFACTOR].arg.d)!=MFX_NOERR) {
    ERREXIT1(tinfo->emethods, "write_mfx_init: mfx_describechannel error %s\n", MSGPARM(mfx_errors[mfx_lasterr]));
   }
   for (i=0; i<3; i++) {
    pos_mfx[i]=pos_tinfo[i];
   }
  }
  if (args[ARGS_CREATE_TRIGGERCHANNEL].is_set) {
   if (mfx_describechannel(local_arg->mfxfile, channel+1, "TRIGGER", "T", DT_TRIGGER, -32768.0, 32767.0)!=MFX_NOERR) {
    ERREXIT1(tinfo->emethods, "write_mfx_init: mfx_describechannel error %s\n", MSGPARM(mfx_errors[mfx_lasterr]));
   }
  }
  /*}}}  */
 } else {
  /*{{{  Append to file*/
  mfx_seek(local_arg->mfxfile, 0L, SEEK_END);
  /*}}}  */
 }
 if ((local_arg->mfxfile->selected_channels=(int *)malloc(NoOfChannels*sizeof(int)))==NULL) {
  ERREXIT(tinfo->emethods, "write_mfx_init: Error allocating selection array\n");
 }
 for (channel=0; channel<NoOfChannels; channel++) {
  local_arg->mfxfile->selected_channels[channel]=channel+1;
 }
 local_arg->mfxfile->nr_of_channels_selected=NoOfChannels;

 tinfo->methods->init_done=TRUE;
}
示例#3
0
/*{{{  get_mfxepoch_init(transform_info_ptr tinfo)*/
METHODDEF void
get_mfxepoch_init(transform_info_ptr tinfo) {
 struct get_mfxepoch_storage *local_arg=(struct get_mfxepoch_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int skipepochs;

 if ((local_arg->fileptr=mfx_open(args[ARGS_IFILE].arg.s, "rb", MFX_DATATYPE))==NULL) {
  ERREXIT2(tinfo->emethods, "get_mfxepoch_init: Can't open mfx file %s: %s\n", 
	   MSGPARM(args[ARGS_IFILE].arg.s), MSGPARM(mfx_errors[mfx_lasterr]));
 }
 if ((tinfo->nr_of_channels=mfx_cselect(local_arg->fileptr, args[ARGS_CHANNELNAMES].arg.s))==0) {
  ERREXIT1(tinfo->emethods, "get_mfxepoch_init: mfx_cselect error %s\n", 
	   MSGPARM(mfx_errors[mfx_lasterr]));
 }

 get_mfxinfo(local_arg->fileptr, tinfo);
 get_mfxinfo_free(tinfo); /* We don't need the channel names etc. here */

 /*{{{  Parse arguments that can be in seconds*/
 local_arg->beforetrig=gettimeslice(tinfo, args[ARGS_BEFORETRIG].arg.s);
 local_arg->aftertrig=gettimeslice(tinfo, args[ARGS_AFTERTRIG].arg.s);
 local_arg->offset=(args[ARGS_OFFSET].is_set ? gettimeslice(tinfo, args[ARGS_OFFSET].arg.s) : 0);
 /*}}}  */
 local_arg->fromepoch=(args[ARGS_FROMEPOCH].is_set ? args[ARGS_FROMEPOCH].arg.i : 1);
 local_arg->epochs=(args[ARGS_EPOCHS].is_set ? args[ARGS_EPOCHS].arg.i : -1);
 local_arg->trigname=(args[ARGS_TRIGNAME].is_set ? args[ARGS_TRIGNAME].arg.s : "TRIGGER");
 if (strcmp(local_arg->trigname, "0")==0) {
  local_arg->trigname=NULL;
  local_arg->offset-= (long int)rint(local_arg->fileptr->fileheader.epoch_begin_latency*tinfo->sfreq);
  local_arg->beforetrig+=local_arg->offset;
  local_arg->aftertrig-=local_arg->offset;
 }

 skipepochs=local_arg->fromepoch-1;
 /*{{{  Skip triggers if fromepoch parameter demands it*/
 while (skipepochs>0) {
  mfx_seektrigger(local_arg->fileptr, local_arg->trigname, args[ARGS_TRIGCODE].arg.i);
  if (mfx_lasterr!=MFX_NOERR) {
   ERREXIT(tinfo->emethods, "get_mfxepoch_init: Error seeking to first trigger\n");
  }
  skipepochs--;
 }
 /*}}}  */

 tinfo->methods->init_done=TRUE;
}
示例#4
0
文件: write_mfx.c 项目: berndf/avg_q
/*{{{  write_mfx(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
write_mfx(transform_info_ptr tinfo) {
 struct write_mfx_storage *local_arg=(struct write_mfx_storage *)tinfo->methods->local_storage;

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

 multiplexed(tinfo);
 if (tinfo->data_type==FREQ_DATA) tinfo->nr_of_points=tinfo->nroffreq;
 if (mfx_write((void *)tinfo->tsdata, tinfo->nr_of_points, local_arg->mfxfile)!=MFX_NOERR) {
  ERREXIT1(tinfo->emethods, "write_mfx_init: mfx_write error %s\n", MSGPARM(mfx_errors[mfx_lasterr]));
 }

 return tinfo->tsdata;	/* Simply to return something `useful' */
}
示例#5
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;
}
示例#6
0
文件: scale_by.c 项目: berndf/avg_q
/*{{{  scale_by_init(transform_info_ptr tinfo)*/
METHODDEF void
scale_by_init(transform_info_ptr tinfo) {
 struct scale_by_storage *local_arg=(struct scale_by_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;

 if (args[ARGS_TYPE].is_set) {
  local_arg->type=(enum scale_by_type)args[ARGS_TYPE].arg.i;
  if (local_arg->type==SCALE_BY_NORMALIZE) {
   ERREXIT(tinfo->emethods, "scale_by_init: Using '1.0' is deprecated. Please use 'invnorm' instead!\n");
  }
 } else {
  local_arg->type=SCALE_BY_FACTOR;
 }
 if (local_arg->type==SCALE_BY_FACTOR
  || local_arg->type==SCALE_BY_INVQUANTILE || local_arg->type==SCALE_BY_INVPOINTQUANTILE
  ) {
  if (!args[ARGS_FACTOR].is_set) {
   ERREXIT(tinfo->emethods, "scale_by_init: A factor must be given!\n");
  }
  local_arg->factor=args[ARGS_FACTOR].arg.d;
  if ((local_arg->type==SCALE_BY_INVQUANTILE || local_arg->type==SCALE_BY_INVPOINTQUANTILE)
   && (local_arg->factor<0 || local_arg->factor>1)) {
    ERREXIT(tinfo->emethods, "scale_by_init: factor must be between 0 and 1 for quantile!\n");
  }
 }

 if (args[ARGS_BYNAME].is_set) {
  if (local_arg->type==SCALE_BY_INVQUANTILE) {
   ERREXIT(tinfo->emethods, "scale_by_init: Channel name list does not work with invquantile!\n");
  }
  /* Note that this is NULL if no channel matched, which is why we need have_channel_list as well... */
  local_arg->channel_list=expand_channel_list(tinfo, args[ARGS_BYNAME].arg.s);
  local_arg->have_channel_list=TRUE;
 } else {
  local_arg->channel_list=NULL;
  local_arg->have_channel_list=FALSE;
 }

 local_arg->fromitem=0;
 local_arg->toitem=tinfo->itemsize-tinfo->leaveright-1;
 if (args[ARGS_ITEMPART].is_set) {
  local_arg->fromitem=local_arg->toitem=args[ARGS_ITEMPART].arg.i;
  if (local_arg->fromitem<0 || local_arg->fromitem>=tinfo->itemsize) {
   ERREXIT1(tinfo->emethods, "scale_by_init: No item number %d in file\n", MSGPARM(local_arg->fromitem));
  }
 }

 tinfo->methods->init_done=TRUE;
}
示例#7
0
/*{{{  export_file_open and export_file_close*/
LOCAL void
export_file_open(transform_info_ptr tinfo) {
 struct export_point_info *exp_info=(struct export_point_info *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;

 if (strcmp(args[ARGS_OFILE].arg.s, "stdout")==0) {
  exp_info->file=stdout;
 } else if (strcmp(args[ARGS_OFILE].arg.s, "stderr")==0) {
  exp_info->file=stderr;
 } else {
  if ((exp_info->file=fopen(args[ARGS_OFILE].arg.s, args[ARGS_APPEND].is_set ? "a" : "w"))==NULL) {
   ERREXIT1(tinfo->emethods, "export_file_open: Can't open file >%s<\n", MSGPARM(args[ARGS_OFILE].arg.s));
  }
 }
}
示例#8
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' */
}
示例#9
0
文件: echo.c 项目: berndf/avg_q
/*{{{  echo_init(transform_info_ptr tinfo) {*/
METHODDEF void
echo_init(transform_info_ptr tinfo) {
 struct echo_storage *local_arg=(struct echo_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 char const *inbuf=args[ARGS_STRING].arg.s;

 growing_buf_init(&local_arg->buf);
 growing_buf_allocate(&local_arg->buf, 0);
 while (*inbuf !='\0') {
  char c=*inbuf++;
  if (c=='\\') {
   char c1;
   switch (c1=*inbuf++) {
    case 'n':
     c='\n';
     break;
    case 't':
     c='\t';
     break;
    case '\0':
     inbuf--;
     break;
    default:
     c=c1;
     break;
   }
   if (c=='\0') break;
  }
  growing_buf_appendchar(&local_arg->buf, c);
 }
 growing_buf_appendchar(&local_arg->buf, '\0');

 if (!args[ARGS_OFILE].is_set) {
  local_arg->outfile=NULL;
 } else if (strcmp(args[ARGS_OFILE].arg.s, "stdout")==0) {
  local_arg->outfile=stdout;
 } else if (strcmp(args[ARGS_OFILE].arg.s, "stderr")==0) {
  local_arg->outfile=stderr;
 } else
 if ((local_arg->outfile=fopen(args[ARGS_OFILE].arg.s, "a"))==NULL) {
  ERREXIT1(tinfo->emethods, "echo_init: Can't open file >%s<\n", MSGPARM(args[ARGS_OFILE].arg.s));
 }

 tinfo->methods->init_done=TRUE;
}
示例#10
0
/*{{{  null_source(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
null_source(transform_info_ptr tinfo) {
 struct null_source_storage *local_arg=(struct null_source_storage *)tinfo->methods->local_storage;
 array myarray;

 if (local_arg->epochs--==0) return NULL;
 tinfo->beforetrig=local_arg->beforetrig;
 tinfo->aftertrig=local_arg->aftertrig;
 tinfo->nr_of_points=local_arg->beforetrig+local_arg->aftertrig;
 tinfo->nr_of_channels=local_arg->nr_of_channels;
 tinfo->nrofaverages=1;
 if (tinfo->nr_of_points<=0) {
  ERREXIT1(tinfo->emethods, "null_source: Invalid nr_of_points %d\n", MSGPARM(tinfo->nr_of_points));
 }

 /*{{{  Configure myarray*/
 myarray.element_skip=tinfo->itemsize=local_arg->itemsize;
 tinfo->multiplexed=FALSE;
 myarray.nr_of_elements=tinfo->nr_of_points;
 myarray.nr_of_vectors=tinfo->nr_of_channels;
 if (array_allocate(&myarray)==NULL || (tinfo->comment=(char *)malloc(MAX_COMMENTLEN))==NULL) {
  ERREXIT(tinfo->emethods, "null_source: Error allocating data\n");
 }
 /*}}}  */

 snprintf(tinfo->comment, MAX_COMMENTLEN, "null_source");

 /* Force create_channelgrid to really allocate the channel info anew.
  * Otherwise, free_tinfo will free someone else's data ! */
 tinfo->channelnames=NULL; tinfo->probepos=NULL;
 create_channelgrid(tinfo); /* Create defaults for any missing channel info */

 local_arg->current_epoch=0;
 tinfo->z_label=NULL;
 tinfo->sfreq=local_arg->sfreq;
 tinfo->tsdata=myarray.start;
 tinfo->length_of_output_region=tinfo->nr_of_channels*tinfo->nr_of_points*tinfo->itemsize;
 tinfo->leaveright=0;
 tinfo->data_type=TIME_DATA;
 local_arg->current_epoch++;

 return tinfo->tsdata;
}
示例#11
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' */
}
示例#12
0
文件: write_rec.c 项目: berndf/avg_q
/*{{{  write_rec_open_file(transform_info_ptr tinfo) {*/
LOCAL void
write_rec_open_file(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=NULL;
 
 if (strcmp(args[ARGS_OFILE].arg.s, "stdout")==0) outfptr=stdout;
 else if (strcmp(args[ARGS_OFILE].arg.s, "stderr")==0) outfptr=stderr;
 local_arg->appendmode=args[ARGS_APPEND].is_set;
 if (local_arg->appendmode) {
  /*{{{  Append mode open if cofile exists and is of non-zero length*/
  if (outfptr==NULL) {
   if ((outfptr=fopen(args[ARGS_OFILE].arg.s, "r+b"))!=NULL) {
    fseek(outfptr, 0L, SEEK_END);
    if (ftell(outfptr)==0L) {
     local_arg->appendmode=FALSE;	/* If at start: write header */
    }
   }
  }
  /*}}}  */
 }
 if (outfptr==NULL) {
  /*{{{  Open the REC file in truncate mode*/
  local_arg->appendmode=FALSE;	/* write header */
  if ((outfptr=fopen(args[ARGS_OFILE].arg.s, "wb"))==NULL) {
   ERREXIT1(tinfo->emethods, "write_rec_open_file: Can't open %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
  }
  /*}}}  */
 }
 local_arg->outfptr=outfptr;
 if (local_arg->appendmode) {
  /* Read rather than write header in append mode */
  fseek(outfptr, 0L, SEEK_SET);
  if (read_struct((char *)&local_arg->fheader, sm_REC_file, outfptr)==0) {
   ERREXIT1(tinfo->emethods, "write_rec_open_file: Can't read header in file %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
  }
# ifndef LITTLE_ENDIAN
  change_byteorder((char *)&local_arg->fheader, sm_REC_file);
# endif
  local_arg->nr_of_records=atoi(local_arg->fheader.nr_of_records);
  fseek(outfptr, 0L, SEEK_END);
 } else {
  /*{{{  Write header*/
  REC_channel_header channelheader;
  const long channelheader_length=CHANNELHEADER_SIZE_PER_CHANNEL*tinfo->nr_of_channels;
  int channel;
  short dd, mm, yy, yyyy, hh, mi, ss;
  char numbuf[NUMBUF_LENGTH];

  setlocale(LC_NUMERIC, "C"); /* Print fractional numbers with decimal point */
#define fileheader local_arg->fheader
  memset(&fileheader, ' ', sizeof(REC_file_header));
  copy_nstring(fileheader.version, "0", sizeof(fileheader.version));
  if (args[ARGS_PATIENT].is_set) copy_nstring(fileheader.patient, args[ARGS_PATIENT].arg.s, sizeof(fileheader.patient));
  if (args[ARGS_RECORDING].is_set) copy_nstring(fileheader.recording, args[ARGS_RECORDING].arg.s, sizeof(fileheader.recording));
  if (args[ARGS_DATETIME].is_set) {
   char * const comma=strchr(args[ARGS_DATETIME].arg.s, ',');
   if (comma==NULL) {
    ERREXIT(tinfo->emethods, "write_rec_open_file: Datetime format is dd.mm.yy,hh.mi.ss !\n");
   }
   copy_nstring(fileheader.startdate, args[ARGS_DATETIME].arg.s, sizeof(fileheader.startdate));
   copy_nstring(fileheader.starttime, comma+1, sizeof(fileheader.starttime));
  } else if (tinfo->comment!=NULL) {
   if (!args[ARGS_RECORDING].is_set) copy_nstring(fileheader.recording, tinfo->comment, sizeof(fileheader.recording));
   if (comment2time(tinfo->comment, &dd, &mm, &yy, &yyyy, &hh, &mi, &ss)) {
    snprintf(numbuf, NUMBUF_LENGTH, "%02d.%02d.%02d", dd, mm, yy);
    copy_nstring(fileheader.startdate, numbuf, sizeof(fileheader.startdate));
    snprintf(numbuf, NUMBUF_LENGTH, "%02d.%02d.%02d", hh, mi, ss);
    copy_nstring(fileheader.starttime, numbuf, sizeof(fileheader.starttime));
   }
  }
  if (*fileheader.startdate==' ') {
   /* Date/time weren't set otherwise: */
   copy_nstring(fileheader.startdate, "00.00.00", sizeof(fileheader.startdate));
   copy_nstring(fileheader.starttime, "00.00.00", sizeof(fileheader.starttime));
  }
  snprintf(numbuf, NUMBUF_LENGTH, "%ld", sm_REC_file[0].offset+channelheader_length);
  copy_nstring(fileheader.bytes_in_header, numbuf, sizeof(fileheader.bytes_in_header));
  copy_nstring(fileheader.data_format_version, (args[ARGS_DATA_FORMAT_VERSION].is_set ? args[ARGS_DATA_FORMAT_VERSION].arg.s : "write_rec file"), sizeof(fileheader.data_format_version));
  local_arg->nr_of_records=0;
  copy_nstring(fileheader.nr_of_records, "-1", sizeof(fileheader.nr_of_records));
  snprintf(numbuf, NUMBUF_LENGTH, "%g", ((double)local_arg->samples_per_record)/tinfo->sfreq);
  copy_nstring(fileheader.duration_s, numbuf, sizeof(fileheader.duration_s));
  snprintf(numbuf, NUMBUF_LENGTH, "%d", tinfo->nr_of_channels);
  copy_nstring(fileheader.nr_of_channels, numbuf, sizeof(fileheader.nr_of_channels));
#ifndef LITTLE_ENDIAN
  change_byteorder((char *)&fileheader, sm_REC_file);
#endif
  write_struct((char *)&fileheader, sm_REC_file, outfptr);
#ifndef LITTLE_ENDIAN
  change_byteorder((char *)&fileheader, sm_REC_file);
#endif
#undef fileheader

  if ((channelheader.label=(char (*)[16])malloc(channelheader_length))==NULL) {
   ERREXIT(tinfo->emethods, "write_rec_open_file: Error allocating channelheader memory\n");
  }
  channelheader.transducer=(char (*)[80])(channelheader.label+tinfo->nr_of_channels);
  channelheader.dimension=(char (*)[8])(channelheader.transducer+tinfo->nr_of_channels);
  channelheader.physmin=(char (*)[8])(channelheader.dimension+tinfo->nr_of_channels);
  channelheader.physmax=(char (*)[8])(channelheader.physmin+tinfo->nr_of_channels);
  channelheader.digmin=(char (*)[8])(channelheader.physmax+tinfo->nr_of_channels);
  channelheader.digmax=(char (*)[8])(channelheader.digmin+tinfo->nr_of_channels);
  channelheader.prefiltering=(char (*)[80])(channelheader.digmax+tinfo->nr_of_channels);
  channelheader.samples_per_record=(char (*)[8])(channelheader.prefiltering+tinfo->nr_of_channels);
  channelheader.reserved=(char (*)[32])(channelheader.samples_per_record+tinfo->nr_of_channels);
  memset(channelheader.label, ' ', channelheader_length);
  for (channel=0; channel<tinfo->nr_of_channels; channel++) {
   copy_nstring(channelheader.dimension[channel], "uV", sizeof(channelheader.dimension[channel]));
   copy_nstring(channelheader.label[channel], tinfo->channelnames[channel], sizeof(channelheader.label[channel]));
   snprintf(numbuf, NUMBUF_LENGTH, "%g", (double)local_arg->digmin*local_arg->resolution);
   copy_nstring(channelheader.physmin[channel], numbuf, sizeof(channelheader.physmin[channel]));
   snprintf(numbuf, NUMBUF_LENGTH, "%g", (double)local_arg->digmax*local_arg->resolution);
   copy_nstring(channelheader.physmax[channel], numbuf, sizeof(channelheader.physmax[channel]));
   snprintf(numbuf, NUMBUF_LENGTH, "%ld", local_arg->digmin);
   copy_nstring(channelheader.digmin[channel], numbuf, sizeof(channelheader.digmin[channel]));
   snprintf(numbuf, NUMBUF_LENGTH, "%ld", local_arg->digmax);
   copy_nstring(channelheader.digmax[channel], numbuf, sizeof(channelheader.digmax[channel]));
   snprintf(numbuf, NUMBUF_LENGTH, "%ld", local_arg->samples_per_record);
   copy_nstring(channelheader.samples_per_record[channel], numbuf, sizeof(channelheader.samples_per_record[channel]));
  }
  setlocale(LC_NUMERIC, ""); /* Reset locale to environment */
  if (tinfo->nr_of_channels!=(int)fwrite((void *)channelheader.label, CHANNELHEADER_SIZE_PER_CHANNEL, tinfo->nr_of_channels, local_arg->outfptr)) {
   ERREXIT(tinfo->emethods, "write_rec_open_file: Error writing channel headers\n");
  }
  free(channelheader.label);
  /*}}}  */
 }
}
示例#13
0
文件: recode.c 项目: berndf/avg_q
/*{{{  recode_init(transform_info_ptr tinfo) {*/
METHODDEF void
recode_init(transform_info_ptr tinfo) {
 struct recode_storage *local_arg=(struct recode_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 growing_buf buf, tokenbuf;
 struct blockdef *inblocks;
 int nr_of_blocks=0, block;
 Bool havearg;

 if (args[ARGS_BYNAME].is_set) {
  /* Note that this is NULL if no channel matched, which is why we need have_channel_list as well... */
  local_arg->channel_list=expand_channel_list(tinfo, args[ARGS_BYNAME].arg.s);
  local_arg->have_channel_list=TRUE;
 } else {
  local_arg->channel_list=NULL;
  local_arg->have_channel_list=FALSE;
 }

 local_arg->fromitem=0;
 local_arg->toitem=tinfo->itemsize-tinfo->leaveright-1;
 if (args[ARGS_ITEMPART].is_set) {
  local_arg->fromitem=local_arg->toitem=args[ARGS_ITEMPART].arg.i;
  if (local_arg->fromitem<0 || local_arg->fromitem>=tinfo->itemsize) {
   ERREXIT1(tinfo->emethods, "recode_init: No item number %d in file\n", MSGPARM(local_arg->fromitem));
  }
 }

 growing_buf_init(&buf);
 growing_buf_takethis(&buf, args[ARGS_BLOCKS].arg.s);
 growing_buf_init(&tokenbuf);
 growing_buf_allocate(&tokenbuf,0);

 havearg=growing_buf_get_firsttoken(&buf,&tokenbuf);
 while (havearg) {
  nr_of_blocks++;
  havearg=growing_buf_get_nexttoken(&buf,&tokenbuf);
 }

 havearg=growing_buf_get_firsttoken(&buf,&tokenbuf);
 if (!havearg || nr_of_blocks%4!=0) {
  ERREXIT(tinfo->emethods, "recode_init: Number of args must be divisible by 4.\n");
 }
 nr_of_blocks/=4;
 if ((local_arg->blockdefs=(struct blockdef *)malloc(nr_of_blocks*sizeof(struct blockdef)))==NULL) {
  ERREXIT(tinfo->emethods, "recode_init: Error allocating blockdefs memory\n");
 }
 for (inblocks=local_arg->blockdefs, block=0; havearg; block++, inblocks++) {
  inblocks->fromstart=get_value(tokenbuf.buffer_start, NULL); growing_buf_get_nexttoken(&buf,&tokenbuf);
  inblocks->fromend=get_value(tokenbuf.buffer_start, NULL); growing_buf_get_nexttoken(&buf,&tokenbuf);
  inblocks->tostart=get_value(tokenbuf.buffer_start, NULL); growing_buf_get_nexttoken(&buf,&tokenbuf);
  inblocks->toend=get_value(tokenbuf.buffer_start, NULL); havearg=growing_buf_get_nexttoken(&buf,&tokenbuf);
  inblocks->last_block=(block==nr_of_blocks-1);
  if (isnan(inblocks->fromstart) || isnan(inblocks->fromend)) {
   if (!isnan(inblocks->fromstart) || !isnan(inblocks->fromend)) {
    ERREXIT(tinfo->emethods, "recode_init: NaN cannot be mixed in from block!\n");
   }
   if (inblocks->tostart!=inblocks->toend) {
    ERREXIT(tinfo->emethods, "recode_init: NaN can only be recoded to one value!\n");
   }
  }
  if (isnan(inblocks->tostart) || isnan(inblocks->toend)) {
   if (!isnan(inblocks->tostart) || !isnan(inblocks->toend)) {
    ERREXIT(tinfo->emethods, "recode_init: NaN cannot be mixed in to block!\n");
   }
  }
 }
 growing_buf_free(&tokenbuf);
 growing_buf_free(&buf);

 tinfo->methods->init_done=TRUE;
}
示例#14
0
文件: project.c 项目: berndf/avg_q
/*{{{  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;
}
示例#15
0
/* This function has all the knowledge about events in the various file types */
LOCAL void 
read_neurofile_build_trigbuffer(transform_info_ptr tinfo) {
 struct read_neurofile_storage *local_arg=(struct read_neurofile_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;

 if (local_arg->triggers.buffer_start==NULL) {
  growing_buf_allocate(&local_arg->triggers, 0);
 } else {
  growing_buf_clear(&local_arg->triggers);
 }
 if (args[ARGS_TRIGFILE].is_set) {
  FILE * const triggerfile=(strcmp(args[ARGS_TRIGFILE].arg.s,"stdin")==0 ? stdin : fopen(args[ARGS_TRIGFILE].arg.s, "r"));
  TRACEMS(tinfo->emethods, 1, "read_neurofile_build_trigbuffer: Reading event file\n");
  if (triggerfile==NULL) {
   ERREXIT1(tinfo->emethods, "read_neurofile_build_trigbuffer: Can't open trigger file >%s<\n", MSGPARM(args[ARGS_TRIGFILE].arg.s));
  }
  while (TRUE) {
   long trigpoint;
   char *description;
   int const code=read_trigger_from_trigfile(triggerfile, tinfo->sfreq, &trigpoint, &description);
   if (code==0) break;
   push_trigger(&local_arg->triggers, trigpoint, code, description);
   free_pointer((void **)&description);
  }
  if (triggerfile!=stdin) fclose(triggerfile);
 } else {
  TRACEMS(tinfo->emethods, 0, "read_neurofile_build_trigbuffer: No trigger source known.\n");
 }
}
示例#16
0
/*{{{  read_neurofile(transform_info_ptr tinfo) {*/
METHODDEF DATATYPE *
read_neurofile(transform_info_ptr tinfo) {
 struct read_neurofile_storage *local_arg=(struct read_neurofile_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 array myarray;
 FILE *infile=local_arg->infile;
 Bool not_correct_trigger=FALSE;
 long trigger_point, file_start_point, file_end_point;
 char *innamebuf;
 int channel;
 char *description=NULL;

 if (local_arg->epochs--==0) return NULL;
 tinfo->beforetrig=local_arg->beforetrig;
 tinfo->aftertrig=local_arg->aftertrig;
 tinfo->nr_of_points=local_arg->beforetrig+local_arg->aftertrig;
 tinfo->nr_of_channels=local_arg->nr_of_channels;
 tinfo->nrofaverages=1;
 if (tinfo->nr_of_points<=0) {
  ERREXIT1(tinfo->emethods, "read_neurofile: Invalid nr_of_points %d\n", MSGPARM(tinfo->nr_of_points));
 }

 /*{{{  Find the next window that fits into the actual data*/
 /* This is just for the Continuous option (no trigger file): */
 file_end_point=local_arg->current_point-1;
 do {
  if (args[ARGS_CONTINUOUS].is_set) {
   /* Simulate a trigger at current_point+beforetrig */
   file_start_point=file_end_point+1;
   trigger_point=file_start_point+tinfo->beforetrig;
   file_end_point=trigger_point+tinfo->aftertrig-1;
   if (local_arg->points_in_file>0 && file_end_point>=local_arg->points_in_file) return NULL;
   local_arg->current_trigger++;
   local_arg->current_point+=tinfo->nr_of_points;
   tinfo->condition=0;
  } else 
  do {
   tinfo->condition=read_neurofile_read_trigger(tinfo, &trigger_point, &description);
   if (tinfo->condition==0) return NULL;	/* No more triggers in file */
   file_start_point=trigger_point-tinfo->beforetrig+local_arg->offset;
   file_end_point=trigger_point+tinfo->aftertrig-1-local_arg->offset;
   
   if (local_arg->trigcodes==NULL) {
    not_correct_trigger=FALSE;
   } else {
    int trigno=0;
    not_correct_trigger=TRUE;
    while (local_arg->trigcodes[trigno]!=0) {
     if (local_arg->trigcodes[trigno]==tinfo->condition) {
      not_correct_trigger=FALSE;
      break;
     }
     trigno++;
    }
   }
  } while (not_correct_trigger || file_start_point<0 || (local_arg->points_in_file>0 && file_end_point>=local_arg->points_in_file));
 } while (--local_arg->fromepoch>0);
 if (description==NULL) {
  TRACEMS3(tinfo->emethods, 1, "read_neurofile: Reading around tag %d at %d, condition=%d\n", MSGPARM(local_arg->current_trigger), MSGPARM(trigger_point), MSGPARM(tinfo->condition));
 } else {
  TRACEMS4(tinfo->emethods, 1, "read_neurofile: Reading around tag %d at %d, condition=%d, description=%s\n", MSGPARM(local_arg->current_trigger), MSGPARM(trigger_point), MSGPARM(tinfo->condition), MSGPARM(description));
 }

 /*{{{  Handle triggers within the epoch (option -T)*/
 if (args[ARGS_TRIGTRANSFER].is_set) {
  int trigs_in_epoch, code;
  long trigpoint;
  long const old_current_trigger=local_arg->current_trigger;
  char *thisdescription;

  /* First trigger entry holds file_start_point */
  push_trigger(&tinfo->triggers, file_start_point, -1, NULL);
  read_neurofile_reset_triggerbuffer(tinfo);
  for (trigs_in_epoch=1; (code=read_neurofile_read_trigger(tinfo, &trigpoint, &thisdescription))!=0;) {
   if (trigpoint>=file_start_point && trigpoint<=file_end_point) {
    push_trigger(&tinfo->triggers, trigpoint-file_start_point, code, thisdescription);
    trigs_in_epoch++;
   }
  }
  push_trigger(&tinfo->triggers, 0, 0, NULL); /* End of list */
  local_arg->current_trigger=old_current_trigger;
 }
 /*}}}  */

 fseek(infile, file_start_point*tinfo->nr_of_channels, SEEK_SET);

 /*{{{  Configure myarray*/
 myarray.element_skip=tinfo->itemsize=1;
 tinfo->multiplexed=TRUE;
 myarray.nr_of_elements=tinfo->nr_of_channels;
 myarray.nr_of_vectors=tinfo->nr_of_points;
 if (array_allocate(&myarray)==NULL || 
  (tinfo->channelnames=(char **)malloc(tinfo->nr_of_channels*sizeof(char *)))==NULL ||
  (innamebuf=(char *)malloc(local_arg->stringlength))==NULL ||
  (tinfo->comment=(char *)malloc(strlen((char *)local_arg->seq.comment)+(1+17+1)))==NULL) {
  ERREXIT(tinfo->emethods, "read_neurofile: Error allocating data\n");
 }
 /*}}}  */

 sprintf(tinfo->comment, "%s %02d/%02d/%02d,%02d:%02d:%02d", local_arg->seq.comment, local_arg->seq.month, local_arg->seq.day, local_arg->seq.year, local_arg->seq.hour, local_arg->seq.minute, local_arg->seq.second);
 for (channel=0; channel<tinfo->nr_of_channels; channel++) {
  strcpy(innamebuf, (char *)local_arg->seq.elnam[channel]);
  tinfo->channelnames[channel]=innamebuf;
  innamebuf+=strlen(innamebuf)+1;
 }

 do {
  signed char exponent;
  short delta;
  if (fread(&exponent, sizeof(exponent), 1, infile)!=1) {
   ERREXIT(tinfo->emethods, "read_neurofile: Error reading data\n");
  }
  delta=exponent;
  exponent&=0x03;
  if (exponent==0x03) {
   delta>>=2;
  } else {
   delta=(delta&0xfffc)<<(exponent*2);
  }
  local_arg->last_values[myarray.current_element]+=delta;
  array_write(&myarray, local_arg->last_values[myarray.current_element]*local_arg->factor);
 } while (myarray.message!=ARRAY_ENDOFSCAN);
示例#17
0
文件: writeasc.c 项目: berndf/avg_q
/*{{{  writeasc_open_file(transform_info_ptr tinfo) {*/
LOCAL void
writeasc_open_file(transform_info_ptr tinfo) {
    struct writeasc_storage *local_arg=(struct writeasc_storage *)tinfo->methods->local_storage;
    transform_argument *args=tinfo->methods->arguments;
    FILE *outfptr=NULL;
    Bool append_mode=args[ARGS_APPEND].is_set;

    if (strcmp(args[ARGS_OFILE].arg.s, "stdout")==0) outfptr=stdout;
    else if (strcmp(args[ARGS_OFILE].arg.s, "stderr")==0) outfptr=stderr;
    if (append_mode) {
        /*{{{  Append mode open*/
        if (outfptr==NULL) {
            if ((outfptr=fopen(args[ARGS_OFILE].arg.s, "a+b"))==NULL) {
                ERREXIT1(tinfo->emethods, "writeasc_init: Can't append to %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
            }
        }
        fseek(outfptr, 0L, 2);
        /* It is important here to overwrite the append_mode flag only for THIS open
         * operation, because writeasc_open_file will get called repeatedly if -c is
         * also set, and then the file will already be there the second time and we want
         * to append to it... */
        if (ftell(outfptr)==0L) append_mode=FALSE;	/* If at start: write header */
        /*}}}  */
    }
    if (outfptr==NULL) {
        /*{{{  Truncate mode open*/
        if ((outfptr=fopen(args[ARGS_OFILE].arg.s, "wb"))==NULL) {
            ERREXIT1(tinfo->emethods, "writeasc_init: Can't open %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
        }
        /*}}}  */
    }
    local_arg->outfptr=outfptr;
    if (append_mode) {
        /* Don't write header in append mode.
         * Also set the local_arg values to (nearly) impossible numbers in order to
         * force these values to be assigned in the epoch header */
        local_arg->sfreq= -123456789;
        local_arg->beforetrig= -123456789;
        local_arg->leaveright= -123456789;
    } else {
        if (args[ARGS_BINARY].is_set) {
            /*{{{  Write binary header*/
            char outbuf[OUTBUFSIZE], *inoutbuf;
            unsigned short shortbuf=ASC_BF_MAGIC;
            fwrite((void *)&shortbuf, 2, 1, outfptr);
            inoutbuf=outbuf;
            snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Sfreq=%f\n", (float)tinfo->sfreq);
            inoutbuf+=strlen(inoutbuf);
            if (tinfo->beforetrig>0) {
                snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "BeforeTrig=%d\n", tinfo->beforetrig);
                inoutbuf+=strlen(inoutbuf);
            }
            if (tinfo->leaveright>0) {
                snprintf(inoutbuf, OUTBUFSIZE-(inoutbuf-outbuf), "Leaveright=%d\n", tinfo->leaveright);
                inoutbuf+=strlen(inoutbuf);
            }
            shortbuf=inoutbuf-outbuf;
            fwrite((void *)&shortbuf, 2, 1, outfptr);
            fwrite((void *)outbuf, (int)shortbuf, 1, outfptr);
            /*}}}  */
        } else {
            /*{{{  Write ascii header*/
            fprintf(outfptr, "Sfreq=%f\n", (float)tinfo->sfreq);
            if (tinfo->beforetrig>0) fprintf(outfptr, "BeforeTrig=%d\n", tinfo->beforetrig);
            if (tinfo->leaveright>0) fprintf(outfptr, "Leaveright=%d\n", tinfo->leaveright);
            /*}}}  */
        }
        local_arg->sfreq=tinfo->sfreq;
        local_arg->beforetrig=tinfo->beforetrig;
        local_arg->leaveright=tinfo->leaveright;
    }
}
示例#18
0
GLOBAL struct source_desc *
var_random_srcmodule(transform_info_ptr tinfo, char **args) {
    int n_harmonics, n_noisedips, i, n_dipoles;
    char **inargs=args;
    DATATYPE *memptr;
    float random_pos=0.0, random_moment=0.0;
    double freq_default=0.1;
    struct source_desc *sourcep;
    struct dipole_desc *dipolep;

    if (args==(char **)NULL) {
        ERREXIT(tinfo->emethods, "var_random_srcmodule: Usage: var_random_dipoles ( n_harmonics n_noisedips )\n");
    }
    if (*inargs!=NULL) n_harmonics=atoi(*inargs++);
    if (*inargs!=NULL) n_noisedips=atoi(*inargs++);
    if (inargs-args!=2) {
        ERREXIT(tinfo->emethods, "var_random_srcmodule: Need at least two arguments ( n_harmonics n_noisedips )\n");
    }
    n_dipoles=n_harmonics+n_noisedips;
    if ((sourcep=(struct source_desc *)malloc(sizeof(struct source_desc)+(sizeof(struct dipole_desc)+3*3*sizeof(DATATYPE))*n_dipoles))==NULL) {
        ERREXIT(tinfo->emethods, "var_random_srcmodule: Error allocating memory\n");
    }
    sourcep->nrofsources=n_dipoles;
    dipolep=sourcep->dipoles=(struct dipole_desc *)(sourcep+1);
    memptr=(DATATYPE *)(dipolep+n_dipoles);
    for (i=0; i<n_dipoles; i++, dipolep++, memptr+=9) {
        dipolep->position.start=memptr;
        dipolep->dip_moment.start=memptr+3;
        dipolep->initial_moment.start=memptr+6;
        /*{{{  Read switchable options: FREQ_DEFAULT, RANDOM_POS, RANDOM_MOMENT keyword*/
        if (*inargs!=NULL && strcmp(*inargs, "FREQ_DEFAULT")==0) {
            if (*++inargs!=NULL) {
                freq_default=atof(*inargs);
                inargs++;
            }
        }
        if (*inargs!=NULL && strcmp(*inargs, "RANDOM_POS")==0) {
            if (*++inargs!=NULL) {
                random_pos=atof(*inargs);
                inargs++;
            }
        }
        if (*inargs!=NULL && strcmp(*inargs, "RANDOM_MOMENT")==0) {
            if (*++inargs!=NULL) {
                random_moment=atof(*inargs);
                inargs++;
            }
        }
        /*}}}  */
        dipolep->position.nr_of_elements=dipolep->dip_moment.nr_of_elements=dipolep->initial_moment.nr_of_elements=3;
        dipolep->position.nr_of_vectors=dipolep->dip_moment.nr_of_vectors=dipolep->initial_moment.nr_of_vectors=1;
        dipolep->position.element_skip=dipolep->dip_moment.element_skip=dipolep->initial_moment.element_skip=1;
        dipolep->position.vector_skip=dipolep->dip_moment.vector_skip=dipolep->initial_moment.vector_skip=3;
        array_setreadwrite(&dipolep->position);
        array_setreadwrite(&dipolep->dip_moment);
        array_setreadwrite(&dipolep->initial_moment);
        array_reset(&dipolep->position);
        array_reset(&dipolep->dip_moment);
        array_reset(&dipolep->initial_moment);
        /* The parameter is the frequency relative to half the sampling frequency: */
        dipolep->time[1]=M_PI*readval(tinfo, &inargs, freq_default);
        if (dipolep->time[1]<=0) {
            ERREXIT1(tinfo->emethods, "var_random_srcmodule: Frequency==%d\n", MSGPARM(dipolep->time[1]));
        }
        if (random_pos>0.0) {
            float x, y, z;
            sphere_random(random_pos, &x, &y, &z);
            array_write(&dipolep->position, readval(tinfo, &inargs, x));
            array_write(&dipolep->position, readval(tinfo, &inargs, y));
            array_write(&dipolep->position, readval(tinfo, &inargs, z));
        } else {
            array_write(&dipolep->position, readval(tinfo, &inargs, 1));
            array_write(&dipolep->position, readval(tinfo, &inargs, 1));
            array_write(&dipolep->position, readval(tinfo, &inargs, 7.5));
        }
        if (random_moment>0.0) {
            float x, y, z;
            sphere_random(random_moment, &x, &y, &z);
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, x));
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, y));
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, z));
        } else {
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, 1));
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, 0));
            array_write(&dipolep->dip_moment, readval(tinfo, &inargs, 0));
        }
        if (i<n_harmonics) {
            /*{{{  Set harmonic behaviour*/
            dipolep->time_function_init= &harmonic_time_init;
            dipolep->time_function= &harmonic_time;
            dipolep->time_function_exit= &harmonic_time_exit;
            /*}}}  */
        } else {
            /*{{{  Set noise behaviour*/
            dipolep->time_function_init= &noise_time_init;
            dipolep->time_function= &noise_time;
            dipolep->time_function_exit= &noise_time_exit;
            /*}}}  */
        }
    }

    return sourcep;
}
示例#19
0
文件: project.c 项目: berndf/avg_q
/*{{{  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;
}
示例#20
0
/* This function not only seeks to the specified point, but also reads
 * the point into the buffer if necessary. The get_singlepoint function
 * then only transfers the data. */
LOCAL void
read_synamps_seek_point(transform_info_ptr tinfo, long point) {
 struct read_synamps_storage *local_arg=(struct read_synamps_storage *)tinfo->methods->local_storage;

 switch(local_arg->SubType) {
  case NST_CONT0:
  case NST_DCMES:
  case NST_CONTINUOUS:
  case NST_SYNAMPS: {
   /*{{{  */
   const int points_per_buf=local_arg->EEG.ChannelOffset/local_arg->bytes_per_sample; /* Note a value of 1 is fixed in read_synamps_init */
   long const buffer_boundary=(point/points_per_buf)*points_per_buf;
   long const new_last_point_in_buffer=buffer_boundary+points_per_buf-1;
   /* This format is neither points fastest nor channels fastest, but
    * points fastest in blocks. No idea why they didn't do channels fastest,
    * it would have rendered the whole file in one order, no matter what buffer
    * size is used internally in programs. This way we MUST use the given buffers. */
   if (new_last_point_in_buffer!=local_arg->last_point_in_buffer) {
    fseek(local_arg->SCAN,point2offset(tinfo,buffer_boundary),SEEK_SET);
    if (fread(local_arg->buffer,1,local_arg->BufferCount,local_arg->SCAN)!=local_arg->BufferCount) {
     ERREXIT(tinfo->emethods, "read_synamps_seek_point: Error reading data\n");
    }
    local_arg->first_point_in_buffer=buffer_boundary;
    local_arg->last_point_in_buffer=new_last_point_in_buffer;
    /*{{{  Swap byte order if necessary*/
#    ifndef LITTLE_ENDIAN
    {uint16_t *pdata=(uint16_t *)local_arg->buffer, *p_end=(uint16_t *)((char *)local_arg->buffer+local_arg->BufferCount);
     while (pdata<p_end) Intel_int16(pdata++);
    }
#    endif
    /*}}}  */
   }
   /*}}}  */
  }
  break;
 default:
  ERREXIT1(tinfo->emethods, "read_synamps_seek_point: Format `%s' is not yet supported\n", MSGPARM(neuroscan_subtype_names[local_arg->SubType]));
  break;
 }
 local_arg->current_point=point;
}
示例#21
0
/*{{{  read_synamps_get_singlepoint(transform_info_ptr tinfo, array *toarray) {*/
LOCAL int
read_synamps_get_singlepoint(transform_info_ptr tinfo, array *toarray) {
 struct read_synamps_storage *local_arg=(struct read_synamps_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;

 if (local_arg->current_point>=local_arg->EEG.NumSamples) return -1;
 read_synamps_seek_point(tinfo, local_arg->current_point);
 switch(local_arg->SubType) {
  case NST_DCMES: {
   /* DC-MES data is unsigned, and the marker channel is skipped: */
   unsigned short *pdata=(unsigned short *)local_arg->buffer+local_arg->current_point-local_arg->first_point_in_buffer+1;
   int channel=0;
   do {
    *pdata^=0x8000;	/* Exclusive or to convert to signed... */
    if (args[ARGS_NOBADCHANS].is_set && local_arg->Channels[channel].bad) {
     toarray->message=ARRAY_CONTINUE;
    } else {
     array_write(toarray, NEUROSCAN_CONVSHORT(&local_arg->Channels[channel], *((signed short *)pdata)));
    }
    pdata+=local_arg->EEG.ChannelOffset/local_arg->bytes_per_sample;
    channel++;
   } while (toarray->message==ARRAY_CONTINUE);
  }
   break;
  case NST_CONT0:
  case NST_CONTINUOUS:
  case NST_SYNAMPS: {
   int channel=0;
   do {
    DATATYPE val;
    if (args[ARGS_NOBADCHANS].is_set && local_arg->Channels[channel].bad) {
     toarray->message=ARRAY_CONTINUE;
    } else {
     if (local_arg->bytes_per_sample==2) {
      int16_t * const pdata=((int16_t *)local_arg->buffer)+local_arg->current_point-local_arg->first_point_in_buffer+channel;
#   ifndef LITTLE_ENDIAN
      Intel_int16(pdata);
#   endif
      val=NEUROSCAN_CONVSHORT(&local_arg->Channels[channel],*pdata);
     } else if (local_arg->bytes_per_sample==4) {
      int32_t * const pdata=((int32_t *)local_arg->buffer)+local_arg->current_point-local_arg->first_point_in_buffer+channel;
#   ifndef LITTLE_ENDIAN
      Intel_int32(pdata);
#   endif
      val=NEUROSCAN_CONVSHORT(&local_arg->Channels[channel],*pdata);
     } else {
      ERREXIT(tinfo->emethods, "read_synamps: Unknown bytes_per_sample\n");
     }
     array_write(toarray, val);
    }
    channel++;
   } while (toarray->message==ARRAY_CONTINUE);
  }
   break;
  default:
   ERREXIT1(tinfo->emethods, "read_synamps_get_singlepoint: Format `%s' is not yet supported\n", MSGPARM(neuroscan_subtype_names[local_arg->SubType]));
   break;
 }
 local_arg->current_point++;
 return 0;
}
示例#22
0
/* This subroutine encapsulates the coding of the different event codes
 * into a unified signed code */
LOCAL void
read_synamps_push_keys(transform_info_ptr tinfo, long position, int TrigVal, int KeyPad, int KeyBoard, enum NEUROSCAN_ACCEPTVALUES Accept) {
 struct read_synamps_storage * const local_arg=(struct read_synamps_storage *)tinfo->methods->local_storage;
 int code;
 if (Accept!=0 && (Accept<NAV_DCRESET || Accept>NAV_STARTSTOP)) {
  TRACEMS2(tinfo->emethods, 0, "read_synamps_push_keys: Unknown Accept value %d at position %d!\n", MSGPARM(Accept), MSGPARM(position));
  return;
 }
 code=TrigVal-KeyPad+neuroscan_accept_translation[Accept];
 if (code==0) {
  /* At least in Edit 4.x, KeyPad F2 is written as KeyBoard=0 with everything else 0 too... */
  code= -(((KeyBoard&0xf)+1)<<4);
 }
 if (code==0) {
  TRACEMS1(tinfo->emethods, 0, "read_synamps_push_keys: Trigger with trigcode 0 at position %d!\n", MSGPARM(position));
 } else {
  push_trigger(&local_arg->triggers, position, code, NULL);
 }
}
示例#23
0
/*{{{  write_synamps_exit(transform_info_ptr tinfo) {*/
METHODDEF void
write_synamps_exit(transform_info_ptr tinfo) {
 struct write_synamps_storage *local_arg=(struct write_synamps_storage *)tinfo->methods->local_storage;
#define SETUP_OFFSET_NSWEEPS 360
#define SETUP_OFFSET_NUMSAMPLES 864
#define SETUP_OFFSET_EVENTTABLEPOS 886

 /* Apparently NeuroScan write this even for epoched files although there's no event table there... 
  * It is important there to compute bytes_per_sample */
 local_arg->EEG.EventTablePos=ftell(local_arg->SCAN);
 if (local_arg->output_format==FORMAT_CNTFILE) {
  TEEG TagType;
  EVENT1 event;
  int const nevents=local_arg->triggers.current_length/sizeof(struct trigger);
  int n;

  TagType.Teeg=TEEG_EVENT_TAB1;
  TagType.Size=(nevents+1)*sm_EVENT1[0].offset;	/* sm_EVENT1[0].offset is sizeof(EVENT1) in the file. */
  TagType.p_o.Offset=0L;
# ifndef LITTLE_ENDIAN
  change_byteorder((char *)&TagType, sm_TEEG);
# endif
  write_struct((char *)&TagType, sm_TEEG, local_arg->SCAN);

  for (n=0; n<nevents; n++) {
   struct trigger * const intrig=((struct trigger *)local_arg->triggers.buffer_start)+n;
   int acc=NAV_STARTSTOP, type=0, resp=0, keyboard=0;
   while (acc>=0 && intrig->code!=neuroscan_accept_translation[acc]) acc--;
   if (acc<0) {
    acc=0;
    if (intrig->code>0) {
     type=intrig->code;
    } else {
     resp=(-intrig->code)&0xf;
     if (resp==0) {
      keyboard=(-intrig->code)>>4;
      if (keyboard==0) {
       TRACEMS1(tinfo->emethods, 1, "write_synamps_exit: Can't decipher event code %d\n", MSGPARM(intrig->code));
      } else {
       keyboard--;
      }
     }
    }
   }
示例#24
0
/*{{{  read_neurofile_init(transform_info_ptr tinfo) {*/
METHODDEF void
read_neurofile_init(transform_info_ptr tinfo) {
 struct read_neurofile_storage *local_arg=(struct read_neurofile_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 int channel;
 FILE *dsc;
#ifdef __GNUC__
 char filename[strlen(args[ARGS_IFILE].arg.s)+5];
#else
 char filename[MAX_PATHLEN];
#endif

 growing_buf_init(&local_arg->triggers);

 strcpy(filename, args[ARGS_IFILE].arg.s);
 strcat(filename, ".dsc");
 if((dsc=fopen(filename, "rb"))==NULL) {
  ERREXIT1(tinfo->emethods, "read_neurofile_init: Can't open dsc file >%s<\n", MSGPARM(filename));
 }
 if (read_struct((char *)&local_arg->seq, sm_sequence, dsc)==0) {
  ERREXIT1(tinfo->emethods, "read_neurofile_init: Can't read header in file >%s<\n", MSGPARM(filename));
 }
 fclose(dsc);
#ifndef LITTLE_ENDIAN
 change_byteorder((char *)&local_arg->seq, sm_sequence);
#endif
 local_arg->points_in_file = 256L*local_arg->seq.length;
 tinfo->points_in_file=local_arg->points_in_file;
 tinfo->sfreq=local_arg->sfreq=neurofile_map_sfreq(local_arg->seq.fastrate);
 local_arg->nr_of_channels=local_arg->seq.nfast;
 local_arg->factor=local_arg->seq.gain/1000.0;
 local_arg->stringlength=0;
 for (channel=0; channel<local_arg->nr_of_channels; channel++) {
  local_arg->stringlength+=strlen((char *)local_arg->seq.elnam[channel])+1;
 }

 /*{{{  Process options*/
 local_arg->fromepoch=(args[ARGS_FROMEPOCH].is_set ? args[ARGS_FROMEPOCH].arg.i : 1);
 local_arg->epochs=(args[ARGS_EPOCHS].is_set ? args[ARGS_EPOCHS].arg.i : -1);
 /*}}}  */
 /*{{{  Parse arguments that can be in seconds*/
 local_arg->beforetrig=tinfo->beforetrig=gettimeslice(tinfo, args[ARGS_BEFORETRIG].arg.s);
 local_arg->aftertrig=tinfo->aftertrig=gettimeslice(tinfo, args[ARGS_AFTERTRIG].arg.s);
 local_arg->offset=(args[ARGS_OFFSET].is_set ? gettimeslice(tinfo, args[ARGS_OFFSET].arg.s) : 0);
 /*}}}  */

 strcpy(filename+strlen(args[ARGS_IFILE].arg.s), ".eeg");
 if((local_arg->infile=fopen(filename, "rb"))==NULL) {
  ERREXIT1(tinfo->emethods, "read_neurofile_init: Can't open file >%s<\n", MSGPARM(filename));
 }
 if ((local_arg->last_values=(DATATYPE *)calloc(local_arg->nr_of_channels, sizeof(DATATYPE)))==NULL) {
  ERREXIT(tinfo->emethods, "read_neurofile_init: Error allocating last_values memory\n");
 }

 local_arg->trigcodes=NULL;
 if (!args[ARGS_CONTINUOUS].is_set) {
  /* The actual trigger file is read when the first event is accessed! */
  if (args[ARGS_TRIGLIST].is_set) {
   local_arg->trigcodes=get_trigcode_list(args[ARGS_TRIGLIST].arg.s);
   if (local_arg->trigcodes==NULL) {
    ERREXIT(tinfo->emethods, "read_neurofile_init: Error allocating triglist memory\n");
   }
  }
 } else {
  if (local_arg->aftertrig==0) {
   /* Continuous mode: If aftertrig==0, automatically read up to the end of file */
   if (local_arg->points_in_file==0) {
    ERREXIT(tinfo->emethods, "read_neurofile: Unable to determine the number of samples in the input file!\n");
   }
   local_arg->aftertrig=local_arg->points_in_file-local_arg->beforetrig;
  }
 }

 read_neurofile_reset_triggerbuffer(tinfo);
 local_arg->current_trigger=0;
 local_arg->current_point=0;

 tinfo->filetriggersp=&local_arg->triggers;

 tinfo->methods->init_done=TRUE;
}
示例#25
0
/*{{{  write_synamps_init(transform_info_ptr tinfo) {*/
METHODDEF void
write_synamps_init(transform_info_ptr tinfo) {
 struct write_synamps_storage *local_arg=(struct write_synamps_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 double xmin, xmax, ymin, ymax;
 int NoOfChannels=tinfo->nr_of_channels;
 int channel;

 growing_buf_init(&local_arg->triggers);
 local_arg->output_format=(args[ARGS_OUTPUTFORMAT].is_set ? (enum output_formats)args[ARGS_OUTPUTFORMAT].arg.i : FORMAT_EEGFILE);
 local_arg->SCAN=fopen(args[ARGS_OFILE].arg.s, "r+b");
 if (!args[ARGS_APPEND].is_set || local_arg->SCAN==NULL) {   /* target does not exist*/
 /*{{{  Create file*/
 if (local_arg->SCAN!=NULL) fclose(local_arg->SCAN);
 /*{{{  Calculate the span in x-y channel positions*/
 xmin=ymin=  FLT_MAX; 
 xmax=ymax= -FLT_MAX; 
 for (channel=0; channel<tinfo->nr_of_channels; channel++) {
  const double this_x=tinfo->probepos[3*channel], this_y=tinfo->probepos[3*channel+1];
  if (this_x>xmax) xmax=this_x;
  if (this_x<xmin) xmin=this_x;
  if (this_y>ymax) ymax=this_y;
  if (this_y<ymin) ymin=this_y;
 }
 if (xmax==xmin) {
  xmax+=0.5;
  xmin-=0.5;
 }
 if (ymax==ymin) {
  ymax+=0.5;
  ymin-=0.5;
 }
 /*}}}  */

 if ((local_arg->SCAN=fopen(args[ARGS_OFILE].arg.s, "wb"))==NULL) {
  ERREXIT1(tinfo->emethods, "write_synamps_init: Can't open %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
 }
 /*{{{  Many settings, taken from example files...*/
 strcpy(local_arg->EEG.rev, "Version 3.0");
 local_arg->EEG.AdditionalFiles=local_arg->EEG.NextFile=local_arg->EEG.PrevFile=0;
 switch (local_arg->output_format) {
  case FORMAT_EEGFILE:
   local_arg->EEG.review = 1;
   local_arg->EEG.savemode=NSM_EEGF;
   local_arg->EEG.type = NTY_EPOCHED;
   local_arg->EEG.ContinousType=0;
   local_arg->EEG.nsweeps=local_arg->EEG.compsweeps=local_arg->EEG.acceptcnt=0;
   break;
  case FORMAT_CNTFILE:
   local_arg->EEG.review = 1;
   local_arg->EEG.savemode=NSM_CONT;
   local_arg->EEG.type = 0;
   local_arg->EEG.ContinousType=NST_SYNAMPS-NST_CONT0;
   local_arg->EEG.nsweeps=1;
   local_arg->EEG.compsweeps=local_arg->EEG.acceptcnt=0;
   break;
  case FORMAT_AVGFILE:
   local_arg->EEG.review = 0;
   local_arg->EEG.savemode=NSM_AVGD;
   local_arg->EEG.type = NTY_AVERAGED;
   local_arg->EEG.ContinousType=0;
   local_arg->EEG.nsweeps=local_arg->EEG.compsweeps=local_arg->EEG.acceptcnt=(tinfo->nrofaverages>0 ? tinfo->nrofaverages : 1);
   break;
 }
 /* Since the comment can be of arbitrary length and thus also larger than the
  * rest of the header, we should limit ourselves to the size of the id field */
 strncpy(local_arg->EEG.id, tinfo->comment, sizeof(local_arg->EEG.id));
 /* The date is coded in the comment, and read_synamps appends the date and time
  * from the corresponding fields and the contents of the id field, so that
  * the comment2time reader could be confused by the two date/time fields if we
  * would not somehow invalidate remnants of the date field here... */
 {char *slash;
  while ((slash=strchr(local_arg->EEG.id, '/'))!=NULL) {
   *slash='|';
  }
 }
 strcpy(local_arg->EEG.oper, "Unspecified");
 strcpy(local_arg->EEG.doctor, "Unspecified");
 strcpy(local_arg->EEG.referral, "Unspecified");
 strcpy(local_arg->EEG.hospital, "Unspecified");
 strcpy(local_arg->EEG.patient, "Unspecified");
 local_arg->EEG.age = 0;
 local_arg->EEG.sex = 'U';
 local_arg->EEG.hand = 'U';
 strcpy(local_arg->EEG.med, "Unspecified");
 strcpy(local_arg->EEG.category, "Unspecified");
 strcpy(local_arg->EEG.state, "Unspecified");
 strcpy(local_arg->EEG.label, "Unspecified");
 {short dd, mm, yy, yyyy, hh, mi, ss;
 if (comment2time(tinfo->comment, &dd, &mm, &yy, &yyyy, &hh, &mi, &ss)) {
  char buffer[16]; /* Must be long enough to fit date (10) and time (12) +1 */
  /* This is necessary because the date field was devised for 2-digit years.
   * With 4-digit years it uses all 10 bytes and the trailing zero
   * does not fit in any more. */
  snprintf(buffer, 16, "%02d/%02d/%04d", mm, dd, yyyy);
  strncpy(local_arg->EEG.date, buffer, sizeof(local_arg->EEG.date));
  snprintf(buffer, 16, "%02d:%02d:%02d", hh, mi, ss);
  strncpy(local_arg->EEG.time, buffer, sizeof(local_arg->EEG.time));
 }
 }
 local_arg->EEG.rejectcnt = 0;
 local_arg->EEG.pnts=(tinfo->data_type==FREQ_DATA ? tinfo->nroffreq : tinfo->nr_of_points);
 local_arg->EEG.nchannels=NoOfChannels;
 local_arg->EEG.avgupdate=1;
 local_arg->EEG.domain=(tinfo->data_type==FREQ_DATA ? 1 : 0);
 local_arg->EEG.variance=0;
 local_arg->EEG.rate=(uint16_t)rint(tinfo->sfreq);
 if (tinfo->data_type==FREQ_DATA) {
  /* I know that this field is supposed to contain the taper window size in %,
     but we need some way to store basefreq and 'rate' is only integer... */
  local_arg->EEG.SpectWinLength=tinfo->basefreq;
 }
 if (local_arg->EEG.rate==0) {
  local_arg->EEG.rate=1;
  TRACEMS(tinfo->emethods, 0, "write_synamps_init: Rate was zero, corrected to 1!\n");
 }
 local_arg->EEG.scale=3.4375;	/* This is a common sensitivity factor, used if sensitivities for channels are zero */
 local_arg->EEG.veogcorrect=0;
 local_arg->EEG.heogcorrect=0;
 local_arg->EEG.aux1correct=0;
 local_arg->EEG.aux2correct=0;
 local_arg->EEG.veogtrig=15;	/* Trigger threshold in percent of the maximum */
 local_arg->EEG.heogtrig=10;
 local_arg->EEG.aux1trig=10;
 local_arg->EEG.aux2trig=10;
 local_arg->EEG.veogchnl=find_channel_number(tinfo, "VEOG");
 local_arg->EEG.heogchnl=find_channel_number(tinfo, "HEOG");
 local_arg->EEG.veogdir=0;	/* 0=positive, 1=negative */
 local_arg->EEG.veog_n=10;	/* "Number of points per waveform", really: minimum acceptable # averages */
 local_arg->EEG.heog_n=10;
 local_arg->EEG.veogmaxcnt=(int16_t)rint(0.3*tinfo->sfreq);	/* "Number of observations per point", really: event window size in points */
 local_arg->EEG.heogmaxcnt=(int16_t)rint(0.5*tinfo->sfreq);
 local_arg->EEG.AmpSensitivity=10;	/* External Amplifier gain */
 local_arg->EEG.baseline=0;
 local_arg->EEG.reject=0;
 local_arg->EEG.trigtype=2;	/* 2=Port */
 local_arg->EEG.trigval=255;	/* Hold */
 local_arg->EEG.dir=0;	/* Invert (negative up)=0 */
 local_arg->EEG.dispmin= -1;	/* displayed y range */
 local_arg->EEG.dispmax= +1;
 local_arg->EEG.DisplayXmin=local_arg->EEG.AutoMin=local_arg->EEG.rejstart=local_arg->EEG.offstart=local_arg->EEG.xmin= -tinfo->beforetrig/tinfo->sfreq;
 local_arg->EEG.DisplayXmax=local_arg->EEG.AutoMax=local_arg->EEG.rejstop=local_arg->EEG.offstop=local_arg->EEG.xmax= tinfo->aftertrig/tinfo->sfreq;
 local_arg->EEG.zmin=0.0;
 local_arg->EEG.zmax=0.1;
 strcpy(local_arg->EEG.ref, "A1-A2");
 strcpy(local_arg->EEG.screen,   "--------");
 local_arg->EEG.CalMode=2;
 local_arg->EEG.CalMethod=0;
 local_arg->EEG.CalUpdate=1;
 local_arg->EEG.CalBaseline=0;
 local_arg->EEG.CalSweeps=5;
 local_arg->EEG.CalAttenuator=1;
 local_arg->EEG.CalPulseVolt=1;
 local_arg->EEG.CalPulseStart=0;
 local_arg->EEG.CalPulseStop=0;
 local_arg->EEG.CalFreq=10;
 strcpy(local_arg->EEG.taskfile, "--------");
 strcpy(local_arg->EEG.seqfile,  "--------");	/* Otherwise tries to read a seqfile */
 local_arg->EEG.HeadGain=150;
 local_arg->EEG.FspFValue=2.5;
 local_arg->EEG.FspBlockSize=200;
 local_arg->EEG.fratio=1.0;
 local_arg->EEG.minor_rev=12;	/* Necessary ! Otherwise a different file structure is assumed... */
 local_arg->EEG.eegupdate=1;

 local_arg->EEG.xscale=local_arg->EEG.yscale=0;
 local_arg->EEG.xsize=40;
 local_arg->EEG.ysize=20;
 local_arg->EEG.ACmode=0;

 local_arg->EEG.XScaleValue=XSCALEVALUE;
 local_arg->EEG.XScaleInterval=XSCALEINTERVAL;
 local_arg->EEG.YScaleValue=YSCALEVALUE;
 local_arg->EEG.YScaleInterval=YSCALEINTERVAL;

 local_arg->EEG.ScaleToolX1=20;
 local_arg->EEG.ScaleToolY1=170;
 local_arg->EEG.ScaleToolX2=23.1535;
 local_arg->EEG.ScaleToolY2=153.87;

 local_arg->EEG.port=715;
 local_arg->EEG.NumSamples=0;
 local_arg->EEG.FilterFlag=0;
 local_arg->EEG.LowCutoff=4;
 local_arg->EEG.LowPoles=2;
 local_arg->EEG.HighCutoff=50;
 local_arg->EEG.HighPoles=2;
 local_arg->EEG.FilterType=3;
 local_arg->EEG.FilterDomain=1;
 local_arg->EEG.SnrFlag=0;
 local_arg->EEG.CoherenceFlag=0;
 local_arg->EEG.ContinousSeconds=4;
 local_arg->EEG.ChannelOffset=sizeof(int16_t);
 local_arg->EEG.AutoCorrectFlag=0;
 local_arg->EEG.DCThreshold='F';
 /*}}}  */
 /*{{{  Write SETUP structure*/
# ifndef LITTLE_ENDIAN
 change_byteorder((char *)&local_arg->EEG, sm_SETUP);
# endif
 write_struct((char *)&local_arg->EEG, sm_SETUP, local_arg->SCAN);
# ifndef LITTLE_ENDIAN
 change_byteorder((char *)&local_arg->EEG, sm_SETUP);
# endif
 /*}}}  */

 if ((local_arg->Channels=(ELECTLOC *)calloc(NoOfChannels,sizeof(ELECTLOC)))==NULL) {
  ERREXIT(tinfo->emethods, "write_synamps_init: Error allocating Channels list\n");
 }
 for (channel=0; channel<NoOfChannels; channel++) {
  /*{{{  Settings in the channel structure*/
  strncpy(local_arg->Channels[channel].lab, tinfo->channelnames[channel],sizeof(local_arg->Channels[channel].lab));
  local_arg->Channels[channel].reference=0;
  local_arg->Channels[channel].skip=0;
  local_arg->Channels[channel].reject=0;
  local_arg->Channels[channel].display=1;
  local_arg->Channels[channel].bad=0;
  local_arg->Channels[channel].n=(local_arg->output_format==FORMAT_AVGFILE ? local_arg->EEG.acceptcnt : (local_arg->output_format==FORMAT_CNTFILE ? 0 : 1));
  local_arg->Channels[channel].avg_reference=0;
  local_arg->Channels[channel].ClipAdd=0;
  local_arg->Channels[channel].x_coord= (tinfo->probepos[3*channel  ]-xmin)/(xmax-xmin)*RANGE_TO_COVER+XOFFSET;
  local_arg->Channels[channel].y_coord=((ymax-tinfo->probepos[3*channel+1])/(ymax-ymin)*RANGE_TO_COVER+YOFFSET)/3;
  local_arg->Channels[channel].veog_wt=0;
  local_arg->Channels[channel].veog_std=0;
  local_arg->Channels[channel].heog_wt=0;
  local_arg->Channels[channel].heog_std=0;
  local_arg->Channels[channel].baseline=0;
  local_arg->Channels[channel].Filtered=0;
  local_arg->Channels[channel].sensitivity=204.8/args[ARGS_CONVFACTOR].arg.d; /* This arranges for conv_factor to act as the expected product before integer truncation */
  local_arg->Channels[channel].Gain=5;
  local_arg->Channels[channel].HiPass=0;	/* 0=DC */
  local_arg->Channels[channel].LoPass=4;
  local_arg->Channels[channel].Page=0;
  local_arg->Channels[channel].Size=0;
  local_arg->Channels[channel].Impedance=0;
  local_arg->Channels[channel].PhysicalChnl=channel;	/* Channel mapping */
  local_arg->Channels[channel].Rectify=0;
  local_arg->Channels[channel].calib=1.0;
  /*}}}  */
  /*{{{  Write ELECTLOC struct*/
#  ifndef LITTLE_ENDIAN
  change_byteorder((char *)&local_arg->Channels[channel], sm_ELECTLOC);
#  endif
  write_struct((char *)&local_arg->Channels[channel], sm_ELECTLOC, local_arg->SCAN);
#  ifndef LITTLE_ENDIAN
  change_byteorder((char *)&local_arg->Channels[channel], sm_ELECTLOC);
#  endif
  /*}}}  */
 }
 local_arg->SizeofHeader = ftell(local_arg->SCAN);
 TRACEMS2(tinfo->emethods, 1, "write_synamps_init: Creating file %s, format `%s'\n", MSGPARM(args[ARGS_OFILE].arg.s), MSGPARM(neuroscan_subtype_names[NEUROSCAN_SUBTYPE(&local_arg->EEG)]));
 /*}}}  */
 } else {
  /*{{{  Append to file*/
  enum NEUROSCAN_SUBTYPES SubType;
  if (read_struct((char *)&local_arg->EEG, sm_SETUP, local_arg->SCAN)==0) {
   ERREXIT(tinfo->emethods, "write_synamps_init: Can't read file header.\n");
  }
#  ifndef LITTLE_ENDIAN
  change_byteorder((char *)&local_arg->EEG, sm_SETUP);
#  endif
  NoOfChannels = local_arg->EEG.nchannels;
  /*{{{  Allocate channel header*/
  if ((local_arg->Channels=(ELECTLOC *)malloc(NoOfChannels*sizeof(ELECTLOC)))==NULL) {
   ERREXIT(tinfo->emethods, "write_synamps_init: Error allocating Channels list\n");
  }
  /*}}}  */
  for (channel=0; channel<NoOfChannels; channel++) {
   if (read_struct((char *)&local_arg->Channels[channel], sm_ELECTLOC, local_arg->SCAN)==0) {
    ERREXIT(tinfo->emethods, "write_synamps_init: Can't read channel headers.\n");
   }
#  ifndef LITTLE_ENDIAN
   change_byteorder((char *)&local_arg->Channels[channel], sm_ELECTLOC);
#  endif
  }
  local_arg->SizeofHeader = ftell(local_arg->SCAN);
  SubType=NEUROSCAN_SUBTYPE(&local_arg->EEG);
  switch (SubType) {
   case NST_EPOCHS:
    if (local_arg->output_format!=FORMAT_EEGFILE) {
     TRACEMS(tinfo->emethods, 0, "write_synamps_init: Appending to epoch file, discarding option -c\n");
     local_arg->output_format=FORMAT_EEGFILE;
    }
    fseek(local_arg->SCAN, 0, SEEK_END);
    break;
   case NST_CONTINUOUS:
   case NST_SYNAMPS: {
    TEEG TagType;
    EVENT1 event;
    if (local_arg->output_format!=FORMAT_CNTFILE) {
     TRACEMS(tinfo->emethods, 0, "write_synamps_init: Appending to continuous file, assuming option -c\n");
     local_arg->output_format=FORMAT_CNTFILE;
    }
    fseek(local_arg->SCAN, local_arg->EEG.EventTablePos, SEEK_SET);
    /* Here we face two evils in one header: Coding enums as chars and
     * allowing longs at odd addresses. Well... */
    if (1==read_struct((char *)&TagType, sm_TEEG, local_arg->SCAN)) {
#    ifndef LITTLE_ENDIAN
     change_byteorder((char *)&TagType, sm_TEEG);
#    endif
     if (TagType.Teeg==TEEG_EVENT_TAB1) {
      /*{{{  Read the event table*/
      int tag;
      int const ntags=TagType.Size/sm_EVENT1[0].offset;	/* sm_EVENT1[0].offset is sizeof(EVENT1) in the file. */
      for (tag=0; tag<ntags; tag++) {
       if (1!=read_struct((char *)&event, sm_EVENT1, local_arg->SCAN)) {
	ERREXIT(tinfo->emethods, "write_synamps_init: Can't read an event table entry.\n");
	break;
       }
#      ifndef LITTLE_ENDIAN
       change_byteorder((char *)&event, sm_EVENT1);
#      endif
       {
       int const TrigVal=event.StimType &0xff;
       int const KeyBoard=event.KeyBoard&0xf;
       int const KeyPad=Event_KeyPad_value(event);
       int const Accept=Event_Accept_value(event);
       int code=TrigVal-KeyPad+neuroscan_accept_translation[Accept];
       if (code==0) {
        code= -((KeyBoard+1)<<4);
       }
       push_trigger(&local_arg->triggers,offset2point(tinfo, event.Offset),code,NULL);
       }
      }
      /*}}}  */
     } else {
      ERREXIT(tinfo->emethods, "write_synamps_init: Type 2 events are not yet supported.\n");
     }
    } else {
     ERREXIT(tinfo->emethods, "write_synamps_init: Can't read the event table header.\n");
    }
    fseek(local_arg->SCAN, local_arg->EEG.EventTablePos, SEEK_SET);
    }
    break;
   default:
    ERREXIT1(tinfo->emethods, "write_synamps: Cannot append to file type `%s'\n", MSGPARM(neuroscan_subtype_names[SubType]));
    break;
  }
  /* Conformance to the incoming epochs is checked in write_synamps */
  TRACEMS1(tinfo->emethods, 1, "write_synamps_init: Appending to file %s\n", MSGPARM(args[ARGS_OFILE].arg.s));
  /*}}}  */
 }

 tinfo->methods->init_done=TRUE;
}
示例#26
0
/* This function has all the knowledge about events in the various file types */
LOCAL void 
read_synamps_build_trigbuffer(transform_info_ptr tinfo) {
 struct read_synamps_storage * const local_arg=(struct read_synamps_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;

 if (local_arg->triggers.buffer_start==NULL) {
  growing_buf_allocate(&local_arg->triggers, 0);
 } else {
  growing_buf_clear(&local_arg->triggers);
 }
 if (args[ARGS_TRIGFILE].is_set) {
  FILE * const triggerfile=(strcmp(args[ARGS_TRIGFILE].arg.s,"stdin")==0 ? stdin : fopen(args[ARGS_TRIGFILE].arg.s, "r"));
  TRACEMS(tinfo->emethods, 1, "read_synamps_build_trigbuffer: Reading event file\n");
  if (triggerfile==NULL) {
   ERREXIT1(tinfo->emethods, "read_synamps_build_trigbuffer: Can't open trigger file >%s<\n", MSGPARM(args[ARGS_TRIGFILE].arg.s));
  }
  while (TRUE) {
   long trigpoint;
   char *description;
   int const code=read_trigger_from_trigfile(triggerfile, tinfo->sfreq, &trigpoint, &description);
   if (code==0) break;
   push_trigger(&local_arg->triggers, trigpoint, code, description);
   free_pointer((void **)&description);
  }
  if (triggerfile!=stdin) fclose(triggerfile);
 } else {
  switch(local_arg->SubType) {
   case NST_CONTINUOUS:
   case NST_SYNAMPS: {
    /*{{{  Read the events header and array*/
    /* We handle errors through setting errormessage, because we want to continue
     * with a warning if we are in continuous mode or read from an event file */
    TEEG TagType;
    EVENT2 event;
    TRACEMS(tinfo->emethods, 1, "read_synamps_build_trigbuffer: Reading event table\n");
    fseek(local_arg->SCAN,local_arg->EEG.EventTablePos,SEEK_SET);
    /* Here we face two evils in one header: Coding enums as chars and
     * allowing longs at odd addresses. Well... */
    if (read_struct((char *)&TagType, sm_TEEG, local_arg->SCAN)==1) {
#    ifndef LITTLE_ENDIAN
     change_byteorder((char *)&TagType, sm_TEEG);
#    endif
     if (TagType.Teeg==TEEG_EVENT_TAB1 || TagType.Teeg==TEEG_EVENT_TAB2) {
      /*{{{  Read the event table*/
      struct_member * const sm_EVENT=(TagType.Teeg==TEEG_EVENT_TAB1 ? sm_EVENT1 : sm_EVENT2);
      int ntags, tag;

      ntags=TagType.Size/sm_EVENT[0].offset;	/* sm_EVENT[0].offset is the size of the structure in file. */
      for (tag=0; tag<ntags; tag++) {
       long trigger_position=0;
       int TrigVal=0, KeyPad=0, KeyBoard=0;
       enum NEUROSCAN_ACCEPTVALUES Accept=(enum NEUROSCAN_ACCEPTVALUES)0;
       if (read_struct((char *)&event, sm_EVENT, local_arg->SCAN)==0) {
	ERREXIT(tinfo->emethods, "read_synamps_build_trigbuffer: Can't read an event table entry.\n");
	break;
       }
#      ifndef LITTLE_ENDIAN
       change_byteorder((char *)&event, sm_EVENT);
#      endif
       trigger_position=offset2point(tinfo,event.Offset);
       TrigVal=event.StimType &0xff;
       KeyBoard=event.KeyBoard&0xf;
       KeyPad=Event_KeyPad_value(event);
       Accept=Event_Accept_value(event);
       if (!args[ARGS_NOREJECTED].is_set || Accept!=NAV_REJECT) {
	read_synamps_push_keys(tinfo, trigger_position, TrigVal, KeyPad, KeyBoard, Accept);
       }
      }
      /*}}}  */
     } else {
      ERREXIT1(tinfo->emethods, "read_synamps_build_trigbuffer: Unknown tag type %d.\n", MSGPARM(TagType.Teeg));
     }
    } else {
     ERREXIT(tinfo->emethods, "read_synamps_build_trigbuffer: Can't read the event table header.\n");
    }
    /*}}}  */
    }
    break;
   case NST_CONT0: {
    /*{{{  CONT0: Two trailing marker channels*/
    long current_triggerpoint=0;
    unsigned short *pdata;
    TRACEMS(tinfo->emethods, 1, "read_synamps_build_trigbuffer: Analyzing CONT0 marker channels\n");
    while (current_triggerpoint<local_arg->EEG.NumSamples) {
     int TrigVal=0, KeyPad=0, KeyBoard=0;
     enum NEUROSCAN_ACCEPTVALUES Accept=(enum NEUROSCAN_ACCEPTVALUES)0;
     read_synamps_seek_point(tinfo, current_triggerpoint);
     pdata=(unsigned short *)local_arg->buffer+current_triggerpoint-local_arg->first_point_in_buffer+local_arg->nchannels;
     TrigVal =pdata[0]&0xff; 
     KeyBoard=pdata[1]&0xf; if (KeyBoard>13) KeyBoard=0;
     if (TrigVal!=0 || KeyBoard!=0) {
      read_synamps_push_keys(tinfo, current_triggerpoint, TrigVal, KeyPad, KeyBoard, Accept);
      current_triggerpoint++;
      while (current_triggerpoint<local_arg->EEG.NumSamples) {
       int This_TrigVal, This_KeyBoard;
       read_synamps_seek_point(tinfo, current_triggerpoint);
       pdata=(unsigned short *)local_arg->buffer+current_triggerpoint-local_arg->first_point_in_buffer+local_arg->nchannels;
       This_TrigVal =pdata[0]&0xff; 
       This_KeyBoard=pdata[1]&0xf; if (This_KeyBoard>13) This_KeyBoard=0;
       if (This_TrigVal!=TrigVal || This_KeyBoard!=KeyBoard) break;
       current_triggerpoint++;
      }
     }
    }
    /*}}}  */
    }
    break;
   case NST_DCMES: { 
    /*{{{  DC-MES: Single, leading marker channel*/
    long current_triggerpoint=0;
    unsigned short *pdata;
    TRACEMS(tinfo->emethods, 1, "read_synamps_build_trigbuffer: Analyzing DCMES marker channel\n");
    while (current_triggerpoint<local_arg->EEG.NumSamples) {
     int TrigVal=0, KeyPad=0, KeyBoard=0;
     enum NEUROSCAN_ACCEPTVALUES Accept=(enum NEUROSCAN_ACCEPTVALUES)0;
     read_synamps_seek_point(tinfo, current_triggerpoint);
     pdata=(unsigned short *)local_arg->buffer+current_triggerpoint-local_arg->first_point_in_buffer;
     TrigVal= *pdata&0xff; 
     KeyBoard=(*pdata>>8)&0xf; if (KeyBoard>13) KeyBoard=0;
     if (TrigVal!=0 || KeyBoard!=0) {
      read_synamps_push_keys(tinfo, current_triggerpoint, TrigVal, KeyPad, KeyBoard, Accept);
      current_triggerpoint++;
      while (current_triggerpoint<local_arg->EEG.NumSamples) {
       int This_TrigVal, This_KeyBoard;
       read_synamps_seek_point(tinfo, current_triggerpoint);
       pdata=(unsigned short *)local_arg->buffer+current_triggerpoint-local_arg->first_point_in_buffer;
       This_TrigVal= *pdata&0xff; 
       This_KeyBoard=(*pdata>>8)&0xf; if (This_KeyBoard>13) This_KeyBoard=0;
       if (This_TrigVal!=TrigVal || This_KeyBoard!=KeyBoard) break;
       current_triggerpoint++;
      }
     }
    }
    /*}}}  */
    }
    break;
   default:
    break;
  }
 }
示例#27
0
/*{{{  get_mfxepoch(transform_info_ptr tinfo)*/
METHODDEF DATATYPE *
get_mfxepoch(transform_info_ptr tinfo) {
 struct get_mfxepoch_storage *local_arg=(struct get_mfxepoch_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 DATATYPE *newepoch;
 int again=FALSE;
 long epochlength;

 if (local_arg->epochs--==0) return NULL;

 do {
  again=FALSE;
  if ((newepoch=(DATATYPE *)mfx_getepoch(local_arg->fileptr, &epochlength, local_arg->beforetrig-local_arg->offset, local_arg->aftertrig+local_arg->offset, local_arg->trigname, args[ARGS_TRIGCODE].arg.i))==NULL) {
   /* MFX_READERR4 is the normal end-of-file 'error' */
   TRACEMS1(tinfo->emethods, (mfx_lasterr==MFX_READERR4 ? 1 : 0), "get_mfxepoch: mfx error >%s<\n", MSGPARM(mfx_errors[mfx_lasterr]));
   /* If the error was due to the beforetrig time being too long, try to
    * skip this epoch and try the next one */
   if (mfx_lasterr==MFX_NEGSEEK) {
    again=TRUE;
    mfx_seektrigger(local_arg->fileptr, local_arg->trigname, args[ARGS_TRIGCODE].arg.i);
    TRACEMS(tinfo->emethods, 1, "get_mfxepoch: Retrying...\n");
   }
  }
 } while (again);
 if (newepoch!=NULL) {
  /* TOUCH TINFO ONLY IF GETEPOCH WAS SUCCESSFUL */
  get_mfxinfo(local_arg->fileptr, tinfo);
  tinfo->z_label=NULL;
  tinfo->nr_of_points=epochlength;
  tinfo->length_of_output_region=epochlength*tinfo->nr_of_channels;
  tinfo->beforetrig=local_arg->beforetrig;
  tinfo->aftertrig=tinfo->nr_of_points-tinfo->beforetrig;
  tinfo->multiplexed=TRUE;
  tinfo->sfreq=1.0/(local_arg->fileptr)->fileheader.sample_period;
  tinfo->data_type=TIME_DATA;
  tinfo->itemsize=1;	/* Still, mfx doesn't support tuple data */
  tinfo->leaveright=0;
  tinfo->nrofaverages=1;
 }
 return newepoch;
}
示例#28
0
/*{{{  read_freiburg_init(transform_info_ptr tinfo) {*/
METHODDEF void
read_freiburg_init(transform_info_ptr tinfo) {
 struct read_freiburg_storage *local_arg=(struct read_freiburg_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 struct stat statbuf;

 /*{{{  Process options*/
 local_arg->fromepoch=(args[ARGS_FROMEPOCH].is_set ? args[ARGS_FROMEPOCH].arg.i : 1);
 local_arg->epochs=(args[ARGS_EPOCHS].is_set ? args[ARGS_EPOCHS].arg.i : -1);
 /*}}}  */
 local_arg->channelnames=NULL;
 local_arg->uV_per_bit=NULL;
 growing_buf_init(&local_arg->segment_table); /* This sets buffer_start=NULL */
 local_arg->nr_of_channels=0;

 if (args[ARGS_CONTINUOUS].is_set) {
  /*{{{  Open a continuous (sleep, Bernd Tritschler) file*/
  FILE *infile;
  local_arg->in_channels= &sleep_channels[0];

  if (stat(args[ARGS_IFILE].arg.s, &statbuf)!= 0 || !S_ISREG(statbuf.st_mode)) {
   /* File does not exist or isn't a regular file: Try BT format */
#ifdef __GNUC__
   char co_name[strlen(args[ARGS_IFILE].arg.s)+4];
   char coa_name[strlen(args[ARGS_IFILE].arg.s)+5];
#else
   char co_name[MAX_PATHLEN];
   char coa_name[MAX_PATHLEN];
#endif
   char coa_buf[MAX_COALINE];
   FILE *coafile;

   strcpy(co_name, args[ARGS_IFILE].arg.s); strcat(co_name, ".co");
   if((infile=fopen(co_name,"rb"))==NULL) {
    ERREXIT1(tinfo->emethods, "read_freiburg_init: Can't open file %s\n", MSGPARM(co_name));
   }
   local_arg->infile=infile;
   if (args[ARGS_REPAIR_OFFSET].is_set) {
    fseek(infile, args[ARGS_REPAIR_OFFSET].arg.i, SEEK_SET);
   } else {
   if (read_struct((char *)&local_arg->btfile, sm_BT_file, infile)==0) {
    ERREXIT1(tinfo->emethods, "read_freiburg_init: Header read error in file %s\n", MSGPARM(co_name));
   }
#  ifndef LITTLE_ENDIAN
   change_byteorder((char *)&local_arg->btfile, sm_BT_file);
#  endif
   }
   strcpy(coa_name, args[ARGS_IFILE].arg.s); strcat(coa_name, ".coa");
   if((coafile=fopen(coa_name,"rb"))==NULL) {
    TRACEMS1(tinfo->emethods, 0, "read_freiburg_init: No file %s found\n", MSGPARM(coa_name));
   } else {
    while (!feof(coafile)) {
     Bool repeat;
     fgets(coa_buf, MAX_COALINE-1, coafile);
     do {
      repeat=FALSE;
      if (strncmp(coa_buf, "Channel_Table ", 14)==0) {
       int havechannels=0, stringlength=0;
       long tablepos=ftell(coafile);
       char *innames;
       while (!feof(coafile)) {
	char *eol;
	fgets(coa_buf, MAX_COALINE-1, coafile);
	if (!isdigit(*coa_buf)) break;
	if (strncmp(coa_buf, "0 0 ", 4)==0) {
	 /* Empty channel descriptors: Don't generate channelnames */
	} else {
	 for (eol=coa_buf+strlen(coa_buf)-1; eol>=coa_buf && (*eol=='\n' || *eol=='\r'); eol--) *eol='\0';
	 /* This includes 1 for the zero at the end: */
	 stringlength+=strlen(strrchr(coa_buf, ' '));
	}
	havechannels++;
       }
       if (havechannels==0) continue;	/* Channel table is unuseable */
       local_arg->nr_of_channels=havechannels;
       innames=NULL;
       if ((stringlength!=0 && 
	   ((local_arg->channelnames=(char **)malloc(havechannels*sizeof(char *)))==NULL || 
	    (innames=(char *)malloc(stringlength))==NULL)) ||
	   (local_arg->uV_per_bit=(float *)malloc(havechannels*sizeof(float)))==NULL) {
	ERREXIT(tinfo->emethods, "read_freiburg_init: Error allocating .coa memory\n");
       }
       fseek(coafile, tablepos, SEEK_SET);
       havechannels=0;
       while (!feof(coafile)) {
	char *eol;
	fgets(coa_buf, MAX_COALINE-1, coafile);
	if (!isdigit(*coa_buf)) break;
	for (eol=coa_buf+strlen(coa_buf)-1; eol>=coa_buf && (*eol=='\n' || *eol=='\r'); eol--) *eol='\0';
	if (innames!=NULL) {
	 strcpy(innames, strrchr(coa_buf, ' ')+1);
	 local_arg->channelnames[havechannels]=innames;
	 innames+=strlen(innames)+1;
	}
	/* The sensitivity in .coa files is given as nV/Bit */
	local_arg->uV_per_bit[havechannels]=atoi(strchr(coa_buf, ' ')+1)/1000.0;
	if (local_arg->uV_per_bit[havechannels]==0.0) {
	 local_arg->uV_per_bit[havechannels]=0.086;
	 TRACEMS1(tinfo->emethods, 1, "read_freiburg_init: Sensitivity for channel %d set to 86 nV/Bit\n", MSGPARM(havechannels));
	}
	havechannels++;
       }
       repeat=TRUE;
      } else if (strncmp(coa_buf, SEGMENT_TABLE_STRING, strlen(SEGMENT_TABLE_STRING))==0) {
       long current_offset=0;
       char *inbuf=coa_buf;
       Bool havesomething=FALSE;

       growing_buf_allocate(&local_arg->segment_table, 0);
       while (!feof(coafile)) {
	int const nextchar=fgetc(coafile);
	if (nextchar=='\r' || nextchar=='\n' || nextchar==' ') {
	 if (havesomething) {
	  *inbuf = '\0';
	  current_offset+=atoi(coa_buf);
	  growing_buf_append(&local_arg->segment_table, (char *)&current_offset, sizeof(long));
	  inbuf=coa_buf;
	  havesomething=FALSE;
	 }
	 if (nextchar=='\n') break;
	} else {
	 *inbuf++ = nextchar;
	 havesomething=TRUE;
	}
       }
       repeat=FALSE;
      }
     } while (repeat);
    }
    fclose(coafile);
    if (local_arg->uV_per_bit==NULL) {
     TRACEMS1(tinfo->emethods, 0, "read_freiburg_init: No channel table found in file %s\n", MSGPARM(coa_name));
    }
    if (local_arg->segment_table.buffer_start==NULL) {
     TRACEMS1(tinfo->emethods, 0, "read_freiburg_init: No segment table found in file %s\n", MSGPARM(coa_name));
    }
    /* Determine the exact number of points in file: Start with the previous
     * segment and add the last segment. */
    fstat(fileno(infile),&statbuf);
    //printf("File size is %ld\n", statbuf.st_size);
    //printf("Last segment (EOF) at %ld\n", ((long *)local_arg->segment_table.buffer_start)[local_arg->segment_table.current_length/sizeof(long)-1]);
    while (local_arg->segment_table.current_length>=1 && ((long *)local_arg->segment_table.buffer_start)[local_arg->segment_table.current_length/sizeof(long)-1]>=statbuf.st_size) {
     //printf("%ld - Removing last segment!\n", ((long *)local_arg->segment_table.buffer_start)[local_arg->segment_table.current_length/sizeof(long)-1]);
     local_arg->segment_table.current_length--;
    }
    /* Size without the last segment */
    tinfo->points_in_file=(local_arg->segment_table.current_length/sizeof(long)-1)*SEGMENT_LENGTH;
    /* Count the points in the last segment */
    {
     array myarray;
     int length_of_last_segment=0;
     myarray.element_skip=tinfo->itemsize=1;
     myarray.nr_of_vectors=1;
     myarray.nr_of_elements=local_arg->nr_of_channels;
     if (array_allocate(&myarray)==NULL) {
      ERREXIT(tinfo->emethods, "read_freiburg_init: Error allocating myarray\n");
     }
     fseek(infile, ((long *)local_arg->segment_table.buffer_start)[local_arg->segment_table.current_length/sizeof(long)-1], SEEK_SET);
     //printf("Seeking to %ld\n", ((long *)local_arg->segment_table.buffer_start)[local_arg->segment_table.current_length/sizeof(long)-1]);
     tinfo->nr_of_channels=local_arg->nr_of_channels; /* This is used by freiburg_get_segment_init! */
     freiburg_get_segment_init(tinfo);
     while (freiburg_get_segment(tinfo, &myarray)==0) length_of_last_segment++;
     freiburg_get_segment_free(tinfo);
     tinfo->points_in_file+=length_of_last_segment;
     TRACEMS1(tinfo->emethods, 1, "read_freiburg_init: Last segment has %ld points\n",length_of_last_segment);
     array_free(&myarray);
    }
   }
   if (local_arg->channelnames==NULL && local_arg->btfile.text[0]=='\0') {
    local_arg->in_channels= &goeppi_channels[0];
    TRACEMS(tinfo->emethods, 0, "read_freiburg_init: Assuming Goeppingen style setup!\n");
   }
   local_arg->continuous_type=SLEEP_BT_TYPE;
   TRACEMS(tinfo->emethods, 1, "read_freiburg_init: Opened file in BT format\n");
  } else {
   if((infile=fopen(args[ARGS_IFILE].arg.s,"rb"))==NULL) {
    ERREXIT1(tinfo->emethods, "read_freiburg_init: Can't open file %s\n", MSGPARM(args[ARGS_IFILE].arg.s));
   }
   if (args[ARGS_REPAIR_OFFSET].is_set) {
    fseek(infile, args[ARGS_REPAIR_OFFSET].arg.i, SEEK_SET);
   } else {
   if (read_struct((char *)&local_arg->btfile, sm_BT_file, infile)==0) {
    ERREXIT1(tinfo->emethods, "read_freiburg_init: Header read error in file %s\n", MSGPARM(args[ARGS_IFILE].arg.s));
   }
#  ifdef LITTLE_ENDIAN
   change_byteorder((char *)&local_arg->btfile, sm_BT_file);
#  endif
   }
   local_arg->continuous_type=SLEEP_KL_TYPE;
   /* Year and day are swapped in KL format with respect to BT format... */
   {short buf=local_arg->btfile.start_year; local_arg->btfile.start_year=local_arg->btfile.start_day; local_arg->btfile.start_day=buf;}
   /* Well, sometimes or most of the time, in KL files the sampling interval 
    * was not set correctly... */
   if (!args[ARGS_SFREQ].is_set && local_arg->btfile.sampling_interval_us!=9765 && local_arg->btfile.sampling_interval_us!=9766) {
    TRACEMS1(tinfo->emethods, 0, "read_freiburg_init: sampling_interval_us was %d, corrected!\n", MSGPARM(local_arg->btfile.sampling_interval_us));
    local_arg->btfile.sampling_interval_us=9766;
   }
   TRACEMS(tinfo->emethods, 1, "read_freiburg_init: Opened file in KL format\n");
  }
  if (args[ARGS_REPAIR_CHANNELS].is_set) local_arg->btfile.nr_of_channels=args[ARGS_REPAIR_CHANNELS].arg.i;
  tinfo->nr_of_channels=local_arg->btfile.nr_of_channels;
  if (tinfo->nr_of_channels<=0 || tinfo->nr_of_channels>MAX_NUMBER_OF_CHANNELS_IN_EP) {
   ERREXIT1(tinfo->emethods, "read_freiburg_init: Impossible: %d channels?\n", MSGPARM(tinfo->nr_of_channels));
  }
  if (local_arg->nr_of_channels==0) {
   local_arg->nr_of_channels=tinfo->nr_of_channels;
  } else {
   if (local_arg->nr_of_channels!=tinfo->nr_of_channels) {
    ERREXIT2(tinfo->emethods, "read_freiburg_init: Setup has %d channels, but the file has %d!\n", MSGPARM(local_arg->nr_of_channels), MSGPARM(tinfo->nr_of_channels));
   }
  }
  local_arg->sfreq=(args[ARGS_SFREQ].is_set ? args[ARGS_SFREQ].arg.d : 1.0e6/local_arg->btfile.sampling_interval_us);
  tinfo->sfreq=local_arg->sfreq;
  if (tinfo->sfreq<=0.0 || tinfo->sfreq>MAX_POSSIBLE_SFREQ) {
   ERREXIT1(tinfo->emethods, "read_freiburg_init: Impossible: sfreq=%gHz?\n", MSGPARM(tinfo->sfreq));
  }

  /*{{{  Parse arguments that can be in seconds*/
  tinfo->nr_of_points=gettimeslice(tinfo, args[ARGS_NCHANNELS].arg.s);
  if (tinfo->nr_of_points<=0) {
   /* Read the whole file as one epoch */
   TRACEMS1(tinfo->emethods, 1, "read_freiburg_init: Reading %ld points\n",tinfo->points_in_file);
   tinfo->nr_of_points=tinfo->points_in_file;
  }
  local_arg->offset=(args[ARGS_OFFSET].is_set ? gettimeslice(tinfo, args[ARGS_OFFSET].arg.s) : 0);
  local_arg->epochlength=tinfo->nr_of_points;
  /*}}}  */

  tinfo->beforetrig= -local_arg->offset;
  tinfo->aftertrig=tinfo->nr_of_points+local_arg->offset;
  /*}}}  */
 } else {
  local_arg->in_channels= &freiburg_channels[0];
  local_arg->current_trigger=0;
  if (stat(args[ARGS_IFILE].arg.s, &statbuf)!=0) {
   ERREXIT1(tinfo->emethods, "read_freiburg_init: Can't stat file %s\n", MSGPARM(args[ARGS_IFILE].arg.s));
  }
  local_arg->nr_of_channels=atoi(args[ARGS_NCHANNELS].arg.s);
  /* average mode if the name does not belong to a directory */
  local_arg->average_mode= !S_ISDIR(statbuf.st_mode);
  tinfo->nr_of_channels=MAX_NUMBER_OF_CHANNELS_IN_EP;
 }
 freiburg_get_segment_init(tinfo);
 local_arg->current_point=0;

 tinfo->methods->init_done=TRUE;
}
示例#29
0
文件: trim.c 项目: 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;
}
示例#30
0
METHODDEF DATATYPE *
read_freiburg(transform_info_ptr tinfo) {
 struct read_freiburg_storage *local_arg=(struct read_freiburg_storage *)tinfo->methods->local_storage;
 transform_argument *args=tinfo->methods->arguments;
 struct freiburg_channels_struct *in_channels=local_arg->in_channels;
 array myarray;
 FILE *infile;
 int i, point, channel;
 int trial_not_accepted;
 long length_of_data;
 short header[FREIBURG_HEADER_LENGTH/sizeof(short)];
 char const *last_sep=strrchr(args[ARGS_IFILE].arg.s, PATHSEP);
 char const *last_component=(last_sep==NULL ? args[ARGS_IFILE].arg.s : last_sep+1);
 char comment[MAX_COMMENTLEN];

 tinfo->nrofaverages=1;
 if (args[ARGS_CONTINUOUS].is_set) {
  /*{{{  Read an epoch from a continuous file*/
  infile=local_arg->infile;

  if (local_arg->epochs--==0) return NULL;

  /*{{{  Configure myarray*/
  myarray.element_skip=tinfo->itemsize=1;
  myarray.nr_of_vectors=tinfo->nr_of_points=local_arg->epochlength;
  myarray.nr_of_elements=tinfo->nr_of_channels=local_arg->nr_of_channels;
  if (array_allocate(&myarray)==NULL) {
   ERREXIT(tinfo->emethods, "read_freiburg: Error allocating data\n");
  }
  tinfo->multiplexed=TRUE;
  /*}}}  */

  do {
   do {
    if (local_arg->segment_table.buffer_start!=NULL && local_arg->current_point%SEGMENT_LENGTH==0) {
     int const segment=local_arg->current_point/SEGMENT_LENGTH;
     long const nr_of_segments=local_arg->segment_table.current_length/sizeof(long);
     if (segment>=nr_of_segments) {
      array_free(&myarray);
      return NULL;
     }
     fseek(infile, ((long *)local_arg->segment_table.buffer_start)[segment], SEEK_SET);
     local_arg->no_last_values=TRUE;
    }
    if (freiburg_get_segment(tinfo, &myarray)!=0) {
     array_free(&myarray);
     return NULL;
    }
   } while (myarray.message!=ARRAY_ENDOFSCAN);
  } while (--local_arg->fromepoch>0);
  snprintf(comment, MAX_COMMENTLEN, "%s %s %02d/%02d/%04d,%02d:%02d:%02d", (local_arg->continuous_type==SLEEP_BT_TYPE ? "sleep_BT" : "sleep_KL"), last_component, local_arg->btfile.start_month, local_arg->btfile.start_day, local_arg->btfile.start_year, local_arg->btfile.start_hour, local_arg->btfile.start_minute, local_arg->btfile.start_second);
  tinfo->sfreq=local_arg->sfreq;
  /*}}}  */
 } else
 /*{{{  Read an epoch from a single (epoched or averaged) file*/
 do {	/* Return here if trial was not accepted */
 trial_not_accepted=FALSE;

 if (local_arg->epochs--==0 || (local_arg->average_mode && local_arg->current_trigger>=1)) return NULL;

 if (local_arg->average_mode) {
  /*{{{  Prepare reading an averaged file*/
  if((infile=fopen(args[ARGS_IFILE].arg.s,"rb"))==NULL) {
   ERREXIT1(tinfo->emethods, "read_freiburg: Can't open file %s\n", MSGPARM(args[ARGS_IFILE].arg.s));
  }
  fseek(infile, 0, SEEK_END);
  length_of_data=ftell(infile)-FREIBURG_HEADER_LENGTH;
  local_arg->current_trigger++;
  snprintf(comment, MAX_COMMENTLEN, "Freiburg-avg %s", last_component);
  /*}}}  */
 } else {
  /*{{{  Build pathname of the single trial to read*/
  /* A directory name was given. */
  char const * const expnumber=args[ARGS_IFILE].arg.s+strlen(args[ARGS_IFILE].arg.s)-2;
#ifdef __GNUC__
#define NEWFILENAME_SIZE (strlen(args[ARGS_IFILE].arg.s)+strlen(last_component)+20)
#else
#define NEWFILENAME_SIZE MAX_PATHLEN
#endif
  char newfilename[NEWFILENAME_SIZE];
  do {	/* Files from which only the parameter part exists are rejected */
   int div100=local_arg->current_trigger/100, mod100=local_arg->current_trigger%100;
   snprintf(newfilename, NEWFILENAME_SIZE, "%s%c%s%02d%c%c%s%02d%02d", args[ARGS_IFILE].arg.s, PATHSEP, last_component, div100, PATHSEP, tolower(expnumber[-1]), expnumber, div100, mod100);
   TRACEMS1(tinfo->emethods, 1, "read_freiburg: Constructed filename %s\n", MSGPARM(newfilename));

   if((infile=fopen(newfilename,"rb"))==NULL) {
    if (local_arg->current_trigger==0) {
     ERREXIT1(tinfo->emethods, "read_freiburg: Can't open file %s\n", MSGPARM(newfilename));
    } else {
     return NULL;
    }
   }
   fseek(infile, 0, SEEK_END);
   length_of_data=ftell(infile)-FREIBURG_HEADER_LENGTH;
   local_arg->current_trigger++;
  } while (length_of_data==0 || --local_arg->fromepoch>0);
  snprintf(comment, MAX_COMMENTLEN, "Freiburg-raw %s", last_component);
  /*}}}  */
 }

 /*{{{  Read the 64-Byte header*/
 fseek(infile, 0, SEEK_SET);
 fread(header, 1, FREIBURG_HEADER_LENGTH, infile);
 for (i=0; i<18; i++) {
# ifdef LITTLE_ENDIAN
  Intel_int16((uint16_t *)&header[i]);
# endif
  TRACEMS2(tinfo->emethods, 3, "read_freiburg: Header %02d: %d\n", MSGPARM(i), MSGPARM(header[i]));
 }
 /*}}}  */

 if (local_arg->average_mode) {
  if ((length_of_data/sizeof(short))%local_arg->nr_of_channels!=0) {
   ERREXIT2(tinfo->emethods, "read_freiburg: length_of_data=%d does not fit with nr_of_channels=%d\n", MSGPARM(length_of_data), MSGPARM(local_arg->nr_of_channels));
  }
  tinfo->nr_of_points=(length_of_data/sizeof(short))/local_arg->nr_of_channels;
  local_arg->sfreq=(args[ARGS_SFREQ].is_set ? args[ARGS_SFREQ].arg.d : 200.0); /* The most likely value */
 } else {
  local_arg->nr_of_channels=header[14];
  /* Note: In a lot of experiments, one point MORE is available in the data
   * than specified in the header, but this occurs erratically. We could only
   * check for this during decompression, but that's probably too much fuss. */
  tinfo->nr_of_points=header[16]/header[15];
  local_arg->sfreq=(args[ARGS_SFREQ].is_set ? args[ARGS_SFREQ].arg.d : 1000.0/header[15]);
 }
 tinfo->sfreq=local_arg->sfreq;
 /*{{{  Parse arguments that can be in seconds*/
 local_arg->offset=(args[ARGS_OFFSET].is_set ? gettimeslice(tinfo, args[ARGS_OFFSET].arg.s) : 0);
 /*}}}  */
 tinfo->beforetrig= -local_arg->offset;
 tinfo->aftertrig=tinfo->nr_of_points+local_arg->offset;

 /*{{{  Configure myarray*/
 myarray.element_skip=tinfo->itemsize=1;
 myarray.nr_of_vectors=tinfo->nr_of_points;
 myarray.nr_of_elements=tinfo->nr_of_channels=local_arg->nr_of_channels;
 if (array_allocate(&myarray)==NULL) {
  ERREXIT(tinfo->emethods, "read_freiburg: Error allocating data\n");
 }
 tinfo->multiplexed=TRUE;
 /*}}}  */

 fseek(infile, FREIBURG_HEADER_LENGTH, SEEK_SET);
 if (local_arg->average_mode) {
  /*{{{  Read averaged epoch*/
  for (point=0; point<tinfo->nr_of_points; point++) {
#ifdef __GNUC__
   short buffer[tinfo->nr_of_channels];
#else
   short buffer[MAX_NR_OF_CHANNELS];
#endif
   if ((int)fread(buffer, sizeof(short), tinfo->nr_of_channels, infile)!=tinfo->nr_of_channels) {
    ERREXIT1(tinfo->emethods, "read_freiburg: Error reading data point %d\n", MSGPARM(point));
   }
   for (channel=0; channel<tinfo->nr_of_channels; channel++) {
#  ifdef LITTLE_ENDIAN
    Intel_int16((uint16_t *)&buffer[channel]);
#  endif
    array_write(&myarray, (DATATYPE)buffer[channel]);
   }
  }
  /*}}}  */
 } else {
  /*{{{  Read compressed single trial*/
#  ifdef DISPLAY_ADJECTIVES
  char *adjektiv_ende=strchr(((char *)header)+36, ' ');
  if (adjektiv_ende!=NULL) *adjektiv_ende='\0';
  printf("Single trial: nr_of_points=%d, nr_of_channels=%d, Adjektiv=%s\n", tinfo->nr_of_points, tinfo->nr_of_channels, ((char *)header)+36);
#  endif
  local_arg->infile=infile;
  do {
   if (freiburg_get_segment(tinfo, &myarray)!=0) {
    TRACEMS1(tinfo->emethods, 0, "read_freiburg: Decompression out of bounds for trial %d - skipped\n", MSGPARM(local_arg->current_trigger-1));
    array_free(&myarray);
    trial_not_accepted=TRUE;
    break;
   }
  } while (myarray.message!=ARRAY_ENDOFSCAN);
  /*}}}  */
 }
 fclose(infile);
 } while (trial_not_accepted);
 /*}}}  */

 /*{{{  Look for a Freiburg channel setup for this number of channels*/
 /* Force create_channelgrid to really allocate the channel info anew.
  * Otherwise, free_tinfo will free someone else's data ! */
 tinfo->channelnames=NULL; tinfo->probepos=NULL;
 if (local_arg->channelnames!=NULL) {
  copy_channelinfo(tinfo, local_arg->channelnames, NULL);
 } else {
  while (in_channels->nr_of_channels!=0 && in_channels->nr_of_channels!=tinfo->nr_of_channels) in_channels++;
  if (in_channels->nr_of_channels==0) {
   TRACEMS1(tinfo->emethods, 1, "read_freiburg: Don't have a setup for %d channels.\n", MSGPARM(tinfo->nr_of_channels));
  } else {
   copy_channelinfo(tinfo, in_channels->channelnames, NULL);
  }
 }
 create_channelgrid(tinfo); /* Create defaults for any missing channel info */
 /*}}}  */
 
 if ((tinfo->comment=(char *)malloc(strlen(comment)+1))==NULL) {
  ERREXIT(tinfo->emethods, "read_freiburg: Error allocating comment memory\n");
 }
 strcpy(tinfo->comment, comment);

 if (local_arg->zero_idiotism_warned==FALSE && local_arg->zero_idiotism_encountered) {
  TRACEMS(tinfo->emethods, 0, "read_freiburg: All-zero data points have been encountered and omitted!\n");
  local_arg->zero_idiotism_warned=TRUE;
 }
 tinfo->z_label=NULL;
 tinfo->tsdata=myarray.start;
 tinfo->length_of_output_region=tinfo->nr_of_channels*tinfo->nr_of_points;
 tinfo->leaveright=0;
 tinfo->data_type=TIME_DATA;

 return tinfo->tsdata;
}