The new patch with the last changes! Hope it's good :-)

Lisa

2010/4/7 Giuseppe Scrivano <[email protected]>

> Giuseppe Scrivano <[email protected]> writes:
>
> > namespace checked
> > {
> >   int read (int fd, void *buf, size_t count)
> >   {
> >     return gnulib::read (fd, buf, count);
> >   }
> > ...
> > }
>
> Obviously I meant:
>
> namespace checked
> {
>  int read (int fd, void *buf, size_t count)
>  {
>     return checkError (gnulib::read (fd, buf, count));
>  }
> ...
> }
>
> Cheers,
> Giuseppe
>



-- 
"Non riuscivo a condividere l'opinione che, se la conoscenza è pericolosa,
la soluzione ideale risiede nell'ignoranza. Mi è sempre parso, invece, che
la risposta autentica a questo problema stia nella saggezza." -- Isaac
Asimov
"The truth can be out there, but lies are inside our heads" -- Terry
Pratchett
From 8def97fa4910844d8beb1bd0b8e9d3f4f5ab41c8 Mon Sep 17 00:00:00 2001
From: Lisa Vitolo <[email protected]>
Date: Tue, 6 Apr 2010 21:09:36 +0200
Subject: [PATCH] Map POSIX errors to new exceptions.

The exception classes were created, representing errno values, and divided
in 3 categories. An abstract superclass allows the developer to get the
error message, the process backtrace, and a numeric value representing the
logging priority of the error from the exception object.
The namespace of checked::function is formed by common used functions that
in case of an error throw the right exception.
---
 myserver/configure.ac                         |    3 +-
 myserver/include/base/Makefile.am             |    2 +-
 myserver/include/base/exceptions/Makefile.am  |    3 +
 myserver/include/base/exceptions/checked.h    |   96 ++++
 myserver/include/base/exceptions/exceptions.h |  700 ++++++++++++++++++++++++
 myserver/src/base/Makefile.am                 |    2 +-
 myserver/src/base/exceptions/Makefile.am      |   21 +
 myserver/src/base/exceptions/checked.cpp      |  704 +++++++++++++++++++++++++
 myserver/src/base/exceptions/exceptions.cpp   |   21 +
 9 files changed, 1549 insertions(+), 3 deletions(-)
 create mode 100644 myserver/include/base/exceptions/Makefile.am
 create mode 100644 myserver/include/base/exceptions/checked.h
 create mode 100644 myserver/include/base/exceptions/exceptions.h
 create mode 100644 myserver/src/base/exceptions/Makefile.am
 create mode 100644 myserver/src/base/exceptions/checked.cpp
 create mode 100644 myserver/src/base/exceptions/exceptions.cpp

diff --git a/myserver/configure.ac b/myserver/configure.ac
index 7b0e2cd..809a622 100644
--- a/myserver/configure.ac
+++ b/myserver/configure.ac
@@ -98,7 +98,7 @@ AC_CHECK_HEADER([sys/sendfile.h], AC_DEFINE(SENDFILE, 1,
 gl_INIT
 
 AC_CHECK_FUNCS(regcomp setgroups localtime_r posix_fallocate \
-		           openat fstatat getpwnam ffsl readdir_r)
+		           openat fstatat getpwnam ffsl readdir_r backtrace backtrace_symbols)
 
 case "${host}" in
     *-*-mingw32*)
