Merge branch 'refactor/systimer_hal_support_other_xtal' into 'master'

systimer: refactor hal to accomodate more xtal choices

Closes IDF-5643

See merge request espressif/esp-idf!19175
This commit is contained in:
morris
2022-07-25 23:36:49 +08:00
39 changed files with 445 additions and 163 deletions

View File

@@ -40,6 +40,10 @@ if(NOT BOOTLOADER_BUILD)
list(APPEND srcs "esp_async_memcpy.c") list(APPEND srcs "esp_async_memcpy.c")
endif() endif()
if(CONFIG_SOC_SYSTIMER_SUPPORTED)
list(APPEND srcs "port/${target}/systimer.c")
endif()
else() else()
# Requires "_esp_error_check_failed()" function # Requires "_esp_error_check_failed()" function
list(APPEND priv_requires "esp_system") list(APPEND priv_requires "esp_system")

View File

@@ -0,0 +1,33 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#pragma once
#include <stdint.h>
#ifdef __cplusplus
extern "C" {
#endif
/**
* @brief Convert ticks to microseconds
*
* @param ticks ticks to convert
* @return microseconds
*/
uint64_t systimer_ticks_to_us(uint64_t ticks) __attribute__((const));
/**
* @brief Convert microseconds to ticks
*
* @param us microseconds to convert
* @return ticks
*/
uint64_t systimer_us_to_ticks(uint64_t us) __attribute__((const));
#ifdef __cplusplus
}
#endif

View File

@@ -28,3 +28,5 @@ entries:
gdma: gdma_stop (noflash) gdma: gdma_stop (noflash)
gdma: gdma_append (noflash) gdma: gdma_append (noflash)
gdma: gdma_reset (noflash) gdma: gdma_reset (noflash)
if SOC_SYSTIMER_SUPPORTED = y:
systimer (noflash)

View File

@@ -0,0 +1,37 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "sdkconfig.h"
#include "esp_private/systimer.h"
/**
* @brief systimer's clock source is fixed to XTAL (40MHz/26MHz), and has a fixed fractional divider (2.5).
* So the resolution of the systimer is 40MHz/2.5 = 16MHz, or 26MHz/2.5 = 10.4MHz.
*/
#if CONFIG_ESP32C2_XTAL_FREQ_40
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks / 16;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 16;
}
#elif CONFIG_ESP32C2_XTAL_FREQ_26
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks * 5 / 52;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 52 / 5;
}
#else
#error "Unsupported XTAL frequency by systimer"
#endif // CONFIG_ESP32C2_XTAL_FREQ_xx

View File

@@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "esp_private/systimer.h"
/**
* @brief systimer's clock source is fixed to XTAL (40MHz), and has a fixed fractional divider (2.5).
* So the resolution of the systimer is 40MHz/2.5 = 16MHz.
*/
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks / 16;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 16;
}

View File

@@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "esp_private/systimer.h"
/**
* @brief systimer's clock source is fixed to XTAL (40MHz), and has a fixed fractional divider (2.5).
* So the resolution of the systimer is 40MHz/2.5 = 16MHz.
*/
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks / 16;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 16;
}

View File

@@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "esp_private/systimer.h"
/**
* @brief systimer's clock source can be switch between XTAL (40MHz) and APB (80MHz).
* But the resolution of the systimer is configured to fix to 80MHz.
*/
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks / 80;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 80;
}

View File

@@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "esp_private/systimer.h"
/**
* @brief systimer's clock source is fixed to XTAL (40MHz), and has a fixed fractional divider (2.5).
* So the resolution of the systimer is 40MHz/2.5 = 16MHz.
*/
uint64_t systimer_ticks_to_us(uint64_t ticks)
{
return ticks / 16;
}
uint64_t systimer_us_to_ticks(uint64_t us)
{
return us * 16;
}

View File

