#include <time.h>
#include <stdio.h> /*标准输入输出定义*/
#include <stdlib.h> /*标准函数库定义*/
#include <unistd.h> /*Unix 标准函数定义*/
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h> /*文件控制定义*/
#include <termios.h> /*PPSIX 终端控制定义*/
#include <errno.h> /*错误号定义*/
#include <poll.h>
#include <pthread.h>
#include <semaphore.h>
#include <netdb.h>
#include <sys/types.h>
#include <sys/time.h>
#include <pthread.h>
#define FALSE 0
#define TRUE 1
#define COM1 "/dev/ttySAC1"
#define COM2 "/dev/ttySAC2"
#define COM3 "/dev/ttySAC3"
#define INFTIM -1
int speed_arr[]={B38400,B19200,B9600,B4800,B2400,B1200,B300,B38400,B19200,B9600,B4800,B2400,B1200,B300,B115200};
int name_arr[] ={38400,19200,9600,4800,2400,1200,300,38400,19200,9600,4800,2400,1200,300,115200};
pthread_mutex_t mutex_rx_thread =PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond_rx_thread =PTHREAD_COND_INITIALIZER;
//设置数据位,停止位,校验位
int set_parity(int fd,int databits,int stopbits,int parity)
{
struct termios options;
if ( tcgetattr( fd,&options) != 0){
perror("SetupSerial 1");
return(FALSE);
}
options.c_cflag &= ~CSIZE;
//设置数据位
switch (databits){
case 7:
options.c_cflag |= CS7;
break;
case 8:
options.c_cflag |= CS8;
break;
default:
return (FALSE);
}
//设置奇偶校验
switch (parity){
case 'n':
case 'N':
options.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG); /*Input*/
options.c_oflag &= ~OPOST; /*Output*/
break;
case 'o':
case 'O':
options.c_cflag |= (PARODD | PARENB); /* 设置为奇效验*/
options.c_iflag |= INPCK; /* Disnable parity checking */
break;
case 'e':
case 'E':
options.c_cflag |= PARENB; /* Enable parity */
options.c_cflag &= ~PARODD; /* 转换为偶效验*/
options.c_iflag |= INPCK; /* Disnable parity checking */
break;
case 'S':
case 's': /*as no parity*/
options.c_cflag &= ~PARENB;
options.c_cflag &= ~CSTOPB;
break;
default:
return (FALSE);
}
// 设置停止位
switch (stopbits){
case 1:
options.c_cflag &= ~CSTOPB;
break;
case 2:
options.c_cflag |= CSTOPB;
break;
default:
fprintf(stderr,"Unsupported stop bits\n");
return (FALSE);
}
//Set input parity option
if ((parity != 'n')&&(parity != 'N'))
options.c_iflag |= INPCK;
options.c_cc[VTIME] = 5; // 0.5 seconds
options.c_cc[VMIN] = 1;
options.c_cflag &= ~HUPCL;
options.c_iflag &= ~INPCK;
options.c_iflag |= IGNBRK;
options.c_iflag &= ~ICRNL;
options.c_iflag &= ~IXON;
options.c_lflag &= ~IEXTEN;
options.c_lflag &= ~ECHOK;
options.c_lflag &= ~ECHOCTL;
options.c_lflag &= ~ECHOKE;
options.c_oflag &= ~ONLCR;
//刷新
tcflush(fd,TCIFLUSH);
if (tcsetattr(fd,TCSANOW,&options) != 0){
return (FALSE);
}
return (TRUE);
}
//设置波特率
int set_speed(int fd,int speed)
{
struct termios opt;
int i;
int status;
tcgetattr(fd,&opt);
for(i=0;i<sizeof(speed_arr)/sizeof(int);i++)
{
if(speed==name_arr[i]){
tcflush(fd,TCIOFLUSH);
cfsetispeed(&opt,speed_arr[i]);
cfsetospeed(&opt,speed_arr[i]);
status=tcsetattr(fd,TCSANOW,&opt);
if(status!=0){
return -1;
}
tcflush(fd,TCIOFLUSH);
}
}
if(tcgetattr(fd,&opt)!=0){
return -1;
}
}
//初始化物理层
int init_serial(char *pSerial)
{
int ret;
int len;
int fd;
printf("init_serial now,com:%s\r\n",pSerial);
//打开COM口
fd=open(pSerial,O_RDWR|O_NOCTTY);
if(fd<0){
printf("open the file errno: the errno=%d\r\n",errno);
return -1;
}
printf("fd:%d\r\n");
//设置数据位
if(set_parity(fd,8,1,'N')<0){
printf("set_Parity failed :the errno=%d\r\n",errno);
return -1;
}
//LOGD("set_Parity success;");
//设置波特率
if(set_speed(fd,115200)<0){
printf("set_speed failed : the errno=%d",errno);
return -1;
}
printf("init serial finish\r\n");
return fd;
}
//接收COM数据线程
void rx_thread(int *arg)
{
int len;
int nfd=1;
int i;
int j;
int fd = *arg;
char serial_buffer[1000];
int serial_buffer_pos;
struct pollfd pfd[1];
pfd[0].fd = fd;
pfd[0].events = POLLIN;
printf("create rx_thread succeed \r\n");
while(1){
//pthread_mutex_lock(&mutex_rx_thread);
//pthread_cond_wait(&cond_rx_thread,&mutex_rx_thread);
//pthread_mutex_unlock(&mutex_rx_thread);
tcflush(fd,TCIFLUSH );
while(1){
if (poll(pfd,nfd,INFTIM)> 0){
if(pfd[0].revents){
len = read(fd,&serial_buffer[serial_buffer_pos],1000);
if(len<0){
printf("RXThread:read the data failed,the errno=%d\r\n",errno);
return;
}
else if (len>0){
//LOGE("RXThread:read len=%d",len);
serial_buffer[serial_buffer_pos+len]=0;
printf("%s",&serial_buffer[serial_buffer_pos]);
if (serial_buffer_pos>900){
printf("[RXThread] Exceed FIFOPKT_MAX_SIZE\r\n ");
tcflush(fd,TCIFLUSH );
continue;
}
}
}
}
}
//LOGE("out the while loop");
}
}
int main(int argc, char **argv){
int fd,ret;
int byte_write=0;
int thread_id;
char *msg = "hello world\r\n";
fd=init_serial(COM2);
if(fd<0){
printf("init serial failed!!\r\n");
return -1;
}
printf("init serial success!!\r\n");
byte_write=write(fd,msg,strlen(msg));
printf("byte wirte :%d\r\n",byte_write);
/*
ret=pthread_create(&thread_id,NULL,(void*)rx_thread,(int*)&fd);
if(ret!=0){
printf("thread_id thread creat errno: the errno=%d\r\n",errno);
return FALSE;
}
*/
return 0;
}
串口应用编程
最新推荐文章于 2023-09-02 09:31:01 发布