Toggle navigation
首页
问答
文章
积分商城
专家
专区
更多专区...
文档中心
返回主站
搜索
提问
会员
中心
登录
注册
AB32VG1
RTC
AB32VG1 评测 RTC
发布于 2021-03-26 23:59:12 浏览:1089
订阅该版
[tocm] #### 前章 这次评测 AB32VG1 的 RTC,特别的激动。因为是我首次真正接触 RISCV 架构的处理器的开发。我喜欢尝试新鲜的事物,所以就充满了激动。平时都是在 Linux 开发,但是官方提供的开发包呢是在 win 下的,没有提供 Linux 环境的工具链。 这时候就只能自己动手了,我喜欢这个过程,特别是在从 github 拉取 riscv/riscv-gnu-toolchain.git 仓库的时候,开始几次总是被中断(虽然我用了 github 增强高速下载脚本)。这个脚本安装后可以加速当前的仓库,但是呢 ```riscv-gnu-toolchain``` 这个仓库有很很多的 submodule。 ```bash ▸git submodule 57dfc2c4d51e770ed3f617e5d1456d1e2bacf3f0 qemu (v4.0.0-1854-g57dfc2c4d5) 2cb5c79dad39dd438fb0f7372ac04cf5aa2a7db7 riscv-binutils (heads/riscv-binutils-2.35) 4ea498a8e1fafeb568530d84db1880066478c86b riscv-dejagnu (heads/riscv-dejagnu-1.6) +4e3d3e40726e1b68bf52fa205c68495124ea60b8 riscv-gcc (heads/master) 63a44e5923c859e99d3a8799fa8132b49a135241 riscv-gdb (remotes/origin/fsf-gdb-10.1-with-sim) 7395b0964db9cc4dd544926414960e9a16842180 riscv-glibc (heads/riscv-glibc-2.29) 415fdd4279b85eeec9d54775ce13c5c412451e08 riscv-newlib (newlib-4.1.0) ``` 在拉取 submodule 的时候就没有这么顺利了。导致前几次都没有成功。后来我尝试使用 `git submodule set-url` 命令来逐一修改这些 submodule 的路径,修改后是这样的: ```diff diff --git a/.gitmodules b/.gitmodules index 16a79de..4d19447 100644 --- a/.gitmodules +++ b/.gitmodules @@ -4,7 +4,7 @@ branch = riscv-binutils-2.35 [submodule "riscv-gcc"] path = riscv-gcc - url = ../riscv-gcc.git + url = https://hub.fastgit.org/riscv/riscv-gcc.git branch = riscv-gcc-10.2.0 [submodule "riscv-glibc"] path = riscv-glibc @@ -16,12 +16,12 @@ branch = riscv-dejagnu-1.6 [submodule "riscv-newlib"] path = riscv-newlib - url = git://sourceware.org/git/newlib-cygwin.git + url = https://hub.fastgit.org/riscv/riscv-newlib.git branch = master [submodule "riscv-gdb"] path = riscv-gdb - url = ../riscv-binutils-gdb.git + url = https://hub.fastgit.org/riscv/riscv-binutils-gdb.git branch = fsf-gdb-10.1-with-sim [submodule "qemu"] path = qemu - url = https://git.qemu.org/git/qemu.git + url = https://gitclone.com/github.com/qemu/qemu.git ``` 修改后发现直接 ```git submodule update init``` 在拉取过程中还是会中断,因为需要拉取的文件实在是太大了。这时候我学会了一招 [分阶段拉取](https://about.gitlab.com/blog/2020/03/13/partial-clone-for-massive-repositories/) 通过添加 --filter 的配置可以有选择性的拉取必要的内容,然后在切换非默认分支的时候继续拉取新的内容。 **这也是在评测过程中对 git 工具使用上的一点收获**。 在配置工具链的时候,第一次使用默认的配置发现编译的时候提示出错,因为默认只是支持 64bit 的。而 **AB32VG1** 是 32 bit 的。所以需要在配置的时候开启 32 bit 的支持,需要添加选项 ``` --enable-multilib``` ``` bash ./configure --enable-multilib ``` 配置之后直接 ```make -j``` 在服务器上编译,大概经过了有半小时左右终于编译完成了。编译出来的内容有 1.6G 大小。 ``` bash ┗─╼[~/red_misc/riscv-gnu-toolchain (master)] ▸du -sh ../riscv_tools_mul 1.6G ../riscv_tools_mul ``` 本来还计划使用 ```openocd``` 完成烧录的流程呢,通过微信群的咨询,发现对方并不支持```JTAG``` 的调试,所以这个也作罢了,只能在 linux 上开发,然后到 windows 上烧录了。这部分章节我还发了一个文章[搭建 linux 下的编译环境,使用 uart1 双线串口作为 console](https://club.rt-thread.org/ask/article/2622.html) 。下面开始正文了。 #### 硬件介绍 我这次评测的是 RTC 部分,重点先看下原理图![原理图部分](https://ftp.bmp.ovh/imgs/2021/03/afa68dcedcd9bf2b.png) 对应的实物图 ![实物图](https://ftp.bmp.ovh/imgs/2021/03/c9cd14e664dcfd33.jpg) 刚开始拿到板子的时候电容 **C7 和 C10** 并没有焊接,我还以为少焊接了呢,回看原理图发现原理图就是 **NC** 的。和 @greedyhao 朱工沟通后才知道内部有电容可以控制外接的 **32.768K** 晶振起振。这都是后话了。 硬件的 RTC 实际也没有太多的东西。还有一个后备电源部分: ![后备电源](https://ftp.bmp.ovh/imgs/2021/03/f21047e497bddf0e.png) 可以看出来 VBAT 是直接通过排针和跳帽连通起来的,所以没有后备电源。这时候正常的情况就是断电之后会检测到掉电重新配置 RTC,而复位等操作并不应该导致时间重新配置。 #### RTC 的功能说明&演示 一般地在系统中 RTC 提供一个计时的功能,比如系统时钟、打印时间戳的时间等等。有关系统时间的测试,我就先从简单的在 ```msh``` 测试 RTC 功能。一个简单的命令 ```date```。在启用 RTC 设备情况下,date 会从 rtc 设备获取时间戳。 ``` C RT_WEAK time_t time(time_t *t) { time_t time_now = ((time_t)-1); /* default is not available */ #ifdef RT_USING_RTC static rt_device_t device = RT_NULL; /* optimization: find rtc device only first */ if (device == RT_NULL) { device = rt_device_find("rtc"); } /* read timestamp from RTC device */ if (device != RT_NULL) { if (rt_device_open(device, 0) == RT_EOK) { rt_device_control(device, RT_DEVICE_CTRL_RTC_GET_TIME, &time_now); rt_device_close(device); } } #endif /* RT_USING_RTC */ /* if t is not NULL, write timestamp to *t */ if (t != RT_NULL) { *t = time_now; } if(time_now == (time_t)-1) { errno = ENOSYS; } return time_now; } RTM_EXPORT(time); ``` 所以只需要注册一个名为 ```RTC``` 的设备,提供一个对应的 control 接口函数,支持 ```RT_DEVICE_CTRL_RTC_GET_TIME``` 命令参数就可以了。刚开始的时候会出现返回值 -1 的错误。调试发现 time_t 的 size 是 8 个字节和 ```AB32VG1``` 实际的长度不匹配。通过添加宏 ``` -D_USE_LONG_TIME_T``` 修复这个问题,对应的 pr [Fix sizeof(time_t) no match with this chip](https://github.com/RT-Thread/rt-thread/pull/4483/files)。修复后就可以 date 命令就正常了。 ``` msh >date 2021 03 23 15 53 55 msh > msh > msh > msh >date Tue Mar 23 15:53:57 2021 msh > msh >date Tue Mar 23 15:54:00 2021 msh >reset reset: command not found. msh >reboot reboot: command not found. msh > \ | / - RT - Thread Operating System / | \ 4.0.3 build Mar 23 2021 2006 - 2021 Copyright by rt-thread team Hello, world msh >date Tue Mar 23 15:54:10 2021 msh > ``` 这里测试功能我就使用 ```ULOG``` 带有时间戳的格式化打印展示下效果(使用 ```uart1``` 作为 console): ![ulog](https://ftp.bmp.ovh/imgs/2021/03/e9c79dc734f46c0f.png) 之前使用 ```Downloader``` 作为 ```console```,效果不对,应该是对那些颜色格式处理的不好,导致打印异常。 ![downloader](https://ftp.bmp.ovh/imgs/2021/03/6e2849594e9a99f5.png) 然后就是评测一下 alarm 中断还有一个 1s 的中断功能(即每秒中断),先展示下效果了: ![test_1s.gif](https://oss-club.rt-thread.org/uploads/20210327/7eb9df75730831fdb401a9e7e5053ca1.gif) 还有 alarm 中断的效果 ![test_alarm.gif](https://oss-club.rt-thread.org/uploads/20210327/32197f9a44fe020ac854fb37e41207ca.gif) 相关的驱动补丁,我也提交了一个 pr [Add alarm and 1 second interrupt support](https://github.com/RT-Thread/rt-thread/pull/4529). 关键的部分就是注册中断处理函数以及开启对应的中断,我发现在 bit ```RTC1SPND``` 会在每秒钟的时候都会置 1 ,为了更好的处理中断,我添加了一个宏 ```RTC_USING_1S_INT``` 在中断处理函数中过滤对 1s 中断的处理,避免在未开启该中断但是开启 ALARM 中断的情况下错误处理 1s 的中断。对应的补丁为: ``` diff diff --git a/bsp/bluetrum/ab32vg1-ab-prougen/board/Kconfig b/bsp/bluetrum/ab32vg1-ab-prougen/board/Kconfig index decdf156d..2bdce74a2 100644 --- a/bsp/bluetrum/ab32vg1-ab-prougen/board/Kconfig +++ b/bsp/bluetrum/ab32vg1-ab-prougen/board/Kconfig @@ -176,6 +176,10 @@ menu "On-chip Peripheral Drivers" config RTC_USING_INTERNAL_CLK bool "Using internal clock RTC" default y + config RTC_USING_1S_INT + bool "Using 1 second interrupt" + depends on RT_USING_ALARM + default n endif menuconfig BSP_USING_ADC diff --git a/bsp/bluetrum/libraries/hal_drivers/drv_rtc.c b/bsp/bluetrum/libraries/hal_drivers/drv_rtc.c index 4f462e904..4749ba51e 100644 --- a/bsp/bluetrum/libraries/hal_drivers/drv_rtc.c +++ b/bsp/bluetrum/libraries/hal_drivers/drv_rtc.c @@ -7,6 +7,7 @@ * Date Author Notes * 2021-01-28 greedyhao first version * 2021-03-19 iysheng modify just set time first power up + * 2021-03-26 iysheng add alarm and 1s interrupt support */ #include "board.h" @@ -134,15 +135,22 @@ void hal_rtc_init(void) irtc_time_write(RTCCNT_CMD, sec); } +#ifdef RT_USING_ALARM + RTCCON |= RTC_CON_ALM_INTERRUPT; +#ifdef RTC_USING_1S_INT + RTCCON |= RTC_CON_1S_INTERRUPT; +#endif +#endif } /************** HAL End *******************/ -static time_t get_rtc_timestamp(void) +static time_t get_rtc_time_stamp(void) { time_t sec = 0; sec = irtc_time_read(RTCCNT_CMD); LOG_D("get rtc time."); + return sec; } @@ -153,6 +161,22 @@ static rt_err_t set_rtc_time_stamp(time_t time_stamp) return RT_EOK; } +static rt_err_t set_rtc_alarm_stamp(time_t alarm_stamp) +{ + irtc_time_write(RTCALM_CMD, alarm_stamp); + + return RT_EOK; +} + +static time_t get_rtc_alarm_stamp(void) +{ + time_t sec = 0; + + sec = irtc_time_read(RTCALM_CMD); + + return sec; +} + static void rt_rtc_init(void) { hal_rtc_init(); @@ -165,8 +189,8 @@ static rt_err_t rt_rtc_control(rt_device_t dev, int cmd, void *args) switch (cmd) { case RT_DEVICE_CTRL_RTC_GET_TIME: - *(rt_uint32_t *)args = get_rtc_timestamp(); - LOG_D("RTC: get rtc_time %x\n", *(rt_uint32_t *)args); + *(rt_uint32_t *)args = get_rtc_time_stamp(); + LOG_D("RTC: get rtc_time %x", *(rt_uint32_t *)args); break; case RT_DEVICE_CTRL_RTC_SET_TIME: @@ -174,7 +198,18 @@ static rt_err_t rt_rtc_control(rt_device_t dev, int cmd, void *args) { result = -RT_ERROR; } - LOG_D("RTC: set rtc_time %x\n", *(rt_uint32_t *)args); + LOG_D("RTC: set rtc_time %x", *(rt_uint32_t *)args); + break; + case RT_DEVICE_CTRL_RTC_SET_ALARM: + if (set_rtc_alarm_stamp(*(rt_uint32_t *)args)) + { + result = -RT_ERROR; + } + LOG_D("RTC: set alarm_stamp %x", *(rt_uint32_t *)args); + break; + case RT_DEVICE_CTRL_RTC_GET_ALARM: + *(rt_uint32_t *)args = get_rtc_alarm_stamp(); + LOG_D("RTC: get alarm_stamp %x", *(rt_uint32_t *)args); break; } @@ -217,15 +252,41 @@ static rt_err_t rt_hw_rtc_register(rt_device_t device, const char *name, rt_uint return rt_device_register(device, name, flag); } +#ifdef RT_USING_ALARM +static void rtc_isr(int vector, void *param) +{ + rt_interrupt_enter(); + + if (RTCCON & RTC_CON_ALM_PEND) + { + RTCCPND |= RTC_CPND_ALM; + } + +#ifdef RTC_USING_1S_INT + if (RTCCON & RTC_CON_1S_PEND) + { + RTCCPND |= RTC_CPND_1S; + } +#endif + + rt_interrupt_leave(); +} +#endif + int rt_hw_rtc_init(void) { rt_err_t result; + result = rt_hw_rtc_register(&rtc, "rtc", RT_DEVICE_FLAG_RDWR); if (result != RT_EOK) { LOG_E("rtc register err code: %d", result); return result; } + +#ifdef RT_USING_ALARM + rt_hw_interrupt_install(IRQ_RTC_VECTOR, rtc_isr, RT_NULL, "rtc_isr"); +#endif LOG_D("rtc init success"); return RT_EOK; } diff --git a/bsp/bluetrum/libraries/hal_libraries/ab32vg1_hal/include/ab32vg1_hal_rtc.h b/bsp/bluetrum/libraries/hal_libraries/ab32vg1_hal/include/ab32vg1_hal_rtc.h index 483f3e3f4..6961d8da9 100644 --- a/bsp/bluetrum/libraries/hal_libraries/ab32vg1_hal/include/ab32vg1_hal_rtc.h +++ b/bsp/bluetrum/libraries/hal_libraries/ab32vg1_hal/include/ab32vg1_hal_rtc.h @@ -32,6 +32,10 @@ enum #define RTC_CON_BAUD_SELECT (0x3u << 1) /*!< Increase clock selection */ #define RTC_CON_CHIP_SELECT (0x1u << 0) /*!< RTC chip select */ +// RTCCPND +#define RTC_CPND_1S (0x1u << 18) /*!< Clear RTC 1S pending */ +#define RTC_CPND_ALM (0x1u << 17) /*!< Clear RTC alarm pendind */ + // RTCCON0 #define RTC_CON0_PWRUP_FIRST (0x01u << 7) /*!< RTC first power up flag */ #define RTC_CON0_INTERNAL_32K (0x01u << 6) /*!< Internal 32K select */ ``` ### 代码 在开发过程中,我向 [RT-Thread 的 mainline ](https://github.com/RT-Thread/rt-thread)提交了四个 pr,目前四个已经全部被合并。 ### 心得体会 在这次评测过程中,我很开心,第一次开发 ```RISCV``` 架构的处理器代码,完成了工具链的编译(虽然这个难度很低,但终究是自己编译出来的啊,嘿嘿,特别是在从 github 拉取代码的过程中还学到了 git submodule set-url 修改子模块地址以及 git clone --filter 参数在拉取大型仓库中的用处呢,有点类似断点续传) 还有很大的收获,在次特别感谢 @greedyhao 朱工在我提交 pr 过程中的指点以及 review。让我的提交被顺利地 merge 了。 * [Add support with uart2 and optimize serial port config](https://github.com/RT-Thread/rt-thread/pull/4474) * [fix do RT_DEVICE_CTRL_CLOSE cmd when close serial](https://github.com/RT-Thread/rt-thread/pull/4480) * [Fix sizeof(time_t) no match with this chip](https://github.com/RT-Thread/rt-thread/pull/4483) * [Add alarm and 1 second interrupt support](https://github.com/RT-Thread/rt-thread/pull/4529) 能为开源社区做贡献,我个人也感觉特别开心,特别是 pr 被 merge 的时候,在这个过程中可以和优秀的人沟通,这也是一件值得开心的事情。
0
条评论
默认排序
按发布时间排序
登录
注册新账号
关于作者
iysheng
这家伙很懒,什么也没写!
文章
10
回答
15
被采纳
4
关注TA
发私信
相关文章
1
RTC驱动框架几点建议
2
求助:RTT在STM32F407上使用内置的RTC设置日期需重启生效,设置时间即时生效,有遇到同样问题的吗?
3
[新人试水] LPC1768 Nano3_9 添加RTC
4
STM32 关于RTC的问题
5
stm32f4xx-HAL BSP的RTC设置不对
6
关于STM32的RTC设置年份不正确的问题
7
RTT的RTC驱动调试
8
rtc驱动中的bkp模块起不到防止时间的重新设置
9
rtc时钟跑十几个小时后,比实际时间快几秒怎么解决
10
stm32如何断电之后开发板rtc时间继续往前跑
推荐文章
1
RT-Thread应用项目汇总
2
玩转RT-Thread系列教程
3
国产MCU移植系列教程汇总,欢迎查看!
4
机器人操作系统 (ROS2) 和 RT-Thread 通信
5
五分钟玩转RT-Thread新社区
6
【技术三千问】之《玩转ART-Pi》,看这篇就够了!干货汇总
7
关于STM32H7开发板上使用SDIO接口驱动SD卡挂载文件系统的问题总结
8
STM32的“GPU”——DMA2D实例详解
9
RT-Thread隐藏的宝藏之completion
10
【ART-PI】RT-Thread 开启RTC 与 Alarm组件
热门标签
RT-Thread Studio
串口
Env
LWIP
SPI
AT
Bootloader
Hardfault
CAN总线
FinSH
ART-Pi
USB
DMA
文件系统
RT-Thread
SCons
RT-Thread Nano
线程
MQTT
STM32
RTC
FAL
rt-smart
ESP8266
I2C_IIC
WIZnet_W5500
UART
ota在线升级
PWM
cubemx
freemodbus
flash
packages_软件包
BSP
潘多拉开发板_Pandora
定时器
ADC
GD32
flashDB
socket
中断
Debug
编译报错
SFUD
msh
rt_mq_消息队列_msg_queue
keil_MDK
ulog
MicroPython
C++_cpp
本月问答贡献
出出啊
1517
个答案
342
次被采纳
小小李sunny
1443
个答案
289
次被采纳
张世争
805
个答案
174
次被采纳
crystal266
547
个答案
161
次被采纳
whj467467222
1222
个答案
148
次被采纳
本月文章贡献
出出啊
1
篇文章
4
次点赞
小小李sunny
1
篇文章
1
次点赞
张世争
1
篇文章
1
次点赞
crystal266
2
篇文章
2
次点赞
whj467467222
2
篇文章
1
次点赞
回到
顶部
发布
问题
投诉
建议
回到
底部