diff options
Diffstat (limited to 'tinyusb/hw/bsp/gd32vf103/system_gd32vf103.c')
-rwxr-xr-x | tinyusb/hw/bsp/gd32vf103/system_gd32vf103.c | 668 |
1 files changed, 0 insertions, 668 deletions
diff --git a/tinyusb/hw/bsp/gd32vf103/system_gd32vf103.c b/tinyusb/hw/bsp/gd32vf103/system_gd32vf103.c deleted file mode 100755 index 29518a54..00000000 --- a/tinyusb/hw/bsp/gd32vf103/system_gd32vf103.c +++ /dev/null @@ -1,668 +0,0 @@ -/*! - \file system_gd32vf103.h -\brief RISC-V Device Peripheral Access Layer Source File for - GD32VF103 Device Series - -*/ - -/* - Copyright (c) 2020, GigaDevice Semiconductor Inc. - - Redistribution and use in source and binary forms, with or without modification, -are permitted provided that the following conditions are met: - - 1. Redistributions of source code must retain the above copyright notice, this - list of conditions and the following disclaimer. - 2. Redistributions in binary form must reproduce the above copyright notice, - this list of conditions and the following disclaimer in the documentation - and/or other materials provided with the distribution. - 3. Neither the name of the copyright holder nor the names of its contributors - may be used to endorse or promote products derived from this software without - specific prior written permission. - - THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" -AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. -IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, -INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT -NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, -WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) -ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY -OF SUCH DAMAGE. -*/ - -/* This file refers the RISC-V standard, some adjustments are made according to GigaDevice chips */ -#include "board.h" - -/* system frequency define */ -#define __IRC8M (IRC8M_VALUE) /* internal 8 MHz RC oscillator frequency */ -#define __HXTAL (HXTAL_VALUE) /* high speed crystal oscillator frequency */ -#define __SYS_OSC_CLK (__IRC8M) /* main oscillator frequency */ -#define __SYSTEM_CLOCK_HXTAL (HXTAL_VALUE) - -#if !defined(__SYSTEM_CLOCK) -#define __SYSTEM_CLOCK 72000000 -#endif - -#if __SYSTEM_CLOCK == 48000000 - #define __SYSTEM_CLOCK_48M_PLL_HXTAL (uint32_t)(48000000) - uint32_t SystemCoreClock = __SYSTEM_CLOCK_48M_PLL_HXTAL; - static void system_clock_48m_hxtal(void); - -#elif __SYSTEM_CLOCK == 72000000 - #define __SYSTEM_CLOCK_72M_PLL_HXTAL (uint32_t)(72000000) - uint32_t SystemCoreClock = __SYSTEM_CLOCK_72M_PLL_HXTAL; - static void system_clock_72m_hxtal(void); - -#elif __SYSTEM_CLOCK == 96000000 - #define __SYSTEM_CLOCK_96M_PLL_HXTAL (uint32_t)(96000000) - uint32_t SystemCoreClock = __SYSTEM_CLOCK_96M_PLL_HXTAL; - static void system_clock_96m_hxtal(void); - -#else -#error No valid system clock configuration set! -#endif - -/* configure the system clock */ -static void system_clock_config(void); - -/*! - \brief configure the system clock - \param[in] none - \param[out] none - \retval none -*/ -static void system_clock_config(void) -{ -#if defined (__SYSTEM_CLOCK_48M_PLL_HXTAL) - system_clock_48m_hxtal(); -#elif defined (__SYSTEM_CLOCK_72M_PLL_HXTAL) - system_clock_72m_hxtal(); -#elif defined (__SYSTEM_CLOCK_96M_PLL_HXTAL) - system_clock_96m_hxtal(); -#endif /* __SYSTEM_CLOCK_HXTAL */ -} - -/*! - \brief setup the microcontroller system, initialize the system - \param[in] none - \param[out] none - \retval none -*/ -void SystemInit(void) -{ - /* reset the RCC clock configuration to the default reset state */ - /* enable IRC8M */ - RCU_CTL |= RCU_CTL_IRC8MEN; - - /* reset SCS, AHBPSC, APB1PSC, APB2PSC, ADCPSC, CKOUT0SEL bits */ - RCU_CFG0 &= ~(RCU_CFG0_SCS | RCU_CFG0_AHBPSC | RCU_CFG0_APB1PSC | RCU_CFG0_APB2PSC | - RCU_CFG0_ADCPSC | RCU_CFG0_ADCPSC_2 | RCU_CFG0_CKOUT0SEL); - - /* reset HXTALEN, CKMEN, PLLEN bits */ - RCU_CTL &= ~(RCU_CTL_HXTALEN | RCU_CTL_CKMEN | RCU_CTL_PLLEN); - - /* Reset HXTALBPS bit */ - RCU_CTL &= ~(RCU_CTL_HXTALBPS); - - /* reset PLLSEL, PREDV0_LSB, PLLMF, USBFSPSC bits */ - - RCU_CFG0 &= ~(RCU_CFG0_PLLSEL | RCU_CFG0_PREDV0_LSB | RCU_CFG0_PLLMF | - RCU_CFG0_USBFSPSC | RCU_CFG0_PLLMF_4); - RCU_CFG1 = 0x00000000U; - - /* Reset HXTALEN, CKMEN, PLLEN, PLL1EN and PLL2EN bits */ - RCU_CTL &= ~(RCU_CTL_PLLEN | RCU_CTL_PLL1EN | RCU_CTL_PLL2EN | RCU_CTL_CKMEN | RCU_CTL_HXTALEN); - /* disable all interrupts */ - RCU_INT = 0x00FF0000U; - - /* Configure the System clock source, PLL Multiplier, AHB/APBx prescalers and Flash settings */ - system_clock_config(); -} - -/*! - \brief update the SystemCoreClock with current core clock retrieved from cpu registers - \param[in] none - \param[out] none - \retval none -*/ -void SystemCoreClockUpdate(void) -{ - uint32_t scss; - uint32_t pllsel, predv0sel, pllmf, ck_src; - uint32_t predv0, predv1, pll1mf; - - scss = GET_BITS(RCU_CFG0, 2, 3); - - switch (scss) - { - /* IRC8M is selected as CK_SYS */ - case SEL_IRC8M: - SystemCoreClock = IRC8M_VALUE; - break; - - /* HXTAL is selected as CK_SYS */ - case SEL_HXTAL: - SystemCoreClock = HXTAL_VALUE; - break; - - /* PLL is selected as CK_SYS */ - case SEL_PLL: - /* PLL clock source selection, HXTAL or IRC8M/2 */ - pllsel = (RCU_CFG0 & RCU_CFG0_PLLSEL); - - - if(RCU_PLLSRC_IRC8M_DIV2 == pllsel){ - /* PLL clock source is IRC8M/2 */ - ck_src = IRC8M_VALUE / 2U; - }else{ - /* PLL clock source is HXTAL */ - ck_src = HXTAL_VALUE; - - predv0sel = (RCU_CFG1 & RCU_CFG1_PREDV0SEL); - - /* source clock use PLL1 */ - if(RCU_PREDV0SRC_CKPLL1 == predv0sel){ - predv1 = ((RCU_CFG1 & RCU_CFG1_PREDV1) >> 4) + 1U; - pll1mf = ((RCU_CFG1 & RCU_CFG1_PLL1MF) >> 8) + 2U; - if(17U == pll1mf){ - pll1mf = 20U; - } - ck_src = (ck_src / predv1) * pll1mf; - } - predv0 = (RCU_CFG1 & RCU_CFG1_PREDV0) + 1U; - ck_src /= predv0; - } - - /* PLL multiplication factor */ - pllmf = GET_BITS(RCU_CFG0, 18, 21); - - if((RCU_CFG0 & RCU_CFG0_PLLMF_4)){ - pllmf |= 0x10U; - } - - if(pllmf >= 15U){ - pllmf += 1U; - }else{ - pllmf += 2U; - } - - SystemCoreClock = ck_src * pllmf; - - if(15U == pllmf){ - /* PLL source clock multiply by 6.5 */ - SystemCoreClock = ck_src * 6U + ck_src / 2U; - } - - break; - - /* IRC8M is selected as CK_SYS */ - default: - SystemCoreClock = IRC8M_VALUE; - break; - } -} - -#if defined (__SYSTEM_CLOCK_48M_PLL_HXTAL) -/*! - \brief configure the system clock to 48M by PLL which selects HXTAL(MD/HD/XD:8M; CL:25M) as its clock source - \param[in] none - \param[out] none - \retval none -*/ -static void system_clock_48m_hxtal(void) -{ - uint32_t timeout = 0U; - uint32_t stab_flag = 0U; - - /* enable HXTAL */ - RCU_CTL |= RCU_CTL_HXTALEN; - - /* wait until HXTAL is stable or the startup time is longer than HXTAL_STARTUP_TIMEOUT */ - do{ - timeout++; - stab_flag = (RCU_CTL & RCU_CTL_HXTALSTB); - }while((0U == stab_flag) && (HXTAL_STARTUP_TIMEOUT != timeout)); - - /* if fail */ - if(0U == (RCU_CTL & RCU_CTL_HXTALSTB)){ - while(1){ - } - } - - /* HXTAL is stable */ - /* AHB = SYSCLK */ - RCU_CFG0 |= RCU_AHB_CKSYS_DIV1; - /* APB2 = AHB/1 */ - RCU_CFG0 |= RCU_APB2_CKAHB_DIV1; - /* APB1 = AHB/2 */ - RCU_CFG0 |= RCU_APB1_CKAHB_DIV2; - - /* CK_PLL = (CK_PREDIV0) * 12 = 48 MHz */ - RCU_CFG0 &= ~(RCU_CFG0_PLLMF | RCU_CFG0_PLLMF_4); - RCU_CFG0 |= (RCU_PLLSRC_HXTAL | RCU_PLL_MUL12); - - if(HXTAL_VALUE==25000000){ - - /* CK_PREDIV0 = (CK_HXTAL)/5 *8 /10 = 4 MHz */ - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV1 | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_CKPLL1 | RCU_PLL1_MUL8 | RCU_PREDV1_DIV5 | RCU_PREDV0_DIV10); - - /* enable PLL1 */ - RCU_CTL |= RCU_CTL_PLL1EN; - /* wait till PLL1 is ready */ - while((RCU_CTL & RCU_CTL_PLL1STB) == 0){ - } - - }else if(HXTAL_VALUE==8000000){ - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PREDV1 | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_HXTAL | RCU_PREDV0_DIV2 ); - } - - - - /* enable PLL */ - RCU_CTL |= RCU_CTL_PLLEN; - - /* wait until PLL is stable */ - while(0U == (RCU_CTL & RCU_CTL_PLLSTB)){ - } - - /* select PLL as system clock */ - RCU_CFG0 &= ~RCU_CFG0_SCS; - RCU_CFG0 |= RCU_CKSYSSRC_PLL; - - /* wait until PLL is selected as system clock */ - while(0U == (RCU_CFG0 & RCU_SCSS_PLL)){ - } -} - -#elif defined (__SYSTEM_CLOCK_72M_PLL_HXTAL) -/*! - \brief configure the system clock to 72M by PLL which selects HXTAL(MD/HD/XD:8M; CL:25M) as its clock source - \param[in] none - \param[out] none - \retval none -*/ -static void system_clock_72m_hxtal(void) -{ - uint32_t timeout = 0U; - uint32_t stab_flag = 0U; - - /* enable HXTAL */ - RCU_CTL |= RCU_CTL_HXTALEN; - - /* wait until HXTAL is stable or the startup time is longer than HXTAL_STARTUP_TIMEOUT */ - do{ - timeout++; - stab_flag = (RCU_CTL & RCU_CTL_HXTALSTB); - }while((0U == stab_flag) && (HXTAL_STARTUP_TIMEOUT != timeout)); - - /* if fail */ - if(0U == (RCU_CTL & RCU_CTL_HXTALSTB)){ - while(1){ - } - } - - /* HXTAL is stable */ - /* AHB = SYSCLK */ - RCU_CFG0 |= RCU_AHB_CKSYS_DIV1; - /* APB2 = AHB/1 */ - RCU_CFG0 |= RCU_APB2_CKAHB_DIV1; - /* APB1 = AHB/2 */ - RCU_CFG0 |= RCU_APB1_CKAHB_DIV2; - - /* CK_PLL = (CK_PREDIV0) * 18 = 72 MHz */ - RCU_CFG0 &= ~(RCU_CFG0_PLLMF | RCU_CFG0_PLLMF_4); - RCU_CFG0 |= (RCU_PLLSRC_HXTAL | RCU_PLL_MUL18); - - - if(HXTAL_VALUE==25000000){ - - /* CK_PREDIV0 = (CK_HXTAL)/5 *8 /10 = 4 MHz */ - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV1 | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_CKPLL1 | RCU_PLL1_MUL8 | RCU_PREDV1_DIV5 | RCU_PREDV0_DIV10); - - /* enable PLL1 */ - RCU_CTL |= RCU_CTL_PLL1EN; - /* wait till PLL1 is ready */ - while((RCU_CTL & RCU_CTL_PLL1STB) == 0){ - } - - }else if(HXTAL_VALUE==8000000){ - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PREDV1 | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_HXTAL | RCU_PREDV0_DIV2 ); - } - - /* enable PLL */ - RCU_CTL |= RCU_CTL_PLLEN; - - /* wait until PLL is stable */ - while(0U == (RCU_CTL & RCU_CTL_PLLSTB)){ - } - - /* select PLL as system clock */ - RCU_CFG0 &= ~RCU_CFG0_SCS; - RCU_CFG0 |= RCU_CKSYSSRC_PLL; - - /* wait until PLL is selected as system clock */ - while(0U == (RCU_CFG0 & RCU_SCSS_PLL)){ - } -} - -#elif defined (__SYSTEM_CLOCK_96M_PLL_HXTAL) -/*! - \brief configure the system clock to 96M by PLL which selects HXTAL(MD/HD/XD:8M; CL:25M) as its clock source - \param[in] none - \param[out] none - \retval none -*/ -static void system_clock_96m_hxtal(void) -{ - uint32_t timeout = 0U; - uint32_t stab_flag = 0U; - - /* enable HXTAL */ - RCU_CTL |= RCU_CTL_HXTALEN; - - /* wait until HXTAL is stable or the startup time is longer than HXTAL_STARTUP_TIMEOUT */ - do{ - timeout++; - stab_flag = (RCU_CTL & RCU_CTL_HXTALSTB); - }while((0U == stab_flag) && (HXTAL_STARTUP_TIMEOUT != timeout)); - - /* if fail */ - if(0U == (RCU_CTL & RCU_CTL_HXTALSTB)){ - while(1){ - } - } - - /* HXTAL is stable */ - /* AHB = SYSCLK */ - RCU_CFG0 |= RCU_AHB_CKSYS_DIV1; - /* APB2 = AHB/1 */ - RCU_CFG0 |= RCU_APB2_CKAHB_DIV1; - /* APB1 = AHB/2 */ - RCU_CFG0 |= RCU_APB1_CKAHB_DIV2; - - if(HXTAL_VALUE==25000000){ - - /* CK_PLL = (CK_PREDIV0) * 24 = 96 MHz */ - RCU_CFG0 &= ~(RCU_CFG0_PLLMF | RCU_CFG0_PLLMF_4); - RCU_CFG0 |= (RCU_PLLSRC_HXTAL | RCU_PLL_MUL24); - - /* CK_PREDIV0 = (CK_HXTAL)/5 *8 /10 = 4 MHz */ - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV1 | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_CKPLL1 | RCU_PLL1_MUL8 | RCU_PREDV1_DIV5 | RCU_PREDV0_DIV10); - /* enable PLL1 */ - RCU_CTL |= RCU_CTL_PLL1EN; - /* wait till PLL1 is ready */ - while((RCU_CTL & RCU_CTL_PLL1STB) == 0){ - } - - }else if(HXTAL_VALUE==8000000){ - /* CK_PLL = (CK_PREDIV0) * 24 = 96 MHz */ - RCU_CFG0 &= ~(RCU_CFG0_PLLMF | RCU_CFG0_PLLMF_4); - RCU_CFG0 |= (RCU_PLLSRC_HXTAL | RCU_PLL_MUL24); - - RCU_CFG1 &= ~(RCU_CFG1_PREDV0SEL | RCU_CFG1_PREDV1 | RCU_CFG1_PLL1MF | RCU_CFG1_PREDV0); - RCU_CFG1 |= (RCU_PREDV0SRC_HXTAL | RCU_PREDV0_DIV2 ); - } - - /* enable PLL */ - RCU_CTL |= RCU_CTL_PLLEN; - - /* wait until PLL is stable */ - while(0U == (RCU_CTL & RCU_CTL_PLLSTB)){ - } - - /* select PLL as system clock */ - RCU_CFG0 &= ~RCU_CFG0_SCS; - RCU_CFG0 |= RCU_CKSYSSRC_PLL; - - /* wait until PLL is selected as system clock */ - while(0U == (RCU_CFG0 & RCU_SCSS_PLL)){ - } -} - -#endif - -/** - * \defgroup NMSIS_Core_IntExcNMI_Handling Interrupt and Exception and NMI Handling - * \brief Functions for interrupt, exception and nmi handle available in system_<device>.c. - * \details - * Nuclei provide a template for interrupt, exception and NMI handling. Silicon Vendor could adapat according - * to their requirement. Silicon vendor could implement interface for different exception code and - * replace current implementation. - * - * @{ - */ -/** \brief Max exception handler number, don't include the NMI(0xFFF) one */ -#define MAX_SYSTEM_EXCEPTION_NUM 12 -/** - * \brief Store the exception handlers for each exception ID - * \note - * - This SystemExceptionHandlers are used to store all the handlers for all - * the exception codes Nuclei N/NX core provided. - * - Exception code 0 - 11, totally 12 exceptions are mapped to SystemExceptionHandlers[0:11] - * - Exception for NMI is also re-routed to exception handling(exception code 0xFFF) in startup code configuration, the handler itself is mapped to SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM] - */ -static unsigned long SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM + 1]; - -/** - * \brief Exception Handler Function Typedef - * \note - * This typedef is only used internal in this system_gd32vf103.c file. - * It is used to do type conversion for registered exception handler before calling it. - */ -typedef void (*EXC_HANDLER)(unsigned long mcause, unsigned long sp); - -/** - * \brief System Default Exception Handler - * \details - * This function provided a default exception and NMI handling code for all exception ids. - * By default, It will just print some information for debug, Vendor can customize it according to its requirements. - */ -static void system_default_exception_handler(unsigned long mcause, unsigned long sp) -{ - /* TODO: Uncomment this if you have implement printf function */ - /*printf("MCAUSE: 0x%lx\r\n", mcause); - printf("MEPC : 0x%lx\r\n", __RV_CSR_READ(CSR_MEPC)); - printf("MTVAL : 0x%lx\r\n", __RV_CSR_READ(CSR_MBADADDR));*/ - while (1); -} - -/** - * \brief Initialize all the default core exception handlers - * \details - * The core exception handler for each exception id will be initialized to \ref system_default_exception_handler. - * \note - * Called in \ref _init function, used to initialize default exception handlers for all exception IDs - */ -static void Exception_Init(void) -{ - for (int i = 0; i < MAX_SYSTEM_EXCEPTION_NUM + 1; i++) { - SystemExceptionHandlers[i] = (unsigned long)system_default_exception_handler; - } -} - -/** - * \brief Register an exception handler for exception code EXCn - * \details - * * For EXCn < \ref MAX_SYSTEM_EXCEPTION_NUM, it will be registered into SystemExceptionHandlers[EXCn-1]. - * * For EXCn == NMI_EXCn, it will be registered into SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM]. - * \param EXCn See \ref EXCn_Type - * \param exc_handler The exception handler for this exception code EXCn - */ -void Exception_Register_EXC(uint32_t EXCn, unsigned long exc_handler) -{ - if ((EXCn < MAX_SYSTEM_EXCEPTION_NUM) && (EXCn != 0)) { - SystemExceptionHandlers[EXCn] = exc_handler; - } else if (EXCn == NMI_EXCn) { - SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM] = exc_handler; - } -} - -/** - * \brief Get current exception handler for exception code EXCn - * \details - * * For EXCn < \ref MAX_SYSTEM_EXCEPTION_NUM, it will return SystemExceptionHandlers[EXCn-1]. - * * For EXCn == NMI_EXCn, it will return SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM]. - * \param EXCn See \ref EXCn_Type - * \return Current exception handler for exception code EXCn, if not found, return 0. - */ -unsigned long Exception_Get_EXC(uint32_t EXCn) -{ - if ((EXCn < MAX_SYSTEM_EXCEPTION_NUM) && (EXCn != 0)) { - return SystemExceptionHandlers[EXCn]; - } else if (EXCn == NMI_EXCn) { - return SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM]; - } else { - return 0; - } -} - -/** - * \brief Common NMI and Exception handler entry - * \details - * This function provided a command entry for NMI and exception. Silicon Vendor could modify - * this template implementation according to requirement. - * \remarks - * - RISCV provided common entry for all types of exception. This is proposed code template - * for exception entry function, Silicon Vendor could modify the implementation. - * - For the core_exception_handler template, we provided exception register function \ref Exception_Register_EXC - * which can help developer to register your exception handler for specific exception number. - */ -uint32_t core_exception_handler(unsigned long mcause, unsigned long sp) -{ - uint32_t EXCn = (uint32_t)(mcause & 0X00000fff); - EXC_HANDLER exc_handler; - - if ((EXCn < MAX_SYSTEM_EXCEPTION_NUM) && (EXCn > 0)) { - exc_handler = (EXC_HANDLER)SystemExceptionHandlers[EXCn]; - } else if (EXCn == NMI_EXCn) { - exc_handler = (EXC_HANDLER)SystemExceptionHandlers[MAX_SYSTEM_EXCEPTION_NUM]; - } else { - exc_handler = (EXC_HANDLER)system_default_exception_handler; - } - if (exc_handler != NULL) { - exc_handler(mcause, sp); - } - return 0; -} -/** @} */ /* End of Doxygen Group NMSIS_Core_ExceptionAndNMI */ - -/** - * \brief initialize eclic config - * \details - * Eclic need initialize after boot up, Vendor could also change the initialization - * configuration. - */ -void ECLIC_Init(void) -{ - /* TODO: Add your own initialization code here. This function will be called by main */ - ECLIC_SetMth(0); - ECLIC_SetCfgNlbits(__ECLIC_INTCTLBITS); -} - -/** - * \brief Initialize a specific IRQ and register the handler - * \details - * This function set vector mode, trigger mode and polarity, interrupt level and priority, - * assign handler for specific IRQn. - * \param [in] IRQn NMI interrupt handler address - * \param [in] shv \ref ECLIC_NON_VECTOR_INTERRUPT means non-vector mode, and \ref ECLIC_VECTOR_INTERRUPT is vector mode - * \param [in] trig_mode see \ref ECLIC_TRIGGER_Type - * \param [in] lvl interupt level - * \param [in] priority interrupt priority - * \param [in] handler interrupt handler, if NULL, handler will not be installed - * \return -1 means invalid input parameter. 0 means successful. - * \remarks - * - This function use to configure specific eclic interrupt and register its interrupt handler and enable its interrupt. - * - If the vector table is placed in read-only section(FLASHXIP mode), handler could not be installed - */ -int32_t ECLIC_Register_IRQ(IRQn_Type IRQn, uint8_t shv, ECLIC_TRIGGER_Type trig_mode, uint8_t lvl, uint8_t priority, void* handler) -{ - if ((IRQn > SOC_INT_MAX) || (shv > ECLIC_VECTOR_INTERRUPT) \ - || (trig_mode > ECLIC_NEGTIVE_EDGE_TRIGGER)) { - return -1; - } - - /* set interrupt vector mode */ - ECLIC_SetShvIRQ(IRQn, shv); - /* set interrupt trigger mode and polarity */ - ECLIC_SetTrigIRQ(IRQn, trig_mode); - /* set interrupt level */ - ECLIC_SetLevelIRQ(IRQn, lvl); - /* set interrupt priority */ - ECLIC_SetPriorityIRQ(IRQn, priority); - if (handler != NULL) { - /* set interrupt handler entry to vector table */ - ECLIC_SetVector(IRQn, (rv_csr_t)handler); - } - /* enable interrupt */ - ECLIC_EnableIRQ(IRQn); - return 0; -} -/** @} */ /* End of Doxygen Group NMSIS_Core_ExceptionAndNMI */ - -/** - * \brief early init function before main - * \details - * This function is executed right before main function. - * For RISC-V gnu toolchain, _init function might not be called - * by __libc_init_array function, so we defined a new function - * to do initialization - */ -void _premain_init(void) -{ - /* Initialize exception default handlers */ - Exception_Init(); - /* ECLIC initialization, mainly MTH and NLBIT */ - ECLIC_Init(); -} - -/** - * \brief finish function after main - * \param [in] status status code return from main - * \details - * This function is executed right after main function. - * For RISC-V gnu toolchain, _fini function might not be called - * by __libc_fini_array function, so we defined a new function - * to do initialization - */ -void _postmain_fini(int status) -{ - /* TODO: Add your own finishing code here, called after main */ -} - -/** - * \brief _init function called in __libc_init_array() - * \details - * This `__libc_init_array()` function is called during startup code, - * user need to implement this function, otherwise when link it will - * error init.c:(.text.__libc_init_array+0x26): undefined reference to `_init' - * \note - * Please use \ref _premain_init function now - */ -void _init(void) -{ - /* Don't put any code here, please use _premain_init now */ -} - -/** - * \brief _fini function called in __libc_fini_array() - * \details - * This `__libc_fini_array()` function is called when exit main. - * user need to implement this function, otherwise when link it will - * error fini.c:(.text.__libc_fini_array+0x28): undefined reference to `_fini' - * \note - * Please use \ref _postmain_fini function now - */ -void _fini(void) -{ - /* Don't put any code here, please use _postmain_fini now */ -} - -/** @} */ /* End of Doxygen Group NMSIS_Core_SystemAndClock */ |