Rev 29 |
|
Rev 31 |
Line 14... |
|
Line 14... |
14 |
#include <math.h> |
|
14 |
#include <math.h> |
15 |
#include <fftw3.h> |
|
15 |
#include <fftw3.h> |
16 |
|
|
16 |
|
17 |
static char *device = "plughw:0,0"; /* playback device */ |
|
17 |
static char *device = "plughw:0,0"; /* playback device */ |
18 |
static snd_pcm_format_t format = SND_PCM_FORMAT_S16; /* sample format */ |
|
18 |
static snd_pcm_format_t format = SND_PCM_FORMAT_S16; /* sample format */ |
19 |
static unsigned int rate = 24000; /* stream rate */ |
|
19 |
static unsigned int rate = 48000; /* stream rate */ |
20 |
//static unsigned int buffer_size = 200000; /* ring buffer length in us */ |
|
- |
|
21 |
//static unsigned int period_size = 10000; /* period time in us */ |
|
- |
|
22 |
static int verbose = 0; /* verbose flag */ |
|
- |
|
23 |
static int resample = 1; /* enable alsa-lib resampling */ |
|
20 |
static int resample = 1; /* enable alsa-lib resampling */ |
24 |
static int period_event = 0; /* produce poll event after each period */ |
|
21 |
static int period_event = 0; /* produce poll event after each period */ |
25 |
|
|
22 |
|
26 |
static snd_pcm_sframes_t buffer_size=7008; // size of buffer at sound card |
|
23 |
static snd_pcm_sframes_t buffer_size=7008; // size of buffer at sound card |
27 |
static snd_pcm_sframes_t period_size=3504; //samples per frame |
|
24 |
static snd_pcm_sframes_t period_size=2336; //samples per frame |
28 |
static snd_output_t *output = NULL; |
|
25 |
static snd_output_t *output = NULL; |
29 |
|
|
26 |
|
30 |
FILE *out; |
|
27 |
FILE *out; |
31 |
|
|
28 |
|
32 |
double df; //frequency resolution |
|
29 |
double df; //frequency resolution |
Line 37... |
|
Line 34... |
37 |
fftw_plan fft_plan_left, fft_plan_right; |
|
34 |
fftw_plan fft_plan_left, fft_plan_right; |
38 |
|
|
35 |
|
39 |
double *spect_avg_left, *spect_avg_right; |
|
36 |
double *spect_avg_left, *spect_avg_right; |
40 |
unsigned int period; |
|
37 |
unsigned int period; |
41 |
|
|
38 |
|
- |
|
|
39 |
#define PERIODS 50 // number of periods to average |
- |
|
|
40 |
|
- |
|
|
41 |
|
42 |
static int set_hwparams(snd_pcm_t *handle, snd_pcm_hw_params_t *params, unsigned int channels) |
|
42 |
static int set_hwparams(snd_pcm_t *handle, snd_pcm_hw_params_t *params, unsigned int channels) |
43 |
{ |
|
43 |
{ |
44 |
unsigned int rrate; |
|
44 |
unsigned int rrate; |
45 |
snd_pcm_uframes_t size; |
|
45 |
snd_pcm_uframes_t size; |
46 |
int err, dir; |
|
46 |
int err, dir; |
Line 175... |
|
Line 175... |
175 |
static void async_capture_callback(snd_async_handler_t *ahandler) |
|
175 |
static void async_capture_callback(snd_async_handler_t *ahandler) |
176 |
{ |
|
176 |
{ |
177 |
snd_pcm_t *handle = snd_async_handler_get_pcm(ahandler); |
|
177 |
snd_pcm_t *handle = snd_async_handler_get_pcm(ahandler); |
178 |
int err; |
|
178 |
int err; |
179 |
unsigned int i, n; |
|
179 |
unsigned int i, n; |
180 |
short signal[300000]; |
|
180 |
short signal[30000]; |
181 |
|
|
181 |
|
182 |
/*signal = calloc( (unsigned int) period_size, sizeof(short) ); |
|
182 |
/*signal = calloc( (unsigned int) period_size, sizeof(short) ); |
183 |
if (signal = NULL) printf("memory allocation failed");*/ |
|
183 |
if (signal = NULL) printf("memory allocation failed");*/ |
184 |
|
|
184 |
|
185 |
while (snd_pcm_avail_update(handle) >= period_size) { // read until data is ready in buffer |
|
185 |
while (snd_pcm_avail_update(handle) >= period_size) { // read until data is ready in buffer |
Line 195... |
|
Line 195... |
195 |
} |
|
195 |
} |
196 |
|
|
196 |
|
197 |
n=0; |
|
197 |
n=0; |
198 |
i=0; |
|
198 |
i=0; |
199 |
do { |
|
199 |
do { |
200 |
inl[n]= signal[i]; |
|
200 |
inl[n]= signal[i]/32768.0; |
201 |
inr[n]= signal[i+1]; |
|
201 |
inr[n]= signal[i+1]/32768.0; |
202 |
n++; |
|
202 |
n++; |
203 |
i+=2; |
|
203 |
i+=2; |
204 |
} while (n < period_size); |
|
204 |
} while (n < period_size); |
205 |
|
|
205 |
|
206 |
fftw_execute(fft_plan_left); |
|
206 |
fftw_execute(fft_plan_left); |
Line 209... |
|
Line 209... |
209 |
for(i=0; i < frequency_bins; i++) spect_avg_left[i] += sqrt( (outl[i][0] * outl[i][0]) + (outl[i][1] * outl[i][1]) ); //acumulate average spectrum |
|
209 |
for(i=0; i < frequency_bins; i++) spect_avg_left[i] += sqrt( (outl[i][0] * outl[i][0]) + (outl[i][1] * outl[i][1]) ); //acumulate average spectrum |
210 |
for(i=0; i < frequency_bins; i++) spect_avg_right[i] += sqrt( (outr[i][0] * outr[i][0]) + (outr[i][1] * outr[i][1]) ); //acumulate average spectrum |
|
210 |
for(i=0; i < frequency_bins; i++) spect_avg_right[i] += sqrt( (outr[i][0] * outr[i][0]) + (outr[i][1] * outr[i][1]) ); //acumulate average spectrum |
211 |
period++; |
|
211 |
period++; |
212 |
} |
|
212 |
} |
213 |
|
|
213 |
|
214 |
if (period > 100) |
|
214 |
if (period > PERIODS) |
215 |
{ |
|
215 |
{ |
216 |
for(i=0; i < frequency_bins; i++) spect_avg_left[i] = spect_avg_left[i]/100; |
|
216 |
for(i=0; i < frequency_bins; i++) spect_avg_left[i] = spect_avg_left[i]/PERIODS; // finally average spectrum data |
217 |
for(i=0; i < frequency_bins; i++) spect_avg_right[i] = spect_avg_right[i]/100; |
|
217 |
for(i=0; i < frequency_bins; i++) spect_avg_right[i] = spect_avg_right[i]/PERIODS; |
218 |
|
|
218 |
|
219 |
out=fopen("/tmp/sidspect","w"); |
|
219 |
out=fopen("/tmp/sidspec","w"); |
220 |
|
|
220 |
|
221 |
for(i=0; i < frequency_bins; i++) |
|
221 |
for(i=0; i < frequency_bins; i++) //write spectrum to file |
222 |
{ |
|
222 |
{ |
223 |
fprintf(out,"%6f %6f %6f\n",(i+0.5)*df, spect_avg_left[i], spect_avg_right[i]); |
|
223 |
fprintf(out,"%.5e %.5e %.5e\n",(i+0.5)*df, spect_avg_left[i], spect_avg_right[i]); |
224 |
spect_avg_left[i]=0; |
|
224 |
spect_avg_left[i]=0; |
225 |
spect_avg_right[i]=0; |
|
225 |
spect_avg_right[i]=0; |
226 |
} |
|
226 |
} |
227 |
fclose(out); |
|
227 |
fclose(out); |
228 |
period=0; |
|
228 |
period=0; |
Line 277... |
|
Line 277... |
277 |
exit(EXIT_FAILURE); |
|
277 |
exit(EXIT_FAILURE); |
278 |
} |
|
278 |
} |
279 |
|
|
279 |
|
280 |
// setup fft |
|
280 |
// setup fft |
281 |
|
|
281 |
|
282 |
df = (double) rate/ (double) frequency_bins * 2.0; |
|
282 |
df = (double) rate/ (double) period_size; |
283 |
|
|
283 |
|
284 |
inl = fftw_malloc(sizeof(double) * period_size); // period_size); |
|
284 |
inl = fftw_malloc(sizeof(double) * period_size); // period_size); |
285 |
outl = fftw_malloc(sizeof(fftw_complex) * frequency_bins); |
|
285 |
outl = fftw_malloc(sizeof(fftw_complex) * frequency_bins); |
286 |
|
|
286 |
|
287 |
inr = fftw_malloc(sizeof(double) * period_size); // period_size); |
|
287 |
inr = fftw_malloc(sizeof(double) * period_size); // period_size); |