/*
* max8640.c
*
* the program for matrix mode MX8640
*
* Copyright v2.0 by shenbo shanghai hunda
*
*
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <signal.h>
#include <termios.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
static struct termios newtios, oldtios; /* terminal settings */
static int saved_portfd = -1; /* serial port fd */
/* cleanup atexit handler */
void reset_tty_atexit(void)
{
if(saved_portfd != -1){
tcsetattr(saved_portfd, TCSANOW, &oldtios);
}
}
/* cleanup signal handler */
void reset_tty_handler(int signal)
{
if(saved_portfd != -1){
tcsetattr(saved_portfd, TCSANOW, &oldtios);
}
_exit(EXIT_FAILURE);
}
int open_port(const char *portname,long baud_rate,int data_bit,int stop_bit,int parity)
{
struct sigaction sa;
int portfd;
long databits = 0;
long stopbits = 0;
long parityof = 0;
long parityoe = 0;
/*Useing for test the program!*/
printf("opening serial port: %s\n", portname);
/* open serial port */
if((portfd = open(portname, O_RDWR|O_NOCTTY)) < 0){
printf("open serial port %s fail\n", portname);
return portfd;
}
/* get serial port params, save away */
//printf("get serial port params, save away\n");
tcgetattr(portfd, &newtios);
memcpy(&oldtios, &newtios, sizeof newtios);
/* Set Data_bit */
switch(data_bit)
{case 5:
databits = CS5;
break;
case 6:
databits = CS6;
break;
case 7:
databits = CS7;
break;
case 8:
databits = CS8;
break;
}
switch(stop_bit)
{case 1:
stopbits= 0;
break;
case 2:
stopbits = CSTOPB;
break;
}
/* Set parity */
switch(parity)
{case 0:
parityof= 0;
parityoe= 0;
break;
case 1:
parityof= PARENB;
parityoe= PARODD;
break;
case 2:
parityof= PARENB;
parityoe= 0;
break;
}
/* configure new values */
printf("configure new values\n");
cfmakeraw(&newtios); /* see man page */
newtios.c_lflag &=~(ICANON|ECHO|ECHOE);
newtios.c_iflag = INPCK|BRKINT; /* ignore parity on input */
newtios.c_oflag &= ~OPOST;
//newtios.c_cflag = CS8|CLOCAL|CREAD;
newtios.c_cflag = databits|stopbits|parityof|parityoe|CLOCAL|CREAD;
newtios.c_cc[VMIN] = 1; /*block until 1 char received */
newtios.c_cc[VTIME] = 0; /*no inter-character timer */
/* Set BAUD */
switch(baud_rate)
{case 600:
printf("configure 600 bp\n");
cfsetospeed(&newtios, B600);
cfsetispeed(&newtios, B600);
break;
case 1200:
printf("configure 1200 bp\n");
cfsetospeed(&newtios, B1200);
cfsetispeed(&newtios, B1200);
break;
case 1800:
printf("configure 1800 bp\n");
cfsetospeed(&newtios, B1800);
cfsetispeed(&newtios, B1800);
break;
case 2400:
printf("configure 2400 bp\n");
cfsetospeed(&newtios, B2400);
cfsetispeed(&newtios, B2400);
break;
case 4800:
printf("configure 4800 bp\n");
cfsetospeed(&newtios, B4800);
cfsetispeed(&newtios, B4800);
break;
case 9600:
printf("configure 9600 bp\n");
cfsetospeed(&newtios, B9600);
cfsetispeed(&newtios, B9600);
break;
case 19200:
printf("configure 19200 bp\n");
cfsetospeed(&newtios, B19200);
cfsetispeed(&newtios, B19200);
break;
case 38400:
printf("configure 38400 bp\n");
cfsetospeed(&newtios, B38400);
cfsetispeed(&newtios, B38400);
break;
case 57600:
printf("configure 57600 bp\n");
cfsetospeed(&newtios, B57600);
cfsetispeed(&newtios, B57600);
break;
}
/* register cleanup stuff */
//printf("register cleanup stuff\n");
atexit(reset_tty_atexit);
memset(&sa, 0, sizeof sa);
sa.sa_handler = reset_tty_handler;
sigaction(SIGHUP, &sa, NULL);
sigaction(SIGINT, &sa, NULL);
sigaction(SIGPIPE, &sa, NULL);
sigaction(SIGTERM, &sa, NULL);
/* apply modified termios */
//printf("apply modified termios\n");
saved_portfd = portfd;
tcflush(portfd, TCIOFLUSH);
tcsetattr(portfd, TCSANOW, &newtios);
//tcsetattr(portfd, TCSADRAIN, &newtios);
//printf("open serial port is ok!\n");
return portfd;
}
void close_port(int portfd)
{
tcsetattr(portfd, TCSANOW, &oldtios);
close(portfd);
saved_portfd = -1;
}