summaryrefslogtreecommitdiff
path: root/utils.h
diff options
context:
space:
mode:
authorJohn Wiegley <johnw@newartisans.com>2007-04-27 10:08:05 +0000
committerJohn Wiegley <johnw@newartisans.com>2008-04-13 03:38:31 -0400
commit4716975cb18795e4a953fc705cf0b7c74d6a1c95 (patch)
tree4e22788779337c306aa9b83282e7a67c52b6004c /utils.h
parent9039e728b2015b54dc87da52f450c27683303392 (diff)
downloadfork-ledger-4716975cb18795e4a953fc705cf0b7c74d6a1c95.tar.gz
fork-ledger-4716975cb18795e4a953fc705cf0b7c74d6a1c95.tar.bz2
fork-ledger-4716975cb18795e4a953fc705cf0b7c74d6a1c95.zip
More work done toward rearranging the utility code.
Diffstat (limited to 'utils.h')
-rw-r--r--utils.h363
1 files changed, 358 insertions, 5 deletions
diff --git a/utils.h b/utils.h
index 4ff8a006..b8e1e3b1 100644
--- a/utils.h
+++ b/utils.h
@@ -3,6 +3,26 @@
#include <system.hh>
+#if defined __FreeBSD__ && __FreeBSD__ <=4
+// FreeBSD has a broken isspace macro, so don't use it
+#undef isspace(c)
+#endif
+
+#if defined(__GNUG__) && __GNUG__ < 3
+namespace std {
+ inline ostream & right (ostream & i) {
+ i.setf(i.right, i.adjustfield);
+ return i;
+ }
+ inline ostream & left (ostream & i) {
+ i.setf(i.left, i.adjustfield);
+ return i;
+ }
+}
+#endif
+
+namespace ledger {
+
// jww (2007-04-23): Need to clean up the following include files. I
// want to following services:
//
@@ -15,10 +35,343 @@
// verification (optionally on, like debugging but silent)
// memory tracing and debugging (and watching for threshholds)
-#include "trace.h"
-#include "debug.h"
-#include "timing.h"
-#include "error.h"
-#include "util.h"
+#import "error.h"
+
+/**********************************************************************
+ *
+ * Default values
+ */
+
+#if defined(FULL_DEBUG)
+#define VERIFY_ON 1
+#define TRACING_ON 1
+#define DEBUG_ON 1
+#define TIMERS_ON 1
+#elif defined(NO_DEBUG)
+#define NO_ASSERTS 1
+#define NO_LOGGING 1
+#else
+#define TIMERS_ON 1
+#endif
+
+/**********************************************************************
+ *
+ * Assertions
+ */
+
+#ifdef assert
+#undef assert
+#endif
+
+#if ! defined(NO_ASSERTS)
+#define ASSERTS_ON 1
+#endif
+#if defined(ASSERTS_ON)
+
+#include <boost/current_function.hpp>
+
+void debug_assert(const ledger::string& reason,
+ const ledger::string& func,
+ const ledger::string& file,
+ unsigned long line);
+
+#define assert(x) \
+ ((x) ? ((void)0) : debug_assert(#x, BOOST_CURRENT_FUNCTION, \
+ __FILE__, __LINE__)
+
+#endif // ASSERTS_ON
+
+/**********************************************************************
+ *
+ * Verification (basically, very slow asserts)
+ */
+
+#if defined(VERIFY_ON)
+
+extern bool verify_enabled;
+
+#define verify(x) (verify_enabled ? assert(x) : ((void)0))
+
+extern int new_calls;
+extern unsigned long new_size;
+
+void * operator new(std::size_t) throw(std::bad_alloc);
+void * operator new[](std::size_t) throw(std::bad_alloc);
+void operator delete(void*) throw();
+void operator delete[](void*) throw();
+void * operator new(std::size_t, const std::nothrow_t&) throw();
+void * operator new[](std::size_t, const std::nothrow_t&) throw();
+void operator delete(void*, const std::nothrow_t&) throw();
+void operator delete[](void*, const std::nothrow_t&) throw();
+
+typedef std::multimap<void *, std::string> live_objects_map;
+typedef std::pair<void *, std::string> live_objects_pair;
+typedef std::pair<unsigned int, std::size_t> count_size_pair;
+typedef std::map<std::string, count_size_pair> object_count_map;
+typedef std::pair<std::string, count_size_pair> object_count_pair;
+
+extern live_objects_map live_objects;
+extern object_count_map live_count;
+extern object_count_map ctor_count;
+extern object_count_map object_count;
+
+bool trace_ctor(void * ptr, const char * cls_name, const char * args,
+ std::size_t cls_size);
+bool trace_dtor(void * ptr, const char * cls_name, std::size_t cls_size);
+
+#define trace_ctor(cls, args) \
+ verify(trace_ctor(this, #cls, args, sizeof(cls)))
+#define trace_dtor(cls) \
+ verify(trace_dtor(this, #cls, sizeof(cls)))
+
+void report_memory(std::ostream& out);
+
+#if ! defined(USE_BOOST_PYTHON)
+
+class string : public std::string
+{
+public:
+ string();
+ string(const string& str);
+ string(const std::string& str);
+ string(const int len, char x);
+ string(const char * str);
+ string(const char * str, const char * end);
+ string(const string& str, int x);
+ string(const string& str, int x, int y);
+ string(const char * str, int x);
+ string(const char * str, int x, int y);
+ ~string();
+};
+
+inline string operator+(const string& __lhs, const string& __rhs)
+{
+ string __str(__lhs);
+ __str.append(__rhs);
+ return __str;
+}
+
+string operator+(const char* __lhs, const string& __rhs);
+string operator+(char __lhs, const string& __rhs);
+
+inline string operator+(const string& __lhs, const char* __rhs)
+{
+ string __str(__lhs);
+ __str.append(__rhs);
+ return __str;
+}
+
+inline string operator+(const string& __lhs, char __rhs)
+{
+ typedef string __string_type;
+ typedef string::size_type __size_type;
+ __string_type __str(__lhs);
+ __str.append(__size_type(1), __rhs);
+ return __str;
+}
+
+inline bool operator==(const string& __lhs, const string& __rhs)
+{ return __lhs.compare(__rhs) == 0; }
+
+inline bool operator==(const char* __lhs, const string& __rhs)
+{ return __rhs.compare(__lhs) == 0; }
+
+inline bool operator==(const string& __lhs, const char* __rhs)
+{ return __lhs.compare(__rhs) == 0; }
+
+inline bool operator!=(const string& __lhs, const string& __rhs)
+{ return __rhs.compare(__lhs) != 0; }
+
+inline bool operator!=(const char* __lhs, const string& __rhs)
+{ return __rhs.compare(__lhs) != 0; }
+
+inline bool operator!=(const string& __lhs, const char* __rhs)
+{ return __lhs.compare(__rhs) != 0; }
+
+#endif
+
+#else // ! VERIFY_ON
+
+#define verify(x)
+#define trace_ctor(cls, args)
+#define trace_dtor(cls)
+
+#endif // VERIFY_ON
+
+/**********************************************************************
+ *
+ * Logging
+ */
+
+#if ! defined(NO_LOGGING)
+#define LOGGING_ON 1
+#endif
+#if defined(LOGGING_ON)
+
+// Logging
+
+enum log_level_t {
+ LOG_OFF = 0,
+ LOG_CRIT,
+ LOG_FATAL,
+ LOG_ASSERT,
+ LOG_ERROR,
+ LOG_VERIFY,
+ LOG_WARN,
+ LOG_INFO,
+ LOG_EXCEPT,
+ LOG_DEBUG,
+ LOG_TRACE,
+ LOG_ALL
+};
+
+extern log_level_t _log_level;
+extern unsigned int _trace_level;
+extern std::string _log_category;
+extern std::ostream * _log_stream;
+extern std::ostringstream _log_buffer;
+
+#define category(cat) \
+ static const char * const _this_category = (cat)
+
+bool logger(log_level_t level);
+
+#if defined(TRACING_ON)
+#define trace(lvl, msg) \
+ (_log_level >= LOG_TRACE && lvl >= _trace_level ? \
+ ((_log_buffer << msg), logger(LOG_TRACE)) : false)
+#else
+#define trace(lvl, msg)
+#endif
+
+#if defined(DEBUG_ON)
+#define debug_(cat, msg) \
+ (_log_level >= LOG_DEBUG && \
+ (_log_category == cat || \
+ _log_category.find(cat ".") == 0) ? \
+ ((_log_buffer << msg), logger(LOG_DEBUG)) : false)
+#define debug(msg) debug_(_this_category, msg)
+#else
+#define debug_(cat, msg)
+#define debug(msg)
+#endif
+
+#define info_(cat, msg) \
+ (_log_level >= LOG_INFO && \
+ (_log_category == cat || \
+ _log_category.find(cat ".") == 0) ? \
+ ((_log_buffer << msg), logger(LOG_INFO)) : false)
+#define info(msg) info_(_this_category, msg)
+
+#define log_macro(level, msg) \
+ (_log_level >= level ? \
+ ((_log_buffer << msg), logger(level)) : false)
+
+#define warn(msg) log_macro(LOG_WARN, msg)
+#define error(msg) log_macro(LOG_ERROR, msg)
+#define fatal(msg) log_macro(LOG_FATAL, msg)
+#define critical(msg) log_macro(LOG_CRIT, msg)
+
+#else // ! LOGGING_ON
+
+#define category(cat)
+#define trace(lvl, msg)
+#define debug(msg)
+#define debug_(cat, msg)
+#define info(msg)
+#define info_(cat, msg)
+#define warn(msg)
+#define error(msg)
+#define fatal(msg)
+#define critical(msg)
+
+/**********************************************************************
+ *
+ * Timers (allows log entries to specify cumulative time spent)
+ */
+
+#if defined(LOGGING_ON) && defined(TIMERS_ON)
+
+struct timer_t {
+ std::clock_t count;
+ std::string message;
+};
+
+typedef std::map<std::string, timer_t> timing_map;
+typedef timing_map::value_type timing_pair;
+
+void start_timer(const char * name);
+void stop_timer(const char * name);
+void finish_timer(const char * name);
+
+#if defined(TRACING_ON)
+#define trace_start(name, lvl, msg) \
+ (trace(lvl, msg) && start_timer(name))
+#define trace_stop(name) stop_timer(name)
+#define trace_finish(name) finish_timer(name)
+#else
+#define trace_start(name, lvl, msg)
+#define trace_stop(name)
+#define trace_finish(name)
+#endif
+
+#if defined(DEBUG_ON)
+#define debug_start(name, msg) \
+ (debug(msg) && start_timer(name))
+#define debug_start_(name, cat, msg) \
+ (debug_(cat, msg) && start_timer(name))
+#define debug_stop(name) stop_timer(name)
+#define debug_finish(name) finish_timer(name)
+#else
+#define debug_start(name, msg)
+#define debug_start_(name, cat, msg)
+#define debug_stop(name)
+#define debug_finish(name)
+#endif
+
+#define info_start(name, msg) \
+ (info(msg) && start_timer(name))
+#define info_start_(name, cat, msg)
+#define info_stop(name) stop_timer(name)
+#define info_finish(name) finish_timer(name)
+
+#else // ! (LOGGING_ON && TIMERS_ON)
+
+#define trace_start(lvl, msg, name)
+#define trace_stop(name)
+#define trace_finish(name)
+
+#define debug_start(name, msg)
+#define debug_start_(name, cat, msg)
+#define debug_stop(name)
+#define debug_finish(name)
+
+#define info_start(name, msg)
+#define info_start_(name, cat, msg)
+#define info_stop(name)
+#define info_finish(name)
+
+#endif // TIMERS_ON
+
+/**********************************************************************
+ *
+ * Debug macros
+ */
+
+#if defined(DEBUG_ON)
+
+#define if_debug_(cat) \
+ if (_log_level >= LOG_DEBUG && \
+ (_log_category == cat || \
+ _log_category.find(cat ".") == 0))
+#define if_debug() if_debug_(_this_category)
+
+#else // ! DEBUG_ON
+
+#define if_debug(cat) if (false)
+
+#endif // DEBUG_ON
+
+// } namespace ledger
#endif // _UTILS_H