Assertion.h
1/*
2 * Copyright (C) 2005-2008 by Dr. Marc Boris Duerner
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * As a special exception, you may use this file as part of a free
10 * software library without restriction. Specifically, if other files
11 * instantiate templates or use macros or inline functions from this
12 * file, or you compile this file and link it with other files to
13 * produce an executable, this file does not by itself cause the
14 * resulting executable to be covered by the GNU General Public
15 * License. This exception does not however invalidate any other
16 * reasons why the executable file might be covered by the GNU Library
17 * General Public License.
18 *
19 * This library is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22 * Lesser General Public License for more details.
23 *
24 * You should have received a copy of the GNU Lesser General Public
25 * License along with this library; if not, write to the Free Software
26 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
27 */
28#ifndef PT_UNIT_ASSERTION_H
29#define PT_UNIT_ASSERTION_H
30
31#include <Pt/Unit/Api.h>
32#include "Pt/SourceInfo.h"
33#include <stdexcept>
34#include <sstream>
35#include <iostream>
36#include <cmath>
37#include <limits>
38
39namespace Pt {
40
41namespace Unit {
42
79 class PT_UNIT_API Assertion
80 {
81 public:
92 Assertion(const std::string& what, const SourceInfo& si);
93
96 const Pt::SourceInfo& sourceInfo() const;
97
98 const char* what() const { return _what.c_str(); }
99
100 private:
101 Pt::SourceInfo _sourceInfo;
102 std::string _what;
103 };
104
105 namespace { bool testCond = false; }
106
107 inline bool getFalse()
108 { return testCond; }
109
119 #define PT_UNIT_ASSERT(cond) \
120 do { \
121 if( !(cond) ) \
122 throw Pt::Unit::Assertion(#cond, PT_SOURCEINFO); \
123 } while (::Pt::Unit::testCond)
124
135 #define PT_UNIT_ASSERT_MSG(cond, what) \
136 do { \
137 if( !(cond) ) \
138 { \
139 std::ostringstream _pt_msg; \
140 _pt_msg << what; \
141 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
142 } \
143 } while (::Pt::Unit::testCond)
144
149 // TODO: deprecated
150 #define PT_UNIT_ASSERT_EQUALS(value1, value2) \
151 do { \
152 if( ! ((value1) == (value2)) ) \
153 { \
154 std::ostringstream _pt_msg; \
155 _pt_msg << "not equal: value1 (" #value1 ")=<" << value1 << "> value2 (" #value2 ")=<" << value2 << '>'; \
156 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
157 } \
158 } while (::Pt::Unit::testCond)
159
170 #define PT_UNIT_ASSERT_EQUAL(value1, value2) \
171 do { \
172 if( ! ((value1) == (value2)) ) \
173 { \
174 std::ostringstream _pt_msg; \
175 _pt_msg << "not equal: (" #value1 ")=<" << value1 << ">, (" #value2 ")=<" << value2 << '>'; \
176 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
177 } \
178 } while (::Pt::Unit::testCond)
179
191 #define PT_UNIT_ASSERT_NEAR(value1, value2) \
192 do { \
193 const double _pt_v1 = static_cast<double>(value1); \
194 const double _pt_v2 = static_cast<double>(value2); \
195 const double _pt_rel_eps = std::sqrt(std::numeric_limits<double>::epsilon()); \
196 const double _pt_abs_eps = std::numeric_limits<double>::min(); \
197 const double _pt_scale = std::fmax(std::fabs(_pt_v1), std::fabs(_pt_v2)); \
198 const double _pt_eps = std::fmax(_pt_rel_eps * _pt_scale, _pt_abs_eps); \
199 if( std::fabs(_pt_v1 - _pt_v2) > _pt_eps ) \
200 { \
201 std::ostringstream _pt_msg; \
202 _pt_msg << "not near: (" #value1 ")=<" << _pt_v1 \
203 << ">, (" #value2 ")=<" << _pt_v2 \
204 << ">, eps=<" << _pt_eps \
205 << ">, diff=<" << std::fabs(_pt_v1 - _pt_v2) << '>'; \
206 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
207 } \
208 } while (::Pt::Unit::testCond)
209
220 #define PT_UNIT_ASSERT_THROW(cond, EX) \
221 do { \
222 struct _pt_ex { }; \
223 try \
224 { \
225 cond; \
226 throw _pt_ex(); \
227 } \
228 catch(const _pt_ex &) \
229 { \
230 std::ostringstream _pt_msg; \
231 _pt_msg << "exception of type " #EX " expected in " #cond; \
232 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
233 } \
234 catch(const EX &) \
235 {} \
236 } while (::Pt::Unit::testCond)
237
246 #define PT_UNIT_ASSERT_NOTHROW(cond) \
247 do { \
248 try { \
249 \
250 cond; \
251 } \
252 catch(const std::exception& e) \
253 { \
254 throw Pt::Unit::Assertion( \
255 std::string("unexpected exception of type ") + typeid(e).name() + ": " + e.what(), \
256 PT_SOURCEINFO); \
257 } \
258 catch(...) \
259 { \
260 throw Pt::Unit::Assertion("unexpected exception." , PT_SOURCEINFO); \
261 } \
262 } while (::Pt::Unit::testCond)
263
272 #define PT_UNIT_FAIL(what) \
273 do { \
274 std::ostringstream _pt_msg; \
275 _pt_msg << what; \
276 throw Pt::Unit::Assertion(_pt_msg.str(), PT_SOURCEINFO); \
277 } while (::Pt::Unit::testCond)
278
279} // namespace
280
281} // namespace
282
283#endif // include guard
Source code info class.
Definition SourceInfo.h:101
const Pt::SourceInfo & sourceInfo() const
Information where assertion failed.
Assertion(const std::string &what, const SourceInfo &si)
Construct from a message and source info.
Protocol and data driven unit testing framework.
Core module.
Definition Allocator.h:33