Lunchbox  1.4.0
debug.h
00001 
00002 /* Copyright (c) 2007-2012, Stefan Eilemann <eile@equalizergraphics.com> 
00003  *
00004  * This library is free software; you can redistribute it and/or modify it under
00005  * the terms of the GNU Lesser General Public License version 2.1 as published
00006  * by the Free Software Foundation.
00007  *  
00008  * This library is distributed in the hope that it will be useful, but WITHOUT
00009  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
00010  * FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
00011  * details.
00012  * 
00013  * You should have received a copy of the GNU Lesser General Public License
00014  * along with this library; if not, write to the Free Software Foundation, Inc.,
00015  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
00016  */
00017 
00018 #ifndef LUNCHBOX_DEBUG_H
00019 #define LUNCHBOX_DEBUG_H
00020 
00021 #include <lunchbox/defines.h>
00022 #include <lunchbox/log.h>
00023 
00024 #include <typeinfo>
00025 
00026 // assertions
00027 // #define LB_RELEASE_ASSERT
00028 
00029 namespace lunchbox
00030 {
00035 LUNCHBOX_API void abort();
00036 
00041 LUNCHBOX_API void checkHeap();
00042 
00049 LUNCHBOX_API std::ostream& sysError( std::ostream& os );
00050 
00057 LUNCHBOX_API std::ostream& backtrace( std::ostream& os );
00058 
00059 LUNCHBOX_API std::string demangleTypeID( const char* mangled ); 
00060 
00062 template< class T > inline std::string className( T* object )
00063     { return demangleTypeID( typeid( *object ).name( )); }
00064 
00065 }
00066 
00067 #ifdef NDEBUG
00068 #  ifdef LB_RELEASE_ASSERT
00069 #    define LBASSERT(x)                                                 \
00070     {                                                                   \
00071         if( !(x) )                                                      \
00072             LBERROR << "##### Assert: " << #x << " #####" << std::endl  \
00073                     << lunchbox::forceFlush;                            \
00074         lunchbox::checkHeap();                                          \
00075     }
00076 #    define LBASSERTINFO(x, info)                                       \
00077     {                                                                   \
00078         if( !(x) )                                                      \
00079             LBERROR << "##### Assert: " << #x << " [" << info << "] #####" \
00080                     << std::endl << lunchbox::forceFlush;               \
00081         lunchbox::checkHeap();                                          \
00082     }
00083 #    define LBCHECK(x) { const bool eqOk = x; LBASSERTINFO( eqOk, #x ) }
00084 #  else
00085 #    define LBASSERT(x)
00086 #    define LBASSERTINFO(x, info)
00087 #    define LBCHECK(x) { x; }
00088 #  endif
00089 
00090 #  define LBUNIMPLEMENTED { LBERROR << "Unimplemented code" << std::endl \
00091                                     << lunchbox::forceFlush; }
00092 #  define LBUNREACHABLE   { LBERROR << "Unreachable code" << std::endl  \
00093                                     << lunchbox::forceFlush; }
00094 #  define LBDONTCALL                                                    \
00095     { LBERROR << "Code is not supposed to be called in this context"    \
00096               << std::endl << lunchbox::forceFlush; }
00097 #  define LBABORT( info ) {                                         \
00098         LBERROR << "##### Abort: " << info << " #####" << std::endl \
00099                 << lunchbox::forceFlush; }
00100 
00101 #else // NDEBUG
00102 
00103 #  define LBASSERT(x)                                                   \
00104     {                                                                   \
00105         if( !(x) )                                                      \
00106         {                                                               \
00107             LBERROR << "Assert: " << #x << " ";                         \
00108             lunchbox::abort();                                          \
00109         }                                                               \
00110         lunchbox::checkHeap();                                          \
00111     } 
00112 #  define LBASSERTINFO(x, info)                                         \
00113     {                                                                   \
00114         if( !(x) )                                                      \
00115         {                                                               \
00116             LBERROR << "Assert: " << #x << " [" << info << "] ";        \
00117             lunchbox::abort();                                          \
00118         }                                                               \
00119         lunchbox::checkHeap();                                          \
00120     }
00121 
00122 #  define LBUNIMPLEMENTED                                               \
00123     { LBERROR << "Unimplemented code in " << lunchbox::className( this ) \
00124               << " ";                                                   \
00125         lunchbox::abort(); }
00126 #  define LBUNREACHABLE                                                 \
00127     { LBERROR << "Unreachable code in " << lunchbox::className( this )  \
00128               << " ";                                                   \
00129         lunchbox::abort(); }
00130 #  define LBDONTCALL                                                    \
00131     { LBERROR << "Code is not supposed to be called in this context, type " \
00132               << lunchbox::className( this ) << " " ;                   \
00133         lunchbox::abort(); }
00134 
00135 #  define LBCHECK(x) { const bool eqOk = x; LBASSERTINFO( eqOk, #x ) }
00136 #  define LBABORT( info ) {                                             \
00137         LBERROR << "Abort: " << info;                                   \
00138         lunchbox::abort(); }
00139 #endif // NDEBUG
00140 
00141 #define LBSAFECAST( to, in ) static_cast< to >( in );   \
00142     LBASSERT( in == 0 || dynamic_cast< to >( static_cast< to >( in )))
00143 
00144 #endif //LUNCHBOX_DEBUG_H