- Main Page
- Classes
- Files

- File List

# include/pion/error.hpp

    00001 // ---------------------------------------------------------------------
    00002 // pion:  a Boost C++ framework for building lightweight HTTP interfaces
    00003 // ---------------------------------------------------------------------
    00004 // Copyright (C) 2007-2012 Cloudmeter, Inc.  (http://www.cloudmeter.com)
    00005 //
    00006 // Distributed under the Boost Software License, Version 1.0.
    00007 // See http://www.boost.org/LICENSE_1_0.txt
    00008 //
    00009
    00010 #ifndef __PION_ERROR_HEADER__
    00011 #define __PION_ERROR_HEADER__
    00012
    00013 #include <string>
    00014 #include <sstream>
    00015 #include <exception>
    00016 #include <boost/version.hpp>
    00017 #include <boost/throw_exception.hpp>
    00018 #include <boost/exception/exception.hpp>
    00019 #include <boost/exception/info.hpp>
    00020 #include <boost/exception/error_info.hpp>
    00021 #include <boost/exception/get_error_info.hpp>
    00022 #include <pion/config.hpp>
    00023
    00024
    00025 namespace pion {    // begin namespace pion
    00026
    00027     //
    00028     // exception: simple exception class for pion errors that generates what()
    00029     // strings with more descriptive messages and optionally arguments as well
    00030     //
    00031     class exception
    00032         : public virtual std::exception, public virtual boost::exception
    00033     {
    00034     public:
    00035         exception() {}
    00036         exception(const std::string& msg) : m_what_msg(msg) {}
    00037         exception(const char * const msg) : m_what_msg(msg) {}
    00038         virtual ~exception() throw () {}
    00039         virtual const char* what() const throw() {
    00040             if (m_what_msg.empty()) update_what_msg();
    00041             return m_what_msg.c_str();
    00042         }
    00043     protected:
    00044         inline void set_what_msg(const char * const msg = NULL, const std::string * const arg1 = NULL, const std::string * const arg2 = NULL, const std::string * const arg3 = NULL) const {
    00045             std::ostringstream tmp;
    00046 #if BOOST_VERSION >= 104700
    00047             tmp << ( msg ? msg : boost::units::detail::demangle(BOOST_EXCEPTION_DYNAMIC_TYPEID(*this).type_->name()) );
    00048 #else
    00049             tmp << ( msg ? msg : boost::units::detail::demangle(BOOST_EXCEPTION_DYNAMIC_TYPEID(*this).type_.name()) );
    00050 #endif
    00051             if (arg1 || arg2 || arg3) tmp << ':';
    00052             if (arg1) tmp << ' ' << *arg1;
    00053             if (arg2) tmp << ' ' << *arg2;
    00054             if (arg3) tmp << ' ' << *arg3;
    00055             m_what_msg = tmp.str();
    00056         }
    00057         virtual void update_what_msg() const { set_what_msg(); }
    00058         mutable std::string m_what_msg;
    00059     };
    00060
    00061
    00068     template <class T>
    00069     static inline std::string
    00070     diagnostic_information( T const & e )
    00071     {
    00072         boost::exception const * const be = dynamic_cast<const boost::exception*>(&e);
    00073         std::exception const * const se = dynamic_cast<const std::exception*>(&e);
    00074         std::ostringstream tmp;
    00075         if (se) {
    00076             tmp << se->what();
    00077         } else {
    00078 #if BOOST_VERSION >= 104700
    00079             tmp << boost::units::detail::demangle(BOOST_EXCEPTION_DYNAMIC_TYPEID(e).type_->name());
    00080 #else
    00081             tmp << boost::units::detail::demangle(BOOST_EXCEPTION_DYNAMIC_TYPEID(e).type_.name());
    00082 #endif
    00083         }
    00084         if (be) {
    00085             //char const * const * fn=boost::get_error_info<boost::throw_function>(*be);
    00086             //if (fn) tmp << " at " << *fn;
    00087             char const * const * f=boost::get_error_info<boost::throw_file>(*be);
    00088             if (f) {
    00089                 tmp << " [" << *f;
    00090                 if (int const * l=boost::get_error_info<boost::throw_line>(*be))
    00091                     tmp << ':' << *l;
    00092                 tmp << "]";
    00093             }
    00094         }
    00095         return tmp.str();
    00096     }
    00097
    00098
    00099     namespace error {    // begin namespace error
    00100
    00101         //
    00102         // pion error info types
    00103         //
    00104
    00106         typedef boost::error_info<struct errinfo_arg_name_,std::string> errinfo_message;
    00107
    00109         typedef boost::error_info<struct errinfo_arg_name_,std::string> errinfo_arg_name;
    00110
    00112         typedef boost::error_info<struct errinfo_file_name_,std::string> errinfo_file_name;
    00113
    00115         typedef boost::error_info<struct errinfo_dir_name_,std::string> errinfo_dir_name;
    00116
    00118         typedef boost::error_info<struct errinfo_plugin_name_,std::string> errinfo_plugin_name;
    00119
    00121         typedef boost::error_info<struct errinfo_dir_name_,std::string> errinfo_symbol_name;
    00122
    00123
    00124         //
    00125         // pion exception types
    00126         //
    00127
    00129         class bad_arg : public pion::exception {
    00130             virtual void update_what_msg() const {
    00131                 set_what_msg("bad argument", boost::get_error_info<errinfo_arg_name>(*this));
    00132             }
    00133         };
    00134
    00136         class bad_config : public pion::exception {
    00137             virtual void update_what_msg() const {
    00138                 set_what_msg("config parser error", boost::get_error_info<errinfo_file_name>(*this));
    00139             }
    00140         };
    00141
    00143         class open_file : public pion::exception {
    00144             virtual void update_what_msg() const {
    00145                 set_what_msg("unable to open file", boost::get_error_info<errinfo_file_name>(*this));
    00146             }
    00147         };
    00148
    00150         class open_plugin : public pion::exception {
    00151             virtual void update_what_msg() const {
    00152                 set_what_msg("unable to open plugin", boost::get_error_info<errinfo_plugin_name>(*this));
    00153             }
    00154         };
    00155
    00157         class read_file : public pion::exception {
    00158             virtual void update_what_msg() const {
    00159                 set_what_msg("unable to read file", boost::get_error_info<errinfo_file_name>(*this));
    00160             }
    00161         };
    00162
    00164         class file_not_found : public pion::exception {
    00165             virtual void update_what_msg() const {
    00166                 set_what_msg("file not found", boost::get_error_info<errinfo_file_name>(*this));
    00167             }
    00168         };
    00169
    00171         class directory_not_found : public pion::exception {
    00172             virtual void update_what_msg() const {
    00173                 set_what_msg("directory not found", boost::get_error_info<errinfo_dir_name>(*this));
    00174             }
    00175         };
    00176
    00178         class plugin_not_found : public pion::exception {
    00179             virtual void update_what_msg() const {
    00180                 set_what_msg("plugin not found", boost::get_error_info<errinfo_plugin_name>(*this));
    00181             }
    00182         };
    00183
    00185         class duplicate_plugin : public pion::exception {
    00186             virtual void update_what_msg() const {
    00187                 set_what_msg("duplicate plugin", boost::get_error_info<errinfo_plugin_name>(*this));
    00188             }
    00189         };
    00190
    00192         class plugin_missing_symbol : public pion::exception {
    00193             virtual void update_what_msg() const {
    00194                 set_what_msg("missing plugin symbol", boost::get_error_info<errinfo_symbol_name>(*this));
    00195             }
    00196         };
    00197
    00199         class plugin_undefined : public pion::exception {
    00200             virtual void update_what_msg() const {
    00201                 set_what_msg("plugin has undefined state");
    00202             }
    00203         };
    00204
    00206         class bad_password_hash : public pion::exception {
    00207             virtual void update_what_msg() const {
    00208                 set_what_msg("bad password hash");
    00209             }
    00210         };
    00211
    00212     }   // end namespace error
    00213
    00214 }   // end namespace pion
    00215
    00216 #endif