changeset 55:4ea1a8838b14

Finished the essentials of descriptors.c
author Jamie Bullock <jamie@postlude.co.uk>
date Sun, 21 Jan 2007 14:40:23 +0000
parents 9762d7e3d129
children 450712b21565
files examples/puredata/xtract~.c src/descriptors.c src/scalar.c src/vector.c xtract/libxtract.h xtract/xtract_macros.h xtract/xtract_scalar.h xtract/xtract_vector.h
diffstat 8 files changed, 554 insertions(+), 52 deletions(-) [+]
line wrap: on
line diff
--- a/examples/puredata/xtract~.c	Thu Jan 11 16:37:50 2007 +0000
+++ b/examples/puredata/xtract~.c	Sun Jan 21 14:40:23 2007 +0000
@@ -105,6 +105,7 @@
     t_xtract_tilde *x = (t_xtract_tilde *)pd_new(xtract_class);
     xtract_mel_filter *mf;
     t_int n, N, f, F, n_args, type;
+    t_float *argv_max;
     t_function_descriptor *fd;
     char *p_name, *p_desc, *author;
     int *year;
@@ -138,6 +139,10 @@
     type = fd[f].argv.type;
 
     if(n_args){
+	for(n = 0; n < n_args; n++){
+		    argv_max = &fd[f].argv.max[n]; 
+		    post("Argument %d, max: %.2f", n, *argv_max);
+	}
 	if(type == MEL_FILTER){
 	    x->memory.argv = (size_t)(n_args * sizeof(xtract_mel_filter));
 	    x->argv = (xtract_mel_filter *)getbytes(x->memory.argv);
--- a/src/descriptors.c	Thu Jan 11 16:37:50 2007 +0000
+++ b/src/descriptors.c	Sun Jan 21 14:40:23 2007 +0000
@@ -26,35 +26,36 @@
 void *xtract_make_descriptors(){
 
     t_function_descriptor *fd, *d;
-    t_type *type;
+    t_type *argv_type;
     int f , F;
-    char *name, *p_name, *desc, *p_desc, *author;
+    char *name, *p_name, *desc, *p_desc, *author, *argv_donor;
+    float *argv_min, *argv_max, *argv_def, *result_min, *result_max;
     int *argc, *year;
     t_vector *data_format; 
-    /* *result_format; */
+    t_unit *data_unit, *argv_unit, *result_unit;
+    t_bool *is_scalar;
+    t_vector *result_format;
 
     f = F = XTRACT_FEATURES;
 
     fd = malloc(XTRACT_FEATURES * sizeof(t_function_descriptor));
 
+    /* FIX - this file probably needs a rewrite for readability */
 
     while(f--){
 
 	d = &fd[f];
 	argc = &d->argc;
-	type = &d->argv.type;
+	argv_type = &d->argv.type;
 
 	switch(f){
 
-	    case  MEAN: 
 	    case  VARIANCE:
 	    case  STANDARD_DEVIATION:
 	    case  AVERAGE_DEVIATION:
-	    case  SPECTRAL_MEAN:
 	    case  SPECTRAL_VARIANCE:
 	    case  SPECTRAL_STANDARD_DEVIATION:
 	    case  SPECTRAL_AVERAGE_DEVIATION:
-	    case  ROLLOFF:
 	    case  SPECTRAL_INHARMONICITY:
 	    case  ODD_EVEN_RATIO:
 	    case  LOWEST_VALUE:
@@ -62,7 +63,7 @@
 	    case  FAILSAFE_F0:
 	    case  TONALITY:
 		*argc = 1;
-		*type = FLOAT;
+		*argv_type = FLOAT;
 		break;
 	    case  SKEWNESS:
 	    case  KURTOSIS:
@@ -73,17 +74,20 @@
 	    case  HARMONIC_SPECTRUM:
 	    case  NOISINESS:
 	    case  CREST:
+	    case  ROLLOFF:
 		*argc = 2;
-		*type = FLOAT;
+		*argv_type = FLOAT;
 		break;
 	    case  MFCC:
 		*argc = 1;
-		*type = MEL_FILTER;
+		*argv_type = MEL_FILTER;
 		break;
 	    case  BARK_COEFFICIENTS:
 		*argc = BARK_BANDS;
-		*type = INT;
+		*argv_type = INT;
 		break;
+	    case  MEAN:
+	    case  SPECTRAL_MEAN:
 	    case  SPECTRAL_CENTROID:
 	    case  IRREGULARITY_K:
 	    case  IRREGULARITY_J:
@@ -111,10 +115,175 @@
 	    case  AUTOCORRELATION:
 	    case  AMDF:
 	    case  ASDF:
+	    default:
 		*argc = 0;
 		break;
+	}
+		
+	argv_min = &d->argv.min[0];
+	argv_max = &d->argv.max[0];
+	argv_def = &d->argv.def[0];
+	argv_unit = &d->argv.unit[0];
+
+	switch (f) {
+	    /* argc = 1 */
+	    case  VARIANCE:
+	    case  SPECTRAL_VARIANCE:
+	    case  STANDARD_DEVIATION:
+	    case  AVERAGE_DEVIATION:
+	    case  SPECTRAL_STANDARD_DEVIATION:
+	    case  SPECTRAL_AVERAGE_DEVIATION:
+	    case  LOWEST_VALUE:
+	    case  TONALITY:
+	    case  MFCC:
+		*argv_min = ANY;
+		*argv_max = ANY;
+		*argv_def = ANY;
+		*argv_unit = ANY;
+	    case  SPECTRAL_INHARMONICITY:
+	    case  ODD_EVEN_RATIO:
+		*argv_min = 0.f;
+		*argv_max = SR_UPPER_LIMIT / 2;
+		*argv_def = FUNDAMENTAL_DEFAULT;
+		*argv_unit = HERTZ;
+	    case  F0:
+	    case  FAILSAFE_F0:
+		*argv_min = SR_LOWER_LIMIT;
+		*argv_max = SR_UPPER_LIMIT;
+		*argv_def = SR_DEFAULT; 
+		*argv_unit = HERTZ;
+	    /* argc = 2 */;
+	    case  ROLLOFF:
+		*argv_min  = FFT_BANDS_MIN;
+		*argv_max = FFT_BANDS_MAX;
+		*argv_def = SPEC_BW_DEF ;
+		*argv_unit = HERTZ;
+		*(argv_min + 1) = 0.f;
+		*(argv_max + 1) = 100.f;
+		*(argv_def + 1) = 95.f;
+		*(argv_unit + 1) = PERCENT;
+	    case  SPECTRUM:
+		*argv_min  = SR_LOWER_LIMIT / 2; 
+		*argv_max = SR_UPPER_LIMIT / 2;
+		*argv_def = SR_DEFAULT / 2;
+		*argv_unit = HERTZ;
+		*(argv_min + 1) = 0;
+		*(argv_max + 1) = 3 ;
+		*(argv_def + 1) = 0;
+		*(argv_unit + 1) = NONE;
+	    case  PEAK_SPECTRUM:
+		*argv_min  = SR_LOWER_LIMIT / 2; 
+		*argv_max = SR_UPPER_LIMIT / 2;
+		*argv_def = SR_DEFAULT / 2;
+		*argv_unit = HERTZ;
+		*(argv_min + 1) = 0.f;
+		*(argv_max + 1) = 100.f ;
+		*(argv_def + 1) = 10.f ;
+		*(argv_unit + 1) = PERCENT;
+	    case  HARMONIC_SPECTRUM:
+		*argv_min = 0.f;
+		*argv_max = SR_UPPER_LIMIT / 2;
+		*argv_def = FUNDAMENTAL_DEFAULT;
+		*argv_unit = HERTZ;
+		*(argv_min + 1) = 0.f;
+		*(argv_max + 1) = 1.f ;
+		*(argv_def + 1) = .1f ;
+		*(argv_unit + 1) = NONE;
+	    case  NOISINESS:
+	    case  SKEWNESS:
+	    case  KURTOSIS:
+	    case  SPECTRAL_SKEWNESS:
+	    case  SPECTRAL_KURTOSIS:
+	    case  CREST:
+		*argv_min = NONE;
+		*argv_max = NONE;
+		*argv_def = NONE;
+		*argv_unit = NONE;
+		*(argv_min + 1) = NONE;
+		*(argv_max + 1) = NONE;
+		*(argv_def + 1) = NONE;
+		*(argv_unit + 1) = NONE;
+	    case  BARK_COEFFICIENTS:
+	    /* BARK_COEFFICIENTS is special because argc = BARK_BANDS */
 	    default:
-		*argc = 0;
+		*argv_min = NONE;
+		*argv_max = NONE;
+		*argv_def = NONE;
+		*argv_unit = NONE;
+	}
+
+	argv_donor = &d->argv.donor[0];
+
+	switch (f) {
+	    /* argc = 1 */
+	    case  VARIANCE:
+		*argv_donor = MEAN;
+		break;
+	    case  SPECTRAL_VARIANCE:
+		*argv_donor = SPECTRAL_MEAN;
+		break;
+	    case  STANDARD_DEVIATION:
+		*argv_donor = VARIANCE;
+		break;
+	    case  AVERAGE_DEVIATION:
+		*argv_donor = MEAN;
+		break;
+	    case  SPECTRAL_STANDARD_DEVIATION:
+		*argv_donor = SPECTRAL_VARIANCE;
+		break;
+	    case  SPECTRAL_AVERAGE_DEVIATION:
+		*argv_donor = SPECTRAL_MEAN;
+		break;
+	    case  SPECTRAL_INHARMONICITY:
+	    case  ODD_EVEN_RATIO:
+		*argv_donor = FAILSAFE_F0;
+		break;
+	    case  TONALITY:
+		*argv_donor = FLATNESS;
+		break;
+	    case  LOWEST_VALUE:
+	    case  F0:
+	    case  FAILSAFE_F0:
+		*argv_donor = ANY;
+		break;
+	    case  MFCC:
+		*argv_donor = INIT_MFCC;
+		break;
+	    /* argc = 2 */;
+	    case  SPECTRUM:
+	    case  ROLLOFF:
+	    case  PEAK_SPECTRUM:
+		*argv_donor = ANY;
+		*(argv_donor + 1) = ANY;
+		break;
+	    case  SKEWNESS:
+	    case  KURTOSIS:
+		*argv_donor = MEAN;
+		*(argv_donor + 1) = STANDARD_DEVIATION;
+		break;
+	    case  SPECTRAL_SKEWNESS:
+	    case  SPECTRAL_KURTOSIS:
+		*argv_donor = SPECTRAL_MEAN;
+		*(argv_donor + 1) = SPECTRAL_STANDARD_DEVIATION;
+		break;
+	    case  HARMONIC_SPECTRUM:
+		*argv_donor = FAILSAFE_F0;
+		*(argv_donor + 1) = ANY;
+		break;
+	    case  NOISINESS:
+		*argv_donor = SUM;
+		*(argv_donor + 1) = SUM;
+		break;
+	    case  CREST:
+		*argv_donor = HIGHEST_VALUE;
+		*(argv_donor + 1) = SPECTRAL_MEAN;
+		break;
+	    /* argc = BARK_BANDS */
+	    case  BARK_COEFFICIENTS:
+		*argv_donor = INIT_BARK;
+		break;
+	    default:
+		*argv_donor = ANY;
 		break;
 	}
 
@@ -198,6 +367,71 @@
 		break;
 	}
 
+        data_unit = &d->data.unit;
+
+	switch(f){
+
+	    case  MEAN: 
+	    case  VARIANCE:
+	    case  STANDARD_DEVIATION:
+	    case  AVERAGE_DEVIATION:
+	    case  SKEWNESS:
+	    case  KURTOSIS:
+	    case  LOWEST_VALUE:
+	    case  HIGHEST_VALUE:
+	    case  SUM:
+	    case  ZCR:
+	    case  PEAK_SPECTRUM:
+	    case  TRISTIMULUS_1:
+	    case  TRISTIMULUS_2:
+	    case  TRISTIMULUS_3:
+	    case  DCT:
+	    case  AMDF:
+	    case  ASDF:
+	    case  IRREGULARITY_K:
+	    case  IRREGULARITY_J:
+	    case  ATTACK_TIME: 
+	    case  DECAY_TIME: 
+	    case  DELTA_FEATURE: 
+	    case  FLUX: 
+	    case  F0:
+	    case  FAILSAFE_F0:
+	    case  MFCC:
+	    case  AUTOCORRELATION:
+	    case  AUTOCORRELATION_FFT:
+	    case  ROLLOFF:
+	    case  NOISINESS:
+	    case  CREST:
+	    case  FLATNESS:
+	    case  POWER:
+	    case  BARK_COEFFICIENTS:
+	    case  RMS_AMPLITUDE:
+	    case  SMOOTHNESS:
+	    case  SPREAD:
+	    case  SHARPNESS:
+	    case  HPS:
+	    case  SPECTRUM:
+	    case  TONALITY:
+	    case  LOUDNESS:
+		*data_unit = ANY;
+		break;
+	    case  SPECTRAL_MEAN:
+	    case  SPECTRAL_VARIANCE:
+	    case  SPECTRAL_STANDARD_DEVIATION:
+	    case  SPECTRAL_AVERAGE_DEVIATION:
+	    case  SPECTRAL_SKEWNESS:
+	    case  SPECTRAL_KURTOSIS:
+	    case  SPECTRAL_CENTROID:
+	    case  SPECTRAL_SLOPE:
+	    case  HARMONIC_SPECTRUM:
+	    case  SPECTRAL_INHARMONICITY:
+		*data_unit = ANY_AMPLITUDE_HERTZ;
+		break;
+	    case  ODD_EVEN_RATIO:
+		*data_unit = HERTZ;
+		break;
+	}
+
 	name = d->algo.name;
 	p_name = d->algo.p_name;
 	desc = d->algo.desc;
@@ -214,6 +448,7 @@
 		strcpy(desc, "Extract the mean of an input vector");
 		strcpy(p_desc, "Extract the mean of a range of values");
 		strcpy(author, "");
+		d->argv.type = NONE;
 		break;
 	    case  VARIANCE:
 		strcpy(name, "variance");
@@ -629,6 +864,241 @@
 		strcpy(author, "");
 		break;
 	}
+
+
+	switch(f){
+
+	    case  VARIANCE:
+	    case  STANDARD_DEVIATION:
+	    case  AVERAGE_DEVIATION:
+	    case  SPECTRAL_VARIANCE:
+	    case  SPECTRAL_STANDARD_DEVIATION:
+	    case  SPECTRAL_AVERAGE_DEVIATION:
+	    case  SPECTRAL_INHARMONICITY:
+	    case  ODD_EVEN_RATIO:
+	    case  LOWEST_VALUE:
+	    case  F0:
+	    case  FAILSAFE_F0:
+	    case  TONALITY:
+		*argc = 1;
+		*argv_type = FLOAT;
+		break;
+	    case  SKEWNESS:
+	    case  KURTOSIS:
+	    case  SPECTRAL_SKEWNESS:
+	    case  SPECTRAL_KURTOSIS:
+	    case  SPECTRUM:
+	    case  PEAK_SPECTRUM:
+	    case  HARMONIC_SPECTRUM:
+	    case  NOISINESS:
+	    case  CREST:
+	    case  ROLLOFF:
+		*argc = 2;
+		*argv_type = FLOAT;
+		break;
+	    case  MFCC:
+		*argc = 1;
+		*argv_type = MEL_FILTER;
+		break;
+	    case  BARK_COEFFICIENTS:
+		*argc = BARK_BANDS;
+		*argv_type = INT;
+		break;
+	    case  MEAN:
+	    case  SPECTRAL_MEAN:
+	    case  SPECTRAL_CENTROID:
+	    case  IRREGULARITY_K:
+	    case  IRREGULARITY_J:
+	    case  TRISTIMULUS_1:
+	    case  TRISTIMULUS_2:
+	    case  TRISTIMULUS_3:
+	    case  SMOOTHNESS:
+	    case  FLATNESS:
+	    case  SPREAD:
+	    case  ZCR:
+	    case  LOUDNESS:
+	    case  HIGHEST_VALUE:
+	    case  SUM:
+	    case  RMS_AMPLITUDE:
+	    case  POWER:
+	    case  SHARPNESS:
+	    case  SPECTRAL_SLOPE:
+	    case  HPS:
+	    case  FLUX: 
+	    case  ATTACK_TIME: 
+	    case  DECAY_TIME: 
+	    case  DELTA_FEATURE: 
+	    case  AUTOCORRELATION_FFT:
+	    case  DCT:
+	    case  AUTOCORRELATION:
+	    case  AMDF:
+	    case  ASDF:
+	    default:
+		*argc = 0;
+		break;
+	}
+    
+	is_scalar = &d->is_scalar;
+
+	switch(f){
+	    case  MEAN:
+	    case  VARIANCE:
+	    case  STANDARD_DEVIATION:
+	    case  AVERAGE_DEVIATION:
+	    case  SKEWNESS:
+	    case  KURTOSIS:
+	    case  SPECTRAL_MEAN:
+	    case  SPECTRAL_VARIANCE:
+	    case  SPECTRAL_STANDARD_DEVIATION:
+	    case  SPECTRAL_AVERAGE_DEVIATION:
+	    case  SPECTRAL_SKEWNESS:
+	    case  SPECTRAL_KURTOSIS:
+	    case  SPECTRAL_CENTROID:
+	    case  IRREGULARITY_K:
+	    case  IRREGULARITY_J:
+	    case  TRISTIMULUS_1:
+	    case  TRISTIMULUS_2:
+	    case  TRISTIMULUS_3:
+	    case  SMOOTHNESS:
+	    case  SPREAD:
+	    case  ZCR:
+	    case  ROLLOFF:
+	    case  LOUDNESS:
+	    case  FLATNESS:
+	    case  TONALITY:
+	    case  CREST:
+	    case  NOISINESS:
+	    case  RMS_AMPLITUDE:
+	    case  SPECTRAL_INHARMONICITY:
+	    case  POWER:
+	    case  ODD_EVEN_RATIO:
+	    case  SHARPNESS:
+	    case  SPECTRAL_SLOPE:
+	    case  LOWEST_VALUE:
+	    case  HIGHEST_VALUE:
+	    case  SUM:
+	    case  HPS:
+	    case  F0:
+	    case  FAILSAFE_F0:
+		*is_scalar = TRUE;
+		break;
+	    case  AUTOCORRELATION:
+	    case  AMDF:
+	    case  ASDF:
+	    case  BARK_COEFFICIENTS:
+	    case  PEAK_SPECTRUM:
+	    case  SPECTRUM:
+	    case  AUTOCORRELATION_FFT:
+	    case  MFCC:
+	    case  DCT:
+	    case  HARMONIC_SPECTRUM:
+		*is_scalar = FALSE;
+		break;
+	    default:
+		*is_scalar = TRUE;
+		break;
+
+	}
+
+	if(*is_scalar){
+
+	    result_unit = &d->result.scalar.unit;
+	    result_min = &d->result.scalar.min;
+	    result_max = &d->result.scalar.max;
+
+	    switch(f){
+		case  MEAN:
+		case  VARIANCE:
+		case  STANDARD_DEVIATION:
+		case  AVERAGE_DEVIATION:
+		case  SKEWNESS:
+		case  KURTOSIS:
+		case  RMS_AMPLITUDE:
+		case  LOWEST_VALUE:
+		case  HIGHEST_VALUE:
+		case  SUM:
+		    *result_unit = ANY;
+		    *result_min = ANY;
+		    *result_max = ANY;
+		    break;
+		case  SPECTRAL_SKEWNESS:
+		case  SPECTRAL_KURTOSIS:
+		case  IRREGULARITY_K:
+		case  IRREGULARITY_J:
+		case  TRISTIMULUS_1:
+		case  TRISTIMULUS_2:
+		case  TRISTIMULUS_3:
+		case  NOISINESS:
+		case  SMOOTHNESS:
+		    *result_unit = NONE;
+		    *result_min = ANY; /* FIX: need to check these */
+		    *result_max = ANY;
+		    break;
+		case  SPECTRAL_MEAN:
+		case  SPECTRAL_VARIANCE:
+		case  SPECTRAL_STANDARD_DEVIATION:
+		case  SPECTRAL_AVERAGE_DEVIATION:
+		case  SPECTRAL_CENTROID:
+		case  SPREAD:
+		case  F0:
+		case  FAILSAFE_F0:
+		case  HPS:
+		case  ROLLOFF:
+		    *result_unit = HERTZ;
+		    *result_min = 0.f;
+		    *result_max = SR_UPPER_LIMIT / 2;
+		case  ZCR:
+		    *result_unit = HERTZ;
+		    *result_min = 0.f;
+		    *result_max = ANY;
+		case  ODD_EVEN_RATIO:
+		    *result_unit = NONE;
+		    *result_min = 0.f;
+		    *result_max = 1.f; 
+		case  LOUDNESS:
+		case  FLATNESS:
+		case  TONALITY:
+		case  CREST:
+		case  SPECTRAL_INHARMONICITY:
+		case  POWER:
+		case  SHARPNESS:
+		case  SPECTRAL_SLOPE:
+		default:
+		    *result_unit = UNKNOWN;
+		    *result_min = UNKNOWN;
+		    *result_max = UNKNOWN; 
+	    }
+	}
+	else {
+
+	    result_min = NULL;
+	    result_max = NULL;
+	    result_unit = &d->result.vector.unit;
+	    result_format = &d->result.vector.format;
+
+	    switch(f) {
+		case  AUTOCORRELATION:
+		case  AMDF:
+		case  ASDF:
+		case  DCT:
+		    *result_format = ARBITRARY_SERIES;
+		    *result_unit = ANY;
+		case  BARK_COEFFICIENTS:
+		    *result_format = BARK_COEFFS;
+		    *result_unit = UNKNOWN; /* FIX: check */
+		case  PEAK_SPECTRUM:
+		case  SPECTRUM:
+		case  HARMONIC_SPECTRUM:
+		    *result_format = SPECTRAL;
+		    *result_unit = ANY_AMPLITUDE_HERTZ;
+		case  AUTOCORRELATION_FFT:
+		case  MFCC:
+		    *result_format = MEL_COEFFS;
+		    *result_unit = UNKNOWN; /* FIX: check */
+		default:
+		    break;
+	    }
+	}
     }
 
     return fd;
--- a/src/scalar.c	Thu Jan 11 16:37:50 2007 +0000
+++ b/src/scalar.c	Sun Jan 21 14:40:23 2007 +0000
@@ -374,18 +374,20 @@
 int xtract_rolloff(const float *data, const int N, const void *argv, float *result){
 
     int n = N;
-    float pivot, temp;
+    float pivot, temp, percentile;
 
     pivot = temp = 0.f;
+    percentile = ((float *)argv)[1];
 
     while(n--) pivot += data[n];   
 
-    pivot *= ((float *)argv)[0];
+    pivot *= percentile / 100.f;
 
     for(n = 0; temp < pivot; n++)
 	temp += data[n];
 
-    *result = (n / (float)N) * (((float *)argv)[1] * .5);
+    *result = n * ((float *)argv)[0];
+    /* *result = (n / (float)N) * (((float *)argv)[1] * .5); */
 
     return SUCCESS;
 }
--- a/src/vector.c	Thu Jan 11 16:37:50 2007 +0000
+++ b/src/vector.c	Sun Jan 21 14:40:23 2007 +0000
@@ -32,7 +32,7 @@
 
 int xtract_spectrum(const float *data, const int N, const void *argv, float *result){
 
-    float *input, *rfft, q, temp;
+    float *input, *rfft, nyquist, temp;
     size_t bytes;
     int n , NxN, M, vector;
     fftwf_plan plan;
@@ -44,10 +44,10 @@
     input = (float *)malloc(bytes = N * sizeof(float));
     input = memcpy(input, data, bytes);
 
-    q = *(float *)argv;
+    nyquist = *(float *)argv;
     vector = (int)*((float *)argv+1);
 
-    CHECK_q;
+    CHECK_nyquist;
 
     plan = fftwf_plan_r2r_1d(N, input, rfft, FFTW_R2HC, FFTW_ESTIMATE);
     
@@ -57,7 +57,7 @@
 	case MAGNITUDE_SPECTRUM:
 	    for(n = 0; n < M; n++){
 		result[n] = sqrt(SQ(rfft[n]) + SQ(rfft[N - n])) / N; 
-		result[M + n] = n * q;
+		result[M + n] = n * nyquist;
 	    }
 	    break;
 	case LOG_MAGNITUDE_SPECTRUM:
@@ -68,13 +68,13 @@
 		    temp = LOG_LIMIT_DB;
 		/*Normalise*/
 		result[n] = (temp + DB_SCALE_OFFSET) / DB_SCALE_OFFSET; 
-		result[M + n] = n * q;
+		result[M + n] = n * nyquist;
 	    }
 	    break;
 	case POWER_SPECTRUM:
 	    for(n = 0; n < M; n++){
 		result[n] = (SQ(rfft[n]) + SQ(rfft[N - n])) / NxN;
-		result[M + n] = n * q;
+		result[M + n] = n * nyquist;
 	    }
 	    break;
 	case LOG_POWER_SPECTRUM:
@@ -84,20 +84,20 @@
 		else
 		    temp = LOG_LIMIT_DB; 		
 		result[n] = (temp + DB_SCALE_OFFSET) / DB_SCALE_OFFSET; 
-		result[M + n] = n * q;
+		result[M + n] = n * nyquist;
 	    }
 	    break;
 	default:
 	    /* MAGNITUDE_SPECTRUM */
 	    for(n = 0; n < M; n++){
 		result[n] = sqrt(SQ(rfft[n]) + SQ(rfft[N - n])) / N; 
-		result[M + n] = n * q;
+		result[M + n] = n * nyquist;
 	    }
 	    break;
     }
     
     /* result[0] = fabs(temp[0]) / N  */
