Re: [Alsa-user] C program for playing sound
Thank you very much, Gerhard! ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
Hello together! On Wed, 24 Jun 2020 17:37:46 -0300 Sleep schrieb: > // Insert samples to framebuffer. > wav = fopen("pcm1611s.wav", "r"); > fseek(wav, 0L, SEEK_END); > size = ftell(wav); > fseek(wav, 0L, SEEK_SET); > buffer = malloc(size); > fread(buffer, sizeof(int16_t), size, wav); > fclose(wav); > size /= sizeof(int16_t); > > // Set ptrbuffer 46 bytes ahead to skip the header. > for (int16_t *ptrbuffer = buffer + 46; size > ptrbuffer - buffer; > ptrbuffer += FRAMEBUFFERSIZE * STEREO * BITS) > { I would: avoid the #defines as far as possible and fetch the values out of the RIFF-header; first read the RIFF-header and with its contents calculate starting point and length of data. It is not guaranteed that the line with „for(“ (always) works – this as a qick response … Grüße, Gerhard ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
Nevermind, it is frames * STEREO here, this is where the error is. ptrbuffer += FRAMEBUFFERSIZE * STEREO * BITS ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
https://files.catbox.moe/5jvu18.wav Here is the recording of the effect as requested, new code below. #include #include #include #define STEREO 2 #define BITS16 / 8 #define FRAMEBUFFERSIZE 512 // in samples #define PERIODS 2 #define SAMPLERATE 11025 void snd_error_checker(int error, char *function_name) { if (error) { printf("Error (%s): %s\n", function_name, snd_strerror(error)); // exit(EXIT_FAILURE); } } int main(void) { snd_pcm_t *handle; uint32_t channels = STEREO; uint32_t sample_size= BITS; // 16 bit uint32_t frame_size = sample_size * channels; snd_pcm_uframes_t frames= FRAMEBUFFERSIZE / frame_size; snd_pcm_uframes_t frames_per_period = frames / PERIODS; int32_t dir = 0; // No idea what this does. snd_pcm_hw_params_t *params; int16_t *buffer; FILE *wav; int32_t size; int error; error = snd_pcm_open(&handle, "default", SND_PCM_STREAM_PLAYBACK, 0); snd_error_checker(error, "snd_pcm_open()"); snd_pcm_hw_params_alloca(¶ms); error = snd_pcm_hw_params_any(handle, params); snd_error_checker(error, "snd_pcm_hw_params_any()"); error = snd_pcm_hw_params_set_buffer_size(handle, params, frames); snd_error_checker(error, "snd_pcm_hw_params_set_buffer_size()"); error = snd_pcm_hw_params_set_period_size(handle, params, frames_per_period, dir); snd_error_checker(error, "snd_pcm_hw_params_set_period_size()"); error = snd_pcm_hw_params_set_rate(handle, params, SAMPLERATE, dir); snd_error_checker(error, "snd_pcm_hw_params_set_rate()"); error = snd_pcm_hw_params_set_access(handle, params, SND_PCM_ACCESS_RW_INTERLEAVED); snd_error_checker(error, "snd_pcm_hw_params_set_access()"); error = snd_pcm_hw_params_set_channels(handle, params, STEREO); snd_error_checker(error, "snd_pcm_hw_params_set_channels()"); error = snd_pcm_hw_params_set_format(handle, params, SND_PCM_FORMAT_S16_LE); snd_error_checker(error, "snd_pcm_hw_params_set_format()"); error = snd_pcm_hw_params(handle, params); snd_error_checker(error, "snd_pcm_hw_params()"); // Insert samples to framebuffer. wav = fopen("pcm1611s.wav", "r"); fseek(wav, 0L, SEEK_END); size = ftell(wav); fseek(wav, 0L, SEEK_SET); buffer = malloc(size); fread(buffer, sizeof(int16_t), size, wav); fclose(wav); size /= sizeof(int16_t); // Set ptrbuffer 46 bytes ahead to skip the header. for (int16_t *ptrbuffer = buffer + 46; size > ptrbuffer - buffer; ptrbuffer += FRAMEBUFFERSIZE * STEREO * BITS) { error = snd_pcm_writei(handle, ptrbuffer, frames); if (error) { snd_pcm_recover(handle, error, 0); } } snd_pcm_drain(handle); snd_pcm_close(handle); exit(EXIT_SUCCESS); } ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
snd_pcm_hw_params_set_buffer_size() and snd_pcm_hw_params_set_period_size() returns an error, a mere "Invalid argument." which doesn't help much, commenting them out doesn't appear to address the scratchy sound. ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
I've used snd_pcm_prepare() because underrun (-EPIPE) was occurring because I had put the wrong value for frames, but despite adjusting the value of the frames, I am still getting the scratchy effect, here is the current code I have, now I am really stuck. Also yeah, "scratchy" would be a better description of the effect I suppose. I might post a recording of the result later, meanwhile here is the code for now, I have removed snd_pcm_prepare() from it. #include #include #include #define STEREO 2 #define BITS 16 / 8 #define FRAMEBUFFERSIZE 512 // in samples #define PERIODS 2 #define SAMPLERATE 11025 int main(void) { snd_pcm_t *handle; uint32_t channels = STEREO; uint32_t sample_size = BITS; // 16 bit uint32_t frame_size = sample_size * channels; snd_pcm_uframes_t frames = FRAMEBUFFERSIZE / frame_size; snd_pcm_uframes_t frames_per_period = frames / PERIODS; int32_t dir = 0; // No idea what this does. snd_pcm_hw_params_t *params; int16_t framebuffer[FRAMEBUFFERSIZE * STEREO * BITS] = {0}; FILE *wav; int32_t size; snd_pcm_open(&handle, "default", SND_PCM_STREAM_PLAYBACK, 0); snd_pcm_hw_params_alloca(¶ms); snd_pcm_hw_params_any(handle, params); snd_pcm_hw_params_set_buffer_size(handle, params, frames); snd_pcm_hw_params_set_period_size(handle, params, frames_per_period, dir); snd_pcm_hw_params_set_rate(handle, params, SAMPLERATE, dir); snd_pcm_hw_params_set_access(handle, params, SND_PCM_ACCESS_RW_INTERLEAVED); snd_pcm_hw_params_set_channels(handle, params, STEREO); snd_pcm_hw_params_set_format(handle, params, SND_PCM_FORMAT_S16_LE); snd_pcm_hw_params(handle, params); // Insert samples to framebuffer. wav = fopen("pcm1611s.wav", "r"); fseek(wav, 0L, SEEK_END); size = ftell(wav); fseek(wav, 0L, SEEK_SET); size /= sizeof(int16_t); while (size > 0) { fread(framebuffer, sizeof(int16_t), FRAMEBUFFERSIZE * STEREO * BITS, wav); snd_pcm_writei(handle, framebuffer, frames); size -= FRAMEBUFFERSIZE * BITS * STEREO; } snd_pcm_drain(handle); snd_pcm_close(handle); exit(EXIT_SUCCESS); } ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
now the problem is that the sound is skipping. Can you provide a recording of what it sounds like? In alsa-lib there is an example test/latency.c which just moves samples from one device to another. When I run it, the sound that comes out of my speakers is what I would call "scratchy". I submitted a bug report here, which has recordings of what I hear when I run ./latency: https://github.com/alsa-project/alsa-lib/issues/53 It was closed by someone named Jaroslav Kysela who is the author of ALSA, according to Wikipedia. But I'm not sure if he read the actual bug report. I don't know where you got the idea to call snd_pcm_prepare in your loop, or why that fixed the problem. I hope this is helpful. Frederick On Tue, Jun 23, 2020 at 04:54:09PM -0300, Sleep wrote: Update, forgot snd_pcm_prepare(), now the problem is that the sound is skipping. #include #include #include #define STEREO 2 #define BITS 16 / 8 #define FRAMEBUFFERSIZE 512 // in samples #define PERIODS 2 #define SAMPLERATE 11025 int main(void) { snd_pcm_t *handle; uint32_t channels = STEREO; uint32_t sample_size = BITS; // 16 bit uint32_t frame_size = sample_size * channels; snd_pcm_uframes_t frames = FRAMEBUFFERSIZE; snd_pcm_uframes_t frames_per_period = frames / PERIODS; int dir = 0; // No idea what this does. snd_pcm_hw_params_t *params; int16_t framebuffer[FRAMEBUFFERSIZE * STEREO * BITS] = {0}; FILE *wav; int size; int status; snd_pcm_open(&handle, "default", SND_PCM_STREAM_PLAYBACK, 0); // SND_PCM_NONBLOCK); snd_pcm_hw_params_alloca(¶ms); snd_pcm_hw_params_any(handle, params); snd_pcm_hw_params_set_buffer_size(handle, params, frames); snd_pcm_hw_params_set_period_size(handle, params, frames_per_period, dir); snd_pcm_hw_params_set_rate(handle, params, SAMPLERATE, dir); snd_pcm_hw_params_set_access(handle, params, SND_PCM_ACCESS_RW_INTERLEAVED); snd_pcm_hw_params_set_channels(handle, params, STEREO); snd_pcm_hw_params_set_format(handle, params, SND_PCM_FORMAT_S16_LE); snd_pcm_hw_params(handle, params); // Insert samples to framebuffer. wav = fopen("pcm1611s.wav", "r"); fseek(wav, 0L, SEEK_END); size = ftell(wav); fseek(wav, 0L, SEEK_SET); size /= sizeof(signed short); while (size > 0) { fread(framebuffer, sizeof(int16_t), FRAMEBUFFERSIZE * STEREO * BITS, wav); status = snd_pcm_writei(handle, framebuffer, frames); if (status == -EPIPE) { snd_pcm_prepare(handle); } size -= FRAMEBUFFERSIZE * STEREO * BITS; } snd_pcm_drain(handle); snd_pcm_close(handle); exit(EXIT_SUCCESS); } ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user
Re: [Alsa-user] C program for playing sound
Update, forgot snd_pcm_prepare(), now the problem is that the sound is skipping. #include #include #include #define STEREO 2 #define BITS 16 / 8 #define FRAMEBUFFERSIZE 512 // in samples #define PERIODS 2 #define SAMPLERATE 11025 int main(void) { snd_pcm_t *handle; uint32_t channels = STEREO; uint32_t sample_size = BITS; // 16 bit uint32_t frame_size = sample_size * channels; snd_pcm_uframes_t frames = FRAMEBUFFERSIZE; snd_pcm_uframes_t frames_per_period = frames / PERIODS; int dir = 0; // No idea what this does. snd_pcm_hw_params_t *params; int16_t framebuffer[FRAMEBUFFERSIZE * STEREO * BITS] = {0}; FILE *wav; int size; int status; snd_pcm_open(&handle, "default", SND_PCM_STREAM_PLAYBACK, 0); // SND_PCM_NONBLOCK); snd_pcm_hw_params_alloca(¶ms); snd_pcm_hw_params_any(handle, params); snd_pcm_hw_params_set_buffer_size(handle, params, frames); snd_pcm_hw_params_set_period_size(handle, params, frames_per_period, dir); snd_pcm_hw_params_set_rate(handle, params, SAMPLERATE, dir); snd_pcm_hw_params_set_access(handle, params, SND_PCM_ACCESS_RW_INTERLEAVED); snd_pcm_hw_params_set_channels(handle, params, STEREO); snd_pcm_hw_params_set_format(handle, params, SND_PCM_FORMAT_S16_LE); snd_pcm_hw_params(handle, params); // Insert samples to framebuffer. wav = fopen("pcm1611s.wav", "r"); fseek(wav, 0L, SEEK_END); size = ftell(wav); fseek(wav, 0L, SEEK_SET); size /= sizeof(signed short); while (size > 0) { fread(framebuffer, sizeof(int16_t), FRAMEBUFFERSIZE * STEREO * BITS, wav); status = snd_pcm_writei(handle, framebuffer, frames); if (status == -EPIPE) { snd_pcm_prepare(handle); } size -= FRAMEBUFFERSIZE * STEREO * BITS; } snd_pcm_drain(handle); snd_pcm_close(handle); exit(EXIT_SUCCESS); } ___ Alsa-user mailing list Alsa-user@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/alsa-user