I2C: Refactor i2c hal and ll

This commit is contained in:
Cao Sen Miao
2022-08-24 16:29:00 +08:00
parent 5e47c7ce13
commit 31b88a4c88
13 changed files with 1669 additions and 2238 deletions

View File

@@ -34,8 +34,6 @@
#include "clk_ctrl_os.h"
#endif
static const char *I2C_TAG = "i2c";
/* DRAM_ATTR is required to avoid I2C array placed in flash, due to accessed from ISR */
@@ -376,8 +374,8 @@ esp_err_t i2c_driver_install(i2c_port_t i2c_num, i2c_mode_t mode, size_t slv_rx_
}
i2c_hw_enable(i2c_num);
//Disable I2C interrupt.
i2c_hal_disable_intr_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_hal_clr_intsts_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_ll_disable_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
//hook isr handler
ret = esp_intr_alloc(i2c_periph_signal[i2c_num].irq, intr_alloc_flags,
i2c_isr_handler_default, p_i2c_obj[i2c_num],
@@ -386,7 +384,7 @@ esp_err_t i2c_driver_install(i2c_port_t i2c_num, i2c_mode_t mode, size_t slv_rx_
#if SOC_I2C_SUPPORT_SLAVE
//Enable I2C slave rx interrupt
if (mode == I2C_MODE_SLAVE) {
i2c_hal_enable_slave_rx_it(&(i2c_context[i2c_num].hal));
i2c_ll_slave_enable_rx_it(i2c_context[i2c_num].hal.dev);
}
#endif // SOC_I2C_SUPPORT_SLAVE
return ESP_OK;
@@ -443,7 +441,7 @@ esp_err_t i2c_driver_delete(i2c_port_t i2c_num)
ESP_RETURN_ON_FALSE(p_i2c_obj[i2c_num] != NULL, ESP_FAIL, I2C_TAG, I2C_DRIVER_ERR_STR);
i2c_obj_t *p_i2c = p_i2c_obj[i2c_num];
i2c_hal_disable_intr_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_ll_disable_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
esp_intr_free(p_i2c->intr_handle);
p_i2c->intr_handle = NULL;
@@ -500,7 +498,7 @@ esp_err_t i2c_reset_tx_fifo(i2c_port_t i2c_num)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_txfifo_rst(&(i2c_context[i2c_num].hal));
i2c_ll_txfifo_rst(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -509,7 +507,7 @@ esp_err_t i2c_reset_rx_fifo(i2c_port_t i2c_num)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_rxfifo_rst(&(i2c_context[i2c_num].hal));
i2c_ll_rxfifo_rst(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -522,7 +520,7 @@ static void IRAM_ATTR i2c_isr_handler_default(void *arg)
// On C3 and S3 targets, the I2C may trigger a spurious interrupt,
// in order to detect these false positive, check the I2C's hardware interrupt mask
uint32_t int_mask;
i2c_hal_get_intsts_mask(&(i2c_context[i2c_num].hal), &int_mask);
i2c_ll_get_intr_mask(i2c_context[i2c_num].hal.dev, &int_mask);
if (int_mask == 0) {
return;
}
@@ -561,25 +559,25 @@ static void IRAM_ATTR i2c_isr_handler_default(void *arg)
}
#if SOC_I2C_SUPPORT_SLAVE
else {
i2c_hal_slave_handle_event(&(i2c_context[i2c_num].hal), &evt_type);
i2c_ll_slave_get_event(i2c_context[i2c_num].hal.dev, &evt_type);
if (evt_type == I2C_INTR_EVENT_TRANS_DONE || evt_type == I2C_INTR_EVENT_RXFIFO_FULL) {
uint32_t rx_fifo_cnt;
i2c_hal_get_rxfifo_cnt(&(i2c_context[i2c_num].hal), &rx_fifo_cnt);
i2c_hal_read_rxfifo(&(i2c_context[i2c_num].hal), p_i2c->data_buf, rx_fifo_cnt);
i2c_ll_get_rxfifo_cnt(i2c_context[i2c_num].hal.dev, &rx_fifo_cnt);
i2c_ll_read_rxfifo(i2c_context[i2c_num].hal.dev, p_i2c->data_buf, rx_fifo_cnt);
xRingbufferSendFromISR(p_i2c->rx_ring_buf, p_i2c->data_buf, rx_fifo_cnt, &HPTaskAwoken);
i2c_hal_slave_clr_rx_it(&(i2c_context[i2c_num].hal));
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, int_mask);
} else if (evt_type == I2C_INTR_EVENT_TXFIFO_EMPTY) {
uint32_t tx_fifo_rem;
i2c_hal_get_txfifo_cnt(&(i2c_context[i2c_num].hal), &tx_fifo_rem);
i2c_ll_get_txfifo_len(i2c_context[i2c_num].hal.dev, &tx_fifo_rem);
size_t size = 0;
uint8_t *data = (uint8_t *) xRingbufferReceiveUpToFromISR(p_i2c->tx_ring_buf, &size, tx_fifo_rem);
if (data) {
i2c_hal_write_txfifo(&(i2c_context[i2c_num].hal), data, size);
i2c_ll_write_txfifo(i2c_context[i2c_num].hal.dev, data, size);
vRingbufferReturnItemFromISR(p_i2c->tx_ring_buf, data, &HPTaskAwoken);
} else {
i2c_hal_disable_slave_tx_it(&(i2c_context[i2c_num].hal));
i2c_ll_slave_disable_tx_it(i2c_context[i2c_num].hal.dev);
}
i2c_hal_slave_clr_tx_it(&(i2c_context[i2c_num].hal));
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, int_mask);
}
}
#endif // SOC_I2C_SUPPORT_SLAVE
@@ -595,8 +593,8 @@ esp_err_t i2c_set_data_mode(i2c_port_t i2c_num, i2c_trans_mode_t tx_trans_mode,
ESP_RETURN_ON_FALSE(tx_trans_mode < I2C_DATA_MODE_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TRANS_MODE_ERR_STR);
ESP_RETURN_ON_FALSE(rx_trans_mode < I2C_DATA_MODE_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TRANS_MODE_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_data_mode(&(i2c_context[i2c_num].hal), tx_trans_mode, rx_trans_mode);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_data_mode(i2c_context[i2c_num].hal.dev, tx_trans_mode, rx_trans_mode);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -604,7 +602,7 @@ esp_err_t i2c_set_data_mode(i2c_port_t i2c_num, i2c_trans_mode_t tx_trans_mode,
esp_err_t i2c_get_data_mode(i2c_port_t i2c_num, i2c_trans_mode_t *tx_trans_mode, i2c_trans_mode_t *rx_trans_mode)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
i2c_hal_get_data_mode(&(i2c_context[i2c_num].hal), tx_trans_mode, rx_trans_mode);
i2c_ll_get_data_mode(i2c_context[i2c_num].hal.dev, tx_trans_mode, rx_trans_mode);
return ESP_OK;
}
@@ -642,7 +640,7 @@ static esp_err_t i2c_master_clear_bus(i2c_port_t i2c_num)
gpio_set_level(sda_io, 1); // STOP, SDA low -> high while SCL is HIGH
i2c_set_pin(i2c_num, sda_io, scl_io, 1, 1, I2C_MODE_MASTER);
#else
i2c_hal_master_clr_bus(&(i2c_context[i2c_num].hal));
i2c_ll_master_clr_bus(i2c_context[i2c_num].hal.dev);
#endif
return ESP_OK;
}
@@ -656,36 +654,24 @@ static esp_err_t i2c_hw_fsm_reset(i2c_port_t i2c_num)
// A workaround for avoiding cause timeout issue when using
// hardware reset.
#if !SOC_I2C_SUPPORT_HW_FSM_RST
int scl_low_period, scl_high_period, scl_wait_high_period;
int scl_start_hold, scl_rstart_setup;
int scl_stop_hold, scl_stop_setup;
int sda_hold, sda_sample;
int timeout;
i2c_hal_timing_config_t timing_config;
uint8_t filter_cfg;
i2c_hal_get_scl_clk_timing(&(i2c_context[i2c_num].hal), &scl_high_period, &scl_low_period, &scl_wait_high_period);
i2c_hal_get_start_timing(&(i2c_context[i2c_num].hal), &scl_rstart_setup, &scl_start_hold);
i2c_hal_get_stop_timing(&(i2c_context[i2c_num].hal), &scl_stop_setup, &scl_stop_hold);
i2c_hal_get_sda_timing(&(i2c_context[i2c_num].hal), &sda_sample, &sda_hold);
i2c_hal_get_tout(&(i2c_context[i2c_num].hal), &timeout);
i2c_hal_get_filter(&(i2c_context[i2c_num].hal), &filter_cfg);
i2c_hal_get_timing_config(&i2c_context[i2c_num].hal, &timing_config);
i2c_ll_get_filter(i2c_context[i2c_num].hal.dev, &filter_cfg);
//to reset the I2C hw module, we need re-enable the hw
i2c_hw_disable(i2c_num);
i2c_master_clear_bus(i2c_num);
i2c_hw_enable(i2c_num);
i2c_hal_master_init(&(i2c_context[i2c_num].hal), i2c_num);
i2c_hal_disable_intr_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_hal_clr_intsts_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_hal_set_scl_clk_timing(&(i2c_context[i2c_num].hal), scl_high_period, scl_low_period, scl_wait_high_period);
i2c_hal_set_start_timing(&(i2c_context[i2c_num].hal), scl_rstart_setup, scl_start_hold);
i2c_hal_set_stop_timing(&(i2c_context[i2c_num].hal), scl_stop_setup, scl_stop_hold);
i2c_hal_set_sda_timing(&(i2c_context[i2c_num].hal), sda_sample, sda_hold);
i2c_hal_set_tout(&(i2c_context[i2c_num].hal), timeout);
i2c_hal_set_filter(&(i2c_context[i2c_num].hal), filter_cfg);
i2c_hal_master_init(&(i2c_context[i2c_num].hal));
i2c_ll_disable_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
i2c_hal_set_timing_config(&i2c_context[i2c_num].hal, &timing_config);
i2c_ll_set_filter(i2c_context[i2c_num].hal.dev, filter_cfg);
#else
i2c_hal_master_fsm_rst(&(i2c_context[i2c_num].hal));
i2c_ll_master_fsm_rst(i2c_context[i2c_num].hal.dev);
i2c_master_clear_bus(i2c_num);
#endif
return ESP_OK;
@@ -769,28 +755,29 @@ esp_err_t i2c_param_config(i2c_port_t i2c_num, const i2c_config_t *i2c_conf)
}
i2c_hw_enable(i2c_num);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_disable_intr_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_hal_clr_intsts_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_ll_disable_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
#if SOC_I2C_SUPPORT_SLAVE
if (i2c_conf->mode == I2C_MODE_SLAVE) { //slave mode
i2c_hal_slave_init(&(i2c_context[i2c_num].hal), i2c_num);
i2c_hal_set_source_clk(&(i2c_context[i2c_num].hal), src_clk);
i2c_hal_set_slave_addr(&(i2c_context[i2c_num].hal), i2c_conf->slave.slave_addr, i2c_conf->slave.addr_10bit_en);
i2c_hal_set_rxfifo_full_thr(&(i2c_context[i2c_num].hal), I2C_FIFO_FULL_THRESH_VAL);
i2c_hal_set_txfifo_empty_thr(&(i2c_context[i2c_num].hal), I2C_FIFO_EMPTY_THRESH_VAL);
i2c_hal_slave_init(&(i2c_context[i2c_num].hal));
i2c_ll_slave_tx_auto_start_en(i2c_context[i2c_num].hal.dev, true);
i2c_ll_set_source_clk(i2c_context[i2c_num].hal.dev, src_clk);
i2c_ll_set_slave_addr(i2c_context[i2c_num].hal.dev, i2c_conf->slave.slave_addr, i2c_conf->slave.addr_10bit_en);
i2c_ll_set_rxfifo_full_thr(i2c_context[i2c_num].hal.dev, I2C_FIFO_FULL_THRESH_VAL);
i2c_ll_set_txfifo_empty_thr(i2c_context[i2c_num].hal.dev, I2C_FIFO_EMPTY_THRESH_VAL);
//set timing for data
i2c_hal_set_sda_timing(&(i2c_context[i2c_num].hal), I2C_SLAVE_SDA_SAMPLE_DEFAULT, I2C_SLAVE_SDA_HOLD_DEFAULT);
i2c_hal_set_tout(&(i2c_context[i2c_num].hal), I2C_SLAVE_TIMEOUT_DEFAULT);
i2c_hal_enable_slave_rx_it(&(i2c_context[i2c_num].hal));
i2c_ll_set_sda_timing(i2c_context[i2c_num].hal.dev, I2C_SLAVE_SDA_SAMPLE_DEFAULT, I2C_SLAVE_SDA_HOLD_DEFAULT);
i2c_ll_set_tout(i2c_context[i2c_num].hal.dev, I2C_SLAVE_TIMEOUT_DEFAULT);
i2c_ll_slave_enable_rx_it(i2c_context[i2c_num].hal.dev);
} else
#endif // SOC_I2C_SUPPORT_SLAVE
{
i2c_hal_master_init(&(i2c_context[i2c_num].hal), i2c_num);
i2c_hal_master_init(&(i2c_context[i2c_num].hal));
//Default, we enable hardware filter
i2c_hal_set_filter(&(i2c_context[i2c_num].hal), I2C_FILTER_CYC_NUM_DEF);
i2c_ll_set_filter(i2c_context[i2c_num].hal.dev, I2C_FILTER_CYC_NUM_DEF);
i2c_hal_set_bus_timing(&(i2c_context[i2c_num].hal), i2c_conf->master.clk_speed, src_clk, s_get_src_clk_freq(src_clk));
}
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -802,8 +789,8 @@ esp_err_t i2c_set_period(i2c_port_t i2c_num, int high_period, int low_period)
ESP_RETURN_ON_FALSE((low_period <= I2C_SCL_LOW_PERIOD_V) && (low_period > 0), ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TIMING_VAL_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_scl_timing(&(i2c_context[i2c_num].hal), high_period, low_period);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_scl_timing(i2c_context[i2c_num].hal.dev, high_period, low_period);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -812,7 +799,7 @@ esp_err_t i2c_get_period(i2c_port_t i2c_num, int *high_period, int *low_period)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX && high_period != NULL && low_period != NULL, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_get_scl_timing(&(i2c_context[i2c_num].hal), high_period, low_period);
i2c_ll_get_scl_timing(i2c_context[i2c_num].hal.dev, high_period, low_period);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -822,8 +809,8 @@ esp_err_t i2c_filter_enable(i2c_port_t i2c_num, uint8_t cyc_num)
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
ESP_RETURN_ON_FALSE(p_i2c_obj[i2c_num] != NULL, ESP_FAIL, I2C_TAG, I2C_DRIVER_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_filter(&(i2c_context[i2c_num].hal), cyc_num);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_filter(i2c_context[i2c_num].hal.dev, cyc_num);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -832,8 +819,8 @@ esp_err_t i2c_filter_disable(i2c_port_t i2c_num)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_filter(&(i2c_context[i2c_num].hal), 0);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_filter(i2c_context[i2c_num].hal.dev, 0);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -845,8 +832,8 @@ esp_err_t i2c_set_start_timing(i2c_port_t i2c_num, int setup_time, int hold_time
ESP_RETURN_ON_FALSE((setup_time <= I2C_SCL_RSTART_SETUP_TIME_V) && (setup_time > 0), ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TIMING_VAL_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_start_timing(&(i2c_context[i2c_num].hal), setup_time, hold_time);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_start_timing(i2c_context[i2c_num].hal.dev, setup_time, hold_time);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -855,7 +842,7 @@ esp_err_t i2c_get_start_timing(i2c_port_t i2c_num, int *setup_time, int *hold_ti
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX && setup_time != NULL && hold_time != NULL, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_get_start_timing(&(i2c_context[i2c_num].hal), setup_time, hold_time);
i2c_ll_get_start_timing(i2c_context[i2c_num].hal.dev, setup_time, hold_time);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -867,8 +854,8 @@ esp_err_t i2c_set_stop_timing(i2c_port_t i2c_num, int setup_time, int hold_time)
ESP_RETURN_ON_FALSE((hold_time <= I2C_SCL_STOP_HOLD_TIME_V) && (hold_time > 0), ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TIMING_VAL_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_stop_timing(&(i2c_context[i2c_num].hal), setup_time, hold_time);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_stop_timing(i2c_context[i2c_num].hal.dev, setup_time, hold_time);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -877,7 +864,7 @@ esp_err_t i2c_get_stop_timing(i2c_port_t i2c_num, int *setup_time, int *hold_tim
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX && setup_time != NULL && hold_time != NULL, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_get_stop_timing(&(i2c_context[i2c_num].hal), setup_time, hold_time);
i2c_ll_get_stop_timing(i2c_context[i2c_num].hal.dev, setup_time, hold_time);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -889,8 +876,8 @@ esp_err_t i2c_set_data_timing(i2c_port_t i2c_num, int sample_time, int hold_time
ESP_RETURN_ON_FALSE((hold_time <= I2C_SDA_HOLD_TIME_V) && (hold_time > 0), ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TIMING_VAL_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_sda_timing(&(i2c_context[i2c_num].hal), sample_time, hold_time);
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_ll_set_sda_timing(i2c_context[i2c_num].hal.dev, sample_time, hold_time);
i2c_ll_update(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -899,7 +886,7 @@ esp_err_t i2c_get_data_timing(i2c_port_t i2c_num, int *sample_time, int *hold_ti
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX && sample_time != NULL && hold_time != NULL, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_get_sda_timing(&(i2c_context[i2c_num].hal), sample_time, hold_time);
i2c_ll_get_sda_timing(i2c_context[i2c_num].hal.dev, sample_time, hold_time);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -910,7 +897,7 @@ esp_err_t i2c_set_timeout(i2c_port_t i2c_num, int timeout)
ESP_RETURN_ON_FALSE((timeout <= I2C_LL_MAX_TIMEOUT) && (timeout > 0), ESP_ERR_INVALID_ARG, I2C_TAG, I2C_TIMING_VAL_ERR_STR);
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_set_tout(&(i2c_context[i2c_num].hal), timeout);
i2c_ll_set_tout(i2c_context[i2c_num].hal.dev, timeout);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
return ESP_OK;
}
@@ -918,7 +905,7 @@ esp_err_t i2c_set_timeout(i2c_port_t i2c_num, int timeout)
esp_err_t i2c_get_timeout(i2c_port_t i2c_num, int *timeout)
{
ESP_RETURN_ON_FALSE(i2c_num < I2C_NUM_MAX && timeout != NULL, ESP_ERR_INVALID_ARG, I2C_TAG, I2C_NUM_ERROR_STR);
i2c_hal_get_tout(&(i2c_context[i2c_num].hal), timeout);
i2c_ll_get_tout(i2c_context[i2c_num].hal.dev, timeout);
return ESP_OK;
}
@@ -1363,7 +1350,7 @@ static void IRAM_ATTR i2c_master_cmd_begin_static(i2c_port_t i2c_num, portBASE_T
i2c_cmd_evt_t evt = { 0 };
if (p_i2c->cmd_link.head != NULL && p_i2c->status == I2C_STATUS_READ) {
i2c_cmd_t *cmd = &p_i2c->cmd_link.head->cmd;
i2c_hal_read_rxfifo(&(i2c_context[i2c_num].hal), cmd->data + cmd->bytes_used, p_i2c->rx_cnt);
i2c_ll_read_rxfifo(i2c_context[i2c_num].hal.dev, cmd->data + cmd->bytes_used, p_i2c->rx_cnt);
/* rx_cnt bytes have just been read, increment the number of bytes used from the buffer */
cmd->bytes_used += p_i2c->rx_cnt;
@@ -1425,10 +1412,10 @@ static void IRAM_ATTR i2c_master_cmd_begin_static(i2c_port_t i2c_num, portBASE_T
write_pr = (uint8_t*) &cmd->data_byte;
}
hw_cmd.byte_num = fifo_fill;
i2c_hal_write_txfifo(&(i2c_context[i2c_num].hal), write_pr, fifo_fill);
i2c_hal_write_cmd_reg(&(i2c_context[i2c_num].hal), hw_cmd, p_i2c->cmd_idx);
i2c_hal_write_cmd_reg(&(i2c_context[i2c_num].hal), hw_end_cmd, p_i2c->cmd_idx + 1);
i2c_hal_enable_master_tx_it(&(i2c_context[i2c_num].hal));
i2c_ll_write_txfifo(i2c_context[i2c_num].hal.dev, write_pr, fifo_fill);
i2c_ll_write_cmd_reg(i2c_context[i2c_num].hal.dev, hw_cmd, p_i2c->cmd_idx);
i2c_ll_write_cmd_reg(i2c_context[i2c_num].hal.dev, hw_end_cmd, p_i2c->cmd_idx + 1);
i2c_ll_master_enable_tx_it(i2c_context[i2c_num].hal.dev);
p_i2c->cmd_idx = 0;
if (i2c_cmd_is_single_byte(cmd) || cmd->total_bytes == cmd->bytes_used) {
p_i2c->cmd_link.head = p_i2c->cmd_link.head->next;
@@ -1443,13 +1430,13 @@ static void IRAM_ATTR i2c_master_cmd_begin_static(i2c_port_t i2c_num, portBASE_T
fifo_fill = MIN(remaining_bytes, SOC_I2C_FIFO_LEN);
p_i2c->rx_cnt = fifo_fill;
hw_cmd.byte_num = fifo_fill;
i2c_hal_write_cmd_reg(&(i2c_context[i2c_num].hal), hw_cmd, p_i2c->cmd_idx);
i2c_hal_write_cmd_reg(&(i2c_context[i2c_num].hal), hw_end_cmd, p_i2c->cmd_idx + 1);
i2c_hal_enable_master_rx_it(&(i2c_context[i2c_num].hal));
i2c_ll_write_cmd_reg(i2c_context[i2c_num].hal.dev, hw_cmd, p_i2c->cmd_idx);
i2c_ll_write_cmd_reg(i2c_context[i2c_num].hal.dev, hw_end_cmd, p_i2c->cmd_idx + 1);
i2c_ll_master_enable_rx_it(i2c_context[i2c_num].hal.dev);
p_i2c->status = I2C_STATUS_READ;
break;
} else {
i2c_hal_write_cmd_reg(&(i2c_context[i2c_num].hal), hw_cmd, p_i2c->cmd_idx);
i2c_ll_write_cmd_reg(i2c_context[i2c_num].hal.dev, hw_cmd, p_i2c->cmd_idx);
}
p_i2c->cmd_idx++;
p_i2c->cmd_link.head = p_i2c->cmd_link.head->next;
@@ -1458,8 +1445,8 @@ static void IRAM_ATTR i2c_master_cmd_begin_static(i2c_port_t i2c_num, portBASE_T
break;
}
}
i2c_hal_update_config(&(i2c_context[i2c_num].hal));
i2c_hal_trans_start(&(i2c_context[i2c_num].hal));
i2c_ll_update(i2c_context[i2c_num].hal.dev);
i2c_ll_trans_start(i2c_context[i2c_num].hal.dev);
return;
}
@@ -1513,7 +1500,7 @@ esp_err_t i2c_master_cmd_begin(i2c_port_t i2c_num, i2c_cmd_handle_t cmd_handle,
#endif
xQueueReset(p_i2c->cmd_evt_queue);
if (p_i2c->status == I2C_STATUS_TIMEOUT
|| i2c_hal_is_bus_busy(&(i2c_context[i2c_num].hal))) {
|| i2c_ll_is_bus_busy(i2c_context[i2c_num].hal.dev)) {
i2c_hw_fsm_reset(i2c_num);
clear_bus_cnt[i2c_num] = 0;
}
@@ -1534,8 +1521,8 @@ esp_err_t i2c_master_cmd_begin(i2c_port_t i2c_num, i2c_cmd_handle_t cmd_handle,
i2c_reset_rx_fifo(i2c_num);
// These two interrupts some times can not be cleared when the FSM gets stuck.
// so we disable them when these two interrupt occurs and re-enable them here.
i2c_hal_disable_intr_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_hal_clr_intsts_mask(&(i2c_context[i2c_num].hal), I2C_LL_INTR_MASK);
i2c_ll_disable_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
i2c_ll_clear_intr_mask(i2c_context[i2c_num].hal.dev, I2C_LL_INTR_MASK);
//start send commands, at most 32 bytes one time, isr handler will process the remaining commands.
i2c_master_cmd_begin_static(i2c_num, NULL);
@@ -1616,7 +1603,7 @@ int i2c_slave_write_buffer(i2c_port_t i2c_num, const uint8_t *data, int size, Ti
cnt = 0;
} else {
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_enable_slave_tx_it(&(i2c_context[i2c_num].hal));
i2c_ll_slave_enable_tx_it(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
cnt = size;
}
@@ -1640,7 +1627,7 @@ int i2c_slave_read_buffer(i2c_port_t i2c_num, uint8_t *data, size_t max_size, Ti
TickType_t ticks_rem = ticks_to_wait;
TickType_t ticks_end = xTaskGetTickCount() + ticks_to_wait;
I2C_ENTER_CRITICAL(&(i2c_context[i2c_num].spinlock));
i2c_hal_enable_slave_rx_it(&(i2c_context[i2c_num].hal));
i2c_ll_slave_enable_rx_it(i2c_context[i2c_num].hal.dev);
I2C_EXIT_CRITICAL(&(i2c_context[i2c_num].spinlock));
while (size_rem && ticks_rem <= ticks_to_wait) {
uint8_t *pdata = (uint8_t *) xRingbufferReceiveUpTo(p_i2c->rx_ring_buf, &size, ticks_to_wait, size_rem);