00001
00002 #include "rcs_defs.hh"
00003 #include "_tty.h"
00004
00005 #ifndef NO_SERIAL_PORT
00006
00007 #include <stdio.h>
00008 #include <stdlib.h>
00009
00010 #ifdef UNIX_LIKE_PLAT
00011 #include <errno.h>
00012 #include <string.h>
00013 #include <sys/types.h>
00014 #include <sys/stat.h>
00015 #include <fcntl.h>
00016 #include <unistd.h>
00017 #include <termios.h>
00018 #endif
00019
00020 #ifdef WIN32
00021 #include <windows.h>
00022 #endif
00023
00024 #include "rcs_prnt.hh"
00025
00026
00027 int
00028 print_serial_port_configuration (RCS_SERIAL_PORT_HANDLE _handle)
00029 {
00030 #ifdef UNIX_LIKE_PLAT
00031 int ttyFileFd = _handle;
00032 struct termios ttysettings;
00033 if (tcgetattr (ttyFileFd, &ttysettings) < 0)
00034 {
00035 rcs_print ("tcgetattr failed.\n");
00036 return -1;
00037 }
00038 rcs_print ("c_iflag: %x ", ttysettings.c_iflag);
00039 if (ttysettings.c_iflag & BRKINT)
00040 rcs_print ("BRKINT ");
00041 if (ttysettings.c_iflag & ICRNL)
00042 rcs_print ("ICRNL ");
00043 if (ttysettings.c_iflag & IGNBRK)
00044 rcs_print ("IGNBRK ");
00045 if (ttysettings.c_iflag & IGNCR)
00046 rcs_print ("IGNCR ");
00047 if (ttysettings.c_iflag & IMAXBEL)
00048 rcs_print ("IMAXBEL ");
00049 if (ttysettings.c_iflag & INLCR)
00050 rcs_print ("INLCR ");
00051 if (ttysettings.c_iflag & INPCK)
00052 rcs_print ("INPCK ");
00053 if (ttysettings.c_iflag & IUCLC)
00054 rcs_print ("IUCLC ");
00055 if (ttysettings.c_iflag & IXANY)
00056 rcs_print ("IXANY ");
00057 if (ttysettings.c_iflag & IXOFF)
00058 rcs_print ("IXOFF ");
00059 if (ttysettings.c_iflag & IXON)
00060 rcs_print ("IXON ");
00061 if (ttysettings.c_iflag & PARMRK)
00062 rcs_print ("PARMRK ");
00063 rcs_print ("\n");
00064 rcs_print ("c_oflag: %x ", ttysettings.c_oflag);
00065 if (ttysettings.c_oflag & BSDLY)
00066 rcs_print ("BSDLY ");
00067 if (ttysettings.c_oflag & CRDLY)
00068 rcs_print ("CRDLY ");
00069 if (ttysettings.c_oflag & FFDLY)
00070 rcs_print ("FFDLY ");
00071 if (ttysettings.c_oflag & NLDLY)
00072 rcs_print ("NLDLY ");
00073 if (ttysettings.c_oflag & OCRNL)
00074 rcs_print ("OCRNL ");
00075 if (ttysettings.c_oflag & OFDEL)
00076 rcs_print ("OFDEL ");
00077 if (ttysettings.c_oflag & OFILL)
00078 rcs_print ("OFILL ");
00079 if (ttysettings.c_oflag & OLCUC)
00080 rcs_print ("OLCUC ");
00081 if (ttysettings.c_oflag & ONLCR)
00082 rcs_print ("ONLCR ");
00083 if (ttysettings.c_oflag & ONLRET)
00084 rcs_print ("ONLRET ");
00085 if (ttysettings.c_oflag & ONOCR)
00086 rcs_print ("ONOCR ");
00087
00088 if (ttysettings.c_oflag & OPOST)
00089 rcs_print ("OPOST ");
00090
00091 if (ttysettings.c_oflag & TABDLY)
00092 rcs_print ("TABDLY ");
00093 if (ttysettings.c_oflag & VTDLY)
00094 rcs_print ("VTDLY ");
00095 rcs_print ("\n");
00096 rcs_print ("c_cflag: %x ", ttysettings.c_cflag);
00097 #ifndef LINUX
00098 if (ttysettings.c_cflag & CCTS_OFLOW)
00099 rcs_print ("CCTS_OFLOW ");
00100 #endif
00101
00102 if (ttysettings.c_cflag & CLOCAL)
00103 rcs_print ("CLOCAL ");
00104 if (ttysettings.c_cflag & CREAD)
00105 rcs_print ("CREAD ");
00106 #ifndef LINUX
00107 if (ttysettings.c_cflag & CRTS_IFLOW)
00108 rcs_print ("CRTS_IFLOW ");
00109 #endif
00110 if ((ttysettings.c_cflag & CSIZE) == CS5)
00111 rcs_print ("CS5 ");
00112 if ((ttysettings.c_cflag & CSIZE) == CS6)
00113 rcs_print ("CS6 ");
00114 if ((ttysettings.c_cflag & CSIZE) == CS7)
00115 rcs_print ("CS7 ");
00116 if ((ttysettings.c_cflag & CSIZE) == CS8)
00117 rcs_print ("CS8 ");
00118 if (ttysettings.c_cflag & CSTOPB)
00119 rcs_print ("CSTOPB ");
00120 if (ttysettings.c_cflag & HUPCL)
00121 rcs_print ("HUPCL ");
00122
00123 if (ttysettings.c_cflag & PARENB)
00124 rcs_print ("PARENB ");
00125 if (ttysettings.c_cflag & PARODD)
00126 rcs_print ("PARODD ");
00127 rcs_print ("\n");
00128 rcs_print ("c_lflag: %x ", ttysettings.c_lflag);
00129
00130 if (ttysettings.c_cflag & ECHO)
00131 rcs_print ("ECHO ");
00132 if (ttysettings.c_cflag & ECHOCTL)
00133 rcs_print ("ECHOCTL ");
00134 if (ttysettings.c_cflag & ECHOE)
00135 rcs_print ("ECHOE ");
00136 if (ttysettings.c_cflag & ECHOK)
00137 rcs_print ("ECHOK ");
00138 if (ttysettings.c_cflag & ECHOKE)
00139 rcs_print ("ECHOKE ");
00140 if (ttysettings.c_cflag & ECHONL)
00141 rcs_print ("ECHONL ");
00142 if (ttysettings.c_cflag & ECHOPRT)
00143 rcs_print ("ECHOPRT ");
00144 if (ttysettings.c_cflag & FLUSHO)
00145 rcs_print ("FLUSHO ");
00146 if (ttysettings.c_cflag & ICANON)
00147 rcs_print ("ICANON ");
00148 if (ttysettings.c_cflag & IEXTEN)
00149 rcs_print ("IEXTEN ");
00150 if (ttysettings.c_cflag & ISIG)
00151 rcs_print ("ISIG ");
00152 if (ttysettings.c_cflag & NOFLSH)
00153 rcs_print ("NOFLSH ");
00154
00155 if (ttysettings.c_cflag & PENDIN)
00156 rcs_print ("PENDIN ");
00157 if (ttysettings.c_cflag & TOSTOP)
00158 rcs_print ("TOSTOP ");
00159 if (ttysettings.c_cflag & XCASE)
00160 rcs_print ("XCASE ");
00161 rcs_print ("\n");
00162 #endif
00163
00164 #ifdef WIN32
00165 DCB dcb;
00166 if (!GetCommState (_handle, &dcb))
00167 {
00168 return -1;
00169 }
00170 rcs_print ("DCBlength=%d\n", dcb.DCBlength);
00171
00172 rcs_print ("BaudRate=%d\n", dcb.BaudRate);
00173 rcs_print ("fBinary=%d\n", dcb.fBinary);
00174 rcs_print ("fParity=%d\n", dcb.fParity);
00175 rcs_print ("fOutxCtsFlow=%d\n", dcb.fOutxCtsFlow);
00176 rcs_print ("fOutxDsrFlow=%d\n", dcb.fOutxDsrFlow);
00177 rcs_print ("fDtrControl=%d\n", dcb.fDsrSensitivity);
00178 rcs_print ("fDsrSensitivity=%d\n", dcb.fDsrSensitivity);
00179 rcs_print ("fTXContinueOnXoff=%d\n", dcb.fTXContinueOnXoff);
00180 rcs_print ("fOutX=%d\n", dcb.fOutX);
00181 rcs_print ("fInX=%d\n", dcb.fInX);
00182 rcs_print ("fErrorChar=%d\n", dcb.fErrorChar);
00183 rcs_print ("fNull=%d\n", dcb.fNull);
00184 rcs_print ("fRtsControl=%d\n", dcb.fRtsControl);
00185 rcs_print ("fAbortOnError=%d\n", dcb.fAbortOnError);
00186 rcs_print ("XonLim=%d\n", dcb.XonLim);
00187 rcs_print ("XoffLim=%d\n", dcb.XoffLim);
00188 rcs_print ("ByteSize=%d\n", dcb.ByteSize);
00189 rcs_print ("Parity=%d\n", dcb.Parity);
00190 rcs_print ("StopBits=%d\n", dcb.StopBits);
00191 rcs_print ("XonChar=%x %c\n", dcb.XoffChar, dcb.XoffChar);
00192 rcs_print ("XoffChar=%x %c\n", dcb.XoffChar, dcb.XoffChar);
00193 rcs_print ("ErrorChar=%x %c\n", dcb.ErrorChar, dcb.ErrorChar);
00194 rcs_print ("EofChar=%x %c\n", dcb.EofChar, dcb.EofChar);
00195 rcs_print ("EvtChar=%x %c\n", dcb.EvtChar, dcb.EvtChar);
00196 return 0;
00197 #endif
00198 }
00199
00200 int
00201 set_serial_port_configuration (RCS_SERIAL_PORT_HANDLE _handle,
00202 struct rcs_serial_port_setting *_settings)
00203 {
00204 #ifdef UNIX_LIKE_PLAT
00205 struct termios ttysettings;
00206 int ttyFileFd = _handle;
00207 speed_t spd = B9600;
00208 if (tcgetattr (ttyFileFd, &ttysettings) < 0)
00209 {
00210 rcs_print_error ("tcgetattr failed: %d -- %s\n",
00211 errno, strerror (errno));
00212 return -1;
00213 }
00214 ttysettings.c_iflag = 0;
00215 ttysettings.c_oflag = 0;
00216 ttysettings.c_cflag = CS8 | CLOCAL | CREAD;
00217 ttysettings.c_lflag = 0;
00218 ttysettings.c_cc[VMIN] = 0;
00219 ttysettings.c_cc[VTIME] = 0;
00220 if (NULL != _settings)
00221 {
00222 switch (_settings->baud_rate)
00223 {
00224 case 300:
00225 spd = B300;
00226 break;
00227
00228 case 600:
00229 spd = B600;
00230 break;
00231
00232 case 1200:
00233 spd = B1200;
00234 break;
00235
00236 case 2400:
00237 spd = B2400;
00238 break;
00239
00240 case 9600:
00241 spd = B9600;
00242 break;
00243
00244 case 19200:
00245 spd = B19200;
00246 break;
00247 }
00248 if (_settings->data_bits == 7)
00249 {
00250 ttysettings.c_cflag &= ~CS8;
00251 ttysettings.c_cflag |= CS7;
00252 }
00253 if (_settings->stop_bits == 2)
00254 {
00255 ttysettings.c_cflag |= CSTOPB;
00256 }
00257 if (_settings->use_parity)
00258 {
00259 ttysettings.c_cflag |= PARENB;
00260 if (!_settings->even_parity)
00261 {
00262 ttysettings.c_cflag |= PARODD;
00263 }
00264 }
00265 }
00266
00267 if (cfsetospeed (&ttysettings, spd) < 0)
00268 {
00269 rcs_print_error ("cfsetospeed failed.\n");
00270 return -1;
00271 }
00272 if (cfsetispeed (&ttysettings, spd) < 0)
00273 {
00274 rcs_print_error ("cfsetispeed failed.\n");
00275 return -1;
00276 }
00277 if (tcsetattr (ttyFileFd, TCSANOW, &ttysettings) < 0)
00278 {
00279 rcs_print_error ("tcsetattr failed. %d -- %s\n",
00280 errno, strerror (errno));
00281 return -1;
00282 }
00283 #endif
00284 #ifdef WIN32
00285 DCB dcb;
00286 if (!GetCommState (_handle, &dcb))
00287 {
00288 return -1;
00289 }
00290
00291 dcb.BaudRate = CBR_9600;
00292 if (NULL != _settings)
00293 {
00294 dcb.BaudRate = _settings->baud_rate;
00295 }
00296 dcb.fBinary = FALSE;
00297 dcb.fParity = NOPARITY;
00298 dcb.fOutxCtsFlow = FALSE;
00299 dcb.fOutxDsrFlow = FALSE;
00300 dcb.fDtrControl = DTR_CONTROL_DISABLE;
00301 dcb.fDsrSensitivity = FALSE;
00302 dcb.fTXContinueOnXoff = TRUE;
00303 dcb.fOutX = FALSE;
00304 dcb.fInX = FALSE;
00305 dcb.fErrorChar = FALSE;
00306 dcb.fNull = FALSE;
00307 dcb.fRtsControl = RTS_CONTROL_DISABLE;
00308 dcb.ByteSize = 8;
00309 dcb.Parity = NOPARITY;
00310 dcb.StopBits = ONESTOPBIT;
00311 if (NULL != _settings)
00312 {
00313 dcb.ByteSize = _settings->data_bits;
00314 if (!_settings->use_parity)
00315 {
00316 dcb.Parity = NOPARITY;
00317 }
00318 else
00319 {
00320 if (!_settings->even_parity)
00321 {
00322 dcb.Parity = ODDPARITY;
00323 }
00324 else
00325 {
00326 dcb.Parity = EVENPARITY;
00327 }
00328 dcb.fParity = TRUE;
00329 }
00330 if (_settings->stop_bits == 2)
00331 {
00332 dcb.StopBits = TWOSTOPBITS;
00333 }
00334 }
00335 if (!SetCommState (_handle, &dcb))
00336 {
00337 return -1;
00338 }
00339 return 0;
00340 #endif
00341 }
00342
00343
00344 RCS_SERIAL_PORT_HANDLE
00345 open_serial_communications_port (char *name)
00346 {
00347 #ifdef UNIX_LIKE_PLAT
00348 int ttyFileFd = open (name, O_RDWR | O_NDELAY);
00349 if (ttyFileFd < 0)
00350 {
00351 rcs_print_error ("Can't open %s : %d %s\n",
00352 name, errno, strerror (errno));
00353 return (-1);
00354 }
00355 if (!isatty (ttyFileFd))
00356 {
00357 rcs_print_error ("open_serial_communications_port: %s is not a tty.\n",
00358 name);
00359 return (-1);
00360 }
00361 return ttyFileFd;
00362 #endif
00363 #ifdef WIN32
00364 HANDLE handle =
00365 CreateFile (name, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING,
00366 FILE_FLAG_NO_BUFFERING, NULL);
00367 return handle;
00368 #endif
00369 }
00370
00371 int
00372 read_serial_communications_port (RCS_SERIAL_PORT_HANDLE _handle, char *buf,
00373 int maxlen)
00374 {
00375 #ifdef UNIX_LIKE_PLAT
00376 int ttyFileFd = _handle;
00377 int bytes_read = read (ttyFileFd, buf, maxlen);
00378 return bytes_read;
00379 #endif
00380 #ifdef WIN32
00381 unsigned long bytes_read = 0;
00382 if (!ReadFile (_handle, buf, maxlen, &bytes_read, NULL))
00383 {
00384 return -1;
00385 }
00386 return bytes_read;
00387 #endif
00388 }
00389
00390 int
00391 write_serial_communications_port (RCS_SERIAL_PORT_HANDLE _handle, char *buf,
00392 int maxlen)
00393 {
00394 #ifdef UNIX_LIKE_PLAT
00395 int ttyFileFd = _handle;
00396 return write (ttyFileFd, buf, maxlen);
00397 #endif
00398 #ifdef WIN32
00399 unsigned long bytes_written = 0;
00400 if (!WriteFile (_handle, buf, maxlen, &bytes_written, NULL))
00401 {
00402 return -1;
00403 }
00404 return bytes_written;
00405 #endif
00406 }
00407
00408 #endif