myexcept.h
Go to the documentation of this file.
00001 
00002 
00003 
00012 
00013 
00014 // A set of classes to simulate exceptions in C++
00015 //
00016 //   Partially copied from Carlos Vidal s article in the C users  journal
00017 //   September 1992, pp 19-28
00018 //
00019 //   Operations defined
00020 //      Try {     }
00021 //      Throw ( exception object )
00022 //      ReThrow
00023 //      Catch ( exception class ) {      }
00024 //      CatchAll {      }
00025 //      CatchAndThrow
00026 //
00027 //   All catch lists must end with a CatchAll or CatchAndThrow statement
00028 //   but not both.
00029 //
00030 //   When exceptions are finally implemented replace Try, Throw(E), Rethrow,
00031 //   Catch, CatchAll, CatchAndThrow by try, throw E, throw, catch,
00032 //   catch(...), and {}.
00033 //
00034 //   All exception classes must be derived from BaseException, have no
00035 //   non-static variables and must include the statement
00036 //
00037 //      static unsigned long Select;
00038 //
00039 //   Any constructor in one of these exception classes must include
00040 //
00041 //      Select = BaseException::Select;
00042 //
00043 //   For each exceptions class, EX_1, some .cpp file must include
00044 //
00045 //      unsigned long EX_1::Select;
00046 //
00047 
00048 
00049 #ifndef EXCEPTION_LIB
00050 #define EXCEPTION_LIB
00051 
00052 #include "include.h"
00053 
00054 #ifdef use_namespace
00055 namespace RBD_COMMON {
00056 #endif
00057 
00058 
00059 void Terminate();
00060 
00061 
00062 //********** classes for setting up exceptions and reporting ************//
00063 
00064 class BaseException;
00065 
00066 class Tracer                             // linked list showing how
00067 {                                        // we got here
00068    const char* entry;
00069    Tracer* previous;
00070 public:
00071    Tracer(const char*);
00072    ~Tracer();
00073    void ReName(const char*);
00074    static void PrintTrace();             // for printing trace
00075    static void AddTrace();               // insert trace in exception record
00076    static Tracer* last;                  // points to Tracer list
00077    friend class BaseException;
00078 };
00079 
00080 
00081 class BaseException                          // The base exception class
00082 {
00083 protected:
00084    static char* what_error;              // error message
00085    static int SoFar;                     // no. characters already entered
00086    static int LastOne;                   // last location in error buffer
00087 public:
00088    static void AddMessage(const char* a_what);
00089                                          // messages about exception
00090    static void AddInt(int value);        // integer to error message
00091    static unsigned long Select;          // for identifying exception
00092    BaseException(const char* a_what = 0);
00093    static const char* what() { return what_error; }
00094                                          // for getting error message
00095 };
00096 
00097 #ifdef TypeDefException
00098 typedef BaseException Exception;        // for compatibility with my older libraries
00099 #endif
00100 
00101 inline Tracer::Tracer(const char* e)
00102    : entry(e), previous(last) { last = this; }
00103 
00104 inline Tracer::~Tracer() { last = previous; }
00105 
00106 inline void Tracer::ReName(const char* e) { entry=e; }
00107 
00108 #ifdef SimulateExceptions                // SimulateExceptions
00109 
00110 #include <setjmp.h>
00111 
00112 
00113 //************* the definitions of Try, Throw and Catch *****************//
00114 
00115 
00116 class JumpItem;
00117 class Janitor;
00118 
00119 class JumpBase         // pointer to a linked list of jmp_buf s
00120 {
00121 public:
00122    static JumpItem *jl;
00123    static jmp_buf env;
00124 };
00125 
00126 class JumpItem         // an item in a linked list of jmp_buf s
00127 {
00128 public:
00129    JumpItem *ji;
00130    jmp_buf env;
00131    Tracer* trace;                     // to keep check on Tracer items
00132    Janitor* janitor;                  // list of items for cleanup
00133    JumpItem() : ji(JumpBase::jl), trace(0), janitor(0)
00134       { JumpBase::jl = this; }
00135    ~JumpItem() { JumpBase::jl = ji; }
00136 };
00137 
00138 void Throw();
00139 
00140 inline void Throw(const BaseException&) { Throw(); }
00141 
00142 #define Try                                             \
00143    if (!setjmp( JumpBase::jl->env )) {                  \
00144    JumpBase::jl->trace = Tracer::last;               \
00145    JumpItem JI387256156;
00146 
00147 #define ReThrow Throw()
00148 
00149 #define Catch(EXCEPTION)                                \
00150    } else if (BaseException::Select == EXCEPTION::Select) {
00151 
00152 #define CatchAll } else
00153 
00154 #define CatchAndThrow  } else Throw();
00155 
00156 
00157 //****************** cleanup heap following Throw ***********************//
00158 
00159 class Janitor
00160 {
00161 protected:
00162    static bool do_not_link;                  // set when new is called
00163    bool OnStack;                             // false if created by new
00164 public:
00165    Janitor* NextJanitor;
00166    virtual void CleanUp() {}
00167    Janitor();
00168    virtual ~Janitor();
00169 };
00170 
00171 
00172 // The tiresome old trick for initializing the Janitor class
00173 // this is needed for classes derived from Janitor which have objects
00174 // declared globally
00175 
00176 class JanitorInitializer
00177 {
00178 public:
00179    JanitorInitializer();
00180 private:
00181    static int ref_count;
00182 };
00183 
00184 static JanitorInitializer JanInit;
00185 
00186 #endif                                // end of SimulateExceptions
00187 
00188 #ifdef UseExceptions
00189 
00190 #define Try try
00191 #define Throw(E) throw E
00192 #define ReThrow throw
00193 #define Catch catch
00194 #define CatchAll catch(...)
00195 #define CatchAndThrow {}
00196 
00197 #endif                                // end of UseExceptions
00198 
00199 
00200 #ifdef DisableExceptions              // Disable exceptions
00201 
00202 #define Try {
00203 #define ReThrow Throw()
00204 #define Catch(EXCEPTION) } if (false) {
00205 #define CatchAll } if (false)
00206 #define CatchAndThrow }
00207 
00208 inline void Throw() { Terminate(); }
00209 inline void Throw(const BaseException&) { Terminate(); }
00210 
00211 
00212 #endif                                // end of DisableExceptions
00213 
00214 #ifndef SimulateExceptions            // ! SimulateExceptions
00215 
00216 class Janitor                         // a dummy version
00217 {
00218 public:
00219    virtual void CleanUp() {}
00220    Janitor() {}
00221    virtual ~Janitor() {}
00222 };
00223 
00224 #endif                                // end of ! SimulateExceptions
00225 
00226 
00227 //******************** FREE_CHECK and NEW_DELETE ***********************//
00228 
00229 #ifdef DO_FREE_CHECK                          // DO_FREE_CHECK
00230 // Routines for tracing whether new and delete calls are balanced
00231 
00232 class FreeCheck;
00233 
00234 class FreeCheckLink
00235 {
00236 protected:
00237    FreeCheckLink* next;
00238    void* ClassStore;
00239    FreeCheckLink();
00240    virtual void Report()=0;                   // print details of link
00241    friend class FreeCheck;
00242 };
00243 
00244 class FCLClass : public FreeCheckLink         // for registering objects
00245 {
00246    char* ClassName;
00247    FCLClass(void* t, char* name);
00248    void Report();
00249    friend class FreeCheck;
00250 };
00251 
00252 class FCLRealArray : public FreeCheckLink     // for registering real arrays
00253 {
00254    char* Operation;
00255    int size;
00256    FCLRealArray(void* t, char* o, int s);
00257    void Report();
00258    friend class FreeCheck;
00259 };
00260 
00261 class FCLIntArray : public FreeCheckLink     // for registering int arrays
00262 {
00263    char* Operation;
00264    int size;
00265    FCLIntArray(void* t, char* o, int s);
00266    void Report();
00267    friend class FreeCheck;
00268 };
00269 
00270 
00271 class FreeCheck
00272 {
00273    static FreeCheckLink* next;
00274    static int BadDelete;
00275 public:
00276    static void Register(void*, char*);
00277    static void DeRegister(void*, char*);
00278    static void RegisterR(void*, char*, int);
00279    static void DeRegisterR(void*, char*, int);
00280    static void RegisterI(void*, char*, int);
00281    static void DeRegisterI(void*, char*, int);
00282    static void Status();
00283    friend class FreeCheckLink;
00284    friend class FCLClass;
00285    friend class FCLRealArray;
00286    friend class FCLIntArray;
00287 };
00288 
00289 #define FREE_CHECK(Class)                                                  \
00290 public:                                                                    \
00291    void* operator new(size_t size)                                         \
00292    {                                                                       \
00293       void* t = ::operator new(size); FreeCheck::Register(t,#Class);       \
00294       return t;                                                            \
00295    }                                                                       \
00296    void operator delete(void* t)                                           \
00297    { FreeCheck::DeRegister(t,#Class); ::operator delete(t); }
00298 
00299 
00300 #ifdef SimulateExceptions         // SimulateExceptions
00301 
00302 #define NEW_DELETE(Class)                                                  \
00303 public:                                                                    \
00304    void* operator new(size_t size)                                         \
00305    {                                                                       \
00306       do_not_link=true;                                                    \
00307       void* t = ::operator new(size); FreeCheck::Register(t,#Class);       \
00308       return t;                                                            \
00309    }                                                                       \
00310    void operator delete(void* t)                                           \
00311    { FreeCheck::DeRegister(t,#Class); ::operator delete(t); }
00312 
00313 
00314 #endif                           // end of SimulateExceptions
00315 
00316 
00317 #define MONITOR_REAL_NEW(Operation, Size, Pointer)                         \
00318         FreeCheck::RegisterR(Pointer, Operation, Size);
00319 #define MONITOR_INT_NEW(Operation, Size, Pointer)                          \
00320         FreeCheck::RegisterI(Pointer, Operation, Size);
00321 #define MONITOR_REAL_DELETE(Operation, Size, Pointer)                      \
00322         FreeCheck::DeRegisterR(Pointer, Operation, Size);
00323 #define MONITOR_INT_DELETE(Operation, Size, Pointer)                       \
00324         FreeCheck::DeRegisterI(Pointer, Operation, Size);
00325 
00326 #else                            // DO_FREE_CHECK not defined
00327 
00328 #define FREE_CHECK(Class) public:
00329 #define MONITOR_REAL_NEW(Operation, Size, Pointer) {}
00330 #define MONITOR_INT_NEW(Operation, Size, Pointer) {}
00331 #define MONITOR_REAL_DELETE(Operation, Size, Pointer) {}
00332 #define MONITOR_INT_DELETE(Operation, Size, Pointer) {}
00333 
00334 
00335 #ifdef SimulateExceptions         // SimulateExceptions
00336 
00337 
00338 #define NEW_DELETE(Class)                                                  \
00339 public:                                                                    \
00340         void* operator new(size_t size)                                    \
00341         { do_not_link=true; void* t = ::operator new(size); return t; }    \
00342         void operator delete(void* t) { ::operator delete(t); }
00343 
00344 #endif                            // end of SimulateExceptions
00345 
00346 #endif                            // end of ! DO_FREE_CHECK
00347 
00348 #ifndef SimulateExceptions        // ! SimulateExceptions
00349 
00350 #define NEW_DELETE(Class) FREE_CHECK(Class)
00351 
00352 #endif                            // end of ! SimulateExceptions
00353 
00354 
00355 //********************* derived exceptions ******************************//
00356 
00357 class Logic_error : public BaseException
00358 {
00359 public:
00360    static unsigned long Select;
00361    Logic_error(const char* a_what = 0);
00362 };
00363 
00364 class Runtime_error : public BaseException
00365 {
00366 public:
00367    static unsigned long Select;
00368    Runtime_error(const char* a_what = 0);
00369 };
00370 
00371 class Domain_error : public Logic_error
00372 {
00373 public:
00374    static unsigned long Select;
00375    Domain_error(const char* a_what = 0);
00376 };
00377 
00378 class Invalid_argument : public Logic_error
00379 {
00380 public:
00381    static unsigned long Select;
00382    Invalid_argument(const char* a_what = 0);
00383 };
00384 
00385 class Length_error : public Logic_error
00386 {
00387 public:
00388    static unsigned long Select;
00389    Length_error(const char* a_what = 0);
00390 };
00391 
00392 class Out_of_range : public Logic_error
00393 {
00394 public:
00395    static unsigned long Select;
00396    Out_of_range(const char* a_what = 0);
00397 };
00398 
00399 //class Bad_cast : public Logic_error
00400 //{
00401 //public:
00402 //   static unsigned long Select;
00403 //   Bad_cast(const char* a_what = 0);
00404 //};
00405 
00406 //class Bad_typeid : public Logic_error
00407 //{
00408 //public:
00409 //   static unsigned long Select;
00410 //   Bad_typeid(const char* a_what = 0);
00411 //};
00412 
00413 class Range_error : public Runtime_error
00414 {
00415 public:
00416    static unsigned long Select;
00417    Range_error(const char* a_what = 0);
00418 };
00419 
00420 class Overflow_error : public Runtime_error
00421 {
00422 public:
00423    static unsigned long Select;
00424    Overflow_error(const char* a_what = 0);
00425 };
00426 
00427 class Bad_alloc : public BaseException
00428 {
00429 public:
00430    static unsigned long Select;
00431    Bad_alloc(const char* a_what = 0);
00432 };
00433 
00434 #ifdef use_namespace
00435 }
00436 #endif
00437 
00438 
00439 #endif                            // end of EXCEPTION_LIB
00440 
00441 
00442 // body file: myexcept.cpp
00443 
00444 
00446 


kni
Author(s): Martin Günther
autogenerated on Thu Aug 27 2015 13:40:07