NewNet/nnunixserversocket.cpp

00001 /*  NewNet - A networking framework in C++
00002     Copyright (C) 2006 Ingmar K. Steen (iksteen@gmail.com)
00003 
00004     This program is free software; you can redistribute it and/or modify
00005     it under the terms of the GNU General Public License as published by
00006     the Free Software Foundation; either version 2 of the License, or
00007     (at your option) any later version.
00008 
00009     This program is distributed in the hope that it will be useful,
00010     but WITHOUT ANY WARRANTY; without even the implied warranty of
00011     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012     GNU General Public License for more details.
00013 
00014     You should have received a copy of the GNU General Public License
00015     along with this program; if not, write to the Free Software
00016     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00017 
00018  */
00019 
00020 #include "nnunixserversocket.h"
00021 #include "nnlog.h"
00022 #include "platform.h"
00023 #include <iostream>
00024 
00025 void
00026 NewNet::UnixServerSocket::listen(const std::string & path)
00027 {
00028   if(path.length() >= UNIX_PATH_MAX)
00029   {
00030     NNLOG("newnet.net.warn", "Unix socket path too long: '%s'.", path.c_str());
00031     setSocketError(ErrorInvalidPath);
00032     cannotListenEvent(this);
00033   }
00034 
00035   unlink(path.c_str());
00036 
00037   struct sockaddr_un address;
00038   memset(&address, 0, sizeof(address));
00039 
00040   address.sun_family = AF_UNIX;
00041   memcpy(address.sun_path, path.c_str(), path.length());
00042 
00043   int sock = socket(PF_UNIX, SOCK_STREAM, 0);
00044   fcntl(sock, F_SETFL, O_NONBLOCK);
00045 
00046   mode_t old_umask = umask(0177);
00047   int ret = bind(sock, (struct sockaddr *)&address, sizeof(struct sockaddr_un));
00048   umask(old_umask);
00049   if(ret != 0)
00050   {
00051     NNLOG("newnet.net.warn", "Cannot bind unix socket to '%s', error: %i.", path.c_str(), errno);
00052     close(sock);
00053     setSocketError(ErrorCannotBind);
00054     cannotListenEvent(this);
00055     return;
00056   }
00057 
00058   if (::listen(sock, 3) != 0)
00059   {
00060     NNLOG("newnet.net.warn", "Cannot listen on unix socket '%s', error: %i.", path.c_str(), errno);
00061     close(sock);
00062     setSocketError(ErrorCannotListen);
00063     cannotListenEvent(this);
00064     return;
00065   }
00066 
00067   m_Path = path;
00068   setDescriptor(sock);  
00069   setSocketState(SocketListening);
00070   listeningEvent(this);
00071 
00072   NNLOG("newnet.net.debug", "Listening on unix socket '%s'.", path.c_str());
00073 }
00074 
00075 void
00076 NewNet::UnixServerSocket::disconnect()
00077 {
00078   if((descriptor() == -1) || (socketState() != SocketListening))
00079   {
00080     NNLOG("newnet.net.warn", "Trying to disconnect an uninitialized unix server socket.");
00081     return;
00082   }
00083   ServerSocket::disconnect();
00084   unlink(m_Path.c_str());
00085 }

Generated on Sun Jan 7 14:00:01 2007 for NewNet by  doxygen 1.5.1