termios结构体
### Termios结构体详解 #### 一、概述 在探讨`termios`结构体之前,我们首先了解一下这个结构体的基本用途。`termios`结构体主要用于控制终端输入输出的属性,尤其是在Linux系统中,它是配置串口的重要工具之一。通过`termios`结构体,可以对串口进行各种配置,比如波特率、数据位、停止位等。 #### 二、结构体定义 `termios`结构体在头文件`<termios.h>`中定义,它包含以下几个主要成员: - `tcflag_t c_iflag;`:输入模式标志。 - `tcflag_t c_oflag;`:输出模式标志。 - `tcflag_t c_cflag;`:控制模式标志。 - `tcflag_t c_lflag;`:本地模式标志。 - `cc_t c_cc[NCCS];`:特殊字符数组。 其中,`tcflag_t`是一个无符号整型类型,用于存储标志位;`cc_t`也是一个无符号整型类型,用于存储特殊字符。 #### 三、成员变量详解 ##### 1. 输入模式标志 (c_iflag) 输入模式标志用于指定输入处理的方式。这些标志包括但不限于: - `IGNBRK`:忽略中断信号(BREAK)。 - `BRKINT`:发送SIGINT信号来响应中断信号。 - `IGNPAR`:忽略奇偶校验错误。 - `PARMRK`:将奇偶校验错误标记为特殊字符。 - `INPCK`:启用奇偶校验。 - `ISTRIP`:删除第8位。 - `INLCR`:将输入的LF转换为CR。 - `IGNCR`:忽略输入的CR。 - `ICRNL`:将输入的CR转换为LF。 - `IUCLC`:转换大写到小写。 - `IXON`:启用软件流控制(XON/XOFF)。 - `IXANY`:任何字符都能启动传输。 - `IXOFF`:启用软件流控制(XON/XOFF)。 ##### 2. 输出模式标志 (c_oflag) 输出模式标志用于指定输出处理的方式。包括但不限于: - `OPOST`:执行后处理。 - `OLCUC`:转换小写到大写。 - `ONLCR`:将输出的NL转换为CR。 - `OCRNL`:将输出的CR转换为NL。 - `ONOCR`:输出CR后再输出NL。 - `ONLRET`:输出NL后再输出CR。 - `OFILL`:填充字符。 - `OFDEL`:设置删除字符。 此外还包括延迟处理相关的标志如`NLDLY`、`CRDLY`、`TABDLY`、`BSDLY`、`VTDLY`、`FFDLY`等。 ##### 3. 控制模式标志 (c_cflag) 控制模式标志用于指定硬件控制方式,包括但不限于: - `CBAUD`:设置波特率。 - `CBAUDEX`:波特率扩展。 - `CSIZE`:设置数据位大小(5、6、7或8位)。 - `CSTOPB`:设置两个停止位。 - `CREAD`:使能接收。 - `PARENB`:使能奇偶校验。 - `PARODD`:设置奇偶校验为奇校验。 - `HUPCL`:挂起时关闭线路。 - `CLOCAL`:不使能远程控制。 - `CRTSCTS`:使能硬件流控制(RTS/CTS)。 ##### 4. 本地模式标志 (c_lflag) 本地模式标志用于指定本地模式的行为。包括但不限于: - `ISIG`:使能信号生成。 - `ICANON`:使能标准输入。 - `XCASE`:转换大写到小写。 - `ECHO`:使能回显。 - `ECHOE`:使能擦除回显。 - `ECHOK`:使能删除行。 - `ECHONL`:使能换行回显。 - `ECHOPRT`:使能擦除回显。 - `TOSTOP`:使能后台信号。 #### 四、函数应用 针对`termios`结构体,有几个常用的函数来读取、设置和控制串口设备: - **tcgetattr(fd, &termios_p);**:获取指定文件描述符`fd`的当前`termios`配置,并将其存储在`termios_p`结构体中。 - **tcsetattr(fd, actions, &termios_p);**:根据`actions`参数的不同值来设置指定文件描述符`fd`的`termios`配置。 - `TCSANOW`:立即应用设置。 - `TCSADRAIN`:等待所有输出完成后应用设置。 - `TCSAFLUSH`:丢弃所有未处理的数据后应用设置。 - **tcsendbreak(fd, duration);**:向串口设备发送一个断开信号。`duration`参数指定了断开信号的持续时间,默认值为0.25秒。 - **tcdrain(fd);**:等待所有输出完成后返回。 - **tcflush(fd, queue_selector);**:清空指定队列中的数据。 - `TCIFLUSH`:清空输入队列。 - `TCOFLUSH`:清空输出队列。 - `TCIOFLUSH`:同时清空输入和输出队列。 - **tcflow(fd, action);**:控制串口设备的流控制状态。 - `TCOOFF`:禁用输出。 - `TCOON`:启用输出。 - `TCIOFF`:禁用输入和输出。 - `TCION`:启用输入和输出。 #### 五、示例代码 下面是一个简单的示例,展示了如何使用`termios`结构体来配置串口: ```c #include <unistd.h> #include <fcntl.h> #include <termios.h> int main() { int fd = open("/dev/ttyUSB0", O_RDWR | O_NOCTTY | O_NDELAY); if (fd == -1) { perror("open"); return -1; } struct termios tty; tcgetattr(fd, &tty); // 设置波特率为9600 cfsetispeed(&tty, B9600); cfsetospeed(&tty, B9600); // 设置数据位为8位 tty.c_cflag &= ~CSIZE; tty.c_cflag |= CS8; // 设置停止位为1位 tty.c_cflag &= ~CSTOPB; // 关闭奇偶校验 tty.c_cflag &= ~PARENB; tty.c_cflag &= ~PARODD; // 设置输入模式 tty.c_iflag &= ~(IGNBRK | BRKINT | PARMRK | ISTRIP | INLCR | IGNCR | ICRNL | IXON); // 设置输出模式 tty.c_oflag &= ~OPOST; // 设置本地模式 tty.c_lflag &= ~(ECHO | ECHONL | ICANON | ISIG | IEXTEN); // 应用设置 tcsetattr(fd, TCSANOW, &tty); close(fd); return 0; } ``` 这段代码首先打开了串口设备`/dev/ttyUSB0`,然后获取了当前的`termios`配置,并对其进行了修改,设置了波特率为9600,数据位为8位,停止位为1位,关闭了奇偶校验,并设置了输入输出模式。将新的配置应用到了串口设备上。 通过以上内容,我们可以看出`termios`结构体是控制串口设备的关键工具,掌握其使用方法对于开发涉及串口通信的应用程序至关重要。