Imported Upstream version 1.72.0
[platform/upstream/boost.git] / libs / contract / doc / tutorial.qbk
1
2 [/ Copyright (C) 2008-2018 Lorenzo Caminiti]
3 [/ Distributed under the Boost Software License, Version 1.0 (see accompanying]
4 [/ file LICENSE_1_0.txt or a copy at http://www.boost.org/LICENSE_1_0.txt).]
5 [/ See: http://www.boost.org/doc/libs/release/libs/contract/doc/html/index.html]
6
7 [section Tutorial]
8
9 This section is a guide to basic usage of this library.
10
11 [section Non-Member Functions]
12
13 Contracts for non-member functions are programmed using [funcref boost::contract::function].
14 For example (see [@../../example/features/non_member.cpp =non_member.cpp=]):
15
16 [import ../example/features/non_member.cpp]
17 [non_member]
18
19 All necessary header files of this library are included by `#include <boost/contract.hpp>`.
20 Alternatively, programmers can selectively include only the header files they actually need among =boost/contract/*.hpp= (see __Getting_Started__).
21
22 It is possible to specify preconditions, postconditions, and exception guarantees for non-member functions (see __Preconditions__, __Postconditions__, and __Exception_Guarantees__).
23
24 The [funcref boost::contract::function] function returns an RAII object that must always be assigned to a local variable of type [classref boost::contract::check] (otherwise this library will generate a run-time error, see [macroref BOOST_CONTRACT_ON_MISSING_CHECK_DECL]).
25 [footnote
26 The name of this local variable is arbitrary, but `c` is often used in this documentation for ["c]heck or ["c]aminiti [^;-)] .
27 ]
28 Furthermore, C++11 `auto` declarations cannot be used here and the [classref boost::contract::check] type must be explicitly specified (otherwise this library will generate a compile-time error prior C++17 and a run-time error post C++17).
29 [footnote
30 *Rationale:*
31 C++17 guaranteed copy elision on function return value voids the trick this library uses to force a compile-time error when `auto` is incorrectly used instead of [classref boost::contract::check].
32 The library still generates a run-time error in this case (also on C++17).
33 In any case, after reading this documentation it should be evident to programmers that `auto` should not be used in [classref boost::contract::check] declarations so this misuse of `auto` should not be an issue in practice.
34 ]
35 The function body is programmed right after the declaration of this RAII object.
36
37 [note
38 In some cases, it might be necessary to program some code before the contract.
39 For example for acquiring resources that will be used while checking the contract like old values, but also to lock mutexes (or other synchronization mechanisms) in multi-threaded programs.
40 ]
41
42 At construction, the [classref boost::contract::check] RAII object for non-member functions does the following (enclosing function entry):
43
44 # Check preconditions, by calling the nullary functor [^['r]]`()` passed to `.precondition(`[^['r]]`)`.
45
46 At destruction instead (enclosing function exit):
47
48 # If the function body did not throw an exception:
49     # Check postconditions, by calling the nullary functor [^['s]]`()` passed to `.postcondition(`[^['s]]`)`.
50 # Else:
51     # Check exception guarantees, by calling the nullary functor [^['e]]`()` passed to `.except(`[^['e]]`)`.
52
53 This ensures that non-member function contracts are correctly checked at run-time (see __Function_Calls__).
54 (Also note that functions will correctly check their contracts even when they are called via function pointers, function objects, etc.)
55
56 [note
57 A non-member function can avoid calling [funcref boost::contract::function] for efficiency but only when it has no preconditions, no postconditions, and no exception guarantees.
58 ]
59
60 [endsect]
61
62 [section Preconditions]
63
64 When preconditions are specified, they are programmed using a functor [^['r]] passed to `.precondition(`[^['r]]`)` that can be called with no parameters as in [^['r]]`()`.
65 Contracts that do not have preconditions simply do not call `.precondition(...)`.
66 Preconditions must appear before postconditions and exception guarantees when these are all present (see __Postconditions__ and __Exception_Guarantees__).
67
68 C++11 lambda functions are convenient to program preconditions, but any other nullary functor can be used (see __No_Lambda_Functions__).
69 [footnote
70 Lambda functions with no parameters can be programmed in C++11 as `[...] () { ... }` but also equivalently as `[...] { ... }`.
71 This second from is often used in this documentation omitting the empty parameter list `()` for brevity.
72 ]
73 For example, for [funcref boost::contract::function] (similarly for public functions, instead destructors do not have preconditions and constructors use [classref boost::contract::constructor_precondition], see __Public_Functions__, __Destructors__, and __Constructors__):
74
75     void f(...) {
76         boost::contract::check c = boost::contract::function()  // Same for all other contracts.
77             .precondition([&] {                                 // Capture by reference or value...
78                 BOOST_CONTRACT_ASSERT(...);                     // ...and should not modify captures.
79                 ...
80             })
81             ...
82         ;
83
84         ...
85     }
86
87 The precondition functor should capture all the variables that it needs to assert the preconditions.
88 These variables can be captured by value when the overhead of copying such variables is acceptable.
89 [footnote
90 In this documentation preconditions often capture variables by reference to avoid extra copies.
91 ]
92 In any case, programmers should not write precondition assertions that modify the value of the captured variables, even when those are captured by reference (see __Constant_Correctness__).
93
94 Any code can be programmed in the precondition functor, but it is recommended to keep this code simple using mainly assertions and if-statements (to avoid programming complex preconditions that might be buggy and also slow to check at run-time).
95 It is also recommended to use [macroref BOOST_CONTRACT_ASSERT] to program precondition assertions because that enables this library to print informative error messages when the asserted conditions are evaluated to be false (note that this is not a variadic macro, see __No_Macros__):
96     
97     BOOST_CONTRACT_ASSERT(``[^['boolean-condition]]``)
98     // Or, if `boolean-condition` contains commas `,` not already within parenthesis `()`...
99     BOOST_CONTRACT_ASSERT((``[^['boolean-condition]]``)) // ...use extra parenthesis (not a variadic macro).
100
101 This library will automatically call the failure handler [funcref boost::contract::precondition_failure] if any of the [macroref BOOST_CONTRACT_ASSERT] conditions are false or, more in general, if calling the functor specified via `.precondition(...)` throws any exception.
102 By default, this failure handler prints an error message to `std::cerr` and terminates the program calling `std::terminate` (see __Throw_on_Failures__ to change the failure handler to throw exceptions, exit the program with an error code, etc.).
103
104 [note
105 Contracts are most useful when their assertions only use public members that are accessible to the caller so the caller can properly check and use the contract.
106 In particular, preconditions of a public function or constructor that use non-public members are essentially incorrect because they cannot be fully checked by the caller (in fact, Eiffel generates a compile-time error in this case).
107 However, this library does not enforce such a constraint and it leaves it up to programmers to only use public members when programming contracts, especially when asserting preconditions (see __Specifications_vs_Implementation__).
108 ]
109
110 [endsect]
111
112 [section Postconditions]
113
114 When postconditions are specified, they are programmed using a functor [^['s]] passed to `.postcondition(`[^['s]]`)` that can be called with no parameters as in [^['s]]`()`.
115 Contracts that do not have postconditions simply do not call `.postcondition(...)`.
116 Postconditions must appear after preconditions but before exception guarantees when these are all present (see __Preconditions__ and __Exception_Guarantees__).
117
118 C++11 lambda functions are convenient to program postconditions, but any other nullary functor can be used (see __No_Lambda_Functions__).
119 For example, for [funcref boost::contract::function] (similarly for all other contracts):
120
121     void f(...) {
122         boost::contract::check c = boost::contract::function()  // Same for all other contracts.
123             ...
124             .postcondition([&] {                                // Capture by reference...
125                 BOOST_CONTRACT_ASSERT(...);                     // ...but should not modify captures.
126                 ...
127             })
128             ...
129         ;
130
131         ...
132     }
133
134 The postcondition functor should capture all the variables that it needs to assert the postconditions.
135 In general, these variables should be captured by reference and not by value (because postconditions need to access the value that these variables will have at function exit, and not the value these variables had when the postcondition functor was first declared).
136 Postconditions can also capture return and old values (see __Return_Values__ and __Old_Values__).
137 In any case, programmers should not write postcondition assertions that modify the value of the captured variables, even when those are captured by reference (see __Constant_Correctness__).
138
139 Any code can be programmed in the postcondition functor, but it is recommended to keep this code simple using mainly assertions and if-statements (to avoid programming complex postconditions that might be buggy and slow to check at run-time).
140 It is also recommended to use [macroref BOOST_CONTRACT_ASSERT] to program postcondition assertions because that enables this library to print informative error messages when the asserted conditions are evaluated to be false (note that this is not a variadic macro, see __No_Macros__):
141
142     BOOST_CONTRACT_ASSERT(``[^['boolean-condition]]``)
143     // Or, if `boolean-condition` has commas `,` not already within parenthesis `()`...
144     BOOST_CONTRACT_ASSERT((``[^['boolean-condition]]``)) // ...use extra parenthesis (not a variadic macro).
145
146 This library will automatically call the failure handler [funcref boost::contract::postcondition_failure] if any of the [macroref BOOST_CONTRACT_ASSERT] conditions are false or, more in general, if calling the functor specified via `.postcondition(...)` throws any exception.
147 By default, this failure handler prints an error message to `std::cerr` and terminates the program calling `std::terminate` (see __Throw_on_Failures__ to change the failure handler to throw exceptions, exit the program with an error code, etc.).
148
149 For non-void virtual public functions and non-void public function overrides, the functor [^['s]] passed to `.postcondition(`[^['s]]`)` is not a nullary functor, instead it is a unary functor taking a variable holding the return value as its one parameter [^['s]]`(`[^['result]]`)` (this is to properly support subcontracting, see __Virtual_Public_Functions__ and __Public_Function_Overrides__).
150
151 [endsect]
152
153 [section Return Values]
154
155 In non-void functions, postconditions might need to access the function return value to program assertions.
156 In these cases, programmers are responsible to declare a local variable before the contract and to assign it to the return value at function exit (when the function does not throw an exception).
157 [footnote
158 The name of the local variable that holds the return value is arbitrary, but `result` is often used in this documentation.
159 ]
160 For example, for [funcref boost::contract::function] (similarly for all other contracts):
161
162     return_type f(...) {
163         return_type result;                                     // Must be later assigned to return value.
164         boost::contract::check c = boost::contract::function()  // Same for all other contracts.
165             ...
166             .postcondition([&] {                                // Also capture `result` reference...
167                 BOOST_CONTRACT_ASSERT(result == ...);           // ...but should not modify captures.
168                 ...
169             })
170             ...
171         ;
172
173         ...
174         return result = ...;                                    // Assign `result` at each return.
175     }
176
177 At any point where the enclosing function returns, programmers are responsible to assign the result variable to the expression being returned.
178 This can be done ensuring that /all/ `return` statements in the function are of the form:
179
180     ``[^['return-type]]`` result;
181     ...
182     return result = ``[^['return-expression]]``;                           // Assign `result` at each return.
183
184 The functor used to program postconditions should capture the result variable by reference and not by value (because postconditions must access the value the result variable will have at function exit, and not the value the result variable had when the postcondition functor was first declared).
185 The return value should never be used in preconditions, old value copies, or exception guarantees (because the return value is not yet correctly evaluated and set when preconditions are checked, old values are copied, or if the function throws an exception).
186 In any case, programmers should not modify the result variable in the contract assertions (see __Constant_Correctness__).
187
188 It is also possible to declared the result variable using `boost::optional` when the function return type does not have a default constructor, or if the default constructor is too expensive or undesirable to execute when first declaring the result variable (see __Optional_Return_Values__).
189
190 Non-void virtual public functions and non-void public function overrides must always declare and use a result variable even when postconditions do not directly use the function return value (this is to properly support subcontracting, see __Virtual_Public_Functions__ and __Public_Function_Overrides__).
191
192 [endsect]
193
194 [section Old Values]
195
196 When old values are used in postconditions or in exception guarantees, programmes are responsible to declare local variables before the contract and to assign them to related old value expressions using [macroref BOOST_CONTRACT_OLDOF].
197 [footnote
198 The name of a local variable that holds an old value is arbitrary, but [^old_['variable-name]] is often used in this documentation.
199 ]
200 For example, for [funcref boost::contract::function] (similarly for all other contracts):
201
202     void f(...) {
203         boost::contract::old_ptr<old_type> old_var = BOOST_CONTRACT_OLDOF(old_expr);
204         ...                                                     // More old value declarations here if needed.
205         boost::contract::check c = boost::contract::function()  // Same for all other contracts.
206             ...                                                 // Preconditions shall not use old values.
207             .postcondition([&] {                                // Capture by reference...
208                 BOOST_CONTRACT_ASSERT(*old_var == ...);         // ...but should not modify captures.
209                 ...
210             })
211             .except([&] {                                       // Capture by reference...
212                 BOOST_CONTRACT_ASSERT(old_var->...);            // ...but should not modify captures.
213                 ...
214             })
215         ;
216
217         ...
218     }
219
220 Old values are handled by this library using the smart pointer class template [classref boost::contract::old_ptr] (so programmers do not directly manage allocation and deallocation of the pointed memory).
221 [footnote
222 *Rationale:*
223 Old values have to be optional values because they need to be left uninitialized when they are not used because both postconditions and exception guarantees are disabled (defining [macroref BOOST_CONTRACT_NO_POSTCONDITIONS] and [macroref BOOST_CONTRACT_NO_EXCEPTS]).
224 That is to avoid old value copies when old values are not used, either a pointer or (better) a `boost::optional` could have been used to achieve that.
225 In addition, old values need to be pointers internally allocated by this library so that they are never copied twice even when calling an overridden function multiple times to check preconditions, postconditions, etc. to implement subcontracting, so a smart pointer class template was used.
226 ]
227 The pointed old value type is automatically qualified as `const` (so old values cannot be mistakenly changed by contract assertions, see __Constant_Correctness__).
228 This library ensures that old value pointers are always not null by the time postconditions and exception guarantees are checked (so programmers can safely dereference and use these pointers in postcondition and exception guarantee assertions using `operator*` and `operator->` without having to check if old value pointers are not null first).
229
230 Old values should not be used in preconditions and this library does not guarantee that old value pointers are always not null when preconditions are checked.
231 [footnote
232 For example, old value pointers might be null in preconditions when postconditions and exception guarantees are disabled defining [macroref BOOST_CONTRACT_NO_POSTCONDITIONS] and [macroref BOOST_CONTRACT_NO_EXCEPTS] (but also when checking an overridden virtual public function contract via subcontracting, etc.).
233 ]
234 See __Old_Values_Copied_at_Body__ for delaying the copy of old values until after class invariants (for constructors, destructors, and public functions) and preconditions are checked (when necessary, this allows to program old value expressions under the simplifying assumption that class invariant and precondition assertions are satisfied already).
235
236 [macroref BOOST_CONTRACT_OLDOF] is a variadic macro and it takes an extra parameter when used in virtual public functions or public function overrides (see __Virtual_Public_Functions__ and __Public_Function_Overrides__).
237 C++11 auto declarations can be used with [macroref BOOST_CONTRACT_OLDOF] for brevity `auto `[^old_['variable-name] = BOOST_CONTRACT_OLDOF(['expression])] (but see also __Old_Value_Requirements__).
238 See __No_Macros__ to program old values without using [macroref BOOST_CONTRACT_OLDOF] (e.g., on compilers that do not support variadic macros).
239
240 [note
241 This library ensures that old values are copied only once.
242 This library also ensures that old values are never copied when postconditions and exception guarantees are disabled defining both [macroref BOOST_CONTRACT_NO_POSTCONDITIONS] and [macroref BOOST_CONTRACT_NO_EXCEPTS] (note that both these two macros must be defined, defining only [macroref BOOST_CONTRACT_NO_POSTCONDITIONS] or only [macroref BOOST_CONTRACT_NO_EXCEPTS] is not sufficient to prevent the run-time cost of old value copies).
243 ]
244
245 [endsect]
246
247 [section Exception Guarantees]
248
249 When exception guarantees are specified, they are programmed using a functor [^['e]] passed to `.except(`[^['e]]`)` that can be called with no parameters as in [^['e]]`()`.
250 Contracts that do not have exception guarantees simply do not call `.except(...)`.
251 Exception guarantees must appear after both preconditions and postconditions when these are all present (see __Preconditions__ and __Postconditions__).
252
253 C++11 lambda functions are convenient to program exception guarantees, but any other nullary functor can be used (see __No_Lambda_Functions__).
254 For example, for [funcref boost::contract::function] (similarly for all other contracts):
255
256     void f(...) {
257         boost::contract::check c = boost::contract::function()  // Same for all other contracts.
258             ...
259             .except([&] {                                       // Capture by reference...
260                 BOOST_CONTRACT_ASSERT(...);                     // ...but should not modify captures.
261                 ...
262             })
263         ;
264
265         ...
266     }
267
268 The exception guarantee functor should capture all the variables that it needs to assert the exception guarantees.
269 In general, these variables should be captured by reference and not by value (because exception guarantees need to access the value that these variables will have when the function throws, and not the value these variables had when the exception guarantee functor was first declared).
270 Exception guarantees can also capture old values (see __Old_Values__) but they should not access the function return value instead (because the return value is not be properly set when the function throws an exception).
271 In any case, programmers should not write exception guarantee assertions that modify the value of the captured variables, even when those are captured by reference (see __Constant_Correctness__).
272
273 [note
274 In real production code, it might be difficult to program meaningful exception guarantees without resorting to expensive old value copies that will slow down execution.
275 Therefore, the authors recognize that exception guarantees, even if supported by this library, might not be used often in practice (and they are not used in most of the examples listed in the rest of this documentation).
276 In any case, these performance considerations are ultimately left to programmers and their specific application domains.
277 ]
278
279 Any code can be programmed in the exception guarantee functor, but it is recommended to keep this code simple using mainly assertions and if-statements (to avoid programming complex exception guarantees that might be buggy and slow to check at run-time).
280 It is also recommended to use [macroref BOOST_CONTRACT_ASSERT] to program exception guarantee assertions because that enables this library to print informative error messages when the asserted conditions are evaluated to be false (note that this is not a variadic macro, see __No_Macros__):
281
282     BOOST_CONTRACT_ASSERT(``[^['boolean-condition]]``)
283     // Or, if `boolean-condition` has commas `,` not already within parenthesis `()`...
284     BOOST_CONTRACT_ASSERT((``[^['boolean-condition]]``)) // ...use extra parenthesis (not a variadic macro).
285
286 This library will automatically call the failure handler [funcref boost::contract::except_failure] if any of the [macroref BOOST_CONTRACT_ASSERT] conditions are false or, more in general, if calling the functor specified via `.except(...)` throws any exception.
287 By default, this failure handler prints an error message to `std::cerr` and terminates the program calling `std::terminate` (see __Throw_on_Failures__ to change the failure handler to exit the program with an error code or to take some other custom action).
288
289 [note
290 While it is technically possible for programmers to specify an exception guarantee handler that throws an exception in case of an exception guarantee failure, this will force C++ to terminate the program.
291 That is because the handler will throw an exception while there is already an active exception on the stack (the exception thrown by the function body that caused the exception guarantees to be checked in the first place).
292 Therefore, programmers should not change the exception guarantee failure handler to throw exceptions.
293 ]
294
295 [endsect]
296
297 [section Class Invariants]
298
299 Public member functions, constructors, and destructors can be programmed to also check class invariants.
300 When class invariants are specified, they are programmed in a public `const` function named `invariant` taking no argument and returning `void`.
301 Classes that do not have invariants, simply do not declare the `invariant` function.
302 [footnote
303 This library uses template meta-programming (SFINAE-based introspection techniques) to check invariants only for classes that declare a member function named by [macroref BOOST_CONTRACT_INVARIANT_FUNC].
304 ]
305 For example:
306
307     class u {
308     public:                                 // Must be public.
309         void invariant() const {            // Must be const.
310             BOOST_CONTRACT_ASSERT(...);
311             ...
312         }
313
314         ...
315     };
316
317 This member function must be `const` because contracts should not modify the object state (see __Constant_Correctness__).
318 This library will generate a compile-time error if the `const` qualifier is missing (unless [macroref BOOST_CONTRACT_PERMISSIVE] is defined).
319
320 Any code can be programmed in the `invariant` function, but it is recommended to keep this code simple using mainly assertions and if-statements (to avoid programming complex invariants that might be buggy and slow to check at run-time).
321 It is also recommended to use [macroref BOOST_CONTRACT_ASSERT] to program class invariant assertions because that enables this library to print informative error messages when the asserted conditions are evaluated to be false (note that this is not a variadic macro, see __No_Macros__):
322     
323     BOOST_CONTRACT_ASSERT(``[^['boolean-condition]]``)
324     // Or, if `boolean-condition` has commas `,` not already within parenthesis `()`...
325     BOOST_CONTRACT_ASSERT((``[^['boolean-condition]]``)) // ...use extra parenthesis (not a variadic macro).
326
327 This library will automatically call failure handlers [funcref boost::contract::entry_invariant_failure] or [funcref boost::contract::exit_invariant_failure] if any of the [macroref BOOST_CONTRACT_ASSERT] conditions are false or, more in general, if the `invariant` function throws an exception when invariants are checked at function entry or exit respectively.
328 By default, these handlers print an error message to `std::cerr` and terminate the program calling `std::terminate` (see __Throw_on_Failures__ to change these failure handlers to throw exceptions, exit the program with an error code, etc.).
329
330 See __Access_Specifiers__ to avoid making the `invariant` member function `public`.
331 [footnote
332 In this documentation the `invariant` member function is often declared `public` for simplicity.
333 However, in production code it might not be acceptable to augment the public members of a class adding the `invariant` function (and that can be avoided using [classref boost::contract::access] as explained in __Access_Specifiers__).
334 ]
335 See [macroref BOOST_CONTRACT_INVARIANT_FUNC] to use a name different from `invariant` (e.g., because `invariant` clashes with other names in user-defined classes).
336
337 [note
338 Contract assertions are not checked (not even class invariants) when data members are accessed directly (this is different from Eiffel where even accessing public data members checks class invariants).
339 Therefore, it might be best for both `class`es and `struct`s (and also `union`s, see __Unions__) that have invariants to have no mutable public data members and to access data members publicly only via appropriate public functions (e.g., setters and getters) that can be programmed to check the class invariants using this library.
340 ]
341
342 See __Volatile_Public_Functions__ to program invariants for classes with `volatile` public functions.
343
344 [heading Static Class Invariants]
345
346 Static public functions can be programmed to check static class invariants.
347 When static class invariants are specified, they are programmed in a public `static` function named `static_invariant` taking no argument and returning `void`.
348 Classes that do not have static class invariants, simply do not declare the `static_invariant` function.
349 [footnote
350 This library uses template meta-programming (SFINAE-based introspection techniques) to check static invariants only for classes that declare a member function named by [macroref BOOST_CONTRACT_STATIC_INVARIANT_FUNC].
351 ]
352 For example:
353
354     class u {
355     public:                                 // Must be public.
356         static void static_invariant() {    // Must be static.
357             BOOST_CONTRACT_ASSERT(...);
358             ...
359         }
360         
361         ...
362     };
363
364 This member function must be `static` (and it correctly cannot access the object `this`).
365 This library will generate a compile-time error if the `static` classifier is missing (unless the [macroref BOOST_CONTRACT_PERMISSIVE] macro is defined).
366
367 Any code can be programmed in the `static_invariant` function, but it is recommended to keep this code simple using mainly assertions and if-statements (to avoid programming complex static invariants that might be buggy and slow to check at run-time).
368 It is also recommended to use [macroref BOOST_CONTRACT_ASSERT] to program the assertions because that enables this library to print informative error messages when the asserted conditions are evaluated to be false (note that this is not a variadic macro, see __No_Macros__):
369     
370     BOOST_CONTRACT_ASSERT(``[^['boolean-condition]]``)
371     // Or, if `boolean-condition` has commas `,` not already within parenthesis `()`...
372     BOOST_CONTRACT_ASSERT((``[^['boolean-condition]]``)) // ...use extra parenthesis (not a variadic macro).
373
374 This library will automatically call failure handlers [funcref boost::contract::entry_invariant_failure] or [funcref boost::contract::exit_invariant_failure] if any of the [macroref BOOST_CONTRACT_ASSERT] conditions are false or, more in general, if the `static_invariant` function throws an exception when invariants are checked at function entry or exit respectively.
375 By default, these handlers print an error message to `std::cerr` and terminate the program calling `std::terminate` (see __Throw_on_Failures__ to change these failure handlers to throw exceptions, exit the program with an error code, etc.).
376
377 See __Access_Specifiers__ to avoid making `static_invariant` member function `public`.
378 [footnote
379 In this documentation the `static_invariant` member function is often declared `public` for simplicity.
380 However, in production code it might not be acceptable to augment the public members of a class adding the `static_invariant` function (and that can be avoided using [classref boost::contract::access] as explained in __Access_Specifiers__).
381 ]
382 See [macroref BOOST_CONTRACT_STATIC_INVARIANT_FUNC] to use a name different from `static_invariant` (e.g., because `static_invariant` clashes with other names in user-defined classes).
383 [footnote
384 *Rationale:*
385 In C++, it is not possible to overload a member function based on the `static` classifier.
386 Therefore, this library has to use different names for the member functions checking non-static and static class invariants (namely for [macroref BOOST_CONTRACT_INVARIANT_FUNC] and for [macroref BOOST_CONTRACT_STATIC_INVARIANT_FUNC]).
387 ]
388
389 [endsect]
390
391 [section Constructors]
392
393 Contracts for constructors are programmed using the [funcref boost::contract::constructor] function and the [classref boost::contract::constructor_precondition] base class.
394 For example (see [@../../example/features/public.cpp =public.cpp=]):
395
396 [import ../example/features/public.cpp]
397 [public_class_begin]
398 [public_constructor]
399 [public_class_end]
400
401 It is not possible to specify preconditions using `.precondition(...)` for constructors (this library will generate a compile-time error if `.precondition(...)` is used on the object returned by [funcref boost::contract::constructor]).
402 Constructor preconditions are specified using the [classref boost::contract::constructor_precondition] base class instead (same considerations as the ones made in __Preconditions__ apply also to the precondition functor passed to [classref boost::contract::constructor_precondition]).
403 Programmes should not access the object `*this` from constructor preconditions (because the object does not exists yet before the constructor body is executed).
404 [footnote
405 See __No_Lambda_Functions__ to enforce this constraint at compile-time (but not recommended because of extra boiler-plate code).
406 ]
407 Constructors without preconditions simply do not explicitly initialize the [classref boost::contract::constructor_precondition] base (because [classref boost::contract::constructor_precondition] default constructor checks no contract).
408 When the [classref boost::contract::constructor_precondition] base class is used:
409 [footnote
410 There is a MSVC bug that was fixed in MSVC 2013 for which lambdas cannot be used in constructor member initialization lists for templates.
411 On MSVC compilers with that bug, an extra (static) member function can be used (together with `bind` and `cref` as needed) to program constructor preconditions instead of using lambdas (see __No_Lambda_Functions__).
412 ]
413
414 * It should be specified as the /first/ class in the inheritance list (so constructor preconditions are checked before initializing any other base class or data member).
415 * Its inheritance access specifier should always be `private` (so this extra base class does not alter the public inheritance tree of its derived classes).
416 * It should never be declared as a `virtual` base (because virtual bases are initialized only once across the entire inheritance hierarchy preventing preconditions of other base classes from being checked).
417 * It takes the derived class as template parameter.
418 [footnote
419 *Rationale:*
420 The [classref boost::contract::constructor_precondition] takes the derived class as its template parameter (using the Curiously Recursive Template Pattern, CRTP) so the instantiated template type is unique for each derived class.
421 This always avoids base class ambiguity resolution errors even when multiple inheritance is used.
422 Note that, as already mentioned, virtual inheritance could not be used instead of the template parameter here to resolve ambiguities (because virtual bases are initialized only once by the outer-most derived class, and that would not allow to properly check preconditions of all base classes).
423 ]
424
425 [note
426 A class can avoid inheriting from [classref boost::contract::constructor_precondition] for efficiency but only when all its constructors have no preconditions.
427 ]
428
429 It is possible to specify postconditions for constructors (see __Postconditions__), but programmers should not access the old value of the object `*this` in constructor postconditions (because the object did not exist yet before the constructor body was executed).
430 [footnote
431 See __No_Lambda_Functions__ to enforce this constraint at compile-time (but not recommended because of extra boiler-plate code).
432 ]
433 It is also possible to specify exceptions guarantees for constructors (see __Exception_Guarantees__), but programmers should not access the object `*this` or its old value in constructor exception guarantees (because the object did not exist before executing the constructor body and it was not properly constructed given the constructor body threw an exception).
434 [footnote
435 See __No_Lambda_Functions__ to enforce these constraints at compile-time (but not recommended because of extra boiler-plate code).
436 ]
437 The [funcref boost::contract::constructor] function takes `this` as a parameter (because constructors check class invariants, see __Class_Invariants__).
438
439 The [funcref boost::contract::constructor] function returns an RAII object that must always be assigned to a local variable of type [classref boost::contract::check] (otherwise this library will generate a run-time error, see [macroref BOOST_CONTRACT_ON_MISSING_CHECK_DECL]).
440 Furthermore, C++11 `auto` declarations cannot be used here and the [classref boost::contract::check] type must be explicitly specified (otherwise this library will generate a compile-time error prior C++17 and a run-time error post C++17).
441 The constructor body is programmed right after the declaration of this RAII object.
442
443 At construction, the [classref boost::contract::check] RAII object for constructors does the following (enclosing constructor entry):
444
445 # Check static class invariants, by calling [^['type-of]]`(*this)::static_invariant()` (but not non-static class invariants because the object does not exist yet).
446
447 At destruction instead (enclosing constructor exit):
448
449 # Check static class invariants, by calling [^['type-of]]`(*this)::static_invariant()`.
450 # If the constructor body did not throw an exception:
451     # Check non-static class invariants, by calling `this->invariant()`.
452     # Check postconditions, by calling the nullary functor [^['s]]`()` passed to `.postcondition(`[^['s]]`)`.
453 # Else:
454     # Check exception guarantees, by calling the nullary functor [^['e]]`()` passed to `.except(`[^['e]]`)`.
455
456 This together with C++ object construction mechanism of base classes and the use of [classref boost::contract::constructor_precondition] ensures that the constructor contracts are correctly checked at run-time (see __Constructor_Calls__).
457
458 [note
459 A constructor can avoid calling [funcref boost::contract::constructor] for efficiency but only when it has no postconditions, no exception guarantees, and its class has no invariants (even if [funcref boost::contract::constructor] is not used by a derived class, contracts of base class constructors will still be correctly checked by C++ object construction mechanism).
460
461 The default constructor and copy constructor automatically generated by C++ will not check contracts.
462 Therefore, unless these constructors are not public or they have no preconditions, no postconditions, no exception guarantees, and their class has no invariants, programmers should manually define them using [funcref boost::contract::constructor] and [classref boost::contract::constructor_precondition].
463 Similar considerations apply to all other constructors automatically generated by C++ (e.g., the move constructor).
464 ]
465
466 [heading Private and Protected Constructors]
467
468 Private and protected constructors can omit [funcref boost::contract::constructor] (because they are not part of the public interface of the class so they are not required to check class invariants, see __Constructor_Calls__).
469 They could still use [classref boost::contract::constructor_precondition] to check preconditions before member initializations, and even use [funcref boost::contract::function] (but not [funcref boost::contract::constructor]) to only check postconditions and exception guarantees without checking class invariants and without calling `.precondition(...)` (see __Private_and_Protected_Functions__).
470 For example:
471
472     class u : private boost::contract::constructor_precondition<u> {
473     protected:
474         // Contract for a protected constructor (same for private constructors).
475         u() : // Still use this base class to check constructor preconditions.
476             boost::contract::constructor_precondition<u>([&] {
477                 BOOST_CONTRACT_ASSERT(...);
478                 ...
479             })
480         {
481             // Following will correctly not check class invariants.
482             boost::contract::check c = boost::contract::function()
483                 // Do not use `.precondition(...)` here.
484                 .postcondition([&] {
485                     BOOST_CONTRACT_ASSERT(...);
486                     ...
487                 })
488                 .except([&] {
489                     BOOST_CONTRACT_ASSERT(...);
490                     ...
491                 })
492             ;
493
494             ... // Constructor body.
495         }
496
497         ...
498     };
499
500 [endsect]
501
502 [section Destructors]
503
504 Contracts for destructors are programmed using [funcref boost::contract::destructor].
505 For example (see [@../../example/features/public.cpp =public.cpp=]):
506
507 [public_class_begin]
508 [public_destructor]
509 [public_class_end]
510
511 It is not possible to specify preconditions for destructors (this library will generate a compile-time error if `.precondition(...)` is used here and that is because destructors can be called at any time after construction so they have no precondition).
512 It is possible to specify postconditions for destructors (see __Postconditions__, and also __Static_Public_Functions__ for an example), but programmers should not access the object `*this` in destructor postconditions (because the object no longer exists after the destructor body has been executed).
513 [footnote
514 See __No_Lambda_Functions__ to enforce this constraint at compile-time (but not recommended because of extra boiler-plate code).
515 ]
516 It is also possible to specify exceptions guarantees for destructors (see __Exception_Guarantees__, even if destructors should usually be programmed to not throw exceptions in C++, in fact destructors are implicitly declared `noexcept` since C++11).
517 [footnote
518 Exceptions guarantees in destructors can access both the object `*this` and its old value because the object existed before executing the destructor body and it still exists given the destructor body failed throwing an exception so technically the object should still be properly constructed and satisfy its class invariants.
519 ]
520 The [funcref boost::contract::destructor] function takes `this` as a parameter (because destructors check class invariants, see __Class_Invariants__).
521
522 The [funcref boost::contract::destructor] function returns an RAII object that must always be assigned to a local variable of type [classref boost::contract::check] (otherwise this library will generate a run-time error, see [macroref BOOST_CONTRACT_ON_MISSING_CHECK_DECL]).
523 Furthermore, C++11 `auto` declarations cannot be used here and the [classref boost::contract::check] type must be explicitly specified (otherwise this library will generate a compile-time error prior C++17 and a run-time error post C++17).
524 The destructor body is programmed right after the declaration of this RAII object.
525
526 At construction, the [classref boost::contract::check] RAII object for destructors does the following (enclosing destructor entry):
527
528 # Check static and non-static class invariants, by calling ['[^type-of]]`(*this)::static_invariant()` __AND__ `this->invariant()`.
529
530 At destruction instead (enclosing destructor exit):
531
532 # Check static class invariants, by calling [^['type-of]]`(*this)::static_invariant()`.
533 # If the destructor body did not throw an exception:
534     # Check postconditions, by calling the nullay functor [^['s]]`()` passed to `.postcondition(`[^['s]]`)`.
535 # Else (even if destructors should generally be programmed not to throw in C++):
536     # Check non-static class invariants, by calling `this->invariant()` (because the object was not successfully destructed).
537     # Check exception guarantees, by calling the nullary functor [^['e]]`()` passed to `.except(`[^['e]]`)`.
538
539 This together with C++ object destruction mechanism of base classes ensures that destructor contracts are correctly checked at run-time (see __Destructor_Calls__).
540
541 [note
542 A destructor can avoid calling [funcref boost::contract::destructor] for efficiency but only when it has no postconditions, no exception guarantees, and its class has no invariants (even if [funcref boost::contract::destructor] is not used by a derived class, contracts of base class destructors will still be correctly checked by C++ object destruction mechanism).
543
544 The default destructor automatically generated by C++ will not check contracts.
545 Therefore, unless the destructor is not public or it has no postconditions, no exception guarantees, and its class has no invariants, programmers should manually define it using [funcref boost::contract::destructor].
546 ]
547
548 [heading Private and Protected Destructors]
549
550 Private and protected destructors can omit [funcref boost::contract::destructor] (because they are not part of the public interface of the class so they are not required to check class invariants, see __Destructor_Calls__).
551 They could use [funcref boost::contract::function] (but not [funcref boost::contract::destructor]) to only check postconditions and exception guarantees without checking class invariants and without calling `.precondition(...)` (see __Private_and_Protected_Functions__).
552 For example:
553
554     class u {
555     protected:
556         // Contract for a protected destructor (same for private destructors).
557         virtual ~u() {
558             // Following will correctly not check class invariants.
559             boost::contract::check c = boost::contract::function()
560                 // Do not use `.precondition(...)` here.
561                 .postcondition([&] {
562                     BOOST_CONTRACT_ASSERT(...);
563                     ...
564                 })
565                 // Could use `.except(...)` here in rare cases of destructors declared to throw.
566             ;
567
568             ... // Destructor body.
569         }
570
571         ...
572     };
573
574 [endsect]
575
576 [section Public Functions]
577
578 Contracts for public functions are programmed using [funcref boost::contract::public_function].
579 In this section, let's consider public functions that are not static, not virtual, and do not override any function from base classes.
580 For example (see [@../../example/features/public.cpp =public.cpp=]):
581
582 [public_class_begin]
583 [public_function]
584 [public_class_end]
585
586 It is possible to specify preconditions, postconditions, and exception guarantees for public functions (see __Preconditions__, __Postconditions__, and __Exception_Guarantees__).
587 When called from non-static public functions, the [funcref boost::contract::public_function] function takes `this` as a parameter (because public functions check class invariants, see __Class_Invariants__).
588
589 The [funcref boost::contract::public_function] function returns an RAII object that must always be assigned to a local variable of type [classref boost::contract::check] (otherwise this library will generate a run-time error, see [macroref BOOST_CONTRACT_ON_MISSING_CHECK_DECL]).
590 Furthermore, C++11 `auto` declarations cannot be used here and the [classref boost::contract::check] type must be explicitly specified (otherwise this library will generate a compile-time error prior C++17 and a run-time error post C++17).
591 The public function body is programmed right after the declaration of this RAII object.
592
593 At construction, the [classref boost::contract::check] RAII object for public functions does the following (enclosing public function entry):
594
595 # Check static and non-static class invariants, by calling [^['type-of]]`(*this)::static_invariant()` __AND__ `this->invariant()`.
596 # Check preconditions, by calling the nullary functor [^['r]]`()` passed to `.precondition(`[^['r]]`)`.
597
598 At destruction instead (enclosing public function exit):
599
600 # Check static and non-static class invariants, by calling [^['type-of]]`(*this)::static_invariant()` __AND__ `this->invariant()` (even if the function body threw an exception).
601 # If the function body did not throw an exception:
602     # Check postconditions, by calling the nullary functor [^['s]]`()` passed to `.postcondition(`[^['s]]`)`.
603 # Else:
604     # Check exception guarantees, by calling the nullary functor [^['e]]`()` passed to `.except(`[^['e]]`)`.
605
606 This ensures that public function contracts are correctly checked at run-time (see __Public_Function_Calls__).
607
608 [note
609 A public function can avoid calling [funcref boost::contract::public_function] for efficiency but only when it has no preconditions, no postconditions, no exception guarantees, it is not virtual, it does not override any virtual function, and its class has no invariants.
610
611 The default copy assignment operator automatically generated by C++ will not check contracts.
612 Therefore, unless this operator is not public or it has no preconditions, no postconditions, no exception guarantees, and its class has no invariants, programmers should manually define it using [funcref boost::contract::public_function].
613 Similar considerations apply to all other operators automatically generated by C++ (e.g., the move operator).
614 ]
615
616 [endsect]
617
618 [section Virtual Public Functions]
619
620 Contracts for public functions are programmed using [funcref boost::contract::public_function].
621 In this section, let's consider public functions that are virtual but that do not override any function from base classes.
622 For example (see [@../../example/features/public.cpp =public.cpp=]):
623
624 [public_class_begin]
625 [public_virtual_function]
626 [public_class_end]
627
628 Virtual public functions must declare an extra trailing parameter of type [classref boost::contract::virtual_]`*` with default value `0` (i.e., `nullptr`).
629 [footnote
630 The name of this extra parameter is arbitrary, but `v` is often used in this documentation.
631 ]
632 This extra parameter is the last parameter and it has a default value so it does not alter the calling interface of the virtual function (callers will rarely, if ever, have to explicitly deal with this extra parameter a part from when manipulating the virtual function type directly for function pointer type-casting, etc.).
633 Programmers must pass the extra virtual parameter as the very first argument to all [macroref BOOST_CONTRACT_OLDOF] and [funcref boost::contract::public_function] calls in the virtual public function definition.
634 [footnote
635 *Rationale:*
636 The [classref boost::contract::virtual_]`*` parameter is used by this library to determine that a function is virtual (in C++ it is not possible to introspect if a function is declared `virtual`).
637 Furthermore, this parameter is internally used by this library to implement subcontracting (specifically to pass result and old values that are evaluated by the overriding function to the contracts of overridden virtual functions in base classes, and also to check preconditions, postconditions, and exception guarantees of overridden virtual functions in __OR__ and __AND__ with contracts of the overriding virtual function).
638 ]
639
640 When called from virtual public functions, the [funcref boost::contract::public_function] function takes `this` as a parameter (because public functions check class invariants, see __Class_Invariants__).
641 For virtual public functions returning `void`:
642
643     class u {
644     public:
645         // A void virtual public function (that does not override).
646         virtual void f(t_1 a_1, ..., t_n a_n, boost::contract::virtual_* v = 0) {
647             boost::contract::check c = boost::contract::public_function(
648                     v, this)                                    // No result parameter...
649                 .precondition([&] { ... })
650                 .postcondition([&] { ... })                     // ...so nullary functor.
651                 .except([&] { ... })
652             ;
653
654             ...
655         }
656
657         ...
658     }
659
660 For virtual public functions not returning `void`, programmers must also pass a reference to the function return value as the second argument to [funcref boost::contract::public_function].
661 In this case, the library will pass this return value reference to the postcondition functor that must therefore take one single argument matching the return type, otherwise this library will generate a compile-time error (the functor parameter can be a constant reference `const&` to avoid extra copies of the return value):
662 [footnote
663 *Rationale:*
664 The extra function result parameter taken by the functor passed to `.postcondition(...)` is used by this library to pass the return value evaluated by the overriding function to all its overridden virtual functions to support subcontracting.
665 ]
666
667     class u {
668     public:
669         // A void virtual public function (that does not override).
670         virtual t f(t_1 a_1, ..., t_n a_n, boost::contract::virtual_* v = 0) {
671             t result;
672             boost::contract::check c = boost::contract::public_function(
673                     v, result, this)                            // Result parameter...
674                 .precondition([&] { ... })
675                 .postcondition([&] (t const& result) { ... })   // ...so unary functor.
676                 .except([&] { ... })
677             ;
678
679             ...                                                 // Assign `result` at each return.
680         }
681
682         ...
683     }
684
685 [important
686 It is the responsibility of the programmers to pass the extra virtual parameter `v` to all [macroref BOOST_CONTRACT_OLDOF] and [funcref boost::contract::public_function] calls within virtual public functions, and also to pass the return value reference after `v` to [funcref boost::contract::public_function] for non-void virtual public functions.
687 This library cannot automatically generate compile-time errors if programmers fail to do so (but in general this will prevent the library from correctly checking contracts at run-time).
688 [footnote
689 *Rationale:*
690 This library does not require programmers to specify the function type when using [funcref boost::contract::public_function] for non-overriding virtual public functions.
691 Therefore, this library does not know if the enclosing function has a non-void return type so it cannot check if the return value reference is passed as required for non-overriding virtual public functions.
692 Instead the function type is passed to this library for virtual public function overrides and that also allows this library to give a compile-time error if the return value reference is missing in those cases.
693 ]
694
695 *Mnemonics:*
696 [:When `v` is present, always pass it as the first argument to [funcref boost::contract::public_function] and [macroref BOOST_CONTRACT_OLDOF].]
697 [:Always pass `result` to [funcref boost::contract::public_function] right after `v` for non-void functions.]
698 ]
699
700 For the rest, considerations made in __Public_Functions__ apply to virtual public functions as well.
701
702 [note
703 A virtual public function should always call [funcref boost::contract::public_function] (even if it has no preconditions, no postconditions, no exception guarantees, and its class has no invariants), otherwise this library will not be able to correctly use it for subcontracting.
704 ]
705
706 [endsect]
707
708 [section Public Function Overrides (Subcontracting)]
709
710 Contracts for public functions are programmed using [funcref boost::contract::public_function].
711 In this section, let's consider public functions (virtual or not) that override virtual public functions from one or more of their public base classes.
712 For example (see [@../../example/features/public.cpp =public.cpp=]):
713 [footnote
714 In this documentation, function overrides are often marked with the code comment `/* override */`.
715 On compilers that support C++11 virtual specifiers, the `override` identifier can be used instead (`override` is not used in the documentation simply because virtual specifiers are not widely supported yet, even by compilers that support C++11 lambda functions).
716 ]
717
718 [public_derived_class_begin]
719 [public_function_override]
720 [public_derived_class_end]
721
722 The extra `typedef` declared using [macroref BOOST_CONTRACT_BASE_TYPES] is required by this library for derived classes and it is internally used to detect base classes for subcontracting (see __Base_Classes__).
723 This library will generate a compile-time error if there is no suitable virtual function to override in any of the public base classes for subcontracting.
724 [footnote
725 The compile-time error generated by the library in this case is similar in principle to the error generated by the C++11 `override` specifier, but it is limited to functions with the extra [classref boost::contract::virtual_]`*` parameter and searched recursively only in `public` base classes passed to [macroref BOOST_CONTRACT_BASE_TYPES] because only those are considered for subcontracting.
726 ]
727
728 When called from  public function overrides, the [funcref boost::contract::public_function] function template takes an explicit template argument `override_`[^['function-name]] that must be defined using [macroref BOOST_CONTRACT_OVERRIDE]:
729     
730     BOOST_CONTRACT_OVERRIDE(``[^['function-name]]``)
731     
732 This can be declared at any point in the public section of the enclosing class (see __Access_Specifiers__ to use [macroref BOOST_CONTRACT_OVERRIDE] also in a non-public section of the class).
733 [macroref BOOST_CONTRACT_OVERRIDE] is used only once in a class for a given function name and overloaded functions can reuse the same [^override_['function-name]] definition (see __Function_Overloads__).
734 [macroref BOOST_CONTRACT_NAMED_OVERRIDE] can be used to generate a name different than [^override_['function-name]] (e.g., to avoid generating C++ reserved names containing double underscores "`__`" for function names that already start with an underscore "`_`", see __Named_Overrides__).
735 For convenience [macroref BOOST_CONTRACT_OVERRIDES] can be used with multiple function names instead of repeating [macroref BOOST_CONTRACT_OVERRIDE] for each function name (on compilers that support variadic macros).
736 For example, for three functions named `f`, `g`, and `h` (but same for any other number of functions), the following:
737
738     BOOST_CONTRACT_OVERRIDES(f, g, h)
739
740 Is equivalent to:
741 [footnote
742 There is no equivalent of [macroref BOOST_CONTRACT_NAMED_OVERRIDE] that operates on multiple function names at once ([macroref BOOST_CONTRACT_NAMED_OVERRIDE] is not expected to be used often so it can simply be repeated multiple times when needed).
743 ]
744
745     BOOST_CONTRACT_OVERRIDE(f)
746     BOOST_CONTRACT_OVERRIDE(g)
747     BOOST_CONTRACT_OVERRIDE(h)
748
749 Public function overrides must always list the extra trailing parameter of type [classref boost::contract::virtual_]`*` with default value `0` (i.e., `nullptr`), even when they are not declared `virtual`, if this parameter is present in the signature of the virtual function being overridden from base classes.
750 Programmers must pass the extra virtual parameter as the very first argument to all [macroref BOOST_CONTRACT_OLDOF] and [funcref boost::contract::public_function] calls in the public function override definition (see __Virtual_Public_Functions__).
751
752 When called from public function overrides, the [funcref boost::contract::public_function] function takes a pointer to the enclosing function, the object `*this` (because public function overrides check class invariants, see __Class_Invariants__), and references to each function argument in the order they appear in the function declaration.
753 [footnote
754 *Rationale:*
755 The object `this` is passed after the function pointer to follow `std::bind`'s syntax.
756 The function pointer and references to all function arguments are needed for public function overrides because this library has to internally call overridden virtual public functions to check their contracts for subcontracting (even if this library will not actually execute the bodies of the overridden functions).
757 ]
758 For public function overrides returning `void`:
759
760     class u {
761     public:
762         // A void public function override.
763         void f(t_1 a_1, ..., t_n a_n, boost::contract::virtual_* v = 0) /* override */ {
764             boost::contract::check c = boost::contract::public_function<override_f>(
765                     v, &u::f, this, a_1, ..., a_n)              // No result parameter...
766                 .precondition([&] { ... })
767                 .postcondition([&] { ... })                     // ...so nullary functor.
768                 .except([&] { ... })
769             ;
770
771             ...
772         }
773         BOOST_CONTRACT_OVERRIDE(f)
774
775         ...
776     }
777
778 For public function overrides not returning `void`, programmers must also pass a reference to the function return value as the second argument to [funcref boost::contract::public_function] (this library will generate a compile-time error otherwise).
779 [footnote
780 *Rationale:*
781 As for non-overriding virtual public functions, also public function overrides use the extra return value parameter to pass it to the overridden functions when subcontracting.
782 In the case of public function overrides, this library has the function pointer so it will generate a compile-time error if the function is non-void and programmers forget to specify the extra return value parameter (this extra error checking is not possible instead for non-overriding virtual public functions because their contracts do not take the function pointer as a parameter, see __Virtual_Public_Functions__).
783 ]
784 In this case, the library will pass this return value reference to the postcondition functor that must therefore take one single argument matching the return type, otherwise this library will generate a compile-time error (the functor parameter can be a constant reference `const&` to avoid extra copies of the return value, similarly to non-overriding non-void __Virtual_Public_Functions__):
785
786     class u {
787     public:
788         // A non-void public function override.
789         t f(t_1 a_1, ..., t_n a_n, boost::contract::virtual_* v = 0) /* override */ {
790             t result;
791             boost::contract::check c = boost::contract::public_function<override_f>(
792                     v, result, &u::f, this, a_1, ..., a_n)      // Result parameter...
793                 .precondition([&] { ... })
794                 .postcondition([&] (t const& result) { ... })   // ...so unary functor.
795                 .except([&] { ... })
796             ;
797
798             ...                                                 // Assign `result` at each return.
799         }
800         BOOST_CONTRACT_OVERRIDE(f)
801
802         ...
803     }
804
805 This library will throw [classref boost::contract::bad_virtual_result_cast] if programmers specify return values for public function overrides in derived classes that are not consistent with the return types of the virtual public functions being overridden in the base classes.
806 [footnote
807 *Rationale:*
808 The `boost::bad_any_cast` exception was not used here because it does not print the from- and to- type names (so it is not descriptive enough).
809 ]
810
811 [important
812 It is the responsibility of the programmers to pass the extra virtual parameter `v` to all [macroref BOOST_CONTRACT_OLDOF] and [funcref boost::contract::public_function] calls within public function overrides, and also to pass the return value reference after `v` to [funcref boost::contract::public_function] for non-void public function overrides.
813 This library cannot always generate compile-time errors if programmers fail to do so (but in general this will prevent the library from correctly checking contracts at run-time).
814
815 *Mnemonics:*
816 [:When `override_...` is present, always pass it as template parameter to [funcref boost::contract::public_function].]
817 [:When `v` is present, always pass it as the first argument to [funcref boost::contract::public_function] and [macroref BOOST_CONTRACT_OLDOF].]
818 [:Always pass `result` to [funcref boost::contract::public_function] right after `v` for non-void functions.]
819 ]
820
821 At construction, the [classref boost::contract::check] RAII object for public function overrides does the following (enclosing public function override entry):
822
823 # Check static and non-static class invariants for all overridden bases and for the derived class in __AND__ with each other, by calling [^['type-of](['overridden-base_1])]`::static_invariant()` __AND__ [^['overridden-base_1]]`.invariant()` __AND__... [^['type-of](['overridden-base_n])]`::static_invariant()` __AND__ [^['overridden-base_n]]`.invariant()` __AND__ [^['type-of]]`(*this)::static_invariant()` __AND__ `this->invariant()`.
824 # Check preconditions for all overridden base functions and for the overriding derived function in __OR__ with each other, by calling the nullary functors [^['r_1]]`()` __OR__... [^['r_n]]`()` __OR__ [^['r]]`()` passed to `.precondition(`[^['r_1]]`)`, ... `.precondition(`[^['r_n]]`)`, `.precondition(`[^['r]]`)` for all of the overridden and overriding functions respectively.
825
826 At destruction instead (enclosing public function override exit):
827
828 # Check static and non-static class invariants for all overridden bases and for the derived class in __AND__ with each other, by calling [^['type-of](['overridden-base_1])]`::static_invariant()` __AND__ [^['overridden-base_1]]`.invariant()` __AND__... [^['type-of](['overridden-base_n])]`::static_invariant()` __AND__ [^['overridden-base_n]]`.invariant()` __AND__ [^['type-of]]`(*this)::static_invariant()` __AND__ `this->invariant()` (even if the function body threw an exception).
829 # If the function body did not throw an exception:
830     # Check postconditions for all overridden base functions and for the overriding derived function in __AND__ with each other, by calling the nullary functors [^['s_1]]`()` __AND__... [^['s_n]]`()` __AND__ [^['s]]`()` passed to `.postcondition(`[^['s_1]]`)`, ... `.postcondition(`[^['s_n]]`)`, `.postcondition(`[^['s]]`)` for all of the overridden and overriding functions respectively (or the unary functors [^['s_1]]`(`[^['result]]`)` __AND__... [^['s_n]]`(`[^['result]]`)` __AND__ [^['s]]`(`[^['result]]`)` for non-void public function overrides).
831 # Else:
832     # Check exception guarantees for all overridden base functions and for the overriding derived function in __AND__ with each other, by calling the nullary functors [^['e_1]]`()` __AND__... [^['e_n]]`()` __AND__ [^['e]]`()` passed to `.except(`[^['e_1]]`)`, ... `.except(`[^['e_n]]`)`, `.except(`[^['e]]`)` for all of the overridden and overriding functions respectively.
833
834 This ensures that contracts and subcontracts of public function overrides are correctly checked at run-time in accordance with the __substitution_principle__ (see __Public_Function_Calls__).
835
836 For the rest, considerations made in __Virtual_Public_Functions__ apply to public function overrides as well.
837
838 [note
839 A public function override should always call [funcref boost::contract::public_function] (even if it has no preconditions, no postconditions, no exception guarantees, and its class has no invariants), otherwise this library will not be able to correctly use it for subcontracting.
840 ]
841
842 [endsect]
843
844 [section Base Classes (Subcontracting)]
845
846 In order for this library to support subcontracting, programmers must specify the bases of a derived class declaring a public member type named `base_types` via a `typedef` using [macroref BOOST_CONTRACT_BASE_TYPES].
847 For example (see [@../../example/features/base_types.cpp =base_types.cpp=]):
848
849 [import ../example/features/base_types.cpp]
850 [base_types]
851
852 For convenience, a /local macro/ named `BASES` can be used to avoid repeating the base list twice (first in the derived class declaration `class `[^['class-name]]` : `[^['base-list]] and then again when invoking `BOOST_CONTRACT_BASE_TYPES(`[^['base-list]]`)`).
853 Being a local macro, `BASES` must be undefined using `#undef BASES` after it is used to declare the `base_types` `typedef` (to avoid name clashes and macro redefinition errors).
854 [footnote
855 The name of this local macro is arbitrary, but `BASES` is often used in this documentation.
856 ]
857
858 [macroref BOOST_CONTRACT_BASE_TYPES] is a variadic macro and accepts a list of bases separated by commas (see __No_Macros__ to program `base_types` without using macros).
859 As already noted in __Constructors__, when the extra base [classref boost::contract::constructor_precondition] is used to program constructor preconditions, its inheritance access level must always be `private` and it must be specified as the very first base.
860
861 [important
862 Each base passed to [macroref BOOST_CONTRACT_BASE_TYPES] must /explicitly/ specify its inheritance access level `public`, `protected`, or `private` (but `virtual` is optional and can be specified either before or after the access level as usual in C++).
863 This library will generate a compile-time error if the first base is missing its inheritance access level, but this library will not be able to always generate an error if the access level is missing for bases after the first one.
864 [footnote
865 *Rationale:*
866 This library explicitly requires the inheritance access level because derived classes must subcontract only from public bases, but not from protected or private bases (see __Public_Function_Calls__).
867 [macroref BOOST_CONTRACT_BASE_TYPES] inspects each inheritance access level using preprocessor meta-programming and removes non-public bases from the list of bases internally used for subcontracting.
868 However, this library cannot always detect when programmers forget to specify the inheritance access level because, when commas are used to separate template parameters passed to base classes, the preprocessor will not be able to correctly use commas to identify the next base class token in the inheritance list (the preprocessor cannot distinguish between commas that are not protected by round parenthesis, like the ones used in templates).
869 Therefore, this library uses the inheritance access level keyword `public`, `protected`, or `private` instead of commas `,` for the preprocessor to correctly find the next base class token in the inheritance list (thus inheritance access levels must always be explicit specified by programmers for each base).
870 ]
871 It is the responsibility of the programmers to make sure that all bases passed to [macroref BOOST_CONTRACT_BASE_TYPES] explicitly specify their inheritance access level (inheritance access levels are instead optional in C++ because `private` is implicitly assumed for `class` types and `public` for `struct` types).
872
873 *Mnemonics:*
874 [:Always explicitly specify the inheritance access level `public`, `protected`, or `private` for base classes passed to [macroref BOOST_CONTRACT_BASE_TYPES].]
875 ]
876
877 See __Access_Specifiers__ to avoid making the `base_types` member type `public`.
878 [footnote
879 In this documentation the `base_type` member type is often declared `public` for simplicity.
880 However, in production code it might not be acceptable to augment the public members of a class adding the `base_types` type (and that can be avoided using [classref boost::contract::access] as explained in __Access_Specifiers__).
881 ]
882 See [macroref BOOST_CONTRACT_BASES_TYPEDEF] to use a name different from `base_types` (e.g., because `base_types` clashes with other names in user-defined classes).
883
884 [endsect]
885
886 [section Static Public Functions]
887
888 Contracts for public functions are programmed using [funcref boost::contract::public_function].
889 In this section, let's consider static public functions.
890 For example (see [@../../example/features/static_public.cpp =static_public.cpp=]):
891
892 [import ../example/features/static_public.cpp]
893 [static_public]
894
895 It is possible to specify preconditions, postconditions, and exception guarantees for static public functions (see __Preconditions__, __Postconditions__, and __Exception_Guarantees__).
896 When called from static public functions, [funcref boost::contract::public_function] cannot take the object `this` as a parameter (because there is no object `this` in static member functions) so the enclosing class type is specified via an explicit template parameter as in [funcref boost::contract::public_function][^<['class-type]>] (the class type is required to check static class invariants, see __Class_Invariants__):
897
898     class u {
899     public:
900         // A static public function.
901         static void f() {
902             boost::contract::check c = boost::contract::public_function<u>() // Class type `u` as explicit template parameter.
903                 .precondition([&] { ... })
904                 .postcondition([&] { ... })
905                 .except([&] { ... })
906             ;
907
908             ...
909         }
910
911         ...
912     };
913
914 The [funcref boost::contract::public_function] function returns an RAII object that must be assigned to a local variable of type [classref boost::contract::check] (otherwise this library will generate a run-time error, see [macroref BOOST_CONTRACT_ON_MISSING_CHECK_DECL]).
915 Furthermore, C++11 `auto` declarations cannot be used here and the [classref boost::contract::check] type must be explicitly specified (otherwise this library will generate a compile-time error prior C++17 and a run-time error post C++17).
916 The static public functions body is programmed right after the declaration of this RAII object.
917
918 At construction, the [classref boost::contract::check] RAII object for static public functions does the following (enclosing static public function entry):
919
920 # Check static class invariants, by calling [^['class-type]]`::static_invariant()` (but never non-static class invariants).
921 # Check preconditions, by calling the nullary functor [^['r]]`()` passed to `.precondition(`[^['r]]`)`.
922
923 At destruction instead (enclosing static public function exit):
924
925 # Check static class invariants, by calling [^['class-type]]`::static_invariant()` (even if the function body threw an exception, but never non-static class invariants).
926 # If the function body did not throw an exception:
927     # Check postconditions, by calling the nullary functor [^['s]]`()` passed to `.postcondition(`[^['s]]`)`.
928 # Else:
929     # Check exception guarantees, by calling the nullary functor [^['e]]`()` passed to `.except(`[^['e]]`)`.
930
931 This ensures that static public function contracts are correctly checked at run-time (static public functions do not subcontract because they have no object `this` and therefore there is no inheritance, see __Public_Function_Calls__).
932
933 [note
934 A static public function can avoid calling [funcref boost::contract::public_function] for efficiency but only when it has no preconditions, no postconditions, no exception guarantees, and its class has no static invariants (the class can still have non-static invariants or base classes instead).
935 ]
936
937 [endsect]
938
939 [endsect]
940