Mercurial > hg > aim92
diff tools/sp_weights.c @ 0:5242703e91d3 tip
Initial checkin for AIM92 aimR8.2 (last updated May 1997).
author | tomwalters |
---|---|
date | Fri, 20 May 2011 15:19:45 +0100 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tools/sp_weights.c Fri May 20 15:19:45 2011 +0100 @@ -0,0 +1,235 @@ +/************************************************************************* + sp_weights.c Map auditory image onto spiral sector-weights contour. +-------------- + + Read auditory image frames (gensai or genspl with output set) from a + file or the stdin. Input must have a pipes header, (for frame dimensions). + + Note, you can use either gensai or genspl output, but remember that their + default options are different, (particularly pwidth, nwidth, and dencf). + + For each frame, (of frameheight*framewidth binary shorts), + write a sector-weights contour, (of m binary shorts), on the stdout. + + Arguments: + -m The number of sectors (default SECTORS). + -fA-B Process the A'th to B'th frame inclusive, + (or the A'th to the eof if b=='e'), (default -o1-e). + -fA Process just the A'th frame. + +*************************************************************************/ + +#include <stdio.h> +#include <math.h> +#include "header.h" +#include "options.h" +#include "units.h" +#include "strmatch.h" + +char applic[] = "Map auditory image frames onto spiral sector-weights contours.\n (Input and output in binary shorts)." ; + +static char *helpstr, *debugstr, *infostr, *fstr, *mstr ; + +static Options option[] = { + { "help" , "off" , &helpstr , "help" , DEBUG }, + { "debug" , "off" , &debugstr , "debugging switch" , DEBUG }, + { "info" , "off" , &infostr , "print frame size information", DEBUG }, + { "frames" , "1-max" , &fstr , "select frames inclusively" , VAL }, + { "nsectors" , "64" , &mstr , "number of sectors" , SVAL }, + ( char * ) 0 } ; + + +#define log2(x) (log((double)x)/log(2.0)) +#define round(x) ((int)(x+0.5)) + +int frameheight, framewidth ; /* Parameters read from header */ +int frames; +double orig_spd ; + +main(argc, argv) +int argc ; +char *argv[] ; +{ + FILE *fp ; + char *header, *val1, *val2 ; + char *headeropt, *versionstr; + int i, a, b; + int m ; /* Number of sectors around spiral */ + int framebytes; /* Number of bytes in each frame */ + short *frame; /* Each frame */ + + fp = openopts( option,argc,argv ) ; + if ( !isoff( helpstr ) ) + helpopts( helpstr, argv[0], applic, option ) ; + + m = atoi( mstr ) ; + + /* parse bounds on number of frames */ + + if ( getvals( fstr, &val1, &val2, "-" ) == BADVAL ) { + fprintf(stderr,"loudness: bad frame selector [%s]\n", fstr ) ; + exit( 1 ) ; + } + a = atoi( val1 ) ; + if ( isempty( val2 ) ) b = a ; + else if ( ismax( val2 ) ) b = 0 ; + else b = atoi( val2 ) ; + + if (b<a && b>0) fprintf(stderr,"sp_weights warning: bad frame specifiers\n"); + + + + /* Read header to find dimensions of auditory image */ + + if ((header = ReadHeader(fp)) == (char *) 0 ) { + fprintf(stderr,"sp_weights: header not found\n"); + exit(1); + } + + if ( (versionstr = HeaderString( header, "Version" )) == (char *)0 ) { + fprintf(stderr,"sp_weights: model version-number not found in header\n"); + exit(1); + } + + if ( (headeropt = HeaderString( header, "frameheight" )) == (char *)0) { + fprintf(stderr,"sp_weights: frameheight not found in header\n"); + exit(1); + } + else frameheight = atoi( headeropt ); + + if ( (headeropt = HeaderString( header, "framewidth" )) == (char *)0) { + fprintf(stderr,"sp_weights: framewidth not found in header\n"); + exit(1); + } + else framewidth = atoi( headeropt ); + + if ( (headeropt = HeaderString( header, "frames" )) == (char *)0) { + fprintf(stderr,"sp_weights: frames not found in header\n"); + exit(1); + } + else frames = atoi( headeropt ); + + if ( (headeropt = HeaderString( header, "orig_spd" )) == (char *)0) { + fprintf(stderr,"sp_weights: orig_spd not found in header\n"); + exit(1); + } + else orig_spd = atof( headeropt ); + + if ( ison( debugstr ) ) { + printf("a=%d b=%d m=%d \n", a, b, m ); + printf("frames=%d frameheight=%d framewidth=%d orig_spd=%.2f\n", frames,frameheight,framewidth,orig_spd ) ; + exit(0); + } + + if ( ison( infostr ) || a==0 ) { + printf("sp_weights input: %s", versionstr ) ; + printf(" frames=%d frameheight=%d framewidth=%d\n", frames,frameheight,framewidth ) ; + exit(0); + } + + if (frames<=0) { + if (frames==0) fprintf(stderr,"sp_weights: zero frames input\n"); + if (frames<0) fprintf(stderr,"sp_weights: garbled number of frames, (start set too big?)\n"); + exit(1); + } + + if (a>frames || b>frames) + fprintf(stderr,"sp_weights warning: bad frame specifiers\n"); + + framebytes = frameheight * framewidth * sizeof(short) ; + + /* Allocate space for an auditory image frame */ + + if (( frame = (short *)malloc( framebytes )) == NULL) + fprintf(stderr,"sp_weights: malloc out of space\n"); + + /* Seek past a-1 frames, then read the next b-a+1 frames, or all */ + /* remaining frames if b==0. */ + + for (i=1 ; i<a && fread(frame,framebytes,1,fp) ; i++) + ; + if (b > 0) + for ( ; i<=b && fread(frame,framebytes,1,fp) ; i++) + write_weights(frame,m); + else + while ( fread(frame,framebytes,1,fp) ) + write_weights(frame,m); + + fclose(fp); +} + + + +/*************************************************************************** + Spoke sector weight routines (originally as src/src8/spoke.c) + + Write m sector weights as binary shorts on the stdout. +***************************************************************************/ + +write_weights(frame,m) +short *frame; +int m; /* number of sectors around the spiral plane */ +{ + static short *sector; + static int *logtime; + int i, k, t, col; + double sum; + static int first=1; /* flag for first-call of this routine */ + + /* Allocate space (first-time call only). */ + if (first) { + first = 0; + /* Allocate space and compute base-2 log time for spoke detection */ + if ( (sector = (short *)malloc( m*sizeof(short) ) ) == NULL) + fprintf(stderr,"sp_weights: malloc out of space\n"); + if ( (logtime = (int *)malloc( framewidth*sizeof(int) ) ) == NULL ) + fprintf(stderr,"sp_weights: malloc out of space\n"); + gen_logtime(logtime,m); + } + /* clear sector bins */ + for (i=0 ; i<m ; i++) + sector[i]=0; + /* for each time point along the SAI frame (with time origin on right) */ + /* (exclude time-origin bin to prevent overweighting by this sample) */ + for (t=round(pow(2.0,orig_spd)) ; t<framewidth ; t++) { + col = (framewidth-1)-t; + /* sum frame column (ie across all frequency channels) */ + for (i=0, k=0, sum=0 ; i<frameheight ; i++, k+=framewidth) + sum += frame[col+k]; + /* Normalize (divide by frameheight) for average magnitude */ + sum /= frameheight; + /* Accumulate sum in log-time sector bin */ + sector[logtime[t]] += sum; + } + /* write total sum activity in spokes around the spiral from the datum */ + /* line in an anticlockwise direction. (ie in "natural order"). */ + for (i=0 ; i<m ; i++) +/* printf("%d\n", sector[i]); */ + fwrite(§or[i], sizeof(short), 1, stdout); +} + +/**************************************************************************** + List the sector numbers, 0,1,...,m-1, which correspond to each time + t=1,2,...,framewidth-1. The return array, "logtime", maps time index onto + a spiral sector number. + (Note that since the sector width increases with radius, there is an + increasing number of adjacent frame indices within the sector bin). +****************************************************************************/ +gen_logtime(logtime, m) +int *logtime; +int m; +{ + int t; + double theta, fptr, iptr; + + logtime[0] = 0; /* special case for log(0) */ + for (t=1 ; t<framewidth ; t++) { + theta = log2(t) - orig_spd; + fptr = modf(theta,&iptr); /* find fractional part of log time */ + /* scale up to given resolution, and round */ + logtime[t] = (int)(0.5+(fptr*m)); + } +} + + +