Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

I2S Simple sound card issues from firmware version 6.6.20 and up #6568

Closed
rhysmorgan134 opened this issue Dec 28, 2024 · 4 comments
Closed

Comments

@rhysmorgan134
Copy link

rhysmorgan134 commented Dec 28, 2024

Describe the bug

I have a dtoverlay utilising simple soundcard that has been working fine for some time. When the Pi5 was released I had some issues but resolved this by point the overlay to <&i2s_clk_consumer> and all was working well. Now since version 6.6.20 I get the following error with the same overlay that was working

[    6.398476] designware-i2s 1f000a4000.i2s: ASoC: error at snd_soc_dai_set_tdm_slot on 1f000a4000.i2s: -22
[    6.398485] designware-i2s 1f000a4000.i2s: simple-card: set_tdm_slot error
[    6.398487]  1f000a4000.i2s-dit-hifi: ASoC: error at snd_soc_link_init on 1f000a4000.i2s-dit-hifi: -22

The overlay in question is below

//Device tree overlay for generic stereo audio codec. ex) Asahi kasei AK4556
/dts-v1/;
/plugin/;

/ {
    compatible = "brcm,bcm2835";

    fragment@0 {
        target = <&sound>;
        __overlay__ {
            compatible = "simple-audio-card";
            simple-audio-card,name = "PiMost";
            status="okay";

            capture_link: simple-audio-card,dai-link@0 {
                format = "i2s";

                // Set RasPi to I2S slave
                bitclock-master = <&r_codec_dai>;
                frame-master = <&r_codec_dai>;

                r_cpu_dai: cpu {
                    sound-dai = <&i2s_clk_consumer>;

                // TDM slot configuration for stereo
                    dai-tdm-slot-num = <2>;
                    dai-tdm-slot-width = <16>;
                };

                r_codec_dai: codec {
                    sound-dai = <&codec_in>;
                };
            };

            playback_link: simple-audio-card,dai-link@1 {
                format = "i2s";

                // Set RasPi to I2S slave
                bitclock-master = <&p_codec_dai>;
                frame-master = <&p_codec_dai>;

                p_cpu_dai: cpu {
                    sound-dai = <&i2s_clk_consumer>;

                // TDM slot configuration for stereo
                    dai-tdm-slot-num = <2>;
                    dai-tdm-slot-width = <16>;
                };

                p_codec_dai: codec {
                    sound-dai = <&codec_out>;
                };
            };
        };
    };

    fragment@1 {
        target-path = "/";
        __overlay__ {
            codec_out: spdif-transmitter {
                #address-cells = <0>;
                #size-cells = <0>;
                #sound-dai-cells = <0>;
                /*
                    "linux,spdif-dit" is used in generic I2S(transmitter) driver.
                    You can see details "linux,spdif-dit" by bellow command
                    modinfo snd_soc_spdif_tx
                */
                compatible = "linux,spdif-dit";
                status = "okay";
            };
            codec_in: spdif-receiver {
                #address-cells = <0>;
                #size-cells = <0>;
                #sound-dai-cells = <0>;
                /*
                    "linux,spdif-dir" is used in generic I2S(receiver) driver.
                    You can see details "linux,spdif-dir" by bellow command
                    modinfo snd_soc_spdif_rx
                */
                compatible = "linux,spdif-dir";
                status = "okay";
            };
        };
    };

    fragment@2 {
        target = <&i2s_clk_consumer>;
        __overlay__ {
            #sound-dai-cells = <0>;
            status = "okay";
        };
    };
};

If I remove all occurances of these two lines then the overlay loads ok.

dai-tdm-slot-num = <2>;
dai-tdm-slot-width = <16>;

Is this expected? I am concerned as to whether it is going to cause issues by not specifying the channels and slot widths?

Thanks

Rhys

Steps to reproduce the behaviour

  • Install overlay
  • reboot the pi
  • run dmesg | grep i2s
  • see the error logs

Device (s)

Raspberry Pi 5

System

Raspberry Pi reference 2024-11-19
Generated using pi-gen, https://github.com/RPi-Distro/pi-gen, 891df1e21ed2b6099a2e6a13e26c91dea44b34d4, stage4

Logs

[    6.398476] designware-i2s 1f000a4000.i2s: ASoC: error at snd_soc_dai_set_tdm_slot on 1f000a4000.i2s: -22
[    6.398485] designware-i2s 1f000a4000.i2s: simple-card: set_tdm_slot error
[    6.398487]  1f000a4000.i2s-dit-hifi: ASoC: error at snd_soc_link_init on 1f000a4000.i2s-dit-hifi: -22

Additional context

If I install this version of raspi-os then it all still works flawlessly

https://downloads.raspberrypi.org/raspios_arm64/images/raspios_arm64-2023-12-06/

@pelwell
Copy link
Contributor

pelwell commented Jan 6, 2025

As of kernel 6.5, the driver for the I2S blocks found in RP1 has required between 0 and 16 slots of 32 bits, and that tx_mask and rx_mask are the same and not zero. More than that, there is code elsewhere in the driver that if the number of TDM slots is non-zero then the data width is forced to 32-bits.

In the kernel you say worked fine (6.1.x), the I2S driver had no set_tdm_slot method. By my reading, this means that snd_soc_dai_set_tdm_slot would return -ENOTSUPP, an error which does not result in a log message but also ends up doing nothing useful.

Have you tried without the TDM configuration? How does 2 channels of 16-bit TDM differ from regular 2 channel 16-bit usage?

@pelwell
Copy link
Contributor

pelwell commented Jan 7, 2025

As far as I can tell, the RP1 I2S hardware has no explicit support for TDM mode: the WS clock always has a 50:50 duty cycle, and there is no support for arbitrary positioning of data within the frame. If it happened to work for you before then I think you don't actually need TDM mode. Which device are you interfacing to?

@rhysmorgan134
Copy link
Author

Thanks Phil, I can confirm it works by removing all tdm references. I've done a bit of further research and reading since your first reply and it makes sense for it to be omitted.

It's talking to a MOST bus HAT I've developed that runs at 44.1khz or 48khz 2 Channel out and in (which from my new understanding tdm is not required), with the HAT acting as master and clock source coming from the fibre optic network.

Thanks a lot for your assistance with this, it's hugely appreciated!

@pelwell
Copy link
Contributor

pelwell commented Jan 7, 2025

Thanks for the confirmation, and for forcing me to understand TDM mode.

@pelwell pelwell closed this as completed Jan 7, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants