Update ESP32 port to ESP-IDF release v4.2 and add ESP-IDF version check (#231)

* Revert "Reintroduce Espressif's IDF v4.2 changes to ESP32 port (#193)"

This reverts commit 3d4d17178f.

* Update ESP32 port files to work with ESP-IDF v4.2 as well as ESP-IDF v3.3

Add changes required to support ESP32-S2

* portmacro.h: Change return type of vApplicationSleep to void

This fixes build failure when automatic light sleep is enabled

* prevent header checks for files with different licensing

Co-authored-by: David Chalco <david@chalco.io>
This commit is contained in:
Shubham Kulkarni 2020-12-23 02:30:45 +05:30 committed by GitHub
parent 341e9f06d0
commit ef4c305244
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
33 changed files with 327 additions and 6890 deletions

View file

@ -82,6 +82,7 @@
#include <xtensa/xtruntime.h>
#include "esp_timer.h" /* required for FreeRTOS run time stats */
#include "esp_system.h"
#include "esp_idf_version.h"
#include <esp_heap_caps.h>
@ -134,9 +135,9 @@
/* owner field values:
* 0 - Uninitialized (invalid)
* portMUX_FREE_VAL - Mux is free, can be locked by either CPU
* CORE_ID_PRO / CORE_ID_APP - Mux is locked to the particular core
* CORE_ID_REGVAL_PRO / CORE_ID_REGVAL_APP - Mux is locked to the particular core
*
* Any value other than portMUX_FREE_VAL, CORE_ID_PRO, CORE_ID_APP indicates corruption
* Any value other than portMUX_FREE_VAL, CORE_ID_REGVAL_PRO, CORE_ID_REGVAL_APP indicates corruption
*/
uint32_t owner;
@ -283,8 +284,11 @@
/*Because the ROM routines don't necessarily handle a stack in external RAM correctly, we force */
/*the stack memory to always be internal. */
#define pvPortMallocTcbMem( size ) heap_caps_malloc( size, MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT )
#define pvPortMallocStackMem( size ) heap_caps_malloc( size, MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT )
#define portTcbMemoryCaps (MALLOC_CAP_INTERNAL|MALLOC_CAP_8BIT)
#define portStackMemoryCaps (MALLOC_CAP_INTERNAL|MALLOC_CAP_8BIT)
#define pvPortMallocTcbMem(size) heap_caps_malloc(size, portTcbMemoryCaps)
#define pvPortMallocStackMem(size) heap_caps_malloc(size, portStackMemoryCaps)
/*xTaskCreateStatic uses these functions to check incoming memory. */
#define portVALID_TCB_MEM( ptr ) ( esp_ptr_internal( ptr ) && esp_ptr_byte_accessible( ptr ) )
@ -307,6 +311,14 @@
uint32_t compare,
uint32_t * set )
{
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
__asm__ __volatile__ (
"WSR %2,SCOMPARE1 \n"
"S32C1I %0, %1, 0 \n"
: "=r" ( *set )
: "r" ( addr ), "r" ( compare ), "0" ( *set )
);
#else
#if ( XCHAL_HAVE_S32C1I > 0 )
__asm__ __volatile__ (
"WSR %2,SCOMPARE1 \n"
@ -333,11 +345,21 @@
*set = old_value;
#endif /* if ( XCHAL_HAVE_S32C1I > 0 ) */
#endif /* #if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0)) */
}
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
void uxPortCompareSetExtram( volatile uint32_t * addr,
uint32_t compare,
uint32_t * set );
#else
static inline void uxPortCompareSetExtram(volatile uint32_t *addr, uint32_t compare, uint32_t *set)
{
#if defined(CONFIG_ESP32_SPIRAM_SUPPORT)
compare_and_set_extram(addr, compare, set);
#endif
}
#endif
/*-----------------------------------------------------------*/
@ -408,11 +430,37 @@
#define PRIVILEGED_DATA
#endif
bool vApplicationSleep( TickType_t xExpectedIdleTime );
void vApplicationSleep( TickType_t xExpectedIdleTime );
void vPortSetStackWatchpoint( void* pxStackStart );
#define portSUPPRESS_TICKS_AND_SLEEP( idleTime ) vApplicationSleep( idleTime )
/*-----------------------------------------------------------*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
/* Architecture specific optimisations. */
#if configUSE_PORT_OPTIMISED_TASK_SELECTION == 1
/* Check the configuration. */
#if( configMAX_PRIORITIES > 32 )
#error configUSE_PORT_OPTIMISED_TASK_SELECTION can only be set to 1 when configMAX_PRIORITIES is less than or equal to 32. It is very rare that a system requires more than 10 to 15 different priorities as tasks that share a priority will time slice.
#endif
/* Store/clear the ready priorities in a bit map. */
#define portRECORD_READY_PRIORITY( uxPriority, uxReadyPriorities ) ( uxReadyPriorities ) |= ( 1UL << ( uxPriority ) )
#define portRESET_READY_PRIORITY( uxPriority, uxReadyPriorities ) ( uxReadyPriorities ) &= ~( 1UL << ( uxPriority ) )
/*-----------------------------------------------------------*/
#define portGET_HIGHEST_PRIORITY( uxTopPriority, uxReadyPriorities ) uxTopPriority = ( 31 - __builtin_clz( ( uxReadyPriorities ) ) )
#endif /* configUSE_PORT_OPTIMISED_TASK_SELECTION */
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/*-----------------------------------------------------------*/
void _xt_coproc_release( volatile void * coproc_sa_base );
@ -429,6 +477,15 @@
#define xPortGetFreeHeapSize esp_get_free_heap_size
#define xPortGetMinimumEverFreeHeapSize esp_get_minimum_free_heap_size
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
/*
* Send an interrupt to another core in order to make the task running
* on it yield for a higher-priority task.
*/
void vPortYieldOtherCore( BaseType_t coreid ) PRIVILEGED_FUNCTION;
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
/*
* Callback to set a watchpoint on the end of the stack. Called every context switch to change the stack
@ -442,6 +499,7 @@
*/
BaseType_t xPortInIsrContext();
/*
* This function will be called in High prio ISRs. Returns true if the current core was in ISR context
* before calling into high prio ISR context.

View file

@ -0,0 +1,88 @@
/*
* Copyright (c) 2017, Intel Corporation
*
* SPDX-License-Identifier: Apache-2.0
*/
/* Copyright 2015-2018 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.
*/
/* File adapted to use on IDF FreeRTOS component, extracted
* originally from zephyr RTOS code base:
* https://github.com/zephyrproject-rtos/zephyr/blob/dafd348/arch/xtensa/include/xtensa-asm2-s.h
*/
#ifndef __XT_ASM_UTILS_H
#define __XT_ASM_UTILS_H
/*
* SPILL_ALL_WINDOWS
*
* Spills all windowed registers (i.e. registers not visible as
* A0-A15) to their ABI-defined spill regions on the stack.
*
* Unlike the Xtensa HAL implementation, this code requires that the
* EXCM and WOE bit be enabled in PS, and relies on repeated hardware
* exception handling to do the register spills. The trick is to do a
* noop write to the high registers, which the hardware will trap
* (into an overflow exception) in the case where those registers are
* already used by an existing call frame. Then it rotates the window
* and repeats until all but the A0-A3 registers of the original frame
* are guaranteed to be spilled, eventually rotating back around into
* the original frame. Advantages:
*
* - Vastly smaller code size
*
* - More easily maintained if changes are needed to window over/underflow
* exception handling.
*
* - Requires no scratch registers to do its work, so can be used safely in any
* context.
*
* - If the WOE bit is not enabled (for example, in code written for
* the CALL0 ABI), this becomes a silent noop and operates compatbily.
*
* - Hilariously it's ACTUALLY FASTER than the HAL routine. And not
* just a little bit, it's MUCH faster. With a mostly full register
* file on an LX6 core (ESP-32) I'm measuring 145 cycles to spill
* registers with this vs. 279 (!) to do it with
* xthal_spill_windows().
*/
.macro SPILL_ALL_WINDOWS
#if XCHAL_NUM_AREGS == 64
and a12, a12, a12
rotw 3
and a12, a12, a12
rotw 3
and a12, a12, a12
rotw 3
and a12, a12, a12
rotw 3
and a12, a12, a12
rotw 4
#elif XCHAL_NUM_AREGS == 32
and a12, a12, a12
rotw 3
and a12, a12, a12
rotw 3
and a4, a4, a4
rotw 2
#else
#error Unrecognized XCHAL_NUM_AREGS
#endif
.endm
#endif

View file

@ -45,6 +45,7 @@ NOTE: The Xtensa architecture requires stack pointer alignment to 16 bytes.
#include <xtensa/corebits.h>
#include <xtensa/config/system.h>
#include <xtensa/xtruntime-frames.h>
#include <esp_idf_version.h>
/* Align a value up to nearest n-byte boundary, where n is a power of 2. */
@ -325,8 +326,19 @@ STRUCT_END(XtSolFrame)
.endm
#endif
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#define CORE_ID_PRO 0xCDCD
#define CORE_ID_APP 0xABAB
#else
#define CORE_ID_REGVAL_PRO 0xCDCD
#define CORE_ID_REGVAL_APP 0xABAB
/* Included for compatibility, recommend using CORE_ID_REGVAL_PRO instead */
#define CORE_ID_PRO CORE_ID_REGVAL_PRO
/* Included for compatibility, recommend using CORE_ID_REGVAL_APP instead */
#define CORE_ID_APP CORE_ID_REGVAL_APP
#endif
/*
-------------------------------------------------------------------------------

View file

@ -96,24 +96,31 @@
#include <xtensa/config/core.h>
#include "xtensa_rtos.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#include "rom/ets_sys.h"
#include "esp_panic.h"
#include "esp_crosscore_int.h"
#else
#if CONFIG_IDF_TARGET_ESP32S2
#include "esp32s2/rom/ets_sys.h"
#elif CONFIG_IDF_TARGET_ESP32
#include "esp32/rom/ets_sys.h"
#endif
#include "esp_private/panic_reason.h"
#include "esp_debug_helpers.h"
#include "esp_private/crosscore_int.h"
#include "esp_log.h"
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
#include "soc/cpu.h"
#include "FreeRTOS.h"
#include "task.h"
#include "esp_private/panic_reason.h"
#include "esp_debug_helpers.h"
#include "esp_heap_caps.h"
#include "esp_private/crosscore_int.h"
#include "esp_intr_alloc.h"
#include "esp_log.h"
/* Defined in portasm.h */
extern void _frxt_tick_timer_init( void );
@ -488,6 +495,8 @@ void vPortSetStackWatchpoint( void * pxStackStart )
{
uint32_t prev;
uint32_t oldlevel = portENTER_CRITICAL_NESTED();
#ifdef CONFIG_FREERTOS_PORTMUX_DEBUG
vPortCPUAcquireMutexIntsDisabled( &extram_mux, portMUX_NO_TIMEOUT, __FUNCTION__, __LINE__ );
#else
@ -506,6 +515,8 @@ void vPortSetStackWatchpoint( void * pxStackStart )
#else
vPortCPUReleaseMutexIntsDisabled( &extram_mux );
#endif
portEXIT_CRITICAL_NESTED(oldlevel);
}
#endif //defined(CONFIG_SPIRAM_SUPPORT)

View file

@ -25,6 +25,7 @@
#include "xtensa_rtos.h"
#include "sdkconfig.h"
#include "esp_idf_version.h"
#define TOPOFSTACK_OFFS 0x00 /* StackType_t *pxTopOfStack */
#define CP_TOPOFSTACK_OFFS 0x04 /* xMPU_SETTINGS.coproc_area */
@ -138,6 +139,7 @@ _frxt_int_enter:
mull a2, a4, a2
add a1, a1, a2 /* for current proc */
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef CONFIG_FREERTOS_FPU_IN_ISR
#if XCHAL_CP_NUM > 0
rsr a3, CPENABLE /* Restore thread scope CPENABLE */
@ -145,9 +147,11 @@ _frxt_int_enter:
s32i a3, a1, 0 /* its trigger */
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
.Lnested:
1:
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef CONFIG_FREERTOS_FPU_IN_ISR
#if XCHAL_CP_NUM > 0
movi a3, 0 /* whilst ISRs pending keep CPENABLE exception active */
@ -155,6 +159,7 @@ _frxt_int_enter:
rsync
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
mov a0, a12 /* restore return addr and return */
ret
@ -192,6 +197,7 @@ _frxt_int_exit:
s32i a2, a3, 0 /* save nesting count */
bnez a2, .Lnesting /* !=0 after decr so still nested */
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef CONFIG_FREERTOS_FPU_IN_ISR
#if XCHAL_CP_NUM > 0
l32i a3, sp, 0 /* Grab last CPENABLE before leave ISR */
@ -200,6 +206,7 @@ _frxt_int_exit:
rsync /* ensure CPENABLE was modified */
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
movi a2, pxCurrentTCB
addx4 a2, a4, a2

View file

@ -48,7 +48,11 @@
#include "portable.h"
/* XOR one core ID with this value to get the other core ID */
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#define CORE_ID_XOR_SWAP ( CORE_ID_PRO ^ CORE_ID_APP )
#else
#define CORE_ID_REGVAL_XOR_SWAP (CORE_ID_REGVAL_PRO ^ CORE_ID_REGVAL_APP)
#endif

View file

@ -70,7 +70,11 @@ static inline bool __attribute__( ( always_inline ) )
#ifdef CONFIG_FREERTOS_PORTMUX_DEBUG
uint32_t owner = mux->owner;
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
if( ( owner != portMUX_FREE_VAL ) && ( owner != CORE_ID_PRO ) && ( owner != CORE_ID_APP ) )
#else
if (owner != portMUX_FREE_VAL && owner != CORE_ID_REGVAL_PRO && owner != CORE_ID_REGVAL_APP)
#endif
{
ets_printf( "ERROR: vPortCPUAcquireMutex: mux %p is uninitialized (0x%X)! Called from %s line %d.\n", mux, owner, fnName, line );
mux->owner = portMUX_FREE_VAL;
@ -84,7 +88,11 @@ static inline bool __attribute__( ( always_inline ) )
/* Note: coreID is the full 32 bit core ID (CORE_ID_PRO/CORE_ID_APP),
* not the 0/1 value returned by xPortGetCoreID()
*/
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
otherCoreID = CORE_ID_XOR_SWAP ^ coreID;
#else
otherCoreID = CORE_ID_REGVAL_XOR_SWAP ^ coreID;
#endif
do
{
@ -163,7 +171,11 @@ static inline bool __attribute__( ( always_inline ) )
mux->lastLockedLine = line;
uint32_t owner = mux->owner;
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
if( ( owner != portMUX_FREE_VAL ) && ( owner != CORE_ID_PRO ) && ( owner != CORE_ID_APP ) )
#else
if (owner != portMUX_FREE_VAL && owner != CORE_ID_REGVAL_PRO && owner != CORE_ID_REGVAL_APP)
#endif
{
ets_printf( "ERROR: vPortCPUReleaseMutex: mux %p is invalid (0x%x)!\n", mux, mux->owner );
}

View file

@ -51,6 +51,10 @@ NOERROR: .error "C preprocessor needed for this file: make sure its filename\
#include "xtensa_rtos.h"
#include "xtensa_context.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#include "xt_asm_utils.h"
#endif
#ifdef XT_USE_OVLY
#include <xtensa/overlay_os_asm.h>
@ -58,8 +62,6 @@ NOERROR: .error "C preprocessor needed for this file: make sure its filename\
.text
/*******************************************************************************
_xt_context_save
@ -97,6 +99,7 @@ Exit conditions:
.align 4
.literal_position
.align 4
_xt_context_save:
s32i a2, sp, XT_STK_A2
@ -143,6 +146,7 @@ _xt_context_save:
mov a9, a0 /* preserve ret addr */
#endif
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#ifndef __XTENSA_CALL0_ABI__
/*
To spill the reg windows, temp. need pre-interrupt stack ptr and a4-15.
@ -175,25 +179,76 @@ _xt_context_save:
l32i a13, sp, XT_STK_TMP1
l32i a9, sp, XT_STK_TMP2
#endif
#endif /* (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0)) */
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
s32i a12, sp, XT_STK_TMP0 /* temp. save stuff in stack frame */
s32i a13, sp, XT_STK_TMP1
s32i a9, sp, XT_STK_TMP2
l32i a12, sp, XT_STK_A12 /* recover original a9,12,13 */
l32i a13, sp, XT_STK_A13
l32i a9, sp, XT_STK_A9
#endif
#if XCHAL_EXTRA_SA_SIZE > 0
/*
NOTE: Normally the xthal_save_extra_nw macro only affects address
registers a2-a5. It is theoretically possible for Xtensa processor
designers to write TIE that causes more address registers to be
affected, but it is generally unlikely. If that ever happens,
more registers need to be saved/restored around this macro invocation.
Here we assume a9,12,13 are preserved.
Future Xtensa tools releases might limit the regs that can be affected.
*/
addi a2, sp, XT_STK_EXTRA /* where to save it */
# if XCHAL_EXTRA_SA_ALIGN > 16
movi a3, -XCHAL_EXTRA_SA_ALIGN
and a2, a2, a3 /* align dynamically >16 bytes */
# endif
call0 xthal_save_extra_nw /* destroys a0,2,3,4,5 */
call0 xthal_save_extra_nw /* destroys a0,2,3 */
#endif
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifndef __XTENSA_CALL0_ABI__
#ifdef XT_USE_OVLY
l32i a9, sp, XT_STK_PC /* recover saved PC */
_xt_overlay_get_state a9, a12, a13
s32i a9, sp, XT_STK_OVLY /* save overlay state */
#endif
/* SPILL_ALL_WINDOWS macro requires window overflow exceptions to be enabled,
* i.e. PS.EXCM cleared and PS.WOE set.
* Since we are going to clear PS.EXCM, we also need to increase INTLEVEL
* at least to XCHAL_EXCM_LEVEL. This matches that value of effective INTLEVEL
* at entry (CINTLEVEL=max(PS.INTLEVEL, XCHAL_EXCM_LEVEL) when PS.EXCM is set.
* Since WindowOverflow exceptions will trigger inside SPILL_ALL_WINDOWS,
* need to save/restore EPC1 as well.
* Note: even though a4-a15 are saved into the exception frame, we should not
* clobber them until after SPILL_ALL_WINDOWS. This is because these registers
* may contain live windows belonging to previous frames in the call stack.
* These frames will be spilled by SPILL_ALL_WINDOWS, and if the register was
* used as a temporary by this code, the temporary value would get stored
* onto the stack, instead of the real value.
*/
rsr a2, PS /* to be restored after SPILL_ALL_WINDOWS */
movi a0, PS_INTLEVEL_MASK
and a3, a2, a0 /* get the current INTLEVEL */
bgeui a3, XCHAL_EXCM_LEVEL, 1f /* calculate max(INTLEVEL, XCHAL_EXCM_LEVEL) */
movi a3, XCHAL_EXCM_LEVEL
1:
movi a0, PS_UM | PS_WOE /* clear EXCM, enable window overflow, set new INTLEVEL */
or a3, a3, a0
wsr a3, ps
rsr a0, EPC1 /* to be restored after SPILL_ALL_WINDOWS */
addi sp, sp, XT_STK_FRMSZ /* restore the interruptee's SP */
SPILL_ALL_WINDOWS
addi sp, sp, -XT_STK_FRMSZ /* return the current stack pointer and proceed with context save*/
wsr a2, PS /* restore to the value at entry */
rsync
wsr a0, EPC1 /* likewise */
#endif /* __XTENSA_CALL0_ABI__ */
l32i a12, sp, XT_STK_TMP0 /* restore the temp saved registers */
l32i a13, sp, XT_STK_TMP1 /* our return address is there */
l32i a9, sp, XT_STK_TMP2
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
#if XCHAL_EXTRA_SA_SIZE > 0 || !defined(__XTENSA_CALL0_ABI__)
mov a0, a9 /* retrieve ret addr */
#endif

View file

@ -34,11 +34,16 @@
#endif
#include "xtensa_rtos.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#include "esp_clk.h"
#else
#if CONFIG_IDF_TARGET_ESP32S2
#include "esp32s2/clk.h"
#elif CONFIG_IDF_TARGET_ESP32
#include "esp32/clk.h"
#endif
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
#ifdef XT_RTOS_TIMER_INT

View file

@ -33,12 +33,17 @@
#include "freertos/FreeRTOS.h"
#include "freertos/xtensa_api.h"
#include "freertos/portable.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#include "rom/ets_sys.h"
#else
#if CONFIG_IDF_TARGET_ESP32S2
#include "esp32s2/rom/ets_sys.h"
#elif CONFIG_IDF_TARGET_ESP32
#include "esp32/rom/ets_sys.h"
#endif
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
#if XCHAL_HAVE_EXCEPTIONS

View file

@ -13,7 +13,12 @@
// limitations under the License.
#include "xtensa_rtos.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#include "esp_panic.h"
#else
#include "esp_private/panic_reason.h"
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
#include "sdkconfig.h"
#include "soc/soc.h"

View file

@ -91,7 +91,12 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*******************************************************************************/
#include "xtensa_rtos.h"
#include "esp_idf_version.h"
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
#include "esp_panic.h"
#else
#include "esp_private/panic_reason.h"
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
#include "sdkconfig.h"
#include "soc/soc.h"
@ -226,11 +231,13 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
rsr a0, EXCSAVE_1 + \level - 1 /* Get exception frame pointer stored in EXCSAVE_x */
l32i a3, a0, XT_STK_A0 /* Copy pre-exception a0 (return address) */
s32e a3, a1, -16
l32i a3, a0, XT_STK_A1 /* Copy pre-exception a1 (stack pointer) */
s32e a3, a1, -12
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Backtracing only needs a0 and a1, no need to create full base save area.
Also need to change current frame's return address to point to pre-exception's
last run instruction.
@ -734,10 +741,12 @@ _xt_user_exc:
*/
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
l32i a3, sp, XT_STK_A0 /* Copy pre-exception a0 (return address) */
s32e a3, sp, -16
l32i a3, sp, XT_STK_A1 /* Copy pre-exception a1 (stack pointer) */
s32e a3, sp, -12
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
rsr a0, EPC_1 /* return address for debug backtrace */
movi a5, 0xC0000000 /* constant with top 2 bits set (call size) */
rsync /* wait for WSR.PS to complete */
@ -983,10 +992,13 @@ _xt_coproc_exc:
/* Get co-processor state save area of new owner thread. */
call0 XT_RTOS_CP_STATE /* a15 = new owner's save area */
#if (ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0))
beqz a15, .L_goto_invalid /* not in a thread (invalid) */
#else
#ifndef CONFIG_FREERTOS_FPU_IN_ISR
beqz a15, .L_goto_invalid
#endif
#endif /* ESP_IDF_VERSION < ESP_IDF_VERSION_VAL(4, 2, 0) */
/*When FPU in ISR is enabled we could deal with zeroed a15 */
@ -1034,8 +1046,12 @@ locking.
/* below, because on restoring from ISR we may have new == old condition used
* to force cp restore to next thread
*/
#ifndef CONFIG_FREERTOS_FPU_IN_ISR
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifndef CONFIG_FREERTOS_FPU_IN_ISR
#endif
beq a15, a2, .L_goto_done /* new owner == old, we're done */
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#endif
#endif
/* If no old owner then nothing to save. */
@ -1078,7 +1094,9 @@ locking.
.L_check_new:
/* Check if any state has to be restored for new owner. */
/* NOTE: a15 = new owner's save area, cannot be zero when we get here. */
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
beqz a15, .L_xt_coproc_done
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
l16ui a3, a15, XT_CPSTORED /* a3 = new owner's CPSTORED */
movi a4, _xt_coproc_sa_offset
@ -1164,6 +1182,7 @@ _xt_lowint1:
movi a0, _xt_user_exit /* save exit point for dispatch */
s32i a0, sp, XT_STK_EXIT
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
/* EXCSAVE_1 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#ifdef XT_DEBUG_BACKTRACE
@ -1172,6 +1191,7 @@ _xt_lowint1:
wsr a0, EXCSAVE_1
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
@ -1256,12 +1276,14 @@ _xt_medint2:
/* EXCSAVE_2 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
mov a0, sp
wsr a0, EXCSAVE_2
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
@ -1337,12 +1359,14 @@ _xt_medint3:
/* EXCSAVE_3 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
mov a0, sp
wsr a0, EXCSAVE_3
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
@ -1417,12 +1441,14 @@ _xt_medint4:
/* EXCSAVE_4 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
mov a0, sp
wsr a0, EXCSAVE_4
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
@ -1497,12 +1523,14 @@ _xt_medint5:
/* EXCSAVE_5 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
mov a0, sp
wsr a0, EXCSAVE_5
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
call0 XT_RTOS_INT_ENTER /* common RTOS interrupt entry */
@ -1576,12 +1604,14 @@ _xt_medint6:
/* EXCSAVE_6 should now be free to use. Use it to keep a copy of the
current stack pointer that points to the exception frame (XT_STK_FRAME).*/
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0))
#ifdef XT_DEBUG_BACKTRACE
#ifndef __XTENSA_CALL0_ABI__
mov a0, sp
wsr a0, EXCSAVE_6
#endif
#endif
#endif /* ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 2, 0) */
/* Save rest of interrupt context and enter RTOS. */
call0 XT_RTOS_INT_ENTER /* common RTOS interrupt entry */