串口调试小节之三 Linux串口应用层编程注意

来源:互联网 发布:淘宝不要搜血滴子 编辑:程序博客网 时间:2024/06/06 13:07

转载地址:http://blog.csdn.net/sun2003shy/article/details/46409565

这里不打算很详细的介绍该如何编写Linux代码,这种代码在百度或者开源项目一找一大堆,这里只对常用会出错的地方做一些介绍,防止掉入这些陷阱。

1、  关于波特率设置:

关于波特率设置的部分看起来简单但是还需要注意一些内容:

A、设置方法,首先需要使用tcgetattr(fd, &options);进行获取,其中optionsstruct termios类型,等到将各个参数设置在options后再调用tcsetattr(fd, TCSANOW, &Opt)函数进行设置。

B、波特率设置:这里有两种方法,两者任选一种,

一种是直接调用Linux的系统函数,使用

cfsetispeed(&options, B19200);

cfsetospeed(&options, B19200);进行设置

一种是直接操作termios的成员变量,使用options.c_cflag |= B19200进行设置,这里强烈不推荐这种方式,因为常会有人忘记这句话options.c_cflag &= ~CSIZE这句话导致波特率没有设置正确造成串口通讯失败。

2、 关于其他控制字,下面会挑一些主要的进行说明,也就是经常出错的一些。

A、打开串口的open函数,除了使用O_RDWR标志之外,通常还会使用O_NOCTTYO_NDELAY这两个标志。
O_NOCTTY:告诉Unix这个程序不想成为“控制终端”控制的程序,不说明这个标志的话,任何输入都会影响你的程序。
O_NDELAY:告诉Unix这个程序不关心DCD信号线状态,即其他端口是否运行,不说明这个标志的话,该程序就会在DCD信号线为低电平时停止。。

B、关于回车部分的设置:

在用write发送数据时没有键入回车,信息就发送不出去,这主要是因为我们在输入输出时是按照规范模式接收到回车或换行才发送,而更多情况下我们是不必键入回车或换行的。此时应转换到行方式输入,不经处理直接发送,设置如下:
Opt.c_lflag &= ~ (ICANON | ECHO | ECHOE | ISIG);
还存在这样的情况:发送字符0X0d的时候,往往接收端得到的字符是0X0a,原因是因为在串口设置中c_iflagc_oflag中存在从NL-CRCR-NL的映射,即串口能把回车和换行当成同一个字符,可以进行如下设置屏蔽之:
Opt.c_iflag &= ~ (INLCR | ICRNL | IGNCR);
Opt.c_oflag &= ~(ONLCR | OCRNL);

还有CREADCLOCAL一般也是必须设置的。

3、 关于串口程序的结构设计:

这一块需要注意的是在linux下你使用的串口是阻塞式读取还是非阻塞式读取,阻塞式读取可以依赖于系统,相对编程比较简单,而非阻塞式则在读取的过程中一定要读取了足够的数据再进行判断,在调试过程中就发现,比如接收3个数据,65 03 06

       出现只接收了65 03 这两个数据就能开始使用一个unsigned short型指针指向03数据所在的地址,经常造成通讯不畅的问题。

关于应用层的其他设置,可参考下文中的各个标志设置。