00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027 #include "ArExport.h"
00028 #include "ariaOSDef.h"
00029 #include "ArSerialConnection.h"
00030 #include "ArLog.h"
00031 #include "ariaUtil.h"
00032
00033
00034 ArSerialConnection::ArSerialConnection()
00035 {
00036 myPort = INVALID_HANDLE_VALUE;
00037 myBaudRate = 9600;
00038 myStatus = STATUS_NEVER_OPENED;
00039 myHardwareControl = false;
00040 buildStrMap();
00041 }
00042
00043 ArSerialConnection::~ArSerialConnection()
00044 {
00045 if (myPort != INVALID_HANDLE_VALUE)
00046 close();
00047 }
00048
00049 void ArSerialConnection::buildStrMap(void)
00050 {
00051 myStrMap[OPEN_COULD_NOT_OPEN_PORT] = "Could not open serial port.";
00052 myStrMap[OPEN_COULD_NOT_SET_UP_PORT] = "Could not set up serial port.";
00053 myStrMap[OPEN_INVALID_BAUD_RATE] = "Baud rate invalid, could not set baud on serial port.";
00054 myStrMap[OPEN_COULD_NOT_SET_BAUD] = "Could not set baud rate on serial port.";
00055 myStrMap[OPEN_ALREADY_OPEN] = "Serial port already open.";
00056 }
00057
00058 const char * ArSerialConnection::getOpenMessage(int messageNumber)
00059 {
00060 return myStrMap[messageNumber].c_str();
00061 }
00062
00063 bool ArSerialConnection::openSimple(void)
00064 {
00065 if (internalOpen() == 0)
00066 return true;
00067 else
00068 return false;
00069 }
00070
00077 void ArSerialConnection::setPort(const char *port)
00078 {
00079 if (port == NULL)
00080 myPortName = "COM1";
00081 else
00082 myPortName = port;
00083 }
00084
00088 const char * ArSerialConnection::getPort(void)
00089 {
00090 return myPortName.c_str();
00091 }
00092
00099 int ArSerialConnection::open(const char *port)
00100 {
00101 setPort(port);
00102 return internalOpen();
00103 }
00104
00105
00106
00107 int ArSerialConnection::internalOpen(void)
00108 {
00109 DCB dcb;
00110
00111
00112 if (myStatus == STATUS_OPEN)
00113 {
00114 ArLog::log(ArLog::Terse,
00115 "ArSerialConnection::open: Serial port already open");
00116 return OPEN_ALREADY_OPEN;
00117 }
00118
00119 myPort = CreateFile(myPortName.c_str(),
00120 GENERIC_READ | GENERIC_WRITE,
00121 0,
00122 NULL,
00123 OPEN_EXISTING,
00124 0,
00125 NULL );
00126
00127 if (myPort == INVALID_HANDLE_VALUE) {
00128 ArLog::log(ArLog::Terse,
00129 "ArSerialConnection::open: Could not open serial port '%s'",
00130 myPortName.c_str());
00131 return OPEN_COULD_NOT_OPEN_PORT;
00132 }
00133
00134 if ( !GetCommState(myPort, &dcb) )
00135 {
00136 ArLog::log(ArLog::Terse,
00137 "ArSerialConnection::open: Could not get port data to set up port");
00138 close();
00139 myStatus = STATUS_OPEN_FAILED;
00140 return OPEN_COULD_NOT_SET_UP_PORT;
00141 }
00142
00143 dcb.ByteSize = 8;
00144 dcb.Parity = NOPARITY;
00145 dcb.StopBits = ONESTOPBIT;
00146 dcb.fOutxCtsFlow = FALSE;
00147 dcb.fOutxDsrFlow = 0;
00148 dcb.fBinary = TRUE;
00149 dcb.fParity = FALSE;
00150 dcb.fNull = FALSE;
00151 dcb.fOutX = FALSE;
00152 dcb.fInX = FALSE;
00153
00154 if ( !SetCommState(myPort, &dcb) )
00155 {
00156 ArLog::log(ArLog::Terse,
00157 "ArSerialConnection::open: Could not set up port");
00158 close();
00159 myStatus = STATUS_OPEN_FAILED;
00160 return OPEN_COULD_NOT_SET_UP_PORT;
00161 }
00162
00163 myStatus = STATUS_OPEN;
00164
00165 if (!setBaud(myBaudRate))
00166 {
00167 ArLog::log(ArLog::Terse,
00168 "ArSerialConnection::open: Could not set baud rate.");
00169 close();
00170 myStatus = STATUS_OPEN_FAILED;
00171 return OPEN_COULD_NOT_SET_BAUD;
00172 }
00173
00174 if (!setHardwareControl(myHardwareControl))
00175 {
00176 ArLog::log(ArLog::Terse,
00177 "ArSerialConnection::open: Could not set hardware control.");
00178 close();
00179 myStatus = STATUS_OPEN_FAILED;
00180 return OPEN_COULD_NOT_SET_UP_PORT;
00181 }
00182
00183 ArLog::log(ArLog::Verbose,
00184 "ArSerialConnection::open: Successfully opened and configured serial port.");
00185 return 0;
00186 }
00187
00188
00189
00190 bool ArSerialConnection::close(void)
00191 {
00192 bool ret;
00193
00194 if (myPort == INVALID_HANDLE_VALUE)
00195 return true;
00196
00197
00198 SetCommMask( myPort, 0 ) ;
00199
00200 EscapeCommFunction( myPort, CLRDTR ) ;
00201
00202 PurgeComm( myPort, PURGE_TXABORT | PURGE_RXABORT | PURGE_TXCLEAR | PURGE_RXCLEAR );
00203
00204 myStatus = STATUS_CLOSED_NORMALLY;
00205
00206 ret = CloseHandle( myPort ) ;
00207 if (ret)
00208 ArLog::log(ArLog::Verbose,
00209 "ArSerialConnection::close: Successfully closed serial port.");
00210 else
00211 ArLog::log(ArLog::Verbose,
00212 "ArSerialConnection::close: Unsuccessfully closed serial port.");
00213 myPort = (HANDLE) INVALID_HANDLE_VALUE;
00214 return ret;
00215 }
00216
00217 int ArSerialConnection::getBaud(void)
00218 {
00219 return myBaudRate;
00220 }
00221
00222 bool ArSerialConnection::setBaud(int baud)
00223 {
00224 DCB dcb;
00225
00226 myBaudRate = baud;
00227
00228 if (getStatus() != STATUS_OPEN)
00229 return true;
00230
00231 if ( !GetCommState(myPort, &dcb) )
00232 {
00233 ArLog::log(ArLog::Terse, "ArSerialConnection::setBaud: Could not get port Data.");
00234 return false;
00235 }
00236
00237 dcb.BaudRate = myBaudRate;
00238
00239 if ( !SetCommState(myPort, &dcb) )
00240 {
00241 ArLog::log(ArLog::Terse,
00242 "ArSerialConnection::setBaud: Could not set port Data.");
00243 return false;
00244 }
00245
00246 return true;
00247 }
00248
00249 bool ArSerialConnection::getHardwareControl(void)
00250 {
00251 return myHardwareControl;
00252 }
00253
00254 bool ArSerialConnection::setHardwareControl(bool hardwareControl)
00255 {
00256 DCB dcb;
00257
00258 myHardwareControl = hardwareControl;
00259
00260 if (getStatus() != STATUS_OPEN)
00261 return true;
00262
00263 if ( !GetCommState(myPort, &dcb) )
00264 {
00265 ArLog::log(ArLog::Terse,
00266 "ArSerialConnection::setBaud: Could not get port Data.");
00267 return false;
00268 }
00269
00270 if (myHardwareControl == 0)
00271 {
00272 dcb.fRtsControl = RTS_CONTROL_ENABLE;
00273 dcb.fDtrControl = DTR_CONTROL_ENABLE;
00274 }
00275 else
00276 {
00277 dcb.fRtsControl = RTS_CONTROL_DISABLE;
00278 dcb.fDtrControl = DTR_CONTROL_DISABLE;
00279 }
00280
00281 if ( !SetCommState(myPort, &dcb) )
00282 {
00283 ArLog::log(ArLog::Terse, "ArSerialConnection::setBaud: Could not set port Data.");
00284 return false;
00285 }
00286
00287 return true;
00288 }
00289
00290 int ArSerialConnection::write(const char *data, unsigned int size)
00291 {
00292 unsigned long ret;
00293
00294 if (myPort != INVALID_HANDLE_VALUE && myStatus == STATUS_OPEN)
00295 {
00296 if (!WriteFile(myPort, data, size, &ret, NULL))
00297 {
00298 ArLog::log(ArLog::Terse, "ArSerialConnection::write: Error on writing.");
00299 perror("ArSerialConnection::write:");
00300 return -1;
00301 }
00302 return ret;
00303 }
00304 ArLog::log(ArLog::Terse, "ArSerialConnection::write: Connection invalid.");
00305 return -1;
00306 }
00307
00308 int ArSerialConnection::read(const char *data, unsigned int size,
00309 unsigned int msWait)
00310 {
00311 COMSTAT stat;
00312 unsigned long ret;
00313 unsigned int numToRead;
00314 ArTime timeDone;
00315
00316 if (myPort != INVALID_HANDLE_VALUE && myStatus == STATUS_OPEN)
00317 {
00318 if (msWait > 0)
00319 {
00320 timeDone.setToNow();
00321 timeDone.addMSec(msWait);
00322 while (timeDone.mSecTo() >= 0)
00323 {
00324 if (!ClearCommError(myPort, &ret, &stat))
00325 return -1;
00326 if (stat.cbInQue < size)
00327 ArUtil::sleep(2);
00328 else
00329 break;
00330 }
00331 }
00332 if (!ClearCommError(myPort, &ret, &stat))
00333 return -1;
00334 if (stat.cbInQue == 0)
00335 return 0;
00336 if (stat.cbInQue > size)
00337 numToRead = size;
00338 else
00339 numToRead = stat.cbInQue;
00340 if (ReadFile( myPort, (void *)data, numToRead, &ret, NULL))
00341 {
00342 return (int)ret;
00343 }
00344 else
00345 {
00346 ArLog::log(ArLog::Terse, "ArSerialConnection::read: Read failed.");
00347 return -1;
00348 }
00349 }
00350 ArLog::log(ArLog::Terse, "ArSerialConnection::read: Connection invalid.");
00351 return -1;
00352 }
00353
00354
00355 int ArSerialConnection::getStatus(void)
00356 {
00357 return myStatus;
00358 }
00359
00360 bool ArSerialConnection::isTimeStamping(void)
00361 {
00362 return false;
00363 }
00364
00365 ArTime ArSerialConnection::getTimeRead(int index)
00366 {
00367 ArTime now;
00368 now.setToNow();
00369 return now;
00370 }
00371
00372 bool ArSerialConnection::getCTS(void)
00373 {
00374 DWORD modemStat;
00375 if (GetCommModemStatus(myPort, &modemStat))
00376 {
00377 return (bool) (modemStat & MS_CTS_ON);
00378 }
00379 else
00380 {
00381 fprintf(stderr, "problem with GetCommModemStatus\n");
00382 return false;
00383 }
00384 }
00385
00386 bool ArSerialConnection::getDSR(void)
00387 {
00388 DWORD modemStat;
00389 if (GetCommModemStatus(myPort, &modemStat))
00390 {
00391 return (bool) (modemStat & MS_DSR_ON);
00392 }
00393 else
00394 {
00395 fprintf(stderr, "problem with GetCommModemStatus\n");
00396 return false;
00397 }
00398 }
00399
00400 bool ArSerialConnection::getDCD(void)
00401 {
00402 DWORD modemStat;
00403 if (GetCommModemStatus(myPort, &modemStat))
00404 {
00405 return (bool) (modemStat & MS_RLSD_ON);
00406 }
00407 else
00408 {
00409 fprintf(stderr, "problem with GetCommModemStatus\n");
00410 return false;
00411 }
00412 }
00413
00414 bool ArSerialConnection::getRing(void)
00415 {
00416 DWORD modemStat;
00417 if (GetCommModemStatus(myPort, &modemStat))
00418 {
00419 return (bool) (modemStat & MS_RING_ON);
00420 }
00421 else
00422 {
00423 fprintf(stderr, "problem with GetCommModemStatus\n");
00424 return false;
00425 }
00426 }
00427