Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members

udpsocket.cc

Go to the documentation of this file.
00001 /*
00002 ** udpsocket.cc
00003 ** Login : Julien Lemoine <speedblue@happycoders.org>
00004 ** Started on  Sun Mar  2 01:01:49 2003 Julien Lemoine
00005 ** $Id: udpsocket.cc,v 1.2 2004/06/01 21:30:54 speedblue Exp $
00006 **
00007 ** Copyright (C) 2003,2004 Julien Lemoine
00008 ** This program is free software; you can redistribute it and/or modify
00009 ** it under the terms of the GNU Lesser General Public License as published by
00010 ** the Free Software Foundation; either version 2 of the License, or
00011 ** (at your option) any later version.
00012 **
00013 ** This program is distributed in the hope that it will be useful,
00014 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
00015 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00016 ** GNU Lesser General Public License for more details.
00017 **
00018 ** You should have received a copy of the GNU Lesser General Public License
00019 ** along with this program; if not, write to the Free Software
00020 ** Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
00021 */
00022 
00023 #include "udpsocket.hh"
00024 
00025 namespace Network
00026 {
00027   void  UdpSocket::connect(const std::string& hostname, int port)
00028   {
00029     _port = port;
00030     _socket = _bind(port, hostname);
00031   }
00032 
00033   void  UdpSocket::connect(int port)
00034   {
00035     _socket = _bind(port);
00036     _port = port;
00037   }
00038 
00039   void  UdpSocket::close()
00040   {
00041     if (_socket > 0)
00042       _close(_socket);
00043     _socket = 0;
00044   }
00045 
00046   std::string   UdpSocket::_read_line_bin(int socket, unsigned int size)
00047   {
00048     char                chr[MAXPKTSIZE];
00049     std::string         str = "";
00050     int                 res = 1;
00051     bool                end = false;
00052 
00053     if (socket < 0)
00054       throw NoConnection("No Socket", HERE);
00055     if (_buffer.size() >= 2 && !size)
00056       {
00057         size = (unsigned char)_buffer[0] * 256 + (unsigned char)_buffer[1];
00058         _buffer = _buffer.substr(2, _buffer.size() - 2);
00059       }
00060     if (size && _buffer.size() >= size)
00061       {
00062         str = _buffer.substr(0, size);
00063         _buffer = _buffer.substr(size, _buffer.size() - size);
00064       }
00065     else
00066       while (!end)
00067         {
00068           memset(chr, 0, MAXPKTSIZE);
00069 #ifdef LIBSOCKET_WIN
00070           res = recv(socket, chr, MAXPKTSIZE, 0);
00071 #else
00072           res = recv(socket, chr, MAXPKTSIZE, MSG_TRUNC);
00073 #endif
00074           if (res <= 0)
00075             throw ConnectionClosed("Connection Closed", HERE);
00076           // _buffer += all octets received
00077           _buffer += std::string(chr, res);
00078           if (!size)
00079             {
00080               // extract size from _buffer and reduce it
00081               size = (unsigned char)_buffer[0] * 256 + (unsigned char)_buffer[1];
00082               _buffer = _buffer.substr(2, _buffer.size() - 2);
00083             }
00084           if (_buffer.size() > size - str.size())
00085             {
00086               str += _buffer.substr(0, size - str.size());
00087               _buffer = _buffer.substr(size - str.size(), 
00088                                        _buffer.size() - size - str.size());
00089             }
00090           else
00091             {
00092               str += _buffer;
00093               _buffer = "";
00094             }
00095           if (str.size() >= size)
00096             end = true;
00097         }
00098     return str;
00099   }
00100 
00101   std::string   UdpSocket::_read_line_bin(int socket, int& port,
00102                                           std::string& host, 
00103                                           unsigned int pkg_size)
00104   {
00105     char                        chr[MAXPKTSIZE];
00106     std::string                 str = "";
00107     int                         res = 1;
00108     struct sockaddr_in          addr;
00109 #ifdef IPV6_ENABLED
00110     struct sockaddr_in6         addr6;
00111 #endif
00112 #ifdef LIBSOCKET_WIN
00113     int                         size;
00114 #else
00115     socklen_t                   size;
00116 #endif
00117     bool                        end = false;
00118 
00119 #ifdef IPV6_ENABLED
00120     if (V4 == _version)
00121 #endif
00122       size = sizeof(addr);
00123 #ifdef IPV6_ENABLED
00124     else
00125       size = sizeof(addr6);
00126 #endif
00127     if (socket < 0)
00128       throw NoConnection("No Socket", HERE);
00129     if (_buffer.size() >= 2 && !pkg_size)
00130       {
00131         pkg_size = (unsigned char)_buffer[0] * 256 + (unsigned char)_buffer[1];
00132         _buffer = _buffer.substr(2, _buffer.size() - 2);
00133       }
00134     if (pkg_size && _buffer.size() >= pkg_size)
00135       {
00136         str = _buffer.substr(0, pkg_size);
00137         _buffer = _buffer.substr(pkg_size, _buffer.size() - pkg_size);
00138       }
00139     else
00140       while (!end)
00141         {
00142 #ifdef LIBSOCKET_WIN
00143           int flags = 0;
00144 #else
00145           int flags = MSG_TRUNC;
00146 #endif
00147 #ifdef IPV6_ENABLED
00148           if (V4 == _version)
00149 #endif
00150             res = recvfrom(socket, chr, MAXPKTSIZE, flags,
00151                            (struct sockaddr *) &addr, &size);
00152 #ifdef IPV6_ENABLED
00153           else
00154             res = recvfrom(socket, chr, MAXPKTSIZE, flags,
00155                            (struct sockaddr *) &addr6, &size);
00156 #endif
00157           if (res <= 0)
00158             throw ConnectionClosed("Connection Closed", HERE);
00159           // _buffer += all octets received
00160           _buffer += std::string(chr, res).substr(0, res);
00161           if (!pkg_size)
00162             {
00163               // extract size from _buffer and reduce it
00164               pkg_size = (unsigned char)_buffer[0] * 256 + 
00165                 (unsigned char)_buffer[1];
00166               _buffer = _buffer.substr(2, _buffer.size() - 2);
00167             }
00168           if (_buffer.size() > pkg_size - str.size())
00169             {
00170               str += _buffer.substr(0, pkg_size - str.size());
00171               _buffer = _buffer.substr(pkg_size - str.size(), 
00172                                        _buffer.size() - pkg_size - str.size());
00173             }
00174           else
00175             {
00176               str += _buffer;
00177               _buffer = "";
00178             }
00179           if (str.size() >= pkg_size)
00180             end = true;
00181         }
00182 #ifdef IPV6_ENABLED
00183     if (V4 == _version)
00184       {
00185 #endif
00186         host = std::string(inet_ntoa(addr.sin_addr));
00187         port = ntohs(addr.sin_port);
00188 #ifdef IPV6_ENABLED
00189       }
00190     else
00191       {
00192         char buf[INET6_ADDRSTRLEN];
00193         if (inet_ntop(AF_INET6, &addr6.sin6_addr, buf, INET6_ADDRSTRLEN) == 0)
00194           throw InetntopError("Not a valid address", HERE);
00195         host = std::string(buf);
00196         port = ntohs(addr6.sin6_port);
00197       }
00198 #endif
00199     return str;
00200   }
00201 
00202 }

Generated on Fri Apr 8 06:13:01 2005 for libsocket by  doxygen 1.4.0