mirror of
https://github.com/espressif/esp-idf.git
synced 2025-10-04 02:50:58 +02:00
I2C: Refactor i2c hal and ll
This commit is contained in:
@@ -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);
|
||||
|
Reference in New Issue
Block a user