LCOV - code coverage report
Current view: top level - testsuite - tpunit.h (source / functions) Hit Total Coverage
Test: STX B+ Tree Testsuite Lines: 77 83 92.8 %
Date: 2013-05-05 Functions: 41 42 97.6 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /**
       2             :  * Copyright (c) 2011 Trevor Pounds
       3             :  *
       4             :  * Permission is hereby granted, free of charge, to any person obtaining a copy
       5             :  * of this software and associated documentation files (the "Software"), to deal
       6             :  * in the Software without restriction, including without limitation the rights
       7             :  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
       8             :  * copies of the Software, and to permit persons to whom the Software is
       9             :  * furnished to do so, subject to the following conditions:
      10             :  *
      11             :  * The above copyright notice and this permission notice shall be included in
      12             :  * all copies or substantial portions of the Software.
      13             :  *
      14             :  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
      15             :  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
      16             :  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
      17             :  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
      18             :  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
      19             :  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
      20             :  * THE SOFTWARE.
      21             :  */
      22             : #ifndef __TPUNITPP_HPP__
      23             : #define __TPUNITPP_HPP__
      24             : 
      25             : /**
      26             :  * Declare printf dependency inline to workaround
      27             :  * potential #include <stdio.h> compiler/linker bugs.
      28             :  */
      29             : extern "C" int printf(const char*, ...);
      30             : 
      31             : /**
      32             :  * TPUNITPP_VERSION macro contains an integer represented by
      33             :  * the value (M*1000000 + N*1000 + P) where M is the major
      34             :  * version, N is the minor version, and P is the patch version.
      35             :  *
      36             :  * TPUNITPP_VERSION_MAJOR is an integer of the major version.
      37             :  * TPUNITPP_VERSION_MINOR is an integer of the minor version.
      38             :  * TPUNITPP_VERSION_PATCH is an integer of the patch version.
      39             :  */
      40             : #define TPUNITPP_VERSION 1000002
      41             : #define TPUNITPP_VERSION_MAJOR 1
      42             : #define TPUNITPP_VERSION_MINOR 0
      43             : #define TPUNITPP_VERSION_PATCH 2
      44             : 
      45             : /**
      46             :  * ABORT(); generates a failure, immediately returning from the
      47             :  * currently executing test function.
      48             :  * FAIL(); generates a failure, allowing the currently executing
      49             :  * test function to continue.
      50             :  * PASS(); does nothing, effectively considered a NOP but may be
      51             :  * useful for annotating test cases with their desired intent.
      52             :  * TRACE(message); adds a trace to the test output with a user
      53             :  * specified string message.
      54             :  */
      55             : #define ABORT() __assert(__FILE__, __LINE__); return;
      56             : #define FAIL()  __assert(__FILE__, __LINE__);
      57             : #define PASS()  /* do nothing */
      58             : #define TRACE(message) __trace(__FILE__, __LINE__, message);
      59             : 
      60             : /**
      61             :  * The set of core macros for basic predicate testing of boolean
      62             :  * expressions and value comparisons.
      63             :  *
      64             :  * ASSERT_*(...); generates a failure, immediately returning from
      65             :  * the currently executing test function if the supplied predicate
      66             :  * is not satisfied.
      67             :  * EXPECT_*(...); generates a failure, allowing the currently
      68             :  * executing test function to continue if the supplied predicate
      69             :  * is not satisified.
      70             :  */
      71             : #define ASSERT_TRUE(condition) do { if(condition) { PASS(); } else { ABORT(); } } while(0)
      72             : #define EXPECT_TRUE(condition) do { if(condition) { PASS(); } else { FAIL(); } } while(0)
      73             : #define ASSERT_FALSE(condition) do { if(condition) { ABORT(); } else { PASS(); } } while(0)
      74             : #define EXPECT_FALSE(condition) do { if(condition) { FAIL(); } else { PASS(); } } while(0)
      75             : #define ASSERT_EQUAL(lhs, rhs) do { if((lhs) == (rhs)) { PASS(); } else { ABORT(); } } while(0)
      76             : #define EXPECT_EQUAL(lhs, rhs) do { if((lhs) == (rhs)) { PASS(); } else { FAIL(); } } while(0)
      77             : #define ASSERT_NOT_EQUAL(lhs, rhs) do { if((lhs) != (rhs)) { PASS(); } else { ABORT(); } } while(0)
      78             : #define EXPECT_NOT_EQUAL(lhs, rhs) do { if((lhs) != (rhs)) { PASS(); } else { FAIL(); } } while(0)
      79             : #define ASSERT_GREATER_THAN(lhs, rhs) do { if((lhs) > (rhs)) { PASS(); } else { ABORT(); } } while(0)
      80             : #define EXPECT_GREATER_THAN(lhs, rhs) do { if((lhs) > (rhs)) { PASS(); } else { FAIL(); } } while(0)
      81             : #define ASSERT_GREATER_THAN_EQUAL(lhs, rhs) do { if((lhs) >= (rhs)) { PASS(); } else { ABORT(); } } while(0)
      82             : #define EXPECT_GREATER_THAN_EQUAL(lhs, rhs) do { if((lhs) >= (rhs)) { PASS(); } else { FAIL(); } } while(0)
      83             : #define ASSERT_LESS_THAN(lhs, rhs) do { if((lhs) < (rhs)) { PASS(); } else { ABORT(); } } while(0)
      84             : #define EXPECT_LESS_THAN(lhs, rhs) do { if((lhs) < (rhs)) { PASS(); } else { FAIL(); } } while(0)
      85             : #define ASSERT_LESS_THAN_EQUAL(lhs, rhs) do { if((lhs) <= (rhs)) { PASS(); } else { ABORT(); } } while(0)
      86             : #define EXPECT_LESS_THAN_EQUAL(lhs, rhs) do { if((lhs) <= (rhs)) { PASS(); } else { FAIL(); } } while(0)
      87             : 
      88             : #define ASSERT(condition) do { if(condition) { PASS(); } else { ABORT(); } } while(0)
      89             : 
      90             : /**
      91             :  * The set of floating-point macros used to compare double/float values.
      92             :  *
      93             :  * ASSERT|EXPECT_FLOAT_EQUAL(lhs, rhs); generates a failure if the given
      94             :  * floating-point values are not within 4 ULPs of each other.
      95             :  * ASSERT|EXPECT_FLOAT_NEAR(lhs, rhs, abs_error); generates a failure if
      96             :  * the given floating-point values exceed the absolute error.
      97             :  */
      98             : #define ASSERT_FLOAT_EQUAL(lhs, rhs) do { if(__fp_equal(lhs, rhs, 4)) { PASS(); } else { ABORT(); } } while(0)
      99             : #define EXPECT_FLOAT_EQUAL(lhs, rhs) do { if(__fp_equal(lhs, rhs, 4)) { PASS(); } else { FAIL(); } } while(0)
     100             : #define ASSERT_FLOAT_NEAR(lhs, rhs, abs_error) do { if((((lhs) > (rhs)) ? (lhs) - (rhs) : (rhs) - (lhs)) <= (abs_error)) { PASS(); } else { ABORT(); } } while(0)
     101             : #define EXPECT_FLOAT_NEAR(lhs, rhs, abs_error) do { if((((lhs) > (rhs)) ? (lhs) - (rhs) : (rhs) - (lhs)) <= (abs_error)) { PASS(); } else { FAIL(); } } while(0)
     102             : 
     103             : /**
     104             :  * The set of macros for checking whether a statement will throw or not
     105             :  * throw an exception. Note, the checked exception macros will generally
     106             :  * not work with compilers that do not support exceptions or have them
     107             :  * explicitly turned off using a compiler flag (e.g. -fno-exceptions).
     108             :  *
     109             :  * ASSERT|EXPECT_THROW(statement, exception); generates a failure if
     110             :  * the given statement does not throw the supplied excetion.
     111             :  * ASSERT|EXPECT_NO_THROW(statement, exception); generates a failure
     112             :  * if the given statement throws any exception. Useful for ensuring
     113             :  * a statement never throws an exception.
     114             :  * ASSERT|EXPECT_ANY_THROW(statement); generates a failure if the
     115             :  * given statement does not throw any exceptions.
     116             :  */
     117             : #define ASSERT_THROW(statement, exception) do { try { statement; ABORT(); } catch(const exception& e) { PASS(); } catch(...) { ABORT(); } } while(0)
     118             : #define EXPECT_THROW(statement, exception) do { try { statement; FAIL(); } catch(const exception& e) { PASS(); } catch(...) { FAIL(); } } while(0)
     119             : #define ASSERT_NO_THROW(statement) do { try { statement; PASS(); } catch(...) { ABORT(); } } while(0)
     120             : #define EXPECT_NO_THROW(statement) do { try { statement; PASS(); } catch(...) { FAIL(); } } while(0)
     121             : #define ASSERT_ANY_THROW(statement) do { try { statement; ABORT(); } catch(...) { PASS(); } } while(0)
     122             : #define EXPECT_ANY_THROW(statement) do { try { statement; FAIL(); } catch(...) { PASS(); } } while(0)
     123             : 
     124             : /**
     125             :  * The set of convenience macros for registering functions with the test
     126             :  * fixture.
     127             :  *
     128             :  * AFTER(function); registers a function to run once after each subsequent
     129             :  * test function within a test fixture.
     130             :  * AFTER_CLASS(function); registers a function to run once after all test
     131             :  * functions within a test fixture. Useful for cleaning up shared state
     132             :  * used by all test functions.
     133             :  * BEFORE(function); registers a function to run once before each subsequent
     134             :  * test function within a test fixture.
     135             :  * BEFORE_CLASS(function); registers a function to run once before all test
     136             :  * functions within a test fixture. Useful for initializing shared state
     137             :  * used by all test functions.
     138             :  * TEST(function); registers a function to run as a test within a test fixture.
     139             :  */
     140             : #define AFTER(M)        After(&M, "After: " #M)
     141             : #define AFTER_CLASS(M)  AfterClass(&M, "AfterClass: " #M)
     142             : #define BEFORE(M)       Before(&M, "Before: " #M)
     143             : #define BEFORE_CLASS(M) BeforeClass(&M, "BeforeClass: " #M)
     144             : #define TEST(M)         Test(&M, #M)
     145             : 
     146             : namespace tpunit
     147             : {
     148             :    /**
     149             :     * The primary class that provides the integration point for creating user
     150             :     * defined test cases. To get started one only needs to derive from TestFixture,
     151             :     * define a few test methods and register them with the base constructor.
     152             :     */
     153             :    class TestFixture
     154             :    {
     155             :       private:
     156             : 
     157             :          /**
     158             :           * An internal class representing a TestFixture class.
     159             :           */
     160             :          struct method
     161             :          {
     162         197 :             method(TestFixture* obj, void (TestFixture::*addr)(), const char* name, unsigned char type)
     163             :                : _this(obj)
     164             :                , _addr(addr)
     165             :                , _name()
     166             :                , _type(type)
     167         197 :                , _next(0)
     168             :             {
     169         197 :                char* dest = _name;
     170        7826 :                while(name && *name != 0)
     171        7432 :                   { *dest++ = *name++; }
     172         197 :                dest = 0;
     173         197 :             }
     174             : 
     175         197 :             ~method()
     176         197 :                { delete _next; }
     177             : 
     178             :             TestFixture* _this;
     179             :             void (TestFixture::*_addr)();
     180             :             char _name[256];
     181             : 
     182             :             enum
     183             :             {
     184             :                AFTER_METHOD,  AFTER_CLASS_METHOD,
     185             :                BEFORE_METHOD, BEFORE_CLASS_METHOD,
     186             :                TEST_METHOD
     187             :             };
     188             :             unsigned char _type;
     189             : 
     190             :             method* _next;
     191             :          };
     192             : 
     193             :          /**
     194             :           * An internal class representing a TestFixture class.
     195             :           */
     196             :          struct fixture
     197             :          {
     198          30 :             fixture()
     199             :                : _afters(0),  _after_classes(0) 
     200             :                , _befores(0), _before_classes(0) 
     201          30 :                , _tests(0),   _next(0)
     202          30 :                {}
     203             : 
     204          30 :             ~fixture()
     205             :             {
     206          30 :                delete _afters;
     207          30 :                delete _after_classes;
     208          30 :                delete _befores;
     209          30 :                delete _before_classes;
     210          30 :                delete _tests;
     211          30 :                delete _next;
     212          30 :             }
     213             : 
     214             :             method* _afters;
     215             :             method* _after_classes;
     216             :             method* _befores;
     217             :             method* _before_classes;
     218             :             method* _tests;
     219             : 
     220             :             fixture* _next;
     221             :          };
     222             : 
     223             :          /**
     224             :           * A struct holding test statistics. 
     225             :           */
     226             :          struct stats
     227             :          {
     228           1 :             stats()
     229             :                : _assertions(0)
     230             :                , _failures(0)
     231             :                , _passes(0)
     232           1 :                , _traces(0)
     233           1 :                {}
     234             : 
     235             :             int _assertions;
     236             :             int _failures;
     237             :             int _passes;
     238             :             int _traces;
     239             :          };
     240             : 
     241             :       public:
     242             : 
     243             :          /**
     244             :           * The base constructor of all test fixtures used to register methods executed by the default runner.
     245             :           *
     246             :           * @param[in] m0...m29 A list of methods to register with the test fixture.
     247             :           */
     248          29 :          TestFixture(method* m0,      method* m1  = 0, method* m2  = 0, method* m3  = 0, method* m4  = 0,
     249             :                      method* m5  = 0, method* m6  = 0, method* m7  = 0, method* m8  = 0, method* m9  = 0,
     250             :                      method* m10 = 0, method* m11 = 0, method* m12 = 0, method* m13 = 0, method* m14 = 0,
     251             :                      method* m15 = 0, method* m16 = 0, method* m17 = 0, method* m18 = 0, method* m19 = 0,
     252             :                      method* m20 = 0, method* m21 = 0, method* m22 = 0, method* m23 = 0, method* m24 = 0,
     253             :                      method* m25 = 0, method* m26 = 0, method* m27 = 0, method* m28 = 0, method* m29 = 0)
     254             :          {
     255          29 :             fixture* f = &__fixtures();
     256          29 :             while(f->_next) { f = f->_next; }
     257          29 :             f = f->_next = new fixture;
     258             : 
     259             :             #define SET_FIXTURE_METHOD(M) \
     260             :                if(M) \
     261             :                { \
     262             :                   method** m = 0; \
     263             :                   switch(M->_type) \
     264             :                   { \
     265             :                      case method::AFTER_METHOD:        m = &f->_afters;         break; \
     266             :                      case method::AFTER_CLASS_METHOD:  m = &f->_after_classes;  break; \
     267             :                      case method::BEFORE_METHOD:       m = &f->_befores;        break; \
     268             :                      case method::BEFORE_CLASS_METHOD: m = &f->_before_classes; break; \
     269             :                      case method::TEST_METHOD:         m = &f->_tests;          break; \
     270             :                   } \
     271             :                   while(*m && (*m)->_next) { m = &(*m)->_next; } \
     272             :                   (*m) ? (*m)->_next = M : *m = M; \
     273             :                }
     274          29 :             SET_FIXTURE_METHOD(m0)  SET_FIXTURE_METHOD(m1)  SET_FIXTURE_METHOD(m2)  SET_FIXTURE_METHOD(m3)
     275          29 :             SET_FIXTURE_METHOD(m4)  SET_FIXTURE_METHOD(m5)  SET_FIXTURE_METHOD(m6)  SET_FIXTURE_METHOD(m7)
     276          29 :             SET_FIXTURE_METHOD(m8)  SET_FIXTURE_METHOD(m9)  SET_FIXTURE_METHOD(m10) SET_FIXTURE_METHOD(m11)
     277          29 :             SET_FIXTURE_METHOD(m12) SET_FIXTURE_METHOD(m13) SET_FIXTURE_METHOD(m14) SET_FIXTURE_METHOD(m15)
     278          29 :             SET_FIXTURE_METHOD(m16) SET_FIXTURE_METHOD(m17) SET_FIXTURE_METHOD(m18) SET_FIXTURE_METHOD(m19)
     279          29 :             SET_FIXTURE_METHOD(m20) SET_FIXTURE_METHOD(m21) SET_FIXTURE_METHOD(m22) SET_FIXTURE_METHOD(m23)
     280          29 :             SET_FIXTURE_METHOD(m24) SET_FIXTURE_METHOD(m25) SET_FIXTURE_METHOD(m26) SET_FIXTURE_METHOD(m27)
     281          29 :             SET_FIXTURE_METHOD(m28) SET_FIXTURE_METHOD(m29)
     282             :             #undef SET_FIXTURE_METHOD
     283          29 :          }
     284             : 
     285             :          /**
     286             :           * Registers a method to run once immediately after each test method registered with the test fixture.
     287             :           *
     288             :           * @param[in] _method A method to register with the test fixture.
     289             :           * @param[in] _name The internal name of the method used when status messages are displayed.
     290             :           */
     291             :          template <typename C>
     292             :          method* After(void (C::*_method)(), const char* _name)
     293             :             { return new method(this, reinterpret_cast<void (TestFixture::*)()>(_method), _name, method::AFTER_METHOD); }
     294             : 
     295             :          /**
     296             :           * Registers a method to run once immediately after all after/before/test methods registered with
     297             :           * the test fixture. Useful for cleaning up shared state used by methods in a test fixture.
     298             :           *
     299             :           * @param[in] _method A method to register with the test fixture.
     300             :           * @param[in] _name The internal name of the method used when status messages are displayed.
     301             :           */
     302             :          template <typename C>
     303             :          method* AfterClass(void (C::*_method)(), const char* _name)
     304             :             { return new method(this, reinterpret_cast<void (TestFixture::*)()>(_method), _name, method::AFTER_CLASS_METHOD); }
     305             : 
     306             :          /**
     307             :           * Registers a method to run once immediately before each test method registered with the test fixture.
     308             :           *
     309             :           * @param[in] _method A method to register with the test fixture.
     310             :           * @param[in] _name The internal name of the method used when status messages are displayed.
     311             :           */
     312             :          template <typename C>
     313             :          method* Before(void (C::*_method)(), const char* _name)
     314             :             { return new method(this, reinterpret_cast<void (TestFixture::*)()>(_method), _name, method::BEFORE_METHOD); }
     315             : 
     316             :          /**
     317             :           * Registers a method to run once immediately before all after/before/test methods registered with
     318             :           * the test fixture. Useful for intializing shared state used by methods in a test fixture.
     319             :           *
     320             :           * @param[in] _method A method to register with the test fixture.
     321             :           * @param[in] _name The internal name of the method used when status messages are displayed.
     322             :           */
     323             :          template <typename C>
     324             :          method* BeforeClass(void (C::*_method)(), const char* _name)
     325             :             { return new method(this, reinterpret_cast<void (TestFixture::*)()>(_method), _name, method::BEFORE_CLASS_METHOD); }
     326             : 
     327             :          /**
     328             :           * Registers a method to run as a test with the test fixture.
     329             :           *
     330             :           * @param[in] _method A method to register with the test fixture.
     331             :           * @param[in] _name The internal name of the method used when status messages are displayed.
     332             :           */
     333             :          template <typename C>
     334         197 :          method* Test(void (C::*_method)(), const char* _name)
     335         197 :             { return new method(this, reinterpret_cast<void (TestFixture::*)()>(_method), _name, method::TEST_METHOD); }
     336             : 
     337             :       protected:
     338             : 
     339           1 :          static int __do_run()
     340             :          {
     341           1 :             fixture* f = __fixtures()._next;
     342          31 :             while(f)
     343             :             {
     344          29 :                printf("[--------------]\n");
     345          29 :                __do_methods(f->_before_classes);
     346          29 :                __do_tests(f);
     347          29 :                __do_methods(f->_after_classes);
     348          29 :                printf("[--------------]\n\n");
     349          29 :                f = f->_next;
     350             :             }
     351           1 :             printf("[==============]\n");
     352           1 :             printf("[ TEST RESULTS ]\n");
     353           1 :             printf("[==============]\n");
     354           1 :             printf("[    PASSED    ] %4i tests\n", __stats()._passes);
     355           1 :             printf("[    FAILED    ] %4i tests\n", __stats()._failures);
     356           1 :             printf("[==============]\n");
     357           1 :             return __stats()._failures;
     358             :          }
     359             : 
     360             :          /**
     361             :           * Determine if two binary32 single precision IEEE 754 floating-point
     362             :           * numbers are equal using unit in the last place (ULP) analysis.
     363             :           *
     364             :           * http://www.cygnus-software.com/papers/comparingfloats/comparingfloats.htm 
     365             :           */
     366             :          static bool __fp_equal(float lhs, float rhs, unsigned char ulps)
     367             :          {
     368             :             union
     369             :             {
     370             :                float f;
     371             :                char  c[4];
     372             :             } lhs_u, rhs_u;
     373             :             lhs_u.f = lhs;
     374             :             rhs_u.f = rhs;
     375             : 
     376             :             bool lil_endian = (static_cast<unsigned char>(0x00FF)) == 0xFF;
     377             :             int msb = lil_endian ? 3 : 0;
     378             :             int lsb = lil_endian ? 0 : 3;
     379             :             if(lhs_u.c[msb] < 0)
     380             :             {
     381             :                lhs_u.c[0 ^ lsb] = 0x00 - lhs_u.c[0 ^ lsb];
     382             :                lhs_u.c[1 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[0 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[1 ^ lsb];
     383             :                lhs_u.c[2 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[1 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[2 ^ lsb];
     384             :                lhs_u.c[3 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[2 ^ lsb]) > 0x00) ? 0x7F : 0x80) - lhs_u.c[3 ^ lsb];
     385             :             }
     386             :             if(rhs_u.c[msb] < 0)
     387             :             {
     388             :                rhs_u.c[0 ^ lsb] = 0x00 - rhs_u.c[0 ^ lsb];
     389             :                rhs_u.c[1 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[0 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[1 ^ lsb];
     390             :                rhs_u.c[2 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[1 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[2 ^ lsb];
     391             :                rhs_u.c[3 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[2 ^ lsb]) > 0x00) ? 0x7F : 0x80) - rhs_u.c[3 ^ lsb];
     392             :             }
     393             :             return (lhs_u.c[1] == rhs_u.c[1] && lhs_u.c[2] == rhs_u.c[2] && lhs_u.c[msb] == rhs_u.c[msb]) &&
     394             :                    ((lhs_u.c[lsb] > rhs_u.c[lsb]) ? lhs_u.c[lsb] - rhs_u.c[lsb] : rhs_u.c[lsb] - lhs_u.c[lsb]) <= ulps;
     395             :          }
     396             : 
     397             :          /**
     398             :           * Determine if two binary64 double precision IEEE 754 floating-point
     399             :           * numbers are equal using unit in the last place (ULP) analysis.
     400             :           *
     401             :           * http://www.cygnus-software.com/papers/comparingfloats/comparingfloats.htm 
     402             :           */
     403             :          static bool __fp_equal(double lhs, double rhs, unsigned char ulps)
     404             :          {
     405             :             union
     406             :             {
     407             :                double d;
     408             :                char   c[8];
     409             :             } lhs_u, rhs_u;
     410             :             lhs_u.d = lhs;
     411             :             rhs_u.d = rhs;
     412             : 
     413             :             bool lil_endian = static_cast<unsigned char>(0x00FF) == 0xFF;
     414             :             int msb = lil_endian ? 7 : 0;
     415             :             int lsb = lil_endian ? 0 : 7;
     416             :             if(lhs_u.c[msb] < 0)
     417             :             {
     418             :                lhs_u.c[0 ^ lsb] = 0x00 - lhs_u.c[0 ^ lsb];
     419             :                lhs_u.c[1 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[0 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[1 ^ lsb];
     420             :                lhs_u.c[2 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[1 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[2 ^ lsb];
     421             :                lhs_u.c[3 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[2 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[3 ^ lsb];
     422             :                lhs_u.c[4 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[3 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[4 ^ lsb];
     423             :                lhs_u.c[5 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[4 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[5 ^ lsb];
     424             :                lhs_u.c[6 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[5 ^ lsb]) > 0x00) ? 0xFF : 0x00) - lhs_u.c[6 ^ lsb];
     425             :                lhs_u.c[7 ^ lsb] = ((static_cast<unsigned char>(lhs_u.c[6 ^ lsb]) > 0x00) ? 0x7F : 0x80) - lhs_u.c[7 ^ lsb];
     426             :             }
     427             :             if(rhs_u.c[msb] < 0)
     428             :             {
     429             :                rhs_u.c[0 ^ lsb] = 0x00 - rhs_u.c[0 ^ lsb];
     430             :                rhs_u.c[1 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[0 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[1 ^ lsb];
     431             :                rhs_u.c[2 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[1 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[2 ^ lsb];
     432             :                rhs_u.c[3 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[2 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[3 ^ lsb];
     433             :                rhs_u.c[4 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[3 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[4 ^ lsb];
     434             :                rhs_u.c[5 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[4 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[5 ^ lsb];
     435             :                rhs_u.c[6 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[5 ^ lsb]) > 0x00) ? 0xFF : 0x00) - rhs_u.c[6 ^ lsb];
     436             :                rhs_u.c[7 ^ lsb] = ((static_cast<unsigned char>(rhs_u.c[6 ^ lsb]) > 0x00) ? 0x7F : 0x80) - rhs_u.c[7 ^ lsb];
     437             :             }
     438             :             return (lhs_u.c[1] == rhs_u.c[1] && lhs_u.c[2] == rhs_u.c[2] &&
     439             :                     lhs_u.c[3] == rhs_u.c[3] && lhs_u.c[4] == rhs_u.c[4] &&
     440             :                     lhs_u.c[5] == rhs_u.c[5] && lhs_u.c[6] == rhs_u.c[6] &&
     441             :                     lhs_u.c[msb] == rhs_u.c[msb]) &&
     442             :                    ((lhs_u.c[lsb] > rhs_u.c[lsb]) ? lhs_u.c[lsb] - rhs_u.c[lsb] : rhs_u.c[lsb] - lhs_u.c[lsb]) <= ulps;
     443             :          }
     444             : 
     445           0 :          static void __assert(const char* _file, int _line)
     446           0 :             { printf("[              ]    assert #%i at %s:%i\n", ++__stats()._assertions, _file, _line); }
     447             : 
     448             :          static void __trace(const char* _file, int _line, const char* _message)
     449             :             { printf("[              ]    trace #%i at %s:%i: %s\n", ++__stats()._traces, _file, _line, _message); }
     450             : 
     451             :       private:
     452             : 
     453         452 :          static void __do_methods(method* m)
     454             :          {
     455         904 :             while(m)
     456             :             {
     457           0 :                (*m->_this.*m->_addr)();
     458           0 :                m = m->_next;
     459             :             }
     460         452 :          }
     461             : 
     462          29 :          static void __do_tests(fixture* f)
     463             :          {
     464          29 :             method* t = f->_tests;
     465         255 :             while(t)
     466             :             {
     467         197 :                __do_methods(f->_befores);
     468             : 
     469         197 :                int _prev_assertions = __stats()._assertions;
     470         197 :                printf("[ RUN          ] %s\n", t->_name);
     471         197 :                (*t->_this.*t->_addr)();
     472         197 :                if(_prev_assertions == __stats()._assertions)
     473             :                {
     474         197 :                   printf("[       PASSED ] %s\n", t->_name);
     475         197 :                   __stats()._passes++;
     476             :                }
     477             :                else
     478             :                {
     479           0 :                   printf("[       FAILED ] %s\n", t->_name);
     480           0 :                   __stats()._failures++;
     481             :                }
     482         197 :                t = t->_next;
     483             : 
     484         197 :                __do_methods(f->_afters);
     485             :             }
     486          29 :          }
     487             : 
     488         594 :          static stats& __stats()
     489             :          {
     490         594 :             static stats _stats;
     491         594 :             return _stats;
     492             :          }
     493             : 
     494          30 :          static fixture& __fixtures()
     495             :          {
     496          30 :             static fixture _fixtures;
     497          30 :             return _fixtures;
     498             :          }
     499             :    };
     500             : 
     501             :    /**
     502             :     * A class containing the primary entry point for running all registered
     503             :     * tpunit++ test cases. Generally this class is wrapped by the user's
     504             :     * \em main function.
     505             :     */
     506             :    class Tests : private TestFixture
     507             :    {
     508             :       public:
     509             : 
     510             :          /**
     511             :           * Run all of the registered test cases and return the number of failed assertions.
     512             :           *
     513             :           * @return The number of failing assertions. (e.g. zero if all tests pass, otherwise non-zero)
     514             :           */
     515           1 :          static int Run() { return TestFixture::__do_run(); }
     516             : 
     517             :       private:
     518             : 
     519             :          Tests() : TestFixture(0) { /* disable instance creation */ }
     520             :    };
     521             : } // namespace tpunit
     522             : #endif //__TPUNITPP_HPP__

Generated by: LCOV version 1.10