debug.html 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252
  1. <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0.1 Transitional//EN">
  2. <html>
  3. <head>
  4. <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
  5. <title>Boost.MultiIndex Documentation - Tutorial -Debugging support</title>
  6. <link rel="stylesheet" href="../style.css" type="text/css">
  7. <link rel="start" href="../index.html">
  8. <link rel="prev" href="creation.html">
  9. <link rel="up" href="index.html">
  10. <link rel="next" href="techniques.html">
  11. </head>
  12. <body>
  13. <h1><img src="../../../../boost.png" alt="boost.png (6897 bytes)" align=
  14. "middle" width="277" height="86">Boost.MultiIndex Tutorial: Debugging support</h1>
  15. <div class="prev_link"><a href="creation.html"><img src="../prev.gif" alt="container creation" border="0"><br>
  16. Container creation
  17. </a></div>
  18. <div class="up_link"><a href="index.html"><img src="../up.gif" alt="Boost.MultiIndex tutorial" border="0"><br>
  19. Boost.MultiIndex tutorial
  20. </a></div>
  21. <div class="next_link"><a href="techniques.html"><img src="../next.gif" alt="techniques" border="0"><br>
  22. Techniques
  23. </a></div><br clear="all" style="clear: all;">
  24. <hr>
  25. <h2>Contents</h2>
  26. <ul>
  27. <li><a href="#debugging_support">Debugging support</a></li>
  28. <li><a href="#safe_mode">Safe mode</a>
  29. <ul>
  30. <li><a href="#serialization_and_safe_mode">Serialization and safe mode</a></li>
  31. </ul>
  32. </li>
  33. <li><a href="#invariant_check">Invariant-checking mode</a></li>
  34. </ul>
  35. <h2><a name="debugging_support">Debugging support</a></h2>
  36. <p>
  37. The concept of <i>Design by Contract</i>, originally developed as part
  38. of Bertrand Meyer's <a href="http://www.eiffel.com">Eiffel</a> language,
  39. revolves around the formulation of a <i>contract</i> between the user
  40. of a library and the implementor, by which the first is required to
  41. respect some <i>preconditions</i> on the values passed when invoking
  42. methods of the library, and the implementor guarantees in return
  43. that certain constraints on the results are met (<i>postconditions</i>),
  44. as well as the honoring of specified internal consistency rules, called
  45. <i>invariants</i>. Eiffel natively supports the three parts of the
  46. contract just described by means of constructs <code>require</code>,
  47. <code>ensure</code> and <code>invariant</code>, respectively.
  48. </p>
  49. <p>
  50. C++ does not enjoy direct support for Design by Contract techniques: these
  51. are customarily implemented as assertion code, often turned off in
  52. release mode for performance reasons. Following this approach,
  53. Boost.MultiIndex provides two distinct debugging modes:
  54. <ul>
  55. <li><i>Safe mode</i> checks preconditions on the invocations to the
  56. facilities of the library,</li>
  57. <li><i>invariant-checking mode</i> performs post-execution checks aimed
  58. at ensuring that the internal consistency of the library is preserved.</li>
  59. </ul>
  60. These two modes are independent of each other and can be set on or off
  61. individually. It is important to note that errors detected by safe mode are
  62. due in principle to faulty code in the user's program, while
  63. invariant-checking mode detects potential <i>internal</i> bugs in the
  64. implementation of Boost.MultiIndex.
  65. </p>
  66. <h2><a name="safe_mode">Safe mode</a></h2>
  67. <p>
  68. The idea of adding precondition checking facilities to STL as a debugging aid
  69. was first introduced by Cay S. Horstmann in his
  70. <a href="http://www.horstmann.com/safestl.html">Safe STL</a> library and later
  71. adopted by <a href="http://www.stlport.com/doc/debug_mode.html">STLport Debug
  72. Mode</a>. Similarly, Boost.MultiIndex features the so-called <i>safe mode</i>
  73. in which all sorts of preconditions are checked when dealing with iterators
  74. and functions of the library.
  75. </p>
  76. <p>
  77. Boost.MultiIndex safe mode is set by globally defining the macro
  78. <code>BOOST_MULTI_INDEX_ENABLE_SAFE_MODE</code>. Error conditions
  79. are checked via the macro <code>BOOST_MULTI_INDEX_SAFE_MODE_ASSERT</code>, which
  80. by default resolves to a call to <a href="../../../../libs/assert">
  81. <code>BOOST_ASSERT</code></a>.
  82. </p>
  83. <p>
  84. If the user decides to define her own version of
  85. <code>BOOST_MULTI_INDEX_SAFE_MODE_ASSERT</code>, it has to take the form
  86. </p>
  87. <blockquote><pre>
  88. <span class=identifier>BOOST_MULTI_INDEX_SAFE_MODE_ASSERT</span><span class=special>(</span><span class=identifier>expr</span><span class=special>,</span><span class=identifier>error_code</span><span class=special>)</span>
  89. </pre></blockquote>
  90. <p>
  91. where <code>expr</code> is the condition checked and <code>error_code</code>
  92. is one value of the <code>safe_mode::error_code</code> enumeration:
  93. </p>
  94. <blockquote><pre>
  95. <span class=keyword>namespace</span> <span class=identifier>boost</span><span class=special>{</span>
  96. <span class=keyword>namespace</span> <span class=identifier>multi_index</span><span class=special>{</span>
  97. <span class=keyword>namespace</span> <span class=identifier>safe_mode</span><span class=special>{</span>
  98. <span class=keyword>enum</span> <span class=identifier>error_code</span>
  99. <span class=special>{</span>
  100. <span class=identifier>invalid_iterator</span><span class=special>,</span> <span class=comment>// vg. default cted or pointing to erased element</span>
  101. <span class=identifier>not_dereferenceable_iterator</span><span class=special>,</span> <span class=comment>// iterator is not dereferenceable</span>
  102. <span class=identifier>not_incrementable_iterator</span><span class=special>,</span> <span class=comment>// iterator points to end of sequence</span>
  103. <span class=identifier>not_decrementable_iterator</span><span class=special>,</span> <span class=comment>// iterator points to beginning of sequence</span>
  104. <span class=identifier>not_owner</span><span class=special>,</span> <span class=comment>// iterator does not belong to the container</span>
  105. <span class=identifier>not_same_owner</span><span class=special>,</span> <span class=comment>// iterators belong to different containers</span>
  106. <span class=identifier>invalid_range</span><span class=special>,</span> <span class=comment>// last not reachable from first</span>
  107. <span class=identifier>inside_range</span><span class=special>,</span> <span class=comment>// iterator lies within a range (and it mustn't)</span>
  108. <span class=identifier>out_of_bounds</span><span class=special>,</span> <span class=comment>// move attempted beyond container limits</span>
  109. <span class=identifier>same_container</span> <span class=comment>// containers ought to be different</span>
  110. <span class=special>};</span>
  111. <span class=special>}</span> <span class=comment>// namespace multi_index::safe_mode</span>
  112. <span class=special>}</span> <span class=comment>// namespace multi_index</span>
  113. <span class=special>}</span> <span class=comment>// namespace boost</span>
  114. </pre></blockquote>
  115. <p>
  116. For instance, the following replacement of
  117. <code>BOOST_MULTI_INDEX_SAFE_MODE_ASSERT</code> throws an exception instead of
  118. asserting:
  119. </p>
  120. <blockquote><pre>
  121. <span class=preprocessor>#include</span> <span class=special>&lt;</span><span class=identifier>boost</span><span class=special>/</span><span class=identifier>multi_index_container</span><span class=special>/</span><span class=identifier>safe_mode_errors</span><span class=special>.</span><span class=identifier>hpp</span><span class=special>&gt;</span>
  122. <span class=keyword>struct</span> <span class=identifier>safe_mode_exception</span>
  123. <span class=special>{</span>
  124. <span class=identifier>safe_mode_exception</span><span class=special>(</span><span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>safe_mode</span><span class=special>::</span><span class=identifier>error_code</span> <span class=identifier>error_code</span><span class=special>):</span>
  125. <span class=identifier>error_code</span><span class=special>(</span><span class=identifier>error_code</span><span class=special>)</span>
  126. <span class=special>{}</span>
  127. <span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>safe_mode</span><span class=special>::</span><span class=identifier>error_code</span> <span class=identifier>error_code</span><span class=special>;</span>
  128. <span class=special>};</span>
  129. <span class=preprocessor>#define</span> <span class=identifier>BOOST_MULTI_INDEX_SAFE_MODE_ASSERT</span><span class=special>(</span><span class=identifier>expr</span><span class=special>,</span><span class=identifier>error_code</span><span class=special>)</span> <span class=special>\</span>
  130. <span class=keyword>if</span><span class=special>(!(</span><span class=identifier>expr</span><span class=special>)){</span><span class=keyword>throw</span> <span class=identifier>safe_mode_exception</span><span class=special>(</span><span class=identifier>error_code</span><span class=special>);}</span>
  131. <span class=comment>// This has to go before the inclusion of any header from Boost.MultiIndex,
  132. // except possibly safe_error_codes.hpp.</span>
  133. </pre></blockquote>
  134. <p>
  135. Other possibilites, like outputting to a log or firing some kind of alert, are
  136. also implementable.
  137. </p>
  138. <p>
  139. <b>Warning:</b> Safe mode adds a very important overhead to the program
  140. both in terms of space and time used, so in general it should not be set for
  141. <code>NDEBUG</code> builds. Also, this mode is intended solely as a debugging aid,
  142. and programs must not rely on it as part of their normal execution flow: in
  143. particular, no guarantee is made that all possible precondition errors are diagnosed,
  144. or that the checks remain stable across different versions of the library.
  145. </p>
  146. <h3><a name="serialization_and_safe_mode">Serialization and safe mode</a></h3>
  147. <p>
  148. Iterators restored from an archive are not subject to safe mode checks. This is
  149. so because it is not possible to automatically know the associated
  150. <code>multi_index_container</code> of an iterator from the serialization
  151. information alone. However, if desired, a restored iterator can be converted to a
  152. checked value by using the following workaround:
  153. </p>
  154. <blockquote><pre>
  155. <span class=identifier>employee_set</span> <span class=identifier>es</span><span class=special>;</span>
  156. <span class=identifier>employee_set</span><span class=special>::</span><span class=identifier>nth_index</span><span class=special>&lt;</span><span class=number>1</span><span class=special>&gt;::</span><span class=identifier>iterator</span> <span class=identifier>it</span><span class=special>;</span>
  157. <span class=comment>// restore es and it from an archive ar</span>
  158. <span class=identifier>ar</span><span class=special>&gt;&gt;</span><span class=identifier>es</span><span class=special>;</span>
  159. <span class=identifier>ar</span><span class=special>&gt;&gt;</span><span class=identifier>it</span><span class=special>;</span> <span class=comment>// it won't benefit from safe mode checks
  160. // Turn it into a checked value by providing Boost.MultiIndex
  161. // with info about the associated container.
  162. // This statement has virtually zero cost if safe mode is turned off.</span>
  163. <span class=identifier>it</span><span class=special>=</span><span class=identifier>es</span><span class=special>.</span><span class=identifier>project</span><span class=special>&lt;</span><span class=number>1</span><span class=special>&gt;(</span><span class=identifier>it</span><span class=special>);</span>
  164. </pre></blockquote>
  165. <h2><a name="invariant_check">Invariant-checking mode</a></h2>
  166. <p>
  167. The so called <i>invariant-checking mode</i> of Boost.MultiIndex can be
  168. set by globally defining the macro
  169. <code>BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING</code>.
  170. When this mode is in effect, all public functions of Boost.MultiIndex
  171. will perform post-execution tests aimed at ensuring that the basic
  172. internal invariants of the data structures managed are preserved.
  173. </p>
  174. <p>
  175. If an invariant test fails, Boost.MultiIndex will indicate the failure
  176. by means of the unary macro <code>BOOST_MULTI_INDEX_INVARIANT_ASSERT</code>.
  177. Unless the user provides a definition for this macro, it defaults to
  178. <a href="../../../../libs/assert">
  179. <code>BOOST_ASSERT</code></a>. Any assertion of this kind should
  180. be regarded in principle as a bug in the library. Please report such
  181. problems, along with as much contextual information as possible, to the
  182. maintainer of the library.
  183. </p>
  184. <p>
  185. It is recommended that users of Boost.MultiIndex always set the
  186. invariant-checking mode in debug builds.
  187. </p>
  188. <hr>
  189. <div class="prev_link"><a href="creation.html"><img src="../prev.gif" alt="container creation" border="0"><br>
  190. Container creation
  191. </a></div>
  192. <div class="up_link"><a href="index.html"><img src="../up.gif" alt="Boost.MultiIndex tutorial" border="0"><br>
  193. Boost.MultiIndex tutorial
  194. </a></div>
  195. <div class="next_link"><a href="techniques.html"><img src="../next.gif" alt="techniques" border="0"><br>
  196. Techniques
  197. </a></div><br clear="all" style="clear: all;">
  198. <br>
  199. <p>Revised July 07th 2017</p>
  200. <p>&copy; Copyright 2003-2017 Joaqu&iacute;n M L&oacute;pez Mu&ntilde;oz.
  201. Distributed under the Boost Software
  202. License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
  203. LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
  204. http://www.boost.org/LICENSE_1_0.txt</a>)
  205. </p>
  206. </body>
  207. </html>