Merge branch 'feature/esp32c3_drivers' into 'master'

driver: Add esp32c3

Closes IDF-2363

See merge request espressif/esp-idf!11650
This commit is contained in:
Angus Gratton 2020-12-23 08:43:31 +08:00
commit 705d797b41
86 changed files with 4279 additions and 779 deletions

View File

@ -1,9 +1,6 @@
idf_build_get_property(target IDF_TARGET)
set(srcs
"adc_common.c"
"dac_common.c"
"dedic_gpio.c"
"gpio.c"
"i2c.c"
"i2s.c"
@ -22,44 +19,62 @@ set(srcs
"spi_slave.c"
"spi_bus_lock.c"
"timer.c"
"touch_sensor_common.c"
"twai.c"
"uart.c")
set(includes "include" "${target}/include")
if(${target} STREQUAL "esp32")
# SDMMC and MCPWM are in ESP32 only.
list(APPEND srcs "mcpwm.c"
list(APPEND srcs "adc_common.c"
"dac_common.c"
"mcpwm.c"
"sdio_slave.c"
"sdmmc_host.c"
"sdmmc_transaction.c"
"touch_sensor_common.c"
"twai.c"
"esp32/touch_sensor.c"
"esp32/adc.c"
"esp32/dac.c")
list(APPEND includes "esp32/include")
endif()
if(${target} STREQUAL "esp32s2")
list(APPEND srcs "esp32s2/rtc_tempsensor.c"
if(IDF_TARGET STREQUAL "esp32s2")
list(APPEND srcs "adc_common.c"
"dac_common.c"
"dedic_gpio.c"
"spi_slave_hd.c"
"touch_sensor_common.c"
"twai.c"
"esp32s2/rtc_tempsensor.c"
"esp32s2/touch_sensor.c"
"esp32s2/adc.c"
"esp32s2/adc2_init_cal.c"
"spi_slave_hd.c"
"esp32s2/dac.c")
list(APPEND includes "esp32s2/include")
endif()
if(${target} STREQUAL "esp32s3")
list(APPEND srcs "spi_slave_hd.c"
list(APPEND srcs "adc_common.c"
"dac_common.c"
"dedic_gpio.c"
"spi_slave_hd.c"
"touch_sensor_common.c"
"twai.c"
)
endif()
if(IDF_TARGET STREQUAL "esp32c3")
list(APPEND srcs "spi_slave_hd.c"
"esp32c3/adc.c"
"esp32c3/rtc_tempsensor.c")
endif()
idf_component_register(SRCS "${srcs}"
INCLUDE_DIRS ${includes}
PRIV_INCLUDE_DIRS "include/driver"
PRIV_REQUIRES efuse esp_pm esp_timer esp_ipc
REQUIRES esp_ringbuf freertos soc hal)
REQUIRES esp_ringbuf freertos soc hal esp_hw_support)
# (REQUIRES cannot hide soc headers, since many arguments in the driver headers are chip-dependent)
# uses C11 atomic feature

View File

@ -2,7 +2,7 @@
# Component Makefile
#
COMPONENT_SRCDIRS := . $(IDF_TARGET)
COMPONENT_OBJEXCLUDE += spi_slave_hd.o
COMPONENT_OBJEXCLUDE += spi_slave_hd.o dedic_gpio.o
COMPONENT_ADD_INCLUDEDIRS := include $(IDF_TARGET)/include $(IDF_TARGET)/include/driver

View File

@ -28,7 +28,6 @@
#include "driver/periph_ctrl.h"
#include "esp_rom_gpio.h"
#include "freertos/FreeRTOS.h"
#if SOC_DEDICATED_GPIO_SUPPORTED
#include "driver/dedic_gpio.h"
#include "soc/dedic_gpio_periph.h"
#if SOC_DEDIC_GPIO_ALLOW_REG_ACCESS
@ -402,4 +401,3 @@ err:
return ret_code;
}
#endif // SOC_DEDIC_GPIO_HAS_INTERRUPT
#endif // SOC_DEDICATED_GPIO_SUPPORTED

View File

@ -118,7 +118,7 @@ esp_err_t adc_i2s_mode_init(adc_unit_t adc_unit, adc_channel_t channel)
}
adc_gpio_init(adc_unit, channel);
ADC_ENTER_CRITICAL();
adc_hal_digi_init();
adc_hal_init();
adc_hal_digi_controller_config(&dig_cfg);
ADC_EXIT_CRITICAL();
@ -128,7 +128,7 @@ esp_err_t adc_i2s_mode_init(adc_unit_t adc_unit, adc_channel_t channel)
esp_err_t adc_digi_init(void)
{
ADC_ENTER_CRITICAL();
adc_hal_digi_init();
adc_hal_init();
ADC_EXIT_CRITICAL();
return ESP_OK;
}

View File

@ -0,0 +1,758 @@
// Copyright 2016-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include <esp_types.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
#include "sdkconfig.h"
#include "esp_intr_alloc.h"
#include "esp_log.h"
#include "sys/lock.h"
#include "freertos/FreeRTOS.h"
#include "freertos/semphr.h"
#include "freertos/timers.h"
#include "freertos/ringbuf.h"
#include "esp32c3/rom/ets_sys.h"
#include "driver/periph_ctrl.h"
#include "driver/gpio.h"
#include "driver/adc.h"
#include "hal/adc_types.h"
#include "hal/adc_hal.h"
#include "hal/dma_types.h"
#define ADC_CHECK_RET(fun_ret) ({ \
if (fun_ret != ESP_OK) { \
ESP_LOGE(ADC_TAG,"%s:%d\n",__FUNCTION__,__LINE__); \
return ESP_FAIL; \
} \
})
static const char *ADC_TAG = "ADC";
#define ADC_CHECK(a, str, ret_val) ({ \
if (!(a)) { \
ESP_LOGE(ADC_TAG,"%s:%d (%s):%s", __FILE__, __LINE__, __FUNCTION__, str); \
return (ret_val); \
} \
})
#define ADC_GET_IO_NUM(periph, channel) (adc_channel_io_map[periph][channel])
#define ADC_CHANNEL_CHECK(periph, channel) ADC_CHECK(channel < SOC_ADC_CHANNEL_NUM(periph), "ADC"#periph" channel error", ESP_ERR_INVALID_ARG)
extern portMUX_TYPE rtc_spinlock; //TODO: Will be placed in the appropriate position after the rtc module is finished.
#define ADC_ENTER_CRITICAL() portENTER_CRITICAL(&rtc_spinlock)
#define ADC_EXIT_CRITICAL() portEXIT_CRITICAL(&rtc_spinlock)
/*---------------------------------------------------------------
Digital Controller Context
---------------------------------------------------------------*/
/**
* 1. adc_digi_mutex: this mutex lock is used for ADC digital controller. On ESP32-C3, the ADC single read APIs (unit1 & unit2)
* and ADC DMA continuous read APIs share the ``apb_saradc_struct.h`` regs.
*
* 2. sar_adc_mutex: this mutex lock is used for SARADC2 module. On ESP32C-C3, the ADC single read APIs (unit2), ADC DMA
* continuous read APIs and WIFI share the SARADC2 analog IP.
*
* Sequence:
* Acquire: 1. sar_adc_mutex; 2. adc_digi_mutex;
* Release: 1. adc_digi_mutex; 2. sar_adc_mutex;
*/
static _lock_t adc_digi_mutex;
#define ADC_DIGI_LOCK_ACQUIRE() _lock_acquire(&adc_digi_mutex)
#define ADC_DIGI_LOCK_RELEASE() _lock_release(&adc_digi_mutex)
static _lock_t sar_adc2_mutex;
#define SAC_ADC2_LOCK_ACQUIRE() _lock_acquire(&sar_adc2_mutex)
#define SAC_ADC2_LOCK_RELEASE() _lock_release(&sar_adc2_mutex)
#define INTERNAL_BUF_NUM 5
#define IN_SUC_EOF_BIT GDMA_LL_EVENT_RX_SUC_EOF
typedef struct adc_digi_context_t {
intr_handle_t dma_intr_hdl; //MD interrupt handle
uint32_t bytes_between_intr; //bytes between in suc eof intr
uint8_t *rx_dma_buf; //dma buffer
adc_dma_hal_context_t hal_dma; //dma context (hal)
adc_dma_hal_config_t hal_dma_config; //dma config (hal)
RingbufHandle_t ringbuf_hdl; //RX ringbuffer handler
bool ringbuf_overflow_flag; //1: ringbuffer overflow
bool driver_start_flag; //1: driver is started; 0: driver is stoped
bool use_adc2; //1: ADC unit2 will be used; 0: ADC unit2 won't be used. This determines whether to acquire sar_adc2_mutex lock or not.
adc_digi_config_t digi_controller_config; //Digital Controller Configuration
} adc_digi_context_t;
static const char* ADC_DMA_TAG = "ADC_DMA:";
static adc_digi_context_t *s_adc_digi_ctx = NULL;
/*---------------------------------------------------------------
ADC Continuous Read Mode (via DMA)
---------------------------------------------------------------*/
static void adc_dma_intr(void* arg);
static int8_t adc_digi_get_io_num(uint8_t adc_unit, uint8_t adc_channel)
{
return adc_channel_io_map[adc_unit][adc_channel];
}
static esp_err_t adc_digi_gpio_init(adc_unit_t adc_unit, uint16_t channel_mask)
{
esp_err_t ret = ESP_OK;
uint64_t gpio_mask = 0;
uint32_t n = 0;
int8_t io = 0;
while (channel_mask) {
if (channel_mask & 0x1) {
io = adc_digi_get_io_num(adc_unit, n);
if (io < 0) {
return ESP_ERR_INVALID_ARG;
}
gpio_mask |= BIT64(io);
}
channel_mask = channel_mask >> 1;
n++;
}
gpio_config_t cfg = {
.pin_bit_mask = gpio_mask,
.mode = GPIO_MODE_DISABLE,
};
ret = gpio_config(&cfg);
return ret;
}
esp_err_t adc_digi_initialize(const adc_digi_init_config_t *init_config)
{
esp_err_t ret = ESP_OK;
s_adc_digi_ctx = calloc(1, sizeof(adc_digi_context_t));
if (s_adc_digi_ctx == NULL) {
ret = ESP_ERR_NO_MEM;
goto cleanup;
}
ret = esp_intr_alloc(SOC_GDMA_ADC_INTR_SOURCE, 0, adc_dma_intr, (void *)s_adc_digi_ctx, &s_adc_digi_ctx->dma_intr_hdl);
if (ret != ESP_OK) {
goto cleanup;
}
//ringbuffer
s_adc_digi_ctx->ringbuf_hdl = xRingbufferCreate(init_config->max_store_buf_size, RINGBUF_TYPE_BYTEBUF);
if (!s_adc_digi_ctx->ringbuf_hdl) {
ret = ESP_ERR_NO_MEM;
goto cleanup;
}
//malloc internal buffer
s_adc_digi_ctx->bytes_between_intr = init_config->conv_num_each_intr;
s_adc_digi_ctx->rx_dma_buf = heap_caps_calloc(1, s_adc_digi_ctx->bytes_between_intr * INTERNAL_BUF_NUM, MALLOC_CAP_INTERNAL);
if (!s_adc_digi_ctx->rx_dma_buf) {
ret = ESP_ERR_NO_MEM;
goto cleanup;
}
//malloc dma descriptor
s_adc_digi_ctx->hal_dma_config.rx_desc = heap_caps_calloc(1, (sizeof(dma_descriptor_t)) * INTERNAL_BUF_NUM, MALLOC_CAP_DMA);
if (!s_adc_digi_ctx->hal_dma_config.rx_desc) {
ret = ESP_ERR_NO_MEM;
goto cleanup;
}
s_adc_digi_ctx->hal_dma_config.desc_max_num = INTERNAL_BUF_NUM;
s_adc_digi_ctx->hal_dma_config.dma_chan = init_config->dma_chan;
//malloc pattern table
s_adc_digi_ctx->digi_controller_config.adc_pattern = calloc(1, SOC_ADC_PATT_LEN_MAX * sizeof(adc_digi_pattern_table_t));
if (!s_adc_digi_ctx->digi_controller_config.adc_pattern) {
ret = ESP_ERR_NO_MEM;
goto cleanup;
}
if (init_config->adc1_chan_mask) {
ret = adc_digi_gpio_init(ADC_NUM_1, init_config->adc1_chan_mask);
if (ret != ESP_OK) {
goto cleanup;
}
}
if (init_config->adc2_chan_mask) {
ret = adc_digi_gpio_init(ADC_NUM_2, init_config->adc2_chan_mask);
if (ret != ESP_OK) {
goto cleanup;
}
}
periph_module_enable(PERIPH_SARADC_MODULE);
periph_module_enable(PERIPH_GDMA_MODULE);
return ret;
cleanup:
adc_digi_deinitialize();
return ret;
}
static IRAM_ATTR void adc_dma_intr(void *arg)
{
portBASE_TYPE taskAwoken = 0;
BaseType_t ret;
//clear the in suc eof interrupt
adc_hal_digi_clr_intr(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config, IN_SUC_EOF_BIT);
while (s_adc_digi_ctx->hal_dma_config.cur_desc_ptr->dw0.owner == 0) {
dma_descriptor_t *current_desc = s_adc_digi_ctx->hal_dma_config.cur_desc_ptr;
ret = xRingbufferSendFromISR(s_adc_digi_ctx->ringbuf_hdl, current_desc->buffer, current_desc->dw0.length, &taskAwoken);
if (ret == pdFALSE) {
//ringbuffer overflow
s_adc_digi_ctx->ringbuf_overflow_flag = 1;
}
s_adc_digi_ctx->hal_dma_config.desc_cnt += 1;
//cycle the dma descriptor and buffers
s_adc_digi_ctx->hal_dma_config.cur_desc_ptr = s_adc_digi_ctx->hal_dma_config.cur_desc_ptr->next;
if (!s_adc_digi_ctx->hal_dma_config.cur_desc_ptr) {
break;
}
}
if (!s_adc_digi_ctx->hal_dma_config.cur_desc_ptr) {
assert(s_adc_digi_ctx->hal_dma_config.desc_cnt == s_adc_digi_ctx->hal_dma_config.desc_max_num);
//reset the current descriptor status
s_adc_digi_ctx->hal_dma_config.cur_desc_ptr = s_adc_digi_ctx->hal_dma_config.rx_desc;
s_adc_digi_ctx->hal_dma_config.desc_cnt = 0;
//start next turns of dma operation
adc_hal_digi_rxdma_start(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
}
if(taskAwoken == pdTRUE) {
portYIELD_FROM_ISR();
}
}
esp_err_t adc_digi_start(void)
{
if (s_adc_digi_ctx->driver_start_flag != 0) {
ESP_LOGE(ADC_TAG, "The driver is already started");
return ESP_ERR_INVALID_STATE;
}
//reset flags
s_adc_digi_ctx->ringbuf_overflow_flag = 0;
s_adc_digi_ctx->driver_start_flag = 1;
//When using SARADC2 module, this task needs to be protected from WIFI
if (s_adc_digi_ctx->use_adc2) {
SAC_ADC2_LOCK_ACQUIRE();
}
ADC_DIGI_LOCK_ACQUIRE();
adc_arbiter_t config = ADC_ARBITER_CONFIG_DEFAULT();
adc_hal_init();
adc_hal_arbiter_config(&config);
adc_hal_digi_init(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
adc_hal_digi_controller_config(&s_adc_digi_ctx->digi_controller_config);
//create dma descriptors
adc_hal_digi_dma_multi_descriptor(&s_adc_digi_ctx->hal_dma_config, s_adc_digi_ctx->rx_dma_buf, s_adc_digi_ctx->bytes_between_intr, s_adc_digi_ctx->hal_dma_config.desc_max_num);
adc_hal_digi_set_eof_num(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config, (s_adc_digi_ctx->bytes_between_intr)/4);
//set the current descriptor pointer
s_adc_digi_ctx->hal_dma_config.cur_desc_ptr = s_adc_digi_ctx->hal_dma_config.rx_desc;
s_adc_digi_ctx->hal_dma_config.desc_cnt = 0;
//enable in suc eof intr
adc_hal_digi_ena_intr(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config, IN_SUC_EOF_BIT);
//start DMA
adc_hal_digi_rxdma_start(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
//start ADC
adc_hal_digi_start(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
return ESP_OK;
}
esp_err_t adc_digi_stop(void)
{
if (s_adc_digi_ctx->driver_start_flag != 1) {
ESP_LOGE(ADC_TAG, "The driver is already stopped");
return ESP_ERR_INVALID_STATE;
}
s_adc_digi_ctx->driver_start_flag = 0;
//disable the in suc eof intrrupt
adc_hal_digi_dis_intr(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config, IN_SUC_EOF_BIT);
//clear the in suc eof interrupt
adc_hal_digi_clr_intr(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config, IN_SUC_EOF_BIT);
//stop DMA
adc_hal_digi_rxdma_stop(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
//stop ADC
adc_hal_digi_stop(&s_adc_digi_ctx->hal_dma, &s_adc_digi_ctx->hal_dma_config);
adc_hal_digi_deinit();
ADC_DIGI_LOCK_RELEASE();
//When using SARADC2 module, this task needs to be protected from WIFI
if (s_adc_digi_ctx->use_adc2) {
SAC_ADC2_LOCK_RELEASE();
}
return ESP_OK;
}
esp_err_t adc_digi_read_bytes(uint8_t *buf, uint32_t length_max, uint32_t *out_length, uint32_t timeout_ms)
{
TickType_t ticks_to_wait;
esp_err_t ret = ESP_OK;
uint8_t *data = NULL;
size_t size = 0;
ticks_to_wait = timeout_ms / portTICK_RATE_MS;
if (timeout_ms == ADC_MAX_DELAY) {
ticks_to_wait = portMAX_DELAY;
}
data = xRingbufferReceiveUpTo(s_adc_digi_ctx->ringbuf_hdl, &size, ticks_to_wait, length_max);
if (!data) {
ESP_LOGW(ADC_DMA_TAG, "No data, increase timeout or reduce conv_num_each_intr");
ret = ESP_ERR_TIMEOUT;
*out_length = 0;
return ret;
}
memcpy(buf, data, size);
vRingbufferReturnItem(s_adc_digi_ctx->ringbuf_hdl, data);
assert((size % 4) == 0);
*out_length = size;
if (s_adc_digi_ctx->ringbuf_overflow_flag) {
ret = ESP_ERR_INVALID_STATE;
}
return ret;
}
esp_err_t adc_digi_deinitialize(void)
{
if (!s_adc_digi_ctx) {
return ESP_ERR_INVALID_STATE;
}
if (s_adc_digi_ctx->driver_start_flag != 0) {
ESP_LOGE(ADC_TAG, "The driver is not stopped");
return ESP_ERR_INVALID_STATE;
}
if (s_adc_digi_ctx->dma_intr_hdl) {
esp_intr_free(s_adc_digi_ctx->dma_intr_hdl);
}
if(s_adc_digi_ctx->ringbuf_hdl) {
vRingbufferDelete(s_adc_digi_ctx->ringbuf_hdl);
s_adc_digi_ctx->ringbuf_hdl = NULL;
}
free(s_adc_digi_ctx->hal_dma_config.rx_desc);
free(s_adc_digi_ctx->digi_controller_config.adc_pattern);
free(s_adc_digi_ctx);
s_adc_digi_ctx = NULL;
periph_module_disable(PERIPH_SARADC_MODULE);
periph_module_disable(PERIPH_GDMA_MODULE);
return ESP_OK;
}
/*---------------------------------------------------------------
ADC Single Read Mode
---------------------------------------------------------------*/
static adc_atten_t s_atten1_single[ADC1_CHANNEL_MAX]; //Array saving attenuate of each channel of ADC1, used by single read API
static adc_atten_t s_atten2_single[ADC2_CHANNEL_MAX]; //Array saving attenuate of each channel of ADC2, used by single read API
esp_err_t adc1_config_width(adc_bits_width_t width_bit)
{
//On ESP32C3, the data width is always 13-bits.
if (width_bit != ADC_WIDTH_BIT_13) {
return ESP_ERR_INVALID_ARG;
}
return ESP_OK;
}
esp_err_t adc1_config_channel_atten(adc1_channel_t channel, adc_atten_t atten)
{
ADC_CHANNEL_CHECK(ADC_NUM_1, channel);
ADC_CHECK(atten < ADC_ATTEN_MAX, "ADC Atten Err", ESP_ERR_INVALID_ARG);
esp_err_t ret = ESP_OK;
s_atten1_single[channel] = atten;
ret = adc_digi_gpio_init(ADC_NUM_1, BIT(channel));
return ret;
}
int adc1_get_raw(adc1_channel_t channel)
{
int result = 0;
adc_digi_config_t dig_cfg = {
.conv_limit_en = 0,
.conv_limit_num = 250,
.interval = 40,
.dig_clk.use_apll = 0,
.dig_clk.div_num = 1,
.dig_clk.div_a = 0,
.dig_clk.div_b = 1,
};
ADC_DIGI_LOCK_ACQUIRE();
adc_hal_digi_controller_config(&dig_cfg);
adc_hal_intr_clear(ADC_EVENT_ADC1_DONE);
adc_hal_onetime_channel(ADC_NUM_1, channel);
adc_hal_set_onetime_atten(s_atten1_single[channel]);
adc_hal_adc1_onetime_sample_enable(true);
//Trigger single read.
adc_hal_onetime_start(&dig_cfg);
while (!adc_hal_intr_get_raw(ADC_EVENT_ADC1_DONE));
adc_hal_intr_clear(ADC_EVENT_ADC1_DONE);
adc_hal_adc1_onetime_sample_enable(false);
result = adc_hal_adc1_read();
adc_hal_digi_deinit();
ADC_DIGI_LOCK_RELEASE();
return result;
}
esp_err_t adc2_config_channel_atten(adc2_channel_t channel, adc_atten_t atten)
{
ADC_CHANNEL_CHECK(ADC_NUM_2, channel);
ADC_CHECK(atten <= ADC_ATTEN_11db, "ADC2 Atten Err", ESP_ERR_INVALID_ARG);
esp_err_t ret = ESP_OK;
s_atten2_single[channel] = atten;
ret = adc_digi_gpio_init(ADC_NUM_2, BIT(channel));
return ret;
}
esp_err_t adc2_get_raw(adc2_channel_t channel, adc_bits_width_t width_bit, int *raw_out)
{
//On ESP32C3, the data width is always 13-bits.
if (width_bit != ADC_WIDTH_BIT_13) {
return ESP_ERR_INVALID_ARG;
}
adc_digi_config_t dig_cfg = {
.conv_limit_en = 0,
.conv_limit_num = 250,
.interval = 40,
.dig_clk.use_apll = 0,
.dig_clk.div_num = 1,
.dig_clk.div_a = 0,
.dig_clk.div_b = 1,
};
SAC_ADC2_LOCK_ACQUIRE();
ADC_DIGI_LOCK_ACQUIRE();
adc_hal_digi_controller_config(&dig_cfg);
adc_hal_intr_clear(ADC_EVENT_ADC2_DONE);
adc_hal_onetime_channel(ADC_NUM_2, channel);
adc_hal_set_onetime_atten(s_atten2_single[channel]);
adc_hal_adc2_onetime_sample_enable(true);
//Trigger single read.
adc_hal_onetime_start(&dig_cfg);
while (!adc_hal_intr_get_raw(ADC_EVENT_ADC2_DONE));
adc_hal_intr_clear(ADC_EVENT_ADC2_DONE);
adc_hal_adc2_onetime_sample_enable(false);
*raw_out = adc_hal_adc2_read();
adc_hal_digi_deinit();
ADC_DIGI_LOCK_RELEASE();
SAC_ADC2_LOCK_RELEASE();
return ESP_OK;
}
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
esp_err_t adc_digi_controller_config(const adc_digi_config_t *config)
{
if (!s_adc_digi_ctx) {
return ESP_ERR_INVALID_STATE;
}
s_adc_digi_ctx->digi_controller_config.conv_limit_en = config->conv_limit_en;
s_adc_digi_ctx->digi_controller_config.conv_limit_num = config->conv_limit_num;
s_adc_digi_ctx->digi_controller_config.adc_pattern_len = config->adc_pattern_len;
s_adc_digi_ctx->digi_controller_config.interval = config->interval;
s_adc_digi_ctx->digi_controller_config.dig_clk = config-> dig_clk;
s_adc_digi_ctx->digi_controller_config.dma_eof_num = config->dma_eof_num;
memcpy(s_adc_digi_ctx->digi_controller_config.adc_pattern, config->adc_pattern, config->adc_pattern_len * sizeof(adc_digi_pattern_table_t));
//See whether ADC2 will be used or not. If yes, the ``sar_adc2_mutex`` should be acquired in the continuous read driver
s_adc_digi_ctx->use_adc2 = 0;
for (int i = 0; i < config->adc_pattern_len; i++) {
if (config->adc_pattern->unit == ADC_NUM_2) {
s_adc_digi_ctx->use_adc2 = 1;
}
}
return ESP_OK;
}
esp_err_t adc_arbiter_config(adc_unit_t adc_unit, adc_arbiter_t *config)
{
if (adc_unit & ADC_UNIT_1) {
return ESP_ERR_NOT_SUPPORTED;
}
ADC_ENTER_CRITICAL();
adc_hal_arbiter_config(config);
ADC_EXIT_CRITICAL();
return ESP_OK;
}
/**
* @brief Set ADC module controller.
* There are five SAR ADC controllers:
* Two digital controller: Continuous conversion mode (DMA). High performance with multiple channel scan modes;
* Two RTC controller: Single conversion modes (Polling). For low power purpose working during deep sleep;
* the other is dedicated for Power detect (PWDET / PKDET), Only support ADC2.
*
* @note Only ADC2 support arbiter to switch controllers automatically. Access to the ADC is based on the priority of the controller.
* @note For ADC1, Controller access is mutually exclusive.
*
* @param adc_unit ADC unit.
* @param ctrl ADC controller, Refer to `adc_ll_controller_t`.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_set_controller(adc_unit_t adc_unit, adc_ll_controller_t ctrl)
{
adc_arbiter_t config = {0};
adc_arbiter_t cfg = ADC_ARBITER_CONFIG_DEFAULT();
if (adc_unit & ADC_UNIT_1) {
adc_hal_set_controller(ADC_NUM_1, ctrl);
}
if (adc_unit & ADC_UNIT_2) {
adc_hal_set_controller(ADC_NUM_2, ctrl);
switch (ctrl) {
case ADC2_CTRL_FORCE_PWDET:
config.pwdet_pri = 2;
config.mode = ADC_ARB_MODE_SHIELD;
adc_hal_arbiter_config(&config);
adc_hal_set_controller(ADC_NUM_2, ADC2_CTRL_PWDET);
break;
case ADC2_CTRL_FORCE_RTC:
config.rtc_pri = 2;
config.mode = ADC_ARB_MODE_SHIELD;
adc_hal_arbiter_config(&config);
adc_hal_set_controller(ADC_NUM_2, ADC_CTRL_RTC);
break;
case ADC2_CTRL_FORCE_DIG:
config.dig_pri = 2;
config.mode = ADC_ARB_MODE_SHIELD;
adc_hal_arbiter_config(&config);
adc_hal_set_controller(ADC_NUM_2, ADC_CTRL_DIG);
break;
default:
adc_hal_arbiter_config(&cfg);
break;
}
}
return ESP_OK;
}
/**
* @brief Reset FSM of adc digital controller.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_reset(void)
{
ADC_ENTER_CRITICAL();
adc_hal_digi_reset();
adc_hal_digi_clear_pattern_table(ADC_NUM_1);
adc_hal_digi_clear_pattern_table(ADC_NUM_2);
ADC_EXIT_CRITICAL();
return ESP_OK;
}
/*************************************/
/* Digital controller filter setting */
/*************************************/
esp_err_t adc_digi_filter_reset(adc_digi_filter_idx_t idx)
{
abort(); // TODO ESP32-C3 IDF-2528
}
esp_err_t adc_digi_filter_set_config(adc_digi_filter_idx_t idx, adc_digi_filter_t *config)
{
abort(); // TODO ESP32-C3 IDF-2528
}
esp_err_t adc_digi_filter_get_config(adc_digi_filter_idx_t idx, adc_digi_filter_t *config)
{
abort(); // TODO ESP32-C3 IDF-2528
}
esp_err_t adc_digi_filter_enable(adc_digi_filter_idx_t idx, bool enable)
{
abort(); // TODO ESP32-C3 IDF-2528
}
/**
* @brief Get the filtered data of adc digital controller filter. For debug.
* The data after each measurement and filtering is updated to the DMA by the digital controller. But it can also be obtained manually through this API.
*
* @param idx Filter index.
* @return Filtered data. if <0, the read data invalid.
*/
int adc_digi_filter_read_data(adc_digi_filter_idx_t idx)
{
abort(); // TODO ESP32-C3 IDF-2528
}
/**************************************/
/* Digital controller monitor setting */
/**************************************/
esp_err_t adc_digi_monitor_set_config(adc_digi_monitor_idx_t idx, adc_digi_monitor_t *config)
{
ADC_ENTER_CRITICAL();
if (idx == ADC_DIGI_MONITOR_IDX0) {
adc_hal_digi_monitor_config(ADC_NUM_1, config);
} else if (idx == ADC_DIGI_MONITOR_IDX1) {
adc_hal_digi_monitor_config(ADC_NUM_2, config);
}
ADC_EXIT_CRITICAL();
return ESP_OK;
}
esp_err_t adc_digi_monitor_enable(adc_digi_monitor_idx_t idx, bool enable)
{
ADC_ENTER_CRITICAL();
if (idx == ADC_DIGI_MONITOR_IDX0) {
adc_hal_digi_monitor_enable(ADC_NUM_1, enable);
} else if (idx == ADC_DIGI_MONITOR_IDX1) {
adc_hal_digi_monitor_enable(ADC_NUM_2, enable);
}
ADC_EXIT_CRITICAL();
return ESP_OK;
}
/**************************************/
/* Digital controller intr setting */
/**************************************/
esp_err_t adc_digi_intr_enable(adc_unit_t adc_unit, adc_digi_intr_t intr_mask)
{
ADC_ENTER_CRITICAL();
if (adc_unit & ADC_UNIT_1) {
adc_hal_digi_intr_enable(ADC_NUM_1, intr_mask);
}
if (adc_unit & ADC_UNIT_2) {
adc_hal_digi_intr_enable(ADC_NUM_2, intr_mask);
}
ADC_EXIT_CRITICAL();
return ESP_OK;
}
esp_err_t adc_digi_intr_disable(adc_unit_t adc_unit, adc_digi_intr_t intr_mask)
{
ADC_ENTER_CRITICAL();
if (adc_unit & ADC_UNIT_1) {
adc_hal_digi_intr_disable(ADC_NUM_1, intr_mask);
}
if (adc_unit & ADC_UNIT_2) {
adc_hal_digi_intr_disable(ADC_NUM_2, intr_mask);
}
ADC_EXIT_CRITICAL();
return ESP_OK;
}
esp_err_t adc_digi_intr_clear(adc_unit_t adc_unit, adc_digi_intr_t intr_mask)
{
ADC_ENTER_CRITICAL();
if (adc_unit & ADC_UNIT_1) {
adc_hal_digi_intr_clear(ADC_NUM_1, intr_mask);
}
if (adc_unit & ADC_UNIT_2) {
adc_hal_digi_intr_clear(ADC_NUM_2, intr_mask);
}
ADC_EXIT_CRITICAL();
return ESP_OK;
}
uint32_t adc_digi_intr_get_status(adc_unit_t adc_unit)
{
uint32_t ret = 0;
ADC_ENTER_CRITICAL();
if (adc_unit & ADC_UNIT_1) {
ret = adc_hal_digi_get_intr_status(ADC_NUM_1);
}
if (adc_unit & ADC_UNIT_2) {
ret = adc_hal_digi_get_intr_status(ADC_NUM_2);
}
ADC_EXIT_CRITICAL();
return ret;
}
static bool s_isr_registered = 0;
static intr_handle_t s_adc_isr_handle = NULL;
esp_err_t adc_digi_isr_register(void (*fn)(void *), void *arg, int intr_alloc_flags)
{
ADC_CHECK((fn != NULL), "Parameter error", ESP_ERR_INVALID_ARG);
ADC_CHECK(s_isr_registered == 0, "ADC ISR have installed, can not install again", ESP_FAIL);
esp_err_t ret = esp_intr_alloc(ETS_APB_ADC_INTR_SOURCE, intr_alloc_flags, fn, arg, &s_adc_isr_handle);
if (ret == ESP_OK) {
s_isr_registered = 1;
}
return ret;
}
esp_err_t adc_digi_isr_deregister(void)
{
esp_err_t ret = ESP_FAIL;
if (s_isr_registered) {
ret = esp_intr_free(s_adc_isr_handle);
if (ret == ESP_OK) {
s_isr_registered = 0;
}
}
return ret;
}
/*---------------------------------------------------------------
RTC controller setting
---------------------------------------------------------------*/

View File

@ -0,0 +1,191 @@
// Copyright 2019-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
#include "driver/adc_common.h"
#ifdef __cplusplus
extern "C" {
#endif
/*---------------------------------------------------------------
Common setting
---------------------------------------------------------------*/
/**
* @brief Config ADC module arbiter.
* The arbiter is to improve the use efficiency of ADC2. After the control right is robbed by the high priority,
* the low priority controller will read the invalid ADC2 data, and the validity of the data can be judged by the flag bit in the data.
*
* @note Only ADC2 support arbiter.
* @note Default priority: Wi-Fi > RTC > Digital;
* @note In normal use, there is no need to call this interface to config arbiter.
*
* @param adc_unit ADC unit.
* @param config Refer to `adc_arbiter_t`.
*
* @return
* - ESP_OK Success
* - ESP_ERR_NOT_SUPPORTED ADC unit not support arbiter.
*/
esp_err_t adc_arbiter_config(adc_unit_t adc_unit, adc_arbiter_t *config);
/*************************************/
/* Digital controller filter setting */
/*************************************/
/**
* @brief Reset adc digital controller filter.
*
* @param idx Filter index.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_filter_reset(adc_digi_filter_idx_t idx);
/**
* @brief Set adc digital controller filter configuration.
*
* @param idx Filter index.
* @param config See ``adc_digi_filter_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_filter_set_config(adc_digi_filter_idx_t idx, adc_digi_filter_t *config);
/**
* @brief Get adc digital controller filter configuration.
*
* @param idx Filter index.
* @param config See ``adc_digi_filter_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_filter_get_config(adc_digi_filter_idx_t idx, adc_digi_filter_t *config);
/**
* @brief Enable/disable adc digital controller filter.
* Filtering the ADC data to obtain smooth data at higher sampling rates.
*
* @param idx Filter index.
* @param enable Enable/Disable filter.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_filter_enable(adc_digi_filter_idx_t idx, bool enable);
/**************************************/
/* Digital controller monitor setting */
/**************************************/
/**
* @brief Config monitor of adc digital controller.
*
* @param idx Monitor index.
* @param config See ``adc_digi_monitor_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_monitor_set_config(adc_digi_monitor_idx_t idx, adc_digi_monitor_t *config);
/**
* @brief Enable/disable monitor of adc digital controller.
*
* @param idx Monitor index.
* @param enable True or false enable monitor.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_monitor_enable(adc_digi_monitor_idx_t idx, bool enable);
/**************************************/
/* Digital controller intr setting */
/**************************************/
/**
* @brief Enable interrupt of adc digital controller by bitmask.
*
* @param adc_unit ADC unit.
* @param intr_mask Interrupt bitmask. See ``adc_digi_intr_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_intr_enable(adc_unit_t adc_unit, adc_digi_intr_t intr_mask);
/**
* @brief Disable interrupt of adc digital controller by bitmask.
*
* @param adc_unit ADC unit.
* @param intr_mask Interrupt bitmask. See ``adc_digi_intr_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_intr_disable(adc_unit_t adc_unit, adc_digi_intr_t intr_mask);
/**
* @brief Clear interrupt of adc digital controller by bitmask.
*
* @param adc_unit ADC unit.
* @param intr_mask Interrupt bitmask. See ``adc_digi_intr_t``.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_digi_intr_clear(adc_unit_t adc_unit, adc_digi_intr_t intr_mask);
/**
* @brief Get interrupt status mask of adc digital controller.
*
* @param adc_unit ADC unit.
* @return
* - intr Interrupt bitmask, See ``adc_digi_intr_t``.
*/
uint32_t adc_digi_intr_get_status(adc_unit_t adc_unit);
/**
* @brief Register ADC interrupt handler, the handler is an ISR.
* The handler will be attached to the same CPU core that this function is running on.
*
* @param fn Interrupt handler function.
* @param arg Parameter for handler function
* @param intr_alloc_flags Flags used to allocate the interrupt. One or multiple (ORred)
* ESP_INTR_FLAG_* values. See esp_intr_alloc.h for more info.
*
* @return
* - ESP_OK Success
* - ESP_ERR_NOT_FOUND Can not find the interrupt that matches the flags.
* - ESP_ERR_INVALID_ARG Function pointer error.
*/
esp_err_t adc_digi_isr_register(void (*fn)(void *), void *arg, int intr_alloc_flags);
/**
* @brief Deregister ADC interrupt handler, the handler is an ISR.
*
* @return
* - ESP_OK Success
* - ESP_ERR_INVALID_ARG hander error.
* - ESP_FAIL ISR not be registered.
*/
esp_err_t adc_digi_isr_deregister(void);
#ifdef __cplusplus
}
#endif

View File

@ -71,7 +71,7 @@ esp_err_t adc_digi_init(void)
{
adc_arbiter_t config = ADC_ARBITER_CONFIG_DEFAULT();
ADC_ENTER_CRITICAL();
adc_hal_digi_init();
adc_hal_init();
adc_hal_arbiter_config(&config);
ADC_EXIT_CRITICAL();
return ESP_OK;
@ -148,12 +148,12 @@ esp_err_t adc_arbiter_config(adc_unit_t adc_unit, adc_arbiter_t *config)
* @note For ADC1, Controller access is mutually exclusive.
*
* @param adc_unit ADC unit.
* @param ctrl ADC controller, Refer to `adc_controller_t`.
* @param ctrl ADC controller, Refer to `adc_ll_controller_t`.
*
* @return
* - ESP_OK Success
*/
esp_err_t adc_set_controller(adc_unit_t adc_unit, adc_controller_t ctrl)
esp_err_t adc_set_controller(adc_unit_t adc_unit, adc_ll_controller_t ctrl)
{
adc_arbiter_t config = {0};
adc_arbiter_t cfg = ADC_ARBITER_CONFIG_DEFAULT();

View File

@ -239,39 +239,6 @@ esp_err_t adc_digi_isr_register(void (*fn)(void *), void *arg, int intr_alloc_fl
*/
esp_err_t adc_digi_isr_deregister(void);
/*---------------------------------------------------------------
RTC controller setting
---------------------------------------------------------------*/
/*---------------------------------------------------------------
Deprecated API
---------------------------------------------------------------*/
/**
* @brief Set I2S data source
*
* @param src I2S DMA data source, I2S DMA can get data from digital signals or from ADC.
*
* @deprecated The ESP32S2 don't use I2S DMA. Call ``adc_digi_controller_config`` instead.
*
* @return
* - ESP_OK success
*/
esp_err_t adc_set_i2s_data_source(adc_i2s_source_t src) __attribute__((deprecated));
/**
* @brief Initialize I2S ADC mode
*
* @param adc_unit ADC unit index
* @param channel ADC channel index
*
* @deprecated The ESP32S2 don't use I2S DMA. Call ``adc_digi_controller_config`` instead.
*
* @return
* - ESP_OK success
* - ESP_ERR_INVALID_ARG Parameter error
*/
esp_err_t adc_i2s_mode_init(adc_unit_t adc_unit, adc_channel_t channel) __attribute__((deprecated));
#ifdef __cplusplus
}
#endif

View File

@ -24,25 +24,47 @@
extern "C" {
#endif
#if CONFIG_IDF_TARGET_ESP32
/**** `adc1_channel_t` will be deprecated functions, combine into `adc_channel_t` ********/
typedef enum {
ADC1_CHANNEL_0 = 0, /*!< ADC1 channel 0 is GPIO36 (ESP32), GPIO1 (ESP32-S2) */
ADC1_CHANNEL_1, /*!< ADC1 channel 1 is GPIO37 (ESP32), GPIO2 (ESP32-S2) */
ADC1_CHANNEL_2, /*!< ADC1 channel 2 is GPIO38 (ESP32), GPIO3 (ESP32-S2) */
ADC1_CHANNEL_3, /*!< ADC1 channel 3 is GPIO39 (ESP32), GPIO4 (ESP32-S2) */
ADC1_CHANNEL_4, /*!< ADC1 channel 4 is GPIO32 (ESP32), GPIO5 (ESP32-S2) */
ADC1_CHANNEL_5, /*!< ADC1 channel 5 is GPIO33 (ESP32), GPIO6 (ESP32-S2) */
ADC1_CHANNEL_6, /*!< ADC1 channel 6 is GPIO34 (ESP32), GPIO7 (ESP32-S2) */
ADC1_CHANNEL_7, /*!< ADC1 channel 7 is GPIO35 (ESP32), GPIO8 (ESP32-S2) */
#if CONFIG_IDF_TARGET_ESP32
ADC1_CHANNEL_0 = 0, /*!< ADC1 channel 0 is GPIO36 */
ADC1_CHANNEL_1, /*!< ADC1 channel 1 is GPIO37 */
ADC1_CHANNEL_2, /*!< ADC1 channel 2 is GPIO38 */
ADC1_CHANNEL_3, /*!< ADC1 channel 3 is GPIO39 */
ADC1_CHANNEL_4, /*!< ADC1 channel 4 is GPIO32 */
ADC1_CHANNEL_5, /*!< ADC1 channel 5 is GPIO33 */
ADC1_CHANNEL_6, /*!< ADC1 channel 6 is GPIO34 */
ADC1_CHANNEL_7, /*!< ADC1 channel 7 is GPIO35 */
ADC1_CHANNEL_MAX,
#elif CONFIG_IDF_TARGET_ESP32S2
ADC1_CHANNEL_8, /*!< ADC1 channel 6 is GPIO9 (ESP32-S2)*/
ADC1_CHANNEL_9, /*!< ADC1 channel 7 is GPIO10 (ESP32-S2) */
ADC1_CHANNEL_MAX,
#endif
} adc1_channel_t;
#elif CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3 // TODO ESP32-S3 channels are wrong IDF-1776
/**** `adc1_channel_t` will be deprecated functions, combine into `adc_channel_t` ********/
typedef enum {
ADC1_CHANNEL_0 = 0, /*!< ADC1 channel 0 is GPIO1 */
ADC1_CHANNEL_1, /*!< ADC1 channel 1 is GPIO2 */
ADC1_CHANNEL_2, /*!< ADC1 channel 2 is GPIO3 */
ADC1_CHANNEL_3, /*!< ADC1 channel 3 is GPIO4 */
ADC1_CHANNEL_4, /*!< ADC1 channel 4 is GPIO5 */
ADC1_CHANNEL_5, /*!< ADC1 channel 5 is GPIO6 */
ADC1_CHANNEL_6, /*!< ADC1 channel 6 is GPIO7 */
ADC1_CHANNEL_7, /*!< ADC1 channel 7 is GPIO8 */
ADC1_CHANNEL_8, /*!< ADC1 channel 6 is GPIO9 */
ADC1_CHANNEL_9, /*!< ADC1 channel 7 is GPIO10 */
ADC1_CHANNEL_MAX,
} adc1_channel_t;
#elif CONFIG_IDF_TARGET_ESP32C3
/**** `adc1_channel_t` will be deprecated functions, combine into `adc_channel_t` ********/
typedef enum {
ADC1_CHANNEL_0 = 0, /*!< ADC1 channel 0 is GPIO0 */
ADC1_CHANNEL_1, /*!< ADC1 channel 1 is GPIO1 */
ADC1_CHANNEL_2, /*!< ADC1 channel 2 is GPIO2 */
ADC1_CHANNEL_3, /*!< ADC1 channel 3 is GPIO3 */
ADC1_CHANNEL_4, /*!< ADC1 channel 4 is GPIO34 */
ADC1_CHANNEL_MAX,
} adc1_channel_t;
#endif // CONFIG_IDF_TARGET_*
#if CONFIG_IDF_TARGET_ESP32 || CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3 // TODO ESP32-S3 channels are wrong IDF-1776
/**** `adc2_channel_t` will be deprecated functions, combine into `adc_channel_t` ********/
typedef enum {
ADC2_CHANNEL_0 = 0, /*!< ADC2 channel 0 is GPIO4 (ESP32), GPIO11 (ESP32-S2) */
@ -57,6 +79,14 @@ typedef enum {
ADC2_CHANNEL_9, /*!< ADC2 channel 9 is GPIO26 (ESP32), GPIO20 (ESP32-S2) */
ADC2_CHANNEL_MAX,
} adc2_channel_t;
#elif CONFIG_IDF_TARGET_ESP32C3
/**** `adc2_channel_t` will be deprecated functions, combine into `adc_channel_t` ********/
typedef enum {
ADC2_CHANNEL_0 = 0, /*!< ADC2 channel 0 is GPIO5 */
ADC2_CHANNEL_MAX,
} adc2_channel_t;
#endif
/**
* @brief ADC rtc controller attenuation option.
@ -73,6 +103,13 @@ typedef enum {
#define ADC_WIDTH_11Bit ADC_WIDTH_BIT_11
#define ADC_WIDTH_12Bit ADC_WIDTH_BIT_12
#if CONFIG_IDF_TARGET_ESP32C3
/**
* @brief Digital ADC DMA read max timeout value, it may make the ``adc_digi_read_bytes`` block forever if the OS supports
*/
#define ADC_MAX_DELAY UINT32_MAX
#endif
/**
* @brief ADC digital controller encode option.
*
@ -84,6 +121,20 @@ typedef enum {
ADC_ENCODE_MAX,
} adc_i2s_encode_t;
#if CONFIG_IDF_TARGET_ESP32C3
//This feature is currently supported on ESP32C3, will be supported on other chips soon
/**
* @brief Digital ADC DMA configuration
*/
typedef struct adc_digi_init_config_s {
uint32_t max_store_buf_size; ///< Max length of the converted data that driver can store before they are processed. When this length is reached, driver will dump out all the old data and start to store them again.
uint32_t conv_num_each_intr; ///< Bytes of data that can be converted in 1 interrupt.
uint32_t dma_chan; ///< DMA channel.
uint16_t adc1_chan_mask; ///< Channel list of ADC1 to be initialized.
uint16_t adc2_chan_mask; ///< Channel list of ADC2 to be initialized.
} adc_digi_init_config_t;
#endif
/*---------------------------------------------------------------
Common setting
---------------------------------------------------------------*/
@ -256,10 +307,8 @@ esp_err_t adc_set_clk_div(uint8_t clk_div);
/**
* @brief Configure ADC capture width.
*
* @note ESP32-S2 only supports ``ADC_WIDTH_BIT_13``.
*
* @param adc_unit ADC unit index
* @param width_bit Bit capture width for ADC unit. ESP32-S2 only supports ``ADC_WIDTH_BIT_13``.
* @param width_bit Bit capture width for ADC unit.
*
* @return
* - ESP_OK success
@ -346,7 +395,7 @@ esp_err_t adc2_config_channel_atten(adc2_channel_t channel, adc_atten_t atten);
* the low priority controller will read the invalid ADC2 data. Default priority: Wi-Fi > RTC > Digital;
*
* @param channel ADC2 channel to read
* @param width_bit Bit capture width for ADC2. ESP32-S2 only supports ``ADC_WIDTH_BIT_13``.
* @param width_bit Bit capture width for ADC2
* @param raw_out the variable to hold the output data.
*
* @return
@ -392,7 +441,8 @@ esp_err_t adc2_vref_to_gpio(gpio_num_t gpio) __attribute__((deprecated));
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
#if CONFIG_IDF_TARGET_ESP32 || CONFIG_IDF_TARGET_ESP32S2
//These APIs are only supported on ESP32 and ESP32-S2. On ESP32-C3 and later chips, please use ``adc_digi_initialize`` and ``adc_digi_deinitialize``
/**
* @brief ADC digital controller initialization.
* @return
@ -406,17 +456,81 @@ esp_err_t adc_digi_init(void);
* - ESP_OK Success
*/
esp_err_t adc_digi_deinit(void);
#endif
/**
* @brief Setting the digital controller.
*
* @param config Pointer to digital controller paramter. Refer to `adc_digi_config_t`.
* @param config Pointer to digital controller paramter. Refer to ``adc_digi_config_t``.
*
* @return
* - ESP_OK Success
* - ESP_ERR_INVALID_STATE Driver state is invalid.
* - ESP_OK On success
*/
esp_err_t adc_digi_controller_config(const adc_digi_config_t *config);
#if CONFIG_IDF_TARGET_ESP32C3
//This feature is currently supported on ESP32C3, will be supported on other chips soon
/*---------------------------------------------------------------
DMA setting
---------------------------------------------------------------*/
/**
* @brief Initialize the Digital ADC.
*
* @param init_config Pointer to Digital ADC initilisation config. Refer to ``adc_digi_init_config_t``.
*
* @return
* - ESP_ERR_INVALID_ARG If the combination of arguments is invalid.
* - ESP_ERR_NOT_FOUND No free interrupt found with the specified flags
* - ESP_ERR_NO_MEM If out of memory
* - ESP_OK On success
*/
esp_err_t adc_digi_initialize(const adc_digi_init_config_t *init_config);
/**
* @brief Start the Digital ADC and DMA peripherals. After this, the hardware starts working.
*
* @return
* - ESP_ERR_INVALID_STATE Driver state is invalid.
* - ESP_OK On success
*/
esp_err_t adc_digi_start(void);
/**
* @brief Stop the Digital ADC and DMA peripherals. After this, the hardware stops working.
*
* @return
* - ESP_ERR_INVALID_STATE Driver state is invalid.
* - ESP_OK On success
*/
esp_err_t adc_digi_stop(void);
/**
* @brief Read bytes from Digital ADC through DMA.
*
* @param[out] buf Buffer to read from ADC.
* @param[in] length_max Expected length of data read from the ADC.
* @param[out] out_length Real length of data read from the ADC via this API.
* @param[in] timeout_ms Time to wait for data via this API, in millisecond.
*
* @return
* - ESP_ERR_INVALID_STATE Driver state is invalid. Usually it means the ADC sampling rate is faster than the task processing rate.
* - ESP_ERR_TIMEOUT Operation timed out
* - ESP_OK On success
*/
esp_err_t adc_digi_read_bytes(uint8_t *buf, uint32_t length_max, uint32_t *out_length, uint32_t timeout_ms);
/**
* @brief Deinitialize the Digital ADC.
*
* @return
* - ESP_ERR_INVALID_STATE Driver state is invalid.
* - ESP_OK On success
*/
esp_err_t adc_digi_deinitialize(void);
#endif //#if CONFIG_IDF_TARGET_ESP32C3
#ifdef __cplusplus
}
#endif

View File

@ -22,7 +22,6 @@
/** SPI master clock is divided by 80MHz apb clock. Below defines are example frequencies, and are accurate. Be free to specify a random frequency, it will be rounded to closest frequency (to macros below if above 8MHz).
* 8MHz
*/
#if APB_CLK_FREQ==80*1000*1000
#define SPI_MASTER_FREQ_8M (APB_CLK_FREQ/10)
#define SPI_MASTER_FREQ_9M (APB_CLK_FREQ/9) ///< 8.89MHz
#define SPI_MASTER_FREQ_10M (APB_CLK_FREQ/8) ///< 10MHz
@ -33,14 +32,6 @@
#define SPI_MASTER_FREQ_26M (APB_CLK_FREQ/3) ///< 26.67MHz
#define SPI_MASTER_FREQ_40M (APB_CLK_FREQ/2) ///< 40MHz
#define SPI_MASTER_FREQ_80M (APB_CLK_FREQ/1) ///< 80MHz
#elif APB_CLK_FREQ==40*1000*1000
#define SPI_MASTER_FREQ_7M (APB_CLK_FREQ/6) ///< 13.33MHz
#define SPI_MASTER_FREQ_8M (APB_CLK_FREQ/5) ///< 16MHz
#define SPI_MASTER_FREQ_10M (APB_CLK_FREQ/4) ///< 20MHz
#define SPI_MASTER_FREQ_13M (APB_CLK_FREQ/3) ///< 26.67MHz
#define SPI_MASTER_FREQ_20M (APB_CLK_FREQ/2) ///< 40MHz
#define SPI_MASTER_FREQ_40M (APB_CLK_FREQ/1) ///< 80MHz
#endif
#ifdef __cplusplus
extern "C"
{

View File

@ -19,10 +19,12 @@
#include "soc/gpio_periph.h"
#include "soc/ledc_periph.h"
#include "soc/rtc.h"
#include "soc/soc_caps.h"
#include "hal/ledc_hal.h"
#include "driver/ledc.h"
#include "esp_rom_gpio.h"
#include "esp_rom_sys.h"
#include "soc/clk_ctrl_os.h"
static const char* LEDC_TAG = "ledc";
@ -93,23 +95,13 @@ static IRAM_ATTR void ledc_ls_channel_update(ledc_mode_t speed_mode, ledc_channe
//We know that CLK8M is about 8M, but don't know the actual value. So we need to do a calibration.
static bool ledc_slow_clk_calibrate(void)
{
#ifdef CONFIG_IDF_TARGET_ESP32
//Enable CLK8M for LEDC
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
//Waiting for CLK8M to turn on
esp_rom_delay_us(DELAY_CLK8M_CLK_SWITCH);
uint32_t cal_val = rtc_clk_cal(RTC_CAL_8MD256, SLOW_CLK_CYC_CALIBRATE);
if(cal_val == 0) {
ESP_LOGE(LEDC_TAG, "CLK8M_CLK calibration failed");
return false;
if (periph_rtc_dig_clk8m_enable()) {
s_ledc_slow_clk_8M = periph_rtc_dig_clk8m_get_freq();
ESP_LOGD(LEDC_TAG, "Calibrate CLK8M_CLK : %d Hz", s_ledc_slow_clk_8M);
return true;
}
s_ledc_slow_clk_8M = 1000000ULL * (1 << RTC_CLK_CAL_FRACT) * 256 / cal_val;
ESP_LOGD(LEDC_TAG, "Calibrate CLK8M_CLK : %d Hz", s_ledc_slow_clk_8M);
return true;
#else
ESP_LOGE(LEDC_TAG, "CLK8M source currently only supported on ESP32");
ESP_LOGE(LEDC_TAG, "Calibrate CLK8M_CLK failed");
return false;
#endif
}
static uint32_t ledc_get_src_clk_freq(ledc_clk_cfg_t clk_cfg)
@ -121,7 +113,7 @@ static uint32_t ledc_get_src_clk_freq(ledc_clk_cfg_t clk_cfg)
src_clk_freq = LEDC_REF_CLK_HZ;
} else if (clk_cfg == LEDC_USE_RTC8M_CLK) {
src_clk_freq = s_ledc_slow_clk_8M;
#ifdef CONFIG_IDF_TARGET_ESP32S2
#if SOC_LEDC_SUPPORT_XTAL_CLOCK
} else if (clk_cfg == LEDC_USE_XTAL_CLK) {
src_clk_freq = rtc_clk_xtal_freq_get() * 1000000;
#endif
@ -349,6 +341,9 @@ esp_err_t ledc_timer_config(const ledc_timer_config_t* timer_conf)
if(p_ledc_obj[speed_mode] == NULL) {
p_ledc_obj[speed_mode] = (ledc_obj_t *) heap_caps_calloc(1, sizeof(ledc_obj_t), MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT);
if (p_ledc_obj[speed_mode] == NULL) {
return ESP_ERR_NO_MEM;
}
ledc_hal_init(&(p_ledc_obj[speed_mode]->ledc_hal), speed_mode);
}
@ -380,11 +375,16 @@ esp_err_t ledc_channel_config(const ledc_channel_config_t* ledc_conf)
LEDC_ARG_CHECK(speed_mode < LEDC_SPEED_MODE_MAX, "speed_mode");
LEDC_ARG_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "gpio_num");
LEDC_ARG_CHECK(timer_select < LEDC_TIMER_MAX, "timer_select");
LEDC_ARG_CHECK(intr_type < LEDC_INTR_MAX, "intr_type");
periph_module_enable(PERIPH_LEDC_MODULE);
esp_err_t ret = ESP_OK;
if(p_ledc_obj[speed_mode] == NULL) {
p_ledc_obj[speed_mode] = (ledc_obj_t *) heap_caps_calloc(1, sizeof(ledc_obj_t), MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT);
if (p_ledc_obj[speed_mode] == NULL) {
return ESP_ERR_NO_MEM;
}
ledc_hal_init(&(p_ledc_obj[speed_mode]->ledc_hal), speed_mode);
}

View File

@ -160,23 +160,33 @@ esp_err_t rtc_gpio_pulldown_dis(gpio_num_t gpio_num)
#endif // SOC_RTCIO_INPUT_OUTPUT_SUPPORTED
#if SOC_RTCIO_HOLD_SUPPORTED
esp_err_t rtc_gpio_hold_en(gpio_num_t gpio_num)
{
#ifdef CONFIG_IDF_TARGET_ESP32C3 // should use HAL here, TODO ESP32-C3 IDF-2511
RTCIO_CHECK(gpio_num <= GPIO_NUM_5, "RTCIO number error", ESP_ERR_INVALID_ARG);
REG_SET_BIT(RTC_CNTL_PAD_HOLD_REG, BIT(gpio_num));
#else
RTCIO_CHECK(rtc_gpio_is_valid_gpio(gpio_num), "RTCIO number error", ESP_ERR_INVALID_ARG);
RTCIO_ENTER_CRITICAL();
rtcio_hal_hold_enable(rtc_io_number_get(gpio_num));
RTCIO_EXIT_CRITICAL();
#endif
return ESP_OK;
}
esp_err_t rtc_gpio_hold_dis(gpio_num_t gpio_num)
{
#ifdef CONFIG_IDF_TARGET_ESP32C3 // should use HAL here, TODO ESP32-C3 IDF-2511
RTCIO_CHECK(gpio_num <= GPIO_NUM_5, "RTCIO number error", ESP_ERR_INVALID_ARG);
REG_CLR_BIT(RTC_CNTL_PAD_HOLD_REG, BIT(gpio_num));
#else
RTCIO_CHECK(rtc_gpio_is_valid_gpio(gpio_num), "RTCIO number error", ESP_ERR_INVALID_ARG);
RTCIO_ENTER_CRITICAL();
rtcio_hal_hold_disable(rtc_io_number_get(gpio_num));
RTCIO_EXIT_CRITICAL();
#endif
return ESP_OK;
}
@ -208,8 +218,22 @@ esp_err_t rtc_gpio_force_hold_dis_all(void)
return ESP_OK;
}
#endif // SOC_RTCIO_HOLD_SUPPORTED
#if SOC_RTCIO_WAKE_SUPPORTED
esp_err_t rtc_gpio_wakeup_enable(gpio_num_t gpio_num, gpio_int_type_t intr_type)
{
#ifdef CONFIG_IDF_TARGET_ESP32C3 // should use HAL here, TODO ESP32-C3 IDF-2511
RTCIO_CHECK(gpio_num <= GPIO_NUM_5, "RTCIO number error", ESP_ERR_INVALID_ARG);
REG_SET_BIT(RTC_CNTL_GPIO_WAKEUP_REG, RTC_CNTL_GPIO_PIN0_WAKEUP_ENABLE_M >> gpio_num);
uint32_t reg = REG_READ(RTC_CNTL_GPIO_WAKEUP_REG);
reg &= (~(RTC_CNTL_GPIO_PIN0_INT_TYPE_V << (RTC_CNTL_GPIO_PIN0_INT_TYPE_S - gpio_num * 3)));
reg |= (intr_type << (RTC_CNTL_GPIO_PIN0_INT_TYPE_S - gpio_num * 3));
REG_WRITE(RTC_CNTL_GPIO_WAKEUP_REG, reg);
ESP_LOGD(RTCIO_TAG, "gpio wake up 0x%08x", REG_READ(RTC_CNTL_GPIO_WAKEUP_REG));
#else
RTCIO_CHECK(rtc_gpio_is_valid_gpio(gpio_num), "RTCIO number error", ESP_ERR_INVALID_ARG);
if (intr_type == GPIO_INTR_POSEDGE || intr_type == GPIO_INTR_NEGEDGE || intr_type == GPIO_INTR_ANYEDGE) {
return ESP_ERR_INVALID_ARG; // Dont support this mode.
@ -217,16 +241,22 @@ esp_err_t rtc_gpio_wakeup_enable(gpio_num_t gpio_num, gpio_int_type_t intr_type)
RTCIO_ENTER_CRITICAL();
rtcio_hal_wakeup_enable(rtc_io_number_get(gpio_num), intr_type);
RTCIO_EXIT_CRITICAL();
#endif // CONFIG_IDF_TARGET_ESP32C3
return ESP_OK;
}
esp_err_t rtc_gpio_wakeup_disable(gpio_num_t gpio_num)
{
#ifdef CONFIG_IDF_TARGET_ESP32C3 // should use HAL here, TODO ESP32-C3 IDF-2511
RTCIO_CHECK(gpio_num <= GPIO_NUM_5, "RTCIO number error", ESP_ERR_INVALID_ARG);
REG_CLR_BIT(RTC_CNTL_GPIO_WAKEUP_REG, RTC_CNTL_GPIO_PIN0_WAKEUP_ENABLE_M >> gpio_num);
#else
RTCIO_CHECK(rtc_gpio_is_valid_gpio(gpio_num), "RTCIO number error", ESP_ERR_INVALID_ARG);
RTCIO_ENTER_CRITICAL();
rtcio_hal_wakeup_disable(rtc_io_number_get(gpio_num));
RTCIO_EXIT_CRITICAL();
#endif
return ESP_OK;
}
#endif // SOC_RTCIO_WAKE_SUPPORTED

View File

@ -22,6 +22,7 @@
#include "stdatomic.h"
#include "esp_log.h"
#include <strings.h>
#include "esp_heap_caps.h"
/*

View File

@ -85,6 +85,41 @@
#define ESP_SPI_SLAVE_TV 0
#define WIRE_DELAY 12.5
#elif CONFIG_IDF_TARGET_ESP32C3
#define TEST_SPI_HOST FSPI_HOST
#define TEST_SLAVE_HOST FSPI_HOST
#define PIN_NUM_MISO FSPI_IOMUX_PIN_NUM_MISO
#define PIN_NUM_MOSI FSPI_IOMUX_PIN_NUM_MOSI
#define PIN_NUM_CLK FSPI_IOMUX_PIN_NUM_CLK
#define PIN_NUM_CS FSPI_IOMUX_PIN_NUM_CS
#define PIN_NUM_WP FSPI_IOMUX_PIN_NUM_WP
#define PIN_NUM_HD FSPI_IOMUX_PIN_NUM_HD
#define SLAVE_PIN_NUM_MISO -1
#define SLAVE_PIN_NUM_MOSI -1
#define SLAVE_PIN_NUM_CLK -1
#define SLAVE_PIN_NUM_CS -1
#define SLAVE_PIN_NUM_WP -1
#define SLAVE_PIN_NUM_HD -1
//NOTE: On esp32c3, there is only 1 GPSPI controller, so master-slave test on single board should be disabled
#define SLAVE_IOMUX_PIN_MISO FSPI_IOMUX_PIN_NUM_MISO
#define SLAVE_IOMUX_PIN_MOSI FSPI_IOMUX_PIN_NUM_MOSI
#define SLAVE_IOMUX_PIN_SCLK FSPI_IOMUX_PIN_NUM_CLK
#define SLAVE_IOMUX_PIN_CS FSPI_IOMUX_PIN_NUM_CS
#define MASTER_IOMUX_PIN_MISO FSPI_IOMUX_PIN_NUM_MISO
#define MASTER_IOMUX_PIN_MOSI FSPI_IOMUX_PIN_NUM_MOSI
#define MASTER_IOMUX_PIN_SCLK FSPI_IOMUX_PIN_NUM_CLK
#define MASTER_IOMUX_PIN_CS FSPI_IOMUX_PIN_NUM_CS
#define GPIO_DELAY 0
#define ESP_SPI_SLAVE_TV 0
#define WIRE_DELAY 12.5
#endif
#define GET_DMA_CHAN(HOST) (HOST)

View File

@ -16,7 +16,6 @@
#include "esp_rom_uart.h"
#include "esp_rom_sys.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
#define WAKE_UP_IGNORE 1 // gpio_wakeup function development is not completed yet, set it deprecated.
@ -35,8 +34,23 @@
#define TEST_GPIO_OUTPUT_PIN 12
#define TEST_GPIO_INPUT_ONLY_PIN 46
#define TEST_GPIO_OUTPUT_MAX GPIO_NUM_46
#elif CONFIG_IDF_TARGET_ESP32S3
#define TEST_GPIO_EXT_OUT_IO 19 // default output GPIO
#define TEST_GPIO_EXT_IN_IO 20 // default input GPIO
#define TEST_GPIO_OUTPUT_PIN 12
#define TEST_GPIO_INPUT_ONLY_PIN 46
#define TEST_GPIO_OUTPUT_MAX GPIO_NUM_47
#elif CONFIG_IDF_TARGET_ESP32C3
#define TEST_GPIO_EXT_OUT_IO 2 // default output GPIO
#define TEST_GPIO_EXT_IN_IO 3 // default input GPIO
#define TEST_GPIO_OUTPUT_PIN 1
#define TEST_GPIO_OUTPUT_MAX GPIO_NUM_21
#endif
// define public test io on all boards(esp32, esp32s2, esp32s3, esp32c3)
#define TEST_IO_9 GPIO_NUM_9
#define TEST_IO_10 GPIO_NUM_10
static volatile int disable_intr_times = 0; // use this to calculate how many times it go into interrupt
static volatile int level_intr_times = 0; // use this to get how many times the level interrupt happened
static volatile int edge_intr_times = 0; // use this to get how many times the edge interrupt happened
@ -62,7 +76,7 @@ static gpio_config_t init_io(gpio_num_t num)
return io_conf;
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
//No runners
// edge interrupt event
static void gpio_isr_edge_handler(void* arg)
@ -95,7 +109,7 @@ static void gpio_isr_level_handler2(void* arg)
esp_rom_printf("GPIO[%d] intr, val: %d, level_intr_times = %d\n", TEST_GPIO_EXT_OUT_IO, gpio_get_level(TEST_GPIO_EXT_OUT_IO), level_intr_times);
esp_rom_printf("GPIO[%d] intr, val: %d, level_intr_times = %d\n", gpio_num, gpio_get_level(gpio_num), level_intr_times);
}
#endif
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
#if !WAKE_UP_IGNORE
// get result of waking up or not
@ -120,7 +134,7 @@ static void trigger_wake_up(void *arg)
gpio_set_level(TEST_GPIO_EXT_OUT_IO, 1);
vTaskDelay(100 / portTICK_RATE_MS);
}
#endif
#endif //!WAKE_UP_IGNORE
static void prompt_to_continue(const char* str)
{
@ -169,16 +183,18 @@ TEST_CASE("GPIO config parameters test", "[gpio]")
io_config.pin_bit_mask = ((uint64_t)1<<TEST_GPIO_OUTPUT_PIN);
TEST_ESP_OK(gpio_config(&io_config));
//This IO is just used for input, C3 doesn't have input only pin.
#if !CONFIG_IDF_TARGET_ESP32C3
io_config.pin_bit_mask = ((uint64_t)1 << TEST_GPIO_INPUT_ONLY_PIN);
io_config.mode = GPIO_MODE_INPUT;
TEST_ESP_OK(gpio_config(&io_config));
io_config.mode = GPIO_MODE_OUTPUT;
// The pin is input only, once set as output should log something
TEST_ASSERT(gpio_config(&io_config) == ESP_ERR_INVALID_ARG);
#endif //!CONFIG_IDF_TARGET_ESP32C3
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
//No runners
TEST_CASE("GPIO rising edge interrupt test", "[gpio][test_env=UT_T1_GPIO]")
{
@ -370,9 +386,10 @@ TEST_CASE("GPIO enable and disable interrupt test", "[gpio][test_env=UT_T1_GPIO]
TEST_ASSERT(gpio_isr_handler_add(TEST_GPIO_EXT_IN_IO, gpio_isr_level_handler, (void*) TEST_GPIO_EXT_IN_IO) == ESP_ERR_INVALID_STATE);
TEST_ASSERT(gpio_isr_handler_remove(TEST_GPIO_EXT_IN_IO) == ESP_ERR_INVALID_STATE);
}
#endif //DISABLED_FOR_TARGETS(ESP32S2)
#endif //DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
// ESP32 Connect GPIO18 with GPIO19, ESP32-S2 Connect GPIO18 with GPIO21
// ESP32 Connect GPIO18 with GPIO19, ESP32-S2 Connect GPIO17 with GPIO21,
// ESP32-S3 Connect GPIO19 with GPIO20, ESP32C3 Connect GPIO2 with GPIO3
// use multimeter to test the voltage, so it is ignored in CI
TEST_CASE("GPIO set gpio output level test", "[gpio][ignore]")
{
@ -396,11 +413,13 @@ TEST_CASE("GPIO set gpio output level test", "[gpio][ignore]")
// tested voltage is around 3.3v
TEST_ASSERT_EQUAL_INT_MESSAGE(gpio_get_level(TEST_GPIO_EXT_IN_IO), 1, "get level error! the level should be high!");
//This IO is just used for input
//This IO is just used for input, C3 doesn't have input only pin.
#if !CONFIG_IDF_TARGET_ESP32C3
io_conf.pin_bit_mask = ((uint64_t)1<<TEST_GPIO_INPUT_ONLY_PIN);
io_conf.mode = GPIO_MODE_OUTPUT;
gpio_config(&io_conf);
TEST_ASSERT(gpio_config(&io_conf) == ESP_ERR_INVALID_ARG);
#endif //!CONFIG_IDF_TARGET_ESP32C3
}
// gpio17 connects to 3.3v pin, gpio19 connects to the GND pin
@ -449,11 +468,11 @@ TEST_CASE("GPIO io pull up/down function", "[gpio]")
TEST_ASSERT_EQUAL_INT_MESSAGE(gpio_get_level(TEST_GPIO_EXT_IN_IO), 0, "gpio_pullup_dis error, it can pull up");
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
//No runners
TEST_CASE("GPIO output and input mode test", "[gpio][test_env=UT_T1_GPIO]")
{
//ESP32 connect io18 and io19, ESP32-S2 connect io18 and io21
//ESP32 connect io18 and io19, ESP32-S2 connect io17 and io21, ESP32-S3 connect io19 and io20, ESP32C3 Connect GPIO2 with GPIO3
gpio_config_t output_io = init_io(TEST_GPIO_EXT_OUT_IO);
gpio_config_t input_io = init_io(TEST_GPIO_EXT_IN_IO);
gpio_config(&output_io);
@ -523,7 +542,7 @@ TEST_CASE("GPIO repeate call service and isr has no memory leak test","[gpio][te
}
TEST_ASSERT_INT32_WITHIN(size, esp_get_free_heap_size(), 100);
}
#endif //DISABLED_FOR_TARGETS(ESP32S2)
#endif //DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
#if !WAKE_UP_IGNORE
//this function development is not completed yet, set it ignored
@ -540,7 +559,7 @@ TEST_CASE("GPIO wake up enable and disenable test", "[gpio][ignore]")
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ASSERT_FALSE(wake_up_result);
}
#endif
#endif // !WAKE_UP_IGNORE
// this case need the resistance to pull up the voltage or pull down the voltage
// ignored because the voltage needs to be tested with multimeter
@ -649,6 +668,7 @@ TEST_CASE("GPIO drive capability test", "[gpio][ignore]")
}
#if !CONFIG_FREERTOS_UNICORE
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
void gpio_enable_task(void *param)
{
int gpio_num = (int)param;
@ -659,46 +679,46 @@ void gpio_enable_task(void *param)
/** Test the GPIO Interrupt Enable API with dual core enabled. The GPIO ISR service routine is registered on one core.
* When the GPIO interrupt on another core is enabled, the GPIO interrupt will be lost.
* First on the core 0, Do the following steps:
* 1. Configure the GPIO18 input_output mode, and enable the rising edge interrupt mode.
* 2. Trigger the GPIO18 interrupt and check if the interrupt responds correctly.
* 3. Disable the GPIO18 interrupt
* 1. Configure the GPIO9 input_output mode, and enable the rising edge interrupt mode.
* 2. Trigger the GPIO9 interrupt and check if the interrupt responds correctly.
* 3. Disable the GPIO9 interrupt
* Then on the core 1, Do the following steps:
* 1. Enable the GPIO18 interrupt again.
* 2. Trigger the GPIO18 interrupt and check if the interrupt responds correctly.
* 1. Enable the GPIO9 interrupt again.
* 2. Trigger the GPIO9 interrupt and check if the interrupt responds correctly.
*
*/
TEST_CASE("GPIO Enable/Disable interrupt on multiple cores", "[gpio][ignore]")
{
const int test_io18 = GPIO_NUM_18;
gpio_config_t io_conf;
io_conf.intr_type = GPIO_INTR_NEGEDGE;
io_conf.mode = GPIO_MODE_INPUT_OUTPUT;
io_conf.pin_bit_mask = (1ULL << test_io18);
io_conf.pin_bit_mask = (1ULL << TEST_IO_9);
io_conf.pull_down_en = 0;
io_conf.pull_up_en = 1;
TEST_ESP_OK(gpio_config(&io_conf));
TEST_ESP_OK(gpio_set_level(test_io18, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 0));
TEST_ESP_OK(gpio_install_isr_service(0));
TEST_ESP_OK(gpio_isr_handler_add(test_io18, gpio_isr_edge_handler, (void*) test_io18));
TEST_ESP_OK(gpio_isr_handler_add(TEST_IO_9, gpio_isr_edge_handler, (void*) TEST_IO_9));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_set_level(test_io18, 1));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 1));
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_set_level(test_io18, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 0));
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_intr_disable(test_io18));
TEST_ESP_OK(gpio_intr_disable(TEST_IO_9));
TEST_ASSERT(edge_intr_times == 1);
xTaskCreatePinnedToCore(gpio_enable_task, "gpio_enable_task", 1024*4, (void*)test_io18, 8, NULL, (xPortGetCoreID() == 0));
xTaskCreatePinnedToCore(gpio_enable_task, "gpio_enable_task", 1024*4, (void*)TEST_IO_9, 8, NULL, (xPortGetCoreID() == 0));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_set_level(test_io18, 1));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 1));
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_set_level(test_io18, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 0));
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_intr_disable(test_io18));
TEST_ESP_OK(gpio_isr_handler_remove(test_io18));
TEST_ESP_OK(gpio_intr_disable(TEST_IO_9));
TEST_ESP_OK(gpio_isr_handler_remove(TEST_IO_9));
gpio_uninstall_isr_service();
TEST_ASSERT(edge_intr_times == 2);
}
#endif
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#endif //!CONFIG_FREERTOS_UNICORE
typedef struct {
int gpio_num;
@ -716,61 +736,57 @@ static void gpio_isr_handler(void* arg)
* But this will incorrectly handle the interrupt disabled GPIOs, because the raw interrupt status register can still be set when
* the trigger signal arrives, even if the interrupt is disabled.
* First on the core 0:
* 1. Configure the GPIO18 and GPIO19(ESP32)/GPIO21(ESP32-S2) input_output mode.
* 2. Enable GPIO18 dual edge triggered interrupt, enable GPIO19(ESP32)/GPIO21(ESP32-S2) falling edge triggered interrupt.
* 3. Trigger GPIO18 interrupt, than disable the GPIO8 interrupt, and than trigger GPIO18 again(This time will not respond to the interrupt).
* 4. Trigger GPIO19(ESP32)/GPIO21(ESP32-S2) interrupt.
* If the bug is not fixed, you will see, in the step 4, the interrupt of GPIO18 will also respond.
* 1. Configure the GPIO9 and GPIO10(ESP32, ESP32C3)/GPIO21(ESP32-S2) input_output mode.
* 2. Enable GPIO9 dual edge triggered interrupt, enable GPIO10(ESP32, ESP32C3)/GPIO21(ESP32-S2) falling edge triggered interrupt.
* 3. Trigger GPIO9 interrupt, than disable the GPIO18 interrupt, and than trigger GPIO18 again(This time will not respond to the interrupt).
* 4. Trigger GPIO10(ESP32, ESP32C3)/GPIO21(ESP32-S2) interrupt.
* If the bug is not fixed, you will see, in the step 4, the interrupt of GPIO9 will also respond.
*/
TEST_CASE("GPIO ISR service test", "[gpio][ignore]")
{
const int test_io18 = GPIO_NUM_18;
const int test_io19 = GPIO_NUM_19;
static gpio_isr_param_t io18_param = {
.gpio_num = GPIO_NUM_18,
static gpio_isr_param_t io9_param = {
.gpio_num = TEST_IO_9,
.isr_cnt = 0,
};
static gpio_isr_param_t io19_param = {
.gpio_num = GPIO_NUM_19,
static gpio_isr_param_t io10_param = {
.gpio_num = TEST_IO_10,
.isr_cnt = 0,
};
gpio_config_t io_conf;
io_conf.intr_type = GPIO_INTR_DISABLE;
io_conf.mode = GPIO_MODE_INPUT_OUTPUT;
io_conf.pin_bit_mask = (1ULL << test_io18) | (1ULL << test_io19);
io_conf.pin_bit_mask = (1ULL << TEST_IO_9) | (1ULL << TEST_IO_10);
io_conf.pull_down_en = 0;
io_conf.pull_up_en = 1;
TEST_ESP_OK(gpio_config(&io_conf));
TEST_ESP_OK(gpio_set_level(test_io18, 0));
TEST_ESP_OK(gpio_set_level(test_io19, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_10, 0));
TEST_ESP_OK(gpio_install_isr_service(0));
TEST_ESP_OK(gpio_set_intr_type(test_io18, GPIO_INTR_ANYEDGE));
TEST_ESP_OK(gpio_set_intr_type(test_io19, GPIO_INTR_NEGEDGE));
TEST_ESP_OK(gpio_isr_handler_add(test_io18, gpio_isr_handler, (void*)&io18_param));
TEST_ESP_OK(gpio_isr_handler_add(test_io19, gpio_isr_handler, (void*)&io19_param));
printf("Triggering the interrupt of GPIO18\n");
TEST_ESP_OK(gpio_set_intr_type(TEST_IO_9, GPIO_INTR_ANYEDGE));
TEST_ESP_OK(gpio_set_intr_type(TEST_IO_10, GPIO_INTR_NEGEDGE));
TEST_ESP_OK(gpio_isr_handler_add(TEST_IO_9, gpio_isr_handler, (void*)&io9_param));
TEST_ESP_OK(gpio_isr_handler_add(TEST_IO_10, gpio_isr_handler, (void*)&io10_param));
printf("Triggering the interrupt of GPIO9\n");
vTaskDelay(1000 / portTICK_RATE_MS);
//Rising edge
TEST_ESP_OK(gpio_set_level(test_io18, 1));
printf("Disable the interrupt of GPIO18");
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 1));
printf("Disable the interrupt of GPIO9\n");
vTaskDelay(100 / portTICK_RATE_MS);
//Disable GPIO18 interrupt, GPIO18 will not respond to the next falling edge interrupt.
TEST_ESP_OK(gpio_intr_disable(test_io18));
//Disable GPIO9 interrupt, GPIO18 will not respond to the next falling edge interrupt.
TEST_ESP_OK(gpio_intr_disable(TEST_IO_9));
vTaskDelay(100 / portTICK_RATE_MS);
//Falling edge
TEST_ESP_OK(gpio_set_level(test_io18, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_9, 0));
printf("Triggering the interrupt of GPIO19\n");
printf("Triggering the interrupt of GPIO10\n");
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_set_level(test_io19, 1));
TEST_ESP_OK(gpio_set_level(TEST_IO_10, 1));
vTaskDelay(100 / portTICK_RATE_MS);
//Falling edge
TEST_ESP_OK(gpio_set_level(test_io19, 0));
TEST_ESP_OK(gpio_set_level(TEST_IO_10, 0));
vTaskDelay(100 / portTICK_RATE_MS);
TEST_ESP_OK(gpio_isr_handler_remove(test_io18));
TEST_ESP_OK(gpio_isr_handler_remove(test_io19));
TEST_ESP_OK(gpio_isr_handler_remove(TEST_IO_9));
TEST_ESP_OK(gpio_isr_handler_remove(TEST_IO_10));
gpio_uninstall_isr_service();
TEST_ASSERT((io18_param.isr_cnt == 1) && (io19_param.isr_cnt == 1));
TEST_ASSERT((io9_param.isr_cnt == 1) && (io10_param.isr_cnt == 1));
}
#endif

