1
0
forked from me/IronOS

Poking I2C

This commit is contained in:
Ben V. Brown
2022-04-02 21:36:34 +11:00
parent 4cacc063d3
commit bf4e57f7a3
240 changed files with 91264 additions and 45415 deletions

View File

@@ -1,6 +1,7 @@
#ifndef FREERTOS_CONFIG_H
#define FREERTOS_CONFIG_H
#include <stdint.h>
#define portCHAR char
#define configSUPPORT_STATIC_ALLOCATION 1
#define configSUPPORT_DYNAMIC_ALLOCATION 0
@@ -67,8 +68,6 @@ void vApplicationSleep(uint32_t xExpectedIdleTime);
#define portSUPPRESS_TICKS_AND_SLEEP(xExpectedIdleTime) vApplicationSleep(xExpectedIdleTime)
#endif
#define portUSING_MPU_WRAPPERS 0
#define INCLUDE_vTaskPrioritySet 1
#define INCLUDE_uxTaskPriorityGet 1
#define INCLUDE_vTaskDelete 1

View File

@@ -7,6 +7,10 @@
#include "BSP.h"
#include "IRQ.h"
#include "Setup.h"
extern "C" {
#include "bl702_glb.h"
#include "bl702_i2c.h"
}
#include <I2C_Wrapper.hpp>
SemaphoreHandle_t FRToSI2C::I2CSemaphore = nullptr;
@@ -27,7 +31,18 @@ uint8_t FRToSI2C::I2C_RegisterRead(uint8_t add, uint8_t reg) {
bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t read_address, uint8_t *p_buffer, uint16_t number_of_byte) {
if (!lock())
return false;
bool res = false; // perform_i2c_transaction(DevAddress, read_address, p_buffer, number_of_byte, false, false);
I2C_Transfer_Cfg i2cCfg = {0, DISABLE, 0, 0, 0, 0};
BL_Err_Type err = ERROR;
i2cCfg.slaveAddr = DevAddress;
i2cCfg.stopEveryByte = DISABLE;
i2cCfg.subAddr = read_address;
i2cCfg.dataSize = number_of_byte;
i2cCfg.data = p_buffer;
i2cCfg.subAddrSize = 1; // one byte address
err = I2C_MasterReceiveBlocking(I2C0_ID, &i2cCfg);
bool res = err == SUCCESS;
if (!res) {
I2C_Unstick();
}
@@ -38,7 +53,18 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t read_address, uint8_t *p_b
bool FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress, uint8_t *p_buffer, uint16_t number_of_byte) {
if (!lock())
return false;
bool res = false; // perform_i2c_transaction(DevAddress, MemAddress, p_buffer, number_of_byte, true, false);
I2C_Transfer_Cfg i2cCfg = {0, DISABLE, 0, 0, 0, 0};
BL_Err_Type err = ERROR;
i2cCfg.slaveAddr = DevAddress;
i2cCfg.stopEveryByte = DISABLE;
i2cCfg.subAddr = MemAddress;
i2cCfg.dataSize = number_of_byte;
i2cCfg.data = p_buffer;
i2cCfg.subAddrSize = 1; // one byte address
err = I2C_MasterSendBlocking(I2C0_ID, &i2cCfg);
bool res = err == SUCCESS;
if (!res) {
I2C_Unstick();
}
@@ -80,7 +106,18 @@ bool FRToSI2C::wakePart(uint16_t DevAddress) {
// wakepart is a special case where only the device address is sent
if (!lock())
return false;
bool res = false; // perform_i2c_transaction(DevAddress, 0, NULL, 0, false, true);
I2C_Transfer_Cfg i2cCfg = {0, DISABLE, 0, 0, 0, 0};
BL_Err_Type err = ERROR;
i2cCfg.slaveAddr = DevAddress;
i2cCfg.stopEveryByte = DISABLE;
i2cCfg.subAddr = 0;
i2cCfg.dataSize = 0;
i2cCfg.data = 0;
i2cCfg.subAddrSize = 0; // one byte address
err = I2C_MasterReceiveBlocking(I2C0_ID, &i2cCfg);
bool res = err == SUCCESS;
if (!res) {
I2C_Unstick();
}

View File

@@ -76,12 +76,12 @@ void ADC0_1_IRQHandler(void) {
// // TIMER_CH0CV(TIMER1) = powerPWM + holdoffTicks / 2;
// // TIMER_PSC(TIMER1) = 36000;
// }
// void setTipPWM(const uint8_t pulse, const bool shouldUseFastModePWM) {
// // PWMSafetyTimer = 10; // This is decremented in the handler for PWM so that the tip pwm is
// // // disabled if the PID task is not scheduled often enough.
// // pendingPWM = pulse;
// // fastPWM = shouldUseFastModePWM;
// }
void setTipPWM(const uint8_t pulse, const bool shouldUseFastModePWM) {
// // PWMSafetyTimer = 10; // This is decremented in the handler for PWM so that the tip pwm is
// // // disabled if the PID task is not scheduled often enough.
// // pendingPWM = pulse;
// // fastPWM = shouldUseFastModePWM;
}
extern osThreadId POWTaskHandle;
// void EXTI5_9_IRQHandler(void) {

View File

@@ -7,53 +7,32 @@
#ifndef BSP_PINE64_PINS_H_
#define BSP_PINE64_PINS_H_
#include "hal_gpio.h"
#define KEY_B_Pin GPIO_PIN_25
#define TMP36_INPUT_Pin GPIO_PIN_20
#define TMP36_ADC_CHANNEL
#define TIP_TEMP_Pin GPIO_PIN_19
#define TIP_TEMP_ADC_CHANNEL
// #define KEY_B_Pin BIT(1)
// #define KEY_B_GPIO_Port GPIOB
// #define TMP36_INPUT_Pin BIT(4)
// #define TMP36_INPUT_GPIO_Port GPIOA
// #define TMP36_ADC0_CHANNEL ADC_CHANNEL_4
// #define TMP36_ADC1_CHANNEL ADC_CHANNEL_4
// #define TIP_TEMP_Pin BIT(1)
// #define TIP_TEMP_GPIO_Port GPIOA
// #define TIP_TEMP_ADC0_CHANNEL ADC_CHANNEL_1
// #define TIP_TEMP_ADC1_CHANNEL ADC_CHANNEL_1
#define VIN_Pin GPIO_PIN_18
#define VIN_ADC_CHANNEL
#define OLED_RESET_Pin GPIO_PIN_3
#define KEY_A_Pin GPIO_PIN_28
#define PWM_Out_Pin GPIO_PIN_21
#define SCL_Pin GPIO_PIN_11
#define SDA_Pin GPIO_PIN_10
// #define VIN_Pin BIT(0)
// #define VIN_GPIO_Port GPIOA
// #define VIN_ADC0_CHANNEL ADC_CHANNEL_0
// #define VIN_ADC1_CHANNEL ADC_CHANNEL_0
// #define OLED_RESET_Pin BIT(9)
// #define OLED_RESET_GPIO_Port GPIOA
// #define KEY_A_Pin BIT(0)
// #define KEY_A_GPIO_Port GPIOB
// #define PWM_Out_Pin BIT(6)
// #define PWM_Out_GPIO_Port GPIOA
// #define SCL_Pin BIT(6)
// #define SCL_GPIO_Port GPIOB
// #define SDA_Pin BIT(7)
// #define SDA_GPIO_Port GPIOB
// #define USB_DM_Pin GPIO_PIN_8
#define QC_DP_LOW_Pin GPIO_PIN_5
// #define USB_DM_Pin BIT(11)
// #define USB_DM_LOW_GPIO_Port GPIOA
// LOW = low resistance, HIGH = high resistance
#define QC_DM_LOW_Pin GPIO_PIN_4
#define QC_DM_HIGH_Pin GPIO_PIN_6
// #define QC_DP_LOW_Pin BIT(7)
// #define QC_DP_LOW_GPIO_Port GPIOA
#define FUSB302_IRQ_Pin GPIO_PIN_16
// // LOW = low resistance, HIGH = high resistance
// #define QC_DM_LOW_Pin BIT(8)
// #define QC_DM_LOW_GPIO_Port GPIOA
// #define QC_DM_HIGH_Pin BIT(10)
// #define QC_DM_HIGH_GPIO_Port GPIOA
// #define FUSB302_IRQ_Pin BIT(5)
// #define FUSB302_IRQ_GPIO_Port GPIOB
// // uart
// #define UART_TX_Pin BIT(2)
// #define UART_TX_GPIO_Port GPIOA
// #define UART_RX_Pin BIT(3)
// #define UART_RX_GPIO_Port GPIOA
// #define UART_PERIF USART1
// uart
#define UART_TX_Pin GPIO_PIN_22
#define UART_RX_Pin GPIO_PIN_23
#endif /* BSP_PINE64_PINS_H_ */

View File

@@ -9,7 +9,10 @@
#include "Debug.h"
#include "FreeRTOSConfig.h"
#include "Pins.h"
extern "C" {
#include "bflb_platform.h"
#include "bl702_i2c.h"
}
#include "history.hpp"
#include <string.h>
#define ADC_NORM_SAMPLES 16
@@ -20,6 +23,10 @@ uint16_t ADCReadings[ADC_NORM_SAMPLES]; // room for 32 lots of the pair of readi
void hardware_init() {
// #TODO
gpio_set_mode(OLED_RESET_Pin, GPIO_OUTPUT_MODE);
gpio_set_mode(KEY_A_Pin, GPIO_INPUT_PD_MODE);
gpio_set_mode(KEY_B_Pin, GPIO_INPUT_PD_MODE);
I2C_SetPrd(I2C0_ID, 15);
}
uint16_t getADCHandleTemp(uint8_t sample) {

View File

@@ -21,8 +21,8 @@
*
*/
#ifndef __BL602_CONFIG_H__
#define __BL602_CONFIG_H__
#ifndef __BL702_CONFIG_H__
#define __BL702_CONFIG_H__
#include "clock_config.h"
#include "peripheral_config.h"

View File

@@ -0,0 +1,112 @@
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
#ifndef FREERTOS_CONFIG_H
#define FREERTOS_CONFIG_H
/*-----------------------------------------------------------
* Application specific definitions.
*
* These definitions should be adjusted for your particular hardware and
* application requirements.
*
* THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE
* FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE.
*
* See http://www.freertos.org/a00110.html.
*----------------------------------------------------------*/
#define configSUPPORT_STATIC_ALLOCATION 1
#define CLINT_CTRL_ADDR (0x02000000UL)
#define configCLINT_BASE_ADDRESS CLINT_CTRL_ADDR
#define configUSE_PREEMPTION 1
#define configUSE_IDLE_HOOK 0
#define configUSE_TICK_HOOK 0
#define configCPU_CLOCK_HZ (1000000UL)
#define configTICK_RATE_HZ ((TickType_t)1000)
#define configMAX_PRIORITIES (7)
#define configMINIMAL_STACK_SIZE ((unsigned short)512) /* Only needs to be this high as some demo tasks also use this constant. In production only the idle task would use this. */
#define configTOTAL_HEAP_SIZE ((size_t)48 * 1024)
#define configMAX_TASK_NAME_LEN (16)
#define configUSE_TRACE_FACILITY 1
#define configUSE_16_BIT_TICKS 0
#define configIDLE_SHOULD_YIELD 0
#define configUSE_MUTEXES 1
#define configQUEUE_REGISTRY_SIZE 8
#define configCHECK_FOR_STACK_OVERFLOW 2
#define configUSE_RECURSIVE_MUTEXES 1
#define configUSE_MALLOC_FAILED_HOOK 1
#define configUSE_APPLICATION_TASK_TAG 0
#define configUSE_COUNTING_SEMAPHORES 1
#define configGENERATE_RUN_TIME_STATS 0
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1
#define configUSE_STATS_FORMATTING_FUNCTIONS 2
#define configUSE_TICKLESS_IDLE 0
/* Co-routine definitions. */
#define configUSE_CO_ROUTINES 0
#define configMAX_CO_ROUTINE_PRIORITIES (2)
/* Software timer definitions. */
#define configUSE_TIMERS 1
#define configTIMER_TASK_PRIORITY (configMAX_PRIORITIES - 1)
#define configTIMER_QUEUE_LENGTH 8
#define configTIMER_TASK_STACK_DEPTH (160)
/* Task priorities. Allow these to be overridden. */
#ifndef uartPRIMARY_PRIORITY
#define uartPRIMARY_PRIORITY (configMAX_PRIORITIES - 3)
#endif
/* Set the following definitions to 1 to include the API function, or zero
to exclude the API function. */
#define INCLUDE_vTaskPrioritySet 1
#define INCLUDE_uxTaskPriorityGet 1
#define INCLUDE_vTaskDelete 1
#define INCLUDE_vTaskCleanUpResources 1
#define INCLUDE_vTaskSuspend 1
#define INCLUDE_vTaskDelayUntil 1
#define INCLUDE_vTaskDelay 1
#define INCLUDE_eTaskGetState 1
#define INCLUDE_xTimerPendFunctionCall 1
#define INCLUDE_xTaskAbortDelay 1
#define INCLUDE_xTaskGetHandle 1
#define INCLUDE_xSemaphoreGetMutexHolder 1
/* Normal assert() semantics without relying on the provision of an assert.h
header file. */
void vAssertCalled(void);
#define configASSERT(x) \
if ((x) == 0) \
vAssertCalled()
#if (configUSE_TICKLESS_IDLE != 0)
void vApplicationSleep(uint32_t xExpectedIdleTime);
#define portSUPPRESS_TICKS_AND_SLEEP(xExpectedIdleTime) vApplicationSleep(xExpectedIdleTime)
#endif
#define portUSING_MPU_WRAPPERS 0
#endif /* FREERTOS_CONFIG_H */

View File

@@ -1,67 +1,67 @@
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*
* The FreeRTOS kernel's RISC-V port is split between the the code that is
* common across all currently supported RISC-V chips (implementations of the
* RISC-V ISA), and code that tailors the port to a specific RISC-V chip:
*
* + FreeRTOS\Source\portable\GCC\RISC-V-RV32\portASM.S contains the code that
* is common to all currently supported RISC-V chips. There is only one
* portASM.S file because the same file is built for all RISC-V target chips.
*
* + Header files called freertos_risc_v_chip_specific_extensions.h contain the
* code that tailors the FreeRTOS kernel's RISC-V port to a specific RISC-V
* chip. There are multiple freertos_risc_v_chip_specific_extensions.h files
* as there are multiple RISC-V chip implementations.
*
* !!!NOTE!!!
* TAKE CARE TO INCLUDE THE CORRECT freertos_risc_v_chip_specific_extensions.h
* HEADER FILE FOR THE CHIP IN USE. This is done using the assembler's (not the
* compiler's!) include path. For example, if the chip in use includes a core
* local interrupter (CLINT) and does not include any chip specific register
* extensions then add the path below to the assembler's include path:
* FreeRTOS\Source\portable\GCC\RISC-V-RV32\chip_specific_extensions\RV32I_CLINT_no_extensions
*
*/
#ifndef __FREERTOS_RISC_V_EXTENSIONS_H__
#define __FREERTOS_RISC_V_EXTENSIONS_H__
#define portasmHAS_CLINT 1
#define portasmADDITIONAL_CONTEXT_SIZE 0 /* Must be even number on 32-bit cores. */
.macro portasmSAVE_ADDITIONAL_REGISTERS
/* No additional registers to save, so this macro does nothing. */
.endm
/* Restore the additional registers found on the Pulpino. */
.macro portasmRESTORE_ADDITIONAL_REGISTERS
/* No additional registers to restore, so this macro does nothing. */
.endm
#endif /* __FREERTOS_RISC_V_EXTENSIONS_H__ */
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*
* The FreeRTOS kernel's RISC-V port is split between the the code that is
* common across all currently supported RISC-V chips (implementations of the
* RISC-V ISA), and code that tailors the port to a specific RISC-V chip:
*
* + FreeRTOS\Source\portable\GCC\RISC-V-RV32\portASM.S contains the code that
* is common to all currently supported RISC-V chips. There is only one
* portASM.S file because the same file is built for all RISC-V target chips.
*
* + Header files called freertos_risc_v_chip_specific_extensions.h contain the
* code that tailors the FreeRTOS kernel's RISC-V port to a specific RISC-V
* chip. There are multiple freertos_risc_v_chip_specific_extensions.h files
* as there are multiple RISC-V chip implementations.
*
* !!!NOTE!!!
* TAKE CARE TO INCLUDE THE CORRECT freertos_risc_v_chip_specific_extensions.h
* HEADER FILE FOR THE CHIP IN USE. This is done using the assembler's (not the
* compiler's!) include path. For example, if the chip in use includes a core
* local interrupter (CLINT) and does not include any chip specific register
* extensions then add the path below to the assembler's include path:
* FreeRTOS\Source\portable\GCC\RISC-V-RV32\chip_specific_extensions\RV32I_CLINT_no_extensions
*
*/
#ifndef __FREERTOS_RISC_V_EXTENSIONS_H__
#define __FREERTOS_RISC_V_EXTENSIONS_H__
#define portasmHAS_CLINT 1
#define portasmADDITIONAL_CONTEXT_SIZE 0 /* Must be even number on 32-bit cores. */
.macro portasmSAVE_ADDITIONAL_REGISTERS
/* No additional registers to save, so this macro does nothing. */
.endm
/* Restore the additional registers found on the Pulpino. */
.macro portasmRESTORE_ADDITIONAL_REGISTERS
/* No additional registers to restore, so this macro does nothing. */
.endm
#endif /* __FREERTOS_RISC_V_EXTENSIONS_H__ */

View File

@@ -1,195 +1,195 @@
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*-----------------------------------------------------------
* Implementation of functions defined in portable.h for the RISC-V RV32 port.
*----------------------------------------------------------*/
/* Scheduler includes. */
#include "FreeRTOS.h"
#include "task.h"
#include "portmacro.h"
#ifndef configCLINT_BASE_ADDRESS
#warning configCLINT_BASE_ADDRESS must be defined in FreeRTOSConfig.h. If the target chip includes a Core Local Interrupter (CLINT) then set configCLINT_BASE_ADDRESS to the CLINT base address. Otherwise set configCLINT_BASE_ADDRESS to 0.
#endif
/* Let the user override the pre-loading of the initial LR with the address of
prvTaskExitError() in case it messes up unwinding of the stack in the
debugger. */
#ifdef configTASK_RETURN_ADDRESS
#define portTASK_RETURN_ADDRESS configTASK_RETURN_ADDRESS
#else
#define portTASK_RETURN_ADDRESS prvTaskExitError
#endif
/* The stack used by interrupt service routines. Set configISR_STACK_SIZE_WORDS
to use a statically allocated array as the interrupt stack. Alternative leave
configISR_STACK_SIZE_WORDS undefined and update the linker script so that a
linker variable names __freertos_irq_stack_top has the same value as the top
of the stack used by main. Using the linker script method will repurpose the
stack that was used by main before the scheduler was started for use as the
interrupt stack after the scheduler has started. */
#ifdef configISR_STACK_SIZE_WORDS
static __attribute__((aligned(16))) StackType_t xISRStack[configISR_STACK_SIZE_WORDS] = { 0 };
const StackType_t xISRStackTop = (StackType_t) & (xISRStack[configISR_STACK_SIZE_WORDS & ~portBYTE_ALIGNMENT_MASK]);
#else
extern const uint32_t __freertos_irq_stack_top[];
const StackType_t xISRStackTop = (StackType_t)__freertos_irq_stack_top;
#endif
/*
* Setup the timer to generate the tick interrupts. The implementation in this
* file is weak to allow application writers to change the timer used to
* generate the tick interrupt.
*/
void vPortSetupTimerInterrupt(void) __attribute__((weak));
/*-----------------------------------------------------------*/
/* Used to program the machine timer compare register. */
uint64_t ullNextTime = 0ULL;
const uint64_t *pullNextTime = &ullNextTime;
const size_t uxTimerIncrementsForOneTick = (size_t)(configCPU_CLOCK_HZ / configTICK_RATE_HZ); /* Assumes increment won't go over 32-bits. */
volatile uint64_t *const pullMachineTimerCompareRegisterBase = (volatile uint64_t *const)(configCLINT_BASE_ADDRESS + 0x4000);
volatile uint64_t *pullMachineTimerCompareRegister = 0;
BaseType_t TrapNetCounter = 0;
const BaseType_t *pTrapNetCounter = &TrapNetCounter;
/* Set configCHECK_FOR_STACK_OVERFLOW to 3 to add ISR stack checking to task
stack checking. A problem in the ISR stack will trigger an assert, not call the
stack overflow hook function (because the stack overflow hook is specific to a
task stack, not the ISR stack). */
#if (configCHECK_FOR_STACK_OVERFLOW > 2)
#warning This path not tested, or even compiled yet.
/* Don't use 0xa5 as the stack fill bytes as that is used by the kernerl for
the task stacks, and so will legitimately appear in many positions within
the ISR stack. */
#define portISR_STACK_FILL_BYTE 0xee
static const uint8_t ucExpectedStackBytes[] = {
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE
};
#define portCHECK_ISR_STACK() configASSERT((memcmp((void *)xISRStack, (void *)ucExpectedStackBytes, sizeof(ucExpectedStackBytes)) == 0))
#else
/* Define the function away. */
#define portCHECK_ISR_STACK()
#endif /* configCHECK_FOR_STACK_OVERFLOW > 2 */
/*-----------------------------------------------------------*/
#if (configCLINT_BASE_ADDRESS != 0)
void vPortSetupTimerInterrupt(void)
{
uint32_t ulCurrentTimeHigh, ulCurrentTimeLow;
volatile uint32_t *const pulTimeHigh = (volatile uint32_t *const)(configCLINT_BASE_ADDRESS + 0xBFFC);
volatile uint32_t *const pulTimeLow = (volatile uint32_t *const)(configCLINT_BASE_ADDRESS + 0xBFF8);
volatile uint32_t ulHartId = 0;
__asm volatile("csrr %0, mhartid"
: "=r"(ulHartId));
pullMachineTimerCompareRegister = &(pullMachineTimerCompareRegisterBase[ulHartId]);
do {
ulCurrentTimeHigh = *pulTimeHigh;
ulCurrentTimeLow = *pulTimeLow;
} while (ulCurrentTimeHigh != *pulTimeHigh);
ullNextTime = (uint64_t)ulCurrentTimeHigh;
ullNextTime <<= 32ULL;
ullNextTime |= (uint64_t)ulCurrentTimeLow;
ullNextTime += (uint64_t)uxTimerIncrementsForOneTick;
*pullMachineTimerCompareRegister = ullNextTime;
/* Prepare the time to use after the next tick interrupt. */
ullNextTime += (uint64_t)uxTimerIncrementsForOneTick;
}
#endif /* ( configCLINT_BASE_ADDRESS != 0 ) */
/*-----------------------------------------------------------*/
BaseType_t xPortStartScheduler(void)
{
extern void xPortStartFirstTask(void);
#if (configASSERT_DEFINED == 1)
{
volatile uint32_t mtvec = 0;
/* Check the least significant two bits of mtvec are 00 - indicating
single vector mode. */
__asm volatile("csrr %0, mtvec"
: "=r"(mtvec));
//configASSERT( ( mtvec & 0x03UL ) == 0 );
/* Check alignment of the interrupt stack - which is the same as the
stack that was being used by main() prior to the scheduler being
started. */
configASSERT((xISRStackTop & portBYTE_ALIGNMENT_MASK) == 0);
}
#endif /* configASSERT_DEFINED */
/* If there is a CLINT then it is ok to use the default implementation
in this file, otherwise vPortSetupTimerInterrupt() must be implemented to
configure whichever clock is to be used to generate the tick interrupt. */
vPortSetupTimerInterrupt();
#if (configCLINT_BASE_ADDRESS != 0)
{
/* Enable mtime and external interrupts. 1<<7 for timer interrupt, 1<<11
for external interrupt. _RB_ What happens here when mtime is not present as
with pulpino? */
__asm volatile("csrs mie, %0" ::"r"(0x880));
}
#else
{
/* Enable external interrupts. */
__asm volatile("csrs mie, %0" ::"r"(0x800));
}
#endif /* configCLINT_BASE_ADDRESS */
*(uint8_t *)(0x02800400 + 7) = 1;
xPortStartFirstTask();
/* Should not get here as after calling xPortStartFirstTask() only tasks
should be executing. */
return pdFAIL;
}
/*-----------------------------------------------------------*/
void vPortEndScheduler(void)
{
/* Not implemented. */
for (;;)
;
}
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*-----------------------------------------------------------
* Implementation of functions defined in portable.h for the RISC-V RV32 port.
*----------------------------------------------------------*/
/* Scheduler includes. */
#include "FreeRTOS.h"
#include "task.h"
#include "portmacro.h"
#ifndef configCLINT_BASE_ADDRESS
#warning configCLINT_BASE_ADDRESS must be defined in FreeRTOSConfig.h. If the target chip includes a Core Local Interrupter (CLINT) then set configCLINT_BASE_ADDRESS to the CLINT base address. Otherwise set configCLINT_BASE_ADDRESS to 0.
#endif
/* Let the user override the pre-loading of the initial LR with the address of
prvTaskExitError() in case it messes up unwinding of the stack in the
debugger. */
#ifdef configTASK_RETURN_ADDRESS
#define portTASK_RETURN_ADDRESS configTASK_RETURN_ADDRESS
#else
#define portTASK_RETURN_ADDRESS prvTaskExitError
#endif
/* The stack used by interrupt service routines. Set configISR_STACK_SIZE_WORDS
to use a statically allocated array as the interrupt stack. Alternative leave
configISR_STACK_SIZE_WORDS undefined and update the linker script so that a
linker variable names __freertos_irq_stack_top has the same value as the top
of the stack used by main. Using the linker script method will repurpose the
stack that was used by main before the scheduler was started for use as the
interrupt stack after the scheduler has started. */
#ifdef configISR_STACK_SIZE_WORDS
static __attribute__((aligned(16))) StackType_t xISRStack[configISR_STACK_SIZE_WORDS] = { 0 };
const StackType_t xISRStackTop = (StackType_t) & (xISRStack[configISR_STACK_SIZE_WORDS & ~portBYTE_ALIGNMENT_MASK]);
#else
extern const uint32_t __freertos_irq_stack_top[];
const StackType_t xISRStackTop = (StackType_t)__freertos_irq_stack_top;
#endif
/*
* Setup the timer to generate the tick interrupts. The implementation in this
* file is weak to allow application writers to change the timer used to
* generate the tick interrupt.
*/
void vPortSetupTimerInterrupt(void) __attribute__((weak));
/*-----------------------------------------------------------*/
/* Used to program the machine timer compare register. */
uint64_t ullNextTime = 0ULL;
const uint64_t *pullNextTime = &ullNextTime;
const size_t uxTimerIncrementsForOneTick = (size_t)(configCPU_CLOCK_HZ / configTICK_RATE_HZ); /* Assumes increment won't go over 32-bits. */
volatile uint64_t *const pullMachineTimerCompareRegisterBase = (volatile uint64_t *const)(configCLINT_BASE_ADDRESS + 0x4000);
volatile uint64_t *pullMachineTimerCompareRegister = 0;
BaseType_t TrapNetCounter = 0;
const BaseType_t *pTrapNetCounter = &TrapNetCounter;
/* Set configCHECK_FOR_STACK_OVERFLOW to 3 to add ISR stack checking to task
stack checking. A problem in the ISR stack will trigger an assert, not call the
stack overflow hook function (because the stack overflow hook is specific to a
task stack, not the ISR stack). */
#if (configCHECK_FOR_STACK_OVERFLOW > 2)
#warning This path not tested, or even compiled yet.
/* Don't use 0xa5 as the stack fill bytes as that is used by the kernerl for
the task stacks, and so will legitimately appear in many positions within
the ISR stack. */
#define portISR_STACK_FILL_BYTE 0xee
static const uint8_t ucExpectedStackBytes[] = {
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE,
portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE, portISR_STACK_FILL_BYTE
};
#define portCHECK_ISR_STACK() configASSERT((memcmp((void *)xISRStack, (void *)ucExpectedStackBytes, sizeof(ucExpectedStackBytes)) == 0))
#else
/* Define the function away. */
#define portCHECK_ISR_STACK()
#endif /* configCHECK_FOR_STACK_OVERFLOW > 2 */
/*-----------------------------------------------------------*/
#if (configCLINT_BASE_ADDRESS != 0)
void vPortSetupTimerInterrupt(void)
{
uint32_t ulCurrentTimeHigh, ulCurrentTimeLow;
volatile uint32_t *const pulTimeHigh = (volatile uint32_t *const)(configCLINT_BASE_ADDRESS + 0xBFFC);
volatile uint32_t *const pulTimeLow = (volatile uint32_t *const)(configCLINT_BASE_ADDRESS + 0xBFF8);
volatile uint32_t ulHartId = 0;
__asm volatile("csrr %0, mhartid"
: "=r"(ulHartId));
pullMachineTimerCompareRegister = &(pullMachineTimerCompareRegisterBase[ulHartId]);
do {
ulCurrentTimeHigh = *pulTimeHigh;
ulCurrentTimeLow = *pulTimeLow;
} while (ulCurrentTimeHigh != *pulTimeHigh);
ullNextTime = (uint64_t)ulCurrentTimeHigh;
ullNextTime <<= 32ULL;
ullNextTime |= (uint64_t)ulCurrentTimeLow;
ullNextTime += (uint64_t)uxTimerIncrementsForOneTick;
*pullMachineTimerCompareRegister = ullNextTime;
/* Prepare the time to use after the next tick interrupt. */
ullNextTime += (uint64_t)uxTimerIncrementsForOneTick;
}
#endif /* ( configCLINT_BASE_ADDRESS != 0 ) */
/*-----------------------------------------------------------*/
BaseType_t xPortStartScheduler(void)
{
extern void xPortStartFirstTask(void);
#if (configASSERT_DEFINED == 1)
{
volatile uint32_t mtvec = 0;
/* Check the least significant two bits of mtvec are 00 - indicating
single vector mode. */
__asm volatile("csrr %0, mtvec"
: "=r"(mtvec));
//configASSERT( ( mtvec & 0x03UL ) == 0 );
/* Check alignment of the interrupt stack - which is the same as the
stack that was being used by main() prior to the scheduler being
started. */
configASSERT((xISRStackTop & portBYTE_ALIGNMENT_MASK) == 0);
}
#endif /* configASSERT_DEFINED */
/* If there is a CLINT then it is ok to use the default implementation
in this file, otherwise vPortSetupTimerInterrupt() must be implemented to
configure whichever clock is to be used to generate the tick interrupt. */
vPortSetupTimerInterrupt();
#if (configCLINT_BASE_ADDRESS != 0)
{
/* Enable mtime and external interrupts. 1<<7 for timer interrupt, 1<<11
for external interrupt. _RB_ What happens here when mtime is not present as
with pulpino? */
__asm volatile("csrs mie, %0" ::"r"(0x880));
}
#else
{
/* Enable external interrupts. */
__asm volatile("csrs mie, %0" ::"r"(0x800));
}
#endif /* configCLINT_BASE_ADDRESS */
*(uint8_t *)(0x02800400 + 7) = 1;
xPortStartFirstTask();
/* Should not get here as after calling xPortStartFirstTask() only tasks
should be executing. */
return pdFAIL;
}
/*-----------------------------------------------------------*/
void vPortEndScheduler(void)
{
/* Not implemented. */
for (;;)
;
}

View File

@@ -1,452 +1,452 @@
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*
* The FreeRTOS kernel's RISC-V port is split between the the code that is
* common across all currently supported RISC-V chips (implementations of the
* RISC-V ISA), and code which tailors the port to a specific RISC-V chip:
*
* + The code that is common to all RISC-V chips is implemented in
* FreeRTOS\Source\portable\GCC\RISC-V-RV32\portASM.S. There is only one
* portASM.S file because the same file is used no matter which RISC-V chip is
* in use.
*
* + The code that tailors the kernel's RISC-V port to a specific RISC-V
* chip is implemented in freertos_risc_v_chip_specific_extensions.h. There
* is one freertos_risc_v_chip_specific_extensions.h that can be used with any
* RISC-V chip that both includes a standard CLINT and does not add to the
* base set of RISC-V registers. There are additional
* freertos_risc_v_chip_specific_extensions.h files for RISC-V implementations
* that do not include a standard CLINT or do add to the base set of RISC-V
* registers.
*
* CARE MUST BE TAKEN TO INCLDUE THE CORRECT
* freertos_risc_v_chip_specific_extensions.h HEADER FILE FOR THE CHIP
* IN USE. To include the correct freertos_risc_v_chip_specific_extensions.h
* header file ensure the path to the correct header file is in the assembler's
* include path.
*
* This freertos_risc_v_chip_specific_extensions.h is for use on RISC-V chips
* that include a standard CLINT and do not add to the base set of RISC-V
* registers.
*
*/
#if __riscv_xlen == 64
#define portWORD_SIZE 8
#define store_x sd
#define load_x ld
#elif __riscv_xlen == 32
#define store_x sw
#define load_x lw
#define portWORD_SIZE 4
#else
#error Assembler did not define __riscv_xlen
#endif
#include "freertos_risc_v_chip_specific_extensions.h"
/* Check the freertos_risc_v_chip_specific_extensions.h and/or command line
definitions. */
#ifndef portasmHAS_CLINT
#error freertos_risc_v_chip_specific_extensions.h must define portasmHAS_CLINT to either 1 (CLINT present) or 0 (clint not present).
#endif
#ifndef portasmHANDLE_INTERRUPT
#error portasmHANDLE_INTERRUPT must be defined to the function to be called to handle external/peripheral interrupts. portasmHANDLE_INTERRUPT can be defined on the assmbler command line or in the appropriate freertos_risc_v_chip_specific_extensions.h header file.
#endif
/* Only the standard core registers are stored by default. Any additional
registers must be saved by the portasmSAVE_ADDITIONAL_REGISTERS and
portasmRESTORE_ADDITIONAL_REGISTERS macros - which can be defined in a chip
specific version of freertos_risc_v_chip_specific_extensions.h. See the notes
at the top of this file. */
#define portCONTEXT_SIZE ( 30 * portWORD_SIZE )
.global xPortStartFirstTask
.global freertos_risc_v_trap_handler
.global pxPortInitialiseStack
.extern pxCurrentTCB
.extern ulPortTrapHandler
.extern vTaskSwitchContext
.extern xTaskIncrementTick
.extern Timer_IRQHandler
.extern pullMachineTimerCompareRegister
.extern pullNextTime
.extern pTrapNetCounter
.extern uxTimerIncrementsForOneTick /* size_t type so 32-bit on 32-bit core and 64-bits on 64-bit core. */
.extern xISRStackTop
.extern portasmHANDLE_INTERRUPT
.extern Trap_Handler
/*-----------------------------------------------------------*/
.align 8
.func
freertos_risc_v_trap_handler:
addi sp, sp, -portCONTEXT_SIZE
store_x x1, 1 * portWORD_SIZE( sp )
store_x x5, 2 * portWORD_SIZE( sp )
store_x x6, 3 * portWORD_SIZE( sp )
store_x x7, 4 * portWORD_SIZE( sp )
store_x x8, 5 * portWORD_SIZE( sp )
store_x x9, 6 * portWORD_SIZE( sp )
store_x x10, 7 * portWORD_SIZE( sp )
store_x x11, 8 * portWORD_SIZE( sp )
store_x x12, 9 * portWORD_SIZE( sp )
store_x x13, 10 * portWORD_SIZE( sp )
store_x x14, 11 * portWORD_SIZE( sp )
store_x x15, 12 * portWORD_SIZE( sp )
store_x x16, 13 * portWORD_SIZE( sp )
store_x x17, 14 * portWORD_SIZE( sp )
store_x x18, 15 * portWORD_SIZE( sp )
store_x x19, 16 * portWORD_SIZE( sp )
store_x x20, 17 * portWORD_SIZE( sp )
store_x x21, 18 * portWORD_SIZE( sp )
store_x x22, 19 * portWORD_SIZE( sp )
store_x x23, 20 * portWORD_SIZE( sp )
store_x x24, 21 * portWORD_SIZE( sp )
store_x x25, 22 * portWORD_SIZE( sp )
store_x x26, 23 * portWORD_SIZE( sp )
store_x x27, 24 * portWORD_SIZE( sp )
store_x x28, 25 * portWORD_SIZE( sp )
store_x x29, 26 * portWORD_SIZE( sp )
store_x x30, 27 * portWORD_SIZE( sp )
store_x x31, 28 * portWORD_SIZE( sp )
csrr t0, mstatus /* Required for MPIE bit. */
store_x t0, 29 * portWORD_SIZE( sp )
portasmSAVE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to save any registers unique to the RISC-V implementation. */
load_x t0, pTrapNetCounter
lw t1, 0( t0 )
addi t1, t1, 1
store_x t1, 0( t0 )
load_x t0, pxCurrentTCB /* Load pxCurrentTCB. */
store_x sp, 0( t0 ) /* Write sp to first TCB member. */
csrr a0, mcause
csrr a1, mepc
li t0, 0x80000FFF
and a0, a0, t0
test_if_asynchronous:
srli a2, a0, __riscv_xlen - 1 /* MSB of mcause is 1 if handing an asynchronous interrupt - shift to LSB to clear other bits. */
beq a2, x0, handle_synchronous /* Branch past interrupt handing if not asynchronous. */
store_x a1, 0( sp ) /* Asynch so save unmodified exception return address. */
handle_asynchronous:
#if( portasmHAS_CLINT != 0 )
test_if_mtimer: /* If there is a CLINT then the mtimer is used to generate the tick interrupt. */
addi t0, x0, 1
slli t0, t0, __riscv_xlen - 1 /* LSB is already set, shift into MSB. Shift 31 on 32-bit or 63 on 64-bit cores. */
addi t1, t0, 7 /* 0x8000[]0007 == machine timer interrupt. */
bne a0, t1, test_if_external_interrupt
load_x t0, pullMachineTimerCompareRegister /* Load address of compare register into t0. */
load_x t1, pullNextTime /* Load the address of ullNextTime into t1. */
#if( __riscv_xlen == 32 )
/* Update the 64-bit mtimer compare match value in two 32-bit writes. */
li t4, -1
lw t2, 0(t1) /* Load the low word of ullNextTime into t2. */
lw t3, 4(t1) /* Load the high word of ullNextTime into t3. */
sw t4, 0(t0) /* Low word no smaller than old value to start with - will be overwritten below. */
sw t3, 4(t0) /* Store high word of ullNextTime into compare register. No smaller than new value. */
sw t2, 0(t0) /* Store low word of ullNextTime into compare register. */
lw t0, uxTimerIncrementsForOneTick /* Load the value of ullTimerIncrementForOneTick into t0 (could this be optimized by storing in an array next to pullNextTime?). */
add t4, t0, t2 /* Add the low word of ullNextTime to the timer increments for one tick (assumes timer increment for one tick fits in 32-bits). */
sltu t5, t4, t2 /* See if the sum of low words overflowed (what about the zero case?). */
add t6, t3, t5 /* Add overflow to high word of ullNextTime. */
sw t4, 0(t1) /* Store new low word of ullNextTime. */
sw t6, 4(t1) /* Store new high word of ullNextTime. */
#endif /* __riscv_xlen == 32 */
#if( __riscv_xlen == 64 )
/* Update the 64-bit mtimer compare match value. */
ld t2, 0(t1) /* Load ullNextTime into t2. */
sd t2, 0(t0) /* Store ullNextTime into compare register. */
ld t0, uxTimerIncrementsForOneTick /* Load the value of ullTimerIncrementForOneTick into t0 (could this be optimized by storing in an array next to pullNextTime?). */
add t4, t0, t2 /* Add ullNextTime to the timer increments for one tick. */
sd t4, 0(t1) /* Store ullNextTime. */
#endif /* __riscv_xlen == 64 */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal xTaskIncrementTick
beqz a0, processed_source /* Don't switch context if incrementing tick didn't unblock a task. */
jal vTaskSwitchContext
j processed_source
test_if_external_interrupt: /* If there is a CLINT and the mtimer interrupt is not pending then check to see if an external interrupt is pending. */
//addi t1, t1, 4 /* 0x80000007 + 4 = 0x8000000b == Machine external interrupt. */
//bne a0, t1, as_yet_unhandled /* Something as yet unhandled. */
#endif /* portasmHAS_CLINT */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal portasmHANDLE_INTERRUPT /* Jump to the interrupt handler if there is no CLINT or if there is a CLINT and it has been determined that an external interrupt is pending. */
j processed_source
handle_synchronous:
addi a1, a1, 4 /* Synchronous so updated exception return address to the instruction after the instruction that generated the exeption. */
store_x a1, 0( sp ) /* Save updated exception return address. */
test_if_environment_call:
li t0, 11 /* 11 == environment call. */
bne a0, t0, is_exception /* Not an M environment call, so some other exception. */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal vTaskSwitchContext
j processed_source
is_exception:
csrr t0, mcause /* For viewing in the debugger only. */
csrr t1, mepc /* For viewing in the debugger only */
csrr t2, mstatus
load_x sp, xISRStackTop
jal Trap_Handler
j is_exception
as_yet_unhandled:
csrr t0, mcause /* For viewing in the debugger only. */
j as_yet_unhandled
processed_source:
load_x t0, pTrapNetCounter
lw t1, 0 ( t0 )
addi t1, t1, -1
store_x t1, 0( t0 )
load_x t1, pxCurrentTCB /* Load pxCurrentTCB. */
load_x sp, 0( t1 ) /* Read sp from first TCB member. */
/* Load mret with the address of the next instruction in the task to run next. */
load_x t0, 0( sp )
csrw mepc, t0
portasmRESTORE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to restore any registers unique to the RISC-V implementation. */
/* Load mstatus with the interrupt enable bits used by the task. */
load_x t0, 29 * portWORD_SIZE( sp )
csrw mstatus, t0 /* Required for MPIE bit. */
load_x x1, 1 * portWORD_SIZE( sp )
load_x x5, 2 * portWORD_SIZE( sp ) /* t0 */
load_x x6, 3 * portWORD_SIZE( sp ) /* t1 */
load_x x7, 4 * portWORD_SIZE( sp ) /* t2 */
load_x x8, 5 * portWORD_SIZE( sp ) /* s0/fp */
load_x x9, 6 * portWORD_SIZE( sp ) /* s1 */
load_x x10, 7 * portWORD_SIZE( sp ) /* a0 */
load_x x11, 8 * portWORD_SIZE( sp ) /* a1 */
load_x x12, 9 * portWORD_SIZE( sp ) /* a2 */
load_x x13, 10 * portWORD_SIZE( sp ) /* a3 */
load_x x14, 11 * portWORD_SIZE( sp ) /* a4 */
load_x x15, 12 * portWORD_SIZE( sp ) /* a5 */
load_x x16, 13 * portWORD_SIZE( sp ) /* a6 */
load_x x17, 14 * portWORD_SIZE( sp ) /* a7 */
load_x x18, 15 * portWORD_SIZE( sp ) /* s2 */
load_x x19, 16 * portWORD_SIZE( sp ) /* s3 */
load_x x20, 17 * portWORD_SIZE( sp ) /* s4 */
load_x x21, 18 * portWORD_SIZE( sp ) /* s5 */
load_x x22, 19 * portWORD_SIZE( sp ) /* s6 */
load_x x23, 20 * portWORD_SIZE( sp ) /* s7 */
load_x x24, 21 * portWORD_SIZE( sp ) /* s8 */
load_x x25, 22 * portWORD_SIZE( sp ) /* s9 */
load_x x26, 23 * portWORD_SIZE( sp ) /* s10 */
load_x x27, 24 * portWORD_SIZE( sp ) /* s11 */
load_x x28, 25 * portWORD_SIZE( sp ) /* t3 */
load_x x29, 26 * portWORD_SIZE( sp ) /* t4 */
load_x x30, 27 * portWORD_SIZE( sp ) /* t5 */
load_x x31, 28 * portWORD_SIZE( sp ) /* t6 */
addi sp, sp, portCONTEXT_SIZE
mret
.endfunc
/*-----------------------------------------------------------*/
.align 8
.func
xPortStartFirstTask:
#if( portasmHAS_CLINT != 0 )
/* If there is a clint then interrupts can branch directly to the FreeRTOS
trap handler. Otherwise the interrupt controller will need to be configured
outside of this file. */
la t0, freertos_risc_v_trap_handler
ori t0, t0, 2
csrw mtvec, t0
#endif /* portasmHAS_CLILNT */
load_x sp, pxCurrentTCB /* Load pxCurrentTCB. */
load_x sp, 0( sp ) /* Read sp from first TCB member. */
load_x x1, 0( sp ) /* Note for starting the scheduler the exception return address is used as the function return address. */
portasmRESTORE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to restore any registers unique to the RISC-V implementation. */
load_x t0, 29 * portWORD_SIZE( sp ) /* mstatus */
addi t0, t0, 0x08 /* Set MIE bit so the first task starts with interrupts enabled - required as returns with ret not eret. */
csrrw x0, mstatus, t0 /* Interrupts enabled from here! */
load_x x5, 2 * portWORD_SIZE( sp ) /* t0 */
load_x x6, 3 * portWORD_SIZE( sp ) /* t1 */
load_x x7, 4 * portWORD_SIZE( sp ) /* t2 */
load_x x8, 5 * portWORD_SIZE( sp ) /* s0/fp */
load_x x9, 6 * portWORD_SIZE( sp ) /* s1 */
load_x x10, 7 * portWORD_SIZE( sp ) /* a0 */
load_x x11, 8 * portWORD_SIZE( sp ) /* a1 */
load_x x12, 9 * portWORD_SIZE( sp ) /* a2 */
load_x x13, 10 * portWORD_SIZE( sp ) /* a3 */
load_x x14, 11 * portWORD_SIZE( sp ) /* a4 */
load_x x15, 12 * portWORD_SIZE( sp ) /* a5 */
load_x x16, 13 * portWORD_SIZE( sp ) /* a6 */
load_x x17, 14 * portWORD_SIZE( sp ) /* a7 */
load_x x18, 15 * portWORD_SIZE( sp ) /* s2 */
load_x x19, 16 * portWORD_SIZE( sp ) /* s3 */
load_x x20, 17 * portWORD_SIZE( sp ) /* s4 */
load_x x21, 18 * portWORD_SIZE( sp ) /* s5 */
load_x x22, 19 * portWORD_SIZE( sp ) /* s6 */
load_x x23, 20 * portWORD_SIZE( sp ) /* s7 */
load_x x24, 21 * portWORD_SIZE( sp ) /* s8 */
load_x x25, 22 * portWORD_SIZE( sp ) /* s9 */
load_x x26, 23 * portWORD_SIZE( sp ) /* s10 */
load_x x27, 24 * portWORD_SIZE( sp ) /* s11 */
load_x x28, 25 * portWORD_SIZE( sp ) /* t3 */
load_x x29, 26 * portWORD_SIZE( sp ) /* t4 */
load_x x30, 27 * portWORD_SIZE( sp ) /* t5 */
load_x x31, 28 * portWORD_SIZE( sp ) /* t6 */
addi sp, sp, portCONTEXT_SIZE
ret
.endfunc
/*-----------------------------------------------------------*/
/*
* Unlike other ports pxPortInitialiseStack() is written in assembly code as it
* needs access to the portasmADDITIONAL_CONTEXT_SIZE constant. The prototype
* for the function is as per the other ports:
* StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters );
*
* As per the standard RISC-V ABI pxTopcOfStack is passed in in a0, pxCode in
* a1, and pvParameters in a2. The new top of stack is passed out in a0.
*
* RISC-V maps registers to ABI names as follows (X1 to X31 integer registers
* for the 'I' profile, X1 to X15 for the 'E' profile, currently I assumed).
*
* Register ABI Name Description Saver
* x0 zero Hard-wired zero -
* x1 ra Return address Caller
* x2 sp Stack pointer Callee
* x3 gp Global pointer -
* x4 tp Thread pointer -
* x5-7 t0-2 Temporaries Caller
* x8 s0/fp Saved register/Frame pointer Callee
* x9 s1 Saved register Callee
* x10-11 a0-1 Function Arguments/return values Caller
* x12-17 a2-7 Function arguments Caller
* x18-27 s2-11 Saved registers Callee
* x28-31 t3-6 Temporaries Caller
*
* The RISC-V context is saved t FreeRTOS tasks in the following stack frame,
* where the global and thread pointers are currently assumed to be constant so
* are not saved:
*
* mstatus
* x31
* x30
* x29
* x28
* x27
* x26
* x25
* x24
* x23
* x22
* x21
* x20
* x19
* x18
* x17
* x16
* x15
* x14
* x13
* x12
* x11
* pvParameters
* x9
* x8
* x7
* x6
* x5
* portTASK_RETURN_ADDRESS
* [chip specific registers go here]
* pxCode
*/
.align 8
.func
pxPortInitialiseStack:
csrr t0, mstatus /* Obtain current mstatus value. */
#if 1
li t1, 0x1880
or t0, t0, t1 /* MPP = 0b11, MPIE = 1 */
andi t0, t0, 0xFFFFFFF7 /* !!! MIE = 0 !!! */
#else
addi t1, x0, 0x188 /* Generate the value 0x1888, which are the MIE, MPIE and privilege bits to set in mstatus. */
slli t1, t1, 4
or t0, t0, t1 /* Set MPIE and MPP bits in mstatus value. */
#endif
addi a0, a0, -portWORD_SIZE
store_x t0, 0(a0) /* mstatus onto the stack. */
addi a0, a0, -(22 * portWORD_SIZE) /* Space for registers x11-x31. */
store_x a2, 0(a0) /* Task parameters (pvParameters parameter) goes into register X10/a0 on the stack. */
addi a0, a0, -(6 * portWORD_SIZE) /* Space for registers x5-x9. */
store_x x0, 0(a0) /* Return address onto the stack, could be portTASK_RETURN_ADDRESS */
addi t0, x0, portasmADDITIONAL_CONTEXT_SIZE /* The number of chip specific additional registers. */
chip_specific_stack_frame: /* First add any chip specific registers to the stack frame being created. */
beq t0, x0, 1f /* No more chip specific registers to save. */
addi a0, a0, -portWORD_SIZE /* Make space for chip specific register. */
store_x x0, 0(a0) /* Give the chip specific register an initial value of zero. */
addi t0, t0, -1 /* Decrement the count of chip specific registers remaining. */
j chip_specific_stack_frame /* Until no more chip specific registers. */
1:
addi a0, a0, -portWORD_SIZE
store_x a1, 0(a0) /* mret value (pxCode parameter) onto the stack. */
ret
.endfunc
/*-----------------------------------------------------------*/
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
/*
* The FreeRTOS kernel's RISC-V port is split between the the code that is
* common across all currently supported RISC-V chips (implementations of the
* RISC-V ISA), and code which tailors the port to a specific RISC-V chip:
*
* + The code that is common to all RISC-V chips is implemented in
* FreeRTOS\Source\portable\GCC\RISC-V-RV32\portASM.S. There is only one
* portASM.S file because the same file is used no matter which RISC-V chip is
* in use.
*
* + The code that tailors the kernel's RISC-V port to a specific RISC-V
* chip is implemented in freertos_risc_v_chip_specific_extensions.h. There
* is one freertos_risc_v_chip_specific_extensions.h that can be used with any
* RISC-V chip that both includes a standard CLINT and does not add to the
* base set of RISC-V registers. There are additional
* freertos_risc_v_chip_specific_extensions.h files for RISC-V implementations
* that do not include a standard CLINT or do add to the base set of RISC-V
* registers.
*
* CARE MUST BE TAKEN TO INCLDUE THE CORRECT
* freertos_risc_v_chip_specific_extensions.h HEADER FILE FOR THE CHIP
* IN USE. To include the correct freertos_risc_v_chip_specific_extensions.h
* header file ensure the path to the correct header file is in the assembler's
* include path.
*
* This freertos_risc_v_chip_specific_extensions.h is for use on RISC-V chips
* that include a standard CLINT and do not add to the base set of RISC-V
* registers.
*
*/
#if __riscv_xlen == 64
#define portWORD_SIZE 8
#define store_x sd
#define load_x ld
#elif __riscv_xlen == 32
#define store_x sw
#define load_x lw
#define portWORD_SIZE 4
#else
#error Assembler did not define __riscv_xlen
#endif
#include "freertos_risc_v_chip_specific_extensions.h"
/* Check the freertos_risc_v_chip_specific_extensions.h and/or command line
definitions. */
#ifndef portasmHAS_CLINT
#error freertos_risc_v_chip_specific_extensions.h must define portasmHAS_CLINT to either 1 (CLINT present) or 0 (clint not present).
#endif
#ifndef portasmHANDLE_INTERRUPT
#error portasmHANDLE_INTERRUPT must be defined to the function to be called to handle external/peripheral interrupts. portasmHANDLE_INTERRUPT can be defined on the assmbler command line or in the appropriate freertos_risc_v_chip_specific_extensions.h header file.
#endif
/* Only the standard core registers are stored by default. Any additional
registers must be saved by the portasmSAVE_ADDITIONAL_REGISTERS and
portasmRESTORE_ADDITIONAL_REGISTERS macros - which can be defined in a chip
specific version of freertos_risc_v_chip_specific_extensions.h. See the notes
at the top of this file. */
#define portCONTEXT_SIZE ( 30 * portWORD_SIZE )
.global xPortStartFirstTask
.global freertos_risc_v_trap_handler
.global pxPortInitialiseStack
.extern pxCurrentTCB
.extern ulPortTrapHandler
.extern vTaskSwitchContext
.extern xTaskIncrementTick
.extern Timer_IRQHandler
.extern pullMachineTimerCompareRegister
.extern pullNextTime
.extern pTrapNetCounter
.extern uxTimerIncrementsForOneTick /* size_t type so 32-bit on 32-bit core and 64-bits on 64-bit core. */
.extern xISRStackTop
.extern portasmHANDLE_INTERRUPT
.extern Trap_Handler
/*-----------------------------------------------------------*/
.align 8
.func
freertos_risc_v_trap_handler:
addi sp, sp, -portCONTEXT_SIZE
store_x x1, 1 * portWORD_SIZE( sp )
store_x x5, 2 * portWORD_SIZE( sp )
store_x x6, 3 * portWORD_SIZE( sp )
store_x x7, 4 * portWORD_SIZE( sp )
store_x x8, 5 * portWORD_SIZE( sp )
store_x x9, 6 * portWORD_SIZE( sp )
store_x x10, 7 * portWORD_SIZE( sp )
store_x x11, 8 * portWORD_SIZE( sp )
store_x x12, 9 * portWORD_SIZE( sp )
store_x x13, 10 * portWORD_SIZE( sp )
store_x x14, 11 * portWORD_SIZE( sp )
store_x x15, 12 * portWORD_SIZE( sp )
store_x x16, 13 * portWORD_SIZE( sp )
store_x x17, 14 * portWORD_SIZE( sp )
store_x x18, 15 * portWORD_SIZE( sp )
store_x x19, 16 * portWORD_SIZE( sp )
store_x x20, 17 * portWORD_SIZE( sp )
store_x x21, 18 * portWORD_SIZE( sp )
store_x x22, 19 * portWORD_SIZE( sp )
store_x x23, 20 * portWORD_SIZE( sp )
store_x x24, 21 * portWORD_SIZE( sp )
store_x x25, 22 * portWORD_SIZE( sp )
store_x x26, 23 * portWORD_SIZE( sp )
store_x x27, 24 * portWORD_SIZE( sp )
store_x x28, 25 * portWORD_SIZE( sp )
store_x x29, 26 * portWORD_SIZE( sp )
store_x x30, 27 * portWORD_SIZE( sp )
store_x x31, 28 * portWORD_SIZE( sp )
csrr t0, mstatus /* Required for MPIE bit. */
store_x t0, 29 * portWORD_SIZE( sp )
portasmSAVE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to save any registers unique to the RISC-V implementation. */
load_x t0, pTrapNetCounter
lw t1, 0( t0 )
addi t1, t1, 1
store_x t1, 0( t0 )
load_x t0, pxCurrentTCB /* Load pxCurrentTCB. */
store_x sp, 0( t0 ) /* Write sp to first TCB member. */
csrr a0, mcause
csrr a1, mepc
li t0, 0x80000FFF
and a0, a0, t0
test_if_asynchronous:
srli a2, a0, __riscv_xlen - 1 /* MSB of mcause is 1 if handing an asynchronous interrupt - shift to LSB to clear other bits. */
beq a2, x0, handle_synchronous /* Branch past interrupt handing if not asynchronous. */
store_x a1, 0( sp ) /* Asynch so save unmodified exception return address. */
handle_asynchronous:
#if( portasmHAS_CLINT != 0 )
test_if_mtimer: /* If there is a CLINT then the mtimer is used to generate the tick interrupt. */
addi t0, x0, 1
slli t0, t0, __riscv_xlen - 1 /* LSB is already set, shift into MSB. Shift 31 on 32-bit or 63 on 64-bit cores. */
addi t1, t0, 7 /* 0x8000[]0007 == machine timer interrupt. */
bne a0, t1, test_if_external_interrupt
load_x t0, pullMachineTimerCompareRegister /* Load address of compare register into t0. */
load_x t1, pullNextTime /* Load the address of ullNextTime into t1. */
#if( __riscv_xlen == 32 )
/* Update the 64-bit mtimer compare match value in two 32-bit writes. */
li t4, -1
lw t2, 0(t1) /* Load the low word of ullNextTime into t2. */
lw t3, 4(t1) /* Load the high word of ullNextTime into t3. */
sw t4, 0(t0) /* Low word no smaller than old value to start with - will be overwritten below. */
sw t3, 4(t0) /* Store high word of ullNextTime into compare register. No smaller than new value. */
sw t2, 0(t0) /* Store low word of ullNextTime into compare register. */
lw t0, uxTimerIncrementsForOneTick /* Load the value of ullTimerIncrementForOneTick into t0 (could this be optimized by storing in an array next to pullNextTime?). */
add t4, t0, t2 /* Add the low word of ullNextTime to the timer increments for one tick (assumes timer increment for one tick fits in 32-bits). */
sltu t5, t4, t2 /* See if the sum of low words overflowed (what about the zero case?). */
add t6, t3, t5 /* Add overflow to high word of ullNextTime. */
sw t4, 0(t1) /* Store new low word of ullNextTime. */
sw t6, 4(t1) /* Store new high word of ullNextTime. */
#endif /* __riscv_xlen == 32 */
#if( __riscv_xlen == 64 )
/* Update the 64-bit mtimer compare match value. */
ld t2, 0(t1) /* Load ullNextTime into t2. */
sd t2, 0(t0) /* Store ullNextTime into compare register. */
ld t0, uxTimerIncrementsForOneTick /* Load the value of ullTimerIncrementForOneTick into t0 (could this be optimized by storing in an array next to pullNextTime?). */
add t4, t0, t2 /* Add ullNextTime to the timer increments for one tick. */
sd t4, 0(t1) /* Store ullNextTime. */
#endif /* __riscv_xlen == 64 */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal xTaskIncrementTick
beqz a0, processed_source /* Don't switch context if incrementing tick didn't unblock a task. */
jal vTaskSwitchContext
j processed_source
test_if_external_interrupt: /* If there is a CLINT and the mtimer interrupt is not pending then check to see if an external interrupt is pending. */
//addi t1, t1, 4 /* 0x80000007 + 4 = 0x8000000b == Machine external interrupt. */
//bne a0, t1, as_yet_unhandled /* Something as yet unhandled. */
#endif /* portasmHAS_CLINT */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal portasmHANDLE_INTERRUPT /* Jump to the interrupt handler if there is no CLINT or if there is a CLINT and it has been determined that an external interrupt is pending. */
j processed_source
handle_synchronous:
addi a1, a1, 4 /* Synchronous so updated exception return address to the instruction after the instruction that generated the exeption. */
store_x a1, 0( sp ) /* Save updated exception return address. */
test_if_environment_call:
li t0, 11 /* 11 == environment call. */
bne a0, t0, is_exception /* Not an M environment call, so some other exception. */
load_x sp, xISRStackTop /* Switch to ISR stack before function call. */
jal vTaskSwitchContext
j processed_source
is_exception:
csrr t0, mcause /* For viewing in the debugger only. */
csrr t1, mepc /* For viewing in the debugger only */
csrr t2, mstatus
load_x sp, xISRStackTop
jal Trap_Handler
j is_exception
as_yet_unhandled:
csrr t0, mcause /* For viewing in the debugger only. */
j as_yet_unhandled
processed_source:
load_x t0, pTrapNetCounter
lw t1, 0 ( t0 )
addi t1, t1, -1
store_x t1, 0( t0 )
load_x t1, pxCurrentTCB /* Load pxCurrentTCB. */
load_x sp, 0( t1 ) /* Read sp from first TCB member. */
/* Load mret with the address of the next instruction in the task to run next. */
load_x t0, 0( sp )
csrw mepc, t0
portasmRESTORE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to restore any registers unique to the RISC-V implementation. */
/* Load mstatus with the interrupt enable bits used by the task. */
load_x t0, 29 * portWORD_SIZE( sp )
csrw mstatus, t0 /* Required for MPIE bit. */
load_x x1, 1 * portWORD_SIZE( sp )
load_x x5, 2 * portWORD_SIZE( sp ) /* t0 */
load_x x6, 3 * portWORD_SIZE( sp ) /* t1 */
load_x x7, 4 * portWORD_SIZE( sp ) /* t2 */
load_x x8, 5 * portWORD_SIZE( sp ) /* s0/fp */
load_x x9, 6 * portWORD_SIZE( sp ) /* s1 */
load_x x10, 7 * portWORD_SIZE( sp ) /* a0 */
load_x x11, 8 * portWORD_SIZE( sp ) /* a1 */
load_x x12, 9 * portWORD_SIZE( sp ) /* a2 */
load_x x13, 10 * portWORD_SIZE( sp ) /* a3 */
load_x x14, 11 * portWORD_SIZE( sp ) /* a4 */
load_x x15, 12 * portWORD_SIZE( sp ) /* a5 */
load_x x16, 13 * portWORD_SIZE( sp ) /* a6 */
load_x x17, 14 * portWORD_SIZE( sp ) /* a7 */
load_x x18, 15 * portWORD_SIZE( sp ) /* s2 */
load_x x19, 16 * portWORD_SIZE( sp ) /* s3 */
load_x x20, 17 * portWORD_SIZE( sp ) /* s4 */
load_x x21, 18 * portWORD_SIZE( sp ) /* s5 */
load_x x22, 19 * portWORD_SIZE( sp ) /* s6 */
load_x x23, 20 * portWORD_SIZE( sp ) /* s7 */
load_x x24, 21 * portWORD_SIZE( sp ) /* s8 */
load_x x25, 22 * portWORD_SIZE( sp ) /* s9 */
load_x x26, 23 * portWORD_SIZE( sp ) /* s10 */
load_x x27, 24 * portWORD_SIZE( sp ) /* s11 */
load_x x28, 25 * portWORD_SIZE( sp ) /* t3 */
load_x x29, 26 * portWORD_SIZE( sp ) /* t4 */
load_x x30, 27 * portWORD_SIZE( sp ) /* t5 */
load_x x31, 28 * portWORD_SIZE( sp ) /* t6 */
addi sp, sp, portCONTEXT_SIZE
mret
.endfunc
/*-----------------------------------------------------------*/
.align 8
.func
xPortStartFirstTask:
#if( portasmHAS_CLINT != 0 )
/* If there is a clint then interrupts can branch directly to the FreeRTOS
trap handler. Otherwise the interrupt controller will need to be configured
outside of this file. */
la t0, freertos_risc_v_trap_handler
ori t0, t0, 2
csrw mtvec, t0
#endif /* portasmHAS_CLILNT */
load_x sp, pxCurrentTCB /* Load pxCurrentTCB. */
load_x sp, 0( sp ) /* Read sp from first TCB member. */
load_x x1, 0( sp ) /* Note for starting the scheduler the exception return address is used as the function return address. */
portasmRESTORE_ADDITIONAL_REGISTERS /* Defined in freertos_risc_v_chip_specific_extensions.h to restore any registers unique to the RISC-V implementation. */
load_x t0, 29 * portWORD_SIZE( sp ) /* mstatus */
addi t0, t0, 0x08 /* Set MIE bit so the first task starts with interrupts enabled - required as returns with ret not eret. */
csrrw x0, mstatus, t0 /* Interrupts enabled from here! */
load_x x5, 2 * portWORD_SIZE( sp ) /* t0 */
load_x x6, 3 * portWORD_SIZE( sp ) /* t1 */
load_x x7, 4 * portWORD_SIZE( sp ) /* t2 */
load_x x8, 5 * portWORD_SIZE( sp ) /* s0/fp */
load_x x9, 6 * portWORD_SIZE( sp ) /* s1 */
load_x x10, 7 * portWORD_SIZE( sp ) /* a0 */
load_x x11, 8 * portWORD_SIZE( sp ) /* a1 */
load_x x12, 9 * portWORD_SIZE( sp ) /* a2 */
load_x x13, 10 * portWORD_SIZE( sp ) /* a3 */
load_x x14, 11 * portWORD_SIZE( sp ) /* a4 */
load_x x15, 12 * portWORD_SIZE( sp ) /* a5 */
load_x x16, 13 * portWORD_SIZE( sp ) /* a6 */
load_x x17, 14 * portWORD_SIZE( sp ) /* a7 */
load_x x18, 15 * portWORD_SIZE( sp ) /* s2 */
load_x x19, 16 * portWORD_SIZE( sp ) /* s3 */
load_x x20, 17 * portWORD_SIZE( sp ) /* s4 */
load_x x21, 18 * portWORD_SIZE( sp ) /* s5 */
load_x x22, 19 * portWORD_SIZE( sp ) /* s6 */
load_x x23, 20 * portWORD_SIZE( sp ) /* s7 */
load_x x24, 21 * portWORD_SIZE( sp ) /* s8 */
load_x x25, 22 * portWORD_SIZE( sp ) /* s9 */
load_x x26, 23 * portWORD_SIZE( sp ) /* s10 */
load_x x27, 24 * portWORD_SIZE( sp ) /* s11 */
load_x x28, 25 * portWORD_SIZE( sp ) /* t3 */
load_x x29, 26 * portWORD_SIZE( sp ) /* t4 */
load_x x30, 27 * portWORD_SIZE( sp ) /* t5 */
load_x x31, 28 * portWORD_SIZE( sp ) /* t6 */
addi sp, sp, portCONTEXT_SIZE
ret
.endfunc
/*-----------------------------------------------------------*/
/*
* Unlike other ports pxPortInitialiseStack() is written in assembly code as it
* needs access to the portasmADDITIONAL_CONTEXT_SIZE constant. The prototype
* for the function is as per the other ports:
* StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters );
*
* As per the standard RISC-V ABI pxTopcOfStack is passed in in a0, pxCode in
* a1, and pvParameters in a2. The new top of stack is passed out in a0.
*
* RISC-V maps registers to ABI names as follows (X1 to X31 integer registers
* for the 'I' profile, X1 to X15 for the 'E' profile, currently I assumed).
*
* Register ABI Name Description Saver
* x0 zero Hard-wired zero -
* x1 ra Return address Caller
* x2 sp Stack pointer Callee
* x3 gp Global pointer -
* x4 tp Thread pointer -
* x5-7 t0-2 Temporaries Caller
* x8 s0/fp Saved register/Frame pointer Callee
* x9 s1 Saved register Callee
* x10-11 a0-1 Function Arguments/return values Caller
* x12-17 a2-7 Function arguments Caller
* x18-27 s2-11 Saved registers Callee
* x28-31 t3-6 Temporaries Caller
*
* The RISC-V context is saved t FreeRTOS tasks in the following stack frame,
* where the global and thread pointers are currently assumed to be constant so
* are not saved:
*
* mstatus
* x31
* x30
* x29
* x28
* x27
* x26
* x25
* x24
* x23
* x22
* x21
* x20
* x19
* x18
* x17
* x16
* x15
* x14
* x13
* x12
* x11
* pvParameters
* x9
* x8
* x7
* x6
* x5
* portTASK_RETURN_ADDRESS
* [chip specific registers go here]
* pxCode
*/
.align 8
.func
pxPortInitialiseStack:
csrr t0, mstatus /* Obtain current mstatus value. */
#if 1
li t1, 0x1880
or t0, t0, t1 /* MPP = 0b11, MPIE = 1 */
andi t0, t0, 0xFFFFFFF7 /* !!! MIE = 0 !!! */
#else
addi t1, x0, 0x188 /* Generate the value 0x1888, which are the MIE, MPIE and privilege bits to set in mstatus. */
slli t1, t1, 4
or t0, t0, t1 /* Set MPIE and MPP bits in mstatus value. */
#endif
addi a0, a0, -portWORD_SIZE
store_x t0, 0(a0) /* mstatus onto the stack. */
addi a0, a0, -(22 * portWORD_SIZE) /* Space for registers x11-x31. */
store_x a2, 0(a0) /* Task parameters (pvParameters parameter) goes into register X10/a0 on the stack. */
addi a0, a0, -(6 * portWORD_SIZE) /* Space for registers x5-x9. */
store_x x0, 0(a0) /* Return address onto the stack, could be portTASK_RETURN_ADDRESS */
addi t0, x0, portasmADDITIONAL_CONTEXT_SIZE /* The number of chip specific additional registers. */
chip_specific_stack_frame: /* First add any chip specific registers to the stack frame being created. */
beq t0, x0, 1f /* No more chip specific registers to save. */
addi a0, a0, -portWORD_SIZE /* Make space for chip specific register. */
store_x x0, 0(a0) /* Give the chip specific register an initial value of zero. */
addi t0, t0, -1 /* Decrement the count of chip specific registers remaining. */
j chip_specific_stack_frame /* Until no more chip specific registers. */
1:
addi a0, a0, -portWORD_SIZE
store_x a1, 0(a0) /* mret value (pxCode parameter) onto the stack. */
ret
.endfunc
/*-----------------------------------------------------------*/

View File

@@ -1,166 +1,166 @@
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
#ifndef PORTMACRO_H
#define PORTMACRO_H
#ifdef __cplusplus
extern "C" {
#endif
/*-----------------------------------------------------------
* Port specific definitions.
*
* The settings in this file configure FreeRTOS correctly for the
* given hardware and compiler.
*
* These settings should not be altered.
*-----------------------------------------------------------
*/
/* Type definitions. */
#if __riscv_xlen == 64
#define portSTACK_TYPE uint64_t
#define portBASE_TYPE int64_t
#define portUBASE_TYPE uint64_t
#define portMAX_DELAY (TickType_t)0xffffffffffffffffUL
#define portPOINTER_SIZE_TYPE uint64_t
#elif __riscv_xlen == 32
#define portSTACK_TYPE uint32_t
#define portBASE_TYPE int /* int32_t */
#define portUBASE_TYPE uint32_t
#define portMAX_DELAY (TickType_t)0xffffffffUL
#ifdef __riscv_float_abi_single
/* better to use float replace double here,
* so that it will generates floating point instructions
*/
#define portDOUBLE float /* double */
#else
#define portDOUBLE double
#endif
#else
#error Assembler did not define __riscv_xlen
#endif
typedef portSTACK_TYPE StackType_t;
typedef portBASE_TYPE BaseType_t;
typedef portUBASE_TYPE UBaseType_t;
typedef portUBASE_TYPE TickType_t;
/* 32-bit tick type on a 32-bit architecture, so reads of the tick count do
not need to be guarded with a critical section. */
#define portTICK_TYPE_IS_ATOMIC 1
/*-----------------------------------------------------------*/
/* Architecture specifics. */
#define portSTACK_GROWTH (-1)
#define portTICK_PERIOD_MS ((TickType_t)1000 / configTICK_RATE_HZ)
#ifdef __riscv64
#error This is the RV32 port that has not yet been adapted for 64.
#define portBYTE_ALIGNMENT 16
#else
#define portBYTE_ALIGNMENT 16
#endif
/*-----------------------------------------------------------*/
/* Scheduler utilities. */
extern BaseType_t TrapNetCounter;
extern void vTaskSwitchContext(void);
#define portYIELD() __asm volatile("ecall");
#define portEND_SWITCHING_ISR(xSwitchRequired) \
if (xSwitchRequired) \
vTaskSwitchContext()
#define portYIELD_FROM_ISR(x) portEND_SWITCHING_ISR(x)
/*-----------------------------------------------------------*/
/* Critical section management. */
#define portCRITICAL_NESTING_IN_TCB 1
extern void vTaskEnterCritical(void);
extern void vTaskExitCritical(void);
#define portSET_INTERRUPT_MASK_FROM_ISR() 0
#define portCLEAR_INTERRUPT_MASK_FROM_ISR(uxSavedStatusValue) (void)uxSavedStatusValue
#define portDISABLE_INTERRUPTS() __asm volatile("csrc mstatus, 8")
#define portENABLE_INTERRUPTS() __asm volatile("csrs mstatus, 8")
#define portENTER_CRITICAL() vTaskEnterCritical()
#define portEXIT_CRITICAL() vTaskExitCritical()
/*-----------------------------------------------------------*/
/* Architecture specific optimisations. */
#ifndef configUSE_PORT_OPTIMISED_TASK_SELECTION
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1
#endif
#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 difference 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 = (31UL - __builtin_clz(uxReadyPriorities))
#endif /* configUSE_PORT_OPTIMISED_TASK_SELECTION */
/*-----------------------------------------------------------*/
/* Task function macros as described on the FreeRTOS.org WEB site. These are
not necessary for to use this port. They are defined so the common demo files
(which build with all the ports) will build. */
#define portTASK_FUNCTION_PROTO(vFunction, pvParameters) void vFunction(void *pvParameters)
#define portTASK_FUNCTION(vFunction, pvParameters) void vFunction(void *pvParameters)
/*-----------------------------------------------------------*/
#define portNOP() __asm volatile(" nop ")
#define portINLINE __inline
#ifndef portFORCE_INLINE
#define portFORCE_INLINE inline __attribute__((always_inline))
#endif
#define portMEMORY_BARRIER() __asm volatile("" :: \
: "memory")
portFORCE_INLINE static BaseType_t xPortIsInsideInterrupt(void)
{
return TrapNetCounter ? 1 : 0;
}
#ifdef __cplusplus
}
#endif
#endif /* PORTMACRO_H */
/*
* FreeRTOS Kernel V10.2.1
* Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
* http://www.FreeRTOS.org
* http://aws.amazon.com/freertos
*
* 1 tab == 4 spaces!
*/
#ifndef PORTMACRO_H
#define PORTMACRO_H
#ifdef __cplusplus
extern "C" {
#endif
/*-----------------------------------------------------------
* Port specific definitions.
*
* The settings in this file configure FreeRTOS correctly for the
* given hardware and compiler.
*
* These settings should not be altered.
*-----------------------------------------------------------
*/
/* Type definitions. */
#if __riscv_xlen == 64
#define portSTACK_TYPE uint64_t
#define portBASE_TYPE int64_t
#define portUBASE_TYPE uint64_t
#define portMAX_DELAY (TickType_t)0xffffffffffffffffUL
#define portPOINTER_SIZE_TYPE uint64_t
#elif __riscv_xlen == 32
#define portSTACK_TYPE uint32_t
#define portBASE_TYPE int /* int32_t */
#define portUBASE_TYPE uint32_t
#define portMAX_DELAY (TickType_t)0xffffffffUL
#ifdef __riscv_float_abi_single
/* better to use float replace double here,
* so that it will generates floating point instructions
*/
#define portDOUBLE float /* double */
#else
#define portDOUBLE double
#endif
#else
#error Assembler did not define __riscv_xlen
#endif
typedef portSTACK_TYPE StackType_t;
typedef portBASE_TYPE BaseType_t;
typedef portUBASE_TYPE UBaseType_t;
typedef portUBASE_TYPE TickType_t;
/* 32-bit tick type on a 32-bit architecture, so reads of the tick count do
not need to be guarded with a critical section. */
#define portTICK_TYPE_IS_ATOMIC 1
/*-----------------------------------------------------------*/
/* Architecture specifics. */
#define portSTACK_GROWTH (-1)
#define portTICK_PERIOD_MS ((TickType_t)1000 / configTICK_RATE_HZ)
#ifdef __riscv64
#error This is the RV32 port that has not yet been adapted for 64.
#define portBYTE_ALIGNMENT 16
#else
#define portBYTE_ALIGNMENT 16
#endif
/*-----------------------------------------------------------*/
/* Scheduler utilities. */
extern BaseType_t TrapNetCounter;
extern void vTaskSwitchContext(void);
#define portYIELD() __asm volatile("ecall");
#define portEND_SWITCHING_ISR(xSwitchRequired) \
if (xSwitchRequired) \
vTaskSwitchContext()
#define portYIELD_FROM_ISR(x) portEND_SWITCHING_ISR(x)
/*-----------------------------------------------------------*/
/* Critical section management. */
#define portCRITICAL_NESTING_IN_TCB 1
extern void vTaskEnterCritical(void);
extern void vTaskExitCritical(void);
#define portSET_INTERRUPT_MASK_FROM_ISR() 0
#define portCLEAR_INTERRUPT_MASK_FROM_ISR(uxSavedStatusValue) (void)uxSavedStatusValue
#define portDISABLE_INTERRUPTS() __asm volatile("csrc mstatus, 8")
#define portENABLE_INTERRUPTS() __asm volatile("csrs mstatus, 8")
#define portENTER_CRITICAL() vTaskEnterCritical()
#define portEXIT_CRITICAL() vTaskExitCritical()
/*-----------------------------------------------------------*/
/* Architecture specific optimisations. */
#ifndef configUSE_PORT_OPTIMISED_TASK_SELECTION
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1
#endif
#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 difference 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 = (31UL - __builtin_clz(uxReadyPriorities))
#endif /* configUSE_PORT_OPTIMISED_TASK_SELECTION */
/*-----------------------------------------------------------*/
/* Task function macros as described on the FreeRTOS.org WEB site. These are
not necessary for to use this port. They are defined so the common demo files
(which build with all the ports) will build. */
#define portTASK_FUNCTION_PROTO(vFunction, pvParameters) void vFunction(void *pvParameters)
#define portTASK_FUNCTION(vFunction, pvParameters) void vFunction(void *pvParameters)
/*-----------------------------------------------------------*/
#define portNOP() __asm volatile(" nop ")
#define portINLINE __inline
#ifndef portFORCE_INLINE
#define portFORCE_INLINE inline __attribute__((always_inline))
#endif
#define portMEMORY_BARRIER() __asm volatile("" :: \
: "memory")
portFORCE_INLINE static BaseType_t xPortIsInsideInterrupt(void)
{
return TrapNetCounter ? 1 : 0;
}
#ifdef __cplusplus
}
#endif
#endif /* PORTMACRO_H */

View File

@@ -1,4 +0,0 @@
#ifndef _ADC_CONFIG_H
#define _ADC_CONFIG_H
#endif

View File

@@ -1,14 +0,0 @@
#ifndef _DAC_CONFIG_H
#define _DAC_CONFIG_H
/* | vref source | rng | output range |
* | Internal | 0 | 0.2~1V |
* | Internal | 1/2 | 0.224~1.425V |
* | Internal | 3 | 0.2~1.8V |
* | Extern | 0 | 0.1Vref~0.5Vref |
* | Extern | 1/2 | 0.1125Vref~0.7125Vref |
* | Extern | 3 | 0.1Vref~0.9Vref |
*/
#define DAC_REF_RNG_DEFAULT_SELECT (0x3) /*!< ADC 1.8V select */
#endif

View File

@@ -1,6 +0,0 @@
#ifndef _SPI_CONFIG_H
#define _SPI_CONFIG_H
#define SPI_DEGLITCH_ENABLE (0)
#define SPI_CONTINUE_TRANSFER_ENABLE (1)
#endif

View File

@@ -1,12 +0,0 @@
#ifndef _UART_CONFIG_H
#define _UART_CONFIG_H
#define UART_CLOCK_SOURCE_160M_ENABLE (1)
#define UART_CTS_FLOWCONTROL_ENABLE (0)
#define UART_RTS_FLOWCONTROL_ENABLE (0)
#define UART_RX_DEGLITCH_ENABLE (0)
#define UART_MSB_FIRST_ENABLE (0)
#define UART_FIFO_MAX_LEN 32
#define UART_DEFAULT_RTO_TIMEOUT 255
#endif

View File

@@ -1,97 +0,0 @@
/**
* *****************************************************************************
* @file hal_gpio.h
* @version 0.1
* @date 2021-03-01
* @brief
* *****************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
* *****************************************************************************
*/
#ifndef __HAL_GPIO__H__
#define __HAL_GPIO__H__
#include "hal_common.h"
#include "drv_device.h"
#include "bl602_config.h"
typedef enum {
GPIO_PIN_0 = 0,
GPIO_PIN_1,
GPIO_PIN_2,
GPIO_PIN_3,
GPIO_PIN_4,
GPIO_PIN_5,
GPIO_PIN_6,
GPIO_PIN_7,
GPIO_PIN_8,
GPIO_PIN_9,
GPIO_PIN_10,
GPIO_PIN_11,
GPIO_PIN_12,
GPIO_PIN_13,
GPIO_PIN_14,
GPIO_PIN_15,
GPIO_PIN_16,
GPIO_PIN_17,
GPIO_PIN_18,
GPIO_PIN_19,
GPIO_PIN_20,
GPIO_PIN_21,
GPIO_PIN_22,
GPIO_PIN_23,
GPIO_PIN_24,
GPIO_PIN_25,
GPIO_PIN_26,
GPIO_PIN_27,
GPIO_PIN_28,
GPIO_PIN_MAX,
} gpio_pin_type;
#define GPIO_OUTPUT_MODE 0
#define GPIO_OUTPUT_PP_MODE 1
#define GPIO_OUTPUT_PD_MODE 2
#define GPIO_INPUT_MODE 3
#define GPIO_INPUT_PP_MODE 4
#define GPIO_INPUT_PD_MODE 5
#define GPIO_ASYNC_RISING_TRIGER_INT_MODE 6
#define GPIO_ASYNC_FALLING_TRIGER_INT_MODE 7
#define GPIO_ASYNC_HIGH_LEVEL_INT_MODE 8
#define GPIO_ASYNC_LOW_LEVEL_INT_MODE 9
#define GPIO_SYNC_RISING_TRIGER_INT_MODE 10
#define GPIO_SYNC_FALLING_TRIGER_INT_MODE 11
#define GPIO_SYNC_HIGH_LEVEL_INT_MODE 12
#define GPIO_SYNC_LOW_LEVEL_INT_MODE 13
void gpio_set_mode(uint32_t pin, uint32_t mode);
void gpio_write(uint32_t pin, uint32_t value);
void gpio_toggle(uint32_t pin);
int gpio_read(uint32_t pin);
void gpio_attach_irq(uint32_t pin, void (*cbFun)(void));
void gpio_irq_enable(uint32_t pin, uint8_t enabled);
#endif

View File

@@ -1,12 +0,0 @@
#ifndef __HAL_MTIMER__H__
#define __HAL_MTIMER__H__
#include "stdint.h"
void mtimer_set_alarm_time(uint64_t ticks, void (*interruptfun)(void));
uint32_t mtimer_get_clk_src_div(void);
uint64_t mtimer_get_time_ms();
uint64_t mtimer_get_time_us();
void mtimer_delay_ms(uint32_t time);
void mtimer_delay_us(uint32_t time);
#endif

View File

@@ -1,148 +0,0 @@
/**
* *****************************************************************************
* @file hal_uart.h
* @version 0.1
* @date 2021-03-01
* @brief
* *****************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
* *****************************************************************************
*/
#ifndef __HAL_UART__H__
#define __HAL_UART__H__
#include "hal_common.h"
#include "drv_device.h"
#include "bl602_config.h"
#define UART_FIFO_LEN 32
#define DEVICE_CTRL_UART_GET_TX_FIFO 0x10
#define DEVICE_CTRL_UART_GET_RX_FIFO 0x11
#define DEVICE_CTRL_UART_ATTACH_TX_DMA 0x12
#define DEVICE_CTRL_UART_ATTACH_RX_DMA 0x13
enum uart_index_type {
#ifdef BSP_USING_UART0
UART0_INDEX,
#endif
#ifdef BSP_USING_UART1
UART1_INDEX,
#endif
#ifdef BSP_USING_UART2
UART2_INDEX,
#endif
#ifdef BSP_USING_UART3
UART3_INDEX,
#endif
#ifdef BSP_USING_UART4
UART4_INDEX,
#endif
UART_MAX_INDEX
};
/*!
* @brief UART data length settings
*
* This enumeration defines the UART data lengths.
*/
typedef enum {
UART_DATA_LEN_5 = 0, /*!< Data length is 5 bits */
UART_DATA_LEN_6 = 1, /*!< Data length is 6 bits */
UART_DATA_LEN_7 = 2, /*!< Data length is 7 bits */
UART_DATA_LEN_8 = 3 /*!< Data length is 8 bits */
} uart_databits_t;
/*!
* @brief UART stop bit settings
*
* This enumeration defines the UART stop bits.
*/
typedef enum {
UART_STOP_ZERO_D_FIVE = 0, /*!< One stop bit */
UART_STOP_ONE = 1, /*!< One stop bit */
UART_STOP_ONE_D_FIVE = 2, /*!< 1.5 stop bit */
UART_STOP_TWO = 3 /*!< Two stop bits */
} uart_stopbits_t;
/*!
* @brief UART parity type settings
*
* This enumeration defines the UART parity types.
*/
typedef enum {
UART_PAR_NONE = 0, /*!< No parity */
UART_PAR_ODD = 1, /*!< Parity bit is odd */
UART_PAR_EVEN = 2, /*!< Parity bit is even */
} uart_parity_t;
enum uart_event_type {
UART_EVENT_TX_END,
UART_EVENT_TX_FIFO,
UART_EVENT_RX_END,
UART_EVENT_RX_FIFO,
UART_EVENT_RTO,
UART_EVENT_UNKNOWN
};
enum uart_it_type {
UART_TX_END_IT = 1 << 0,
UART_RX_END_IT = 1 << 1,
UART_TX_FIFO_IT = 1 << 2,
UART_RX_FIFO_IT = 1 << 3,
UART_RTO_IT = 1 << 4,
UART_PCE_IT = 1 << 5,
UART_TX_FER_IT = 1 << 6,
UART_RX_FER_IT = 1 << 7,
UART_ALL_IT = 1 << 8
};
typedef struct
{
uint32_t baudrate;
uart_databits_t databits;
uart_stopbits_t stopbits;
uart_parity_t parity;
} uart_param_cfg_t;
typedef struct uart_device {
struct device parent;
uint8_t id;
uint32_t baudrate;
uart_databits_t databits;
uart_stopbits_t stopbits;
uart_parity_t parity;
uint8_t fifo_threshold;
void *tx_dma;
void *rx_dma;
} uart_device_t;
#define UART_DEV(dev) ((uart_device_t *)dev)
int uart_register(enum uart_index_type index, const char *name);
#endif

View File

@@ -1,351 +0,0 @@
#include "hal_boot2.h"
#include "hal_gpio.h"
#include "hal_flash.h"
#include "bl602_glb.h"
#include "bl602_ef_ctrl.h"
#include "bl602_hbn.h"
#include "bl602_xip_sflash.h"
#include "bl602_sf_cfg.h"
#include "bl602_sf_cfg_ext.h"
#include "bl602_glb.h"
#include "bl602_xip_sflash_ext.h"
#include "tzc_sec_reg.h"
#include "softcrc.h"
#include "hal_sec_hash.h"
/**
* @brief boot2 custom
*
* @param None
* @return uint32
*/
uint32_t hal_boot2_custom(void)
{
uint32_t sw_cfg, flash_pin_cfg;
EF_Ctrl_Read_Sw_Usage(0, (uint32_t *)&sw_cfg);
/* flash_pin_cfg
* 0:internal flash with io switch,
* 1:internal flash no io switch,
* 2:GPIO 17-22
* 3:GPIO 0-2 & 20-22
*/
flash_pin_cfg = ((sw_cfg>>16)&0x3);
if((flash_pin_cfg == 0)||(flash_pin_cfg == 1)){
gpio_set_mode(GPIO_PIN_20, GPIO_OUTPUT_MODE);
gpio_write(GPIO_PIN_20, 0);
}
return 0;
}
/**
* @brief get efuse Boot2 config
*
* @param g_efuse_cfg
* @param
* @param
* @return None
*/
void hal_boot2_get_efuse_cfg(boot2_efuse_hw_config *efuse_cfg)
{
uint32_t tmp;
uint32_t rootClk;
uint8_t hdiv = 0, bdiv = 0;
/* save bclk fclk div and root clock sel */
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
rootClk = BL_RD_REG(HBN_BASE, HBN_GLB);
/* change root clock to rc32m for efuse operation */
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_RC32M);
/* Get sign and aes type*/
EF_Ctrl_Read_Secure_Boot((EF_Ctrl_Sign_Type *)efuse_cfg->sign, (EF_Ctrl_SF_AES_Type *)efuse_cfg->encrypted);
/* Get hash:aes key slot 0 and slot1*/
EF_Ctrl_Read_AES_Key(0, (uint32_t *)efuse_cfg->pk_hash_cpu0, 8);
EF_Ctrl_Read_Chip_ID(efuse_cfg->chip_id);
/* Get HBN check sign config */
EF_Ctrl_Read_Sw_Usage(0, &tmp);
efuse_cfg->hbn_check_sign = (tmp >> 22) & 0x01;
/* restore bclk fclk div and root clock sel */
GLB_Set_System_CLK_Div(hdiv, bdiv);
BL_WR_REG(HBN_BASE, HBN_GLB,rootClk);
__NOP();__NOP();__NOP();__NOP();
}
/**
* @brief reset sec eng clock
*
* @return
*/
void hal_boot2_reset_sec_eng(void)
{
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_SEC);
}
/**
* @brief system soft reset
*
* @return
*/
void hal_boot2_sw_system_reset(void)
{
GLB_SW_System_Reset();
}
/**
* @brief
*
* @param flag
* @param
* @param
* @return
*/
void hal_boot2_set_psmode_status(uint32_t flag)
{
HBN_Set_Status_Flag(flag);
}
/**
* @brief
*
* @param
* @param
* @param
* @return flag
*/
uint32_t hal_boot2_get_psmode_status(void)
{
return HBN_Get_Status_Flag();
}
/**
* @brief
*
* @param
* @param
* @param
* @return user define flag
*/
uint32_t hal_boot2_get_user_fw(void)
{
return BL_RD_WORD(HBN_BASE + HBN_RSV0_OFFSET);
}
/**
* @brief clr user define flag
*
* @param
* @param
* @param
* @return
*/
void hal_boot2_clr_user_fw(void)
{
uint32_t *p = (uint32_t *)(HBN_BASE + HBN_RSV0_OFFSET);
*p = 0;
}
/**
* @brief hal_boot2_sboot_finish
*
* @return
*/
void ATTR_TCM_SECTION hal_boot2_sboot_finish(void)
{
uint32_t tmp_val;
tmp_val = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmp_val = BL_SET_REG_BITS_VAL(tmp_val, TZC_SEC_TZC_SBOOT_DONE, 0xf);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmp_val);
}
/**
* @brief hal_boot2_uart_gpio_init
*
* @return
*/
void hal_boot2_uart_gpio_init(void)
{
GLB_GPIO_Type gpios[]={GPIO_PIN_7,GPIO_PIN_16};
GLB_GPIO_Func_Init(GPIO_FUN_UART,gpios,2);
GLB_UART_Fun_Sel((GPIO_PIN_7 % 8), GLB_UART_SIG_FUN_UART0_RXD);
GLB_UART_Fun_Sel((GPIO_PIN_16 % 8), GLB_UART_SIG_FUN_UART0_TXD);
}
/**
* @brief hal_boot2_debug_uart_gpio_init
*
* @return
*/
void hal_boot2_debug_uart_gpio_init(void)
{
GLB_GPIO_Type gpios[]={GPIO_PIN_8};
GLB_GPIO_Func_Init(GPIO_FUN_UART,gpios,1);
GLB_UART_Sig_Swap_Set(UART_SIG_SWAP_GPIO8_GPIO15);
GLB_UART_Fun_Sel(GLB_UART_SIG_4, GLB_UART_SIG_FUN_UART1_TXD);
}
/**
* @brief hal_boot2_debug_uart_gpio_deinit
*
* @return
*/
void hal_boot2_debug_uart_gpio_deinit(void)
{
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_UART0);
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_UART1);
GLB_UART_Sig_Swap_Set(UART_SIG_SWAP_NONE);
}
/****************************************************************************/ /**
* @brief Check if the input public key is the same as burned in the efuse
*
* @param g_boot_img_cfg: Boot image config pointer
* @param data: Image data pointer
*
* @return boot_error_code type
*
*******************************************************************************/
int32_t hal_boot_parse_bootheader(boot2_image_config *boot_img_cfg, uint8_t *data)
{
struct hal_bootheader_t *header = (struct hal_bootheader_t *)data;
uint32_t crc;
uint32_t crc_pass = 0;
uint32_t i = 0;
uint32_t *phash = (uint32_t *)header->hash;
int32_t ret;
if (header->bootCfg.bval.crcIgnore == 1 && header->crc32 == HAL_BOOT2_DEADBEEF_VAL) {
//MSG("Crc ignored\r\n");
crc_pass = 1;
} else {
crc = BFLB_Soft_CRC32((uint8_t *)header, sizeof(struct hal_bootheader_t) - sizeof(header->crc32));
if (header->crc32 == crc) {
crc_pass = 1;
}
}
if (crc_pass) {
if (header->bootCfg.bval.notLoadInBoot) {
return 0x0202;
}
/* Get which CPU's img it is*/
for (i = 0; i < HAL_BOOT2_CPU_MAX; i++) {
if (0 == memcmp((void *)&header->magicCode, HAL_BOOT2_CPU0_MAGIC,
sizeof(header->magicCode))) {
break;
} else if (0 == memcmp((void *)&header->magicCode, HAL_BOOT2_CPU1_MAGIC,
sizeof(header->magicCode))) {
break;
}
}
if (i == HAL_BOOT2_CPU_MAX) {
/* No cpu img magic match */
//MSG_ERR("Magic code error\r\n");
return 0x0203;
}
boot_img_cfg->cpu_type = i;
boot_img_cfg->entry_point = 0;
/* Set image valid 0 as default */
boot_img_cfg->img_valid = 0;
/* Deal with pll config */
/* Encrypt and sign */
boot_img_cfg->encrypt_type = header->bootCfg.bval.encrypt_type;
boot_img_cfg->sign_type = header->bootCfg.bval.sign;
boot_img_cfg->key_sel = header->bootCfg.bval.key_sel;
/* Xip relative */
boot_img_cfg->no_segment = header->bootCfg.bval.no_segment;
boot_img_cfg->cache_enable = header->bootCfg.bval.cache_enable;
boot_img_cfg->aes_region_lock = header->bootCfg.bval.aes_region_lock;
boot_img_cfg->halt_cpu1 = header->bootCfg.bval.halt_cpu1;
boot_img_cfg->cache_way_disable = header->bootCfg.bval.cache_way_disable;
boot_img_cfg->hash_ignore = header->bootCfg.bval.hash_ignore;
/* Firmware len*/
boot_img_cfg->img_segment_info.img_len = header->img_segment_info.img_len;
/* Boot entry and flash offset */
boot_img_cfg->entry_point = header->bootEntry;
boot_img_cfg->img_start.flash_offset = header->img_start.flash_offset;
//MSG("sign %d,encrypt:%d\r\n", boot_img_cfg->sign_type,boot_img_cfg->encrypt_type);
/* Check encrypt and sign match*/
if (g_efuse_cfg.encrypted[i] != 0) {
if (boot_img_cfg->encrypt_type == 0) {
//MSG_ERR("Encrypt not fit\r\n");
return 0x0205;
}
}
if (g_efuse_cfg.sign[i] ^ boot_img_cfg->sign_type) {
//MSG_ERR("sign not fit\r\n");
boot_img_cfg->sign_type = g_efuse_cfg.sign[i];
return 0x0206;
}
if (g_ps_mode == 1 && (!g_efuse_cfg.hbn_check_sign)) {
/* In HBN Mode, if user select to ignore hash and sign*/
boot_img_cfg->hash_ignore = 1;
} else if ((boot_img_cfg->hash_ignore == 1 && *phash != HAL_BOOT2_DEADBEEF_VAL) ||
g_efuse_cfg.sign[i] != 0) {
/* If signed or user not really want to ignore, hash can't be ignored*/
boot_img_cfg->hash_ignore = 0;
}
if (g_user_hash_ignored) {
boot_img_cfg->hash_ignore = 1;
}
ARCH_MemCpy_Fast(boot_img_cfg->img_hash, header->hash, sizeof(header->hash));
if (boot_img_cfg->img_segment_info.img_len == 0) {
return 0x0207;
}
/* Start hash here*/
//Sec_Eng_SHA256_Init(&g_sha_ctx, SEC_ENG_SHA_ID0, SEC_ENG_SHA256, g_sha_tmp_buf, g_padding);
//Sec_Eng_SHA_Start(SEC_ENG_SHA_ID0);
device_unregister("dev_check_hash");
sec_hash_sha256_register(0,"dev_check_hash");
dev_check_hash = device_find("dev_check_hash");
if(dev_check_hash){
ret = device_open(dev_check_hash, 0);
if(ret){
//MSG_ERR("hash dev open err\r\n");
return 0xffff;
}
}else{
//MSG_ERR("hash dev find err\r\n");
return 0xffff;
}
} else {
//MSG_ERR("bootheader crc error\r\n");
//blsp_dump_data((uint8_t *)&crc, 4);
return 0x0204;
}
return 0;
}
void hal_boot2_clean_cache(void)
{

View File

@@ -1,185 +0,0 @@
#include "bl602_glb.h"
#include "hal_clock.h"
static uint32_t mtimer_get_clk_src_div(void)
{
return (system_clock_get(SYSTEM_CLOCK_BCLK) / 1000 / 1000 - 1);
}
void system_clock_init(void)
{
/*select root clock*/
GLB_Set_System_CLK(XTAL_TYPE, BSP_ROOT_CLOCK_SOURCE);
/*set fclk/hclk and bclk clock*/
GLB_Set_System_CLK_Div(BSP_FCLK_DIV, BSP_BCLK_DIV);
GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, mtimer_get_clk_src_div());
#if XTAL_32K_TYPE == INTERNAL_RC_32K
HBN_32K_Sel(HBN_32K_RC);
HBN_Power_Off_Xtal_32K();
#else
HBN_32K_Sel(HBN_32K_XTAL);
HBN_Power_On_Xtal_32K();
#endif
#if (XTAL_TYPE == INTERNAL_RC_32M) || (XTAL_TYPE == XTAL_NONE)
HBN_Set_XCLK_CLK_Sel(HBN_XCLK_CLK_RC32M);
#else
HBN_Set_XCLK_CLK_Sel(HBN_XCLK_CLK_XTAL);
#endif
}
void system_mtimer_clock_init(void)
{
GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, mtimer_get_clk_src_div());
}
void system_mtimer_clock_reinit(void)
{
/* reinit clock to 10M */
GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, 7);
}
void peripheral_clock_init(void)
{
#if defined(BSP_USING_UART0) || defined(BSP_USING_UART1)
#if BSP_UART_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_PLL_160M
GLB_Set_UART_CLK(ENABLE, HBN_UART_CLK_160M, BSP_UART_CLOCK_DIV);
#elif BSP_UART_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_FCLK
GLB_Set_UART_CLK(ENABLE, HBN_UART_CLK_FCLK, BSP_UART_CLOCK_DIV);
#endif
#endif
#if defined(BSP_USING_I2C0)
GLB_Set_I2C_CLK(ENABLE, BSP_I2C_CLOCK_DIV);
#endif
#if defined(BSP_USING_SPI0)
GLB_Set_SPI_CLK(ENABLE, BSP_SPI_CLOCK_DIV);
#endif
#if defined(BSP_USING_PWM)
#if BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_RC_32K
#elif BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_BCLK
#elif BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
#endif
#endif
#if defined(BSP_USING_IR)
GLB_Set_IR_CLK(ENABLE, 0, BSP_IR_CLOCK_DIV);
#endif
#if defined(BSP_USING_ADC0)
#if BSP_ADC_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL
GLB_Set_ADC_CLK(ENABLE, GLB_ADC_CLK_AUDIO_PLL, BSP_ADC_CLOCK_DIV);
#elif BSP_ADC_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
GLB_Set_ADC_CLK(ENABLE, GLB_ADC_CLK_XCLK, BSP_ADC_CLOCK_DIV);
#endif
#endif
#if defined(BSP_USING_DAC0)
GLB_Set_DAC_CLK(ENABLE, GLB_ADC_CLK_XCLK, BSP_DAC_CLOCK_DIV);
#endif
}
uint32_t system_clock_get(enum system_clock_type type)
{
switch (type) {
case SYSTEM_CLOCK_ROOT_CLOCK:
if (GLB_Get_Root_CLK_Sel() == 0) {
return 32 * 1000 * 1000;
} else if (GLB_Get_Root_CLK_Sel() == 1)
return 32 * 1000 * 1000;
else {
uint32_t tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG0);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, GLB_REG_PLL_SEL);
if (tmpVal == 0) {
return 48 * 1000 * 1000;
} else if (tmpVal == 1) {
return 120 * 1000 * 1000;
} else if (tmpVal == 2) {
return 160 * 1000 * 1000;
} else if (tmpVal == 3) {
return 192 * 1000 * 1000;
} else {
return 0;
}
}
case SYSTEM_CLOCK_FCLK:
return system_clock_get(SYSTEM_CLOCK_ROOT_CLOCK) / (GLB_Get_HCLK_Div() + 1);
case SYSTEM_CLOCK_BCLK:
return system_clock_get(SYSTEM_CLOCK_ROOT_CLOCK) / (GLB_Get_HCLK_Div() + 1) / (GLB_Get_BCLK_Div() + 1);
case SYSTEM_CLOCK_XCLK:
switch (XTAL_TYPE) {
case XTAL_NONE:
return 32000000;
case EXTERNAL_XTAL_24M:
return 24000000;
case EXTERNAL_XTAL_32M:
return 32000000;
case EXTERNAL_XTAL_38P4M:
return 38400000;
case EXTERNAL_XTAL_40M:
return 40000000;
case EXTERNAL_XTAL_26M:
return 26000000;
case INTERNAL_RC_32M:
return 32000000;
default:
break;
}
default:
break;
}
return 0;
}
uint32_t peripheral_clock_get(enum peripheral_clock_type type)
{
uint32_t tmpVal;
uint32_t div;
switch (type) {
#if defined(BSP_USING_UART0) || defined(BSP_USING_UART1)
case PERIPHERAL_CLOCK_UART:
tmpVal = BL_RD_REG(HBN_BASE, HBN_GLB);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, HBN_UART_CLK_SEL);
div = BL_RD_REG(GLB_BASE, GLB_CLK_CFG2);
div = BL_GET_REG_BITS_VAL(div, GLB_UART_CLK_DIV);
if (tmpVal == HBN_UART_CLK_FCLK) {
return system_clock_get(SYSTEM_CLOCK_FCLK) / (div + 1);
} else if (tmpVal == HBN_UART_CLK_160M) {
return 160000000 / (div + 1);
}
#endif
#if defined(BSP_USING_SPI0)
case PERIPHERAL_CLOCK_SPI:
tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG3);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_SPI_CLK_DIV);
return system_clock_get(SYSTEM_CLOCK_BCLK) / (div + 1);
#endif
case PERIPHERAL_CLOCK_I2C:
#if defined(BSP_USING_I2C0)
tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG3);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_I2C_CLK_DIV);
return system_clock_get(SYSTEM_CLOCK_BCLK) / (div + 1);
#endif
case PERIPHERAL_CLOCK_ADC:
case PERIPHERAL_CLOCK_DAC:
return 32000000;
default:
break;
}
(void)(tmpVal);
(void)(div);
return 0;
}

View File

@@ -1,251 +0,0 @@
#ifndef __BL602_H__
#define __BL602_H__
/** @addtogroup Configuration_section_for_RISCV
* @{
*/
/**
* @brief Configuration of the Processor and Core Peripherals
*/
#define SystemCoreClockSet(val) BL_WR_WORD(0x4000F108, val)
#define SystemCoreClockGet(val) BL_RD_WORD(0x4000F108)
/**
* @}
*/
/** @addtogroup Peripheral_interrupt_number_definition
* @{
*/
#ifdef ARCH_ARM
#define IRQ_NUM_BASE 0
#endif
#ifdef ARCH_RISCV
#define IRQ_NUM_BASE 16
#endif
/**
* @brief BL602 Interrupt Number Definition, according to the selected device
* in @ref Library_configuration_section
*/
typedef enum {
#ifdef ARCH_ARM
/****** Cortex-M4 Processor Exceptions Numbers ****************************************************************/
NonMaskableInt_IRQn = -14, /*!< 2 Cortex-M4 Non Maskable Interrupt */
HardFault_IRQn = -13, /*!< 3 Cortex-M4 Hard Fault Interrupt */
MemoryManagement_IRQn = -12, /*!< 4 Cortex-M4 Memory Management Interrupt */
BusFault_IRQn = -11, /*!< 5 Cortex-M4 Bus Fault Interrupt */
UsageFault_IRQn = -10, /*!< 6 Cortex-M4 Usage Fault Interrupt */
SVCall_IRQn = -5, /*!< 11 Cortex-M4 SV Call Interrupt */
DebugMonitor_IRQn = -4, /*!< 12 Cortex-M4 Debug Monitor Interrupt */
PendSV_IRQn = -2, /*!< 14 Cortex-M4 Pend SV Interrupt */
SysTick_IRQn = -1, /*!< 15 Cortex-M4 System Tick Interrupt */
#endif
#ifdef ARCH_RISCV
MSOFT_IRQn = 3, /*!< 3 RISCV machine software Interrupt */
MTIME_IRQn = 7, /*!< 7 RISCV machine time Interrupt */
MEXT_IRQn = 11, /*!< 11 RISCV external Interrupt */
CLIC_SOFT_PEND_IRQn = 12, /*!< 12 RISCV CLIC software pending Interrupt */
#endif
/****** BL602 specific Interrupt Numbers **********************************************************************/
BMX_ERR_IRQn = IRQ_NUM_BASE + 0, /*!< BMX Error Interrupt */
BMX_TO_IRQn = IRQ_NUM_BASE + 1, /*!< BMX Timeout Interrupt */
L1C_BMX_ERR_IRQn = IRQ_NUM_BASE + 2, /*!< L1C BMX Error Interrupt */
L1C_BMX_TO_IRQn = IRQ_NUM_BASE + 3, /*!< L1C BMX Timeout Interrupt */
SEC_BMX_ERR_IRQn = IRQ_NUM_BASE + 4, /*!< SEC BMX Error Interrupt */
RF_TOP_INT0_IRQn = IRQ_NUM_BASE + 5, /*!< RF_TOP_INT0 Interrupt */
RF_TOP_INT1_IRQn = IRQ_NUM_BASE + 6, /*!< RF_TOP_INT1 Interrupt */
SDIO_IRQn = IRQ_NUM_BASE + 7, /*!< SDIO Interrupt */
DMA_BMX_ERR_IRQn = IRQ_NUM_BASE + 8, /*!< DMA BMX Error Interrupt */
SEC_GMAC_IRQn = IRQ_NUM_BASE + 9, /*!< SEC_ENG_GMAC_INT Interrupt */
SEC_CDET_IRQn = IRQ_NUM_BASE + 10, /*!< SEC_ENG_CDET_INT Interrupt */
SEC_PKA_IRQn = IRQ_NUM_BASE + 11, /*!< SEC_ENG_PKA_INT Interrupt */
SEC_TRNG_IRQn = IRQ_NUM_BASE + 12, /*!< SEC_ENG_TRNG_INT Interrupt */
SEC_AES_IRQn = IRQ_NUM_BASE + 13, /*!< SEC_ENG_AES_INT Interrupt */
SEC_SHA_IRQn = IRQ_NUM_BASE + 14, /*!< SEC_ENG_SHA_INT Interrupt */
DMA_ALL_IRQn = IRQ_NUM_BASE + 15, /*!< DMA ALL Interrupt */
RESERVED0 = IRQ_NUM_BASE + 16, /*!< RESERVED Interrupt */
RESERVED1 = IRQ_NUM_BASE + 17, /*!< RESERVED Interrupt */
RESERVED2 = IRQ_NUM_BASE + 18, /*!< RESERVED Interrupt */
IRTX_IRQn = IRQ_NUM_BASE + 19, /*!< IR TX Interrupt */
IRRX_IRQn = IRQ_NUM_BASE + 20, /*!< IR RX Interrupt */
RESERVED3 = IRQ_NUM_BASE + 21, /*!< RESERVED Interrupt */
RESERVED4 = IRQ_NUM_BASE + 22, /*!< RESERVED Interrupt */
SF_CTRL_IRQn = IRQ_NUM_BASE + 23, /*!< SF_CTRL Interrupt */
RESERVED5 = IRQ_NUM_BASE + 24, /*!< RESERVED Interrupt */
GPADC_DMA_IRQn = IRQ_NUM_BASE + 25, /*!< GPADC_DMA Interrupt */
EFUSE_IRQn = IRQ_NUM_BASE + 26, /*!< Efuse Interrupt */
SPI_IRQn = IRQ_NUM_BASE + 27, /*!< SPI Interrupt */
RESERVED6 = IRQ_NUM_BASE + 28, /*!< RESERVED Interrupt */
UART0_IRQn = IRQ_NUM_BASE + 29, /*!< UART Interrupt */
UART1_IRQn = IRQ_NUM_BASE + 30, /*!< UART1 Interrupt */
RESERVED7 = IRQ_NUM_BASE + 31, /*!< RESERVED Interrupt */
I2C_IRQn = IRQ_NUM_BASE + 32, /*!< I2C Interrupt */
RESERVED8 = IRQ_NUM_BASE + 33, /*!< RESERVED Interrupt */
PWM_IRQn = IRQ_NUM_BASE + 34, /*!< PWM Interrupt */
RESERVED9 = IRQ_NUM_BASE + 35, /*!< RESERVED Interrupt */
TIMER_CH0_IRQn = IRQ_NUM_BASE + 36, /*!< Timer Channel 0 Interrupt */
TIMER_CH1_IRQn = IRQ_NUM_BASE + 37, /*!< Timer Channel 1 Interrupt */
TIMER_WDT_IRQn = IRQ_NUM_BASE + 38, /*!< Timer Watch Dog Interrupt */
RESERVED10 = IRQ_NUM_BASE + 39, /*!< RESERVED Interrupt */
RESERVED11 = IRQ_NUM_BASE + 40, /*!< RESERVED Interrupt */
RESERVED12 = IRQ_NUM_BASE + 41, /*!< RESERVED Interrupt */
RESERVED13 = IRQ_NUM_BASE + 42, /*!< RESERVED Interrupt */
RESERVED14 = IRQ_NUM_BASE + 43, /*!< RESERVED Interrupt */
GPIO_INT0_IRQn = IRQ_NUM_BASE + 44, /*!< RESERVED Interrupt */
RESERVED16 = IRQ_NUM_BASE + 45, /*!< RESERVED Interrupt */
RESERVED17 = IRQ_NUM_BASE + 46, /*!< RESERVED Interrupt */
RESERVED18 = IRQ_NUM_BASE + 47, /*!< RESERVED Interrupt */
RESERVED19 = IRQ_NUM_BASE + 48, /*!< RESERVED Interrupt */
RESERVED20 = IRQ_NUM_BASE + 49, /*!< RESERVED Interrupt */
PDS_WAKEUP_IRQn = IRQ_NUM_BASE + 50, /*!< PDS Wakeup Interrupt */
HBN_OUT0_IRQn = IRQ_NUM_BASE + 51, /*!< Hibernate out 0 Interrupt */
HBN_OUT1_IRQn = IRQ_NUM_BASE + 52, /*!< Hibernate out 1 Interrupt */
BOR_IRQn = IRQ_NUM_BASE + 53, /*!< BOR Interrupt */
WIFI_IRQn = IRQ_NUM_BASE + 54, /*!< WIFI To CPU Interrupt */
BZ_PHY_IRQn = IRQ_NUM_BASE + 55, /*!< RESERVED Interrupt */
BLE_IRQn = IRQ_NUM_BASE + 56, /*!< RESERVED Interrupt */
MAC_TXRX_TIMER_IRQn = IRQ_NUM_BASE + 57, /*!< mac_int_tx_rx_timer Interrupt */
MAC_TXRX_MISC_IRQn = IRQ_NUM_BASE + 58, /*!< mac_int_tx_rx_misc Interrupt */
MAC_RX_TRG_IRQn = IRQ_NUM_BASE + 59, /*!< mac_int_rx_trigger Interrupt */
MAC_TX_TRG_IRQn = IRQ_NUM_BASE + 60, /*!< mac_int_tx_trigger Interrupt */
MAC_GEN_IRQn = IRQ_NUM_BASE + 61, /*!< mac_int_gen Interrupt */
MAC_PORT_TRG_IRQn = IRQ_NUM_BASE + 62, /*!< mac_int_port_trigger Interrupt */
WIFI_IPC_PUBLIC_IRQn = IRQ_NUM_BASE + 63, /*!< wifi IPC public Interrupt */
IRQn_LAST,
} IRQn_Type;
/**
* @brief BL602 Memory Map Definitions
*/
#define BL602_FLASH_XIP_BASE 0x23000000
#define BL602_FLASH_XIP_END (0x23000000 + 16 * 1024 * 1024)
#define BL602_FLASH_XIP_REMAP0_BASE 0x33000000
#define BL602_FLASH_XIP_REMAP0_END (0x33000000 + 16 * 1024 * 1024)
#define BL602_FLASH_XIP_REMAP1_BASE 0x43000000
#define BL602_FLASH_XIP_REMAP1_END (0x43000000 + 16 * 1024 * 1024)
#define BL602_FLASH_XIP_REMAP2_BASE 0x53000000
#define BL602_FLASH_XIP_REMAP2_END (0x53000000 + 16 * 1024 * 1024)
#define BL602_WRAM_BASE 0x42020000
#define BL602_WRAM_END (0x42020000 + 176 * 1024)
#define BL602_WRAM_REMAP0_BASE 0x22020000
#define BL602_WRAM_REMAP0_END (0x22020000 + 176 * 1024)
#define BL602_WRAM_REMAP1_BASE 0x32020000
#define BL602_WRAM_REMAP1_END (0x32020000 + 176 * 1024)
#define BL602_WRAM_REMAP2_BASE 0x52020000
#define BL602_WRAM_REMAP2_END (0x52020000 + 176 * 1024)
#define BL602_TCM_BASE 0x22008000
#define BL602_TCM_END (0x22008000 + (96 + 176) * 1024)
#define BL602_TCM_REMAP0_BASE 0x32008000
#define BL602_TCM_REMAP0_END (0x32008000 + (96 + 176) * 1024)
#define BL602_TCM_REMAP1_BASE 0x42008000
#define BL602_TCM_REMAP1_END (0x42008000 + (96 + 176) * 1024)
#define BL602_TCM_REMAP2_BASE 0x52008000
#define BL602_TCM_REMAP2_END (0x52008000 + (96 + 176) * 1024)
/*@} end of group Memory_Map_Section */
/* BL602 peripherals base address */
#define GLB_BASE ((uint32_t)0x40000000)
#define RF_BASE ((uint32_t)0x40001000)
#define GPIP_BASE ((uint32_t)0x40002000) /*!< AUX module base address */
#define SEC_DBG_BASE ((uint32_t)0x40003000) /*!< Security Debug module base address */
#define SEC_ENG_BASE ((uint32_t)0x40004000) /*!< Security Engine module base address */
#define TZC_SEC_BASE ((uint32_t)0x40005000) /*!< Trustzone control security base address */
#define TZC_NSEC_BASE ((uint32_t)0x40006000) /*!< Trustzone control none-security base address */
#define EF_DATA_BASE ((uint32_t)0x40007000)
#define EF_CTRL_BASE ((uint32_t)0x40007000)
#define CCI_BASE ((uint32_t)0x40008000)
#define L1C_BASE ((uint32_t)0x40009000) /*!< L1 cache config base address */
#define UART0_BASE ((uint32_t)0x4000A000)
#define UART1_BASE ((uint32_t)0x4000A100)
#define SPI_BASE ((uint32_t)0x4000A200)
#define I2C_BASE ((uint32_t)0x4000A300)
#define PWM_BASE ((uint32_t)0x4000A400)
#define TIMER_BASE ((uint32_t)0x4000A500)
#define IR_BASE ((uint32_t)0x4000A600)
#define SF_CTRL_BASE ((uint32_t)0x4000B000)
#define SF_CTRL_BUF_BASE ((uint32_t)0x4000B700)
#define DMA_BASE ((uint32_t)0x4000C000)
#define SDU_BASE ((uint32_t)0x4000D000)
#define PDS_BASE ((uint32_t)0x4000E000) /*!< Power down sleep module base address */
#define HBN_BASE ((uint32_t)0x4000F000) /*!< Hibernate module base address */
#define AON_BASE ((uint32_t)0x4000F000) /*!< Always on module base address */
#define HBN_RAM_BASE ((uint32_t)0x40010000)
typedef enum {
BL_AHB_SLAVE1_GLB = 0x00,
BL_AHB_SLAVE1_RF = 0x01,
BL_AHB_SLAVE1_GPIP_PHY_AGC = 0x02,
BL_AHB_SLAVE1_SEC_DBG = 0x03,
BL_AHB_SLAVE1_SEC = 0x04,
BL_AHB_SLAVE1_TZ1 = 0x05,
BL_AHB_SLAVE1_TZ2 = 0x06,
BL_AHB_SLAVE1_EFUSE = 0x07,
BL_AHB_SLAVE1_CCI = 0x08,
BL_AHB_SLAVE1_L1C = 0x09,
BL_AHB_SLAVE1_RSVD0A = 0x0A,
BL_AHB_SLAVE1_SFC = 0x0B,
BL_AHB_SLAVE1_DMA = 0x0C,
BL_AHB_SLAVE1_SDU = 0x0D,
BL_AHB_SLAVE1_PDS_HBN_AON_HBNRAM = 0x0E,
BL_AHB_SLAVE1_RSVD0F = 0x0F,
BL_AHB_SLAVE1_UART0 = 0x10,
BL_AHB_SLAVE1_UART1 = 0x11,
BL_AHB_SLAVE1_SPI = 0x12,
BL_AHB_SLAVE1_I2C = 0x13,
BL_AHB_SLAVE1_PWM = 0x14,
BL_AHB_SLAVE1_TMR = 0x15,
BL_AHB_SLAVE1_IRR = 0x16,
BL_AHB_SLAVE1_CKS = 0x17,
BL_AHB_SLAVE1_MAX = 0x18,
} BL_AHB_Slave1_Type;
typedef enum {
BL_AHB_SEC_ENG_AES0 = 0,
BL_AHB_SEC_ENG_AES1,
BL_AHB_SEC_ENG_SHA0,
BL_AHB_SEC_ENG_SHA1,
} BL_AHB_Sec_Eng_Type;
typedef enum {
BL_AHB_DMA0_CH0 = 0,
BL_AHB_DMA0_CH1,
BL_AHB_DMA0_CH2,
BL_AHB_DMA0_CH3,
BL_AHB_DMA0_CH4,
} BL_AHB_DMA0_CHNL_Type;
typedef enum {
BL_CORE_MASTER_IBUS_CPU = 0,
BL_CORE_MASTER_DBUS_CPU,
BL_CORE_MASTER_BUS_S2F,
BL_CORE_MASTER_MAX,
} BL_Core_Master_Type;
typedef enum {
BL_CORE_SLAVE0_DTCM_CPU = 0,
BL_CORE_SLAVE0_MAX,
} BL_Core_Slave0_Type;
typedef enum {
BL_CORE_SLAVE1_XIP_CPU = 0,
BL_CORE_SLAVE1_ITCM_CPU,
BL_CORE_SLAVE1_ROM,
BL_CORE_SLAVE1_MAX,
} BL_Core_Slave1_Type;
typedef enum {
BL_CORE_SLAVE2_F2S = 0,
BL_CORE_SLAVE2_MAX,
} BL_Core_Slave2_Type;
/**
* @}
*/
#include <stdint.h>
#include <system_bl602.h>
#endif

View File

@@ -1,86 +0,0 @@
#include "bl602.h"
#include "bl602_glb.h"
#include "bl602_hbn.h"
#include "risc-v/Core/Include/clic.h"
/*----------------------------------------------------------------------------
Define clocks
*----------------------------------------------------------------------------*/
#define SYSTEM_CLOCK (32000000UL)
/*----------------------------------------------------------------------------
Vector Table
*----------------------------------------------------------------------------*/
#define VECT_TAB_OFFSET 0x00 /*!< Vector Table base offset field.
This value must be a multiple of 0x200. */
/*----------------------------------------------------------------------------
System initialization function
*----------------------------------------------------------------------------*/
void system_bor_init(void)
{
HBN_BOR_CFG_Type borCfg = { 1 /* pu_bor */, 0 /* irq_bor_en */, 1 /* bor_vth */, 1 /* bor_sel */ };
HBN_Set_BOR_Cfg(&borCfg);
}
void SystemInit(void)
{
uint32_t *p;
uint32_t i = 0;
uint32_t tmpVal = 0;
__disable_irq();
/* disable hardware_pullup_pull_down (reg_en_hw_pu_pd = 0) */
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
tmpVal = BL_CLR_REG_BIT(tmpVal, HBN_REG_EN_HW_PU_PD);
BL_WR_REG(HBN_BASE, HBN_IRQ_MODE, tmpVal);
/* GLB_Set_EM_Sel(GLB_EM_0KB); */
tmpVal = BL_RD_REG(GLB_BASE, GLB_SEAM_MISC);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_EM_SEL, GLB_EM_0KB);
BL_WR_REG(GLB_BASE, GLB_SEAM_MISC, tmpVal);
/* Fix 26M xtal clkpll_sdmin */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_SDM);
if (0x49D39D == BL_GET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN)) {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x49D89E);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_SDM, tmpVal);
}
/* Restore default setting*/
/* GLB_UART_Sig_Swap_Set(UART_SIG_SWAP_NONE); */
tmpVal = BL_RD_REG(GLB_BASE, GLB_PARM);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_UART_SWAP_SET, UART_SIG_SWAP_NONE);
BL_WR_REG(GLB_BASE, GLB_PARM, tmpVal);
/* GLB_JTAG_Sig_Swap_Set(JTAG_SIG_SWAP_NONE); */
tmpVal = BL_RD_REG(GLB_BASE, GLB_PARM);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_JTAG_SWAP_SET, JTAG_SIG_SWAP_NONE);
BL_WR_REG(GLB_BASE, GLB_PARM, tmpVal);
/* CLear all interrupt */
p = (uint32_t *)(CLIC_HART0_ADDR + CLIC_INTIE);
for (i = 0; i < (IRQn_LAST + 3) / 4; i++) {
p[i] = 0;
}
p = (uint32_t *)(CLIC_HART0_ADDR + CLIC_INTIP);
for (i = 0; i < (IRQn_LAST + 3) / 4; i++) {
p[i] = 0;
}
/* init bor for all platform */
system_bor_init();
/* global IRQ enable */
__enable_irq();
}
void System_Post_Init(void)
{
PDS_Trim_RC32M();
HBN_Trim_RC32K();
}

View File

@@ -1,22 +0,0 @@
#ifndef __SYSTEM_BL602_H__
#define __SYSTEM_BL602_H__
/**
* @brief PLL Clock type definition
*/
extern uint32_t SystemCoreClock;
typedef void (*pFunc)(void);
#define CPU_Interrupt_Enable clic_enable_interrupt
#define CPU_Interrupt_Disable clic_disable_interrupt
#define CPU_Interrupt_Pending_Clear clic_clear_pending
extern void SystemCoreClockUpdate(void);
extern void SystemInit(void);
void clic_enable_interrupt(uint32_t source);
void clic_disable_interrupt(uint32_t source);
void clic_clear_pending(uint32_t source);
void Interrupt_Handler_Register(IRQn_Type irq, pFunc interruptFun);
void System_NVIC_SetPriority(IRQn_Type IRQn, uint32_t PreemptPriority, uint32_t SubPriority);
#endif

View File

@@ -1,444 +0,0 @@
/**
******************************************************************************
* @file bl602_gpio.h
* @version V1.2
* @date 2019-12-14
* @brief This file is the description of.IP register
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2019 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#ifndef __BL602_GPIO_H__
#define __BL602_GPIO_H__
typedef enum {
GLB_GPIO_PIN_0 = 0,
GLB_GPIO_PIN_1,
GLB_GPIO_PIN_2,
GLB_GPIO_PIN_3,
GLB_GPIO_PIN_4,
GLB_GPIO_PIN_5,
GLB_GPIO_PIN_6,
GLB_GPIO_PIN_7,
GLB_GPIO_PIN_8,
GLB_GPIO_PIN_9,
GLB_GPIO_PIN_10,
GLB_GPIO_PIN_11,
GLB_GPIO_PIN_12,
GLB_GPIO_PIN_13,
GLB_GPIO_PIN_14,
GLB_GPIO_PIN_15,
GLB_GPIO_PIN_16,
GLB_GPIO_PIN_17,
GLB_GPIO_PIN_18,
GLB_GPIO_PIN_19,
GLB_GPIO_PIN_20,
GLB_GPIO_PIN_21,
GLB_GPIO_PIN_22,
GLB_GPIO_PIN_MAX,
} GLB_GPIO_Type;
#define GPIO_MODE_INPUT ((uint32_t)0x00000000U) /*!< Input Floating Mode */
#define GPIO_MODE_OUTPUT ((uint32_t)0x00000001U) /*!< Output Push Pull Mode */
#define GPIO_MODE_AF ((uint32_t)0x00000002U) /*!< Alternate function */
#define GPIO_MODE_ANALOG ((uint32_t)0x00000003U) /*!< Analog function */
#define GPIO_PULL_UP ((uint32_t)0x00000000U) /*!< GPIO pull up */
#define GPIO_PULL_DOWN ((uint32_t)0x00000001U) /*!< GPIO pull down */
#define GPIO_PULL_NONE ((uint32_t)0x00000002U) /*!< GPIO no pull up or down */
typedef enum {
GPIO_FUN_SDIO = 1,
GPIO_FUN_FLASH = 2,
GPIO_FUN_SPI = 4,
GPIO_FUN_I2C = 6,
GPIO_FUN_UART = 7,
GPIO_FUN_PWM = 8,
GPIO_FUN_EXT_PA = 9,
GPIO_FUN_ANALOG = 10,
GPIO_FUN_SWGPIO = 11,
GPIO_FUN_GPIO = 11,
GPIO_FUN_JTAG = 14,
GPIO_FUN_UART0_RTS = 0x70,
GPIO_FUN_UART0_CTS = 0x71,
GPIO_FUN_UART0_TX = 0x72,
GPIO_FUN_UART0_RX = 0x73,
GPIO_FUN_UART1_RTS = 0x74,
GPIO_FUN_UART1_CTS = 0x75,
GPIO_FUN_UART1_TX = 0x76,
GPIO_FUN_UART1_RX = 0x77,
GPIO_FUN_GPIO_OUTPUT = 0x80,
GPIO_FUN_GPIO_INPUT = 0x81,
GPIO_FUN_UNUSED = 255,
} GLB_GPIO_FUNC_Type;
typedef struct
{
uint8_t gpioPin;
uint8_t gpioFun;
uint8_t gpioMode;
uint8_t pullType;
uint8_t drive;
uint8_t smtCtrl;
} GLB_GPIO_Cfg_Type;
/* GPIO0 function definition */
#define GPIO0_FUN_SDIO_CLK 1
#define GPIO0_FUN_SF_D1 2
#define GPIO0_FUN_UNUSED3 3
#define GPIO0_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO0_FUN_UNUSED5 5
#define GPIO0_FUN_I2C_SCL 6
#define GPIO0_FUN_UART_SIG0 7
#define GPIO0_FUN_PWM_CH0 8
#define GPIO0_FUN_FEM_GPIO_0 9
#define GPIO0_FUN_ATEST_IN 10
#define GPIO0_FUN_SWGPIO_0 11
#define GPIO0_FUN_E21_TMS 14
/* GPIO1 function definition */
#define GPIO1_FUN_SDIO_CMD 1
#define GPIO1_FUN_SF_D2 2
#define GPIO1_FUN_UNUSED3 3
#define GPIO1_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO1_FUN_UNUSED5 5
#define GPIO1_FUN_I2C_SDA 6
#define GPIO1_FUN_UART_SIG1 7
#define GPIO1_FUN_PWM_CH1 8
#define GPIO1_FUN_FEM_GPIO_1 9
#define GPIO1_FUN_ATEST_IP 10
#define GPIO1_FUN_SWGPIO_1 11
#define GPIO1_FUN_E21_TDI 14
/* GPIO2 function definition */
#define GPIO2_FUN_SDIO_DAT0 1
#define GPIO2_FUN_SF_D3 2
#define GPIO2_FUN_UNUSED3 3
#define GPIO2_FUN_SPI_SS 4
#define GPIO2_FUN_UNUSED5 5
#define GPIO2_FUN_I2C_SCL 6
#define GPIO2_FUN_UART_SIG2 7
#define GPIO2_FUN_PWM_CH2 8
#define GPIO2_FUN_FEM_GPIO_2 9
#define GPIO2_FUN_ATEST_QN 10
#define GPIO2_FUN_SWGPIO_2 11
#define GPIO2_FUN_E21_TCK 14
/* GPIO3 function definition */
#define GPIO3_FUN_SDIO_DAT1 1
#define GPIO3_FUN_UNUSED2 2
#define GPIO3_FUN_UNUSED3 3
#define GPIO3_FUN_SPI_SCLK 4
#define GPIO3_FUN_UNUSED5 5
#define GPIO3_FUN_I2C_SDA 6
#define GPIO3_FUN_UART_SIG3 7
#define GPIO3_FUN_PWM_CH3 8
#define GPIO3_FUN_FEM_GPIO_3 9
#define GPIO3_FUN_ATEST_QP 10
#define GPIO3_FUN_SWGPIO_3 11
#define GPIO3_FUN_E21_TDO 14
/* GPIO4 function definition */
#define GPIO4_FUN_SDIO_DAT2 1
#define GPIO4_FUN_UNUSED2 2
#define GPIO4_FUN_UNUSED3 3
#define GPIO4_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO4_FUN_UNUSED5 5
#define GPIO4_FUN_I2C_SCL 6
#define GPIO4_FUN_UART_SIG4 7
#define GPIO4_FUN_PWM_CH4 8
#define GPIO4_FUN_FEM_GPIO_0 9
#define GPIO4_FUN_GPIP_CH1 10
#define GPIO4_FUN_SWGPIO_4 11
#define GPIO4_FUN_E21_TMS 14
/* GPIO5 function definition */
#define GPIO5_FUN_SDIO_DAT3 1
#define GPIO5_FUN_UNUSED2 2
#define GPIO5_FUN_UNUSED3 3
#define GPIO5_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO5_FUN_UNUSED5 5
#define GPIO5_FUN_I2C_SDA 6
#define GPIO5_FUN_UART_SIG5 7
#define GPIO5_FUN_PWM_CH0 8
#define GPIO5_FUN_FEM_GPIO_1 9
#define GPIO5_FUN_GPIP_CH4 10
#define GPIO5_FUN_SWGPIO_5 11
#define GPIO5_FUN_E21_TDI 14
/* GPIO6 function definition */
#define GPIO6_FUN_UNUSED1 1
#define GPIO6_FUN_UNUSED2 2
#define GPIO6_FUN_UNUSED3 3
#define GPIO6_FUN_SPI_SS 4
#define GPIO6_FUN_UNUSED5 5
#define GPIO6_FUN_I2C_SCL 6
#define GPIO6_FUN_UART_SIG6 7
#define GPIO6_FUN_PWM_CH1 8
#define GPIO6_FUN_FEM_GPIO_2 9
#define GPIO6_FUN_GPIP_CH5 10
#define GPIO6_FUN_SWGPIO_6 11
#define GPIO6_FUN_E21_TCK 14
/* GPIO7 function definition */
#define GPIO7_FUN_UNUSED1 1
#define GPIO7_FUN_UNUSED2 2
#define GPIO7_FUN_UNUSED3 3
#define GPIO7_FUN_SPI_SCLK 4
#define GPIO7_FUN_UNUSED5 5
#define GPIO7_FUN_I2C_SDA 6
#define GPIO7_FUN_UART_SIG7 7
#define GPIO7_FUN_PWM_CH2 8
#define GPIO7_FUN_FEM_GPIO_3 9
#define GPIO7_FUN_UNUSED10 10
#define GPIO7_FUN_SWGPIO_7 11
#define GPIO7_FUN_E21_TDO 14
/* GPIO8 function definition */
#define GPIO8_FUN_UNUSED1 1
#define GPIO8_FUN_UNUSED2 2
#define GPIO8_FUN_UNUSED3 3
#define GPIO8_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO8_FUN_UNUSED5 5
#define GPIO8_FUN_I2C_SCL 6
#define GPIO8_FUN_UART_SIG0 7
#define GPIO8_FUN_PWM_CH3 8
#define GPIO8_FUN_FEM_GPIO_0 9
#define GPIO8_FUN_UNUSED10 10
#define GPIO8_FUN_SWGPIO_8 11
#define GPIO8_FUN_E21_TMS 14
/* GPIO9 function definition */
#define GPIO9_FUN_UNUSED1 1
#define GPIO9_FUN_UNUSED2 2
#define GPIO9_FUN_UNUSED3 3
#define GPIO9_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO9_FUN_UNUSED5 5
#define GPIO9_FUN_I2C_SDA 6
#define GPIO9_FUN_UART_SIG1 7
#define GPIO9_FUN_PWM_CH4 8
#define GPIO9_FUN_FEM_GPIO_1 9
#define GPIO9_FUN_GPIP_CH6_GPIP_CH7 10
#define GPIO9_FUN_SWGPIO_9 11
#define GPIO9_FUN_E21_TDI 14
/* GPIO10 function definition */
#define GPIO10_FUN_UNUSED1 1
#define GPIO10_FUN_UNUSED2 2
#define GPIO10_FUN_UNUSED3 3
#define GPIO10_FUN_SPI_SS 4
#define GPIO10_FUN_UNUSED5 5
#define GPIO10_FUN_I2C_SCL 6
#define GPIO10_FUN_UART_SIG2 7
#define GPIO10_FUN_PWM_CH0 8
#define GPIO10_FUN_FEM_GPIO_2 9
#define GPIO10_FUN_MICBIAS_GPIP_CH8_GPIP_CH9 10
#define GPIO10_FUN_SWGPIO_10 11
#define GPIO10_FUN_E21_TCK 14
/* GPIO11 function definition */
#define GPIO11_FUN_UNUSED1 1
#define GPIO11_FUN_UNUSED2 2
#define GPIO11_FUN_UNUSED3 3
#define GPIO11_FUN_SPI_SCLK 4
#define GPIO11_FUN_UNUSED5 5
#define GPIO11_FUN_I2C_SDA 6
#define GPIO11_FUN_UART_SIG3 7
#define GPIO11_FUN_PWM_CH1 8
#define GPIO11_FUN_FEM_GPIO_3 9
#define GPIO11_FUN_IRLED_OUT_GPIP_CH10 10
#define GPIO11_FUN_SWGPIO_11 11
#define GPIO11_FUN_E21_TDO 14
/* GPIO12 function definition */
#define GPIO12_FUN_UNUSED1 1
#define GPIO12_FUN_UNUSED2 2
#define GPIO12_FUN_UNUSED3 3
#define GPIO12_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO12_FUN_UNUSED5 5
#define GPIO12_FUN_I2C_SCL 6
#define GPIO12_FUN_UART_SIG4 7
#define GPIO12_FUN_PWM_CH2 8
#define GPIO12_FUN_FEM_GPIO_0 9
#define GPIO12_FUN_GPIP_CH0_GPADC_VREF_EXT 10
#define GPIO12_FUN_SWGPIO_12 11
#define GPIO12_FUN_E21_TMS 14
/* GPIO13 function definition */
#define GPIO13_FUN_UNUSED1 1
#define GPIO13_FUN_UNUSED2 2
#define GPIO13_FUN_UNUSED3 3
#define GPIO13_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO13_FUN_UNUSED5 5
#define GPIO13_FUN_I2C_SDA 6
#define GPIO13_FUN_UART_SIG5 7
#define GPIO13_FUN_PWM_CH3 8
#define GPIO13_FUN_FEM_GPIO_1 9
#define GPIO13_FUN_GPIP_CH3 10
#define GPIO13_FUN_SWGPIO_13 11
#define GPIO13_FUN_E21_TDI 14
/* GPIO14 function definition */
#define GPIO14_FUN_UNUSED1 1
#define GPIO14_FUN_UNUSED2 2
#define GPIO14_FUN_UNUSED3 3
#define GPIO14_FUN_SPI_SS 4
#define GPIO14_FUN_UNUSED5 5
#define GPIO14_FUN_I2C_SCL 6
#define GPIO14_FUN_UART_SIG6 7
#define GPIO14_FUN_PWM_CH4 8
#define GPIO14_FUN_FEM_GPIO_2 9
#define GPIO14_FUN_GPIP_CH2 10
#define GPIO14_FUN_SWGPIO_14 11
#define GPIO14_FUN_E21_TCK 14
/* GPIO15 function definition */
#define GPIO15_FUN_UNUSED1 1
#define GPIO15_FUN_UNUSED2 2
#define GPIO15_FUN_UNUSED3 3
#define GPIO15_FUN_SPI_SCLK 4
#define GPIO15_FUN_UNUSED5 5
#define GPIO15_FUN_I2C_SDA 6
#define GPIO15_FUN_UART_SIG7 7
#define GPIO15_FUN_PWM_CH0 8
#define GPIO15_FUN_FEM_GPIO_3 9
#define GPIO15_FUN_PSW_IRRCV_OUT_GPIP_CH11 10
#define GPIO15_FUN_SWGPIO_15 11
#define GPIO15_FUN_E21_TDO 14
/* GPIO16 function definition */
#define GPIO16_FUN_UNUSED1 1
#define GPIO16_FUN_UNUSED2 2
#define GPIO16_FUN_UNUSED3 3
#define GPIO16_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO16_FUN_UNUSED5 5
#define GPIO16_FUN_I2C_SCL 6
#define GPIO16_FUN_UART_SIG0 7
#define GPIO16_FUN_PWM_CH1 8
#define GPIO16_FUN_FEM_GPIO_0 9
#define GPIO16_FUN_UNUSED10 10
#define GPIO16_FUN_SWGPIO_16 11
#define GPIO16_FUN_E21_TMS 14
/* GPIO17 function definition */
#define GPIO17_FUN_UNUSED1 1
#define GPIO17_FUN_SF_D3 2
#define GPIO17_FUN_UNUSED3 3
#define GPIO17_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO17_FUN_UNUSED5 5
#define GPIO17_FUN_I2C_SDA 6
#define GPIO17_FUN_UART_SIG1 7
#define GPIO17_FUN_PWM_CH2 8
#define GPIO17_FUN_FEM_GPIO_1 9
#define GPIO17_FUN_PMIP_DC_TP_OUT 10
#define GPIO17_FUN_SWGPIO_17 11
#define GPIO17_FUN_E21_TDI 14
/* GPIO18 function definition */
#define GPIO18_FUN_UNUSED1 1
#define GPIO18_FUN_SF_D2 2
#define GPIO18_FUN_UNUSED3 3
#define GPIO18_FUN_SPI_SS 4
#define GPIO18_FUN_UNUSED5 5
#define GPIO18_FUN_I2C_SCL 6
#define GPIO18_FUN_UART_SIG2 7
#define GPIO18_FUN_PWM_CH3 8
#define GPIO18_FUN_FEM_GPIO_2 9
#define GPIO18_FUN_UNUSED10 10
#define GPIO18_FUN_SWGPIO_18 11
#define GPIO18_FUN_E21_TCK 14
/* GPIO19 function definition */
#define GPIO19_FUN_UNUSED1 1
#define GPIO19_FUN_SF_D1 2
#define GPIO19_FUN_UNUSED3 3
#define GPIO19_FUN_SPI_SCLK 4
#define GPIO19_FUN_UNUSED5 5
#define GPIO19_FUN_I2C_SDA 6
#define GPIO19_FUN_UART_SIG3 7
#define GPIO19_FUN_PWM_CH4 8
#define GPIO19_FUN_FEM_GPIO_3 9
#define GPIO19_FUN_UNUSED10 10
#define GPIO19_FUN_SWGPIO_19 11
#define GPIO19_FUN_E21_TDO 14
/* GPIO20 function definition */
#define GPIO20_FUN_UNUSED1 1
#define GPIO20_FUN_SF_D0 2
#define GPIO20_FUN_UNUSED3 3
#define GPIO20_FUN_SPI_MOSI_SPI_MISO 4
#define GPIO20_FUN_UNUSED5 5
#define GPIO20_FUN_I2C_SCL 6
#define GPIO20_FUN_UART_SIG4 7
#define GPIO20_FUN_PWM_CH0 8
#define GPIO20_FUN_FEM_GPIO_0 9
#define GPIO20_FUN_UNUSED10 10
#define GPIO20_FUN_SWGPIO_20 11
#define GPIO20_FUN_E21_TMS 14
/* GPIO21 function definition */
#define GPIO21_FUN_UNUSED1 1
#define GPIO21_FUN_SF_CS 2
#define GPIO21_FUN_UNUSED3 3
#define GPIO21_FUN_SPI_MISO_SPI_MOSI 4
#define GPIO21_FUN_UNUSED5 5
#define GPIO21_FUN_I2C_SDA 6
#define GPIO21_FUN_UART_SIG5 7
#define GPIO21_FUN_PWM_CH1 8
#define GPIO21_FUN_FEM_GPIO_1 9
#define GPIO21_FUN_UNUSED10 10
#define GPIO21_FUN_SWGPIO_21 11
#define GPIO21_FUN_E21_TDI 14
/* GPIO22 function definition */
#define GPIO22_FUN_UNUSED1 1
#define GPIO22_FUN_SF_CLK_OUT 2
#define GPIO22_FUN_UNUSED3 3
#define GPIO22_FUN_SPI_SS 4
#define GPIO22_FUN_UNUSED5 5
#define GPIO22_FUN_I2C_SCL 6
#define GPIO22_FUN_UART_SIG6 7
#define GPIO22_FUN_PWM_CH2 8
#define GPIO22_FUN_FEM_GPIO_2 9
#define GPIO22_FUN_UNUSED10 10
#define GPIO22_FUN_SWGPIO_22 11
#define GPIO22_FUN_E21_TCK 14
#endif /*__BL602_GPIO_H__ */

View File

@@ -1,24 +0,0 @@
#ifndef __BL602_MFG_EFUSE_H__
#define __BL602_MFG_EFUSE_H__
#include "stdint.h"
uint8_t mfg_efuse_get_rf_cal_slots(void);
void mfg_efuse_set_rf_cal_slots(uint8_t slots);
uint8_t mfg_efuse_is_xtal_capcode_slot_empty(uint8_t reload);
int8_t mfg_efuse_write_xtal_capcode_pre(uint8_t capcode, uint8_t program);
void mfg_efuse_write_xtal_capcode(void);
int8_t mfg_efuse_read_xtal_capcode(uint8_t *capcode, uint8_t reload);
uint8_t mfg_efuse_is_poweroffset_slot_empty(uint8_t reload);
int8_t mfg_efuse_write_poweroffset_pre(int8_t pwrOffset[14], uint8_t program);
void mfg_efuse_write_poweroffset(void);
int8_t mfg_efuse_read_poweroffset(int8_t pwrOffset[14], uint8_t reload);
uint8_t mfg_efuse_is_macaddr_slot_empty(uint8_t reload);
int8_t mfg_efuse_write_macaddr_pre(uint8_t mac[6], uint8_t program);
void mfg_efuse_write_macaddr(void);
int8_t mfg_efuse_read_macaddr(uint8_t mac[6], uint8_t reload);
int8_t mfg_efuse_read(uint32_t addr, uint32_t *data, uint32_t countInword, uint8_t reload);
int8_t mfg_efuse_program(void);
int8_t mfg_efuse_write_pre(uint32_t addr, uint32_t *data, uint32_t countInword);
#endif /*__MFG_GPIO_API_H__*/

View File

@@ -1,18 +0,0 @@
#ifndef __BL602_MFG_FLASH_H__
#define __BL602_MFG_FLASH_H__
#include "stdint.h"
#include "bl602_sflash.h"
int8_t mfg_flash_init(SPI_Flash_Cfg_Type *flashCfg);
int8_t mfg_flash_write_xtal_capcode_pre(uint8_t capcode, uint8_t program);
void mfg_flash_write_xtal_capcode(void);
int8_t mfg_flash_read_xtal_capcode(uint8_t *capcode, uint8_t reload);
int8_t mfg_flash_write_poweroffset_pre(int8_t pwrOffset[14], uint8_t program);
void mfg_flash_write_poweroffset(void);
int8_t mfg_flash_read_poweroffset(int8_t pwrOffset[14], uint8_t reload);
int8_t mfg_flash_write_macaddr_pre(uint8_t mac[6], uint8_t program);
void mfg_flash_write_macaddr(void);
int8_t mfg_flash_read_macaddr(uint8_t mac[6], uint8_t reload);
#endif /*__MFG_GPIO_API_H__*/

View File

@@ -1,29 +0,0 @@
#ifndef __BL602_MFG_MEDIA_H__
#define __BL602_MFG_MEDIA_H__
#include "stdint.h"
#include "bl602_sflash.h"
int8_t mfg_media_init_need_lock(SPI_Flash_Cfg_Type *flashCfg);
int8_t mfg_media_init_with_lock(SPI_Flash_Cfg_Type *flashCfg);
uint8_t mfg_media_is_xtal_capcode_slot_empty(uint8_t reload);
int8_t mfg_media_write_xtal_capcode_pre_need_lock(uint8_t capcode, uint8_t program);
int8_t mfg_media_write_xtal_capcode_pre_with_lock(uint8_t capcode, uint8_t program);
void mfg_media_write_xtal_capcode_need_lock(void);
void mfg_media_write_xtal_capcode_with_lock(void);
int8_t mfg_media_read_xtal_capcode_need_lock(uint8_t *capcode, uint8_t reload);
int8_t mfg_media_read_xtal_capcode_with_lock(uint8_t *capcode, uint8_t reload);
uint8_t mfg_media_is_poweroffset_slot_empty(uint8_t reload);
int8_t mfg_media_write_poweroffset_pre_need_lock(int8_t pwrOffset[14], uint8_t program);
int8_t mfg_media_write_poweroffset_pre_with_lock(int8_t pwrOffset[14], uint8_t program);
void mfg_media_write_poweroffset_need_lock(void);
void mfg_media_write_poweroffset_with_lock(void);
int8_t mfg_media_read_poweroffset_need_lock(int8_t pwrOffset[14], uint8_t reload);
int8_t mfg_media_read_poweroffset_with_lock(int8_t pwrOffset[14], uint8_t reload);
uint8_t mfg_media_is_macaddr_slot_empty(uint8_t reload);
int8_t mfg_media_write_macaddr_pre_need_lock(uint8_t mac[6], uint8_t program);
int8_t mfg_media_write_macaddr_pre_with_lock(uint8_t mac[6], uint8_t program);
void mfg_media_write_macaddr_need_lock(void);
void mfg_media_write_macaddr_with_lock(void);
int8_t mfg_media_read_macaddr_need_lock(uint8_t mac[6], uint8_t reload);
int8_t mfg_media_read_macaddr_with_lock(uint8_t mac[6], uint8_t reload);
#endif /*__MFG_GPIO_API_H__*/

View File

@@ -1,502 +0,0 @@
/**
******************************************************************************
* @file bl602_pds.h
* @version V1.0
* @date
* @brief This file is the standard driver header file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#ifndef __BL602_PDS_H__
#define __BL602_PDS_H__
#include "pds_reg.h"
#include "bl602_ef_ctrl.h"
#include "bl602_aon.h"
#include "bl602_hbn.h"
#include "bl602_sflash.h"
#include "bl602_common.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup PDS
* @{
*/
/** @defgroup PDS_Public_Types
* @{
*/
/**
* @brief PDS LDO level type definition
*/
typedef enum {
PDS_LDO_LEVEL_0P60V = 0, /*!< PDS LDO voltage 0.60V */
PDS_LDO_LEVEL_0P65V = 1, /*!< PDS LDO voltage 0.65V */
PDS_LDO_LEVEL_0P70V = 2, /*!< PDS LDO voltage 0.70V */
PDS_LDO_LEVEL_0P75V = 3, /*!< PDS LDO voltage 0.75V */
PDS_LDO_LEVEL_0P80V = 4, /*!< PDS LDO voltage 0.80V */
PDS_LDO_LEVEL_0P85V = 5, /*!< PDS LDO voltage 0.85V */
PDS_LDO_LEVEL_0P90V = 6, /*!< PDS LDO voltage 0.90V */
PDS_LDO_LEVEL_0P95V = 7, /*!< PDS LDO voltage 0.95V */
PDS_LDO_LEVEL_1P00V = 8, /*!< PDS LDO voltage 1.00V */
PDS_LDO_LEVEL_1P05V = 9, /*!< PDS LDO voltage 1.05V */
PDS_LDO_LEVEL_1P10V = 10, /*!< PDS LDO voltage 1.10V */
PDS_LDO_LEVEL_1P15V = 11, /*!< PDS LDO voltage 1.15V */
PDS_LDO_LEVEL_1P20V = 12, /*!< PDS LDO voltage 1.20V */
PDS_LDO_LEVEL_1P25V = 13, /*!< PDS LDO voltage 1.25V */
PDS_LDO_LEVEL_1P30V = 14, /*!< PDS LDO voltage 1.30V */
PDS_LDO_LEVEL_1P35V = 15, /*!< PDS LDO voltage 1.35V */
} PDS_LDO_LEVEL_Type;
/**
* @brief PDS configuration type definition
*/
typedef struct
{
uint32_t pdsStart : 1; /*!< [0]PDS Start */
uint32_t sleepForever : 1; /*!< [1]PDS sleep forever */
uint32_t xtalForceOff : 1; /*!< [2]Power off xtal force */
uint32_t saveWiFiState : 1; /*!< [3]Save WIFI State Before Enter PDS */
uint32_t dcdc18Off : 1; /*!< [4]power down dcdc18 during PDS */
uint32_t bgSysOff : 1; /*!< [5]power down bg_sys during PDS */
uint32_t rsv6_7 : 2; /*!< [7:6]reserve */
uint32_t clkOff : 1; /*!< [8]gate clock during PDS (each pwr domain has its own control) */
uint32_t memStby : 1; /*!< [9]mem_stby during PDS (each power domain can has its own control) */
uint32_t rsv10 : 1; /*!< [10]reserve */
uint32_t isolation : 1; /*!< [11]Isolation during PDS (each power domain can has its own control) */
uint32_t waitXtalRdy : 1; /*!< [12]wait XTAL Ready during before PDS Interrupt */
uint32_t pdsPwrOff : 1; /*!< [13]Power off during PDS (each power domain can has its own control) */
uint32_t xtalOff : 1; /*!< [14]xtal power down during PDS */
uint32_t socEnbForceOn : 1; /*!< [15]pds_soc_enb always active */
uint32_t pdsRstSocEn : 1; /*!< [16]pds_rst controlled by PDS */
uint32_t pdsRC32mOn : 1; /*!< [17]RC32M always on or RC32M on/off controlled by PDS state */
uint32_t pdsLdoVselEn : 1; /*!< [18]PDS "SLEEP" control LDO voltage enable */
uint32_t rsv19_20 : 2; /*!< [20:19]reserve */
uint32_t wfiMask : 1; /*!< [21]pds start condition mask np_wfi */
uint32_t ldo11Off : 1; /*!< [22]power down ldo11 during PDS */
uint32_t rsv23 : 1; /*!< [23]reserve */
uint32_t pdsLdoVol : 4; /*!< [27:24]LDO voltage value in PDS mode */
uint32_t pdsCtlRfSel : 2; /*!< [29:28]select the way RF controlled by PDS */
uint32_t pdsCtlPllSel : 2; /*!< [31:30]select the way PLL controlled by PDS */
} PDS_CTL_Type;
/**
* @brief PDS force configuration type definition
*/
typedef struct
{
uint32_t cpuPwrOff : 1; /*!< [0] */
uint32_t cpuRst : 1; /*!< [1] */
uint32_t cpuMemStby : 1; /*!< [2] */
uint32_t cpuGateClk : 1; /*!< [3] */
uint32_t rsv4_11 : 8; /*!< [11:4]reserve */
uint32_t WbPwrOff : 1; /*!< [12] */
uint32_t WbRst : 1; /*!< [13] */
uint32_t WbMemStby : 1; /*!< [14] */
uint32_t WbGateClk : 1; /*!< [15] */
uint32_t rsv16_23 : 8; /*!< [23:16]reserve */
uint32_t MiscPwrOff : 1; /*!< [24] */
uint32_t MiscRst : 1; /*!< [25] */
uint32_t MiscMemStby : 1; /*!< [26] */
uint32_t MiscGateClk : 1; /*!< [27] */
uint32_t rsv28_31 : 4; /*!< [31:28]reserve */
} PDS_CTL4_Type;
/**
* @brief PDS interrupt type definition
*/
typedef enum {
PDS_INT_WAKEUP = 0, /*!< PDS wakeup interrupt(assert bit while wakeup, include PDS_Timer/...) */
PDS_INT_HBN_GPIO_IRRX_BLE_WIFI = 1, /*!< PDS in interrupt source HBN_Wakeup_Source/All_GPIO_Wakeup/IRRX/BLE_Wakeup_Eveent/WIFI_Wakeup_Event */
PDS_INT_RF_DONE = 2, /*!< PDS RF done interrupt */
PDS_INT_PLL_DONE = 3, /*!< PDS PLL done interrupt */
PDS_INT_MAX = 4, /*!< PDS int max number */
} PDS_INT_Type;
/**
* @brief PDS force configuration type definition
*/
typedef struct
{
uint32_t forceCpuPwrOff : 1; /*!< [0]manual force NP power off */
uint32_t rsv1 : 1; /*!< [1]reserve */
uint32_t forceWbPwrOff : 1; /*!< [2]manual force WB power off */
uint32_t rsv3 : 1; /*!< [3]reserve */
uint32_t forceCpuIsoPwrOff : 1; /*!< [4]manual force NP isolation */
uint32_t rsv5 : 1; /*!< [5]reserve */
uint32_t forceWbIsoPwrOff : 1; /*!< [6]manual force WB isolation */
uint32_t rsv7 : 1; /*!< [7]reserve */
uint32_t forceCpuPdsRst : 1; /*!< [8]manual force NP pds reset */
uint32_t rsv9 : 1; /*!< [9]reserve */
uint32_t forceWbPdsRst : 1; /*!< [10]manual force WB pds reset */
uint32_t rsv11 : 1; /*!< [11]reserve */
uint32_t forceCpuMemStby : 1; /*!< [12]manual force NP memory sleep */
uint32_t rsv13 : 1; /*!< [13]reserve */
uint32_t forceWbMemStby : 1; /*!< [14]manual force WB memory sleep */
uint32_t rsv15 : 1; /*!< [15]reserve */
uint32_t forceCpuGateClk : 1; /*!< [16]manual force NP clock gated */
uint32_t rsv17 : 1; /*!< [17]reserve */
uint32_t forceWbGateClk : 1; /*!< [18]manual force WB clock gated */
uint32_t rsv19_31 : 12; /*!< [31:19]reserve */
} PDS_CTL2_Type;
/**
* @brief PDS force configuration type definition
*/
typedef struct
{
uint32_t rsv0 : 1; /*!< [0]reserve */
uint32_t forceMiscPwrOff : 1; /*!< [1]manual force MISC pwr_off */
uint32_t rsv2_3 : 2; /*!< [3:2]reserve */
uint32_t forceMiscIsoEn : 1; /*!< [4]manual force MISC iso_en */
uint32_t rsv5_6 : 2; /*!< [6:5]reserve */
uint32_t forceMiscPdsRst : 1; /*!< [7]manual force MISC pds_rst */
uint32_t rsv8_9 : 2; /*!< [9:8]reserve */
uint32_t forceMiscMemStby : 1; /*!< [10]manual force MISC mem_stby */
uint32_t rsv11_12 : 2; /*!< [12:11]reserve */
uint32_t forceMiscGateClk : 1; /*!< [13]manual force MISC gate_clk */
uint32_t rsv14_23 : 10; /*!< [23:14]reserve */
uint32_t CpuIsoEn : 1; /*!< [24]make NP isolated at PDS Sleep state */
uint32_t rsv25_26 : 2; /*!< [26:25]reserve */
uint32_t WbIsoEn : 1; /*!< [27]make WB isolated at PDS Sleep state */
uint32_t rsv28_29 : 2; /*!< [29:28]reserve */
uint32_t MiscIsoEn : 1; /*!< [30]make misc isolated at PDS Sleep state */
uint32_t rsv31 : 1; /*!< [31]reserve */
} PDS_CTL3_Type;
/**
* @brief PDS default level configuration type definition
*/
typedef struct
{
PDS_CTL_Type pdsCtl; /*!< PDS_CTL configuration */
PDS_CTL2_Type pdsCtl2; /*!< PDS_CTL2 configuration */
PDS_CTL3_Type pdsCtl3; /*!< PDS_CTL3 configuration */
PDS_CTL4_Type pdsCtl4; /*!< PDS_CTL4 configuration */
} PDS_DEFAULT_LV_CFG_Type;
/**
* @brief PDS PLL status type definition
*/
typedef enum {
PDS_PLL_STS_OFF = 0, /*!< 2'b00 */
PDS_PLL_STS_SFREG = 1, /*!< 2'b01 */
PDS_PLL_STS_PU = 2, /*!< 2'b10 */
PDS_PLL_STS_RDY = 3, /*!< 2'b11 */
} PDS_PLL_STS_Type;
/**
* @brief PDS RF status type definition
*/
typedef enum {
PDS_RF_STS_OFF = 0, /*!< 4'b0000 */
PDS_RF_STS_PU_MBG = 1, /*!< 4'b0001 */
PDS_RF_STS_PU_LDO15RF = 3, /*!< 4'b0011 */
PDS_RF_STS_PU_SFREG = 7, /*!< 4'b0111 */
PDS_RF_STS_WB_EN_AON = 15, /*!< 4'b1111 */
} PDS_RF_STS_Type;
/**
* @brief PDS status type definition
*/
typedef enum {
PDS_STS_IDLE = 0, /*!< 4'b0000 */
PDS_STS_ECG = 8, /*!< 4'b1000 */
PDS_STS_ERST = 12, /*!< 4'b1100 */
PDS_STS_EISO = 15, /*!< 4'b1111 */
PDS_STS_POFF = 7, /*!< 4'b0111 */
PDS_STS_PRE_BGON = 3, /*!< 4'b0011 */
PDS_STS_PRE_BGON1 = 1, /*!< 4'b0001 */
PDS_STS_BGON = 5, /*!< 4'b0101 */
PDS_STS_CLK_SW_32M = 4, /*!< 4'b0100 */
PDS_STS_PON_DCDC = 6, /*!< 4'b0110 */
PDS_STS_PON_LDO11_MISC = 14, /*!< 4'b1110 */
PDS_STS_PON = 10, /*!< 4'b1010 */
PDS_STS_DISO = 2, /*!< 4'b0010 */
PDS_STS_DCG = 13, /*!< 4'b1101 */
PDS_STS_DRST = 11, /*!< 4'b1011 */
PDS_STS_WAIT_EFUSE = 9, /*!< 4'b1001 */
} PDS_STS_Type;
/**
* @brief PDS RAM configuration type definition
*/
typedef struct
{
uint32_t PDS_RAM_CFG_0KB_16KB_CPU_RAM_RET : 1; /*!< [0] 0~16KB cpu_ram RET */
uint32_t PDS_RAM_CFG_16KB_32KB_CPU_RAM_RET : 1; /*!< [1] 16~32KB cpu_ram RET */
uint32_t PDS_RAM_CFG_32KB_48KB_CPU_RAM_RET : 1; /*!< [2] 32~48KB cpu_ram RET */
uint32_t PDS_RAM_CFG_48KB_64KB_CPU_RAM_RET : 1; /*!< [3] 48~64KB cpu_ram RET */
uint32_t PDS_RAM_CFG_0KB_16KB_CPU_RAM_SLP : 1; /*!< [4] 0~16KB cpu_ram SLP */
uint32_t PDS_RAM_CFG_16KB_32KB_CPU_RAM_SLP : 1; /*!< [5] 16~32KB cpu_ram SLP */
uint32_t PDS_RAM_CFG_32KB_48KB_CPU_RAM_SLP : 1; /*!< [6] 32~48KB cpu_ram SLP */
uint32_t PDS_RAM_CFG_48KB_64KB_CPU_RAM_SLP : 1; /*!< [7] 48~64KB cpu_ram SLP */
uint32_t PDS_RAM_CFG_RSV : 24; /*!< [31:8]reserve */
} PDS_RAM_CFG_Type;
/**
* @brief PLL XTAL type definition
*/
typedef enum {
PDS_PLL_XTAL_NONE, /*!< XTAL is none */
PDS_PLL_XTAL_24M, /*!< XTAL is 24M */
PDS_PLL_XTAL_32M, /*!< XTAL is 32M */
PDS_PLL_XTAL_38P4M, /*!< XTAL is 38.4M */
PDS_PLL_XTAL_40M, /*!< XTAL is 40M */
PDS_PLL_XTAL_26M, /*!< XTAL is 26M */
PDS_PLL_XTAL_RC32M, /*!< XTAL is RC32M */
} PDS_PLL_XTAL_Type;
/**
* @brief PLL output clock type definition
*/
typedef enum {
PDS_PLL_CLK_480M, /*!< PLL output clock:480M */
PDS_PLL_CLK_240M, /*!< PLL output clock:240M */
PDS_PLL_CLK_192M, /*!< PLL output clock:192M */
PDS_PLL_CLK_160M, /*!< PLL output clock:160M */
PDS_PLL_CLK_120M, /*!< PLL output clock:120M */
PDS_PLL_CLK_96M, /*!< PLL output clock:96M */
PDS_PLL_CLK_80M, /*!< PLL output clock:80M */
PDS_PLL_CLK_48M, /*!< PLL output clock:48M */
PDS_PLL_CLK_32M, /*!< PLL output clock:32M */
} PDS_PLL_CLK_Type;
/**
* @brief PDS level 0/1/2/3 mode HBN GPIO interrupt trigger type definition
*/
typedef enum {
PDS_AON_GPIO_INT_TRIGGER_SYNC_FALLING_EDGE, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: sync falling edge trigger */
PDS_AON_GPIO_INT_TRIGGER_SYNC_RISING_EDGE, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: sync rising edge trigger */
PDS_AON_GPIO_INT_TRIGGER_SYNC_LOW_LEVEL, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: sync low level trigger */
PDS_AON_GPIO_INT_TRIGGER_SYNC_HIGH_LEVEL, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: sync high level trigger */
PDS_AON_GPIO_INT_TRIGGER_ASYNC_FALLING_EDGE, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: async falling edge trigger */
PDS_AON_GPIO_INT_TRIGGER_ASYNC_RISING_EDGE, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: async rising edge trigger */
PDS_AON_GPIO_INT_TRIGGER_ASYNC_LOW_LEVEL, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: async low level trigger */
PDS_AON_GPIO_INT_TRIGGER_ASYNC_HIGH_LEVEL, /*!< PDS level 0/1/2/3 mode HBN GPIO INT trigger type: async high level trigger */
} PDS_AON_GPIO_INT_Trigger_Type;
/**
* @brief PDS APP configuration type definition
*/
typedef struct
{
uint8_t pdsLevel; /*!< PDS level */
uint8_t turnOffRF; /*!< Wheather turn off RF */
uint8_t useXtal32k; /*!< Wheather use xtal 32K as 32K clock source,otherwise use rc32k */
uint8_t pdsAonGpioWakeupSrc; /*!< PDS level 0/1/2/3 mode always on GPIO Wakeup source(HBN wakeup pin) */
PDS_AON_GPIO_INT_Trigger_Type pdsAonGpioTrigType; /*!< PDS level 0/1/2/3 mode always on GPIO Triger type(HBN wakeup pin) */
uint8_t powerDownFlash; /*!< Whether power down flash */
uint8_t turnOffFlashPad; /*!< Whether turn off embedded flash pad */
uint8_t ocramRetetion; /*!< Whether OCRAM Retention */
uint8_t turnoffPLL; /*!< Whether trun off PLL */
uint8_t xtalType; /*!< XTal type, used when user choose turn off PLL, PDS will turn on when exit PDS mode */
uint8_t flashContRead; /*!< Whether enable flash continue read */
uint32_t sleepTime; /*!< PDS sleep time */
SPI_Flash_Cfg_Type *flashCfg; /*!< Flash config pointer, used when power down flash */
PDS_LDO_LEVEL_Type ldoLevel; /*!< LDO level */
void (*preCbFun)(void); /*!< Pre callback function */
void (*postCbFun)(void); /*!< Post callback function */
} PDS_APP_CFG_Type;
/*@} end of group PDS_Public_Types */
/** @defgroup PDS_Public_Constants
* @{
*/
/** @defgroup PDS_LDO_LEVEL_TYPE
* @{
*/
#define IS_PDS_LDO_LEVEL_TYPE(type) (((type) == PDS_LDO_LEVEL_0P60V) || \
((type) == PDS_LDO_LEVEL_0P65V) || \
((type) == PDS_LDO_LEVEL_0P70V) || \
((type) == PDS_LDO_LEVEL_0P75V) || \
((type) == PDS_LDO_LEVEL_0P80V) || \
((type) == PDS_LDO_LEVEL_0P85V) || \
((type) == PDS_LDO_LEVEL_0P90V) || \
((type) == PDS_LDO_LEVEL_0P95V) || \
((type) == PDS_LDO_LEVEL_1P00V) || \
((type) == PDS_LDO_LEVEL_1P05V) || \
((type) == PDS_LDO_LEVEL_1P10V) || \
((type) == PDS_LDO_LEVEL_1P15V) || \
((type) == PDS_LDO_LEVEL_1P20V) || \
((type) == PDS_LDO_LEVEL_1P25V) || \
((type) == PDS_LDO_LEVEL_1P30V) || \
((type) == PDS_LDO_LEVEL_1P35V))
/** @defgroup PDS_INT_TYPE
* @{
*/
#define IS_PDS_INT_TYPE(type) (((type) == PDS_INT_WAKEUP) || \
((type) == PDS_INT_HBN_GPIO_IRRX_BLE_WIFI) || \
((type) == PDS_INT_RF_DONE) || \
((type) == PDS_INT_PLL_DONE) || \
((type) == PDS_INT_MAX))
/** @defgroup PDS_PLL_STS_TYPE
* @{
*/
#define IS_PDS_PLL_STS_TYPE(type) (((type) == PDS_PLL_STS_OFF) || \
((type) == PDS_PLL_STS_SFREG) || \
((type) == PDS_PLL_STS_PU) || \
((type) == PDS_PLL_STS_RDY))
/** @defgroup PDS_RF_STS_TYPE
* @{
*/
#define IS_PDS_RF_STS_TYPE(type) (((type) == PDS_RF_STS_OFF) || \
((type) == PDS_RF_STS_PU_MBG) || \
((type) == PDS_RF_STS_PU_LDO15RF) || \
((type) == PDS_RF_STS_PU_SFREG) || \
((type) == PDS_RF_STS_WB_EN_AON))
/** @defgroup PDS_STS_TYPE
* @{
*/
#define IS_PDS_STS_TYPE(type) (((type) == PDS_STS_IDLE) || \
((type) == PDS_STS_ECG) || \
((type) == PDS_STS_ERST) || \
((type) == PDS_STS_EISO) || \
((type) == PDS_STS_POFF) || \
((type) == PDS_STS_PRE_BGON) || \
((type) == PDS_STS_PRE_BGON1) || \
((type) == PDS_STS_BGON) || \
((type) == PDS_STS_CLK_SW_32M) || \
((type) == PDS_STS_PON_DCDC) || \
((type) == PDS_STS_PON_LDO11_MISC) || \
((type) == PDS_STS_PON) || \
((type) == PDS_STS_DISO) || \
((type) == PDS_STS_DCG) || \
((type) == PDS_STS_DRST) || \
((type) == PDS_STS_WAIT_EFUSE))
/** @defgroup PDS_PLL_XTAL_TYPE
* @{
*/
#define IS_PDS_PLL_XTAL_TYPE(type) (((type) == PDS_PLL_XTAL_NONE) || \
((type) == PDS_PLL_XTAL_24M) || \
((type) == PDS_PLL_XTAL_32M) || \
((type) == PDS_PLL_XTAL_38P4M) || \
((type) == PDS_PLL_XTAL_40M) || \
((type) == PDS_PLL_XTAL_26M) || \
((type) == PDS_PLL_XTAL_RC32M))
/** @defgroup PDS_PLL_CLK_TYPE
* @{
*/
#define IS_PDS_PLL_CLK_TYPE(type) (((type) == PDS_PLL_CLK_480M) || \
((type) == PDS_PLL_CLK_240M) || \
((type) == PDS_PLL_CLK_192M) || \
((type) == PDS_PLL_CLK_160M) || \
((type) == PDS_PLL_CLK_120M) || \
((type) == PDS_PLL_CLK_96M) || \
((type) == PDS_PLL_CLK_80M) || \
((type) == PDS_PLL_CLK_48M) || \
((type) == PDS_PLL_CLK_32M))
/** @defgroup PDS_AON_GPIO_INT_TRIGGER_TYPE
* @{
*/
#define IS_PDS_AON_GPIO_INT_TRIGGER_TYPE(type) (((type) == PDS_AON_GPIO_INT_TRIGGER_SYNC_FALLING_EDGE) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_SYNC_RISING_EDGE) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_SYNC_LOW_LEVEL) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_SYNC_HIGH_LEVEL) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_ASYNC_FALLING_EDGE) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_ASYNC_RISING_EDGE) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_ASYNC_LOW_LEVEL) || \
((type) == PDS_AON_GPIO_INT_TRIGGER_ASYNC_HIGH_LEVEL))
/*@} end of group PDS_Public_Constants */
/** @defgroup PDS_Public_Macros
* @{
*/
#define PDS_LDO_MIN_PU_CNT (25) /* LDO need 25 cycles to power up */
#define PDS_WARMUP_LATENCY_CNT (38) /* LDO hw warmup compensation latency cycles */
#define PDS_FORCE_PWR_OFF_OFFSET (0)
#define PDS_FORCE_ISO_EN_OFFSET (4)
#define PDS_FORCE_PDS_RST_OFFSET (8)
#define PDS_FORCE_MEM_STBY_OFFSET (12)
#define PDS_FORCE_GATE_CLK_OFFSET (16)
#define PDS_INT_MASK_BIT_OFFSET (8)
#define PDS_AON_WAKEUP_GPIO_NONE (0x00)
#define PDS_AON_WAKEUP_GPIO_7 (0x01)
#define PDS_AON_WAKEUP_GPIO_8 (0x02)
#define PDS_AON_WAKEUP_GPIO_ALL (0x03)
/*@} end of group PDS_Public_Macros */
/** @defgroup PDS_Public_Functions
* @{
*/
/*----------*/
#ifndef BFLB_USE_HAL_DRIVER
void PDS_WAKEUP_IRQHandler(void);
#endif
/*----------*/
BL_Err_Type PDS_Reset(void);
BL_Err_Type PDS_Enable(PDS_CTL_Type *cfg, PDS_CTL4_Type *cfg4, uint32_t pdsSleepCnt);
BL_Err_Type PDS_Force_Config(PDS_CTL2_Type *cfg2, PDS_CTL3_Type *cfg3);
BL_Err_Type PDS_RAM_Config(PDS_RAM_CFG_Type *ramCfg);
/*----------*/
BL_Err_Type PDS_Default_Level_Config(PDS_DEFAULT_LV_CFG_Type *defaultLvCfg,
PDS_RAM_CFG_Type *ramCfg, uint32_t pdsSleepCnt);
/*----------*/
BL_Err_Type PDS_IntMask(PDS_INT_Type intType, BL_Mask_Type intMask);
BL_Sts_Type PDS_Get_IntStatus(PDS_INT_Type intType);
BL_Err_Type PDS_IntClear(void);
PDS_PLL_STS_Type PDS_Get_PdsPllStstus(void);
PDS_RF_STS_Type PDS_Get_PdsRfStstus(void);
PDS_STS_Type PDS_Get_PdsStstus(void);
BL_Err_Type PDS_WAKEUP_IRQHandler_Install(void);
BL_Err_Type PDS_Int_Callback_Install(PDS_INT_Type intType, intCallback_Type *cbFun);
/*----------*/
BL_Err_Type PDS_Trim_RC32M(void);
BL_Err_Type PDS_Select_RC32M_As_PLL_Ref(void);
BL_Err_Type PDS_Select_XTAL_As_PLL_Ref(void);
BL_Err_Type PDS_Power_On_PLL(PDS_PLL_XTAL_Type xtalType);
BL_Err_Type PDS_Fix_Xtal_Settig(void);
BL_Err_Type PDS_Enable_PLL_All_Clks(void);
BL_Err_Type PDS_Enable_PLL_Clk(PDS_PLL_CLK_Type pllClk);
BL_Err_Type PDS_Disable_PLL_All_Clks(void);
BL_Err_Type PDS_Disable_PLL_Clk(PDS_PLL_CLK_Type pllClk);
BL_Err_Type PDS_Power_Off_PLL(void);
/*----------*/;
/*@} end of group PDS_Public_Functions */
/*@} end of group PDS */
/*@} end of group BL602_Peripheral_Driver */
#endif /* __BL602_PDS_H__ */

View File

@@ -1,184 +0,0 @@
#ifndef __BL602_SDU_H__
#define __BL602_SDU_H__
#include "bl602.h"
#include "bl602_common.h"
#define NUM_FUNC 1
#define FUNC_WIFI 0
// SDIO I/O Enable
#define BL_SDIO_IO_ENABLE SDU_BASE + 0x00000002
//CCCR (Fn0) Registers
// SDIO Device Sleep
#define BL_SDIO_DEV_SLEEP SDU_BASE + 0x00000092
// Start Address of CCR
#define BL_SDIO_CCR_BASE SDU_BASE + 0x00000100
// Address offset of CCR between two functions
#define BL_SDIO_CCR_FUNC_OFFSET 0x00000100
// Address for sdio block size information
#define SDIO_FN1_BLK_SIZE_0 (SDU_BASE + 0x00000028)
#define SDIO_FN1_BLK_SIZE_1 (SDU_BASE + 0x00000029)
#define SDIO_FN1_BLK_SIZE_1_MASK 0x01
#define BL_FUNC_SCRATCH_BASE SDU_BASE + 0x00000160
typedef struct
{
uint8_t HostToCardEvent; // 0x100/200
uint8_t HostIntCause; // 0x101/201
uint8_t HostIntMask; // 0x102/202
uint8_t HostIntStatus; // 0x103/203
uint16_t RdBitMap; // 0x104/204
uint16_t WrBitMap; // 0x106/206
uint16_t RdLen[16]; // 0x108/208
uint8_t HostTransferStatus; // 0x128/228
uint8_t reserved1[0x130 - 0x128 - 1];
uint8_t CardToHostEvent; // 0x130/230
uint8_t reserved2[3];
uint8_t CardIntMask; // 0x134/234
uint8_t reserved3[3];
uint8_t CardIntStatus; // 0x138/238
uint8_t reserved4[3];
uint8_t CardIntMode; // 0x13C/23C
uint8_t reserved5[3];
uint32_t SqReadBase; // 0x140/240
uint32_t SqWriteBase; // 0x144/244
uint8_t RdIdx; // 0x148/248
uint8_t WrIdx; // 0x149/249
uint8_t DnldQueueWrPtr; // 0x14A/24A
uint8_t UpldQueueWrPtr; // 0x14B/24B
uint8_t DnldQueue[8]; // 0x14C/24C
uint8_t UpldQueue[8]; // 0x154/254
uint8_t ChipRev; // 0x15C //RO
uint8_t reserved6; // 0x15D //NOT_DEFINE
uint8_t IPRev0; // 0x15E //RO
uint8_t IPRev1; // 0x15F //RO
uint8_t reserved7[4]; // 0x160/260
uint16_t Scratch2; // 0x164/264
uint16_t Scratch1; // 0x166/266
uint8_t Ocr0; // 0x168/268
uint8_t Ocr1; // 0x169/269
uint8_t Ocr2; // 0x16A/26A
uint8_t Config; // 0x16B/26B
uint32_t Config2; // 0x16C/26C
uint32_t Debug; // 0x170/270
uint32_t DmaAddr; // 0x174/274
uint8_t IoPort[3]; // 0x178/278
} __attribute__((packed)) HidSdio_RegMap_t, *pHidSdio_RegMap_t;
// Common I/O Area Registers (CIA) Offset
//
// Bit Def. Host To Card Interrupt Event (Offset 0x100/200)
#define SDIO_HCR_CONFIG_HostPwrUp (1 << 1)
// Bit Def. Host Transfer Status (Offset 0x128/228)
#define SDIO_CCR_HOST_INT_DnLdReStart (1 << 0)
#define SDIO_CCR_HOST_INT_UpLdReStart (1 << 1)
#define SDIO_CCR_HOST_INT_DnLdCRC_err (1 << 2)
// Bit Def. Card To Host Interrupt Event (Offset 0x130/230)
#define SDIO_CCR_CS_DnLdRdy (1 << 0)
#define SDIO_CCR_CS_UpLdRdy (1 << 1)
#define SDIO_CCR_CS_ReadCISRdy (1 << 2)
#define SDIO_CCR_CS_IORdy (1 << 3)
// Bit Def. Card Interrupt Mask (Offset 0x134/234)
#define SDIO_CCR_CIM_DnLdOvr (1 << 0)
#define SDIO_CCR_CIM_UpLdOvr (1 << 1)
#define SDIO_CCR_CIM_Abort (1 << 2)
#define SDIO_CCR_CIM_PwrDn (1 << 3)
#define SDIO_CCR_CIM_PwrUp (1 << 4)
#define SDIO_CCR_CIM_MASK 0x0007
// Bit Def. Card Interrupt Status (Offset 0x138/238)
#define SDIO_CCR_CIC_DnLdOvr (1 << 0)
#define SDIO_CCR_CIC_UpLdOvr (1 << 1)
#define SDIO_CCR_CIC_Abort (1 << 2)
#define SDIO_CCR_CIC_PwrDn (1 << 3)
#define SDIO_CCR_CIC_PwrUp (1 << 4)
#define SDIO_CCR_CIC_MASK 0x001F
// Bit Def. Card Interrupt RSR (Offset 0x13C/23C)
#define SDIO_CCR_CIO_DnLdOvr (1 << 0)
#define SDIO_CCR_CIO_UpLdOvr (1 << 1)
#define SDIO_CCR_CIO_Abort (1 << 2)
#define SDIO_CCR_CIO_PwrDn (1 << 3)
#define SDIO_CCR_CIO_PwrUp (1 << 4)
#define SDIO_CCR_CIO_MASK 0x001F
//Config2 register mask
#define CONFIG2_MSK 0x00000C00
//CardIntMode register mask
#define CARD_INT_MODE_MSK 0x00000003
#define HOST_INT_MSK 0x00000002
//=============================================================================
// PUBLIC MACROS
//=============================================================================
#define BL_REGS8(x) (*(volatile unsigned char *)(x))
#define BL_REGS16(x) (*(volatile unsigned short *)(x))
#define BL_REGS32(x) (*(volatile unsigned long *)(x))
#define BL_READ_REGS8(reg, val) ((val) = BL_REGS8(reg))
#define BL_READ_REGS16(reg, val) ((val) = BL_REGS16(reg))
#define BL_READ_REGS32(reg, val) ((val) = BL_REGS32(reg))
#define BL_READ_BYTE(reg, val) ((val) = BL_REGS8(reg))
#define BL_READ_HWORD(reg, val) ((val) = BL_REGS16(reg)) /*half word; */
#define BL_READ_WORD(reg, val) ((val) = BL_REGS32(reg)) /*32 bits */
#define BL_WRITE_REGS8(reg, val) (BL_REGS8(reg) = (val))
#define BL_WRITE_REGS16(reg, val) (BL_REGS16(reg) = (val))
#define BL_WRITE_REGS32(reg, val) (BL_REGS32(reg) = (val))
#define BL_WRITE_BYTE(reg, val) (BL_REGS8(reg) = (val))
#define BL_WRITE_HWORD(reg, val) (BL_REGS16(reg) = (val)) /*half word; */
#define BL_WRITE_WORD(reg, val) (BL_REGS32(reg) = (val)) /*32 bits */
// Write uint32 to a low 16-bit register and a high 16-bit register
#define WRITE2REGS(lo, hi, u32) \
BL_WRITE_HWORD(lo, (uint16_t)((u32)&0xffff)); \
BL_WRITE_HWORD(hi, (uint16_t)(((u32) >> 16) & 0xffff))
#define BL_REGS8_SETBITS(reg, val) (BL_REGS8(reg) |= (uint8)(val))
#define BL_REGS16_SETBITS(reg, val) (BL_REGS16(reg) |= (uint16)(val))
#define BL_REGS32_SETBITS(reg, val) (BL_REGS32(reg) |= (val))
#define BL_REGS8_CLRBITS(reg, val) (BL_REGS8(reg) = (uint8)(BL_REGS8(reg) & ~(val)))
#define BL_REGS16_CLRBITS(reg, val) (BL_REGS16(reg) = (uint16)(BL_REGS16(reg) & ~(val)))
#define BL_REGS32_CLRBITS(reg, val) (BL_REGS32(reg) = (BL_REGS32(reg) & ~(val)))
//=============================================================================
// ENUM TYPE DEFINITION
//=============================================================================
/******************************************************************/
/*!
* \enum SDIO_CMD_TYPE
*
*******************************************************************/
typedef enum {
IOCTL_GET_CONFIG = 0, /*!< Get configuration info */
/* HID IOCTLs*/
IOCTL_HID_GET_BLOCK_SIZE, /*!< Get Block size */
} SDIO_CMD_TYPE;
//=============================================================================
// FUNCTION DECLARATION
//=============================================================================
extern void sdio_GEN_CARD2HOST_INT(uint32_t port_id, uint16_t value);
extern uint32_t sdio_ioctl(uint32_t port_id, SDIO_CMD_TYPE cmd, void *arg);
//=============================================================================
// Variable DECLARATION
//=============================================================================
extern volatile pHidSdio_RegMap_t SdioFuncReg[];
extern uint8_t flag_mport[];
#endif /* __BL602_SDU_H__ */

View File

@@ -1,533 +0,0 @@
#include "bl602_glb.h"
#include "bl602_mfg_efuse.h"
#include "bl602_ef_ctrl.h"
static uint8_t rf_cal_slots = 3;
extern void main(void);
#define RF_CAL_SLOT_CFG_OFFSET (4 * 13)
#ifdef BFLB_MCU_SDK
#include "bflb_platform.h"
#define mfg_print MSG
#else
#define mfg_print printf
#endif
uint8_t mfg_efuse_get_rf_cal_slots(void)
{
#if 0
uint8_t *pslot;
pslot = (uint8_t *)((((uint32_t)main) & 0xfff00000) + RF_CAL_SLOT_CFG_OFFSET);
if(*pslot != 0)
{
rf_cal_slots = *pslot;
}
#endif
return rf_cal_slots;
}
void mfg_efuse_set_rf_cal_slots(uint8_t slots)
{
rf_cal_slots = slots;
}
uint8_t mfg_efuse_is_xtal_capcode_slot_empty(uint8_t reload)
{
uint8_t empty = 0;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_CapCode_Slot_Empty(0, reload)) {
mfg_print("Empty slot:%d\r\n", 0);
empty = 1;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_CapCode_Slot_Empty(1, reload)) {
mfg_print("Empty slot:%d\r\n", 1);
empty = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_CapCode_Slot_Empty(2, reload)) {
mfg_print("Empty slot:%d\r\n", 2);
empty = 1;
} else {
mfg_print("No empty slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
return empty;
}
int8_t mfg_efuse_write_xtal_capcode_pre(uint8_t capcode, uint8_t program)
{
BL_Err_Type ret = SUCCESS;
uint8_t slot = 0xff;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_CapCode_Slot_Empty(0, 1)) {
slot = 0;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_CapCode_Slot_Empty(1, 1)) {
slot = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_CapCode_Slot_Empty(2, 1)) {
slot = 2;
} else {
mfg_print("No empty slot found\r\n");
}
if (slot != 0xff) {
ret = EF_Ctrl_Write_CapCode_Opt(slot, capcode, program);
mfg_print("Write slot:%d\r\n", slot);
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
void mfg_efuse_write_xtal_capcode(void)
{
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
EF_Ctrl_Program_Direct_R0(0, NULL, 0);
while (SET == EF_Ctrl_Busy())
;
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
}
int8_t mfg_efuse_read_xtal_capcode(uint8_t *capcode, uint8_t reload)
{
uint8_t slot = 0xff;
BL_Err_Type ret = ERROR;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 3 && (!EF_Ctrl_Is_CapCode_Slot_Empty(2, reload))) {
slot = 2;
} else if (rf_cal_slots >= 2 && (!EF_Ctrl_Is_CapCode_Slot_Empty(1, reload))) {
slot = 1;
} else if (rf_cal_slots >= 1 && (!EF_Ctrl_Is_CapCode_Slot_Empty(0, reload))) {
slot = 0;
}
if (slot != 0xff) {
mfg_print("Read slot:%d\r\n", slot);
ret = EF_Ctrl_Read_CapCode_Opt(slot, capcode, reload);
} else {
mfg_print("No written slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
uint8_t mfg_efuse_is_poweroffset_slot_empty(uint8_t reload)
{
uint8_t empty = 0;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_PowerOffset_Slot_Empty(0, reload)) {
mfg_print("Empty slot:%d\r\n", 0);
empty = 1;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_PowerOffset_Slot_Empty(1, reload)) {
mfg_print("Empty slot:%d\r\n", 1);
empty = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_PowerOffset_Slot_Empty(2, reload)) {
mfg_print("Empty slot:%d\r\n", 2);
empty = 1;
} else {
mfg_print("No empty slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
return empty;
}
int8_t mfg_efuse_write_poweroffset_pre(int8_t pwrOffset[14], uint8_t program)
{
BL_Err_Type ret = SUCCESS;
uint8_t slot = 0xff;
int8_t pwrOffsetTmp[3];
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_PowerOffset_Slot_Empty(0, 1)) {
slot = 0;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_PowerOffset_Slot_Empty(1, 1)) {
slot = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_PowerOffset_Slot_Empty(2, 1)) {
slot = 2;
} else {
mfg_print("No empty slot found\r\n");
}
if (slot != 0xff) {
pwrOffsetTmp[0] = pwrOffset[0];
pwrOffsetTmp[1] = pwrOffset[6];
pwrOffsetTmp[2] = pwrOffset[12];
ret = EF_Ctrl_Write_PowerOffset_Opt(slot, pwrOffsetTmp, program);
mfg_print("Write slot:%d\r\n", slot);
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
void mfg_efuse_write_poweroffset(void)
{
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
EF_Ctrl_Program_Direct_R0(0, NULL, 0);
while (SET == EF_Ctrl_Busy())
;
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
}
int8_t mfg_efuse_read_poweroffset(int8_t pwrOffset[14], uint8_t reload)
{
uint8_t slot = 0xff;
BL_Err_Type ret = ERROR;
int8_t pwrOffsetTmp[3];
int32_t step = 0;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 3 && (!EF_Ctrl_Is_PowerOffset_Slot_Empty(2, reload))) {
slot = 2;
} else if (rf_cal_slots >= 2 && (!EF_Ctrl_Is_PowerOffset_Slot_Empty(1, reload))) {
slot = 1;
} else if (rf_cal_slots >= 1 && (!EF_Ctrl_Is_PowerOffset_Slot_Empty(0, reload))) {
slot = 0;
}
if (slot != 0xff) {
mfg_print("Read slot:%d\r\n", slot);
ret = EF_Ctrl_Read_PowerOffset_Opt(slot, pwrOffsetTmp, reload);
memset(pwrOffset, 0, 14);
pwrOffset[0] = pwrOffsetTmp[0];
step = (pwrOffsetTmp[1] - pwrOffsetTmp[0]) * 100 / 6;
pwrOffset[1] = (step + 50) / 100 + pwrOffsetTmp[0];
pwrOffset[2] = (step * 2 + 50) / 100 + pwrOffsetTmp[0];
pwrOffset[3] = (step * 3 + 50) / 100 + pwrOffsetTmp[0];
pwrOffset[4] = (step * 4 + 50) / 100 + pwrOffsetTmp[0];
pwrOffset[5] = (step * 5 + 50) / 100 + pwrOffsetTmp[0];
pwrOffset[6] = pwrOffsetTmp[1];
step = (pwrOffsetTmp[2] - pwrOffsetTmp[1]) * 100 / 6;
pwrOffset[7] = (step + 50) / 100 + pwrOffsetTmp[1];
pwrOffset[8] = (step * 2 + 50) / 100 + pwrOffsetTmp[1];
pwrOffset[9] = (step * 3 + 50) / 100 + pwrOffsetTmp[1];
pwrOffset[10] = (step * 4 + 50) / 100 + pwrOffsetTmp[1];
pwrOffset[11] = (step * 5 + 50) / 100 + pwrOffsetTmp[1];
pwrOffset[12] = pwrOffsetTmp[2];
pwrOffset[13] = (step * 7 + 50) / 100 + pwrOffsetTmp[1];
} else {
mfg_print("No written slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
uint8_t mfg_efuse_is_macaddr_slot_empty(uint8_t reload)
{
uint8_t empty = 0;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_MAC_Address_Slot_Empty(0, reload)) {
mfg_print("Empty slot:%d\r\n", 0);
empty = 1;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_MAC_Address_Slot_Empty(1, reload)) {
mfg_print("Empty slot:%d\r\n", 1);
empty = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_MAC_Address_Slot_Empty(2, reload)) {
mfg_print("Empty slot:%d\r\n", 2);
empty = 1;
} else {
mfg_print("No empty slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
return empty;
}
int8_t mfg_efuse_write_macaddr_pre(uint8_t mac[6], uint8_t program)
{
BL_Err_Type ret = SUCCESS;
uint8_t slot = 0xff;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 1 && EF_Ctrl_Is_MAC_Address_Slot_Empty(0, 1)) {
slot = 0;
} else if (rf_cal_slots >= 2 && EF_Ctrl_Is_MAC_Address_Slot_Empty(1, 1)) {
slot = 1;
} else if (rf_cal_slots >= 3 && EF_Ctrl_Is_MAC_Address_Slot_Empty(2, 1)) {
slot = 2;
} else {
mfg_print("No empty slot found\r\n");
}
if (slot != 0xff) {
ret = EF_Ctrl_Write_MAC_Address_Opt(slot, mac, program);
mfg_print("Write slot:%d\r\n", slot);
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
void mfg_efuse_write_macaddr(void)
{
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
EF_Ctrl_Program_Direct_R0(0, NULL, 0);
while (SET == EF_Ctrl_Busy())
;
//EF_Ctrl_Program_Direct_R1(0,NULL,0);
//while(SET==EF_Ctrl_Busy());
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
}
int8_t mfg_efuse_read_macaddr(uint8_t mac[6], uint8_t reload)
{
uint8_t slot = 0xff;
BL_Err_Type ret = ERROR;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
#if 1
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (rf_cal_slots >= 3 && (!EF_Ctrl_Is_MAC_Address_Slot_Empty(2, reload))) {
slot = 2;
} else if (rf_cal_slots >= 2 && (!EF_Ctrl_Is_MAC_Address_Slot_Empty(1, reload))) {
slot = 1;
} else if (rf_cal_slots >= 1 && (!EF_Ctrl_Is_MAC_Address_Slot_Empty(0, reload))) {
slot = 0;
}
if (slot != 0xff) {
mfg_print("Read slot:%d\r\n", slot);
ret = EF_Ctrl_Read_MAC_Address_Opt(slot, mac, reload);
} else {
mfg_print("No written slot found\r\n");
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
#endif
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
int8_t mfg_efuse_write_pre(uint32_t addr, uint32_t *data, uint32_t countInword)
{
BL_Err_Type ret = SUCCESS;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
if (addr > 128) {
return -1;
}
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
EF_Ctrl_Write_R0(addr / 4, data, countInword);
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
int8_t mfg_efuse_read(uint32_t addr, uint32_t *data, uint32_t countInword, uint8_t reload)
{
BL_Err_Type ret = SUCCESS;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
if (addr > 128) {
return -1;
}
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
if (reload) {
EF_Ctrl_Read_Direct_R0(addr / 4, data, countInword);
} else {
EF_Ctrl_Read_R0(addr / 4, data, countInword);
}
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}
int8_t mfg_efuse_program(void)
{
BL_Err_Type ret = SUCCESS;
uint8_t hdiv = 0, bdiv = 0;
HBN_ROOT_CLK_Type rtClk = GLB_Get_Root_CLK_Sel();
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_XTAL);
EF_Ctrl_Program_Direct_R0(0, NULL, 0);
while (SET == EF_Ctrl_Busy())
;
GLB_Set_System_CLK_Div(hdiv, bdiv);
HBN_Set_ROOT_CLK_Sel(rtClk);
if (ret == SUCCESS) {
return 0;
} else {
return -1;
}
}

View File

@@ -1,244 +0,0 @@
#include "bl602_mfg_flash.h"
#include "partition.h"
#include "softcrc.h"
#include "bl602_xip_sflash_ext.h"
// static rf_para_flash_t rf_para;
static uint32_t rf_para_addr = 0;
static SPI_Flash_Cfg_Type *pFlashCfg;
#ifdef BFLB_MCU_SDK
#include "bflb_platform.h"
#define mfg_print MSG
#else
#define mfg_print printf
#endif
//#define RF_PARA_MAGIC_FLAG 0x41504652
#define RF_PARA_MAGIC_FLAG 0x41
#define RF_PARA_VALID_FLAG 0x5A
#define RF_PARA_PART_NAME "rf_para"
// PtTable_Stuff_Config ptTableStuff[2];
// PtTable_Entry_Config ptEntry = { 0 };
/*partiton need this*/
// void main(void)
// {
// }
// static BL_Err_Type PtTable_Flash_Read(uint32_t addr, uint8_t *data, uint32_t len)
// {
// XIP_SFlash_Read_Need_Lock_Ext(pFlashCfg, addr, data, len);
// return SUCCESS;
// }
int8_t mfg_flash_init(SPI_Flash_Cfg_Type *flashCfg)
{
// PtTable_ID_Type activeID;
// PtTable_Error_Type ret;
// pFlashCfg = flashCfg;
// if (pFlashCfg != NULL) {
// PtTable_Set_Flash_Operation(NULL, NULL, PtTable_Flash_Read);
// activeID = PtTable_Get_Active_Partition_Need_Lock(ptTableStuff);
// if (PT_TABLE_ID_INVALID == activeID) {
// mfg_print("No valid PT\r\n");
// return -1;
// }
// ret = PtTable_Get_Active_Entries_By_Name(&ptTableStuff[activeID], (uint8_t *)RF_PARA_PART_NAME, &ptEntry);
// if (PT_ERROR_SUCCESS == ret) {
// rf_para_addr = ptEntry.Address[0];
// mfg_print("RF para flash address=%08x\r\n", (unsigned int)rf_para_addr);
// return 0;
// } else {
// mfg_print("Not found " RF_PARA_PART_NAME "\r\n");
// return -1;
// }
// }
return -1;
}
static int8_t mfg_flash_program(void)
{
BL_Err_Type ret;
mfg_print("mfg_flash_write\r\n");
ret = XIP_SFlash_Erase_Need_Lock_Ext(pFlashCfg, rf_para_addr, rf_para_addr + 15);
if (ret != SUCCESS) {
mfg_print("Flash erase error\r\n");
return -1;
}
// ret = XIP_SFlash_Write_Need_Lock_Ext(pFlashCfg, rf_para_addr, (uint8_t *)&rf_para, sizeof(rf_para));
// if (ret != SUCCESS) {
// mfg_print("Flash write error\r\n");
return -1;
// }
// return 0;
}
static int8_t mfg_flash_read(void)
{
// BL_Err_Type ret;
mfg_print("mfg_flash_read\r\n");
// ret = XIP_SFlash_Read_Need_Lock_Ext(pFlashCfg, rf_para_addr, (uint8_t *)&rf_para, sizeof(rf_para));
// if (ret != SUCCESS) {
// mfg_print("Flash write error\r\n");
// return -1;
// }
return 0;
}
int8_t mfg_flash_write_xtal_capcode_pre(uint8_t capcode, uint8_t program)
{
// rf_para.magic = RF_PARA_MAGIC_FLAG;
// rf_para.capcode_valid = RF_PARA_VALID_FLAG;
// rf_para.capcode = capcode;
// rf_para.crc32 = BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8);
// if (program) {
// return mfg_flash_program();
// } else {
return 0;
// }
}
void mfg_flash_write_xtal_capcode(void)
{
mfg_flash_program();
}
int8_t mfg_flash_read_xtal_capcode(uint8_t *capcode, uint8_t reload)
{
if ((reload != 0) && (mfg_flash_read() != 0)) {
return -1;
}
// if (rf_para.magic == RF_PARA_MAGIC_FLAG) {
// if (rf_para.crc32 == (BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8))) {
// if (rf_para.capcode_valid == RF_PARA_VALID_FLAG) {
// *capcode = rf_para.capcode;
// return 0;
// }
// }
// }
return -1;
}
int8_t mfg_flash_write_poweroffset_pre(int8_t pwrOffset[14], uint8_t program)
{
// rf_para.magic = RF_PARA_MAGIC_FLAG;
// rf_para.poweroffset_valid = RF_PARA_VALID_FLAG;
// rf_para.poweroffset[0] = pwrOffset[0];
// rf_para.poweroffset[1] = pwrOffset[6];
// rf_para.poweroffset[2] = pwrOffset[12];
// rf_para.crc32 = BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8);
// if (program) {
// return mfg_flash_program();
// } else {
return 0;
// }
}
void mfg_flash_write_poweroffset(void)
{
mfg_flash_program();
}
int8_t mfg_flash_read_poweroffset(int8_t pwrOffset[14], uint8_t reload)
{
// int8_t pwrOffsetTmp[3];
// int32_t step = 0;
if ((reload != 0) && (mfg_flash_read() != 0)) {
return -1;
}
// if (rf_para.magic == RF_PARA_MAGIC_FLAG) {
// if (rf_para.crc32 == (BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8))) {
// if (rf_para.poweroffset_valid == RF_PARA_VALID_FLAG) {
// memset(pwrOffset, 0, 14);
// pwrOffsetTmp[0] = rf_para.poweroffset[0];
// pwrOffsetTmp[1] = rf_para.poweroffset[1];
// pwrOffsetTmp[2] = rf_para.poweroffset[2];
// pwrOffset[0] = pwrOffsetTmp[0];
// step = (pwrOffsetTmp[1] - pwrOffsetTmp[0]) * 100 / 6;
// pwrOffset[1] = (step + 50) / 100 + pwrOffsetTmp[0];
// pwrOffset[2] = (step * 2 + 50) / 100 + pwrOffsetTmp[0];
// pwrOffset[3] = (step * 3 + 50) / 100 + pwrOffsetTmp[0];
// pwrOffset[4] = (step * 4 + 50) / 100 + pwrOffsetTmp[0];
// pwrOffset[5] = (step * 5 + 50) / 100 + pwrOffsetTmp[0];
// pwrOffset[6] = pwrOffsetTmp[1];
// step = (pwrOffsetTmp[2] - pwrOffsetTmp[1]) * 100 / 6;
// pwrOffset[7] = (step + 50) / 100 + pwrOffsetTmp[1];
// pwrOffset[8] = (step * 2 + 50) / 100 + pwrOffsetTmp[1];
// pwrOffset[9] = (step * 3 + 50) / 100 + pwrOffsetTmp[1];
// pwrOffset[10] = (step * 4 + 50) / 100 + pwrOffsetTmp[1];
// pwrOffset[11] = (step * 5 + 50) / 100 + pwrOffsetTmp[1];
// pwrOffset[12] = pwrOffsetTmp[2];
// pwrOffset[13] = (step * 7 + 50) / 100 + pwrOffsetTmp[1];
// return 0;
// }
// }
// }
return -1;
}
int8_t mfg_flash_write_macaddr_pre(uint8_t mac[6], uint8_t program)
{
// rf_para.magic = RF_PARA_MAGIC_FLAG;
// rf_para.mac_valid = RF_PARA_VALID_FLAG;
// memcpy(rf_para.mac, mac, 6);
// rf_para.crc32 = BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8);
// if (program) {
// return mfg_flash_program();
// } else {
return 0;
// }
}
void mfg_flash_write_macaddr(void)
{
mfg_flash_program();
}
int8_t mfg_flash_read_macaddr(uint8_t mac[6], uint8_t reload)
{
if ((reload != 0) && (mfg_flash_read() != 0)) {
mfg_print("mfg_flash_read fail\r\n");
return -1;
}
// if (rf_para.magic == RF_PARA_MAGIC_FLAG) {
// if (rf_para.crc32 == (BFLB_Soft_CRC32(&rf_para.capcode_valid, sizeof(rf_para) - 8))) {
// if (rf_para.mac_valid == RF_PARA_VALID_FLAG) {
// memcpy(mac, rf_para.mac, 6);
// return 0;
// }
// }
// }
return -1;
}

View File

@@ -1,222 +0,0 @@
#include "bl602_mfg_media.h"
#include "bl602_mfg_efuse.h"
#include "bl602_mfg_flash.h"
#include "hal_common.h"
static uint8_t rf_para_on_flash = 0;
int8_t mfg_media_init_need_lock(SPI_Flash_Cfg_Type *flashCfg)
{
if (0 == mfg_flash_init(flashCfg)) {
rf_para_on_flash = 1;
} else {
rf_para_on_flash = 0;
}
return 0;
}
int8_t mfg_media_init_with_lock(SPI_Flash_Cfg_Type *flashCfg)
{
int8_t ret;
cpu_global_irq_disable();
ret = mfg_media_init_need_lock(flashCfg);
cpu_global_irq_enable();
return ret;
}
uint8_t mfg_media_is_xtal_capcode_slot_empty(uint8_t reload)
{
if (rf_para_on_flash) {
return 1;
} else {
return mfg_efuse_is_xtal_capcode_slot_empty(reload);
}
}
int8_t mfg_media_write_xtal_capcode_pre_need_lock(uint8_t capcode, uint8_t program)
{
if (rf_para_on_flash) {
return mfg_flash_write_xtal_capcode_pre(capcode, program);
} else {
return mfg_efuse_write_xtal_capcode_pre(capcode, program);
}
}
int8_t mfg_media_write_xtal_capcode_pre_with_lock(uint8_t capcode, uint8_t program)
{
int8_t ret;
cpu_global_irq_disable();
ret = mfg_media_write_xtal_capcode_pre_need_lock(capcode, program);
cpu_global_irq_enable();
return ret;
}
void mfg_media_write_xtal_capcode_need_lock(void)
{
if (rf_para_on_flash) {
return mfg_flash_write_xtal_capcode();
} else {
return mfg_efuse_write_xtal_capcode();
}
}
void mfg_media_write_xtal_capcode_with_lock(void)
{
cpu_global_irq_disable();
mfg_media_write_xtal_capcode_need_lock();
cpu_global_irq_enable();
}
int8_t mfg_media_read_xtal_capcode_need_lock(uint8_t *capcode, uint8_t reload)
{
if (rf_para_on_flash) {
return mfg_flash_read_xtal_capcode(capcode, reload);
} else {
return mfg_efuse_read_xtal_capcode(capcode, reload);
}
}
int8_t mfg_media_read_xtal_capcode_with_lock(uint8_t *capcode, uint8_t reload)
{
int8_t ret;
cpu_global_irq_disable();
ret = mfg_media_read_xtal_capcode_need_lock(capcode, reload);
cpu_global_irq_enable();
return ret;
}
uint8_t mfg_media_is_poweroffset_slot_empty(uint8_t reload)
{
if (rf_para_on_flash) {
return 1;
} else {
return mfg_efuse_is_poweroffset_slot_empty(reload);
}
}
int8_t mfg_media_write_poweroffset_pre_need_lock(int8_t pwrOffset[14], uint8_t program)
{
if (rf_para_on_flash) {
return mfg_flash_write_poweroffset_pre(pwrOffset, program);
} else {
return mfg_efuse_write_poweroffset_pre(pwrOffset, program);
}
}
int8_t mfg_media_write_poweroffset_pre_with_lock(int8_t pwrOffset[14], uint8_t program)
{
int ret;
cpu_global_irq_disable();
ret = mfg_media_write_poweroffset_pre_need_lock(pwrOffset, program);
cpu_global_irq_enable();
return ret;
}
void mfg_media_write_poweroffset_need_lock(void)
{
if (rf_para_on_flash) {
return mfg_flash_write_poweroffset();
} else {
return mfg_efuse_write_poweroffset();
}
}
void mfg_media_write_poweroffset_with_lock(void)
{
cpu_global_irq_disable();
mfg_media_write_poweroffset_need_lock();
cpu_global_irq_enable();
}
int8_t mfg_media_read_poweroffset_need_lock(int8_t pwrOffset[14], uint8_t reload)
{
if (rf_para_on_flash) {
return mfg_flash_read_poweroffset(pwrOffset, reload);
} else {
return mfg_efuse_read_poweroffset(pwrOffset, reload);
}
}
int8_t mfg_media_read_poweroffset_with_lock(int8_t pwrOffset[14], uint8_t reload)
{
int ret;
cpu_global_irq_disable();
ret = mfg_media_read_poweroffset_need_lock(pwrOffset, reload);
cpu_global_irq_enable();
return ret;
}
uint8_t mfg_media_is_macaddr_slot_empty(uint8_t reload)
{
if (rf_para_on_flash) {
return 1;
} else {
return mfg_efuse_is_macaddr_slot_empty(reload);
}
}
int8_t mfg_media_write_macaddr_pre_need_lock(uint8_t mac[6], uint8_t program)
{
if (rf_para_on_flash) {
return mfg_flash_write_macaddr_pre(mac, program);
} else {
return mfg_efuse_write_macaddr_pre(mac, program);
}
}
int8_t mfg_media_write_macaddr_pre_with_lock(uint8_t mac[6], uint8_t program)
{
int ret;
cpu_global_irq_disable();
ret = mfg_media_write_macaddr_pre_need_lock(mac, program);
cpu_global_irq_enable();
return ret;
}
void mfg_media_write_macaddr_need_lock(void)
{
if (rf_para_on_flash) {
mfg_flash_write_macaddr();
} else {
mfg_efuse_write_macaddr();
}
}
void mfg_media_write_macaddr_with_lock(void)
{
cpu_global_irq_disable();
mfg_media_write_macaddr_need_lock();
cpu_global_irq_enable();
}
int8_t mfg_media_read_macaddr_need_lock(uint8_t mac[6], uint8_t reload)
{
if (rf_para_on_flash) {
return mfg_flash_read_macaddr(mac, reload);
} else {
return mfg_efuse_read_macaddr(mac, reload);
}
}
int8_t mfg_media_read_macaddr_with_lock(uint8_t mac[6], uint8_t reload)
{
int ret;
cpu_global_irq_disable();
ret = mfg_media_read_macaddr_need_lock(mac, reload);
cpu_global_irq_enable();
return ret;
}

View File

@@ -1,831 +0,0 @@
/**
******************************************************************************
* @file bl602_pds.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "bl602.h"
#include "bl602_pds.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup PDS
* @{
*/
/** @defgroup PDS_Private_Macros
* @{
*/
/*@} end of group PDS_Private_Macros */
/** @defgroup PDS_Private_Types
* @{
*/
/*@} end of group PDS_Private_Types */
/** @defgroup PDS_Private_Variables
* @{
*/
static intCallback_Type *pdsIntCbfArra[4][1] = { { NULL }, { NULL }, { NULL }, { NULL } };
/*@} end of group PDS_Private_Variables */
/** @defgroup PDS_Global_Variables
* @{
*/
/*@} end of group PDS_Global_Variables */
/** @defgroup PDS_Private_Fun_Declaration
* @{
*/
/*@} end of group PDS_Private_Fun_Declaration */
/** @defgroup PDS_Private_Functions
* @{
*/
/*@} end of group PDS_Private_Functions */
/** @defgroup PDS_Public_Functions
* @{
*/
/****************************************************************************/ /**
* @brief PDS software reset
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_TCM_SECTION PDS_Reset(void)
{
uint32_t tmpVal = 0;
tmpVal = *(uint32_t *)0x40000014;
tmpVal = tmpVal | (1 << 14);
*(uint32_t *)0x40000014 = tmpVal;
tmpVal = *(uint32_t *)0x40000014;
tmpVal = tmpVal & ~(1 << 14);
*(uint32_t *)0x40000014 = tmpVal;
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Enable power down sleep
*
* @param cfg: power down sleep configuration 1
* @param cfg4: power down sleep configuration 2
* @param pdsSleepCnt: power down sleep count cycle
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_TCM_SECTION PDS_Enable(PDS_CTL_Type *cfg, PDS_CTL4_Type *cfg4, uint32_t pdsSleepCnt)
{
/* PDS sleep time 0 <=> sleep forever */
/* PDS sleep time 1~PDS_WARMUP_LATENCY_CNT <=> error */
/* PDS sleep time >PDS_WARMUP_LATENCY_CNT <=> correct */
if (!pdsSleepCnt) {
cfg->sleepForever = 1;
} else if ((pdsSleepCnt) && (pdsSleepCnt <= PDS_WARMUP_LATENCY_CNT)) {
return ERROR;
} else {
BL_WR_REG(PDS_BASE, PDS_TIME1, pdsSleepCnt - PDS_WARMUP_LATENCY_CNT);
}
/* PDS_CTL4 config */
BL_WR_REG(PDS_BASE, PDS_CTL4, *(uint32_t *)cfg4);
/* PDS_CTL config */
if (cfg->pdsStart) {
BL_WR_REG(PDS_BASE, PDS_CTL, (*(uint32_t *)cfg & ~(1 << 0)));
BL_WR_REG(PDS_BASE, PDS_CTL, (*(uint32_t *)cfg | (1 << 0)));
} else {
BL_WR_REG(PDS_BASE, PDS_CTL, *(uint32_t *)cfg);
}
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief power down sleep force configure
*
* @param cfg2: power down sleep force configuration 1
* @param cfg3: power down sleep force configuration 2
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_TCM_SECTION PDS_Force_Config(PDS_CTL2_Type *cfg2, PDS_CTL3_Type *cfg3)
{
/* PDS_CTL2 config */
BL_WR_REG(PDS_BASE, PDS_CTL2, *(uint32_t *)cfg2);
/* PDS_CTL3 config */
BL_WR_REG(PDS_BASE, PDS_CTL3, *(uint32_t *)cfg3);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief power down sleep ram configure
*
* @param ramCfg: power down sleep force ram configuration
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_TCM_SECTION PDS_RAM_Config(PDS_RAM_CFG_Type *ramCfg)
{
uint32_t tmpVal = 0;
if (NULL == ramCfg) {
return SUCCESS;
}
tmpVal = BL_RD_REG(GLB_BASE, GLB_MBIST_CTL);
/* enter bist mode (make ram idle/slp) */
//tmpVal = tmpVal&~0x1F;
//tmpVal = tmpVal|0x18;
/* enter bist mode (make ram ret) */
tmpVal = tmpVal | (0x1 << 3);
BL_WR_REG(GLB_BASE, GLB_MBIST_CTL, tmpVal);
/* PDS_RAM1 config */
BL_WR_REG(PDS_BASE, PDS_RAM1, *(uint32_t *)ramCfg);
tmpVal = BL_RD_REG(GLB_BASE, GLB_MBIST_CTL);
/* exit bist mode (make ram idle/slp) */
//tmpVal = tmpVal&~0x1F;
/* exit bist mode (make ram ret) */
tmpVal = tmpVal & ~(0x1 << 3);
BL_WR_REG(GLB_BASE, GLB_MBIST_CTL, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief power down sleep force configure
*
* @param defaultLvCfg: power down sleep default level configuration
* @param ramCfg: ram configuration
* @param pdsSleepCnt: power down sleep time count
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_TCM_SECTION PDS_Default_Level_Config(PDS_DEFAULT_LV_CFG_Type *defaultLvCfg, PDS_RAM_CFG_Type *ramCfg, uint32_t pdsSleepCnt)
{
/* RAM config need fix after ECO */
PDS_RAM_Config(ramCfg);
PDS_Force_Config((PDS_CTL2_Type *)&(defaultLvCfg->pdsCtl2), (PDS_CTL3_Type *)&(defaultLvCfg->pdsCtl3));
PDS_Enable((PDS_CTL_Type *)&(defaultLvCfg->pdsCtl), (PDS_CTL4_Type *)&(defaultLvCfg->pdsCtl4), pdsSleepCnt);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief power down sleep int mask
*
* @param intType: PDS int type
* @param intMask: MASK or UNMASK
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type PDS_IntMask(PDS_INT_Type intType, BL_Mask_Type intMask)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_INT);
if (intMask != UNMASK) {
tmpVal = tmpVal | (1 << (intType + PDS_INT_MASK_BIT_OFFSET));
} else {
tmpVal = tmpVal & ~(1 << (intType + PDS_INT_MASK_BIT_OFFSET));
}
BL_WR_REG(PDS_BASE, PDS_INT, tmpVal);
return SUCCESS;
}
/****************************************************************************/ /**
* @brief get power down sleep int status
*
* @param intType: PDS int type
*
* @return SET or RESET
*
*******************************************************************************/
BL_Sts_Type PDS_Get_IntStatus(PDS_INT_Type intType)
{
return (BL_RD_REG(PDS_BASE, PDS_INT) & (1 << intType)) ? SET : RESET;
}
/****************************************************************************/ /**
* @brief clear power down sleep int status
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type PDS_IntClear(void)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_INT);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CR_PDS_INT_CLR);
BL_WR_REG(PDS_BASE, PDS_INT, tmpVal);
tmpVal = BL_RD_REG(PDS_BASE, PDS_INT);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CR_PDS_INT_CLR);
BL_WR_REG(PDS_BASE, PDS_INT, tmpVal);
tmpVal = BL_RD_REG(PDS_BASE, PDS_INT);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CR_PDS_INT_CLR);
BL_WR_REG(PDS_BASE, PDS_INT, tmpVal);
return SUCCESS;
}
/****************************************************************************/ /**
* @brief get power down sleep PLL status
*
* @param None
*
* @return PDS PLL status
*
*******************************************************************************/
PDS_PLL_STS_Type PDS_Get_PdsPllStstus(void)
{
return (PDS_PLL_STS_Type)BL_GET_REG_BITS_VAL(BL_RD_REG(PDS_BASE, PDS_STAT), PDS_RO_PDS_PLL_STATE);
}
/****************************************************************************/ /**
* @brief get power down sleep RF status
*
* @param None
*
* @return PDS RF status
*
*******************************************************************************/
PDS_RF_STS_Type PDS_Get_PdsRfStstus(void)
{
return (PDS_RF_STS_Type)BL_GET_REG_BITS_VAL(BL_RD_REG(PDS_BASE, PDS_STAT), PDS_RO_PDS_RF_STATE);
}
/****************************************************************************/ /**
* @brief get power down sleep status
*
* @param None
*
* @return PDS status
*
*******************************************************************************/
PDS_STS_Type PDS_Get_PdsStstus(void)
{
return (PDS_STS_Type)BL_GET_REG_BITS_VAL(BL_RD_REG(PDS_BASE, PDS_STAT), PDS_RO_PDS_STATE);
}
/****************************************************************************/ /**
* @brief PDS wakeup IRQHandler install
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type PDS_WAKEUP_IRQHandler_Install(void)
{
#ifndef BFLB_USE_HAL_DRIVER
Interrupt_Handler_Register(PDS_WAKEUP_IRQn, PDS_WAKEUP_IRQHandler);
#endif
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Install PDS interrupt callback function
*
* @param intType: PDS int type
* @param cbFun: cbFun: Pointer to interrupt callback function. The type should be void (*fn)(void)
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type PDS_Int_Callback_Install(PDS_INT_Type intType, intCallback_Type *cbFun)
{
pdsIntCbfArra[intType][0] = cbFun;
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Trim RC32M
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Trim_RC32M(void)
{
Efuse_Ana_RC32M_Trim_Type trim;
int32_t tmpVal = 0;
EF_Ctrl_Read_RC32M_Trim(&trim);
if (trim.trimRc32mExtCodeEn) {
if (trim.trimRc32mCodeFrExtParity == EF_Ctrl_Get_Trim_Parity(trim.trimRc32mCodeFrExt, 8)) {
tmpVal = BL_RD_REG(PDS_BASE, PDS_RC32M_CTRL0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_RC32M_CODE_FR_EXT, trim.trimRc32mCodeFrExt);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_RC32M_EXT_CODE_EN);
BL_WR_REG(PDS_BASE, PDS_RC32M_CTRL0, tmpVal);
BL602_Delay_US(2);
return SUCCESS;
}
}
return ERROR;
}
#endif
/****************************************************************************/ /**
* @brief Select RC32M as PLL ref source
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Select_RC32M_As_PLL_Ref(void)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_REFCLK_SEL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_XTAL_RC32M_SEL);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Select XTAL as PLL ref source
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Select_XTAL_As_PLL_Ref(void)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_REFCLK_SEL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_XTAL_RC32M_SEL);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Power on PLL
*
* @param xtalType: xtal type
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Power_On_PLL(PDS_PLL_XTAL_Type xtalType)
{
uint32_t tmpVal = 0;
/* Check parameter*/
CHECK_PARAM(IS_PDS_PLL_XTAL_TYPE(xtalType));
/**************************/
/* select PLL XTAL source */
/**************************/
if ((xtalType == PDS_PLL_XTAL_RC32M) || (xtalType == PDS_PLL_XTAL_NONE)) {
PDS_Trim_RC32M();
PDS_Select_RC32M_As_PLL_Ref();
} else {
PDS_Select_XTAL_As_PLL_Ref();
}
/*******************************************/
/* PLL power down first, not indispensable */
/*******************************************/
/* power off PLL first, this step is not indispensable */
PDS_Power_Off_PLL();
/********************/
/* PLL param config */
/********************/
/* clkpll_icp_1u */
/* clkpll_icp_5u */
/* clkpll_int_frac_sw */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_CP);
if (xtalType == PDS_PLL_XTAL_26M) {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_ICP_1U, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_ICP_5U, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_INT_FRAC_SW, 1);
} else {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_ICP_1U, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_ICP_5U, 2);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_INT_FRAC_SW, 0);
}
BL_WR_REG(PDS_BASE, PDS_CLKPLL_CP, tmpVal);
/* clkpll_c3 */
/* clkpll_cz */
/* clkpll_rz */
/* clkpll_r4 */
/* clkpll_r4_short */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_RZ);
if (xtalType == PDS_PLL_XTAL_26M) {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_C3, 2);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_CZ, 2);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_RZ, 5);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_R4_SHORT, 0);
} else {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_C3, 3);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_CZ, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_RZ, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_R4_SHORT, 1);
}
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_R4, 2);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_RZ, tmpVal);
/* clkpll_refdiv_ratio */
/* clkpll_postdiv */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_POSTDIV, 0x14);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_REFDIV_RATIO, 2);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_TOP_CTRL, tmpVal);
/* clkpll_sdmin */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_SDM);
switch (xtalType) {
case PDS_PLL_XTAL_NONE:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x3C0000);
break;
case PDS_PLL_XTAL_24M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x500000);
break;
case PDS_PLL_XTAL_32M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x3C0000);
break;
case PDS_PLL_XTAL_38P4M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x320000);
break;
case PDS_PLL_XTAL_40M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x300000);
break;
case PDS_PLL_XTAL_26M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x49D39D);
break;
case PDS_PLL_XTAL_RC32M:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x3C0000);
break;
default:
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x3C0000);
break;
}
BL_WR_REG(PDS_BASE, PDS_CLKPLL_SDM, tmpVal);
/* clkpll_sel_fb_clk */
/* clkpll_sel_sample_clk can be 0/1, default is 1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_FBDV);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SEL_FB_CLK, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SEL_SAMPLE_CLK, 1);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_FBDV, tmpVal);
/*************************/
/* PLL power up sequence */
/*************************/
/* pu_clkpll_sfreg=1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_PU_CLKPLL_SFREG);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
BL602_Delay_US(5);
/* pu_clkpll=1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_PU_CLKPLL);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
/* clkpll_pu_cp=1 */
/* clkpll_pu_pfd=1 */
/* clkpll_pu_fbdv=1 */
/* clkpll_pu_postdiv=1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_PU_CP);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_PU_PFD);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_PU_FBDV);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_PU_POSTDIV);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
BL602_Delay_US(5);
/* clkpll_sdm_reset=1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_SDM_RESET);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
BL602_Delay_US(1);
/* clkpll_reset_fbdv=1 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_SET_REG_BIT(tmpVal, PDS_CLKPLL_RESET_FBDV);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
BL602_Delay_US(2);
/* clkpll_reset_fbdv=0 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_RESET_FBDV);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
BL602_Delay_US(1);
/* clkpll_sdm_reset=0 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_SDM_RESET);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Fix XTAL26M Setting
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_CLOCK_SECTION PDS_Fix_Xtal_Settig(void)
{
uint32_t tmpVal;
/* Fix 26M xtal clkpll_sdmin */
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_SDM);
if (0x49D39D == BL_GET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN)) {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, PDS_CLKPLL_SDMIN, 0x49D89E);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_SDM, tmpVal);
}
return SUCCESS;
}
/** PLL output config **/
/*
[8] 1'h0 r/w clkpll_en_32m
[7] 1'h0 r/w clkpll_en_48m
[6] 1'h0 r/w clkpll_en_80m
[5] 1'h0 r/w clkpll_en_96m
[4] 1'h0 r/w clkpll_en_120m
[3] 1'h0 r/w clkpll_en_160m
[2] 1'h0 r/w clkpll_en_192m
[1] 1'h0 r/w clkpll_en_240m
[0] 1'h0 r/w clkpll_en_480m
*/
/****************************************************************************/ /**
* @brief Enable all PLL clock
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Enable_PLL_All_Clks(void)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN);
tmpVal |= 0x1FF;
BL_WR_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Disable all PLL clock
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Disable_PLL_All_Clks(void)
{
uint32_t tmpVal = 0;
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN);
tmpVal &= (~0x1FF);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Enable PLL clock
*
* @param pllClk: PLL clock type
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Enable_PLL_Clk(PDS_PLL_CLK_Type pllClk)
{
uint32_t tmpVal = 0;
/* Check parameter*/
CHECK_PARAM(IS_PDS_PLL_CLK_TYPE(pllClk));
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN);
tmpVal |= (1 << pllClk);
BL_WR_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Disable PLL clock
*
* @param pllClk: PLL clock type
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Disable_PLL_Clk(PDS_PLL_CLK_Type pllClk)
{
uint32_t tmpVal = 0;
/* Check parameter*/
CHECK_PARAM(IS_PDS_PLL_CLK_TYPE(pllClk));
tmpVal = BL_RD_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN);
tmpVal &= (~(1 << pllClk));
BL_WR_REG(PDS_BASE, PDS_CLKPLL_OUTPUT_EN, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Power off PLL
*
* @param None
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
#ifndef BFLB_USE_ROM_DRIVER
__WEAK
BL_Err_Type ATTR_CLOCK_SECTION PDS_Power_Off_PLL(void)
{
uint32_t tmpVal = 0;
/* pu_clkpll_sfreg=0 */
/* pu_clkpll=0 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_PU_CLKPLL_SFREG);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_PU_CLKPLL);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
/* clkpll_pu_cp=0 */
/* clkpll_pu_pfd=0 */
/* clkpll_pu_fbdv=0 */
/* clkpll_pu_postdiv=0 */
tmpVal = BL_RD_REG(PDS_BASE, PDS_PU_RST_CLKPLL);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_PU_CP);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_PU_PFD);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_PU_FBDV);
tmpVal = BL_CLR_REG_BIT(tmpVal, PDS_CLKPLL_PU_POSTDIV);
BL_WR_REG(PDS_BASE, PDS_PU_RST_CLKPLL, tmpVal);
return SUCCESS;
}
#endif
/****************************************************************************/ /**
* @brief Power down sleep wake up interrupt handler
*
* @param None
*
* @return None
*
*******************************************************************************/
#ifndef BFLB_USE_HAL_DRIVER
void PDS_WAKEUP_IRQHandler(void)
{
for (PDS_INT_Type intType = PDS_INT_WAKEUP; intType < PDS_INT_MAX; intType++) {
if (PDS_Get_IntStatus(intType) && (pdsIntCbfArra[intType][0] != NULL)) {
pdsIntCbfArra[intType][0]();
}
}
PDS_IntClear();
}
#endif
/*@} end of group PDS_Public_Functions */
/*@} end of group PDS */
/*@} end of group BL602_Peripheral_Driver */

View File

@@ -1,292 +0,0 @@
/**
******************************************************************************
* @file bl602_romdriver.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "bl602_romdriver.h"
#include "bl602_sflash_ext.h"
#include <string.h>
/** @addtogroup BL602_Periph_Driver
* @{
*/
/** @defgroup ROMDRIVER
* @brief ROMDRIVER common functions
* @{
*/
/** @defgroup ROMDRIVER_Private_Type
* @{
*/
/*@} end of group ROMDRIVER_Private_Type*/
/** @defgroup ROMDRIVER_Private_Defines
* @{
*/
/*@} end of group ROMDRIVER_Private_Defines */
/** @defgroup ROMDRIVER_Private_Variables
* @{
*/
/*@} end of group ROMDRIVER_Private_Variables */
/** @defgroup ROMDRIVER_Global_Variables
* @{
*/
uint32_t const romDriverTable[] = {
0x06020002,
0x00000000,
0x00000000,
0x00000000,
[ROM_API_INDEX_AON_Power_On_MBG] = (uint32_t)AON_Power_On_MBG,
[ROM_API_INDEX_AON_Power_Off_MBG] = (uint32_t)AON_Power_Off_MBG,
[ROM_API_INDEX_AON_Power_On_XTAL] = (uint32_t)AON_Power_On_XTAL,
[ROM_API_INDEX_AON_Set_Xtal_CapCode] = (uint32_t)AON_Set_Xtal_CapCode,
[ROM_API_INDEX_AON_Get_Xtal_CapCode] = (uint32_t)AON_Get_Xtal_CapCode,
[ROM_API_INDEX_AON_Power_Off_XTAL] = (uint32_t)AON_Power_Off_XTAL,
[ROM_API_INDEX_AON_Power_On_BG] = (uint32_t)AON_Power_On_BG,
[ROM_API_INDEX_AON_Power_Off_BG] = (uint32_t)AON_Power_Off_BG,
[ROM_API_INDEX_AON_Power_On_LDO11_SOC] = (uint32_t)AON_Power_On_LDO11_SOC,
[ROM_API_INDEX_AON_Power_Off_LDO11_SOC] = (uint32_t)AON_Power_Off_LDO11_SOC,
[ROM_API_INDEX_AON_Power_On_LDO15_RF] = (uint32_t)AON_Power_On_LDO15_RF,
[ROM_API_INDEX_AON_Power_Off_LDO15_RF] = (uint32_t)AON_Power_Off_LDO15_RF,
[ROM_API_INDEX_AON_Power_On_SFReg] = (uint32_t)AON_Power_On_SFReg,
[ROM_API_INDEX_AON_Power_Off_SFReg] = (uint32_t)AON_Power_Off_SFReg,
[ROM_API_INDEX_AON_LowPower_Enter_PDS0] = (uint32_t)AON_LowPower_Enter_PDS0,
[ROM_API_INDEX_AON_LowPower_Exit_PDS0] = (uint32_t)AON_LowPower_Exit_PDS0,
[ROM_API_INDEX_ASM_Delay_Us] = (uint32_t)ASM_Delay_Us,
[ROM_API_INDEX_BL602_Delay_US] = (uint32_t)BL602_Delay_US,
[ROM_API_INDEX_BL602_Delay_MS] = (uint32_t)BL602_Delay_MS,
[ROM_API_INDEX_BL602_MemCpy] = (uint32_t)BL602_MemCpy,
[ROM_API_INDEX_BL602_MemCpy4] = (uint32_t)BL602_MemCpy4,
[ROM_API_INDEX_BL602_MemCpy_Fast] = (uint32_t)BL602_MemCpy_Fast,
[ROM_API_INDEX_BL602_MemSet] = (uint32_t)BL602_MemSet,
[ROM_API_INDEX_BL602_MemSet4] = (uint32_t)BL602_MemSet4,
[ROM_API_INDEX_BL602_MemCmp] = (uint32_t)BL602_MemCmp,
[ROM_API_INDEX_EF_Ctrl_Sw_AHB_Clk_0] = (uint32_t)EF_Ctrl_Sw_AHB_Clk_0,
[ROM_API_INDEX_EF_Ctrl_Program_Efuse_0] = (uint32_t)EF_Ctrl_Program_Efuse_0,
[ROM_API_INDEX_EF_Ctrl_Load_Efuse_R0] = (uint32_t)EF_Ctrl_Load_Efuse_R0,
[ROM_API_INDEX_EF_Ctrl_Busy] = (uint32_t)EF_Ctrl_Busy,
[ROM_API_INDEX_EF_Ctrl_AutoLoad_Done] = (uint32_t)EF_Ctrl_AutoLoad_Done,
[ROM_API_INDEX_EF_Ctrl_Get_Trim_Parity] = (uint32_t)EF_Ctrl_Get_Trim_Parity,
[ROM_API_INDEX_EF_Ctrl_Read_RC32M_Trim] = (uint32_t)EF_Ctrl_Read_RC32M_Trim,
[ROM_API_INDEX_EF_Ctrl_Read_RC32K_Trim] = (uint32_t)EF_Ctrl_Read_RC32K_Trim,
[ROM_API_INDEX_EF_Ctrl_Clear] = (uint32_t)EF_Ctrl_Clear,
[ROM_API_INDEX_GLB_Get_Root_CLK_Sel] = (uint32_t)GLB_Get_Root_CLK_Sel,
[ROM_API_INDEX_GLB_Set_System_CLK_Div] = (uint32_t)GLB_Set_System_CLK_Div,
[ROM_API_INDEX_GLB_Get_BCLK_Div] = (uint32_t)GLB_Get_BCLK_Div,
[ROM_API_INDEX_GLB_Get_HCLK_Div] = (uint32_t)GLB_Get_HCLK_Div,
[ROM_API_INDEX_Update_SystemCoreClockWith_XTAL] = (uint32_t)Update_SystemCoreClockWith_XTAL,
[ROM_API_INDEX_GLB_Set_System_CLK] = (uint32_t)GLB_Set_System_CLK,
[ROM_API_INDEX_System_Core_Clock_Update_From_RC32M] = (uint32_t)System_Core_Clock_Update_From_RC32M,
[ROM_API_INDEX_GLB_Set_SF_CLK] = (uint32_t)GLB_Set_SF_CLK,
[ROM_API_INDEX_GLB_Set_PKA_CLK_Sel] = (uint32_t)GLB_Set_PKA_CLK_Sel,
[ROM_API_INDEX_GLB_SW_System_Reset] = (uint32_t)GLB_SW_System_Reset,
[ROM_API_INDEX_GLB_SW_CPU_Reset] = (uint32_t)GLB_SW_CPU_Reset,
[ROM_API_INDEX_GLB_SW_POR_Reset] = (uint32_t)GLB_SW_POR_Reset,
[ROM_API_INDEX_GLB_Select_Internal_Flash] = (uint32_t)GLB_Select_Internal_Flash,
[ROM_API_INDEX_GLB_Select_External_Flash] = (uint32_t)GLB_Select_External_Flash,
[ROM_API_INDEX_GLB_Deswap_Flash_Pin] = (uint32_t)GLB_Deswap_Flash_Pin,
[ROM_API_INDEX_GLB_Swap_Flash_Pin] = (uint32_t)GLB_Swap_Flash_Pin,
[ROM_API_INDEX_GLB_GPIO_Init] = (uint32_t)GLB_GPIO_Init,
[ROM_API_INDEX_GLB_GPIO_OUTPUT_Enable] = (uint32_t)GLB_GPIO_OUTPUT_Enable,
[ROM_API_INDEX_GLB_GPIO_OUTPUT_Disable] = (uint32_t)GLB_GPIO_OUTPUT_Disable,
[ROM_API_INDEX_GLB_GPIO_Set_HZ] = (uint32_t)GLB_GPIO_Set_HZ,
[ROM_API_INDEX_GLB_GPIO_Get_Fun] = (uint32_t)GLB_GPIO_Get_Fun,
[ROM_API_INDEX_HBN_Mode_Enter] = (uint32_t)HBN_Mode_Enter,
[ROM_API_INDEX_HBN_Power_Down_Flash] = (uint32_t)HBN_Power_Down_Flash,
[ROM_API_INDEX_HBN_Enable] = (uint32_t)HBN_Enable,
[ROM_API_INDEX_HBN_Reset] = (uint32_t)HBN_Reset,
[ROM_API_INDEX_HBN_Set_Ldo11_Aon_Vout] = (uint32_t)HBN_Set_Ldo11_Aon_Vout,
[ROM_API_INDEX_HBN_Set_Ldo11_Rt_Vout] = (uint32_t)HBN_Set_Ldo11_Rt_Vout,
[ROM_API_INDEX_HBN_Set_Ldo11_Soc_Vout] = (uint32_t)HBN_Set_Ldo11_Soc_Vout,
[ROM_API_INDEX_HBN_32K_Sel] = (uint32_t)HBN_32K_Sel,
[ROM_API_INDEX_HBN_Set_ROOT_CLK_Sel] = (uint32_t)HBN_Set_ROOT_CLK_Sel,
[ROM_API_INDEX_HBN_Power_On_Xtal_32K] = (uint32_t)HBN_Power_On_Xtal_32K,
[ROM_API_INDEX_HBN_Power_Off_Xtal_32K] = (uint32_t)HBN_Power_Off_Xtal_32K,
[ROM_API_INDEX_HBN_Power_On_RC32K] = (uint32_t)HBN_Power_On_RC32K,
[ROM_API_INDEX_HBN_Power_Off_RC32K] = (uint32_t)HBN_Power_Off_RC32K,
[ROM_API_INDEX_HBN_Trim_RC32K] = (uint32_t)HBN_Trim_RC32K,
[ROM_API_INDEX_HBN_Hw_Pu_Pd_Cfg] = (uint32_t)HBN_Hw_Pu_Pd_Cfg,
[ROM_API_INDEX_HBN_Pin_WakeUp_Mask] = (uint32_t)HBN_Pin_WakeUp_Mask,
[ROM_API_INDEX_HBN_GPIO7_Dbg_Pull_Cfg] = (uint32_t)HBN_GPIO7_Dbg_Pull_Cfg,
[ROM_API_INDEX_HBN_Set_Embedded_Flash_Pullup] = (uint32_t)HBN_Set_Embedded_Flash_Pullup,
[ROM_API_INDEX_L1C_Set_Wrap] = (uint32_t)L1C_Set_Wrap,
[ROM_API_INDEX_L1C_Set_Way_Disable] = (uint32_t)L1C_Set_Way_Disable,
[ROM_API_INDEX_L1C_IROM_2T_Access_Set] = (uint32_t)L1C_IROM_2T_Access_Set,
[ROM_API_INDEX_PDS_Reset] = (uint32_t)PDS_Reset,
[ROM_API_INDEX_PDS_Enable] = (uint32_t)PDS_Enable,
[ROM_API_INDEX_PDS_Force_Config] = (uint32_t)PDS_Force_Config,
[ROM_API_INDEX_PDS_RAM_Config] = (uint32_t)PDS_RAM_Config,
[ROM_API_INDEX_PDS_Default_Level_Config] = (uint32_t)PDS_Default_Level_Config,
[ROM_API_INDEX_PDS_Trim_RC32M] = (uint32_t)PDS_Trim_RC32M,
[ROM_API_INDEX_PDS_Select_RC32M_As_PLL_Ref] = (uint32_t)PDS_Select_RC32M_As_PLL_Ref,
[ROM_API_INDEX_PDS_Select_XTAL_As_PLL_Ref] = (uint32_t)PDS_Select_XTAL_As_PLL_Ref,
[ROM_API_INDEX_PDS_Power_On_PLL] = (uint32_t)PDS_Power_On_PLL,
[ROM_API_INDEX_PDS_Enable_PLL_All_Clks] = (uint32_t)PDS_Enable_PLL_All_Clks,
[ROM_API_INDEX_PDS_Disable_PLL_All_Clks] = (uint32_t)PDS_Disable_PLL_All_Clks,
[ROM_API_INDEX_PDS_Enable_PLL_Clk] = (uint32_t)PDS_Enable_PLL_Clk,
[ROM_API_INDEX_PDS_Disable_PLL_Clk] = (uint32_t)PDS_Disable_PLL_Clk,
[ROM_API_INDEX_PDS_Power_Off_PLL] = (uint32_t)PDS_Power_Off_PLL,
[ROM_API_INDEX_SEC_Eng_Turn_On_Sec_Ring] = (uint32_t)SEC_Eng_Turn_On_Sec_Ring,
[ROM_API_INDEX_SEC_Eng_Turn_Off_Sec_Ring] = (uint32_t)SEC_Eng_Turn_Off_Sec_Ring,
[ROM_API_INDEX_SFlash_Init] = (uint32_t)SFlash_Init,
[ROM_API_INDEX_SFlash_SetSPIMode] = (uint32_t)SFlash_SetSPIMode,
[ROM_API_INDEX_SFlash_Read_Reg] = (uint32_t)SFlash_Read_Reg,
[ROM_API_INDEX_SFlash_Write_Reg] = (uint32_t)SFlash_Write_Reg,
[ROM_API_INDEX_SFlash_Busy] = (uint32_t)SFlash_Busy,
[ROM_API_INDEX_SFlash_Write_Enable] = (uint32_t)SFlash_Write_Enable,
[ROM_API_INDEX_SFlash_Qspi_Enable] = (uint32_t)SFlash_Qspi_Enable,
[ROM_API_INDEX_SFlash_Volatile_Reg_Write_Enable] = (uint32_t)SFlash_Volatile_Reg_Write_Enable,
[ROM_API_INDEX_SFlash_Chip_Erase] = (uint32_t)SFlash_Chip_Erase,
[ROM_API_INDEX_SFlash_Sector_Erase] = (uint32_t)SFlash_Sector_Erase,
[ROM_API_INDEX_SFlash_Blk32_Erase] = (uint32_t)SFlash_Blk32_Erase,
[ROM_API_INDEX_SFlash_Blk64_Erase] = (uint32_t)SFlash_Blk64_Erase,
[ROM_API_INDEX_SFlash_Erase] = (uint32_t)SFlash_Erase,
[ROM_API_INDEX_SFlash_Program] = (uint32_t)SFlash_Program,
[ROM_API_INDEX_SFlash_GetUniqueId] = (uint32_t)SFlash_GetUniqueId,
[ROM_API_INDEX_SFlash_GetJedecId] = (uint32_t)SFlash_GetJedecId,
[ROM_API_INDEX_SFlash_GetDeviceId] = (uint32_t)SFlash_GetDeviceId,
[ROM_API_INDEX_SFlash_Powerdown] = (uint32_t)SFlash_Powerdown,
[ROM_API_INDEX_SFlash_Releae_Powerdown] = (uint32_t)SFlash_Releae_Powerdown,
[ROM_API_INDEX_SFlash_SetBurstWrap] = (uint32_t)SFlash_SetBurstWrap,
[ROM_API_INDEX_SFlash_DisableBurstWrap] = (uint32_t)SFlash_DisableBurstWrap,
[ROM_API_INDEX_SFlash_Software_Reset] = (uint32_t)SFlash_Software_Reset,
[ROM_API_INDEX_SFlash_Reset_Continue_Read] = (uint32_t)SFlash_Reset_Continue_Read,
[ROM_API_INDEX_SFlash_Set_IDbus_Cfg] = (uint32_t)SFlash_Set_IDbus_Cfg,
[ROM_API_INDEX_SFlash_IDbus_Read_Enable] = (uint32_t)SFlash_IDbus_Read_Enable,
[ROM_API_INDEX_SFlash_Cache_Enable_Set] = (uint32_t)SFlash_Cache_Enable_Set,
[ROM_API_INDEX_SFlash_Cache_Flush] = (uint32_t)SFlash_Cache_Flush,
[ROM_API_INDEX_SFlash_Cache_Read_Enable] = (uint32_t)SFlash_Cache_Read_Enable,
[ROM_API_INDEX_SFlash_Cache_Hit_Count_Get] = (uint32_t)SFlash_Cache_Hit_Count_Get,
[ROM_API_INDEX_SFlash_Cache_Miss_Count_Get] = (uint32_t)SFlash_Cache_Miss_Count_Get,
[ROM_API_INDEX_SFlash_Cache_Read_Disable] = (uint32_t)SFlash_Cache_Read_Disable,
[ROM_API_INDEX_SFlash_Read] = (uint32_t)SFlash_Read,
[ROM_API_INDEX_SFlash_Read_Reg_With_Cmd] = (uint32_t)SFlash_Read_Reg_With_Cmd,
[ROM_API_INDEX_SFlash_Write_Reg_With_Cmd] = (uint32_t)SFlash_Write_Reg_With_Cmd,
[ROM_API_INDEX_SFlash_Restore_From_Powerdown] = (uint32_t)SFlash_Restore_From_Powerdown,
[ROM_API_INDEX_SF_Cfg_Init_Ext_Flash_Gpio] = (uint32_t)SF_Cfg_Init_Ext_Flash_Gpio,
[ROM_API_INDEX_SF_Cfg_Init_Internal_Flash_Gpio] = (uint32_t)SF_Cfg_Init_Internal_Flash_Gpio,
[ROM_API_INDEX_SF_Cfg_Deinit_Ext_Flash_Gpio] = (uint32_t)SF_Cfg_Deinit_Ext_Flash_Gpio,
[ROM_API_INDEX_SF_Cfg_Restore_GPIO17_Fun] = (uint32_t)SF_Cfg_Restore_GPIO17_Fun,
[ROM_API_INDEX_SF_Cfg_Get_Flash_Cfg_Need_Lock] = (uint32_t)SF_Cfg_Get_Flash_Cfg_Need_Lock,
[ROM_API_INDEX_SF_Cfg_Init_Flash_Gpio] = (uint32_t)SF_Cfg_Init_Flash_Gpio,
[ROM_API_INDEX_SF_Cfg_Flash_Identify] = (uint32_t)SF_Cfg_Flash_Identify,
[ROM_API_INDEX_SF_Ctrl_Enable] = (uint32_t)SF_Ctrl_Enable,
[ROM_API_INDEX_SF_Ctrl_Select_Pad] = (uint32_t)SF_Ctrl_Select_Pad,
[ROM_API_INDEX_SF_Ctrl_Set_Owner] = (uint32_t)SF_Ctrl_Set_Owner,
[ROM_API_INDEX_SF_Ctrl_Disable] = (uint32_t)SF_Ctrl_Disable,
[ROM_API_INDEX_SF_Ctrl_AES_Enable_BE] = (uint32_t)SF_Ctrl_AES_Enable_BE,
[ROM_API_INDEX_SF_Ctrl_AES_Enable_LE] = (uint32_t)SF_Ctrl_AES_Enable_LE,
[ROM_API_INDEX_SF_Ctrl_AES_Set_Region] = (uint32_t)SF_Ctrl_AES_Set_Region,
[ROM_API_INDEX_SF_Ctrl_AES_Set_Key] = (uint32_t)SF_Ctrl_AES_Set_Key,
[ROM_API_INDEX_SF_Ctrl_AES_Set_Key_BE] = (uint32_t)SF_Ctrl_AES_Set_Key_BE,
[ROM_API_INDEX_SF_Ctrl_AES_Set_IV] = (uint32_t)SF_Ctrl_AES_Set_IV,
[ROM_API_INDEX_SF_Ctrl_AES_Set_IV_BE] = (uint32_t)SF_Ctrl_AES_Set_IV_BE,
[ROM_API_INDEX_SF_Ctrl_AES_Enable] = (uint32_t)SF_Ctrl_AES_Enable,
[ROM_API_INDEX_SF_Ctrl_AES_Disable] = (uint32_t)SF_Ctrl_AES_Disable,
[ROM_API_INDEX_SF_Ctrl_Set_Flash_Image_Offset] = (uint32_t)SF_Ctrl_Set_Flash_Image_Offset,
[ROM_API_INDEX_SF_Ctrl_Get_Flash_Image_Offset] = (uint32_t)SF_Ctrl_Get_Flash_Image_Offset,
[ROM_API_INDEX_SF_Ctrl_Select_Clock] = (uint32_t)SF_Ctrl_Select_Clock,
[ROM_API_INDEX_SF_Ctrl_SendCmd] = (uint32_t)SF_Ctrl_SendCmd,
[ROM_API_INDEX_SF_Ctrl_Icache_Set] = (uint32_t)SF_Ctrl_Icache_Set,
[ROM_API_INDEX_SF_Ctrl_Icache2_Set] = (uint32_t)SF_Ctrl_Icache2_Set,
[ROM_API_INDEX_SF_Ctrl_GetBusyState] = (uint32_t)SF_Ctrl_GetBusyState,
[ROM_API_INDEX_SF_Ctrl_Is_AES_Enable] = (uint32_t)SF_Ctrl_Is_AES_Enable,
[ROM_API_INDEX_SF_Ctrl_Get_Clock_Delay] = (uint32_t)SF_Ctrl_Get_Clock_Delay,
[ROM_API_INDEX_SF_Ctrl_Set_Clock_Delay] = (uint32_t)SF_Ctrl_Set_Clock_Delay,
[ROM_API_INDEX_XIP_SFlash_State_Save] = (uint32_t)XIP_SFlash_State_Save,
[ROM_API_INDEX_XIP_SFlash_State_Restore] = (uint32_t)XIP_SFlash_State_Restore,
[ROM_API_INDEX_XIP_SFlash_Erase_Need_Lock] = (uint32_t)XIP_SFlash_Erase_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_Write_Need_Lock] = (uint32_t)XIP_SFlash_Write_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_Read_Need_Lock] = (uint32_t)XIP_SFlash_Read_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_GetJedecId_Need_Lock] = (uint32_t)XIP_SFlash_GetJedecId_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_GetDeviceId_Need_Lock] = (uint32_t)XIP_SFlash_GetDeviceId_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_GetUniqueId_Need_Lock] = (uint32_t)XIP_SFlash_GetUniqueId_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_Read_Via_Cache_Need_Lock] = (uint32_t)XIP_SFlash_Read_Via_Cache_Need_Lock,
[ROM_API_INDEX_XIP_SFlash_Read_With_Lock] = (uint32_t)XIP_SFlash_Read_With_Lock,
[ROM_API_INDEX_XIP_SFlash_Write_With_Lock] = (uint32_t)XIP_SFlash_Write_With_Lock,
[ROM_API_INDEX_XIP_SFlash_Erase_With_Lock] = (uint32_t)XIP_SFlash_Erase_With_Lock,
[ROM_API_INDEX_XIP_SFlash_Opt_Enter] = (uint32_t)XIP_SFlash_Opt_Enter,
[ROM_API_INDEX_XIP_SFlash_Opt_Exit] = (uint32_t)XIP_SFlash_Opt_Exit,
[ROM_API_INDEX_BFLB_Soft_CRC32] = (uint32_t)BFLB_Soft_CRC32,
[ROM_API_INDEX_FUNC_EMPTY_START... ROM_API_INDEX_FUNC_EMPTY_END] = 0xdeedbeef,
};
/*@} end of group ROMDRIVER_Global_Variables */
/** @defgroup ROMDRIVER_Private_FunctionDeclaration
* @{
*/
/*@} end of group ROMDRIVER_Private_FunctionDeclaration */
/** @defgroup ROMDRIVER_Private_Functions
* @{
*/
/*@} end of group ROMDRIVER_Private_Functions */
/** @defgroup ROMDRIVER_Public_Functions
* @{
*/
/*@} end of group ROMDRIVER_Public_Functions */
/*@} end of group ROMDRIVER_COMMON */
/*@} end of group BL602_Periph_Driver */

View File

@@ -1,74 +0,0 @@
#include "bl602_sdu.h"
volatile pHidSdio_RegMap_t SdioFuncReg[] = {
(pHidSdio_RegMap_t)(BL_SDIO_CCR_BASE),
#if NUM_FUNC == 2
(pHidSdio_RegMap_t)(BL_SDIO_CCR_BASE + BL_SDIO_CCR_FUNC_OFFSET)
#elif NUM_FUNC == 3
(pHidSdio_RegMap_t)(BL_SDIO_CCR_BASE + BL_SDIO_CCR_FUNC_OFFSET),
(pHidSdio_RegMap_t)(BL_SDIO_CCR_BASE + (2 * BL_SDIO_CCR_FUNC_OFFSET))
#endif
};
/* if flag_mport = 0, then it supports mport
* flag_mport = 1, then mport disabled
*/
uint8_t flag_mport[NUM_FUNC] = {
0,
#if NUM_FUNC == 2
1
#elif NUM_FUNC == 3
1, 1
#endif
};
void sdio_GEN_CARD2HOST_INT(uint32_t port_id, uint16_t value)
{
/* We do not want to generate Download rdy for command port
* only. Currently there is a condition where if we generate
* download ready for command, followed by a download
* ready for data, the download ready for data would be gated
* by the SDIO controller. To avoid this we do not generate
* a download ready for command. Download ready is only generated for data.
*/
/*
if (!flag_mport[port_id] &&
(value & SDIO_CCR_CS_DnLdRdy) && (prev_WrBitMap[port_id] == 0x01))
{
value &= ~SDIO_CCR_CS_DnLdRdy;
if (!value)
{
return;
}
}
*/
SdioFuncReg[port_id]->CardToHostEvent = value;
}
uint32_t sdio_ioctl(uint32_t port_id, SDIO_CMD_TYPE cmd, void *arg)
{
switch (cmd) {
case IOCTL_HID_GET_BLOCK_SIZE: {
if (port_id == FUNC_WIFI) {
uint32_t blockSize = BL_REGS8(SDIO_FN1_BLK_SIZE_0);
blockSize |= ((BL_REGS8(SDIO_FN1_BLK_SIZE_1) &
SDIO_FN1_BLK_SIZE_1_MASK)
<< 8);
if (blockSize == 0) {
blockSize = 512;
}
return (blockSize);
}
break;
}
default:
break;
}
return 0;
}

View File

@@ -1,789 +0,0 @@
/**
******************************************************************************
* @file bl602_sf_cfg_ext.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "bl602_glb.h"
#include "bl602_sf_cfg.h"
#include "bl602_sf_cfg_ext.h"
#include "bl602_xip_sflash.h"
#include "bl602_romdriver.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup SF_CFG_EXT
* @{
*/
/** @defgroup SF_CFG_EXT_Private_Macros
* @{
*/
#define BFLB_FLASH_CFG_MAGIC "FCFG"
/*@} end of group SF_CFG_EXT_Private_Macros */
/** @defgroup SF_CFG_EXT_Private_Types
* @{
*/
typedef struct {
uint32_t jedecID;
char *name;
const SPI_Flash_Cfg_Type *cfg;
}Flash_Info_t;
/*@} end of group SF_CFG_EXT_Private_Types */
/** @defgroup SF_CFG_EXT_Private_Variables
* @{
*/
static const ATTR_TCM_CONST_SECTION SPI_Flash_Cfg_Type flashCfg_FM_25Q08={
.resetCreadCmd=0xff,
.resetCreadCmdSize=3,
.mid=0xc8,
.deBurstWrapCmd=0x77,
.deBurstWrapCmdDmyClk=0x3,
.deBurstWrapDataMode=SF_CTRL_DATA_4_LINES,
.deBurstWrapData=0xF0,
/*reg*/
.writeEnableCmd=0x06,
.wrEnableIndex=0x00,
.wrEnableBit=0x01,
.wrEnableReadRegLen=0x01,
.qeIndex=1,
.qeBit=0x01,
.qeWriteRegLen=0x02,
.qeReadRegLen=0x1,
.busyIndex=0,
.busyBit=0x00,
.busyReadRegLen=0x1,
.releasePowerDown=0xab,
.readRegCmd[0]=0x05,
.readRegCmd[1]=0x35,
.writeRegCmd[0]=0x01,
.writeRegCmd[1]=0x01,
.fastReadQioCmd=0xeb,
.frQioDmyClk=16/8,
.cReadSupport=1,
.cReadMode=0xa0,
.burstWrapCmd=0x77,
.burstWrapCmdDmyClk=0x3,
.burstWrapDataMode=SF_CTRL_DATA_4_LINES,
.burstWrapData=0x40,
/*erase*/
.chipEraseCmd=0xc7,
.sectorEraseCmd=0x20,
.blk32EraseCmd=0x52,
.blk64EraseCmd=0xd8,
/*write*/
.pageProgramCmd=0x02,
.qpageProgramCmd=0x32,
.qppAddrMode=SF_CTRL_ADDR_1_LINE,
.ioMode=SF_CTRL_QIO_MODE,
.clkDelay=1,
.clkInvert=0x01,
.resetEnCmd=0x66,
.resetCmd=0x99,
.cRExit=0xff,
.wrEnableWriteRegLen=0x00,
/*id*/
.jedecIdCmd=0x9f,
.jedecIdCmdDmyClk=0,
.qpiJedecIdCmd=0x9f,
.qpiJedecIdCmdDmyClk=0x00,
.sectorSize=4,
.pageSize=256,
/*read*/
.fastReadCmd=0x0b,
.frDmyClk=8/8,
.qpiFastReadCmd =0x0b,
.qpiFrDmyClk=8/8,
.fastReadDoCmd=0x3b,
.frDoDmyClk=8/8,
.fastReadDioCmd=0xbb,
.frDioDmyClk=0,
.fastReadQoCmd=0x6b,
.frQoDmyClk=8/8,
.qpiFastReadQioCmd=0xeb,
.qpiFrQioDmyClk=16/8,
.qpiPageProgramCmd=0x02,
.writeVregEnableCmd=0x50,
/* qpi mode */
.enterQpi=0x38,
.exitQpi=0xff,
/*AC*/
.timeEsector=300,
.timeE32k=1200,
.timeE64k=1200,
.timePagePgm=5,
.timeCe=33000,
.pdDelay=20,
.qeData=0,
};
static const ATTR_TCM_CONST_SECTION SPI_Flash_Cfg_Type flashCfg_Gd_Md_40D={
.resetCreadCmd=0xff,
.resetCreadCmdSize=3,
.mid=0x51,
.deBurstWrapCmd=0x77,
.deBurstWrapCmdDmyClk=0x3,
.deBurstWrapDataMode=SF_CTRL_DATA_4_LINES,
.deBurstWrapData=0xF0,
/*reg*/
.writeEnableCmd=0x06,
.wrEnableIndex=0x00,
.wrEnableBit=0x01,
.wrEnableReadRegLen=0x01,
.qeIndex=1,
.qeBit=0x01,
.qeWriteRegLen=0x02,
.qeReadRegLen=0x1,
.busyIndex=0,
.busyBit=0x00,
.busyReadRegLen=0x1,
.releasePowerDown=0xab,
.readRegCmd[0]=0x05,
.readRegCmd[1]=0x35,
.writeRegCmd[0]=0x01,
.writeRegCmd[1]=0x01,
.fastReadQioCmd=0xeb,
.frQioDmyClk=16/8,
.cReadSupport=0,
.cReadMode=0xA0,
.burstWrapCmd=0x77,
.burstWrapCmdDmyClk=0x3,
.burstWrapDataMode=SF_CTRL_DATA_4_LINES,
.burstWrapData=0x40,
/*erase*/
.chipEraseCmd=0xc7,
.sectorEraseCmd=0x20,
.blk32EraseCmd=0x52,
.blk64EraseCmd=0xd8,
/*write*/
.pageProgramCmd=0x02,
.qpageProgramCmd=0x32,
.qppAddrMode=SF_CTRL_ADDR_1_LINE,
.ioMode=0x11,
.clkDelay=1,
.clkInvert=0x01,
.resetEnCmd=0x66,
.resetCmd=0x99,
.cRExit=0xff,
.wrEnableWriteRegLen=0x00,
/*id*/
.jedecIdCmd=0x9f,
.jedecIdCmdDmyClk=0,
.qpiJedecIdCmd=0x9f,
.qpiJedecIdCmdDmyClk=0x00,
.sectorSize=4,
.pageSize=256,
/*read*/
.fastReadCmd=0x0b,
.frDmyClk=8/8,
.qpiFastReadCmd =0x0b,
.qpiFrDmyClk=8/8,
.fastReadDoCmd=0x3b,
.frDoDmyClk=8/8,
.fastReadDioCmd=0xbb,
.frDioDmyClk=0,
.fastReadQoCmd=0x6b,
.frQoDmyClk=8/8,
.qpiFastReadQioCmd=0xeb,
.qpiFrQioDmyClk=16/8,
.qpiPageProgramCmd=0x02,
.writeVregEnableCmd=0x50,
/* qpi mode */
.enterQpi=0x38,
.exitQpi=0xff,
/*AC*/
.timeEsector=300,
.timeE32k=1200,
.timeE64k=1200,
.timePagePgm=5,
.timeCe=33000,
.pdDelay=20,
.qeData=0,
};
static const ATTR_TCM_CONST_SECTION SPI_Flash_Cfg_Type flashCfg_XM25QH16={
.resetCreadCmd=0xff,
.resetCreadCmdSize=3,
.mid=0x20,
.deBurstWrapCmd=0x77,
.deBurstWrapCmdDmyClk=0x3,
.deBurstWrapDataMode=SF_CTRL_DATA_4_LINES,
.deBurstWrapData=0xF0,
/*reg*/
.writeEnableCmd=0x06,
.wrEnableIndex=0x00,
.wrEnableBit=0x01,
.wrEnableReadRegLen=0x01,
.qeIndex=1,
.qeBit=0x01,
.qeWriteRegLen=0x01,
.qeReadRegLen=0x1,
.busyIndex=0,
.busyBit=0x00,
.busyReadRegLen=0x1,
.releasePowerDown=0xab,
.readRegCmd[0]=0x05,
.readRegCmd[1]=0x35,
.writeRegCmd[0]=0x01,
.writeRegCmd[1]=0x31,
.fastReadQioCmd=0xeb,
.frQioDmyClk=16/8,
.cReadSupport=1,
.cReadMode=0x20,
.burstWrapCmd=0x77,
.burstWrapCmdDmyClk=0x3,
.burstWrapDataMode=SF_CTRL_DATA_4_LINES,
.burstWrapData=0x40,
/*erase*/
.chipEraseCmd=0xc7,
.sectorEraseCmd=0x20,
.blk32EraseCmd=0x52,
.blk64EraseCmd=0xd8,
/*write*/
.pageProgramCmd=0x02,
.qpageProgramCmd=0x32,
.qppAddrMode=SF_CTRL_ADDR_1_LINE,
.ioMode=SF_CTRL_QIO_MODE,
.clkDelay=1,
.clkInvert=0x01,
.resetEnCmd=0x66,
.resetCmd=0x99,
.cRExit=0xff,
.wrEnableWriteRegLen=0x00,
/*id*/
.jedecIdCmd=0x9f,
.jedecIdCmdDmyClk=0,
.qpiJedecIdCmd=0x9f,
.qpiJedecIdCmdDmyClk=0x00,
.sectorSize=4,
.pageSize=256,
/*read*/
.fastReadCmd=0x0b,
.frDmyClk=8/8,
.qpiFastReadCmd =0x0b,
.qpiFrDmyClk=8/8,
.fastReadDoCmd=0x3b,
.frDoDmyClk=8/8,
.fastReadDioCmd=0xbb,
.frDioDmyClk=0,
.fastReadQoCmd=0x6b,
.frQoDmyClk=8/8,
.qpiFastReadQioCmd=0xeb,
.qpiFrQioDmyClk=16/8,
.qpiPageProgramCmd=0x02,
.writeVregEnableCmd=0x50,
/* qpi mode */
.enterQpi=0x38,
.exitQpi=0xff,
/*AC*/
.timeEsector=400,
.timeE32k=1600,
.timeE64k=2000,
.timePagePgm=5,
.timeCe=33000,
.pdDelay=3,
.qeData=0,
};
static const ATTR_TCM_CONST_SECTION SPI_Flash_Cfg_Type flashCfg_MX_KH25={
.resetCreadCmd=0xff,
.resetCreadCmdSize=3,
.mid=0xc2,
.deBurstWrapCmd=0x77,
.deBurstWrapCmdDmyClk=0x3,
.deBurstWrapDataMode=SF_CTRL_DATA_4_LINES,
.deBurstWrapData=0xF0,
/*reg*/
.writeEnableCmd=0x06,
.wrEnableIndex=0x00,
.wrEnableBit=0x01,
.wrEnableReadRegLen=0x01,
.qeIndex=1,
.qeBit=0x01,
.qeWriteRegLen=0x01,
.qeReadRegLen=0x1,
.busyIndex=0,
.busyBit=0x00,
.busyReadRegLen=0x1,
.releasePowerDown=0xab,
.readRegCmd[0]=0x05,
.readRegCmd[1]=0x00,
.writeRegCmd[0]=0x01,
.writeRegCmd[1]=0x00,
.fastReadQioCmd=0xeb,
.frQioDmyClk=16/8,
.cReadSupport=0,
.cReadMode=0x20,
.burstWrapCmd=0x77,
.burstWrapCmdDmyClk=0x3,
.burstWrapDataMode=SF_CTRL_DATA_4_LINES,
.burstWrapData=0x40,
/*erase*/
.chipEraseCmd=0xc7,
.sectorEraseCmd=0x20,
.blk32EraseCmd=0x52,
.blk64EraseCmd=0xd8,
/*write*/
.pageProgramCmd=0x02,
.qpageProgramCmd=0x32,
.qppAddrMode=SF_CTRL_ADDR_1_LINE,
.ioMode=0x11,
.clkDelay=1,
.clkInvert=0x01,
.resetEnCmd=0x66,
.resetCmd=0x99,
.cRExit=0xff,
.wrEnableWriteRegLen=0x00,
/*id*/
.jedecIdCmd=0x9f,
.jedecIdCmdDmyClk=0,
.qpiJedecIdCmd=0x9f,
.qpiJedecIdCmdDmyClk=0x00,
.sectorSize=4,
.pageSize=256,
/*read*/
.fastReadCmd=0x0b,
.frDmyClk=8/8,
.qpiFastReadCmd =0x0b,
.qpiFrDmyClk=8/8,
.fastReadDoCmd=0x3b,
.frDoDmyClk=8/8,
.fastReadDioCmd=0xbb,
.frDioDmyClk=0,
.fastReadQoCmd=0x6b,
.frQoDmyClk=8/8,
.qpiFastReadQioCmd=0xeb,
.qpiFrQioDmyClk=16/8,
.qpiPageProgramCmd=0x02,
.writeVregEnableCmd=0x50,
/* qpi mode */
.enterQpi=0x38,
.exitQpi=0xff,
/*AC*/
.timeEsector=300,
.timeE32k=1200,
.timeE64k=1200,
.timePagePgm=5,
.timeCe=33000,
.pdDelay=20,
.qeData=0,
};
static const ATTR_TCM_CONST_SECTION SPI_Flash_Cfg_Type flashCfg_ZD_25Q16B={
.resetCreadCmd=0xff,
.resetCreadCmdSize=3,
.mid=0xba,
.deBurstWrapCmd=0x77,
.deBurstWrapCmdDmyClk=0x3,
.deBurstWrapDataMode=SF_CTRL_DATA_4_LINES,
.deBurstWrapData=0xF0,
/*reg*/
.writeEnableCmd=0x06,
.wrEnableIndex=0x00,
.wrEnableBit=0x01,
.wrEnableReadRegLen=0x01,
.qeIndex=1,
.qeBit=0x01,
.qeWriteRegLen=0x02,
.qeReadRegLen=0x1,
.busyIndex=0,
.busyBit=0x00,
.busyReadRegLen=0x1,
.releasePowerDown=0xab,
.readRegCmd[0]=0x05,
.readRegCmd[1]=0x35,
.writeRegCmd[0]=0x01,
.writeRegCmd[1]=0x01,
.fastReadQioCmd=0xeb,
.frQioDmyClk=16/8,
.cReadSupport=1,
.cReadMode=0xa0,
.burstWrapCmd=0x77,
.burstWrapCmdDmyClk=0x3,
.burstWrapDataMode=SF_CTRL_DATA_4_LINES,
.burstWrapData=0x40,
/*erase*/
.chipEraseCmd=0xc7,
.sectorEraseCmd=0x20,
.blk32EraseCmd=0x52,
.blk64EraseCmd=0xd8,
/*write*/
.pageProgramCmd=0x02,
.qpageProgramCmd=0x32,
.qppAddrMode=SF_CTRL_ADDR_1_LINE,
.ioMode=0x14,
.clkDelay=1,
.clkInvert=0x01,
.resetEnCmd=0x66,
.resetCmd=0x99,
.cRExit=0xff,
.wrEnableWriteRegLen=0x00,
/*id*/
.jedecIdCmd=0x9f,
.jedecIdCmdDmyClk=0,
.qpiJedecIdCmd=0x9f,
.qpiJedecIdCmdDmyClk=0x00,
.sectorSize=4,
.pageSize=256,
/*read*/
.fastReadCmd=0x0b,
.frDmyClk=8/8,
.qpiFastReadCmd =0x0b,
.qpiFrDmyClk=8/8,
.fastReadDoCmd=0x3b,
.frDoDmyClk=8/8,
.fastReadDioCmd=0xbb,
.frDioDmyClk=0,
.fastReadQoCmd=0x6b,
.frQoDmyClk=8/8,
.qpiFastReadQioCmd=0xeb,
.qpiFrQioDmyClk=16/8,
.qpiPageProgramCmd=0x02,
.writeVregEnableCmd=0x50,
/* qpi mode */
.enterQpi=0x38,
.exitQpi=0xff,
/*AC*/
.timeEsector=300,
.timeE32k=1200,
.timeE64k=1200,
.timePagePgm=5,
.timeCe=33000,
.pdDelay=20,
.qeData=0,
};
static const ATTR_TCM_CONST_SECTION Flash_Info_t flashInfos[]={
{
.jedecID=0x1440A1,
//.name="FM_25Q08",
.cfg=&flashCfg_FM_25Q08,
},
{
.jedecID=0x134051,
//.name="GD_MD04D_04_33",
.cfg=&flashCfg_Gd_Md_40D,
},
{
.jedecID=0x144020,
//.name="XM_25QH80_80_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x154020,
//.name="XM_25QH16_16_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x164020,
//.name="XM_25QH32_32_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x174020,
//.name="XM_25QH64_64_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x1320C2,
//.name="MX_KH40_04_33",
.cfg=&flashCfg_MX_KH25,
},
{
.jedecID=0x1420C2,
//.name="MX_KH80_08_33",
.cfg=&flashCfg_MX_KH25,
},
{
.jedecID=0x1520C2,
//.name="MX_KH16_16_33",
.cfg=&flashCfg_MX_KH25,
},
{
.jedecID=0x13325E,
//.name="ZB_D40B_80_33",
.cfg=&flashCfg_MX_KH25,
},
{
.jedecID=0x14325E,
//.name="ZB_D80B_80_33",
.cfg=&flashCfg_MX_KH25,
},
{
.jedecID=0x15405E,
//.name="ZB_25Q16B_15_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x16405E,
//.name="ZB_25Q32B_16_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x17405E,
//.name="ZB_25VQ64_64_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x15605E,
//.name="ZB_25VQ16_16_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x15345E,
//.name="ZB_25WQ16_16_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x1560EB,
//.name="TH_25Q16",
.cfg=&flashCfg_FM_25Q08,
},
{
.jedecID=0x1740C8,
//.name="GD_25Q64E_64_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x1840C8,
//.name="GD_25Q127C_128_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x176085,
//.name="Puya_P25Q64H_64_33",
.cfg=&flashCfg_XM25QH16,
},
{
.jedecID=0x17400B,
//.name="XT_25F64B",
.cfg=&flashCfg_FM_25Q08,
},
{
.jedecID=0x1560BA,
//.name="ZD_25Q16B",
.cfg=&flashCfg_ZD_25Q16B,
},
{
.jedecID=0x1460CD,
//.name="TH_25Q80HB",
.cfg=&flashCfg_FM_25Q08,
},
{
.jedecID=0x1870EF,
//.name="W25Q128JV_128_33",
.cfg=&flashCfg_XM25QH16,
},
};
/*@} end of group SF_CFG_EXT_Private_Variables */
/** @defgroup SF_CFG_EXT_Global_Variables
* @{
*/
/*@} end of group SF_CFG_EXT_Global_Variables */
/** @defgroup SF_CFG_EXT_Private_Fun_Declaration
* @{
*/
/*@} end of group SF_CFG_EXT_Private_Fun_Declaration */
/** @defgroup SF_CFG_EXT_Public_Functions
* @{
*/
/****************************************************************************//**
* @brief Get flash config according to flash ID
*
* @param flashID: Flash ID
* @param pFlashCfg: Flash config pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SF_Cfg_Get_Flash_Cfg_Need_Lock_Ext(uint32_t flashID,SPI_Flash_Cfg_Type * pFlashCfg)
{
uint32_t i;
uint8_t buf[sizeof(SPI_Flash_Cfg_Type)+8];
uint32_t crc,*pCrc;
char flashCfgMagic[] = "FCFG";
if(flashID==0){
XIP_SFlash_Read_Via_Cache_Need_Lock(8+BL602_FLASH_XIP_BASE,buf,sizeof(SPI_Flash_Cfg_Type)+8);
if(BL602_MemCmp(buf,flashCfgMagic,4)==0){
crc=BFLB_Soft_CRC32((uint8_t *)buf+4,sizeof(SPI_Flash_Cfg_Type));
pCrc=(uint32_t *)(buf+4+sizeof(SPI_Flash_Cfg_Type));
if(*pCrc==crc){
BL602_MemCpy_Fast(pFlashCfg,(uint8_t *)buf+4,sizeof(SPI_Flash_Cfg_Type));
return SUCCESS ;
}
}
}else{
if(SF_Cfg_Get_Flash_Cfg_Need_Lock(flashID, pFlashCfg) == SUCCESS){
return SUCCESS;
}
for(i=0;i<sizeof(flashInfos)/sizeof(flashInfos[0]);i++){
if(flashInfos[i].jedecID==flashID){
BL602_MemCpy_Fast(pFlashCfg,flashInfos[i].cfg,sizeof(SPI_Flash_Cfg_Type));
return SUCCESS;
}
}
}
return ERROR;
}
/****************************************************************************//**
* @brief Identify one flash
*
* @param callFromFlash: code run at flash or ram
* @param autoScan: Auto scan all GPIO pin
* @param flashPinCfg: Specify flash GPIO config, not auto scan
* @param restoreDefault: Wether restore default flash GPIO config
* @param pFlashCfg: Flash config pointer
*
* @return Flash ID
*
*******************************************************************************/
uint32_t ATTR_TCM_SECTION SF_Cfg_Flash_Identify_Ext(uint8_t callFromFlash,
uint32_t autoScan,uint32_t flashPinCfg,uint8_t restoreDefault,SPI_Flash_Cfg_Type * pFlashCfg)
{
uint32_t jdecId=0;
uint32_t i=0;
uint32_t ret=0;
ret=SF_Cfg_Flash_Identify(callFromFlash,autoScan,flashPinCfg,restoreDefault,pFlashCfg);
if(callFromFlash){
SFlash_Set_IDbus_Cfg(pFlashCfg,pFlashCfg->ioMode&0xf,1,0,32);
}
if((ret&BFLB_FLASH_ID_VALID_FLAG)!=0){
return ret;
}
jdecId=(ret&0xffffff);
for(i=0;i<sizeof(flashInfos)/sizeof(flashInfos[0]);i++){
if(flashInfos[i].jedecID==jdecId){
BL602_MemCpy_Fast(pFlashCfg,flashInfos[i].cfg,sizeof(SPI_Flash_Cfg_Type));
break;
}
}
if(i==sizeof(flashInfos)/sizeof(flashInfos[0])){
return jdecId;
}else{
return (jdecId|BFLB_FLASH_ID_VALID_FLAG);
}
}
/*@} end of group SF_CFG_EXT_Public_Functions */
/*@} end of group SF_CFG_EXT */
/*@} end of group BL602_Peripheral_Driver */

View File

@@ -1,608 +0,0 @@
/**
******************************************************************************
* @file bl602_sflash_ext.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "bl602_l1c.h"
#include "bl602_sflash_ext.h"
#include "bl602_sf_ctrl.h"
#include "l1c_reg.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup SFLASH_EXT
* @{
*/
/** @defgroup SFLASH_EXT_Private_Macros
* @{
*/
/*@} end of group SFLASH_EXT_Private_Macros */
/** @defgroup SFLASH_EXT_Private_Types
* @{
*/
/*@} end of group SFLASH_EXT_Private_Types */
/** @defgroup SFLASH_EXT_Private_Variables
* @{
*/
#define SFCTRL_BUSY_STATE_TIMEOUT (5 * 160 * 1000)
/*@} end of group SFLASH_EXT_Private_Variables */
/** @defgroup SFLASH_EXT_Global_Variables
* @{
*/
/*@} end of group SFLASH_EXT_Global_Variables */
/** @defgroup SFLASH_EXT_Private_Fun_Declaration
* @{
*/
/*@} end of group SFLASH_EXT_Private_Fun_Declaration */
/** @defgroup SFLASH_EXT_Private_Functions
* @{
*/
/*@} end of group SFLASH_EXT_Private_Functions */
/** @defgroup SFLASH_EXT_Public_Functions
* @{
*/
/****************************************************************************/ /**
* @brief Sflash restore from power down
*
* @param pFlashCfg: Flash configuration pointer
* @param flashContRead: Whether enable continuous read
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_Restore_From_Powerdown(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t flashContRead)
{
BL_Err_Type stat = SUCCESS;
uint32_t jdecId = 0;
uint8_t tmp[8];
uint8_t ioMode = pFlashCfg->ioMode & 0xf;
/* Wake flash up from power down */
SFlash_Releae_Powerdown(pFlashCfg);
BL602_Delay_US(120);
SFlash_GetJedecId(pFlashCfg, (uint8_t *)&jdecId);
if (SF_CTRL_QO_MODE == ioMode || SF_CTRL_QIO_MODE == ioMode) {
SFlash_Qspi_Enable(pFlashCfg);
}
if (((pFlashCfg->ioMode >> 4) & 0x01) == 1) {
/* unwrap */
L1C_Set_Wrap(DISABLE);
} else {
/* burst wrap */
L1C_Set_Wrap(ENABLE);
/* For command that is setting register instead of send command, we need write enable */
SFlash_Write_Enable(pFlashCfg);
SFlash_SetBurstWrap(pFlashCfg);
}
if (flashContRead) {
stat = SFlash_Read(pFlashCfg, ioMode, 1, 0x00000000, (uint8_t *)tmp, sizeof(tmp));
stat = SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
stat = SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 0, 0, 32);
}
return stat;
}
/****************************************************************************/ /**
* @brief Sflash enable RCV mode to recovery for erase while power drop
*
* @param pFlashCfg: Flash configuration pointer
* @param rCmd: Read RCV register cmd
* @param wCmd: Write RCV register cmd
* @param bitPos: RCV register bit pos
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_RCV_Enable(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t rCmd, uint8_t wCmd, uint8_t bitPos)
{
BL_Err_Type stat;
uint32_t cnt = 0;
uint32_t tempVal = 0;
while (SET == SFlash_Busy(pFlashCfg)) {
BL602_Delay_US(500);
cnt++;
if (cnt > 20000 * 3) {
return ERROR;
}
}
stat = SFlash_Read_Reg_With_Cmd(pFlashCfg, rCmd, (uint8_t *)&tempVal, 1);
if (SUCCESS != stat) {
stat = ERROR;
}
if (((tempVal >> bitPos) & 0x01) > 0) {
return SUCCESS;
}
tempVal |= (uint32_t)(1 << bitPos);
stat = SFlash_Write_Enable(pFlashCfg);
if (SUCCESS != stat) {
stat = ERROR;
}
stat = SFlash_Write_Reg_With_Cmd(pFlashCfg, wCmd, (uint8_t *)&tempVal, 1);
if (SUCCESS != stat) {
return stat;
}
while (SET == SFlash_Busy(pFlashCfg)) {
BL602_Delay_US(500);
cnt++;
if (cnt > 20000 * 3) {
return ERROR;
}
}
stat = SFlash_Read_Reg_With_Cmd(pFlashCfg, rCmd, (uint8_t *)&tempVal, 1);
if (SUCCESS != stat) {
stat = ERROR;
}
if (((tempVal >> bitPos) & 0x01) <= 0) {
return ERROR;
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Erase flash security register one block
*
* @param pFlashCfg: Flash configuration pointer
* @param pSecRegCfg: Security register configuration pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_Erase_Security_Register(SPI_Flash_Cfg_Type *pFlashCfg, SFlash_Sec_Reg_Cfg *pSecRegCfg)
{
uint32_t cnt = 0;
uint8_t cmd = 0;
uint8_t secOptMode = 0;
uint32_t timeOut = 0;
SF_Ctrl_Cmd_Cfg_Type flashCmd;
if (pSecRegCfg->enterSecOptCmd != 0x00) {
secOptMode = 1;
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->enterSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
BL_Err_Type stat = SFlash_Write_Enable(pFlashCfg);
if (stat != SUCCESS) {
return stat;
}
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
cmd = pSecRegCfg->eraseCmd;
flashCmd.cmdBuf[0] = (cmd << 24) | (pSecRegCfg->blockNum << 12);
/* rwFlag don't care */
flashCmd.rwFlag = SF_CTRL_READ;
flashCmd.addrSize = 3;
SF_Ctrl_SendCmd(&flashCmd);
while (SET == SFlash_Busy(pFlashCfg)) {
BL602_Delay_US(500);
cnt++;
if (cnt > pFlashCfg->timeEsector * 3) {
return ERROR;
}
}
if (secOptMode > 0) {
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->exitSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Program flash security register one block
*
* @param pFlashCfg: Flash configuration pointer
* @param pSecRegCfg: Security register configuration pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_Program_Security_Register(SPI_Flash_Cfg_Type *pFlashCfg, SFlash_Sec_Reg_Cfg *pSecRegCfg)
{
uint8_t *const flashCtrlBuf = (uint8_t *)SF_CTRL_BUF_BASE;
uint32_t i = 0, curLen = 0;
uint32_t cnt = 0;
BL_Err_Type stat;
uint8_t cmd;
uint8_t secOptMode = 0;
uint8_t *data = pSecRegCfg->data;
uint32_t addr = pSecRegCfg->addr;
uint32_t len = pSecRegCfg->len;
uint32_t currentAddr = 0;
uint32_t timeOut = 0;
SF_Ctrl_Cmd_Cfg_Type flashCmd;
if (pSecRegCfg->enterSecOptCmd != 0x00) {
secOptMode = 1;
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->enterSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
/* Prepare command */
flashCmd.rwFlag = SF_CTRL_WRITE;
flashCmd.addrSize = 3;
cmd = pSecRegCfg->programCmd;
for (i = 0; i < len;) {
/* Write enable is needed for every program */
stat = SFlash_Write_Enable(pFlashCfg);
if (stat != SUCCESS) {
return stat;
}
/* Get current programmed length within page size */
curLen = 256 - addr % 256;
if (curLen > len - i) {
curLen = len - i;
}
currentAddr = (pSecRegCfg->blockNum << 12) | addr;
/* Prepare command */
BL602_MemCpy_Fast(flashCtrlBuf, data, curLen);
flashCmd.cmdBuf[0] = (cmd << 24) | (currentAddr);
flashCmd.nbData = curLen;
SF_Ctrl_SendCmd(&flashCmd);
/* Adjust address and programmed length */
addr += curLen;
i += curLen;
data += curLen;
/* Wait for write done */
cnt = 0;
while (SET == SFlash_Busy(pFlashCfg)) {
BL602_Delay_US(100);
cnt++;
if (cnt > pFlashCfg->timePagePgm * 20) {
return ERROR;
}
}
}
if (secOptMode > 0) {
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->exitSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Read data from flash security register one block
*
* @param pSecRegCfg: Security register configuration pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_Read_Security_Register(SFlash_Sec_Reg_Cfg *pSecRegCfg)
{
uint8_t *const flashCtrlBuf = (uint8_t *)SF_CTRL_BUF_BASE;
uint32_t curLen, i;
uint8_t cmd;
uint8_t secOptMode = 0;
uint8_t *data = pSecRegCfg->data;
uint32_t addr = pSecRegCfg->addr;
uint32_t len = pSecRegCfg->len;
uint32_t currentAddr = 0;
uint32_t timeOut = 0;
SF_Ctrl_Cmd_Cfg_Type flashCmd;
if (pSecRegCfg->enterSecOptCmd != 0x00) {
secOptMode = 1;
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->enterSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
/* Prepare command */
flashCmd.rwFlag = SF_CTRL_READ;
flashCmd.addrSize = 3;
flashCmd.dummyClks = 1;
cmd = pSecRegCfg->readCmd;
/* Read data */
for (i = 0; i < len;) {
currentAddr = (pSecRegCfg->blockNum << 12) | addr;
/* Prepare command */
flashCmd.cmdBuf[0] = (cmd << 24) | (currentAddr);
curLen = len - i;
if (curLen >= FLASH_CTRL_BUF_SIZE) {
curLen = FLASH_CTRL_BUF_SIZE;
flashCmd.nbData = curLen;
} else {
/* Make sf_ctrl word read */
flashCmd.nbData = ((curLen + 3) >> 2) << 2;
}
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
BL602_MemCpy_Fast(data, flashCtrlBuf, curLen);
addr += curLen;
i += curLen;
data += curLen;
}
if (secOptMode > 0) {
if (((uint32_t)&flashCmd) % 4 == 0) {
BL602_MemSet4((uint32_t *)&flashCmd, 0, sizeof(flashCmd) / 4);
} else {
BL602_MemSet(&flashCmd, 0, sizeof(flashCmd));
}
flashCmd.cmdBuf[0] = (pSecRegCfg->exitSecOptCmd << 24);
flashCmd.rwFlag = SF_CTRL_WRITE;
SF_Ctrl_SendCmd(&flashCmd);
timeOut = SFCTRL_BUSY_STATE_TIMEOUT;
while (SET == SF_Ctrl_GetBusyState()) {
timeOut--;
if (timeOut == 0) {
return TIMEOUT;
}
}
}
return SUCCESS;
}
/****************************************************************************//**
* @brief Clear flash status register
*
* @param pFlashCfg: Flash configuration pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
BL_Err_Type ATTR_TCM_SECTION SFlash_Clear_Status_Register(SPI_Flash_Cfg_Type *pFlashCfg)
{
uint32_t ret = 0;
uint32_t qeValue = 0;
uint32_t regValue = 0;
uint32_t readValue = 0;
uint8_t readRegValue0 = 0;
uint8_t readRegValue1 = 0;
if((pFlashCfg->ioMode&0xf)==SF_CTRL_QO_MODE || (pFlashCfg->ioMode&0xf)==SF_CTRL_QIO_MODE){
qeValue = 1;
}
SFlash_Read_Reg(pFlashCfg, 0, (uint8_t *)&readRegValue0, 1);
SFlash_Read_Reg(pFlashCfg, 1, (uint8_t *)&readRegValue1, 1);
readValue = (readRegValue0|(readRegValue1<<8));
if ((readValue & (~((1<<(pFlashCfg->qeIndex*8+pFlashCfg->qeBit)) |
(1<<(pFlashCfg->busyIndex*8+pFlashCfg->busyBit)) |
(1<<(pFlashCfg->wrEnableIndex*8+pFlashCfg->wrEnableBit))))) == 0){
return SUCCESS;
}
ret = SFlash_Write_Enable(pFlashCfg);
if (SUCCESS != ret) {
return ERROR;
}
if (pFlashCfg->qeWriteRegLen == 2) {
regValue = (qeValue<<(pFlashCfg->qeIndex*8+pFlashCfg->qeBit));
SFlash_Write_Reg(pFlashCfg, 0, (uint8_t *)&regValue, 2);
} else {
if (pFlashCfg->qeIndex == 0) {
regValue = (qeValue<<pFlashCfg->qeBit);
} else {
regValue = 0;
}
SFlash_Write_Reg(pFlashCfg, 0, (uint8_t *)&regValue, 1);
ret = SFlash_Write_Enable(pFlashCfg);
if (SUCCESS != ret) {
return ERROR;
}
if (pFlashCfg->qeIndex == 1) {
regValue = (qeValue<<pFlashCfg->qeBit);
} else {
regValue = 0;
}
SFlash_Write_Reg(pFlashCfg, 1, (uint8_t *)&regValue, 1);
}
return SUCCESS;
}
/*@} end of group SFLASH_EXT_Public_Functions */
/*@} end of group SFLASH_EXT */
/*@} end of group BL602_Peripheral_Driver */

View File

@@ -1,233 +0,0 @@
/**
******************************************************************************
* @file bl602_tzc_sec.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "string.h"
#include "bl602_tzc_sec.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup TZC_SEC
* @{
*/
/** @defgroup TZC_SEC_Private_Macros
* @{
*/
/*@} end of group TZC_SEC_Private_Macros */
/** @defgroup TZC_SEC_Private_Types
* @{
*/
/*@} end of group TZC_SEC_Private_Types */
/** @defgroup TZC_SEC_Private_Variables
* @{
*/
/*@} end of group TZC_SEC_Private_Variables */
/** @defgroup TZC_SEC_Global_Variables
* @{
*/
/*@} end of group TZC_SEC_Global_Variables */
/** @defgroup TZC_SEC_Private_Fun_Declaration
* @{
*/
/*@} end of group TZC_SEC_Private_Fun_Declaration */
/** @defgroup TZC_SEC_Public_Functions
* @{
*/
/****************************************************************************/ /**
* @brief TZC Security boot set
*
* @param Val: 0 for security boot start, and 0xf for security boot finished
*
* @return None
*
*******************************************************************************/
void TZC_Sboot_Set(uint8_t Val)
{
uint32_t tmpVal;
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_SBOOT_DONE, Val);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmpVal);
}
/****************************************************************************/ /**
* @brief TZC Set ROM0 R0 protect range
*
* @param start: Start address to protect
* @param end: End address to protect
*
* @return None
*
*******************************************************************************/
void TZC_Set_Rom0_R0_Protect(uint32_t start, uint32_t end)
{
uint32_t tmpVal;
/* Set Range */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM0_R0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_START, start >> 10);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_END, end >> 10);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM0_R0, tmpVal);
/* Enable */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_ID0_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_ID1_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_EN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R0_LOCK, 1);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmpVal);
}
/****************************************************************************/ /**
* @brief TZC Set ROM0 R1 protect range
*
* @param start: Start address to protect
* @param end: End address to protect
*
* @return None
*
*******************************************************************************/
void TZC_Set_Rom0_R1_Protect(uint32_t start, uint32_t end)
{
uint32_t tmpVal;
/* Set Range */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM0_R1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_START, start >> 10);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_END, end >> 10);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM0_R1, tmpVal);
/* Enable */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_ID0_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_ID1_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_EN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM0_R1_LOCK, 1);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmpVal);
}
/****************************************************************************/ /**
* @brief TZC Set ROM1 R0 protect range
*
* @param start: Start address to protect
* @param end: End address to protect
*
* @return None
*
*******************************************************************************/
void TZC_Set_Rom1_R0_Protect(uint32_t start, uint32_t end)
{
uint32_t tmpVal;
/* Set Range */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM1_R0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_START, start >> 10);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_END, end >> 10);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM1_R0, tmpVal);
/* Enable */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_ID0_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_ID1_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_EN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R0_LOCK, 1);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmpVal);
}
/****************************************************************************/ /**
* @brief TZC Set ROM1 R1 protect range
*
* @param start: Start address to protect
* @param end: End address to protect
*
* @return None
*
*******************************************************************************/
void TZC_Set_Rom1_R1_Protect(uint32_t start, uint32_t end)
{
uint32_t tmpVal;
/* Set Range */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM1_R1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_START, start >> 10);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_END, end >> 10);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM1_R1, tmpVal);
/* Enable */
tmpVal = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_ID0_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_ID1_EN, 0);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_EN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, TZC_SEC_TZC_ROM1_R1_LOCK, 1);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmpVal);
}
/*@} end of group TZC_SEC_Public_Functions */
/*@} end of group TZC_SEC */
/*@} end of group BL602_Peripheral_Driver */

View File

@@ -1,583 +0,0 @@
/**
******************************************************************************
* @file bl602_xip_sflash_ext.c
* @version V1.0
* @date
* @brief This file is the standard driver c file
******************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
*
* 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 Bouffalo Lab 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.
*
******************************************************************************
*/
#include "string.h"
#include "bl602_sf_cfg.h"
#include "bl602_sf_cfg_ext.h"
#include "bl602_xip_sflash.h"
#include "bl602_xip_sflash_ext.h"
/** @addtogroup BL602_Peripheral_Driver
* @{
*/
/** @addtogroup XIP_SFLASH_EXT
* @{
*/
/** @defgroup XIP_SFLASH_EXT_Private_Macros
* @{
*/
/*@} end of group XIP_SFLASH_EXT_Private_Macros */
/** @defgroup XIP_SFLASH_EXT_Private_Types
* @{
*/
/*@} end of group XIP_SFLASH_EXT_Private_Types */
/** @defgroup XIP_SFLASH_EXT_Private_Variables
* @{
*/
static SPI_Flash_Cfg_Type flashCfg;
static uint8_t aesEnable;
/*@} end of group XIP_SFLASH_EXT_Private_Variables */
/** @defgroup XIP_SFLASH_EXT_Global_Variables
* @{
*/
/*@} end of group XIP_SFLASH_EXT_Global_Variables */
/** @defgroup XIP_SFLASH_EXT_Private_Fun_Declaration
* @{
*/
/*@} end of group XIP_SFLASH_EXT_Private_Fun_Declaration */
/** @defgroup XIP_SFLASH_EXT_Private_Functions
* @{
*/
/*@} end of group XIP_SFLASH_EXT_Private_Functions */
/** @defgroup XIP_SFLASH_EXT_Public_Functions
* @{
*/
/****************************************************************************//**
* @brief Save flash controller state
*
* @param pFlashCfg: Flash config pointer
* @param offset: CPU XIP flash offset pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_State_Save_Ext(SPI_Flash_Cfg_Type *pFlashCfg,uint32_t *offset)
{
/* XIP_SFlash_Delay */
volatile uint32_t i=32*2;
while(i--);
SF_Ctrl_Set_Owner(SF_CTRL_OWNER_SAHB);
/* Exit form continous read for accepting command */
SFlash_Reset_Continue_Read(pFlashCfg);
/* Send software reset command(80bv has no this command)to deburst wrap for ISSI like */
SFlash_Software_Reset(pFlashCfg);
/* For disable command that is setting register instaed of send command, we need write enable */
SFlash_DisableBurstWrap(pFlashCfg);
if ((pFlashCfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (pFlashCfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
/* Enable QE again in case reset command make it reset */
SFlash_Qspi_Enable(pFlashCfg);
}
/* Deburst again to make sure */
SFlash_DisableBurstWrap(pFlashCfg);
/* Clear offset setting*/
*offset=SF_Ctrl_Get_Flash_Image_Offset();
SF_Ctrl_Set_Flash_Image_Offset(0);
return SUCCESS;
}
/****************************************************************************//**
* @brief Restore flash controller state
*
* @param pFlashCfg: Flash config pointer
* @param offset: CPU XIP flash offset
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_State_Restore_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint32_t offset)
{
uint32_t tmp[1];
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode & 0xf;
SF_Ctrl_Set_Flash_Image_Offset(offset);
if (((pFlashCfg->ioMode >> 4) & 0x01) == 0) {
if ((pFlashCfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (pFlashCfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
SFlash_SetBurstWrap(pFlashCfg);
}
}
SFlash_Read(pFlashCfg, ioMode, 1, 0x0, (uint8_t *)tmp, sizeof(tmp));
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
return SUCCESS;
}
/*@} end of group XIP_SFLASH_EXT_Public_Functions */
/** @defgroup XIP_SFLASH_EXT_Public_Functions
* @{
*/
/****************************************************************************/ /**
* @brief Erase flash one region
*
* @param pFlashCfg: Flash config pointer
* @param startaddr: start address to erase
* @param endaddr: end address(include this address) to erase
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_Erase_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint32_t startaddr, uint32_t endaddr)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode&0xf;
XIP_SFlash_Opt_Enter(&aesEnable);
stat=XIP_SFlash_State_Save(pFlashCfg,&offset);
if(stat!=SUCCESS){
SFlash_Set_IDbus_Cfg(pFlashCfg,ioMode,1,0,32);
}else{
stat=SFlash_Erase(pFlashCfg,startaddr,endaddr);
XIP_SFlash_State_Restore_Ext(pFlashCfg,offset);
}
XIP_SFlash_Opt_Exit(aesEnable);
return stat;
}
/****************************************************************************/ /**
* @brief Program flash one region
*
* @param pFlashCfg: Flash config pointer
* @param addr: start address to be programed
* @param data: data pointer to be programed
* @param len: data length to be programed
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_Write_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode&0xf;
XIP_SFlash_Opt_Enter(&aesEnable);
stat=XIP_SFlash_State_Save(pFlashCfg,&offset);
if(stat!=SUCCESS){
SFlash_Set_IDbus_Cfg(pFlashCfg,ioMode,1,0,32);
}else{
stat= SFlash_Program(pFlashCfg,ioMode,addr,data,len);
XIP_SFlash_State_Restore_Ext(pFlashCfg,offset);
}
XIP_SFlash_Opt_Exit(aesEnable);
return stat;
}
/****************************************************************************/ /**
* @brief Read data from flash
*
* @param pFlashCfg: Flash config pointer
* @param addr: flash read start address
* @param data: data pointer to store data read from flash
* @param len: data length to read
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_Read_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode&0xf;
XIP_SFlash_Opt_Enter(&aesEnable);
stat=XIP_SFlash_State_Save(pFlashCfg,&offset);
if(stat!=SUCCESS){
SFlash_Set_IDbus_Cfg(pFlashCfg,ioMode,1,0,32);
}else{
stat=SFlash_Read(pFlashCfg,ioMode,0,addr, data,len);
XIP_SFlash_State_Restore_Ext(pFlashCfg,offset);
}
XIP_SFlash_Opt_Exit(aesEnable);
return stat;
}
/****************************************************************************//**
* @brief Clear flash status register need lock
*
* @param pFlashCfg: Flash config pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_Clear_Status_Register_Need_Lock(SPI_Flash_Cfg_Type *pFlashCfg)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode&0xf;
stat=XIP_SFlash_State_Save(pFlashCfg, &offset);
if (stat != SUCCESS) {
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
stat=SFlash_Clear_Status_Register(pFlashCfg);
XIP_SFlash_State_Restore_Ext(pFlashCfg, offset);
}
return stat;
}
/****************************************************************************//**
* @brief Get Flash Jedec ID
*
* @param pFlashCfg: Flash config pointer
* @param data: data pointer to store Jedec ID Read from flash
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_GetJedecId_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t *data)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode & 0xf;
stat = XIP_SFlash_State_Save(pFlashCfg, &offset);
if (stat != SUCCESS) {
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
SFlash_GetJedecId(pFlashCfg, data);
XIP_SFlash_State_Restore_Ext(pFlashCfg, offset);
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Get Flash Device ID
*
* @param pFlashCfg: Flash config pointer
* @param data: data pointer to store Device ID Read from flash
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_GetDeviceId_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t *data)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode & 0xf;
stat = XIP_SFlash_State_Save(pFlashCfg, &offset);
if (stat != SUCCESS) {
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
SFlash_GetDeviceId(data);
XIP_SFlash_State_Restore_Ext(pFlashCfg, offset);
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Get Flash Unique ID
*
* @param pFlashCfg: Flash config pointer
* @param data: data pointer to store Device ID Read from flash
* @param idLen: Unique id len
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_GetUniqueId_Need_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t *data, uint8_t idLen)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode & 0xf;
stat = XIP_SFlash_State_Save(pFlashCfg, &offset);
if (stat != SUCCESS) {
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
SFlash_GetUniqueId(data, idLen);
XIP_SFlash_State_Restore_Ext(pFlashCfg, offset);
}
return SUCCESS;
}
/****************************************************************************/ /**
* @brief Sflash enable RCV mode to recovery for erase while power drop need lock
*
* @param pFlashCfg: Flash config pointer
* @param rCmd: Read RCV register cmd
* @param wCmd: Write RCV register cmd
* @param bitPos: RCV register bit pos
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_RCV_Enable_Need_Lock(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t rCmd, uint8_t wCmd, uint8_t bitPos)
{
BL_Err_Type stat;
uint32_t offset;
SF_Ctrl_IO_Type ioMode = (SF_Ctrl_IO_Type)pFlashCfg->ioMode & 0xf;
stat = XIP_SFlash_State_Save(pFlashCfg, &offset);
if (stat != SUCCESS) {
SFlash_Set_IDbus_Cfg(pFlashCfg, ioMode, 1, 0, 32);
} else {
stat = SFlash_RCV_Enable(pFlashCfg, rCmd, wCmd, bitPos);
XIP_SFlash_State_Restore_Ext(pFlashCfg, offset);
}
return stat;
}
/****************************************************************************//**
* @brief Read data from flash with lock
*
* @param pFlashCfg: Flash config pointer
* @param addr: flash read start address
* @param dst: data pointer to store data read from flash
* @param len: data length to read
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Read_With_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg,uint32_t addr, uint8_t *dst, int len)
{
__disable_irq();
XIP_SFlash_Read_Need_Lock_Ext(pFlashCfg, addr, dst, len);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Program flash one region with lock
*
* @param pFlashCfg: Flash config pointer
* @param addr: Start address to be programed
* @param src: Data pointer to be programed
* @param len: Data length to be programed
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Write_With_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg,uint32_t addr, uint8_t *src, int len)
{
__disable_irq();
XIP_SFlash_Write_Need_Lock_Ext(pFlashCfg, addr, src, len);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Erase flash one region with lock
*
* @param pFlashCfg: Flash config pointer
* @param addr: Start address to be erased
* @param len: Data length to be erased
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Erase_With_Lock_Ext(SPI_Flash_Cfg_Type *pFlashCfg,uint32_t addr, int len)
{
__disable_irq();
XIP_SFlash_Erase_Need_Lock_Ext(pFlashCfg, addr, addr + len - 1);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Clear flash status register with lock
*
* @param pFlashCfg: Flash config pointer
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Clear_Status_Register_With_Lock(SPI_Flash_Cfg_Type *pFlashCfg)
{
__disable_irq();
XIP_SFlash_Clear_Status_Register_Need_Lock(pFlashCfg);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Sflash enable RCV mode to recovery for erase while power drop with lock
*
* @param pFlashCfg: Flash config pointer
* @param rCmd: Read RCV register cmd
* @param wCmd: Write RCV register cmd
* @param bitPos: RCV register bit pos
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_RCV_Enable_With_Lock(SPI_Flash_Cfg_Type *pFlashCfg, uint8_t rCmd, uint8_t wCmd, uint8_t bitPos)
{
__disable_irq();
XIP_SFlash_RCV_Enable_Need_Lock(pFlashCfg, rCmd, wCmd, bitPos);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Read data from flash with lock
*
* @param pFlashCfg:Flash config pointer
*
* @return SUCCESS or ERROR
*
*******************************************************************************/
__WEAK
BL_Err_Type ATTR_TCM_SECTION XIP_SFlash_Init(SPI_Flash_Cfg_Type *pFlashCfg)
{
uint32_t ret;
if(pFlashCfg==NULL){
/* Get flash config identify */
XIP_SFlash_Opt_Enter(&aesEnable);
ret=SF_Cfg_Flash_Identify_Ext(1,1,0,0,&flashCfg);
XIP_SFlash_Opt_Exit(aesEnable);
if((ret&BFLB_FLASH_ID_VALID_FLAG)==0){
return ERROR;
}
}else{
memcpy(&flashCfg,pFlashCfg,sizeof(flashCfg));
}
return SUCCESS;
}
/****************************************************************************//**
* @brief Read data from flash with lock
*
* @param addr: flash read start address
* @param dst: data pointer to store data read from flash
* @param len: data length to read
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Read(uint32_t addr, uint8_t *dst, int len)
{
__disable_irq();
XIP_SFlash_Opt_Enter(&aesEnable);
XIP_SFlash_Read_Need_Lock_Ext(&flashCfg, addr, dst, len);
XIP_SFlash_Opt_Exit(aesEnable);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Program flash one region with lock
*
* @param addr: Start address to be programed
* @param src: Data pointer to be programed
* @param len: Data length to be programed
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Write(uint32_t addr, uint8_t *src, int len)
{
__disable_irq();
XIP_SFlash_Opt_Enter(&aesEnable);
XIP_SFlash_Write_Need_Lock_Ext(&flashCfg, addr, src, len);
XIP_SFlash_Opt_Exit(aesEnable);
__enable_irq();
return 0;
}
/****************************************************************************//**
* @brief Erase flash one region with lock
*
* @param addr: Start address to be erased
* @param len: Data length to be erased
*
* @return 0
*
*******************************************************************************/
__WEAK
int ATTR_TCM_SECTION XIP_SFlash_Erase(uint32_t addr, int len)
{
__disable_irq();
XIP_SFlash_Opt_Enter(&aesEnable);
XIP_SFlash_Erase_Need_Lock_Ext(&flashCfg, addr, addr + len - 1);
XIP_SFlash_Opt_Exit(aesEnable);
__enable_irq();
return 0;
}
/*@} end of group XIP_SFLASH_EXT_Public_Functions */
/*@} end of group XIP_SFLASH_EXT */
/*@} end of group BL602_Peripheral_Driver */

View File

@@ -1,66 +1,64 @@
################# Add global include #################
list(APPEND ADD_INCLUDE
"${CMAKE_CURRENT_SOURCE_DIR}"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/inc"
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/inc"
"${CMAKE_CURRENT_SOURCE_DIR}/startup"
"${CMAKE_CURRENT_SOURCE_DIR}/regs"
)
#######################################################
################# Add private include #################
list(APPEND ADD_PRIVATE_INCLUDE
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/default_config"
)
#######################################################
############## Add current dir source files ###########
file(GLOB_RECURSE sources
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/*.c"
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/src/*.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/interrupt.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/system_bl602.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/GCC/entry.S"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/GCC/start_load.c"
)
list(APPEND ADD_SRCS ${sources})
# aux_source_directory(src ADD_SRCS)
list(REMOVE_ITEM ADD_SRCS "${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl602_mfg_efuse.c"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl602_mfg_media.c"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl602_mfg_flash.c"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl602_romdriver.c")
#######################################################
########### Add required/dependent components #########
list(APPEND ADD_REQUIREMENTS common)
#######################################################
############ Add static libs ##########################
# if(CONFIG_COMPONENT1_INCLUDE_STATIC_LIB)
# list(APPEND ADD_STATIC_LIB "lib/libtest.a")
# endif()
#######################################################
############ Add dynamic libs #########################
# list(APPEND ADD_DYNAMIC_LIB "lib/arch/v831/libmaix_nn.so"
# "lib/arch/v831/libmaix_cam.so"
# )
#######################################################
############ Add global compile option ################
#add components denpend on this component
if(CONFIG_ROMAPI)
list(APPEND ADD_DEFINITIONS -DBFLB_USE_ROM_DRIVER)
endif()
if(CONFIG_HALAPI)
list(APPEND ADD_DEFINITIONS -DBFLB_USE_HAL_DRIVER)
endif()
list(APPEND ADD_DEFINITIONS -DARCH_RISCV)
#######################################################
############ Add private compile option ################
#add compile option for this component that won't affect other modules
# list(APPEND ADD_DEFINITIONS_PRIVATE -DAAAAA=1)
#######################################################
generate_library()
################# Add global include #################
list(APPEND ADD_INCLUDE
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/inc"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/inc"
"${CMAKE_CURRENT_SOURCE_DIR}/regs"
"${CMAKE_CURRENT_SOURCE_DIR}/startup"
"${CMAKE_CURRENT_SOURCE_DIR}"
)
#######################################################
################# Add private include #################
list(APPEND ADD_PRIVATE_INCLUDE
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/default_config"
)
#######################################################
############## Add current dir source files ###########
file(GLOB_RECURSE sources
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/*.c"
"${CMAKE_CURRENT_SOURCE_DIR}/hal_drv/src/*.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/interrupt.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/system_bl702.c"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/GCC/entry.S"
"${CMAKE_CURRENT_SOURCE_DIR}/startup/GCC/start_load.c"
)
list(APPEND ADD_SRCS ${sources})
# aux_source_directory(src ADD_SRCS)
list(REMOVE_ITEM ADD_SRCS "${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl702_snflash.c"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl702_romdriver.c"
"${CMAKE_CURRENT_SOURCE_DIR}/std_drv/src/bl702_clock.c"
)
#######################################################
########### Add required/dependent components #########
list(APPEND ADD_REQUIREMENTS common)
#######################################################
############ Add static libs ##########################
#list(APPEND ADD_STATIC_LIB "lib/libtest.a")
#######################################################
############ Add dynamic libs #########################
# list(APPEND ADD_DYNAMIC_LIB "lib/arch/v831/libmaix_nn.so"
# "lib/arch/v831/libmaix_cam.so"
# )
#######################################################
############ Add global compile option ################
#add components denpend on this component
if(CONFIG_ROMAPI)
list(APPEND ADD_DEFINITIONS -DBFLB_USE_ROM_DRIVER)
endif()
if(CONFIG_HALAPI)
list(APPEND ADD_DEFINITIONS -DBFLB_USE_HAL_DRIVER)
endif()
list(APPEND ADD_DEFINITIONS -DARCH_RISCV)
#######################################################
############ Add private compile option ################
#add compile option for this component that won't affect other modules
# list(APPEND ADD_PRIVATE_DEFINITIONS -DAAAAA=1)
#######################################################
generate_library()

View File

@@ -1,9 +1,9 @@
/****************************************************************************************
* @file map.txt
* @file bl702_flash.ld
*
* @brief This file is the map file (gnuarm or armgcc).
*
* Copyright (C) BouffaloLab 2018
* Copyright (C) BouffaloLab 2021
*
****************************************************************************************
*/
@@ -11,21 +11,21 @@
/* configure the CPU type */
OUTPUT_ARCH( "riscv" )
/* link with the standard c library */
/*INPUT(-lc)*/
/* INPUT(-lc) */
/* link with the standard GCC library */
/*INPUT(-lgcc)*/
/* INPUT(-lgcc) */
/* configure the entry point */
ENTRY(_enter)
StackSize = 0x0400; /* 1KB */
HeapSize = 0x1000; /* 4KB */
StackSize = 0x1000; /* 4KB */
MEMORY
{
xip_memory (rx) : ORIGIN = 0x23000000, LENGTH = 1024K
itcm_memory (rx) : ORIGIN = 0x22010000, LENGTH = 16K
dtcm_memory (rx) : ORIGIN = 0x42014000, LENGTH = 48K
ram_memory (!rx) : ORIGIN = 0x42020000, LENGTH = 176K
itcm_memory (rx) : ORIGIN = 0x22014000, LENGTH = 16K
dtcm_memory (rx) : ORIGIN = 0x42018000, LENGTH = 16K
ram_memory (!rx) : ORIGIN = 0x4201C000, LENGTH = 80K
hbn_memory (rx) : ORIGIN = 0x40010000, LENGTH = 0xE00 /* hbn ram 4K used 3.5K*/
}
SECTIONS
@@ -39,7 +39,6 @@ SECTIONS
KEEP (*(.text.metal.init.enter))
KEEP (*(SORT_NONE(.init)))
/* section information for shell */
. = ALIGN(4);
__fsymtab_start = .;
@@ -51,30 +50,34 @@ SECTIONS
KEEP(*(VSymTab))
__vsymtab_end = .;
/* section information for usb desc */
. = ALIGN(4);
_usb_desc_start = .;
KEEP(*(usb_desc))
. = ALIGN(4);
_usb_desc_end = .;
*(.text)
*(.text.*)
/*put .rodata**/
*(EXCLUDE_FILE( *bl602_glb*.o* \
*bl602_pds*.o* \
*bl602_common*.o* \
*bl602_sf_cfg*.o* \
*bl602_sf_cfg_ext*.o* \
*bl602_sf_ctrl*.o* \
*bl602_sflash*.o* \
*bl602_sflash_ext*.o* \
*bl602_xip_sflash*.o* \
*bl602_xip_sflash_ext*.o* \
*bl602_ef_ctrl*.o*) .rodata*)
*(.rodata)
*(.rodata.*)
*(EXCLUDE_FILE( *bl702_glb*.o* \
*bl702_pds*.o* \
*bl702_common*.o* \
*bl702_sf_cfg*.o* \
*bl702_sf_cfg_ext*.o* \
*bl702_sf_ctrl*.o* \
*bl702_sflash*.o* \
*bl702_sflash_ext*.o* \
*bl702_xip_sflash*.o* \
*bl702_xip_sflash_ext*.o* \
*bl702_ef_ctrl*.o*) .rodata*)
*(.srodata)
*(.srodata.*)
. = ALIGN(4);
__text_code_end__ = .;
} > xip_memory
. = ALIGN(4);
@@ -90,23 +93,36 @@ SECTIONS
*(.sclock_rlt_code.*)
*(.sclock_rlt_const.*)
*bl602_glb*.o*(.rodata*)
*bl602_pds*.o*(.rodata*)
*bl602_common*.o*(.rodata*)
*bl602_sf_cfg*.o*(.rodata*)
*bl602_sf_cfg_ext*.o*(.rodata*)
*bl602_sf_ctrl*.o*(.rodata*)
*bl602_sflash*.o*(.rodata*)
*bl602_sflash_ext*.o*(.rodata*)
*bl602_xip_sflash*.o*(.rodata*)
*bl602_xip_sflash_ext*.o*(.rodata*)
*bl602_ef_ctrl*.o*(.rodata*)
*bl702_glb*.o*(.rodata*)
*bl702_pds*.o*(.rodata*)
*bl702_common*.o*(.rodata*)
*bl702_sf_cfg*.o*(.rodata*)
*bl702_sf_cfg_ext*.o*(.rodata*)
*bl702_sf_ctrl*.o*(.rodata*)
*bl702_sflash*.o*(.rodata*)
*bl702_sflash_ext*.o*(.rodata*)
*bl702_xip_sflash*.o*(.rodata*)
*bl702_xip_sflash_ext*.o*(.rodata*)
*bl702_ef_ctrl*.o*(.rodata*)
. = ALIGN(4);
__tcm_code_end__ = .;
} > itcm_memory
__dtcm_load_addr = __itcm_load_addr + SIZEOF(.itcm_region);
__hbn_load_addr = __itcm_load_addr + SIZEOF(.itcm_region);
.hbn_ram_region : AT (__hbn_load_addr)
{
. = ALIGN(4);
__hbn_ram_start__ = .;
*bl702_hbn_wakeup*.o*(.rodata*)
*(.hbn_ram_code*)
*(.hbn_ram_data)
. = ALIGN(4);
__hbn_ram_end__ = .;
} > hbn_memory
__dtcm_load_addr = __hbn_load_addr + SIZEOF(.hbn_ram_region);
.dtcm_region : AT (__dtcm_load_addr)
{
@@ -114,28 +130,12 @@ SECTIONS
__tcm_data_start__ = .;
*(.tcm_data)
/* *finger_print.o(.data*) */
. = ALIGN(4);
__tcm_data_end__ = .;
} > dtcm_memory
/* .heap_dummy section doesn't contains any symbols. It is only
* used for linker to calculate size of heap sections, and assign
* values to heap symbols later */
.heap_dummy (NOLOAD):
{
. = ALIGN(0x4);
. = . + HeapSize;
. = ALIGN(0x4);
} > dtcm_memory
_HeapBase = ORIGIN(dtcm_memory) + LENGTH(dtcm_memory) - StackSize - HeapSize;
_HeapSize = HeapSize;
/* Check if data + heap + stack exceeds RAM limit */
ASSERT(_HeapBase >= __tcm_data_end__, "region RAM overflowed with stack")
/*************************************************************************/
/* .stack_dummy section doesn't contains any symbols. It is only
* used for linker to calculate size of stack sections, and assign
@@ -220,14 +220,16 @@ SECTIONS
. = ALIGN(4);
__HeapBase = .;
/*__end__ = .;*/
/*end = __end__;*/
KEEP(*(.heap*))
. = ALIGN(4);
__HeapLimit = .;
} > ram_memory
PROVIDE (__heap_min_size = 0x400);
__HeapLimit = ORIGIN(ram_memory) + LENGTH(ram_memory);
ASSERT((__HeapLimit - __HeapBase ) >= __heap_min_size, "heap size is too short.")
}

View File

@@ -0,0 +1,194 @@
/****************************************************************************************
* @file bl702_ram.ld
*
* @brief This file is the map file (gnuarm or armgcc).
*
* Copyright (C) BouffaloLab 2021
*
****************************************************************************************
*/
/* configure the CPU type */
OUTPUT_ARCH( "riscv" )
/* link with the standard c library */
/* INPUT(-lc) */
/* link with the standard GCC library */
/* INPUT(-lgcc) */
/* configure the entry point */
ENTRY(_enter)
StackSize = 0x0400; /* 1KB */
MEMORY
{
itcm_memory (rx) : ORIGIN = 0x22010000, LENGTH = 32K
dtcm_memory (rx) : ORIGIN = 0x42018000, LENGTH = 32K
ram_memory (!rx) : ORIGIN = 0x42020000, LENGTH = 48K
hbn_memory (rx) : ORIGIN = 0x40010000, LENGTH = 4K /* hbn ram 4K*/
}
SECTIONS
{
PROVIDE(__metal_chicken_bit = 0);
.text :
{
. = ALIGN(4);
__text_code_start__ = .;
KEEP (*(.text.metal.init.enter))
KEEP (*(SORT_NONE(.init)))
*(.text)
*(.text.*)
*(.rodata)
*(.rodata.*)
*(.srodata)
*(.srodata.*)
*(.tcm_code.*)
*(.tcm_const.*)
*(.sclock_rlt_code.*)
*(.sclock_rlt_const.*)
. = ALIGN(4);
__text_code_end__ = .;
} > itcm_memory
. = ALIGN(4);
__itcm_load_addr = .;
.itcm_region : AT (__itcm_load_addr)
{
. = ALIGN(4);
__tcm_code_start__ = .;
. = ALIGN(4);
__tcm_code_end__ = .;
} > itcm_memory
__hbn_load_addr = __itcm_load_addr + SIZEOF(.itcm_region);
.hbn_ram_region : AT (__hbn_load_addr)
{
. = ALIGN(4);
__hbn_ram_start__ = .;
*(.hbn_ram_code)
*(.hbn_data)
. = ALIGN(4);
__hbn_ram_end__ = .;
} > hbn_memory
__dtcm_load_addr = __hbn_load_addr + SIZEOF(.hbn_ram_region);
.dtcm_region : AT (__dtcm_load_addr)
{
. = ALIGN(4);
__tcm_data_start__ = .;
*(.tcm_data)
. = ALIGN(4);
__tcm_data_end__ = .;
} > dtcm_memory
/*************************************************************************/
/* .stack_dummy section doesn't contains any symbols. It is only
* used for linker to calculate size of stack sections, and assign
* values to stack symbols later */
.stack_dummy (NOLOAD):
{
. = ALIGN(0x4);
. = . + StackSize;
. = ALIGN(0x4);
} > dtcm_memory
/* Set stack top to end of RAM, and stack limit move down by
* size of stack_dummy section */
__StackTop = ORIGIN(dtcm_memory) + LENGTH(dtcm_memory);
__StackLimit = __StackTop - SIZEOF(.stack_dummy);
/* Check if data + heap + stack exceeds RAM limit */
ASSERT(__StackLimit >= __tcm_data_end__, "region RAM overflowed with stack")
/*************************************************************************/
__system_ram_load_addr = __dtcm_load_addr + SIZEOF(.dtcm_region);
.system_ram_data_region : AT (__system_ram_load_addr)
{
. = ALIGN(4);
__system_ram_data_start__ = .;
*(.system_ram)
. = ALIGN(4);
__system_ram_data_end__ = .;
} > ram_memory
__ram_load_addr = __system_ram_load_addr + SIZEOF(.system_ram_data_region);
/* Data section */
RAM_DATA : AT (__ram_load_addr)
{
. = ALIGN(4);
__ram_data_start__ = .;
PROVIDE( __global_pointer$ = . + 0x800 );
*(.data)
*(.data.*)
*(.sdata)
*(.sdata.*)
*(.sdata2)
*(.sdata2.*)
. = ALIGN(4);
__ram_data_end__ = .;
} > ram_memory
.bss (NOLOAD) :
{
. = ALIGN(4);
__bss_start__ = .;
*(.bss*)
*(.sbss*)
*(COMMON)
. = ALIGN(4);
__bss_end__ = .;
} > ram_memory
.noinit_data (NOLOAD) :
{
. = ALIGN(4);
__noinit_data_start__ = .;
*(.noinit_data*)
. = ALIGN(4);
__noinit_data_end__ = .;
} > ram_memory
.heap (NOLOAD):
{
. = ALIGN(4);
__HeapBase = .;
/*__end__ = .;*/
/*end = __end__;*/
KEEP(*(.heap*))
. = ALIGN(4);
__HeapLimit = .;
} > ram_memory
PROVIDE (__heap_min_size = 0x400);
__HeapLimit = ORIGIN(ram_memory) + LENGTH(ram_memory);
ASSERT((__HeapLimit - __HeapBase ) >= __heap_min_size, "heap size is too short.")
}

View File

@@ -19,13 +19,14 @@ ENTRY(_enter)
StackSize = 0x1000; /* 4KB */
HeapSize = 0x0; /* 0KB */
PROVIDE(__boot2_pass_param_addr = 0x42049C00);/* 0x42030000+103*1024 */
PROVIDE(__boot2_pass_param_addr = 0x4202DC00);
MEMORY
{
xip_memory (rx) : ORIGIN = 0x23000000, LENGTH = 48K
itcm_memory (rx) : ORIGIN = 0x2201c000, LENGTH = 16K
dtcm_memory (rx) : ORIGIN = 0x42020000, LENGTH = 4K
ram_memory (!rx) : ORIGIN = 0x42021000, LENGTH = 156K
xip_memory (rx) : ORIGIN = 0x23000000, LENGTH = 64K
itcm_memory (rx) : ORIGIN = 0x22014000, LENGTH = 16K
dtcm_memory (rx) : ORIGIN = 0x42018000, LENGTH = 4K
ram_memory (!rx) : ORIGIN = 0x42019000/*0x42020000*/, LENGTH = 88K
}
SECTIONS
@@ -40,7 +41,14 @@ SECTIONS
KEEP (*(.text.metal.init.enter))
KEEP (*(SORT_NONE(.init)))
*(EXCLUDE_FILE ( *bl602_uart*.o* *hal_uart*.o* ) .text*)
/* section information for usb desc */
. = ALIGN(4);
_usb_desc_start = .;
KEEP(*(usb_desc))
. = ALIGN(4);
_usb_desc_end = .;
*(EXCLUDE_FILE ( *bl702_uart*.o* *hal_uart*.o* ) .text*)
*(.rodata)
*(.rodata.*)
@@ -62,13 +70,13 @@ SECTIONS
*(.tcm_const.*)
*(.sclock_rlt_code.*)
*(.sclock_rlt_const.*)
*bl602_romapi*.o*(.text)
*bl602_romapi*.o*(.text.*)
*bl602_romapi*.o*(.rodata)
*bl602_romapi*.o*(.rodata.*)
*bl602_romapi*.o*(.srodata)
*bl602_romapi*.o*(.srodata.*)
*bl602_uart*.o* (.text*)
*bl702_romapi*.o*(.text)
*bl702_romapi*.o*(.text.*)
*bl702_romapi*.o*(.rodata)
*bl702_romapi*.o*(.rodata.*)
*bl702_romapi*.o*(.srodata)
*bl702_romapi*.o*(.srodata.*)
*bl702_uart*.o* (.text*)
*hal_uart*.o* (.text*)
. = ALIGN(4);
__tcm_code_end__ = .;
@@ -82,7 +90,7 @@ SECTIONS
. = ALIGN(4);
__tcm_data_start__ = .;
*(.tcm_data.*)
*(.tcm_data)
/* *finger_print.o(.data*) */
. = ALIGN(4);

View File

@@ -1,10 +1,11 @@
SET(CPU_ARCH "RISCV")
SET(MCPU "e24")
SET(MCPU "riscv-e24")
SET(MARCH "rv32imafc")
SET(MABI "ilp32f")
list(APPEND GLOBAL_C_FLAGS -march=${MARCH} -mabi=${MABI})
list(APPEND GLOBAL_LD_FLAGS -march=${MARCH} -mabi=${MABI})
SET(LINKER_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/bl602_flash.ld)
SET(LINKER_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/bl702_flash.ld)
SET(RAM_LINKER_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/bl702_ram.ld)
SET(BOOT2_LINKER_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/blsp_boot2_iap_flash.ld)

View File

@@ -0,0 +1,17 @@
#ifndef _ADC_CONFIG_H
#define _ADC_CONFIG_H
#define ADC_DATA_WIDIH_12 (0)
#define ADC_V18_SELECT (2) /*!< ADC 1.8V select */
#define ADC_V11_SELECT (1) /*!< ADC 1.1V select */
#define ADC_PGA_VCM (0) /*!< ADC VCM value */
#define ADC_PGA_GAIN1 (0) /*!< PGA gain 1 */
#define ADC_PGA_GAIN2 (0) /*!< PGA gain 2 */
#define ADC_CHOP_MODE (2) /*!< ADC chop mode select */
#define ADC_BIAS_SELECT (0) /*!< ADC current form main bandgap or aon bandgap */
#define ADC_OFFSET_CALIB_EN (0) /*!< Offset calibration enable */
#define ADC_OFFSER_CALIB_VAL (0) /*!< Offset calibration value */
#endif

View File

@@ -0,0 +1,7 @@
#ifndef _DAC_CONFIG_H
#define _DAC_CONFIG_H
#define DAC_REF_SEL (0)
#define DAC_EXT_REF_GPIO (7)
#endif

View File

@@ -0,0 +1,11 @@
#ifndef _I2S_CONFIG_H
#define _I2S_CONFIG_H
#define I2S_ADUIO_PLL_DEFAULT AUDIO_PLL_12288000_HZ
#define I2S_DATA_ENDIAN I2S_DATA_ENDIAN_MSB
#define I2S_MONO_CHANNEL I2S_RX_MONO_MODE_RIGHT_CHANNEL
#define I2S_LR_EXCHANGE DISABLE /*The position of L/R channel data within each entry is exchanged if enabled*/
#define I2S_FS_INVERT DISABLE
#define I2S_BCLK_INVERT DISABLE
#endif

View File

@@ -0,0 +1,16 @@
#ifndef _UART_CONFIG_H
#define _UART_CONFIG_H
#define UART_CTS_FLOWCONTROL_ENABLE (0)
#define UART_RTS_FLOWCONTROL_ENABLE (0)
#define UART_RX_DEGLITCH_ENABLE (0)
#define UART_MSB_FIRST_ENABLE (0)
#define UART_TX_SWCONTROL_ENABLE (0)
#define UART_TX_LINMODE_ENABLE (0)
#define UART_RX_LINMODE_ENABLE (0)
#define UART_TX_BREAKBIT_CNT (0)
#define UART_FIFO_MAX_LEN 128
#define UART_DEFAULT_RTO_TIMEOUT 100
#endif

View File

@@ -0,0 +1,62 @@
#ifndef __HAL_ACOMP_H__
#define __HAL_ACOMP_H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
enum acomp_channel_type {
ACOMP_CHANNEL_ADC_CHANNEL0, /*!< Analog compare channel,ADC input channel 0 */
ACOMP_CHANNEL_ADC_CHANNEL1, /*!< Analog compare channel,ADC input channel 1 */
ACOMP_CHANNEL_ADC_CHANNEL2, /*!< Analog compare channel,ADC input channel 2 */
ACOMP_CHANNEL_ADC_CHANNEL3, /*!< Analog compare channel,ADC input channel 3 */
ACOMP_CHANNEL_ADC_CHANNEL4, /*!< Analog compare channel,ADC input channel 4 */
ACOMP_CHANNEL_ADC_CHANNEL5, /*!< Analog compare channel,ADC input channel 5 */
ACOMP_CHANNEL_ADC_CHANNEL6, /*!< Analog compare channel,ADC input channel 6 */
ACOMP_CHANNEL_ADC_CHANNEL7, /*!< Analog compare channel,ADC input channel 7 */
ACOMP_CHANNEL_DAC_CHANNELA, /*!< Analog compare channel,DAC output channel A */
ACOMP_CHANNEL_DAC_CHANNELB, /*!< Analog compare channel,DAC output channel B */
ACOMP_CHANNEL_VREF_1P2V, /*!< Analog compare channel,1.2V ref voltage */
ACOMP_CHANNEL_0P375VBAT, /*!< Analog compare channel,6/16Vbat */
ACOMP_CHANNEL_0P25VBAT, /*!< Analog compare channel,4/16Vbat */
ACOMP_CHANNEL_0P1875VBAT, /*!< Analog compare channel,3/16Vbat */
ACOMP_CHANNEL_0P3125VBAT, /*!< Analog compare channel,5/16Vbat */
ACOMP_CHANNEL_VSS, /*!< Analog compare channel,vss */
};
enum acomp_hysteresis_vol_type {
ACOMP_HYSTERESIS_VOLT_NONE, /*!< Analog compare hysteresis voltage none */
ACOMP_HYSTERESIS_VOLT_10MV, /*!< Analog compare hysteresis voltage 10mv */
ACOMP_HYSTERESIS_VOLT_20MV, /*!< Analog compare hysteresis voltage 20mv */
ACOMP_HYSTERESIS_VOLT_30MV, /*!< Analog compare hysteresis voltage 30mv */
ACOMP_HYSTERESIS_VOLT_40MV, /*!< Analog compare hysteresis voltage 40mv */
ACOMP_HYSTERESIS_VOLT_50MV, /*!< Analog compare hysteresis voltage 50mv */
ACOMP_HYSTERESIS_VOLT_60MV, /*!< Analog compare hysteresis voltage 60mv */
ACOMP_HYSTERESIS_VOLT_70MV, /*!< Analog compare hysteresis voltage 70mv */
};
enum acomp_it_type {
ACOMP_POSITIVE_IT = 1 << 0,
ACOMP_NEGATIVE_IT = 1 << 1,
};
typedef struct acomp_device {
enum acomp_channel_type pos_ch;
enum acomp_channel_type neg_ch;
enum acomp_hysteresis_vol_type pos_hysteresis_vol;
enum acomp_hysteresis_vol_type neg_hysteresis_vol;
} acomp_device_t;
void acomp_init(uint8_t idx,acomp_device_t *device);
void acomp_enable(uint8_t idx);
void acomp_disable(uint8_t idx);
void acomp_interrupt_mask(uint8_t idx,uint32_t flag);
void acomp_interrupt_unmask(uint8_t idx,uint32_t flag);
int acomp_get_result(uint8_t idx);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,185 @@
/**
* @file hal_adc.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_ADC__H__
#define __HAL_ADC__H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_ADC_CHANNEL_START 0x10
#define DEVICE_CTRL_ADC_CHANNEL_STOP 0x11
#define DEVICE_CTRL_ADC_CHANNEL_CONFIG 0x12
#define DEVICE_CTRL_ADC_VBAT_ON 0x13
#define DEVICE_CTRL_ADC_VBAT_OFF 0x14
#define DEVICE_CTRL_ADC_TSEN_ON 0x15
#define DEVICE_CTRL_ADC_TSEN_OFF 0x16
#define DEVICE_CTRL_ADC_DATA_PARSE 0x17
enum adc_index_type {
#ifdef BSP_USING_ADC0
ADC0_INDEX,
#endif
ADC_MAX_INDEX
};
#define adc_channel_start(dev) device_control(dev, DEVICE_CTRL_ADC_CHANNEL_START, NULL)
#define adc_channel_stop(dev) device_control(dev, DEVICE_CTRL_ADC_CHANNEL_STOP, NULL)
#define adc_channel_config(dev, list) device_control(dev, DEVICE_CTRL_ADC_CHANNEL_CONFIG, list)
typedef enum {
ADC_CHANNEL0, /* ADC channel 0 */
ADC_CHANNEL1, /* ADC channel 1 */
ADC_CHANNEL2, /* ADC channel 2 */
ADC_CHANNEL3, /* ADC channel 3 */
ADC_CHANNEL4, /* ADC channel 4 */
ADC_CHANNEL5, /* ADC channel 5 */
ADC_CHANNEL6, /* ADC channel 6 */
ADC_CHANNEL7, /* ADC channel 7 */
ADC_CHANNEL8, /* ADC channel 8 */
ADC_CHANNEL9, /* ADC channel 9 */
ADC_CHANNEL10, /* ADC channel 10 */
ADC_CHANNEL11, /* ADC channel 11 */
ADC_CHANNEL_DAC_OUTA, /* DACA, ADC channel 12 */
ADC_CHANNEL_DAC_OUTB, /* DACB, ADC channel 13 */
ADC_CHANNEL_TSEN_P, /* TSenp, ADC channel 14 */
ADC_CHANNEL_TSEN_N, /* TSenn, ADC channel 15 */
ADC_CHANNEL_VREF, /* Vref, ADC channel 16 */
ADC_CHANNEL_DCTEST, /* DCTest, ADC channel 17 */
ADC_CHANNEL_VABT_HALF, /* VBAT/2, ADC channel 18 */
ADC_CHANNEL_SENP3, /* SenVP3, ADC channel 19 */
ADC_CHANNEL_SENP2, /* SenVP2, ADC channel 20 */
ADC_CHANNEL_SENP1, /* SenVP1, ADC channel 21 */
ADC_CHANNEL_SENP0, /* SenVP0, ADC channel 22 */
ADC_CHANNEL_GND, /* GND, ADC channel 23 */
} adc_channel_t;
typedef enum {
ADC_CLOCK_DIV_1, /*!< ADC clock:on 32M clock is 32M */
ADC_CLOCK_DIV_4, /*!< ADC clock:on 32M clock is 8M */
ADC_CLOCK_DIV_8, /*!< ADC clock:on 32M clock is 4M */
ADC_CLOCK_DIV_12, /*!< ADC clock:on 32M clock is 2.666M */
ADC_CLOCK_DIV_16, /*!< ADC clock:on 32M clock is 2M */
ADC_CLOCK_DIV_20, /*!< ADC clock:on 32M clock is 1.6M */
ADC_CLOCK_DIV_24, /*!< ADC clock:on 32M clock is 1.333M */
ADC_CLOCK_DIV_32, /*!< ADC clock:on 32M clock is 1M */
} adc_clk_div_t;
typedef enum {
ADC_VREF_3V2 = 0, /* ADC select 3.2V as reference voltage */
ADC_VREF_2V = 1, /* ADC select 2V as reference voltage */
} adc_vref_t;
/**
* @brief ADC data width type definition
*/
typedef enum {
ADC_DATA_WIDTH_12B, /*!< ADC 12 bits */
ADC_DATA_WIDTH_14B_WITH_16_AVERAGE, /*!< ADC 14 bits,and the value is average of 16 converts */
ADC_DATA_WIDTH_14B_WITH_64_AVERAGE, /*!< ADC 14 bits,and the value is average of 64 converts */
ADC_DATA_WIDTH_16B_WITH_128_AVERAGE, /*!< ADC 16 bits,and the value is average of 128 converts */
ADC_DATA_WIDTH_16B_WITH_256_AVERAGE, /*!< ADC 16 bits,and the value is average of 256 converts */
} adc_data_width_t;
/**
* @brief ADC FIFO threshold type definition
*/
typedef enum {
ADC_FIFO_THRESHOLD_1BYTE, /*!< ADC FIFO threshold is 1 */
ADC_FIFO_THRESHOLD_4BYTE, /*!< ADC FIFO threshold is 4 */
ADC_FIFO_THRESHOLD_8BYTE, /*!< ADC FIFO threshold is 8 */
ADC_FIFO_THRESHOLD_16BYTE, /*!< ADC FIFO threshold is 16 */
} adc_fifo_threshold_t;
/**
* @brief ADC PGA gain type definition
*/
typedef enum {
ADC_GAIN_NONE, /*!< No PGA gain */
ADC_GAIN_1, /*!< PGA gain 1 */
ADC_GAIN_2, /*!< PGA gain 2 */
ADC_GAIN_4, /*!< PGA gain 4 */
ADC_GAIN_8, /*!< PGA gain 8 */
ADC_GAIN_16, /*!< PGA gain 16 */
ADC_GAIN_32, /*!< PGA gain 32 */
} adc_pga_gain_t;
enum adc_event_type {
ADC_EVENT_UNDERRUN,
ADC_EVENT_OVERRUN,
ADC_EVENT_FIFO,
ADC_EVENT_UNKNOWN
};
enum adc_it_type {
ADC_UNDERRUN_IT = 1 << 2,
ADC_OVERRUN_IT = 1 << 3,
ADC_FIFO_IT = 1 << 5,
};
typedef struct {
uint8_t *pos_channel;
uint8_t *neg_channel;
uint8_t num;
} adc_channel_cfg_t;
typedef struct {
int8_t posChan; /*!< Positive channel */
int8_t negChan; /*!< Negative channel */
uint16_t value; /*!< ADC value */
float volt; /*!< ADC voltage result */
} adc_channel_val_t;
typedef struct
{
uint32_t *input;
adc_channel_val_t *output;
uint32_t num;
} adc_data_parse_t;
typedef struct adc_device {
struct device parent;
adc_clk_div_t clk_div; /* CLK is not more than 2Mhz */
adc_vref_t vref; /* ADC voltage reference*/
bool continuous_conv_mode; /** conversion mode: shot conversion mode or continuous conversion mode. */
bool differential_mode; /** Channel type: single-ended or differential. */
adc_data_width_t data_width;
adc_fifo_threshold_t fifo_threshold;
adc_pga_gain_t gain;
void *rx_dma;
} adc_device_t;
#define ADC_DEV(dev) ((adc_device_t *)dev)
int adc_register(enum adc_index_type index, const char *name);
int adc_trim_tsen(uint16_t *tsen_offset);
float adc_get_tsen(uint16_t tsen_offset);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -36,47 +36,63 @@
#ifndef __HAL_BOOT2_H__
#define __HAL_BOOT2_H__
#include "hal_common.h"
#include "bl602_sflash.h"
#include "bl602_glb.h"
#ifdef __cplusplus
extern "C"{
#endif
#define BL_TCM_BASE BL602_TCM_BASE
#define BL_SYS_CLK_PLL GLB_SYS_CLK_PLL160M
#define BL_SFLASH_CLK GLB_SFLASH_CLK_80M
#include "hal_common.h"
#include "bl702_sflash.h"
#include "bl702_glb.h"
#define BL_TCM_BASE BL702_TCM_BASE
#define BL_SYS_CLK_PLL GLB_SYS_CLK_DLL144M
#define BL_SFLASH_CLK GLB_SFLASH_CLK_72M
#define HAL_PLL_CFG_MAGICCODE "PCFG"
#define HAL_EFUSE_CPU_MAX 2
#define HAL_EFUSE_PK_HASH_SIZE 256 / 8
#define HAL_BOOT2_PK_HASH_SIZE 256 / 8
#define HAL_BOOT2_IMG_HASH_SIZE 256 / 8
#define HAL_BOOT2_ECC_KEYXSIZE 256 / 8
#define HAL_BOOT2_ECC_KEYYSIZE 256 / 8
#define HAL_BOOT2_SIGN_MAXSIZE (2048 / 8)
#define HAL_BOOT2_DEADBEEF_VAL 0xdeadbeef
#define HAL_BOOT2_CPU0_MAGIC "BFNP"
#define HAL_BOOT2_CPU1_MAGIC "BFAP"
#define HAL_BOOT2_CP_FLAG 0x02
#define HAL_BOOT2_MP_FLAG 0x01
#define HAL_BOOT2_SP_FLAG 0x00
#define HAL_BOOT2_SUPPORT_DECOMPRESS 1 /* 1 support decompress, 0 not support */
#define HAL_BOOT2_SUPPORT_USB_IAP 0 /* 1 support decompress, 0 not support */
#define HAL_BOOT2_SUPPORT_EFLASH_LOADER_RAM 1 /* 1 support decompress, 0 not support */
#define HAL_BOOT2_SUPPORT_EFLASH_LOADER_FLASH 0 /* 1 support decompress, 0 not support */
#define HAL_BOOT2_FW_IMG_OFFSET_AFTER_HEADER 4*1024
#define HAL_BOOT2_HASH_SIZE 256 / 8
#define HAL_BOOT2_ECC_KEYXSIZE 256 / 8
#define HAL_BOOT2_ECC_KEYYSIZE 256 / 8
#define HAL_BOOT2_SIGN_MAXSIZE 2048 / 8
#define HAL_BOOT2_DEADBEEF_VAL 0xdeadbeef
#define HAL_BOOT2_CPU_GROUP_MAX 1
#define HAL_BOOT2_CPU_MAX 1
#define HAL_BOOT2_RAM_IMG_COUNT_MAX 0
#define HAL_BOOT2_CPU0_MAGIC "BFNP"
#define HAL_BOOT2_CPU1_MAGIC "BFAP"
#define HAL_BOOT2_FW_IMG_OFFSET_AFTER_HEADER 4*1024
typedef struct
{
uint8_t encrypted[HAL_EFUSE_CPU_MAX];
uint8_t sign[HAL_EFUSE_CPU_MAX];
uint8_t encrypted[HAL_BOOT2_CPU_GROUP_MAX];
uint8_t sign[HAL_BOOT2_CPU_GROUP_MAX];
uint8_t hbn_check_sign;
uint8_t rsvd[3];
uint8_t rsvd[1];
uint8_t chip_id[8];
uint8_t pk_hash_cpu0[HAL_EFUSE_PK_HASH_SIZE];
uint8_t pk_hash_cpu1[HAL_EFUSE_PK_HASH_SIZE];
uint8_t pk_hash_cpu0[HAL_BOOT2_PK_HASH_SIZE];
uint8_t pk_hash_cpu1[HAL_BOOT2_PK_HASH_SIZE];
uint8_t uart_download_cfg;
uint8_t sf_pin_cfg;
uint8_t keep_dbg_port_closed;
uint8_t boot_pin_cfg;
} boot2_efuse_hw_config;
struct __attribute__((packed, aligned(4))) hal_flash_config
{
uint32_t magicCode; /*'FCFG'*/
SPI_Flash_Cfg_Type cfg;
uint32_t crc32;
} ;
typedef struct
{
uint8_t xtal_type;
@@ -96,115 +112,124 @@ typedef struct
uint32_t crc32;
} hal_pll_config;
typedef struct
{
uint32_t magicCode; /*'FCFG'*/
SPI_Flash_Cfg_Type cfg;
uint32_t crc32;
} hal_flash_config;
struct __attribute__((packed, aligned(4))) hal_basic_cfg_t {
uint32_t sign_type : 2; /* [1: 0] for sign */
uint32_t encrypt_type : 2; /* [3: 2] for encrypt */
uint32_t key_sel : 2; /* [5: 4] key slot */
uint32_t xts_mode : 1; /* [6] for xts mode */
uint32_t aes_region_lock : 1; /* [7] rsvd */
uint32_t no_segment : 1; /* [8] no segment info */
uint32_t boot2_enable : 1; /* [9] boot2 enable */
uint32_t boot2_rollback : 1; /* [10] boot2 rollback */
uint32_t cpu_master_id : 4; /* [14: 11] master id */
uint32_t notload_in_bootrom : 1; /* [15] notload in bootrom */
uint32_t crc_ignore : 1; /* [16] ignore crc */
uint32_t hash_ignore : 1; /* [17] hash ignore */
uint32_t power_on_mm : 1; /* [18] power on mm */
uint32_t em_sel : 3; /* [21: 19] em_sel */
uint32_t cmds_en : 1; /* [22] command spliter enable */
uint32_t cmds_wrap_mode : 2; /* [24: 23] cmds wrap mode */
uint32_t cmds_wrap_len : 4; /* [28: 25] cmds wrap len */
uint32_t icache_invalid : 1; /* [29] icache invalid */
uint32_t dcache_invalid : 1; /* [30] dcache invalid */
uint32_t fpga_halt_release : 1; /* [31] FPGA halt release function */
uint32_t group_image_offset; /* flash controller offset */
uint32_t aes_region_len; /* aes region length */
uint32_t img_len_cnt; /* image length or segment count */
uint32_t hash[8]; /* hash of the image */
};
struct __attribute__((packed, aligned(4))) hal_cpu_cfg_t {
uint8_t config_enable; /* coinfig this cpu */
uint8_t halt_cpu; /* halt this cpu */
uint8_t cache_enable : 1; /* cache setting */
uint8_t cache_wa : 1; /* cache setting */
uint8_t cache_wb : 1; /* cache setting */
uint8_t cache_wt : 1; /* cache setting */
uint8_t cache_way_dis : 4; /* cache setting */
uint8_t rsvd;
uint32_t image_address_offset; /* image address on flash */
uint32_t boot_entry; /* entry point of the m0 image */
uint32_t msp_val; /* msp value */
};
struct hal_bootheader_t
{
uint32_t magicCode; /*'BFXP'*/
uint32_t rivison;
hal_flash_config flash_cfg;
hal_pll_config clk_cfg;
__PACKED_UNION
{
__PACKED_STRUCT
{
uint32_t sign : 2; /* [1: 0] for sign*/
uint32_t encrypt_type : 2; /* [3: 2] for encrypt */
uint32_t key_sel : 2; /* [5: 4] for key sel in boot interface*/
uint32_t rsvd6_7 : 2; /* [7: 6] for encrypt*/
uint32_t no_segment : 1; /* [8] no segment info */
uint32_t cache_enable : 1; /* [9] for cache */
uint32_t notLoadInBoot : 1; /* [10] not load this img in bootrom */
uint32_t aes_region_lock : 1; /* [11] aes region lock */
uint32_t cache_way_disable : 4; /* [15: 12] cache way disable info*/
uint32_t crcIgnore : 1; /* [16] ignore crc */
uint32_t hash_ignore : 1; /* [17] hash crc */
uint32_t halt_cpu1 : 1; /* [18] halt ap */
uint32_t rsvd19_31 : 13; /* [31:19] rsvd */
}
bval;
uint32_t wval;
}
bootCfg;
__PACKED_UNION
{
uint32_t segment_cnt;
uint32_t img_len;
}
img_segment_info;
uint32_t bootEntry; /* entry point of the image*/
__PACKED_UNION
{
uint32_t ram_addr;
uint32_t flash_offset;
}
img_start;
uint8_t hash[HAL_BOOT2_HASH_SIZE]; /*hash of the image*/
uint32_t rsv1;
uint32_t rsv2;
uint32_t crc32;
{
uint32_t magicCode; /*'BFXP'*/
uint32_t rivison;
struct hal_flash_config flash_cfg;
hal_pll_config clk_cfg;
__PACKED_UNION
{
__PACKED_STRUCT
{
uint32_t sign : 2; /* [1: 0] for sign*/
uint32_t encrypt_type : 2; /* [3: 2] for encrypt */
uint32_t key_sel : 2; /* [5: 4] for key sel in boot interface*/
uint32_t rsvd6_7 : 2; /* [7: 6] for encrypt*/
uint32_t no_segment : 1; /* [8] no segment info */
uint32_t cache_enable : 1; /* [9] for cache */
uint32_t notLoadInBoot : 1; /* [10] not load this img in bootrom */
uint32_t aes_region_lock : 1; /* [11] aes region lock */
uint32_t cache_way_disable : 4; /* [15: 12] cache way disable info*/
uint32_t crcIgnore : 1; /* [16] ignore crc */
uint32_t hash_ignore : 1; /* [17] hash crc */
uint32_t halt_cpu1 : 1; /* [18] halt ap */
uint32_t rsvd19_31 : 13; /* [31:19] rsvd */
}
bval;
uint32_t wval;
}
bootCfg;
__PACKED_UNION
{
uint32_t segment_cnt;
uint32_t img_len;
}
img_segment_info;
uint32_t bootEntry; /* entry point of the image*/
__PACKED_UNION
{
uint32_t ram_addr;
uint32_t flash_offset;
}
img_start;
uint8_t hash[HAL_BOOT2_IMG_HASH_SIZE]; /*hash of the image*/
uint32_t rsv1;
uint32_t rsv2;
uint32_t crc32;
} ;
typedef struct
{
uint8_t encrypt_type;
uint8_t sign_type;
uint8_t key_sel;
uint8_t img_valid;
uint8_t no_segment;
uint8_t cache_enable;
uint8_t cache_way_disable;
uint8_t hash_ignore;
uint8_t aes_region_lock;
uint8_t halt_cpu1;
uint8_t cpu_type;
uint8_t r[1];
__PACKED_UNION
{
uint32_t segment_cnt;
uint32_t img_len;
}
img_segment_info;
uint32_t msp_val;
uint32_t entry_point;
__PACKED_UNION
{
uint32_t ram_addr;
uint32_t flash_offset;
}
img_start;
uint32_t sig_len;
uint32_t sig_len2;
uint32_t deal_len;
uint32_t max_input_len;
uint8_t img_hash[HAL_BOOT2_HASH_SIZE]; //hash of the whole (all)images
uint8_t aes_iv[16 + 4]; //iv in boot header
uint8_t eckye_x[HAL_BOOT2_ECC_KEYXSIZE]; //ec key in boot header
uint8_t eckey_y[HAL_BOOT2_ECC_KEYYSIZE]; //ec key in boot header
uint8_t eckey_x2[HAL_BOOT2_ECC_KEYXSIZE]; //ec key in boot header
uint8_t eckey_y2[HAL_BOOT2_ECC_KEYYSIZE]; //ec key in boot header
uint8_t signature[HAL_BOOT2_SIGN_MAXSIZE]; //signature in boot header
uint8_t signature2[HAL_BOOT2_SIGN_MAXSIZE]; //signature in boot header
} boot2_image_config;
typedef struct
{
uint8_t img_valid;
uint8_t pk_src;
uint8_t rsvd[2];
struct hal_basic_cfg_t basic_cfg;
struct hal_cpu_cfg_t cpu_cfg[HAL_BOOT2_CPU_MAX];
uint8_t aes_iv[16 + 4]; //iv in boot header
uint8_t eckye_x[HAL_BOOT2_ECC_KEYXSIZE]; //ec key in boot header
uint8_t eckey_y[HAL_BOOT2_ECC_KEYYSIZE]; //ec key in boot header
uint8_t eckey_x2[HAL_BOOT2_ECC_KEYXSIZE]; //ec key in boot header
uint8_t eckey_y2[HAL_BOOT2_ECC_KEYYSIZE]; //ec key in boot header
uint8_t signature[HAL_BOOT2_SIGN_MAXSIZE]; //signature in boot header
uint8_t signature2[HAL_BOOT2_SIGN_MAXSIZE]; //signature in boot header
} boot2_image_config;
extern boot2_efuse_hw_config g_efuse_cfg;
extern uint8_t g_ps_mode;
@@ -212,6 +237,8 @@ extern uint32_t g_user_hash_ignored;
extern struct device *dev_check_hash;
uint32_t hal_boot2_custom(void);
void hal_boot2_reset_sec_eng(void);
void hal_boot2_sw_system_reset(void);
@@ -224,8 +251,23 @@ int32_t hal_boot2_get_clk_cfg(hal_pll_config *cfg);
void hal_boot2_sboot_finish(void);
void hal_boot2_uart_gpio_init(void);
void hal_boot2_debug_uart_gpio_init(void);
#if HAL_BOOT2_SUPPORT_USB_IAP
void hal_boot2_debug_usb_port_init(void);
#endif
void hal_boot2_debug_uart_gpio_deinit(void);
int32_t hal_boot_parse_bootheader(boot2_image_config *boot_img_cfg, uint8_t *data);
void hal_boot2_clean_cache(void);
BL_Err_Type hal_boot2_set_cache(uint8_t cont_read, boot2_image_config *boot_img_cfg);
void hal_boot2_get_ram_img_cnt(char* img_name[],uint32_t *ram_img_cnt );
void hal_boot2_get_img_info(uint8_t *data, uint32_t *image_offset, uint32_t *img_len,uint8_t **hash);
void hal_boot2_release_cpu(uint32_t core, uint32_t boot_addr);
uint32_t hal_boot2_get_xip_addr(uint32_t flash_addr);
uint32_t hal_boot2_get_grp_count(void);
uint32_t hal_boot2_get_cpu_count(void);
uint32_t hal_boot2_get_feature_flag(void);
uint32_t hal_boot2_get_bootheader_offset(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,112 @@
/**
* @file hal_cam.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_CAM_H__
#define __HAL_CAM_H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_CAM_FRAME_CUT 0x10
#define DEVICE_CTRL_CAM_FRAME_DROP 0x11
#define DEVICE_CTRL_CAM_FRAME_WRAP 0x12
enum cam_index_type {
#ifdef BSP_USING_CAM0
CAM0_INDEX,
#endif
CAM_MAX_INDEX
};
#define CAM_AUTO_MODE 0
#define CAM_MANUAL_MODE 1
#define CAM_FRAME_PLANAR_MODE 0
#define CAM_FRAME_INTERLEAVE_MODE 1
#define CAM_HSPOLARITY_LOW 0
#define CAM_HSPOLARITY_HIGH 1
#define CAM_VSPOLARITY_LOW 0
#define CAM_VSPOLARITY_HIGH 1
#define CAM_YUV_FORMAT_YUV422 0
#define CAM_YUV_FORMAT_YUV420_EVEN 1
#define CAM_YUV_FORMAT_YUV420_ODD 2
#define CAM_YUV_FORMAT_YUV400_EVEN 3
#define CAM_YUV_FORMAT_YUV400_ODD 4
enum cam_it_type {
CAM_FRAME_IT = 1 << 0,
};
enum cam_event_type {
CAM_EVENT_FRAME = 0,
};
typedef struct {
int16_t x0;
int16_t x1;
int16_t y0;
int16_t y1;
} cam_frame_area_t;
typedef struct {
uint32_t frame_addr;
uint32_t frame_count;
} cam_frame_info_t;
typedef struct cam_device {
struct device parent;
uint8_t id;
uint8_t software_mode;
uint8_t frame_mode;
uint8_t yuv_format;
uint8_t hsp;
uint8_t vsp;
uint32_t cam_write_ram_addr;
uint32_t cam_write_ram_size;
uint32_t cam_frame_size;
// planar mode need use:
uint32_t cam_write_ram_addr1;
uint32_t cam_write_ram_size1;
uint32_t cam_frame_size1;
} cam_device_t;
#define CAM_DEV(dev) ((cam_device_t *)dev)
int cam_register(enum cam_index_type index, const char *name);
void cam_drop_one_frame_interleave(void);
uint8_t cam_get_one_frame_interleave(uint8_t **pic, uint32_t *len);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -2,7 +2,7 @@
* @file hal_clock.h
* @brief
*
* Copyright 2019-2030 Bouffalolab team
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
@@ -23,42 +23,51 @@
#ifndef __HAL_CLOCK__H__
#define __HAL_CLOCK__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "bl602_config.h"
#include "bl702_config.h"
/*XTAL_TYPE*/
#define XTAL_NONE 0
#define EXTERNAL_XTAL_24M 1
#define EXTERNAL_XTAL_32M 2
#define EXTERNAL_XTAL_38P4M 3
#define EXTERNAL_XTAL_40M 4
#define EXTERNAL_XTAL_26M 5
#define INTERNAL_RC_32M 6
#define XTAL_NONE 0
#define EXTERNAL_XTAL_32M 1
#define INTERNAL_RC_32M 2
/*CLOCK_32K_XTAL*/
#define EXTERNAL_XTAL_32K 1
#define INTERNAL_RC_32K 0
#define EXTERNAL_XTAL_32K 0
#define INTERNAL_RC_32K 1
/*BSP_ROOT_CLOCK_SOURCE*/
#if (XTAL_TYPE == INTERNAL_RC_32M) || (XTAL_TYPE == XTAL_NONE)
#if XTAL_TYPE != EXTERNAL_XTAL_32M
#define ROOT_CLOCK_SOURCE_XCLK 0
#else
#define ROOT_CLOCK_SOURCE_XCLK 1
#endif
#define ROOT_CLOCK_SOURCE_PLL_48M 2
#define ROOT_CLOCK_SOURCE_PLL_120M 3
#define ROOT_CLOCK_SOURCE_PLL_160M 4
#define ROOT_CLOCK_SOURCE_PLL_192M 5
#define ROOT_CLOCK_SOURCE_PLL_57P6M 2
#define ROOT_CLOCK_SOURCE_PLL_96M 3
#define ROOT_CLOCK_SOURCE_PLL_144M 4
/*BSP_XXX_CLOCK_SOURCE*/
#define ROOT_CLOCK_SOURCE_FCLK 6
#define ROOT_CLOCK_SOURCE_BCLK 7
#define ROOT_CLOCK_SOURCE_32K_CLK 5
#define ROOT_CLOCK_SOURCE_FCLK 6
#define ROOT_CLOCK_SOURCE_BCLK 7
#define ROOT_CLOCK_SOURCE_1K_CLK 8
/*BSP_AUDIO_PLL_CLOCK_SOURCE*/
#define ROOT_CLOCK_SOURCE_AUPLL_12288000_HZ 9
#define ROOT_CLOCK_SOURCE_AUPLL_11289600_HZ 10
#define ROOT_CLOCK_SOURCE_AUPLL_5644800_HZ 11
#define ROOT_CLOCK_SOURCE_AUPLL_24576000_HZ 12
#define ROOT_CLOCK_SOURCE_AUPLL_24000000_HZ 13
enum system_clock_type {
SYSTEM_CLOCK_ROOT_CLOCK = 0,
SYSTEM_CLOCK_FCLK,
SYSTEM_CLOCK_BCLK,
SYSTEM_CLOCK_XCLK,
SYSTEM_CLOCK_ROOT_CLOCK = 0, /* clock source before fclk_div*/
SYSTEM_CLOCK_FCLK, /* clock source after fclk_div*/
SYSTEM_CLOCK_BCLK, /* clock source after bclk_div*/
SYSTEM_CLOCK_XCLK, /* xtal clock*/
SYSTEM_CLOCK_32K_CLK,
SYSTEM_CLOCK_AUPLL,
};
enum peripheral_clock_type {
PERIPHERAL_CLOCK_UART = 0,
@@ -66,12 +75,21 @@ enum peripheral_clock_type {
PERIPHERAL_CLOCK_I2C,
PERIPHERAL_CLOCK_ADC,
PERIPHERAL_CLOCK_DAC,
PERIPHERAL_CLOCK_I2S,
PERIPHERAL_CLOCK_PWM,
PERIPHERAL_CLOCK_CAM,
PERIPHERAL_CLOCK_TIMER0,
PERIPHERAL_CLOCK_TIMER1,
PERIPHERAL_CLOCK_WDT,
};
void system_clock_init(void);
void system_mtimer_clock_init(void);
void system_mtimer_clock_reinit(void);
void peripheral_clock_init(void);
uint32_t system_clock_get(enum system_clock_type type);
uint32_t peripheral_clock_get(enum peripheral_clock_type type);
void system_mtimer_clock_init(void);
void system_mtimer_clock_reinit(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -23,7 +23,11 @@
#ifndef __HAL_COMMON__H__
#define __HAL_COMMON__H__
#include "bl602_common.h"
#ifdef __cplusplus
extern "C" {
#endif
#include "bl702_common.h"
void cpu_global_irq_enable(void);
void cpu_global_irq_disable(void);
@@ -31,5 +35,12 @@ void hal_por_reset(void);
void hal_system_reset(void);
void hal_cpu_reset(void);
void hal_get_chip_id(uint8_t chip_id[8]);
void hal_enter_usb_iap(void);
void hal_jump2app(uint32_t flash_offset);
int hal_get_trng_seed(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -29,7 +29,7 @@ extern "C" {
#include "hal_common.h"
#include "drv_device.h"
#include "bl602_config.h"
#include "bl702_config.h"
enum dac_index_type {
#ifdef BSP_USING_DAC0
@@ -55,17 +55,6 @@ enum dac_sample_frequence {
DAC_SAMPLE_FREQ_500KHZ,
};
/**
* @brief DAC clock divider type definition
*/
typedef enum {
DAC_CLK_DIV_16, /*!< ADC clock:on 32M clock is 2M */
DAC_CLK_DIV_32, /*!< ADC clock:on 32M clock is 1M */
DAC_CLK_DIV_RESERVE, /*!< reserved */
DAC_CLK_DIV_64, /*!< ADC clock:on 32M clock is 0.5M */
DAC_CLK_DIV_1, /*!< ADC clock:on 32M clock is 32M */
} DAC_CLK_Type;
typedef struct dac_device {
struct device parent;
enum dac_sample_frequence sample_freq;

View File

@@ -23,9 +23,13 @@
#ifndef __HAL_DMA__H__
#define __HAL_DMA__H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl602_config.h"
#include "bl702_config.h"
#define DEVICE_CTRL_DMA_CHANNEL_GET_STATUS 0x10
#define DEVICE_CTRL_DMA_CHANNEL_START 0x11
@@ -92,7 +96,7 @@ enum dma_index_type {
#define DMA_ADDR_SPI_RDR (0x4000A200 + 0x8C)
#define DMA_ADDR_I2S_TDR (0x4000AA00 + 0x88)
#define DMA_ADDR_I2S_RDR (0x4000AA00 + 0x8C)
#define DMA_ADDR_ADC0_DR (0x40002000 + 0x04)
#define DMA_ADDR_ADC_RDR (0x40002000 + 0x04)
#define DMA_ADDR_DAC_TDR (0x40002000 + 0X48)
#define DMA_REQUEST_NONE 0x00000000 /*!< DMA request peripheral:None */
@@ -108,6 +112,14 @@ enum dma_index_type {
#define DMA_REQUEST_I2S_TX 0x00000015 /*!< DMA request peripheral:I2S TX */
#define DMA_REQUEST_ADC0 0x00000016 /*!< DMA request peripheral:ADC0 */
#define DMA_REQUEST_DAC0 0x00000017 /*!< DMA request peripheral:DAC0 */
#define DMA_REQUEST_USB_EP0 0x00000018 /*!< DMA request peripheral:USB EP0*/
#define DMA_REQUEST_USB_EP1 0x00000019 /*!< DMA request peripheral:USB EP1*/
#define DMA_REQUEST_USB_EP2 0x0000001A /*!< DMA request peripheral:USB EP2*/
#define DMA_REQUEST_USB_EP3 0x0000001B /*!< DMA request peripheral:USB EP3*/
#define DMA_REQUEST_USB_EP4 0x0000001C /*!< DMA request peripheral:USB EP4*/
#define DMA_REQUEST_USB_EP5 0x0000001D /*!< DMA request peripheral:USB EP5*/
#define DMA_REQUEST_USB_EP6 0x0000001E /*!< DMA request peripheral:USB EP6*/
#define DMA_REQUEST_USB_EP7 0x0000001F /*!< DMA request peripheral:USB EP7 */
/**
* @brief DMA transfer direction type definition
@@ -171,4 +183,8 @@ int dma_register(enum dma_index_type index, const char *name);
int dma_allocate_register(const char *name);
int dma_reload(struct device *dev, uint32_t src_addr, uint32_t dst_addr, uint32_t transfer_size);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,110 @@
/**
* @file hal_emac.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_EMAC_H__
#define __HAL_EMAC_H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#include "bl702_emac.h"
typedef struct emac_device {
struct device parent;
uint8_t mac_addr[6]; /*!< mac address */
} emac_device_t;
/**
* @brief EMAC PHY configuration type definition
*/
typedef struct
{
uint8_t auto_negotiation; /*!< Speed and mode auto negotiation */
uint8_t full_duplex; /*!< Duplex mode */
#define PHY_STATE_DOWN (0) /* PHY is not usable */
#define PHY_STATE_READY (1) /* PHY is OK, wait for controller */
#define PHY_STATE_UP (2) /* Network is ready for TX/RX */
#define PHY_STATE_RUNNING (3) /* working */
#define PHY_STATE_NOLINK (4) /* no cable connected */
#define PHY_STATE_STOPPED (5) /* PHY has been stopped */
#define PHY_STATE_TESTING (6) /* in test mode */
uint8_t phy_state; /*!< down,ready,up,running,nolink,halted */
uint16_t speed; /*!< Speed mode */
uint16_t phy_address; /*!< PHY address */
uint32_t phy_id; /*!< PHY OUI */
} emac_phy_cfg_t;
#define FULL_PACKET (uint32_t)(-1)
#define NOFULL_PACKET (uint32_t)(0)
#ifndef ETH_TX_BUFFER_SIZE
#define ETH_TX_BUFFER_SIZE (ETH_MAX_PACKET_SIZE)
#endif
#ifndef ETH_RX_BUFFER_SIZE
#define ETH_RX_BUFFER_SIZE (ETH_MAX_PACKET_SIZE)
#endif
#define EMAC_TX_COMMON_FLAGS (EMAC_BD_FIELD_MSK(TX_RD) | \
EMAC_BD_FIELD_MSK(TX_IRQ) | \
EMAC_BD_FIELD_MSK(TX_PAD) | \
EMAC_BD_FIELD_MSK(TX_CRC))
#define EMAC_RX_COMMON_FLAGS (ETH_MAX_PACKET_SIZE << 16) | \
EMAC_BD_FIELD_MSK(RX_IRQ) )
typedef enum _BD_TYPE_ {
EMAC_BD_TYPE_INVLAID,
EMAC_BD_TYPE_TX,
EMAC_BD_TYPE_RX,
EMAC_BD_TYPE_NONE,
EMAC_BD_TYPE_MAX = 0x7FFFFFFF
} EMAC_BD_TYPE_e;
int emac_init(emac_device_t *emac_cfg);
int emac_bd_init(uint8_t *ethTxBuff, uint8_t txBufCount, uint8_t *ethRxBuff, uint8_t rxBufCount);
int emac_bd_tx_enqueue(uint32_t flags, uint32_t len, const uint8_t *data_in);
int emac_bd_rx_dequeue(uint32_t flags, uint32_t *len, uint8_t *data_out);
__WEAK void emac_rx_done_callback_app(void);
__WEAK void emac_rx_error_callback_app(void);
__WEAK void emac_rx_busy_callback_app(void);
__WEAK void emac_tx_error_callback_app(void);
__WEAK void emac_tx_done_callback_app(void);
int emac_phy_set_address(uint16_t phyAddress);
int emac_phy_config_full_duplex(uint8_t fullDuplex);
int emac_phy_reg_read(uint16_t phyReg, uint16_t *regValue);
int emac_phy_reg_write(uint16_t phyReg, uint16_t regValue);
int emac_stop(void);
int emac_start(void);
int emac_start_tx(void);
int emac_stop_tx(void);
int emac_start_rx(void);
int emac_stop_rx(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -23,11 +23,16 @@
#ifndef __HAL_FLASH__H__
#define __HAL_FLASH__H__
#include "hal_common.h"
#include "bl602_sflash.h"
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "bl702_sflash.h"
#include "bl702_sflash_ext.h"
#define BL_FLASH_XIP_BASE BL602_FLASH_XIP_BASE
#define FLASH_NOT_DETECT 0x10
#define BL_FLASH_XIP_BASE BL702_FLASH_XIP_BASE
uint32_t flash_get_jedecid(void);
BL_Err_Type flash_init(void);
@@ -38,5 +43,8 @@ BL_Err_Type flash_write(uint32_t addr, uint8_t *data, uint32_t len);
BL_Err_Type flash_erase(uint32_t startaddr, uint32_t len);
BL_Err_Type flash_set_cache(uint8_t cont_read, uint8_t cache_enable, uint8_t cache_way_disable, uint32_t flash_offset);
BL_Err_Type flash_get_cfg(uint8_t **cfg_addr, uint32_t *len);
BL_Err_Type flash_write_protect_set(SFlash_Protect_Kh25v40_Type protect);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,96 @@
/**
* @file hal_gpio.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_GPIO__H__
#define __HAL_GPIO__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
enum gpio_pin_type {
GPIO_PIN_0 = 0,
GPIO_PIN_1,
GPIO_PIN_2,
GPIO_PIN_3,
GPIO_PIN_4,
GPIO_PIN_5,
GPIO_PIN_6,
GPIO_PIN_7,
GPIO_PIN_8,
GPIO_PIN_9,
GPIO_PIN_10,
GPIO_PIN_11,
GPIO_PIN_12,
GPIO_PIN_13,
GPIO_PIN_14,
GPIO_PIN_15,
GPIO_PIN_16,
GPIO_PIN_17,
GPIO_PIN_18,
GPIO_PIN_19,
GPIO_PIN_20,
GPIO_PIN_21,
GPIO_PIN_22,
GPIO_PIN_23,
GPIO_PIN_24,
GPIO_PIN_25,
GPIO_PIN_26,
GPIO_PIN_27,
GPIO_PIN_28,
GPIO_PIN_29,
GPIO_PIN_30,
GPIO_PIN_31,
GPIO_PIN_MAX,
};
#define GPIO_OUTPUT_MODE 0
#define GPIO_OUTPUT_PP_MODE 1
#define GPIO_OUTPUT_PD_MODE 2
#define GPIO_INPUT_MODE 3
#define GPIO_INPUT_PP_MODE 4
#define GPIO_INPUT_PD_MODE 5
#define GPIO_ASYNC_RISING_TRIGER_INT_MODE 6
#define GPIO_ASYNC_FALLING_TRIGER_INT_MODE 7
#define GPIO_ASYNC_HIGH_LEVEL_INT_MODE 8
#define GPIO_ASYNC_LOW_LEVEL_INT_MODE 9
#define GPIO_SYNC_RISING_TRIGER_INT_MODE 10
#define GPIO_SYNC_FALLING_TRIGER_INT_MODE 11
#define GPIO_SYNC_HIGH_LEVEL_INT_MODE 12
#define GPIO_SYNC_LOW_LEVEL_INT_MODE 13
#define GPIO_HZ_MODE 14
void gpio_set_mode(uint32_t pin, uint32_t mode);
void gpio_write(uint32_t pin, uint32_t value);
void gpio_toggle(uint32_t pin);
int gpio_read(uint32_t pin);
void gpio_attach_irq(uint32_t pin, void (*cbfun)(uint32_t pin));
void gpio_irq_enable(uint32_t pin, uint8_t enabled);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,75 @@
/**
* @file hal_i2c.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_I2C__H__
#define __HAL_I2C__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
enum i2c_index_type {
#ifdef BSP_USING_I2C0
I2C0_INDEX,
#endif
I2C_MAX_INDEX
};
#define I2C_WR 0x0000
#define I2C_RD 0x0001
#define I2C_RW_MASK 0x0001
#define SUB_ADDR_0BYTE 0x0010
#define SUB_ADDR_1BYTE 0x0020
#define SUB_ADDR_2BYTE 0x0040
#define I2C_HW_MODE 0
#define I2C_SW_MODE 1
typedef struct i2c_msg {
uint8_t slaveaddr;
uint32_t subaddr;
uint16_t flags;
uint16_t len;
uint8_t *buf;
} i2c_msg_t;
typedef struct i2c_device {
struct device parent;
uint8_t id;
uint8_t mode;
uint32_t phase;
} i2c_device_t;
#define I2C_DEV(dev) ((i2c_device_t *)dev)
int i2c_register(enum i2c_index_type index, const char *name);
int i2c_transfer(struct device *dev, i2c_msg_t msgs[], uint32_t num);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,125 @@
/**
* @file hal_i2s.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_I2S__H__
#define __HAL_I2S__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_I2S_GET_TX_FIFO 0x10
#define DEVICE_CTRL_I2S_GET_RX_FIFO 0x11
#define DEVICE_CTRL_I2S_SET_SAMPL_FREQ 0x12
enum i2s_index_type {
#ifdef BSP_USING_I2S0
I2S0_INDEX,
#endif
I2S_MAX_INDEX
};
#define I2S_DEFAULT_RTO_TIMEOUT 15
/*!
* @brief I2S mode type settings
*
* This enumeration defines the I2S mode type
*/
typedef enum {
I2S_MODE_STD, /*!< I2S STD Mode */
I2S_MODE_LEFT, /*!< Left-Justified Mode */
I2S_MODE_RIGHT, /*!< Right-Justified Mode */
I2S_MODE_DSP_A, /*!< DSP/PCM Mode A*/
I2S_MODE_DSP_B, /*!< DSP/PCM Mode B*/
} interface_mode_t;
/*!
* @brief I2S frame size settings
*
* This enumeration defines the frame size type
*/
typedef enum {
I2S_FRAME_LEN_8 = 1, /*!< I2S frame size 8 bits */
I2S_FRAME_LEN_16 = 2, /*!< I2S frame size 16 bits */
I2S_FRAME_LEN_24 = 3, /*!< I2S frame size 24 bits */
I2S_FRAME_LEN_32 = 4, /*!< I2S frame size 32 bits */
} i2s_frame_size_t;
/*!
* @brief I2S data size settings
*
* This enumeration defines the data size type
*/
typedef enum {
I2S_DATA_LEN_8 = 1, /*!< I2S data size 8 bits */
I2S_DATA_LEN_16 = 2, /*!< I2S data size 16 bits */
I2S_DATA_LEN_24 = 3, /*!< I2S data size 24 bits */
I2S_DATA_LEN_32 = 4, /*!< I2S data size 32 bits */
} i2s_data_size_t;
/*!
* @brief I2S frame channel settings
*
* This enumeration defines the frame channel mode type
*/
typedef enum {
I2S_FS_CHANNELS_NUM_MONO = 1, /*!< I2S frame is for 1 channels */
I2S_FS_CHANNELS_NUM_2 = 2, /*!< I2S frame is for 2 channels */
I2S_FS_CHANNELS_NUM_3 = 3, /*!< I2S frame is for 3 channels, DSP mode only, frame_size must equal data_size*/
I2S_FS_CHANNELS_NUM_4 = 4, /*!< I2S frame is for 4 channels, DSP mode only, frame_size must equal data_size*/
} i2s_channel_num_t;
typedef enum {
I2S_MODE_MASTER = 0, /*!< I2S as master */
I2S_MODE_SLAVE, /*!< I2S as slave */
} i2s_mode_t;
typedef struct i2s_device {
struct device parent;
uint8_t id;
i2s_mode_t iis_mode;
interface_mode_t interface_mode;
uint32_t sampl_freq_hz; /*!< I2S sample data frequency in Hz */
i2s_channel_num_t channel_num;
i2s_frame_size_t frame_size;
i2s_data_size_t data_size;
uint8_t fifo_threshold; /*!< I2S receive and transmit threshold*/
void *tx_dma;
void *rx_dma;
} i2s_device_t;
#define I2S_DEV(dev) ((i2s_device_t *)dev)
int i2s_register(enum i2s_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,97 @@
/**
* @file hal_keyscan.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_KEYSCAN__H__
#define __HAL_KEYSCAN__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_KEYSCAN_GET_KEYCODE 0x10
enum keyscan_index_type {
#ifdef BSP_USING_KEYSCAN
KEYSCAN_INDEX,
#endif
KEYSCAN_MAX_INDEX
};
enum col_num_type {
COL_NUM_1 = 1,
COL_NUM_2,
COL_NUM_3,
COL_NUM_4,
COL_NUM_5,
COL_NUM_6,
COL_NUM_7,
COL_NUM_8,
COL_NUM_9,
COL_NUM_10,
COL_NUM_11,
COL_NUM_12,
COL_NUM_13,
COL_NUM_14,
COL_NUM_15,
COL_NUM_16,
COL_NUM_17,
COL_NUM_18,
COL_NUM_19,
COL_NUM_20
};
enum row_num_type {
ROW_NUM_1 = 1,
ROW_NUM_2,
ROW_NUM_3,
ROW_NUM_4,
ROW_NUM_5,
ROW_NUM_6,
ROW_NUM_7,
ROW_NUM_8,
};
enum keyscan_event_type {
KEYSCAN_EVENT_TRIG,
KEYSCAN_EVENT_UNKNOWN
};
typedef struct keyscan_device {
struct device parent;
enum col_num_type col_num;
enum row_num_type row_num;
uint8_t deglitch_count;
} keyscan_device_t;
#define KEYSCAN_DEV(dev) ((keyscan_device_t *)dev)
int keyscan_register(enum keyscan_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,77 @@
/**
* @file hal_mjpeg.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_MJPEG__H__
#define __HAL_MJPEG__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define MJPEG_PACKET_ADD_NONE 0
#define MJPEG_PACKET_ADD_DEFAULT 1 << 0
#define MJPEG_PACKET_ADD_FRAME_HEAD 1 << 1
#define MJPEG_PACKET_ADD_FRAME_TAIL 1 << 2
#define MJPEG_PACKET_ADD_END_TAIL 1 << 3
/**
* @brief MJPEG YUV format definition
*/
typedef enum {
MJPEG_YUV_FORMAT_YUV420, /*!< MJPEG YUV420 planar mode */
MJPEG_YUV_FORMAT_YUV400, /*!< MJPEG YUV400 grey scale mode */
MJPEG_YUV_FORMAT_YUV422_PLANAR, /*!< MJPEG YUV422 planar mode */
MJPEG_YUV_FORMAT_YUV422_INTERLEAVE, /*!< MJPEG YUV422 interleave mode */
} mjpeg_yuv_format_t;
typedef struct mjpeg_device {
struct device parent;
uint8_t quality;
mjpeg_yuv_format_t yuv_format;
uint32_t write_buffer_addr; /*!< MJPEG buffer addr */
uint32_t write_buffer_size; /*!< MJPEG buffer size */
uint32_t read_buffer_addr;
uint32_t read_buffer_size;
uint16_t resolution_x; /*!< CAM RESOLUTION X */
uint16_t resolution_y; /*!< CAM RESOLUTION Y */
uint8_t packet_cut_mode;
uint16_t frame_head_length;
uint16_t packet_head_length;
uint16_t packet_body_length;
uint16_t packet_tail_length;
} mjpeg_device_t;
void mjpeg_init(mjpeg_device_t *mjpeg_cfg);
void mjpeg_start(void);
void mjpeg_stop(void);
uint8_t mjpeg_get_one_frame(uint8_t **pic, uint32_t *len, uint8_t *q);
void mjpeg_drop_one_frame(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,42 @@
/**
* @file hal_mtimer.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_MTIMER__H__
#define __HAL_MTIMER__H__
#include "stdint.h"
#ifdef __cplusplus
extern "C"{
#endif
void mtimer_set_alarm_time(uint64_t ticks, void (*interruptfun)(void));
uint64_t mtimer_get_time_ms();
uint64_t mtimer_get_time_us();
void mtimer_delay_ms(uint32_t time);
void mtimer_delay_us(uint32_t time);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,75 @@
/**
* @file hal_pm.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_PM__H__
#define __HAL_PM__H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
enum pm_pds_sleep_level {
PM_PDS_LEVEL_0,
PM_PDS_LEVEL_1,
PM_PDS_LEVEL_2,
PM_PDS_LEVEL_3,
PM_PDS_LEVEL_4, /*do not recommend to use*/
PM_PDS_LEVEL_5, /*do not recommend to use*/
PM_PDS_LEVEL_6, /*do not recommend to use*/
PM_PDS_LEVEL_7, /*do not recommend to use*/
PM_PDS_LEVEL_31 = 31,
};
enum pm_hbn_sleep_level {
PM_HBN_LEVEL_0,
PM_HBN_LEVEL_1,
PM_HBN_LEVEL_2,
};
enum pm_event_type {
PM_HBN_WAKEUP_EVENT_NONE,
PM_HBN_GPIO9_WAKEUP_EVENT,
PM_HBN_GPIO10_WAKEUP_EVENT,
PM_HBN_GPIO11_WAKEUP_EVENT,
PM_HBN_GPIO12_WAKEUP_EVENT,
PM_HBN_RTC_WAKEUP_EVENT,
PM_HBN_BOR_WAKEUP_EVENT,
PM_HBN_ACOMP0_WAKEUP_EVENT,
PM_HBN_ACOMP1_WAKEUP_EVENT,
};
void pm_pds_mode_enter(enum pm_pds_sleep_level pds_level, uint32_t sleep_time);
void pm_hbn_mode_enter(enum pm_hbn_sleep_level hbn_level, uint8_t sleep_time);
void pm_hbn_enter_again(bool reset);
void pm_set_wakeup_callback(void (*wakeup_callback)(void));
enum pm_event_type pm_get_wakeup_event(void);
void pm_bor_init(void);
void pm_hbn_out0_irq_register(void);
void pm_hbn_out1_irq_register(void);
void pm_irq_callback(enum pm_event_type event);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,33 @@
/**
* @file hal_pm_util.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_PM_UTIL_H__
#define __HAL_PM_UTIL_H__
#include "hal_common.h"
#define ATTR_PDS_RAM_SECTION __attribute__((section(".pds_ram_code")))
#define ATTR_PDS_RAM_CONST_SECTION __attribute__((section(".pds_ram_data")))
uint32_t hal_pds_enter_with_time_compensation(uint32_t pdsLevel, uint32_t pdsSleepCycles);
void pm_set_hardware_recovery_callback(void (*hardware_recovery_cb)(void));
#endif

View File

@@ -0,0 +1,90 @@
/**
* @file hal_pwm.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_PWM__H__
#define __HAL_PWM__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_PWM_FREQUENCE_CONFIG 0x10
#define DEVICE_CTRL_PWM_DUTYCYCLE_CONFIG 0x11
#define DEVICE_CTRL_PWM_IT_PULSE_COUNT_CONFIG 0x12
enum pwm_index_type {
#ifdef BSP_USING_PWM_CH0
PWM_CH0_INDEX,
#endif
#ifdef BSP_USING_PWM_CH1
PWM_CH1_INDEX,
#endif
#ifdef BSP_USING_PWM_CH2
PWM_CH2_INDEX,
#endif
#ifdef BSP_USING_PWM_CH3
PWM_CH3_INDEX,
#endif
#ifdef BSP_USING_PWM_CH4
PWM_CH4_INDEX,
#endif
PWM_MAX_INDEX
};
#define pwm_channel_start(dev) device_control(dev, DEVICE_CTRL_RESUME, NULL)
#define pwm_channel_stop(dev) device_control(dev, DEVICE_CTRL_SUSPEND, NULL)
#define pwm_channel_freq_update(dev, count) device_control(dev, DEVICE_CTRL_PWM_FREQUENCE_CONFIG, (void *)count)
#define pwm_channel_dutycycle_update(dev, cfg) device_control(dev, DEVICE_CTRL_PWM_DUTYCYCLE_CONFIG, cfg)
#define pwm_it_pulse_count_update(dev, count) device_control(dev, DEVICE_CTRL_PWM_IT_PULSE_COUNT_CONFIG, (void *)count)
enum pwm_event_type {
PWM_EVENT_COMPLETE,
};
typedef struct
{
uint16_t threshold_low;
uint16_t threshold_high;
} pwm_dutycycle_config_t;
typedef struct pwm_device {
struct device parent;
uint8_t ch;
uint8_t polarity_invert_mode;
uint16_t period;
uint16_t threshold_low;
uint16_t threshold_high;
uint16_t it_pulse_count;
} pwm_device_t;
#define PWM_DEV(dev) ((pwm_device_t *)dev)
int pwm_register(enum pwm_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,83 @@
/**
* @file hal_qdec.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_QDEC__H__
#define __HAL_QDEC__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_GET_SAMPLE_VAL (0x10)
#define DEVICE_CTRL_GET_SAMPLE_DIR (0x11)
#define DEVICE_CTRL_GET_ERROR_CNT (0x12)
enum qdec_index_type {
#ifdef BSP_USING_QDEC0
QDEC0_INDEX,
#endif
#ifdef BSP_USING_QDEC1
QDEC1_INDEX,
#endif
#ifdef BSP_USING_QDEC2
QDEC2_INDEX,
#endif
QDEC_MAX_INDEX,
};
enum qdec_event_type {
QDEC_REPORT_EVENT = 1 << 0, /*!< report interrupt */
QDEC_SAMPLE_EVENT = 1 << 1, /*!< sample interrupt */
QDEC_ERROR_EVENT = 1 << 2, /*!< error interrupt */
QDEC_OVERFLOW_EVENT = 1 << 3, /*!< ACC1 and ACC2 overflow interrupt */
QDEC_ALL_EVENT = 1 << 4, /*!< interrupt max num */
};
typedef struct qdec_device {
struct device parent;
uint8_t id;
uint8_t acc_mode;
uint8_t sample_mode;
uint8_t sample_period;
uint8_t report_mode;
uint32_t report_period;
uint8_t led_en;
uint8_t led_swap;
uint16_t led_period;
uint8_t deglitch_en;
uint8_t deglitch_strength;
} qdec_device_t;
#define QDEC_DEV(dev) ((qdec_device_t *)dev)
int qdec_register(enum qdec_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif // __HAL_QDEC_H__

View File

@@ -1,64 +1,39 @@
/**
* @file hal_common.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_common.h"
#include "bl602_ef_ctrl.h"
#include "bl602_romdriver.h"
volatile uint32_t nesting = 0;
void ATTR_TCM_SECTION cpu_global_irq_enable(void)
{
nesting--;
if (nesting == 0) {
__enable_irq();
}
}
void ATTR_TCM_SECTION cpu_global_irq_disable(void)
{
__disable_irq();
nesting++;
}
void hal_por_reset(void)
{
RomDriver_GLB_SW_POR_Reset();
}
void hal_system_reset(void)
{
RomDriver_GLB_SW_System_Reset();
}
void hal_cpu_reset(void)
{
RomDriver_GLB_SW_CPU_Reset();
}
void hal_get_chip_id(uint8_t chip_id[8])
{
chip_id[6] = 0;
chip_id[7] = 0;
EF_Ctrl_Read_MAC_Address(chip_id);
}
/**
* @file hal_rtc.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_RTC__H__
#define __HAL_RTC__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
void rtc_init(uint64_t sleep_time);
void rtc_set_timestamp(uint64_t time_stamp);
uint64_t rtc_get_timestamp(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,62 @@
/**
* @file hal_sec_aes.h
* @brief
*
* Copyright 2019-2030 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_SEC_AES__H__
#define __HAL_SEC_AES__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
typedef enum {
SEC_AES_CBC,
SEC_AES_CTR,
SEC_AES_ECB
} sec_aes_type;
typedef enum {
SEC_AES_KEY_128,
SEC_AES_KEY_256,
SEC_AES_KEY_192
} sec_aes_key_type;
typedef struct sec_aes_handle_t {
sec_aes_type aes_type;
sec_aes_key_type key_type;
} sec_aes_handle_t;
typedef enum {
SEC_AES_DIR_ENCRYPT,
SEC_AES_DIR_DECRYPT
} sec_aes_dir_type;
int sec_aes_init(sec_aes_handle_t *handle, sec_aes_type aes_tye, sec_aes_key_type key_type);
int sec_aes_setkey(sec_aes_handle_t *handle, const uint8_t *key, uint8_t key_len, const uint8_t *nonce, uint8_t dir);
int sec_aes_encrypt(sec_aes_handle_t *handle, const uint8_t *in, uint32_t len, size_t offset, uint8_t *out);
int sec_aes_decrypt(sec_aes_handle_t *handle, const uint8_t *in, uint32_t len, size_t offset, uint8_t *out);
int sec_aes_deinit(sec_aes_handle_t *handle);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,63 @@
/**
* @file hal_sec_dsa.h
* @brief
*
* Copyright 2019-2030 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_SEC_DSA__H__
#define __HAL_SEC_DSA__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
typedef struct sec_dsa_crt_cfg_tag {
uint32_t *dP;
uint32_t *dQ;
uint32_t *qInv;
uint32_t *p;
uint32_t *invR_p;
uint32_t *primeN_p;
uint32_t *q;
uint32_t *invR_q;
uint32_t *primeN_q;
} sec_dsa_crt_cfg_t;
typedef struct
{
uint32_t size;
uint32_t crtSize;
uint32_t *n;
uint32_t *e;
uint32_t *d;
sec_dsa_crt_cfg_t crtCfg;
} sec_dsa_handle_t;
int sec_dsa_init(sec_dsa_handle_t *handle, uint32_t size);
int sec_dsa_mexp_binary(uint32_t size, const uint32_t *a, const uint32_t *b, const uint32_t *c, uint32_t *r);
int sec_dsa_mexp_mont(uint32_t size, uint32_t *a, uint32_t *b, uint32_t *c, uint32_t *invR_c, uint32_t *primeN_c, uint32_t *r);
int sec_dsa_decrypt_crt(uint32_t size, uint32_t *c, sec_dsa_crt_cfg_t *crtCfg, uint32_t *d, uint32_t *r);
int sec_dsa_sign(sec_dsa_handle_t *handle, const uint32_t *hash, uint32_t hashLenInWord, uint32_t *s);
int sec_dsa_verify(sec_dsa_handle_t *handle, const uint32_t *hash, uint32_t hashLenInWord, const uint32_t *s);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -23,10 +23,16 @@
#ifndef __HAL_SEC_ECDSA__H__
#define __HAL_SEC_ECDSA__H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
typedef enum {
ECP_SECP256R1 = 0,
ECP_SECP256K1 = 1,
ECP_TYPE_MAX = 2,
} sec_ecp_type;
typedef struct
@@ -57,5 +63,7 @@ int sec_ecc_get_random_value(uint32_t *randomData, uint32_t *maxRef, uint32_t si
int sec_eng_trng_enable(void);
void sec_eng_trng_disable(void);
int sec_eng_trng_read(uint8_t data[32]);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -23,9 +23,13 @@
#ifndef __HAL_SEC_HASH__H__
#define __HAL_SEC_HASH__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl602_config.h"
#include "bl702_config.h"
enum sec_hash_index_type {
SEC_HASH0_INDEX,
@@ -48,7 +52,21 @@ typedef struct sec_hash_device {
uint8_t type; /*!< Sha has feed data */
} sec_hash_device_t;
int sec_hash_register(enum sec_hash_index_type index, const char *name);
int sec_hash_sha256_register(enum sec_hash_index_type index, const char *name);
typedef struct
{
uint32_t shaBuf[64 / 4]; /*!< Data not processed but in this temp buffer */
uint32_t shaPadding[64 / 4]; /*!< Padding data */
uint8_t type; /*!< Sha has feed data */
} sec_hash_handle_t;
#endif
int sec_hash_init(sec_hash_handle_t *handle, uint8_t type);
int sec_hash_deinit(sec_hash_handle_t *handle);
int sec_hash_update(sec_hash_handle_t *handle, const void *buffer, uint32_t size);
int sec_hash_finish(sec_hash_handle_t *handle, void *buffer);
int sec_hash_sha256_register(enum sec_hash_index_type index, const char *name);
int sec_hash_sha224_register(enum sec_hash_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,123 @@
/**
* @file hal_spi.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_SPI__H__
#define __HAL_SPI__H__
#ifdef __cplusplus
extern "C" {
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define SPI_FIFO_LEN 4
#define DEVICE_CTRL_SPI_CONFIG_CLOCK 0x10
#define DEVICE_CTRL_SPI_GET_TX_FIFO 0x11
#define DEVICE_CTRL_SPI_GET_RX_FIFO 0x12
#define DEVICE_CTRL_SPI_CLEAR_TX_FIFO 0x13
#define DEVICE_CTRL_SPI_CLEAR_RX_FIFO 0x14
#define DEVICE_CTRL_SPI_GET_BUS_BUSY_STATUS 0x15
enum spi_index_type {
#ifdef BSP_USING_SPI0
SPI0_INDEX,
#endif
SPI_MAX_INDEX
};
/** @defgroup SPI_Direction SPI Direction Mode
* @{
*/
#define SPI_LSB_BYTE0_DIRECTION_FIRST 0
#define SPI_LSB_BYTE3_DIRECTION_FIRST 1
#define SPI_MSB_BYTE0_DIRECTION_FIRST 2
#define SPI_MSB_BYTE3_DIRECTION_FIRST 3
/** @defgroup SPI_Data_Size SPI Data Size
* @{
*/
#define SPI_DATASIZE_8BIT 0
#define SPI_DATASIZE_16BIT 1
#define SPI_DATASIZE_24BIT 2
#define SPI_DATASIZE_32BIT 3
/** @defgroup SPI_Clock_Polarity SPI Clock Polarity
* @{
*/
#define SPI_POLARITY_LOW 0
#define SPI_POLARITY_HIGH 1
/** @defgroup SPI_Clock_Phase SPI Clock Phase
* @{
*/
#define SPI_PHASE_1EDGE 0
#define SPI_PHASE_2EDGE 1
/** @defgroup
* @{
*/
#define SPI_SLVAE_MODE 0
#define SPI_MASTER_MODE 1
#define SPI_TRANSFER_TYPE_8BIT 0
#define SPI_TRANSFER_TYPE_16BIT 1
#define SPI_TRANSFER_TPYE_24BIT 2
#define SPI_TRANSFER_TYPE_32BIT 3
enum spi_event_type {
SPI_EVENT_TX_FIFO,
SPI_EVENT_RX_FIFO,
SPI_EVENT_UNKNOWN
};
typedef struct spi_device {
struct device parent;
uint8_t id;
uint32_t clk;
uint8_t mode;
uint8_t direction;
uint8_t clk_polaraity;
uint8_t clk_phase;
uint8_t datasize;
uint8_t fifo_threshold;
uint8_t pin_swap_enable; /*swap mosi and miso*/
uint8_t delitch_cnt;
void *tx_dma;
void *rx_dma;
} spi_device_t;
#define SPI_DEV(dev) ((spi_device_t *)dev)
int spi_register(enum spi_index_type index, const char *name);
int spi_transmit(struct device *dev, void *buffer, uint32_t size, uint8_t type);
int spi_receive(struct device *dev, void *buffer, uint32_t size, uint8_t type);
int spi_transmit_receive(struct device *dev, const void *send_buf, void *recv_buf, uint32_t length, uint8_t type);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,97 @@
/**
* @file hal_timer.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_TIMER__H__
#define __HAL_TIMER__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
enum timer_index_type {
#ifdef BSP_USING_TIMER0
TIMER0_INDEX,
#endif
#ifdef BSP_USING_TIMER1
TIMER1_INDEX,
#endif
TIMER_MAX_INDEX
};
enum timer_preload_trigger_type {
TIMER_PRELOAD_TRIGGER_NONE,
TIMER_PRELOAD_TRIGGER_COMP0,
TIMER_PRELOAD_TRIGGER_COMP1,
TIMER_PRELOAD_TRIGGER_COMP2,
};
enum timer_cnt_mode_type {
TIMER_CNT_PRELOAD,
TIMER_CNT_FREERUN,
};
enum timer_compare_id_type {
TIMER_COMPARE_ID_0,
TIMER_COMPARE_ID_1,
TIMER_COMPARE_ID_2,
};
enum timer_it_type {
TIMER_COMP0_IT = 1 << 0,
TIMER_COMP1_IT = 1 << 1,
TIMER_COMP2_IT = 1 << 2,
};
enum timer_event_type {
TIMER_EVENT_COMP0,
TIMER_EVENT_COMP1,
TIMER_EVENT_COMP2,
TIMER_EVENT_UNKNOWN
};
typedef struct timer_timeout_cfg {
enum timer_compare_id_type timeout_id;
uint32_t timeout_val;
} timer_timeout_cfg_t;
typedef struct timer_device {
struct device parent;
uint8_t id;
enum timer_cnt_mode_type cnt_mode;
enum timer_preload_trigger_type trigger;
uint32_t reload;
uint32_t timeout1;
uint32_t timeout2;
uint32_t timeout3;
} timer_device_t;
#define TIMER_DEV(dev) ((timer_device_t *)dev)
int timer_register(enum timer_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,136 @@
/**
* @file hal_uart.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_UART__H__
#define __HAL_UART__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define UART_FIFO_LEN 128
#define DEVICE_CTRL_UART_GET_TX_FIFO 0x10
#define DEVICE_CTRL_UART_GET_RX_FIFO 0x11
#define DEVICE_CTRL_UART_CLEAR_TX_FIFO 0x12
#define DEVICE_CTRL_UART_CLEAR_RX_FIFO 0x13
enum uart_index_type {
#ifdef BSP_USING_UART0
UART0_INDEX,
#endif
#ifdef BSP_USING_UART1
UART1_INDEX,
#endif
UART_MAX_INDEX
};
/*!
* @brief UART data length settings
*
* This enumeration defines the UART data lengths.
*/
typedef enum {
UART_DATA_LEN_5 = 0, /*!< Data length is 5 bits */
UART_DATA_LEN_6 = 1, /*!< Data length is 6 bits */
UART_DATA_LEN_7 = 2, /*!< Data length is 7 bits */
UART_DATA_LEN_8 = 3 /*!< Data length is 8 bits */
} uart_databits_t;
/*!
* @brief UART stop bit settings
*
* This enumeration defines the UART stop bits.
*/
typedef enum {
UART_STOP_ZERO_D_FIVE = 0, /*!< 0.5 stop bit */
UART_STOP_ONE = 1, /*!< 1 stop bit */
UART_STOP_ONE_D_FIVE = 2, /*!< 1.5 stop bit */
UART_STOP_TWO = 3 /*!< 2 stop bits */
} uart_stopbits_t;
/*!
* @brief UART parity type settings
*
* This enumeration defines the UART parity types.
*/
typedef enum {
UART_PAR_NONE = 0, /*!< No parity */
UART_PAR_ODD = 1, /*!< Parity bit is odd */
UART_PAR_EVEN = 2, /*!< Parity bit is even */
} uart_parity_t;
enum uart_event_type {
UART_EVENT_TX_END,
UART_EVENT_TX_FIFO,
UART_EVENT_RX_END,
UART_EVENT_RX_FIFO,
UART_EVENT_RTO,
UART_EVENT_PCE,
UART_EVENT_TX_FER,
UART_EVENT_RX_FER,
UART_EVENT_UNKNOWN
};
enum uart_it_type {
UART_TX_END_IT = 1 << 0,
UART_RX_END_IT = 1 << 1,
UART_TX_FIFO_IT = 1 << 2,
UART_RX_FIFO_IT = 1 << 3,
UART_RTO_IT = 1 << 4,
UART_PCE_IT = 1 << 5,
UART_TX_FER_IT = 1 << 6,
UART_RX_FER_IT = 1 << 7,
UART_ALL_IT = 1 << 8
};
typedef struct
{
uint32_t baudrate;
uart_databits_t databits;
uart_stopbits_t stopbits;
uart_parity_t parity;
} uart_param_cfg_t;
typedef struct uart_device {
struct device parent;
uint8_t id;
uint32_t baudrate;
uart_databits_t databits;
uart_stopbits_t stopbits;
uart_parity_t parity;
uint8_t fifo_threshold;
void *tx_dma;
void *rx_dma;
} uart_device_t;
#define UART_DEV(dev) ((uart_device_t *)dev)
int uart_register(enum uart_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,236 @@
/**
* @file hal_usb.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_USB__H__
#define __HAL_USB__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "ring_buffer.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_USB_DC_SET_ACK 0X10
#define DEVICE_CTRL_USB_DC_ENUM_ON 0X11
#define DEVICE_CTRL_USB_DC_ENUM_OFF 0X12
#define DEVICE_CTRL_USB_DC_GET_EP_TX_FIFO_CNT 0x13
#define DEVICE_CTRL_USB_DC_GET_EP_RX_FIFO_CNT 0x14
#define DEVICE_CTRL_USB_DC_SET_TX_DMA 0x15
#define DEVICE_CTRL_USB_DC_SET_RX_DMA 0x16
enum usb_index_type {
#ifdef BSP_USING_USB
USB_INDEX,
#endif
USB_MAX_INDEX
};
/**
* USB endpoint Transfer Type mask.
*/
#define USBD_EP_TYPE_CTRL 0
#define USBD_EP_TYPE_ISOC 1
#define USBD_EP_TYPE_BULK 2
#define USBD_EP_TYPE_INTR 3
#define USBD_EP_TYPE_MASK 3
/**
* USB endpoint direction and number.
*/
#define USB_EP_DIR_MASK 0x80U
#define USB_EP_DIR_IN 0x80U
#define USB_EP_DIR_OUT 0x00U
#define USB_EP_OUT_MSK 0x7FU
#define USB_EP_IN_MSK 0x80U
/** Get endpoint index (number) from endpoint address */
#define USB_EP_GET_IDX(ep) ((ep) & ~USB_EP_DIR_MASK)
/** Get direction from endpoint address */
#define USB_EP_GET_DIR(ep) ((ep)&USB_EP_DIR_MASK)
/** Get endpoint address from endpoint index and direction */
#define USB_EP_GET_ADDR(idx, dir) ((idx) | ((dir)&USB_EP_DIR_MASK))
/** True if the endpoint is an IN endpoint */
#define USB_EP_DIR_IS_IN(ep) (USB_EP_GET_DIR(ep) == USB_EP_DIR_IN)
/** True if the endpoint is an OUT endpoint */
#define USB_EP_DIR_IS_OUT(ep) (USB_EP_GET_DIR(ep) == USB_EP_DIR_OUT)
#define USB_SET_EP_OUT(ep) (ep & USB_EP_OUT_MSK)
#define USB_SET_EP_IN(ep) (ep | USB_EP_IN_MSK)
#define USB_OUT_EP_NUM 8
#define USB_IN_EP_NUM 8
#define USB_CTRL_EP_MPS 64 /**< maximum packet size (MPS) for EP 0 */
#define USB_FS_MAX_PACKET_SIZE 64 /**< full speed MPS for bulk EP */
/* Default USB control EP, always 0 and 0x80 */
#define USB_CONTROL_OUT_EP0 0
#define USB_CONTROL_IN_EP0 0x80
#define USB_DC_EP_TYPE_CTRL 0x5 /*0*/
#define USB_DC_EP_TYPE_ISOC 0x2 /*1*/
#define USB_DC_EP_TYPE_BULK 0x4 /*2*/
#define USB_DC_EP_TYPE_INTR 0x0 /*3*/
#define USB_DC_EP1_IN_DR (0x4000D800 + 0x118)
#define USB_DC_EP1_OUT_DR (0x4000D800 + 0x11c)
#define USB_DC_EP2_IN_DR (0x4000D800 + 0x128)
#define USB_DC_EP2_OUT_DR (0x4000D800 + 0x12c)
#define USB_DC_EP3_IN_DR (0x4000D800 + 0x138)
#define USB_DC_EP3_OUT_DR (0x4000D800 + 0x13c)
#define USB_DC_EP4_IN_DR (0x4000D800 + 0x148)
#define USB_DC_EP4_OUT_DR (0x4000D800 + 0x14c)
#define USB_DC_EP5_IN_DR (0x4000D800 + 0x158)
#define USB_DC_EP5_OUT_DR (0x4000D800 + 0x15c)
#define USB_DC_EP6_IN_DR (0x4000D800 + 0x168)
#define USB_DC_EP6_OUT_DR (0x4000D800 + 0x16c)
#define USB_DC_EP7_IN_DR (0x4000D800 + 0x178)
#define USB_DC_EP7_OUT_DR (0x4000D800 + 0x17c)
enum usb_dc_event_type {
/** USB error reported by the controller */
USB_DC_EVENT_ERROR,
/** USB reset */
USB_DC_EVENT_RESET,
/** Start of Frame received */
USB_DC_EVENT_SOF,
/** USB connection established, hardware enumeration is completed */
USB_DC_EVENT_CONNECTED,
/** USB configuration done */
USB_DC_EVENT_CONFIGURED,
/** USB connection suspended by the HOST */
USB_DC_EVENT_SUSPEND,
/** USB connection lost */
USB_DC_EVENT_DISCONNECTED,
/** USB connection resumed by the HOST */
USB_DC_EVENT_RESUME,
/** USB interface selected */
USB_DC_EVENT_SET_INTERFACE,
/** USB interface selected */
USB_DC_EVENT_SET_REMOTE_WAKEUP,
/** USB interface selected */
USB_DC_EVENT_CLEAR_REMOTE_WAKEUP,
/** Set Feature ENDPOINT_HALT received */
USB_DC_EVENT_SET_HALT,
/** Clear Feature ENDPOINT_HALT received */
USB_DC_EVENT_CLEAR_HALT,
/** setup packet received */
USB_DC_EVENT_SETUP_NOTIFY,
/** ep0 in packet received */
USB_DC_EVENT_EP0_IN_NOTIFY,
/** ep0 out packet received */
USB_DC_EVENT_EP0_OUT_NOTIFY,
/** ep in packet except ep0 received */
USB_DC_EVENT_EP_IN_NOTIFY,
/** ep out packet except ep0 received */
USB_DC_EVENT_EP_OUT_NOTIFY,
/** Initial USB connection status */
USB_DC_EVENT_UNKNOWN
};
enum usb_dc_ep_it_type {
USB_SOF_IT = 1 << 0,
USB_EP1_DATA_IN_IT = 1 << 10,
USB_EP1_DATA_OUT_IT = 1 << 11,
USB_EP2_DATA_IN_IT = 1 << 12,
USB_EP2_DATA_OUT_IT = 1 << 13,
USB_EP3_DATA_IN_IT = 1 << 14,
USB_EP3_DATA_OUT_IT = 1 << 15,
USB_EP4_DATA_IN_IT = 1 << 16,
USB_EP4_DATA_OUT_IT = 1 << 17,
USB_EP5_DATA_IN_IT = 1 << 18,
USB_EP5_DATA_OUT_IT = 1 << 19,
USB_EP6_DATA_IN_IT = 1 << 20,
USB_EP6_DATA_OUT_IT = 1 << 21,
USB_EP7_DATA_IN_IT = 1 << 22,
USB_EP7_DATA_OUT_IT = 1 << 23,
};
enum usb_error_type {
USB_DC_OK = 0,
USB_DC_EP_DIR_ERR = 1,
USB_DC_EP_EN_ERR = 2,
USB_DC_EP_TIMEOUT_ERR = 3,
USB_DC_ADDR_ERR = 4,
USB_DC_RB_SIZE_SMALL_ERR = 5,
USB_DC_ZLP_ERR = 6,
};
/**
* @brief USB Endpoint Configuration.
*
* Structure containing the USB endpoint configuration.
*/
struct usb_dc_ep_cfg {
/** The number associated with the EP in the device
* configuration structure
* IN EP = 0x80 | \<endpoint number\>
* OUT EP = 0x00 | \<endpoint number\>
*/
uint8_t ep_addr;
/** Endpoint max packet size */
uint16_t ep_mps;
/** Endpoint Transfer Type.
* May be Bulk, Interrupt, Control or Isochronous
*/
uint8_t ep_type;
};
/*
* USB endpoint structure.
*/
typedef struct
{
uint8_t ep_ena;
uint32_t is_stalled;
struct usb_dc_ep_cfg ep_cfg;
} usb_dc_ep_state_t;
typedef struct usb_dc_device {
struct device parent;
uint8_t id;
usb_dc_ep_state_t in_ep[8]; /*!< IN endpoint parameters */
usb_dc_ep_state_t out_ep[8]; /*!< OUT endpoint parameters */
void *tx_dma;
void *rx_dma;
} usb_dc_device_t;
int usb_dc_register(enum usb_index_type index, const char *name);
int usb_dc_set_dev_address(const uint8_t addr);
int usb_dc_ep_open(struct device *dev, const struct usb_dc_ep_cfg *ep_cfg);
int usb_dc_ep_close(const uint8_t ep);
int usb_dc_ep_set_stall(const uint8_t ep);
int usb_dc_ep_clear_stall(const uint8_t ep);
int usb_dc_ep_is_stalled(struct device *dev, const uint8_t ep, uint8_t *stalled);
int usb_dc_ep_write(struct device *dev, const uint8_t ep, const uint8_t *data, uint32_t data_len, uint32_t *ret_bytes);
int usb_dc_ep_read(struct device *dev, const uint8_t ep, uint8_t *data, uint32_t data_len, uint32_t *read_bytes);
int usb_dc_receive_to_ringbuffer(struct device *dev, Ring_Buffer_Type *rb, uint8_t ep);
int usb_dc_send_from_ringbuffer(struct device *dev, Ring_Buffer_Type *rb, uint8_t ep);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,64 @@
/**
* @file hal_wdt.h
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#ifndef __HAL_WDT__H__
#define __HAL_WDT__H__
#ifdef __cplusplus
extern "C"{
#endif
#include "hal_common.h"
#include "drv_device.h"
#include "bl702_config.h"
#define DEVICE_CTRL_GET_WDT_COUNTER (0x10)
#define DEVICE_CTRL_RST_WDT_COUNTER (0x11)
#define DEVICE_CTRL_GET_RST_STATUS (0x12)
#define DEVICE_CTRL_CLR_RST_STATUS (0x13)
enum wdt_index_type {
#ifdef BSP_USING_WDT
WDT_INDEX,
#endif
WDT_MAX_INDEX
};
enum wdt_event_type {
WDT_EVENT,
WDT_EVENT_UNKNOWN
};
typedef struct wdt_device {
struct device parent;
uint8_t id;
uint32_t wdt_timeout;
} wdt_device_t;
#define WDT_DEV(dev) ((wdt_device_t *)dev)
int wdt_write(struct device *dev, uint32_t pos, const void *buffer, uint32_t size);
int wdt_register(enum wdt_index_type index, const char *name);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,146 @@
#include "hal_acomp.h"
#include "bl702_acomp.h"
#include "hbn_reg.h"
void acomp_init(uint8_t idx, acomp_device_t *device)
{
uint32_t tmpVal;
if (idx == 0) {
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
tmpVal &= ~(1 << 20);
tmpVal &= ~(1 << 21);
BL_WR_REG(HBN_BASE, HBN_IRQ_MODE, tmpVal);
/* Disable ACOMP first */
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP0_CTRL);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_ACOMP0_EN);
tmpVal = BL_WR_REG(AON_BASE, AON_ACOMP0_CTRL, tmpVal);
/* Set ACOMP config */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_MUXEN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_POS_SEL, device->pos_ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_NEG_SEL, device->neg_ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_LEVEL_SEL, AON_ACOMP_LEVEL_FACTOR_1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_BIAS_PROG, AON_ACOMP_BIAS_POWER_MODE1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_HYST_SELP, device->pos_hysteresis_vol);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP0_HYST_SELN, device->neg_hysteresis_vol);
BL_WR_REG(AON_BASE, AON_ACOMP0_CTRL, tmpVal);
} else {
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
tmpVal &= ~(1 << 22);
tmpVal &= ~(1 << 23);
BL_WR_REG(HBN_BASE, HBN_IRQ_MODE, tmpVal);
/* Disable ACOMP first */
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP1_CTRL);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_ACOMP1_EN);
tmpVal = BL_WR_REG(AON_BASE, AON_ACOMP1_CTRL, tmpVal);
/* Set ACOMP config */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_MUXEN, 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_POS_SEL, device->pos_ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_NEG_SEL, device->neg_ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_LEVEL_SEL, AON_ACOMP_LEVEL_FACTOR_1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_BIAS_PROG, AON_ACOMP_BIAS_POWER_MODE1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_HYST_SELP, device->pos_hysteresis_vol);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_ACOMP1_HYST_SELN, device->neg_hysteresis_vol);
BL_WR_REG(AON_BASE, AON_ACOMP1_CTRL, tmpVal);
}
}
void acomp_enable(uint8_t idx)
{
uint32_t tmpVal;
if (idx == 0) {
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP0_CTRL);
tmpVal = BL_SET_REG_BIT(tmpVal, AON_ACOMP0_EN);
BL_WR_REG(AON_BASE, AON_ACOMP0_CTRL, tmpVal);
} else {
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP1_CTRL);
tmpVal = BL_SET_REG_BIT(tmpVal, AON_ACOMP1_EN);
BL_WR_REG(AON_BASE, AON_ACOMP1_CTRL, tmpVal);
}
}
void acomp_disable(uint8_t idx)
{
uint32_t tmpVal;
if (idx == 0) {
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP0_CTRL);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_ACOMP0_EN);
BL_WR_REG(AON_BASE, AON_ACOMP0_CTRL, tmpVal);
} else {
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP1_CTRL);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_ACOMP1_EN);
BL_WR_REG(AON_BASE, AON_ACOMP1_CTRL, tmpVal);
}
}
void acomp_interrupt_mask(uint8_t idx, uint32_t flag)
{
uint32_t tmpVal;
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
if (idx == 0) {
tmpVal &= ~(flag << 20);
} else {
tmpVal &= ~(flag << 22);
}
}
void acomp_interrupt_unmask(uint8_t idx, uint32_t flag)
{
uint32_t tmpVal;
if (idx == 0) {
/* set clear bit */
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_CLR);
tmpVal |= (1 << 20);
BL_WR_REG(HBN_BASE, HBN_IRQ_CLR, tmpVal);
/* unset clear bit */
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_CLR);
tmpVal &= (~(1 << 20));
BL_WR_REG(HBN_BASE, HBN_IRQ_CLR, tmpVal);
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
tmpVal |= (flag << 20);
} else {
/* set clear bit */
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_CLR);
tmpVal |= (1 << 22);
BL_WR_REG(HBN_BASE, HBN_IRQ_CLR, tmpVal);
/* unset clear bit */
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_CLR);
tmpVal &= (~(1 << 22));
BL_WR_REG(HBN_BASE, HBN_IRQ_CLR, tmpVal);
tmpVal = BL_RD_REG(HBN_BASE, HBN_IRQ_MODE);
tmpVal |= (flag << 22);
}
BL_WR_REG(HBN_BASE, HBN_IRQ_MODE, tmpVal);
}
int acomp_get_result(uint8_t idx)
{
uint32_t tmpVal;
tmpVal = BL_RD_REG(AON_BASE, AON_ACOMP_CTRL);
/* Disable ACOMP first */
if (idx == 0) {
if (BL_IS_REG_BIT_SET(tmpVal, AON_ACOMP0_OUT_RAW)) {
return 1;
} else {
return 0;
}
} else {
if (BL_IS_REG_BIT_SET(tmpVal, AON_ACOMP1_OUT_RAW)) {
return 1;
} else {
return 0;
}
}
}

View File

@@ -0,0 +1,427 @@
/**
* @file hal_adc.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_adc.h"
#include "hal_clock.h"
#include "hal_dma.h"
#include "bl702_glb.h"
#include "bl702_dma.h"
#include "bl702_adc.h"
#include "adc_config.h"
#ifdef BSP_USING_ADC0
static void ADC_IRQ(void);
#endif
static adc_device_t adcx_device[ADC_MAX_INDEX] = {
#ifdef BSP_USING_ADC0
ADC0_CONFIG,
#endif
};
/**
* @brief Check whether Channel Corresponding IO is configed success by Board System
*
* @param pos_list pos channel list
* @param neg_list negative channel list
* @param channelNum channel number
*/
uint8_t adc_check_channel_status(uint8_t *pos_list, uint8_t *neg_list, uint16_t channelNum)
{
uint16_t i = 0;
uint8_t channel_io_reference_table[] = {
GLB_GPIO_PIN_8, /* CH0 IO */
GLB_GPIO_PIN_15, /* CH1 IO */
GLB_GPIO_PIN_17, /* CH2 IO */
GLB_GPIO_PIN_11, /* CH3 IO */
GLB_GPIO_PIN_12, /* CH4 IO */
GLB_GPIO_PIN_14, /* CH5 IO */
GLB_GPIO_PIN_7, /* CH6 IO */
GLB_GPIO_PIN_9, /* CH7 IO */
GLB_GPIO_PIN_18, /* CH8 IO */
GLB_GPIO_PIN_19, /* CH9 IO */
GLB_GPIO_PIN_20, /* CH10 IO */
GLB_GPIO_PIN_21, /* CH11 IO */
};
for (i = 0; i < channelNum; i++) {
if (pos_list[i] > ADC_CHANNEL11) {
continue;
}
if (GLB_GPIO_Get_Fun(channel_io_reference_table[pos_list[i]]) != GPIO_FUN_ANALOG) {
return ERROR;
}
}
return SUCCESS;
}
/**
* @brief
*
* @param dev
* @param oflag
* @return int
*/
int adc_open(struct device *dev, uint16_t oflag)
{
adc_device_t *adc_device = (adc_device_t *)dev;
ADC_CFG_Type adc_cfg = { 0 };
ADC_FIFO_Cfg_Type adc_fifo_cfg = { 0 };
CPU_Interrupt_Disable(GPADC_DMA_IRQn);
ADC_IntMask(ADC_INT_ALL, MASK);
adc_cfg.clkDiv = adc_device->clk_div;
adc_cfg.vref = adc_device->vref;
adc_cfg.resWidth = adc_device->data_width;
adc_cfg.inputMode = adc_device->differential_mode;
adc_cfg.v18Sel = ADC_V18_SELECT;
adc_cfg.v11Sel = ADC_V11_SELECT;
adc_cfg.gain1 = ADC_PGA_GAIN1;
adc_cfg.gain2 = ADC_PGA_GAIN2;
adc_cfg.chopMode = ADC_CHOP_MODE;
adc_cfg.biasSel = ADC_BIAS_SELECT;
adc_cfg.vcm = ADC_PGA_VCM;
adc_cfg.offsetCalibEn = ADC_OFFSET_CALIB_EN;
adc_cfg.offsetCalibVal = ADC_OFFSER_CALIB_VAL;
adc_fifo_cfg.dmaEn = DISABLE;
adc_fifo_cfg.fifoThreshold = adc_device->fifo_threshold;
if (oflag & DEVICE_OFLAG_STREAM_TX) {
}
if ((oflag & DEVICE_OFLAG_INT_TX) || (oflag & DEVICE_OFLAG_INT_RX)) {
#ifdef BSP_USING_ADC0
Interrupt_Handler_Register(GPADC_DMA_IRQn, ADC_IRQ);
#endif
}
if (oflag & DEVICE_OFLAG_DMA_TX) {
}
if (oflag & DEVICE_OFLAG_DMA_RX) {
adc_fifo_cfg.dmaEn = ENABLE;
}
ADC_Disable();
ADC_Enable();
ADC_Reset();
ADC_Init(&adc_cfg);
ADC_FIFO_Cfg(&adc_fifo_cfg);
return 0;
}
/**
* @brief
*
* @param dev
* @return int
*/
int adc_close(struct device *dev)
{
uint32_t tmpVal;
ADC_IntMask(ADC_INT_ALL, MASK);
/* disable convert start */
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CMD);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_GPADC_CONV_START);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CMD, tmpVal);
/*disable adc */
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CMD);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_GPADC_GLOBAL_EN);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CMD, tmpVal);
/*disable vbat */
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CONFIG2);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_GPADC_VBAT_EN);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CONFIG2, tmpVal);
ADC_Reset();
return 0;
}
/**
* @brief
*
* @param dev
* @param cmd
* @param args
* @return int
*/
int adc_control(struct device *dev, int cmd, void *args)
{
adc_device_t *adc_device = (adc_device_t *)dev;
adc_channel_cfg_t *adc_channel_cfg = (adc_channel_cfg_t *)args;
uint8_t rlt = 0;
switch (cmd) {
case DEVICE_CTRL_SET_INT: {
uint32_t offset = __builtin_ctz((uint32_t)args);
while ((2 <= offset) && (offset < 6)) {
if ((uint32_t)args & (1 << offset)) {
ADC_IntMask(offset, UNMASK);
}
offset++;
}
CPU_Interrupt_Enable(GPADC_DMA_IRQn);
break;
}
case DEVICE_CTRL_CLR_INT: {
uint32_t offset = __builtin_ctz((uint32_t)args);
while ((2 <= offset) && (offset < 6)) {
if ((uint32_t)args & (1 << offset)) {
ADC_IntMask(offset, UNMASK);
}
offset++;
}
CPU_Interrupt_Disable(GPADC_DMA_IRQn);
break;
}
case DEVICE_CTRL_GET_INT:
break;
case DEVICE_CTRL_CONFIG:
break;
case DEVICE_CTRL_ADC_CHANNEL_CONFIG:
if (adc_channel_cfg->num == 1) {
ADC_Channel_Config(*adc_channel_cfg->pos_channel, *adc_channel_cfg->neg_channel, adc_device->continuous_conv_mode);
rlt = adc_check_channel_status(adc_channel_cfg->pos_channel, adc_channel_cfg->neg_channel, 1);
} else {
ADC_Scan_Channel_Config(adc_channel_cfg->pos_channel, adc_channel_cfg->neg_channel, adc_channel_cfg->num, adc_device->continuous_conv_mode);
rlt = adc_check_channel_status(adc_channel_cfg->pos_channel, adc_channel_cfg->neg_channel, adc_channel_cfg->num);
}
break;
case DEVICE_CTRL_ADC_CHANNEL_START: {
uint32_t regCmd;
/* disable convert start */
regCmd = BL_RD_REG(AON_BASE, AON_GPADC_REG_CMD);
regCmd = BL_CLR_REG_BIT(regCmd, AON_GPADC_CONV_START);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CMD, regCmd);
BL702_Delay_US(100);
/* enable convert start */
regCmd = BL_RD_REG(AON_BASE, AON_GPADC_REG_CMD);
regCmd = BL_SET_REG_BIT(regCmd, AON_GPADC_CONV_START);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CMD, regCmd);
} break;
case DEVICE_CTRL_ADC_CHANNEL_STOP: {
uint32_t tmpVal;
/* disable convert start */
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CMD);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_GPADC_CONV_START);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CMD, tmpVal);
break;
}
case DEVICE_CTRL_ADC_VBAT_ON: {
uint32_t tmpVal;
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CONFIG2);
tmpVal = BL_SET_REG_BIT(tmpVal, AON_GPADC_VBAT_EN);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CONFIG2, tmpVal);
break;
}
case DEVICE_CTRL_ADC_VBAT_OFF: {
uint32_t tmpVal;
tmpVal = BL_RD_REG(AON_BASE, AON_GPADC_REG_CONFIG2);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_GPADC_VBAT_EN);
BL_WR_REG(AON_BASE, AON_GPADC_REG_CONFIG2, tmpVal);
break;
}
case DEVICE_CTRL_ADC_TSEN_ON:
ADC_Tsen_Init(ADC_TSEN_MOD_INTERNAL_DIODE);
break;
case DEVICE_CTRL_ADC_TSEN_OFF:
break;
case DEVICE_CTRL_ATTACH_RX_DMA:
adc_device->rx_dma = (struct device *)args;
break;
case DEVICE_CTRL_ADC_DATA_PARSE: {
adc_data_parse_t *parse = (adc_data_parse_t *)args;
ADC_Parse_Result(parse->input, parse->num, (ADC_Result_Type *)parse->output);
}
break;
default:
break;
}
return rlt;
}
// int adc_write(struct device *dev, uint32_t pos, const void *buffer, uint32_t size)
// {
// return 0;
// }
/**
* @brief
*
* @param dev
* @param pos
* @param buffer
* @param size
* @return int
*/
int adc_read(struct device *dev, uint32_t pos, void *buffer, uint32_t size)
{
uint32_t adc_fifo_val[32];
int ret = -1;
adc_device_t *adc_device = (adc_device_t *)dev;
if (dev->oflag & DEVICE_OFLAG_STREAM_RX) {
if (size > 32)
return -1;
while (ADC_Get_FIFO_Count() < size) {
}
for (uint32_t i = 0; i < size; i++) {
adc_fifo_val[i] = ADC_Read_FIFO();
}
adc_channel_val_t *adc_parse_val = (adc_channel_val_t *)buffer;
ADC_Parse_Result(adc_fifo_val, size, (ADC_Result_Type *)adc_parse_val);
return size;
} else if (dev->oflag & DEVICE_OFLAG_DMA_RX) {
struct device *dma_ch = (struct device *)adc_device->rx_dma;
if (!dma_ch)
return -1;
ret = dma_reload(dma_ch, (uint32_t)DMA_ADDR_ADC_RDR, (uint32_t)buffer, size);
dma_channel_start(dma_ch);
return ret;
}
return ret;
}
int adc_trim_tsen(uint16_t *tsen_offset)
{
return ADC_Trim_TSEN(tsen_offset);
}
float adc_get_tsen(uint16_t tsen_offset)
{
return TSEN_Get_Temp(tsen_offset);
}
/**
* @brief
*
* @param index
* @param name
* @return int
*/
int adc_register(enum adc_index_type index, const char *name)
{
struct device *dev;
if (ADC_MAX_INDEX == 0) {
return -DEVICE_EINVAL;
}
dev = &(adcx_device[index].parent);
dev->open = adc_open;
dev->close = adc_close;
dev->control = adc_control;
dev->write = NULL;
dev->read = adc_read;
dev->type = DEVICE_CLASS_ADC;
dev->handle = NULL;
return device_register(dev, name);
}
/**
* @brief
*
* @param handle
*/
void adc_isr(adc_device_t *handle)
{
if (!handle->parent.callback)
return;
if (ADC_GetIntStatus(ADC_INT_POS_SATURATION) == SET && ADC_IntGetMask(ADC_INT_POS_SATURATION) == UNMASK) {
//handle->parent.callback(&handle->parent, NULL, 0, ADC_EVEN_INT_POS_SATURATION);
ADC_IntClr(ADC_INT_POS_SATURATION);
}
if (ADC_GetIntStatus(ADC_INT_NEG_SATURATION) == SET && ADC_IntGetMask(ADC_INT_NEG_SATURATION) == UNMASK) {
//handle->parent.callback(&handle->parent, NULL, 0, ADC_EVEN_INT_NEG_SATURATION);
ADC_IntClr(ADC_INT_NEG_SATURATION);
}
if (ADC_GetIntStatus(ADC_INT_FIFO_UNDERRUN) == SET && ADC_IntGetMask(ADC_INT_FIFO_UNDERRUN) == UNMASK) {
ADC_IntClr(ADC_INT_FIFO_UNDERRUN);
handle->parent.callback(&handle->parent, NULL, 0, ADC_EVENT_UNDERRUN);
}
if (ADC_GetIntStatus(ADC_INT_FIFO_OVERRUN) == SET && ADC_IntGetMask(ADC_INT_FIFO_OVERRUN) == UNMASK) {
ADC_IntClr(ADC_INT_FIFO_OVERRUN);
handle->parent.callback(&handle->parent, NULL, 0, ADC_EVENT_OVERRUN);
}
if (ADC_GetIntStatus(ADC_INT_FIFO_READY) == SET && ADC_IntGetMask(ADC_INT_FIFO_READY) == UNMASK) {
ADC_IntClr(ADC_INT_FIFO_READY);
uint32_t adc_count = ADC_Get_FIFO_Count();
uint32_t adc_fifo_val[32];
adc_channel_val_t adc_parse_val[32];
for (uint32_t i = 0; i < adc_count; i++) {
adc_fifo_val[i] = ADC_Read_FIFO();
}
ADC_Parse_Result(adc_fifo_val, adc_count, (ADC_Result_Type *)adc_parse_val);
handle->parent.callback(&handle->parent, (void *)adc_parse_val, adc_count, ADC_EVENT_FIFO);
}
}
#ifdef BSP_USING_ADC0
void ADC_IRQ(void)
{
adc_isr(&adcx_device[ADC0_INDEX]);
}
#endif

View File

@@ -0,0 +1,477 @@
#include "hal_boot2.h"
#include "hal_flash.h"
#include "bl702_ef_ctrl.h"
#include "bl702_hbn.h"
#include "bl702_glb.h"
#include "bl702_xip_sflash.h"
#include "tzc_sec_reg.h"
#include "hal_gpio.h"
#include "softcrc.h"
#include "hal_sec_hash.h"
/**
* @brief boot2 custom
*
* @param None
* @return uint32
*/
uint32_t hal_boot2_custom(void)
{
return 0;
}
/**
* @brief get efuse Boot2 config
*
* @param g_efuse_cfg
* @param
* @param
* @return None
*/
void hal_boot2_get_efuse_cfg(boot2_efuse_hw_config *efuse_cfg)
{
uint32_t tmp;
uint32_t rootClk;
uint8_t hdiv = 0, bdiv = 0;
/* save bclk fclk div and root clock sel */
bdiv = GLB_Get_BCLK_Div();
hdiv = GLB_Get_HCLK_Div();
rootClk = BL_RD_REG(HBN_BASE, HBN_GLB);
/* change root clock to rc32m for efuse operation */
HBN_Set_ROOT_CLK_Sel(HBN_ROOT_CLK_RC32M);
/* Get sign and aes type*/
EF_Ctrl_Read_Secure_Boot((EF_Ctrl_Sign_Type *)efuse_cfg->sign, (EF_Ctrl_SF_AES_Type *)efuse_cfg->encrypted);
/* Get hash:aes key slot 0 and slot1*/
EF_Ctrl_Read_AES_Key(0, (uint32_t *)efuse_cfg->pk_hash_cpu0, 8);
EF_Ctrl_Read_Chip_ID(efuse_cfg->chip_id);
/* Get HBN check sign config */
EF_Ctrl_Read_Sw_Usage(0, &tmp);
efuse_cfg->hbn_check_sign = (tmp >> 22) & 0x01;
/* restore bclk fclk div and root clock sel */
GLB_Set_System_CLK_Div(hdiv, bdiv);
BL_WR_REG(HBN_BASE, HBN_GLB, rootClk);
__NOP();
__NOP();
__NOP();
__NOP();
}
/**
* @brief reset sec eng clock
*
* @return
*/
void hal_boot2_reset_sec_eng(void)
{
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_SEC);
}
/**
* @brief system soft reset
*
* @return
*/
void hal_boot2_sw_system_reset(void)
{
GLB_SW_System_Reset();
}
/**
* @brief
*
* @param flag
* @param
* @param
* @return
*/
void hal_boot2_set_psmode_status(uint32_t flag)
{
HBN_Set_Status_Flag(flag);
}
/**
* @brief
*
* @param
* @param
* @param
* @return flag
*/
uint32_t hal_boot2_get_psmode_status(void)
{
return HBN_Get_Status_Flag();
}
/**
* @brief
*
* @param
* @param
* @param
* @return user define flag
*/
uint32_t hal_boot2_get_user_fw(void)
{
return BL_RD_WORD(HBN_BASE + HBN_RSV0_OFFSET);
}
/**
* @brief clr user define flag
*
* @param
* @param
* @param
* @return
*/
void hal_boot2_clr_user_fw(void)
{
uint32_t *p = (uint32_t *)(HBN_BASE + HBN_RSV0_OFFSET);
*p = 0;
}
/**
* @brief hal_boot2_sboot_finish
*
* @return
*/
void ATTR_TCM_SECTION hal_boot2_sboot_finish(void)
{
uint32_t tmp_val;
tmp_val = BL_RD_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL);
tmp_val = BL_SET_REG_BITS_VAL(tmp_val, TZC_SEC_TZC_SBOOT_DONE, 0xf);
BL_WR_REG(TZC_SEC_BASE, TZC_SEC_TZC_ROM_CTRL, tmp_val);
}
/**
* @brief hal_boot2_uart_gpio_init
*
* @return
*/
void hal_boot2_uart_gpio_init(void)
{
GLB_GPIO_Type gpios[] = { GPIO_PIN_14, GPIO_PIN_15 };
GLB_GPIO_Func_Init(GPIO_FUN_UART, gpios, 2);
GLB_UART_Fun_Sel((GPIO_PIN_14 % 8), GLB_UART_SIG_FUN_UART0_TXD); // GPIO_FUN_UART1_TX
GLB_UART_Fun_Sel((GPIO_PIN_15 % 8), GLB_UART_SIG_FUN_UART0_RXD);
}
/**
* @brief hal_boot2_pll_init
*
* @return
*/
void hal_boot2_debug_uart_gpio_init(void)
{
GLB_GPIO_Type gpios[] = { GPIO_PIN_17 };
GLB_GPIO_Func_Init(GPIO_FUN_UART, gpios, 1);
GLB_UART_Fun_Sel((GPIO_PIN_17 % 8), GLB_UART_SIG_FUN_UART1_TXD);
}
/**
* @brief hal_boot2_debug_usb_port_init
*
* @return
*/
#if HAL_BOOT2_SUPPORT_USB_IAP
void hal_boot2_debug_usb_port_init(void)
{
/* must do this , or usb can not be recognized */
cpu_global_irq_disable();
cpu_global_irq_enable();
GLB_GPIO_Type gpios[] = { GPIO_PIN_7, GPIO_PIN_8 };
GLB_GPIO_Func_Init(GPIO_FUN_ANALOG, gpios, 2);
}
#endif
/**
* @brief hal_boot2_debug_uart_gpio_deinit
*
* @return
*/
void hal_boot2_debug_uart_gpio_deinit(void)
{
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_UART0);
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_UART1);
GLB_UART_Sig_Swap_Set(UART_SIG_SWAP_NONE);
}
/****************************************************************************/ /**
* @brief Check bootheader crc
*
* @param data: bootheader data pointer
*
* @return boot_error_code type
*
*******************************************************************************/
static uint32_t hal_boot_check_bootheader(struct hal_bootheader_t *header)
{
uint32_t crc_pass = 0;
uint32_t crc;
if (header->bootCfg.bval.crcIgnore == 1 && header->crc32 == HAL_BOOT2_DEADBEEF_VAL) {
//MSG("Crc ignored\r\n");
crc_pass = 1;
} else {
crc = BFLB_Soft_CRC32((uint8_t *)header, sizeof(struct hal_bootheader_t) - sizeof(header->crc32));
if (header->crc32 == crc) {
crc_pass = 1;
}
}
return crc_pass;
}
/****************************************************************************/ /**
* @brief Check if the input public key is the same as burned in the efuse
*
* @param g_boot_img_cfg: Boot image config pointer
* @param data: Image data pointer
*
* @return boot_error_code type
*
*******************************************************************************/
int32_t hal_boot_parse_bootheader(boot2_image_config *boot_img_cfg, uint8_t *data)
{
struct hal_bootheader_t *header = (struct hal_bootheader_t *)data;
uint32_t crc_pass = 0;
uint32_t i = 0;
uint32_t *phash = (uint32_t *)header->hash;
crc_pass=hal_boot_check_bootheader(header);
if (!crc_pass) {
//MSG_ERR("bootheader crc error\r\n");
//blsp_dump_data((uint8_t *)&crc, 4);
return 0x0204;
}
if (header->bootCfg.bval.notLoadInBoot) {
return 0x0202;
}
/* Get which CPU's img it is*/
for (i = 0; i < HAL_BOOT2_CPU_MAX; i++) {
if (0 == memcmp((void *)&header->magicCode, HAL_BOOT2_CPU0_MAGIC,
sizeof(header->magicCode))) {
break;
} else if (0 == memcmp((void *)&header->magicCode, HAL_BOOT2_CPU1_MAGIC,
sizeof(header->magicCode))) {
break;
}
}
if (i == HAL_BOOT2_CPU_MAX) {
/* No cpu img magic match */
//MSG_ERR("Magic code error\r\n");
return 0x0203;
}
if(boot_img_cfg==NULL){
return 0;
}
boot_img_cfg->pk_src=i;
boot_img_cfg->img_valid=0;
/* Deal with pll config */
/* Encrypt and sign */
boot_img_cfg->basic_cfg.encrypt_type = header->bootCfg.bval.encrypt_type;
boot_img_cfg->basic_cfg.sign_type = header->bootCfg.bval.sign;
boot_img_cfg->basic_cfg.key_sel = header->bootCfg.bval.key_sel;
/* Xip relative */
boot_img_cfg->basic_cfg.no_segment = header->bootCfg.bval.no_segment;
boot_img_cfg->cpu_cfg[0].cache_enable = header->bootCfg.bval.cache_enable;
boot_img_cfg->basic_cfg.aes_region_lock = header->bootCfg.bval.aes_region_lock;
//boot_img_cfg->cpu_cfg[1].halt_cpu = header->bootCfg.bval.halt_cpu1;
boot_img_cfg->cpu_cfg[0].cache_way_dis = header->bootCfg.bval.cache_way_disable;
boot_img_cfg->basic_cfg.hash_ignore = header->bootCfg.bval.hash_ignore;
/* Firmware len*/
boot_img_cfg->basic_cfg.img_len_cnt= header->img_segment_info.img_len;
/* Boot entry and flash offset */
boot_img_cfg->cpu_cfg[0].boot_entry = header->bootEntry;
boot_img_cfg->basic_cfg.group_image_offset = header->img_start.flash_offset;
boot_img_cfg->cpu_cfg[0].config_enable=1;
boot_img_cfg->cpu_cfg[0].halt_cpu =0;
//MSG("sign %d,encrypt:%d\r\n", boot_img_cfg->sign_type,boot_img_cfg->encrypt_type);
/* Check encrypt and sign match*/
if (g_efuse_cfg.encrypted[i] != 0) {
if (boot_img_cfg->basic_cfg.encrypt_type == 0) {
//MSG_ERR("Encrypt not fit\r\n");
return 0x0205;
}
}
if (g_efuse_cfg.sign[i] !=boot_img_cfg->basic_cfg.sign_type) {
//MSG_ERR("sign not fit\r\n");
boot_img_cfg->basic_cfg.sign_type = g_efuse_cfg.sign[i];
return 0x0206;
}
if (g_ps_mode == 1 && (!g_efuse_cfg.hbn_check_sign)) {
/* In HBN Mode, if user select to ignore hash and sign*/
boot_img_cfg->basic_cfg.hash_ignore = 1;
} else if ((boot_img_cfg->basic_cfg.hash_ignore == 1 && *phash != HAL_BOOT2_DEADBEEF_VAL) ||
g_efuse_cfg.sign[i] != 0) {
/* If signed or user not really want to ignore, hash can't be ignored*/
boot_img_cfg->basic_cfg.hash_ignore = 0;
}
if (g_user_hash_ignored) {
boot_img_cfg->basic_cfg.hash_ignore = 1;
}
ARCH_MemCpy_Fast(boot_img_cfg->basic_cfg.hash, header->hash, sizeof(header->hash));
if (boot_img_cfg->basic_cfg.img_len_cnt == 0) {
return 0x0207;
}
return 0;
}
void ATTR_TCM_SECTION hal_boot2_clean_cache(void)
{
/* no need clean again since hal_boot2_set_cache will also clean
unused way,and bl702 no data cache except psram */
}
BL_Err_Type ATTR_TCM_SECTION hal_boot2_set_cache(uint8_t cont_read, boot2_image_config *boot_img_cfg)
{
return flash_set_cache(cont_read, boot_img_cfg->cpu_cfg[0].cache_enable,
boot_img_cfg->cpu_cfg[0].cache_way_dis,
boot_img_cfg->basic_cfg.group_image_offset);
}
/****************************************************************************/ /**
* @brief get the ram image name and count
*
* @param img_name: ram image name in partition
* @param ram_img_cnt: ram image count that support boot from flash
*
* @return None
*
*******************************************************************************/
void hal_boot2_get_ram_img_cnt(char* img_name[],uint32_t *ram_img_cnt )
{
*ram_img_cnt=0;
}
/****************************************************************************/ /**
* @brief get the ram image info
*
* @param data: bootheader information
* @param image_offset: ram image offset in flash(from of bootheader)
* @param img_len: ram image length
* @param hash: pointer to hash pointer
*
* @return None
*
*******************************************************************************/
void hal_boot2_get_img_info(uint8_t *data, uint32_t *image_offset, uint32_t *img_len,uint8_t **hash)
{
*img_len=0;
}
/****************************************************************************/ /**
* @brief release other cpu to boot up
*
* @param core: core number
* @param boot_addr: boot address
*
* @return None
*
*******************************************************************************/
void ATTR_TCM_SECTION hal_boot2_release_cpu(uint32_t core, uint32_t boot_addr)
{
}
/****************************************************************************/ /**
* @brief get xip address according to flash addr
*
* @param flash_addr: flash address
*
* @return XIP Address
*
*******************************************************************************/
uint32_t hal_boot2_get_xip_addr(uint32_t flash_addr)
{
uint32_t img_offset= SF_Ctrl_Get_Flash_Image_Offset();
if(flash_addr>=img_offset){
return BL702_FLASH_XIP_BASE+(flash_addr-img_offset);
}else{
return 0;
}
}
/****************************************************************************/ /**
* @brief get multi-group count
*
* @param None
*
* @return 1 for multi-group 0 for not
*
*******************************************************************************/
uint32_t hal_boot2_get_grp_count(void)
{
return 1;
}
/****************************************************************************/ /**
* @brief get cpu count
*
* @param None
*
* @return 1 for multi-group 0 for not
*
*******************************************************************************/
uint32_t hal_boot2_get_cpu_count(void)
{
return 1;
}
/****************************************************************************/ /**
* @brief get cpu count
*
* @param None
*
* @return 1 for multi-group 0 for not
*
*******************************************************************************/
uint32_t ATTR_TCM_SECTION hal_boot2_get_feature_flag(void)
{
return HAL_BOOT2_SP_FLAG;
}
/****************************************************************************/ /**
* @brief get boot header offset
*
* @param None
*
* @return bootheader offset
*
*******************************************************************************/
uint32_t hal_boot2_get_bootheader_offset(void)
{
return 0x00;
}

View File

@@ -0,0 +1,342 @@
/**
* @file hal_cam.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_cam.h"
#include "bl702_cam.h"
#include "bl702_glb.h"
#ifdef BSP_USING_CAM0
static void CAM0_IRQ(void);
#endif
static cam_device_t camx_device[CAM_MAX_INDEX] = {
#ifdef BSP_USING_CAM0
CAM0_CONFIG,
#endif
};
/**
* @brief
*
* @param dev
* @param oflag
* @return int
*/
int cam_open(struct device *dev, uint16_t oflag)
{
cam_device_t *cam_device = (cam_device_t *)dev;
CAM_CFG_Type camera_cfg = { 0 };
uint32_t tmpVal;
/* Disable camera module */
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_CLR_REG_BIT(tmpVal, CAM_REG_DVP_ENABLE);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
camera_cfg.swMode = cam_device->software_mode;
camera_cfg.frameMode = cam_device->frame_mode;
camera_cfg.yuvMode = cam_device->yuv_format;
camera_cfg.waitCount = 0x40;
camera_cfg.linePol = cam_device->hsp;
camera_cfg.framePol = cam_device->vsp;
camera_cfg.burstType = CAM_BURST_TYPE_INCR16;
camera_cfg.camSensorMode = CAM_SENSOR_MODE_V_AND_H;
camera_cfg.memStart0 = cam_device->cam_write_ram_addr;
camera_cfg.memSize0 = cam_device->cam_write_ram_size;
camera_cfg.frameSize0 = cam_device->cam_frame_size;
/* planar mode*/
camera_cfg.memStart1 = cam_device->cam_write_ram_addr1;
camera_cfg.memSize1 = cam_device->cam_write_ram_size1;
camera_cfg.frameSize1 = cam_device->cam_frame_size1;
CAM_Init(&camera_cfg);
if (oflag & DEVICE_OFLAG_INT_RX) {
#ifdef BSP_USING_CAM0
Interrupt_Handler_Register(CAM_IRQn, CAM0_IRQ);
#endif
}
return 0;
}
/**
* @brief
*
* @param dev
* @return int
*/
int cam_close(struct device *dev)
{
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_CAM);
return 0;
}
/**
* @brief
*
* @param dev
* @param cmd
* @param args
* @return int
*/
int cam_control(struct device *dev, int cmd, void *args)
{
cam_device_t *cam_device = (cam_device_t *)dev;
switch (cmd) {
case DEVICE_CTRL_SET_INT:
if ((uint32_t)args == CAM_FRAME_IT) {
CAM_IntMask(CAM_INT_NORMAL_0, UNMASK);
CPU_Interrupt_Enable(CAM_IRQn);
}
break;
case DEVICE_CTRL_CLR_INT:
if ((uint32_t)args == CAM_FRAME_IT) {
CAM_IntMask(CAM_INT_NORMAL_0, MASK);
CPU_Interrupt_Disable(CAM_IRQn);
}
break;
case DEVICE_CTRL_RESUME: {
uint32_t tmpVal;
/* Enable camera module */
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_SET_REG_BIT(tmpVal, CAM_REG_DVP_ENABLE);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
} break;
case DEVICE_CTRL_SUSPEND: {
uint32_t tmpVal;
/* Disable camera module */
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_CLR_REG_BIT(tmpVal, CAM_REG_DVP_ENABLE);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
} break;
case DEVICE_CTRL_CAM_FRAME_CUT: {
cam_frame_area_t *cfg = (cam_frame_area_t *)args;
BL_WR_REG(CAM_BASE, CAM_HSYNC_CONTROL, ((cfg->x0 * 2) << 16) + (cfg->x1 * 2));
BL_WR_REG(CAM_BASE, CAM_VSYNC_CONTROL, ((cfg->y0) << 16) + cfg->y1);
} break;
case DEVICE_CTRL_CAM_FRAME_DROP:
if (cam_device->frame_mode == CAM_FRAME_INTERLEAVE_MODE) {
/* Pop one frame */
BL_WR_REG(CAM_BASE, CAM_DVP_FRAME_FIFO_POP, 1);
} else {
/* Pop one frame */
BL_WR_REG(CAM_BASE, CAM_DVP_FRAME_FIFO_POP, 3);
}
break;
case DEVICE_CTRL_CAM_FRAME_WRAP: {
uint32_t tmpVal;
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, CAM_REG_HW_MODE_FWRAP, ((uint32_t)args) & 0x01);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
} break;
default:
break;
}
return 0;
}
/**
* @brief
*
* @param dev
* @param pos
* @param buffer
* @param size
* @return int
*/
int cam_read(struct device *dev, uint32_t pos, void *buffer, uint32_t size)
{
if (!BL_GET_REG_BITS_VAL(BL_RD_REG(CAM_BASE, CAM_DVP_STATUS_AND_ERROR), CAM_FRAME_VALID_CNT_0)) {
return -1;
}
cam_frame_info_t *frame_info = (cam_frame_info_t *)buffer;
frame_info->frame_addr = BL_RD_REG(CAM_BASE, CAM_FRAME_START_ADDR0_0);
frame_info->frame_count = BL_RD_REG(CAM_BASE, CAM_FRAME_BYTE_CNT0_0);
return 0;
}
/**
* @brief
*
* @param index
* @param name
* @return int
*/
int cam_register(enum cam_index_type index, const char *name)
{
struct device *dev;
if (CAM_MAX_INDEX == 0) {
return -DEVICE_EINVAL;
}
dev = &(camx_device[index].parent);
dev->open = cam_open;
dev->close = cam_close;
dev->control = cam_control;
dev->write = NULL;
dev->read = cam_read;
dev->type = DEVICE_CLASS_CAMERA;
dev->handle = NULL;
return device_register(dev, name);
}
void cam_isr(cam_device_t *handle)
{
uint32_t tmpVal;
if (!handle->parent.callback)
return;
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP_STATUS_AND_ERROR);
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_NORMAL_INT_0)) {
CAM_IntClr(CAM_INT_NORMAL_0);
handle->parent.callback(&handle->parent, NULL, 0, CAM_EVENT_FRAME);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_NORMAL_INT_1)) {
CAM_IntClr(CAM_INT_NORMAL_1);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_MEM_INT_0)) {
CAM_IntClr(CAM_INT_MEMORY_OVERWRITE_0);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_MEM_INT_1)) {
CAM_IntClr(CAM_INT_MEMORY_OVERWRITE_1);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_FRAME_INT_0)) {
CAM_IntClr(CAM_INT_FRAME_OVERWRITE_0);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_FRAME_INT_1)) {
CAM_IntClr(CAM_INT_FRAME_OVERWRITE_1);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_FIFO_INT_0)) {
CAM_IntClr(CAM_INT_FIFO_OVERWRITE_0);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_FIFO_INT_1)) {
CAM_IntClr(CAM_INT_FIFO_OVERWRITE_1);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_HCNT_INT)) {
CAM_IntClr(CAM_INT_HSYNC_CNT_ERROR);
}
if (BL_IS_REG_BIT_SET(tmpVal, CAM_STS_VCNT_INT)) {
CAM_IntClr(CAM_INT_VSYNC_CNT_ERROR);
}
}
#ifdef BSP_USING_CAM0
void CAM0_IRQ(void)
{
cam_isr(&camx_device[CAM0_INDEX]);
}
#endif
/**
* @brief
*
*/
void cam_start(void)
{
uint32_t tmpVal;
/* Enable camera module */
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_SET_REG_BIT(tmpVal, CAM_REG_DVP_ENABLE);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
}
/**
* @brief
*
*/
void cam_stop(void)
{
uint32_t tmpVal;
/* Disable camera module */
tmpVal = BL_RD_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE);
tmpVal = BL_CLR_REG_BIT(tmpVal, CAM_REG_DVP_ENABLE);
BL_WR_REG(CAM_BASE, CAM_DVP2AXI_CONFIGUE, tmpVal);
}
/**
* @brief
*
* @param pic
* @param len
*/
uint8_t cam_get_one_frame_interleave(uint8_t **pic, uint32_t *len)
{
if (!BL_GET_REG_BITS_VAL(BL_RD_REG(CAM_BASE, CAM_DVP_STATUS_AND_ERROR), CAM_FRAME_VALID_CNT_0)) {
return -1;
}
*pic = (uint8_t *)BL_RD_REG(CAM_BASE, CAM_FRAME_START_ADDR0_0);
*len = BL_RD_REG(CAM_BASE, CAM_FRAME_BYTE_CNT0_0);
return 0;
}
uint8_t cam_get_one_frame_planar(CAM_YUV_Mode_Type yuv, uint8_t **picYY, uint32_t *lenYY, uint8_t **picUV, uint32_t *lenUV)
{
CAM_Planar_Frame_Info info;
arch_memset(&info, 0, sizeof(info));
CAM_Planar_Get_Frame_Info(&info);
if (yuv == CAM_YUV400_EVEN || yuv == CAM_YUV400_ODD) {
if (info.validFrames0 == 0 && info.validFrames1 == 0) {
return ERROR;
}
} else {
if (info.validFrames0 == 0 || info.validFrames1 == 0) {
return ERROR;
}
}
*picYY = (uint8_t *)(info.curFrameAddr0);
*lenYY = info.curFrameBytes0;
*picUV = (uint8_t *)(info.curFrameAddr1);
*lenUV = info.curFrameBytes1;
return SUCCESS;
}
void cam_drop_one_frame_interleave(void)
{
/* Pop one frame */
BL_WR_REG(CAM_BASE, CAM_DVP_FRAME_FIFO_POP, 1);
}
void cam_drop_one_frame_planar(void)
{
/* Pop one frame */
BL_WR_REG(CAM_BASE, CAM_DVP_FRAME_FIFO_POP, 3);
}

View File

@@ -0,0 +1,660 @@
/**
* @file hal_clock.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_clock.h"
#include "bl702_glb.h"
#include "bl702_pwm.h"
#include "bl702_timer.h"
#if XTAL_TYPE != EXTERNAL_XTAL_32M
static void internal_rc32m_init(void) {
uint32_t tmpVal;
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_XTAL_CAPCODE_EXTRA_AON);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_XTAL_CAPCODE_OUT_AON, 0);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_XTAL_CAPCODE_IN_AON, 0);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_XTAL_RDY_SEL_AON, 0);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
tmpVal = BL_RD_REG(AON_BASE, AON_TSEN);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, AON_XTAL_RDY_INT_SEL_AON, 0);
BL_WR_REG(AON_BASE, AON_TSEN, tmpVal);
for (uint32_t i = 0; i < 20000; i++) {
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_SET_REG_BIT(tmpVal, AON_XTAL_EXT_SEL_AON);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
tmpVal = BL_RD_REG(AON_BASE, AON_XTAL_CFG);
tmpVal = BL_CLR_REG_BIT(tmpVal, AON_XTAL_EXT_SEL_AON);
BL_WR_REG(AON_BASE, AON_XTAL_CFG, tmpVal);
if (BL_IS_REG_BIT_SET(BL_RD_REG(GLB_BASE, GLB_CLK_CFG0), GLB_CHIP_RDY))
break;
}
}
#endif
static uint32_t mtimer_get_clk_src_div(void) { return (system_clock_get(SYSTEM_CLOCK_BCLK) / 1000 / 1000 - 1); }
static void peripheral_clock_gate_all() {
uint32_t tmpVal;
tmpVal = BL_RD_REG(GLB_BASE, GLB_CGEN_CFG1);
// tmpVal &= (~(1 << BL_AHB_SLAVE1_GPIP));
// tmpVal &= (~(1 << BL_AHB_SLAVE1_SEC_DBG));
// tmpVal &= (~(1 << BL_AHB_SLAVE1_SEC));
tmpVal &= (~(1 << BL_AHB_SLAVE1_TZ1));
tmpVal &= (~(1 << BL_AHB_SLAVE1_TZ2));
tmpVal &= (~(1 << BL_AHB_SLAVE1_DMA));
tmpVal &= (~(1 << BL_AHB_SLAVE1_EMAC));
tmpVal &= (~(1 << BL_AHB_SLAVE1_UART0));
tmpVal &= (~(1 << BL_AHB_SLAVE1_UART1));
tmpVal &= (~(1 << BL_AHB_SLAVE1_SPI));
tmpVal &= (~(1 << BL_AHB_SLAVE1_I2C));
tmpVal &= (~(1 << BL_AHB_SLAVE1_PWM));
tmpVal &= (~(1 << BL_AHB_SLAVE1_TMR));
tmpVal &= (~(1 << BL_AHB_SLAVE1_IRR));
tmpVal &= (~(1 << BL_AHB_SLAVE1_CKS));
tmpVal &= (~(1 << 24)); // QDEC0
tmpVal &= (~(1 << 25)); // QDEC1
tmpVal &= (~(1 << 26)); // QDEC2/I2S
tmpVal &= (~(1 << 27)); // KYS
tmpVal &= (~(1 << BL_AHB_SLAVE1_USB));
tmpVal &= (~(1 << BL_AHB_SLAVE1_CAM));
tmpVal &= (~(1 << BL_AHB_SLAVE1_MJPEG));
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
}
void system_clock_init(void) {
#if XTAL_TYPE != EXTERNAL_XTAL_32M
internal_rc32m_init();
AON_Power_Off_XTAL();
#endif
/*select root clock*/
GLB_Set_System_CLK(XTAL_TYPE, BSP_ROOT_CLOCK_SOURCE);
#if BSP_ROOT_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_PLL_57P6M
/* fix 57.6M */
SystemCoreClockSet(57.6 * 1000 * 1000);
#endif
/*set fclk/hclk and bclk clock*/
GLB_Set_System_CLK_Div(BSP_FCLK_DIV, BSP_BCLK_DIV);
/* Set MTimer the same frequency as SystemCoreClock */
GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, mtimer_get_clk_src_div());
#ifndef FAST_WAKEUP
#ifdef BSP_AUDIO_PLL_CLOCK_SOURCE
PDS_Set_Audio_PLL_Freq(BSP_AUDIO_PLL_CLOCK_SOURCE - ROOT_CLOCK_SOURCE_AUPLL_12288000_HZ);
#endif
#endif
#if XTAL_32K_TYPE == INTERNAL_RC_32K
HBN_32K_Sel(HBN_32K_RC);
HBN_Power_Off_Xtal_32K();
#else
HBN_Power_On_Xtal_32K();
HBN_32K_Sel(HBN_32K_XTAL);
#endif
#if XTAL_TYPE == EXTERNAL_XTAL_32M
HBN_Set_XCLK_CLK_Sel(HBN_XCLK_CLK_XTAL);
#else
HBN_Set_XCLK_CLK_Sel(HBN_XCLK_CLK_RC32M);
#endif
}
void peripheral_clock_init(void) {
uint32_t tmpVal = 0;
peripheral_clock_gate_all();
tmpVal = BL_RD_REG(GLB_BASE, GLB_CGEN_CFG1);
#if defined(BSP_USING_UART0) || defined(BSP_USING_UART1)
#if defined(BSP_USING_UART0)
tmpVal |= (1 << BL_AHB_SLAVE1_UART0);
#endif
#if defined(BSP_USING_UART1)
tmpVal |= (1 << BL_AHB_SLAVE1_UART1);
#endif
#if BSP_UART_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_PLL_96M
GLB_Set_UART_CLK(ENABLE, HBN_UART_CLK_96M, BSP_UART_CLOCK_DIV);
#elif BSP_UART_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_FCLK
GLB_Set_UART_CLK(ENABLE, HBN_UART_CLK_FCLK, BSP_UART_CLOCK_DIV);
#else
#error "please select correct uart clock source"
#endif
#endif
#if defined(BSP_USING_I2C0)
#if BSP_I2C_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_BCLK
tmpVal |= (1 << BL_AHB_SLAVE1_I2C);
GLB_Set_I2C_CLK(ENABLE, BSP_I2C_CLOCK_DIV);
#else
#error "please select correct i2c clock source"
#endif
#endif
#if defined(BSP_USING_SPI0)
#if BSP_SPI_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_BCLK
tmpVal |= (1 << BL_AHB_SLAVE1_SPI);
GLB_Set_SPI_CLK(ENABLE, BSP_SPI_CLOCK_DIV);
#else
#error "please select correct spi clock source"
#endif
#endif
#if defined(BSP_USING_TIMER0)
tmpVal |= (1 << BL_AHB_SLAVE1_TMR);
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
#if BSP_TIMER0_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_FCLK
/* Configure timer clock source */
uint32_t tmp = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_CS_1, TIMER_CLKSRC_FCLK);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp);
/* Configure timer clock division */
tmp = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR2, BSP_TIMER0_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp);
#elif BSP_TIMER0_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
/* Configure timer clock source */
uint32_t tmp = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_CS_1, TIMER_CLKSRC_XTAL);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp);
/* Configure timer clock division */
tmp = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR2, BSP_TIMER0_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp);
#elif BSP_TIMER0_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_32K_CLK
/* Configure timer clock source */
uint32_t tmp = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_CS_1, TIMER_CLKSRC_32K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp);
/* Configure timer clock division */
tmp = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR2, BSP_TIMER0_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp);
#elif BSP_TIMER0_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_1K_CLK
/* Configure timer clock source */
uint32_t tmp = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_CS_1, TIMER_CLKSRC_1K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp);
/* Configure timer clock division */
tmp = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR2, BSP_TIMER0_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp);
#else
#error "please select correct timer0 clock source"
#endif
#endif
#if defined(BSP_USING_TIMER1)
tmpVal |= (1 << BL_AHB_SLAVE1_TMR);
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
#if BSP_TIMER1_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_FCLK
/* Configure timer clock source */
uint32_t tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_CS_2, TIMER_CLKSRC_FCLK);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp1);
/* Configure timer clock division */
tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_TCDR3, BSP_TIMER1_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp1);
#elif BSP_TIMER1_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
/* Configure timer clock source */
uint32_t tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_CS_2, TIMER_CLKSRC_XTAL);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp1);
/* Configure timer clock division */
tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_TCDR3, BSP_TIMER1_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp1);
#elif BSP_TIMER1_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_32K_CLK
/* Configure timer clock source */
uint32_t tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_CS_2, TIMER_CLKSRC_32K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp1);
/* Configure timer clock division */
tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp1 = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR3, BSP_TIMER1_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp1);
#elif BSP_TIMER1_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_1K_CLK
/* Configure timer clock source */
uint32_t tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmp1 = BL_SET_REG_BITS_VAL(tmp1, TIMER_CS_2, TIMER_CLKSRC_1K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmp1);
/* Configure timer clock division */
tmp1 = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmp1 = BL_SET_REG_BITS_VAL(tmp, TIMER_TCDR3, BSP_TIMER1_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmp1);
#else
#error "please select correct timer1 clock source"
#endif
#endif
#if defined(BSP_USING_WDT)
tmpVal |= (1 << BL_AHB_SLAVE1_TMR);
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
#if BSP_WDT_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_FCLK
/* Configure watchdog timer clock source */
uint32_t tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_CS_WDT, TIMER_CLKSRC_FCLK);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmpwdt);
/* Configure watchdog timer clock division */
tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_WCDR, BSP_WDT_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmpwdt);
#elif BSP_WDT_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
/* Configure watchdog timer clock source */
uint32_t tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_CS_WDT, TIMER_CLKSRC_XTAL);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmpwdt);
/* Configure watchdog timer clock division */
tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_WCDR, BSP_WDT_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmpwdt);
#elif BSP_WDT_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_32K_CLK
/* Configure watchdog timer clock source */
uint32_t tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_CS_WDT, TIMER_CLKSRC_32K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmpwdt);
/* Configure watchdog timer clock division */
tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_WCDR, BSP_WDT_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmpwdt);
#elif BSP_WDT_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_1K_CLK
/* Configure watchdog timer clock source */
uint32_t tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_CS_WDT, TIMER_CLKSRC_1K);
BL_WR_REG(TIMER_BASE, TIMER_TCCR, tmpwdt);
/* Configure watchdog timer clock division */
tmpwdt = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
tmpwdt = BL_SET_REG_BITS_VAL(tmpwdt, TIMER_WCDR, BSP_WDT_CLOCK_DIV);
BL_WR_REG(TIMER_BASE, TIMER_TCDR, tmpwdt);
#else
#error "please select correct watchdog timer clock source"
#endif
#endif
#if defined(BSP_USING_PWM_CH0) || defined(BSP_USING_PWM_CH1) || defined(BSP_USING_PWM_CH2) || defined(BSP_USING_PWM_CH3) || defined(BSP_USING_PWM_CH4) || defined(BSP_USING_PWM_CH5)
tmpVal |= (1 << BL_AHB_SLAVE1_PWM);
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
uint32_t timeoutCnt = 160 * 1000;
uint32_t tmp_pwm;
uint32_t PWMx;
#if BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_32K_CLK
for (int i = 0; i < 5; i++) {
PWMx = PWM_BASE + PWM_CHANNEL_OFFSET + (i)*0x20;
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
BL_WR_REG(PWMx, PWM_CONFIG, BL_SET_REG_BIT(tmp_pwm, PWM_STOP_EN));
while (!BL_IS_REG_BIT_SET(BL_RD_REG(PWMx, PWM_CONFIG), PWM_STS_TOP)) {
timeoutCnt--;
if (timeoutCnt == 0) {
return;
}
}
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
tmp_pwm = BL_SET_REG_BITS_VAL(tmp_pwm, PWM_REG_CLK_SEL, PWM_CLK_32K);
BL_WR_REG(PWMx, PWM_CONFIG, tmp_pwm);
/* Config pwm division */
BL_WR_REG(PWMx, PWM_CLKDIV, BSP_PWM_CLOCK_DIV + 1);
}
#elif BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_BCLK
for (int i = 0; i < 5; i++) {
PWMx = PWM_BASE + PWM_CHANNEL_OFFSET + (i)*0x20;
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
BL_WR_REG(PWMx, PWM_CONFIG, BL_SET_REG_BIT(tmp_pwm, PWM_STOP_EN));
while (!BL_IS_REG_BIT_SET(BL_RD_REG(PWMx, PWM_CONFIG), PWM_STS_TOP)) {
timeoutCnt--;
if (timeoutCnt == 0) {
return;
}
}
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
tmp_pwm = BL_SET_REG_BITS_VAL(tmp_pwm, PWM_REG_CLK_SEL, PWM_CLK_BCLK);
BL_WR_REG(PWMx, PWM_CONFIG, tmp_pwm);
/* Config pwm division */
BL_WR_REG(PWMx, PWM_CLKDIV, BSP_PWM_CLOCK_DIV + 1);
}
#elif BSP_PWM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
for (int i = 0; i < 5; i++) {
PWMx = PWM_BASE + PWM_CHANNEL_OFFSET + (i)*0x20;
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
BL_WR_REG(PWMx, PWM_CONFIG, BL_SET_REG_BIT(tmp_pwm, PWM_STOP_EN));
while (!BL_IS_REG_BIT_SET(BL_RD_REG(PWMx, PWM_CONFIG), PWM_STS_TOP)) {
timeoutCnt--;
if (timeoutCnt == 0) {
return;
}
}
tmp_pwm = BL_RD_REG(PWMx, PWM_CONFIG);
tmp_pwm = BL_SET_REG_BITS_VAL(tmp_pwm, PWM_REG_CLK_SEL, PWM_CLK_XCLK);
BL_WR_REG(PWMx, PWM_CONFIG, tmp_pwm);
/* Config pwm division */
BL_WR_REG(PWMx, PWM_CLKDIV, BSP_PWM_CLOCK_DIV + 1);
}
#else
#error "please select correct pwm clock source"
#endif
#endif
#if defined(BSP_USING_IR)
tmpVal |= (1 << BL_AHB_SLAVE1_IRR);
GLB_Set_IR_CLK(ENABLE, 0, BSP_IR_CLOCK_DIV);
#endif
#if defined(BSP_USING_I2S0)
tmpVal |= (1 << BL_AHB_SLAVE1_I2S);
GLB_Set_I2S_CLK(ENABLE, GLB_I2S_OUT_REF_CLK_NONE);
#endif
#if defined(BSP_USING_ADC0)
tmpVal |= (1 << BL_AHB_SLAVE1_GPIP);
#if BSP_ADC_CLOCK_SOURCE >= ROOT_CLOCK_SOURCE_AUPLL_12288000_HZ
GLB_Set_ADC_CLK(ENABLE, GLB_ADC_CLK_AUDIO_PLL, BSP_ADC_CLOCK_DIV);
#elif BSP_ADC_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
GLB_Set_ADC_CLK(ENABLE, GLB_ADC_CLK_XCLK, BSP_ADC_CLOCK_DIV);
#else
#error "please select correct adc clock source"
#endif
#endif
#if defined(BSP_USING_DAC0)
tmpVal |= (1 << BL_AHB_SLAVE1_GPIP);
#if BSP_DAC_CLOCK_SOURCE >= ROOT_CLOCK_SOURCE_AUPLL_12288000_HZ
GLB_Set_DAC_CLK(ENABLE, GLB_DAC_CLK_AUDIO_PLL, BSP_DAC_CLOCK_DIV + 1);
#elif BSP_DAC_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
GLB_Set_DAC_CLK(ENABLE, GLB_DAC_CLK_XCLK, BSP_DAC_CLOCK_DIV + 1);
#else
#error "please select correct dac clock source"
#endif
#endif
#if defined(BSP_USING_CAM0)
tmpVal |= (1 << BL_AHB_SLAVE1_CAM);
#if BSP_CAM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_PLL_96M
GLB_Set_CAM_CLK(ENABLE, GLB_CAM_CLK_DLL96M, BSP_CAM_CLOCK_DIV);
GLB_SWAP_EMAC_CAM_Pin(GLB_EMAC_CAM_PIN_CAM);
#elif BSP_CAM_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
GLB_Set_CAM_CLK(ENABLE, GLB_CAM_CLK_XCLK, BSP_CAM_CLOCK_DIV);
GLB_SWAP_EMAC_CAM_Pin(GLB_EMAC_CAM_PIN_CAM);
#else
#error "please select correct camera clock source"
#endif
#endif
#if defined(BSP_USING_QDEC0) || defined(BSP_USING_QDEC1) || defined(BSP_USING_QDEC2) || defined(BSP_USING_KEYSCAN)
#ifdef BSP_USING_KEYSCAN
tmpVal |= (1 << 27);
#endif
#if defined(BSP_USING_QDEC0)
tmpVal |= (1 << 24);
#endif
#if defined(BSP_USING_QDEC1)
tmpVal |= (1 << 25);
#endif
#if defined(BSP_USING_QDEC2)
tmpVal |= (1 << 26);
#endif
#if BSP_QDEC_KEYSCAN_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_32K_CLK
GLB_Set_QDEC_CLK(GLB_QDEC_CLK_F32K, BSP_QDEC_KEYSCAN_CLOCK_DIV);
#elif BSP_QDEC_KEYSCAN_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_XCLK
GLB_Set_QDEC_CLK(GLB_QDEC_CLK_XCLK, BSP_QDEC_KEYSCAN_CLOCK_DIV);
#else
#error "please select correct qdec or keyscan clock source"
#endif
#endif
#if defined(BSP_USING_USB)
tmpVal |= (1 << BL_AHB_SLAVE1_USB);
GLB_Set_USB_CLK(1);
#endif
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
}
uint32_t system_clock_get(enum system_clock_type type) {
switch (type) {
case SYSTEM_CLOCK_ROOT_CLOCK:
if (GLB_Get_Root_CLK_Sel() == 0) {
return 32 * 1000 * 1000;
} else if (GLB_Get_Root_CLK_Sel() == 1)
return 32 * 1000 * 1000;
else {
uint32_t tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG0);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, GLB_REG_PLL_SEL);
if (tmpVal == 0) {
return 57.6 * 1000 * 1000;
} else if (tmpVal == 1) {
return 96 * 1000 * 1000;
} else if (tmpVal == 2) {
return 144 * 1000 * 1000;
} else {
return 0;
}
}
case SYSTEM_CLOCK_FCLK:
return system_clock_get(SYSTEM_CLOCK_ROOT_CLOCK) / (GLB_Get_HCLK_Div() + 1);
case SYSTEM_CLOCK_BCLK:
return system_clock_get(SYSTEM_CLOCK_ROOT_CLOCK) / (GLB_Get_HCLK_Div() + 1) / (GLB_Get_BCLK_Div() + 1);
case SYSTEM_CLOCK_XCLK:
return 32000000;
case SYSTEM_CLOCK_32K_CLK:
return 32000;
case SYSTEM_CLOCK_AUPLL:
#ifdef BSP_AUDIO_PLL_CLOCK_SOURCE
if (BSP_AUDIO_PLL_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL_12288000_HZ) {
return 12288000;
} else if (BSP_AUDIO_PLL_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL_11289600_HZ) {
return 11289600;
} else if (BSP_AUDIO_PLL_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL_5644800_HZ) {
return 5644800;
} else if (BSP_AUDIO_PLL_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL_24576000_HZ) {
return 24576000;
} else if (BSP_AUDIO_PLL_CLOCK_SOURCE == ROOT_CLOCK_SOURCE_AUPLL_24000000_HZ) {
return 24000000;
}
#endif
default:
break;
}
return 0;
}
uint32_t peripheral_clock_get(enum peripheral_clock_type type) {
uint32_t tmpVal;
uint32_t div;
switch (type) {
#if defined(BSP_USING_UART0) || defined(BSP_USING_UART1)
case PERIPHERAL_CLOCK_UART:
tmpVal = BL_RD_REG(HBN_BASE, HBN_GLB);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, HBN_UART_CLK_SEL);
div = BL_RD_REG(GLB_BASE, GLB_CLK_CFG2);
div = BL_GET_REG_BITS_VAL(div, GLB_UART_CLK_DIV);
if (tmpVal == HBN_UART_CLK_FCLK) {
return system_clock_get(SYSTEM_CLOCK_FCLK) / (div + 1);
} else if (tmpVal == HBN_UART_CLK_96M) {
return 96000000 / (div + 1);
}
#endif
#if defined(BSP_USING_SPI0)
case PERIPHERAL_CLOCK_SPI:
tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG3);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_SPI_CLK_DIV);
return system_clock_get(SYSTEM_CLOCK_BCLK) / (div + 1);
#endif
#if defined(BSP_USING_I2C0)
case PERIPHERAL_CLOCK_I2C:
tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG3);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_I2C_CLK_DIV);
return system_clock_get(SYSTEM_CLOCK_BCLK) / (div + 1);
#endif
#if defined(BSP_USING_I2S0)
case PERIPHERAL_CLOCK_I2S:
return system_clock_get(SYSTEM_CLOCK_AUPLL);
#endif
#if defined(BSP_USING_ADC0)
case PERIPHERAL_CLOCK_ADC:
tmpVal = BL_RD_REG(GLB_BASE, GLB_GPADC_32M_SRC_CTRL);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_GPADC_32M_CLK_DIV);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, GLB_GPADC_32M_CLK_SEL);
if (tmpVal == GLB_ADC_CLK_AUDIO_PLL) {
return system_clock_get(SYSTEM_CLOCK_AUPLL) / (div + 1);
} else if (tmpVal == GLB_ADC_CLK_XCLK) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / (div + 1);
}
#endif
#if defined(BSP_USING_DAC0)
case PERIPHERAL_CLOCK_DAC:
tmpVal = BL_RD_REG(GLB_BASE, GLB_DIG32K_WAKEUP_CTRL);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_DIG_512K_DIV);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, GLB_DIG_CLK_SRC_SEL);
if (tmpVal == GLB_DAC_CLK_AUDIO_PLL) {
return system_clock_get(SYSTEM_CLOCK_AUPLL) / div;
} else if (tmpVal == GLB_DAC_CLK_XCLK) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / div;
}
#endif
#if defined(BSP_USING_TIMER0)
case PERIPHERAL_CLOCK_TIMER0:
tmpVal = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, TIMER_CS_1);
div = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
div = BL_GET_REG_BITS_VAL(div, TIMER_TCDR2);
if (tmpVal == TIMER_CLKSRC_FCLK) {
return system_clock_get(SYSTEM_CLOCK_FCLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_32K) {
return system_clock_get(SYSTEM_CLOCK_32K_CLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_1K) {
return 1000 / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_XTAL) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / (div + 1);
}
#endif
#if defined(BSP_USING_TIMER1)
case PERIPHERAL_CLOCK_TIMER1:
tmpVal = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, TIMER_CS_2);
div = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
div = BL_GET_REG_BITS_VAL(div, TIMER_TCDR3);
if (tmpVal == TIMER_CLKSRC_FCLK) {
return system_clock_get(SYSTEM_CLOCK_FCLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_32K) {
return system_clock_get(SYSTEM_CLOCK_32K_CLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_1K) {
return 1000 / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_XTAL) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / (div + 1);
}
#endif
#if defined(BSP_USING_WDT)
case PERIPHERAL_CLOCK_WDT:
tmpVal = BL_RD_REG(TIMER_BASE, TIMER_TCCR);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, TIMER_CS_WDT);
div = BL_RD_REG(TIMER_BASE, TIMER_TCDR);
div = BL_GET_REG_BITS_VAL(div, TIMER_WCDR);
if (tmpVal == TIMER_CLKSRC_FCLK) {
return system_clock_get(SYSTEM_CLOCK_FCLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_32K) {
return system_clock_get(SYSTEM_CLOCK_32K_CLK) / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_1K) {
return 1000 / (div + 1);
} else if (tmpVal == TIMER_CLKSRC_XTAL) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / (div + 1);
}
#endif
#if defined(BSP_USING_PWM_CH0) || defined(BSP_USING_PWM_CH1) || defined(BSP_USING_PWM_CH2) || defined(BSP_USING_PWM_CH3) || defined(BSP_USING_PWM_CH4)
case PERIPHERAL_CLOCK_PWM:
tmpVal = BL_RD_REG(PWM_BASE + PWM_CHANNEL_OFFSET, PWM_CONFIG);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, PWM_REG_CLK_SEL);
div = BL_RD_REG(PWM_BASE + PWM_CHANNEL_OFFSET, PWM_CLKDIV);
if (tmpVal == PWM_CLK_XCLK) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / div;
} else if (tmpVal == PWM_CLK_BCLK) {
return system_clock_get(SYSTEM_CLOCK_BCLK) / div;
} else if (tmpVal == PWM_CLK_32K) {
return system_clock_get(SYSTEM_CLOCK_32K_CLK) / div;
}
#endif
#if defined(BSP_USING_CAM)
case PERIPHERAL_CLOCK_CAM:
tmpVal = BL_RD_REG(GLB_BASE, GLB_CLK_CFG1);
tmpVal = BL_GET_REG_BITS_VAL(tmpVal, GLB_REG_CAM_REF_CLK_SRC_SEL);
div = BL_GET_REG_BITS_VAL(tmpVal, GLB_REG_CAM_REF_CLK_DIV);
if (tmpVal == GLB_CAM_CLK_XCLK) {
return system_clock_get(SYSTEM_CLOCK_XCLK) / (div + 1);
} else if (tmpVal == GLB_CAM_CLK_DLL96M) {
return 96000000 / (div + 1);
}
#endif
default:
break;
}
(void)(tmpVal);
(void)(div);
return 0;
}
void system_mtimer_clock_init(void) { GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, mtimer_get_clk_src_div()); }
void system_mtimer_clock_reinit(void) {
/* reinit clock to 10M */
GLB_Set_MTimer_CLK(1, GLB_MTIMER_CLK_BCLK, 7);
}

View File

@@ -0,0 +1,104 @@
/**
* @file hal_common.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_common.h"
#include "bl702_ef_ctrl.h"
#include "bl702_romdriver.h"
#include "bl702_sec_eng.h"
#include "bl702_l1c.h"
#include "hbn_reg.h"
volatile uint32_t nesting = 0;
void ATTR_TCM_SECTION cpu_global_irq_enable(void)
{
nesting--;
if (nesting == 0) {
__enable_irq();
}
}
void ATTR_TCM_SECTION cpu_global_irq_disable(void)
{
__disable_irq();
nesting++;
}
void hal_por_reset(void)
{
RomDriver_GLB_SW_POR_Reset();
}
void hal_system_reset(void)
{
RomDriver_GLB_SW_System_Reset();
}
void hal_cpu_reset(void)
{
RomDriver_GLB_SW_CPU_Reset();
}
void hal_get_chip_id(uint8_t chip_id[8])
{
EF_Ctrl_Read_MAC_Address(chip_id);
}
void hal_enter_usb_iap(void)
{
BL_WR_WORD(HBN_BASE + HBN_RSV0_OFFSET, 0x00425355); //"\0BSU"
arch_delay_ms(1000);
RomDriver_GLB_SW_POR_Reset();
}
void ATTR_TCM_SECTION hal_jump2app(uint32_t flash_offset)
{
/*flash_offset from 48K to 3.98M*/
if ((flash_offset >= 0xc000) && (flash_offset < (0x400000 - 20 * 1024))) {
void (*app_main)(void) = (void (*)(void))0x23000000;
BL_WR_REG(SF_CTRL_BASE, SF_CTRL_SF_ID0_OFFSET, flash_offset);
L1C_Cache_Flush_Ext();
app_main();
} else {
while(1)
{}
}
}
int hal_get_trng_seed(void)
{
uint32_t seed[8];
uint32_t tmpVal;
tmpVal = BL_RD_REG(GLB_BASE, GLB_CGEN_CFG1);
tmpVal |= (1 << BL_AHB_SLAVE1_SEC);
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
Sec_Eng_Trng_Enable();
Sec_Eng_Trng_Read((uint8_t *)seed);
Sec_Eng_Trng_Disable();
tmpVal = BL_RD_REG(GLB_BASE, GLB_CGEN_CFG1);
tmpVal &= (~(1 << BL_AHB_SLAVE1_SEC));
BL_WR_REG(GLB_BASE, GLB_CGEN_CFG1, tmpVal);
return seed[0];
}

View File

@@ -23,9 +23,8 @@
#include "hal_dac.h"
#include "hal_dma.h"
#include "hal_clock.h"
#include "bl602_dac.h"
#include "bl602_glb.h"
#include "dac_config.h"
#include "bl702_dac.h"
#include "bl702_glb.h"
static dac_device_t dacx_device[] = {
#ifdef BSP_USING_DAC0
@@ -49,10 +48,10 @@ int dac_open(struct device *dev, uint16_t oflag)
uint32_t dac_clk = peripheral_clock_get(PERIPHERAL_CLOCK_DAC);
if ((GLB_GPIO_Get_Fun(GLB_GPIO_PIN_13) == GPIO_FUN_ANALOG) && (dac_device->channels & DAC_CHANNEL_0)) {
if ((GLB_GPIO_Get_Fun(GLB_GPIO_PIN_11) == GPIO_FUN_ANALOG) && (dac_device->channels & DAC_CHANNEL_0)) {
dac_channel_enable_check |= DAC_CHANNEL_0;
}
if ((GLB_GPIO_Get_Fun(GLB_GPIO_PIN_14) == GPIO_FUN_ANALOG) && (dac_device->channels & DAC_CHANNEL_1)) {
if ((GLB_GPIO_Get_Fun(GLB_GPIO_PIN_17) == GPIO_FUN_ANALOG) && (dac_device->channels & DAC_CHANNEL_1)) {
dac_channel_enable_check |= DAC_CHANNEL_1;
}
@@ -95,7 +94,7 @@ int dac_open(struct device *dev, uint16_t oflag)
tmpVal = BL_RD_REG(GLB_BASE, GLB_GPDAC_CTRL);
/*dac vref select*/
if (dac_device->vref == DAC_VREF_EXTERNAL) {
if (GLB_GPIO_Get_Fun(GLB_GPIO_PIN_12) != GPIO_FUN_ANALOG)
if (GLB_GPIO_Get_Fun(GLB_GPIO_PIN_7) != GPIO_FUN_ANALOG)
return -1;
tmpVal = BL_SET_REG_BIT(tmpVal, GLB_GPDAC_REF_SEL);
} else {
@@ -144,18 +143,18 @@ int dac_open(struct device *dev, uint16_t oflag)
BL_WR_REG(GPIP_BASE, GPIP_GPDAC_CONFIG, tmpVal);
/* GLB enable or disable channel */
if (dac_channel_enable_check) {
if (dac_channel_enable_check & DAC_CHANNEL_0) {
/* a channel */
tmpVal = BL_RD_REG(GLB_BASE, GLB_GPDAC_ACTRL);
tmpVal = BL_SET_REG_BIT(tmpVal, GLB_GPDAC_IOA_EN);
tmpVal = BL_SET_REG_BIT(tmpVal, GLB_GPDAC_A_EN);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_GPDAC_A_RNG, DAC_REF_RNG_DEFAULT_SELECT);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_GPDAC_A_RNG, 0x03);
tmpVal = BL_WR_REG(GLB_BASE, GLB_GPDAC_ACTRL, tmpVal);
}
if (dac_channel_enable_check) {
if (dac_channel_enable_check & DAC_CHANNEL_1) {
/* b channel */
tmpVal = BL_RD_REG(GLB_BASE, GLB_GPDAC_BCTRL);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_GPDAC_B_RNG, DAC_REF_RNG_DEFAULT_SELECT);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_GPDAC_B_RNG, 0x03);
tmpVal = BL_SET_REG_BIT(tmpVal, GLB_GPDAC_IOB_EN);
tmpVal = BL_SET_REG_BIT(tmpVal, GLB_GPDAC_B_EN);
tmpVal = BL_WR_REG(GLB_BASE, GLB_GPDAC_BCTRL, tmpVal);

View File

@@ -21,7 +21,7 @@
*
*/
#include "hal_dma.h"
#include "bl602_dma.h"
#include "bl702_dma.h"
#define DMA_CHANNEL_BASE(id_base, ch) ((id_base) + DMA_CHANNEL_OFFSET + (ch)*0x100)
@@ -138,7 +138,6 @@ int dma_control(struct device *dev, int cmd, void *args)
break;
case DEVICE_CTRL_CONFIG:
break;
case DEVICE_CTRL_DMA_CHANNEL_UPDATE:
@@ -263,6 +262,7 @@ int dma_allocate_register(const char *name)
// dev->write = dma_write;
// dev->read = dma_read;
dev->status = DEVICE_UNREGISTER;
dev->type = DEVICE_CLASS_DMA;
dev->handle = NULL;
@@ -280,6 +280,9 @@ int dma_allocate_register(const char *name)
*/
int dma_reload(struct device *dev, uint32_t src_addr, uint32_t dst_addr, uint32_t transfer_size)
{
#if defined(BSP_USING_DMA0_CH0) || defined(BSP_USING_DMA0_CH1) || defined(BSP_USING_DMA0_CH2) || defined(BSP_USING_DMA0_CH3) || \
defined(BSP_USING_DMA0_CH4) || defined(BSP_USING_DMA0_CH5) || defined(BSP_USING_DMA0_CH6) || defined(BSP_USING_DMA0_CH7)
uint32_t malloc_count;
uint32_t remain_len;
uint32_t actual_transfer_len = 0;
@@ -329,12 +332,7 @@ int dma_reload(struct device *dev, uint32_t src_addr, uint32_t dst_addr, uint32_
malloc_count++;
}
if (dma_device->lli_cfg) {
free(dma_device->lli_cfg);
dma_device->lli_cfg = (dma_lli_ctrl_t *)malloc(sizeof(dma_lli_ctrl_t) * malloc_count);
} else {
dma_device->lli_cfg = (dma_lli_ctrl_t *)malloc(sizeof(dma_lli_ctrl_t) * malloc_count);
}
dma_device->lli_cfg = (dma_lli_ctrl_t *)realloc(dma_device->lli_cfg, sizeof(dma_lli_ctrl_t) * malloc_count);
if (dma_device->lli_cfg) {
/*transfer_size will be integer multiple of 4095*n or 4095*2*n or 4095*4*n,(n>0) */
@@ -369,7 +367,7 @@ int dma_reload(struct device *dev, uint32_t src_addr, uint32_t dst_addr, uint32_
dma_device->lli_cfg[i - 1].nextlli = (uint32_t)&dma_device->lli_cfg[i];
}
memcpy(&dma_device->lli_cfg[i].cfg, &dma_ctrl_cfg, sizeof(dma_control_data_t));
dma_device->lli_cfg[i].cfg = dma_ctrl_cfg;
}
BL_WR_REG(dma_channel_base[dma_device->id][dma_device->ch], DMA_SRCADDR, dma_device->lli_cfg[0].src_addr);
BL_WR_REG(dma_channel_base[dma_device->id][dma_device->ch], DMA_DSTADDR, dma_device->lli_cfg[0].dst_addr);
@@ -378,64 +376,56 @@ int dma_reload(struct device *dev, uint32_t src_addr, uint32_t dst_addr, uint32_
} else {
return -2;
}
#endif
return 0;
}
/**
* @brief
*
* @param handle
*/
void dma_isr(dma_device_t *handle)
void dma_channel_isr(dma_device_t *handle)
{
uint32_t tmpVal;
uint32_t intClr;
/* Get DMA register */
if (handle->id == 0) {
uint32_t DMAChs = DMA_BASE;
uint32_t DMAChs = DMA_BASE;
for (uint8_t i = 0; i < DMA_MAX_INDEX; i++) {
tmpVal = BL_RD_REG(DMAChs, DMA_INTTCSTATUS);
if (!handle->parent.callback) {
return;
}
if ((BL_GET_REG_BITS_VAL(tmpVal, DMA_INTTCSTATUS) & (1 << handle[i].ch)) != 0) {
/* Clear interrupt */
tmpVal = BL_RD_REG(DMAChs, DMA_INTTCCLEAR);
intClr = BL_GET_REG_BITS_VAL(tmpVal, DMA_INTTCCLEAR);
intClr |= (1 << handle[i].ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, DMA_INTTCCLEAR, intClr);
BL_WR_REG(DMAChs, DMA_INTTCCLEAR, tmpVal);
tmpVal = BL_RD_REG(DMAChs, DMA_INTTCSTATUS);
if ((BL_GET_REG_BITS_VAL(tmpVal, DMA_INTTCSTATUS) & (1 << handle->ch)) != 0) {
/* Clear interrupt */
tmpVal = BL_RD_REG(DMAChs, DMA_INTTCCLEAR);
intClr = BL_GET_REG_BITS_VAL(tmpVal, DMA_INTTCCLEAR);
intClr |= (1 << handle->ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, DMA_INTTCCLEAR, intClr);
BL_WR_REG(DMAChs, DMA_INTTCCLEAR, tmpVal);
handle->parent.callback(&handle->parent, NULL, 0, DMA_INT_TCOMPLETED);
}
if (handle[i].parent.callback) {
handle[i].parent.callback(&handle[i].parent, NULL, 0, DMA_INT_TCOMPLETED);
}
}
}
for (uint8_t i = 0; i < DMA_MAX_INDEX; i++) {
tmpVal = BL_RD_REG(DMAChs, DMA_INTERRORSTATUS);
if ((BL_GET_REG_BITS_VAL(tmpVal, DMA_INTERRORSTATUS) & (1 << handle[i].ch)) != 0) {
/*Clear interrupt */
tmpVal = BL_RD_REG(DMAChs, DMA_INTERRCLR);
intClr = BL_GET_REG_BITS_VAL(tmpVal, DMA_INTERRCLR);
intClr |= (1 << handle[i].ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, DMA_INTERRCLR, intClr);
BL_WR_REG(DMAChs, DMA_INTERRCLR, tmpVal);
if (handle[i].parent.callback) {
handle[i].parent.callback(&handle->parent, NULL, 0, DMA_INT_ERR);
}
}
}
} else {
tmpVal = BL_RD_REG(DMAChs, DMA_INTERRORSTATUS);
if ((BL_GET_REG_BITS_VAL(tmpVal, DMA_INTERRORSTATUS) & (1 << handle->ch)) != 0) {
/*Clear interrupt */
tmpVal = BL_RD_REG(DMAChs, DMA_INTERRCLR);
intClr = BL_GET_REG_BITS_VAL(tmpVal, DMA_INTERRCLR);
intClr |= (1 << handle->ch);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, DMA_INTERRCLR, intClr);
BL_WR_REG(DMAChs, DMA_INTERRCLR, tmpVal);
handle->parent.callback(&handle->parent, NULL, 0, DMA_INT_ERR);
}
}
/**
* @brief
*
*/
static void DMA0_IRQ(void)
void DMA0_IRQ(void)
{
dma_isr(&dmax_device[0]);
for (uint8_t i = 0; i < DMA_MAX_INDEX; i++) {
dma_channel_isr(&dmax_device[i]);
}
}

View File

@@ -0,0 +1,569 @@
/**
* @file hal_emac.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "bl702_emac.h"
#include "bl702_glb.h"
#include "hal_emac.h"
#ifndef MSG
#define MSG(a,...)
#endif
#define EMAC_USE_INSIDE_CLOCK (0)
#define TAG "EMAC_BD: "
static EMAC_Handle_Type ethHandle;
static EMAC_Handle_Type *thiz = NULL;
/**
* @brief
*
*/
static void emac_gpio_init(void)
{
uint8_t emacPins[] = { GLB_GPIO_PIN_0, GLB_GPIO_PIN_1, GLB_GPIO_PIN_2,
GLB_GPIO_PIN_7, GLB_GPIO_PIN_8,
GLB_GPIO_PIN_18, GLB_GPIO_PIN_19, GLB_GPIO_PIN_20, GLB_GPIO_PIN_21, GLB_GPIO_PIN_22 };
GLB_SWAP_EMAC_CAM_Pin(GLB_EMAC_CAM_PIN_EMAC);
GLB_GPIO_Func_Init(GPIO_FUN_ETHER_MAC, (GLB_GPIO_Type *)emacPins, sizeof(emacPins));
}
/**
* @brief
*
* @param bdt
* @return int
*/
static uint32_t emac_bd_get_cur_active(EMAC_BD_TYPE_e bdt)
{
uint32_t bd = 0;
bd = BL_RD_REG(EMAC_BASE, EMAC_TX_BD_NUM);
if (bdt == EMAC_BD_TYPE_TX) {
bd &= EMAC_TXBDPTR_MSK;
bd >>= EMAC_TXBDPTR_POS;
}
if (bdt == EMAC_BD_TYPE_RX) {
bd &= EMAC_RXBDPTR_MSK;
bd >>= EMAC_RXBDPTR_POS;
}
return bd;
}
/**
* @brief
*
* @param index
* @return int
*/
static int emac_bd_rx_enqueue(uint32_t index)
{
BL_Err_Type err = SUCCESS;
thiz->rxIndexEMAC = index;
return err;
}
/**
* @brief
*
* @param index
* @return int
*/
static void emac_bd_rx_on_err(uint32_t index)
{
/* to do index - 1 */
// uint32_t tmp_bd = 0;
// tmp_bd = BL_RD_REG(EMAC_BASE, EMAC_TX_BD_NUM);
// if (index == tmp_bd) {
// index += (tmp_bd - 1);
// } else {
// index -= 1;
// }
// MSG("i:%x,csl%x\r\n", 5, thiz->bd[5].C_S_L);
// MSG("i:%x,csl%x\r\n", 6, thiz->bd[6].C_S_L);
// MSG("i:%x,csl%x\r\n", 7, thiz->bd[7].C_S_L);
// MSG("i:%x,csl%x\r\n", 8, thiz->bd[8].C_S_L);
// MSG("i:%x,csl%x\r\n", 9, thiz->bd[9].C_S_L);
/* handle error */
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_OR)) {
MSG("EMAC RX OR Error at %s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_RE)) {
MSG("MAC RX RE Error at %s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_DN)) {
MSG("MAC RX DN Error at %s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_TL)) {
MSG("MAC RX TL Error at %s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_CRC)) {
MSG("MAC RX CRC Error at %s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(RX_LC)) {
MSG("MAC RX LC Error at %s:%d\r\n", __func__, __LINE__);
}
thiz->bd[index].C_S_L &= ~0xff;
/* RX BD is ready for RX */
thiz->bd[index].C_S_L |= EMAC_BD_FIELD_MSK(RX_E);
}
/**
* @brief this func will be called in ISR
*
* @param index
* @return int
*/
static int emac_bd_tx_dequeue(uint32_t index)
{
BL_Err_Type err = SUCCESS;
EMAC_BD_Desc_Type *DMADesc;
thiz->txIndexEMAC = index;
DMADesc = &thiz->bd[thiz->txIndexEMAC];
/* release this tx BD to SW (HW will do this) */
DMADesc->C_S_L &= EMAC_BD_FIELD_UMSK(TX_RD);
return err;
}
/**
* @brief
*
* @param index
* @return int
*/
static void emac_bd_tx_on_err(uint32_t index)
{
/* handle error */
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_UR)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_RTRY)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_RL)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_LC)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_DF)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
if (thiz->bd[index].C_S_L & EMAC_BD_FIELD_MSK(TX_CS)) {
MSG("%s:%d\r\n", __func__, __LINE__);
}
thiz->bd[index].C_S_L &= ~0xff;
}
/**
* @brief
*
*/
__WEAK void emac_tx_done_callback_app(void)
{
}
/**
* @brief
*
*/
static void emac_tx_done_callback(void)
{
uint32_t index = 0;
index = emac_bd_get_cur_active(EMAC_BD_TYPE_TX);
emac_bd_tx_dequeue(index);
emac_tx_done_callback_app();
}
/**
* @brief
*
*/
__WEAK void emac_tx_error_callback_app(void)
{
}
/**
* @brief
*
*/
static void emac_tx_error_callback(void)
{
uint32_t index = 0;
index = emac_bd_get_cur_active(EMAC_BD_TYPE_TX);
emac_bd_tx_on_err(index);
}
/**
* @brief
*
*/
__WEAK void emac_rx_done_callback_app(void)
{
}
/**
* @brief
*
*/
static void emac_rx_done_callback(void)
{
uint32_t index = 0;
index = emac_bd_get_cur_active(EMAC_BD_TYPE_RX);
emac_bd_rx_enqueue(index);
emac_rx_done_callback_app();
}
/**
* @brief
*
*/
__WEAK void emac_rx_error_callback_app(void)
{
}
/**
* @brief
*
*/
static void emac_rx_error_callback(void)
{
uint32_t index;
index = emac_bd_get_cur_active(EMAC_BD_TYPE_RX);
emac_bd_rx_on_err(index);
emac_rx_error_callback_app();
}
/**
* @brief
*
*/
__WEAK void emac_rx_busy_callback_app(void)
{
}
/**
* @brief
*
*/
static void emac_rx_busy_callback(void)
{
MSG("EMAC Rx busy at %s:%d\r\n", __func__, __LINE__);
emac_rx_busy_callback_app();
}
/**
* @brief
*
* @param emac_cfg
* @return int
*/
int emac_init(emac_device_t *emac_cfg)
{
EMAC_CFG_Type emacCfg = {
.recvSmallFrame = ENABLE, /*!< Receive small frmae or not */
.recvHugeFrame = DISABLE, /*!< Receive huge frmae(>64K bytes) or not */
.padEnable = ENABLE, /*!< Enable padding for frame which is less than MINFL or not */
.crcEnable = ENABLE, /*!< Enable hardware CRC or not */
.noPreamble = DISABLE, /*!< Enable preamble or not */
.recvBroadCast = ENABLE, /*!< Receive broadcast frame or not */
.interFrameGapCheck = ENABLE, /*!< Check inter frame gap or not */
.miiNoPreamble = ENABLE, /*!< Enable MII interface preamble or not */
.miiClkDiv = 49, /*!< MII interface clock divider from bus clock */
.maxTxRetry = 16, /*!< Maximum tx retry count */
.interFrameGapValue = 24, /*!< Inter frame gap vaule in clock cycles(default 24)*/
.minFrameLen = 64, /*!< Minimum frame length */
.maxFrameLen = ETH_MAX_PACKET_SIZE, /*!< Maximum frame length */
.collisionValid = 16, /*!< Collision valid value */
.macAddr[0] = 0x18, /*!< MAC Address */
.macAddr[1] = 0xB0,
.macAddr[2] = 0x09,
.macAddr[3] = 0x00,
.macAddr[4] = 0x12,
.macAddr[5] = 0x34,
};
BL_Err_Type err = SUCCESS;
/* init emac giio */
emac_gpio_init();
memcpy(emacCfg.macAddr, emac_cfg->mac_addr, 6);
#if EMAC_USE_INSIDE_CLOCK
//enable audio clock */
PDS_Enable_PLL_Clk(PDS_PLL_CLK_48M);
PDS_Set_Audio_PLL_Freq(AUDIO_PLL_50000000_HZ);
GLB_Set_ETH_REF_O_CLK_Sel(GLB_ETH_REF_CLK_OUT_INSIDE_50M);
#else
GLB_Set_ETH_REF_O_CLK_Sel(GLB_ETH_REF_CLK_OUT_OUTSIDE_50M);
#endif
GLB_AHB_Slave1_Clock_Gate(DISABLE, BL_AHB_SLAVE1_EMAC);
//GLB_Invert_ETH_RX_CLK(0);
//GLB_Invert_ETH_TX_CLK(0);
EMAC_Init(&emacCfg);
EMAC_Int_Callback_Install(EMAC_INT_TX_DONE_IDX, emac_tx_done_callback);
EMAC_Int_Callback_Install(EMAC_INT_TX_ERROR_IDX, emac_tx_error_callback);
EMAC_Int_Callback_Install(EMAC_INT_RX_DONE_IDX, emac_rx_done_callback);
EMAC_Int_Callback_Install(EMAC_INT_RX_ERROR_IDX, emac_rx_error_callback);
EMAC_Int_Callback_Install(EMAC_INT_RX_BUSY_IDX, emac_rx_busy_callback);
CPU_Interrupt_Enable(EMAC_IRQn);
EMAC_ClrIntStatus(EMAC_INT_ALL);
EMAC_IntMask(EMAC_INT_ALL, UNMASK);
//EMAC_Enable();
return err;
}
/**
* @brief
*
* @param eth_tx_buff
* @param tx_buf_count
* @param eth_rx_buff
* @param rx_buf_count
* @return int
*/
int emac_bd_init(uint8_t *eth_tx_buff, uint8_t tx_buf_count, uint8_t *eth_rx_buff, uint8_t rx_buf_count)
{
BL_Err_Type err = SUCCESS;
thiz = &ethHandle;
/* init the BDs in emac with buffer address */
err = EMAC_DMADescListInit(thiz, (uint8_t *)eth_tx_buff, tx_buf_count,
(uint8_t *)eth_rx_buff, rx_buf_count);
return err;
}
/**
* @brief
*
* @param flags
* @param len
* @param data_in
* @return int
*/
int emac_bd_tx_enqueue(uint32_t flags, uint32_t len, const uint8_t *data_in)
{
BL_Err_Type err = SUCCESS;
EMAC_BD_Desc_Type *DMADesc;
DMADesc = &thiz->bd[thiz->txIndexCPU];
if (FULL_PACKET == flags) {
// MSG("full packet,len:%d\r\n", len);
flags = (EMAC_TX_COMMON_FLAGS | EMAC_BD_FIELD_MSK(TX_EOF));
} else if (NOFULL_PACKET == flags) {
// MSG("nofull packet\r\n");
flags = EMAC_TX_COMMON_FLAGS;
}
if (DMADesc->C_S_L & EMAC_BD_FIELD_MSK(TX_RD)) {
/* no free BD, lost sync with DMA TX? */
err = NORESC;
// MSG_ERR(TAG"%s:%d\n", __func__, __LINE__);
} else {
DMADesc->Buffer = (uint32_t)data_in;
// MSG("tx q flags:%d,len:%d,data:0x%x\r\n", flags, len, data_in);
// ARCH_MemCpy_Fast((void *)DMADesc->Buffer, data_in, len);
DMADesc->C_S_L = flags | (len << BD_TX_LEN_POS);
/* move to next TX BD */
if ((++thiz->txIndexCPU) > thiz->txBuffLimit) {
/* the last BD */
DMADesc->C_S_L |= EMAC_BD_FIELD_MSK(TX_WR);
/* wrap back */
thiz->txIndexCPU = 0;
}
}
return err;
}
/**
* @brief
*
* @param flags
* @param len
* @param data_out
* @return int
*/
int emac_bd_rx_dequeue(uint32_t flags, uint32_t *len, uint8_t *data_out)
{
BL_Err_Type err = SUCCESS;
EMAC_BD_Desc_Type *DMADesc;
DMADesc = &thiz->bd[thiz->rxIndexCPU];
if (DMADesc->C_S_L & EMAC_BD_FIELD_MSK(RX_E)) {
/* current RX BD is empty */
err = NORESC;
*len = 0;
} else {
*len = (thiz->bd[thiz->rxIndexCPU].C_S_L & EMAC_BD_FIELD_MSK(RX_LEN)) >> BD_RX_LEN_POS;
if (data_out) {
ARCH_MemCpy_Fast(data_out, (const void *)DMADesc->Buffer, *len);
}
/* RX BD can be used for another receive */
DMADesc->C_S_L |= EMAC_BD_FIELD_MSK(RX_E);
/* move to next RX BD */
if ((++thiz->rxIndexCPU) > thiz->rxBuffLimit) {
/* the last BD */
DMADesc->C_S_L |= EMAC_BD_FIELD_MSK(RX_WR);
/* wrap back */
thiz->rxIndexCPU = thiz->txBuffLimit + 1;
}
}
return err;
}
/**
* @brief
*
* @param phyAddress
* @return int
*/
int emac_phy_set_address(uint16_t phyAddress)
{
EMAC_Phy_SetAddress(phyAddress);
return 0;
}
/**
* @brief
*
* @param fullDuplex
* @return int
*/
int emac_phy_config_full_duplex(uint8_t fullDuplex)
{
EMAC_Phy_Set_Full_Duplex(fullDuplex);
return 0;
}
/**
* @brief
*
* @param phyReg
* @param regValue
* @return int
*/
int emac_phy_reg_read(uint16_t phyReg, uint16_t *regValue)
{
if (EMAC_Phy_Read(phyReg, regValue) != SUCCESS) {
return -1;
}
return 0;
}
/**
* @brief
*
* @param phyReg
* @param regValue
* @return int
*/
int emac_phy_reg_write(uint16_t phyReg, uint16_t regValue)
{
if (EMAC_Phy_Write(phyReg, regValue) != SUCCESS) {
return -1;
}
return 0;
}
int emac_stop(void)
{
return EMAC_Disable();
}
int emac_start(void)
{
EMAC_Enable();
return 0;
}
int emac_start_tx(void)
{
return EMAC_Enable_TX();
}
int emac_stop_tx(void)
{
return EMAC_Disable_TX();
}
int emac_start_rx(void)
{
return EMAC_Enable_RX();
}
int emac_stop_rx(void)
{
return EMAC_Disable_RX();
}

View File

@@ -1,334 +1,346 @@
/**
* @file hal_flash.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "bl602_glb.h"
#include "bl602_xip_sflash.h"
#include "bl602_xip_sflash_ext.h"
#include "bl602_sf_cfg.h"
#include "bl602_sf_cfg_ext.h"
#include "hal_flash.h"
static uint32_t g_jedec_id = 0;
static SPI_Flash_Cfg_Type g_flash_cfg;
/**
* @brief flash_get_jedecid
*
* @return BL_Err_Type
*/
uint32_t flash_get_jedecid(void)
{
uint32_t jid = 0;
jid = ((g_jedec_id&0xff)<<16) + (g_jedec_id&0xff00) + ((g_jedec_id&0xff0000)>>16);
return jid;
}
/**
* @brief flash_get_cfg
*
* @return BL_Err_Type
*/
BL_Err_Type flash_get_cfg(uint8_t **cfg_addr, uint32_t *len)
{
*cfg_addr = (uint8_t *)&g_flash_cfg;
*len = sizeof(SPI_Flash_Cfg_Type);
return SUCCESS;
}
/**
* @brief flash_set_qspi_enable
*
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_set_qspi_enable(SPI_Flash_Cfg_Type *p_flash_cfg)
{
if ((p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
SFlash_Qspi_Enable(p_flash_cfg);
}
return SUCCESS;
}
/**
* @brief flash_set_l1c_wrap
*
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_set_l1c_wrap(SPI_Flash_Cfg_Type *p_flash_cfg)
{
if (((p_flash_cfg->ioMode >> 4) & 0x01) == 1) {
L1C_Set_Wrap(DISABLE);
} else {
L1C_Set_Wrap(ENABLE);
if ((p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
SFlash_SetBurstWrap(p_flash_cfg);
}
}
return SUCCESS;
}
/**
* @brief flash_config_init
*
* @return BL_Err_Type
*/
static BL_Err_Type ATTR_TCM_SECTION flash_config_init(SPI_Flash_Cfg_Type *p_flash_cfg, uint8_t *jedec_id)
{
BL_Err_Type ret = ERROR;
uint8_t isAesEnable = 0;
uint32_t jid = 0;
uint32_t offset = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
XIP_SFlash_State_Save(p_flash_cfg, &offset);
SFlash_GetJedecId(p_flash_cfg, (uint8_t *)&jid);
arch_memcpy(jedec_id, (uint8_t *)&jid, 3);
jid &= 0xFFFFFF;
g_jedec_id = jid;
ret = SF_Cfg_Get_Flash_Cfg_Need_Lock_Ext(jid, p_flash_cfg);
if (ret == SUCCESS) {
p_flash_cfg->mid = (jid & 0xff);
}
/* Set flash controler from p_flash_cfg */
flash_set_qspi_enable(p_flash_cfg);
flash_set_l1c_wrap(p_flash_cfg);
XIP_SFlash_State_Restore_Ext(p_flash_cfg, offset);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
return ret;
}
/**
* @brief multi flash adapter
*
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_init(void)
{
BL_Err_Type ret = ERROR;
uint8_t clkDelay = 1;
uint8_t clkInvert = 1;
uint32_t jedec_id = 0;
cpu_global_irq_disable();
SFlash_Cache_Flush();
SF_Cfg_Get_Flash_Cfg_Need_Lock_Ext(0, &g_flash_cfg);
SFlash_Cache_Flush();
cpu_global_irq_enable();
if (g_flash_cfg.mid != 0xff) {
return SUCCESS;
}
clkDelay = g_flash_cfg.clkDelay;
clkInvert = g_flash_cfg.clkInvert;
g_flash_cfg.ioMode = g_flash_cfg.ioMode & 0x0f;
ret = flash_config_init(&g_flash_cfg, (uint8_t *)&jedec_id);
#if 0
MSG("flash ID = %08x\r\n", jedec_id);
bflb_platform_dump((uint8_t *)&g_flash_cfg, sizeof(g_flash_cfg));
if (ret != SUCCESS) {
MSG("flash config init fail!\r\n");
}
#endif
g_flash_cfg.clkDelay = clkDelay;
g_flash_cfg.clkInvert = clkInvert;
return ret;
}
/**
* @brief read jedec id
*
* @param data
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read_jedec_id(uint8_t *data)
{
uint8_t isAesEnable = 0;
uint32_t jid = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
XIP_SFlash_GetJedecId_Need_Lock_Ext(&g_flash_cfg /*, g_flash_cfg.ioMode & 0x0f*/, (uint8_t *)&jid);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
jid &= 0xFFFFFF;
arch_memcpy(data, (void *)&jid, 4);
return SUCCESS;
}
/**
* @brief read flash data via xip
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read_via_xip(uint32_t addr, uint8_t *data, uint32_t len)
{
cpu_global_irq_disable();
SFlash_Cache_Flush();
XIP_SFlash_Read_Via_Cache_Need_Lock(addr, data, len);
SFlash_Cache_Flush();
cpu_global_irq_enable();
return SUCCESS;
}
/**
* @brief flash read data
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read(uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type ret = ERROR;
uint8_t isAesEnable = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
ret = XIP_SFlash_Read_Need_Lock_Ext(&g_flash_cfg, addr, data, len);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash write data
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_write(uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type ret = ERROR;
uint8_t isAesEnable = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
ret = XIP_SFlash_Write_Need_Lock_Ext(&g_flash_cfg, addr, data, len);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash erase
*
* @param startaddr
* @param endaddr
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_erase(uint32_t startaddr, uint32_t len)
{
BL_Err_Type ret = ERROR;
uint8_t isAesEnable = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
ret = XIP_SFlash_Erase_Need_Lock_Ext(&g_flash_cfg, startaddr, startaddr + len - 1);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash clear status register
*
* @param None
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_clear_status_register(void)
{
BL_Err_Type ret = ERROR;
uint8_t isAesEnable = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter(&isAesEnable);
ret = XIP_SFlash_Clear_Status_Register_Need_Lock(&g_flash_cfg);
XIP_SFlash_Opt_Exit(isAesEnable);
cpu_global_irq_enable();
return ret;
}
/**
* @brief set flash cache
*
* @param cont_read
* @param cache_enable
* @param cache_way_disable
* @param flash_offset
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_set_cache(uint8_t cont_read, uint8_t cache_enable, uint8_t cache_way_disable, uint32_t flash_offset)
{
uint8_t isAesEnable = 0;
uint32_t tmp[1];
BL_Err_Type stat;
SF_Ctrl_Set_Owner(SF_CTRL_OWNER_SAHB);
XIP_SFlash_Opt_Enter(&isAesEnable);
/* To make it simple, exit cont read anyway */
SFlash_Reset_Continue_Read(&g_flash_cfg);
if (g_flash_cfg.cReadSupport == 0) {
cont_read = 0;
}
if (cont_read == 1) {
stat = SFlash_Read(&g_flash_cfg, g_flash_cfg.ioMode & 0xf, 1, 0x00000000, (uint8_t *)tmp, sizeof(tmp));
if (SUCCESS != stat) {
XIP_SFlash_Opt_Exit(isAesEnable);
return ERROR;
}
}
/* Set default value */
SFlash_Cache_Enable_Set(0xf);
if (cache_enable) {
SF_Ctrl_Set_Flash_Image_Offset(flash_offset);
SFlash_Cache_Read_Enable(&g_flash_cfg, g_flash_cfg.ioMode & 0xf, cont_read, cache_way_disable);
}
XIP_SFlash_Opt_Exit(isAesEnable);
return SUCCESS;
}
/**
* @file hal_flash.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "bl702_glb.h"
#include "bl702_xip_sflash.h"
#include "bl702_xip_sflash_ext.h"
#include "bl702_sf_cfg.h"
#include "bl702_sf_cfg_ext.h"
#include "hal_flash.h"
static uint32_t g_jedec_id = 0;
static SPI_Flash_Cfg_Type g_flash_cfg;
/**
* @brief flash_get_jedecid
*
* @return BL_Err_Type
*/
uint32_t flash_get_jedecid(void)
{
uint32_t jid = 0;
jid = ((g_jedec_id&0xff)<<16) + (g_jedec_id&0xff00) + ((g_jedec_id&0xff0000)>>16);
return jid;
}
/**
* @brief flash_get_cfg
*
* @return BL_Err_Type
*/
BL_Err_Type flash_get_cfg(uint8_t **cfg_addr, uint32_t *len)
{
*cfg_addr = (uint8_t *)&g_flash_cfg;
*len = sizeof(SPI_Flash_Cfg_Type);
return SUCCESS;
}
/**
* @brief flash_set_qspi_enable
*
* @return BL_Err_Type
*/
static BL_Err_Type ATTR_TCM_SECTION flash_set_qspi_enable(SPI_Flash_Cfg_Type *p_flash_cfg)
{
if ((p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
SFlash_Qspi_Enable(p_flash_cfg);
}
return SUCCESS;
}
/**
* @brief flash_set_l1c_wrap
*
* @return BL_Err_Type
*/
static BL_Err_Type ATTR_TCM_SECTION flash_set_l1c_wrap(SPI_Flash_Cfg_Type *p_flash_cfg)
{
if (((p_flash_cfg->ioMode >> 4) & 0x01) == 1) {
L1C_Set_Wrap(DISABLE);
} else {
L1C_Set_Wrap(ENABLE);
if ((p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (p_flash_cfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
SFlash_SetBurstWrap(p_flash_cfg);
}
}
return SUCCESS;
}
/**
* @brief flash_config_init
*
* @return BL_Err_Type
*/
static BL_Err_Type ATTR_TCM_SECTION flash_config_init(SPI_Flash_Cfg_Type *p_flash_cfg, uint8_t *jedec_id)
{
BL_Err_Type ret = ERROR;
uint32_t jid = 0;
uint32_t offset = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
XIP_SFlash_State_Save(p_flash_cfg, &offset);
SFlash_GetJedecId(p_flash_cfg, (uint8_t *)&jid);
arch_memcpy(jedec_id, (uint8_t *)&jid, 3);
jid &= 0xFFFFFF;
g_jedec_id = jid;
ret = SF_Cfg_Get_Flash_Cfg_Need_Lock_Ext(jid, p_flash_cfg);
if (ret == SUCCESS) {
p_flash_cfg->mid = (jid & 0xff);
}
/* Set flash controler from p_flash_cfg */
flash_set_qspi_enable(p_flash_cfg);
flash_set_l1c_wrap(p_flash_cfg);
XIP_SFlash_State_Restore(p_flash_cfg, p_flash_cfg->ioMode & 0x0f, offset);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief multi flash adapter
*
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_init(void)
{
BL_Err_Type ret = ERROR;
uint8_t clkDelay = 1;
uint8_t clkInvert = 1;
uint32_t jedec_id = 0;
cpu_global_irq_disable();
L1C_Cache_Flush_Ext();
SF_Cfg_Get_Flash_Cfg_Need_Lock_Ext(0, &g_flash_cfg);
L1C_Cache_Flush_Ext();
cpu_global_irq_enable();
if (g_flash_cfg.mid != 0xff) {
return SUCCESS;
}
clkDelay = g_flash_cfg.clkDelay;
clkInvert = g_flash_cfg.clkInvert;
g_flash_cfg.ioMode = g_flash_cfg.ioMode & 0x0f;
ret = flash_config_init(&g_flash_cfg, (uint8_t *)&jedec_id);
#if 0
MSG("flash ID = %08x\r\n", jedec_id);
bflb_platform_dump((uint8_t *)&g_flash_cfg, sizeof(g_flash_cfg));
if (ret != SUCCESS) {
MSG("flash config init fail!\r\n");
}
#endif
g_flash_cfg.clkDelay = clkDelay;
g_flash_cfg.clkInvert = clkInvert;
return ret;
}
/**
* @brief read jedec id
*
* @param data
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read_jedec_id(uint8_t *data)
{
uint32_t jid = 0;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
XIP_SFlash_GetJedecId_Need_Lock(&g_flash_cfg, g_flash_cfg.ioMode & 0x0f, (uint8_t *)&jid);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
jid &= 0xFFFFFF;
arch_memcpy(data, (void *)&jid, 4);
return SUCCESS;
}
/**
* @brief read flash data via xip
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read_via_xip(uint32_t addr, uint8_t *data, uint32_t len)
{
cpu_global_irq_disable();
L1C_Cache_Flush_Ext();
XIP_SFlash_Read_Via_Cache_Need_Lock(addr, data, len);
L1C_Cache_Flush_Ext();
cpu_global_irq_enable();
return SUCCESS;
}
/**
* @brief flash read data
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_read(uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type ret = ERROR;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
ret = XIP_SFlash_Read_Need_Lock(&g_flash_cfg, g_flash_cfg.ioMode & 0x0f, addr, data, len);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash write data
*
* @param addr
* @param data
* @param len
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_write(uint32_t addr, uint8_t *data, uint32_t len)
{
BL_Err_Type ret = ERROR;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
ret = XIP_SFlash_Write_Need_Lock(&g_flash_cfg, g_flash_cfg.ioMode & 0x0f, addr, data, len);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash erase
*
* @param startaddr
* @param endaddr
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_erase(uint32_t startaddr, uint32_t len)
{
BL_Err_Type ret = ERROR;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
ret = XIP_SFlash_Erase_Need_Lock(&g_flash_cfg, g_flash_cfg.ioMode & 0x0f, startaddr, startaddr + len - 1);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash write protect set
*
* @param protect
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_write_protect_set(SFlash_Protect_Kh25v40_Type protect)
{
BL_Err_Type ret = ERROR;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
ret = XIP_SFlash_KH25V40_Write_Protect_Need_Lock(&g_flash_cfg, protect);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief flash clear status register
*
* @param None
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_clear_status_register(void)
{
BL_Err_Type ret = ERROR;
cpu_global_irq_disable();
XIP_SFlash_Opt_Enter();
ret = XIP_SFlash_Clear_Status_Register_Need_Lock(&g_flash_cfg);
XIP_SFlash_Opt_Exit();
cpu_global_irq_enable();
return ret;
}
/**
* @brief set flash cache
*
* @param cont_read
* @param cache_enable
* @param cache_way_disable
* @param flash_offset
* @return BL_Err_Type
*/
BL_Err_Type ATTR_TCM_SECTION flash_set_cache(uint8_t cont_read, uint8_t cache_enable, uint8_t cache_way_disable, uint32_t flash_offset)
{
uint32_t tmp[1];
BL_Err_Type stat;
SF_Ctrl_Set_Owner(SF_CTRL_OWNER_SAHB);
XIP_SFlash_Opt_Enter();
/* To make it simple, exit cont read anyway */
SFlash_Reset_Continue_Read(&g_flash_cfg);
if (g_flash_cfg.cReadSupport == 0) {
cont_read = 0;
}
if (cont_read == 1) {
stat = SFlash_Read(&g_flash_cfg, g_flash_cfg.ioMode & 0xf, 1, 0x00000000, (uint8_t *)tmp, sizeof(tmp));
if (SUCCESS != stat) {
XIP_SFlash_Opt_Exit();
return ERROR;
}
}
/* Set default value */
L1C_Cache_Enable_Set(0xf);
if (cache_enable) {
SF_Ctrl_Set_Flash_Image_Offset(flash_offset);
SFlash_Cache_Read_Enable(&g_flash_cfg, g_flash_cfg.ioMode & 0xf, cont_read, cache_way_disable);
}
XIP_SFlash_Opt_Exit();
return SUCCESS;
}

View File

@@ -1,42 +1,39 @@
/**
* *****************************************************************************
* @file hal_gpio.c
* @version 0.1
* @date 2021-03-01
* @brief
* *****************************************************************************
* @attention
*
* <h2><center>&copy; COPYRIGHT(c) 2020 Bouffalo Lab</center></h2>
* Copyright (c) 2021 Bouffalolab team
*
* 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 Bouffalo Lab nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you 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
*
* 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.
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* *****************************************************************************
*/
#include "bl602_glb.h"
#include "bl602_gpio.h"
#include "bl702_glb.h"
#include "bl702_gpio.h"
#include "hal_gpio.h"
static void GPIO_IRQ(void);
struct gpio_int_cfg_private {
slist_t list;
uint32_t pin;
void (*cbfun)(uint32_t pin);
};
static slist_t gpio_int_head = SLIST_OBJECT_INIT(gpio_int_head);
/**
* @brief
*
@@ -82,15 +79,14 @@ void gpio_set_mode(uint32_t pin, uint32_t mode)
gpio_cfg.gpioMode = GPIO_MODE_INPUT;
gpio_cfg.pullType = GPIO_PULL_DOWN;
break;
case GPIO_HZ_MODE:
GLB_GPIO_Set_HZ(pin);
default:
CPU_Interrupt_Disable(GPIO_INT0_IRQn);
GLB_GPIO_IntMask(pin, MASK);
gpio_cfg.gpioMode = GPIO_MODE_INPUT;
GLB_GPIO_INT0_IRQHandler_Install();
if (mode == GPIO_ASYNC_RISING_TRIGER_INT_MODE) {
gpio_cfg.pullType = GPIO_PULL_DOWN;
GLB_Set_GPIO_IntMod(pin, GLB_GPIO_INT_CONTROL_ASYNC, GLB_GPIO_INT_TRIG_POS_PULSE);
@@ -135,7 +131,6 @@ void gpio_set_mode(uint32_t pin, uint32_t mode)
return;
}
CPU_Interrupt_Enable(GPIO_INT0_IRQn);
break;
}
@@ -149,7 +144,14 @@ void gpio_set_mode(uint32_t pin, uint32_t mode)
*/
void gpio_write(uint32_t pin, uint32_t value)
{
GLB_GPIO_Write(pin, value);
uint32_t tmp = BL_RD_REG(GLB_BASE, GLB_GPIO_OUTPUT);
if (value)
tmp |= (1 << pin);
else
tmp &= ~(1 << pin);
BL_WR_REG(GLB_BASE, GLB_GPIO_OUTPUT, tmp);
}
/**
* @brief
@@ -158,6 +160,9 @@ void gpio_write(uint32_t pin, uint32_t value)
*/
void gpio_toggle(uint32_t pin)
{
uint32_t tmp = BL_RD_REG(GLB_BASE, GLB_GPIO_OUTPUT);
tmp ^= (1 << pin);
BL_WR_REG(GLB_BASE, GLB_GPIO_OUTPUT, tmp);
}
/**
* @brief
@@ -167,7 +172,7 @@ void gpio_toggle(uint32_t pin)
*/
int gpio_read(uint32_t pin)
{
return GLB_GPIO_Read(pin);
return ((BL_RD_REG(GLB_BASE, GLB_GPIO_INPUT) & (1 << pin)) ? 1 : 0);
}
/**
* @brief
@@ -175,9 +180,15 @@ int gpio_read(uint32_t pin)
* @param pin
* @param cbFun
*/
void gpio_attach_irq(uint32_t pin, void (*cbFun)(void))
void gpio_attach_irq(uint32_t pin, void (*cbfun)(uint32_t pin))
{
GLB_GPIO_INT0_Callback_Install(pin, cbFun);
struct gpio_int_cfg_private *int_cfg = malloc(sizeof(struct gpio_int_cfg_private));
int_cfg->cbfun = cbfun;
int_cfg->pin = pin;
slist_add_tail(&gpio_int_head, &int_cfg->list);
CPU_Interrupt_Disable(GPIO_INT0_IRQn);
Interrupt_Handler_Register(GPIO_INT0_IRQn, GPIO_IRQ);
CPU_Interrupt_Enable(GPIO_INT0_IRQn);
}
/**
* @brief
@@ -192,4 +203,32 @@ void gpio_irq_enable(uint32_t pin, uint8_t enabled)
} else {
GLB_GPIO_IntMask(pin, MASK);
}
}
static void GPIO_IRQ(void)
{
slist_t *i;
uint32_t timeOut = 0;
#define GLB_GPIO_INT0_CLEAR_TIMEOUT (32)
slist_for_each(i, &gpio_int_head)
{
struct gpio_int_cfg_private *int_cfg = slist_entry(i, struct gpio_int_cfg_private, list);
if (SET == GLB_Get_GPIO_IntStatus(int_cfg->pin)) {
int_cfg->cbfun(int_cfg->pin);
GLB_GPIO_IntClear(int_cfg->pin, SET);
/* timeout check */
timeOut = GLB_GPIO_INT0_CLEAR_TIMEOUT;
do {
timeOut--;
} while ((SET == GLB_Get_GPIO_IntStatus(int_cfg->pin)) && timeOut);
if (!timeOut) {
//MSG("WARNING: Clear GPIO interrupt status fail.\r\n");
}
GLB_GPIO_IntClear(int_cfg->pin, RESET);
}
}
}

View File

@@ -0,0 +1,172 @@
/**
* @file hal_i2c.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_i2c.h"
#include "bl702_i2c.h"
#include "bl702_glb.h"
static i2c_device_t i2cx_device[I2C_MAX_INDEX] = {
#ifdef BSP_USING_I2C0
I2C0_CONFIG,
#endif
#ifdef BSP_USING_I2C1
I2C1_CONFIG,
#endif
};
/**
* @brief
*
* @param dev
* @param oflag
* @return int
*/
int i2c_open(struct device *dev, uint16_t oflag)
{
i2c_device_t *i2c_device = (i2c_device_t *)dev;
if (i2c_device->mode == I2C_HW_MODE) {
I2C_SetPrd(i2c_device->id, i2c_device->phase);
}
return 0;
}
// int i2c_close(struct device *dev)
// {
// return 0;
// }
// int i2c_control(struct device *dev, int cmd, void *args)
// {
// //i2c_device_t *i2c_device = (i2c_device_t *)dev;
// switch (cmd)
// {
// case DEVICE_CTRL_SET_INT /* constant-expression */:
// break;
// case DEVICE_CTRL_CLR_INT /* constant-expression */:
// /* code */
// /* Enable UART interrupt*/
// break;
// case DEVICE_CTRL_GET_INT /* constant-expression */:
// /* code */
// break;
// case DEVICE_CTRL_CONFIG /* constant-expression */:
// /* code */
// break;
// case 4 /* constant-expression */:
// /* code */
// break;
// case 5 /* constant-expression */:
// /* code */
// break;
// default:
// break;
// }
// return 0;
// }
// int i2c_write(struct device *dev, uint32_t pos, const void *buffer, uint32_t size)
// {
// return 0;
// }
// int i2c_read(struct device *dev, uint32_t pos, void *buffer, uint32_t size)
// {
// return 0;
// }
/**
* @brief
*
* @param index
* @param name
* @param flag
* @return int
*/
int i2c_register(enum i2c_index_type index, const char *name)
{
struct device *dev;
if (I2C_MAX_INDEX == 0) {
return -DEVICE_EINVAL;
}
dev = &(i2cx_device[index].parent);
dev->open = i2c_open;
dev->close = NULL;
dev->control = NULL;
dev->write = NULL;
dev->read = NULL;
dev->type = DEVICE_CLASS_I2C;
dev->handle = NULL;
return device_register(dev, name);
}
/**
* @brief
*
* @param dev
* @param msgs
* @param num
* @return uint32_t
*/
int i2c_transfer(struct device *dev, i2c_msg_t msgs[], uint32_t num)
{
i2c_msg_t *msg;
I2C_Transfer_Cfg i2cCfg = { 0 };
i2c_device_t *i2c_device = (i2c_device_t *)dev;
if (i2c_device->mode == I2C_HW_MODE) {
for (uint32_t i = 0; i < num; i++) {
msg = &msgs[i];
i2cCfg.slaveAddr = msg->slaveaddr;
i2cCfg.stopEveryByte = DISABLE;
i2cCfg.subAddr = msg->subaddr;
i2cCfg.dataSize = msg->len;
i2cCfg.data = msg->buf;
if (msg->flags & SUB_ADDR_0BYTE) {
i2cCfg.subAddrSize = 0;
} else if (msg->flags & SUB_ADDR_1BYTE) {
i2cCfg.subAddrSize = 1;
} else if (msg->flags & SUB_ADDR_2BYTE) {
i2cCfg.subAddrSize = 2;
}
if ((msg->flags & I2C_RW_MASK) == I2C_WR) {
return I2C_MasterSendBlocking(i2c_device->id, &i2cCfg);
} else if ((msg->flags & I2C_RW_MASK) == I2C_RD) {
return I2C_MasterReceiveBlocking(i2c_device->id, &i2cCfg);
}
}
} else {
}
return 0;
}

View File

@@ -0,0 +1,379 @@
/**
* @file hal_i2s.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_i2s.h"
#include "hal_clock.h"
#include "hal_dma.h"
#include "bl702_i2s.h"
#include "bl702_glb.h"
#include "i2s_config.h"
static i2s_device_t i2sx_device[I2S_MAX_INDEX] = {
#ifdef BSP_USING_I2S0
I2S0_CONFIG,
#endif
};
int i2s_open(struct device *dev, uint16_t oflag)
{
i2s_device_t *i2s_device = (i2s_device_t *)dev;
I2S_CFG_Type i2sCfg = { 0 };
I2S_FifoCfg_Type fifoCfg = { 0 };
i2sCfg.audioFreqHz = system_clock_get(SYSTEM_CLOCK_AUPLL);
i2sCfg.sampleFreqHz = i2s_device->sampl_freq_hz;
/*!< default I2S msb first */
i2sCfg.endianType = I2S_DATA_ENDIAN;
/* Config the I2S type */
switch (i2s_device->interface_mode) {
case I2S_MODE_STD:
i2sCfg.modeType = I2S_MODE_I2S_LEFT;
i2sCfg.fsMode = I2S_FS_MODE_EVEN;
i2sCfg.dataOffset = 1;
break;
case I2S_MODE_LEFT:
i2sCfg.modeType = I2S_MODE_I2S_LEFT;
i2sCfg.fsMode = I2S_FS_MODE_EVEN;
i2sCfg.dataOffset = 0;
break;
case I2S_MODE_RIGHT:
i2sCfg.modeType = I2S_MODE_I2S_RIGHT;
i2sCfg.fsMode = I2S_FS_MODE_EVEN;
i2sCfg.dataOffset = 0;
break;
case I2S_MODE_DSP_A:
i2sCfg.modeType = I2S_MODE_I2S_DSP;
i2sCfg.fsMode = I2S_FS_MODE_1T;
i2sCfg.dataOffset = 1;
break;
case I2S_MODE_DSP_B:
i2sCfg.modeType = I2S_MODE_I2S_DSP;
i2sCfg.fsMode = I2S_FS_MODE_1T;
i2sCfg.dataOffset = 0;
break;
default:
return ERROR;
break;
}
/* Config the frame/data Size */
switch (i2s_device->frame_size) {
case I2S_FRAME_LEN_8:
i2sCfg.frameSize = I2S_SIZE_FRAME_8;
break;
case I2S_FRAME_LEN_16:
i2sCfg.frameSize = I2S_SIZE_FRAME_16;
break;
case I2S_FRAME_LEN_24:
i2sCfg.frameSize = I2S_SIZE_FRAME_24;
break;
case I2S_FRAME_LEN_32:
i2sCfg.frameSize = I2S_SIZE_FRAME_32;
break;
default:
return ERROR;
break;
}
switch (i2s_device->data_size) {
case I2S_DATA_LEN_8:
i2sCfg.dataSize = I2S_SIZE_DATA_8;
break;
case I2S_DATA_LEN_16:
i2sCfg.dataSize = I2S_SIZE_DATA_16;
break;
case I2S_DATA_LEN_24:
i2sCfg.dataSize = I2S_SIZE_DATA_24;
break;
case I2S_DATA_LEN_32:
i2sCfg.dataSize = I2S_SIZE_DATA_32;
break;
default:
return ERROR;
break;
}
fifoCfg.lRMerge = DISABLE;
fifoCfg.frameDataExchange = DISABLE;
/* Config the Channel number */
switch (i2s_device->channel_num) {
case I2S_FS_CHANNELS_NUM_MONO:
i2sCfg.monoMode = ENABLE;
i2sCfg.fsChannel = I2S_FS_CHANNELS_2;
i2sCfg.monoModeChannel = I2S_MONO_CHANNEL;
break;
case I2S_FS_CHANNELS_NUM_2:
i2sCfg.monoMode = DISABLE;
i2sCfg.fsChannel = I2S_FS_CHANNELS_2;
if (i2s_device->data_size == I2S_DATA_LEN_8 || i2s_device->data_size == I2S_DATA_LEN_16) {
fifoCfg.lRMerge = ENABLE;
fifoCfg.frameDataExchange = I2S_LR_EXCHANGE;
}
break;
case I2S_FS_CHANNELS_NUM_3:
if ((i2s_device->interface_mode != I2S_MODE_DSP_A) && (i2s_device->interface_mode != I2S_MODE_DSP_B)) {
return ERROR;
}
i2sCfg.monoMode = DISABLE;
i2sCfg.fsChannel = I2S_FS_CHANNELS_3;
break;
case I2S_FS_CHANNELS_NUM_4:
if ((i2s_device->interface_mode != I2S_MODE_DSP_A) && (i2s_device->interface_mode != I2S_MODE_DSP_B)) {
return ERROR;
}
i2sCfg.monoMode = DISABLE;
i2sCfg.fsChannel = I2S_FS_CHANNELS_4;
default:
return ERROR;
break;
}
/* Config the bclk/fs invert */
i2sCfg.bclkInvert = I2S_BCLK_INVERT;
i2sCfg.fsInvert = I2S_FS_INVERT;
if (oflag & DEVICE_OFLAG_INT_TX) {
}
if (oflag & DEVICE_OFLAG_INT_RX) {
}
fifoCfg.txfifoDmaEnable = (oflag & DEVICE_OFLAG_DMA_TX) ? ENABLE : DISABLE;
fifoCfg.rxfifoDmaEnable = (oflag & DEVICE_OFLAG_DMA_RX) ? ENABLE : DISABLE;
fifoCfg.txFifoLevel = i2s_device->fifo_threshold;
fifoCfg.rxFifoLevel = i2s_device->fifo_threshold;
/* I2S Init */
I2S_Disable();
I2S_Init(&i2sCfg);
I2S_FifoConfig(&fifoCfg);
if (i2s_device->iis_mode == I2S_MODE_MASTER)
I2S_Enable(I2S_ROLE_MASTER);
else if (i2s_device->iis_mode == I2S_MODE_SLAVE)
I2S_Enable(I2S_ROLE_SLAVE);
return 0;
}
int i2s_close(struct device *dev)
{
//i2s_device_t* uart_device = (i2s_device_t*)dev;
I2S_Disable();
GLB_AHB_Slave1_Reset(BL_AHB_SLAVE1_I2S);
return 0;
}
int i2s_control(struct device *dev, int cmd, void *args)
{
i2s_device_t *i2s_device = (i2s_device_t *)dev;
I2S_CFG_Type i2sCfg;
switch (cmd) {
case DEVICE_CTRL_SET_INT:
for (uint16_t i = 0, j = 1; i < 8; i++, j <<= 1) {
if ((uint32_t)args & j) {
/* code */
}
}
break;
case DEVICE_CTRL_CLR_INT:
for (uint16_t i = 0, j = 1; i < 8; i++, j <<= 1) {
if ((uint32_t)args & j) {
/* code */
}
}
break;
case DEVICE_CTRL_GET_INT:
/* code */
break;
case DEVICE_CTRL_RESUME:
/* code */
break;
case DEVICE_CTRL_SUSPEND:
/* code */
break;
case DEVICE_CTRL_CONFIG:
/* code */
break;
case DEVICE_CTRL_ATTACH_TX_DMA /* constant-expression */:
i2s_device->tx_dma = (struct device *)args;
break;
case DEVICE_CTRL_ATTACH_RX_DMA /* constant-expression */:
i2s_device->rx_dma = (struct device *)args;
break;
case DEVICE_CTRL_I2S_GET_TX_FIFO:
return I2S_GetTxFIFO_AvlCnt();
case DEVICE_CTRL_I2S_GET_RX_FIFO:
return I2S_GetRxFIFO_AvlCnt();
case DEVICE_CTRL_I2S_SET_SAMPL_FREQ:
switch (i2s_device->frame_size) {
case I2S_FRAME_LEN_8:
i2sCfg.frameSize = I2S_SIZE_FRAME_8;
break;
case I2S_FRAME_LEN_16:
i2sCfg.frameSize = I2S_SIZE_FRAME_16;
break;
case I2S_FRAME_LEN_24:
i2sCfg.frameSize = I2S_SIZE_FRAME_24;
break;
case I2S_FRAME_LEN_32:
i2sCfg.frameSize = I2S_SIZE_FRAME_32;
break;
default:
return ERROR;
break;
}
i2sCfg.audioFreqHz = system_clock_get(SYSTEM_CLOCK_AUPLL);
i2sCfg.sampleFreqHz = (uint32_t)args;
I2S_SetBclkPeriod(&i2sCfg);
break;
default:
return ERROR;
break;
}
return SUCCESS;
}
int i2s_write(struct device *dev, uint32_t pos, const void *buffer, uint32_t size)
{
i2s_device_t *i2s_device = (i2s_device_t *)dev;
if (dev->oflag & DEVICE_OFLAG_DMA_TX) {
struct device *dma_ch = (struct device *)i2s_device->tx_dma;
if (!dma_ch) {
return -1;
}
if (i2s_device->id == 0) {
dma_reload(dma_ch, (uint32_t)buffer, (uint32_t)DMA_ADDR_I2S_TDR, size);
dma_channel_start(dma_ch);
} else if (i2s_device->id == 1) {
dma_reload(dma_ch, (uint32_t)buffer, (uint32_t)DMA_ADDR_I2S_TDR, size);
dma_channel_start(dma_ch);
}
return 0;
} else {
return 0;
}
}
int i2s_read(struct device *dev, uint32_t pos, void *buffer, uint32_t size)
{
i2s_device_t *i2s_device = (i2s_device_t *)dev;
if (dev->oflag & DEVICE_OFLAG_DMA_RX) {
struct device *dma_ch = (struct device *)i2s_device->rx_dma;
if (!dma_ch) {
return -1;
}
if (i2s_device->id == 0) {
dma_reload(dma_ch, (uint32_t)DMA_ADDR_I2S_RDR, (uint32_t)buffer, size);
dma_channel_start(dma_ch);
} else if (i2s_device->id == 1) {
dma_reload(dma_ch, (uint32_t)DMA_ADDR_I2S_RDR, (uint32_t)buffer, size);
dma_channel_start(dma_ch);
}
return 0;
} else {
return 0;
}
}
int i2s_register(enum i2s_index_type index, const char *name)
{
struct device *dev;
if (I2S_MAX_INDEX == 0) {
return -DEVICE_EINVAL;
}
dev = &(i2sx_device[index].parent);
dev->open = i2s_open;
dev->close = i2s_close;
dev->control = i2s_control;
dev->write = i2s_write;
dev->read = i2s_read;
dev->type = DEVICE_CLASS_I2S;
dev->handle = NULL;
return device_register(dev, name);
}
void i2s_isr(i2s_device_t *handle)
{
return;
}
void I2S_IRQ(void)
{
i2s_isr(&i2sx_device[0]);
}

View File

@@ -0,0 +1,159 @@
/**
* @file hal_keyscan.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "hal_keyscan.h"
#include "kys_reg.h"
#include "bl702_glb.h"
#ifdef BSP_USING_KEYSCAN
static void KeyScan_IRQ(void);
#endif
static keyscan_device_t keyscan_device[KEYSCAN_MAX_INDEX] = {
#ifdef BSP_USING_KEYSCAN
KEYSCAN_CONFIG
#endif
};
/**
* @brief
*
* @param dev
* @param oflag
* @return int
*/
int keyscan_open(struct device *dev, uint16_t oflag)
{
uint32_t tmpVal;
keyscan_device_t *keyscan_device_local = (keyscan_device_t *)dev;
tmpVal = BL_RD_REG(KYS_BASE, KYS_KS_CTRL);
/* Set col and row */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_COL_NUM, keyscan_device_local->col_num - 1);
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_ROW_NUM, keyscan_device_local->row_num - 1);
/* Set idle duration between column scans */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_RC_EXT, 0);
/* ghost key event detection not support*/
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_GHOST_EN, 0);
if (keyscan_device_local->deglitch_count) {
/* Enable or disable deglitch function */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_DEG_EN, 1);
/* Set deglitch count */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_DEG_CNT, keyscan_device_local->deglitch_count);
} else {
/* Enable or disable deglitch function */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_DEG_EN, 0);
/* Set deglitch count */
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, KYS_DEG_CNT, 0);
}
/* Write back */
BL_WR_REG(KYS_BASE, KYS_KS_CTRL, tmpVal);
return 0;
}
int keyscan_control(struct device *dev, int cmd, void *args)
{
switch (cmd) {
case DEVICE_CTRL_SET_INT /* constant-expression */:
#ifdef BSP_USING_KEYSCAN
Interrupt_Handler_Register(KYS_IRQn, KeyScan_IRQ);
#endif
BL_WR_REG(KYS_BASE, KYS_KS_INT_EN, 1);
CPU_Interrupt_Enable(KYS_IRQn);
break;
case DEVICE_CTRL_CLR_INT /* constant-expression */:
Interrupt_Handler_Register(KYS_IRQn, NULL);
BL_WR_REG(KYS_BASE, KYS_KS_INT_EN, 0);
CPU_Interrupt_Disable(KYS_IRQn);
break;
case DEVICE_CTRL_GET_INT:
return (BL_RD_REG(KYS_BASE, KYS_KS_INT_STS) & 0xf);
case DEVICE_CTRL_RESUME: {
uint32_t tmpVal;
tmpVal = BL_RD_REG(KYS_BASE, KYS_KS_CTRL);
BL_WR_REG(KYS_BASE, KYS_KS_CTRL, BL_SET_REG_BIT(tmpVal, KYS_KS_EN));
} break;
case DEVICE_CTRL_SUSPEND: {
uint32_t tmpVal;
tmpVal = BL_RD_REG(KYS_BASE, KYS_KS_CTRL);
BL_WR_REG(KYS_BASE, KYS_KS_CTRL, BL_CLR_REG_BIT(tmpVal, KYS_KS_EN));
} break;
case DEVICE_CTRL_KEYSCAN_GET_KEYCODE: {
uint32_t *key_code = (uint32_t *)args;
*key_code = BL_RD_REG(KYS_BASE, KYS_KEYCODE_VALUE);
BL_WR_REG(KYS_BASE, KYS_KEYCODE_CLR, 0xf);
} break;
default:
break;
}
return 0;
}
/**
* @brief
*
* @param index
* @param name
* @param flag
* @return int
*/
int keyscan_register(enum keyscan_index_type index, const char *name)
{
struct device *dev;
if (KEYSCAN_MAX_INDEX == 0) {
return -DEVICE_EINVAL;
}
dev = &(keyscan_device[index].parent);
dev->open = keyscan_open;
dev->close = NULL;
dev->control = keyscan_control;
dev->write = NULL;
dev->read = NULL;
dev->type = DEVICE_CLASS_KEYSCAN;
dev->handle = NULL;
return device_register(dev, name);
}
#if defined(BSP_USING_KEYSCAN)
static void KeyScan_IRQ(void)
{
if (keyscan_device[KEYSCAN_INDEX].parent.callback) {
keyscan_device[KEYSCAN_INDEX].parent.callback(&keyscan_device[KEYSCAN_INDEX].parent, (void *)(BL_RD_REG(KYS_BASE, KYS_KEYCODE_VALUE)), 0, KEYSCAN_EVENT_TRIG);
}
BL_WR_REG(KYS_BASE, KYS_KEYCODE_CLR, 0xf);
}
#endif

View File

@@ -0,0 +1,131 @@
/**
* @file hal_mjpeg.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "bl702_mjpeg.h"
#include "bl702_glb.h"
#include "hal_mjpeg.h"
void mjpeg_init(mjpeg_device_t *mjpeg_cfg)
{
MJPEG_Packet_Type packetCfg = { 0 };
MJPEG_CFG_Type mjpegCfg = {
.burst = MJPEG_BURST_INCR16,
.quality = mjpeg_cfg->quality,
.yuv = mjpeg_cfg->yuv_format,
.waitCount = 0x400,
.bufferMjpeg = mjpeg_cfg->write_buffer_addr,
.sizeMjpeg = mjpeg_cfg->write_buffer_size,
.bufferCamYY = mjpeg_cfg->read_buffer_addr,
.sizeCamYY = mjpeg_cfg->read_buffer_size,
.bufferCamUV = 0,
.sizeCamUV = 0,
.resolutionX = mjpeg_cfg->resolution_x,
.resolutionY = mjpeg_cfg->resolution_y,
.bitOrderEnable = ENABLE,
.evenOrderEnable = ENABLE,
.swapModeEnable = DISABLE,
.overStopEnable = ENABLE,
.reflectDmy = DISABLE,
.verticalDmy = DISABLE,
.horizationalDmy = DISABLE,
};
GLB_AHB_Slave1_Clock_Gate(DISABLE, BL_AHB_SLAVE1_MJPEG);
uint32_t tmpVal;
/* Disable mjpeg module */
tmpVal = BL_RD_REG(MJPEG_BASE, MJPEG_CONTROL_1);
tmpVal = BL_CLR_REG_BIT(tmpVal, MJPEG_REG_MJPEG_ENABLE);
BL_WR_REG(MJPEG_BASE, MJPEG_CONTROL_1, tmpVal);
MJPEG_Init(&mjpegCfg);
if (mjpeg_cfg->packet_cut_mode & MJPEG_PACKET_ADD_DEFAULT) {
packetCfg.packetEnable = ENABLE;
packetCfg.packetHead = mjpeg_cfg->packet_head_length;
packetCfg.packetBody = mjpeg_cfg->packet_body_length;
packetCfg.packetTail = mjpeg_cfg->packet_tail_length;
}
if (mjpeg_cfg->packet_cut_mode & MJPEG_PACKET_ADD_FRAME_HEAD) {
packetCfg.frameHead = mjpeg_cfg->frame_head_length;
}
if (mjpeg_cfg->packet_cut_mode & MJPEG_PACKET_ADD_FRAME_TAIL) {
packetCfg.frameTail = ENABLE;
}
if (mjpeg_cfg->packet_cut_mode & MJPEG_PACKET_ADD_END_TAIL) {
packetCfg.endToTail = ENABLE;
}
MJPEG_Packet_Config(&packetCfg);
if (mjpeg_cfg->yuv_format == MJPEG_YUV_FORMAT_YUV422_INTERLEAVE) {
MJPEG_Set_YUYV_Order_Interleave(1, 0, 3, 2);
}
}
void mjpeg_start(void)
{
uint32_t tmpVal;
/* Enable mjpeg module */
tmpVal = BL_RD_REG(MJPEG_BASE, MJPEG_CONTROL_1);
tmpVal = BL_SET_REG_BIT(tmpVal, MJPEG_REG_MJPEG_ENABLE);
BL_WR_REG(MJPEG_BASE, MJPEG_CONTROL_1, tmpVal);
}
void mjpeg_stop(void)
{
uint32_t tmpVal;
/* Disable mjpeg module */
tmpVal = BL_RD_REG(MJPEG_BASE, MJPEG_CONTROL_1);
tmpVal = BL_CLR_REG_BIT(tmpVal, MJPEG_REG_MJPEG_ENABLE);
BL_WR_REG(MJPEG_BASE, MJPEG_CONTROL_1, tmpVal);
}
uint8_t mjpeg_get_one_frame(uint8_t **pic, uint32_t *len, uint8_t *q)
{
MJPEG_Frame_Info info;
arch_memset(&info, 0, sizeof(info));
MJPEG_Get_Frame_Info(&info);
if (info.validFrames == 0) {
return ERROR;
}
*pic = (uint8_t *)(info.curFrameAddr);
*len = info.curFrameBytes;
*q = info.curFrameQ;
return SUCCESS;
}
void mjpeg_drop_one_frame(void)
{
MJPEG_Pop_Frame();
}

View File

@@ -21,7 +21,7 @@
*
*/
#include "hal_mtimer.h"
#include "bl602_glb.h"
#include "bl702_glb.h"
#include "risc-v/Core/Include/clic.h"
static void (*systick_callback)(void);

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,321 @@
/**
* @file hal_pm_util.c
* @brief
*
* Copyright (c) 2021 Bouffalolab team
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
*/
#include "bl702_romdriver.h"
#include "bl702_sf_ctrl.h"
#include "bl702_glb.h"
#include "hal_clock.h"
#include "hal_pm.h"
#include "hal_pm_util.h"
/* Cache Way Disable, will get from l1c register */
extern uint8_t cacheWayDisable;
/* PSRAM IO Configuration, will get from glb register */
extern uint32_t psramIoCfg;
/* Flash offset value, will get from sf_ctrl register */
extern uint32_t flash_offset;
extern void pm_pds31_fast_mode_enter(enum pm_pds_sleep_level pds_level, uint32_t sleep_time);
extern SPI_Flash_Cfg_Type *flash_cfg;
void ATTR_PDS_RAM_SECTION pm_pds_fastboot_entry(void);
void (*hardware_recovery)(void) = NULL;
/**
* @brief hal_pds_enter_with_time_compensation
*
* @param pdsLevel pds level support 0~3,31
* @param pdsSleepCycles user set sleep time, clock of pds_time is 32768hz
* @return uint32_t actual sleep time(ms)
*
* @note If necessaryplease application layer call vTaskStepTick
*/
uint32_t hal_pds_enter_with_time_compensation(uint32_t pdsLevel, uint32_t pdsSleepCycles)
{
uint32_t rtcLowBeforeSleep = 0, rtcHighBeforeSleep = 0;
uint32_t rtcLowAfterSleep = 0, rtcHighAfterSleep = 0;
uint32_t actualSleepDuration_32768cycles = 0;
uint32_t actualSleepDuration_ms = 0;
pm_set_wakeup_callback(pm_pds_fastboot_entry);
HBN_Get_RTC_Timer_Val(&rtcLowBeforeSleep, &rtcHighBeforeSleep);
pm_pds31_fast_mode_enter(pdsLevel, pdsSleepCycles);
HBN_Get_RTC_Timer_Val(&rtcLowAfterSleep, &rtcHighAfterSleep);
CHECK_PARAM((rtcHighAfterSleep - rtcHighBeforeSleep) <= 1); // make sure sleep less than 1 hour (2^32 us > 1 hour)
actualSleepDuration_32768cycles = (rtcLowAfterSleep - rtcLowBeforeSleep);
actualSleepDuration_ms = (actualSleepDuration_32768cycles >> 5) - (actualSleepDuration_32768cycles >> 11) - (actualSleepDuration_32768cycles >> 12);
// vTaskStepTick(actualSleepDuration_ms);
return actualSleepDuration_ms;
}
/**
* @brief get delay value of spi flash init
*
* @param delay_index
* @return uint8_t
*/
static uint8_t ATTR_PDS_RAM_SECTION bflb_spi_flash_get_delay_val(uint8_t delay_index)
{
switch (delay_index) {
case 0:
return 0x00;
case 1:
return 0x80;
case 2:
return 0xc0;
case 3:
return 0xe0;
case 4:
return 0xf0;
case 5:
return 0xf8;
case 6:
return 0xfc;
case 7:
return 0xfe;
default:
return 0x00;
}
}
/**
* @brief config spi flash
*
* @param pFlashCfg flash parameter
*/
static void ATTR_PDS_RAM_SECTION bflb_spi_flash_set_sf_ctrl(SPI_Flash_Cfg_Type *pFlashCfg)
{
SF_Ctrl_Cfg_Type sfCtrlCfg;
uint8_t delay_index;
sfCtrlCfg.owner = SF_CTRL_OWNER_SAHB;
/* bit0-3 for clk delay */
sfCtrlCfg.clkDelay = (pFlashCfg->clkDelay & 0x0f);
/* bit0 for clk invert */
sfCtrlCfg.clkInvert = pFlashCfg->clkInvert & 0x01;
/* bit1 for rx clk invert */
sfCtrlCfg.rxClkInvert = (pFlashCfg->clkInvert >> 1) & 0x01;
/* bit4-6 for do delay */
delay_index = (pFlashCfg->clkDelay >> 4) & 0x07;
sfCtrlCfg.doDelay = bflb_spi_flash_get_delay_val(delay_index);
/* bit2-4 for di delay */
delay_index = (pFlashCfg->clkInvert >> 2) & 0x07;
sfCtrlCfg.diDelay = bflb_spi_flash_get_delay_val(delay_index);
/* bit5-7 for oe delay */
delay_index = (pFlashCfg->clkInvert >> 5) & 0x07;
sfCtrlCfg.oeDelay = bflb_spi_flash_get_delay_val(delay_index);
RomDriver_SFlash_Init(&sfCtrlCfg);
}
/**
* @brief
*
* @param media_boot
* @return int32_t
*/
int32_t ATTR_PDS_RAM_SECTION pm_spi_flash_init(uint8_t media_boot)
{
uint32_t stat;
uint32_t jdecId = 0;
uint32_t flash_read_try = 0;
/*use fclk as flash clok */
RomDriver_GLB_Set_SF_CLK(1, GLB_SFLASH_CLK_XCLK, 0); // 32M
RomDriver_SF_Ctrl_Set_Clock_Delay(0);
bflb_spi_flash_set_sf_ctrl(flash_cfg);
/* Wake flash up from power down */
RomDriver_SFlash_Releae_Powerdown(flash_cfg);
//ARCH_Delay_US(15*((pFlashCfg->pdDelay&0x7)+1));
RomDriver_BL702_Delay_US(120);
do {
if (flash_read_try > 4) {
// bflb_bootrom_printd("Flash read id TO\r\n");
break;
} else if (flash_read_try > 0) {
RomDriver_BL702_Delay_US(500);
}
// bflb_bootrom_printd("reset flash\r\n");
/* Exit form continous read for accepting command */
RomDriver_SFlash_Reset_Continue_Read(flash_cfg);
/* Send software reset command(80bv has no this command)to deburst wrap for ISSI like */
RomDriver_SFlash_Software_Reset(flash_cfg);
/* Disable burst may be removed(except for 80BV) and only work with winbond,but just for make sure */
RomDriver_SFlash_Write_Enable(flash_cfg);
/* For disable command that is setting register instaed of send command, we need write enable */
RomDriver_SFlash_DisableBurstWrap(flash_cfg);
stat = RomDriver_SFlash_SetSPIMode(SF_CTRL_SPI_MODE);
if (SUCCESS != stat) {
// bflb_bootrom_printe("enter spi mode fail %d\r\n", stat);
// return BFLB_BOOTROM_FLASH_INIT_ERROR;
return -1;
}
RomDriver_SFlash_GetJedecId(flash_cfg, (uint8_t *)&jdecId);
/* Dummy disable burstwrap for make sure */
RomDriver_SFlash_Write_Enable(flash_cfg);
/* For disable command that is setting register instead of send command, we need write enable */
RomDriver_SFlash_DisableBurstWrap(flash_cfg);
jdecId = jdecId & 0xffffff;
// bflb_bootrom_printd("ID =%08x\r\n", jdecId);
flash_read_try++;
} while ((jdecId & 0x00ffff) == 0 || (jdecId & 0xffff00) == 0 || (jdecId & 0x00ffff) == 0xffff || (jdecId & 0xffff00) == 0xffff00);
/*clear offset setting*/
// reset image offset
BL_WR_REG(SF_CTRL_BASE, SF_CTRL_SF_ID0_OFFSET, flash_offset);
/* set read mode */
if ((flash_cfg->ioMode & 0x0f) == SF_CTRL_QO_MODE || (flash_cfg->ioMode & 0x0f) == SF_CTRL_QIO_MODE) {
stat = RomDriver_SFlash_Qspi_Enable(flash_cfg);
}
if (media_boot) {
RomDriver_L1C_Set_Wrap(DISABLE);
RomDriver_SFlash_Cache_Read_Enable(flash_cfg, flash_cfg->ioMode & 0xf, 0, 0x00);
}
return jdecId;
}
// can be placed in flash, here placed in pds section to reduce fast boot time
static void ATTR_PDS_RAM_SECTION pm_pds_restore_cpu_reg(void)
{
__asm__ __volatile__(
"la a2, __ld_pds_bak_addr\n\t"
"lw ra, 0(a2)\n\t"
"lw sp, 1*4(a2)\n\t"
"lw tp, 2*4(a2)\n\t"
"lw t0, 3*4(a2)\n\t"
"lw t1, 4*4(a2)\n\t"
"lw t2, 5*4(a2)\n\t"
"lw fp, 6*4(a2)\n\t"
"lw s1, 7*4(a2)\n\t"
"lw a0, 8*4(a2)\n\t"
"lw a1, 9*4(a2)\n\t"
"lw a3, 10*4(a2)\n\t"
"lw a4, 11*4(a2)\n\t"
"lw a5, 12*4(a2)\n\t"
"lw a6, 13*4(a2)\n\t"
"lw a7, 14*4(a2)\n\t"
"lw s2, 15*4(a2)\n\t"
"lw s3, 16*4(a2)\n\t"
"lw s4, 17*4(a2)\n\t"
"lw s5, 18*4(a2)\n\t"
"lw s6, 19*4(a2)\n\t"
"lw s7, 20*4(a2)\n\t"
"lw s8, 21*4(a2)\n\t"
"lw s9, 22*4(a2)\n\t"
"lw s10, 23*4(a2)\n\t"
"lw s11, 24*4(a2)\n\t"
"lw t3, 25*4(a2)\n\t"
"lw t4, 26*4(a2)\n\t"
"lw t5, 27*4(a2)\n\t"
"lw t6, 28*4(a2)\n\t"
"csrw mtvec, a0\n\t"
"csrw mstatus,a1\n\t"
"ret\n\t");
}
void ATTR_PDS_RAM_SECTION sf_io_select(void)
{
uint32_t tmpVal = 0;
uint8_t flashCfg = 0;
uint8_t psramCfg = 0;
uint8_t isInternalFlash = 0;
uint8_t isInternalPsram = 0;
/* SF io select from efuse value */
tmpVal = BL_RD_WORD(0x40007074);
flashCfg = ((tmpVal >> 26) & 7);
psramCfg = ((tmpVal >> 24) & 3);
if (flashCfg == 1 || flashCfg == 2) {
isInternalFlash = 1;
} else {
isInternalFlash = 0;
}
if (psramCfg == 1) {
isInternalPsram = 1;
} else {
isInternalPsram = 0;
}
tmpVal = BL_RD_REG(GLB_BASE, GLB_GPIO_USE_PSRAM__IO);
if (isInternalFlash == 1 && isInternalPsram == 0) {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_CFG_GPIO_USE_PSRAM_IO, 0x3f);
} else {
tmpVal = BL_SET_REG_BITS_VAL(tmpVal, GLB_CFG_GPIO_USE_PSRAM_IO, 0x00);
}
BL_WR_REG(GLB_BASE, GLB_GPIO_USE_PSRAM__IO, tmpVal);
}
// must be placed in pds section
void ATTR_PDS_RAM_SECTION pm_pds_fastboot_entry(void)
{
// reload gp register
__asm__ __volatile__(
".option push\n\t"
".option norelax\n\t"
"la gp, __global_pointer$\n\t"
".option pop\n\t");
#if XTAL_TYPE != INTERNAL_RC_32M
/* power on Xtal_32M*/
(*(volatile uint32_t *)(AON_BASE + AON_RF_TOP_AON_OFFSET)) |= (3 << 4);
#endif
// recovery flash pad and param
RomDriver_SF_Cfg_Init_Flash_Gpio(0, 1);
pm_spi_flash_init(1);
sf_io_select();
/* Recovery hardware , include tcm , gpio and clock */
if (hardware_recovery) {
hardware_recovery();
}
// Restore cpu registers
pm_pds_restore_cpu_reg();
}
void pm_set_hardware_recovery_callback(void (*hardware_recovery_cb)(void))
{
hardware_recovery = hardware_recovery_cb;
}

Some files were not shown because too many files have changed in this diff Show More