kopia lustrzana https://github.com/xdsopl/robot36
rearranged and fixed alsa init code
rodzic
b7bb471c4f
commit
c609ba488f
229
alsa.c
229
alsa.c
|
@ -79,6 +79,64 @@ int write_alsa(struct pcm *pcm, short *buff, int frames)
|
||||||
|
|
||||||
int open_alsa_read(struct pcm **p, char *name)
|
int open_alsa_read(struct pcm **p, char *name)
|
||||||
{
|
{
|
||||||
|
snd_pcm_t *pcm;
|
||||||
|
if (snd_pcm_open(&pcm, name, SND_PCM_STREAM_CAPTURE, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error opening PCM device %s\n", name);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
snd_pcm_hw_params_t *params;
|
||||||
|
snd_pcm_hw_params_alloca(¶ms);
|
||||||
|
if (snd_pcm_hw_params_any(pcm, params) < 0) {
|
||||||
|
fprintf(stderr, "Can not configure this PCM device.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_access(pcm, params, SND_PCM_ACCESS_RW_INTERLEAVED) < 0) {
|
||||||
|
fprintf(stderr, "Error setting access.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_format(pcm, params, SND_PCM_FORMAT_S16_LE) < 0) {
|
||||||
|
fprintf(stderr, "Error setting S16_LE format.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_rate_resample(pcm, params, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error disabling resampling.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned rate_min = 8000;
|
||||||
|
int dir_min = 0;
|
||||||
|
if (snd_pcm_hw_params_set_rate_min(pcm, params, &rate_min, &dir_min) < 0 || rate_min < 8000) {
|
||||||
|
fprintf(stderr, "Error setting min rate.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params(pcm, params) < 0) {
|
||||||
|
fprintf(stderr, "Error setting HW params.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
unsigned int rate = 0;
|
||||||
|
if (snd_pcm_hw_params_get_rate(params, &rate, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error getting rate.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
unsigned int channels = 0;
|
||||||
|
if (snd_pcm_hw_params_get_channels(params, &channels) < 0) {
|
||||||
|
fprintf(stderr, "Error getting channels.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
struct alsa *alsa = (struct alsa *)malloc(sizeof(struct alsa));
|
struct alsa *alsa = (struct alsa *)malloc(sizeof(struct alsa));
|
||||||
alsa->base.close = close_alsa;
|
alsa->base.close = close_alsa;
|
||||||
alsa->base.info = info_alsa;
|
alsa->base.info = info_alsa;
|
||||||
|
@ -87,73 +145,6 @@ int open_alsa_read(struct pcm **p, char *name)
|
||||||
alsa->base.rw = read_alsa;
|
alsa->base.rw = read_alsa;
|
||||||
alsa->base.data = (void *)alsa;
|
alsa->base.data = (void *)alsa;
|
||||||
|
|
||||||
snd_pcm_t *pcm;
|
|
||||||
snd_pcm_hw_params_t *params;
|
|
||||||
snd_pcm_hw_params_alloca(¶ms);
|
|
||||||
|
|
||||||
if (snd_pcm_open(&pcm, name, SND_PCM_STREAM_CAPTURE, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error opening PCM device %s\n", name);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_any(pcm, params) < 0) {
|
|
||||||
fprintf(stderr, "Can not configure this PCM device.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_access(pcm, params, SND_PCM_ACCESS_RW_INTERLEAVED) < 0) {
|
|
||||||
fprintf(stderr, "Error setting access.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_format(pcm, params, SND_PCM_FORMAT_S16_LE) < 0) {
|
|
||||||
fprintf(stderr, "Error setting S16_LE format.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_rate_resample(pcm, params, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error disabling resampling.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
unsigned rate_min = 8000;
|
|
||||||
int dir_min = 0;
|
|
||||||
if (snd_pcm_hw_params_set_rate_min(pcm, params, &rate_min, &dir_min) < 0 || rate_min < 8000) {
|
|
||||||
fprintf(stderr, "Error setting min rate.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params(pcm, params) < 0) {
|
|
||||||
fprintf(stderr, "Error setting HW params.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
unsigned int rate = 0;
|
|
||||||
if (snd_pcm_hw_params_get_rate(params, &rate, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error getting rate.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
unsigned int channels = 0;
|
|
||||||
if (snd_pcm_hw_params_get_channels(params, &channels) < 0) {
|
|
||||||
fprintf(stderr, "Error getting channels.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
alsa->pcm = pcm;
|
alsa->pcm = pcm;
|
||||||
alsa->r = rate;
|
alsa->r = rate;
|
||||||
alsa->c = channels;
|
alsa->c = channels;
|
||||||
|
@ -164,6 +155,56 @@ int open_alsa_read(struct pcm **p, char *name)
|
||||||
|
|
||||||
int open_alsa_write(struct pcm **p, char *name, int rate, int channels, float seconds)
|
int open_alsa_write(struct pcm **p, char *name, int rate, int channels, float seconds)
|
||||||
{
|
{
|
||||||
|
snd_pcm_t *pcm;
|
||||||
|
if (snd_pcm_open(&pcm, name, SND_PCM_STREAM_PLAYBACK, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error opening PCM device %s\n", name);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
snd_pcm_hw_params_t *params;
|
||||||
|
snd_pcm_hw_params_alloca(¶ms);
|
||||||
|
if (snd_pcm_hw_params_any(pcm, params) < 0) {
|
||||||
|
fprintf(stderr, "Can not configure this PCM device.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_access(pcm, params, SND_PCM_ACCESS_RW_INTERLEAVED) < 0) {
|
||||||
|
fprintf(stderr, "Error setting access.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_format(pcm, params, SND_PCM_FORMAT_S16_LE) < 0) {
|
||||||
|
fprintf(stderr, "Error setting S16_LE format.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_rate_resample(pcm, params, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error disabling resampling.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_rate_near(pcm, params, (unsigned int *)&rate, 0) < 0) {
|
||||||
|
fprintf(stderr, "Error setting rate.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params_set_channels_near(pcm, params, (unsigned int *)&channels) < 0) {
|
||||||
|
fprintf(stderr, "Error setting channels.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (snd_pcm_hw_params(pcm, params) < 0) {
|
||||||
|
fprintf(stderr, "Error setting HW params.\n");
|
||||||
|
snd_pcm_close(pcm);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
struct alsa *alsa = (struct alsa *)malloc(sizeof(struct alsa));
|
struct alsa *alsa = (struct alsa *)malloc(sizeof(struct alsa));
|
||||||
alsa->base.close = close_alsa;
|
alsa->base.close = close_alsa;
|
||||||
alsa->base.info = info_alsa;
|
alsa->base.info = info_alsa;
|
||||||
|
@ -172,60 +213,6 @@ int open_alsa_write(struct pcm **p, char *name, int rate, int channels, float se
|
||||||
alsa->base.rw = write_alsa;
|
alsa->base.rw = write_alsa;
|
||||||
alsa->base.data = (void *)alsa;
|
alsa->base.data = (void *)alsa;
|
||||||
|
|
||||||
snd_pcm_t *pcm;
|
|
||||||
snd_pcm_hw_params_t *params;
|
|
||||||
snd_pcm_hw_params_alloca(¶ms);
|
|
||||||
|
|
||||||
if (snd_pcm_open(&pcm, name, SND_PCM_STREAM_PLAYBACK, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error opening PCM device %s\n", name);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_any(pcm, params) < 0) {
|
|
||||||
fprintf(stderr, "Can not configure this PCM device.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_access(pcm, params, SND_PCM_ACCESS_RW_INTERLEAVED) < 0) {
|
|
||||||
fprintf(stderr, "Error setting access.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_format(pcm, params, SND_PCM_FORMAT_S16_LE) < 0) {
|
|
||||||
fprintf(stderr, "Error setting S16_LE format.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_rate_resample(pcm, params, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error disabling resampling.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_rate_near(pcm, params, (unsigned int *)&rate, 0) < 0) {
|
|
||||||
fprintf(stderr, "Error setting rate.\n");
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params_set_channels_near(pcm, params, (unsigned int *)&channels) < 0) {
|
|
||||||
fprintf(stderr, "Error setting channels.\n");
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (snd_pcm_hw_params(pcm, params) < 0) {
|
|
||||||
fprintf(stderr, "Error setting HW params.\n");
|
|
||||||
snd_pcm_close(alsa->pcm);
|
|
||||||
free(alsa);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
alsa->pcm = pcm;
|
alsa->pcm = pcm;
|
||||||
alsa->r = rate;
|
alsa->r = rate;
|
||||||
alsa->c = channels;
|
alsa->c = channels;
|
||||||
|
|
Ładowanie…
Reference in New Issue