diff options
author | Lu, Han <han.lu@intel.com> | 2016-02-29 10:33:45 +0800 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2016-03-01 10:31:00 +0100 |
commit | 380c9fa444e88f259c6cdc51b18365b80f73c17b (patch) | |
tree | 4713614047bf9e00978b788d6e2759f659e37ec3 | |
parent | 84fa5bf945e6a366890c835810c6be5222db31ac (diff) | |
download | alsa-utils-380c9fa444e88f259c6cdc51b18365b80f73c17b.tar.gz |
alsabat: truncate sample frames for faster FFT analysis
Truncate the sample frames to powers of 2, since the FFTW algorithm
runs especially fast in this case, and other sizes may be computed
by means of a slow, general-purpose algorithm.
In my test environment applying the patch, a sound clip of 33072
frames is cut off to 32768 frames before analysis, and the time
cost is reduced from 6.128s to 0.224s.
Signed-off-by: Lu, Han <han.lu@intel.com>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
-rw-r--r-- | bat/analyze.c | 21 | ||||
-rw-r--r-- | bat/common.h | 6 |
2 files changed, 27 insertions, 0 deletions
diff --git a/bat/analyze.c b/bat/analyze.c index 60e2d1c..5cfdac3 100644 --- a/bat/analyze.c +++ b/bat/analyze.c @@ -256,6 +256,20 @@ static int reorder_data(struct bat *bat) return 0; } +/* truncate sample frames for faster FFT analysis process */ +static int truncate_frames(struct bat *bat) +{ + int shift = SHIFT_MAX; + + for (; shift > SHIFT_MIN; shift--) + if (bat->frames & (1 << shift)) { + bat->frames = 1 << shift; + return 0; + } + + return -EINVAL; +} + int analyze_capture(struct bat *bat) { int err = 0; @@ -263,6 +277,13 @@ int analyze_capture(struct bat *bat) int c; struct analyze a; + err = truncate_frames(bat); + if (err < 0) { + fprintf(bat->err, _("Invalid frame number for analysis: %d\n"), + bat->frames); + return err; + } + fprintf(bat->log, _("\nBAT analysis: signal has %d frames at %d Hz,"), bat->frames, bat->rate); fprintf(bat->log, _(" %d channels, %d bytes per sample.\n"), diff --git a/bat/common.h b/bat/common.h index c04452d..7346d9f 100644 --- a/bat/common.h +++ b/bat/common.h @@ -63,6 +63,12 @@ #define FOUND_DC (1<<1) #define FOUND_WRONG_PEAK (1<<0) +/* Truncate sample frames to (1 << N), for faster FFT analysis process. The + * valid range of N is (SHIFT_MIN, SHIFT_MAX). When N increases, the analysis + * will be more time-consuming, and the result will be more accurate. */ +#define SHIFT_MAX (sizeof(int) * 8 - 2) +#define SHIFT_MIN 8 + struct wav_header { unsigned int magic; /* 'RIFF' */ unsigned int length; /* file len */ |