在.NET环境下实现树莓派的GPIO与UART控制
树莓派串口介绍操作
- 串口介绍
关于树莓派的串口可以先参考两个地方
- 树莓派的官方介绍,地址:https://www.raspberrypi.com/documentation/computers/configuration.html#configuring-uarts.
- 树莓派实验室的文章,地址:
https://shumeipai.nxez.com/2021/08/09/raspberry-pi-4-activating-additional-uart-ports.html.
根据上面的内容我们知道树莓派4的串口有六组
根据上面的介绍,基本清楚,6组串口uart0 作为蓝牙的,uart1 miniUART可以作为串口控制台输出
uart2~uart5可作为正常串口使用
- uart0,可以不用管,作为蓝牙,当然禁用蓝牙可以多一个串口,也可以和uart1调换映射。方式可参考其他:https://zhuanlan.zhihu.com/p/106904186.
- uart1 miniUART,就是波特率根据CPU主频来的,有点不稳定的因素。可作为串口控制台输出使用
配置如下
sudo raspi-config
回车进入下一步
yes就是启用控制台输出,然后OK回车,回到页面,选中Finish回车完成配置,此时可将USB转TTL模块接入GPIO14、15(BCM编码)
sudo reboot
重启可以在串口控制台看到树莓派的启动打印信息,可登录。
- uart2~uart5,这四组串口是可以随意使用的,默认是不打开的
#查看所有串口
dtoverlay -a | grep uart
- 开启uart2-uart5
// 编辑配置文件
sudo nano /boot/config.txt
在文件结尾添加如下:
dtoverlay=uart2
dtoverlay=uart3
dtoverlay=uart4
dtoverlay=uart5
添加完重启设备生效。
- 重启后查看是否生效
// 查看串口
ls /dev/ttyAMA*
可以看见开启的四路已经生效,现在有五组串口,还有一组用作串口控制台登录所以没有显示。
- 串口号与IO口编号对应关系
//BCM编码
GPIO14 = TXD0 -> ttyAMA0
GPIO15 = RXD0 -> ttyAMA0
GPIO0 = TXD2 -> ttyAMA1
GPIO1 = RXD2 -> ttyAMA1
GPIO4 = TXD3 -> ttyAMA2
GPIO5 = RXD3 -> ttyAMA2
GPIO8 = TXD4 -> ttyAMA3
GPIO9 = RXD4 -> ttyAMA3
GPIO12 = TXD5 -> ttyAMA4
GPIO13 = RXD5 -> ttyAMA4
代码编写移植
我们接着在上一节的工程下进行
我们先添加串口控制的依赖包 System.IO.Ports,和上一节的操作方式一样。
代码如下,注意using引用
using System;
using System.Device.Gpio;
using System.IO.Ports;
using System.Threading;
namespace RaspberryTest
{
class Program
{
public static SerialPort serialPort1 = new();//注册串口
static void Main(string[] args)
{
Console.WriteLine("Hello World!");
//GPIO设置
Console.WriteLine("Blinking LED. Press Ctrl+C to end.");
int pin = 27;
using var controller = new GpioController();
controller.OpenPin(pin, PinMode.Output); //输出模式
//controller.OpenPin(pin, PinMode.Input); //输入模式
bool ledOn = true;
//串口设置
serialPort1.DataReceived += new SerialDataReceivedEventHandler(serialPort1_DataReceived); //串口接受注册
string[] coms = SerialPort.GetPortNames();//获取串口号
for (int i = 0; i < coms.Length; i++)
{
Console.WriteLine(coms[i]);//打印出口号
}
serialPort1.PortName = "/dev/ttyAMA2"; //串口号,相当于Windows下的COM口
serialPort1.BaudRate = 115200; //波特率
serialPort1.Open(); //打开串口
while (true)
{
controller.Write(pin, ((ledOn) ? PinValue.High : PinValue.Low)); //控制输出电平
//controller.Read(pin); //读取输入电平
ledOn = !ledOn;
Thread.Sleep(1000);
serialPort1.Write("I'm OK!");
}
}
//串口收到数据会自动进入这个函数
private static void serialPort1_DataReceived(object sender, SerialDataReceivedEventArgs e)//串口数据接受
{
Console.WriteLine(serialPort1.ReadExisting());//打印串口接收
}
}
}
这里我们打开的是ttyAMA2,也就是uart3,对应引脚如下
为了方便测试我没有接usb->ttl串口模块,我是直接将这两个脚用杜邦线短接起来,那么我发什么就会收到什么。
生成代码
将工程目录下的文件传输到树莓派上。在树莓派上,到相应的文件夹下运行
dotnet RaspberryTest.dll
实验效果
开始打印了串口号,我这里多出了4个ttyUSB的串口,因为的树莓派上接了EC20模块,是模块虚拟出来的4个串口,都识别出来了,我发送出去的I’m OK!也返回回来了。
ctrl+c //结束运行
到此树莓派上的C#串口控制实现完成。