Line data Source code
1 : // (C) Copyright Gennadiy Rozental 2001.
2 : // Distributed under the Boost Software License, Version 1.0.
3 : // (See accompanying file LICENSE_1_0.txt or copy at
4 : // http://www.boost.org/LICENSE_1_0.txt)
5 :
6 : // See http://www.boost.org/libs/test for the library home page.
7 : //
8 : // File : $RCSfile$
9 : //
10 : // Version : $Revision: 74248 $
11 : //
12 : // Description : implementation details for old toolbox
13 : // ***************************************************************************
14 :
15 : #ifndef BOOST_TEST_TOOLS_OLD_IMPL_HPP_012705GER
16 : #define BOOST_TEST_TOOLS_OLD_IMPL_HPP_012705GER
17 :
18 : // Boost.Test
19 : #include <boost/test/unit_test_log.hpp>
20 : #include <boost/test/tools/assertion_result.hpp>
21 : #include <boost/test/tools/floating_point_comparison.hpp>
22 :
23 : #include <boost/test/tools/detail/fwd.hpp>
24 : #include <boost/test/tools/detail/print_helper.hpp>
25 :
26 : // Boost
27 : #include <boost/limits.hpp>
28 : #include <boost/numeric/conversion/conversion_traits.hpp> // for numeric::conversion_traits
29 : #include <boost/type_traits/is_array.hpp>
30 :
31 : #include <boost/preprocessor/repetition/repeat.hpp>
32 : #include <boost/preprocessor/arithmetic/add.hpp>
33 :
34 : // STL
35 : #include <cstddef> // for std::size_t
36 : #include <climits> // for CHAR_BIT
37 :
38 : #include <boost/test/detail/suppress_warnings.hpp>
39 :
40 : //____________________________________________________________________________//
41 :
42 : namespace boost {
43 : namespace test_tools {
44 : namespace tt_detail {
45 :
46 : // ************************************************************************** //
47 : // ************** old TOOLBOX Implementation ************** //
48 : // ************************************************************************** //
49 :
50 : // This function adds level of indirection, but it makes sure we evaluate predicate
51 : // arguments only once
52 :
53 : #ifndef BOOST_TEST_PROD
54 : #define TEMPL_PARAMS( z, m, dummy ) , typename BOOST_JOIN( Arg, m )
55 :
56 : #define FUNC_PARAMS( z, m, dummy ) \
57 : , BOOST_JOIN( Arg, m ) const& BOOST_JOIN( arg, m ) \
58 : , char const* BOOST_JOIN( BOOST_JOIN( arg, m ), _descr ) \
59 : /**/
60 :
61 : #define PRED_PARAMS( z, m, dummy ) BOOST_PP_COMMA_IF( m ) BOOST_JOIN( arg, m )
62 :
63 : #define ARG_INFO( z, m, dummy ) \
64 : , BOOST_JOIN( BOOST_JOIN( arg, m ), _descr ) \
65 : , &static_cast<const unit_test::lazy_ostream&>(unit_test::lazy_ostream::instance() \
66 : << ::boost::test_tools::tt_detail::print_helper( BOOST_JOIN( arg, m ) )) \
67 : /**/
68 :
69 : #define IMPL_FRWD( z, n, dummy ) \
70 : template<typename Pred \
71 : BOOST_PP_REPEAT_ ## z( BOOST_PP_ADD( n, 1 ), TEMPL_PARAMS, _ )> \
72 : inline bool \
73 : check_frwd( Pred P, unit_test::lazy_ostream const& assertion_descr, \
74 : const_string file_name, std::size_t line_num, \
75 : tool_level tl, check_type ct \
76 : BOOST_PP_REPEAT_ ## z( BOOST_PP_ADD( n, 1 ), FUNC_PARAMS, _ ) \
77 : ) \
78 : { \
79 : return \
80 : report_assertion( P( BOOST_PP_REPEAT_ ## z(BOOST_PP_ADD(n, 1), PRED_PARAMS,_) ),\
81 : assertion_descr, file_name, line_num, tl, ct, \
82 : BOOST_PP_ADD( n, 1 ) \
83 : BOOST_PP_REPEAT_ ## z( BOOST_PP_ADD( n, 1 ), ARG_INFO, _ ) \
84 : ); \
85 : } \
86 : /**/
87 :
88 : #ifndef BOOST_TEST_MAX_PREDICATE_ARITY
89 : #define BOOST_TEST_MAX_PREDICATE_ARITY 5
90 : #endif
91 :
92 2188029 : BOOST_PP_REPEAT( BOOST_TEST_MAX_PREDICATE_ARITY, IMPL_FRWD, _ )
93 :
94 : #undef TEMPL_PARAMS
95 : #undef FUNC_PARAMS
96 : #undef PRED_INFO
97 : #undef ARG_INFO
98 : #undef IMPL_FRWD
99 :
100 : #endif
101 :
102 : //____________________________________________________________________________//
103 :
104 : template <class Left, class Right>
105 2187883 : inline assertion_result equal_impl( Left const& left, Right const& right )
106 : {
107 2187883 : return left == right;
108 0 : }
109 :
110 : //____________________________________________________________________________//
111 :
112 : inline assertion_result equal_impl( char* left, char const* right ) { return equal_impl( static_cast<char const*>(left), static_cast<char const*>(right) ); }
113 : inline assertion_result equal_impl( char const* left, char* right ) { return equal_impl( static_cast<char const*>(left), static_cast<char const*>(right) ); }
114 : inline assertion_result equal_impl( char* left, char* right ) { return equal_impl( static_cast<char const*>(left), static_cast<char const*>(right) ); }
115 :
116 : #if !defined( BOOST_NO_CWCHAR )
117 : BOOST_TEST_DECL assertion_result equal_impl( wchar_t const* left, wchar_t const* right );
118 : inline assertion_result equal_impl( wchar_t* left, wchar_t const* right ) { return equal_impl( static_cast<wchar_t const*>(left), static_cast<wchar_t const*>(right) ); }
119 : inline assertion_result equal_impl( wchar_t const* left, wchar_t* right ) { return equal_impl( static_cast<wchar_t const*>(left), static_cast<wchar_t const*>(right) ); }
120 : inline assertion_result equal_impl( wchar_t* left, wchar_t* right ) { return equal_impl( static_cast<wchar_t const*>(left), static_cast<wchar_t const*>(right) ); }
121 : #endif
122 :
123 : //____________________________________________________________________________//
124 :
125 : struct equal_impl_frwd {
126 : template <typename Left, typename Right>
127 : inline assertion_result
128 2187885 : call_impl( Left const& left, Right const& right, mpl::false_ ) const
129 : {
130 2187885 : return equal_impl( left, right );
131 : }
132 :
133 : template <typename Left, typename Right>
134 : inline assertion_result
135 6 : call_impl( Left const& left, Right const& right, mpl::true_ ) const
136 : {
137 6 : return (*this)( right, &left[0] );
138 : }
139 :
140 : template <typename Left, typename Right>
141 : inline assertion_result
142 2187891 : operator()( Left const& left, Right const& right ) const
143 : {
144 : typedef typename is_array<Left>::type left_is_array;
145 2187891 : return call_impl( left, right, left_is_array() );
146 : }
147 : };
148 :
149 : //____________________________________________________________________________//
150 :
151 : struct ne_impl {
152 : template <class Left, class Right>
153 202 : assertion_result operator()( Left const& left, Right const& right )
154 : {
155 202 : return !equal_impl_frwd()( left, right );
156 0 : }
157 : };
158 :
159 : //____________________________________________________________________________//
160 :
161 : struct lt_impl {
162 : template <class Left, class Right>
163 5 : assertion_result operator()( Left const& left, Right const& right )
164 : {
165 5 : return left < right;
166 : }
167 : };
168 :
169 : //____________________________________________________________________________//
170 :
171 : struct le_impl {
172 : template <class Left, class Right>
173 13 : assertion_result operator()( Left const& left, Right const& right )
174 : {
175 13 : return left <= right;
176 : }
177 : };
178 :
179 : //____________________________________________________________________________//
180 :
181 : struct gt_impl {
182 : template <class Left, class Right>
183 9 : assertion_result operator()( Left const& left, Right const& right )
184 : {
185 9 : return left > right;
186 : }
187 : };
188 :
189 : //____________________________________________________________________________//
190 :
191 : struct ge_impl {
192 : template <class Left, class Right>
193 113 : assertion_result operator()( Left const& left, Right const& right )
194 : {
195 113 : return left >= right;
196 : }
197 : };
198 :
199 : //____________________________________________________________________________//
200 :
201 : struct equal_coll_impl {
202 : template <typename Left, typename Right>
203 39 : assertion_result operator()( Left left_begin, Left left_end, Right right_begin, Right right_end )
204 : {
205 39 : assertion_result pr( true );
206 39 : std::size_t pos = 0;
207 :
208 557 : for( ; left_begin != left_end && right_begin != right_end; ++left_begin, ++right_begin, ++pos ) {
209 514 : if( *left_begin != *right_begin ) {
210 0 : pr = false;
211 0 : pr.message() << "\nMismatch at position " << pos << ": "
212 0 : << ::boost::test_tools::tt_detail::print_helper(*left_begin)
213 0 : << " != "
214 0 : << ::boost::test_tools::tt_detail::print_helper(*right_begin);
215 0 : }
216 514 : }
217 :
218 39 : if( left_begin != left_end ) {
219 0 : std::size_t r_size = pos;
220 0 : while( left_begin != left_end ) {
221 0 : ++pos;
222 0 : ++left_begin;
223 : }
224 :
225 0 : pr = false;
226 0 : pr.message() << "\nCollections size mismatch: " << pos << " != " << r_size;
227 0 : }
228 :
229 39 : if( right_begin != right_end ) {
230 0 : std::size_t l_size = pos;
231 0 : while( right_begin != right_end ) {
232 0 : ++pos;
233 0 : ++right_begin;
234 : }
235 :
236 0 : pr = false;
237 0 : pr.message() << "\nCollections size mismatch: " << l_size << " != " << pos;
238 0 : }
239 :
240 39 : return pr;
241 39 : }
242 : };
243 :
244 : //____________________________________________________________________________//
245 :
246 : struct bitwise_equal_impl {
247 : template <class Left, class Right>
248 : assertion_result operator()( Left const& left, Right const& right )
249 : {
250 : assertion_result pr( true );
251 :
252 : std::size_t left_bit_size = sizeof(Left)*CHAR_BIT;
253 : std::size_t right_bit_size = sizeof(Right)*CHAR_BIT;
254 :
255 : static Left const leftOne( 1 );
256 : static Right const rightOne( 1 );
257 :
258 : std::size_t total_bits = left_bit_size < right_bit_size ? left_bit_size : right_bit_size;
259 :
260 : for( std::size_t counter = 0; counter < total_bits; ++counter ) {
261 : if( ( left & ( leftOne << counter ) ) != ( right & ( rightOne << counter ) ) ) {
262 : pr = false;
263 : pr.message() << "\nMismatch at position " << counter;
264 : }
265 : }
266 :
267 : if( left_bit_size != right_bit_size ) {
268 : pr = false;
269 : pr.message() << "\nOperands bit sizes mismatch: " << left_bit_size << " != " << right_bit_size;
270 : }
271 :
272 : return pr;
273 : }
274 : };
275 :
276 : //____________________________________________________________________________//
277 :
278 : template<typename FPT1, typename FPT2>
279 : struct comp_supertype {
280 : // deduce "better" type from types of arguments being compared
281 : // if one type is floating and the second integral we use floating type and
282 : // value of integral type is promoted to the floating. The same for float and double
283 : // But we don't want to compare two values of integral types using this tool.
284 : typedef typename numeric::conversion_traits<FPT1,FPT2>::supertype type;
285 : BOOST_STATIC_ASSERT_MSG( !is_integral<type>::value, "Only floating-point types can be compared!");
286 : };
287 :
288 : } // namespace tt_detail
289 :
290 : namespace fpc = math::fpc;
291 :
292 : // ************************************************************************** //
293 : // ************** check_is_close ************** //
294 : // ************************************************************************** //
295 :
296 : struct BOOST_TEST_DECL check_is_close_t {
297 : // Public typedefs
298 : typedef assertion_result result_type;
299 :
300 : template<typename FPT1, typename FPT2, typename ToleranceType>
301 : assertion_result
302 4 : operator()( FPT1 left, FPT2 right, ToleranceType tolerance ) const
303 : {
304 : typedef typename tt_detail::comp_supertype<FPT1,FPT2>::type super_type;
305 4 : fpc::close_at_tolerance<super_type> pred( tolerance, fpc::FPC_STRONG );
306 :
307 4 : assertion_result ar( pred( static_cast<super_type>(left), static_cast<super_type>(right) ) );
308 :
309 4 : if( !ar )
310 0 : ar.message() << pred.tested_rel_diff();
311 :
312 4 : return ar;
313 4 : }
314 : };
315 :
316 : //____________________________________________________________________________//
317 :
318 : template<typename FPT1, typename FPT2, typename ToleranceType>
319 : inline assertion_result
320 : check_is_close( FPT1 left, FPT2 right, ToleranceType tolerance )
321 : {
322 : return check_is_close_t()( left, right, tolerance );
323 : }
324 :
325 : //____________________________________________________________________________//
326 :
327 : // ************************************************************************** //
328 : // ************** check_is_small ************** //
329 : // ************************************************************************** //
330 :
331 : struct BOOST_TEST_DECL check_is_small_t {
332 : // Public typedefs
333 : typedef bool result_type;
334 :
335 : template<typename FPT>
336 : bool
337 : operator()( FPT fpv, FPT tolerance ) const
338 : {
339 : return fpc::is_small( fpv, tolerance );
340 : }
341 : };
342 :
343 : //____________________________________________________________________________//
344 :
345 : template<typename FPT>
346 : inline bool
347 : check_is_small( FPT fpv, FPT tolerance )
348 : {
349 : return fpc::is_small( fpv, tolerance );
350 : }
351 :
352 : //____________________________________________________________________________//
353 :
354 : } // namespace test_tools
355 : } // namespace boost
356 :
357 : #include <boost/test/detail/enable_warnings.hpp>
358 :
359 : #endif // BOOST_TEST_TOOLS_OLD_IMPL_HPP_012705GER
|