📄 port.c
字号:
/*
* 参数 : int stopbit;
* 返回值 :
* 描述 : 设置停止位
*/
static void tty_set_stopbit(INT8 stopbit)
{
if (2 == stopbit) {
termios_new.c_cflag |= CSTOPB; // 2 stop bits
} else {
termios_new.c_cflag &= ~CSTOPB; // 1 stop bit
}
}
/*
* 参数 :
* 返回值 :
* 描述 : 准备读数据
*/
static void tty_sig_handler()
{
char recvbuf[CHAR_MAX + 1];
int retval;
fd_set fs_read;
int byte_recv = 0;
int bytes = 0;
int status;
INT8 bit_value;
int i=0;
FD_ZERO(&fs_read);
FD_SET(fd, &fs_read);
tv_timeout.tv_sec = 0;
tv_timeout.tv_usec = 500;
//判断RI信号
/* if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
tty_tcflush(TCIFLUSH);
return;
}
bit_value = get_bit_value(status, 8);
if (1 != bit_value) { //没有上报数据
#ifdef _DEBUG_
printf("没有上报数据\n");
#endif
tty_tcflush(TCIFLUSH);
return;
}
//数据读取 至DTR=1;
if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
tty_tcflush(TCIFLUSH);
return;
}
status |= TIOCM_DTR;
if (tty_set_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("设置状态错误!\n");
#endif
tty_tcflush(TCIFLUSH);
return;
}
*/
//接收数据到临时缓冲
while (1) {
retval = select(fd + 1, &fs_read, NULL, NULL, &tv_timeout);
if (retval) {
ioctl(fd, FIONREAD, &bytes); //取得缓冲区中数据的数量
#ifdef _DEBUG_
//printf("缓冲区有数据: %d\n", bytes);
#endif
//读取数据
byte_recv = read(fd, recvbuf, bytes);
for(i=0;i<bytes;i++)
{
printf("--%read bytes--i:%d:--data--%x--%\n",i,recvbuf[i]);
}
} else {
break;
}
if (byte_recv > 0) {
tty_data_add(recvbuf, byte_recv); //加入到临时缓冲
#ifdef _DEBUG_
//recvbuf[byte_recv] = '\0';
//fprintf(stderr, "%s", recvbuf);
//fprintf(stderr, "\n");
//fflush(stderr);
#endif
}
if (byte_recv > 80) {
tv_timeout.tv_sec = 0;
tv_timeout.tv_usec = 500;
} else {
tv_timeout.tv_sec = 0;
tv_timeout.tv_usec = 200;
}
}
/*
//数据读取结束 至DTR=0;
if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
return;
}
status &= ~TIOCM_DTR;
if (tty_set_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("设置状态错误!\n");
#endif
return;
}
*/
return;
}
/*
* 参数 :
* 返回值 : 0--正常;-1--错误
* 描述 : 设置读信号灯(如有IO则调用sa_handler处理)
*/
int tty_set_read_sigon()
{
static struct sigaction sigaction_io;
sigaction_io.sa_handler = tty_sig_handler;
sigemptyset(&(sigaction_io.sa_mask));
sigaction_io.sa_flags = 0;
sigaction_io.sa_restorer = NULL;
sigaction(SIGIO, &sigaction_io, NULL);
// allow the process to receive SIGIO
if (-1 == fcntl(fd, F_SETFL, O_ASYNC)) {
printf("O_ASYNC----\n");
return (-1);
} else if (-1 == fcntl(fd, F_SETOWN, getpid())) {
printf("getpid()----\n");
return (-1);
}
return (0);
}
/*
* 参数 :
* 返回值 : 0--取正常;-1--取错误
status:串口信号状态
* 描述 : 取串口信号状态
*/
int tty_get_signal(int *status)
{
if (!tty_is_open()) {
return (E_CLOSED);
}
if (-1 == ioctl(fd, TIOCMGET, status)) {
#ifdef _DEBUG_
fprintf(stderr, "取信号状态错误\n");
#endif
return (E_GET_ERROR);
}
return S_PROCESS;
}
/*
* 参数 : status:串口信号状态
* 返回值 :0--设置正常;-1--设置错误
* 描述 : 设置串口信号状态
*/
int tty_set_signal(int *status)
{
if (!tty_is_open()) {
return (E_CLOSED);
}
if (-1 == ioctl(fd, TIOCMSET, status)) {
#ifdef _DEBUG_
fprintf(stderr, "设置信号状态错误\n");
#endif
return (E_SET_ERROR);
}
return S_PROCESS;
}
/*
* 参数 : queue 刷新序列
* 返回值 :0--正常;-1--错误
* 描述 : 刷新串口读写缓冲
*/
int tty_tcflush(int queue)
{
return (tcflush(fd, queue));
}
/*
* 参数 :
* 返回值 :
* 描述 : 控制信号恢复
*/
int tty_signal_resume()
{
int status;
tty_get_signal(&status);
status &= ~TIOCM_RTS;
status &= ~TIOCM_DTR;
tty_set_signal(&status);
return 0;
}
/*
* 参数 :
* 返回值 :
* 描述 : 信道请求
*/
int tty_rts_request()
{
int status, i;
INT8 bit_value;
while (1) { //判断RTS == 0? 等待信道
if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
return E_GET_ERROR;
}
bit_value = get_bit_value(status, 3);
if (0 == bit_value) {
break;
}
}
//发送RTS = 1信号
for (i = 0; i < 3; ++i) {
status |= TIOCM_RTS;
if (tty_set_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("设置状态错误!\n");
#endif
return E_SET_ERROR;
}
if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
return E_GET_ERROR;
}
//取CTS状态值
bit_value = get_bit_value(status, 6);
if (1 == bit_value) {
return S_PROCESS;
}
}
return E_SET_ERROR;
}
/*
* 参数 :
* 返回值 :
* 描述 : 信道释放
*/
int tty_rts_cancel()
{
int status;
INT8 bit_value;
//发送RTS = 0信号
status &= ~TIOCM_RTS;
if (tty_set_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("设置状态错误!\n");
#endif
return E_SET_ERROR;
}
if (tty_get_signal(&status) != S_PROCESS) {
#ifdef _DEBUG_
printf("取状态错误!\n");
#endif
return E_GET_ERROR;
}
//取CTS状态值
bit_value = get_bit_value(status, 6);
if (0 == bit_value) {
return S_PROCESS;
}
return E_SET_ERROR;
}
/*
* 参数 :
* 返回值 :
* 描述 : 串口指令接收
*/
void tty_input(void)
{
return;
}
/*
* 参数 :
* 返回值 : 0--发送 -1--异常
* 描述 : 串口指令发送
*/
int tty_output(BYTE * send_data, UINT32 len)
{
int total_len = 0;
//信道控制权获取
if (tty_rts_request() != S_PROCESS) { //失败
#ifdef _DEBUG_
printf("信道控制权获取失败\n");
#endif
return -1;
}
//数据发送
total_len = tty_write(send_data, len);
if (total_len <= 0) {
#ifdef _DEBUG_
printf("发送数据失败!\n");
#endif
return -1;
}
#ifdef _DEBUG_
printf("成功发送数据:%d\n", total_len);
#endif
//信到控制权释放
if (tty_rts_cancel() != S_PROCESS) { //失败
#ifdef _DEBUG_
printf("信道控制权释放失败\n");
#endif
return -1;
}
return 0;
}
/*
*读数据
*/
void read_data()
{
while(1)
{
tty_set_read_sigon();
}
}
/*
*写数据
*/
void write_data()
{
char wbuf[10];
strcpy(wbuf,"0");
while(1)
{
sleep(2);
tty_write(wbuf, 5);
}
}
int main(int argc, char **argv)
{
int ret, status;
UINT8 wbuf[10];
UINT8 rbuf[10];
pid_t pid_recv, pid_send;
int retval = 0;
unsigned char c, c_str[10];
pthread_t send_id, receive_id; //Thread ID
if (argc <2 )
{
printf("arguments too few.\n");
exit(-1);
}
if (!isdigit(*argv[1]))
{
printf("Illegal param, must be digit(0-8)!!!\n\n");
exit(-1);
}
bzero(wbuf, sizeof(wbuf));
bzero(rbuf, sizeof(rbuf));
memcpy(wbuf, "HELLO", sizeof(wbuf));
tty_open(&portinfo,argv[1]);
for(;;)
{
if (pthread_create(&send_id, NULL, write_data, NULL)!= 0)
{
printf("create send fail");
}
if (pthread_create(&receive_id, NULL, read_data, NULL)!= 0)
{
printf("create receive fail");
}
pthread_join(send_id, NULL);
pthread_join(receive_id, NULL);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -