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 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 
00045 #include <pressure_cells/BufferedAsyncSerial.h>
00046 #include <string>
00047 #include <algorithm>
00048 #include <iostream>
00049 #include <boost/bind.hpp>
00050 
00051 using namespace std;
00052 
00053 using namespace boost;
00054 
00055 
00056 
00057 
00058 
00059 BufferedAsyncSerial::BufferedAsyncSerial (  ):AsyncSerial (  )
00060 {
00061    setReadCallback ( boost::bind ( &BufferedAsyncSerial::readCallback, this, _1, _2 ) );
00062 }
00063 
00064 BufferedAsyncSerial::BufferedAsyncSerial ( const std::string & devname,
00065                                            unsigned int baud_rate,
00066                                            asio::serial_port_base::parity opt_parity,
00067                                            asio::
00068                                            serial_port_base::character_size opt_csize,
00069                                            asio::serial_port_base::flow_control opt_flow,
00070                                            asio::serial_port_base::stop_bits opt_stop ):
00071 AsyncSerial ( devname, baud_rate, opt_parity, opt_csize, opt_flow, opt_stop )
00072 {
00073    setReadCallback ( boost::bind ( &BufferedAsyncSerial::readCallback, this, _1, _2 ) );
00074 }
00075 
00076 size_t BufferedAsyncSerial::read ( char *data, size_t size )
00077 {
00078    lock_guard < mutex > l ( readQueueMutex );
00079    size_t
00080       result = min ( size, readQueue.size (  ) );
00081 
00082    vector < char >::iterator
00083       it = readQueue.begin (  ) + result;
00084 
00085    copy ( readQueue.begin (  ), it, data );
00086    readQueue.erase ( readQueue.begin (  ), it );
00087    return result;
00088 }
00089 
00090 std::vector < char >
00091 BufferedAsyncSerial::read (  )
00092 {
00093    lock_guard < mutex > l ( readQueueMutex );
00094    vector < char >result;
00095 
00096    result.swap ( readQueue );
00097    return result;
00098 }
00099 
00100 std::string BufferedAsyncSerial::readString (  )
00101 {
00102    lock_guard < mutex > l ( readQueueMutex );
00103    string result ( readQueue.begin (  ), readQueue.end (  ) );
00104 
00105    readQueue.clear (  );
00106    return result;
00107 }
00108 
00109 std::string BufferedAsyncSerial::readStringUntil ( const std::string delim )
00110 {
00111    lock_guard < mutex > l ( readQueueMutex );
00112    vector < char >::iterator
00113       it = findStringInVector ( readQueue, delim );
00114 
00115    if ( it == readQueue.end (  ) )
00116       return "";
00117    string result ( readQueue.begin (  ), it );
00118 
00119    it += delim.size (  );       
00120    readQueue.erase ( readQueue.begin (  ), it );
00121    return result;
00122 }
00123 
00124 void
00125   BufferedAsyncSerial::readCallback ( const char *data, size_t len )
00126 {
00127    lock_guard < mutex > l ( readQueueMutex );
00128    readQueue.insert ( readQueue.end (  ), data, data + len );
00129 }
00130 
00131 std::vector < char >::iterator
00132 BufferedAsyncSerial::findStringInVector ( std::vector < char >&v, const std::string & s )
00133 {
00134    if ( s.size (  ) == 0 )
00135       return v.end (  );
00136 
00137    vector < char >::iterator it = v.begin (  );
00138 
00139    for ( ;; )
00140      {
00141         vector < char >::iterator result = find ( it, v.end (  ), s[0] );
00142 
00143         if ( result == v.end (  ) )
00144            return v.end (  );   
00145 
00146         for ( size_t i = 0; i < s.size (  ); i++ )
00147           {
00148              vector < char >::iterator temp = result + i;
00149 
00150              if ( temp == v.end (  ) )
00151                 return v.end (  );
00152              if ( s[i] != *temp )
00153                 goto mismatch;
00154           }
00155         
00156         return result;
00157 
00158       mismatch:
00159         it = result + 1;
00160      }
00161 }
00162 
00163 BufferedAsyncSerial::~BufferedAsyncSerial (  )
00164 {
00165    clearReadCallback (  );
00166 }