NUMLUA_API int luaopen_numlua_fft (lua_State *L) { fftw_import_system_wisdom(); /* plan */ lua_newtable(L); /* metatable */ lua_pushvalue(L, -1); nl_register(L, plan_mt, 1); lua_pushliteral(L, PLAN_LIBNAME); lua_setfield(L, -2, "__type"); /* fft */ luaL_newlib(L, fft_func); lua_pushvalue(L, -2); /* plan metatable */ lua_pushcclosure(L, fft_plan, 1); lua_setfield(L, -2, "plan"); /* fft.plan */ lua_newtable(L); /* planner flags */ lua_pushinteger(L, FFTW_ESTIMATE); lua_setfield(L, -2, "estimate"); lua_pushinteger(L, FFTW_MEASURE); lua_setfield(L, -2, "measure"); lua_pushinteger(L, FFTW_PATIENT); lua_setfield(L, -2, "patient"); lua_pushinteger(L, FFTW_EXHAUSTIVE); lua_setfield(L, -2, "exhaustive"); lua_pushinteger(L, FFTW_WISDOM_ONLY); lua_setfield(L, -2, "wisdomonly"); lua_setfield(L, -2, "flag"); /* fft.flag */ return 1; }
static void gwy_process_import_fftw_wisdom(void) { #ifdef HAVE_FFTW3 G_GNUC_UNUSED gboolean ok; ok = fftw_import_system_wisdom(); gwy_debug("FFTW3 system wisdom imported: %d", ok); #endif }
/** * Find the mismatches without filtering. This is the complete method in the case where * the complexity is unbounded by k, but only applies in one case in the bounded method. * @TODO: Move this elsewhere; it doesn't apply just to unbounded. Perhaps the same for the above * @param text A character array containing the text * @param pattern A character array containing the pattern * @param n the length of the text * @param m the length of the pattern * @param k The threshold, k. If k < 0 or >= m hamming distance at all * alignments will be found * @param results. An unsigned array to store the hamming distance in. Must be * of size n-m+1. If NULL, results are printed to stdout. * @param numMatches an unsigned pointer to a location to store the number * of k-mismatches found. Note that if k < 0 or >= m this is just n-m. * @param sortedPattern. An array of charAndPosition structs, that is sorted but contain * indices of original location in the pattern * @param positionLookup. An int array of indexes into the sortedPattern saying where to find * the start of infrequent characters, or NOT_IN_PATTERN or FREQUENT_CHAR. */ void findMismatchesWithoutFiltering(char *text, char *pattern, int n, int m,int k, int *numMatches,struct SP_KM_MATCHING_POSITIONS *listOfMatches,unsigned flags, struct charAndPosition *sortedPattern,struct position *positionLookup){ int i; int transformSize = 2*m; if(transformSize < 2048 && n > 4096){ transformSize = 2048; } //Use double as we will compute Fourier Transform of this double *maskedPattern = (double *)fftw_malloc(sizeof(double)*transformSize); //Zero the top "half" of the masked pattern -- this will never be touched for(i=m;i<transformSize;i++){ maskedPattern[i] = 0.0; } //Repeat for text, except we mask potential "overflow" of chunks past n int overflowed = n + (transformSize - m); double *maskedText = (double *)fftw_malloc(sizeof(double)*overflowed); for(i=n;i<overflowed;i++){ maskedText[i] = 0.0; } //We will re-use plans across multiple masked patterns, so define these here fftw_plan forward = NULL; fftw_plan inverse =NULL; if(!fftw_import_system_wisdom()){ printf("Failed to read system wisdom!\n"); } //Create an array that we will use to add matches for each character at //each alignment int *matches = (int *) calloc(n-m+1,sizeof(int)); int positionInPattern; short charType; int numFFTMatches = 0; double numInfrequentComparisons = 0.0; for(i=0;i<n;i++){ charType = positionLookup[(int)text[i]].charType; positionInPattern = positionLookup[(int)text[i]].index; if(charType==FREQUENT_CHAR){ maskTextAndPattern(text,pattern,n,m,maskedText,maskedPattern,text[i]); printf("Frequent char %c\n",text[i]); computeNumMatchesWithFFT(maskedText,maskedPattern,n,m,transformSize,matches,&forward,&inverse); numFFTMatches++; //This will compute matches for ALL of the same character in the text, so now mark this as not occuring in the pattern positionLookup[(int)text[i]].charType=NOT_IN_PATTERN; }else if(charType ==INFREQUENT_CHAR){ //printf("Infrequent char %c\n",text[i]); //Loop though all of the up to O(threshold) characters that are infrequent while(positionInPattern < m && sortedPattern[positionInPattern].index <= i && sortedPattern[positionInPattern].c == text[i]){ // printf("i-sortedPattern[positionInPattern].index+1: %d\n",i-sortedPattern[positionInPattern].index+1); // printf("i: %d\n",i); // printf("sortedPattern[positionInPattern].index: %d\n",sortedPattern[positionInPattern].index); if(i-sortedPattern[positionInPattern].index < n-m+1){ matches[i-sortedPattern[positionInPattern].index]++; } positionInPattern++; numInfrequentComparisons++; } } } //printf("Calculated %d matches using Fourier Transforms\n",numFFTMatches); //printf("Performed %d (*c) comparisons for infrequent characters\n",(int)numInfrequentComparisons); //We now have matches, so we can compute (and output if necessary) mis-matches int hamDistance; for(i=0;i<n-m+1;i++){ hamDistance = m - matches[i]; if(hamDistance <= k){ (*numMatches)++; if(listOfMatches!=NULL){ sp_km_addToListOfMatches(listOfMatches,i,hamDistance); }else{ printf("Hamming distance at text[%d]: %d\n",i,hamDistance); } if(flags & SP_KM_FIRST_MATCH_ONLY){ return; } } } done(); free(matches); fftw_free(maskedPattern); fftw_free(maskedText); fftw_destroy_plan(forward); fftw_destroy_plan(inverse); fftw_forget_wisdom(); fftw_cleanup(); }
// Set up sync vector for search correlator // Use current estimates of sample rate void generate_sync(double symrate){ int ind,k; unsigned char data[10]; unsigned char symbols[2*8*10]; // The last 5 bytes (40 bits) of each 1024-bit minor frame are constants given below // Run them through the encoder and use the last 34 symbols as the sync vector // Those are the only invariant symbols from the encoder, after the user data has been flushed memset(data,0,sizeof(data)); data[0] = 0x12; data[1] = 0xfc; data[2] = 0x81; data[3] = 0x9f; data[4] = 0xbe; encode(symbols,data,10,0); #if 1 for(k=0;k<80;k++) printf(" %d",symbols[k]); printf("\n"); #endif // Update numbers based on current sample rate Symrate = symrate; Synclen = SYNCBITS * Symbolsamples + 1; // Fudge to prevent off-by-one overrun printf("Symbol rate: %'.3lf Hz; samples/sym: %'.3lf; samples/frame: %'.1lf; samples in sync: %'d\n", symrate,Samprate/symrate,2*FRAMEBITS*Symbolsamples,Synclen); if(Syncvector != NULL) free(Syncvector); if((Syncvector = malloc(sizeof(*Syncvector) * (int)Synclen)) == NULL){ fprintf(stderr,"Can't malloc sync vector\n"); exit(3); } // Manchester encode last 34 symbols in sequence ind = 0; for(k=0;k<SYNCBITS;k++){ // First half of manchester symbol for(;ind < (k+0.5) * Symbolsamples;ind++) Syncvector[ind] = symbols[k+80-SYNCBITS] ? -1 : 1; // Second half for(;ind < (k+1) * Symbolsamples;ind++) Syncvector[ind] = symbols[k+80-SYNCBITS] ? 1 : -1; } assert(ind <= Synclen); #if 0 for(k=0;k<Synclen;k++){ putchar(Syncvector[k] == 1 ? '+':'-'); } putchar('\n'); printf("sync vector done\n"); #endif // Set up FFT correlator Corr_size = 2*Framesamples; Corr_size = 1 << 20; // hack!! change to round Corr_size up to next power of 2 Corr_input = fftw_alloc_real(Corr_size); assert(Corr_input != NULL); Corr_vector = fftw_alloc_real(Corr_size); assert(Corr_vector != NULL); Corr_result = fftw_alloc_real(Corr_size); assert(Corr_result != NULL); Corr_vector_transform = fftw_alloc_complex(Corr_size); assert(Corr_vector_transform != NULL); Corr_data_transform = fftw_alloc_complex(Corr_size); assert(Corr_data_transform != NULL); fftw_import_system_wisdom(); Corr_ffr = fftw_plan_dft_c2r_1d(Corr_size,Corr_data_transform,Corr_result,FFTW_ESTIMATE); assert(Corr_ffr != NULL); Corr_ff2 = fftw_plan_dft_r2c_1d(Corr_size,Corr_input,Corr_data_transform,FFTW_ESTIMATE); assert(Corr_ff2 != NULL); Corr_ff1 = fftw_plan_dft_r2c_1d(Corr_size,Corr_vector,Corr_vector_transform,FFTW_ESTIMATE); // Load up the sync vector for(k=0;k<Synclen;k++) Corr_vector[k] = Syncvector[k]; // Zero pad for(;k<Corr_size;k++) Corr_vector[k] = 0; fftw_execute(Corr_ff1); // Compute transform of sync vector // Take complex conjugate so we don't have to do it every time for(k=0;k<Corr_size;k++) Corr_vector_transform[k] = conj(Corr_vector_transform[k]); }
/* ATS_SOUND *tracker (ANARGS *anargs, char *soundfile) * partial tracking function * anargs: pointer to analysis parameters * soundfile: path to input file * returns an ATS_SOUND with data issued from analysis */ ATS_SOUND *tracker (ANARGS *anargs, char *soundfile, char *resfile) { int fd, M_2, first_point, filptr, n_partials = 0; int frame_n, k, sflen, *win_samps, peaks_size, tracks_size = 0; int i, frame, i_tmp; float *window, norm, sfdur, f_tmp; /* declare structures and buffers */ ATS_SOUND *sound = NULL; ATS_PEAK *peaks, *tracks = NULL, cpy_peak; ATS_FRAME *ana_frames = NULL, *unmatched_peaks = NULL; mus_sample_t **bufs; ATS_FFT fft; #ifdef FFTW fftw_plan plan; FILE *fftw_wisdom_file; #endif /* open input file we get srate and total_samps in file in anargs */ if ((fd = mus_sound_open_input(soundfile))== -1) { fprintf(stderr, "%s: %s\n", soundfile, strerror(errno)); return(NULL); } /* warn about multi-channel sound files */ if (mus_sound_chans(soundfile) > 1) { fprintf(stderr, "Error: file has %d channels, must be mono!\n", mus_sound_chans(soundfile)); return(NULL); } fprintf(stderr, "tracking...\n"); /* get sample rate and # of frames from file header */ anargs->srate = mus_sound_srate(soundfile); sflen = mus_sound_frames(soundfile); sfdur = (float)sflen/anargs->srate; /* check analysis parameters */ /* check start time */ if( !(anargs->start >= 0.0 && anargs->start < sfdur) ){ fprintf(stderr, "Warning: start %f out of bounds, corrected to 0.0\n", anargs->start); anargs->start = (float)0.0; } /* check duration */ if(anargs->duration == ATSA_DUR) { anargs->duration = sfdur - anargs->start; } f_tmp = anargs->duration + anargs->start; if( !(anargs->duration > 0.0 && f_tmp <= sfdur) ){ fprintf(stderr, "Warning: duration %f out of bounds, limited to file duration\n", anargs->duration); anargs->duration = sfdur - anargs->start; } /* print time bounds */ fprintf(stderr, "start: %f duration: %f file dur: %f\n", anargs->start, anargs->duration , sfdur); /* check lowest frequency */ if( !(anargs->lowest_freq > 0.0 && anargs->lowest_freq < anargs->highest_freq)){ fprintf(stderr, "Warning: lowest freq. %f out of bounds, forced to default: %f\n", anargs->lowest_freq, ATSA_LFREQ); anargs->lowest_freq = ATSA_LFREQ; } /* check highest frequency */ if( !(anargs->highest_freq > anargs->lowest_freq && anargs->highest_freq <= anargs->srate * 0.5 )){ fprintf(stderr, "Warning: highest freq. %f out of bounds, forced to default: %f\n", anargs->highest_freq, ATSA_HFREQ); anargs->highest_freq = ATSA_HFREQ; } /* frequency deviation */ if( !(anargs->freq_dev > 0.0 && anargs->freq_dev < 1.0) ){ fprintf(stderr, "Warning: freq. dev. %f out of bounds, should be > 0.0 and <= 1.0, forced to default: %f\n", anargs->freq_dev, ATSA_FREQDEV); anargs->freq_dev = ATSA_FREQDEV; } /* window cycles */ if( !(anargs->win_cycles >= 1 && anargs->win_cycles <= 8) ){ fprintf(stderr, "Warning: windows cycles %d out of bounds, should be between 1 and 8, forced to default: %d\n", anargs->win_cycles, ATSA_WCYCLES); anargs->win_cycles = ATSA_WCYCLES; } /* window type */ if( !(anargs->win_type >= 0 && anargs->win_type <= 3) ){ fprintf(stderr, "Warning: window type %d out of bounds, should be between 0 and 3, forced to default: %d\n", anargs->win_type, ATSA_WTYPE); anargs->win_type = ATSA_WTYPE; } /* hop size */ if( !(anargs->hop_size > 0.0 && anargs->hop_size <= 1.0) ){ fprintf(stderr, "Warning: hop size %f out of bounds, should be > 0.0 and <= 1.0, forced to default: %f\n", anargs->hop_size, ATSA_HSIZE); anargs->hop_size = ATSA_HSIZE; } /* lowest mag */ if( !(anargs->lowest_mag <= 0.0) ){ fprintf(stderr, "Warning: lowest magnitude %f out of bounds, should be >= 0.0 and <= 1.0, forced to default: %f\n", anargs->lowest_mag, ATSA_LMAG); anargs->lowest_mag = ATSA_LMAG; } /* set some values before checking next set of parameters */ anargs->first_smp = (int)floor(anargs->start * (float)anargs->srate); anargs->total_samps = (int)floor(anargs->duration * (float)anargs->srate); /* fundamental cycles */ anargs->cycle_smp = (int)floor((double)anargs->win_cycles * (double)anargs->srate / (double)anargs->lowest_freq); /* window size */ anargs->win_size = (anargs->cycle_smp % 2 == 0) ? anargs->cycle_smp+1 : anargs->cycle_smp; /* calculate hop samples */ anargs->hop_smp = floor( (float)anargs->win_size * anargs->hop_size ); /* compute total number of frames */ anargs->frames = compute_frames(anargs); /* check that we have enough frames for the analysis */ if( !(anargs->frames >= ATSA_MFRAMES) ){ fprintf(stderr, "Error: %d frames are not enough for analysis, nead at least %d\n", anargs->frames , ATSA_MFRAMES); return(NULL); } /* check other user parameters */ /* track length */ if( !(anargs->track_len >= 1 && anargs->track_len < anargs->frames) ){ i_tmp = (ATSA_TRKLEN < anargs->frames) ? ATSA_TRKLEN : anargs->frames-1; fprintf(stderr, "Warning: track length %d out of bounds, forced to: %d\n", anargs->track_len , i_tmp); anargs->track_len = i_tmp; } /* min. segment length */ if( !(anargs->min_seg_len >= 1 && anargs->min_seg_len < anargs->frames) ){ i_tmp = (ATSA_MSEGLEN < anargs->frames) ? ATSA_MSEGLEN : anargs->frames-1; fprintf(stderr, "Warning: min. segment length %d out of bounds, forced to: %d\n", anargs->min_seg_len, i_tmp); anargs->min_seg_len = i_tmp; } /* min. gap length */ if( !(anargs->min_gap_len >= 0 && anargs->min_gap_len < anargs->frames) ){ i_tmp = (ATSA_MGAPLEN < anargs->frames) ? ATSA_MGAPLEN : anargs->frames-1; fprintf(stderr, "Warning: min. gap length %d out of bounds, forced to: %d\n", anargs->min_gap_len, i_tmp); anargs->min_gap_len = i_tmp; } /* SMR threshold */ if( !(anargs->SMR_thres >= 0.0 && anargs->SMR_thres < ATSA_MAX_DB_SPL) ){ fprintf(stderr, "Warning: SMR threshold %f out of bounds, shoul be >= 0.0 and < %f dB SPL, forced to default: %f\n", anargs->SMR_thres, ATSA_MAX_DB_SPL, ATSA_SMRTHRES); anargs->SMR_thres = ATSA_SMRTHRES; } /* min. seg. SMR */ if( !(anargs->min_seg_SMR >= anargs->SMR_thres && anargs->min_seg_SMR < ATSA_MAX_DB_SPL) ){ fprintf(stderr, "Warning: min. seg. SMR %f out of bounds, shoul be >= %f and < %f dB SPL, forced to default: %f\n", anargs->min_seg_SMR, anargs->SMR_thres, ATSA_MAX_DB_SPL, ATSA_MSEGSMR); anargs->min_seg_SMR = ATSA_MSEGSMR; } /* last peak contibution */ if( !(anargs->last_peak_cont >= 0.0 && anargs->last_peak_cont <= 1.0) ){ fprintf(stderr, "Warning: last peak contibution %f out of bounds, should be >= 0.0 and <= 1.0, forced to default: %f\n", anargs->last_peak_cont, ATSA_LPKCONT); anargs->last_peak_cont = ATSA_LPKCONT; } /* SMR cont. */ if( !(anargs->SMR_cont >= 0.0 && anargs->SMR_cont <= 1.0) ){ fprintf(stderr, "Warning: SMR contibution %f out of bounds, should be >= 0.0 and <= 1.0, forced to default: %f\n", anargs->SMR_cont, ATSA_SMRCONT); anargs->SMR_cont = ATSA_SMRCONT; } /* continue computing parameters */ /* fft size */ anargs->fft_size = ppp2(2*anargs->win_size); /* allocate memory for sound, we read the whole sound in memory */ bufs = (mus_sample_t **)malloc(sizeof(mus_sample_t*)); bufs[0] = (mus_sample_t *)malloc(sflen * sizeof(mus_sample_t)); /* bufs = malloc(sizeof(mus_sample_t*)); bufs[0] = malloc(sflen * sizeof(mus_sample_t)); */ /* make our window */ window = make_window(anargs->win_type, anargs->win_size); /* get window norm */ norm = window_norm(window, anargs->win_size); /* fft mag for computing frequencies */ anargs->fft_mag = (double)anargs->srate / (double)anargs->fft_size; /* lowest fft bin for analysis */ anargs->lowest_bin = floor( anargs->lowest_freq / anargs->fft_mag ); /* highest fft bin for analisis */ anargs->highest_bin = floor( anargs->highest_freq / anargs->fft_mag ); /* allocate an array analysis frames in memory */ ana_frames = (ATS_FRAME *)malloc(anargs->frames * sizeof(ATS_FRAME)); /* alocate memory to store mid-point window sample numbers */ win_samps = (int *)malloc(anargs->frames * sizeof(int)); /* center point of window */ M_2 = floor((anargs->win_size - 1) / 2); /* first point in fft buffer to write */ first_point = anargs->fft_size - M_2; /* half a window from first sample */ filptr = anargs->first_smp - M_2; /* read sound into memory */ mus_sound_read(fd, 0, sflen-1, 1, bufs); /* make our fft-struct */ fft.size = anargs->fft_size; fft.rate = anargs->srate; #ifdef FFTW fft.data = fftw_malloc(sizeof(fftw_complex) * fft.size); if(fftw_import_system_wisdom()) fprintf(stderr, "system wisdom loaded!\n"); else fprintf(stderr, "cannot locate system wisdom!\n"); if((fftw_wisdom_file = fopen("ats-wisdom", "r")) != NULL) { fftw_import_wisdom_from_file(fftw_wisdom_file); fprintf(stderr, "ats-wisdom loaded!\n"); fclose(fftw_wisdom_file); } else fprintf(stderr, "cannot locate ats-wisdom!\n"); plan = fftw_plan_dft_1d(fft.size, fft.data, fft.data, FFTW_FORWARD, FFTW_PATIENT); #else fft.fdr = (double *)malloc(anargs->fft_size * sizeof(double)); fft.fdi = (double *)malloc(anargs->fft_size * sizeof(double)); #endif /* main loop */ for (frame_n=0; frame_n<anargs->frames; frame_n++) { /* clear fft arrays */ #ifdef FFTW for(k=0; k<fft.size; k++) fft.data[k][0] = fft.data[k][1] = 0.0f; #else for(k=0; k<fft.size; k++) fft.fdr[k] = fft.fdi[k] = 0.0f; #endif /* multiply by window */ for (k=0; k<anargs->win_size; k++) { if ((filptr >= 0) && (filptr < sflen)) #ifdef FFTW fft.data[(k+first_point)%fft.size][0] = window[k] * MUS_SAMPLE_TO_FLOAT(bufs[0][filptr]); #else fft.fdr[(k+first_point)%anargs->fft_size] = window[k] * MUS_SAMPLE_TO_FLOAT(bufs[0][filptr]); #endif filptr++; } /* we keep sample numbers of window midpoints in win_samps array */ win_samps[frame_n] = filptr - M_2 - 1; /* move file pointer back */ filptr = filptr - anargs->win_size + anargs->hop_smp; /* take the fft */ #ifdef FFTW fftw_execute(plan); #else fft_slow(fft.fdr, fft.fdi, fft.size, 1); #endif /* peak detection */ peaks_size = 0; peaks = peak_detection(&fft, anargs->lowest_bin, anargs->highest_bin, anargs->lowest_mag, norm, &peaks_size); /* peak tracking */ if (peaks != NULL) { /* evaluate peaks SMR (masking curves) */ evaluate_smr(peaks, peaks_size); if (frame_n) { /* initialize or update tracks */ if ((tracks = update_tracks(tracks, &tracks_size, anargs->track_len, frame_n, ana_frames, anargs->last_peak_cont)) != NULL) { /* do peak matching */ unmatched_peaks = peak_tracking(tracks, &tracks_size, peaks, &peaks_size, anargs->freq_dev, 2.0 * anargs->SMR_cont, &n_partials); /* kill unmatched peaks from previous frame */ if(unmatched_peaks[0].peaks != NULL) { for(k=0; k<unmatched_peaks[0].n_peaks; k++) { cpy_peak = unmatched_peaks[0].peaks[k]; cpy_peak.amp = cpy_peak.smr = 0.0; peaks = push_peak(&cpy_peak, peaks, &peaks_size); } free(unmatched_peaks[0].peaks); } /* give birth to peaks from new frame */ if(unmatched_peaks[1].peaks != NULL) { for(k=0; k<unmatched_peaks[1].n_peaks; k++) { tracks = push_peak(&unmatched_peaks[1].peaks[k], tracks, &tracks_size); unmatched_peaks[1].peaks[k].amp = unmatched_peaks[1].peaks[k].smr = 0.0; ana_frames[frame_n-1].peaks = push_peak(&unmatched_peaks[1].peaks[k], ana_frames[frame_n-1].peaks, &ana_frames[frame_n-1].n_peaks); } free(unmatched_peaks[1].peaks); } } else { /* give number to all peaks */ qsort(peaks, peaks_size, sizeof(ATS_PEAK), peak_frq_inc); for(k=0; k<peaks_size; k++) peaks[k].track = n_partials++; } } else { /* give number to all peaks */ qsort(peaks, peaks_size, sizeof(ATS_PEAK), peak_frq_inc); for(k=0; k<peaks_size; k++) peaks[k].track = n_partials++; } /* attach peaks to ana_frames */ ana_frames[frame_n].peaks = peaks; ana_frames[frame_n].n_peaks = n_partials; ana_frames[frame_n].time = (double)(win_samps[frame_n] - anargs->first_smp) / (double)anargs->srate; /* free memory */ free(unmatched_peaks); } else { /* if no peaks found, initialize empty frame */ ana_frames[frame_n].peaks = NULL; ana_frames[frame_n].n_peaks = 0; ana_frames[frame_n].time = (double)(win_samps[frame_n] - anargs->first_smp) / (double)anargs->srate; } } /* free up some memory */ free(window); free(tracks); #ifdef FFTW fftw_destroy_plan(plan); fftw_free(fft.data); #else free(fft.fdr); free(fft.fdi); #endif /* init sound */ fprintf(stderr, "Initializing ATS data..."); sound = (ATS_SOUND *)malloc(sizeof(ATS_SOUND)); init_sound(sound, anargs->srate, (int)(anargs->hop_size * anargs->win_size), anargs->win_size, anargs->frames, anargs->duration, n_partials, ((anargs->type == 3 || anargs->type == 4) ? 1 : 0)); /* store values from frames into the arrays */ for(k=0; k<n_partials; k++) { for(frame=0; frame<sound->frames; frame++) { sound->time[k][frame] = ana_frames[frame].time; for(i=0; i<ana_frames[frame].n_peaks; i++) if(ana_frames[frame].peaks[i].track == k) { sound->amp[k][frame] = ana_frames[frame].peaks[i].amp; sound->frq[k][frame] = ana_frames[frame].peaks[i].frq; sound->pha[k][frame] = ana_frames[frame].peaks[i].pha; sound->smr[k][frame] = ana_frames[frame].peaks[i].smr; } } } fprintf(stderr, "done!\n"); /* free up ana_frames memory */ /* first, free all peaks in each slot of ana_frames... */ for (k=0; k<anargs->frames; k++) free(ana_frames[k].peaks); /* ...then free ana_frames */ free(ana_frames); /* optimize sound */ optimize_sound(anargs, sound); /* compute residual */ if( anargs->type == 3 || anargs->type == 4 ) { fprintf(stderr, "Computing residual..."); compute_residual(bufs, sflen, resfile, sound, win_samps, anargs->srate); fprintf(stderr, "done!\n"); } /* free the rest of the memory */ free(win_samps); free(bufs[0]); free(bufs); /* analyze residual */ if( anargs->type == 3 || anargs->type == 4 ) { fprintf(stderr, "Analyzing residual..."); residual_analysis(ATSA_RES_FILE, sound); fprintf(stderr, "done!\n"); } #ifdef FFTW fftw_wisdom_file = fopen("ats-wisdom", "w"); fftw_export_wisdom_to_file(fftw_wisdom_file); fclose(fftw_wisdom_file); #endif fprintf(stderr, "tracking completed.\n"); return(sound); }
/** * Main function * * Reads command line specifying input and output files, and optionally wisdom file, * measure level, and flag preventing import of system wide wisdom, and then creates * plans for each problem specified in the input file. Accumulated wisdom is written * to the output file, and a human readable description of the plans successfully * created is written to stdout. Any warnings or errors are written to stderr. */ int main(int argc, char **argv) { static int measurelvl=3; static int nosys=0; UINT4 transform_size; char input_line[LINE_MAX]; char type; char direc; FILE *infp=NULL, *outfp=NULL, *wisfp=NULL; int optindex, optreturn, retval; static struct LALoption long_options[] = { /* Options setting flags */ {"no-system-wisdom",no_argument,&nosys,1}, /* Options specifying input/output */ {"input",required_argument,NULL,'i'}, {"output",required_argument,NULL,'o'}, {"wisdom",required_argument,NULL,'w'}, {"measurelvl",required_argument,NULL,'l'}, {"help",no_argument,NULL,'h'}, {0,0,0,0} }; while ( (optreturn = LALgetopt_long(argc,argv,"ni:o:w:l:h",long_options,&optindex)) != -1) { switch(optreturn) { case 0: break; /* Everything done in setting flag */ case 'n': nosys=1; break; case 'i': infp = LALFopen(LALoptarg,"r+"); if (!infp) { fprintf(stderr,"Error: Could not open input file %s\n",LALoptarg); if (outfp) LALFclose(outfp); exit(EXIT_FAILURE); } break; case 'o': outfp = LALFopen(LALoptarg,"w+"); if (!outfp) { fprintf(stderr,"Error: Could not open output file %s\n",LALoptarg); if (infp) LALFclose(infp); exit(EXIT_FAILURE); } break; case 'w': wisfp = LALFopen(LALoptarg,"r+"); if (!wisfp) { fprintf(stderr,"Error: Could not open input wisdom file %s for reading\n",LALoptarg); if (infp) LALFclose(infp); if (outfp) LALFclose(outfp); exit(EXIT_FAILURE); } else { retval = fftw_import_wisdom_from_file(wisfp); if (!retval) { /* Retval is zero if UNsuccessful */ fprintf(stderr,"Error: Could not read wisdom from input wisdom file %s\n",LALoptarg); if (infp) LALFclose(infp); if (outfp) LALFclose(outfp); LALFclose(wisfp); exit(EXIT_FAILURE); } LALFclose(wisfp); } fprintf(stderr,"Read in existing wisdom from file %s\n",LALoptarg); break; case 'l': if ( sscanf(LALoptarg,"%d",&measurelvl) != 1) { fprintf(stderr,"Error: invalid measure level %s.\n",LALoptarg); if (infp) LALFclose(infp); if (outfp) LALFclose(outfp); exit(EXIT_FAILURE); } if ( (measurelvl<0) || (measurelvl>3) ) { fprintf(stderr,"Error: invalid measure level %d.\n",measurelvl); if (infp) LALFclose(infp); if (outfp) LALFclose(outfp); } break; case 'h': /* Fall through */ case '?': print_help(); break; default: exit(EXIT_FAILURE); } /* switch(optreturn) */ } /* while(optreturn != -1) */ /* Check to make sure mandatory options were given */ if (!infp) { fprintf(stderr,"Error: You must specify an input file with -i <FILE> or --input=<FILE>\n"); if (outfp) LALFclose(outfp); exit(EXIT_FAILURE); } if (!outfp) { fprintf(stderr,"Error: You must specify an output file with -o <FILE> or --output=<FILE>\n"); if (infp) LALFclose(infp); exit(EXIT_FAILURE); } /* Only after processing all options do we know if we should read in system wisdom file */ if (!nosys) { retval = fftw_import_system_wisdom(); if (!retval) { /* Retval is zero if UNsuccessful */ fprintf(stderr,"Warning: Could not import system wisdom file /etc/fftw/wisdom\n"); } } else { fprintf(stderr,"Skipped import of system wisdom file /etc/fftw/wisdom\n"); } /* Process the input file */ while ( (fgets(input_line,LINE_MAX,infp) != NULL) ) { if (sscanf(input_line,"%c%c%" LAL_UINT4_FORMAT, &type, &direc, &transform_size) == 3) { /* Yes, it's ugly, but we don't have to worry about locales: */ if ( !( (type=='r') || (type=='R') || (type=='c') || (type=='C') ) ) { fprintf(stderr,"Error: Invalid type specifier %c; must be 'r' (real) or 'c' (complex). ",type); fprintf(stderr,"Problem %c%c%" LAL_UINT4_FORMAT " will be skipped!\n", type, direc, transform_size); } else if ( !( (direc=='f') || (direc=='b') || (direc=='r') || (direc=='F') || (direc=='B') || (direc=='R') ) ) { fprintf(stderr,"Error: Invalid direction specifier %c; must be 'f' (forward) or 'b'/'r' (backward/reverse). ", direc); fprintf(stderr,"Problem %c%c%" LAL_UINT4_FORMAT " will be skipped!\n",type,direc,transform_size); } else { retval = plan_problem(type,direc,transform_size,measurelvl); if (retval) { fprintf(stderr,"Unable to create plan %c%c%" LAL_UINT4_FORMAT "; skipping!\n", type,direc,transform_size); } else { fprintf(stdout,"Created double-precision %s %s plan, size %" LAL_UINT4_FORMAT " with measure level %d and FFTW_UNALIGNED\n", ( (type=='r') || (type=='R') ) ? "REAL4" : "COMPLEX8", ( (direc=='f') || (direc=='F') ) ? "forward" : "reverse", transform_size, measurelvl); } } } else { fprintf(stderr,"Error: Invalid problem specifier. Problem: %s will be skipped\n",input_line); } } fftw_export_wisdom_to_file(outfp); LALFclose(infp); LALFclose(outfp); exit(EXIT_SUCCESS); }
int main(int argc,char **args) { Vec x, b, u, u2; Mat A, L, PL; KSP ksp; // PC pc; PetscReal norm; PetscInt m1 = 5, m = 8,n = 7, p=1, d=0, dd, its; PetscErrorCode ierr; // PetscTruth user_defined_pc, user_defined_mat; ierr = PetscInitialize(&argc,&args,(char *)0,help); CHKERRQ(ierr); ierr = fftw_import_system_wisdom(); CHKERRQ(ierr); ierr = PetscOptionsGetInt(PETSC_NULL,"-m1",&m1,PETSC_NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(PETSC_NULL,"-m",&m,PETSC_NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(PETSC_NULL,"-n",&n,PETSC_NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(PETSC_NULL,"-p",&p,PETSC_NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(PETSC_NULL,"-d",&d,PETSC_NULL);CHKERRQ(ierr); if (n == 1) dd = 1; else if (p == 1) dd = 2; else dd = 3; int dim[] = { m, n, p }; // ierr = VecCreate(PETSC_COMM_WORLD, &u2);CHKERRQ(ierr); // ierr = VecSetSizes(u2, PETSC_DECIDE, m * n);CHKERRQ(ierr); // ierr = VecSetFromOptions(u2);CHKERRQ(ierr); ierr = VecCreateSeq(PETSC_COMM_WORLD, m * n * p, &u); CHKERRQ(ierr); ierr = VecDuplicate(u, &b);CHKERRQ(ierr); ierr = VecDuplicate(u, &u2);CHKERRQ(ierr); ierr = VecDuplicate(u, &x);CHKERRQ(ierr); ierr = MatCreateCheb(PETSC_COMM_WORLD, dd, d, dim, FFTW_ESTIMATE, x, b, &A); CHKERRQ(ierr); ierr = MatPoissonCreate(PETSC_COMM_WORLD, dd, dim, FFTW_ESTIMATE, x, b, &L); CHKERRQ(ierr); ierr = AssemblePoissonPC2(m, n, &PL); CHKERRQ(ierr); if (false) { PetscTruth flag; ierr = MatIsSymmetric(PL, 1e-4, &flag); CHKERRQ(ierr); printf("Symmetric? %d\n", flag); } ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); ierr = KSPSetOperators(ksp,L,PL,DIFFERENT_NONZERO_PATTERN);CHKERRQ(ierr); ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); // 3-D solution function double *uu, *uu2; ierr = VecGetArray(u, &uu); CHKERRQ(ierr); ierr = VecGetArray(u2, &uu2); CHKERRQ(ierr); for (int i=0; i < m; i++) { double x = (m==1) ? 0 : cos (i * PI / (m-1)); for (int j=0; j < n; j++) { double y = (n==1) ? 0 : cos (j * PI / (n-1)); for (int k=0; k < p; k++) { // double z = (p==1) ? 0 : cos (k * PI / (p-1)); int ix = (i*n + j) * p + k; uu[ix] = cos(0.5 * PI * x) * cos (0.5 * PI * y); uu2[ix] = 0.5 * PI * PI * uu[ix]; // uu[ix] = pow(x, 4) * pow(y, 3) + pow(y, 5); // uu2[ix] = -(4 * 3 * pow(x, 2) * pow(y, 3) + 3 * 2 * pow(x,4) * y + 5 * 4 * pow(y, 3)); //uu[ix] = } } } ierr = VecRestoreArray(u, &uu); CHKERRQ(ierr); ierr = VecRestoreArray(u2, &uu2); CHKERRQ(ierr); ierr = VecCopy(u2, b); CHKERRQ(ierr); #if 0 ierr = MatMult(PL, u, x); CHKERRQ(ierr); //ierr = VecCopy(b, x); CHKERRQ(ierr); ierr = VecView(x, PETSC_VIEWER_STDOUT_SELF); CHKERRQ(ierr); printf("\n"); ierr = VecView(u2, PETSC_VIEWER_STDOUT_SELF); CHKERRQ(ierr); printf("\n"); ierr = VecAXPY(x, -1.0, u2);CHKERRQ(ierr); ierr = VecNorm(x, NORM_INFINITY, &norm);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm of error %A\n",norm);CHKERRQ(ierr); #endif // ierr = MatMult(L, u, b); CHKERRQ(ierr); #if BC { // Set up boundary conditions double *uu, *bb; const int m = dim[0], n = dim[1]; ierr = VecGetArray(u, &uu); CHKERRQ(ierr); ierr = VecGetArray(b, &bb); CHKERRQ(ierr); for (int i = 0; i < m; i++) { int ix0 = i * n + 0; int ixn = i * n + n - 1; bb[ix0] = uu[ix0]; bb[ixn] = uu[ixn]; } for (int j = 0; j < n; j++) { int ix0 = 1 * n + j; int ixn = (m-2) * n + j; bb[ix0] = uu[ix0]; bb[ixn] = uu[ixn]; } ierr = VecRestoreArray(u, &uu); CHKERRQ(ierr); ierr = VecRestoreArray(b, &bb); CHKERRQ(ierr); } #endif #if SOLVE ierr = VecSet(x, 0.0); CHKERRQ(ierr); ierr = KSPSolve(ksp, b, x); CHKERRQ(ierr); /* ierr = VecView(b, PETSC_VIEWER_STDOUT_SELF); CHKERRQ(ierr); */ /* printf("\n"); */ /* ierr = VecView(u, PETSC_VIEWER_STDOUT_SELF); CHKERRQ(ierr); */ /* printf("\n"); */ /* ierr = VecView(x, PETSC_VIEWER_STDOUT_SELF); CHKERRQ(ierr); */ /* printf("\n"); */ ierr = VecAXPY(x, -1.0, u); CHKERRQ(ierr); ierr = VecNorm(x, NORM_INFINITY, &norm); CHKERRQ(ierr); ierr = KSPGetIterationNumber(ksp, &its); CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD, "Norm of error %A iterations %D\n", norm, its); CHKERRQ(ierr); // ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm of error %A\n",norm);CHKERRQ(ierr); #endif /* Free work space. All PETSc objects should be destroyed when they are no longer needed. */ ierr = KSPDestroy(ksp);CHKERRQ(ierr); ierr = VecDestroy(u);CHKERRQ(ierr); ierr = VecDestroy(x);CHKERRQ(ierr); ierr = VecDestroy(b);CHKERRQ(ierr); ierr = MatDestroy(A);CHKERRQ(ierr); /* if (user_defined_pc) { */ /* ierr = SampleShellPCDestroy(shell);CHKERRQ(ierr); */ /* } */ ierr = PetscFinalize();CHKERRQ(ierr); return 0; }