1. 基本的串口通信程序。先读取内容,再将内容写回串口。
- #include <stdio.h>
- #include <stdlib.h>
- #include <unistd.h>
- #include <sys/types.h>
- #include <sys/stat.h>
- #include <fcntl.h>
- #include <termios.h>
- #include <errno.h>
- main()
- {
- int fd;
- int i;
- int len;
- int n = 0;
- char read_buf[256];
- char write_buf[256];
- struct termios opt;
- fd = open("/dev/ttyATH0", O_RDWR|O_NOCTTY|O_NDELAY);
- if(fd == -1)
- {
- perror("open serial 0\n");
- exit(0);
- }
- tcgetattr(fd, &opt);
- bzero(&opt, sizeof(opt));
- tcflush(fd, TCIOFLUSH);
- cfsetispeed(&opt, B115200);
- cfsetospeed(&opt, B115200);
- opt.c_cflag &= ~CSIZE;
- opt.c_cflag |= CS8;
- opt.c_cflag &= ~CSTOPB;
- opt.c_cflag &= ~PARENB;
- opt.c_cflag &= ~CRTSCTS;
- opt.c_cflag |= (CLOCAL | CREAD);
- opt.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);
- opt.c_oflag &= ~OPOST;
- opt.c_cc[VTIME] = 0;
- opt.c_cc[VMIN] = 0;
- tcflush(fd, TCIOFLUSH);
- printf("configure complete\n");
- if(tcsetattr(fd, TCSANOW, &opt) != 0)
- {
- perror("serial error");
- return -1;
- }
- printf("start send and receive data\n");
- while(1)
- {
- n = 0;
- len = 0;
- bzero(read_buf, sizeof(read_buf));
- bzero(write_buf, sizeof(write_buf));
- while( (n = read(fd, read_buf, sizeof(read_buf))) > 0 )
- {
- for(i = len; i < (len + n); i++)
- {
- write_buf[i] = read_buf[i - len];
- }
- len += n;
- }
- write_buf[len] = '\0';
- printf("Len %d \n", len);
- printf("%s \n", write_buf);
- n = write(fd, write_buf, len);
- printf("write %d chars\n",n);
- sleep(2);
- }
- }
2. 注意
- opt.c_cc[VTIME] = 0;
- opt.c_cc[VMIN] = 0;
在这两个值均为0 的情况下,read不管有没有数据都会立即返回。详细情况在linux下man tcsetattr.
如果不设定这两个值,那么read只有收到回车后才会读取缓存中的数据。
异常处理:
如果串口被系统占用,只能SSH,必须如下操作
一、修改 /etc/inittab
####ttyS0::askfirst:/bin/ash --login
####ttyS1::askfirst:/bin/ash --login
把最下面的两行注释掉即可
二、
释放ttyS0作为通信串口
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <termios.h>
#include <errno.h>
void CloseConsole(void) {
int fp;
struct termios options;
printf("change1\n");
fp = open("/dev/tty1",O_RDONLY); // 改变console
ioctl(fp,TIOCCONS);
close(fp);
fp = open("/dev/tts/0",O_RDWR|O_NOCTTY|O_NDELAY); //打开串口0读写
if(fp == -1) exit(0);
tcgetattr(fp,&options);
cfsetispeed(&options,B115200);
cfsetospeed(&options,B115200);
options.c_cflag |= (CLOCAL|CREAD);
tcsetattr(fp,TCSANOW,&options);
write(fp,"hello world!\n123",15);
close(fp); //关闭串口0
fp = open("/dev/tty0",O_RDONLY); //恢复console 到串口0
ioctl(fp,TIOCCONS);
close(fp);
printf("change2\n");
}
关于关闭SHELL对串口的占用,使之能做普通的串口通信和拨号
1、步骤:
在内核编译过程中执行make menuconfig
Character devices --->
Serial drivers --->
S3C2410 serial port support
[ ] Console on S3C2410 serial port 【注】去掉这项即可,不必修改busybox/init.c了
< > 8250/16550 and compatible serial support (EXPERIMENTAL)
2、备注:
这样就不能用ttyS0口来登录ARM开发板了,你可以选择用TELNET的方式来登录。
做法:telnet 192.168.0.12(你的开发板的IP地址)
输入:“root”用户名就可以进入你的开发板了
3、OK..
http://blog.csdn.net/neiloid/article/details/7585876