nrf54L Series I2S MCLK divider?

Hi ... have code that outputs I2S in master mode.    The slave, a NAU8822 device requires Master Clock Source between 8 and 33MHz.

The 54L MCLK pin is duplicating the BCLK frequency, currently 1,2MHz odd.    Datasheet for 54L Series, page 324 says ..

Example:  NRF_I2S->CONFIG.RATIO = I2S_CONFIG_RATIO_RATIO_256X << I2S_CONFIG_RATIO_RATIO_Pos;      

The issue however is that the SDK uses a i2c_config struct for setting up the I2S.   No option exists to set the divide ratio.   

No examples or test example code seem to show a solution for this.  

Can you please assist in how I can set the divide ratio for the MCLK.

Thank you

Brian 

  

Parents
  • Hi Brian,

    I think you are using the Zephyr I2S driver together and the i2s_config struct, rather than i2c, right?

    The Zephyr I2S driver is several layers of abstraction higher than the registers you are referring from the datasheet. With the Zephyr I2S driver, you will care about the two fields of the i2s_config struct:

    frame_clk_freq

    word_size

    You just need to configure those fields to the appropriate values for your I2S device, and the driver will calculate and configure the ratio under the hood.

    For reference, the function that does the conversion is: sdk-zephyr/drivers/i2s/i2s_nrfx.c at v4.0.99-ncs1-1 · nrfconnect/sdk-zephyr.

    Hieu

  • Hi Hieu

    Firstly, the 'i2c' referenced in my question is a typo .. indeed it was meant to be i2s.
    Your response does not answer my question I'm afraid. Let me explain ..

    So my code has the following bit of code .. straight from Nordic Zephyr example. Those that exist all seem to follow the exact same setup.

    /* Configure I2S stream */
    i2s_cfg.word_size = 16U;
    i2s_cfg.channels = 2U;
    i2s_cfg.format = I2S_FMT_DATA_FORMAT_I2S;
    i2s_cfg.frame_clk_freq = 44100;
    i2s_cfg.block_size = BLOCK_SIZE;
    i2s_cfg.timeout = 2000;

    This code produces an approx. 44100Hz LR Clock a expected. The word size being 16 bits results in a clock of approx. 1,38MHz.  
    All as expected. But Master Clock pin output still the same frequency as the bit clock pin output.

    Regards the response pointing out 'word_size" and "frame_clk_freq"
    The WORD Size referenced is 16 bits and frame is 44,1KHz. These variables produce correct bit pattern output.

    Your response - "You just need to configure those fields to the appropriate values for your I2S device, and the driver will calculate and configure the ratio under the hood"

    Well no .. not for Master Clock. I need a multiple of the 1,38MHz clocked out of the MASTER CLOCK pin. This is what the Master Clock pin is for.   What am I missing?

    Thank you

    Brian 

  • Hello Hieu,

    I am facing a similar issue with a nRF54L15 and a TLV320DAC3100: I also need a MCK which is a lot higher than the BCK.

    I do not think that the Zephyr API has to be changed: An extension in the devicetree bindings only for the Nordic SOC would be sufficient. For example, if a MCK clock is set in the devicetree for a Nordic I2S device (e.g. in an overlay) the automatic calculation of the requested mck could be skipped (see function nrfx_i2s_prescalers_calc in nrfx/drivers/src/nrfx_i2s.c)

    Best regards

    Stefan

  • Mmmh, nrfx_i2s.c is not a Zephyr driver. So the nrfx_i2s_clk_params_t might be extended by a "requested_mck" field which could be filled by the Zephyr driver and kept at/set to 0 for the non-Zepyhr use case

  • Hi Stefan,

    My apology for the late follow up.

    That is an interesting idea. Would you like to make a pull request for it?
    There are some guidelines, but you can just get the implementation out and I can help you adjust things as needed.

    If you would like to stop just at sharing the idea, that is of course also welcomed. I will create a task on our backlog.

    Best regards,

    Hieu

  • Hi Hieu,

    I had a closer look at the driver in nrfx_i2s.c, but I do not understand the logic of how the divider values are calculated. Furthermore I am only using Zephyr, but this driver is most likely also used for baremetal configurations. So I do not understand how an addition to a struct which is used by both approaches would be intitialized in the baremetal world (will the element be set to zero).

    So I am not going to prepare a pull request.

    Best regards

    Stefan

  • Hi Stefan, I have taken over this case from Hieu for a bit.

    Stefan Schmidt said:

    So I am not going to prepare a pull request.

    That is fine. I'll see if I can create a job for this on our backlog here. Thanks for the suggestion!

    Regards,

    Elfving

Reply Children
No Data
Related