00001 #include "LCDConnection.h" 00002 #include "LCDException.h" 00003 #include "string.h" 00004 #include <string.h> 00005 #include <errno.h> 00006 #include <fcntl.h> 00007 #include <iostream> 00008 00009 using namespace std; 00010 00011 LCDConnection::LCDConnection() 00012 { 00013 _isConnected = false; 00014 memset(&_addr, 0, sizeof (_addr)); 00015 _sock = socket (AF_INET, SOCK_STREAM, 0 ); 00016 00017 if (!isValid()) 00018 { 00019 throw LCDException(LCD_SOCKET_CREATION_ERROR); 00020 } 00021 00022 int on = 1; 00023 if (setsockopt(_sock, SOL_SOCKET, SO_REUSEADDR, (const char*) &on, sizeof (on)) == -1) 00024 { 00025 throw LCDException(LCD_SOCKET_CREATION_ERROR); 00026 } 00027 } 00028 00029 LCDConnection::LCDConnection(const string &host, const int port) 00030 { 00031 LCDConnection(); 00032 connect(host, port); 00033 } 00034 00035 LCDConnection::LCDConnection(const LCDConnection &source) 00036 { 00037 _sock = source._sock; 00038 _isConnected = source._isConnected; 00039 } 00040 00041 LCDConnection::~LCDConnection() 00042 { 00043 disconnect(); 00044 } 00045 00046 bool LCDConnection::isValid() const 00047 { 00048 return _sock != -1; 00049 } 00050 00051 void LCDConnection::connect(const string &host, const int port) 00052 { 00053 if (!isValid()) 00054 { 00055 throw LCDException(LCD_SOCKET_CREATION_ERROR); 00056 } 00057 00058 _addr.sin_family = AF_INET; 00059 _addr.sin_port = htons(port); 00060 00061 int status = inet_pton(AF_INET, host.c_str(), &_addr.sin_addr); 00062 00063 if (errno == EAFNOSUPPORT) 00064 { 00065 throw LCDException(LCD_SOCKET_NOT_SUPPORTED); 00066 } 00067 00068 status = ::connect(_sock, (sockaddr *)&_addr, sizeof(_addr) ); 00069 00070 if (status != 0) 00071 { 00072 throw LCDException(LCD_SOCKET_CONNECTION_ERROR); 00073 } 00074 00075 _isConnected = true; 00076 } 00077 00078 void LCDConnection::disconnect() 00079 { 00080 if (isValid()) 00081 { 00082 ::close(_sock); 00083 } 00084 } 00085 00086 void LCDConnection::send(const string &toSend) 00087 { 00088 string s = toSend + "\r\n"; 00089 00090 cerr << "Sending : " << s << endl; 00091 00092 if (!_isConnected) 00093 { 00094 throw LCDException(LCD_SOCKET_NOT_CONNECTED); 00095 } 00096 00097 int total = s.size(); 00098 int offset = 0; 00099 int sent; 00100 00101 while (offset != total) 00102 { 00103 sent = ::send(_sock, s.c_str() + offset, s.size() - offset, 0); 00104 if ( ((sent == -1) && (errno != EAGAIN)) || (sent == 0) ) 00105 { 00106 throw LCDException(LCD_SOCKET_SEND_ERROR); 00107 } 00108 else 00109 { 00110 offset += sent; 00111 } 00112 } 00113 } 00114 00115 string LCDConnection::recv() 00116 { 00117 if (!_isConnected) 00118 { 00119 throw LCDException(LCD_SOCKET_NOT_CONNECTED); 00120 } 00121 00122 char buf[LCD_MAXRECV + 1]; 00123 memset (buf, 0, LCD_MAXRECV + 1); 00124 char *current = buf - 1; 00125 int status; 00126 00127 do 00128 { 00129 current++; 00130 status = ::recv(_sock, current, 1, 0); 00131 if (status == -1) 00132 { 00133 throw LCDException(LCD_SOCKET_RECV_ERROR); 00134 } 00135 } while ( (*current != '\0' ) && (*current != '\r' ) && (*current != '\n' ) && ((current - buf) < LCD_MAXRECV) ); 00136 00137 *current = '\0'; 00138 00139 string result(buf); 00140 00141 cerr << "Receiving : " << result << endl; 00142 00143 return result; 00144 } 00145 00146 LCDConnection & LCDConnection::operator = (const LCDConnection ©) 00147 { 00148 disconnect(); 00149 00150 _sock = copy._sock; 00151 _isConnected = copy._isConnected; 00152 } 00153 00154 const LCDConnection& LCDConnection::operator << (const string &s) 00155 { 00156 send(s); 00157 return *this; 00158 } 00159 00160 const LCDConnection& LCDConnection::operator >> (string &s) 00161 { 00162 s = recv(); 00163 return *this; 00164 } 00165