View File

@ -14,24 +14,36 @@
#include "soc/gpio_periph.h"
#include "soc/i2c_periph.h"
#include "esp_system.h"
#include "driver/pcnt.h"
#include "soc/uart_struct.h"
#include "driver/periph_ctrl.h"
#include "esp_rom_gpio.h"
#define DATA_LENGTH 512 /*!<Data buffer length for test buffer*/
#define RW_TEST_LENGTH 129 /*!<Data length for r/w test, any value from 0-DATA_LENGTH*/
#define DELAY_TIME_BETWEEN_ITEMS_MS 1234 /*!< delay time between different test items */
#if CONFIG_IDF_TARGET_ESP32C3
#define I2C_SLAVE_SCL_IO 5 /*!<gpio number for i2c slave clock */
#define I2C_SLAVE_SDA_IO 6 /*!<gpio number for i2c slave data */
#else
#define I2C_SLAVE_SCL_IO 19 /*!<gpio number for i2c slave clock */
#define I2C_SLAVE_SDA_IO 18 /*!<gpio number for i2c slave data */
#endif
#define I2C_SLAVE_NUM I2C_NUM_0 /*!<I2C port number for slave dev */
#define I2C_SLAVE_TX_BUF_LEN (2*DATA_LENGTH) /*!<I2C slave tx buffer size */
#define I2C_SLAVE_RX_BUF_LEN (2*DATA_LENGTH) /*!<I2C slave rx buffer size */
#if CONFIG_IDF_TARGET_ESP32C3
#define I2C_MASTER_SCL_IO 5 /*!<gpio number for i2c master clock */
#define I2C_MASTER_SDA_IO 6 /*!<gpio number for i2c master data */
#else
#define I2C_MASTER_SCL_IO 19 /*!< gpio number for I2C master clock */
#define I2C_MASTER_SDA_IO 18 /*!< gpio number for I2C master data */
#define I2C_MASTER_NUM I2C_NUM_1 /*!< I2C port number for master dev */
#define I2C_MASTER_SDA_IO 18 /*!< gpio number for I2C master data */
#endif
#define I2C_MASTER_NUM I2C_NUM_0 /*!< I2C port number for master dev */
#define I2C_MASTER_TX_BUF_DISABLE 0 /*!< I2C master do not need buffer */
#define I2C_MASTER_RX_BUF_DISABLE 0 /*!< I2C master do not need buffer */
#define I2C_MASTER_FREQ_HZ 100000 /*!< I2C master clock frequency */
@ -50,7 +62,13 @@
#define HIGHEST_LIMIT 10000
#define LOWEST_LIMIT -10000
static DRAM_ATTR i2c_dev_t *const I2C[I2C_NUM_MAX] = { &I2C0, &I2C1 };
static DRAM_ATTR i2c_dev_t *const I2C[SOC_I2C_NUM] = { &I2C0,
#if SOC_I2C_NUM > 1
&I2C1,
#endif
};
static esp_err_t i2c_master_write_slave(i2c_port_t i2c_num, uint8_t *data_wr, size_t size)
{
@ -248,7 +266,7 @@ TEST_CASE("I2C driver memory leaking check", "[i2c]")
TEST_ASSERT_INT_WITHIN(100, size, esp_get_free_heap_size());
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
// print the reading buffer
static void disp_buf(uint8_t *buf, int len)
@ -378,7 +396,7 @@ static void slave_write_buffer_test(void)
TEST_CASE_MULTIPLE_DEVICES("I2C master read slave test", "[i2c][test_env=UT_T2_I2C][timeout=150]", master_read_slave_test, slave_write_buffer_test);
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32, ESP32C3)
static void i2c_master_write_read_test(void)
{
uint8_t *data_rd = (uint8_t *) malloc(DATA_LENGTH);
@ -519,8 +537,8 @@ static void i2c_slave_repeat_read(void)
TEST_CASE_MULTIPLE_DEVICES("I2C repeat write test", "[i2c][test_env=UT_T2_I2C][timeout=150]", i2c_master_repeat_write, i2c_slave_repeat_read);
#endif //DISABLED_FOR_TARGET(ESP32S2, ESP32)
#endif //DISABLED_FOR_TARGET(ESP32S2)
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
static volatile bool exit_flag;
static bool test_read_func;
@ -629,7 +647,7 @@ TEST_CASE("I2C general API test", "[i2c]")
}
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
//Init uart baud rate detection
static void uart_aut_baud_det_init(int rxd_io_num)
{
@ -693,4 +711,4 @@ TEST_CASE("I2C SCL freq test (local test)", "[i2c][ignore]")
TEST_ESP_OK(i2c_driver_delete(i2c_num));
}
#endif
#endif // TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)

