Created
November 22, 2013 14:35
-
-
Save dennis-hamester/7600799 to your computer and use it in GitHub Desktop.
alsa rpi bug test tool
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #include <stdio.h> | |
| #include <stdlib.h> | |
| #include <limits.h> | |
| #include <math.h> | |
| #include <time.h> | |
| #include <alsa/asoundlib.h> | |
| #define BUFSIZE 1024 | |
| #define PI 3.141592654 | |
| int main (int argc, char *argv[]) | |
| { | |
| snd_pcm_hw_params_t *hw_params; | |
| snd_pcm_t *playback_handle; | |
| unsigned int rate = 48000; | |
| double frequency = 750.0; | |
| unsigned int channels; | |
| unsigned int buffer_time; | |
| int iters; | |
| int16_t *buf; | |
| int dir = 0; | |
| int err; | |
| int i; | |
| if(argc < 2) { | |
| printf("alsa-playback device rate frequency\n"); | |
| exit(1); | |
| } | |
| if(argc > 2) | |
| rate = atoi(argv[2]); | |
| if(argc > 3) | |
| frequency = atof(argv[3]); | |
| printf("rate: %u -- frequency: %lf\n", rate, frequency); | |
| iters = rate / (BUFSIZE / 10); | |
| if ((err = snd_pcm_open (&playback_handle, argv[1], SND_PCM_STREAM_PLAYBACK, 0)) < 0) { | |
| fprintf(stderr, "cannot open audio device %s (%s)\n", argv[1], | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if((err = snd_pcm_hw_params_malloc(&hw_params)) < 0) { | |
| fprintf(stderr, "cannot allocate hardware parameter structure (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_any(playback_handle, hw_params)) < 0) { | |
| fprintf(stderr, "cannot initia lize hardware parameter structure (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_set_access (playback_handle, hw_params, | |
| SND_PCM_ACCESS_RW_INTERLEAVED)) < 0) { | |
| fprintf(stderr, "cannot set access type (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_set_format (playback_handle, hw_params, | |
| SND_PCM_FORMAT_S16_LE)) < 0) { | |
| fprintf(stderr, "cannot set sample format (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_set_rate_near(playback_handle, hw_params, | |
| &rate, &dir)) < 0) { | |
| fprintf(stderr, "cannot set sample rate (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_set_channels_first (playback_handle, hw_params, &channels)) < 0) { | |
| fprintf(stderr, "cannot set channels to first (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params_set_buffer_time_last (playback_handle, hw_params, &buffer_time, &dir)) < 0) { | |
| fprintf(stderr, "cannot set buffer time to last (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| if ((err = snd_pcm_hw_params(playback_handle, hw_params)) < 0) { | |
| fprintf(stderr, "cannot set parameters (%s)\n", snd_strerror(err)); | |
| exit(1); | |
| } | |
| snd_pcm_uframes_t bufsize; | |
| snd_pcm_hw_params_get_buffer_size(hw_params, &bufsize); | |
| printf("bufsize %lu\n", bufsize); | |
| snd_pcm_hw_params_free (hw_params); | |
| if ((err = snd_pcm_prepare(playback_handle)) < 0) { | |
| fprintf (stderr, "cannot prepare audio interface for use (%s)\n", | |
| snd_strerror(err)); | |
| exit(1); | |
| } | |
| buf = calloc(channels * BUFSIZE, 2); | |
| for (i = 0; i < BUFSIZE; i++) { | |
| int16_t val = (int16_t)(sin(2.0*PI*i/(rate/frequency)) * 16384.0); | |
| buf[channels*i] = val; | |
| } | |
| printf("queue data %d\n", iters); | |
| snd_pcm_uframes_t written = 0; | |
| for (i = 0; i < iters; i++) { | |
| written += snd_pcm_writei(playback_handle, buf, BUFSIZE); | |
| if(written > rate) { | |
| snd_pcm_drop(playback_handle); | |
| snd_pcm_prepare(playback_handle); | |
| written -= rate; | |
| printf("drop; playback should stop _now_\n"); | |
| } | |
| } | |
| printf("done queuing\n"); | |
| printf("dropping one last time\n"); | |
| snd_pcm_drop(playback_handle); | |
| printf("playback should have long stopped by now\n"); | |
| sleep(10); | |
| snd_pcm_close(playback_handle); | |
| exit(0); | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment