LCOV - code coverage report
Current view: top level - src/Kinematics/RV2AJ - Serial.cpp (source / functions) Hit Total Coverage
Test: HLR Lines: 1 54 1.9 %
Date: 2018-01-10 14:31:03 Functions: 2 8 25.0 %

          Line data    Source code
       1             : #include "Serial.hpp"
       2             : 
       3             : #include <cstring>
       4             : #include <iostream>
       5             : #include <stdexcept>
       6             : #include <string>
       7             : #include <fcntl.h>
       8             : #include <termios.h>
       9             : #include <unistd.h>
      10             : 
      11             : namespace HLR
      12             : {
      13             : namespace Kinematics
      14             : {
      15             : namespace RV2AJ
      16             : {
      17           0 : Serial::~Serial()
      18             : {
      19             :     try
      20             :     {
      21           0 :         if (opened())
      22             :         {
      23           0 :             close();
      24             :         }
      25             :     }
      26           0 :     catch (...)
      27             :     {
      28             :         // This may happen when close() is called after the if statement
      29             :         // not a real problem, so continue destructing and do not crash
      30             :         // the application.
      31           0 :         std::cerr << "caught exception in Serial::~Serial" << std::endl;
      32             :     }
      33           0 : }
      34             : 
      35           0 : void Serial::open(const std::string& dev)
      36             : {
      37             :     // Verify args.
      38           0 :     if (dev.empty())
      39             :     {
      40           0 :         throw std::invalid_argument("invalid device name");
      41             :     }
      42             : 
      43             :     // Check if open.
      44           0 :     if (opened())
      45             :     {
      46           0 :         throw std::runtime_error("device already open");
      47             :     }
      48             : 
      49             :     // Open device.
      50           0 :     fd = ::open(dev.c_str(), O_RDWR | O_NOCTTY | O_SYNC);
      51           0 :     if (!opened())
      52             :     {
      53           0 :         throw std::runtime_error("could not open device");
      54             :     }
      55             : 
      56             :     // Create termios tty mapping.
      57             :     struct termios tty;
      58           0 :     memset(&tty, 0, sizeof(tty));
      59           0 :     if (tcgetattr(fd, &tty) != 0)
      60             :     {
      61           0 :         ::close(fd);
      62           0 :         fd = -1;
      63           0 :         throw std::runtime_error("could not get device attributes");
      64             :     }
      65             : 
      66             :     // Set baud rate.
      67           0 :     cfsetispeed(&tty, B9600);
      68           0 :     cfsetospeed(&tty, B9600);
      69             : 
      70             :     // Set tty properties.
      71             :     // Some sets are probably not needed.
      72           0 :     tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS8; // 8-bit chars
      73           0 :     tty.c_iflag &= ~IGNBRK;                     // disable break processing
      74           0 :     tty.c_lflag = 0;     // no signaling chars, echo, canonical processing
      75           0 :     tty.c_oflag = 0;     // no remapping, delays
      76           0 :     tty.c_cc[VMIN] = 1;  // block when reading for 1 char
      77           0 :     tty.c_cc[VTIME] = 0; // do not timeout on read, block instead
      78           0 :     tty.c_iflag &= ~(IXON | IXOFF | IXANY); // disable xon/xoff controls
      79           0 :     tty.c_cflag |= (CLOCAL | CREAD);        // ignore modem control, allow read
      80           0 :     tty.c_cflag &= ~(PARENB | PARODD);      // disable parity
      81           0 :     tty.c_cflag |= 0;                       // set to 1 to enable parity
      82           0 :     tty.c_cflag &= ~CSTOPB;                 // stop bit
      83             : 
      84             :     // Write tty properties.
      85           0 :     if (tcsetattr(fd, TCSANOW, &tty) != 0)
      86             :     {
      87           0 :         ::close(fd);
      88           0 :         fd = -1;
      89           0 :         throw std::runtime_error("could not set tty properties");
      90             :     }
      91           0 : }
      92             : 
      93           0 : void Serial::close()
      94             : {
      95             :     // Check if open.
      96           0 :     if (!opened())
      97             :     {
      98           0 :         throw std::runtime_error("file is not opened");
      99             :     }
     100             : 
     101             :     // Close device.
     102           0 :     ::close(fd);
     103           0 :     fd = -1;
     104           0 : }
     105             : 
     106           0 : bool Serial::opened() const
     107             : {
     108           0 :     return fd >= 0;
     109             : }
     110             : 
     111           0 : void Serial::write(const std::string& msg)
     112             : {
     113             :     // Verify args.
     114           0 :     if (msg.empty())
     115             :     {
     116           0 :         throw std::invalid_argument("empty message");
     117             :     }
     118             : 
     119             :     // Check if open.
     120           0 :     if (!opened())
     121             :     {
     122           0 :         throw std::runtime_error("device not open");
     123             :     }
     124             : 
     125             :     // Write msg. The \0 terminator is not sent over the serial port.
     126           0 :     if (::write(fd, msg.c_str(), msg.length() * sizeof(char)) == -1)
     127             :     {
     128           0 :         throw std::runtime_error("could not write data to device");
     129             :     }
     130           0 : }
     131             : 
     132             : } // namespace RV2AJ
     133             : } // namespace Kinematics
     134           3 : } // namespace HLR

Generated by: LCOV version 1.12