Skip to content

Commit 365865b

Browse files
morimotobroonie
authored andcommitted
ASoC: audio-graph-card2: Use extra format on each DAI
Current ASoC is using dai_link->dai_fmt to set DAI format for both CPU/Codec. But because it is using same settings, and SND_SOC_DAIFMT_CLOCK_PROVIDER is flipped for CPU, we can't set both CPU/Codec as clock consumer, for example. To solve this issue, this patch uses extra format for each DAI which can keep compatibility with legacy system, 1. SND_SOC_DAIFMT_FORMAT_MASK 2. SND_SOC_DAIFMT_CLOCK 3. SND_SOC_DAIFMT_INV 4. SND_SOC_DAIFMT_CLOCK_PROVIDER Legacy dai_fmt includes 1, 2, 3, 4 New idea dai_fmt includes 1, 2, 3 ext_fmt includes 4 Signed-off-by: Kuninori Morimoto <[email protected]> Tested-by: Stephen Gordon <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Mark Brown <[email protected]>
1 parent 24410f4 commit 365865b

File tree

1 file changed

+44
-32
lines changed

1 file changed

+44
-32
lines changed

sound/soc/generic/audio-graph-card2.c

Lines changed: 44 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -667,8 +667,7 @@ static int graph_parse_node(struct simple_util_priv *priv,
667667
return graph_parse_node_single(priv, gtype, port, li, is_cpu);
668668
}
669669