View File

@ -15,7 +15,7 @@
#include "math.h"
#include "esp_rom_gpio.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
#define SAMPLE_RATE (36000)
#define SAMPLE_BITS (16)

View File

@ -17,23 +17,88 @@
#include "freertos/task.h"
#include "freertos/semphr.h"
#include "freertos/queue.h"
#include "freertos/xtensa_api.h"
#include "unity.h"
#include "soc/ledc_periph.h"
#include "esp_system.h"
#include "driver/pcnt.h"
#include "driver/ledc.h"
#include "driver/gpio.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#define PULSE_IO 18
#define PCNT_INPUT_IO 4
#define PCNT_CTRL_FLOATING_IO 5
#define HIGHEST_LIMIT 10000
#define LOWEST_LIMIT -10000
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if SOC_LEDC_SUPPORT_HS_MODE
#define TEST_SPEED_MODE LEDC_HIGH_SPEED_MODE
#define SPEED_MODE_LIST {LEDC_HIGH_SPEED_MODE, LEDC_LOW_SPEED_MODE}
#else
#define TEST_SPEED_MODE LEDC_LOW_SPEED_MODE
#define SPEED_MODE_LIST {LEDC_LOW_SPEED_MODE}
#endif
static ledc_channel_config_t initialize_channel_config(void)
{
ledc_channel_config_t config;
memset(&config, 0, sizeof(ledc_channel_config_t));
config.gpio_num = PULSE_IO;
config.speed_mode = TEST_SPEED_MODE;
config.channel = LEDC_CHANNEL_0;
config.intr_type = LEDC_INTR_DISABLE;
config.timer_sel = LEDC_TIMER_0;
config.duty = 4000;
config.hpoint = 0;
return config;
}
static ledc_timer_config_t create_default_timer_config(void)
{
ledc_timer_config_t ledc_time_config;
memset(&ledc_time_config, 0, sizeof(ledc_timer_config_t));
ledc_time_config.speed_mode = TEST_SPEED_MODE;
ledc_time_config.duty_resolution = LEDC_TIMER_13_BIT;
ledc_time_config.timer_num = LEDC_TIMER_0;
ledc_time_config.freq_hz = 2000;
ledc_time_config.clk_cfg = LEDC_USE_APB_CLK;
return ledc_time_config;
}
static void timer_duty_set_get(ledc_mode_t speed_mode, ledc_channel_t channel, uint32_t duty)
{
TEST_ESP_OK(ledc_set_duty(speed_mode, channel, duty));
TEST_ESP_OK(ledc_update_duty(speed_mode, channel));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(speed_mode, channel), duty);
}
// use logic analyzer to view
static void timer_duty_test(ledc_channel_t channel, ledc_timer_bit_t timer_bit, ledc_timer_t timer, ledc_mode_t speed_mode)
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.speed_mode = speed_mode;
ledc_ch_config.channel = channel;
ledc_ch_config.timer_sel = timer;
ledc_timer_config_t ledc_time_config = create_default_timer_config();
ledc_time_config.speed_mode = speed_mode;
ledc_time_config.duty_resolution = timer_bit;
ledc_time_config.timer_num = timer;
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
// duty ratio: (2^duty)/(2^timer_bit)
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 0);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 1);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 1 << 12); // 50% duty
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, (1 << 13) - 1);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, (1 << 13) - 2);
}
#if SOC_PCNT_SUPPORTED
#include "driver/pcnt.h" // TODO: C3 doesn't have PCNT peripheral
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
//no runners
// use PCNT to test the waveform of LEDC
@ -101,182 +166,135 @@ static void timer_frequency_test(ledc_channel_t channel, ledc_timer_bit_t timer_
frequency_set_get(ledc_ch_config.speed_mode, ledc_ch_config.timer_sel, 9000, 9025, 5);
}
static void timer_duty_set_get(ledc_mode_t speed_mode, ledc_channel_t channel, uint32_t duty)
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
#endif // SOC_PCNT_SUPPORTED
TEST_CASE("LEDC channel config wrong gpio", "[ledc]")
{
TEST_ESP_OK(ledc_set_duty(speed_mode, channel, duty));
TEST_ESP_OK(ledc_update_duty(speed_mode, channel));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(speed_mode, channel), duty);
}
// use logic analyzer to view
static void timer_duty_test(ledc_channel_t channel, ledc_timer_bit_t timer_bit, ledc_timer_t timer, ledc_mode_t speed_mode)
{
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = speed_mode,
.channel = channel,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = timer,
.duty = 4000,
.hpoint = 0,
};
ledc_timer_config_t ledc_time_config = {
.speed_mode = speed_mode,
.duty_resolution = timer_bit,
.timer_num = timer,
.freq_hz = 5000,
.clk_cfg = LEDC_USE_APB_CLK,
};
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
// duty ratio: (2^duty)/(2^timer_bit)
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 0);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 1);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, 1 << 12); // 50% duty
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, (1 << 13) - 1);
timer_duty_set_get(ledc_ch_config.speed_mode, ledc_ch_config.channel, (1 << 13) - 2);
}
TEST_CASE("LEDC error log channel and timer config", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
//channel configuration test
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = test_speed_mode,
.channel = LEDC_CHANNEL_0,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = LEDC_TIMER_0,
.duty = 4000,
.hpoint = 0,
};
// basic right parameter test
ledc_channel_config_t temp_ch_config = ledc_ch_config;
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
// with wrong GPIO using
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.gpio_num = GPIO_NUM_MAX;
TEST_ASSERT(ledc_channel_config(&ledc_ch_config) == ESP_ERR_INVALID_ARG);
// with wrong speed
ledc_ch_config = temp_ch_config;
}
TEST_CASE("LEDC channel config wrong speed", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.speed_mode = LEDC_SPEED_MODE_MAX;
TEST_ASSERT(ledc_channel_config(&ledc_ch_config) == ESP_ERR_INVALID_ARG);
}
// with wrong channel
ledc_ch_config = temp_ch_config;
TEST_CASE("LEDC channel config wrong channel", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.channel = LEDC_CHANNEL_MAX;
TEST_ASSERT(ledc_channel_config(&ledc_ch_config) == ESP_ERR_INVALID_ARG);
}
// with wrong interruption type
ledc_ch_config = temp_ch_config;
TEST_CASE("LEDC channel config wrong interrupt type", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.intr_type = 2;
TEST_ASSERT_FALSE((void *)ledc_channel_config(&ledc_ch_config));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, ledc_channel_config(&ledc_ch_config));
}
// with wrong timer
ledc_ch_config = temp_ch_config;
ledc_ch_config.timer_sel = 4;
TEST_ASSERT(ledc_channel_config(&ledc_ch_config) == ESP_ERR_INVALID_ARG);
TEST_CASE("LEDC wrong timer", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.timer_sel = LEDC_TIMER_MAX;
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, ledc_channel_config(&ledc_ch_config));
}
ledc_ch_config = temp_ch_config;
ledc_ch_config.duty = 12000;
TEST_ASSERT_FALSE((void *)ledc_channel_config(&ledc_ch_config));
TEST_CASE("LEDC channel config basic parameter test", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
TEST_ASSERT_EQUAL(ESP_OK, ledc_channel_config(&ledc_ch_config));
}
// timer configuration test
ledc_timer_config_t ledc_time_config;
ledc_time_config.speed_mode = test_speed_mode;
ledc_time_config.duty_resolution = LEDC_TIMER_13_BIT;
ledc_time_config.timer_num = LEDC_TIMER_0;
ledc_time_config.freq_hz = 5000;
ledc_time_config.clk_cfg = LEDC_USE_APB_CLK;
ledc_timer_config_t temp_timer_config = ledc_time_config;
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
ledc_time_config.speed_mode = LEDC_SPEED_MODE_MAX;
TEST_ASSERT(ledc_timer_config(&ledc_time_config) == ESP_ERR_INVALID_ARG);
// wrong duty_resolution
ledc_time_config = temp_timer_config;
TEST_CASE("LEDC wrong duty resolution", "[ledc]")
{
ledc_timer_config_t ledc_time_config = create_default_timer_config();
ledc_time_config.duty_resolution = LEDC_TIMER_BIT_MAX;
TEST_ASSERT(ledc_timer_config(&ledc_time_config) == ESP_ERR_INVALID_ARG);
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, ledc_timer_config(&ledc_time_config));
}
// wrong timer
ledc_time_config = temp_timer_config;
ledc_time_config.timer_num = 4;
TEST_ASSERT(ledc_timer_config(&ledc_time_config) == ESP_ERR_INVALID_ARG);
TEST_CASE("LEDC timer config wrong timer", "[ledc]")
{
ledc_timer_config_t ledc_time_config = create_default_timer_config();
ledc_time_config.timer_num = LEDC_TIMER_MAX;
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, ledc_timer_config(&ledc_time_config));
}
TEST_CASE("LEDC timer config wrong speed mode", "[ledc]")
{
ledc_timer_config_t ledc_time_config = create_default_timer_config();
ledc_time_config.speed_mode = LEDC_SPEED_MODE_MAX;
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, ledc_timer_config(&ledc_time_config));
}
TEST_CASE("LEDC timer config basic parameter test", "[ledc]")
{
ledc_timer_config_t ledc_time_config = create_default_timer_config();
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
}
TEST_CASE("LEDC error log channel and timer config", "[ledc]")
{
const ledc_mode_t test_speed_mode = TEST_SPEED_MODE;
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_timer_config_t ledc_time_config = create_default_timer_config();
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
uint32_t current_level = LEDC.channel_group[test_speed_mode].channel[LEDC_CHANNEL_0].conf0.idle_lv;
TEST_ESP_OK(ledc_stop(test_speed_mode, LEDC_CHANNEL_0, !current_level));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32( LEDC.channel_group[test_speed_mode].channel[LEDC_CHANNEL_0].conf0.idle_lv, !current_level);
TEST_ASSERT_EQUAL_INT32(LEDC.channel_group[test_speed_mode].channel[LEDC_CHANNEL_0].conf0.idle_lv, !current_level);
}
TEST_CASE("LEDC normal channel and timer config", "[ledc][test_env=UT_T1_LEDC]")
TEST_CASE("LEDC iterate over all channel and timer configs", "[ledc]")
{
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.channel = LEDC_CHANNEL_0,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = LEDC_TIMER_0,
.duty = 4000,
.hpoint = 0,
};
ledc_channel_config_t temp_ch_config = ledc_ch_config;
ledc_timer_config_t ledc_time_config = {
.duty_resolution = LEDC_TIMER_13_BIT,
.timer_num = LEDC_TIMER_0,
.freq_hz = 5000,
.clk_cfg = LEDC_USE_APB_CLK,
};
ledc_timer_config_t temp_time_config = ledc_time_config;
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_timer_config_t ledc_time_config = create_default_timer_config();
// use all kinds of speed mode, channel, timer combination to test all of possible configuration
#ifdef CONFIG_IDF_TARGET_ESP32
ledc_mode_t speed_mode[LEDC_SPEED_MODE_MAX] = {LEDC_HIGH_SPEED_MODE, LEDC_LOW_SPEED_MODE};
#elif defined CONFIG_IDF_TARGET_ESP32S2
ledc_mode_t speed_mode[LEDC_SPEED_MODE_MAX] = {LEDC_LOW_SPEED_MODE};
#endif
ledc_channel_t channel_type[8] = {LEDC_CHANNEL_0, LEDC_CHANNEL_1, LEDC_CHANNEL_2, LEDC_CHANNEL_3, LEDC_CHANNEL_4, LEDC_CHANNEL_5, LEDC_CHANNEL_6, LEDC_CHANNEL_7};
ledc_mode_t speed_mode[LEDC_SPEED_MODE_MAX] = SPEED_MODE_LIST;
ledc_channel_t channels[8] = {LEDC_CHANNEL_0, LEDC_CHANNEL_1, LEDC_CHANNEL_2, LEDC_CHANNEL_3, LEDC_CHANNEL_4, LEDC_CHANNEL_5};
ledc_timer_t timer_select[4] = {LEDC_TIMER_0, LEDC_TIMER_1, LEDC_TIMER_2, LEDC_TIMER_3};
for (int i = 0; i < LEDC_SPEED_MODE_MAX; i++) {
ledc_ch_config.speed_mode = speed_mode[i];
ledc_time_config.speed_mode = speed_mode[i];
for (int j = 0; j < 8; j++) {
ledc_ch_config.channel = channel_type[j];
ledc_ch_config.channel = channels[j];
for (int k = 0; k < 4; k++) {
ledc_ch_config.timer_sel = timer_select[k];
ledc_time_config.timer_num = timer_select[k];
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
ledc_ch_config = temp_ch_config;
ledc_time_config = temp_time_config;
}
}
}
}
// set it ignore: need to debug
TEST_CASE("LEDC set and get frequency", "[ledc][test_env=UT_T1_LEDC][timeout=60][ignore]")
TEST_CASE("LEDC memory leak test", "[ledc]")
{
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_0, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_1, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_2, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_3, LEDC_HIGH_SPEED_MODE);
#endif
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_0, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_1, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_2, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_3, LEDC_LOW_SPEED_MODE);
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
ledc_timer_config_t ledc_time_config = create_default_timer_config();
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
uint32_t size = esp_get_free_heap_size();
uint32_t i;
// install and uninstall for 1000 times to test whether memory leaking exists
for (i = 0; i <= 1000; i++) {
TEST_ESP_OK(ledc_fade_func_install(0));
ledc_fade_func_uninstall();
}
TEST_ASSERT_INT32_WITHIN(100, size, esp_get_free_heap_size());
TEST_ESP_OK(ledc_stop(ledc_time_config.speed_mode, LEDC_CHANNEL_0, 0));
}
// the duty need to be detected by waveform given by the logic analyzer
@ -284,11 +302,7 @@ TEST_CASE("LEDC set and get frequency", "[ledc][test_env=UT_T1_LEDC][timeout=60]
TEST_CASE("LEDC set and get dut(with logic analyzer)", "[ledc][ignore]")
{
ledc_timer_t timer_list[4] = {LEDC_TIMER_0, LEDC_TIMER_1, LEDC_TIMER_2, LEDC_TIMER_3};
#ifdef CONFIG_IDF_TARGET_ESP32
ledc_mode_t speed_mode_list[LEDC_SPEED_MODE_MAX] = {LEDC_HIGH_SPEED_MODE, LEDC_LOW_SPEED_MODE};
#elif defined CONFIG_IDF_TARGET_ESP32S2
ledc_mode_t speed_mode_list[LEDC_SPEED_MODE_MAX] = {LEDC_LOW_SPEED_MODE};
#endif
ledc_mode_t speed_mode_list[LEDC_SPEED_MODE_MAX] = SPEED_MODE_LIST;
for(int i=0; i<LEDC_TIMER_MAX-1; i++) {
for(int j=0; j<LEDC_SPEED_MODE_MAX; j++) {
timer_duty_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, timer_list[i], speed_mode_list[j]);
@ -296,13 +310,85 @@ TEST_CASE("LEDC set and get dut(with logic analyzer)", "[ledc][ignore]")
}
}
TEST_CASE("LEDC fade with time(logic analyzer)", "[ledc][ignore]")
{
const ledc_mode_t test_speed_mode = TEST_SPEED_MODE;
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.duty = 0;
ledc_timer_config_t ledc_time_config = create_default_timer_config();
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
//initialize fade service
TEST_ESP_OK(ledc_fade_func_install(0));
TEST_ESP_OK(ledc_set_fade_with_time(test_speed_mode, LEDC_CHANNEL_0, 4000, 1000));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_WAIT_DONE));
// TODO: allows for 5% deviation here due to driver code (IDF-2099)
vTaskDelay(1050 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 4000);
TEST_ESP_OK(ledc_set_fade_with_time(test_speed_mode, LEDC_CHANNEL_0, 0, 1000));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_NO_WAIT));
vTaskDelay(1050 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 0);
//deinitial fade service
ledc_fade_func_uninstall();
}
TEST_CASE("LEDC fade with step(logic analyzer)", "[ledc][ignore]")
{
const ledc_mode_t test_speed_mode = TEST_SPEED_MODE;
ledc_channel_config_t ledc_ch_config = initialize_channel_config();
ledc_ch_config.duty = 0;
ledc_timer_config_t ledc_time_config = create_default_timer_config();
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
//initialize fade service.
TEST_ESP_OK(ledc_fade_func_install(0));
TEST_ESP_OK(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 4000, 2, 1));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_WAIT_DONE));
vTaskDelay(1050 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 4000);
TEST_ESP_OK(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 0, 4, 2));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_NO_WAIT));
vTaskDelay(1050 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 0);
//scaler=0 check
TEST_ASSERT(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 4000, 0, 1) == ESP_ERR_INVALID_ARG);
//deinitial fade service
ledc_fade_func_uninstall();
}
#if SOC_PCNT_SUPPORTED
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
TEST_CASE("LEDC set and get frequency", "[ledc][test_env=UT_T1_LEDC][timeout=60][ignore]")
{
#if SOC_LEDC_SUPPORT_HS_MODE
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_0, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_1, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_2, LEDC_HIGH_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_3, LEDC_HIGH_SPEED_MODE);
#endif // SOC_LEDC_SUPPORT_HS_MODE
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_0, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_1, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_2, LEDC_LOW_SPEED_MODE);
timer_frequency_test(LEDC_CHANNEL_0, LEDC_TIMER_13_BIT, LEDC_TIMER_3, LEDC_LOW_SPEED_MODE);
}
TEST_CASE("LEDC timer set", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
const ledc_mode_t test_speed_mode = TEST_SPEED_MODE;
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = test_speed_mode,
@ -354,11 +440,7 @@ TEST_CASE("LEDC timer set", "[ledc][test_env=UT_T1_LEDC]")
TEST_CASE("LEDC timer pause and resume", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
const ledc_mode_t test_speed_mode = TEST_SPEED_MODE;
int16_t count;
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
@ -405,145 +487,6 @@ TEST_CASE("LEDC timer pause and resume", "[ledc][test_env=UT_T1_LEDC]")
TEST_ASSERT_UINT32_WITHIN(5, count, 5000);
}
TEST_CASE("LEDC fade with time(logic analyzer)", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_FREERTOS_CHECK_PORT_CRITICAL_COMPLIANCE
return;
#endif
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = test_speed_mode,
.channel = LEDC_CHANNEL_0,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = LEDC_TIMER_0,
.duty = 0,
.hpoint = 0,
};
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
ledc_timer_config_t ledc_time_config = {
.speed_mode = test_speed_mode,
.duty_resolution = LEDC_TIMER_13_BIT,
.timer_num = LEDC_TIMER_0,
.freq_hz = 5000,
.clk_cfg = LEDC_USE_APB_CLK,
};
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
//initialize fade service
TEST_ESP_OK(ledc_fade_func_install(0));
TEST_ESP_OK(ledc_set_fade_with_time(test_speed_mode, LEDC_CHANNEL_0, 4000, 1000));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_WAIT_DONE));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 4000);
TEST_ESP_OK(ledc_set_fade_with_time(test_speed_mode, LEDC_CHANNEL_0, 0, 1000));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_NO_WAIT));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 0);
//deinitial fade service
ledc_fade_func_uninstall();
}
TEST_CASE("LEDC fade with step(logic analyzer)", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_FREERTOS_CHECK_PORT_CRITICAL_COMPLIANCE
return;
#endif
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = test_speed_mode,
.channel = LEDC_CHANNEL_0,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = LEDC_TIMER_0,
.duty = 0,
.hpoint = 0,
};
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
ledc_timer_config_t ledc_time_config = {
.speed_mode = test_speed_mode,
.duty_resolution = LEDC_TIMER_13_BIT,
.timer_num = LEDC_TIMER_0,
.freq_hz = 5000,
.clk_cfg = LEDC_USE_APB_CLK,
};
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
//initialize fade service.
TEST_ESP_OK(ledc_fade_func_install(0));
TEST_ESP_OK(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 4000, 2, 1));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_WAIT_DONE));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 4000);
TEST_ESP_OK(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 0, 4, 2));
TEST_ESP_OK(ledc_fade_start(test_speed_mode, LEDC_CHANNEL_0, LEDC_FADE_NO_WAIT));
vTaskDelay(1000 / portTICK_RATE_MS);
TEST_ASSERT_EQUAL_INT32(ledc_get_duty(test_speed_mode, LEDC_CHANNEL_0), 0);
//scaler=0 check
TEST_ASSERT(ledc_set_fade_with_step(test_speed_mode, LEDC_CHANNEL_0, 4000, 0, 1) == ESP_ERR_INVALID_ARG);
//deinitial fade service
ledc_fade_func_uninstall();
}
// memory leaking problem detecting
TEST_CASE("LEDC memory test", "[ledc][test_env=UT_T1_LEDC]")
{
#ifdef CONFIG_IDF_TARGET_ESP32
const ledc_mode_t test_speed_mode = LEDC_HIGH_SPEED_MODE;
#elif defined CONFIG_IDF_TARGET_ESP32S2
const ledc_mode_t test_speed_mode = LEDC_LOW_SPEED_MODE;
#endif
ledc_channel_config_t ledc_ch_config = {
.gpio_num = PULSE_IO,
.speed_mode = test_speed_mode,
.channel = LEDC_CHANNEL_0,
.intr_type = LEDC_INTR_DISABLE,
.timer_sel = LEDC_TIMER_0,
.duty = 0,
.hpoint = 0,
};
TEST_ESP_OK(ledc_channel_config(&ledc_ch_config));
ledc_timer_config_t ledc_time_config = {
.speed_mode = test_speed_mode,
.duty_resolution = LEDC_TIMER_13_BIT,
.timer_num = LEDC_TIMER_0,
.freq_hz = 5000,
.clk_cfg = LEDC_USE_APB_CLK,
};
TEST_ESP_OK(ledc_timer_config(&ledc_time_config));
uint32_t size = esp_get_free_heap_size();
uint32_t i;
// install and uninstall for 1000 times to test whether memory leaking exists
for (i = 0; i <= 1000; i++) {
TEST_ESP_OK(ledc_fade_func_install(0));
ledc_fade_func_uninstall();
}
TEST_ASSERT_INT32_WITHIN(100, size, esp_get_free_heap_size());
TEST_ESP_OK(ledc_stop(test_speed_mode, LEDC_CHANNEL_0, 0));
}
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#endif
#endif // SOC_PCNT_SUPPORTED