-    result[M] = q * .5;
+    result[M] = nyquist * .5;
     
     fftwf_destroy_plan(plan);
     fftwf_free(rfft);
@@ -279,25 +279,25 @@
 
 int xtract_peak_spectrum(const float *data, const int N, const void *argv, float *result){
 
-    float thresh, max, y, y2, y3, p, q, *input = NULL;
+    float threshold, max, y, y2, y3, p, nyquist, *input = NULL;
     size_t bytes;
     int n = N, M, rv = SUCCESS;
 
-    thresh = max = y = y2 = y3 = p = q = 0.f;
+    threshold = max = y = y2 = y3 = p = nyquist = 0.f;
     
     if(argv != NULL){
-        thresh = ((float *)argv)[0];
-        q = ((float *)argv)[1];
+        nyquist = ((float *)argv)[0];
+        threshold = ((float *)argv)[1];
     }
     else
         rv = BAD_ARGV;
 
-    if(thresh < 0 || thresh > 100){
-        thresh = 0;
+    if(threshold < 0 || threshold > 100){
+        threshold = 0;
         rv = BAD_ARGV;
     }
 
-    CHECK_q;
+    CHECK_nyquist;
 
     input = (float *)malloc(bytes = N * sizeof(float));
 
@@ -311,15 +311,15 @@
     while(n--)
         max = MAX(max, input[n]);
     
-    thresh *= .01 * max;
+    threshold *= .01 * max;
 
     result[0] = 0;
     result[M] = 0;
 
     for(n = 1; n < M; n++){
-        if(input[n] >= thresh){
+        if(input[n] >= threshold){
             if(input[n] > input[n - 1] && input[n] > input[n + 1]){
-                result[M + n] = q * (n + (p = .5 * (y = input[n-1] - 
+                result[M + n] = nyquist * (n + (p = .5 * (y = input[n-1] - 
 				(y3 = input[n+1])) / (input[n - 1] - 2 * 
 				    (y2 = input[n]) + input[n + 1])));
                 result[n] = y2 - .25 * (y - y3) * p;
@@ -344,12 +344,12 @@
     int n = (N >> 1), M = n; 
 
     const float *freqs, *amps;
-    float f0, thresh, ratio, nearest, distance;
+    float f0, threshold, ratio, nearest, distance;
 
     amps = data;
     freqs = data + n;
     f0 = *((float *)argv);
-    thresh = *((float *)argv+1);
+    threshold = *((float *)argv+1);
 
     ratio = nearest = distance = 0.f;
 
@@ -358,7 +358,7 @@
 	    ratio = freqs[n] / f0;
 	    nearest = round(ratio);
 	    distance = fabs(nearest - ratio);
-	    if(distance > thresh)
+	    if(distance > threshold)
 		result[n] = result[M + n] = 0.f;
 	    else {
 		result[n] = amps[n];
--- a/xtract/libxtract.h	Thu Jan 11 16:37:50 2007 +0000
+++ b/xtract/libxtract.h	Sun Jan 21 14:40:23 2007 +0000
@@ -112,6 +112,12 @@
     HARMONIC_SPECTRUM
 };
 
+/** \brief Enumeration of feature initialisation functions */
+enum feature_init_ {
+    INIT_MFCC = 100,
+    INIT_BARK
+};
+
 /** \brief Enumeration of feature types */
 enum feature_types_ {
     SCALAR,
@@ -146,14 +152,20 @@
 /** \brief Enumeration of data types*/
 typedef enum type_ {
     FLOAT,
+    FLOATARRAY,
     INT,
     MEL_FILTER
 } t_type;
 
 /** \brief Enumeration of units*/
 typedef enum unit_ {
-    HERTZ,
-    DBFS
+    /* NONE, ANY */
+    HERTZ = 2,
+    ANY_AMPLITUDE_HERTZ,
+    DBFS,
+    DBFS_HERTZ,
+    PERCENT,
+    SONE
 } t_unit;
 
 /** \brief Boolean */
@@ -217,6 +229,7 @@
 
     t_bool is_scalar;
 
+    /* The result.<> entries in descritors.c need to be checked */
     union {
 
 	struct {
--- a/xtract/xtract_macros.h	Thu Jan 11 16:37:50 2007 +0000
+++ b/xtract/xtract_macros.h	Sun Jan 21 14:40:23 2007 +0000
@@ -35,16 +35,29 @@
 #define MIN(a, b) ((a) < (b) ? (a) : (b))
 #define MAX(a, b) ((a) > (b) ? (a) : (b))
 #define NEEDS_FFTW printf("LibXtract must be compiled with fftw support to use this function.\n")
-#define CHECK_q if(!q) q = 44100.f / N
 
 #define VERY_SMALL_NUMBER 2e-42
 #define LOG_LIMIT VERY_SMALL_NUMBER
 #define LOG_LIMIT_DB -96
 #define DB_SCALE_OFFSET 96
 #define VERY_BIG_NUMBER 2e42
-#define SR_LIMIT 192000
+#define SR_UPPER_LIMIT 192000
+#define SR_LOWER_LIMIT 22050
+#define SR_DEFAULT 44100
+#define FUNDAMENTAL_DEFAULT 440
+#define CHECK_nyquist if(!nyquist) nyquist = SR_DEFAULT / N
+#define SR_LIMIT SR_UPPER_LIMIT
+#define FFT_BANDS_MIN 16
+#define FFT_BANDS_MAX 65536
+#define FFT_BANDS_DEF 1024
+#define SPEC_BW_MIN 0.168 /* Minimum spectral bandwidth (= SR_LOWER_LIMIT / \
+		      FFT_BANDS_MAX*/ 
+#define SPEC_BW_MAX 12000 /* SR_UPPER_LIMIT / FFT_BANDS_MIN */
+#define SPEC_BW_DEF 43.066 /* SR_DEFAULT / FFT_BANDS_DEF */
 #define BARK_BANDS 26
 #define NONE 0
+#define ANY -1
+#define UNKNOWN -2
 #define MAXARGS 4
 #define MAX_NAME_LENGTH 64
 #define MAX_AUTHOR_LENGTH 128
--- a/xtract/xtract_scalar.h	Thu Jan 11 16:37:50 2007 +0000
+++ b/xtract/xtract_scalar.h	Sun Jan 21 14:40:23 2007 +0000
@@ -220,7 +220,7 @@
  * 
  * \param *data: a pointer to the first element in an array of floats representing the magnitude coefficients from the spectrum of an audio vector, (e.g. the first half of the array pointed to by *result from xtract_spectrum().
  * \param N: the number of elements to be considered
- * \param *argv: a pointer to an array containing a floating point value representing the threshold for rolloff, i.e. the percentile at which the rolloff is determined, expressed in the range 0-1.0, and a float representing the sample rate in Hz
+ * \param *argv: a pointer to an array containing a float representing (samplerate / N ) and  a float representing the threshold for rolloff, i.e. the percentile at which the rolloff is determined, expressed as a percentage, and  
  * \param *result: the spectral rolloff in Hz of N values from the array pointed to by *data. This is the point in the spectrum below which argv[0] of the energy is distributed.
  */
 int xtract_rolloff(const float *data, const int N, const void *argv, float *result);
@@ -258,10 +258,10 @@
 
 /** \brief Extract the noisiness of an input vector using a method described by Tae Hong Park (2000)
  * 
- * \param *data: a pointer to the first element in an array of floats representing the magnitude coefficients from the spectrum of an audio vector, (e.g. the first half of the array pointed to by *result from xtract_spectrum().
- * \param N: the number of elements to be considered
- * \param *argv: a pointer to NULL
- * \param *result: the noisiness of N values from the array pointed to by *data
+ * \param *data: a pointer to NULL
+ * \param N: 
+ * \param *argv: a pointer to an array containing a float represnting the number of harmonic partials in a spectrum, and a float representing the number of partials in a spectrum
+ * \param *result: the noisiness coefficient as calculated from argv
  */
 int xtract_noisiness(const float *data, const int N, const void *argv, float *result);
 
@@ -285,9 +285,9 @@
 
 /** \brief Extract the spectral crest of an input vector using a method described by Peeters (2003)
  * 
- * \param *data: a pointer to the first element in an array of floats representing the magnitude coefficients from the spectrum of an audio vector, (e.g. the first half of the array pointed to by *result from xtract_spectrum().
- * \param N: the number of elements to be considered
- * \param *argv: a pointer to NULL
+ * \param *data: a pointer to NULL
+ * \param N: not used 
+ * \param *argv: a pointer to an array containing a float representing the maximum value in a spectrum, and a float representing the mean value of a spectrum
  * \param *result: the spectral crest of N values from the array pointed to by *data
  */
 int xtract_crest(const float *data, const int N, const void *argv, float *result);
@@ -306,7 +306,7 @@
  * 
  * \param *data: a pointer to the first element in an array of floats representing the frequencies of the harmonic spectrum of an audio vector. It is sufficient to pass in a pointer to the second half of the array pointed to by *result from xtract_harmonic_spectrum().
  * \param N: the number of elements to be considered. If using the array pointed to by *result from xtract_harmonics, N should equal half the total array size i.e., just the frequencies of the peaks.
- * \param *argv: a pointer to NULL
+ * \param *argv: a pointer to a float representing the fundamental frequency of the input vector.
  * \param *result: the odd/even harmonic ratio of N values from the array pointed to by *data
  */
 int xtract_odd_even_ratio(const float *data, const int N, const void *argv, float *result);
--- a/xtract/xtract_vector.h	Thu Jan 11 16:37:50 2007 +0000
+++ b/xtract/xtract_vector.h	Sun Jan 21 14:40:23 2007 +0000
@@ -112,11 +112,10 @@
 /** \brief Extract the amplitude and frequency of spectral peaks from a magnitude spectrum
  * \param *data: a pointer to an array of size N containing N/2 magnitude/power/log magnitude/log power coefficients and N/2 bin frequencies. (e.g. the first half of the array pointed to by *result from xtract_spectrum().
  * \param N: the size of the output array (note: the input array can be of size N/2, i.e. just the magnitudes)
- * \param *argv: a pointer to an array containing the peak threshold as percentage of the magnitude of the maximum peak found, and a float representing (samplerate / N)  
+ * \param *argv: a pointer to an array of floats, the first representing (samplerate / N), the second representing the peak threshold as percentage of the magnitude of the maximum peak found
  * \param *result: a pointer to an array of size N containing N/2 magnitude/power/log magnitude/log power coefficients and N/2 bin frequencies.
  *
  */
-
 int xtract_peak_spectrum(const float *data, const int N, const void *argv, float *result);
 
 /** \brief Extract the harmonic spectrum of from a of a peak spectrum