[alsa-devel] Question about struct snd_soc_dai() :: cpu_dai->codec
Kuninori Morimoto
kuninori.morimoto.gx at renesas.com
Thu Aug 4 04:38:33 CEST 2016
Hi Lars
> I think moving forward we should get rid of the whole CPU/CODEC/platform
> concept. This is an outdated view of how the hardware looks like. When ASoC
> was initially introduce all hardware basically had a CPU side DAI, a CODEC
> side DAI and a DMA. The DMA was connected to the CPU DAI and the CPU DAI was
> connected to the CODEC DAI and that was it. The CPU side was also really
> simple, no signal processing, no signal routing, just the raw audio data
> directly transferred via DMA (or PIO sometimes) to the CPU DAI controller.
> And all digital audio was assumed to be in a single digital domain running
> at them same clock rate.
>
> This no longer reflects todays typical systems. Sometimes you have more than
> those three components (e.g. additional amplifier IC, BT chip ...),
> sometimes you less (just a DAC or ADC directly connected to a DMA in the
> SoC). You often have complex routing and processing capabilities on the host
> side. Also you have often multiple digital domains with sample-rate
> converters between them.
>
> Yet still at the core ASoC keeps the CPU/CODEC/platform concept. DPCM e.g.
> tries to work with these concepts by introducing frontend and backend DAIs
> and use dummy components to compensate for when the software model does not
> match the hardware model. This makes it code more complicated than it has to
> be and less efficient than it can be.
I agree to your opinion.
OTOH, we would like to use/keep existing current all drivers.
Thus, I think we need super many small and slow steps.
Or, we need new ASoC2 ?
I can agree that we should get rid of current CPU/Codec/Platform,
but, removing all of them is a little bit over-kill for me.
I think ALSA SoC "framework" should care "component" only,
and it doesn't care what it was.
OTOH "driver" side can use existing CPU/Codec/Platform and/or AUX/compr
etc as helper ? (I'm not sure detail of AUX/compr actually...)
And each "component" has "dai".
My image is like this.
This allows many / few components, and many / few DAIs.
Current DPCM style is automatically supported,
and it is easy to add new style device.
What do you think ?
/*
* DAI has parent (= component) pointer
* and rtd interface list_head
*/
struct snd_soc_dai {
...
struct snd_soc_component *component; /* parent */
struct list_head *dai_node; /* struct snd_soc_pcm_runtime */
};
/*
* Each component has at least 1 DAI
*
* CPU/Codec will have many DAIs
* Card/Platform and other will have dummy DAI as interface
*/
struct snd_soc_component {
...
struct snd_soc_dai *dais;
};
/*
* We can use Card/CPU/Codec/Platform/AUX/COMPR helper,
* all includes "component".
* Of course each driver can create original one,
* or don't use helper is no problem
*/
struct snd_soc_card {
...
struct snd_soc_component component;
};
struct snd_soc_cpu {
...
struct snd_soc_component component;
};
struct snd_soc_codec {
...
struct snd_soc_component component;
};
struct snd_soc_platform {
...
struct snd_soc_component component;
};
struct snd_soc_aux {
...
struct snd_soc_component component;
};
struct snd_soc_compr {
...
struct snd_soc_component component;
};
...
/*
* rtd has each DAI interface list.
* But it doesn't care what it was
*/
struct snd_soc_pcm_runtime {
...
struct list_head *dai_node_head; /* struct snd_soc_dai */
}
/*
* each function just call dai or component function
* it doesn't care what it was
*/
static int soc_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
{
struct snd_soc_pcm_runtime *rtd = substream->private_data;
struct snd_soc_component *component;
struct snd_soc_dai *dai;
int ret = 0;
/*
* call each component's ops
*/
list_for_each_entry(dai, rtd->xxx) {
component = snd_soc_dai_to_component(dai);
ret = component->ops->trigger(dai, xxx);
if (ret < 0)
goto trigger_end;
}
trigger_end:
return ret;
}
More information about the Alsa-devel
mailing list