View File

@ -14,7 +14,6 @@
*/
#include <stdio.h>
#include "esp_system.h"
#include "driver/pcnt.h"
#include "unity.h"
#include "test_utils.h"
#include "freertos/FreeRTOS.h"
@ -25,10 +24,10 @@
#include "soc/rtc.h"
#include "soc/soc_caps.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if SOC_MCPWM_SUPPORTED
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#include "soc/mcpwm_periph.h"
#include "driver/pcnt.h"
#include "driver/mcpwm.h"
@ -788,6 +787,5 @@ TEST_CASE("MCPWM unit1, timer2 capture test", "[mcpwm][test_env=UT_T1_MCPWM][tim
capture_test(MCPWM_UNIT_1, MCPWM_TIMER_2, MCPWM_POS_EDGE);
}
#endif
#endif
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#endif // SOC_MCPWM_SUPPORTED

View File

@ -1,5 +1,4 @@
// RMT driver unit test is based on extended NEC protocol
// Please don't use channel number: SOC_RMT_CHANNELS_NUM - 1
#include <stdio.h>
#include <string.h>
#include "sdkconfig.h"
@ -16,7 +15,7 @@
#define RMT_TX_CHANNEL_ENCODING_END (SOC_RMT_TX_CHANNELS_NUM-1)
// CI ONLY: Don't connect any other signals to this GPIO
#define RMT_DATA_IO (12) // bind signal RMT_SIG_OUT0_IDX and RMT_SIG_IN0_IDX on the same GPIO
#define RMT_DATA_IO (4) // bind signal RMT_SIG_OUT0_IDX and RMT_SIG_IN0_IDX on the same GPIO
#define RMT_TESTBENCH_FLAGS_ALWAYS_ON (1<<0)
#define RMT_TESTBENCH_FLAGS_CARRIER_ON (1<<1)
@ -103,7 +102,7 @@ static void rmt_clean_testbench(int tx_channel, int rx_channel)
}
}
TEST_CASE("RMT wrong configuration", "[rmt][error]")
TEST_CASE("RMT wrong configuration", "[rmt]")
{
rmt_config_t correct_config = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, 0);
rmt_config_t wrong_config = correct_config;
@ -179,25 +178,30 @@ TEST_CASE("RMT miscellaneous functions", "[rmt]")
TEST_CASE("RMT multiple channels", "[rmt]")
{
rmt_config_t tx_cfg1 = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, 0);
rmt_config_t tx_cfg = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, 0);
for (int i = 0; i < SOC_RMT_TX_CHANNELS_NUM; i++) {
tx_cfg.channel = i;
TEST_ESP_OK(rmt_config(&tx_cfg));
TEST_ESP_OK(rmt_driver_install(tx_cfg.channel, 0, 0));
}
TEST_ESP_OK(rmt_config(&tx_cfg1));
TEST_ESP_OK(rmt_driver_install(tx_cfg1.channel, 0, 0));
for (int i = 0; i < SOC_RMT_TX_CHANNELS_NUM; i++) {
TEST_ESP_OK(rmt_driver_uninstall(i));
}
rmt_config_t tx_cfg2 = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, 1);
TEST_ESP_OK(rmt_config(&tx_cfg2));
TEST_ESP_OK(rmt_driver_install(tx_cfg2.channel, 0, 0));
rmt_config_t rx_cfg = RMT_DEFAULT_CONFIG_RX(RMT_DATA_IO, RMT_RX_CHANNEL_ENCODING_START);
for (int i = RMT_RX_CHANNEL_ENCODING_START; i < SOC_RMT_CHANNELS_NUM; i++) {
rx_cfg.channel = i;
TEST_ESP_OK(rmt_config(&rx_cfg));
TEST_ESP_OK(rmt_driver_install(rx_cfg.channel, 0, 0));
}
rmt_config_t tx_cfg3 = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, 2);
TEST_ESP_OK(rmt_config(&tx_cfg3));
TEST_ESP_OK(rmt_driver_install(tx_cfg3.channel, 0, 0));
TEST_ESP_OK(rmt_driver_uninstall(2));
TEST_ESP_OK(rmt_driver_uninstall(1));
TEST_ESP_OK(rmt_driver_uninstall(0));
for (int i = RMT_RX_CHANNEL_ENCODING_START; i < SOC_RMT_CHANNELS_NUM; i++) {
TEST_ESP_OK(rmt_driver_uninstall(i));
}
}
TEST_CASE("RMT install/uninstall test", "[rmt][pressure]")
TEST_CASE("RMT install/uninstall test", "[rmt]")
{
rmt_config_t tx_cfg = RMT_DEFAULT_CONFIG_TX(RMT_DATA_IO, RMT_TX_CHANNEL_ENCODING_END);
TEST_ESP_OK(rmt_config(&tx_cfg));
@ -449,8 +453,8 @@ TEST_CASE("RMT TX simultaneously", "[rmt]")
frames[i].level1 = 0;
frames[i].duration1 = 0;
rmt_config_t tx_config0 = RMT_DEFAULT_CONFIG_TX(12, channel0);
rmt_config_t tx_config1 = RMT_DEFAULT_CONFIG_TX(13, channel1);
rmt_config_t tx_config0 = RMT_DEFAULT_CONFIG_TX(4, channel0);
rmt_config_t tx_config1 = RMT_DEFAULT_CONFIG_TX(5, channel1);
TEST_ESP_OK(rmt_config(&tx_config0));
TEST_ESP_OK(rmt_config(&tx_config1));

View File

@ -9,8 +9,6 @@
#include "esp_log.h"
#include "esp_system.h" // for uint32_t esp_random()
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#define UART_TAG "Uart"
#define UART_NUM1 (UART_NUM_1)
#define BUF_SIZE (100)
@ -31,7 +29,7 @@
// Wait timeout for uart driver
#define PACKET_READ_TICS (1000 / portTICK_RATE_MS)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
//No runners
// The table for fast CRC16 calculation
@ -289,6 +287,4 @@ static void rs485_master(void)
*/
TEST_CASE_MULTIPLE_DEVICES("RS485 half duplex uart multiple devices test.", "[driver_RS485][test_env=UT_T2_RS485]", rs485_master, rs485_slave);
#endif
#endif
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)

View File

@ -16,7 +16,7 @@
#include "esp_log.h"
#include "soc/rtc_io_periph.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
#define RTCIO_CHECK(condition) TEST_ASSERT_MESSAGE((condition == ESP_OK), "ret is not ESP_OK")
#define RTCIO_VERIFY(condition, msg) TEST_ASSERT_MESSAGE((condition), msg)

View File