670-
static void graph_parse_daifmt(struct device_node *node,
671-
unsigned int *daifmt, unsigned int *bit_frame)
670+
static void graph_parse_daifmt(struct device_node *node, unsigned int *daifmt)
672671
{
673672
unsigned int fmt;
674673

@@ -693,16 +692,6 @@ static void graph_parse_daifmt(struct device_node *node,
693692
* };
694693
*/
695694

696-
/*
697-
* clock_provider:
698-
*
699-
* It can be judged it is provider
700-
* if (A) or (B) or (C) has bitclock-master / frame-master flag.
701-
*
702-
* use "or"
703-
*/
704-
*bit_frame |= snd_soc_daifmt_parse_clock_provider_as_bitmap(node, NULL);
705-
706695
#define update_daifmt(name) \
707696
if (!(*daifmt & SND_SOC_DAIFMT_##name##_MASK) && \
708697
(fmt & SND_SOC_DAIFMT_##name##_MASK)) \
@@ -720,6 +709,17 @@ static void graph_parse_daifmt(struct device_node *node,
720709
update_daifmt(INV);
721710
}
722711

712+
static unsigned int graph_parse_bitframe(struct device_node *ep)
713+
{
714+
struct device_node *port __free(device_node) = ep_to_port(ep);
715+
struct device_node *ports __free(device_node) = port_to_ports(port);
716+
717+
return snd_soc_daifmt_clock_provider_from_bitmap(
718+
snd_soc_daifmt_parse_clock_provider_as_bitmap(ep, NULL) |
719+
snd_soc_daifmt_parse_clock_provider_as_bitmap(port, NULL) |
720+
snd_soc_daifmt_parse_clock_provider_as_bitmap(ports, NULL));
721+
}
722+
723723
static void graph_link_init(struct simple_util_priv *priv,
724724
struct device_node *lnk,
725725
struct device_node *port_cpu,
@@ -730,15 +730,19 @@ static void graph_link_init(struct simple_util_priv *priv,
730730
struct snd_soc_dai_link *dai_link = simple_priv_to_link(priv, li->link);
731731
struct simple_dai_props *dai_props = simple_priv_to_props(priv, li->link);
732732
struct device_node *ep_cpu, *ep_codec;
733-
unsigned int daifmt = 0, daiclk = 0;
733+
struct device_node *multi_cpu_port = NULL, *multi_codec_port = NULL;
734+
struct snd_soc_dai_link_component *dlc;
735+
unsigned int daifmt = 0;
734736
bool playback_only = 0, capture_only = 0;
735737
enum snd_soc_trigger_order trigger_start = SND_SOC_TRIGGER_ORDER_DEFAULT;
736738
enum snd_soc_trigger_order trigger_stop = SND_SOC_TRIGGER_ORDER_DEFAULT;
737-
unsigned int bit_frame = 0;
739+
int multi_cpu_port_idx = 1, multi_codec_port_idx = 1;
740+
int i;
738741

739742
of_node_get(port_cpu);
740743
if (graph_lnk_is_multi(port_cpu)) {
741-
ep_cpu = graph_get_next_multi_ep(&port_cpu, 1);
744+
multi_cpu_port = port_cpu;
745+
ep_cpu = graph_get_next_multi_ep(&multi_cpu_port, multi_cpu_port_idx++);
742746
of_node_put(port_cpu);
743747
port_cpu = ep_to_port(ep_cpu);
744748
} else {
@@ -748,21 +752,22 @@ static void graph_link_init(struct simple_util_priv *priv,
748752

749753
of_node_get(port_codec);
750754
if (graph_lnk_is_multi(port_codec)) {
751-
ep_codec = graph_get_next_multi_ep(&port_codec, 1);
755+
multi_codec_port = port_codec;
756+
ep_codec = graph_get_next_multi_ep(&multi_codec_port, multi_codec_port_idx++);
752757
of_node_put(port_codec);
753758
port_codec = ep_to_port(ep_codec);
754759
} else {
755760
ep_codec = of_graph_get_next_port_endpoint(port_codec, NULL);
756761
}
757762
struct device_node *ports_codec __free(device_node) = port_to_ports(port_codec);
758763

759-
graph_parse_daifmt(ep_cpu, &daifmt, &bit_frame);
760-
graph_parse_daifmt(ep_codec, &daifmt, &bit_frame);
761-
graph_parse_daifmt(port_cpu, &daifmt, &bit_frame);
762-
graph_parse_daifmt(port_codec, &daifmt, &bit_frame);
763-
graph_parse_daifmt(ports_cpu, &daifmt, &bit_frame);
764-
graph_parse_daifmt(ports_codec, &daifmt, &bit_frame);
765-
graph_parse_daifmt(lnk, &daifmt, &bit_frame);
764+
graph_parse_daifmt(ep_cpu, &daifmt);
765+
graph_parse_daifmt(ep_codec, &daifmt);
766+
graph_parse_daifmt(port_cpu, &daifmt);
767+
graph_parse_daifmt(port_codec, &daifmt);
768+
graph_parse_daifmt(ports_cpu, &daifmt);
769+
graph_parse_daifmt(ports_codec, &daifmt);
770+
graph_parse_daifmt(lnk, &daifmt);
766771

767772
graph_util_parse_link_direction(lnk, &playback_only, &capture_only);
768773
graph_util_parse_link_direction(ports_cpu, &playback_only, &capture_only);
@@ -788,22 +793,29 @@ static void graph_link_init(struct simple_util_priv *priv,
788793
graph_util_parse_trigger_order(priv, ep_cpu, &trigger_start, &trigger_stop);
789794
graph_util_parse_trigger_order(priv, ep_codec, &trigger_start, &trigger_stop);
790795

791-
/*
792-
* convert bit_frame
793-
* We need to flip clock_provider if it was CPU node,
794-
* because it is Codec base.
795-
*/
796-
daiclk = snd_soc_daifmt_clock_provider_from_bitmap(bit_frame);
797-
if (is_cpu_node)
798-
daiclk = snd_soc_daifmt_clock_provider_flipped(daiclk);
796+
for_each_link_cpus(dai_link, i, dlc) {
797+
dlc->ext_fmt = graph_parse_bitframe(ep_cpu);
798+
799+
if (multi_cpu_port)
800+
ep_cpu = graph_get_next_multi_ep(&multi_cpu_port, multi_cpu_port_idx++);
801+
}
802+
803+
for_each_link_codecs(dai_link, i, dlc) {
804+
dlc->ext_fmt = graph_parse_bitframe(ep_codec);
805+
806+
if (multi_codec_port)
807+
ep_codec = graph_get_next_multi_ep(&multi_codec_port, multi_codec_port_idx++);
808+
}
809+
810+
/*** Don't use port_cpu / port_codec after here ***/
799811

800812
dai_link->playback_only = playback_only;
801813
dai_link->capture_only = capture_only;
802814

803815
dai_link->trigger_start = trigger_start;
804816
dai_link->trigger_stop = trigger_stop;
805817

806-
dai_link->dai_fmt = daifmt | daiclk;
818+
dai_link->dai_fmt = daifmt;
807819
dai_link->init = simple_util_dai_init;
808820
dai_link->ops = &graph_ops;
809821
if (priv->ops)

0 commit comments

Comments
 (0)