目录
6.1 系统提示low voltage detected, date/time is not reliable.
1. 环境
- 芯片:全志T113
- 内核:Linux TinaLinux 5.4.61
- 系统:T113-S3 Tina5.0
2. 前言
硬件部门交付的主板上外挂了一颗RTC时钟芯片PCF8563,我需要实现pcf8563的驱动、外部rtc同步到系统、开机自动同步时间等工作。
这类时钟芯片大多数是通过i2c通讯和soc进行连接,而且linux内核自带了pcf8563的驱动,如果顺利的话,开发起来是非常顺利的。但是由于不熟悉流程,所以踩了很多坑,写下来作为记录供后人参考。
3. 硬件设计
外围电路参考
对比当前原理图设计,符合参考设计
所以我们的工作就是通过i2c读取时钟芯片寄存器来获取时间,连接方式:
RTC_I2C2_SCL -> PG14
RTC_I2C2_SDA -> PG15
4. 内核配置
进入kernel_menuconfig
make kernel_menuconfig
跳转到
->Device Driver
->Real Time Clock
4.1 启用debug
在系统初始化和调用rtc时能显示debug信息
往下看到Allwinner sunxi RTC,这是系统内置rtc
可以看到默认启用了系统内置的rtc以及两个附加功能,我选择了把内置时钟关掉,这样以后在系统中不会出现两个rtc设备,避免后续使用错误
4.2 关闭系统自带rtc
4.3 启用pcf8563驱动支持
注意不要选错成相近的型号。
不管是NXP的还是飞利浦的PCF8563,都是选这个8563,不同厂商的同型号料一般是pin to pin,引脚和功能都是一样的
内核配置结束,保存退出
5. 在设备树中配置rtc设备节点
5.1 确认i2c引脚配置
查看原理图,外部rtc的i2c线连接到了i2c2
参考【全志T113-S3_100ask】6-编写IIC驱动GY-302(twi)_全志twi-CSDN博客
得知i2c2,也就是设备树中的twi2
查看T113芯片手册,可知twi2默认是分配给引脚PE12、PE13
而原理图上分配给了PG14、PG15,位于function3功能
所以需要在板设备树board.dts中修改设备twi2_pins引脚配置为PG14、PG15
T113-Tina/device/config/chips/t113_i/configs/evb1_auto/board.dts
5.2 添加设备节点
阅读内核驱动中的pcf8563移植说明,可以知道我们应该怎么添加设备节点
T113-Tina/kernel/linux-5.4/Documentation/devicetree/bindings/rtc/pcf8563.txt
找到&twi2,在&twi2的设备树中增加pcf8563节点,并把status状态改为okay来启用
下面代码中绿色部分是增加的代码
&twi2 {
clock-frequency = <400000>;
pinctrl-0 = <&twi2_pins_a>;
pinctrl-1 = <&twi2_pins_b>;
pinctrl-names = "default", "sleep";
twi_drv_used = <1>;
dmas = <&dma 45>, <&dma 45>;
dma-names = "tx", "rx";
status = "okay";
+ pcf8563: pcf8563@51 {
+ status = "okay";
+ compatible = "nxp,pcf8563";
+ reg = <0x51>; // 读a3h, 写a2h: a3 >> 1 = 0x51
+ #clock-cells = <0>;
+ };
};
小课堂:关于reg的计算方式
i2c从机地址通常由7位的二进制数值组成,但linux在实际通讯使用时会扩展为8位,在最低位拼接一位操作位,0表示写,1表示读。
比如pcf8563的从机地址从芯片文档中可知:
从机地址 | 读 | 写 |
十六进制 | 0xA3 | 0xA2 |
二进制 | 1010001 | 10100010 |
所以要取这个i2c设备的从机地址,是将0xA3或者0xA2右移一位得到
0xA3 >> 1 = 0x51
简单理解,就是将读写地址的二进制的最后一位去掉,再转换成16进制
10100011 -> 1010001 = 0x51
5.3 确认驱动成功
编译烧录后可以在开机启动日志中识别到rtc-pcf8563
在设备树dtsi中查看 tw2的地址 2502800
根据tw2的地址,查看tw2设备树
cd /sys/firmware/devicetree/base/soc@3000000/twi@2502800/
ls
能看到pcf8563@51,说明设备树rtc节点配置正确
ls /dev/
也能查看到rtc0设备
说明系统能成功识别到pcf8563
5.4 联网后校准系统时间
在联网后,使用ntp来同步网络时间到系统
ntpd -p cn.pool.ntp.org -q
5.5 查看和设置rtc时钟
查看rtc详细信息
cat /proc/driver/rtc
查看rtc时间
hwclock -r
设置rtc时间与系统时间同步
hwclock -w
掉电后启动设备,测试外部rtc时间保存正常,也成功同步到了系统,验证pcf8563调试成功
6. 过程中遇到的问题
6.1 系统提示low voltage detected, date/time is not reliable.
参考RTC时钟操作记录_rtc-pcf8563 0-0051: low voltage detected-CSDN博客
搜索得知是rtc掉电检测器生效,pcf8563首次操作前处于未初始化状态、或者是出现过电压过低的情况会报这个错,表示rtc时间不再可信
寄存器VL位置被置为高
查看pcf8563芯片手册可确认原理
使用hwclock命令写入rtc一次即可解决
使用hwclock命令写入rtc一次即可解决
6.2 开机后系统时间还原为1970年
排查内核配置是否有启用这个开机自动从外部RTC同步时间的选项
也可以排查一下RTC开机后的时间是否还原为1970年,如果是的话,大概率是RTC是内部的,外部RTC没驱动起来,所以一掉电内部RTC就丢时间了。所以在一开始要把内部RTC关闭掉,这样 /dev/rtc0 这个设备一定是外部的,如果连 /dev/rtc0 设备都没有的话那就说明外部rtc没有成功驱动,重点排查i2c接口引脚定义是否正确、是否在内核配置中启用驱动支持。
RTC 驱动会注册生成串口设备/dev/rtcN,如果关闭了内置的rtc的话,只会有一个外部的rtc0