@ -5,7 +5,7 @@
#include "soc/soc_caps.h"
#include "driver/sigmadelta.h"
TEST_CASE("Sigma-Delta config test", "[sigma_delta]")
TEST_CASE("SigmaDelta config test", "[sigma_delta]")
{
sigmadelta_config_t sigmadelta_cfg = {
.sigmadelta_prescale = 80,

View File

@ -7,7 +7,7 @@
#include "test/test_common_spi.h"
#include "unity.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
#if CONFIG_IDF_TARGET_ESP32
// The VSPI pins on UT_T1_ESP_FLASH are connected to a external flash
@ -345,6 +345,6 @@ TEST_CASE("spi master can be used on SPI1", "[spi]")
//TODO: add a case when a non-polling transaction happened in the bus-acquiring time and then release the bus then queue a new trans
#endif
#endif //!CONFIG_ESP32_SPIRAM_SUPPORT
#endif
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)

View File

@ -264,6 +264,7 @@ TEST_CASE("SPI Master test, interaction of multiple devs", "[spi]") {
TEST_ASSERT(success);
}
#if !DISABLED_FOR_TARGETS(ESP32C3) //There is no input-only pin on esp32c3, so this test could be ignored.
static esp_err_t test_master_pins(int mosi, int miso, int sclk, int cs)
{
esp_err_t ret;
@ -322,6 +323,9 @@ TEST_CASE("spi placed on input-only pins", "[spi]")
TEST_ESP_OK(test_slave_pins(PIN_NUM_MOSI, PIN_NUM_MISO, PIN_NUM_CLK, INPUT_ONLY_PIN));
}
//There is no input-only pin on esp32c3, so this test could be ignored.
#endif //#if !DISABLED_FOR_TARGETS(ESP32C3)
TEST_CASE("spi bus setting with different pin configs", "[spi]")
{
spi_bus_config_t cfg;
@ -366,6 +370,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_SLAVE, &flags_o));
TEST_ASSERT_EQUAL_HEX32( flags_expected, flags_o );
#if !DISABLED_FOR_TARGETS(ESP32C3) //There is no input-only pin on esp32c3, so this test could be ignored.
ESP_LOGI(TAG, "test master 5 output pins and MOSI on input-only pin...");
flags_expected = SPICOMMON_BUSFLAG_SCLK | SPICOMMON_BUSFLAG_MOSI | SPICOMMON_BUSFLAG_MISO | SPICOMMON_BUSFLAG_WPHD | SPICOMMON_BUSFLAG_GPIO_PINS;
cfg = (spi_bus_config_t){.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
@ -394,6 +399,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.max_transfer_sz = 8, .flags = flags_expected};
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_SLAVE, &flags_o));
TEST_ASSERT_EQUAL_HEX32( flags_expected, flags_o );
#endif
ESP_LOGI(TAG, "check native flag for 6 output pins...");
flags_expected = SPICOMMON_BUSFLAG_IOMUX_PINS;
@ -411,6 +417,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_MASTER, &flags_o));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_SLAVE, &flags_o));
#if !DISABLED_FOR_TARGETS(ESP32C3) //There is no input-only pin on esp32c3, so this test could be ignored.
ESP_LOGI(TAG, "check dual flag for master 5 output pins and MISO/MOSI on input-only pin...");
flags_expected = SPICOMMON_BUSFLAG_DUAL | SPICOMMON_BUSFLAG_GPIO_PINS;
cfg = (spi_bus_config_t){.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
@ -432,6 +439,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.max_transfer_sz = 8, .flags = flags_expected};
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_MASTER, &flags_o));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, 0, flags_expected|SPICOMMON_BUSFLAG_SLAVE, &flags_o));
#endif
ESP_LOGI(TAG, "check sclk flag...");
flags_expected = SPICOMMON_BUSFLAG_SCLK;
@ -552,20 +560,23 @@ TEST_CASE("SPI Master DMA test, TX and RX in different regions", "[spi]")
TEST_ASSERT(esp_ptr_in_dram(data_malloc));
#endif
TEST_ASSERT(data_malloc != NULL);
TEST_ASSERT(esp_ptr_in_dram(data_dram));
TEST_ASSERT(esp_ptr_in_drom(data_drom));
ESP_LOGI(TAG, "dram: %p", data_dram);
ESP_LOGI(TAG, "drom: %p, malloc: %p", data_drom, data_malloc);
//refer to soc_memory_layout.c
#ifndef CONFIG_ESP32C3_MEMPROT_FEATURE
uint32_t* data_iram = (uint32_t*)heap_caps_malloc(324, MALLOC_CAP_EXEC);
TEST_ASSERT(data_iram != NULL);
ESP_LOGI(TAG, "iram: %p, dram: %p", data_iram, data_dram);
ESP_LOGI(TAG, "drom: %p, malloc: %p", data_drom, data_malloc);
TEST_ASSERT(esp_ptr_in_dram(data_dram));
TEST_ASSERT(esp_ptr_executable(data_iram) || esp_ptr_in_iram(data_iram) || esp_ptr_in_diram_iram(data_iram));
TEST_ASSERT(esp_ptr_in_drom(data_drom));
ESP_LOGI(TAG, "iram: %p", data_iram);
#endif
srand(52);
for (int i = 0; i < 320/4; i++) {
#ifndef CONFIG_ESP32C3_MEMPROT_FEATURE
data_iram[i] = rand();
#endif
data_dram[i] = rand();
data_malloc[i] = rand();
}
@ -588,10 +599,9 @@ TEST_CASE("SPI Master DMA test, TX and RX in different regions", "[spi]")
#define TEST_REGION_SIZE 5
static spi_transaction_t trans[TEST_REGION_SIZE];
int x;
memset(trans, 0, sizeof(trans));
#ifndef CONFIG_ESP32C3_MEMPROT_FEATURE
trans[0].length = 320*8,
trans[0].tx_buffer = data_iram;
trans[0].rx_buffer = data_malloc+1;
@ -601,12 +611,13 @@ TEST_CASE("SPI Master DMA test, TX and RX in different regions", "[spi]")
trans[1].rx_buffer = data_iram;
trans[2].length = 320*8,
trans[2].tx_buffer = data_malloc+2;
trans[2].rx_buffer = data_dram;
trans[2].tx_buffer = data_drom;
trans[2].rx_buffer = data_iram;
#endif
trans[3].length = 320*8,
trans[3].tx_buffer = data_drom;
trans[3].rx_buffer = data_iram;
trans[3].tx_buffer = data_malloc+2;
trans[3].rx_buffer = data_dram;
trans[4].length = 4*8,
trans[4].flags = SPI_TRANS_USE_RXDATA | SPI_TRANS_USE_TXDATA;
@ -616,7 +627,11 @@ TEST_CASE("SPI Master DMA test, TX and RX in different regions", "[spi]")
*ptr = 0xbc124960;
//Queue all transactions.
#ifndef CONFIG_ESP32C3_MEMPROT_FEATURE
for (x=0; x<TEST_REGION_SIZE; x++) {
#else
for (x=3; x<TEST_REGION_SIZE; x++) {
#endif
ESP_LOGI(TAG, "transmitting %d...", x);
ret=spi_device_transmit(spi,&trans[x]);
TEST_ASSERT(ret==ESP_OK);
@ -629,7 +644,9 @@ TEST_CASE("SPI Master DMA test, TX and RX in different regions", "[spi]")
TEST_ASSERT(spi_bus_remove_device(spi) == ESP_OK);
TEST_ASSERT(spi_bus_free(TEST_SPI_HOST) == ESP_OK);
free(data_malloc);
#ifndef CONFIG_ESP32C3_MEMPROT_FEATURE
free(data_iram);
#endif
}
//this part tests 3 DMA issues in master mode, full-duplex in IDF2.1
@ -707,6 +724,8 @@ TEST_CASE("SPI Master DMA test: length, start, not aligned", "[spi]")
TEST_ASSERT(spi_bus_free(TEST_SPI_HOST) == ESP_OK);
}
#if !DISABLED_FOR_TARGETS(ESP32C3) //There is only one GPSPI controller, so single-board test is disabled.
static uint8_t bitswap(uint8_t in)
{
uint8_t out = 0;
@ -940,6 +959,10 @@ TEST_CASE("SPI master variable dummy test", "[spi]")
master_free_device_bus(spi);
}
//There is only one GPSPI controller, so single-board test is disabled.
#endif //#if !DISABLED_FOR_TARGETS(ESP32C3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32C3)
/********************************************************************************
* Test SPI transaction interval
********************************************************************************/
@ -955,6 +978,8 @@ TEST_CASE("SPI master variable dummy test", "[spi]")
#define GET_US_BY_CCOUNT(t) ((double)t/CONFIG_ESP32S2_DEFAULT_CPU_FREQ_MHZ)
#elif CONFIG_IDF_TARGET_ESP32S3
#define GET_US_BY_CCOUNT(t) ((double)t/CONFIG_ESP32S3_DEFAULT_CPU_FREQ_MHZ)
#elif CONFIG_IDF_TARGET_ESP32C3
#define GET_US_BY_CCOUNT(t) ((double)t/CONFIG_ESP32C3_DEFAULT_CPU_FREQ_MHZ)
#endif
static void speed_setup(spi_device_handle_t* spi, bool use_dma)
@ -1092,4 +1117,6 @@ TEST_CASE("spi_speed","[spi]")
spi_device_release_bus(spi);
master_free_device_bus(spi);
}
#endif
#endif // CONFIG_FREERTOS_CHECK_PORT_CRITICAL_COMPLIANCE
#endif // #if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32C3)

View File

@ -1,10 +1,13 @@
#include "esp_log.h"
#include "esp_attr.h"
#include "soc/spi_periph.h"
#include "sdkconfig.h"
#include "test/test_common_spi.h"
#include "driver/spi_master.h"
#include "driver/spi_slave.h"
#include "esp_log.h"
#include "soc/spi_periph.h"
#include "test/test_common_spi.h"
#include "sdkconfig.h"
#if !DISABLED_FOR_TARGETS(ESP32C3)
//There is only one GPSPI controller on ESP32C3, so single-board test is disabled.
#ifndef MIN
#define MIN(a, b)((a) > (b)? (b): (a))
@ -613,7 +616,7 @@ TEST_CASE("Slave receive correct data", "[spi]")
}
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
//These tests are ESP32 only due to lack of runners
/********************************************************************************
* Test By Master & Slave (2 boards)
@ -1163,4 +1166,6 @@ spitest_param_set_t mode_conf[] = {
};
TEST_SPI_MASTER_SLAVE(MODE, mode_conf, "")
#endif
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32S3, ESP32C3)
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32C3)

View File

@ -24,7 +24,7 @@
#include "hal/spi_ll.h"
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)
/********************************************************************************
* Test SIO
@ -102,7 +102,7 @@ TEST_CASE("local test sio", "[spi]")
master_free_device_bus(spi);
}
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2)
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32C3)
//These tests are ESP32 only due to lack of runners
/********************************************************************************
* Test SIO Master & Slave
@ -220,6 +220,6 @@ void test_sio_slave(void)
}
TEST_CASE_MULTIPLE_DEVICES("sio mode", "[spi][test_env=Example_SPI_Multi_device]", test_sio_master, test_sio_slave);
#endif
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S2, ESP32C3)
#endif
#endif // !TEMPORARY_DISABLED_FOR_TARGETS(ESP32S3, ESP32C3)

View File

@ -3,15 +3,18 @@
*/
#include <string.h>
#include "sdkconfig.h"
#include "unity.h"
#include "test/test_common_spi.h"
#include "driver/spi_master.h"
#include "driver/spi_slave.h"
#include "driver/gpio.h"
#include "esp_log.h"
#include "sdkconfig.h"
#include "test/test_common_spi.h"
#include "esp_rom_gpio.h"
//There is only one GPSPI controller, so single-board test is disabled.
#if !DISABLED_FOR_TARGETS(ESP32C3)
#ifndef CONFIG_SPIRAM
//This test should be removed once the timing test is merged.
@ -142,3 +145,5 @@ TEST_CASE("test slave send unaligned","[spi]")
}
#endif // !CONFIG_SPIRAM
#endif // !TEMPORARY_DISABLED_FOR_TARGETS

View File

@ -6,11 +6,15 @@
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/semphr.h"
#include "unity.h"
#include "soc/spi_periph.h"
#include "driver/spi_master.h"
#include "esp_serial_slave_link/essl_spi.h"
#if !DISABLED_FOR_TARGETS(ESP32C3)
//There is only one GPSPI controller on ESP32C3, so single-board test is disabled.
#if SOC_SPI_SUPPORT_SLAVE_HD_VER2
#include "driver/spi_slave_hd.h"
#include "esp_rom_gpio.h"
@ -490,7 +494,7 @@ TEST_SPI_HD(HD, hd_conf);
*
* This test checks that the previous trans will not influence the data slave prepared for the next transaction.
*/
TEST_CASE("test spi slave hd continuous mode, master too long", "[spi][spi_slv_hd]")
TEST_CASE("test spi slave hd segment mode, master too long", "[spi][spi_slv_hd]")
{
spi_device_handle_t spi;
spitest_param_set_t *cfg = &hd_conf[0];
@ -583,4 +587,6 @@ TEST_CASE("test spi slave hd continuous mode, master too long", "[spi][spi_slv_h
master_free_device_bus(spi);
}
#endif //SOC_SPI_SUPPORT_SLAVE_HD_VER2
#endif //SOC_SPI_SUPPORT_SLAVE_HD_VER2
#endif //#if !DISABLED_FOR_TARGETS(ESP32C3)

View File

@ -30,11 +30,16 @@ typedef struct {
#define TIMER_INFO_INIT(TG, TID) {.timer_group = (TG), .timer_idx = (TID),}
static timer_info_t timer_info[4] = {
static timer_info_t timer_info[] = {
#if !CONFIG_IDF_TARGET_ESP32C3
TIMER_INFO_INIT(TIMER_GROUP_0, TIMER_0),
TIMER_INFO_INIT(TIMER_GROUP_0, TIMER_1),
TIMER_INFO_INIT(TIMER_GROUP_1, TIMER_0),
TIMER_INFO_INIT(TIMER_GROUP_1, TIMER_1),
#else
TIMER_INFO_INIT(TIMER_GROUP_0, TIMER_0),
TIMER_INFO_INIT(TIMER_GROUP_1, TIMER_0),
#endif
};
static intr_handle_t timer_isr_handles[SOC_TIMER_GROUP_TOTAL_TIMERS];
@ -236,6 +241,7 @@ static void timer_intr_enable_and_start(int timer_group, int timer_idx, double a
TEST_ESP_OK(timer_pause(timer_group, timer_idx));
TEST_ESP_OK(timer_set_counter_value(timer_group, timer_idx, 0x0));
TEST_ESP_OK(timer_set_alarm_value(timer_group, timer_idx, alarm_time * TIMER_SCALE));
TEST_ESP_OK(timer_set_alarm(timer_group, timer_idx, TIMER_ALARM_EN));
TEST_ESP_OK(timer_enable_intr(timer_group, timer_idx));
TEST_ESP_OK(timer_start(timer_group, timer_idx));
}
@ -507,8 +513,8 @@ TEST_CASE("Timer divider", "[hw_timer]")
.intr_type = TIMER_INTR_LEVEL
};
uint64_t set_timer_val = 0;
uint64_t time_val[4];
uint64_t comp_time_val[4];
uint64_t time_val[TIMER_GROUP_MAX * TIMER_MAX];
uint64_t comp_time_val[TIMER_GROUP_MAX * TIMER_MAX];
all_timer_init(&config, true);
all_timer_pause();
@ -526,7 +532,7 @@ TEST_CASE("Timer divider", "[hw_timer]")
all_timer_start();
vTaskDelay(1000 / portTICK_PERIOD_MS); //delay the same time
all_timer_get_counter_value(set_timer_val, false, comp_time_val);
for (i = 0; i < 4; i++) {
for (i = 0; i < TIMER_GROUP_MAX * TIMER_MAX; i++) {
TEST_ASSERT_INT_WITHIN(5000, 5000000, time_val[i]);
TEST_ASSERT_INT_WITHIN(10000, 10000000, comp_time_val[i]);
}
@ -538,7 +544,7 @@ TEST_CASE("Timer divider", "[hw_timer]")
all_timer_start();
vTaskDelay(1000 / portTICK_PERIOD_MS); //delay the same time
all_timer_get_counter_value(set_timer_val, false, comp_time_val);
for (i = 0; i < 4; i++) {
for (i = 0; i < TIMER_GROUP_MAX * TIMER_MAX; i++) {
TEST_ASSERT_INT_WITHIN(5000, 5000000, time_val[i]);
TEST_ASSERT_INT_WITHIN(3126, 312500, comp_time_val[i]);
}
@ -550,7 +556,7 @@ TEST_CASE("Timer divider", "[hw_timer]")
all_timer_start();
vTaskDelay(1000 / portTICK_PERIOD_MS);
all_timer_get_counter_value(set_timer_val, false, comp_time_val);
for (i = 0; i < 4; i++) {
for (i = 0; i < TIMER_GROUP_MAX * TIMER_MAX; i++) {
TEST_ASSERT_INT_WITHIN(5000, 5000000, time_val[i]);
TEST_ASSERT_INT_WITHIN(40000, 40000000, comp_time_val[i]);
}
@ -561,7 +567,7 @@ TEST_CASE("Timer divider", "[hw_timer]")
all_timer_start();
vTaskDelay(1000 / portTICK_PERIOD_MS); //delay the same time
all_timer_get_counter_value(set_timer_val, false, comp_time_val);
for (i = 0; i < 4; i++) {
for (i = 0; i < TIMER_GROUP_MAX * TIMER_MAX; i++) {
TEST_ASSERT_INT_WITHIN(5000, 5000000, time_val[i]);
TEST_ASSERT_INT_WITHIN(2, 1220, comp_time_val[i]);
}
@ -604,8 +610,8 @@ TEST_CASE("Timer enable alarm", "[hw_timer]")
// disable alarm of tg0_timer1
alarm_flag = false;
TEST_ESP_OK(timer_set_alarm(TIMER_GROUP_0, TIMER_0, TIMER_ALARM_DIS));
timer_intr_enable_and_start(TIMER_GROUP_0, TIMER_0, 1.2);
TEST_ESP_OK(timer_set_alarm(TIMER_GROUP_0, TIMER_0, TIMER_ALARM_DIS));
vTaskDelay(2000 / portTICK_PERIOD_MS);
TEST_ASSERT_EQUAL(false, alarm_flag);
@ -618,8 +624,8 @@ TEST_CASE("Timer enable alarm", "[hw_timer]")
// disable alarm of tg1_timer0
alarm_flag = false;
TEST_ESP_OK(timer_set_alarm(TIMER_GROUP_1, TIMER_0, TIMER_ALARM_DIS));
timer_intr_enable_and_start(TIMER_GROUP_1, TIMER_0, 1.2);
TEST_ESP_OK(timer_set_alarm(TIMER_GROUP_1, TIMER_0, TIMER_ALARM_DIS));
vTaskDelay(2000 / portTICK_PERIOD_MS);
TEST_ASSERT_EQUAL(false, alarm_flag);
all_timer_isr_unreg();
@ -682,8 +688,13 @@ TEST_CASE("Timer auto reload", "[hw_timer]")
// test disable auto_reload
timer_intr_enable_and_start(TIMER_GROUP_0, TIMER_0, 1.14);
timer_isr_check(TIMER_GROUP_0, TIMER_0, TIMER_AUTORELOAD_DIS, 1.14 * TIMER_SCALE);
timer_intr_enable_and_start(TIMER_GROUP_1, TIMER_0, 1.14);
timer_isr_check(TIMER_GROUP_1, TIMER_0, TIMER_AUTORELOAD_DIS, 1.14 * TIMER_SCALE);
//test enable auto_reload
TEST_ESP_OK(timer_set_auto_reload(TIMER_GROUP_0, TIMER_0, TIMER_AUTORELOAD_EN));
timer_intr_enable_and_start(TIMER_GROUP_0, TIMER_0, 1.4);
timer_isr_check(TIMER_GROUP_0, TIMER_0, TIMER_AUTORELOAD_EN, 0);
TEST_ESP_OK(timer_set_auto_reload(TIMER_GROUP_1, TIMER_0, TIMER_AUTORELOAD_EN));
timer_intr_enable_and_start(TIMER_GROUP_1, TIMER_0, 1.4);
timer_isr_check(TIMER_GROUP_1, TIMER_0, TIMER_AUTORELOAD_EN, 0);

View File

@ -13,8 +13,11 @@
// limitations under the License.
/*
Tests for the touch sensor device driver
Tests for the touch sensor device driver for ESP32
*/
#include "sdkconfig.h"
#if CONFIG_IDF_TARGET_ESP32
#include "esp_system.h"
#include "driver/touch_pad.h"
#include "unity.h"
@ -34,8 +37,6 @@
#include "soc/rtc_io_struct.h"
#include "esp_rom_sys.h"
#if !DISABLED_FOR_TARGETS(ESP8266, ESP32S2, ESP32S3) // This testcase for ESP32
static const char *TAG = "test_touch";
#define TOUCH_READ_INVALID_VAL (0)
@ -374,4 +375,4 @@ TEST_CASE("Touch Sensor interrupt test", "[touch]")
TEST_ESP_OK( test_touch_interrupt() );
}
#endif // !DISABLED_FOR_TARGETS(ESP8266, ESP32)
#endif // CONFIG_IDF_TARGET_ESP32

View File

@ -13,8 +13,11 @@
// limitations under the License.
/*
Tests for the touch sensor device driver
Tests for the touch sensor device driver for ESP32-S2 only
*/
#include "sdkconfig.h"
#if CONFIG_IDF_TARGET_ESP32S2
#include <string.h>
#include "esp_system.h"
#include "driver/touch_pad.h"
@ -38,8 +41,6 @@
#include "driver/rtc_io.h"
#include "esp_rom_sys.h"
#if !DISABLED_FOR_TARGETS(ESP8266, ESP32, ESP32S3) // This testcase for ESP32S2
static const char *TAG = "test_touch";
#define PLATFORM_SELECT (1) //0: pxp; 1: chip
@ -2122,4 +2123,4 @@ void test_touch_slope_debug(int pad_num)
TEST_ESP_OK( touch_pad_deinit() );
}
#endif // !DISABLED_FOR_TARGETS(ESP8266, ESP32)
#endif // CONFIG_IDF_TARGET_ESP32S2

View File

@ -20,7 +20,6 @@
#include "sys/lock.h"
#include "soc/soc_pins.h"
#include "freertos/FreeRTOS.h"
#include "freertos/xtensa_api.h"
#include "freertos/semphr.h"
#include "freertos/timers.h"
#include "esp_intr_alloc.h"
@ -28,7 +27,6 @@
#include "driver/touch_pad.h"
#include "driver/rtc_cntl.h"
#include "driver/gpio.h"
#include "hal/touch_sensor_types.h"
#include "hal/touch_sensor_hal.h"
@ -43,12 +41,12 @@ static const char *TOUCH_TAG = "TOUCH_SENSOR";
#define TOUCH_CHANNEL_CHECK(channel) do { \
TOUCH_CHECK(channel < SOC_TOUCH_SENSOR_NUM && channel >= 0, "Touch channel error", ESP_ERR_INVALID_ARG); \
} while (0);
#elif defined CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3
#else // !CONFIG_IDF_TARGET_ESP32
#define TOUCH_CHANNEL_CHECK(channel) do { \
TOUCH_CHECK(channel < SOC_TOUCH_SENSOR_NUM && channel >= 0, "Touch channel error", ESP_ERR_INVALID_ARG); \
TOUCH_CHECK(channel != SOC_TOUCH_DENOISE_CHANNEL, "TOUCH0 is internal denoise channel", ESP_ERR_INVALID_ARG); \
} while (0);
#endif
#endif // CONFIG_IDF_TARGET_ESP32
#define TOUCH_GET_IO_NUM(channel) (touch_sensor_channel_io_map[channel])
@ -195,7 +193,7 @@ esp_err_t touch_pad_set_thresh(touch_pad_t touch_num, uint16_t threshold)
TOUCH_EXIT_CRITICAL();
return ESP_OK;
}
#elif CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3
#else // !CONFIG_IDF_TARGET_ESP32
esp_err_t touch_pad_set_thresh(touch_pad_t touch_num, uint32_t threshold)
{
TOUCH_CHANNEL_CHECK(touch_num);
@ -206,7 +204,7 @@ esp_err_t touch_pad_set_thresh(touch_pad_t touch_num, uint32_t threshold)
TOUCH_EXIT_CRITICAL();
return ESP_OK;
}
#endif
#endif // CONFIG_IDF_TARGET_ESP32
#ifdef CONFIG_IDF_TARGET_ESP32
esp_err_t touch_pad_get_thresh(touch_pad_t touch_num, uint16_t *threshold)
@ -215,7 +213,7 @@ esp_err_t touch_pad_get_thresh(touch_pad_t touch_num, uint16_t *threshold)
touch_hal_get_threshold(touch_num, threshold);
return ESP_OK;
}
#elif CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3
#else // !CONFIG_IDF_TARGET_ESP32
esp_err_t touch_pad_get_thresh(touch_pad_t touch_num, uint32_t *threshold)
{
TOUCH_CHANNEL_CHECK(touch_num);
@ -224,7 +222,7 @@ esp_err_t touch_pad_get_thresh(touch_pad_t touch_num, uint32_t *threshold)
touch_hal_get_threshold(touch_num, threshold);
return ESP_OK;
}
#endif
#endif // CONFIG_IDF_TARGET_ESP32
esp_err_t touch_pad_get_wakeup_status(touch_pad_t *pad_num)
{

View File

@ -5,8 +5,12 @@ if(${target} STREQUAL "esp32")
list(APPEND requires efuse)
endif()
idf_component_register(SRCS "compare_set.c"
"cpu_util.c"
set(srcs "compare_set.c" "cpu_util.c")
if(NOT BOOTLOADER_BUILD)
list(APPEND srcs "clk_ctrl_os.c")
endif()
idf_component_register(SRCS ${srcs}
INCLUDE_DIRS include
REQUIRES ${requires}
PRIV_REQUIRES efuse

View File

@ -0,0 +1,56 @@
// Copyright 2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include <freertos/FreeRTOS.h>
#include "soc/clk_ctrl_os.h"
#define DELAY_RTC_CLK_SWITCH 5
static portMUX_TYPE periph_spinlock = portMUX_INITIALIZER_UNLOCKED;
static uint8_t s_periph_ref_counts = 0;
static uint32_t s_rtc_clk_freq = 0; // Frequency of the 8M/256 clock in Hz
bool periph_rtc_dig_clk8m_enable(void)
{
portENTER_CRITICAL(&periph_spinlock);
if (s_periph_ref_counts == 0) {
rtc_dig_clk8m_enable();
s_rtc_clk_freq = rtc_clk_freq_cal(rtc_clk_cal(RTC_CAL_8MD256, 100));
if (s_rtc_clk_freq == 0) {
portEXIT_CRITICAL(&periph_spinlock);
return false;
}
}
s_periph_ref_counts++;
portEXIT_CRITICAL(&periph_spinlock);
return true;
}
uint32_t periph_rtc_dig_clk8m_get_freq(void)
{
return s_rtc_clk_freq * 256;
}
void periph_rtc_dig_clk8m_disable(void)
{
portENTER_CRITICAL(&periph_spinlock);
assert(s_periph_ref_counts > 0);
s_periph_ref_counts--;
if (s_periph_ref_counts == 0) {
s_rtc_clk_freq = 0;
rtc_dig_clk8m_disable();
}
portEXIT_CRITICAL(&periph_spinlock);
}

View File

@ -2,3 +2,7 @@ COMPONENT_SRCDIRS := . port/$(IDF_TARGET)
COMPONENT_ADD_INCLUDEDIRS := . include port/$(IDF_TARGET)/private_include
port/$(IDF_TARGET)/rtc_clk.o: CFLAGS += -fno-jump-tables -fno-tree-switch-conversion
ifdef IS_BOOTLOADER_BUILD
COMPONENT_OBJEXCLUDE += clk_ctrl_os.o
endif

View File

@ -0,0 +1,50 @@
// Copyright 2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include "soc/rtc.h"
#ifdef __cplusplus
extern "C" {
#endif
/**
* @brief This function is used to enable the digital 8m rtc clock,
* to support the peripherals.
*
* @note If this function is called a number of times, the `periph_rtc_dig_clk8m_disable`
* function needs to be called same times to disable.
*
* @return true: success for enable the rtc 8M clock, false: rtc 8M clock enable failed
*/
bool periph_rtc_dig_clk8m_enable(void);
/**
* @brief This function is used to disable the rtc digital clock, which should be called
* with the `periph_rtc_dig_clk8m_enable` pairedly
*
* @note If this function is called a number of times, the `periph_rtc_dig_clk8m_disable`
* function needs to be called same times to disable.
*/
void periph_rtc_dig_clk8m_disable(void);
/**
* @brief This function is used to get the real clock frequency value of the rtc clock
*
* @return The real clock value
*/
uint32_t periph_rtc_dig_clk8m_get_freq(void);
#ifdef __cplusplus
}
#endif

View File

@ -101,6 +101,7 @@
#define RTC_PLL_FREQ_320M 320
#define RTC_PLL_FREQ_480M 480
#define DELAY_RTC_CLK_SWITCH 5
static void rtc_clk_cpu_freq_to_8m(void);
static void rtc_clk_bbpll_disable(void);
@ -773,6 +774,18 @@ uint32_t rtc_clk_apb_freq_get(void)
return freq_hz - remainder;
}
void rtc_dig_clk8m_enable(void)
{
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
void rtc_dig_clk8m_disable(void)
{
CLEAR_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
/* Name used in libphy.a:phy_chip_v7.o
* TODO: update the library to use rtc_clk_xtal_freq_get
*/

View File

@ -167,3 +167,11 @@ void rtc_clk_wait_for_slow_cycle(void)
esp_rom_delay_us(1);
}
}
uint32_t rtc_clk_freq_cal(uint32_t cal_val)
{
if (cal_val == 0) {
return 0; // cal_val will be denominator, return 0 as the symbol of failure.
}
return 1000000ULL * (1 << RTC_CLK_CAL_FRACT) / cal_val;
}

View File

@ -0,0 +1,183 @@
// Copyright 2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_bbpll.h
* @brief Register definitions for digital PLL (BBPLL)
*
* This file lists register fields of BBPLL, located on an internal configuration
* bus. These definitions are used via macros defined in regi2c_ctrl.h, by
* rtc_clk_cpu_freq_set function in rtc_clk.c.
*/
#define I2C_BBPLL 0x66
#define I2C_BBPLL_HOSTID 0
#define I2C_BBPLL_IR_CAL_DELAY 0
#define I2C_BBPLL_IR_CAL_DELAY_MSB 3
#define I2C_BBPLL_IR_CAL_DELAY_LSB 0
#define I2C_BBPLL_IR_CAL_CK_DIV 0
#define I2C_BBPLL_IR_CAL_CK_DIV_MSB 7
#define I2C_BBPLL_IR_CAL_CK_DIV_LSB 4
#define I2C_BBPLL_IR_CAL_EXT_CAP 1
#define I2C_BBPLL_IR_CAL_EXT_CAP_MSB 3
#define I2C_BBPLL_IR_CAL_EXT_CAP_LSB 0
#define I2C_BBPLL_IR_CAL_ENX_CAP 1
#define I2C_BBPLL_IR_CAL_ENX_CAP_MSB 4
#define I2C_BBPLL_IR_CAL_ENX_CAP_LSB 4
#define I2C_BBPLL_IR_CAL_RSTB 1
#define I2C_BBPLL_IR_CAL_RSTB_MSB 5
#define I2C_BBPLL_IR_CAL_RSTB_LSB 5
#define I2C_BBPLL_IR_CAL_START 1
#define I2C_BBPLL_IR_CAL_START_MSB 6
#define I2C_BBPLL_IR_CAL_START_LSB 6
#define I2C_BBPLL_IR_CAL_UNSTOP 1
#define I2C_BBPLL_IR_CAL_UNSTOP_MSB 7
#define I2C_BBPLL_IR_CAL_UNSTOP_LSB 7
#define I2C_BBPLL_OC_REF_DIV 2
#define I2C_BBPLL_OC_REF_DIV_MSB 3
#define I2C_BBPLL_OC_REF_DIV_LSB 0
#define I2C_BBPLL_OC_DCHGP 2
#define I2C_BBPLL_OC_DCHGP_MSB 6
#define I2C_BBPLL_OC_DCHGP_LSB 4
#define I2C_BBPLL_OC_ENB_FCAL 2
#define I2C_BBPLL_OC_ENB_FCAL_MSB 7
#define I2C_BBPLL_OC_ENB_FCAL_LSB 7
#define I2C_BBPLL_OC_DIV_7_0 3
#define I2C_BBPLL_OC_DIV_7_0_MSB 7
#define I2C_BBPLL_OC_DIV_7_0_LSB 0
#define I2C_BBPLL_RSTB_DIV_ADC 4
#define I2C_BBPLL_RSTB_DIV_ADC_MSB 0
#define I2C_BBPLL_RSTB_DIV_ADC_LSB 0
#define I2C_BBPLL_MODE_HF 4
#define I2C_BBPLL_MODE_HF_MSB 1
#define I2C_BBPLL_MODE_HF_LSB 1
#define I2C_BBPLL_DIV_ADC 4
#define I2C_BBPLL_DIV_ADC_MSB 3
#define I2C_BBPLL_DIV_ADC_LSB 2
#define I2C_BBPLL_DIV_DAC 4
#define I2C_BBPLL_DIV_DAC_MSB 4
#define I2C_BBPLL_DIV_DAC_LSB 4
#define I2C_BBPLL_DIV_CPU 4
#define I2C_BBPLL_DIV_CPU_MSB 5
#define I2C_BBPLL_DIV_CPU_LSB 5
#define I2C_BBPLL_OC_ENB_VCON 4
#define I2C_BBPLL_OC_ENB_VCON_MSB 6
#define I2C_BBPLL_OC_ENB_VCON_LSB 6
#define I2C_BBPLL_OC_TSCHGP 4
#define I2C_BBPLL_OC_TSCHGP_MSB 7
#define I2C_BBPLL_OC_TSCHGP_LSB 7
#define I2C_BBPLL_OC_DR1 5
#define I2C_BBPLL_OC_DR1_MSB 2
#define I2C_BBPLL_OC_DR1_LSB 0
#define I2C_BBPLL_OC_DR3 5
#define I2C_BBPLL_OC_DR3_MSB 6
#define I2C_BBPLL_OC_DR3_LSB 4
#define I2C_BBPLL_EN_USB 5
#define I2C_BBPLL_EN_USB_MSB 7
#define I2C_BBPLL_EN_USB_LSB 7
#define I2C_BBPLL_OC_DCUR 6
#define I2C_BBPLL_OC_DCUR_MSB 2
#define I2C_BBPLL_OC_DCUR_LSB 0
#define I2C_BBPLL_INC_CUR 6
#define I2C_BBPLL_INC_CUR_MSB 3
#define I2C_BBPLL_INC_CUR_LSB 3
#define I2C_BBPLL_OC_DHREF_SEL 6
#define I2C_BBPLL_OC_DHREF_SEL_MSB 5
#define I2C_BBPLL_OC_DHREF_SEL_LSB 4
#define I2C_BBPLL_OC_DLREF_SEL 6
#define I2C_BBPLL_OC_DLREF_SEL_MSB 7
#define I2C_BBPLL_OC_DLREF_SEL_LSB 6
#define I2C_BBPLL_OR_CAL_CAP 8
#define I2C_BBPLL_OR_CAL_CAP_MSB 3
#define I2C_BBPLL_OR_CAL_CAP_LSB 0
#define I2C_BBPLL_OR_CAL_UDF 8
#define I2C_BBPLL_OR_CAL_UDF_MSB 4
#define I2C_BBPLL_OR_CAL_UDF_LSB 4
#define I2C_BBPLL_OR_CAL_OVF 8
#define I2C_BBPLL_OR_CAL_OVF_MSB 5
#define I2C_BBPLL_OR_CAL_OVF_LSB 5
#define I2C_BBPLL_OR_CAL_END 8
#define I2C_BBPLL_OR_CAL_END_MSB 6
#define I2C_BBPLL_OR_CAL_END_LSB 6
#define I2C_BBPLL_OR_LOCK 8
#define I2C_BBPLL_OR_LOCK_MSB 7
#define I2C_BBPLL_OR_LOCK_LSB 7
#define I2C_BBPLL_OC_VCO_DBIAS 9
#define I2C_BBPLL_OC_VCO_DBIAS_MSB 1
#define I2C_BBPLL_OC_VCO_DBIAS_LSB 0
#define I2C_BBPLL_BBADC_DELAY2 9
#define I2C_BBPLL_BBADC_DELAY2_MSB 3
#define I2C_BBPLL_BBADC_DELAY2_LSB 2
#define I2C_BBPLL_BBADC_DVDD 9
#define I2C_BBPLL_BBADC_DVDD_MSB 5
#define I2C_BBPLL_BBADC_DVDD_LSB 4
#define I2C_BBPLL_BBADC_DREF 9
#define I2C_BBPLL_BBADC_DREF_MSB 7
#define I2C_BBPLL_BBADC_DREF_LSB 6
#define I2C_BBPLL_BBADC_DCUR 10
#define I2C_BBPLL_BBADC_DCUR_MSB 1
#define I2C_BBPLL_BBADC_DCUR_LSB 0
#define I2C_BBPLL_BBADC_INPUT_SHORT 10
#define I2C_BBPLL_BBADC_INPUT_SHORT_MSB 2
#define I2C_BBPLL_BBADC_INPUT_SHORT_LSB 2
#define I2C_BBPLL_ENT_PLL 10
#define I2C_BBPLL_ENT_PLL_MSB 3
#define I2C_BBPLL_ENT_PLL_LSB 3
#define I2C_BBPLL_DTEST 10
#define I2C_BBPLL_DTEST_MSB 5
#define I2C_BBPLL_DTEST_LSB 4
#define I2C_BBPLL_ENT_ADC 10
#define I2C_BBPLL_ENT_ADC_MSB 7
#define I2C_BBPLL_ENT_ADC_LSB 6

View File

@ -0,0 +1,30 @@
// Copyright 2015-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_bias.h
* @brief Register definitions for bias
*
* This file lists register fields of BIAS. These definitions are used via macros defined in regi2c_ctrl.h, by
* bootloader_hardware_init function in bootloader_esp32c3.c.
*/
#define I2C_BIAS 0X6A
#define I2C_BIAS_HOSTID 0
#define I2C_BIAS_DREG_1P1_PVT 1
#define I2C_BIAS_DREG_1P1_PVT_MSB 3
#define I2C_BIAS_DREG_1P1_PVT_LSB 0

View File

@ -0,0 +1,30 @@
// Copyright 2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_brownout.h
* @brief Register definitions for brownout detector
*
* This file lists register fields of the brownout detector, located on an internal configuration
* bus. These definitions are used via macros defined in regi2c_ctrl.h.
*/
#define I2C_BOD 0x61
#define I2C_BOD_HOSTID 1
#define I2C_BOD_THRESHOLD 0x5
#define I2C_BOD_THRESHOLD_MSB 2
#define I2C_BOD_THRESHOLD_LSB 0

View File

@ -0,0 +1,68 @@
// Copyright 2015-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_dig_reg.h
* @brief Register definitions for digital to get rtc voltage & digital voltage
* by setting rtc_dbias_Wak & dig_dbias_wak or by analog self-calibration.
*/
#define I2C_DIG_REG 0x6D
#define I2C_DIG_REG_HOSTID 0
#define I2C_DIG_REG_EXT_RTC_DREG 4
#define I2C_DIG_REG_EXT_RTC_DREG_MSB 4
#define I2C_DIG_REG_EXT_RTC_DREG_LSB 0
#define I2C_DIG_REG_ENX_RTC_DREG 4
#define I2C_DIG_REG_ENX_RTC_DREG_MSB 7
#define I2C_DIG_REG_ENX_RTC_DREG_LSB 7
#define I2C_DIG_REG_EXT_RTC_DREG_SLEEP 5
#define I2C_DIG_REG_EXT_RTC_DREG_SLEEP_MSB 4
#define I2C_DIG_REG_EXT_RTC_DREG_SLEEP_LSB 0
#define I2C_DIG_REG_ENX_RTC_DREG_SLEEP 5
#define I2C_DIG_REG_ENX_RTC_DREG_SLEEP_MSB 7
#define I2C_DIG_REG_ENX_RTC_DREG_SLEEP_LSB 7
#define I2C_DIG_REG_EXT_DIG_DREG 6
#define I2C_DIG_REG_EXT_DIG_DREG_MSB 4
#define I2C_DIG_REG_EXT_DIG_DREG_LSB 0
#define I2C_DIG_REG_ENX_DIG_DREG 6
#define I2C_DIG_REG_ENX_DIG_DREG_MSB 7
#define I2C_DIG_REG_ENX_DIG_DREG_LSB 7
#define I2C_DIG_REG_EXT_DIG_DREG_SLEEP 7
#define I2C_DIG_REG_EXT_DIG_DREG_SLEEP_MSB 4
#define I2C_DIG_REG_EXT_DIG_DREG_SLEEP_LSB 0
#define I2C_DIG_REG_ENX_DIG_DREG_SLEEP 7
#define I2C_DIG_REG_ENX_DIG_DREG_SLEEP_MSB 7
#define I2C_DIG_REG_ENX_DIG_DREG_SLEEP_LSB 7
#define I2C_DIG_REG_OR_EN_CONT_CAL 9
#define I2C_DIG_REG_OR_EN_CONT_CAL_MSB 7
#define I2C_DIG_REG_OR_EN_CONT_CAL_LSB 7
#define I2C_DIG_REG_XPD_RTC_REG 13
#define I2C_DIG_REG_XPD_RTC_REG_MSB 2
#define I2C_DIG_REG_XPD_RTC_REG_LSB 2
#define I2C_DIG_REG_XPD_DIG_REG 13
#define I2C_DIG_REG_XPD_DIG_REG_MSB 3
#define I2C_DIG_REG_XPD_DIG_REG_LSB 3

View File

@ -0,0 +1,43 @@
// Copyright 2015-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_lp_bias.h
* @brief Register definitions for analog to calibrate o_code for getting a more precise voltage.
*
* This file lists register fields of low power dbais, located on an internal configuration
* bus. These definitions are used via macros defined in regi2c_ctrl.h, by
* rtc_init function in rtc_init.c.
*/
#define I2C_ULP 0x61
#define I2C_ULP_HOSTID 0
#define I2C_ULP_IR_RESETB 0
#define I2C_ULP_IR_RESETB_MSB 0
#define I2C_ULP_IR_RESETB_LSB 0
#define I2C_ULP_O_DONE_FLAG 3
#define I2C_ULP_O_DONE_FLAG_MSB 0
#define I2C_ULP_O_DONE_FLAG_LSB 0
#define I2C_ULP_BG_O_DONE_FLAG 3
#define I2C_ULP_BG_O_DONE_FLAG_MSB 3
#define I2C_ULP_BG_O_DONE_FLAG_LSB 3
#define I2C_ULP_IR_FORCE_XPD_IPH 0
#define I2C_ULP_IR_FORCE_XPD_IPH_MSB 4
#define I2C_ULP_IR_FORCE_XPD_IPH_LSB 4

View File

@ -0,0 +1,83 @@
// Copyright 2019-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
/**
* @file regi2c_saradc.h
* @brief Register definitions for analog to calibrate initial code for getting a more precise voltage of SAR ADC.
*
* This file lists register fields of SAR, located on an internal configuration
* bus. These definitions are used via macros defined in regi2c_ctrl.h, by
* function in adc_ll.h.
*/
#define I2C_SAR_ADC 0X69
#define I2C_SAR_ADC_HOSTID 1
#define ADC_SAR1_ENCAL_GND_ADDR 0x7
#define ADC_SAR1_ENCAL_GND_ADDR_MSB 5
#define ADC_SAR1_ENCAL_GND_ADDR_LSB 5
#define ADC_SAR2_ENCAL_GND_ADDR 0x7
#define ADC_SAR2_ENCAL_GND_ADDR_MSB 7
#define ADC_SAR2_ENCAL_GND_ADDR_LSB 7
#define ADC_SAR1_INITIAL_CODE_HIGH_ADDR 0x1
#define ADC_SAR1_INITIAL_CODE_HIGH_ADDR_MSB 0x3
#define ADC_SAR1_INITIAL_CODE_HIGH_ADDR_LSB 0x0
#define ADC_SAR1_INITIAL_CODE_LOW_ADDR 0x0
#define ADC_SAR1_INITIAL_CODE_LOW_ADDR_MSB 0x7
#define ADC_SAR1_INITIAL_CODE_LOW_ADDR_LSB 0x0
#define ADC_SAR2_INITIAL_CODE_HIGH_ADDR 0x4
#define ADC_SAR2_INITIAL_CODE_HIGH_ADDR_MSB 0x3
#define ADC_SAR2_INITIAL_CODE_HIGH_ADDR_LSB 0x0
#define ADC_SAR2_INITIAL_CODE_LOW_ADDR 0x3
#define ADC_SAR2_INITIAL_CODE_LOW_ADDR_MSB 0x7
#define ADC_SAR2_INITIAL_CODE_LOW_ADDR_LSB 0x0
#define ADC_SAR1_DREF_ADDR 0x2
#define ADC_SAR1_DREF_ADDR_MSB 0x6
#define ADC_SAR1_DREF_ADDR_LSB 0x4
#define ADC_SAR2_DREF_ADDR 0x5
#define ADC_SAR2_DREF_ADDR_MSB 0x6
#define ADC_SAR2_DREF_ADDR_LSB 0x4
#define ADC_SAR1_SAMPLE_CYCLE_ADDR 0x2
#define ADC_SAR1_SAMPLE_CYCLE_ADDR_MSB 0x2
#define ADC_SAR1_SAMPLE_CYCLE_ADDR_LSB 0x0
#define ADC_SARADC_DTEST_RTC_ADDR 0x7
#define ADC_SARADC_DTEST_RTC_ADDR_MSB 1
#define ADC_SARADC_DTEST_RTC_ADDR_LSB 0
#define ADC_SARADC_ENT_TSENS_ADDR 0x7
#define ADC_SARADC_ENT_TSENS_ADDR_MSB 2
#define ADC_SARADC_ENT_TSENS_ADDR_LSB 2
#define ADC_SARADC_ENT_RTC_ADDR 0x7
#define ADC_SARADC_ENT_RTC_ADDR_MSB 3
#define ADC_SARADC_ENT_RTC_ADDR_LSB 3
#define ADC_SARADC_ENCAL_REF_ADDR 0x7
#define ADC_SARADC_ENCAL_REF_ADDR_MSB 4
#define ADC_SARADC_ENCAL_REF_ADDR_LSB 4
#define I2C_SARADC_TSENS_DAC 0x6
#define I2C_SARADC_TSENS_DAC_MSB 3
#define I2C_SARADC_TSENS_DAC_LSB 0

View File

@ -0,0 +1,80 @@
// Copyright 2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// Copyright 2015-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
#include <stdint.h>
#include "regi2c_bbpll.h"
#include "regi2c_lp_bias.h"
#include "regi2c_dig_reg.h"
#include "regi2c_bias.h"
#include "regi2c_saradc.h"
#ifdef __cplusplus
extern "C" {
#endif
/* Analog function control register */
#define ANA_CONFIG_REG 0x6000E044
#define ANA_CONFIG_S (8)
#define ANA_CONFIG_M (0x3FF)
/* Clear to enable APLL */
#define I2C_APLL_M (BIT(14))
/* Clear to enable BBPLL */
#define I2C_BBPLL_M (BIT(17))
#define SAR_I2C_FORCE_PD BIT(18)
#define SAR_I2C_FORCE_PU BIT(16)
#define ANA_CONFIG2_REG 0x6000E048
#define ANA_CONFIG2_M (BIT(18))
/* ROM functions which read/write internal control bus */
uint8_t rom_i2c_readReg(uint8_t block, uint8_t host_id, uint8_t reg_add);
uint8_t rom_i2c_readReg_Mask(uint8_t block, uint8_t host_id, uint8_t reg_add, uint8_t msb, uint8_t lsb);
void rom_i2c_writeReg(uint8_t block, uint8_t host_id, uint8_t reg_add, uint8_t data);
void rom_i2c_writeReg_Mask(uint8_t block, uint8_t host_id, uint8_t reg_add, uint8_t msb, uint8_t lsb, uint8_t data);
/* Convenience macros for the above functions, these use register definitions
* from regi2c_bbpll.h/regi2c_dig_reg.h/regi2c_lp_bias.h/regi2c_bias.h header files.
*/
#define REGI2C_WRITE_MASK(block, reg_add, indata) \
rom_i2c_writeReg_Mask(block, block##_HOSTID, reg_add, reg_add##_MSB, reg_add##_LSB, indata)
#define REGI2C_READ_MASK(block, reg_add) \
rom_i2c_readReg_Mask(block, block##_HOSTID, reg_add, reg_add##_MSB, reg_add##_LSB)
#define REGI2C_WRITE(block, reg_add, indata) \
rom_i2c_writeReg(block, block##_HOSTID, reg_add, indata)
#define REGI2C_READ(block, reg_add) \
rom_i2c_readReg(block, block##_HOSTID, reg_add)
#ifdef __cplusplus
}
#endif

View File

@ -37,6 +37,7 @@ static const char *TAG = "rtc_clk";
#define RTC_PLL_FREQ_320M 320
#define RTC_PLL_FREQ_480M 480
#define DELAY_RTC_CLK_SWITCH 5
// Current PLL frequency, in MHZ (320 or 480). Zero if PLL is not enabled.
static int s_cur_pll_freq;
@ -559,6 +560,18 @@ void rtc_clk_8m_divider_set(uint32_t div)
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_CK8M_DIV_SEL_VLD);
}
void rtc_dig_clk8m_enable(void)
{
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
void rtc_dig_clk8m_disable(void)
{
CLEAR_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
/* Name used in libphy.a:phy_chip_v7.o
* TODO: update the library to use rtc_clk_xtal_freq_get
*/

View File

@ -179,3 +179,11 @@ void rtc_clk_wait_for_slow_cycle(void) //This function may not by useful any mor
esp_rom_delay_us(1);
}
}
uint32_t rtc_clk_freq_cal(uint32_t cal_val)
{
if (cal_val == 0) {
return 0; // cal_val will be denominator, return 0 as the symbol of failure.
}
return 1000000ULL * (1 << RTC_CLK_CAL_FRACT) / cal_val;
}

View File

@ -37,6 +37,7 @@ static const char *TAG = "rtc_clk";
#define RTC_PLL_FREQ_320M 320
#define RTC_PLL_FREQ_480M 480
#define DELAY_RTC_CLK_SWITCH 5
// Current PLL frequency, in MHZ (320 or 480). Zero if PLL is not enabled.
// On the ESP32-S2, 480MHz PLL is enabled at reset.
@ -539,6 +540,18 @@ void rtc_clk_8m_divider_set(uint32_t div)
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_CK8M_DIV_SEL_VLD);
}
void rtc_dig_clk8m_enable(void)
{
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
void rtc_dig_clk8m_disable(void)
{
CLEAR_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
/* Name used in libphy.a:phy_chip_v7.o
* TODO: update the library to use rtc_clk_xtal_freq_get
*/

View File

@ -184,3 +184,11 @@ void rtc_clk_wait_for_slow_cycle(void) //This function may not by useful any mor
esp_rom_delay_us(1);
}
}
uint32_t rtc_clk_freq_cal(uint32_t cal_val)
{
if (cal_val == 0) {
return 0; // cal_val will be denominator, return 0 as the symbol of failure.
}
return 1000000ULL * (1 << RTC_CLK_CAL_FRACT) / cal_val;
}

View File

@ -38,6 +38,7 @@ static const char *TAG = "rtc_clk";
#define RTC_PLL_FREQ_320M 320
#define RTC_PLL_FREQ_480M 480
#define DELAY_RTC_CLK_SWITCH 5
// Current PLL frequency, in MHZ (320 or 480). Zero if PLL is not enabled.
static int s_cur_pll_freq = RTC_PLL_FREQ_480M;
@ -556,6 +557,18 @@ void rtc_clk_8m_divider_set(uint32_t div)
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_CK8M_DIV_SEL_VLD);
}
void rtc_dig_clk8m_enable(void)
{
SET_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
void rtc_dig_clk8m_disable(void)
{
CLEAR_PERI_REG_MASK(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN_M);
esp_rom_delay_us(DELAY_RTC_CLK_SWITCH);
}
/* Name used in libphy.a:phy_chip_v7.o
* TODO: update the library to use rtc_clk_xtal_freq_get
*/

View File

@ -178,3 +178,11 @@ void rtc_clk_wait_for_slow_cycle(void) //This function may not by useful any mor
esp_rom_delay_us(1);
}
}
uint32_t rtc_clk_freq_cal(uint32_t cal_val)
{
if (cal_val == 0) {
return 0; // cal_val will be denominator, return 0 as the symbol of failure.
}
return 1000000ULL * (1 << RTC_CLK_CAL_FRACT) / cal_val;
}