@@ -398,6 +398,7 @@ AC_CONFIG_FILES([ po/Makefile.in
     include/base/Makefile
     include/base/bitvec/Makefile
     include/base/read_directory/Makefile
+    include/base/exceptions/Makefile
     include/base/file/Makefile
     include/base/pipe/Makefile
     include/base/base64/Makefile
diff --git a/myserver/include/base/Makefile.am b/myserver/include/base/Makefile.am
index dfafe80..97cbc85 100644
--- a/myserver/include/base/Makefile.am
+++ b/myserver/include/base/Makefile.am
@@ -18,4 +18,4 @@ baseincludedir=$(includedir)/myserver/include/base
 baseinclude_HEADERS = utility.h
 SUBDIRS = base64 bitvec crypt dynamic_lib file files_cache read_directory \
 					hash_map home_dir mem_buff multicast pipe process regex safetime \
-					slab socket socket_pair ssl string sync thread unix_socket xml
+					slab socket socket_pair ssl string sync thread unix_socket xml exceptions
diff --git a/myserver/include/base/exceptions/Makefile.am b/myserver/include/base/exceptions/Makefile.am
new file mode 100644
index 0000000..4356022
--- /dev/null
+++ b/myserver/include/base/exceptions/Makefile.am
@@ -0,0 +1,3 @@
+exceptionsincludedir=$(includedir)/myserver/include/base/exceptions
+exceptionsinclude_HEADERS = checked.h exceptions.h
+SUBDIRS =
diff --git a/myserver/include/base/exceptions/checked.h b/myserver/include/base/exceptions/checked.h
new file mode 100644
index 0000000..8502904
--- /dev/null
+++ b/myserver/include/base/exceptions/checked.h
@@ -0,0 +1,96 @@
+/*
+MyServer
+Copyright (C) 2002, 2003, 2004, 2008, 2009, 2010 Free Software
+Foundation, Inc.
+Copyright (C) 2010, Lisa Vitolo (shainer)
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef CHECKED_H
+# define CHECKED_H
+
+# include "myserver.h"
+# include <errno.h>
+
+# include <alloca.h>
+# include <dirent.h>
+# include <fcntl.h>
+# include <regex.h>
+# include <signal.h>
+# include <stdio.h>
+# include <stdlib.h>
+# include <sys/ioctl.h>
+# include <sys/select.h>
+# include <sys/socket.h>
+# include <sys/stat.h>
+# include <sys/time.h>
+# include <sys/wait.h>
+# include <time.h>
+# include <unistd.h>
+# include <wchar.h>
+# include <wctype.h>
+
+# include <include/base/exceptions/exceptions.h>
+
+/*!
+ * Group of checked functions that throws an exception in case of error,
+ * instead of just setting errno
+ */
+namespace checked
+{
+  int accept (int fd, struct sockaddr *addr, socklen_t *addrlen);
+  int bind (int fd, const struct sockaddr *addr, socklen_t addrlen);
+  int chown (const char *file, uid_t uid, gid_t gid);
+  int close (int fd);
+  int closedir (DIR *);
+  int connect (int fd, const struct sockaddr *addr, socklen_t addrlen);
+  int dup (int oldfd);
+  int dup2 (int oldfd, int newfd);
+  int fstat (int fd, struct stat *buf);
+  int fstatat (int fd, char const *name, struct stat *st, int flags);
+  char * getcwd (char *buf, size_t size);
+  int gethostname (char *name, size_t len);
+  int getsockname (int fd, struct sockaddr *addr, socklen_t *addrlen);
+  int gettimeofday (struct timeval *, void *);
+  struct tm * gmtime_r (time_t const *__timer, struct tm * __result);
+  int listen (int fd, int backlog);
+  struct tm * localtime_r (time_t const *__timer, struct tm *__result);
+  int lstat (const char *name, struct stat *buf);
+  void * memchr (void const *__s, int __c, size_t __n);
+  int mkdir (char const *name, mode_t mode);
+  time_t mktime (struct tm *__tp);
+  int open (const char *filename, int flags);
+  DIR * opendir (const char *);
+  ssize_t read (int fd, void *buf, size_t count);
+  void * realloc (void *ptr, size_t size);
+  ssize_t recv (int fd, void *buf, size_t len, int flags);
+  int remove (const char *name);
+  int rename (const char *old_filename, const char *new_filename);
+  int rmdir (char const *name);
+  int select (int, fd_set *, fd_set *, fd_set *, struct timeval *);
+  ssize_t send (int fd, const void *buf, size_t len, int flags);
+  int setsockopt (int fd, int level, int optname, const void * optval, socklen_t optlen);
+  int shutdown (int fd, int how);
+  int sigaction (int signum, const struct sigaction *act, struct sigaction *oldact);
+  int sigaddset (sigset_t *set, int signum);
+  int sigemptyset (sigset_t *set);
+  int sigprocmask (int how, const sigset_t *set, sigset_t *oldset);
+  int socket (int domain, int type, int protocol);
+  char * strdup (char const *__s);
+  int unlink (char const *file);
+  ssize_t write (int fd, const void *buf, size_t count);
+
+  void raiseException ();
+}
+
+#endif
diff --git a/myserver/include/base/exceptions/exceptions.h b/myserver/include/base/exceptions/exceptions.h
new file mode 100644
index 0000000..39e18b9
--- /dev/null
+++ b/myserver/include/base/exceptions/exceptions.h
@@ -0,0 +1,700 @@
+/*
+MyServer
+Copyright (C) 2002, 2003, 2004, 2008, 2009, 2010 Free Software
+Foundation, Inc.
+Copyright (C) 2010, Lisa Vitolo (shainer)
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef EXCEPTIONS_H
+# define EXCEPTIONS_H
+
+# include "myserver.h"
+
+# include <exception>
+# include <errno.h>
+# include <execinfo.h>
+# include <stdlib.h>
+# include <string.h>
+
+# include <include/log/stream/log_stream.h>
+
+using namespace std;
+
+/*!
+ * This class describes an abstract MyServer exception
+ */ 
+class AbstractServerException: public exception
+{
+  public:
+    /*!
+     * Constructor of the class
+     */
+  	AbstractServerException ()
+  	{
+	  localErrno = errno;
+	  buffer = NULL;
+	  btString = NULL;
+	  }
+	
+  	int getErrno ()
+  	{
+	  return localErrno;
+	  }
+
+    /*!
+     * Returns the process backtrace of the application
+     * at the moment of the error
+     */	
+	  char **getBacktrace ()
+	  {
+	    if (localErrno == ENOMEM) /* it's not safe to allocate more */
+	    {
+        return NULL;
+      }
+	
+	    if (buffer == NULL)
+	    {	
+	      #ifdef HAVE_BACKTRACE
+	        size = 20;
+		      buffer = (void **) gnulib::malloc (sizeof(void *) * size);
+		      int w = backtrace (buffer, size);
+        #endif
+		
+	      #ifdef HAVE_BACKTRACE_SYMBOLS
+		      btString = (char **) gnulib::malloc (sizeof(char *) * w);
+		      btString = backtrace_symbols(buffer, w);
+	      #endif
+	    }
+	  
+	    return btString;
+	  }
+	
+	  /*!
+	   * Returns a string representing the error
+	   */
+  	virtual const char* what () const throw ()
+  	{
+      return gnulib::strerror (localErrno);
+  	}
+	
+	  enum LoggingLevel getLogLevel()
+	  {
+	    return logLevel;
+	  }
+	
+	  virtual ~AbstractServerException () throw ()
+	  {
+	    if (buffer)
+	    {
+	      free (buffer);
+	    }
+	  
+	    if (btString)
+	    {
+	      free (btString);
+	    }
+	  }
+	
+  protected:
+    int localErrno;
+    char **btString;
+    
+    void setLogLevel (enum LoggingLevel l)
+    {
+	    logLevel = l;
+	  }
+
+  private:
+    void **buffer;
+    int size;
+    enum LoggingLevel logLevel;
+};
+
+/*
+ * Generic categories to group together more exceptions of the same type
+ */
+class GenericFileException : public AbstractServerException
+{
+  public:
+    GenericFileException () : AbstractServerException () {}
+};
+
+class GenericSocketException : public AbstractServerException
+{
+  public:
+    GenericSocketException () : AbstractServerException () {}
+};
+
+class GenericMemoryException : public AbstractServerException
+{
+  public:
+    GenericMemoryException () : AbstractServerException () {}
+};
+
+/*
+ * Exceptions
+ */
+class AbortedConnectionException : public GenericSocketException
+{
+  public:
+    AbortedConnectionException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class AddressException : public GenericSocketException
+{
+  public:
+    AddressException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class ArgumentListException : public GenericFileException
+{
+  public:
+    ArgumentListException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class BadDescriptorException : public GenericSocketException
+{
+  public:
+    BadDescriptorException () : GenericSocketException ()
+    {
+	  setLogLevel (MYSERVER_LOG_MSG_WARNING);
+	}
+};
+
+class BlockingException : public GenericFileException
+{
+  public:
+    BlockingException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class BufferOverflowException : public GenericMemoryException
+{
+  public:
+    BufferOverflowException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class BusyResourceException : public GenericFileException
+{
+  public:
+    BusyResourceException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class ByteException : public GenericMemoryException
+{
+  public:
+    ByteException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class CancelException : public GenericSocketException
+{
+  public:
+    CancelException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class ChannelOutOfRangeException : public GenericSocketException
+{
+  public:
+    ChannelOutOfRangeException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class ConnectionInProgressException : public GenericSocketException
+{
+  public:
+    ConnectionInProgressException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class DeadlockException : public GenericFileException
+{
+  public:
+    DeadlockException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class DestAddressException : public GenericSocketException
+{
+  public:
+    DestAddressException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class DeviceException : public GenericFileException
+{
+  public:
+    DeviceException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class DirectoryException : public GenericFileException
+{
+  public:
+    DirectoryException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class DiskQuotaException : public GenericMemoryException
+{
+  public:
+    DiskQuotaException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class ExecFormatException : public GenericMemoryException
+{
+  public:
+    ExecFormatException () : GenericMemoryException ()
+    {
+      setLogLevel(MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class FaultException : public GenericMemoryException
+{
+  public:
+    FaultException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class FileExistsException : public GenericFileException
+{
+  public:
+    FileExistsException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class FileNotFoundException : public GenericFileException
+{
+  public:
+    FileNotFoundException () : GenericFileException ()
+    {
+	  setLogLevel (MYSERVER_LOG_MSG_WARNING);
+	}
+};
+
+class FileTooLargeException : public GenericFileException
+{
+  public:
+    FileTooLargeException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class FileTooLongException : public GenericFileException
+{
+  public:
+    FileTooLongException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class FilesystemException : public GenericFileException
+{
+  public:
+    FilesystemException () : GenericFileException ()
+    {
+      setLogLevel(MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class FunctionException : public GenericMemoryException
+{
+  public:
+    FunctionException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class HaltException : public GenericMemoryException
+{
+  public:
+    HaltException () : GenericMemoryException ()
+    {
+      setLogLevel(MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class HostDownException : public GenericSocketException
+{
+  public:
+    HostDownException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class IOException : public GenericFileException
+{
+  public:
+    IOException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class IdentifierException : public GenericFileException
+{
+  public:
+    IdentifierException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class InvalidExchangeException : public GenericSocketException
+{
+  public:
+    InvalidExchangeException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class InvalidResourceException : public GenericFileException
+{
+  public:
+    InvalidResourceException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class KeyException : public GenericSocketException
+{
+  public:
+    KeyException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class LibraryException : public GenericFileException
+{
+  public:
+    LibraryException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class LinkException : public GenericFileException
+{
+  public:
+    LinkException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class MathException : public GenericMemoryException
+{
+  public:
+    MathException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class MediaException : public GenericFileException
+{
+  public:
+    MediaException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class MemoryOverflowException : public GenericMemoryException
+{
+  public:
+    MemoryOverflowException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class MessageException : public GenericSocketException
+{
+  public:
+    MessageException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class MultihopException : public GenericSocketException
+{
+  public:
+    MultihopException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class NamedFileException : public GenericFileException
+{
+  public:
+    NamedFileException () : GenericFileException ()
+    {
+	  setLogLevel (MYSERVER_LOG_MSG_WARNING);
+	}
+};
+
+class NetworkException : public GenericSocketException
+{
+  public:
+    NetworkException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class OverflowException : public GenericMemoryException
+{
+  public:
+    OverflowException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class PermissionDeniedException : public GenericFileException
+{
+  public:
+    PermissionDeniedException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class PipeException : public GenericFileException
+{
+  public:
+    PipeException () : GenericFileException ()
+    {
+	  setLogLevel (MYSERVER_LOG_MSG_ERROR);
+	}
+};
+
+class ProcessException : public GenericFileException
+{
+  public:
+    ProcessException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class ProgressException : public GenericSocketException
+{
+  public:
+    ProgressException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class ProtocolException : public GenericSocketException
+{
+  public:
+    ProtocolException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class ReadException : public GenericSocketException
+{
+  public:
+    ReadException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class RefusedConnectionException : public GenericSocketException
+{
+  public:
+    RefusedConnectionException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class RemoteIOException : public GenericSocketException
+{
+  public:
+    RemoteIOException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class RequestCodeException : public GenericSocketException
+{
+  public:
+    RequestCodeException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class RequestDescriptorException : public GenericSocketException
+{
+  public:
+    RequestDescriptorException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class ResetException : public GenericSocketException
+{
+  public:
+    ResetException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class SendException : public GenericSocketException
+{
+  public:
+    SendException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+class SlotException : public GenericMemoryException
+{
+  public:
+    SlotException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class SocketException : public GenericSocketException
+{
+  public:
+    SocketException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class StreamException : public GenericSocketException
+{
+  public:
+    StreamException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class TimerException : public GenericMemoryException
+{
+  public:
+    TimerException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_INFO);
+    }
+};
+
+class TooManyFileException : public GenericMemoryException
+{
+  public:
+    TooManyFileException () : GenericMemoryException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+/*
+ * Thrown if an unknown error occurs
+ */
+class UnknownException : public AbstractServerException
+{
+  public:
+    UnknownException () : AbstractServerException ()
+    {
+	  setLogLevel (MYSERVER_LOG_MSG_INFO);
+	}
+};
+
+class UnreachHostException : public GenericSocketException
+{
+  public:
+    UnreachHostException () : GenericSocketException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_ERROR);
+    }
+};
+
+class UserException : public GenericFileException
+{
+  public:
+    UserException () : GenericFileException ()
+    {
+      setLogLevel (MYSERVER_LOG_MSG_WARNING);
+    }
+};
+
+#endif
diff --git a/myserver/src/base/Makefile.am b/myserver/src/base/Makefile.am
index 020963d..5ca2c6e 100644
--- a/myserver/src/base/Makefile.am
+++ b/myserver/src/base/Makefile.am
@@ -19,7 +19,7 @@ lib_LIBRARIES = libbase.a
 libbase_a_SOURCES = utility.cpp
 SUBDIRS = base64 bitvec crypt dynamic_lib file files_cache read_directory \
 	  hash_map home_dir mem_buff multicast pipe process regex safetime slab \
-	  socket socket_pair ssl string sync thread xml unix_socket
+	  socket socket_pair ssl string sync thread xml unix_socket exceptions
 AM_CPPFLAGS = $(all_includes) -I$(top_builddir)/lib -I$(top_srcdir)/lib
 
 install:
diff --git a/myserver/src/base/exceptions/Makefile.am b/myserver/src/base/exceptions/Makefile.am
new file mode 100644
index 0000000..480589e
--- /dev/null
+++ b/myserver/src/base/exceptions/Makefile.am
@@ -0,0 +1,21 @@
+# GNU MyServer
+#
+# Copyright (C) 2002-2010 Free Software Foundation, Inc.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+AM_CXXFLAGS="-I$(top_srcdir)/lib"
+lib_LIBRARIES = libexceptions.a
+libexceptions_a_SOURCES = checked.cpp exceptions.cpp
+SUBDIRS =
+AM_CPPFLAGS = $(all_includes)
diff --git a/myserver/src/base/exceptions/checked.cpp b/myserver/src/base/exceptions/checked.cpp
new file mode 100644
index 0000000..7920169
--- /dev/null
+++ b/myserver/src/base/exceptions/checked.cpp
@@ -0,0 +1,704 @@
+/*
+MyServer
+Copyright (C) 2002, 2003, 2004, 2008, 2009, 2010 Free Software
+Foundation, Inc.
+Copyright (C) 2010, Lisa Vitolo (shainer)
+
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+#include <include/base/exceptions/checked.h>
+
+/*!
+ * Check if the last operation was successful
+ * \param x The function's return value
+ */
+static inline int checkError (int x)
+{
+  if (x < 0)
+  {
+    checked::raiseException ();
+  }
+
+  return x;
+}
+
+/*!
+ * \see checkError
+ */
+static inline const void *checkErrorNull (const void *x)
+{
+  if (x == NULL)
+  {
+    checked::raiseException ();
+  }
+  
+  return x;
+}
+
+namespace checked
+{
+  int accept (int fd, struct sockaddr *addr, socklen_t *addrlen)
+  {
+    return checkError (gnulib::accept (fd, addr, addrlen));
+  }
+  
+  int bind (int fd, const struct sockaddr *addr, socklen_t addrlen)
+  {
+    return checkError (gnulib::bind (fd, addr, addrlen));
+  }
+  
+  int chown (const char *file, uid_t uid, gid_t gid)
+  {
+    return checkError (gnulib::chown (file, uid, gid));
+  }
+  
+  int close (int fd)
+  {
+    return checkError (gnulib::close (fd));
+  }
+  
+  int closedir (DIR *dirp)
+  {
+    return checkError (gnulib::closedir (dirp));
+  }
+  
+  int connect (int fd, const struct sockaddr *addr, socklen_t addrlen)
+  {
+    return checkError (gnulib::connect (fd, addr, addrlen));
+  }
+  
+  int dup (int oldfd)
+  {
+    return checkError (gnulib::dup (oldfd));
+  }
+  
+  int dup2 (int oldfd, int newfd)
+  {
+    return checkError (gnulib::dup2 (oldfd, newfd));
+  }
+  
+  int fstat (int fd, struct stat *buf)
+  {
+    return checkError (gnulib::fstat (fd, buf));
+  }
+  
+  int fstatat (int fd, char const *name, struct stat *st, int flags)
+  {
+    return checkError (gnulib::fstatat (fd, name, st, flags));
+  }
+  
+  char * getcwd (char *buf, size_t size)
+  {
+    return (char *) checkErrorNull (gnulib::getcwd (buf, size));
+  }
+  
+  int gethostname (char *name, size_t len)
+  {
+    return checkError (gnulib::gethostname (name, len)); 
+  }
+  
+  int getsockname (int fd, struct sockaddr *addr, socklen_t *addrlen)
+  {
+    return checkError (gnulib::getsockname (fd, addr, addrlen));
+  }
+  
+  int gettimeofday (struct timeval *tv, struct timezone *tz)
+  {
+    return checkError (gnulib::gettimeofday (tv, tz));
+  }
+  
+  struct tm * gmtime_r (time_t const *__timer, struct tm * __result)
+  {
+    return (struct tm *) checkErrorNull (gnulib::gmtime_r (__timer, __result));
+  }
+  
+  int listen (int fd, int backlog)
+  {
+    return checkError (gnulib::listen (fd, backlog));
+  }
+  
+  struct tm * localtime_r (time_t const * __timer, struct tm *__result)
+  {
+    return (struct tm *) checkErrorNull (gnulib::localtime_r (__timer, __result));
+  }
+  
+  int lstat (const char *name, struct stat *buf)
+  {
+    return checkError (gnulib::lstat (name, buf));
+  }
+  
+  void * memchr (void const *__s, int __c, size_t __n)
+  {
+    return (void *) checkErrorNull (gnulib::memchr (__s, __c, __n));
+  }
+  
+  int mkdir (char const *name, mode_t mode)
+  {
+    return checkError (gnulib::mkdir (name, mode));
+  }
+  
+  time_t mktime (struct tm *__tp)
+  {
+    return checkError (gnulib::mktime (__tp));
+  }
+  
+  int open (const char *filename, int flags)
+  {
+    return checkError (gnulib::open (filename, flags, 0));
+  }
+  
+  DIR * opendir (const char *name)
+  {
+    return (DIR *) checkErrorNull (gnulib::opendir (name));
+  }
+  
+  ssize_t read(int fd, void *buf, size_t count)
+  {
+    return checkError (::read (fd, buf, count));
+  }
+  
+  void * realloc (void *ptr, size_t size)
+  {
+    return (void *) checkErrorNull (gnulib::realloc (ptr, size));
+  }
+  
+  ssize_t recv (int fd, void *buf, size_t len, int flags)
+  {
+    return checkError (gnulib::recv (fd, buf, len, flags));
+  }
+  
+  int remove (const char *name)
+  {
+    return checkError (gnulib::remove (name));
+  }
+  
+  int rename (const char *old_filename, const char *new_filename)
+  {
+    return checkError (gnulib::rename (old_filename, new_filename));
+  }
+  
+  int rmdir (char const *name)
+  {
+    return checkError (gnulib::rmdir (name));
+  }
+  
+  int select (int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout)
+  {
+    return checkError (gnulib::select (nfds, readfds, writefds, exceptfds, timeout));
+  }
+  
+  ssize_t send (int fd, const void *buf, size_t len, int flags)
+  {
+    return checkError (gnulib::send (fd, buf, len, flags));
+  }
+  
+  int setsockopt (int fd, int level, int optname, const void * optval, socklen_t optlen)
+  {
+    return checkError (gnulib::setsockopt (fd, level, optname, optval, optlen));
+  }
+  
+  int shutdown (int fd, int how)
+  {
+    return checkError (gnulib::shutdown (fd, how));
+  }
+  
+  int sigaction (int signum, const struct sigaction *act, struct sigaction *oldact)
+  {
+    return checkError (gnulib::sigaction (signum, act, oldact));
+  }
+  
+  int sigaddset (sigset_t *set, int signum)
+  {
+    return checkError (gnulib::sigaddset (set, signum));
+  }
+  
+  int sigemptyset (sigset_t *set)
+  {
+    return checkError (gnulib::sigemptyset (set));
+  }
+  
+  int sigprocmask (int how, const sigset_t *set, sigset_t *oldset)
+  {
+    return checkError (gnulib::sigprocmask (how, set, oldset));
+  }
+  
+  int socket (int domain, int type, int protocol)
+  {
+    return checkError (gnulib::socket (domain, type, protocol));
+  }
+  
+  char * strdup (char const *__s)
+  {
+    return (char *) checkErrorNull (gnulib::strdup (__s));
+  }
+  
+  int unlink (char const *file)
+  {
+    return checkError (gnulib::unlink (file));
+  }
+  
+  ssize_t write (int fd, const void *buf, size_t count)
+  {
+    return checkError (gnulib::write (fd, buf, count));
+  }
+  
+  /*
+   * Maps POSIX errors to exceptions
+   */
+  void raiseException ()
+  {
+    switch(errno)
+    {
+      case E2BIG:
+        throw ArgumentListException ();
+        break;
+  
+      case EACCES:
+        throw PermissionDeniedException ();
+        break;
+  
+      case EADDRINUSE:
+        throw AddressException ();
+        break;
+  
+      case EADDRNOTAVAIL:
+        throw AddressException ();
+        break;
+  
+      case EAFNOSUPPORT:
+        throw ProtocolException ();
+        break;
+  
+      case EAGAIN:
+        throw InvalidResourceException ();
+        break;
+  
+      case EALREADY:
+        throw ProgressException ();
+        break;
+    
+      case EBADE:
+        throw InvalidExchangeException ();
+        break;
+  
+      case EBADF:
+        throw BadDescriptorException ();
+        break;
+  
+      case EBADFD:
+        throw BadDescriptorException ();
+        break;
+  
+      case EBADMSG:
+        throw MessageException ();
+        break;
+  
+      case EBADR:
+        throw RequestCodeException ();
+        break;
+    
+      case EBADRQC:
+        throw RequestCodeException ();
+        break;
+  
+      case EBADSLT:
+        throw SlotException ();
+        break;
+  
+      case EBUSY:
+        throw BusyResourceException ();
+        break;
+  
+      case ECANCELED:
+        throw CancelException ();
+        break;
+  
+      case ECHILD:
+        throw ProcessException ();
+        break;
+  
+      case ECHRNG:
+        throw ChannelOutOfRangeException ();
+        break;
+  
+      case ECOMM:
+        throw SendException ();
+        break;
+  
+      case ECONNABORTED:
+        throw AbortedConnectionException ();
+        break;
+  
+      case ECONNREFUSED:
+        throw RefusedConnectionException ();
+        break;
+  
+      case ECONNRESET:
+        throw ResetException ();
+        break;
+  
+      case EDEADLK:
+        throw DeadlockException ();
+        break;
+  
+      case EDESTADDRREQ:
+        throw AddressException ();
+        break;
+  
+      case EDOM:
+        throw MathException ();
+        break;
+  
+      case EDQUOT:
+        throw DiskQuotaException ();
+        break;
+  
+      case EEXIST:
+        throw FileExistsException ();
+        break;
+  
+      case EFAULT:
+        throw FaultException ();
+        break;
+  
+      case EFBIG:
+        throw FileTooLargeException ();
+        break;
+  
+      case EHOSTDOWN:
+        throw HostDownException ();
+        break;
+  
+      case EHOSTUNREACH:
+        throw UnreachHostException ();
+        break;
+  
+      case EIDRM:
+        throw IdentifierException ();
+        break;
+  
+      case EILSEQ:
+        throw ByteException ();
+        break;
+    
+      case EINPROGRESS:
+        throw ProgressException ();
+        break;
+  
+      case EINTR:
+        throw FunctionException ();
+        break;
+  
+      case EINVAL:
+        throw ArgumentListException ();
+        break;
+  
+      case EIO:
+        throw IOException ();
+        break;
+  
+      case EISCONN:
+        throw SocketException ();
+        break;
+  
+      case EISDIR:
+        throw DirectoryException ();
+        break;
+  
+      case EISNAM:
+        throw NamedFileException ();
+        break;
+  
+      case EKEYEXPIRED:
+        throw KeyException ();
+        break;
+  
+      case EKEYREJECTED:
+        throw KeyException ();
+        break;
+  
+      case EKEYREVOKED:
+        throw KeyException ();
+        break;
+  
+      case EL2HLT:
+        throw HaltException ();
+        break;
+  
+      case EL2NSYNC:
+        throw HaltException ();
+        break;
+  
+      case EL3HLT:
+        throw HaltException ();
+        break;
+  
+      case ELIBACC:
+        throw LibraryException ();
+        break;
+  
+      case ELIBBAD:
+        throw LibraryException ();
+        break;
+  
+      case ELIBMAX:
+        throw LibraryException ();
+        break;
+  
+      case ELIBSCN:
+        throw LibraryException ();
+        break;
+  
+      case ELIBEXEC:
+        throw LibraryException ();
+        break;
+  
+      case ELOOP:
+        throw LinkException ();
+        break;
+  
+      case EMEDIUMTYPE:
+        throw MediaException ();
+        break;
+  
+      case EMFILE:
+        throw TooManyFileException ();
+        break;
+  
+      case EMLINK:
+        throw LinkException ();
+        break;
+  
+      case EMSGSIZE:
+        throw MessageException ();
+        break;
+  
+      case EMULTIHOP:
+        throw MultihopException ();
+        break;
+  
+      case ENAMETOOLONG:
+        throw FileTooLongException ();
+        break;
+  
+      case ENETRESET:
+        throw NetworkException ();
+        break;
+  
+      case ENETUNREACH:
+        throw NetworkException ();
+        break;
+  
+      case ENFILE:
+        throw FilesystemException ();
+        break;
+  
+      case ENOBUFS:
+        throw BufferOverflowException ();
+        break;
+  
+      case ENODATA:
+        throw StreamException ();
+        break;
+  
+      case ENODEV:
+        throw DeviceException ();
+        break;
+  
+      case ENOENT:
+        throw FileNotFoundException ();
+        break;
+  
+      case ENOEXEC:
+        throw ExecFormatException ();
+        break;
+  
+      case ENOKEY:
+        throw KeyException ();
+        break;
+  
+      case ENOLINK:
+        throw LinkException ();
+        break;
+  
+      case ENOMEDIUM:
+        throw MediaException ();
+        break;
+  
+      case ENOMEM:
+        throw MemoryOverflowException ();
+        break;
+  
+      case ENOMSG:
+        throw MessageException ();
+        break;
+  
+      case ENONET:
+        throw NetworkException ();
+        break;
+  
+      case ENOSPC:
+        throw OverflowException ();
+        break;
+  
+      case ENOSR:
+        throw StreamException ();
+        break;
+  
+      case ENOSTR:
+        throw StreamException ();
+        break;
+  
+      case ENOSYS:
+        throw FunctionException ();
+        break;
+  
+      case ENOTBLK:
+        throw BlockingException ();
+        break;
+  
+      case ENOTCONN:
+        throw SocketException ();
+        break;
+  
+      case ENOTDIR:
+        throw DirectoryException ();
+        break;
+  
+      case ENOTEMPTY:
+        throw DirectoryException ();
+        break;
+  
+      case ENOTSOCK:
+        throw SocketException ();
+        break;
+  
+      case ENOTTY:
+        throw IOException ();
+        break;
+  
+      case ENOTUNIQ:
+        throw NetworkException ();
+        break;
+  
+      case ENXIO:
+        throw DeviceException ();
+        break;
+  
+      case EOVERFLOW:
+        throw OverflowException ();
+        break;
+  
+      case EPERM:
+        throw PermissionDeniedException ();
+        break;
+  
+      case EPFNOSUPPORT:
+        throw ProtocolException ();
+        break;
+  
+      case EPIPE:
+        throw PipeException ();
+        break;
+  
+      case EPROTO:
+        throw ProtocolException ();
+        break;
+  
+      case EPROTONOSUPPORT:
+        throw ProtocolException ();
+        break;
+  
+      case EPROTOTYPE:
+        throw ProtocolException ();
+        break;
+  
+      case ERANGE:
+        throw OverflowException ();
+        break;
+  
+      case EREMCHG:
+        throw AddressException ();
+        break;
+  
+      case EREMOTEIO:
+        throw IOException ();
+        break;
+  
+      case ERESTART:
+        throw FunctionException ();
+        break;
+  
+      case EROFS:
+        throw FilesystemException ();
+        break;
+  
+      case ESHUTDOWN:
+        throw SendException ();
+        break;
+    
+      case ESPIPE:
+        throw PipeException ();
+        break;
+  
+      case ESOCKTNOSUPPORT:
+        throw SocketException ();
+        break;
+  
+      case ESRCH:
+        throw ProcessException ();
+        break;
+    
+      case ESTALE:
+        throw GenericFileException ();
+        break;
+  
+      case ESTRPIPE:
+        throw PipeException ();
+        break;
+  
+      case ETIME:
+        throw TimerException ();
+        break;
+  
+      case ETIMEDOUT:
+        throw TimerException ();
+        break;
+  
+      case ETXTBSY:
+        throw BusyResourceException ();
+        break;
+  
+      case EUNATCH:
+        throw ProtocolException ();
+        break;
+  
+      case EUSERS:
+        throw UserException ();
+        break;
+  
+      case EXDEV:
+        throw LinkException ();
+        break;
+  
+      case EXFULL:
+        throw InvalidExchangeException ();
+        break;
+  
+      default:
+        throw UnknownException ();
+        break;
+    }
+  }
+}
diff --git a/myserver/src/base/exceptions/exceptions.cpp b/myserver/src/base/exceptions/exceptions.cpp
new file mode 100644
index 0000000..1605f03
--- /dev/null
+++ b/myserver/src/base/exceptions/exceptions.cpp
@@ -0,0 +1,21 @@
+/*
+MyServer
+Copyright (C) 2002, 2003, 2004, 2008, 2009, 2010 Free Software
+Foundation, Inc.
+Copyright (C) 2010, Lisa Vitolo (shainer)
+
+See include/base/exceptions/exceptions.h
+
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
-- 
1.7.0

Reply via email to