@@ -28,6 +28,10 @@ if(CONFIG_IDF_TARGET_ARCH_XTENSA)
list(APPEND sources "patches/esp_rom_longjmp.S") list(APPEND sources "patches/esp_rom_longjmp.S")
endif() endif()
if(CONFIG_SOC_SYSTIMER_SUPPORTED)
list(APPEND sources "patches/esp_rom_systimer.c")
endif()
idf_component_register(SRCS ${sources} idf_component_register(SRCS ${sources}
INCLUDE_DIRS ${include_dirs} INCLUDE_DIRS ${include_dirs}
PRIV_REQUIRES ${private_required_comp} PRIV_REQUIRES ${private_required_comp}

View File

@@ -211,20 +211,21 @@ PROVIDE( wdt_hal_handle_intr = 0x40000298 );
PROVIDE( wdt_hal_feed = 0x4000029c ); PROVIDE( wdt_hal_feed = 0x4000029c );
PROVIDE( wdt_hal_set_flashboot_en = 0x400002a0 ); PROVIDE( wdt_hal_set_flashboot_en = 0x400002a0 );
PROVIDE( wdt_hal_is_enabled = 0x400002a4 ); PROVIDE( wdt_hal_is_enabled = 0x400002a4 );
PROVIDE( systimer_hal_init = 0x400002a8 );
PROVIDE( systimer_hal_get_counter_value = 0x400002ac ); PROVIDE( systimer_hal_get_counter_value = 0x400002ac );
PROVIDE( systimer_hal_get_time = 0x400002b0 );
PROVIDE( systimer_hal_set_alarm_target = 0x400002b4 );
PROVIDE( systimer_hal_set_alarm_period = 0x400002b8 );
PROVIDE( systimer_hal_get_alarm_value = 0x400002bc ); PROVIDE( systimer_hal_get_alarm_value = 0x400002bc );
PROVIDE( systimer_hal_enable_alarm_int = 0x400002c0 ); PROVIDE( systimer_hal_enable_alarm_int = 0x400002c0 );
PROVIDE( systimer_hal_on_apb_freq_update = 0x400002c4 );
PROVIDE( systimer_hal_counter_value_advance = 0x400002c8 );
PROVIDE( systimer_hal_enable_counter = 0x400002cc ); PROVIDE( systimer_hal_enable_counter = 0x400002cc );
PROVIDE( systimer_hal_select_alarm_mode = 0x400002d0 ); PROVIDE( systimer_hal_select_alarm_mode = 0x400002d0 );
PROVIDE( systimer_hal_connect_alarm_counter = 0x400002d4 ); PROVIDE( systimer_hal_connect_alarm_counter = 0x400002d4 );
PROVIDE( systimer_hal_counter_can_stall_by_cpu = 0x400002d8 ); PROVIDE( systimer_hal_counter_can_stall_by_cpu = 0x400002d8 );
/* The following ROM functions are commented out because they're patched in the esp_rom_systimer.c */
/* PROVIDE( systimer_hal_init = 0x400002a8 ); */
/* PROVIDE( systimer_hal_get_time = 0x400002b0 ); */
/* PROVIDE( systimer_hal_set_alarm_target = 0x400002b4 ); */
/* PROVIDE( systimer_hal_set_alarm_period = 0x400002b8 ); */
/* PROVIDE( systimer_hal_counter_value_advance = 0x400002c8 ); */
/*************************************** /***************************************
Group heap Group heap

View File

@@ -3,3 +3,5 @@ archive: libesp_rom.a
entries: entries:
esp_rom_spiflash (noflash) esp_rom_spiflash (noflash)
esp_rom_regi2c (noflash) esp_rom_regi2c (noflash)
if SOC_SYSTIMER_SUPPORTED = y:
esp_rom_systimer (noflash)

View File

@@ -0,0 +1,67 @@
/*
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#include "sdkconfig.h"
#include <stddef.h>
#include "hal/systimer_hal.h"
#include "hal/systimer_ll.h"
#if CONFIG_HAL_SYSTIMER_USE_ROM_IMPL
#if CONFIG_IDF_TARGET_ESP32C2
void systimer_hal_init(systimer_hal_context_t *hal)
{
hal->dev = &SYSTIMER;
systimer_ll_enable_clock(hal->dev, true);
}
void systimer_hal_deinit(systimer_hal_context_t *hal)
{
systimer_ll_enable_clock(hal->dev, false);
hal->dev = NULL;
}
void systimer_hal_set_tick_rate_ops(systimer_hal_context_t *hal, systimer_hal_tick_rate_ops_t *ops)
{
hal->ticks_to_us = ops->ticks_to_us;
hal->us_to_ticks = ops->us_to_ticks;
}
uint64_t systimer_hal_get_time(systimer_hal_context_t *hal, uint32_t counter_id)
{
return hal->ticks_to_us(systimer_hal_get_counter_value(hal, counter_id));
}
void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_id, uint64_t target)
{
systimer_counter_value_t alarm = {
.val = hal->us_to_ticks(target),
};
systimer_ll_enable_alarm(hal->dev, alarm_id, false);
systimer_ll_set_alarm_target(hal->dev, alarm_id, alarm.val);
systimer_ll_apply_alarm_value(hal->dev, alarm_id);
systimer_ll_enable_alarm(hal->dev, alarm_id, true);
}
void systimer_hal_set_alarm_period(systimer_hal_context_t *hal, uint32_t alarm_id, uint32_t period)
{
systimer_ll_enable_alarm(hal->dev, alarm_id, false);
systimer_ll_set_alarm_period(hal->dev, alarm_id, hal->us_to_ticks(period));
systimer_ll_apply_alarm_value(hal->dev, alarm_id);
systimer_ll_enable_alarm(hal->dev, alarm_id, true);
}
void systimer_hal_counter_value_advance(systimer_hal_context_t *hal, uint32_t counter_id, int64_t time_us)
{
systimer_counter_value_t new_count = {
.val = systimer_hal_get_counter_value(hal, counter_id) + hal->us_to_ticks(time_us),
};
systimer_ll_set_counter_value(hal->dev, counter_id, new_count.val);
systimer_ll_apply_counter_value(hal->dev, counter_id);
}
#endif // CONFIG_IDF_TARGET_ESP32C2
#endif // CONFIG_HAL_SYSTIMER_USE_ROM_IMPL

View File

@@ -4,7 +4,8 @@
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
*/ */
#include "sys/param.h" #include <sys/param.h>
#include "sdkconfig.h"
#include "esp_timer_impl.h" #include "esp_timer_impl.h"
#include "esp_err.h" #include "esp_err.h"
#include "esp_timer.h" #include "esp_timer.h"
@@ -15,6 +16,8 @@
#include "soc/periph_defs.h" #include "soc/periph_defs.h"
#include "soc/soc_caps.h" #include "soc/soc_caps.h"
#include "esp_private/esp_clk.h" #include "esp_private/esp_clk.h"
#include "esp_private/systimer.h"
#include "esp_private/periph_ctrl.h"
#include "freertos/FreeRTOS.h" #include "freertos/FreeRTOS.h"
#include "hal/systimer_ll.h" #include "hal/systimer_ll.h"
#include "hal/systimer_types.h" #include "hal/systimer_types.h"
@@ -64,7 +67,9 @@ uint64_t IRAM_ATTR esp_timer_impl_get_counter_reg(void)
int64_t IRAM_ATTR esp_timer_impl_get_time(void) int64_t IRAM_ATTR esp_timer_impl_get_time(void)
{ {
return systimer_hal_get_counter_value(&systimer_hal, SYSTIMER_LL_COUNTER_CLOCK) * SYSTIMER_LL_TICKS_PER_US_DIV / SYSTIMER_LL_TICKS_PER_US; // we hope the execution time of this function won't > 1us
// thus, to save one function call, we didn't use the existing `systimer_hal_get_time`
return systimer_hal.ticks_to_us(systimer_hal_get_counter_value(&systimer_hal, SYSTIMER_LL_COUNTER_CLOCK));
} }
int64_t esp_timer_get_time(void) __attribute__((alias("esp_timer_impl_get_time"))); int64_t esp_timer_get_time(void) __attribute__((alias("esp_timer_impl_get_time")));
@@ -96,7 +101,7 @@ static void IRAM_ATTR timer_alarm_isr(void *arg)
void IRAM_ATTR esp_timer_impl_update_apb_freq(uint32_t apb_ticks_per_us) void IRAM_ATTR esp_timer_impl_update_apb_freq(uint32_t apb_ticks_per_us)
{ {
#if !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US #if !SOC_SYSTIMER_FIXED_DIVIDER
systimer_hal_on_apb_freq_update(&systimer_hal, apb_ticks_per_us); systimer_hal_on_apb_freq_update(&systimer_hal, apb_ticks_per_us);
#endif #endif
} }
@@ -105,7 +110,7 @@ void esp_timer_impl_set(uint64_t new_us)
{ {
portENTER_CRITICAL_SAFE(&s_time_update_lock); portENTER_CRITICAL_SAFE(&s_time_update_lock);
systimer_counter_value_t new_count = { systimer_counter_value_t new_count = {
.val = new_us * SYSTIMER_LL_TICKS_PER_US / SYSTIMER_LL_TICKS_PER_US_DIV .val = systimer_hal.us_to_ticks(new_us),
}; };
systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_CLOCK, new_count.val); systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_CLOCK, new_count.val);
systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_CLOCK); systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_CLOCK);
@@ -121,9 +126,15 @@ void esp_timer_impl_advance(int64_t time_diff_us)
esp_err_t esp_timer_impl_early_init(void) esp_err_t esp_timer_impl_early_init(void)
{ {
periph_module_enable(PERIPH_SYSTIMER_MODULE);
systimer_hal_tick_rate_ops_t ops = {
.ticks_to_us = systimer_ticks_to_us,
.us_to_ticks = systimer_us_to_ticks,
};
systimer_hal_init(&systimer_hal); systimer_hal_init(&systimer_hal);
systimer_hal_set_tick_rate_ops(&systimer_hal, &ops);
#if !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US #if !SOC_SYSTIMER_FIXED_DIVIDER
assert(esp_clk_xtal_freq() == (40 * 1000000) && assert(esp_clk_xtal_freq() == (40 * 1000000) &&
"update the step for xtal to support other XTAL:APB frequency ratios"); "update the step for xtal to support other XTAL:APB frequency ratios");
systimer_hal_set_steps_per_tick(&systimer_hal, 0, 2); // for xtal systimer_hal_set_steps_per_tick(&systimer_hal, 0, 2); // for xtal

View File

@@ -15,10 +15,12 @@
#include "riscv/riscv_interrupts.h" #include "riscv/riscv_interrupts.h"
#include "riscv/interrupt.h" #include "riscv/interrupt.h"
#include "esp_private/crosscore_int.h" #include "esp_private/crosscore_int.h"
#include "esp_private/esp_int_wdt.h"
#include "esp_private/periph_ctrl.h"
#include "esp_private/systimer.h"
#include "esp_attr.h" #include "esp_attr.h"
#include "esp_system.h" #include "esp_system.h"
#include "esp_heap_caps_init.h" #include "esp_heap_caps_init.h"
#include "esp_private/esp_int_wdt.h"
#include "esp_task_wdt.h" #include "esp_task_wdt.h"
#include "esp_task.h" #include "esp_task.h"
#include "esp_intr_alloc.h" #include "esp_intr_alloc.h"
@@ -136,7 +138,13 @@ void vPortSetupTimer(void)
ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL)); ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL));
if (cpuid == 0) { if (cpuid == 0) {
periph_module_enable(PERIPH_SYSTIMER_MODULE);
systimer_hal_init(&systimer_hal); systimer_hal_init(&systimer_hal);
systimer_hal_tick_rate_ops_t ops = {
.ticks_to_us = systimer_ticks_to_us,
.us_to_ticks = systimer_us_to_ticks,
};
systimer_hal_set_tick_rate_ops(&systimer_hal, &ops);
systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0); systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0);
systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK); systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK);
@@ -211,7 +219,7 @@ IRAM_ATTR void SysTickIsrHandler(void *arg)
extern void app_main(void); extern void app_main(void);
static void main_task(void* args) static void main_task(void *args)
{ {
#if !CONFIG_FREERTOS_UNICORE #if !CONFIG_FREERTOS_UNICORE
// Wait for FreeRTOS initialization to finish on APP CPU, before replacing its startup stack // Wait for FreeRTOS initialization to finish on APP CPU, before replacing its startup stack
@@ -423,7 +431,7 @@ void *pvPortMalloc( size_t xSize )
return heap_caps_malloc(xSize, FREERTOS_SMP_MALLOC_CAPS); return heap_caps_malloc(xSize, FREERTOS_SMP_MALLOC_CAPS);
} }
void vPortFree( void * pv ) void vPortFree( void *pv )
{ {
heap_caps_free(pv); heap_caps_free(pv);
} }
@@ -599,7 +607,7 @@ StackType_t *pxPortInitialiseStack(StackType_t *pxTopOfStack, TaskFunction_t pxC
// ------- Thread Local Storage Pointers Deletion Callbacks ------- // ------- Thread Local Storage Pointers Deletion Callbacks -------
#if ( CONFIG_FREERTOS_TLSP_DELETION_CALLBACKS ) #if ( CONFIG_FREERTOS_TLSP_DELETION_CALLBACKS )
void vPortTLSPointersDelCb( void * pxTCB ) void vPortTLSPointersDelCb( void *pxTCB )
{ {
/* Typecast pxTCB to StaticTask_t type to access TCB struct members. /* Typecast pxTCB to StaticTask_t type to access TCB struct members.
* pvDummy15 corresponds to pvThreadLocalStoragePointers member of the TCB. * pvDummy15 corresponds to pvThreadLocalStoragePointers member of the TCB.
@@ -612,10 +620,8 @@ void vPortTLSPointersDelCb( void * pxTCB )
/* We need to iterate over half the depth of the pvThreadLocalStoragePointers area /* We need to iterate over half the depth of the pvThreadLocalStoragePointers area
* to access all TLS pointers and their respective TLS deletion callbacks. * to access all TLS pointers and their respective TLS deletion callbacks.
*/ */
for( int x = 0; x < ( configNUM_THREAD_LOCAL_STORAGE_POINTERS / 2 ); x++ ) for ( int x = 0; x < ( configNUM_THREAD_LOCAL_STORAGE_POINTERS / 2 ); x++ ) {
{ if ( pvThreadLocalStoragePointersDelCallback[ x ] != NULL ) { //If del cb is set
if ( pvThreadLocalStoragePointersDelCallback[ x ] != NULL ) //If del cb is set
{
/* In case the TLSP deletion callback has been overwritten by a TLS pointer, gracefully abort. */ /* In case the TLSP deletion callback has been overwritten by a TLS pointer, gracefully abort. */
if ( !esp_ptr_executable( pvThreadLocalStoragePointersDelCallback[ x ] ) ) { if ( !esp_ptr_executable( pvThreadLocalStoragePointersDelCallback[ x ] ) ) {
ESP_LOGE("FreeRTOS", "Fatal error: TLSP deletion callback at index %d overwritten with non-excutable pointer %p", x, pvThreadLocalStoragePointersDelCallback[ x ]); ESP_LOGE("FreeRTOS", "Fatal error: TLSP deletion callback at index %d overwritten with non-excutable pointer %p", x, pvThreadLocalStoragePointersDelCallback[ x ]);
@@ -642,7 +648,7 @@ BaseType_t xPortSysTickHandler(void)
BaseType_t ret = xTaskIncrementTick(); BaseType_t ret = xTaskIncrementTick();
//Manually call the IDF tick hooks //Manually call the IDF tick hooks
esp_vApplicationTickHook(); esp_vApplicationTickHook();
if(ret != pdFALSE) { if (ret != pdFALSE) {
portYIELD_FROM_ISR(); portYIELD_FROM_ISR();
} else { } else {
traceISR_EXIT(); traceISR_EXIT();

View File

@@ -18,6 +18,8 @@
#include "xtensa/config/core-isa.h" #include "xtensa/config/core-isa.h"
#include "xtensa/xtruntime.h" #include "xtensa/xtruntime.h"
#include "esp_private/esp_int_wdt.h" #include "esp_private/esp_int_wdt.h"
#include "esp_private/systimer.h"
#include "esp_private/periph_ctrl.h"
#include "esp_heap_caps.h" #include "esp_heap_caps.h"
#include "esp_system.h" #include "esp_system.h"
#include "esp_task.h" #include "esp_task.h"
@@ -215,7 +217,13 @@ void vPortSetupTimer(void)
ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL)); ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL));
if (cpuid == 0) { if (cpuid == 0) {
periph_module_enable(PERIPH_SYSTIMER_MODULE);
systimer_hal_init(&systimer_hal); systimer_hal_init(&systimer_hal);
systimer_hal_tick_rate_ops_t ops = {
.ticks_to_us = systimer_ticks_to_us,
.us_to_ticks = systimer_us_to_ticks,
};
systimer_hal_set_tick_rate_ops(&systimer_hal, &ops);
systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0); systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0);
systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK); systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK);
@@ -292,7 +300,7 @@ static const char *TAG = "cpu_start";
extern void app_main(void); extern void app_main(void);
static void main_task(void* args) static void main_task(void *args)
{ {
#if !CONFIG_FREERTOS_UNICORE #if !CONFIG_FREERTOS_UNICORE
// Wait for FreeRTOS initialization to finish on APP CPU, before replacing its startup stack // Wait for FreeRTOS initialization to finish on APP CPU, before replacing its startup stack
@@ -487,7 +495,7 @@ void *pvPortMalloc( size_t xSize )
return heap_caps_malloc(xSize, FREERTOS_SMP_MALLOC_CAPS); return heap_caps_malloc(xSize, FREERTOS_SMP_MALLOC_CAPS);
} }
void vPortFree( void * pv ) void vPortFree( void *pv )
{ {
heap_caps_free(pv); heap_caps_free(pv);
} }
@@ -701,9 +709,9 @@ StackType_t * pxPortInitialiseStack( StackType_t * pxTopOfStack,
void _xt_coproc_release(volatile void *coproc_sa_base, BaseType_t xCoreID); void _xt_coproc_release(volatile void *coproc_sa_base, BaseType_t xCoreID);
void vPortCleanUpCoprocArea( void * pxTCB ) void vPortCleanUpCoprocArea( void *pxTCB )
{ {
StackType_t * coproc_area; StackType_t *coproc_area;
BaseType_t xCoreID; BaseType_t xCoreID;
/* Calculate the coproc save area in the stack from the TCB base */ /* Calculate the coproc save area in the stack from the TCB base */
@@ -724,7 +732,7 @@ void vPortCleanUpCoprocArea( void * pxTCB )
// ------- Thread Local Storage Pointers Deletion Callbacks ------- // ------- Thread Local Storage Pointers Deletion Callbacks -------
#if ( CONFIG_FREERTOS_TLSP_DELETION_CALLBACKS ) #if ( CONFIG_FREERTOS_TLSP_DELETION_CALLBACKS )
void vPortTLSPointersDelCb( void * pxTCB ) void vPortTLSPointersDelCb( void *pxTCB )
{ {
/* Typecast pxTCB to StaticTask_t type to access TCB struct members. /* Typecast pxTCB to StaticTask_t type to access TCB struct members.
* pvDummy15 corresponds to pvThreadLocalStoragePointers member of the TCB. * pvDummy15 corresponds to pvThreadLocalStoragePointers member of the TCB.
@@ -737,10 +745,8 @@ void vPortTLSPointersDelCb( void * pxTCB )
/* We need to iterate over half the depth of the pvThreadLocalStoragePointers area /* We need to iterate over half the depth of the pvThreadLocalStoragePointers area
* to access all TLS pointers and their respective TLS deletion callbacks. * to access all TLS pointers and their respective TLS deletion callbacks.
*/ */
for( int x = 0; x < ( configNUM_THREAD_LOCAL_STORAGE_POINTERS / 2 ); x++ ) for ( int x = 0; x < ( configNUM_THREAD_LOCAL_STORAGE_POINTERS / 2 ); x++ ) {
{ if ( pvThreadLocalStoragePointersDelCallback[ x ] != NULL ) { //If del cb is set
if ( pvThreadLocalStoragePointersDelCallback[ x ] != NULL ) //If del cb is set
{
/* In case the TLSP deletion callback has been overwritten by a TLS pointer, gracefully abort. */ /* In case the TLSP deletion callback has been overwritten by a TLS pointer, gracefully abort. */
if ( !esp_ptr_executable( pvThreadLocalStoragePointersDelCallback[ x ] ) ) { if ( !esp_ptr_executable( pvThreadLocalStoragePointersDelCallback[ x ] ) ) {
// We call EARLY log here as currently portCLEAN_UP_TCB() is called in a critical section // We call EARLY log here as currently portCLEAN_UP_TCB() is called in a critical section

View File

@@ -11,6 +11,8 @@
#include "esp_intr_alloc.h" #include "esp_intr_alloc.h"
#include "esp_err.h" #include "esp_err.h"
#include "esp_log.h" #include "esp_log.h"
#include "esp_private/systimer.h"
#include "esp_private/periph_ctrl.h"
#include "sdkconfig.h" #include "sdkconfig.h"
#ifdef CONFIG_FREERTOS_SYSTICK_USES_SYSTIMER #ifdef CONFIG_FREERTOS_SYSTICK_USES_SYSTIMER
#include "soc/periph_defs.h" #include "soc/periph_defs.h"
@@ -80,7 +82,13 @@ void vPortSetupTimer(void)
ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL)); ESP_ERROR_CHECK(esp_intr_alloc(ETS_SYSTIMER_TARGET0_EDGE_INTR_SOURCE + cpuid, ESP_INTR_FLAG_IRAM | level, SysTickIsrHandler, &systimer_hal, NULL));
if (cpuid == 0) { if (cpuid == 0) {
periph_module_enable(PERIPH_SYSTIMER_MODULE);
systimer_hal_init(&systimer_hal); systimer_hal_init(&systimer_hal);
systimer_hal_tick_rate_ops_t ops = {
.ticks_to_us = systimer_ticks_to_us,
.us_to_ticks = systimer_us_to_ticks,
};
systimer_hal_set_tick_rate_ops(&systimer_hal, &ops);
systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0); systimer_ll_set_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK, 0);
systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK); systimer_ll_apply_counter_value(systimer_hal.dev, SYSTIMER_LL_COUNTER_OS_TICK);

View File

@@ -67,7 +67,7 @@ menu "Hardware Abstraction Layer (HAL) and Low Level (LL)"
config HAL_SYSTIMER_USE_ROM_IMPL config HAL_SYSTIMER_USE_ROM_IMPL
bool "Use ROM implementation of SysTimer HAL driver" bool "Use ROM implementation of SysTimer HAL driver"
depends on ESP_ROM_HAS_HAL_SYSTIMER && !ESP32C2_XTAL_FREQ_26 depends on ESP_ROM_HAS_HAL_SYSTIMER
default y default y
help help
Enable this flag to use HAL functions from ROM instead of ESP-IDF. Enable this flag to use HAL functions from ROM instead of ESP-IDF.

View File

@@ -9,20 +9,11 @@
#include <stdbool.h> #include <stdbool.h>
#include "soc/systimer_struct.h" #include "soc/systimer_struct.h"
#include "hal/assert.h" #include "hal/assert.h"
#include "sdkconfig.h"
#define SYSTIMER_LL_COUNTER_CLOCK (0) // Counter used for "wallclock" time #define SYSTIMER_LL_COUNTER_CLOCK 0 // Counter used by esptimer, to generate the system level wall clock
#define SYSTIMER_LL_COUNTER_OS_TICK (1) // Counter used for OS tick #define SYSTIMER_LL_COUNTER_OS_TICK 1 // Counter used by RTOS porting layer, to generate the OS tick
#define SYSTIMER_LL_ALARM_OS_TICK_CORE0 (0) // Alarm used for OS tick of CPU core 0 #define SYSTIMER_LL_ALARM_OS_TICK_CORE0 0 // Alarm used by OS tick, dedicated for core 0
#define SYSTIMER_LL_ALARM_CLOCK (2) // Alarm used for "wallclock" time #define SYSTIMER_LL_ALARM_CLOCK 2 // Alarm used by esptimer
#ifdef CONFIG_ESP32C2_XTAL_FREQ_26
#define SYSTIMER_LL_TICKS_PER_US (52) // (26 / 2.5) = 10.4 = 52/5 systimer ticks per us
#define SYSTIMER_LL_TICKS_PER_US_DIV (5)
#else
#define SYSTIMER_LL_TICKS_PER_US (16) // 16 systimer ticks == 1us
#define SYSTIMER_LL_TICKS_PER_US_DIV (1)
#endif // ESP32C2_XTAL_FREQ_*
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {

View File

@@ -10,13 +10,10 @@
#include "soc/systimer_struct.h" #include "soc/systimer_struct.h"
#include "hal/assert.h" #include "hal/assert.h"
#define SYSTIMER_LL_COUNTER_CLOCK (0) // Counter used for "wallclock" time #define SYSTIMER_LL_COUNTER_CLOCK 0 // Counter used by esptimer, to generate the system level wall clock
#define SYSTIMER_LL_COUNTER_OS_TICK (1) // Counter used for OS tick #define SYSTIMER_LL_COUNTER_OS_TICK 1 // Counter used by RTOS porting layer, to generate the OS tick
#define SYSTIMER_LL_ALARM_OS_TICK_CORE0 (0) // Alarm used for OS tick of CPU core 0 #define SYSTIMER_LL_ALARM_OS_TICK_CORE0 0 // Alarm used by OS tick, dedicated for core 0
#define SYSTIMER_LL_ALARM_CLOCK (2) // Alarm used for "wallclock" time #define SYSTIMER_LL_ALARM_CLOCK 2 // Alarm used by esptimer
#define SYSTIMER_LL_TICKS_PER_US (16) // 16 systimer ticks == 1us
#define SYSTIMER_LL_TICKS_PER_US_DIV (1)
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {

View File

@@ -10,13 +10,10 @@
#include "soc/systimer_struct.h" #include "soc/systimer_struct.h"
#include "hal/assert.h" #include "hal/assert.h"
#define SYSTIMER_LL_COUNTER_CLOCK (0) // Counter used for "wallclock" time #define SYSTIMER_LL_COUNTER_CLOCK 0 // Counter used by esptimer, to generate the system level wall clock
#define SYSTIMER_LL_COUNTER_OS_TICK (1) // Counter used for OS tick #define SYSTIMER_LL_COUNTER_OS_TICK 1 // Counter used by RTOS porting layer, to generate the OS tick
#define SYSTIMER_LL_ALARM_OS_TICK_CORE0 (0) // Alarm used for OS tick of CPU core 0 #define SYSTIMER_LL_ALARM_OS_TICK_CORE0 0 // Alarm used by OS tick, dedicated for core 0
#define SYSTIMER_LL_ALARM_CLOCK (2) // Alarm used for "wallclock" time #define SYSTIMER_LL_ALARM_CLOCK 2 // Alarm used by esptimer
#define SYSTIMER_LL_TICKS_PER_US (16) // 16 systimer ticks == 1us
#define SYSTIMER_LL_TICKS_PER_US_DIV (1)
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {

View File

@@ -10,11 +10,8 @@
#include "soc/systimer_struct.h" #include "soc/systimer_struct.h"
#include "hal/assert.h" #include "hal/assert.h"
#define SYSTIMER_LL_COUNTER_CLOCK (0) // Counter used for "wallclock" time #define SYSTIMER_LL_COUNTER_CLOCK 0 // Counter used by esptimer, to generate the system level wall clock
#define SYSTIMER_LL_ALARM_CLOCK (2) // Alarm used for "wallclock" time #define SYSTIMER_LL_ALARM_CLOCK 2 // Alarm used by esptimer
#define SYSTIMER_LL_TICKS_PER_US (80) // 80 systimer ticks == 1us
#define SYSTIMER_LL_TICKS_PER_US_DIV (1)
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {

View File

@@ -10,14 +10,11 @@
#include "soc/systimer_struct.h" #include "soc/systimer_struct.h"
#include "hal/assert.h" #include "hal/assert.h"
#define SYSTIMER_LL_COUNTER_CLOCK (0) // Counter used for "wallclock" time #define SYSTIMER_LL_COUNTER_CLOCK 0 // Counter used by esptimer, to generate the system level wall clock
#define SYSTIMER_LL_COUNTER_OS_TICK (1) // Counter used for OS tick #define SYSTIMER_LL_COUNTER_OS_TICK 1 // Counter used by RTOS porting layer, to generate the OS tick
#define SYSTIMER_LL_ALARM_OS_TICK_CORE0 (0) // Alarm used for OS tick of CPU core 0 #define SYSTIMER_LL_ALARM_OS_TICK_CORE0 0 // Alarm used by OS tick, dedicated for core 0
#define SYSTIMER_LL_ALARM_OS_TICK_CORE1 (1) // Alarm used for OS tick of CPU core 1 #define SYSTIMER_LL_ALARM_OS_TICK_CORE1 1 // Alarm used by OS tick, dedicated for core 1
#define SYSTIMER_LL_ALARM_CLOCK (2) // Alarm used for "wallclock" time #define SYSTIMER_LL_ALARM_CLOCK 2 // Alarm used by esptimer
#define SYSTIMER_LL_TICKS_PER_US (16) // 16 systimer ticks == 1us
#define SYSTIMER_LL_TICKS_PER_US_DIV (1)
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {

View File

@@ -8,23 +8,51 @@
#include <stdint.h> #include <stdint.h>
#include <stdbool.h> #include <stdbool.h>
#include "soc/soc_caps.h"
#include "soc/systimer_struct.h"
#include "hal/systimer_types.h" #include "hal/systimer_types.h"
#include "soc/soc_caps.h"
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
#endif #endif
typedef struct systimer_dev_t *systimer_soc_handle_t; // systimer SOC layer handle
// the definitions of the following functions are provided by esp_hw_support component, see esp_hw_support/port/${TARGET}/systimer.c
typedef uint64_t (*ticks_to_us_func_t)(uint64_t ticks); // prototype of function to convert ticks to microseconds
typedef uint64_t (*us_to_ticks_func_t)(uint64_t us); // prototype of function to convert microseconds to ticks
/**
* @brief systimer HAL context structure
*/
typedef struct { typedef struct {
systimer_dev_t *dev; systimer_soc_handle_t dev; /*!< systimer peripheral base address */
ticks_to_us_func_t ticks_to_us; /*!< function to convert ticks to microseconds */
us_to_ticks_func_t us_to_ticks; /*!< function to convert microseconds to ticks */
} systimer_hal_context_t; } systimer_hal_context_t;
/**
* @brief systimer HAL configuration structure
*/
typedef struct {
ticks_to_us_func_t ticks_to_us; /*!< function to convert ticks to microseconds */
us_to_ticks_func_t us_to_ticks; /*!< function to convert microseconds to ticks */
} systimer_hal_tick_rate_ops_t;
/** /**
* @brief initialize systimer in HAL layer * @brief initialize systimer in HAL layer
*/ */
void systimer_hal_init(systimer_hal_context_t *hal); void systimer_hal_init(systimer_hal_context_t *hal);
/**
* @brief Deinitialize systimer HAL layer
*/
void systimer_hal_deinit(systimer_hal_context_t *hal);
/**
* @brief Set tick rate operation functions
*/
void systimer_hal_set_tick_rate_ops(systimer_hal_context_t *hal, systimer_hal_tick_rate_ops_t *ops);
/** /**
* @brief enable systimer counter * @brief enable systimer counter
*/ */
@@ -85,7 +113,7 @@ void systimer_hal_connect_alarm_counter(systimer_hal_context_t *hal, uint32_t al
*/ */
void systimer_hal_counter_can_stall_by_cpu(systimer_hal_context_t *hal, uint32_t counter_id, uint32_t cpu_id, bool can); void systimer_hal_counter_can_stall_by_cpu(systimer_hal_context_t *hal, uint32_t counter_id, uint32_t cpu_id, bool can);
#if !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US #if !SOC_SYSTIMER_FIXED_DIVIDER
/** /**
* @brief set increase steps for systimer counter on different clock source * @brief set increase steps for systimer counter on different clock source
*/ */

View File

@@ -4,21 +4,32 @@
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
*/ */
#include <stddef.h>
#include <sys/param.h> #include <sys/param.h>
#include "soc/soc_caps.h" #include "soc/soc_caps.h"
#include "hal/systimer_hal.h" #include "hal/systimer_hal.h"
#include "hal/systimer_ll.h" #include "hal/systimer_ll.h"
#include "hal/systimer_types.h" #include "hal/systimer_types.h"
#include "hal/clk_gate_ll.h"
#include "hal/assert.h" #include "hal/assert.h"
void systimer_hal_init(systimer_hal_context_t *hal) void systimer_hal_init(systimer_hal_context_t *hal)
{ {
hal->dev = &SYSTIMER; hal->dev = &SYSTIMER;
periph_ll_enable_clk_clear_rst(PERIPH_SYSTIMER_MODULE);
systimer_ll_enable_clock(hal->dev, true); systimer_ll_enable_clock(hal->dev, true);
} }
void systimer_hal_deinit(systimer_hal_context_t *hal)
{
systimer_ll_enable_clock(hal->dev, false);
hal->dev = NULL;
}
void systimer_hal_set_tick_rate_ops(systimer_hal_context_t *hal, systimer_hal_tick_rate_ops_t *ops)
{
hal->ticks_to_us = ops->ticks_to_us;
hal->us_to_ticks = ops->us_to_ticks;
}
uint64_t systimer_hal_get_counter_value(systimer_hal_context_t *hal, uint32_t counter_id) uint64_t systimer_hal_get_counter_value(systimer_hal_context_t *hal, uint32_t counter_id)
{ {
uint32_t lo, lo_start, hi; uint32_t lo, lo_start, hi;
@@ -47,14 +58,14 @@ uint64_t systimer_hal_get_counter_value(systimer_hal_context_t *hal, uint32_t co
uint64_t systimer_hal_get_time(systimer_hal_context_t *hal, uint32_t counter_id) uint64_t systimer_hal_get_time(systimer_hal_context_t *hal, uint32_t counter_id)
{ {
return systimer_hal_get_counter_value(hal, counter_id) * SYSTIMER_LL_TICKS_PER_US_DIV / SYSTIMER_LL_TICKS_PER_US; return hal->ticks_to_us(systimer_hal_get_counter_value(hal, counter_id));
} }
#if SOC_SYSTIMER_ALARM_MISS_COMPENSATE #if SOC_SYSTIMER_ALARM_MISS_COMPENSATE
void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_id, uint64_t target) void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_id, uint64_t target)
{ {
systimer_counter_value_t alarm = { systimer_counter_value_t alarm = {
.val = target * SYSTIMER_LL_TICKS_PER_US / SYSTIMER_LL_TICKS_PER_US_DIV .val = hal->us_to_ticks(target),
}; };
systimer_ll_enable_alarm(hal->dev, alarm_id, false); systimer_ll_enable_alarm(hal->dev, alarm_id, false);
systimer_ll_set_alarm_target(hal->dev, alarm_id, alarm.val); systimer_ll_set_alarm_target(hal->dev, alarm_id, alarm.val);
@@ -64,13 +75,11 @@ void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_i
#else // SOC_SYSTIMER_ALARM_MISS_COMPENSATE #else // SOC_SYSTIMER_ALARM_MISS_COMPENSATE
_Static_assert(SYSTIMER_LL_TICKS_PER_US_DIV == 1, "SYSTIMER_LL_TICKS_PER_US_DIV > 1 && !SOC_SYSTIMER_ALARM_MISS_COMPENSATE hasn't been supported");
void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_id, uint64_t timestamp) void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_id, uint64_t timestamp)
{ {
int64_t offset = SYSTIMER_LL_TICKS_PER_US * 2; int64_t offset = hal->us_to_ticks(1) * 2;
uint64_t now_time = systimer_hal_get_counter_value(hal, 0); uint64_t now_time = systimer_hal_get_counter_value(hal, 0);
systimer_counter_value_t alarm = { .val = MAX(timestamp * SYSTIMER_LL_TICKS_PER_US, now_time + offset) }; systimer_counter_value_t alarm = { .val = MAX(hal->us_to_ticks(timestamp), now_time + offset) };
do { do {
systimer_ll_enable_alarm(hal->dev, alarm_id, false); systimer_ll_enable_alarm(hal->dev, alarm_id, false);
systimer_ll_set_alarm_target(hal->dev, alarm_id, alarm.val); systimer_ll_set_alarm_target(hal->dev, alarm_id, alarm.val);
@@ -79,7 +88,7 @@ void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_i
int64_t delta = (int64_t)alarm.val - (int64_t)now_time; int64_t delta = (int64_t)alarm.val - (int64_t)now_time;
if (delta <= 0 && !systimer_ll_is_alarm_int_fired(hal->dev, alarm_id)) { if (delta <= 0 && !systimer_ll_is_alarm_int_fired(hal->dev, alarm_id)) {
// new alarm is less than the counter and the interrupt flag is not set // new alarm is less than the counter and the interrupt flag is not set
offset += -1 * delta + SYSTIMER_LL_TICKS_PER_US * 2; offset += -1 * delta + hal->us_to_ticks(1) * 2;
alarm.val = now_time + offset; alarm.val = now_time + offset;
} else { } else {
// finish if either (alarm > counter) or the interrupt flag is already set. // finish if either (alarm > counter) or the interrupt flag is already set.
@@ -92,7 +101,7 @@ void systimer_hal_set_alarm_target(systimer_hal_context_t *hal, uint32_t alarm_i
void systimer_hal_set_alarm_period(systimer_hal_context_t *hal, uint32_t alarm_id, uint32_t period) void systimer_hal_set_alarm_period(systimer_hal_context_t *hal, uint32_t alarm_id, uint32_t period)
{ {
systimer_ll_enable_alarm(hal->dev, alarm_id, false); systimer_ll_enable_alarm(hal->dev, alarm_id, false);
systimer_ll_set_alarm_period(hal->dev, alarm_id, period * SYSTIMER_LL_TICKS_PER_US / SYSTIMER_LL_TICKS_PER_US_DIV); systimer_ll_set_alarm_period(hal->dev, alarm_id, hal->us_to_ticks(period));
systimer_ll_apply_alarm_value(hal->dev, alarm_id); systimer_ll_apply_alarm_value(hal->dev, alarm_id);
systimer_ll_enable_alarm(hal->dev, alarm_id, true); systimer_ll_enable_alarm(hal->dev, alarm_id, true);
} }
@@ -110,8 +119,7 @@ void systimer_hal_enable_alarm_int(systimer_hal_context_t *hal, uint32_t alarm_i
void systimer_hal_counter_value_advance(systimer_hal_context_t *hal, uint32_t counter_id, int64_t time_us) void systimer_hal_counter_value_advance(systimer_hal_context_t *hal, uint32_t counter_id, int64_t time_us)
{ {
systimer_counter_value_t new_count = { systimer_counter_value_t new_count = {
.val = systimer_hal_get_counter_value(hal, counter_id) .val = systimer_hal_get_counter_value(hal, counter_id) + hal->us_to_ticks(time_us),
+ time_us * SYSTIMER_LL_TICKS_PER_US / SYSTIMER_LL_TICKS_PER_US_DIV
}; };
systimer_ll_set_counter_value(hal->dev, counter_id, new_count.val); systimer_ll_set_counter_value(hal->dev, counter_id, new_count.val);
systimer_ll_apply_counter_value(hal->dev, counter_id); systimer_ll_apply_counter_value(hal->dev, counter_id);
@@ -146,9 +154,7 @@ void systimer_hal_counter_can_stall_by_cpu(systimer_hal_context_t *hal, uint32_t
systimer_ll_counter_can_stall_by_cpu(hal->dev, counter_id, cpu_id, can); systimer_ll_counter_can_stall_by_cpu(hal->dev, counter_id, cpu_id, can);
} }
#if !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US #if !SOC_SYSTIMER_FIXED_DIVIDER
_Static_assert(SYSTIMER_LL_TICKS_PER_US_DIV == 1, "SYSTIMER_LL_TICKS_PER_US_DIV > 1 && !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US hasn't been supported");
void systimer_hal_set_steps_per_tick(systimer_hal_context_t *hal, int clock_source, uint32_t steps) void systimer_hal_set_steps_per_tick(systimer_hal_context_t *hal, int clock_source, uint32_t steps)
{ {
@@ -178,9 +184,9 @@ void systimer_hal_on_apb_freq_update(systimer_hal_context_t *hal, uint32_t apb_t
* If this was called when switching APB clock to XTAL, need to adjust * If this was called when switching APB clock to XTAL, need to adjust
* XTAL_STEP value accordingly. * XTAL_STEP value accordingly.
*/ */
if (apb_ticks_per_us != SYSTIMER_LL_TICKS_PER_US) { if (apb_ticks_per_us != hal->us_to_ticks(1)) {
HAL_ASSERT((SYSTIMER_LL_TICKS_PER_US % apb_ticks_per_us) == 0 && "TICK_PER_US should be divisible by APB frequency (in MHz)"); HAL_ASSERT((hal->us_to_ticks(1) % apb_ticks_per_us) == 0 && "TICK_PER_US should be divisible by APB frequency (in MHz)");
systimer_ll_set_step_for_xtal(hal->dev, SYSTIMER_LL_TICKS_PER_US / apb_ticks_per_us); systimer_ll_set_step_for_xtal(hal->dev, hal->us_to_ticks(1) / apb_ticks_per_us);
} }
} }
#endif // !SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US #endif // !SOC_SYSTIMER_FIXED_DIVIDER

View File

@@ -63,6 +63,10 @@ config SOC_SECURE_BOOT_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_ADC_DIG_CTRL_SUPPORTED config SOC_ADC_DIG_CTRL_SUPPORTED
bool bool
default y default y
@@ -391,10 +395,6 @@ config SOC_MEMSPI_SRC_FREQ_15M_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SYSTIMER_COUNTER_NUM config SOC_SYSTIMER_COUNTER_NUM
int int
default 2 default 2
@@ -411,7 +411,7 @@ config SOC_SYSTIMER_BIT_WIDTH_HI
int int
default 20 default 20
config SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US config SOC_SYSTIMER_FIXED_DIVIDER
bool bool
default y default y

View File

@@ -40,6 +40,7 @@
#define SOC_ECC_SUPPORTED 1 #define SOC_ECC_SUPPORTED 1
#define SOC_FLASH_ENC_SUPPORTED 1 #define SOC_FLASH_ENC_SUPPORTED 1
#define SOC_SECURE_BOOT_SUPPORTED 1 #define SOC_SECURE_BOOT_SUPPORTED 1
#define SOC_SYSTIMER_SUPPORTED 1
/*-------------------------- ADC CAPS -------------------------------*/ /*-------------------------- ADC CAPS -------------------------------*/
/*!< SAR ADC Module*/ /*!< SAR ADC Module*/
@@ -203,14 +204,13 @@
#define SOC_MEMSPI_SRC_FREQ_15M_SUPPORTED 1 #define SOC_MEMSPI_SRC_FREQ_15M_SUPPORTED 1
/*-------------------------- SYSTIMER CAPS ----------------------------------*/ /*-------------------------- SYSTIMER CAPS ----------------------------------*/
#define SOC_SYSTIMER_SUPPORTED 1 #define SOC_SYSTIMER_COUNTER_NUM 2 // Number of counter units
#define SOC_SYSTIMER_COUNTER_NUM (2) // Number of counter units #define SOC_SYSTIMER_ALARM_NUM 3 // Number of alarm units
#define SOC_SYSTIMER_ALARM_NUM (3) // Number of alarm units #define SOC_SYSTIMER_BIT_WIDTH_LO 32 // Bit width of systimer low part
#define SOC_SYSTIMER_BIT_WIDTH_LO (32) // Bit width of systimer low part #define SOC_SYSTIMER_BIT_WIDTH_HI 20 // Bit width of systimer high part
#define SOC_SYSTIMER_BIT_WIDTH_HI (20) // Bit width of systimer high part #define SOC_SYSTIMER_FIXED_DIVIDER 1 // Clock source divider is fixed: 2.5
#define SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US (1) // Number of ticks per microsecond is fixed (16 ticks/us if 40MHz XTAL; 10.4 ticks/us if 26MHz XTAL) #define SOC_SYSTIMER_INT_LEVEL 1 // Systimer peripheral uses level interrupt
#define SOC_SYSTIMER_INT_LEVEL (1) // Systimer peripheral uses level interrupt #define SOC_SYSTIMER_ALARM_MISS_COMPENSATE 1 // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
#define SOC_SYSTIMER_ALARM_MISS_COMPENSATE (1) // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
/*--------------------------- TIMER GROUP CAPS ---------------------------------------*/ /*--------------------------- TIMER GROUP CAPS ---------------------------------------*/
#define SOC_TIMER_GROUPS (1U) #define SOC_TIMER_GROUPS (1U)

View File

@@ -324,7 +324,7 @@ typedef union {
} systimer_date_reg_t; } systimer_date_reg_t;
typedef struct { typedef struct systimer_dev_t {
volatile systimer_conf_reg_t conf; volatile systimer_conf_reg_t conf;
volatile systimer_unit_op_reg_t unit_op[2]; volatile systimer_unit_op_reg_t unit_op[2];
volatile systimer_unit_load_val_reg_t unit_load_val[2]; volatile systimer_unit_load_val_reg_t unit_load_val[2];

View File

@@ -75,6 +75,10 @@ config SOC_SDM_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SUPPORT_COEXISTENCE config SOC_SUPPORT_COEXISTENCE
bool bool
default y default y
@@ -603,10 +607,6 @@ config SOC_MEMSPI_SRC_FREQ_20M_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SYSTIMER_COUNTER_NUM config SOC_SYSTIMER_COUNTER_NUM
int int
default 2 default 2
@@ -623,7 +623,7 @@ config SOC_SYSTIMER_BIT_WIDTH_HI
int int
default 20 default 20
config SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US config SOC_SYSTIMER_FIXED_DIVIDER
bool bool
default y default y

View File

@@ -43,6 +43,7 @@
#define SOC_I2S_SUPPORTED 1 #define SOC_I2S_SUPPORTED 1
#define SOC_RMT_SUPPORTED 1 #define SOC_RMT_SUPPORTED 1
#define SOC_SDM_SUPPORTED 1 #define SOC_SDM_SUPPORTED 1
#define SOC_SYSTIMER_SUPPORTED 1
#define SOC_SUPPORT_COEXISTENCE 1 #define SOC_SUPPORT_COEXISTENCE 1
#define SOC_AES_SUPPORTED 1 #define SOC_AES_SUPPORTED 1
#define SOC_MPI_SUPPORTED 1 #define SOC_MPI_SUPPORTED 1
@@ -288,14 +289,13 @@
#define SOC_MEMSPI_SRC_FREQ_20M_SUPPORTED 1 #define SOC_MEMSPI_SRC_FREQ_20M_SUPPORTED 1
/*-------------------------- SYSTIMER CAPS ----------------------------------*/ /*-------------------------- SYSTIMER CAPS ----------------------------------*/
#define SOC_SYSTIMER_SUPPORTED 1 #define SOC_SYSTIMER_COUNTER_NUM 2 // Number of counter units
#define SOC_SYSTIMER_COUNTER_NUM (2) // Number of counter units #define SOC_SYSTIMER_ALARM_NUM 3 // Number of alarm units
#define SOC_SYSTIMER_ALARM_NUM (3) // Number of alarm units #define SOC_SYSTIMER_BIT_WIDTH_LO 32 // Bit width of systimer low part
#define SOC_SYSTIMER_BIT_WIDTH_LO (32) // Bit width of systimer low part #define SOC_SYSTIMER_BIT_WIDTH_HI 20 // Bit width of systimer high part
#define SOC_SYSTIMER_BIT_WIDTH_HI (20) // Bit width of systimer high part #define SOC_SYSTIMER_FIXED_DIVIDER 1 // Clock source divider is fixed: 2.5
#define SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US (1) // Number of ticks per microsecond is fixed (16 ticks/us) #define SOC_SYSTIMER_INT_LEVEL 1 // Systimer peripheral uses level interrupt
#define SOC_SYSTIMER_INT_LEVEL (1) // Systimer peripheral uses level interrupt #define SOC_SYSTIMER_ALARM_MISS_COMPENSATE 1 // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
#define SOC_SYSTIMER_ALARM_MISS_COMPENSATE (1) // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
/*--------------------------- TIMER GROUP CAPS ---------------------------------------*/ /*--------------------------- TIMER GROUP CAPS ---------------------------------------*/
#define SOC_TIMER_GROUPS (2) #define SOC_TIMER_GROUPS (2)

View File

@@ -323,7 +323,7 @@ typedef union {
} systimer_date_reg_t; } systimer_date_reg_t;
typedef struct { typedef struct systimer_dev_t {
volatile systimer_conf_reg_t conf; volatile systimer_conf_reg_t conf;
volatile systimer_unit_op_reg_t unit_op[2]; volatile systimer_unit_op_reg_t unit_op[2];
volatile systimer_unit_load_val_reg_t unit_load_val[2]; volatile systimer_unit_load_val_reg_t unit_load_val[2];

View File

@@ -67,6 +67,10 @@ config SOC_SDM_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_AES_SUPPORTED config SOC_AES_SUPPORTED
bool bool
default y default y
@@ -579,10 +583,6 @@ config SOC_MEMSPI_SRC_FREQ_12M_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SYSTIMER_COUNTER_NUM config SOC_SYSTIMER_COUNTER_NUM
int int
default 2 default 2
@@ -599,7 +599,7 @@ config SOC_SYSTIMER_BIT_WIDTH_HI
int int
default 20 default 20
config SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US config SOC_SYSTIMER_FIXED_DIVIDER
bool bool
default y default y

View File

@@ -49,6 +49,7 @@
#define SOC_I2S_SUPPORTED 1 #define SOC_I2S_SUPPORTED 1
#define SOC_RMT_SUPPORTED 1 #define SOC_RMT_SUPPORTED 1
#define SOC_SDM_SUPPORTED 1 #define SOC_SDM_SUPPORTED 1
#define SOC_SYSTIMER_SUPPORTED 1
#define SOC_AES_SUPPORTED 1 #define SOC_AES_SUPPORTED 1
#define SOC_MPI_SUPPORTED 1 #define SOC_MPI_SUPPORTED 1
#define SOC_SHA_SUPPORTED 1 #define SOC_SHA_SUPPORTED 1
@@ -293,14 +294,13 @@
#define SOC_MEMSPI_SRC_FREQ_12M_SUPPORTED 1 #define SOC_MEMSPI_SRC_FREQ_12M_SUPPORTED 1
/*-------------------------- SYSTIMER CAPS ----------------------------------*/ /*-------------------------- SYSTIMER CAPS ----------------------------------*/
#define SOC_SYSTIMER_SUPPORTED 1 #define SOC_SYSTIMER_COUNTER_NUM 2 // Number of counter units
#define SOC_SYSTIMER_COUNTER_NUM (2) // Number of counter units #define SOC_SYSTIMER_ALARM_NUM 3 // Number of alarm units
#define SOC_SYSTIMER_ALARM_NUM (3) // Number of alarm units #define SOC_SYSTIMER_BIT_WIDTH_LO 32 // Bit width of systimer low part
#define SOC_SYSTIMER_BIT_WIDTH_LO (32) // Bit width of systimer low part #define SOC_SYSTIMER_BIT_WIDTH_HI 20 // Bit width of systimer high part
#define SOC_SYSTIMER_BIT_WIDTH_HI (20) // Bit width of systimer high part #define SOC_SYSTIMER_FIXED_DIVIDER 1 // Clock source divider is fixed: 2.5
#define SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US (1) // Number of ticks per microsecond is fixed (16 ticks/us) #define SOC_SYSTIMER_INT_LEVEL 1 // Systimer peripheral uses level interrupt
#define SOC_SYSTIMER_INT_LEVEL (1) // Systimer peripheral uses level interrupt #define SOC_SYSTIMER_ALARM_MISS_COMPENSATE 1 // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
#define SOC_SYSTIMER_ALARM_MISS_COMPENSATE (1) // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
/*--------------------------- TIMER GROUP CAPS ---------------------------------------*/ /*--------------------------- TIMER GROUP CAPS ---------------------------------------*/
#define SOC_TIMER_GROUPS (2) #define SOC_TIMER_GROUPS (2)

View File

@@ -314,7 +314,7 @@ typedef union {
} systimer_date_reg_t; } systimer_date_reg_t;
typedef struct { typedef struct systimer_dev_t {
volatile systimer_conf_reg_t conf; volatile systimer_conf_reg_t conf;
volatile systimer_unit_op_reg_t unit_op[2]; volatile systimer_unit_op_reg_t unit_op[2];
volatile systimer_unit_load_val_reg_t unit_load_val[2]; volatile systimer_unit_load_val_reg_t unit_load_val[2];

View File

@@ -99,6 +99,10 @@ config SOC_SDM_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SUPPORT_COEXISTENCE config SOC_SUPPORT_COEXISTENCE
bool bool
default n default n
@@ -619,10 +623,6 @@ config SOC_SYSTIMER_BIT_WIDTH_HI
int int
default 32 default 32
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_TIMER_GROUPS config SOC_TIMER_GROUPS
int int
default 2 default 2

View File

@@ -63,6 +63,7 @@
#define SOC_I2S_SUPPORTED 1 #define SOC_I2S_SUPPORTED 1
#define SOC_RMT_SUPPORTED 1 #define SOC_RMT_SUPPORTED 1
#define SOC_SDM_SUPPORTED 1 #define SOC_SDM_SUPPORTED 1
#define SOC_SYSTIMER_SUPPORTED 1
#define SOC_SUPPORT_COEXISTENCE 0 #define SOC_SUPPORT_COEXISTENCE 0
#define SOC_AES_SUPPORTED 1 #define SOC_AES_SUPPORTED 1
#define SOC_MPI_SUPPORTED 1 #define SOC_MPI_SUPPORTED 1
@@ -273,13 +274,12 @@
#define SOC_MEMSPI_SRC_FREQ_20M_SUPPORTED 1 #define SOC_MEMSPI_SRC_FREQ_20M_SUPPORTED 1
/*-------------------------- SYSTIMER CAPS ----------------------------------*/ /*-------------------------- SYSTIMER CAPS ----------------------------------*/
#define SOC_SYSTIMER_COUNTER_NUM (1) // Number of counter units #define SOC_SYSTIMER_COUNTER_NUM 1 // Number of counter units
#define SOC_SYSTIMER_ALARM_NUM (3) // Number of alarm units #define SOC_SYSTIMER_ALARM_NUM 3 // Number of alarm units
#define SOC_SYSTIMER_BIT_WIDTH_LO (32) // Bit width of systimer low part #define SOC_SYSTIMER_BIT_WIDTH_LO 32 // Bit width of systimer low part
#define SOC_SYSTIMER_BIT_WIDTH_HI (32) // Bit width of systimer high part #define SOC_SYSTIMER_BIT_WIDTH_HI 32 // Bit width of systimer high part
/*-------------------------- TIMER GROUP CAPS --------------------------------*/ /*-------------------------- TIMER GROUP CAPS --------------------------------*/
#define SOC_SYSTIMER_SUPPORTED 1
#define SOC_TIMER_GROUPS (2) #define SOC_TIMER_GROUPS (2)
#define SOC_TIMER_GROUP_TIMERS_PER_GROUP (2) #define SOC_TIMER_GROUP_TIMERS_PER_GROUP (2)
#define SOC_TIMER_GROUP_COUNTER_BIT_WIDTH (64) #define SOC_TIMER_GROUP_COUNTER_BIT_WIDTH (64)

View File

@@ -267,7 +267,7 @@ typedef union {
} systimer_date_reg_t; } systimer_date_reg_t;
typedef struct { typedef struct systimer_dev_t {
volatile systimer_conf_reg_t conf; volatile systimer_conf_reg_t conf;
volatile systimer_load_reg_t load; volatile systimer_load_reg_t load;
volatile systimer_load_hi_reg_t load_hi; volatile systimer_load_hi_reg_t load_hi;

View File

@@ -151,6 +151,10 @@ config SOC_SDM_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SUPPORT_COEXISTENCE config SOC_SUPPORT_COEXISTENCE
bool bool
default y default y
@@ -683,10 +687,6 @@ config SOC_SPIRAM_SUPPORTED
bool bool
default y default y
config SOC_SYSTIMER_SUPPORTED
bool
default y
config SOC_SYSTIMER_COUNTER_NUM config SOC_SYSTIMER_COUNTER_NUM
int int
default 2 default 2
@@ -703,7 +703,7 @@ config SOC_SYSTIMER_BIT_WIDTH_HI
int int
default 20 default 20
config SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US config SOC_SYSTIMER_FIXED_DIVIDER
bool bool
default y default y

View File

@@ -52,6 +52,7 @@
#define SOC_I2S_SUPPORTED 1 #define SOC_I2S_SUPPORTED 1
#define SOC_RMT_SUPPORTED 1 #define SOC_RMT_SUPPORTED 1
#define SOC_SDM_SUPPORTED 1 #define SOC_SDM_SUPPORTED 1
#define SOC_SYSTIMER_SUPPORTED 1
#define SOC_SUPPORT_COEXISTENCE 1 #define SOC_SUPPORT_COEXISTENCE 1
#define SOC_TEMP_SENSOR_SUPPORTED 1 #define SOC_TEMP_SENSOR_SUPPORTED 1
#define SOC_AES_SUPPORTED 1 #define SOC_AES_SUPPORTED 1
@@ -282,14 +283,13 @@
#define SOC_SPIRAM_SUPPORTED 1 #define SOC_SPIRAM_SUPPORTED 1
/*-------------------------- SYS TIMER CAPS ----------------------------------*/ /*-------------------------- SYS TIMER CAPS ----------------------------------*/
#define SOC_SYSTIMER_SUPPORTED 1 #define SOC_SYSTIMER_COUNTER_NUM 2 // Number of counter units
#define SOC_SYSTIMER_COUNTER_NUM (2) // Number of counter units #define SOC_SYSTIMER_ALARM_NUM 3 // Number of alarm units
#define SOC_SYSTIMER_ALARM_NUM (3) // Number of alarm units #define SOC_SYSTIMER_BIT_WIDTH_LO 32 // Bit width of systimer low part
#define SOC_SYSTIMER_BIT_WIDTH_LO (32) // Bit width of systimer low part #define SOC_SYSTIMER_BIT_WIDTH_HI 20 // Bit width of systimer high part
#define SOC_SYSTIMER_BIT_WIDTH_HI (20) // Bit width of systimer high part #define SOC_SYSTIMER_FIXED_DIVIDER 1 // Clock source divider is fixed: 2.5
#define SOC_SYSTIMER_HAS_FIXED_TICKS_PER_US (1) // Number of ticks per microsecond is fixed (16 ticks/us) #define SOC_SYSTIMER_INT_LEVEL 1 // Systimer peripheral uses level
#define SOC_SYSTIMER_INT_LEVEL (1) // Systimer peripheral uses level #define SOC_SYSTIMER_ALARM_MISS_COMPENSATE 1 // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
#define SOC_SYSTIMER_ALARM_MISS_COMPENSATE (1) // Systimer peripheral can generate interrupt immediately if t(target) > t(current)
/*-------------------------- TIMER GROUP CAPS --------------------------------*/ /*-------------------------- TIMER GROUP CAPS --------------------------------*/
#define SOC_TIMER_GROUPS (2) #define SOC_TIMER_GROUPS (2)

View File

@@ -357,7 +357,7 @@ typedef union {
} systimer_date_reg_t; } systimer_date_reg_t;
typedef struct { typedef struct systimer_dev_t {
volatile systimer_conf_reg_t conf; volatile systimer_conf_reg_t conf;
volatile systimer_unit_op_reg_t unit_op[2]; volatile systimer_unit_op_reg_t unit_op[2];
volatile systimer_unit_load_val_reg_t unit_load_val[2]; volatile systimer_unit_load_val_reg_t unit_load_val[2];