-
背景:你是否遇到过"树莓派的WiFi连不上网络,有线连接树莓派也不具备条件"的情况?这个时候,你想通过终端连接到树莓派上还剩下哪些选择?串口就是其中一个可行的办法。对大多数人来说,这种连接方法都算比较少见,但它确实是一个在网络断链时的好方法。 -
目标:让 macOS 通过 USB-TTL (CH340) 模块连接树莓派 GPIO 串口,获得一个完全不依赖网络的终端/登录通道(等同于 SSH 控制台,但走串口线)。 -
树莓派版本:3B Rev 1.2
1. 先认识 CH340 模块:它是什么,能帮我们做什么
1.1 CH340 是什么
CH340 是一颗国产的"USB 转串口"芯片(这类芯片也常被叫做 USB-UART 桥接芯片)。市面上卖的那种USB-TTL 小板,核心就是这颗芯片,板上通常还会引出一排针脚,标着 VCC / 5V / 3V3 / TXD / RXD / GND。
下面是我用AI绘制的CH340模块3D图:


它做的事情可以一句话讲清楚:把你的电脑 USB 口变成一个"串口"。电脑这边看到的是一个串口设备,另一端(比如树莓派、单片机)看到的是标准的串口信号,CH340 负责在两者之间翻译数据。这样电脑就能通过串口协议和另一台设备互相收发数据了。
关于驱动
三个主流系统(Windows / macOS / Linux)都有 CH340 的驱动,多数情况下插上就能用,不需要手动装。
macOS 这边,驱动生效的标志是:系统里出现一个叫 /dev/cu.usbserial-XXX 的设备文件。你可以把它理解成"串口的门牌号"——终端程序(比如我们后面要用的 screen)就是靠打开这个文件来跟串口通信的。名字里的 XXX 是一串数字,每次插拔可能不一样。所以你插上 CH340 后,先执行下面这条命令确认一下设备在不在:
- ounter(line
ls /dev/cu.usbserial*
能看到类似 /dev/cu.usbserial-110 的输出,就说明驱动没问题,可以继续往下走了。如果什么输出都没有,那多半是驱动没装好。
文章来源:https://www.codelast.com/
关于电平(电压标准)
串口信号的电平有两种常见标准:5V 和 3.3V。树莓派的 GPIO 是 3.3V 逻辑,所以接树莓派时要注意别让 5V 电平直接灌进 GPIO 引脚。CH340 小板一般 3.3V/5V 都兼容,本文的接法只用到 TXD、RXD、GND 三根线,不涉及供电脚,所以只要别把 5V 引脚接到树莓派上就行(后面 2 章会细说)。
1.2 用它连树莓派,具体能做什么
| 用途 | 说明 |
|---|---|
| 断网时的兜底登录 | 树莓派网络出问题(WiFi 连不上、网线也没条件)时,这是唯一还能进系统改配置、查日志的办法,也是本文的核心场景 |
| 看启动早期日志 | GPIO 串口在系统启动很早期就能输出文字,内核启动卡住时靠它看看到底死在哪一步 |
| 给单片机下载/调试程序 | Arduino、STM32、ESP32 这类板子常用串口烧录程序、打印调试信息 |
| 在没网络时传小文件 | 可以用 base64 之类的文本协议走串口慢慢传,9600 波特率下大约 0.8KB/s,只适合传很小的文件 |
| 接其他 TTL 串口外设 | GPS 模块、蓝牙模块、需要 AT 指令的模块等,很多都是串口接口,可以共用这套接线思路 |
| 学习串口原理 | 串口是最基础的通信接口,折腾一遍能搞明白 tty、波特率、流控这些概念 |
1.3 为什么把它定位成"备用通道",而不是日常主力
-
慢。9600 波特率换算下来每秒大约只有 0.8KB,敲命令、改配置够用,传文件会等到怀疑人生; -
电脑得用一根 USB 线物理连着树莓派附近,人不在旁边就用不了; -
日常调试当然还是 WiFi/网线 SSH 舒服,串口的意义在于:当网络这条路彻底断了,你还有一条路能进系统。
2. 硬件准备与接线
2.1 需要准备的东西
| 部件 | 说明 |
|---|---|
| CH340 USB-TTL 小板 | 网上很常见,板上一排针脚通常标着 5V、VCC、3V3、TXD、RXD、GND |
| 杜邦线 | 母对母,准备 3~4 根 |
| 一台电脑(本文以 macOS 为例) |
装好 CH340 驱动,插上后能看到/dev/cu.usbserial-XXX 设备 |
2.2 ⚠️ 接线规则:交叉 + 共地(最容易错的一步)
先解释一下串口的两根数据线:
-
TXD:发送(Transmit)——这根线负责"说"; -
RXD:接收(Receive)——这根线负责"听"。
通信要成立,必须一方的发送接到另一方的接收,也就是交叉接:
| CH340 小板 | 树莓派 40-pin 排针 |
|---|---|
| GND | Pin 6 / 9 / 14 / 20 / 25 / 30 / 34 / 39(这些全是 GND,任选一个) |
| TXD(发送) | Pin 10,也就是树莓派的 RXD / GPIO15 |
| RXD(接收) | Pin 8,也就是树莓派的 TXD / GPIO14 |
| VCC / 3V3 / 5V | 一律不接 |
三个容易踩的坑:
-
TXD 和 RXD 必须交叉,绝不能 TXD 对 TXD。 如果接成 TXD 对 TXD,两边都在"说"、没人"听",结果就是完全收不到任何数据。记住这个画面:两个人都只对着对方说话、却都把耳朵捂上,谁也听不见谁。 -
GND 必须共地。 意思是 CH340 的地线和树莓派的地线要连在一起,让两边有共同的电压参考点。如果不共地,表现是完全没有输出,或者收到一堆乱码(最常见的现象是收到 0 字节)。这一步看着不起眼,实际上一大半"没反应"的问题都出在它身上。 -
不要把 VCC / 3V3 / 5V 接到树莓派上。 树莓派自己有电源,CH340 小板靠 USB 口供电,两边电源脚对接会造成双电源冲突,严重时可能烧东西。
另外,杜邦线插拔多了容易接触不良。如果怀疑接触问题,换一根线、或者重新插紧往往就好了。
文章来源:https://www.codelast.com/
2.3 接线示意图
下面这张图把树莓派 40-pin 排针全部画出来了。排针是竖着排列的:左边一列是奇数号 1、3、5…,右边一列是偶数号 2、4、6…,从上往下递增。蓝色高亮的是我们真正用到的三个脚。

图中三个高亮触点分别是:
-
Pin 8:树莓派的 TXD(GPIO14)——接 CH340 的 RXD; -
Pin 10:树莓派的 RXD(GPIO15)——接 CH340 的 TXD; -
Pin 20:GND——图里选它只作示例,实际上树莓派上一堆 GND 脚(Pin 6/9/14/20/25/30/34/39)任选一个接都行。
再次强调:CH340 的 TXD 必须接树莓派的 RXD,CH340 的 RXD 必须接树莓派的 TXD,其他引脚一律不接。
3. 树莓派端要改的配置
要让树莓派通过 GPIO 串口提供登录服务,需要改三个系统文件。因为本文假设的场景是"树莓派已经没有任何网络连接",所以先讲怎么在没有网络的情况下修改这些文件,再逐个讲每个文件改什么。
文章来源:https://www.codelast.com/
3.1 没有网络时怎么改系统文件(拔卡方式)
先认识要改的三个文件:
| 文件 | 所在分区 | 作用 |
|---|---|---|
/boot/firmware/config.txt |
boot 分区(FAT32) | 启用 GPIO 串口、决定用哪个 UART(3.2 节) |
/boot/firmware/cmdline.txt |
boot 分区(FAT32) | 让内核把启动日志输出到串口,并定好波特率(3.3 节) |
/etc/systemd/system/serial-getty@*.service.d/override.conf |
系统分区(ext4) | 让系统在串口上启动登录程序(3.4 节) |
这里有个背景知识需要先说明:树莓派的 SD 卡(TF 卡)其实分成两个分区。一个是 boot 分区,格式是 FAT32,里面放的是开机要用的配置文件(config.txt、cmdline.txt 都在这里);另一个是 系统分区,格式是 ext4,装着整个操作系统。FAT32 分区在任何电脑上都能直接读写,而 ext4 分区普通电脑默认是看不到的。
拔卡修改的具体步骤:
-
关机断电:先在树莓派上正常关机,然后断开电源。切记不能带电拔卡,容易损坏文件系统; -
取出 TF 卡,用读卡器插到电脑上; -
改 boot 分区的文件:boot 分区是 FAT32,插上后电脑会直接识别。macOS 下它会自动挂载成一个盘,一般叫 /Volumes/bootfs,直接用文本编辑器打开里面的config.txt、cmdline.txt修改保存就行;Windows、Linux 同理,打开 TF 卡对应的盘符/挂载点就能看到这两个文件; -
系统分区里的文件:如果你需要改第三个文件( serial-getty的 override),它在 ext4 系统分区里,普通电脑默认看不到。macOS 要用debugfs之类的 ext4 工具(需要 root 权限),Windows 可以用 ext2fsd 之类的软件。如果觉得这一步麻烦,可以先跳过它——先只改 boot 分区里的两个文件,等接上串口发现确实登录不了,再回头处理 3.4 节的问题; -
安全弹出 TF 卡(macOS 里右键推出),插回树莓派,重新上电。
两个容易困惑的点,提前说明:
-
路径差异:新版 Raspberry Pi OS(Debian 12/13)里,boot 分区在系统内挂在 /boot/firmware/;老版本是挂在/boot/。但不管系统内路径怎么写,文件本身就在 boot 分区根目录里——你拔卡插电脑后,直接看盘符根目录下有没有config.txt就行,不用管/boot/firmware这种路径。 -
全新卡 vs 用过的卡:如果你是刚烧录好系统、还没第一次开机的卡,也可以插电脑直接改 boot 分区,效果和改 /boot/firmware/一样;如果是已经用过的卡,改之前一定要先正常关机再拔。
3.2 启用 GPIO 串口,并决定用哪个 UART
树莓派 GPIO 上引出的串口默认是关闭的,需要在 /boot/firmware/config.txt 里打开它。用文本编辑器打开这个文件,在文件末尾追加:
- ounter(line
enable_uart=1
光打开还不够,树莓派 3 上有个特殊情况需要决定:这颗芯片其实有两个串口硬件——一个叫 PL011(质量好、波特率准,但默认分配给蓝牙用),一个叫 mini-UART(功能弱一些、波特率会随 CPU 频率漂移)。GPIO 引出的串口到底用哪个,由要不要给蓝牙让路决定。有三个方案:
| 方案 | config.txt 里的写法 | 结果 |
|---|---|---|
| 1. 关闭蓝牙,串口用最好的 PL011 |
dtoverlay=disable-bt |
GPIO 串口是/dev/ttyAMA0(PL011,波特率最准),但蓝牙彻底没了 |
| 2. 串口用 PL011、蓝牙挤到 mini-UART |
dtoverlay=miniuart-bt |
理论可行,但在部分树莓派 3 上会导致蓝牙固件加载失败,不推荐 |
| 3. 什么都不加,维持默认 | (不加 dtoverlay) |
蓝牙正常用 PL011;GPIO 串口退而求其次用 mini-UART,即/dev/ttyS0 |
怎么选,取决于你要不要蓝牙:
-
还要用蓝牙:选方案 3。GPIO 串口会是 /dev/serial0 -> ttyS0(mini-UART)。因为 mini-UART 的波特率会随 CPU 频率漂移,建议把波特率定在 9600 这种低速档,或者去固定 CPU 频率,否则可能出现乱码; -
不需要蓝牙,只想要最稳定的串口:选方案 1。GPIO 串口是 /dev/serial0 -> ttyAMA0(PL011),波特率精确,省心。
后面各小节的命令都以 方案 3(设备名
ttyS0) 为例。如果你选了方案 1,把命令里出现的ttyS0全部换成ttyAMA0即可。
顺带一提:/dev/serial0 是一个软链接,它总是指向"当前 GPIO 串口实际对应的那个设备"(ttyS0 或 ttyAMA0),所以不确定时先执行 ls -l /dev/serial0 看一眼它指向谁,心里就有数了。
3.3 让内核把启动信息输出到串口(顺便定波特率)
Linux 内核启动时的日志默认是输出到屏幕的。我们希望它同时也输出到 GPIO 串口,这样就算树莓派没接屏幕,也能从串口看到启动过程。
这个行为由 /boot/firmware/cmdline.txt 控制。用文本编辑器打开它,确认里面有这样一段(注意是 serial0,不是别的):
- ounter(line
console=serial0,9600
serial0 就是 GPIO 串口的软链接名,9600 是波特率。如果文件里同时有 console=tty1 之类的(那是输出到本地屏幕的),不要删掉它们,只把 serial0 这一段波特率定为 9600 就好。
波特率这个东西,后面会反复强调:发送端和接收端必须用同一个波特率,否则收到的就是乱码。
3.4 让系统在串口上启动登录程序(serial-getty)
前面两步只是让内核往串口输出日志,但光有日志还不能登录。要登录,系统里得有一个程序在串口上等着,显示 login: 提示符、接受你输入用户名密码——这个程序叫 getty,对应的系统服务是 serial-getty@<串口设备>.service。
树莓派系统在检测到 GPIO 串口启用后,一般会自动启动对应的 serial-getty 服务。但有一个很常见的坑:getty 的波特率必须和内核 console 的波特率一致(都是 9600)。如果登录提示符不出现,多半就是 getty 没启动,或者波特率不对。
手动确认/修正的方法是给 getty 写一个配置文件,强制指定设备和波特率。在树莓派上创建 /etc/systemd/system/serial-getty@ttyS0.service.d/override.conf(目录可能要自己建):
- ounter(line
- ounter(line
- ounter(line
[Service]ExecStart=ExecStart=-/sbin/agetty --noclear --keep-baud ttyS0 9600 vt100
如果你的 GPIO 串口实际是
ttyAMA0(方案 1),就把上面两处ttyS0换成ttyAMA0,文件名也跟着改成serial-getty@ttyAMA0.service.d/override.conf。
然后重新加载 systemd 并启用服务:
- ounter(line
- ounter(line
sudo systemctl daemon-reloadsudo systemctl enable --now serial-getty@ttyS0.service
验证服务确实在跑:
- ounter(line
- ounter(line
systemctl is-active serial-getty@ttyS0 # 应该输出 activesystemctl list-units | grep ttyS0 # 能看到 serial-getty 在运行
到这里,树莓派端的配置就齐了:GPIO 串口已启用、内核往串口输出日志、getty 在串口上等你登录。
4. macOS 这一端怎么连
4.1 先确认设备名
CH340 插上后 macOS 会自动给它分配一个设备文件,名字是 /dev/cu.usbserial-XXXX(也可能是 /dev/tty.usbserial-XXXX)。注意末尾那串数字每次重新插拔都可能变(比如这次是 11310,下次变成 11320,再下次是 110),所以别死记一个名字,每次用之前先查一下:
- ounter(line
ls /dev/cu.usbserial*
如果这条命令什么都查不到,说明驱动没装好,去 WCH 官网装 macOS 驱动。
4.2 用 screen 连上去
macOS 自带的 screen 命令就能当串口终端用:
- ounter(line
screen /dev/cu.usbserial-110 9600
格式是 screen 设备文件 波特率,把设备名换成你上一步查到的实际名字。连接成功后,按一下回车,应该能看到:
- ounter(line
rpi login:
输入树莓派的用户名和密码,就进入 shell 了,用法和 SSH 完全一样。
退出 screen 的方法:先按 Ctrl+A,松开后再按 K,最后按 y 确认退出。
4.3 不想开终端?也可以用命令直接收发
如果你是脚本/程序要自动化测试串口,不需要交互式终端,可以用下面的方式非交互地验证:
- ounter(line
- ounter(line
- ounter(line
- ounter(line
- ounter(line
DEV=/dev/cu.usbserial-110 # 换成你实际的设备名stty -f "$DEV" 9600 raw -echo # 设置波特率 9600,关闭回显(timeout 4 cat "$DEV" > /tmp/rx.txt &) # 后台启动一个读取,读 4 秒printf '\r' > "$DEV" # 往串口写一个回车,触发登录提示cat /tmp/rx.txt # 查看收到的内容,应该能看到 "rpi login:"
stty 负责配置串口参数,cat 负责读,printf 负责写——把串口当成一个文件来读写就行。
5. 调试记录:踩过的坑
下面这些是实际接线、调通过程中遇到的问题。如果你一次就成功了,可以跳过本章;如果哪里不对,按顺序排查通常能解决。
文章来源:https://www.codelast.com/
5.1 第一次接上:完全没有输出,或者全是乱码
刚接上时最常见的两个现象:读串口读到 0 字节(什么都没有),或者读到 40~70 字节的乱码。
按下面的顺序排查:
第 1 步:先确认 CH340 小板本身是好的(环回测试)
把 CH340 和树莓派的接线全部断开,然后用一根杜邦线把 CH340 板上的 TXD 和 RXD 短接(直接连在一起)。这样一来,CH340 自己发出去的数据会原路回到自己。然后用 screen 连上串口随便敲几个字:如果敲什么回显什么,说明 CH340 小板、USB 线、驱动这一整条链路都是好的,问题出在树莓派那一侧。
不想开终端的话,也可以用命令自动验证:
- ounter(line
- ounter(line
- ounter(line
- ounter(line
stty -f $DEV 115200 raw -echo(timeout 8 cat $DEV > /tmp/loop.txt &) # 后台读printf 'HELLO_LOOP' > $DEV # 写入一串测试文字grep HELLO_LOOP /tmp/loop.txt && echo OK # 能在读到的内容里找到它 => 模块正常
如果这步通过,说明小板没问题,继续看第 2 步。
第 2 步:检查 GND 是否共地、TXD/RXD 是否交叉
读到的字节数是 0 时,优先怀疑两件事:GND 没接(换一个 GND 引脚试试),或者 TXD/RXD 没交叉。我实际遇到过:把 GND 从 Pin 30 换到 Pin 20 之后,读到的数据从 0 字节一下子变成 182 字节——共地的影响就是这么明显。
第 3 步:把 TXD 和 RXD 两根线对调
如果前面都查过还是没数据,把 TXD、RXD 两根线互换位置再试。很多时候数据从无到有,就差这一下。
5.2 有数据了,但是全是乱码 → 波特率不对
现象:能收到数据了,但内容完全没法看,全是乱码;而且换了好几档波特率读出来的都是"长度差不多的乱码"。
这是因为两边的波特率不一致。串口通信里,发送方和接收方必须用同样的波特率(相当于约定同样的说话语速),否则对方听到的就是无意义的声音。
推荐用"矩阵测试"来找到正确的波特率:树莓派和 macOS 两边同步切到同一个波特率,树莓派持续发一段特征文字,macOS 在另一边读,看哪一档能读出可读的文本。
树莓派侧(示例用 9600):
- ounter(line
- ounter(line
sudo stty -F /dev/ttyS0 9600 raw -echo # ttyS0 或 ttyAMA0,按你实际设备名for i in 1 2 3 4; do echo -n "MATRIX_BAUD_9600_$i" > /dev/ttyS0; sleep 0.2; done
macOS 侧:
- ounter(line
- ounter(line
- ounter(line
stty -f $DEV 9600 raw -echo(timeout 4 cat $DEV > /tmp/mx.txt &)grep MATRIX_BAUD /tmp/mx.txt && echo 通过
我实际测试的结果是:9600 波特率下两边完全互通,反而 115200 读出来是乱的——这块 CH340 小板在 115200 这个高速档上精度不稳。所以最后统一把波特率定在 9600(8 数据位、无校验、1 停止位,也就是常说的 8N1),内核 console、getty、macOS 端全部用 9600。
5.3 能看到内核日志,但没有 login 提示 → getty 没起来
现象:串口上能看到内核启动的日志,但日志播完就没了,一直没有 login: 提示符。
这说明问题不在硬件,而在系统这边——没有程序在串口上等你登录,也就是 3.4 节说的 getty 没有正确启动,或者它的波特率和 console 不一致。解决办法就是按 3.4 节写好 override 文件、启用对应的 serial-getty@<设备>.service。
5.4 换了个 USB 口,就连不上了 → 设备名变了
现象:之前明明连得好好的,换了个 USB 口再插,screen 报错 [screen is terminating]。
原因在 4.1 节说过:设备名末尾的数字每次插拔都可能变。换了 USB 口,旧名字就失效了。解决办法很简单:重新执行 ls /dev/cu.usbserial* 查出新的设备名,用新名字重新连接。
6. 最终验证(确认可用)
配置全部完成后,用下面两条验证整个链路是通的。
文章来源:https://www.codelast.com/
交互式验证(macOS 终端里):
- ounter(line
- ounter(line
screen /dev/cu.usbserial-110 9600# 应该看到 rpi login:,输入用户名密码进入 shell
非交互式验证(脚本里用):
- ounter(line
- ounter(line
printf '\r' > $DEVtimeout 5 cat $DEV # 应该能看到 "rpi login:"
文章来源:https://www.codelast.com/
➤➤ 版权声明 ➤➤
转载需注明出处:codelast.com
感谢关注我的微信公众号(微信扫一扫):

以及我的微信视频号:

