mirror of
https://github.com/espressif/esp-idf
synced 2025-03-09 09:09:10 -04:00
i2s: fix the data lagging of slave role
Closes https://github.com/espressif/esp-idf/issues/9513
This commit is contained in:
parent
4d0ac129b4
commit
af0c0bd8ce
@ -346,7 +346,7 @@ component_ut_pytest_esp32s3_generic_multi_device:
|
||||
- .rules:test:component_ut-esp32s3
|
||||
needs:
|
||||
- build_pytest_components_esp32s3
|
||||
tags: [ esp32s3, Example_SPI_Quad_Multi_device, generic_multi_device ]
|
||||
tags: [ esp32s3, generic_multi_device ]
|
||||
|
||||
component_ut_pytest_esp32c2_generic:
|
||||
extends:
|
||||
|
@ -7,10 +7,6 @@ components/driver/test_apps/i2s_test_apps:
|
||||
components/driver/test_apps/i2s_test_apps/i2s_tdm:
|
||||
disable:
|
||||
- if: SOC_I2S_SUPPORTS_TDM != 1
|
||||
disable_test:
|
||||
- if: IDF_TARGET != "esp32s3"
|
||||
temporary: true
|
||||
reason: lack of runners
|
||||
|
||||
components/driver/test_apps/i2s_test_apps/legacy_i2s_adc_dac:
|
||||
disable:
|
||||
|
@ -49,8 +49,12 @@ static esp_err_t i2s_tdm_calculate_clock(i2s_chan_handle_t handle, const i2s_tdm
|
||||
}
|
||||
} while (clk_info->bclk_div <= 2);
|
||||
} else {
|
||||
/* For slave mode, mclk >= bclk * 8, so fix bclk_div to 2 first */
|
||||
clk_info->bclk_div = 8;
|
||||
if (clk_cfg->bclk_div < 8) {
|
||||
ESP_LOGW(TAG, "the current bclk division is too small, adjust the bclk division to 8");
|
||||
clk_info->bclk_div = 8;
|
||||
} else {
|
||||
clk_info->bclk_div = clk_cfg->bclk_div;
|
||||
}
|
||||
clk_info->bclk = rate * handle->total_slot * slot_bits;
|
||||
clk_info->mclk = clk_info->bclk * clk_info->bclk_div;
|
||||
}
|
||||
|
@ -118,6 +118,7 @@ extern "C" {
|
||||
.sample_rate_hz = rate, \
|
||||
.clk_src = I2S_CLK_SRC_DEFAULT, \
|
||||
.mclk_multiple = I2S_MCLK_MULTIPLE_256, \
|
||||
.bclk_div = 8, \
|
||||
}
|
||||
|
||||
/**
|
||||
@ -150,7 +151,8 @@ typedef struct {
|
||||
/* General fields */
|
||||
uint32_t sample_rate_hz; /*!< I2S sample rate */
|
||||
i2s_clock_src_t clk_src; /*!< Choose clock source */
|
||||
i2s_mclk_multiple_t mclk_multiple; /*!< The multiple of mclk to the sample rate */
|
||||
i2s_mclk_multiple_t mclk_multiple; /*!< The multiple of mclk to the sample rate, only take effect for master role */
|
||||
uint32_t bclk_div; /*!< The division from mclk to bclk, only take effect for slave role, it shouldn't be smaller than 8. Increase this field when data sent by slave lag behind */
|
||||
} i2s_tdm_clk_config_t;
|
||||
|
||||
/**
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "unity.h"
|
||||
#include "unity_test_utils.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "driver/i2s_tdm.h"
|
||||
|
||||
@ -159,7 +160,7 @@ static void test_i2s_tdm_master(uint32_t sample_rate, i2s_data_bit_width_t bit_w
|
||||
xTaskNotifyGive(subtask_handle); // notify subtask to exit
|
||||
xTaskNotifyWait(0, ULONG_MAX, NULL, portMAX_DELAY); // wait subtask to do some cleanups
|
||||
ESP_LOGI(TAG, "Deleting subtask");
|
||||
vTaskDelete(subtask_handle); // delete subtask
|
||||
unity_utils_task_delete(subtask_handle); // delete subtask
|
||||
|
||||
ESP_LOGI(TAG, "I2S TDM master receive stop");
|
||||
TEST_ESP_OK(i2s_channel_disable(i2s_tdm_rx_handle));
|
||||
@ -205,6 +206,9 @@ static void test_i2s_tdm_slave(uint32_t sample_rate, i2s_data_bit_width_t bit_wi
|
||||
.din = TEST_I2S_DO_IO // on slave, swap DI and DO pin
|
||||
},
|
||||
};
|
||||
if (sample_rate >= 96000) {
|
||||
i2s_tdm_config.clk_cfg.bclk_div = 12;
|
||||
}
|
||||
TEST_ESP_OK(i2s_channel_init_tdm_mode(i2s_tdm_tx_handle, &i2s_tdm_config));
|
||||
TEST_ESP_OK(i2s_channel_init_tdm_mode(i2s_tdm_rx_handle, &i2s_tdm_config));
|
||||
|
||||
|
@ -23,7 +23,8 @@ def run_multi_device_case(master: Dut, slave: Dut, case_name: str) -> None:
|
||||
|
||||
|
||||
@pytest.mark.esp32s3
|
||||
@pytest.mark.Example_SPI_Quad_Multi_device # to be changed to `generic_multi_device` in the future
|
||||
@pytest.mark.esp32c3
|
||||
@pytest.mark.generic_multi_device
|
||||
@pytest.mark.parametrize('count', [
|
||||
2,
|
||||
], indirect=True)
|
||||
|
@ -108,7 +108,7 @@ Overview of All Modes
|
||||
========= ======== ======== ======== ======== ======== ==========
|
||||
ESP32 I2S 0/1 I2S 0 I2S 0 none I2S 0 I2S 0
|
||||
ESP32S2 I2S 0 none none none none I2S 0
|
||||
ESP32C3 I2S 0 I2S 0 none I2S0 none none
|
||||
ESP32C3 I2S 0 I2S 0 none I2S 0 none none
|
||||
ESP32S3 I2S 0/1 I2S 0 I2S 0 I2S 0/1 none none
|
||||
========= ======== ======== ======== ======== ======== ==========
|
||||
|
||||
@ -723,6 +723,12 @@ Here is the table of the data that received in the buffer with different :cpp:me
|
||||
Please refer to :ref:`i2s-api-reference-i2s_tdm` for TDM API information.
|
||||
And for more details, please refer to :component_file:`driver/include/driver/i2s_tdm.h`.
|
||||
|
||||
.. note::
|
||||
|
||||
When setting the clock configuration for a slave role, please be aware that :cpp:member:`i2s_tdm_clk_config_t::bclk_div` should not be smaller than 8 (hardware limitation), increase this field can reduce the data lagging that sent from the slave. In the high sample rate case, the data might lag behind more than one ``bclk`` which will lead data malposition, you can try to increase :cpp:member:`i2s_tdm_clk_config_t::bclk_div` gradually to correct it.
|
||||
|
||||
As :cpp:member:`i2s_tdm_clk_config_t::bclk_div` is the division of ``mclk`` to ``bclk``, increase it will also increase the ``mclk`` frequency, therefore, the clock calculation might failed if the ``mclk`` is too high to divide from the source clock, which means :cpp:member:`i2s_tdm_clk_config_t::bclk_div` is not the bigger the better.
|
||||
|
||||
TDM TX Mode
|
||||
~~~~~~~~~~~
|
||||
|
||||
|
@ -66,7 +66,7 @@ markers =
|
||||
|
||||
# multi-dut markers
|
||||
multi_dut_generic: tests should be run on generic runners, at least have two duts connected.
|
||||
Example_SPI_Quad_Multi_device: SPI multi device marker
|
||||
generic_multi_device: generic multiple devices whose corresponding gpio pins are connected to each other.
|
||||
|
||||
# host_test markers
|
||||
host_test: tests which shouldn not be built at the build stage, and instead built in host_test stage.
|
||||
|
Loading…
x
Reference in New Issue
Block a user