From 386b7d3366f1359a265da207a9cafa3edf553b64 Mon Sep 17 00:00:00 2001 From: Joshua Bakita Date: Mon, 7 Oct 2019 19:13:39 -0400 Subject: Reorganize and commit all the modified TACLeBench code and run scripts --- all_pairs/source/audiobeam/README | 86 + all_pairs/source/audiobeam/audiobeam.c | 594 +++ all_pairs/source/audiobeam/audiobeam.h | 50 + all_pairs/source/audiobeam/audiobeaminput.c | 5784 +++++++++++++++++++++++ all_pairs/source/audiobeam/audiobeamlibm.c | 423 ++ all_pairs/source/audiobeam/audiobeamlibm.h | 59 + all_pairs/source/audiobeam/audiobeamlibmalloc.c | 14 + all_pairs/source/audiobeam/audiobeamlibmalloc.h | 27 + all_pairs/source/audiobeam/audiobeamlibmath.h | 69 + all_pairs/source/audiobeam/changeLog.txt | 36 + all_pairs/source/audiobeam/license.txt | 21 + 11 files changed, 7163 insertions(+) create mode 100644 all_pairs/source/audiobeam/README create mode 100644 all_pairs/source/audiobeam/audiobeam.c create mode 100644 all_pairs/source/audiobeam/audiobeam.h create mode 100644 all_pairs/source/audiobeam/audiobeaminput.c create mode 100644 all_pairs/source/audiobeam/audiobeamlibm.c create mode 100644 all_pairs/source/audiobeam/audiobeamlibm.h create mode 100644 all_pairs/source/audiobeam/audiobeamlibmalloc.c create mode 100644 all_pairs/source/audiobeam/audiobeamlibmalloc.h create mode 100644 all_pairs/source/audiobeam/audiobeamlibmath.h create mode 100644 all_pairs/source/audiobeam/changeLog.txt create mode 100644 all_pairs/source/audiobeam/license.txt (limited to 'all_pairs/source/audiobeam') diff --git a/all_pairs/source/audiobeam/README b/all_pairs/source/audiobeam/README new file mode 100644 index 0000000..e228eda --- /dev/null +++ b/all_pairs/source/audiobeam/README @@ -0,0 +1,86 @@ +Readme file for Oxygen beamforming source code distribution +----------------------------------------------------------- + +This is a very very beta distribution of beamforming source code from +MIT LCS. + +There is only one source file, main.c, and one header file, +main.h. You can compile everything using the Makefile included in the +distribution. + +The input to the program is a text file containing floating +point values for the signal read on each of the microphones. For n +microphones, each line of the text files represents a temporal sample +and should contain n floating point values separated by spaces, e.g.: + +-1.8569790e-004 -9.0919049e-004 3.6711283e-004 -1.0073081e-005 ... + +There are several modes of operation for the program: + +1. The most basic mode is to process the microphone data and to +calculate the output based on one beam focused on a particular point +in space. The coordinates for the microphones and the focus point are +specified inside main.c (eventually to be moved to a separate file). + +2. Far field search mode. This mode assumes a far-field source (which +means we have a planar wavefront) and a linear array, and sweeps over +180 degrees in the plane of the array. The microphone coordinates are +specified in main.c, and the NUM_ANGLES constant defines how many +angle values should be tested (a value of 180 means one beam per each +degree). The energy of the signal over a particular window +(ANGLE_ENERGY_WINDOW_SIZE) is computed for each beam. The direction +with maximum energy is considered the direction that the speech signal +is coming from, and is printed out by the program. + +3. Near-field hill climbing mode. This mode accepts a starting +coordinate and attempts to "hill-climb" through the space seeking the +maximum energy. Each of the x, y, and z coordinates are perturbed in +the positive and negative directions at each time interval +(GRID_ENERGY_WINDOW_SIZE) by a step size (GRID_STEP_SIZE). This +perturbation, along with the original coordinate, produces seven +coordinates to be tested. The direction with the maximum energy +replaces the current reference coordinate. For instance, if we have a +starting reference coordinate of (1,1,0) and our step size is 0.01, we +will evaluate the energy for the following seven beams: + +(1,1,0) +(0.99,1,0) +(1.01,1,0) +(1,0.99,0) +(1,1.01,0) +(1,1,-0.01) +(1,1,0.01) + +Now let's say the beam (1,1.01,0) has the maximum energy; then this +coordinate will replace the original reference coordinate of (1,1,0). + +For methods 2, and 3, we are not outputting anything to disk, we are +just printing the result. This is because we have just started to work +with these methods, and have not applied them in real systems. This +code is currently being ported to RAW. + +To get a list of parameters for the delay_and_sum executable that is +generated when the source is compiled, just type ./delay_and_sum . + +There is some sample data included with the program, in the data +directory. There is some data for a near-field and far-field +source. The README.txt file in each directory specifies the microphone +and source position. The data1 file, when processed with a beamformer +aligned in the proper direction should produce something like a sinc +function (see +http://ccrma-www.stanford.edu/~jos/Interpolation/sinc_function.html). + +The data2 file should produce an audio signal of a woman saying "the +simplest method". If the beamformer is aligned properly, the noise +should be reduced significantly over the source signal from only one +of the microphones (use print_datafile.pl to isolate one +microphone). You can convert the data file that the program produces +to wave files using sox. + + + + + +--------------------------------- +Eugene Weinstein +ecoder@mit.edu \ No newline at end of file diff --git a/all_pairs/source/audiobeam/audiobeam.c b/all_pairs/source/audiobeam/audiobeam.c new file mode 100644 index 0000000..ed5d656 --- /dev/null +++ b/all_pairs/source/audiobeam/audiobeam.c @@ -0,0 +1,594 @@ +/* + + This program is part of the TACLeBench benchmark suite. + Version V 2.0 + + Name: audiobeam + + Author: Eugene Weinstein + + Function: Audio beam former + + Source: StreamIt + http://groups.csail.mit.edu/cag/streamit/ + + Changes: no functional changes + + License: see license.txt + +*/ + + +/* + Include section +*/ + +#include "../extra.h" +#include "audiobeamlibm.h" +#include "audiobeamlibmalloc.h" +#include "audiobeam.h" + +/* + Forward declaration of functions +*/ + +void audiobeam_init(); +int audiobeam_return(); +void audiobeam_main( void ); +//int main( void ); +void audiobeam_preprocess_delays( struct audiobeam_PreprocessedDelays + prep_delays[], float *delays ); +float *audiobeam_parse_line( float *float_arr, int num_mic ); +long int audiobeam_find_max_in_arr( float *arr, int size ); +long int audiobeam_find_min_in_arr( float *arr, int size ); +int audiobeam_wrapped_inc_offset( int i, int offset, int max_i ); +int audiobeam_wrapped_dec_offset( int i, int offset, int max_i ); +int audiobeam_wrapped_inc( int i, int max_i ); +int audiobeam_wrapped_dec( int i, int max_i ); +struct audiobeam_DataQueue *audiobeam_init_data_queue( int max_delay, + int num_mic ); +struct audiobeam_Delays *audiobeam_init_delays ( int num_angles, int num_mic ); +void audiobeam_calc_distances( float *source_location, + float audiobeam_mic_locations[15][3], + float *distances, + int num_mic ); +void audiobeam_calc_delays( float *distances, float *delays, int sound_speed, + int sampling_rate, int num_mic ); +void audiobeam_adjust_delays( float *delays, int num_mic ); +float *audiobeam_calc_weights_lr ( int num_mic ); +float *audiobeam_calc_weights_left_only ( int num_mic ); +float audiobeam_calculate_energy( float *samples, int num_samples ); +float audiobeam_do_beamforming( struct audiobeam_PreprocessedDelays + preprocessed_delays[], + float **sample_queue, + int queue_head, + long int max_delay, + int num_mic, + float *weights ); +int audiobeam_process_signal( struct audiobeam_Delays *delays, int num_mic, + float sampling_rate, float **beamform_results, + struct audiobeam_DataQueue *queue, + int num_beams, int window, float *weights ); +int audiobeam_calc_beamforming_result( struct audiobeam_Delays *delays, + float **beamform_results, + float *energies, + struct audiobeam_DataQueue *queue, + int num_beams, int window, + int hamming ); +void audiobeam_calc_single_pos( float source_location[3], + float audiobeam_mic_locations[15][3], + int hamming ); + + +/* + Declaration of global variables +*/ + +extern float audiobeam_input[5760]; +extern float audiobeam_mic_locations[15][3]; +extern float audiobeam_source_location[3]; +extern float audiobeam_origin_location[3]; +int audiobeam_input_pos; +int audiobeam_checksum; + + +/* + Initialization- and return-value-related functions +*/ + +void audiobeam_init() +{ + audiobeam_input_pos = 0; + audiobeam_checksum = 0; + + unsigned int i; + unsigned char *p; + volatile char bitmask = 0; + + /* + Apply volatile XOR-bitmask to entire input array. + */ + p = ( unsigned char * ) &audiobeam_input[ 0 ]; + _Pragma( "loopbound min 23040 max 23040" ) + for ( i = 0; i < sizeof( audiobeam_input ); ++i, ++p ) + *p ^= bitmask; + + p = ( unsigned char * ) &audiobeam_mic_locations[ 0 ]; + _Pragma( "loopbound min 180 max 180" ) + for ( i = 0; i < sizeof( audiobeam_mic_locations ); ++i, ++p ) + *p ^= bitmask; + + p = ( unsigned char * ) &audiobeam_source_location[ 0 ]; + _Pragma( "loopbound min 12 max 12" ) + for ( i = 0; i < sizeof( audiobeam_source_location ); ++i, ++p ) + *p ^= bitmask; + + p = ( unsigned char * ) &audiobeam_origin_location[ 0 ]; + _Pragma( "loopbound min 12 max 12" ) + for ( i = 0; i < sizeof( audiobeam_origin_location ); ++i, ++p ) + *p ^= bitmask; +} + + +int audiobeam_return() +{ + return ( audiobeam_checksum +1!= 0 ); +} + + +/* + Algorithm core functions +*/ + +void audiobeam_preprocess_delays( struct audiobeam_PreprocessedDelays + prep_delays[], float *delays ) +{ + int i; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < 15; i++ ) { + prep_delays[i].delay = delays[i]; + prep_delays[i].high = ( int ) audiobeam_ceil( delays[i] ); + prep_delays[i].low = ( int ) audiobeam_floor( delays[i] ); + prep_delays[i].offset = delays[i] - prep_delays[i].low; + } +} + + +float *audiobeam_parse_line( float *float_arr, int num_mic ) +{ + int i; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < num_mic; i++ ) + float_arr[i] = audiobeam_input[audiobeam_input_pos++]; + + return float_arr; +} + + +long int audiobeam_find_max_in_arr( float *arr, int size ) +{ + int i; + float max = 0; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < size; i++ ) { + if ( arr[i] > max ) + max = arr[i]; + } + + return audiobeam_ceil( max ); +} + + +long int audiobeam_find_min_in_arr( float *arr, int size ) +{ + int i; + float min = arr[0]; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < size; i++ ) { + if ( arr[i] < min ) + min = arr[i]; + } + + return audiobeam_floor( min ); +} + + +int audiobeam_wrapped_inc_offset( int i, int offset, int max_i ) +{ + if ( i + offset > max_i ) + return ( i + offset - max_i - 1 ); + else + return ( i + offset ); +} + + +int audiobeam_wrapped_dec_offset( int i, int offset, int max_i ) +{ + if ( i - offset < 0 ) + return ( max_i - ( offset - i ) + 1 ); + else + return ( i - offset ); +} + + +int audiobeam_wrapped_inc( int i, int max_i ) +{ + return audiobeam_wrapped_inc_offset( i, 1, max_i ); +} + + +int audiobeam_wrapped_dec( int i, int max_i ) +{ + return audiobeam_wrapped_dec_offset( i, 1, max_i ); +} + + +struct audiobeam_DataQueue *audiobeam_init_data_queue( int max_delay, + int num_mic ) +{ + int i, j; + + struct audiobeam_DataQueue *queue; + queue = ( struct audiobeam_DataQueue * ) audiobeam_malloc( sizeof( + struct audiobeam_DataQueue ) ); + queue->sample_queue = ( float ** ) audiobeam_malloc( ( max_delay + 1 ) + * sizeof( float * ) ); + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < ( max_delay + 1 ); i++ ) { + ( queue->sample_queue )[i] = ( float * ) audiobeam_malloc( num_mic + * sizeof( float ) ); + _Pragma( "loopbound min 15 max 15" ) + for ( j = 0; j < num_mic; j++ ) { + ( queue->sample_queue )[i][j] = 0.0; // Initialize values to 0 + } + } + + queue->head = 0; + queue->tail = 0; + queue->full = 0; + + return queue; +} + + +struct audiobeam_Delays *audiobeam_init_delays ( int num_angles, int num_mic ) +{ + struct audiobeam_Delays *delays; + int i; + + delays = ( struct audiobeam_Delays * ) audiobeam_malloc( sizeof( + struct audiobeam_Delays ) ); + + // Initialize the delays array + delays->delay_values = ( float ** ) audiobeam_malloc( num_angles + * sizeof( float * ) ); + + _Pragma( "loopbound min 1 max 1" ) + for ( i = 0; i < ( num_angles ); i++ ) { + delays->delay_values[i] = ( float * ) audiobeam_malloc( num_mic + * sizeof( float ) ); + } + + return delays; +} + +void audiobeam_calc_distances( float *source_location, + float audiobeam_mic_locations[15][3], + float *distances, + int num_mic ) +{ + int i; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < num_mic; i++ ) { + distances[i] = ( audiobeam_sqrt( ( audiobeam_mic_locations[i][0] + - source_location[0] ) * + ( audiobeam_mic_locations[i][0] + - source_location[0] ) + + ( audiobeam_mic_locations[i][1] + - source_location[1] ) * + ( audiobeam_mic_locations[i][1] + - source_location[1] ) + + ( audiobeam_mic_locations[i][2] + - source_location[2] ) * + ( audiobeam_mic_locations[i][2] + - source_location[2] ) ) ); + } +} + + +void audiobeam_calc_delays( float *distances, float *delays, int sound_speed, + int sampling_rate, int num_mic ) +{ + int i; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < num_mic; i++ ) + delays[i] = ( distances[i] / sound_speed ) * sampling_rate; +} + + +void audiobeam_adjust_delays( float *delays, int num_mic ) +{ + int i; + long int min_delay = audiobeam_find_min_in_arr ( delays, num_mic ) - 1; + + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < num_mic; i++ ) + delays[i] -= min_delay; +} + + +float *audiobeam_calc_weights_lr ( int num_mic ) +{ + float *weights = ( float * ) audiobeam_malloc( num_mic * sizeof( float ) ); + int index = 0; + int y, z; + + int half = num_mic / 4; + + _Pragma( "loopbound min 0 max 0" ) + for ( z = 1; z >= -1; z -= 2 ) { + _Pragma( "loopbound min 0 max 0" ) + for ( y = 0; y < half; y++ ) { + weights[index] = 0.54 + 0.46 * audiobeam_cos( audiobeam_M_PI * y + / half ); + index++; + } + _Pragma( "loopbound min 0 max 0" ) + for ( y = 0; y < half; y++ ) { + weights[index] = 0.54 + 0.46 * audiobeam_cos( audiobeam_M_PI * ( -y ) + / half ); + index++; + } + } + + return weights; +} + + +float *audiobeam_calc_weights_left_only ( int num_mic ) +{ + float *weights = ( float * ) audiobeam_malloc( num_mic * sizeof( float ) ); + int index = 0; + int y; + + int half = num_mic / 2; + + _Pragma( "loopbound min 15 max 15" ) + for ( y = -half; y <= half; y++ ) { + weights[index] = 0.54 + 0.46 * audiobeam_cos( audiobeam_M_PI * y / half ); + index++; + } + + return weights; +} + + +float audiobeam_calculate_energy( float *samples, int num_samples ) +{ + int i; + float sum = 0.0; + + _Pragma( "loopbound min 0 max 0" ) + for ( i = 0; i < num_samples; i++ ) + sum += ( samples[i] * samples[i] ); + + return sum; +} + + +float audiobeam_do_beamforming( struct audiobeam_PreprocessedDelays + preprocessed_delays[], + float **sample_queue, + int queue_head, + long int max_delay, + int num_mic, + float *weights ) +{ + int i; + float sum = 0; + int delay_floor; + int delay_ceil; + int low_index; + int high_index; + float interpolated_value; + + // add up all the num_mic delayed samples + _Pragma( "loopbound min 15 max 15" ) + for ( i = 0; i < num_mic; i++ ) { + delay_floor = preprocessed_delays[i].low; + delay_ceil = preprocessed_delays[i].high; + + // Inline wrap around here + // Low index gets index of sample right before desired sample + low_index = queue_head + delay_floor; + if ( low_index > max_delay ) + low_index -= ( max_delay + 1 ); + + // High index gets index of sample right after desired sample + high_index = queue_head + delay_ceil; + if ( high_index > max_delay ) + high_index -= ( max_delay + 1 ); + + // i gives the value of the microphone we want. However, since + // the array only has microphones first_mic to last_mic, we + // need to offset our index by first_mic + + interpolated_value = ( ( ( sample_queue[high_index][i] - + sample_queue[low_index][i] ) + * ( preprocessed_delays[i].offset ) ) + + sample_queue[low_index][i] ); + + // If we have microphone weights, multiply the value by the weight + if ( weights != 0 ) + sum += ( interpolated_value * weights[i] ); + else + sum += interpolated_value; + } + + return sum; + +} + + +int audiobeam_process_signal( struct audiobeam_Delays *delays, int num_mic, + float sampling_rate, float **beamform_results, + struct audiobeam_DataQueue *queue, + int num_beams, int window, float *weights ) +{ + int i, j; + float time_index = 0; + float time_index_inc = ( 1.0 / sampling_rate ); + + float value; + + int done = 0; + + struct audiobeam_PreprocessedDelays preprocessed_delays[15]; + + audiobeam_preprocess_delays( preprocessed_delays, delays->delay_values[0] ); + + _Pragma( "loopbound min 13 max 13" ) + for ( i = 0; i < delays->max_delay - 1; i++ ) { + if ( audiobeam_input_pos < 5760 ) + audiobeam_parse_line( ( queue->sample_queue )[queue->head], 15 ); + else + return -1; + queue->head = audiobeam_wrapped_inc( queue->head, delays->max_delay ); + } + _Pragma( "loopbound min 371 max 371" ) + for ( i = 0; ( i < window ) || ( window < 0 ) ; i++ ) { + if ( audiobeam_input_pos < 5760 ) + audiobeam_parse_line( ( queue->sample_queue )[queue->head], 15 ); + else { + done = 1; + break; + } + + _Pragma( "loopbound min 1 max 1" ) + for ( j = 0; j < num_beams; j++ ) { + value = audiobeam_do_beamforming( preprocessed_delays, + ( queue->sample_queue ), + audiobeam_wrapped_inc( queue->head, + delays->max_delay ), + delays->max_delay, num_mic, weights ); + + + value = value / num_mic; + + if ( beamform_results != 0 ) + beamform_results[j][i] = value; + } + + queue->tail = queue->head; + queue->head = audiobeam_wrapped_inc( queue->head, delays->max_delay ); + + time_index += time_index_inc; + } + + return ( done ); +} + + +int audiobeam_calc_beamforming_result( struct audiobeam_Delays *delays, + float **beamform_results, + float *energies, + struct audiobeam_DataQueue *queue, + int num_beams, int window, + int hamming ) +{ + int i; + int done; + float *weights = 0; + + if ( hamming ) { + if ( ( 15 % 2 ) == 1 ) + weights = audiobeam_calc_weights_left_only( 15 ); + else + weights = audiobeam_calc_weights_lr( 15 ); + } + + done = audiobeam_process_signal( delays, 15, 16000, + beamform_results, + queue, num_beams, window, weights ); + + if ( beamform_results != 0 ) { + _Pragma( "loopbound min 1 max 1" ) + for ( i = 0; i < num_beams; i++ ) + energies[i] = audiobeam_calculate_energy( beamform_results[i], window ); + } + return done; +} + + +void audiobeam_calc_single_pos( float source_location[3], + float audiobeam_mic_locations[15][3], + int hamming ) +{ + float mic_distances[15]; + struct audiobeam_Delays *delays = audiobeam_init_delays( 1, 15 ); + struct audiobeam_DataQueue *queue; + + float **beamform_results; + float *energies; + + beamform_results = ( float ** ) audiobeam_malloc( 1 * sizeof( float * ) ); + beamform_results[0] = ( float * ) audiobeam_malloc( 384 * sizeof( float ) ); + energies = ( float * ) audiobeam_malloc( 1 * sizeof( float * ) ); + + // Calculate distances from source to each of mics + audiobeam_calc_distances( source_location, audiobeam_mic_locations, + mic_distances, 15 ); + + audiobeam_calc_delays( mic_distances, + delays->delay_values[0], + 342, 16000, 15 ); + + audiobeam_adjust_delays( delays->delay_values[0], 15 ); + + delays->max_delay = audiobeam_find_max_in_arr ( delays->delay_values[0], 15 ); + + queue = audiobeam_init_data_queue( delays->max_delay, 15 ); + + audiobeam_calc_beamforming_result( delays, beamform_results, + energies, queue, 1, -1, hamming ); + + audiobeam_checksum += beamform_results[0][0] * 1000; +} + + +/* + Main functions +*/ + +void _Pragma( "entrypoint" ) audiobeam_main( void ) +{ + char hamming = 1; + audiobeam_calc_single_pos( audiobeam_source_location, + audiobeam_mic_locations, + hamming ); +} + + +int main( int argc, char **argv ) +{ + //SET_UP + int jobsComplete; + int maxJobs=100; + for (jobsComplete=-1; jobsComplete