瑞芯微|rk3568 uart快速上手
一、调试环境
平台:rk3568
kernel: 4.19.232
SDK: rk_android11.0_sdk
Board: rk3568-evb1-ddr4-v10
二、 rk3568 uart控制器
1. 特性:
rk3568 UART控制器特性如下:
- UART控制器通道:UART0~UART8 【datasheet好像写的有问题】
- 包含2组64字节的 FIFO,用于接收和传输
- 支持流控
- 支持速率 115.2Kbps, 460.8Kbps, 921.6Kbps, 1.5Mbps, 3Mbps, 4Mbps
- 支持5、6、7、8 bits数据位。
- 支持1、1.5、2 bits停止位。
- 支持奇校验和偶校验。
- 支持基于中断/DMA 模式
2. UART控制器架构
APB INTERFACE
处理器通过APB接口访问UART的数据,做控制,以及状态信息。
UART支持8、16和32位的APB数据总线宽度。Register block
负责UART的主要功能,包括控制、状态和中断产生。Modem Synchronization block
同步modem输入信号.FIFO block
负责FIFO控制和存储或向发送信号以控制外部RAM。Baud Clock Generator
收发比特率设置。Serial Transmitter
数据发送模块。Serial Receiver
数据接收模块。
3. 控制器驱动
瑞芯微提供sdk中已经提供了8250uart驱动。
以下为主要驱动文件:
drivers/tty/serial/8250/8250_core.c # 8250串口驱动核心
drivers/tty/serial/8250/8250_dw.c # Synopsis DesignWare 8250串口驱动
drivers/tty/serial/8250/8250_dma.c # 8250串口DMA驱动
drivers/tty/serial/8250/8250_port.c # 8250串口端口操作
drivers/tty/serial/8250/8250_early.c # 8250串口early console驱动
4. 设备树:
普通串口设备将会根据dts中的aliase来对串口进行编号,对应注册成ttySx设备。
dts中的aliases如下:
aliases {
serial0 = &uart0;
serial1 = &uart1;
serial2 = &uart2;
serial3 = &uart3;
......
@kernel\arch\arm64\boot\dts\rockchip\rk3568.dtsi
uart6: serial@fe6a0000 {
compatible = "rockchip,rk3568-uart", "snps,dw-apb-uart";
reg = <0x0 0xfe6a0000 0x0 0x100>;
interrupts = <GIC_SPI 122 IRQ_TYPE_LEVEL_HIGH>;
clocks = <&cru SCLK_UART6>, <&cru PCLK_UART6>;
clock-names = "baudclk", "apb_pclk";
reg-shift = <2>;
reg-io-width = <4>;
dmas = <&dmac0 12>, <&dmac0 13>;
pinctrl-names = "default";
pinctrl-0 = <&uart6m0_xfer>;
status = "disabled";
};
UART的板级dts配置只有以下参数允许修改:
- dma-names:
"tx" 打开tx dma
"rx" 打开rx dma
"!tx" 关闭tx dma
"!rx" 关闭rx dma - pinctrl-0:
&uart1m0_xfer 配置tx和rx引脚为iomux group 0
&uart1m1_xfer 配置tx和rx引脚为iomux group 1
&uart1m0_ctsn和&uart1m0_rtsn 配置硬件自动流控cts和rts引脚为iomux group 0
&uart1m1_ctsn和&uart1m1_rtsn 配置硬件自动流控cts和rts引脚为iomux group 1 - status:
"okay" 打开
"disabled" 关闭
引脚说明在下面定义:
以UART6为例:
@kernel\arch\arm64\boot\dts\rockchip\rk3568-pinctrl.dtsi
uart6 {
/omit-if-no-ref/
uart6m0_xfer: uart6m0-xfer {
rockchip,pins =
/* uart6_rxm0 */
<2 RK_PA3 3 &pcfg_pull_up>,
/* uart6_txm0 */
<2 RK_PA4 3 &pcfg_pull_up>;
};
/omit-if-no-ref/
uart6m0_ctsn: uart6m0-ctsn {
rockchip,pins =
/* uart6m0_ctsn */
<2 RK_PC0 3 &pcfg_pull_none>;
};
/omit-if-no-ref/
uart6m0_rtsn: uart6m0-rtsn {
rockchip,pins =
/* uart6m0_rtsn */
<2 RK_PB7 3 &pcfg_pull_none>;
};
/omit-if-no-ref/
uart6m1_xfer: uart6m1-xfer {
rockchip,pins =
/* uart6_rxm1 */
<1 RK_PD6 3 &pcfg_pull_up>,
/* uart6_txm1 */
<1 RK_PD5 3 &pcfg_pull_up>;
};
};
5. 使用硬件自动流控
UART使用硬件自动流控时,需要确保UART驱动使能硬件自动流控功能,且在dts中已经切换cts和rts流控引脚的iomux。
建议在高波特率(1.5M波特率及以上)、大数据量的场景下都使用硬件自动流控,即使用四线UART。
6. 使用串口唤醒系统
串口唤醒系统功能是在系统待机时串口保持打开,并且把串口中断设置为唤醒源。使用时需要在dts中增
加以下参数:
&uart1 {
wakeup-source;
};
注意,串口唤醒系统需要同时修改trust固件,请联系Rockchip以获取支持。
三、 移植
1. 修改设备树
sdk中UART默认并没有打开,所以我们只需要修改设备树就可以了。
下面以uart6为例,带流控:
/arch/arm64/boot/dts/rockchip/rk3568-evb1-ddr4-v10.dtsi
&uart6{
status = "okay";
pinctrl-names = "default";
pinctrl-0 = <&uart6m1_xfer >;
};
注意:
引脚选择有两种配置: m0、m1;
编写设备树之前,查看电路图先确认,
公板是m1。
只有m0支持流控,如果需要支持设置 pinctrl-0:
pinctrl-0 = <&uart6m0_xfer &uart6m0_ctsn &uart6m0_rtsn>;
重新编译烧录boot.img即可。
查看设备文件
rk3568_r:/ # ls /dev/ttyS*
/dev/ttyS6 /dev/ttyS8
其中ttyS8是给蓝牙使用。
2. 引脚复用问题:uart6与gmac0冲突
uart6引脚与以太网口Gmac0会有冲突:
@kernel\arch\arm64\boot\dts\rockchip\rk3568-pinctrl.dtsi
gmac0 {
/omit-if-no-ref/
gmac0_miim: gmac0-miim {
rockchip,pins =
/* gmac0_mdc */
<2 RK_PC3 2 &pcfg_pull_none>,
/* gmac0_mdio */
<2 RK_PC4 2 &pcfg_pull_none>;
};
…………………………
/omit-if-no-ref/
gmac0_rgmii_bus: gmac0-rgmii-bus {
rockchip,pins =
/* gmac0_rxd2 */
<2 RK_PA3 2 &pcfg_pull_none>,
/* gmac0_rxd3 */
<2 RK_PA4 2 &pcfg_pull_none>,
/* gmac0_txd2 */
<2 RK_PA6 2 &pcfg_pull_none_drv_level_2>,
/* gmac0_txd3 */
<2 RK_PA7 2 &pcfg_pull_none_drv_level_2>;
};
};
只需要禁用gmac0即可
/arch/arm64/boot/dts/rockchip/rk3568-evb1-ddr4-v10.dtsi
&gmac0 {
………………
phy-handle = <&rgmii_phy0>;
status = "disable";
};
3. 通过寄存器,查看引脚复用配置情况
uart6使用到的引脚如下:
1) GRF_GPIO1D_IOMUX_H
Address: Operational Base + offset (0x001C)
2) GRF_GPIO2A_IOMUX_L
Address: Operational Base + offset (0x0020)
3) GRF_GPIO2A_IOMUX_H
Address: Operational Base + offset (0x0024)
4) GRF_GPIO2B_IOMUX_H
Address: Operational Base + offset (0x002C)
5) GRF_GPIO2C_IOMUX_L
Address: Operational Base + offset (0x0030)
uart6寄存器配置对应位位置如下图所示:,
我们只设置m1引脚为uart6的收发引脚,m0引脚未设置
所以只有寄存器 0xFDC60000+0x1c 的 bit[11:4]为 33
四、测试
公板预留了UART2~UART7的接口(4根线),
一口君不会焊接线,所以直接找的硬件工程师把线连好,
我只负责测试。
板子上的测试程序,瑞芯微官方已经提供了: ts_uart.uart
该工具获取,见文章底部。
1. 移植ts_uart.uart
adb root
adb remount
adb push ts_uart.uart /bin
adb push send_0x55 /bin
adb push send_00_ff /bin
2. ts_uart.uart实用
1) 查看ts_uart.uart帮助信息:
rk3568_r:/ # ts_uart.uart
Use the following format to run the HS-UART TEST PROGRAM
ts_uart v1.1
For sending data:
./ts_uart <tx_rx(s/r)> <file_name> <baudrate> <flow_control(0/1)> <max_delay(0-100)> <random_size(0/1)>
tx_rx : send data from file (s) or receive data (r) to put in file
file_name : file name to send data from or place data in
baudrate : baud rate used for TX/RX
flow_control : enables (1) or disables (0) Hardware flow control using RTS/CTS lines
max_delay : defines delay in seconds between each data burst when sending. Choose 0 for continuous stream.
random_size : enables (1) or disables (0) random size data bursts when sending. Choose 0 for max size.
max_delay and random_size are useful for sleep/wakeup over UART testing. ONLY meaningful when sending data
Examples:
Sending data (no delays)
ts_uart s init.rc 1500000 0 0 0 /dev/ttyS0
loop back mode:
ts_uart m init.rc 1500000 0 0 0 /dev/ttyS0
receive, data must be 0x55
ts_uart r init.rc 1500000 0 0 0 /dev/ttyS0
2) 非流控read:
ts_uart.uart r init.rc 115200 0 0 0 /dev/ttyS6
3) 流控read:
ts_uart.uart r init.rc 115200 1 0 0 /dev/ttyS6
4) 非流控write:
ts_uart.uart s /data/send_0x55.0x55 115200 0 0 0 /dev/ttyS6
5) 流控write:
ts_uart.uart s /data/send_0x55.0x55 115200 1 0 0 /dev/ttyS6
五、编写自己的测试程序
下面是一口君自己编写的测试程序,可以实现简单的数据收发,
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<unistd.h>
#include<termios.h>
#include<string.h>
int set_opt(int fd,int nSpeed, int nBits, char nEvent, int nStop)
{
struct termios newtio,oldtio;
if ( tcgetattr( fd,&oldtio) != 0)
{
perror("SetupSerial 1");
return -1;
}
bzero( &newtio, sizeof( newtio ) );
newtio.c_cflag |= CLOCAL | CREAD;
newtio.c_cflag &= ~CSIZE;
switch( nBits )
{
case 7:
newtio.c_cflag |= CS7;
break;
case 8:
newtio.c_cflag |= CS8;
break;
}
switch( nEvent )
{
case 'O':
newtio.c_cflag |= PARENB;
newtio.c_cflag |= PARODD;
newtio.c_iflag |= (INPCK | ISTRIP);
break;
case 'E':
newtio.c_iflag |= (INPCK | ISTRIP);
newtio.c_cflag |= PARENB;
newtio.c_cflag &= ~PARODD;
break;
case 'N':
newtio.c_cflag &= ~PARENB;
break;
}
switch( nSpeed )
{
case 2400:
cfsetispeed(&newtio, B2400);
cfsetospeed(&newtio, B2400);
break;
case 4800:
cfsetispeed(&newtio, B4800);
cfsetospeed(&newtio, B4800);
break;
case 9600:
cfsetispeed(&newtio, B9600);
cfsetospeed(&newtio, B9600);
break;
case 115200:
cfsetispeed(&newtio, B115200);
cfsetospeed(&newtio, B115200);
break;
case 460800:
cfsetispeed(&newtio, B460800);
cfsetospeed(&newtio, B460800);
break;
default:
cfsetispeed(&newtio, B9600);
cfsetospeed(&newtio, B9600);
break;
}
if( nStop == 1 )
newtio.c_cflag &= ~CSTOPB;
else if ( nStop == 2 )
newtio.c_cflag |= CSTOPB;
newtio.c_cc[VTIME] = 0;
newtio.c_cc[VMIN] = 0;
tcflush(fd,TCIFLUSH);
if((tcsetattr(fd,TCSANOW,&newtio))!=0)
{
perror("com set error");
return -1;
}
// printf("set done!\n\r");
return 0;
}
int main(void)
{
int fd1;
char data[10] = "yikoupeng";
char buf[100]={0};
fd1 = open( "/dev/ttyS6", O_RDWR);
if (fd1 == -1)
exit(1);
nset = set_opt(fd1, 115200, 8, 'N', 1);
if (nset == -1)
{
exit(1);
}
printf("write start!\n");
write(fd1,data,strlen(data));
read(fd1,buf,sizeof(buf));
printf("rcv:%s\n",buf);
close(fd1);
return 0;
}
工具ts_uart.uart s获取
公众号后台回复:rxw
瑞芯微|rk3568 uart快速上手的更多相关文章
- 瑞芯微RK3399宣布系统开源,进入百余种行业市场!
集微网消息,2月24日瑞芯微官方突然宣布, Rockchip RK3399Linux系统开源!作为Rockchip旗舰级芯片,RK3399具有高性能.高扩展.全能型应用特性. 这一重磅消息立马刷爆朋友 ...
- Linux下更新瑞芯微固件
有这样的需求,是因为提供的BSP中是在windows下烧写的系统.我直接在linux下开发,每次编译后代码都要在windows下烧写,是一个很麻烦的事情.为了解决这个问题我尝试着用VirtualBox ...
- 9.7寸RK3188瑞芯微四核爱立顺M33平板电脑 - 深圳吉祥星晨科技有限公司 - 华强商情网
9.7寸RK3188瑞芯微四核爱立顺M33平板电脑 - 深圳吉祥星晨科技有限公司 - 华强商情网 欢迎加入 2000人超级QQ群,平板电脑行业交流群:221371451,平板电脑产品及报价群:5765 ...
- 瑞芯微发布最新旗舰应用处理器-RK3588
在瑞芯微电子第四届“开发者之春”大会上,瑞芯微推出了新一代8nm旗舰处理器-RK3588 这个芯片将采用8nm 制程工艺.基于A76+A55 内核组合,具备4K UI性能.8K VPU,拥有NPU2. ...
- 瑞芯微ROCK960 RK3399固件烧录总结
1 下载固件 进入瑞芯微ROCK960下载主页 https://www.96boards.org/documentation/consumer/rock/downloads/ 选择os固件, Debi ...
- 瑞芯微RK3399六核-迅为3399开发板介绍
迅为3399开发板基于瑞芯微的RK3399处理器设计,Rockchip RK3399是瑞芯微推出的一款低功耗.高性能的应用处理器芯片,该芯片基于Big.Little架构,即具有独立的NEON协同处理器 ...
- 瑞芯微RKnanC芯片处理器介绍
RKnanC是一种低成本.低功耗.高效率的数字多媒体芯片,它是基于ARM的低功耗处理器结构和硬件加速器.它是专为便携式音频产品应用,如MP3播放器等. RKnanC可以支持各种音频标准的解码,如MP3 ...
- 瑞芯微RK3188如何配置USB摄像头支持
- 瑞芯微RK3188摄像头相关参数的配置
- 瑞芯微ROCK960 RK3399烧录image后扩容rootfs
问题描述: RK3399开发板烧录官网提供的ubuntu镜像: Ubuntu 16.04 Server arm64(下载地址:https://www.96boards.org/documentatio ...
随机推荐
- python重拾第十三天-那就做个堡垒机吧
本节内容 项目实战:运维堡垒机开发 前景介绍 到目前为止,很多公司对堡垒机依然不太感冒,其实是没有充分认识到堡垒机在IT管理中的重要作用的,很多人觉得,堡垒机就是跳板机,其实这个认识是不全面的,跳板功 ...
- 【资料分享】RK3568开发板规格书(4x ARM Cortex-A55(64bit),主频1.8GHz)
1 开发板简介 创龙科技TL3568-EVM是一款基于瑞芯微RK3568J/RK3568B2处理器设计的四核ARM Cortex-A55国产工业评估板,每核主频高达1.8GHz/2.0GHz,由核心板 ...
- mermaid语法画图
mermaid 脚本语言 graph TB 从上到下 graph BT 从下到上 graph RL 从右到左 graph LR 从左到右 graph LR; A001-->B001; graph ...
- power bi创建切片器导航
现在很多报告使用的是按钮导航,今天分享另外一种方式:切片器导航. 第一步: 新建一个页面导航表,主页-输入数据-[填写列名,每页报表的表名] 如图: [页面导航表] 第二步: 添加一个切片器,将页面导 ...
- 机器学习策略篇:快速搭建你的第一个系统,并进行迭代(Build your first system quickly, then iterate)
快速搭建的第一个系统,并进行迭代 如果正在考虑建立一个新的语音识别系统,其实可以走很多方向,可以优先考虑很多事情. 比如,有一些特定的技术,可以让语音识别系统对嘈杂的背景更加健壮,嘈杂的背景可能是说咖 ...
- Java异步判断线程池所有任务是否执行完成的方法
1.使用ExecutorService和CountDownLatch的方法示例 在Java中,当我们使用线程池(如ExecutorService)来执行异步任务时,常常需要知道所有任务是否都已经完成. ...
- leetcode简单(设计):[225, 232, 303, 703, 705, 706, 933, 1603, 1656, 09, 30, 041, 03.06]
目录 225. 用队列实现栈(先入后出) 232. 用栈实现队列(先入先出) 303. 区域和检索 - 数组不可变 703. 数据流中的第 K 大元素 705. 设计哈希集合 706. 设计哈希映射 ...
- elementplus弹窗可拖拽draggable,点击空白处不消失close-on-click-modal,modal是否去掉遮罩层
<el-dialog :modal="false" v-model="dialogVisible" title="" width=&q ...
- sql server 编写函数,去除小数点后多余的0
sql server 编写函数,去除小数点后多余的0 要在 SQL Server 中编写一个函数来去除小数点后多余的零,你可以使用以下示例的方法: CREATE FUNCTION dbo.Remove ...
- Node.js 处理 File
Node.js 处理 File fs 模块 常规使用 运用递归遍历目录树 创建文件和目录 读写文件 path 模块 对于 file 的理解,此处 fs 模块 Node.js 提供了处理文件系统的内置模 ...