未验证 提交 8baaf732 编写于 作者: L luobeihai 提交者: GitHub

add apm32 can driver and add apm32e1/s1 rtt driver support (#7170)

* add apm32 can driver and add apm32e1/s1 rtt driver support

* format some files

* modified action.yml file and modified bsp picture and add bsp README.md
上级 93f3cb30
......@@ -222,12 +222,16 @@ jobs:
- "Infineon/psoc6-evaluationkit-062S2"
- "apm32/apm32f103xe-minibroard"
- "apm32/apm32f407ig-minibroard"
- "apm32/apm32f407zg-evalboard"
- "apm32/apm32f072vb-miniboard"
- "apm32/apm32f107vc-evalboard"
- "apm32/apm32f030r8-miniboard"
- "apm32/apm32f051r8-evalboard"
- "apm32/apm32f091vc-miniboard"
- "apm32/apm32f103vb-miniboard"
- "apm32/apm32e103ze-evalboard"
- "apm32/apm32e103ze-tinyboard"
- "apm32/apm32s103vb-miniboard"
- "at32/at32f403a-start"
- "at32/at32f407-start"
- "at32/at32f413-start"
......
# APM32 系列 BSP 说明
APM32 系列 BSP 目前支持情况如下表所示:
| **BSP 文件夹名称** | **开发板名称** |
| :----------------------------------------------- | :------------------------------- |
| **F0 系列** | |
| [apm32f030r8-miniboard](apm32f030r8-miniboard) | 极海官方 APM32F030R8-MINI 开发板 |
| [apm32f051r8-evalboard](apm32f051r8-evalboard) | 极海官方 APM32F051R8-EVAL 开发板 |
| [apm32f072vb-miniboard](apm32f072vb-miniboard) | 极海官方 APM32F072VB-MINI 开发板 |
| [apm32f091vc-miniboard](apm32f091vc-miniboard) | 极海官方 APM32F091VC-MINI 开发板 |
| **F1 系列** | |
| [apm32f103xe-minibroard](apm32f103xe-minibroard) | 极海官方 APM32F103ZE-MINI 开发板 |
| [apm32f103vb-miniboard](apm32f103vb-miniboard) | 极海官方 APM32F103VB-MINI 开发板 |
| [apm32f107vc-evalboard](apm32f107vc-evalboard) | 极海官方 APM32F107VC-EVAL 开发板 |
| **E1 系列** | |
| [apm32e103ze-evalboard](apm32e103ze-evalboard) | 极海官方 APM32E103ZE-EVAL 开发板 |
| [apm32e103ze-tinyboard](apm32e103ze-tinyboard) | 极海官方 APM32E103ZE-Tiny 开发板 |
| **S1 系列** | |
| [apm32s103vb-miniboard](apm32s103vb-miniboard) | 极海官方 APM32S03VB-MINI 开发板 |
| **F4 系列** | |
| [apm32f407ig-minibroard](apm32f407ig-minibroard) | 极海官方 APM32F407IG-MINI 开发板 |
| [apm32f407zg-evalboard](apm32f407zg-evalboard) | 极海官方 APM32F407ZG-EVAL 开发板 |
此差异已折叠。
*.pyc
*.map
*.dblite
*.elf
*.bin
*.hex
*.axf
*.exe
*.pdb
*.idb
*.ilk
*.old
build
Debug
documentation/html
packages/
*~
*.o
*.obj
*.out
*.bak
*.dep
*.lib
*.i
*.d
.DS_Stor*
.config 3
.config 4
.config 5
Midea-X1
*.uimg
GPATH
GRTAGS
GTAGS
.vscode
JLinkLog.txt
JLinkSettings.ini
DebugConfig/
RTE/
settings/
*.uvguix*
cconfig.h
mainmenu "RT-Thread Configuration"
config BSP_DIR
string
option env="BSP_ROOT"
default "."
config RTT_DIR
string
option env="RTT_ROOT"
default "../../.."
config PKGS_DIR
string
option env="PKGS_ROOT"
default "packages"
source "$RTT_DIR/Kconfig"
source "$PKGS_DIR/Kconfig"
source "../libraries/Kconfig"
source "board/Kconfig"
# APM32E103ZE EVAL BOARD BSP 说明
## 简介
本文档为 APM32E103ZE EVAL 开发板(EVAL BOARD)的 BSP (板级支持包) 说明。
主要内容如下:
- 开发板资源介绍
- BSP 快速上手
通过阅读快速上手章节开发者可以快速地上手该 BSP,将 RT-Thread 运行在开发板上。
## 开发板介绍
APM32E103ZE EVAL BOARD,采用标准JTAG/SWD调试接口,引出了全部的IO。开发板外观如下图所示:
![board](figures/APM32E103ZE-EVAL.png)
- 有关开发板和芯片的详情可至极海官网查阅。[官网开发板链接 ](https://www.geehy.com/support/apm32?id=192)
该开发板常用 **板载资源** 如下:
- MCU:APM32E103ZET6,主频 120MHz,512KB FLASH ,128KB RAM
- 外部 RAM:M12L64164A(外部SDRAM,2MB)
- 外部 FLASH:W25Q16(SPI, 2MB)
- 常用外设
- LED:3个,(红色,PD13/PD14/PD15)
- 按键:3个,K1(PF9),K2(PC13),K3(PA0)
- 常用接口:RS232转串口、SD卡接口、双CAN接口、USB SLAVE
- 调试接口:标准 JTAG/SWD
## 外设支持
本 BSP 目前对外设的支持情况如下:
| **板载外设** | **支持情况** | **备注** |
| :----------- | :----------: | :------------------------------------ |
| RS232转串口 | 支持 | 使用 UART1/ UART2(通过跳线选择) |
| SPI Flash | 支持 | 使用 W25Q16 芯片 |
| SD卡 | 支持 | 支持 FATFS 文件系统 |
| SDRAM | 支持 | 使用 M12L64164A 芯片 |
| **片上外设** | **支持情况** | **备注** |
| GPIO | 支持 | PA0, PA1... PG15 ---> PIN: 0, 1...108 |
| UART | 支持 | UART1/2 |
| ADC | 支持 | ADC1/2/3 |
| DAC | 支持 | DAC1 |
| RTC | 支持 | 支持外部晶振和内部低速时钟 |
| TMR | 支持 | TMR1/2/3/4/5/6/7/8 |
| PWM | 支持 | TMR3 ->CH1/2/3/4 |
| I2C | 支持 | 软件I2C |
| SPI | 支持 | SPI1/2/3 |
| WDT | 支持 | IWDT |
| SDIO | 支持 | |
| Flash | 支持 | 已适配 [FAL](https://github.com/RT-Thread-packages/fal) |
| CAN | 支持 | CAN1/CAN2 |
## 使用说明
本章节是为刚接触 RT-Thread 的新手准备的使用说明,遵循简单的步骤即可将 RT-Thread 操作系统运行在该开发板上,看到实验效果 。
### 快速上手
本 BSP 为开发者提供MDK5 工程。下面以 MDK5 开发环境为例,介绍如何将系统运行起来。
#### 硬件连接
使用数据线连接开发板到 PC,打开电源开关。
#### 编译下载
- 方式一:MDK
双击 project.uvprojx 文件,打开 MDK5 工程,编译并下载程序到开发板。
> 工程默认配置使用 J-Link 仿真器下载程序,在通过 J-Link 连接开发板的基础上,点击下载按钮即可下载程序到开发板
- 方式二:J-Flash下载
通过ENV工具的scons指令或MDK编译出bin文件后,再使用J-Flash工具将bin文件下载至开发板即可,大致步骤如下:
##### 1、建立J-Flash工程
![board](figures/JFlash_Leader_01.png)
**注意**:步骤4选择芯片型号时,要根据自己的开发板所用的芯片型号进行选择。比如本开发板,则选择对应的 **APM32E103ZET6**
##### 2、连接开发板
![board](figures/JFlash_Leader_02.png)
##### 3、将bin文件拖至工程,起始地址设为0x8000000
![board](figures/JFlash_Leader_03.png)
##### 4、点击下载
![board](figures/JFlash_Leader_04.png)
#### 运行结果
下载程序成功之后,系统会自动运行,LED 闪烁
连接开发板对应串口到 PC , 在终端工具里打开相应的串口(115200-8-1-N),复位设备后,可以看到 RT-Thread 的输出信息:
```bash
\ | /
- RT - Thread Operating System
/ | \ 4.1.0 build Aug 20 2021
2006 - 2021 Copyright by rt-thread team
msh >
```
## 注意事项
- 可在极海官方网站进行所需资料下载,如pack安装包和MINI开发板原理图等(www.geehy.com);
## 联系人信息
-[abbbcc ](https://gitee.com/abbbcc)
-[stevetong459 ](https://github.com/stevetong459)
-[luobeihai](https://github.com/luobeihai)
\ No newline at end of file
# for module compiling
import os
Import('RTT_ROOT')
from building import *
cwd = GetCurrentDir()
objs = []
list = os.listdir(cwd)
for d in list:
path = os.path.join(cwd, d)
if os.path.isfile(os.path.join(path, 'SConscript')):
objs = objs + SConscript(os.path.join(d, 'SConscript'))
Return('objs')
import os
import sys
import rtconfig
if os.getenv('RTT_ROOT'):
RTT_ROOT = os.getenv('RTT_ROOT')
else:
RTT_ROOT = os.path.normpath(os.getcwd() + '/../../..')
sys.path = sys.path + [os.path.join(RTT_ROOT, 'tools')]
try:
from building import *
except:
print('Cannot found RT-Thread root directory, please check RTT_ROOT')
print(RTT_ROOT)
exit(-1)
TARGET = 'rt-thread.' + rtconfig.TARGET_EXT
DefaultEnvironment(tools=[])
env = Environment(tools = ['mingw'],
AS = rtconfig.AS, ASFLAGS = rtconfig.AFLAGS,
CC = rtconfig.CC, CFLAGS = rtconfig.CFLAGS,
AR = rtconfig.AR, ARFLAGS = '-rc',
CXX = rtconfig.CXX, CXXFLAGS = rtconfig.CXXFLAGS,
LINK = rtconfig.LINK, LINKFLAGS = rtconfig.LFLAGS)
env.PrependENVPath('PATH', rtconfig.EXEC_PATH)
if rtconfig.PLATFORM in ['iccarm']:
env.Replace(CCCOM = ['$CC $CFLAGS $CPPFLAGS $_CPPDEFFLAGS $_CPPINCFLAGS -o $TARGET $SOURCES'])
env.Replace(ARFLAGS = [''])
env.Replace(LINKCOM = env["LINKCOM"] + ' --map rt-thread.map')
Export('RTT_ROOT')
Export('rtconfig')
SDK_ROOT = os.path.abspath('./')
if os.path.exists(SDK_ROOT + '/libraries'):
libraries_path_prefix = SDK_ROOT + '/libraries'
else:
libraries_path_prefix = os.path.dirname(SDK_ROOT) + '/libraries'
SDK_LIB = libraries_path_prefix
Export('SDK_LIB')
# prepare building environment
objs = PrepareBuilding(env, RTT_ROOT, has_libcpu=False)
apm32_library = 'APM32E10x_Library'
rtconfig.BSP_LIBRARY_TYPE = apm32_library
# include libraries
objs.extend(SConscript(os.path.join(libraries_path_prefix, apm32_library, 'SConscript')))
# include drivers
objs.extend(SConscript(os.path.join(libraries_path_prefix, 'Drivers', 'SConscript')))
# make a building
DoBuilding(TARGET, objs)
Import('RTT_ROOT')
Import('rtconfig')
from building import *
cwd = GetCurrentDir()
src = Glob('*.c')
CPPPATH = [cwd]
group = DefineGroup('Applications', src, depend = [''], CPPPATH = CPPPATH)
Return('group')
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-26 luobeihai first version
*/
#include <rtthread.h>
#include <rtdevice.h>
#include <board.h>
/* defined the LED1 pin: PD13 */
#define LED1_PIN GET_PIN(D, 13)
int main(void)
{
uint32_t sysclock = 0;
/* set LED1 pin mode to output */
rt_pin_mode(LED1_PIN, PIN_MODE_OUTPUT);
/* Print system clock */
sysclock = RCM_ReadSYSCLKFreq();
rt_kprintf("System Clock: %d\n", sysclock);
while (1)
{
rt_pin_write(LED1_PIN, PIN_HIGH);
rt_thread_mdelay(500);
rt_pin_write(LED1_PIN, PIN_LOW);
rt_thread_mdelay(500);
}
}
menu "Hardware Drivers Config"
config SOC_APM32E103ZE
bool
select SOC_SERIES_APM32E1
select RT_USING_COMPONENTS_INIT
select RT_USING_USER_MAIN
default y
menu "Onboard Peripheral Drivers"
config BSP_USING_USB_TO_USART
bool "Enable USB TO USART (uart1)"
select BSP_USING_UART
select BSP_USING_UART1
default y
config BSP_USING_SPI_FLASH
bool "Enable SPI FLASH (W25Q16 spi3)"
select BSP_USING_SPI
select BSP_USING_SPI3
select RT_USING_SFUD
select RT_SFUD_USING_SFDP
default n
config BSP_USING_EEPROM
bool "Enable I2C EEPROM (i2c1)"
select BSP_USING_I2C
select BSP_USING_I2C1
default n
config BSP_USING_SDCARD
bool "Enable SDCARD (sdio)"
select BSP_USING_SDIO
select RT_USING_DFS
select RT_USING_DFS_ELMFAT
default n
config BSP_USING_SDRAM
bool "Enable SDRAM"
select BSP_USING_DMC
default n
endmenu
menu "On-chip Peripheral Drivers"
config BSP_USING_GPIO
bool "Enable GPIO"
select RT_USING_PIN
default y
menuconfig BSP_USING_UART
bool "Enable UART"
default y
select RT_USING_SERIAL
if BSP_USING_UART
config BSP_USING_UART1
bool "Enable UART1"
default y
config BSP_USING_UART2
bool "Enable UART2"
default n
endif
menuconfig BSP_USING_ADC
bool "Enable ADC"
default n
select RT_USING_ADC
if BSP_USING_ADC
config BSP_USING_ADC1
bool "Enable ADC1"
default n
config BSP_USING_ADC2
bool "Enable ADC2"
default n
config BSP_USING_ADC3
bool "Enable ADC3"
default n
endif
menuconfig BSP_USING_DAC
bool "Enable DAC"
default n
select RT_USING_DAC
if BSP_USING_DAC
config BSP_USING_DAC1
bool "Enable DAC1"
default n
endif
menuconfig BSP_USING_ONCHIP_RTC
bool "Enable RTC"
select RT_USING_RTC
default n
if BSP_USING_ONCHIP_RTC
choice
prompt "Select clock source"
default BSP_RTC_USING_LSE
config BSP_RTC_USING_LSE
bool "RTC USING LSE"
config BSP_RTC_USING_LSI
bool "RTC USING LSI"
endchoice
endif
menuconfig BSP_USING_I2C
bool "Enable I2C BUS (software simulation)"
default n
select RT_USING_I2C
select RT_USING_I2C_BITOPS
select RT_USING_PIN
if BSP_USING_I2C
config BSP_USING_I2C1
bool "Enable I2C1 BUS"
if BSP_USING_I2C1
comment "Notice: PB6 --> 22; PB7 --> 23"
config BSP_I2C1_SCL_PIN
int "i2c1 scl pin number"
range 0 63
default 22
config BSP_I2C1_SDA_PIN
int "I2C1 sda pin number"
range 0 63
default 23
endif
config BSP_USING_I2C2
bool "Enable I2C2 BUS"
if BSP_USING_I2C2
comment "Notice: PA0 --> 0; PA1 --> 1"
config BSP_I2C2_SCL_PIN
int "i2c2 scl pin number"
range 0 63
default 22
config BSP_I2C2_SDA_PIN
int "I2C2 sda pin number"
range 0 63
default 23
endif
config BSP_USING_I2C3
bool "Enable I2C3 BUS"
if BSP_USING_I2C3
comment "Notice: PB0 --> 16; PB1 --> 17"
config BSP_I2C3_SCL_PIN
int "i2c3 scl pin number"
range 0 63
default 8
config BSP_I2C3_SDA_PIN
int "I2C3 sda pin number"
range 0 63
default 41
endif
endif
menuconfig BSP_USING_SPI
bool "Enable SPI"
default n
select RT_USING_SPI
if BSP_USING_SPI
config BSP_USING_SPI1
bool "Enable SPI1"
default n
config BSP_USING_SPI2
bool "Enable SPI2"
default n
config BSP_USING_SPI3
bool "Enable SPI3"
default n
endif
menuconfig BSP_USING_TMR
bool "Enable Timer"
default n
select RT_USING_HWTIMER
if BSP_USING_TMR
config BSP_USING_TMR1
bool "Enable TMR1"
default n
config BSP_USING_TMR2
bool "Enable TMR2"
default n
config BSP_USING_TMR3
bool "Enable TMR3"
default n
config BSP_USING_TMR4
bool "Enable TMR4"
default n
config BSP_USING_TMR5
bool "Enable TMR5"
default n
config BSP_USING_TMR6
bool "Enable TMR6"
default n
config BSP_USING_TMR7
bool "Enable TMR7"
default n
config BSP_USING_TMR8
bool "Enable TMR8"
default n
endif
menuconfig BSP_USING_PWM
bool "Enable PWM"
default n
select RT_USING_PWM
if BSP_USING_PWM
menuconfig BSP_USING_PWM3
bool "Enable timer3 output PWM"
default n
if BSP_USING_PWM3
config BSP_USING_PWM3_CH1
bool "Enable PWM3 channel1"
default n
config BSP_USING_PWM3_CH2
bool "Enable PWM3 channel2"
default n
config BSP_USING_PWM3_CH3
bool "Enable PWM3 channel3"
default n
config BSP_USING_PWM3_CH4
bool "Enable PWM3 channel4"
default n
endif
endif
menuconfig BSP_USING_CAN
bool "Enable CAN"
default n
select RT_USING_CAN
if BSP_USING_CAN
config BSP_USING_CAN1
bool "Enable CAN1"
default n
config BSP_USING_CAN2
bool "Enable CAN2"
default n
endif
config BSP_USING_SDIO
bool "Enable SDIO"
select RT_USING_SDIO
select RT_USING_DFS
default n
config BSP_USING_ON_CHIP_FLASH
bool "Enable on-chip FLASH"
default n
config BSP_USING_WDT
bool "Enable Watchdog Timer"
select RT_USING_WDT
default n
config BSP_USING_DMC
bool
default n
endmenu
endmenu
import os
import rtconfig
from building import *
Import('SDK_LIB')
cwd = GetCurrentDir()
# add general drivers
src = Split('''
board.c
''')
if GetDepend(['BSP_USING_SPI_FLASH']):
src += Glob('ports/spi_flash_init.c')
if GetDepend(['BSP_USING_SDCARD']):
src += Glob('ports/sdcard_port.c')
if GetDepend(['BSP_USING_SDRAM']):
src += Glob('ports/drv_sdram.c')
path = [cwd]
path += [cwd + '/ports']
startup_path_prefix = SDK_LIB
if rtconfig.PLATFORM in ['armcc', 'armclang']:
src += [startup_path_prefix + '/APM32E10x_Library/Device/Geehy/APM32E10x/Source/arm/startup_apm32e10x_hd.s']
if rtconfig.PLATFORM in ['iccarm']:
src += [startup_path_prefix + '/APM32E10x_Library/Device/Geehy/APM32E10x/Source/iar/startup_apm32e10x_hd.s']
if rtconfig.PLATFORM in ['gcc']:
src += [startup_path_prefix + '/APM32E10x_Library/Device/Geehy/APM32E10x/Source/gcc/startup_apm32e10x_hd.S']
# You can select chips from the list above
CPPDEFINES = ['APM32E10X_HD']
group = DefineGroup('Drivers', src, depend = [''], CPPPATH = path, CPPDEFINES = CPPDEFINES)
Return('group')
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-26 luobeihai first version
*/
#include "board.h"
void apm32_usart_init(void)
{
GPIO_Config_T GPIO_ConfigStruct;
#ifdef BSP_USING_UART1
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOA | RCM_APB2_PERIPH_USART1);
GPIO_ConfigStruct.mode = GPIO_MODE_AF_PP;
GPIO_ConfigStruct.pin = GPIO_PIN_9;
GPIO_ConfigStruct.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOA, &GPIO_ConfigStruct);
GPIO_ConfigStruct.mode = GPIO_MODE_IN_PU;
GPIO_ConfigStruct.pin = GPIO_PIN_10;
GPIO_Config(GPIOA, &GPIO_ConfigStruct);
#endif
#ifdef BSP_USING_UART2
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOA);
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_USART2);
GPIO_ConfigStruct.mode = GPIO_MODE_AF_PP;
GPIO_ConfigStruct.pin = GPIO_PIN_2;
GPIO_ConfigStruct.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOA, &GPIO_ConfigStruct);
GPIO_ConfigStruct.mode = GPIO_MODE_IN_PU;
GPIO_ConfigStruct.pin = GPIO_PIN_3;
GPIO_Config(GPIOA, &GPIO_ConfigStruct);
#endif
}
/**
* apm32 timer gpio init
*
*/
void apm32_msp_timer_init(void *Instance)
{
#ifdef BSP_USING_PWM3
GPIO_Config_T gpio_config;
TMR_T *tmr_x = (TMR_T *)Instance;
if (tmr_x == TMR3)
{
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_TMR3);
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOC | RCM_APB2_PERIPH_AFIO);
GPIO_ConfigPinRemap(GPIO_FULL_REMAP_TMR3);
/* TMR3 channel 1 gpio config */
gpio_config.pin = GPIO_PIN_6;
gpio_config.mode = GPIO_MODE_AF_PP;
gpio_config.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOC, &gpio_config);
/* TMR3 channel 2 gpio config */
gpio_config.pin = GPIO_PIN_7;
GPIO_Config(GPIOC, &gpio_config);
/* TMR3 channel 3 gpio config */
gpio_config.pin = GPIO_PIN_8;
GPIO_Config(GPIOC, &gpio_config);
/* TMR3 channel 4 gpio config */
gpio_config.pin = GPIO_PIN_9;
GPIO_Config(GPIOC, &gpio_config);
}
#endif
}
/**
* apm32 spi gpio init
*
*/
void apm32_msp_spi_init(void *Instance)
{
#ifdef BSP_USING_SPI
GPIO_Config_T gpioConfig;
SPI_T *spi_x = (SPI_T *)Instance;
if(spi_x == SPI3)
{
/* Enable related Clock */
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_SPI3);
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOB | RCM_APB2_PERIPH_AFIO);
GPIO_ConfigPinRemap(GPIO_REMAP_SWJ_JTAGDISABLE);
/* Configure FLASH_SPI pins: SCK */
gpioConfig.pin = GPIO_PIN_3;
gpioConfig.mode = GPIO_MODE_AF_PP;
gpioConfig.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOB, &gpioConfig);
/* Configure FLASH_SPI pins: MOSI */
gpioConfig.pin = GPIO_PIN_5;
GPIO_Config(GPIOB, &gpioConfig);
/* Configure FLASH_SPI pins: MISO */
gpioConfig.pin = GPIO_PIN_4;
gpioConfig.mode = GPIO_MODE_IN_FLOATING;
GPIO_Config(GPIOB, &gpioConfig);
}
#endif
}
/**
* apm32 sdio gpio init
*
*/
void apm32_msp_sdio_init(void *Instance)
{
#ifdef BSP_USING_SDIO
GPIO_Config_T GPIO_InitStructure;
/* Enable the GPIO Clock */
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOC | RCM_APB2_PERIPH_GPIOD);
/* Enable the SDIO Clock */
RCM_EnableAHBPeriphClock(RCM_AHB_PERIPH_SDIO);
/* Configure the GPIO pin */
GPIO_InitStructure.pin = GPIO_PIN_8 | GPIO_PIN_9 | GPIO_PIN_10 | GPIO_PIN_11 | GPIO_PIN_12;
GPIO_InitStructure.mode = GPIO_MODE_AF_PP;
GPIO_InitStructure.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOC, &GPIO_InitStructure);
GPIO_InitStructure.pin = GPIO_PIN_2;
GPIO_Config(GPIOD, &GPIO_InitStructure);
#endif
}
void apm32_msp_can_init(void *Instance)
{
#if defined(BSP_USING_CAN1) || defined(BSP_USING_CAN2)
GPIO_Config_T GPIO_InitStructure;
CAN_T *CANx = (CAN_T *)Instance;
if (CAN1 == CANx)
{
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_CAN1);
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_AFIO);
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOB);
GPIO_ConfigPinRemap(GPIO_REMAP1_CAN1);
/* CAN1 Tx */
GPIO_InitStructure.pin = GPIO_PIN_9;
GPIO_InitStructure.mode = GPIO_MODE_AF_PP;
GPIO_InitStructure.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOB, &GPIO_InitStructure);
/* CAN1 Rx */
GPIO_InitStructure.pin = GPIO_PIN_8;
GPIO_InitStructure.mode = GPIO_MODE_IN_FLOATING;
GPIO_Config(GPIOB, &GPIO_InitStructure);
}
else if (CAN2 == CANx)
{
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_CAN2);
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOB);
/* CAN2 Tx */
GPIO_InitStructure.pin = GPIO_PIN_13;
GPIO_InitStructure.mode = GPIO_MODE_AF_PP;
GPIO_InitStructure.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOB, &GPIO_InitStructure);
/* CAN2 Rx */
GPIO_InitStructure.pin = GPIO_PIN_12;
GPIO_InitStructure.mode = GPIO_MODE_IN_FLOATING;
GPIO_Config(GPIOB, &GPIO_InitStructure);
}
#endif
}
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-26 luobeihai first version
*/
#ifndef __BOARD_H__
#define __BOARD_H__
#include <rtthread.h>
#include <apm32e10x.h>
#include "apm32e10x_gpio.h"
#include "apm32e10x_rcm.h"
#include "apm32e10x_misc.h"
#include "apm32e10x_rcm.h"
#include "apm32e10x_eint.h"
#include "apm32e10x_usart.h"
#include "apm32e10x_dma.h"
#if defined(RT_USING_ADC)
#include "apm32e10x_adc.h"
#endif
#if defined(RT_USING_DAC)
#include "apm32e10x_dac.h"
#endif
#if defined(RT_USING_RTC)
#include "apm32e10x_rtc.h"
#include "apm32e10x_pmu.h"
#endif
#if defined(RT_USING_SPI)
#include "apm32e10x_spi.h"
#endif
#if defined(RT_USING_HWTIMER) || defined(RT_USING_PWM)
#include "apm32e10x_tmr.h"
#endif
#if defined(RT_USING_WDT)
#include "apm32e10x_iwdt.h"
#include "apm32e10x_wwdt.h"
#endif
#if defined(BSP_USING_SDCARD)
#include "apm32e10x_sdio.h"
#endif
#if defined(BSP_USING_ON_CHIP_FLASH)
#include "apm32e10x_fmc.h"
#endif
#if defined(RT_USING_CAN)
#include "apm32e10x_can.h"
#endif
#if defined(BSP_USING_SDRAM)
#include "apm32e10x_dmc.h"
#endif
#include "drv_common.h"
#include "drv_gpio.h"
#ifdef __cplusplus
extern "C" {
#endif
#define APM32_FLASH_START_ADRESS ((uint32_t)0x08000000)
#define APM32_FLASH_SIZE (512 * 1024)
#define APM32_FLASH_END_ADDRESS ((uint32_t)(APM32_FLASH_START_ADRESS + APM32_FLASH_SIZE))
/* Internal SRAM memory size[Kbytes] <6-128>, Default: 128 */
#define APM32_SRAM_SIZE 128
#define APM32_SRAM_END (0x20000000 + APM32_SRAM_SIZE * 1024)
#if defined(__ARMCC_VERSION)
extern int Image$$RW_IRAM1$$ZI$$Limit;
#define HEAP_BEGIN ((void *)&Image$$RW_IRAM1$$ZI$$Limit)
#elif __ICCARM__
#pragma section="CSTACK"
#define HEAP_BEGIN (__segment_end("CSTACK"))
#else
extern int __bss_end;
#define HEAP_BEGIN ((void *)&__bss_end)
#endif
#define HEAP_END APM32_SRAM_END
void SystemClock_Config(void);
void apm32_usart_init(void);
#ifdef __cplusplus
}
#endif
#endif /* __BOARD_H__ */
/*###ICF### Section handled by ICF editor, don't touch! ****/
/*-Editor annotation file-*/
/* IcfEditorFile="$TOOLKIT_DIR$\config\ide\IcfEditor\cortex_v1_0.xml" */
/*-Specials-*/
define symbol __ICFEDIT_intvec_start__ = 0x08000000;
/*-Memory Regions-*/
define symbol __ICFEDIT_region_ROM_start__ = 0x08000000;
define symbol __ICFEDIT_region_ROM_end__ = 0x0807FFFF;
define symbol __ICFEDIT_region_RAM_start__ = 0x20000000;
define symbol __ICFEDIT_region_RAM_end__ = 0x2001FFFF;
/*-Sizes-*/
define symbol __ICFEDIT_size_cstack__ = 0x0400;
define symbol __ICFEDIT_size_heap__ = 0x0000;
/**** End of ICF editor section. ###ICF###*/
define memory mem with size = 4G;
define region ROM_region = mem:[from __ICFEDIT_region_ROM_start__ to __ICFEDIT_region_ROM_end__];
define region RAM_region = mem:[from __ICFEDIT_region_RAM_start__ to __ICFEDIT_region_RAM_end__];
define block CSTACK with alignment = 8, size = __ICFEDIT_size_cstack__ { };
initialize by copy { readwrite };
do not initialize { section .noinit };
place at address mem:__ICFEDIT_intvec_start__ { readonly section .intvec };
place in ROM_region { readonly };
place in RAM_region { readwrite, last block CSTACK};
/*
* linker script for APM32E10x with GNU ld
*/
/* Program Entry, set to mark it as "used" and avoid gc */
MEMORY
{
ROM (rx) : ORIGIN = 0x08000000, LENGTH = 512K /* 512K flash */
RAM (rw) : ORIGIN = 0x20000000, LENGTH = 128K /* 128K sram */
}
ENTRY(Reset_Handler)
_system_stack_size = 0x400;
SECTIONS
{
.text :
{
. = ALIGN(4);
_stext = .;
KEEP(*(.isr_vector)) /* Startup code */
. = ALIGN(4);
*(.text) /* remaining code */
*(.text.*) /* remaining code */
*(.rodata) /* read-only data (constants) */
*(.rodata*)
*(.glue_7)
*(.glue_7t)
*(.gnu.linkonce.t*)
/* section information for finsh shell */
. = ALIGN(4);
__fsymtab_start = .;
KEEP(*(FSymTab))
__fsymtab_end = .;
. = ALIGN(4);
__vsymtab_start = .;
KEEP(*(VSymTab))
__vsymtab_end = .;
/* section information for initial. */
. = ALIGN(4);
__rt_init_start = .;
KEEP(*(SORT(.rti_fn*)))
__rt_init_end = .;
. = ALIGN(4);
PROVIDE(__ctors_start__ = .);
KEEP (*(SORT(.init_array.*)))
KEEP (*(.init_array))
PROVIDE(__ctors_end__ = .);
. = ALIGN(4);
_etext = .;
} > ROM = 0
/* .ARM.exidx is sorted, so has to go in its own output section. */
__exidx_start = .;
.ARM.exidx :
{
*(.ARM.exidx* .gnu.linkonce.armexidx.*)
/* This is used by the startup in order to initialize the .data secion */
_sidata = .;
_start_address_init_data = .;
} > ROM
__exidx_end = .;
/* .data section which is used for initialized data */
.data : AT (_sidata)
{
. = ALIGN(4);
/* This is used by the startup in order to initialize the .data secion */
_sdata = . ;
_start_address_data = .;
*(.data)
*(.data.*)
*(.gnu.linkonce.d*)
PROVIDE(__dtors_start__ = .);
KEEP(*(SORT(.dtors.*)))
KEEP(*(.dtors))
PROVIDE(__dtors_end__ = .);
. = ALIGN(4);
/* This is used by the startup in order to initialize the .data secion */
_edata = . ;
_end_address_data = .;
} >RAM
.stack :
{
. = ALIGN(4);
_sstack = .;
. = . + _system_stack_size;
. = ALIGN(4);
_estack = .;
_end_stack = .;
} >RAM
__bss_start = .;
_start_address_bss = .;
.bss :
{
. = ALIGN(4);
/* This is used by the startup in order to initialize the .bss secion */
_sbss = .;
*(.bss)
*(.bss.*)
*(COMMON)
. = ALIGN(4);
/* This is used by the startup in order to initialize the .bss secion */
_ebss = . ;
*(.bss.init)
} > RAM
__bss_end = .;
_end_address_bss = .;
_end = .;
/* Stabs debugging sections. */
.stab 0 : { *(.stab) }
.stabstr 0 : { *(.stabstr) }
.stab.excl 0 : { *(.stab.excl) }
.stab.exclstr 0 : { *(.stab.exclstr) }
.stab.index 0 : { *(.stab.index) }
.stab.indexstr 0 : { *(.stab.indexstr) }
.comment 0 : { *(.comment) }
/* DWARF debug sections.
* Symbols in the DWARF debugging sections are relative to the beginning
* of the section so we begin them at 0. */
/* DWARF 1 */
.debug 0 : { *(.debug) }
.line 0 : { *(.line) }
/* GNU DWARF 1 extensions */
.debug_srcinfo 0 : { *(.debug_srcinfo) }
.debug_sfnames 0 : { *(.debug_sfnames) }
/* DWARF 1.1 and DWARF 2 */
.debug_aranges 0 : { *(.debug_aranges) }
.debug_pubnames 0 : { *(.debug_pubnames) }
/* DWARF 2 */
.debug_info 0 : { *(.debug_info .gnu.linkonce.wi.*) }
.debug_abbrev 0 : { *(.debug_abbrev) }
.debug_line 0 : { *(.debug_line) }
.debug_frame 0 : { *(.debug_frame) }
.debug_str 0 : { *(.debug_str) }
.debug_loc 0 : { *(.debug_loc) }
.debug_macinfo 0 : { *(.debug_macinfo) }
/* SGI/MIPS DWARF 2 extensions */
.debug_weaknames 0 : { *(.debug_weaknames) }
.debug_funcnames 0 : { *(.debug_funcnames) }
.debug_typenames 0 : { *(.debug_typenames) }
.debug_varnames 0 : { *(.debug_varnames) }
}
; *************************************************************
; *** Scatter-Loading Description File generated by uVision ***
; *************************************************************
LR_IROM1 0x08000000 0x00080000 { ; load region size_region
ER_IROM1 0x08000000 0x00080000 { ; load address = execution address
*.o (RESET, +First)
*(InRoot$$Sections)
.ANY (+RO)
.ANY (+XO)
}
RW_IRAM1 0x20000000 0x00020000 { ; RW data
.ANY (+RW +ZI)
}
}
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-28 luobeihai first version
*/
#include <board.h>
#ifdef BSP_USING_SDRAM
#include "drv_sdram.h"
#define DRV_DEBUG
#define LOG_TAG "drv.sdram"
#include <drv_log.h>
/* SDRAM GPIO Clock */
#define RCM_SDRAM_GPIO_PERIPH (RCM_APB2_PERIPH_AFIO | \
RCM_APB2_PERIPH_GPIOB | \
RCM_APB2_PERIPH_GPIOC | \
RCM_APB2_PERIPH_GPIOD | \
RCM_APB2_PERIPH_GPIOE | \
RCM_APB2_PERIPH_GPIOF | \
RCM_APB2_PERIPH_GPIOG)
/* SDRAM Peripheral Clock */
#define RCM_SDRAM_PERIPH (RCM_AHB_PERIPH_SMC)
#ifdef RT_USING_MEMHEAP_AS_HEAP
static struct rt_memheap system_heap;
#endif
/**
* @brief SDRAM divider Number
*/
typedef enum
{
RCM_DMC_DIV_1,
RCM_DMC_DIV_2,
RCM_DMC_DIV_4 = 3
} RCM_DMC_DIV_T;
/**
* @brief Configs the SDRAM clock prescaler
* @param SDRAMDiv: Specifies the SDRAM clock prescaler from the DMC clock.
* @retval None
*/
static void RCM_ConfigSDRAMCLK(RCM_DMC_DIV_T SDRAMDiv)
{
RCM->CFG_B.SDRAMPSC = SDRAMDiv;
}
/**
* @brief sdram gpio init
* @param None
* @retval None
*/
static void SDRAM_GPIO_Init(void)
{
GPIO_Config_T gpioConfig;
RCM_EnableAPB2PeriphClock(RCM_SDRAM_GPIO_PERIPH);
/** SDRAM pins assignment */
/**
+-------------------------+--------------------------+--------------------------+
| PB10 <-> MMC_SDRAM_UDQM | PC10 <-> MMC_SDRAM_D8 | PD2 <-> MMC_SDRAM_D10 |
| PB11 <-> MMC_SDRAM_CKE | PC11 <-> MMC_SDRAM_D9 | PD3 <-> MMC_SDRAM_D11 |
| | | PD4 <-> MMC_SDRAM_D12 |
| | | PD5 <-> MMC_SDRAM_D13 |
| | | PD6 <-> MMC_SDRAM_D14 |
+-------------------------+--------------------------+--------------------------+
| PE3 <-> MMC_SDRAM_D4 | PF0 <-> MMC_SDRAM_D7 | PG0 <-> MMC_SDRAM_A3 |
| PE5 <-> MMC_SDRAM_D5 | PF2 <-> MMC_SDRAM_NCS | PG9 <-> MMC_SDRAM_D15 |
| PE6 <-> MMC_SDRAM_D6 | PF4 <-> MMC_SDRAM_NRAS | PG12 <-> MMC_SDRAM_D0 |
| PE8 <-> MMC_SDRAM_A4 | PF5 <-> MMC_SDRAM_NCAS | PG13 <-> MMC_SDRAM_D1 |
| PE9 <-> MMC_SDRAM_A5 | PF6 <-> MMC_SDRAM_NWE | PG14 <-> MMC_SDRAM_D2 |
| PE10 <-> MMC_SDRAM_A6 | PF10 <-> MMC_SDRAM_LDQM | PG15 <-> MMC_SDRAM_D3 |
| PE11 <-> MMC_SDRAM_A7 | PF11 <-> MMC_SDRAM_Bank | |
| PE12 <-> MMC_SDRAM_A8 | PF12 <-> MMC_SDRAM_A10 | |
| PE13 <-> MMC_SDRAM_A9 | PF13 <-> MMC_SDRAM_A0 | |
| PE15 <-> MMC_SDRAM_CLK | PF14 <-> MMC_SDRAM_A1 | |
| | PF15 <-> MMC_SDRAM_A2 | |
+-------------------------+--------------------------+--------------------------+
*/
gpioConfig.speed = GPIO_SPEED_50MHz;
gpioConfig.mode = GPIO_MODE_AF_PP;
gpioConfig.pin = GPIO_PIN_10 | GPIO_PIN_11;
GPIO_Config(GPIOB, &gpioConfig);
gpioConfig.pin = GPIO_PIN_10 | GPIO_PIN_11;
GPIO_Config(GPIOC, &gpioConfig);
gpioConfig.pin = GPIO_PIN_2 | GPIO_PIN_3 |
GPIO_PIN_4 | GPIO_PIN_5 |
GPIO_PIN_6;
GPIO_Config(GPIOD, &gpioConfig);
gpioConfig.pin = GPIO_PIN_3 | GPIO_PIN_5 |
GPIO_PIN_6 | GPIO_PIN_8 |
GPIO_PIN_9 | GPIO_PIN_10|
GPIO_PIN_11 | GPIO_PIN_12 |
GPIO_PIN_13 | GPIO_PIN_15 ;
GPIO_Config(GPIOE, &gpioConfig);
gpioConfig.pin = GPIO_PIN_0 | GPIO_PIN_2 | GPIO_PIN_4 |
GPIO_PIN_5 | GPIO_PIN_6 |
GPIO_PIN_10 |GPIO_PIN_11 |
GPIO_PIN_12 | GPIO_PIN_13|
GPIO_PIN_14 | GPIO_PIN_15;
GPIO_Config(GPIOF, &gpioConfig);
gpioConfig.pin = GPIO_PIN_0 | GPIO_PIN_9|
GPIO_PIN_12 | GPIO_PIN_13 |
GPIO_PIN_14 | GPIO_PIN_15;
GPIO_Config(GPIOG, &gpioConfig);
}
/**
* @brief sdram init
* @param None
* @retval None
*/
static int SDRAM_Init(void)
{
int result = RT_EOK;
DMC_Config_T dmc_init_config;
DMC_TimingConfig_T dmc_timing_config;
/* Config the SDRAM clock prescaler */
RCM_ConfigSDRAMCLK(RCM_DMC_DIV_2);
/* enable sdram clock */
RCM_EnableAHBPeriphClock(RCM_SDRAM_PERIPH);
/* sdram gpio init */
SDRAM_GPIO_Init();
/* dmc timing config */
dmc_timing_config.latencyCAS = DMC_CAS_LATENCY_3; //!< Configure CAS latency period
dmc_timing_config.tARP = DMC_AUTO_REFRESH_10; //!< Configure auto refresh period
dmc_timing_config.tRAS = DMC_RAS_MINIMUM_5; //!< Configure line activation and precharging minimum time
dmc_timing_config.tCMD = DMC_ATA_CMD_7; //!< Configure active to active period
dmc_timing_config.tRCD = DMC_DELAY_TIME_2; //!< Configure RAS To CAS delay Time
dmc_timing_config.tRP = DMC_PRECHARGE_2; //!< Configure precharge period
dmc_timing_config.tWR = DMC_NEXT_PRECHARGE_2; //!< Configure time between the Last Data and The Next Precharge for write
dmc_timing_config.tXSR = 6; //!< Configure XSR0
dmc_timing_config.tRFP = 0xC3; //!< Configure refresh Cycle
#if SDRAM_TARGET_BANK == 1
dmc_init_config.bankWidth = DMC_BANK_WIDTH_1; //!< Configure bank address width
#else
dmc_init_config.bankWidth = DMC_BANK_WIDTH_2; //!< Configure bank address width
#endif
dmc_init_config.clkPhase = DMC_CLK_PHASE_REVERSE; //!< Configure clock phase
dmc_init_config.rowWidth = SDRAM_ROW_BITS; //!< Configure row address width
dmc_init_config.colWidth = SDRAM_COLUMN_BITS; //!< Configure column address width
dmc_init_config.memorySize = SDRAM_MEMORY_SIZE;
dmc_init_config.timing = dmc_timing_config;
DMC_Config(&dmc_init_config);
DMC_ConfigOpenBank(DMC_BANK_NUMBER_2);
DMC_EnableAccelerateModule();
DMC_Enable();
LOG_D("sdram clock: %d MHz\r\n", RCM_ReadSYSCLKFreq()/1000000/(RCM->CFG_B.SDRAMPSC + 1));
LOG_D("sdram init success, mapped at 0x%X, size is %d bytes, data width is %d", SDRAM_BANK_ADDR, SDRAM_SIZE, SDRAM_DATA_WIDTH);
#ifdef RT_USING_MEMHEAP_AS_HEAP
/* If RT_USING_MEMHEAP_AS_HEAP is enabled, SDRAM is initialized to the heap */
rt_memheap_init(&system_heap, "sdram", (void *)SDRAM_BANK_ADDR, SDRAM_SIZE);
#endif
return result;
}
INIT_BOARD_EXPORT(SDRAM_Init);
#ifdef DRV_DEBUG
#ifdef FINSH_USING_MSH
int sdram_test(void)
{
int i = 0;
uint32_t start_time = 0, time_cast = 0;
#if SDRAM_DATA_WIDTH == 8
char data_width = 1;
uint8_t data = 0;
#elif SDRAM_DATA_WIDTH == 16
char data_width = 2;
uint16_t data = 0;
#else
char data_width = 4;
uint32_t data = 0;
#endif
/* write data */
LOG_D("Writing the %ld bytes data, waiting....", SDRAM_SIZE);
start_time = rt_tick_get();
for (i = 0; i < SDRAM_SIZE / data_width; i++)
{
#if SDRAM_DATA_WIDTH == 8
*(__IO uint8_t *)(SDRAM_BANK_ADDR + i * data_width) = (uint8_t)(i % 100);
#elif SDRAM_DATA_WIDTH == 16
*(__IO uint16_t *)(SDRAM_BANK_ADDR + i * data_width) = (uint16_t)(i % 1000);
#else
*(__IO uint32_t *)(SDRAM_BANK_ADDR + i * data_width) = (uint32_t)(i % 1000);
#endif
}
time_cast = rt_tick_get() - start_time;
LOG_D("Write data success, total time: %d.%03dS.", time_cast / RT_TICK_PER_SECOND,
time_cast % RT_TICK_PER_SECOND / ((RT_TICK_PER_SECOND * 1 + 999) / 1000));
/* read data */
LOG_D("start Reading and verifying data, waiting....");
for (i = 0; i < SDRAM_SIZE / data_width; i++)
{
#if SDRAM_DATA_WIDTH == 8
data = *(__IO uint8_t *)(SDRAM_BANK_ADDR + i * data_width);
if (data != i % 100)
{
LOG_E("SDRAM test failed!");
break;
}
#elif SDRAM_DATA_WIDTH == 16
data = *(__IO uint16_t *)(SDRAM_BANK_ADDR + i * data_width);
if (data != i % 1000)
{
LOG_E("SDRAM test failed!");
break;
}
#else
data = *(__IO uint32_t *)(SDRAM_BANK_ADDR + i * data_width);
if (data != i % 1000)
{
LOG_E("SDRAM test failed!");
break;
}
#endif
}
if (i >= SDRAM_SIZE / data_width)
{
LOG_D("SDRAM test success!");
}
return RT_EOK;
}
MSH_CMD_EXPORT(sdram_test, sdram test)
#endif /* FINSH_USING_MSH */
#endif /* DRV_DEBUG */
#endif /* BSP_USING_SDRAM */
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-28 luobeihai first version
*/
#ifndef __DRV_SDRAM_H__
#define __DRV_SDRAM_H__
/* parameters for sdram peripheral */
/* Bank1 or Bank2 */
#define SDRAM_TARGET_BANK 1
/* apm32f407 Bank Addr: 0x60000000 */
#define SDRAM_BANK_ADDR ((uint32_t)0x60000000)
/* data width: 8, 16, 32 */
#define SDRAM_DATA_WIDTH 16
/* column bit numbers */
#define SDRAM_COLUMN_BITS DMC_COL_WIDTH_8
/* row bit numbers */
#define SDRAM_ROW_BITS DMC_ROW_WIDTH_11
#define SDRAM_MEMORY_SIZE DMC_MEMORY_SIZE_2MB
#define SDRAM_SIZE ((uint32_t)0x200000)
/* memory mode register */
#define SDRAM_MODEREG_BURST_LENGTH_1 ((uint16_t)0x0000)
#define SDRAM_MODEREG_BURST_LENGTH_2 ((uint16_t)0x0001)
#define SDRAM_MODEREG_BURST_LENGTH_4 ((uint16_t)0x0002)
#define SDRAM_MODEREG_BURST_LENGTH_8 ((uint16_t)0x0004)
#define SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL ((uint16_t)0x0000)
#define SDRAM_MODEREG_BURST_TYPE_INTERLEAVED ((uint16_t)0x0008)
#define SDRAM_MODEREG_CAS_LATENCY_2 ((uint16_t)0x0020)
#define SDRAM_MODEREG_CAS_LATENCY_3 ((uint16_t)0x0030)
#define SDRAM_MODEREG_OPERATING_MODE_STANDARD ((uint16_t)0x0000)
#define SDRAM_MODEREG_WRITEBURST_MODE_PROGRAMMED ((uint16_t)0x0000)
#define SDRAM_MODEREG_WRITEBURST_MODE_SINGLE ((uint16_t)0x0200)
#endif
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-28 luobeihai first version
*/
#ifndef _FAL_CFG_H_
#define _FAL_CFG_H_
#include <rtthread.h>
#include <board.h>
extern const struct fal_flash_dev apm32_onchip_flash;
/* flash device table */
#define FAL_FLASH_DEV_TABLE \
{ \
&apm32_onchip_flash, \
}
/* ====================== Partition Configuration ========================== */
#ifdef FAL_PART_HAS_TABLE_CFG
/* partition table */
#define FAL_PART_TABLE \
{ \
{FAL_PART_MAGIC_WROD, "app", "onchip_flash", 0, 496 * 1024, 0}, \
{FAL_PART_MAGIC_WROD, "param", "onchip_flash", 496* 1024 , 16 * 1024, 0}, \
}
#endif /* FAL_PART_HAS_TABLE_CFG */
#endif /* _FAL_CFG_H_ */
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-27 luobeihai first version
*/
#include <rtthread.h>
#ifdef BSP_USING_SDCARD
#include <dfs_elm.h>
#include <dfs_fs.h>
#include <dfs_file.h>
#include <unistd.h>
#include <stdio.h>
#include <sys/stat.h>
#include <sys/statfs.h>
#define DBG_TAG "app.card"
#define DBG_LVL DBG_INFO
#include <rtdbg.h>
void sd_mount(void *parameter)
{
while (1)
{
rt_thread_mdelay(500);
if(rt_device_find("sd0") != RT_NULL)
{
if (dfs_mount("sd0", "/", "elm", 0, 0) == RT_EOK)
{
LOG_I("sd card mount to '/'");
break;
}
else
{
LOG_W("sd card mount to '/' failed!");
}
}
}
}
int apm32_sdcard_mount(void)
{
rt_thread_t tid;
tid = rt_thread_create("sd_mount", sd_mount, RT_NULL,
2048, RT_THREAD_PRIORITY_MAX - 2, 20);
if (tid != RT_NULL)
{
rt_thread_startup(tid);
}
else
{
LOG_E("create sd_mount thread err!");
}
return RT_EOK;
}
INIT_APP_EXPORT(apm32_sdcard_mount);
#endif /* BSP_USING_SDCARD */
/*
* Copyright (c) 2006-2023, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
* 2023-03-28 luobeihai first version
*/
#include <rtthread.h>
#include "spi_flash.h"
#include "spi_flash_sfud.h"
#include "drv_spi.h"
#if defined(BSP_USING_SPI_FLASH)
static int rt_hw_spi_flash_init(void)
{
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOA);
rt_hw_spi_device_attach("spi3", "spi30", GPIOA, GPIO_PIN_15);
if (RT_NULL == rt_sfud_flash_probe("W25Q16", "spi30"))
{
return -RT_ERROR;
}
return RT_EOK;
}
INIT_COMPONENT_EXPORT(rt_hw_spi_flash_init);
#endif
此差异已折叠。
<?xml version="1.0" encoding="iso-8859-1"?>
<workspace>
<project>
<path>$WS_DIR$\project.ewp</path>
</project>
<batchBuild/>
</workspace>
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
<?xml version="1.0" encoding="iso-8859-1"?>
<workspace>
<project>
<path>$WS_DIR$\template.ewp</path>
</project>
<batchBuild/>
</workspace>
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册