1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170
|
=== Stones of Nvwa ===
The Name
Nvwa ("v" is pronounced like the French "u"), is one of the most
ancient Chinese goddesses. She was said to have created human beings,
and, when the evil god Gong-gong crashed himself upon one of the
pillars that support the sky and made a hole in it, she repaired the
sky with five-coloured stones.
I thought of the name Nvwa by analogy with Loki. Since it is so small
a project and it contains utilities instead of a complete framework, I
think "stones" a good metaphor.
Code Organization
Some may think that it is better to include like "#include <nvwa/...>".
However, I have reasons to avoid that. I would like to make the Nvwa
files drop-ins for other projects. One may simply copy them and use
them. It is not necessary to keep them in a separate directory -- of
course, not doing so will make it difficult to do cvs update.
Some may also wonder why I do not put the contents in namespace nvwa
instead of the global one. Um, some stuff, say, debug_new, simply
cannot be put in a namespace. And the copy-and-use usage pattern also
prevents me from doing that. But this is not unchangeable. Other
opinions, especially those resulting from real usage, are welcome.
Contents
A brief introduction follows. Check the Doxygen documentation for
more (technical) details.
* boolarray.cpp
* boolarray.h
A replacement of std::vector<bool>. I wrote it before I knew of
vector<bool>, or I might not have written it at all. However, it is
faster than any vector<bool> implementation I know, and it has
members like at, set, reset, flip, and count. I myself find "count"
very useful.
* class_level_lock.h
The Loki ClassLevelLockable adapted to use the fast_mutex layer. One
minor divergence from Loki is that the template has an additional
template parameter _RealLock to boost the performance in non-locking
scenarios. In that case, if you have a decent compiler, you probably
want to define HAS_CLASS_TEMPLATE_PARTIAL_SPECIALIZATION to 1 for
even better optimization. Cf. object_level_lock.h.
* cont_ptr_utils.h
Utility functors for containers of pointers adapted from Scott Meyers'
Effective STL.
* debug_new.cpp
* debug_new.h
A cross-platform, thread-safe memory leak detector. It is a
light-weight one designed only to catch unmatched pairs of
new/delete. I know there are already many existing memory leak
detectors, but as far as I know, free solutions are generally slow,
memory-consuming, and quite complicated to use. This solution is
very easy to use, and has very low space/time overheads. Just link
in debug_new.cpp for leakage report, and include debug_new.h for
additional file/line information. It will automatically switch on
multi-threading when the appropriate option of a recognized compiler
is specified. Check fast_mutex.h for more threading details.
Special support for gcc/binutils has been added to debug_new lately.
Even if the header file debug_new.h is not included, or
_DEBUG_NEW_REDEFINE_NEW is defined to 0 when it is included,
file/line information can be displayed if debugging symbols are
present in the executable, since debug_new stores the caller
addresses of memory allocation/deallocation routines and they will be
converted with addr2line on the fly. This makes memory tracing much
easier.
With an idea from Greg Herlihy's post in comp.lang.c++.moderated, the
implementation was much improved in 2007. The most significant
result is that placement new can be used with debug_new now! Full
support for new(std::nothrow) is provided, with its null-returning
error semantics (by default). Memory corruption will be checked on
freeing the pointers and checking the leaks, and a new function
check_mem_corruption is added for your on-demand use in debugging.
You may also want to define _DEBUG_NEW_TAILCHECK to something like 4
for past-end memory corruption check, which is off by default to
ensure performance is not affected.
NOTE for GCC 3.x users: Unless you are using a very old GCC 3.x
release (before 3.2.2), most probably you would want to define the
environment variable GLIBCPP_FORCE_NEW ("set GLIBCPP_FORCE_NEW=1" in
Windows command prompt and "export GLIBCPP_FORCE_NEW=1" in BASH, for
example) to get precise results of leak reports; otherwise the memory
pooling in libstdc++-v3 could cause false positives. I do not know
of the status of GCC 3.2.1, but I do know that 3.0.x, 3.1.x, and 3.2
do NOT support this method (but one is not supposed to be still using
those interim releases, right? I personally test mostly on GCC
2.95.3, 3.2.3, and 3.4.2 now). -- For GCC 3.4 and later, the variable
name is changed to GLIBCXX_FORCE_NEW.
An article on its design and implementation is available at
http://nvwa.sourceforge.net/article/debug_new.htm
* fast_mutex.h
The threading transparent layer simulating a non-recursive mutex. It
supports POSIX threads and Win32 threads currently, as well as a
no-threads mode. Unlike Loki and some other libraries, threading
mode is not to be specified in code, but detected from the
environment. It will automatically switch on multi-threading when
the "-MT"/"-MD" option of MSVC, the "-mthreads" option of MinGW GCC,
or the "-pthread" option of GCC under POSIX environments, is used.
One advantage of the current implementation is that the construction
and destruction of a static object using a static fast_mutex not yet
constructed or already destroyed are allowed to work (with
lock/unlock operations ignored), and there are re-entry checks for
lock/unlock operations when the preprocessing symbol _DEBUG is
defined.
* fixed_mem_pool.h
A memory pool implementation that requires initialization (allocates
a fixed-size chunk) prior to its use. It is simple and makes no
memory fragmentation, but the memory pool size cannot be changed
after initialization. Macros are provided to easily make a class use
pooled new/delete.
* mem_pool_base.cpp
* mem_pool_base.h
A class solely to be inherited by memory pool implementations. It is
used by static_mem_pool and fixed_mem_pool.
* object_level_lock.h
The Loki ObjectLevelLockable adapted to use the fast_mutex layer.
The member function get_locked_object does not exist in Loki, but is
also taken from Mr Alexandrescu's article. Cf. class_level_lock.h.
* pctimer.h
A function to get a high-resolution timer for Win32/Cygwin/Unix. It
is quite useful for measurement and optimization.
* set_assign.h
Utility routines to make up for the fact that STL only has set_union
(+) and set_difference (-) algorithms but no corresponding += and -=
operations available.
* static_mem_pool.cpp
* static_mem_pool.h
A memory pool implementation to pool memory blocks according to
compile-time block sizes. Macros are provided to easily make a class
use pooled new/delete.
An article on its design and implementation is available at
http://nvwa.sourceforge.net/article/static_mem_pool.htm
$Id: README,v 1.13 2008/09/11 15:47:52 adah Exp $
vim:autoindent:expandtab:formatoptions=tcqlm:textwidth=72:
|