332 lines
9.6 KiB
C
332 lines
9.6 KiB
C
/* Standard includes. */
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <assert.h>
|
|
|
|
#include "fr30xx.h"
|
|
|
|
/* FreeRTOS kernel includes. */
|
|
#include "FreeRTOS.h"
|
|
#include "task.h"
|
|
|
|
#include "fdb_app.h"
|
|
#include "host.h"
|
|
|
|
#include "app_task.h"
|
|
#include "app_at.h"
|
|
|
|
/* hardware handlers */
|
|
static UART_HandleTypeDef Uart3_handle;
|
|
static CALI_HandleTypeDef cali_handle;
|
|
|
|
#if ENABLE_RTOS_MONITOR == 1
|
|
/* FreeRTOS running status monitor task */
|
|
static TaskHandle_t monitor_task_handle;
|
|
volatile unsigned int CPU_RunTime;
|
|
static uint8_t CPU_RunInfo[2048];
|
|
#endif
|
|
|
|
/* APP task */
|
|
TaskHandle_t app_task_handle;
|
|
|
|
void controller_start(void);
|
|
void host_start(void);
|
|
|
|
#if defined(__CC_ARM) || defined(__ARMCC_VERSION)
|
|
int fputc(int c, FILE *fp)
|
|
{
|
|
uart_transmit(&Uart3_handle, (void *)&c, 1);
|
|
while(!(Uart3_handle.UARTx->USR.TFE));
|
|
|
|
return c;
|
|
}
|
|
#endif
|
|
#ifdef __GNUC__
|
|
int _write(int file, char *ptr, int len)
|
|
{
|
|
uart_transmit(&Uart3_handle, (void *)ptr, len);
|
|
while(!(Uart3_handle.UARTx->USR.TFE));
|
|
return len;
|
|
}
|
|
#endif
|
|
|
|
#ifdef __ICCARM__
|
|
int putchar(int c)
|
|
{
|
|
uart_transmit(&Uart3_handle, (void *)&c, 1);
|
|
while(!(Uart3_handle.UARTx->USR.TFE));
|
|
return c;
|
|
}
|
|
#endif
|
|
|
|
#if ENABLE_RTOS_MONITOR == 1
|
|
static void monitor_task(void *arg)
|
|
{
|
|
while(1) {
|
|
vTaskDelay(2000000);
|
|
|
|
memset(CPU_RunInfo,0,2048);
|
|
vTaskList((char *)&CPU_RunInfo);
|
|
printf("---------------------------------------------\r\n");
|
|
printf("name state priority stack seq\r\n");
|
|
printf("%s", CPU_RunInfo);
|
|
printf("---------------------------------------------\r\n");
|
|
|
|
memset(CPU_RunInfo,0,400);
|
|
vTaskGetRunTimeStats((char *)&CPU_RunInfo);
|
|
printf("name counter usage\r\n");
|
|
printf("%s", CPU_RunInfo);
|
|
printf("---------------------------------------------\r\n");
|
|
}
|
|
}
|
|
#endif
|
|
|
|
void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName )
|
|
{
|
|
( void ) pcTaskName;
|
|
( void ) pxTask;
|
|
|
|
assert( 0 );
|
|
}
|
|
|
|
void vApplicationTickHook(void)
|
|
{
|
|
#if ENABLE_RTOS_MONITOR == 1
|
|
CPU_RunTime++;
|
|
#endif
|
|
}
|
|
|
|
static void cali_done_handle(CALI_HandleTypeDef *hcali, uint32_t result)
|
|
{
|
|
system_set_LPRCCLK(cali_calc_rc_freq(hcali, result));
|
|
system_prevent_sleep_clear(SYSTEM_PREVENT_SLEEP_TYPE_CALIBRATION);
|
|
}
|
|
|
|
__RAM_CODE bool user_deep_sleep_check(void)
|
|
{
|
|
return host_before_sleep_check();
|
|
}
|
|
|
|
__RAM_CODE void user_entry_before_sleep(void)
|
|
{
|
|
ool_write16(PMU_REG_PIN_PULL_EN, 0x3fff);
|
|
ool_write16(PMU_REG_PIN_PULL_SEL, 0x3fff);
|
|
|
|
/* gpio_PD Wakeup Init */
|
|
SYSTEM->PortD_InputCutoffDisable = 0x0000ffff;
|
|
|
|
ool_write(PMU_REG_PMU_GATE_M, ool_read(PMU_REG_PMU_GATE_M) | 0x40);
|
|
}
|
|
|
|
__RAM_CODE void user_entry_after_sleep(void)
|
|
{
|
|
GPIO_InitTypeDef gpio_config;
|
|
|
|
/*
|
|
* enable pull up of all 3.3v IO, these configuration will be latched by set
|
|
* BIT6 of PMU_REG_PMU_GATE_M regsiter. used to avoid electric leakage
|
|
*/
|
|
SYSTEM->PortA_PullSelect = 0x0000ffff;
|
|
SYSTEM->PortB_PullSelect = 0x00000fff;
|
|
SYSTEM->PortC_PullSelect = 0x00000000;
|
|
SYSTEM->PortD_PullSelect = 0x0000ffff;
|
|
SYSTEM->PortA_PullEN = 0x00007fff;
|
|
SYSTEM->PortB_PullEN = 0x00000dff;
|
|
SYSTEM->PortC_PullEN = 0x00000000;
|
|
SYSTEM->PortD_PullEN = 0x0000ffff;
|
|
SYSTEM->QspiPadConfig.QSPI_PullEN = 0x0000000;
|
|
|
|
host_hci_reinit();
|
|
ool_write(PMU_REG_PMU_GATE_M, ool_read(PMU_REG_PMU_GATE_M) & (~0x40));
|
|
NVIC_SetPriority(UART0_IRQn, 2);
|
|
NVIC_EnableIRQ(UART0_IRQn);
|
|
NVIC_SetPriority(PMU_IRQn, 4);
|
|
NVIC_EnableIRQ(PMU_IRQn);
|
|
|
|
/* configure PA0 and PA1 to UART0 function */
|
|
__SYSTEM_GPIOA_CLK_ENABLE();
|
|
gpio_config.Pin = GPIO_PIN_4 | GPIO_PIN_5;
|
|
gpio_config.Mode = GPIO_MODE_AF_PP;
|
|
gpio_config.Pull = GPIO_PULLUP;
|
|
gpio_config.Alternate = GPIO_FUNCTION_1;
|
|
gpio_init(GPIOB, &gpio_config);
|
|
|
|
/* UART0: used for Log and AT command */
|
|
__SYSTEM_UART3_CLK_ENABLE();
|
|
Uart3_handle.UARTx = UART3;
|
|
Uart3_handle.Init.BaudRate = 115200;
|
|
Uart3_handle.Init.DataLength = UART_DATA_LENGTH_8BIT;
|
|
Uart3_handle.Init.StopBits = UART_STOPBITS_1;
|
|
Uart3_handle.Init.Parity = UART_PARITY_NONE;
|
|
Uart3_handle.Init.FIFO_Mode = UART_FIFO_ENABLE;
|
|
Uart3_handle.TxCpltCallback = NULL;
|
|
Uart3_handle.RxCpltCallback = app_at_rx_done;
|
|
uart_init(&Uart3_handle);
|
|
|
|
/* restart calibration */
|
|
__SYSTEM_CALI_CLK_ENABLE();
|
|
cali_handle.mode = CALI_UP_MODE_NORMAL;
|
|
cali_handle.rc_cnt = 60;
|
|
cali_handle.DoneCallback = cali_done_handle;
|
|
cali_init(&cali_handle);
|
|
cali_start_IT(&cali_handle);
|
|
system_prevent_sleep_set(SYSTEM_PREVENT_SLEEP_TYPE_CALIBRATION);
|
|
NVIC_SetPriority(CALI_IRQn, 2);
|
|
NVIC_EnableIRQ(CALI_IRQn);
|
|
}
|
|
|
|
int main( void )
|
|
{
|
|
GPIO_InitTypeDef gpio_config;
|
|
|
|
system_delay_us(1000000);
|
|
|
|
/* configure all interrupt priority to 2 */
|
|
*(volatile uint32_t *)0xE000E400 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E404 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E408 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E40C = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E410 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E414 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E418 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E41C = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E420 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E424 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E428 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E42C = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E430 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E434 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E438 = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E43C = 0x40404040;
|
|
*(volatile uint32_t *)0xE000E440 = 0x40404040;
|
|
|
|
pmu_init();
|
|
/* Power Keep: 32KB PRAM, 128KB SRAM */
|
|
ool_write16(PMU_REG_PKSRAM_GATE, ~0x0063);
|
|
|
|
/* reinit flash controller */
|
|
system_cache_enable(true);
|
|
SYSTEM->QspiPadConfig.QSPI_FuncMux = 0x00000500;
|
|
flash_enable_quad(QSPI0);
|
|
flash_init_controller(QSPI0, FLASH_RD_TYPE_DUAL, FLASH_WR_TYPE_SINGLE);
|
|
flash_set_baudrate(QSPI0, QSPI_BAUDRATE_DIV_4);
|
|
|
|
/* configure PB4 and PB5 to UART3 function */
|
|
gpio_config.Pin = GPIO_PIN_4 | GPIO_PIN_5;
|
|
gpio_config.Mode = GPIO_MODE_AF_PP;
|
|
gpio_config.Pull = GPIO_PULLUP;
|
|
gpio_config.Alternate = GPIO_FUNCTION_1;
|
|
gpio_init(GPIOB, &gpio_config);
|
|
|
|
/* UART2: used for Log and AT command */
|
|
__SYSTEM_UART3_CLK_ENABLE();
|
|
Uart3_handle.UARTx = UART3;
|
|
Uart3_handle.Init.BaudRate = 115200;
|
|
Uart3_handle.Init.DataLength = UART_DATA_LENGTH_8BIT;
|
|
Uart3_handle.Init.StopBits = UART_STOPBITS_1;
|
|
Uart3_handle.Init.Parity = UART_PARITY_NONE;
|
|
Uart3_handle.Init.FIFO_Mode = UART_FIFO_ENABLE;
|
|
Uart3_handle.TxCpltCallback = NULL;
|
|
Uart3_handle.RxCpltCallback = app_at_rx_done;
|
|
uart_init(&Uart3_handle);
|
|
NVIC_SetPriority(UART3_IRQn, 4);
|
|
NVIC_EnableIRQ(UART3_IRQn);
|
|
|
|
/* do calibration, get current RC frequency */
|
|
__SYSTEM_CALI_CLK_ENABLE();
|
|
cali_handle.mode = CALI_UP_MODE_NORMAL;
|
|
cali_handle.rc_cnt = 200;
|
|
cali_handle.DoneCallback = cali_done_handle;
|
|
cali_init(&cali_handle);
|
|
cali_start_IT(&cali_handle);
|
|
system_prevent_sleep_set(SYSTEM_PREVENT_SLEEP_TYPE_CALIBRATION);
|
|
NVIC_SetPriority(CALI_IRQn, 4);
|
|
NVIC_EnableIRQ(CALI_IRQn);
|
|
|
|
/* init flashdb to store user data */
|
|
flashdb_init();
|
|
printf("start running\r\n");
|
|
/* Create tasks */
|
|
#if ENABLE_RTOS_MONITOR == 1
|
|
xTaskCreate(monitor_task, "monitor", MONITOR_TASK_STACK_SIZE, NULL, MONITOR_TASK_PRIORITY, &monitor_task_handle);
|
|
#endif
|
|
|
|
/* create application task */
|
|
app_task_init();
|
|
|
|
/* initialize AT command */
|
|
app_at_init(&Uart3_handle);
|
|
|
|
/*
|
|
* enable pull up of all 3.3v IO, these configuration will be latched by set
|
|
* BIT6 of PMU_REG_PMU_GATE_M regsiter. used to avoid electric leakage
|
|
*/
|
|
SYSTEM->PortA_PullSelect = 0x0000ffff;
|
|
SYSTEM->PortB_PullSelect = 0x00000fff;
|
|
SYSTEM->PortC_PullSelect = 0x00000000;
|
|
SYSTEM->PortD_PullSelect = 0x0000ffff;
|
|
SYSTEM->PortA_PullEN = 0x00007fff;
|
|
SYSTEM->PortB_PullEN = 0x00000dff;
|
|
SYSTEM->PortC_PullEN = 0x00000000;
|
|
SYSTEM->PortD_PullEN = 0x0000ffff;
|
|
SYSTEM->QspiPadConfig.QSPI_PullEN = 0x0000000;
|
|
|
|
/* enable sleep */
|
|
// system_prevent_sleep_clear(SYSTEM_PREVENT_SLEEP_TYPE_DISABLE);
|
|
|
|
printf("FR5090: BTDM test: 0x%04x.\r\n", ool_read16(PMU_REG_PIN_INPUT_EN));
|
|
|
|
/* Start the scheduler itself. */
|
|
vTaskStartScheduler();
|
|
|
|
return 0;
|
|
}
|
|
|
|
void uart3_irq(void)
|
|
{
|
|
uart_IRQHandler(&Uart3_handle);
|
|
}
|
|
|
|
void PMU_GPIO_GROUPH_IRQHandler(void)
|
|
{
|
|
struct app_task_event *event;
|
|
event = app_task_event_alloc(APP_TASK_EVENT_GPIO_PD_WAKEUP, 0, true);
|
|
app_task_event_post(event, false);
|
|
|
|
system_prevent_sleep_set(SYSTEM_PREVENT_SLEEP_TYPE_DISABLE);
|
|
}
|
|
|
|
void PMU_GPIO_PMU_IRQHandler(void)
|
|
{
|
|
uint16_t data = ool_read16(PMU_REG_PIN_DATA);
|
|
uint16_t result = ool_read16(PMU_REG_PIN_XOR_RESULT);
|
|
|
|
/* update last value with latest data */
|
|
ool_write16(PMU_REG_PIN_LAST_V, data);
|
|
/* clear last XOR result */
|
|
ool_write16(PMU_REG_PIN_XOR_CLR, result);
|
|
|
|
if (((data & PMU_PIN_0) == 0) &(ool_read(PMU_REG_PIN_XOR_EN) & PMU_PIN_0)) {
|
|
system_prevent_sleep_set(SYSTEM_PREVENT_SLEEP_TYPE_DISABLE);
|
|
|
|
struct app_task_event *event;
|
|
event = app_task_event_alloc(APP_TASK_EVENT_PMU_WAKEUP, 0, true);
|
|
app_task_event_post(event, false);
|
|
|
|
return;
|
|
}
|
|
|
|
if (data & PMU_PIN_9) {
|
|
system_prevent_sleep_clear(SYSTEM_PREVENT_SLEEP_TYPE_HCI_RX);
|
|
}
|
|
else {
|
|
system_prevent_sleep_set(SYSTEM_PREVENT_SLEEP_TYPE_HCI_RX);
|
|
}
|
|
}
|
|
|
|
void cali_irq(void)
|
|
{
|
|
cali_IRQHandler(&cali_handle);
|
|
}
|
|
|