[PATCH 4/7] ASoC: sun8i-codec: Add a quirk for LRCK inversion

Samuel Holland
2020-07-26T01:28:13Z

On the A64, as tested using the PinePhone, the current code causes the
left/right channels to be swapped during I2S playback from the CPU on
AIF1, and breaks DSP_A communication with the modem on AIF2. Both of
these are fixed when LRCK is no longer inverted.

Trusting that the comment in the code is correct, the existing behavior
is kept for the A33.

Signed-off-by: Samuel Holland <samuel@sholland.org>
---
sound/soc/sunxi/sun8i-codec.c | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)

diff --git a/sound/soc/sunxi/sun8i-codec.c b/sound/soc/sunxi/sun8i-codec.c
index a75be9e82d22..304683a71acd 100644
--- a/sound/soc/sunxi/sun8i-codec.c
+++ b/sound/soc/sunxi/sun8i-codec.c
@@ -88,6 +88,7 @@

struct sun8i_codec_quirks {
bool legacy_widgets : 1;
+ bool lrck_inversion : 1;
};

struct sun8i_codec {
@@ -215,18 +216,19 @@ static int sun8i_set_fmt(struct snd_soc_dai *dai, unsigned int fmt)
value << SUN8I_AIF1CLK_CTRL_AIF1_BCLK_INV);

/*
- * It appears that the DAI and the codec don't share the same
- * polarity for the LRCK signal when they mean 'normal' and
- * 'inverted' in the datasheet.
+ * It appears that the DAI and the codec in the A33 SoC don't
+ * share the same polarity for the LRCK signal when they mean
+ * 'normal' and 'inverted' in the datasheet.
*
* Since the DAI here is our regular i2s driver that have been
* tested with way more codecs than just this one, it means
* that the codec probably gets it backward, and we have to
* invert the value here.
*/
+ value ^= scodec->quirks->lrck_inversion;
regmap_update_bits(scodec->regmap, SUN8I_AIF1CLK_CTRL,
BIT(SUN8I_AIF1CLK_CTRL_AIF1_LRCK_INV),
- !value << SUN8I_AIF1CLK_CTRL_AIF1_LRCK_INV);
+ value << SUN8I_AIF1CLK_CTRL_AIF1_LRCK_INV);

/* DAI format */
switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
@@ -673,6 +675,7 @@ static int sun8i_codec_remove(struct platform_device *pdev)

static const struct sun8i_codec_quirks sun8i_a33_quirks = {
.legacy_widgets = true,
+ .lrck_inversion = true,
};

static const struct sun8i_codec_quirks sun50i_a64_quirks = {