第一章 串口通信基础
本章简单介绍串口通信,RS-232及其它在计算机上使用的标准。并介绍如何用C程序来访问串口。
什么叫串行通信?
计算机在传输数据的过程中,一次传输一个bit或者多个bits。串行便是指一次传输一个bit。串行通信设备很多:大多数网络设备,键盘,鼠标,调制解调器及终端等。在传输过程中,每一个bit要么是1(on)要么是0(off),也可以标记为space和mark状态。串行数据的速度用bps或波特率burd来衡量。串行设备和终端也可以叫为数据通信设备(DCE Data Communication Equipment),或数据中断设备(DTE Data Terminal Equipment)。
什么是RS-232?
常说的RS-232是EIA(Electronic Industries Association)定义的串行通信电气标准。RS-232分为A,B,C三类。最常用的是RS-232C,用-3V--12V表示mark(on),用+3V-+12V表示space(off)。RS-232C定义传输路径为8m。
Table 1为RS-232的pin定义,其他标准还有RS-422和RS-574。RS-422采用差分信号,RS-574则是9-pin的标准。
Table 1 - RS-232 Pin Assignments | |||||||||
Pin | Description | Pin | Description | Pin | Description | Pin | Description | Pin | Description |
1 | Earth Ground | 6 | DSR - Data Set Ready | 11 | Unassigned | 16 | Secondary RXD | 21 | Signal Quality Detect |
2 | TXD - Transmitted Data | 7 | GND - Logic Ground | 12 | Secondary DCD | 17 | Receiver Clock | 22 | Ring Detect |
3 | RXD - Received Data | 8 | DCD - Data Carrier Detect | 13 | Secondary CTS | 18 | Unassigned | 23 | Data Rate Select |
4 | RTS - Request To Send | 9 | Reserved | 14 | Secondary TXD | 19 | Secondary RTS | 24 | Transmit Clock |
5 | CTS - Clear To Send | 10 | Reserved | 15 | Transmit Clock | 20 | DTR - Data Terminal Ready | 25 | Unassigned |
RS-232为串行通信定义了18中不同的信号线。UNIX环境中只使用其中6中信号。
GND-Logic Ground
逻辑地logic groud不是信号,但是其它信号用其作为参考电平(reference voltage)。
TXD-Transmitted Data
TxD发送信号,mark(on)表示1,space(off)表示0。
RXD-Received Data
RXD接收信号,mark(on)表示1,space(off)表示0。
DCD-Data Carrier Detect
DCD数据载波检测,space voltage表示设备是连上的。
DTR-Data Terminal Ready
DTR数据终端就绪,space voltage表示就绪。当打开一个串口时,DTR自动就绪。
CTS-Clear To Send
CTS清除发送,space voltage表示已经发送了数据。
RTS-Requeset To Send
RTS请求发送,space voltage表示有数据准备传输。
异步通信
串行通信需要识别传输数据的结束和开始。这就需要启动位start bit和停止位stop bit。低位先传输。
奇偶校验有偶校验even parity和奇校验odd parity。此外还有space parity,mark parity和no parity。Space parity表示校验位始终为0,mark parity表示校验位始终为1,no parity这表示没有parity位。停止位可为1,1.5或者2位。异步数据格式可以标识为“8N1”,“7E1”等, 分别表示为8 data bits, no parity, 1 stop bit和7 data bits, even parity, 1 stop bit。
流控制
流控制可以分为软件流控制和硬件流控制。软件流控制使用特殊的字符作为启动(XON or DC1, 021 octal)和停止(XOFF or DC3, 023 octal)。硬件流控制则使用CTR/RTS信号。当接收端准备好接收数据时,设定CTS为space voltage,当没有准备好时,设定为makr voltage。同理,发送端准备发送数据时,设定RTS为space voltage。但是要注意,并不是所有的硬件和操作系统都支持CTS/RTS。
Break是指什么?
通常情况下,发送和接收信号线处于mark voltage状态。当信号在很长一段时间,如1/4到1/2 second都保持在space voltage,就说break condition发生了。Break condition可用来复位communication line或者切换硬体(如MODEM)的工作模式。
同步通信
同步通信中,发送端和接收端都必须保持相同的数据率。即使是同步通信,也必须标识数据的开始。常使用的方法是用数据包协议如Serial Data Link Control(“SDLC”)和High-Speed Data Link Control(“HDLC”)。
访问串口
UNIX对串口的访问是通过device file来完成的。下表列出了不同的系统中表示串口的文件。
Table 2 - Serial Port Device Files | ||
System | Port 1 | Port 2 |
IRIX® | /dev/ttyf1 | /dev/ttyf2 |
CYGWIN | /dev/com1 | /dev/com2 |
Solaris®/SunOS® | /dev/ttya | /dev/ttyb |
Linux® | /dev/ttyS0 | /dev/ttyS1 |
Digital UNIX® | /dev/tty01 | /dev/tty02 |
打开串口
Opening a serial port
#include <stdio.h> /* Starndard input/output definitions */
#include <string.h> /* String function definitions */
#include <unistd.h> /* UNIX stardard function definitions */
#include <fcntl.h> /* File control definitions */
#include <errno.h> /*Error number definitions */
#include <termios.h> /*POSIX terminal control definitions */
int
open_port(void)
{
int fd;
fd = open(“/dev/ttys0”, O_RDWR | O_NOCTTY | O_NDELAY);
if (fd == -1)
{
perror(“open_port: Unable to open /dev/ttys0 –“);
}
else
fcntl(fd, F_SETFL, 0);
return (fd);
}
其中O_NOCTTY表示没有”controlling terminal”,如果不这样指定,那么其他输入如键盘信号等都会影响到该进程。
给串口写入数据
n = write(fd, “ATZ/r”, 4);
if (n < 0)
fputs(“write() of 4 bytes failed!/n”, stderr);
从端口读数据
当用read函数从端口读数据时,要注意到默认情况是如果串口输入缓冲有数据,则返回这些数据,如果没有,则阻塞发生,直到有数据进入缓冲区或者定时器满为止。可以通过
fcntl(fd, F_SETFL, FNDELAY)
以使read函数,在没有数据时,直接返回0。使用
fcntl(fd, F_SETFL, 0)
恢复到默认模式。
关闭串口
fclose(fd);