mirror of
https://github.com/espressif/esp-protocols.git
synced 2025-06-30 20:00:57 +02:00
fix(eppp): Fix SIDO host to check/clear interrupts atomically
This commit is contained in:
@ -8,6 +8,7 @@
|
|||||||
#define MAX_SDIO_PAYLOAD 1500
|
#define MAX_SDIO_PAYLOAD 1500
|
||||||
#define SDIO_ALIGN(size) (((size) + 3U) & ~(3U))
|
#define SDIO_ALIGN(size) (((size) + 3U) & ~(3U))
|
||||||
#define SDIO_PAYLOAD SDIO_ALIGN(MAX_SDIO_PAYLOAD)
|
#define SDIO_PAYLOAD SDIO_ALIGN(MAX_SDIO_PAYLOAD)
|
||||||
|
#define PPP_SOF 0x7E
|
||||||
|
|
||||||
// Interrupts and registers
|
// Interrupts and registers
|
||||||
#define SLAVE_INTR 0
|
#define SLAVE_INTR 0
|
||||||
|
@ -22,14 +22,13 @@
|
|||||||
#define TIMEOUT_MAX UINT32_MAX
|
#define TIMEOUT_MAX UINT32_MAX
|
||||||
// Short timeout for sending/receiving ESSL packets
|
// Short timeout for sending/receiving ESSL packets
|
||||||
#define PACKET_TIMEOUT_MS 50
|
#define PACKET_TIMEOUT_MS 50
|
||||||
// Used for padding unaligned packets, to simplify the logic and keep PPP protocol intact when padded
|
|
||||||
#define PPP_SOF 0x7E
|
|
||||||
static const char *TAG = "eppp_sdio_host";
|
static const char *TAG = "eppp_sdio_host";
|
||||||
static SemaphoreHandle_t s_essl_mutex = NULL;
|
static SemaphoreHandle_t s_essl_mutex = NULL;
|
||||||
static essl_handle_t s_essl = NULL;
|
static essl_handle_t s_essl = NULL;
|
||||||
static sdmmc_card_t *s_card = NULL;
|
static sdmmc_card_t *s_card = NULL;
|
||||||
|
|
||||||
static CACHE_ALIGNED_ATTR uint8_t send_buffer[SDIO_PAYLOAD];
|
static DRAM_DMA_ALIGNED_ATTR uint8_t send_buffer[SDIO_PAYLOAD];
|
||||||
static DMA_ATTR uint8_t rcv_buffer[SDIO_PAYLOAD];
|
static DMA_ATTR uint8_t rcv_buffer[SDIO_PAYLOAD];
|
||||||
|
|
||||||
esp_err_t eppp_sdio_host_tx(void *h, void *buffer, size_t len)
|
esp_err_t eppp_sdio_host_tx(void *h, void *buffer, size_t len)
|
||||||
@ -92,6 +91,7 @@ esp_err_t eppp_sdio_host_init(struct eppp_config_sdio_s *eppp_config)
|
|||||||
|
|
||||||
sdmmc_host_t config = SDMMC_HOST_DEFAULT();
|
sdmmc_host_t config = SDMMC_HOST_DEFAULT();
|
||||||
config.flags = SDMMC_HOST_FLAG_4BIT;
|
config.flags = SDMMC_HOST_FLAG_4BIT;
|
||||||
|
config.flags |= SDMMC_HOST_FLAG_ALLOC_ALIGNED_BUF;
|
||||||
config.max_freq_khz = SDMMC_FREQ_HIGHSPEED;
|
config.max_freq_khz = SDMMC_FREQ_HIGHSPEED;
|
||||||
|
|
||||||
s_card = (sdmmc_card_t *)malloc(sizeof(sdmmc_card_t));
|
s_card = (sdmmc_card_t *)malloc(sizeof(sdmmc_card_t));
|
||||||
@ -117,9 +117,8 @@ err:
|
|||||||
static esp_err_t get_intr(uint32_t *out_raw)
|
static esp_err_t get_intr(uint32_t *out_raw)
|
||||||
{
|
{
|
||||||
esp_err_t ret = ESP_OK;
|
esp_err_t ret = ESP_OK;
|
||||||
ESP_GOTO_ON_ERROR(essl_wait_int(s_essl, TIMEOUT_MAX), err, TAG, "essl-wait-int failed");
|
ESP_GOTO_ON_ERROR(essl_get_intr(s_essl, out_raw, NULL, 0), err, TAG, "essl-get-int failed");
|
||||||
ESP_GOTO_ON_ERROR(essl_get_intr(s_essl, out_raw, NULL, TIMEOUT_MAX), err, TAG, "essl-get-int failed");
|
ESP_GOTO_ON_ERROR(essl_clear_intr(s_essl, *out_raw, 0), err, TAG, "essl-clear-int failed");
|
||||||
ESP_GOTO_ON_ERROR(essl_clear_intr(s_essl, *out_raw, TIMEOUT_MAX), err, TAG, "essl-clear-int failed");
|
|
||||||
ESP_LOGD(TAG, "intr: %08"PRIX32, *out_raw);
|
ESP_LOGD(TAG, "intr: %08"PRIX32, *out_raw);
|
||||||
err:
|
err:
|
||||||
return ret;
|
return ret;
|
||||||
@ -128,16 +127,22 @@ err:
|
|||||||
esp_err_t eppp_sdio_host_rx(esp_netif_t *netif)
|
esp_err_t eppp_sdio_host_rx(esp_netif_t *netif)
|
||||||
{
|
{
|
||||||
uint32_t intr;
|
uint32_t intr;
|
||||||
esp_err_t err = get_intr(&intr);
|
esp_err_t err = essl_wait_int(s_essl, TIMEOUT_MAX);
|
||||||
if (err == ESP_ERR_TIMEOUT) {
|
if (err == ESP_ERR_TIMEOUT) {
|
||||||
return ESP_OK;
|
return ESP_OK;
|
||||||
}
|
}
|
||||||
|
xSemaphoreTake(s_essl_mutex, portMAX_DELAY);
|
||||||
|
err = get_intr(&intr);
|
||||||
|
if (err == ESP_ERR_TIMEOUT) {
|
||||||
|
xSemaphoreGive(s_essl_mutex);
|
||||||
|
return ESP_OK;
|
||||||
|
}
|
||||||
if (err != ESP_OK) {
|
if (err != ESP_OK) {
|
||||||
ESP_LOGE(TAG, "failed to check for interrupts %d", err);
|
ESP_LOGE(TAG, "failed to check for interrupts %d", err);
|
||||||
|
xSemaphoreGive(s_essl_mutex);
|
||||||
return ESP_FAIL;
|
return ESP_FAIL;
|
||||||
}
|
}
|
||||||
if (intr & ESSL_SDIO_DEF_ESP32.new_packet_intr_mask) {
|
if (intr & ESSL_SDIO_DEF_ESP32.new_packet_intr_mask) {
|
||||||
xSemaphoreTake(s_essl_mutex, portMAX_DELAY);
|
|
||||||
esp_err_t ret;
|
esp_err_t ret;
|
||||||
do {
|
do {
|
||||||
size_t size_read = SDIO_PAYLOAD;
|
size_t size_read = SDIO_PAYLOAD;
|
||||||
@ -158,8 +163,8 @@ esp_err_t eppp_sdio_host_rx(esp_netif_t *netif)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (ret == ESP_ERR_NOT_FINISHED);
|
} while (ret == ESP_ERR_NOT_FINISHED);
|
||||||
xSemaphoreGive(s_essl_mutex);
|
|
||||||
}
|
}
|
||||||
|
xSemaphoreGive(s_essl_mutex);
|
||||||
return ESP_OK;
|
return ESP_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -12,12 +12,12 @@
|
|||||||
#include "eppp_sdio.h"
|
#include "eppp_sdio.h"
|
||||||
#include "esp_check.h"
|
#include "esp_check.h"
|
||||||
|
|
||||||
#if CONFIG_EPPP_LINK_DEVICE_SDIO_SLAV
|
#if CONFIG_EPPP_LINK_DEVICE_SDIO_SLAVE
|
||||||
#define BUFFER_NUM 4
|
#define BUFFER_NUM 4
|
||||||
|
#define BUFFER_SIZE SDIO_PAYLOAD
|
||||||
static const char *TAG = "eppp_sdio_slave";
|
static const char *TAG = "eppp_sdio_slave";
|
||||||
static WORD_ALIGNED_ATTR uint8_t sdio_slave_rx_buffer[BUFFER_NUM][SDIO_PAYLOAD];
|
static DMA_ATTR uint8_t sdio_slave_rx_buffer[BUFFER_NUM][BUFFER_SIZE];
|
||||||
static WORD_ALIGNED_ATTR uint8_t sdio_slave_tx_buffer[SDIO_PAYLOAD];
|
static DMA_ATTR uint8_t sdio_slave_tx_buffer[SDIO_PAYLOAD];
|
||||||
static int s_slave_request = 0;
|
static int s_slave_request = 0;
|
||||||
|
|
||||||
esp_err_t eppp_sdio_slave_tx(void *h, void *buffer, size_t len)
|
esp_err_t eppp_sdio_slave_tx(void *h, void *buffer, size_t len)
|
||||||
@ -30,7 +30,7 @@ esp_err_t eppp_sdio_slave_tx(void *h, void *buffer, size_t len)
|
|||||||
size_t send_len = SDIO_ALIGN(len);
|
size_t send_len = SDIO_ALIGN(len);
|
||||||
if (send_len > len) {
|
if (send_len > len) {
|
||||||
// pad with SOF's if the size is not 4 bytes aligned
|
// pad with SOF's if the size is not 4 bytes aligned
|
||||||
memset(&sdio_slave_tx_buffer[len], 0x7E, send_len - len);
|
memset(&sdio_slave_tx_buffer[len], PPP_SOF, send_len - len);
|
||||||
}
|
}
|
||||||
|
|
||||||
ESP_LOG_BUFFER_HEXDUMP(TAG, sdio_slave_tx_buffer, send_len, ESP_LOG_VERBOSE);
|
ESP_LOG_BUFFER_HEXDUMP(TAG, sdio_slave_tx_buffer, send_len, ESP_LOG_VERBOSE);
|
||||||
@ -92,6 +92,7 @@ again:
|
|||||||
goto again;
|
goto again;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
ESP_LOG_BUFFER_HEXDUMP(TAG, ptr, length, ESP_LOG_VERBOSE);
|
||||||
return ESP_OK;
|
return ESP_OK;
|
||||||
}
|
}
|
||||||
ESP_LOGE(TAG, "Error when receiving packet %d", ret);
|
ESP_LOGE(TAG, "Error when receiving packet %d", ret);
|
||||||
@ -113,10 +114,8 @@ esp_err_t eppp_sdio_slave_init(void)
|
|||||||
sdio_slave_config_t config = {
|
sdio_slave_config_t config = {
|
||||||
.sending_mode = SDIO_SLAVE_SEND_PACKET,
|
.sending_mode = SDIO_SLAVE_SEND_PACKET,
|
||||||
.send_queue_size = BUFFER_NUM,
|
.send_queue_size = BUFFER_NUM,
|
||||||
.recv_buffer_size = SDIO_PAYLOAD,
|
.recv_buffer_size = BUFFER_SIZE,
|
||||||
.event_cb = event_cb,
|
.event_cb = event_cb,
|
||||||
.flags = SDIO_SLAVE_FLAG_HIGH_SPEED,
|
|
||||||
.timing = SDIO_SLAVE_TIMING_NSEND_PSAMPLE,
|
|
||||||
};
|
};
|
||||||
esp_err_t ret = sdio_slave_initialize(&config);
|
esp_err_t ret = sdio_slave_initialize(&config);
|
||||||
if (ret != ESP_OK) {
|
if (ret != ESP_OK) {
|
||||||
|
Reference in New Issue
Block a user