ALSA: asihpi - Fix format validity check.
Sharing and not reinitialising static pcm_hardware struct resulted in stream format validity flags being incorrectly shared between cards. Fix and clarify by declaring locally and initialising in the open functions. Signed-off-by: Eliot Blennerhassett <eblennerhassett@audioscience.com> Signed-off-by: Takashi Iwai <tiwai@suse.de>
This commit is contained in:
parent
c1d70dd9c4
commit
68d5339322
@ -938,15 +938,15 @@ snd_card_asihpi_playback_pointer(struct snd_pcm_substream *substream)
|
|||||||
return ptr;
|
return ptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void snd_card_asihpi_playback_format(struct snd_card_asihpi *asihpi,
|
static u64 snd_card_asihpi_playback_formats(struct snd_card_asihpi *asihpi,
|
||||||
u32 h_stream,
|
u32 h_stream)
|
||||||
struct snd_pcm_hardware *pcmhw)
|
|
||||||
{
|
{
|
||||||
struct hpi_format hpi_format;
|
struct hpi_format hpi_format;
|
||||||
u16 format;
|
u16 format;
|
||||||
u16 err;
|
u16 err;
|
||||||
u32 h_control;
|
u32 h_control;
|
||||||
u32 sample_rate = 48000;
|
u32 sample_rate = 48000;
|
||||||
|
u64 formats = 0;
|
||||||
|
|
||||||
/* on cards without SRC, must query at valid rate,
|
/* on cards without SRC, must query at valid rate,
|
||||||
* maybe set by external sync
|
* maybe set by external sync
|
||||||
@ -966,32 +966,24 @@ static void snd_card_asihpi_playback_format(struct snd_card_asihpi *asihpi,
|
|||||||
if (!err)
|
if (!err)
|
||||||
err = hpi_outstream_query_format(h_stream, &hpi_format);
|
err = hpi_outstream_query_format(h_stream, &hpi_format);
|
||||||
if (!err && (hpi_to_alsa_formats[format] != -1))
|
if (!err && (hpi_to_alsa_formats[format] != -1))
|
||||||
pcmhw->formats |= (1ULL << hpi_to_alsa_formats[format]);
|
formats |= (1ULL << hpi_to_alsa_formats[format]);
|
||||||
}
|
}
|
||||||
|
return formats;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct snd_pcm_hardware snd_card_asihpi_playback = {
|
|
||||||
.buffer_bytes_max = BUFFER_BYTES_MAX,
|
|
||||||
.period_bytes_min = PERIOD_BYTES_MIN,
|
|
||||||
.period_bytes_max = BUFFER_BYTES_MAX / PERIODS_MIN,
|
|
||||||
.periods_min = PERIODS_MIN,
|
|
||||||
.periods_max = BUFFER_BYTES_MAX / PERIOD_BYTES_MIN,
|
|
||||||
.fifo_size = 0,
|
|
||||||
};
|
|
||||||
|
|
||||||
static int snd_card_asihpi_playback_open(struct snd_pcm_substream *substream)
|
static int snd_card_asihpi_playback_open(struct snd_pcm_substream *substream)
|
||||||
{
|
{
|
||||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||||
struct snd_card_asihpi_pcm *dpcm;
|
struct snd_card_asihpi_pcm *dpcm;
|
||||||
struct snd_card_asihpi *card = snd_pcm_substream_chip(substream);
|
struct snd_card_asihpi *card = snd_pcm_substream_chip(substream);
|
||||||
|
struct snd_pcm_hardware snd_card_asihpi_playback;
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
dpcm = kzalloc(sizeof(*dpcm), GFP_KERNEL);
|
dpcm = kzalloc(sizeof(*dpcm), GFP_KERNEL);
|
||||||
if (dpcm == NULL)
|
if (dpcm == NULL)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
err =
|
err = hpi_outstream_open(card->hpi->adapter->index,
|
||||||
hpi_outstream_open(card->hpi->adapter->index,
|
|
||||||
substream->number, &dpcm->h_stream);
|
substream->number, &dpcm->h_stream);
|
||||||
hpi_handle_error(err);
|
hpi_handle_error(err);
|
||||||
if (err)
|
if (err)
|
||||||
@ -1013,13 +1005,19 @@ static int snd_card_asihpi_playback_open(struct snd_pcm_substream *substream)
|
|||||||
runtime->private_data = dpcm;
|
runtime->private_data = dpcm;
|
||||||
runtime->private_free = snd_card_asihpi_runtime_free;
|
runtime->private_free = snd_card_asihpi_runtime_free;
|
||||||
|
|
||||||
snd_card_asihpi_playback.channels_max = card->out_max_chans;
|
memset(&snd_card_asihpi_playback, 0, sizeof(snd_card_asihpi_playback));
|
||||||
snd_card_asihpi_playback.channels_min = card->out_min_chans;
|
snd_card_asihpi_playback.buffer_bytes_max = BUFFER_BYTES_MAX;
|
||||||
|
snd_card_asihpi_playback.period_bytes_min = PERIOD_BYTES_MIN;
|
||||||
/*?snd_card_asihpi_playback.period_bytes_min =
|
/*?snd_card_asihpi_playback.period_bytes_min =
|
||||||
card->out_max_chans * 4096; */
|
card->out_max_chans * 4096; */
|
||||||
|
snd_card_asihpi_playback.period_bytes_max = BUFFER_BYTES_MAX / PERIODS_MIN;
|
||||||
snd_card_asihpi_playback_format(card, dpcm->h_stream,
|
snd_card_asihpi_playback.periods_min = PERIODS_MIN;
|
||||||
&snd_card_asihpi_playback);
|
snd_card_asihpi_playback.periods_max = BUFFER_BYTES_MAX / PERIOD_BYTES_MIN;
|
||||||
|
/* snd_card_asihpi_playback.fifo_size = 0; */
|
||||||
|
snd_card_asihpi_playback.channels_max = card->out_max_chans;
|
||||||
|
snd_card_asihpi_playback.channels_min = card->out_min_chans;
|
||||||
|
snd_card_asihpi_playback.formats =
|
||||||
|
snd_card_asihpi_playback_formats(card, dpcm->h_stream);
|
||||||
|
|
||||||
snd_card_asihpi_pcm_samplerates(card, &snd_card_asihpi_playback);
|
snd_card_asihpi_pcm_samplerates(card, &snd_card_asihpi_playback);
|
||||||
|
|
||||||
@ -1116,15 +1114,15 @@ static int snd_card_asihpi_capture_prepare(struct snd_pcm_substream *substream)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void snd_card_asihpi_capture_format(struct snd_card_asihpi *asihpi,
|
static u64 snd_card_asihpi_capture_formats(struct snd_card_asihpi *asihpi,
|
||||||
u32 h_stream,
|
u32 h_stream)
|
||||||
struct snd_pcm_hardware *pcmhw)
|
|
||||||
{
|
{
|
||||||
struct hpi_format hpi_format;
|
struct hpi_format hpi_format;
|
||||||
u16 format;
|
u16 format;
|
||||||
u16 err;
|
u16 err;
|
||||||
u32 h_control;
|
u32 h_control;
|
||||||
u32 sample_rate = 48000;
|
u32 sample_rate = 48000;
|
||||||
|
u64 formats = 0;
|
||||||
|
|
||||||
/* on cards without SRC, must query at valid rate,
|
/* on cards without SRC, must query at valid rate,
|
||||||
maybe set by external sync */
|
maybe set by external sync */
|
||||||
@ -1144,25 +1142,17 @@ static void snd_card_asihpi_capture_format(struct snd_card_asihpi *asihpi,
|
|||||||
if (!err)
|
if (!err)
|
||||||
err = hpi_instream_query_format(h_stream, &hpi_format);
|
err = hpi_instream_query_format(h_stream, &hpi_format);
|
||||||
if (!err)
|
if (!err)
|
||||||
pcmhw->formats |= (1ULL << hpi_to_alsa_formats[format]);
|
formats |= (1ULL << hpi_to_alsa_formats[format]);
|
||||||
}
|
}
|
||||||
|
return formats;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static struct snd_pcm_hardware snd_card_asihpi_capture = {
|
|
||||||
.buffer_bytes_max = BUFFER_BYTES_MAX,
|
|
||||||
.period_bytes_min = PERIOD_BYTES_MIN,
|
|
||||||
.period_bytes_max = BUFFER_BYTES_MAX / PERIODS_MIN,
|
|
||||||
.periods_min = PERIODS_MIN,
|
|
||||||
.periods_max = BUFFER_BYTES_MAX / PERIOD_BYTES_MIN,
|
|
||||||
.fifo_size = 0,
|
|
||||||
};
|
|
||||||
|
|
||||||
static int snd_card_asihpi_capture_open(struct snd_pcm_substream *substream)
|
static int snd_card_asihpi_capture_open(struct snd_pcm_substream *substream)
|
||||||
{
|
{
|
||||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||||
struct snd_card_asihpi *card = snd_pcm_substream_chip(substream);
|
struct snd_card_asihpi *card = snd_pcm_substream_chip(substream);
|
||||||
struct snd_card_asihpi_pcm *dpcm;
|
struct snd_card_asihpi_pcm *dpcm;
|
||||||
|
struct snd_pcm_hardware snd_card_asihpi_capture;
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
dpcm = kzalloc(sizeof(*dpcm), GFP_KERNEL);
|
dpcm = kzalloc(sizeof(*dpcm), GFP_KERNEL);
|
||||||
@ -1189,10 +1179,17 @@ static int snd_card_asihpi_capture_open(struct snd_pcm_substream *substream)
|
|||||||
runtime->private_data = dpcm;
|
runtime->private_data = dpcm;
|
||||||
runtime->private_free = snd_card_asihpi_runtime_free;
|
runtime->private_free = snd_card_asihpi_runtime_free;
|
||||||
|
|
||||||
|
memset(&snd_card_asihpi_capture, 0, sizeof(snd_card_asihpi_capture));
|
||||||
|
snd_card_asihpi_capture.buffer_bytes_max = BUFFER_BYTES_MAX;
|
||||||
|
snd_card_asihpi_capture.period_bytes_min = PERIOD_BYTES_MIN;
|
||||||
|
snd_card_asihpi_capture.period_bytes_max = BUFFER_BYTES_MAX / PERIODS_MIN;
|
||||||
|
snd_card_asihpi_capture.periods_min = PERIODS_MIN;
|
||||||
|
snd_card_asihpi_capture.periods_max = BUFFER_BYTES_MAX / PERIOD_BYTES_MIN;
|
||||||
|
/* snd_card_asihpi_capture.fifo_size = 0; */
|
||||||
snd_card_asihpi_capture.channels_max = card->in_max_chans;
|
snd_card_asihpi_capture.channels_max = card->in_max_chans;
|
||||||
snd_card_asihpi_capture.channels_min = card->in_min_chans;
|
snd_card_asihpi_capture.channels_min = card->in_min_chans;
|
||||||
snd_card_asihpi_capture_format(card, dpcm->h_stream,
|
snd_card_asihpi_capture.formats =
|
||||||
&snd_card_asihpi_capture);
|
snd_card_asihpi_capture_formats(card, dpcm->h_stream);
|
||||||
snd_card_asihpi_pcm_samplerates(card, &snd_card_asihpi_capture);
|
snd_card_asihpi_pcm_samplerates(card, &snd_card_asihpi_capture);
|
||||||
snd_card_asihpi_capture.info = SNDRV_PCM_INFO_INTERLEAVED |
|
snd_card_asihpi_capture.info = SNDRV_PCM_INFO_INTERLEAVED |
|
||||||
SNDRV_PCM_INFO_MMAP |
|
SNDRV_PCM_INFO_MMAP |
|
||||||
|
Loading…
Reference in New Issue
Block a user