View File

@ -1,4 +1,4 @@
// Copyright 2019 Espressif Systems (Shanghai) PTE LTD
// Copyright 2019-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
@ -15,6 +15,11 @@
#include "hal/adc_hal.h"
#include "hal/adc_hal_conf.h"
#if CONFIG_IDF_TARGET_ESP32C3
#include "soc/soc.h"
#include "esp_rom_sys.h"
#endif
void adc_hal_init(void)
{
// Set internal FSM wait time, fixed value.
@ -24,6 +29,7 @@ void adc_hal_init(void)
adc_hal_pwdet_set_cct(SOC_ADC_PWDET_CCT_DEFAULT);
adc_ll_digi_output_invert(ADC_NUM_1, SOC_ADC_DIGI_DATA_INVERT_DEFAULT(ADC_NUM_1));
adc_ll_digi_output_invert(ADC_NUM_2, SOC_ADC_DIGI_DATA_INVERT_DEFAULT(ADC_NUM_2));
adc_ll_digi_set_clk_div(SOC_ADC_DIGI_SAR_CLK_DIV_DEFAULT);
}
void adc_hal_deinit(void)
@ -39,3 +45,189 @@ int adc_hal_convert(adc_ll_num_t adc_n, int channel, int *value)
*value = adc_ll_rtc_get_convert_value(adc_n);
return (int)adc_ll_rtc_analysis_raw_data(adc_n, (uint16_t)(*value));
}
#if CONFIG_IDF_TARGET_ESP32C3
//This feature is currently supported on ESP32C3, will be supported on other chips soon
/*---------------------------------------------------------------
DMA setting
---------------------------------------------------------------*/
void adc_hal_digi_dma_multi_descriptor(adc_dma_hal_config_t *dma_config, uint8_t *data_buf, uint32_t size, uint32_t num)
{
assert(((uint32_t)data_buf % 4) == 0);
assert((size % 4) == 0);
dma_descriptor_t *desc = dma_config->rx_desc;
uint32_t n = 0;
while (num--) {
desc[n].dw0.size = size;
desc[n].dw0.suc_eof = 0;
desc[n].dw0.owner = 1;
desc[n].buffer = data_buf;
desc[n].next = &desc[n+1];
data_buf += size;
n++;
}
desc[n-1].next = NULL;
}
void adc_hal_digi_rxdma_start(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config)
{
gdma_ll_rx_reset_channel(adc_dma_ctx->dev, dma_config->dma_chan);
gdma_ll_rx_set_desc_addr(adc_dma_ctx->dev, dma_config->dma_chan, (uint32_t)dma_config->rx_desc);
gdma_ll_rx_start(adc_dma_ctx->dev, dma_config->dma_chan);
}
void adc_hal_digi_rxdma_stop(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config)
{
gdma_ll_rx_stop(adc_dma_ctx->dev, dma_config->dma_chan);
}
void adc_hal_digi_ena_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask)
{
gdma_ll_enable_interrupt(adc_dma_ctx->dev, dma_config->dma_chan, mask, true);
}
void adc_hal_digi_clr_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask)
{
gdma_ll_clear_interrupt_status(adc_dma_ctx->dev, dma_config->dma_chan, mask);
}
void adc_hal_digi_dis_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask)
{
gdma_ll_enable_interrupt(adc_dma_ctx->dev, dma_config->dma_chan, mask, false);
}
void adc_hal_digi_set_eof_num(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t num)
{
adc_ll_digi_dma_set_eof_num(num);
}
void adc_hal_digi_start(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config)
{
//Set to 1: the ADC data will be sent to the DMA
adc_ll_digi_dma_enable();
//enable sar adc timer
adc_ll_digi_trigger_enable();
}
void adc_hal_digi_stop(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config)
{
//Set to 0: the ADC data won't be sent to the DMA
adc_ll_digi_dma_disable();
//disable sar adc timer
adc_ll_digi_trigger_disable();
}
void adc_hal_digi_init(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config)
{
adc_dma_ctx->dev = &GDMA;
gdma_ll_enable_clock(adc_dma_ctx->dev, true);
gdma_ll_clear_interrupt_status(adc_dma_ctx->dev, dma_config->dma_chan, UINT32_MAX);
gdma_ll_rx_connect_to_periph(adc_dma_ctx->dev, dma_config->dma_chan, GDMA_LL_TRIG_SRC_ADC_DAC);
}
/*---------------------------------------------------------------
Single Read
---------------------------------------------------------------*/
void adc_hal_onetime_start(adc_digi_config_t *adc_digi_config)
{
/**
* There is a hardware limitation. If the APB clock frequency is high, the step of this reg signal: ``onetime_start`` may not be captured by the
* ADC digital controller (when its clock frequency is too slow). A rough estimate for this step should be at least 3 ADC digital controller
* clock cycle.
*
* This limitation will be removed in hardware future versions.
*
*/
uint32_t digi_clk = APB_CLK_FREQ / (adc_digi_config->dig_clk.div_num + adc_digi_config->dig_clk.div_a / adc_digi_config->dig_clk.div_b + 1);
//Convert frequency to time (us). Since decimals are removed by this division operation. Add 1 here in case of the fact that delay is not enough.
uint32_t delay = (1000 * 1000) / digi_clk + 1;
//3 ADC digital controller clock cycle
delay = delay * 3;
//This coefficient (8) is got from test. When digi_clk is not smaller than ``APB_CLK_FREQ/8``, no delay is needed.
if (digi_clk >= APB_CLK_FREQ/8) {
delay = 0;
}
adc_ll_onetime_start(false);
esp_rom_delay_us(delay);
adc_ll_onetime_start(true);
//No need to delay here. Becuase if the start signal is not seen, there won't be a done intr.
}
void adc_hal_adc1_onetime_sample_enable(bool enable)
{
if (enable) {
adc_ll_adc1_onetime_sample_ena();
} else {
adc_ll_adc1_onetime_sample_dis();
}
}
void adc_hal_adc2_onetime_sample_enable(bool enable)
{
if (enable) {
adc_ll_adc2_onetime_sample_ena();
} else {
adc_ll_adc2_onetime_sample_dis();
}
}
void adc_hal_onetime_channel(adc_ll_num_t unit, adc_channel_t channel)
{
adc_ll_onetime_set_channel(unit, channel);
}
void adc_hal_set_onetime_atten(adc_atten_t atten)
{
adc_ll_onetime_set_atten(atten);
}
uint32_t adc_hal_adc1_read(void)
{
return adc_ll_adc1_read();
}
uint32_t adc_hal_adc2_read(void)
{
return adc_ll_adc2_read();
}
//--------------------INTR-------------------------------
static adc_ll_intr_t get_event_intr(adc_event_t event)
{
adc_ll_intr_t intr_mask = 0;
if (event & ADC_EVENT_ADC1_DONE) {
intr_mask |= ADC_LL_INTR_ADC1_DONE;
}
if (event & ADC_EVENT_ADC2_DONE) {
intr_mask |= ADC_LL_INTR_ADC2_DONE;
}
return intr_mask;
}
void adc_hal_intr_enable(adc_event_t event)
{
adc_ll_intr_enable(get_event_intr(event));
}
void adc_hal_intr_disable(adc_event_t event)
{
adc_ll_intr_disable(get_event_intr(event));
}
void adc_hal_intr_clear(adc_event_t event)
{
adc_ll_intr_clear(get_event_intr(event));
}
bool adc_hal_intr_get_raw(adc_event_t event)
{
return adc_ll_intr_get_raw(get_event_intr(event));
}
bool adc_hal_intr_get_status(adc_event_t event)
{
return adc_ll_intr_get_status(get_event_intr(event));
}
#endif

View File

@ -18,12 +18,6 @@
#include "hal/adc_hal_conf.h"
#include "hal/adc_types.h"
void adc_hal_digi_init(void)
{
adc_hal_init();
adc_ll_digi_set_clk_div(SOC_ADC_DIGI_SAR_CLK_DIV_DEFAULT);
}
void adc_hal_digi_deinit(void)
{
adc_ll_digi_clear_pattern_table(ADC_NUM_1);

View File

@ -154,7 +154,7 @@ static inline uint32_t spi_ll_get_running_cmd(spi_dev_t *hw)
}
/**
* Reset SPI CPU FIFO
* Reset SPI CPU TX FIFO
*
* @param hw Beginning address of the peripheral registers.
*/

View File

