📄 sct.c
字号:
/****************************************************************************** SCT, Serial Communication Tracer ** CopyRight (C) by Bruce (ZhaoFei), zhaofei@zflogic.com, * http://www.zflogic.com* ** All sources in the package are copyrighted under the the terms of GNU GPL****************************************************************************** * This program is free software; you can redistribute it and/or modify* it under the terms of the GNU General Public License as published by* the Free Software Foundation; either version 2 of the License, or* (at your option) any later version.** This program is distributed in the hope that it will be useful,* but WITHOUT ANY WARRANTY; without even the implied warranty of* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the* GNU General Public License for more details.** You should have received a copy of the GNU General Public License* along with this program; if not, write to the Free Software* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA** If you intend to use this pragram commercially on a regular basis you* must contact the author for an appropriate donation.* ***************************************************************************/#include "stdhdr.h"#include "util.h"#define SCT_L#include "sct.h"#include "tio.h"#define FPATH_CONF "/etc/sct.conf"#define MAXBUFS 10#define MAXBUFSIZE (32 * 1024)#define UNDER_DEV "this function is under development\n"#define deal_with_errarg() do{ printf("Arguments error,pelease input 'help %s' for help\n",parv[0]); return;} while(0)devstat_t devstat,defl_devstat; struct bufstat_t { bool used; int size; uchar *buf;};struct bufstat_t bufstat[MAXBUFS]; void cmd_stat(int parc, char *parv[]){ if (parc != 1) deal_with_errarg(); printf("Device: %s\n",devstat.devname); printf("Frameset: %s\n",devstat.frameset); printf("Handshake: "); printf("\n "); if(devstat.hsflag & HS_RTSCTS) printf("RTS/CTS = ON"); else printf("RTS/CTS = OFF"); printf("\n "); if(devstat.hsflag & HS_XONXOFF) printf("XON/XOFF = ON"); else printf("XON/XOFF = OFF"); printf("\n"); if(devstat.opened) printf("Active: YES\n"); else printf("Active: NO\n"); }void cmd_port(int parc, char *parv[]){ if (parc != 2) deal_with_errarg(); if (devstat.opened) printf("You can't change a port while it's opened\n"); else { strcpy(devstat.devname,parv[1]); printf("Current port is changed to "); printf(devstat.devname); printf("\n"); } }void cmd_frame(int parc, char *parv[]){ devstat_t old_dt; if (parc != 2) deal_with_errarg(); if (devstat.opened) { printf("You can't change frameset while the port opened\n"); return; } memcpy(&old_dt,&devstat,sizeof(devstat));//save old setting if (parse_frameset(&devstat,parv[1])) { strcpy(devstat.frameset,parv[1]); printf("Current frameset is changed to %s\n",devstat.frameset); } else { memcpy(&devstat,&old_dt,sizeof(devstat)); //resume old setting printf("frameset not correct\n"); }}void cmd_handshake(int parc, char *parv[]){ bool well_done = true; devstat_t old_dt; if (parc<2 || parc>3) deal_with_errarg(); if (devstat.opened) { printf("You can't change handshaking while the port opened\n"); return; } //check arguments if (parc == 2) { if (!strcmp("+rts",parv[1]) || !strcmp("+rtscts",parv[1])) devstat.hsflag |= HS_RTSCTS; else if (!strcmp("+xonxoff", parv[1])) devstat.hsflag |= HS_XONXOFF; else if (!strcmp("-rts", parv[1]) || !strcmp("-rtscts",parv[1])) devstat.hsflag ^= HS_RTSCTS; else if (!strcmp("-xonxoff", parv[1])) devstat.hsflag ^= HS_XONXOFF; else if (!strcmp("none", parv[1])) devstat.hsflag = 0; else well_done = false; } else if(parc == 3) { if(!strcmp("+",parv[1]) && (!strcmp("rts",parv[2]) || !strcmp("rtscts",parv[2]))) devstat.hsflag |= HS_RTSCTS; else if(!strcmp("+",parv[1]) && !strcmp("xonxoff",parv[2])) devstat.hsflag |= HS_XONXOFF; else if(!strcmp("-",parv[1]) && (!strcmp("rts",parv[2]) || !strcmp("rtscts",parv[2]))) devstat.hsflag |= HS_RTSCTS; else if(!strcmp("-",parv[1]) && !strcmp("xonxoff",parv[2])) devstat.hsflag |= HS_XONXOFF; else well_done = false; }else well_done=false; if (!well_done) deal_with_errarg(); else{ printf("current handshake: "); printf("\n "); if (devstat.hsflag & HS_RTSCTS) printf("RTS/CTS = ON"); else printf("RTS/CTS = OFF"); printf("\n "); if (devstat.hsflag & HS_XONXOFF) printf("XON/XOFF = ON"); else printf("XON/XOFF = OFF"); printf("\n"); } }void cmd_open(int parc, char *parv[]){ int fd,c, res; struct termios oldtio,newtio; if (parc != 1) deal_with_errarg(); if(devstat.opened){ printf("current port already opened!\n"); return; } /* ensure that we use the correct parameters to open the port * added by lynx, 2003-0412 */ parse_frameset(&devstat,devstat.frameset); fd = open(devstat.devname, O_RDWR | O_NOCTTY ); if (fd <0) {printf("fail to open %s!\n",devstat.devname); return; } tcgetattr(fd,&oldtio); bzero((uchar *)&newtio, sizeof(newtio)); /* setting baudrate. use POSIX's recommended method: * cfsetospeed and cfsetispeed * added by lynx, 2003-0412 */ res = cfsetospeed(&newtio,devstat.baudrate); if (res == -1) printf("set out speed of port error.\n"); res = cfsetispeed(&newtio,devstat.baudrate); if (res == -1) printf("set in speed of port error.\n"); /* add databits and stopbits setting * modified by lynx, 2003-0412 */ newtio.c_cflag |= (devstat.databits| devstat.stopbits | CS8 | CLOCAL | CREAD); if (devstat.parity == EVENPARITY) { newtio.c_cflag |= PARENB; printf("event parity enabled...\n"); } else if (devstat.parity == ODDPARITY) { newtio.c_cflag |= (PARENB | PARODD); printf("odd parity enabled...\n"); } if (devstat.hsflag & HS_RTSCTS) {#ifdef _SCO_UNIX newtio.c_cflag |= RTSFLOW ; newtio.c_cflag |= CTSFLOW;#else //linux newtio.c_cflag |= (CRTSCTS);#endif printf("Rts/Cts flow control enabled...\n"); } if (devstat.hsflag & HS_XONXOFF) { newtio.c_iflag |= (IXON | IXOFF); printf("Xon/Xoff flow control enabled...\n"); } newtio.c_iflag = IGNPAR ; //ingorn parity check error newtio.c_oflag = 0; newtio.c_lflag = 0 ; newtio.c_cc[VTIME] = 0; newtio.c_cc[VMIN] = 1; tcflush(fd, TCIOFLUSH); //flush both input and output io tcsetattr(fd,TCSANOW,&newtio); //asign new setting to device memcpy(&(devstat.oldtio),&oldtio,sizeof(oldtio)); //save old setting devstat.fd=fd; devstat.opened=true; printf("current port opened now\n");}void cmd_close(int parc, char *parv[]){ if (parc != 1) deal_with_errarg(); if (!devstat.opened) { printf("current port did not open before\n"); return; } tcsetattr(devstat.fd, TCSANOW, &(devstat.oldtio)); close(devstat.fd); devstat.opened = false; printf("current port closed\n"); }void cmd_term(int parc, char *parv[]){ bool stop; struct termios out_tios; fd_set readset, writeset; int res; char buf[255],key; if (parc != 1) deal_with_errarg(); if (!devstat.opened) { printf("Please opend port first!\n"); return; } printf("Auto apply NL while receive CR\n"); printf("Entered Terminal mode now, input 'Ctrl-C' for break\n"); tio_saveset(STDOUT_FILENO,&out_tios); //save stdout setting tio_raw(STDOUT_FILENO); //set stdout to row mode stop=false; FD_ZERO(&readset); FD_ZERO(&writeset); while (!stop) { FD_SET(STDIN_FILENO, &readset); FD_SET(devstat.fd, &readset); if (select(devstat.fd+1,&readset,&writeset,NULL,NULL) < 0) { stop=true; continue; } //key input event if (FD_ISSET(STDIN_FILENO,&readset)){ read(STDIN_FILENO,&key,1); if(key==0x7f) key=0x08; //backspace write(devstat.fd,&key,1); //write input to serial port if(key==3){ //wait remote answer for Ctrl-C sleep(1); stop=true; continue; } } //receive event if (FD_ISSET(devstat.fd,&readset)) { //write serial import to screen read(devstat.fd, buf, 1); write(STDOUT_FILENO,buf,1); } } tio_reset(STDOUT_FILENO,&out_tios); //reset stdout printf("Term stoped\n");}#define DISP_MASK 0#define DISP_ASC 1#define DISP_HEX 2void cmd_echo(int parc, char *parv[]){ bool stop; int dispmode,res,totrcv,i; char key,buf[255],outch[10]; struct termios out_tios; fd_set readset, writeset; if (parc == 1) dispmode = DISP_HEX; else if (parc == 2) { if ( !strcmp(parv[1],"a") || !strcmp(parv[1],"asc")) dispmode = DISP_ASC; else if ( !strcmp(parv[1],"h") || !strcmp(parv[1],"hex")) dispmode = DISP_HEX; else if ( !strcmp(parv[1],"m") || !strcmp(parv[1],"mask")) dispmode = DISP_MASK; else deal_with_errarg(); } else { deal_with_errarg(); } if (!devstat.opened) { printf("Please open port first\n"); return; } switch (dispmode) { case DISP_MASK: printf("Incoming data will not display\n"); break; case DISP_ASC: printf("Incoming data will displayed as ascii form\n"); break; case DISP_HEX: printf("Incoming data will displayed as hex form\n"); break; } printf("Enter echo mode now, input 'Ctrl-C' for break\n"); tio_saveset(STDOUT_FILENO, &out_tios); tio_raw(STDOUT_FILENO); FD_ZERO(&readset); FD_ZERO(&writeset); stop=false; totrcv=0; while (!stop) { FD_SET(STDIN_FILENO, &readset); FD_SET(devstat.fd, &readset); if ( (select(devstat.fd+1, &readset, &writeset, NULL, NULL) < 0)){ stop = true; continue; } if (FD_ISSET(devstat.fd, &readset)) { res = read(devstat.fd, buf, 1); write(devstat.fd, buf, res); switch (dispmode) { case DISP_MASK: break; case DISP_ASC: for (i = 0; i < res; i++) { if(!(totrcv % 80)) write(STDOUT_FILENO,"\x0d\x0a",2); sprintf(outch,"%c",buf[i]); write(STDOUT_FILENO,outch,1); totrcv++; } break; case DISP_HEX: for (i = 0; i < res; i++) { if(!(totrcv % 24)) write(STDOUT_FILENO,"\x0d\x0a",2); sprintf(outch,"%02X ",buf[i]); write(STDOUT_FILENO,outch,strlen(outch)); totrcv++; } break; }//end of switch } if ( FD_ISSET(STDIN_FILENO, &readset)) { read(STDIN_FILENO, &key, 1); if(key == 3) { //ctrl-c stop = true; sleep(1); } } }//end of while tio_reset(STDOUT_FILENO, &out_tios); printf("\nEcho stoped,received and replied %d chars at all\n",totrcv);}/* setbuf bufno dataform */#define INP_ASC 1#define INP_HEX 2void cmd_setbuf(int parc, char *parv[]){ char ch; int inpmode,i,bufno; struct termios in_tios; char buf[1024]; //check arguments if (parc != 3) deal_with_errarg(); bufno=atoi(parv[1]); if (bufno<0 || bufno>9){ printf("Buf number out of range\n"); return; } if (!strcmp(parv[2],"a") || !strcmp(parv[2],"asc")) inpmode = INP_ASC; else if( !strcmp(parv[2],"h") || !strcmp(parv[2],"hex")) inpmode = INP_HEX; else { printf("Invalid input mode as %s\n",parv[2]); return; } //init buf if (!bufstat[bufno].used) { bufstat[bufno].buf = malloc(MAXBUFSIZE); bufstat[bufno].used = true; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -