我用的usb-serial接口线是pl2303, 所以linux kernel加入pl2303支持后(或者以模块方式加载),插入usb-serial,系统自动在增加了/dev/ttyUSB0这个设备
接下来就是程序验证一下串口功能,在网上找了一个发送和接收程序,写的相当罗嗦,但是能工作
1. receive.c程序清单:
#include <stdio.h>
#include <string.h>
#include <malloc.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <termios.h>
#include "math.h"
#define max_buffer_size 100 /*定义缓冲区最大宽度*/
/*********************************************************/
int fd,s;
int open_serial(int k)
{
if(k==0) /*串口选择*/
{
fd = open("/dev/ttyS0",O_RDWR|O_NOCTTY); /*读写方式打开串口*/
perror("open /dev/ttyS0");
}
else
{
fd = open("/dev/ttyS1",O_RDWR|O_NOCTTY);
perror("open /dev/ttyS1");
}
if(fd == -1) /*打开失败*/
return -1;
else
return 0;
}
/********************************************************************/
int main()
{
char hd[max_buffer_size],*rbuf; /*定义接收缓冲区*/
int flag_close, retv,i,ncount="0";
struct termios opt;
int realdata="0";
/*******************************************************************/
open_serial(0); /*打开串口1*/
/*******************************************************************/
tcgetattr(fd,&opt);
cfmakeraw(&opt);
/*****************************************************************/
cfsetispeed(&opt,B9600); /*波特率设置为9600bps*/
cfsetospeed(&opt,B9600);
/*******************************************************************/
tcsetattr(fd,TCSANOW,&opt);
rbuf="hd"; /*数据保存*/
printf("ready for receiving data.../n");
retv="read"(fd,rbuf,1); /*接收数据*/
if(retv==-1)
{
perror("read"); /*读状态标志判断*/
}
/*************************开始接收数据******************************/
while(*rbuf!='/n') /*判断数据是否接收完毕*/
{
ncount+=1;
rbuf++;
retv="read"(fd,rbuf,1);
if(retv==-1)
{
perror("read");
}
}
/*******************************************************************/
printf("The data received is:/n"); /*输出接收到的数据*/
for(i="0";i<ncount;i++)
{
printf("%c",hd[i]);
}
printf("/n");
flag_close =close(fd);
if(flag_close ==-1) /*判断是否成功关闭文件*/
printf(“Close the Device failur!/n”);
return 0;
}
/****************************结束***********************************/
2.send.c程序清单
/*******************************************************
* File Name: send.c
* Description: send data to serial_Port
* Date:
*******************************************************/
/******************头文件定义******************/
#include <stdio.h>
#include <string.h>
#include <malloc.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <termios.h>
#define max_buffer_size 100 /*定义缓冲区最大宽度*/
/*******************************************/
int fd; /*定义设备文件描述符*/
int flag_close;
int open_serial(int k)
{
if(k==0) /*串口选择*/
{
fd = open("/dev/ttyS0",O_RDWR|O_NOCTTY); /*读写方式打开串口*/
perror("open /dev/ttyS0");
}
else
{
fd = open("/dev/ttyS1",O_RDWR|O_NOCTTY);
perror("open /dev/ttyS1");
}
if(fd == -1) /*打开失败*/
return -1;
else
return 0;
}
/********************************************************************/
int main(int argc, char *argv[ ] )
{
char sbuf[]={"Hello,this is a Serial_Port test!/n"};/*待发送的内容,以/n为结束标志*/
int sfd,retv,i;
struct termios option;
int length="sizeof"(sbuf);/*发送缓冲区数据宽度*/
/*******************************************************************/
open_serial(0); /*打开串口1*/
/*******************************************************************/
printf("ready for sending data.../n"); /*准备开始发送数据*/
tcgetattr(fd,&option);
cfmakeraw(&option);
/*****************************************************************/
cfsetispeed(&opt,B9600); /*波特率设置为9600bps*/
cfsetospeed(&opt,B9600);
/*******************************************************************/
tcsetattr(fd,TCSANOW,&option);
retv="write"(fd,sbuf,length); /*接收数据*/
if(retv==-1)
{
perror("write");
}
printf("the number of char sent is %d/n",retv);
flag_close =close(fd);
if(flag_close ==-1) /*判断是否成功关闭文件*/
printf(“Close the Device failur!/n”);
return 0;
}
/****************************结束***********************************/
编译send receive上传到板子上, 开一个adb shell执行./receive, 开另外一个adb shell执行 ./send,可以看到receive端接收到了数据
之前我用usb-serial一端连接设备,另外一端连接到自己的PC上,在板子和PC上分别跑receive和send程序,receive阻塞,无法收到数据。搞了两天,最后发现是不能直连,必须找个转接头(2接3, 3 接2)。我们平时用的连接设备到开发板的也是直连线,这种线直连两台PC是不能通信的。
因为手头没有转接头,放弃了在设备和PC通信的想法,用线连接2和3脚,在设备上测试串口功能。
因为Usb-serial有多种芯片,对应不同的芯片驱动,在Ubuntu的机器上,可以把这些驱动编译为模块方式,在插入usb-serial转换器时,USB子系统会先检测设备的基本信息,再根据这些信息自动加载相应的驱动。
但是在我的板子上,不知为何插入usb-serial转换器不能执行自动加载驱动,这涉及到hotplug, udev和USB子系统,有时间我会再研究一下。
暂时的解决办法就是把pl2303直接编译到内核中。