@ -20,13 +20,6 @@
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
void adc_hal_digi_init(void)
{
adc_hal_init();
adc_ll_digi_set_clk_div(SOC_ADC_DIGI_SAR_CLK_DIV_DEFAULT);
}
void adc_hal_digi_deinit(void)
{
adc_ll_digi_trigger_disable(); // boss
@ -40,37 +33,29 @@ void adc_hal_digi_deinit(void)
adc_hal_deinit();
}
static inline void adc_set_init_code(adc_ll_num_t adc_n, adc_channel_t channel, adc_atten_t atten)
{
uint32_t cal_val = adc_hal_calibration(adc_n, channel, atten, true, false);
adc_hal_set_calibration_param(adc_n, cal_val);
}
void adc_hal_digi_controller_config(const adc_digi_config_t *cfg)
{
//only one pattern table is supported on C3, but LL still needs one argument.
const int pattern_both = 0;
/* If enable digtal controller, adc xpd should always on. */
adc_ll_set_power_manage(ADC_POWER_SW_ON);
/* Single channel mode or multi channel mode. */
adc_ll_digi_set_convert_mode(cfg->conv_mode);
if (cfg->conv_mode & ADC_CONV_SINGLE_UNIT_1) {
if (cfg->adc1_pattern_len) {
adc_ll_digi_clear_pattern_table(ADC_NUM_1);
adc_ll_digi_set_pattern_table_len(ADC_NUM_1, cfg->adc1_pattern_len);
for (int i = 0; i < cfg->adc1_pattern_len; i++) {
adc_ll_digi_set_pattern_table(ADC_NUM_1, i, cfg->adc1_pattern[i]);
}
if (cfg->adc_pattern_len) {
adc_ll_digi_clear_pattern_table(pattern_both);
adc_ll_digi_set_pattern_table_len(pattern_both, cfg->adc_pattern_len);
for (int i = 0; i < cfg->adc_pattern_len; i++) {
adc_ll_digi_set_pattern_table(pattern_both, i, cfg->adc_pattern[i]);
adc_set_init_code(pattern_both, cfg->adc_pattern[i].channel, cfg->adc_pattern[i].atten);
}
}
if (cfg->conv_mode & ADC_CONV_SINGLE_UNIT_2) {
if (cfg->adc2_pattern_len) {
adc_ll_digi_clear_pattern_table(ADC_NUM_2);
adc_ll_digi_set_pattern_table_len(ADC_NUM_2, cfg->adc2_pattern_len);
for (int i = 0; i < cfg->adc2_pattern_len; i++) {
adc_ll_digi_set_pattern_table(ADC_NUM_2, i, cfg->adc2_pattern[i]);
}
}
}
if (cfg->conv_mode & ADC_CONV_SINGLE_UNIT_1) {
adc_ll_set_controller(ADC_NUM_1, ADC_CTRL_DIG);
}
if (cfg->conv_mode & ADC_CONV_SINGLE_UNIT_2) {
adc_ll_set_controller(ADC_NUM_2, ADC_CTRL_DIG);
}
adc_ll_digi_set_output_format(cfg->format);
adc_ll_set_controller(pattern_both, ADC_CTRL_DIG);
if (cfg->conv_limit_en) {
adc_ll_digi_set_convert_limit_num(cfg->conv_limit_num);
adc_ll_digi_convert_limit_enable();
@ -80,7 +65,6 @@ void adc_hal_digi_controller_config(const adc_digi_config_t *cfg)
adc_ll_digi_set_trigger_interval(cfg->interval);
adc_hal_digi_clk_config(&cfg->dig_clk);
adc_ll_digi_dma_set_eof_num(cfg->dma_eof_num);
}
/**
@ -154,27 +138,44 @@ void adc_hal_arbiter_config(adc_arbiter_t *config)
/*---------------------------------------------------------------
ADC calibration setting
---------------------------------------------------------------*/
#define ADC_HAL_CAL_TIMES (10)
#define ADC_HAL_CAL_OFFSET_RANGE (4096)
static uint32_t read_cal_channel(adc_ll_num_t adc_n, int channel)
#define ADC_HAL_CAL_OFFSET_RANGE (4096)
#define ADC_HAL_CAL_TIMES (10)
static uint16_t s_adc_cali_param[ADC_NUM_MAX][ADC_ATTEN_MAX] = { {0}, {0} };
static uint32_t adc_hal_read_self_cal(adc_ll_num_t adc_n, int channel)
{
adc_ll_rtc_start_convert(adc_n, channel);
while (adc_ll_rtc_convert_is_done(adc_n) != true);
return (uint32_t)adc_ll_rtc_get_convert_value(adc_n);
}
uint32_t adc_hal_self_calibration(adc_ll_num_t adc_n, adc_channel_t channel, adc_atten_t atten, bool internal_gnd)
uint32_t adc_hal_calibration(adc_ll_num_t adc_n, adc_channel_t channel, adc_atten_t atten, bool internal_gnd, bool force_cal)
{
adc_hal_set_power_manage(ADC_POWER_SW_ON);
if (!force_cal) {
if (s_adc_cali_param[adc_n][atten]) {
return (uint32_t)s_adc_cali_param[adc_n][atten];
}
}
uint32_t code_list[ADC_HAL_CAL_TIMES] = {0};
uint32_t code_sum = 0;
uint32_t code_h = 0;
uint32_t code_l = 0;
uint32_t chk_code = 0;
uint32_t dout = 0;
adc_hal_set_power_manage(ADC_POWER_SW_ON);
if (adc_n == ADC_NUM_2) {
adc_arbiter_t config = ADC_ARBITER_CONFIG_DEFAULT();
adc_hal_arbiter_config(&config);
}
adc_hal_set_controller(adc_n, ADC_CTRL_RTC); //Set controller
// adc_hal_arbiter_config(adc_arbiter_t *config)
adc_ll_calibration_prepare(adc_n, channel, internal_gnd);
/* Enable/disable internal connect GND (for calibration). */
if (internal_gnd) {
adc_ll_rtc_disable_channel(adc_n, channel);
@ -184,31 +185,25 @@ uint32_t adc_hal_self_calibration(adc_ll_num_t adc_n, adc_channel_t channel, adc
adc_ll_set_atten(adc_n, channel, atten);
}
uint32_t code_list[ADC_HAL_CAL_TIMES] = {0};
uint32_t code_sum = 0;
uint32_t code_h = 0;
uint32_t code_l = 0;
uint32_t chk_code = 0;
for (uint8_t rpt = 0 ; rpt < ADC_HAL_CAL_TIMES ; rpt ++) {
code_h = ADC_HAL_CAL_OFFSET_RANGE;
code_l = 0;
chk_code = (code_h + code_l) / 2;
adc_ll_set_calibration_param(adc_n, chk_code);
uint32_t self_cal = read_cal_channel(adc_n, channel);
dout = adc_hal_read_self_cal(adc_n, channel);
while (code_h - code_l > 1) {
if (self_cal == 0) {
if (dout == 0) {
code_h = chk_code;
} else {
code_l = chk_code;
}
chk_code = (code_h + code_l) / 2;
adc_ll_set_calibration_param(adc_n, chk_code);
self_cal = read_cal_channel(adc_n, channel);
dout = adc_hal_read_self_cal(adc_n, channel);
if ((code_h - code_l == 1)) {
chk_code += 1;
adc_ll_set_calibration_param(adc_n, chk_code);
self_cal = read_cal_channel(adc_n, channel);
dout = adc_hal_read_self_cal(adc_n, channel);
}
}
code_list[rpt] = chk_code;
@ -225,10 +220,12 @@ uint32_t adc_hal_self_calibration(adc_ll_num_t adc_n, adc_channel_t channel, adc
}
}
chk_code = code_h + code_l;
uint32_t ret = ((code_sum - chk_code) % (ADC_HAL_CAL_TIMES - 2) < 4)
dout = ((code_sum - chk_code) % (ADC_HAL_CAL_TIMES - 2) < 4)
? (code_sum - chk_code) / (ADC_HAL_CAL_TIMES - 2)
: (code_sum - chk_code) / (ADC_HAL_CAL_TIMES - 2) + 1;
adc_ll_set_calibration_param(adc_n, dout);
adc_ll_calibration_finish(adc_n);
return ret;
s_adc_cali_param[adc_n][atten] = (uint16_t)dout;
return dout;
}

View File

@ -16,8 +16,8 @@
#include "hal/brownout_hal.h"
#include "soc/rtc_cntl_struct.h"
#include "soc/rtc_cntl_reg.h"
#include "i2c_rtc_clk.h"
#include "i2c_brownout.h"
#include "regi2c_ctrl.h"
#include "regi2c_brownout.h"
void brownout_hal_config(const brownout_hal_config_t *cfg)

View File

@ -34,11 +34,6 @@ extern "C" {
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
/**
* Digital controller initialization.
*/
void adc_hal_digi_init(void);
/**
* Digital controller deinitialization.
*/

View File

@ -11,14 +11,9 @@
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#pragma once
#define SOC_ADC_PERIPH_NUM (2)
#define SOC_ADC_PATT_LEN_MAX (16)
#define SOC_ADC_CHANNEL_NUM(PERIPH_NUM) (10)
#define SOC_ADC_MAX_CHANNEL_NUM (10)
#define SOC_ADC1_DATA_INVERT_DEFAULT (0)
#define SOC_ADC2_DATA_INVERT_DEFAULT (0)
@ -29,14 +24,6 @@
#define SOC_ADC_FSM_STANDBY_WAIT_DEFAULT (100)
#define ADC_FSM_SAMPLE_CYCLE_DEFAULT (2)
/**
* Check if adc support digital controller (DMA) mode.
* @value
* - 1 : support;
* - 0 : not support;
*/
#define SOC_ADC_SUPPORT_DMA_MODE(PERIPH_NUM) ((PERIPH_NUM==0)? 1: 1)
#define SOC_ADC_PWDET_CCT_DEFAULT (4)
#define SOC_ADC_SAR_CLK_DIV_DEFAULT(PERIPH_NUM) ((PERIPH_NUM==0)? 2 : 1)

File diff suppressed because it is too large Load Diff

View File

@ -28,6 +28,8 @@ extern "C" {
static inline uint32_t periph_ll_get_clk_en_mask(periph_module_t periph)
{
switch (periph) {
case PERIPH_SARADC_MODULE:
return SYSTEM_APB_SARADC_CLK_EN;
case PERIPH_RMT_MODULE:
return SYSTEM_RMT_CLK_EN;
case PERIPH_LEDC_MODULE:
@ -89,6 +91,8 @@ static inline uint32_t periph_ll_get_rst_en_mask(periph_module_t periph, bool en
(void)enable; // unused
switch (periph) {
case PERIPH_SARADC_MODULE:
return SYSTEM_APB_SARADC_RST;
case PERIPH_RMT_MODULE:
return SYSTEM_RMT_RST;
case PERIPH_LEDC_MODULE:

View File

@ -18,7 +18,7 @@
* See readme.md in soc/include/hal/readme.md
******************************************************************************/
// The LL layer for ESP32-S3 GPIO register operations
// The LL layer for ESP32-C3 GPIO register operations
#pragma once
@ -34,6 +34,8 @@ extern "C" {
// Get GPIO hardware instance with giving gpio num
#define GPIO_LL_GET_HW(num) (((num) == 0) ? (&GPIO) : NULL)
#define GPIO_LL_PRO_CPU_INTR_ENA (BIT(0))
#define GPIO_LL_PRO_CPU_NMI_INTR_ENA (BIT(1))
/**
* @brief Enable pull-up on GPIO.
*
@ -133,7 +135,7 @@ static inline void gpio_ll_clear_intr_status(gpio_dev_t *hw, uint32_t mask)
*/
static inline void gpio_ll_clear_intr_status_high(gpio_dev_t *hw, uint32_t mask)
{
// hw->status1_w1tc.intr_st = mask;
// Not supported on C3
}
/**
@ -146,7 +148,7 @@ static inline void gpio_ll_clear_intr_status_high(gpio_dev_t *hw, uint32_t mask)
static inline void gpio_ll_intr_enable_on_core(gpio_dev_t *hw, uint32_t core_id, gpio_num_t gpio_num)
{
if (core_id == 0) {
GPIO.pin[gpio_num].int_ena = GPIO_PRO_CPU_INTR_ENA; //enable pro cpu intr
GPIO.pin[gpio_num].int_ena = GPIO_LL_PRO_CPU_INTR_ENA; //enable pro cpu intr
} else {
// GPIO.pin[gpio_num].int_ena = GPIO_APP_CPU_INTR_ENA; //enable pro cpu intr
}
@ -193,12 +195,7 @@ static inline void gpio_ll_input_enable(gpio_dev_t *hw, gpio_num_t gpio_num)
*/
static inline void gpio_ll_output_disable(gpio_dev_t *hw, gpio_num_t gpio_num)
{
if (gpio_num < 32) {
hw->enable_w1tc.enable_w1tc = (0x1 << gpio_num);
} else {
// hw->enable1_w1tc.data = (0x1 << (gpio_num - 32));
}
hw->enable_w1tc.enable_w1tc = (0x1 << gpio_num);
// Ensure no other output signal is routed via GPIO matrix to this pin
REG_WRITE(GPIO_FUNC0_OUT_SEL_CFG_REG + (gpio_num * 4),
SIG_GPIO_OUT_IDX);
@ -212,11 +209,7 @@ static inline void gpio_ll_output_disable(gpio_dev_t *hw, gpio_num_t gpio_num)
*/
static inline void gpio_ll_output_enable(gpio_dev_t *hw, gpio_num_t gpio_num)
{
if (gpio_num < 32) {
hw->enable_w1ts.enable_w1ts = (0x1 << gpio_num);
} else {
// hw->enable1_w1ts.data = (0x1 << (gpio_num - 32));
}
hw->enable_w1ts.enable_w1ts = (0x1 << gpio_num);
}
/**
@ -251,17 +244,9 @@ static inline void gpio_ll_od_enable(gpio_dev_t *hw, gpio_num_t gpio_num)
static inline void gpio_ll_set_level(gpio_dev_t *hw, gpio_num_t gpio_num, uint32_t level)
{
if (level) {
if (gpio_num < 32) {
hw->out_w1ts.out_w1ts = (1 << gpio_num);
} else {
// hw->out1_w1ts.data = (1 << (gpio_num - 32));
}
hw->out_w1ts.out_w1ts = (1 << gpio_num);
} else {
if (gpio_num < 32) {
hw->out_w1tc.out_w1tc = (1 << gpio_num);
} else {
// hw->out1_w1tc.data = (1 << (gpio_num - 32));
}
hw->out_w1tc.out_w1tc = (1 << gpio_num);
}
}
@ -279,11 +264,7 @@ static inline void gpio_ll_set_level(gpio_dev_t *hw, gpio_num_t gpio_num, uint32
*/
static inline int gpio_ll_get_level(gpio_dev_t *hw, gpio_num_t gpio_num)
{
if (gpio_num < 32) {
return (hw->in.data >> gpio_num) & 0x1;
} else {
return 0; // Less than 32 GPIOs in ESP32-C3
}
return (hw->in.data >> gpio_num) & 0x1;
}
/**

View File

@ -0,0 +1,145 @@
// Copyright 2015-2020 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
/*******************************************************************************
* NOTICE
* The ll is not public api, don't use in application code.
* See readme.md in soc/include/hal/readme.md
******************************************************************************/
/* Note: ESP32-C3 does not have a full RTC_IO module, this LL only controls
hold/wakeup/32kHz crystal functions for IOs */
#pragma once
#include <stdlib.h>
#include "soc/rtc_cntl_reg.h"
#include "hal/rtc_io_types.h"
#include "hal/gpio_types.h"
#ifdef __cplusplus
extern "C" {
#endif
typedef enum {
RTCIO_FUNC_RTC = 0x0, /*!< The pin controled by RTC module. */
RTCIO_FUNC_DIGITAL = 0x1, /*!< The pin controlled by DIGITAL module. */
} rtcio_ll_func_t;
typedef enum {
RTCIO_WAKEUP_DISABLE = 0, /*!< Disable GPIO interrupt */
RTCIO_WAKEUP_LOW_LEVEL = 0x4, /*!< GPIO interrupt type : input low level trigger */
RTCIO_WAKEUP_HIGH_LEVEL = 0x5, /*!< GPIO interrupt type : input high level trigger */
} rtcio_ll_wake_type_t;
typedef enum {
RTCIO_OUTPUT_NORMAL = 0, /*!< RTCIO output mode is normal. */
RTCIO_OUTPUT_OD = 0x1, /*!< RTCIO output mode is open-drain. */
} rtcio_ll_out_mode_t;
/**
* @brief Select the rtcio function.
*
* @note The RTC function must be selected before the pad analog function is enabled.
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
* @param func Select pin function.
*/
static inline void rtcio_ll_function_select(int rtcio_num, rtcio_ll_func_t func)
{
abort(); // TODO ESP32-C3 IDF-2407
}
/**
* Enable force hold function for RTC IO pad.
*
* Enabling HOLD function will cause the pad to lock current status, such as,
* input/output enable, input/output value, function, drive strength values.
* This function is useful when going into light or deep sleep mode to prevent
* the pin configuration from changing.
*
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
*/
static inline void rtcio_ll_force_hold_enable(int rtcio_num)
{
abort(); // TODO ESP32-C3 IDF-2407
}
/**
* Disable hold function on an RTC IO pad
*
* @note If disable the pad hold, the status of pad maybe changed in sleep mode.
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
*/
static inline void rtcio_ll_force_hold_disable(int rtcio_num)
{
abort(); // TODO ESP32-C3 IDF-2407
}
/**
* Enable force hold function for RTC IO pad.
*
* Enabling HOLD function will cause the pad to lock current status, such as,
* input/output enable, input/output value, function, drive strength values.
* This function is useful when going into light or deep sleep mode to prevent
* the pin configuration from changing.
*
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
*/
static inline void rtcio_ll_force_hold_all(void)
{
abort(); // TODO ESP32-C3 IDF-2407
}
/**
* Disable hold function on an RTC IO pad
*
* @note If disable the pad hold, the status of pad maybe changed in sleep mode.
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
*/
static inline void rtcio_ll_force_unhold_all(void)
{
CLEAR_PERI_REG_MASK(RTC_CNTL_PWC_REG, RTC_CNTL_PAD_FORCE_HOLD_M);
}
/**
* Enable wakeup function and set wakeup type from light sleep status for rtcio.
*
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
* @param type Wakeup on high level or low level.
*/
static inline void rtcio_ll_wakeup_enable(int rtcio_num, rtcio_ll_wake_type_t type)
{
abort(); // TODO ESP32-C3 IDF-2407
}
/**
* Disable wakeup function from light sleep status for rtcio.
*
* @param rtcio_num The index of rtcio. 0 ~ MAX(rtcio).
*/
static inline void rtcio_ll_wakeup_disable(int rtcio_num)
{
abort(); // TODO ESP32-C3 IDF-2407
}
static inline void rtcio_ll_ext0_set_wakeup_pin(int rtcio_num, int level)
{
abort(); // TODO ESP32-C3 IDF-2106 IDF-2407
}
#ifdef __cplusplus
}
#endif

View File

@ -15,7 +15,6 @@
#include <stdbool.h>
#include "soc/hwcrypto_reg.h"
#include "soc/dport_access.h"
#include "hal/sha_types.h"
#ifdef __cplusplus
@ -127,8 +126,12 @@ static inline void sha_ll_fill_text_block(const void *input_text, size_t block_w
static inline void sha_ll_read_digest(esp_sha_type sha_type, void *digest_state, size_t digest_word_len)
{
uint32_t *digest_state_words = (uint32_t *)digest_state;
const size_t REG_WIDTH = sizeof(uint32_t);
for (size_t i = 0; i < digest_word_len; i++) {
digest_state_words[i] = REG_READ(SHA_H_BASE + (i * REG_WIDTH));
}
esp_dport_access_read_buffer(digest_state_words, SHA_H_BASE, digest_word_len);
}
/**

View File

@ -325,13 +325,7 @@ FORCE_INLINE_ATTR void timer_ll_get_intr_raw_status(timer_group_t group_num, uin
*/
static inline void timer_ll_set_level_int_enable(timg_dev_t *hw, timer_idx_t timer_num, bool level_int_en)
{
switch (timer_num) {
case 0:
hw->int_ena.t0 = level_int_en;
break;
default:
break;
}
// Only "level" interrupts are supported on this target
}
/**
@ -346,15 +340,8 @@ static inline void timer_ll_set_level_int_enable(timg_dev_t *hw, timer_idx_t tim
*/
static inline bool timer_ll_get_level_int_enable(timg_dev_t *hw, timer_idx_t timer_num)
{
bool enable = false;
switch (timer_num) {
case 0:
enable = hw->int_ena.t0;
break;
default:
break;
}
return enable;
// Only "level" interrupts are supported on this target
return true;
}
/**

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
// The HAL layer for ADC (esp32s2 specific part)
// The HAL layer for ADC (ESP32-S2 specific part)
#include "sdkconfig.h"
#include "hal/adc_hal.h"
@ -23,13 +23,6 @@
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
void adc_hal_digi_init(void)
{
adc_hal_init();
adc_ll_digi_set_clk_div(SOC_ADC_DIGI_SAR_CLK_DIV_DEFAULT);
}
void adc_hal_digi_deinit(void)
{
adc_ll_digi_trigger_disable(); // boss

View File

@ -49,7 +49,7 @@ typedef struct {
};
uint16_t val;
};
} adc_rtc_output_data_t;
} adc_ll_rtc_output_data_t;
/**
* @brief ADC controller type selection.
@ -67,7 +67,7 @@ typedef enum {
ADC2_CTRL_FORCE_RTC = 4, /*!<For ADC2. Arbiter in shield mode. Force select RTC controller work. */
ADC2_CTRL_FORCE_ULP = 5, /*!<For ADC2. Arbiter in shield mode. Force select RTC controller work. */
ADC2_CTRL_FORCE_DIG = 6, /*!<For ADC2. Arbiter in shield mode. Force select digital controller work. */
} adc_controller_t;
} adc_ll_controller_t;
/*---------------------------------------------------------------
Digital controller setting
@ -841,7 +841,7 @@ static inline adc_ll_rtc_raw_data_t adc_ll_rtc_analysis_raw_data(adc_ll_num_t ad
if (adc_n == ADC_NUM_1) {
return ADC_RTC_DATA_OK;
}
adc_rtc_output_data_t *temp = (adc_rtc_output_data_t *)&raw_data;
adc_ll_rtc_output_data_t *temp = (adc_ll_rtc_output_data_t *)&raw_data;
if (temp->flag == 0) {
return ADC_RTC_DATA_OK;
} else if (temp->flag == 1) {
@ -980,7 +980,7 @@ static inline adc_atten_t adc_ll_get_atten(adc_ll_num_t adc_n, adc_channel_t cha
* @param adc_n ADC unit.
* @param ctrl ADC controller.
*/
static inline void adc_ll_set_controller(adc_ll_num_t adc_n, adc_controller_t ctrl)
static inline void adc_ll_set_controller(adc_ll_num_t adc_n, adc_ll_controller_t ctrl)
{
if (adc_n == ADC_NUM_1) {
switch ( ctrl ) {

View File

@ -34,11 +34,6 @@ extern "C" {
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
/**
* Digital controller initialization.
*/
void adc_hal_digi_init(void);
/**
* Digital controller deinitialization.
*/

View File

@ -64,7 +64,7 @@ typedef struct {
};
uint16_t val;
};
} adc_rtc_output_data_t;
} adc_ll_rtc_output_data_t;
#ifdef _MSC_VER
#pragma pack(pop)
@ -86,7 +86,7 @@ typedef enum {
ADC2_CTRL_FORCE_RTC = 4, /*!<For ADC2. Arbiter in shield mode. Force select RTC controller work. */
ADC2_CTRL_FORCE_ULP = 5, /*!<For ADC2. Arbiter in shield mode. Force select RTC controller work. */
ADC2_CTRL_FORCE_DIG = 6, /*!<For ADC2. Arbiter in shield mode. Force select digital controller work. */
} adc_controller_t;
} adc_ll_controller_t;
/*---------------------------------------------------------------
Digital controller setting
@ -755,7 +755,7 @@ static inline adc_ll_rtc_raw_data_t adc_ll_rtc_analysis_raw_data(adc_ll_num_t ad
if (adc_n == ADC_NUM_1) {
return ADC_RTC_DATA_OK;
}
adc_rtc_output_data_t *temp = (adc_rtc_output_data_t *)&raw_data;
adc_ll_rtc_output_data_t *temp = (adc_ll_rtc_output_data_t *)&raw_data;
if (temp->flag == 0) {
return ADC_RTC_DATA_OK;
} else if (temp->flag == 1) {
@ -872,7 +872,7 @@ static inline adc_atten_t adc_ll_get_atten(adc_ll_num_t adc_n, adc_channel_t cha
* @param adc_n ADC unit.
* @param ctrl ADC controller.
*/
static inline void adc_ll_set_controller(adc_ll_num_t adc_n, adc_controller_t ctrl)
static inline void adc_ll_set_controller(adc_ll_num_t adc_n, adc_ll_controller_t ctrl)
{
if (adc_n == ADC_NUM_1) {
switch ( ctrl ) {

View File

@ -185,11 +185,6 @@ int adc_hal_convert(adc_ll_num_t adc_n, int channel, int *value);
/*---------------------------------------------------------------
Digital controller setting
---------------------------------------------------------------*/
/**
* Digital controller initialization.
*/
void adc_hal_digi_init(void);
/**
* Digital controller deinitialization.
*/
@ -208,3 +203,74 @@ void adc_hal_digi_controller_config(const adc_digi_config_t *cfg);
* @param adc_n ADC unit.
*/
#define adc_hal_digi_clear_pattern_table(adc_n) adc_ll_digi_clear_pattern_table(adc_n)
#if CONFIG_IDF_TARGET_ESP32C3
/*---------------------------------------------------------------
DMA setting
---------------------------------------------------------------*/
#include "soc/gdma_struct.h"
#include "hal/gdma_ll.h"
#include "hal/dma_types.h"
#include "hal/adc_ll.h"
#include "hal/dma_types.h"
typedef struct adc_dma_hal_context_t {
gdma_dev_t *dev; //address of the general DMA
} adc_dma_hal_context_t;
typedef struct adc_dma_hal_config_t {
dma_descriptor_t *rx_desc; //dma descriptor
dma_descriptor_t *cur_desc_ptr; //pointer to the current descriptor
uint32_t desc_max_num; //number of the descriptors linked once
uint32_t desc_cnt;
uint32_t dma_chan;
} adc_dma_hal_config_t;
void adc_hal_digi_dma_multi_descriptor(adc_dma_hal_config_t *dma_config, uint8_t *data_buf, uint32_t size, uint32_t num);
void adc_hal_digi_rxdma_start(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config);
void adc_hal_digi_rxdma_stop(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config);
void adc_hal_digi_ena_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask);
void adc_hal_digi_clr_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask);
void adc_hal_digi_dis_intr(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t mask);
void adc_hal_digi_set_eof_num(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config, uint32_t num);
void adc_hal_digi_start(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config);
void adc_hal_digi_stop(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config);
void adc_hal_digi_init(adc_dma_hal_context_t *adc_dma_ctx, adc_dma_hal_config_t *dma_config);
/*---------------------------------------------------------------
Single Read
---------------------------------------------------------------*/
void adc_hal_onetime_start(adc_digi_config_t *adc_digi_config);
void adc_hal_adc1_onetime_sample_enable(bool enable);
void adc_hal_adc2_onetime_sample_enable(bool enable);
void adc_hal_onetime_channel(adc_ll_num_t unit, adc_channel_t channel);
void adc_hal_set_onetime_atten(adc_atten_t atten);
uint32_t adc_hal_adc1_read(void);
uint32_t adc_hal_adc2_read(void);
void adc_hal_intr_enable(adc_event_t event);
void adc_hal_intr_disable(adc_event_t event);
void adc_hal_intr_clear(adc_event_t event);
bool adc_hal_intr_get_raw(adc_event_t event);
bool adc_hal_intr_get_status(adc_event_t event);
#endif //#if CONFIG_IDF_TARGET_ESP32C3

View File

@ -81,20 +81,20 @@ typedef enum {
/**
* @brief ADC resolution setting option.
*
* @note For ESP32-S2. Only 13 bit resolution is supported.
* For ESP32. 13 bit resolution is not supported.
*/
typedef enum {
ADC_WIDTH_BIT_9 = 0, /*!< ADC capture width is 9Bit. Only ESP32 is supported. */
ADC_WIDTH_BIT_10 = 1, /*!< ADC capture width is 10Bit. Only ESP32 is supported. */
ADC_WIDTH_BIT_11 = 2, /*!< ADC capture width is 11Bit. Only ESP32 is supported. */
ADC_WIDTH_BIT_12 = 3, /*!< ADC capture width is 12Bit. Only ESP32 is supported. */
#if !CONFIG_IDF_TARGET_ESP32
ADC_WIDTH_BIT_13 = 4, /*!< ADC capture width is 13Bit. Only ESP32-S2 is supported. */
#if CONFIG_IDF_TARGET_ESP32
ADC_WIDTH_BIT_9 = 0, /*!< ADC capture width is 9Bit. */
ADC_WIDTH_BIT_10 = 1, /*!< ADC capture width is 10Bit. */
ADC_WIDTH_BIT_11 = 2, /*!< ADC capture width is 11Bit. */
ADC_WIDTH_BIT_12 = 3, /*!< ADC capture width is 12Bit. */
#elif CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32C3 || CONFIG_IDF_TARGET_ESP32S3
ADC_WIDTH_BIT_13 = 4, /*!< ADC capture width is 13Bit. */
#endif
ADC_WIDTH_MAX,
} adc_bits_width_t;
/**
* @brief ADC digital controller (DMA mode) work mode.
*
@ -123,16 +123,21 @@ typedef struct {
1: measurement range 0 - 1100mV,
2: measurement range 0 - 1350mV,
3: measurement range 0 - 2600mV. */
#ifdef CONFIG_IDF_TARGET_ESP32
#if CONFIG_IDF_TARGET_ESP32
uint8_t bit_width: 2; /*!< ADC resolution.
- 0: 9 bit;
- 1: 10 bit;
- 2: 11 bit;
- 3: 12 bit. */
#else
int8_t channel: 4; /*!< ADC channel index. */
#elif CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3
uint8_t reserved: 2; /*!< reserved0 */
uint8_t channel: 4; /*!< ADC channel index. */
#elif CONFIG_IDF_TARGET_ESP32C3
uint8_t channel: 3; /*!< ADC channel index. */
uint8_t unit: 1; /*!< ADC unit index. */
uint8_t reserved: 2; /*!< reserved0 */
#endif
uint8_t channel: 4; /*!< ADC channel index. */
};
uint8_t val; /*!<Raw data value */
};
@ -149,6 +154,7 @@ typedef enum {
ADC_DIGI_FORMAT_MAX,
} adc_digi_output_format_t;
#if CONFIG_IDF_TARGET_ESP32 || CONFIG_IDF_TARGET_ESP32S2
/**
* @brief ADC digital controller (DMA mode) output data format.
* Used to analyze the acquired ADC (DMA) data.
@ -174,6 +180,26 @@ typedef struct {
uint16_t val; /*!<Raw data value */
};
} adc_digi_output_data_t;
#endif
#if CONFIG_IDF_TARGET_ESP32C3
/**
* @brief ADC digital controller (DMA mode) output data format.
* Used to analyze the acquired ADC (DMA) data.
*/
typedef struct {
union {
struct {
uint32_t data: 13; /*!<ADC real output data info. Resolution: 13 bit. */
uint32_t channel: 3; /*!<ADC channel index info.
If (channel < ADC_CHANNEL_MAX), The data is valid.
If (channel > ADC_CHANNEL_MAX), The data is invalid. */
uint32_t unit: 1; /*!<ADC unit index info. 0: ADC1; 1: ADC2. */
uint32_t reserved: 15;
} type2;
uint32_t val;
};
} adc_digi_output_data_t;
#endif
#if !CONFIG_IDF_TARGET_ESP32
@ -193,7 +219,6 @@ typedef struct {
} adc_digi_clk_t;
#endif //!CONFIG_IDF_TARGET_ESP32
/**
* @brief ADC digital controller (DMA mode) configuration parameters.
*
@ -226,28 +251,36 @@ typedef struct {
* +---------------------+--------+--------+--------+
*/
typedef struct {
bool conv_limit_en; /*!<Enable the function of limiting ADC conversion times.
If the number of ADC conversion trigger count is equal to the `limit_num`, the conversion is stopped. */
uint32_t conv_limit_num; /*!<Set the upper limit of the number of ADC conversion triggers. Range: 1 ~ 255. */
uint32_t adc1_pattern_len; /*!<Pattern table length for digital controller. Range: 0 ~ 16 (0: Don't change the pattern table setting).
The pattern table that defines the conversion rules for each SAR ADC. Each table has 16 items, in which channel selection,
resolution and attenuation are stored. When the conversion is started, the controller reads conversion rules from the
pattern table one by one. For each controller the scan sequence has at most 16 different rules before repeating itself. */
uint32_t adc2_pattern_len; /*!<Refer to ``adc1_pattern_len`` */
bool conv_limit_en; /*!<Enable the function of limiting ADC conversion times.
If the number of ADC conversion trigger count is equal to the `limit_num`, the conversion is stopped. */
uint32_t conv_limit_num; /*!<Set the upper limit of the number of ADC conversion triggers. Range: 1 ~ 255. */
#if CONFIG_IDF_TARGET_ESP32 || CONFIG_IDF_TARGET_ESP32S2
uint32_t adc1_pattern_len; /*!<Pattern table length for digital controller. Range: 0 ~ 16 (0: Don't change the pattern table setting).
The pattern table that defines the conversion rules for each SAR ADC. Each table has 16 items, in which channel selection,
resolution and attenuation are stored. When the conversion is started, the controller reads conversion rules from the
pattern table one by one. For each controller the scan sequence has at most 16 different rules before repeating itself. */
uint32_t adc2_pattern_len; /*!<Refer to ``adc1_pattern_len`` */
adc_digi_pattern_table_t *adc1_pattern; /*!<Pointer to pattern table for digital controller. The table size defined by `adc1_pattern_len`. */
adc_digi_pattern_table_t *adc2_pattern; /*!<Refer to `adc1_pattern` */
adc_digi_convert_mode_t conv_mode; /*!<ADC conversion mode for digital controller. See ``adc_digi_convert_mode_t``. */
adc_digi_output_format_t format; /*!<ADC output data format for digital controller. See ``adc_digi_output_format_t``. */
#elif CONFIG_IDF_TARGET_ESP32C3
uint32_t adc_pattern_len; /*!<Pattern table length for digital controller. Range: 0 ~ 7 (0: Don't change the pattern table setting).
The pattern table that defines the conversion rules for each SAR ADC. Each table has 7 items, in which channel selection,
resolution and attenuation are stored. When the conversion is started, the controller reads conversion rules from the
pattern table one by one. For each controller the scan sequence has at most 16 different rules before repeating itself. */
adc_digi_pattern_table_t *adc_pattern; /*!<Pointer to pattern table for digital controller. The table size defined by `adc_pattern_len`. */
#endif
#if !CONFIG_IDF_TARGET_ESP32
uint32_t interval; /*!<The number of interval clock cycles for the digital controller to trigger the measurement.
The unit is the divided clock. Range: 40 ~ 4095.
Expression: `trigger_meas_freq` = `controller_clk` / 2 / interval. Refer to ``adc_digi_clk_t``.
Note: The sampling rate of each channel is also related to the conversion mode (See ``adc_digi_convert_mode_t``) and pattern table settings. */
adc_digi_clk_t dig_clk; /*!<ADC digital controller clock divider settings. Refer to ``adc_digi_clk_t``.
Note: The clocks of the DAC digital controller use the ADC digital controller clock divider. */
uint32_t dma_eof_num; /*!<DMA eof num of adc digital controller.
If the number of measurements reaches `dma_eof_num`, then `dma_in_suc_eof` signal is generated in DMA.
Note: The converted data in the DMA in link buffer will be multiple of two bytes. */
uint32_t interval; /*!<The number of interval clock cycles for the digital controller to trigger the measurement.
The unit is the divided clock. Range: 40 ~ 4095.
Expression: `trigger_meas_freq` = `controller_clk` / 2 / interval. Refer to ``adc_digi_clk_t``.
Note: The sampling rate of each channel is also related to the conversion mode (See ``adc_digi_convert_mode_t``) and pattern table settings. */
adc_digi_clk_t dig_clk; /*!<ADC digital controller clock divider settings. Refer to ``adc_digi_clk_t``.
Note: The clocks of the DAC digital controller use the ADC digital controller clock divider. */
uint32_t dma_eof_num; /*!<DMA eof num of adc digital controller.
If the number of measurements reaches `dma_eof_num`, then `dma_in_suc_eof` signal is generated in DMA.
Note: The converted data in the DMA in link buffer will be multiple of two bytes. */
#endif
} adc_digi_config_t;
@ -378,3 +411,10 @@ typedef struct {
} adc_digi_monitor_t;
#endif // CONFIG_IDF_TARGET_ESP32S2 || CONFIG_IDF_TARGET_ESP32S3
#if CONFIG_IDF_TARGET_ESP32C3
typedef enum {
ADC_EVENT_ADC1_DONE = BIT(0),
ADC_EVENT_ADC2_DONE = BIT(1),
} adc_event_t;
#endif

View File

@ -26,8 +26,6 @@ typedef enum {
GPIO_PORT_MAX,
} gpio_port_t;
/** @cond */ //Doxy command to hide preprocessor definitions from docs */
#define GPIO_SEL_0 (BIT(0)) /*!< Pin 0 selected */
#define GPIO_SEL_1 (BIT(1)) /*!< Pin 1 selected */
#define GPIO_SEL_2 (BIT(2)) /*!< Pin 2 selected */
@ -108,12 +106,10 @@ typedef enum {
#define GPIO_PIN_REG_25 IO_MUX_GPIO25_REG
#define GPIO_PIN_REG_26 IO_MUX_GPIO26_REG
#define GPIO_PIN_REG_27 IO_MUX_GPIO27_REG
#if CONFIG_IDF_TARGET_ESP32S2
#define GPIO_PIN_REG_28 IO_MUX_GPIO28_REG
#define GPIO_PIN_REG_29 IO_MUX_GPIO29_REG
#define GPIO_PIN_REG_30 IO_MUX_GPIO30_REG
#define GPIO_PIN_REG_31 IO_MUX_GPIO31_REG
#endif
#define GPIO_PIN_REG_32 IO_MUX_GPIO32_REG
#define GPIO_PIN_REG_33 IO_MUX_GPIO33_REG
#define GPIO_PIN_REG_34 IO_MUX_GPIO34_REG
@ -122,7 +118,6 @@ typedef enum {
#define GPIO_PIN_REG_37 IO_MUX_GPIO37_REG
#define GPIO_PIN_REG_38 IO_MUX_GPIO38_REG
#define GPIO_PIN_REG_39 IO_MUX_GPIO39_REG
#if SOC_GPIO_PIN_COUNT > 40
#define GPIO_PIN_REG_40 IO_MUX_GPIO40_REG
#define GPIO_PIN_REG_41 IO_MUX_GPIO41_REG
#define GPIO_PIN_REG_42 IO_MUX_GPIO42_REG
@ -130,10 +125,8 @@ typedef enum {
#define GPIO_PIN_REG_44 IO_MUX_GPIO44_REG
#define GPIO_PIN_REG_45 IO_MUX_GPIO45_REG
#define GPIO_PIN_REG_46 IO_MUX_GPIO46_REG
#endif
/** @endcond */
#if CONFIG_IDF_TARGET_ESP32
typedef enum {
GPIO_NUM_NC = -1, /*!< Use to signal not connected to S/W */
GPIO_NUM_0 = 0, /*!< GPIO0, input and output */
@ -158,14 +151,9 @@ typedef enum {
GPIO_NUM_19 = 19, /*!< GPIO19, input and output */
GPIO_NUM_20 = 20, /*!< GPIO20, input and output */
GPIO_NUM_21 = 21, /*!< GPIO21, input and output */
#if SOC_GPIO_PIN_COUNT > 22
#if CONFIG_IDF_TARGET_ESP32
GPIO_NUM_22 = 22, /*!< GPIO22, input and output */
GPIO_NUM_23 = 23, /*!< GPIO23, input and output */
GPIO_NUM_25 = 25, /*!< GPIO25, input and output */
#endif // CONFIG_IDF_TARGET_ESP32
/* Note: The missing IO is because it is used inside the chip. */
GPIO_NUM_26 = 26, /*!< GPIO26, input and output */
GPIO_NUM_27 = 27, /*!< GPIO27, input and output */
GPIO_NUM_28 = 28, /*!< GPIO28, input and output */
@ -174,14 +162,54 @@ typedef enum {
GPIO_NUM_31 = 31, /*!< GPIO31, input and output */
GPIO_NUM_32 = 32, /*!< GPIO32, input and output */
GPIO_NUM_33 = 33, /*!< GPIO33, input and output */
GPIO_NUM_34 = 34, /*!< GPIO34, input mode only(ESP32) / input and output(ESP32-S2) */
GPIO_NUM_35 = 35, /*!< GPIO35, input mode only(ESP32) / input and output(ESP32-S2) */
GPIO_NUM_36 = 36, /*!< GPIO36, input mode only(ESP32) / input and output(ESP32-S2) */
GPIO_NUM_37 = 37, /*!< GPIO37, input mode only(ESP32) / input and output(ESP32-S2) */
GPIO_NUM_38 = 38, /*!< GPIO38, input mode only(ESP32) / input and output(ESP32-S2) */
GPIO_NUM_39 = 39, /*!< GPIO39, input mode only(ESP32) / input and output(ESP32-S2) */
#endif // SOC_GPIO_PIN_COUNT > 22
#if SOC_GPIO_PIN_COUNT > 40
GPIO_NUM_34 = 34, /*!< GPIO34, input mode only */
GPIO_NUM_35 = 35, /*!< GPIO35, input mode only */
GPIO_NUM_36 = 36, /*!< GPIO36, input mode only */
GPIO_NUM_37 = 37, /*!< GPIO37, input mode only */
GPIO_NUM_38 = 38, /*!< GPIO38, input mode only */
GPIO_NUM_39 = 39, /*!< GPIO39, input mode only */
GPIO_NUM_MAX,
/** @endcond */
} gpio_num_t;
#elif CONFIG_IDF_TARGET_ESP32S2
typedef enum {
GPIO_NUM_NC = -1, /*!< Use to signal not connected to S/W */
GPIO_NUM_0 = 0, /*!< GPIO0, input and output */
GPIO_NUM_1 = 1, /*!< GPIO1, input and output */
GPIO_NUM_2 = 2, /*!< GPIO2, input and output */
GPIO_NUM_3 = 3, /*!< GPIO3, input and output */
GPIO_NUM_4 = 4, /*!< GPIO4, input and output */
GPIO_NUM_5 = 5, /*!< GPIO5, input and output */
GPIO_NUM_6 = 6, /*!< GPIO6, input and output */
GPIO_NUM_7 = 7, /*!< GPIO7, input and output */
GPIO_NUM_8 = 8, /*!< GPIO8, input and output */
GPIO_NUM_9 = 9, /*!< GPIO9, input and output */
GPIO_NUM_10 = 10, /*!< GPIO10, input and output */
GPIO_NUM_11 = 11, /*!< GPIO11, input and output */
GPIO_NUM_12 = 12, /*!< GPIO12, input and output */
GPIO_NUM_13 = 13, /*!< GPIO13, input and output */
GPIO_NUM_14 = 14, /*!< GPIO14, input and output */
GPIO_NUM_15 = 15, /*!< GPIO15, input and output */
GPIO_NUM_16 = 16, /*!< GPIO16, input and output */
GPIO_NUM_17 = 17, /*!< GPIO17, input and output */
GPIO_NUM_18 = 18, /*!< GPIO18, input and output */
GPIO_NUM_19 = 19, /*!< GPIO19, input and output */
GPIO_NUM_20 = 20, /*!< GPIO20, input and output */
GPIO_NUM_21 = 21, /*!< GPIO21, input and output */
GPIO_NUM_26 = 26, /*!< GPIO26, input and output */
GPIO_NUM_27 = 27, /*!< GPIO27, input and output */
GPIO_NUM_28 = 28, /*!< GPIO28, input and output */
GPIO_NUM_29 = 29, /*!< GPIO29, input and output */
GPIO_NUM_30 = 30, /*!< GPIO30, input and output */
GPIO_NUM_31 = 31, /*!< GPIO31, input and output */
GPIO_NUM_32 = 32, /*!< GPIO32, input and output */
GPIO_NUM_33 = 33, /*!< GPIO33, input and output */
GPIO_NUM_34 = 34, /*!< GPIO34, input and output */
GPIO_NUM_35 = 35, /*!< GPIO35, input and output */
GPIO_NUM_36 = 36, /*!< GPIO36, input and output */
GPIO_NUM_37 = 37, /*!< GPIO37, input and output */
GPIO_NUM_38 = 38, /*!< GPIO38, input and output */
GPIO_NUM_39 = 39, /*!< GPIO39, input and output */
GPIO_NUM_40 = 40, /*!< GPIO40, input and output */
GPIO_NUM_41 = 41, /*!< GPIO41, input and output */
GPIO_NUM_42 = 42, /*!< GPIO42, input and output */
@ -189,10 +217,89 @@ typedef enum {
GPIO_NUM_44 = 44, /*!< GPIO44, input and output */
GPIO_NUM_45 = 45, /*!< GPIO45, input and output */
GPIO_NUM_46 = 46, /*!< GPIO46, input mode only */
#endif // GPIO_PIN_COUNT > 40
GPIO_NUM_MAX,
/** @endcond */
} gpio_num_t;
#elif CONFIG_IDF_TARGET_ESP32S3
typedef enum {
GPIO_NUM_NC = -1, /*!< Use to signal not connected to S/W */
GPIO_NUM_0 = 0, /*!< GPIO0, input and output */
GPIO_NUM_1 = 1, /*!< GPIO1, input and output */
GPIO_NUM_2 = 2, /*!< GPIO2, input and output */
GPIO_NUM_3 = 3, /*!< GPIO3, input and output */
GPIO_NUM_4 = 4, /*!< GPIO4, input and output */
GPIO_NUM_5 = 5, /*!< GPIO5, input and output */
GPIO_NUM_6 = 6, /*!< GPIO6, input and output */
GPIO_NUM_7 = 7, /*!< GPIO7, input and output */
GPIO_NUM_8 = 8, /*!< GPIO8, input and output */
GPIO_NUM_9 = 9, /*!< GPIO9, input and output */
GPIO_NUM_10 = 10, /*!< GPIO10, input and output */
GPIO_NUM_11 = 11, /*!< GPIO11, input and output */
GPIO_NUM_12 = 12, /*!< GPIO12, input and output */
GPIO_NUM_13 = 13, /*!< GPIO13, input and output */
GPIO_NUM_14 = 14, /*!< GPIO14, input and output */
GPIO_NUM_15 = 15, /*!< GPIO15, input and output */
GPIO_NUM_16 = 16, /*!< GPIO16, input and output */
GPIO_NUM_17 = 17, /*!< GPIO17, input and output */
GPIO_NUM_18 = 18, /*!< GPIO18, input and output */
GPIO_NUM_19 = 19, /*!< GPIO19, input and output */
GPIO_NUM_20 = 20, /*!< GPIO20, input and output */
GPIO_NUM_21 = 21, /*!< GPIO21, input and output */
GPIO_NUM_26 = 26, /*!< GPIO26, input and output */
GPIO_NUM_27 = 27, /*!< GPIO27, input and output */
GPIO_NUM_28 = 28, /*!< GPIO28, input and output */
GPIO_NUM_29 = 29, /*!< GPIO29, input and output */
GPIO_NUM_30 = 30, /*!< GPIO30, input and output */
GPIO_NUM_31 = 31, /*!< GPIO31, input and output */
GPIO_NUM_32 = 32, /*!< GPIO32, input and output */
GPIO_NUM_33 = 33, /*!< GPIO33, input and output */
GPIO_NUM_34 = 34, /*!< GPIO34, input and output */
GPIO_NUM_35 = 35, /*!< GPIO35, input and output */
GPIO_NUM_36 = 36, /*!< GPIO36, input and output */
GPIO_NUM_37 = 37, /*!< GPIO37, input and output */
GPIO_NUM_38 = 38, /*!< GPIO38, input and output */
GPIO_NUM_39 = 39, /*!< GPIO39, input and output */
GPIO_NUM_40 = 40, /*!< GPIO40, input and output */
GPIO_NUM_41 = 41, /*!< GPIO41, input and output */
GPIO_NUM_42 = 42, /*!< GPIO42, input and output */
GPIO_NUM_43 = 43, /*!< GPIO43, input and output */
GPIO_NUM_44 = 44, /*!< GPIO44, input and output */
GPIO_NUM_45 = 45, /*!< GPIO45, input and output */
GPIO_NUM_46 = 46, /*!< GPIO46, input mode only */
GPIO_NUM_47 = 47, /*!< GPIO47, input and output */
GPIO_NUM_MAX,
/** @endcond */
} gpio_num_t;
#elif CONFIG_IDF_TARGET_ESP32C3
typedef enum {
GPIO_NUM_NC = -1, /*!< Use to signal not connected to S/W */
GPIO_NUM_0 = 0, /*!< GPIO0, input and output */
GPIO_NUM_1 = 1, /*!< GPIO1, input and output */
GPIO_NUM_2 = 2, /*!< GPIO2, input and output */
GPIO_NUM_3 = 3, /*!< GPIO3, input and output */
GPIO_NUM_4 = 4, /*!< GPIO4, input and output */
GPIO_NUM_5 = 5, /*!< GPIO5, input and output */
GPIO_NUM_6 = 6, /*!< GPIO6, input and output */
GPIO_NUM_7 = 7, /*!< GPIO7, input and output */
GPIO_NUM_8 = 8, /*!< GPIO8, input and output */
GPIO_NUM_9 = 9, /*!< GPIO9, input and output */
GPIO_NUM_10 = 10, /*!< GPIO10, input and output */
GPIO_NUM_11 = 11, /*!< GPIO11, input and output */
GPIO_NUM_12 = 12, /*!< GPIO12, input and output */
GPIO_NUM_13 = 13, /*!< GPIO13, input and output */
GPIO_NUM_14 = 14, /*!< GPIO14, input and output */
GPIO_NUM_15 = 15, /*!< GPIO15, input and output */
GPIO_NUM_16 = 16, /*!< GPIO16, input and output */
GPIO_NUM_17 = 17, /*!< GPIO17, input and output */
GPIO_NUM_18 = 18, /*!< GPIO18, input and output */
// TODO: ESP32C3 IDF-2463
GPIO_NUM_20 = 20, /*!< GPIO20, input and output */
GPIO_NUM_21 = 21, /*!< GPIO21, input and output */
GPIO_NUM_22 = 22, /*!< GPIO22, input and output */
GPIO_NUM_MAX,
/** @endcond */
} gpio_num_t;
#endif
typedef enum {
GPIO_INTR_DISABLE = 0, /*!< Disable GPIO interrupt */

View File

@ -60,12 +60,20 @@ inline static size_t state_length(esp_sha_type type)
case SHA2_224:
case SHA2_256:
return SHA256_STATE_LEN_WORDS;
#if SOC_SHA_SUPPORT_SHA384
case SHA2_384:
return SHA512_STATE_LEN_WORDS;
#endif
#if SOC_SHA_SUPPORT_SHA512
case SHA2_512:
return SHA512_STATE_LEN_WORDS;
#endif
#if SOC_SHA_SUPPORT_SHA512_T
case SHA2_512224:
case SHA2_512256:
case SHA2_512T:
return SHA512_STATE_LEN_WORDS;
#endif
default:
return 0;
}

View File

@ -6,6 +6,11 @@
#include "hal/mpu_hal.h"
// TODO ESP32-C3 IDF-2375
// LL still not implemented
#if !TEMPORARY_DISABLED_FOR_TARGETS(ESP32C3)
volatile static int RTC_NOINIT_ATTR access = 0;
static void trigger_illegal_access(void)
@ -41,3 +46,5 @@ void check_access(void)
TEST_CASE_MULTIPLE_STAGES("Can set illegal access regions", "[soc][mpu]",
trigger_illegal_access,
check_access);
#endif //!TEMPORARY_DISABLED_FOR_TARGETS(ESP32C3)

View File

@ -459,6 +459,29 @@ uint64_t rtc_time_get(void);
*/
void rtc_clk_wait_for_slow_cycle(void);
/**
* @brief Enable the rtc digital 8M clock
*
* This function is used to enable the digital rtc 8M clock to support peripherals.
* For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above.
*/
void rtc_dig_clk8m_enable(void);
/**
* @brief Disable the rtc digital 8M clock
*
* This function is used to disable the digital rtc 8M clock, which is only used to support peripherals.
*/
void rtc_dig_clk8m_disable(void);
/**
* @brief Calculate the real clock value after the clock calibration
*
* @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal`
* @return Frequency of the clock in Hz
*/
uint32_t rtc_clk_freq_cal(uint32_t cal_val);
/**
* @brief sleep configuration for rtc_sleep_init function
*/

View File

@ -0,0 +1,26 @@
// Copyright 2010-2016 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _SOC_CLKOUT_CHANNEL_H
#define _SOC_CLKOUT_CHANNEL_H
//CLKOUT channels
#define CLKOUT_GPIO20_DIRECT_CHANNEL CLKOUT_CHANNEL_1
#define CLKOUT_CHANNEL_1_DIRECT_GPIO_NUM 20
#define CLKOUT_GPIO19_DIRECT_CHANNEL CLKOUT_CHANNEL_2
#define CLKOUT_CHANNEL_2_DIRECT_GPIO_NUM 19
#define CLKOUT_GPIO18_DIRECT_CHANNEL CLKOUT_CHANNEL_3
#define CLKOUT_CHANNEL_3_DIRECT_GPIO_NUM 18
#endif

View File

@ -18,23 +18,21 @@
extern "C" {
#endif
// ESP32-C3 has 1 GPIO peripheral
#define SOC_GPIO_PORT (1)
#define SOC_GPIO_PIN_COUNT (22)
// Target has no full RTC IO subsystem, so GPIO is 100% "independent" of RTC
// On ESP32-C3, Digital IOs have their own registers to control pullup/down/capability, independent with RTC registers.
#define GPIO_SUPPORTS_RTC_INDEPENDENT (1)
// Force hold is a new function of ESP32-C3
#define GPIO_SUPPORTS_FORCE_HOLD (1)
#define GPIO_PRO_CPU_INTR_ENA (BIT(0))
#define GPIO_PRO_CPU_NMI_INTR_ENA (BIT(1))
#define GPIO_MODE_DEF_DISABLE (0)
#define GPIO_MODE_DEF_INPUT (BIT0)
#define GPIO_MODE_DEF_OUTPUT (BIT1)
#define GPIO_MODE_DEF_OD (BIT2)
// TODO ESP32-C3 IDF-2119 - check if any IOs are not full featured GPIO
#define SOC_GPIO_VALID_GPIO_MASK ((1U<<SOC_GPIO_PIN_COUNT) - 1)
#define SOC_GPIO_VALID_OUTPUT_GPIO_MASK SOC_GPIO_VALID_GPIO_MASK

View File

@ -13,6 +13,7 @@
// limitations under the License.
#ifndef _SOC_GPIO_STRUCT_H_
#define _SOC_GPIO_STRUCT_H_
#include <stdint.h>
#ifdef __cplusplus
extern "C" {
#endif

View File

@ -45,6 +45,7 @@ typedef enum {
PERIPH_DS_MODULE,
PERIPH_GDMA_MODULE,
PERIPH_SYSTIMER_MODULE,
PERIPH_SARADC_MODULE,
PERIPH_MODULE_MAX
} periph_module_t;

View File

@ -562,6 +562,29 @@ uint64_t rtc_deep_slp_time_get(void);
*/
void rtc_clk_wait_for_slow_cycle(void);
/**
* @brief Enable the rtc digital 8M clock
*
* This function is used to enable the digital rtc 8M clock to support peripherals.
* For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above.
*/
void rtc_dig_clk8m_enable(void);
/**
* @brief Disable the rtc digital 8M clock
*
* This function is used to disable the digital rtc 8M clock, which is only used to support peripherals.
*/
void rtc_dig_clk8m_disable(void);
/**
* @brief Calculate the real clock value after the clock calibration
*
* @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal`
* @return Frequency of the clock in Hz
*/
uint32_t rtc_clk_freq_cal(uint32_t cal_val);
/**
* @brief Power down flags for rtc_sleep_pd function
*/

View File

@ -8,19 +8,22 @@
#define SOC_CPU_CORES_NUM 1
#define SOC_GDMA_SUPPORTED 1
// There are 3 DMA channels on ESP32-C3
// Attention: These fixed DMA channels are temporarily workaround before we have a centralized DMA controller API to help alloc the channel dynamically
// Remove them when GDMA driver API is ready
#define SOC_GDMA_M2M_DMA_CHANNEL (0)
#define SOC_GDMA_SHA_DMA_CHANNEL (1)
#define SOC_GDMA_SPI2_DMA_CHANNEL (2)
#define SOC_GDMA_ADC_DMA_CHANNEL (0)
//NOTE: The CHx number should be consistent with the selected DMA channel above
#define SOC_GDMA_SPI2_INTR_SOURCE ETS_DMA_CH2_INTR_SOURCE
//On C3, there is only 1 GPSPI controller (GPSPI2)
#define SOC_GDMA_SPI3_DMA_CHANNEL SOC_GDMA_SPI2_DMA_CHANNEL
#define SOC_GDMA_ADC_INTR_SOURCE ETS_DMA_CH0_INTR_SOURCE
#include "rmt_caps.h"
#include "adc_caps.h"
#include "dac_caps.h"
#include "i2c_caps.h"
#include "mpu_caps.h"
@ -53,3 +56,18 @@
#define SOC_AES_SUPPORT_AES_128 (1)
#define SOC_AES_SUPPORT_AES_256 (1)
/*-------------------------- ADC CAPS -------------------------------*/
#define SOC_ADC_PERIPH_NUM (2)
#define SOC_ADC_PATT_LEN_MAX (16)
#define SOC_ADC_CHANNEL_NUM(PERIPH_NUM) ((PERIPH_NUM==0)? 5 : 1)
#define SOC_ADC_MAX_CHANNEL_NUM (10)
/**
* Check if adc support digital controller (DMA) mode.
* @value
* - 1 : support;
* - 0 : not support;
*/
#define SOC_ADC_SUPPORT_DMA_MODE(PERIPH_NUM) 1

View File

@ -588,6 +588,29 @@ uint64_t rtc_deep_slp_time_get(void);
*/
void rtc_clk_wait_for_slow_cycle(void);
/**
* @brief Enable the rtc digital 8M clock
*
* This function is used to enable the digital rtc 8M clock to support peripherals.
* For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above.
*/
void rtc_dig_clk8m_enable(void);
/**
* @brief Disable the rtc digital 8M clock
*
* This function is used to disable the digital rtc 8M clock, which is only used to support peripherals.
*/
void rtc_dig_clk8m_disable(void);
/**
* @brief Calculate the real clock value after the clock calibration
*
* @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal`
* @return Frequency of the clock in Hz
*/
uint32_t rtc_clk_freq_cal(uint32_t cal_val);
/**
* @brief Power down flags for rtc_sleep_pd function
*/

View File

@ -27,10 +27,10 @@ extern "C" {
// Force hold is a new function of ESP32-S3
#define SOC_GPIO_SUPPORT_FORCE_HOLD (1)
// 0~47 except from 22~25, 47 are valid
#define SOC_GPIO_VALID_GPIO_MASK (0xFFFFFFFFFFFFULL & ~(0ULL | BIT22 | BIT23 | BIT24 | BIT25 | BIT47))
// GPIO 46, 47 are input only
#define SOC_GPIO_VALID_OUTPUT_GPIO_MASK (SOC_GPIO_VALID_GPIO_MASK & ~(0ULL | BIT46 | BIT47))
// 0~47 except from 22~25 are valid
#define SOC_GPIO_VALID_GPIO_MASK (0xFFFFFFFFFFFFULL & ~(0ULL | BIT22 | BIT23 | BIT24 | BIT25))
// GPIO 46 is input only
#define SOC_GPIO_VALID_OUTPUT_GPIO_MASK (SOC_GPIO_VALID_GPIO_MASK & ~(0ULL | BIT46))
#ifdef __cplusplus

View File

@ -21,5 +21,3 @@
// ESP32-S3 have 1 I2S
#define SOC_I2S_NUM (1)
#define SOC_I2S_SUPPORT_PDM (0) // ESP32-S3 do not support PDM

View File

@ -562,6 +562,29 @@ uint64_t rtc_deep_slp_time_get(void);
*/
void rtc_clk_wait_for_slow_cycle(void);
/**
* @brief Enable the rtc digital 8M clock
*
* This function is used to enable the digital rtc 8M clock to support peripherals.
* For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above.
*/
void rtc_dig_clk8m_enable(void);
/**
* @brief Disable the rtc digital 8M clock
*
* This function is used to disable the digital rtc 8M clock, which is only used to support peripherals.
*/
void rtc_dig_clk8m_disable(void);
/**
* @brief Calculate the real clock value after the clock calibration
*
* @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal`
* @return Frequency of the clock in Hz
*/
uint32_t rtc_clk_freq_cal(uint32_t cal_val);
/**
* @brief Power up flags for rtc_sleep_pd function
*/

View File

@ -359,7 +359,7 @@ component_ut_test_001:
UT_001:
extends: .unit_test_32_template
parallel: 45
parallel: 47
tags:
- ESP32_IDF
- UT_T1_1
@ -506,7 +506,7 @@ UT_034:
UT_035:
extends: .unit_test_s2_template
parallel: 47
parallel: 48
tags:
- ESP32S2_IDF
- UT_T1_1