time_test.cpp
Go to the documentation of this file.
00001 /***************************************************************************
00002   tag: Peter Soetens  Fri Feb 11 15:59:13 CET 2005  time_test.cpp
00003 
00004                         time_test.cpp -  description
00005                            -------------------
00006     begin                : Fri February 11 2005
00007     copyright            : (C) 2005 Peter Soetens
00008     email                : peter.soetens@mech.kuleuven.ac.be
00009 
00010  ***************************************************************************
00011  *                                                                         *
00012  *   This program is free software; you can redistribute it and/or modify  *
00013  *   it under the terms of the GNU General Public License as published by  *
00014  *   the Free Software Foundation; either version 2 of the License, or     *
00015  *   (at your option) any later version.                                   *
00016  *                                                                         *
00017  ***************************************************************************/
00018 
00019 #include "unit.hpp"
00020 
00021 #include "time_test.hpp"
00022 #include <boost/bind.hpp>
00023 #include <os/Timer.hpp>
00024 #include <rtt-detail-fwd.hpp>
00025 #include <iostream>
00026 
00027 #define EPSILON 0.000000002
00028 
00029 // Registers the fixture into the 'registry'
00030 //CPPUNIT_TEST_SUITE_REGISTRATION( TimeTest );
00031 
00032 using namespace std;
00033 using namespace RTT;
00034 using namespace RTT::detail;
00035 using namespace boost;
00036 
00037 TimeTest::TimeTest()
00038 {
00039     hbg = TimeService::Instance();
00040     long_ns = 9007199254740992LL;       // == 2^53
00041     //long_ns = 4503599627370496LL;       // == 2^52
00042     //long_ns = 123456789123456789LL; // 1.234...e17 ns == approx 4 years, but double can not represent this.
00043     long_S  = 9007199.254740992;
00044     //long_S  = 4.503599627370496e14;
00045     normal_ns = 1000000000; // 1s
00046     normal_S = 1.0; // 1s
00047     small_ns = 10;  //  10ns
00048     small_S = 10e-9; //  10ns
00049     small_t = 10;
00050     normal_t = 1000000000; // 1e9 ticks
00051     long_t  = long_ns;     // == 2^53
00052 }
00053 
00054 TimeTest::~TimeTest()
00055 {
00056     hbg->enableSystemClock( true );
00057 }
00058 
00059 struct TestTimer
00060     : public Timer
00061 {
00062     std::vector< std::pair<Timer::TimerId, Seconds> > occured;
00063     TimeService::Seconds mstart;
00064     TestTimer()
00065         :Timer(32, ORO_SCHED_RT, os::HighestPriority)
00066     {
00067         occured.reserve(100);
00068         mstart = TimeService::Instance()->secondsSince(0);
00069     }
00070     void timeout(Timer::TimerId id)
00071     {
00072         Seconds now = TimeService::Instance()->secondsSince( 0 );
00073         occured.push_back( std::make_pair(id, now) );
00074         //cout << "Occured: "<< id <<" on " << now - mstart <<"\n";
00075     }
00076 
00077     ~TestTimer()
00078     {
00079         cout.flush();
00080     }
00081 };
00082 
00083 BOOST_FIXTURE_TEST_SUITE( TimeTestSuite, TimeTest )
00084 
00085 BOOST_AUTO_TEST_CASE( testSecondsConversion )
00086 {
00087     // Test one way
00088     BOOST_REQUIRE_EQUAL( long_ns  , Seconds_to_nsecs(long_S)  );
00089     BOOST_REQUIRE_EQUAL( normal_ns, Seconds_to_nsecs(normal_S));
00090     BOOST_REQUIRE_EQUAL( small_ns , Seconds_to_nsecs(small_S) );
00091 
00092     // Test other way
00093     BOOST_REQUIRE_EQUAL( long_S  , nsecs_to_Seconds(long_ns));
00094     BOOST_REQUIRE_EQUAL( normal_S, nsecs_to_Seconds(normal_ns));
00095     BOOST_REQUIRE_EQUAL( small_S , nsecs_to_Seconds(small_ns));
00096 
00097     // Test invariance of conversions :
00098     BOOST_REQUIRE_EQUAL( long_ns  , Seconds_to_nsecs( nsecs_to_Seconds(long_ns) ));
00099     BOOST_REQUIRE_EQUAL( normal_ns, Seconds_to_nsecs( nsecs_to_Seconds(normal_ns) ));
00100     BOOST_REQUIRE_EQUAL( small_ns , Seconds_to_nsecs( nsecs_to_Seconds(small_ns) ));
00101     BOOST_REQUIRE_EQUAL( long_S  , nsecs_to_Seconds( Seconds_to_nsecs(long_S) ));
00102     BOOST_REQUIRE_EQUAL( normal_S, nsecs_to_Seconds( Seconds_to_nsecs(normal_S) ));
00103     BOOST_REQUIRE_EQUAL( small_S , nsecs_to_Seconds( Seconds_to_nsecs(small_S) ));
00104 }
00105 
00106 BOOST_AUTO_TEST_CASE( testTicksConversion )
00107 {
00108     // Test ticks conversion invariance :
00109     // margin is in % rounding error.
00110     int margin = 1;
00111 //#if defined( OROCOS_TARGET_LXRT) || defined(OROCOS_TARGET_XENOMAI)
00112 //    int small_margin = 25; // 25% of 8ns : allow a two-off.
00113 //#else
00114 //    int small_margin = 10; // 10% of 8ns : allow a one-off.
00115 //#endif
00116 
00117     // I'm removing the small conversions because they test more the underlying RTOS than Orocos and the underlying RTOS
00118     // isn't fixing this for years...
00119     BOOST_REQUIRE_CLOSE( (double)long_ns  , (double)TimeService::ticks2nsecs( TimeService::nsecs2ticks( long_ns )), margin );
00120     BOOST_REQUIRE_CLOSE( (double)normal_ns, (double)TimeService::ticks2nsecs( TimeService::nsecs2ticks( normal_ns )), margin );
00121     //BOOST_REQUIRE_CLOSE( (double)small_ns , (double)TimeService::ticks2nsecs( TimeService::nsecs2ticks( small_ns )), small_margin );
00122     BOOST_REQUIRE_CLOSE( (double)long_t  , (double)TimeService::nsecs2ticks( TimeService::ticks2nsecs( long_t )), margin );
00123     BOOST_REQUIRE_CLOSE( (double)normal_t, (double)TimeService::nsecs2ticks( TimeService::ticks2nsecs( normal_t )), margin );
00124     //BOOST_REQUIRE_CLOSE( (double)small_t , (double)TimeService::nsecs2ticks( TimeService::ticks2nsecs( small_t )), small_margin );
00125 }
00126 
00127 BOOST_AUTO_TEST_CASE( testTimeProgress )
00128 {
00129     // A time measurement takes time :
00130     TimeService::ticks t = hbg->getTicks();
00131     usleep(100000);
00132     BOOST_CHECK( t !=  hbg->getTicks() );
00133     BOOST_CHECK( 0 !=  hbg->ticksSince(t) );
00134     BOOST_CHECK( 0 !=  hbg->secondsSince(t) );
00135 
00136     // With Re-init of t :
00137     t = 0;
00138     BOOST_REQUIRE_EQUAL( TimeService::ticks(0) , hbg->getTicks( t ) );
00139     t = 0;
00140     // BOOST_REQUIRE_EQUAL( Seconds(0.0) , hbg->getSeconds( t ) );
00141 
00142     // Stop Time Progress:
00143     hbg->enableSystemClock( false );
00144     t = hbg->getTicks();
00145     BOOST_REQUIRE_EQUAL( t ,  hbg->getTicks() );
00146     BOOST_REQUIRE_EQUAL( TimeService::ticks(0) ,  hbg->ticksSince(t) );
00147     // BOOST_REQUIRE_EQUAL( Seconds(0.0) ,  hbg->secondsSince(t) );
00148 
00149     Seconds change_S  = 0.123456789;
00150 
00151     hbg->secondsChange( change_S );
00152     BOOST_CHECK( t !=  hbg->getTicks() ); // ticks must have changed
00153     BOOST_CHECK( -EPSILON < (change_S - hbg->secondsSince(t)) &&
00154                      EPSILON > (change_S - hbg->secondsSince(t)) );
00155 
00156     // Restart Time Progress
00157     hbg->enableSystemClock( true );
00158     BOOST_CHECK( t !=  hbg->getTicks() );
00159     BOOST_CHECK( TimeService::ticks(0) !=  hbg->ticksSince(t) );
00160     BOOST_CHECK( Seconds(0.0) !=  hbg->secondsSince(t) );
00161 
00162 }
00163 
00164 BOOST_AUTO_TEST_CASE( testTimers )
00165 {
00166     TestTimer timer;
00167     Seconds now = hbg->secondsSince( 0 );
00168     // Test arming
00169     BOOST_CHECK( timer.arm(0, 0.5) );
00170     BOOST_CHECK( timer.arm(1, 0.6) );
00171     BOOST_CHECK( timer.arm(2, 0.5) );
00172 
00173     BOOST_CHECK( timer.arm(3, 0.8) );
00174     BOOST_CHECK( timer.arm(3, 0.9) );
00175 
00176     BOOST_CHECK( timer.isArmed( 0 ) );
00177     BOOST_CHECK( timer.isArmed( 1 ) );
00178     BOOST_CHECK( timer.isArmed( 2 ) );
00179     BOOST_CHECK( timer.isArmed( 3 ) );
00180 
00181     sleep(1);
00182 
00183     // Test clearing
00184     BOOST_CHECK( !timer.isArmed( 0 ) );
00185     BOOST_CHECK( !timer.isArmed( 1 ) );
00186     BOOST_CHECK( !timer.isArmed( 2 ) );
00187     BOOST_CHECK( !timer.isArmed( 3 ) );
00188 
00189     // Test sequence
00190     BOOST_CHECK( timer.occured.size() == 4 );
00191     BOOST_CHECK( timer.occured[0].first == 0 );
00192     BOOST_CHECK( timer.occured[1].first == 2 );
00193     BOOST_CHECK( timer.occured[2].first == 1 );
00194     BOOST_CHECK( timer.occured[3].first == 3 );
00195 
00196     // Test timeliness
00197     BOOST_REQUIRE_CLOSE( timer.occured[0].second, now+0.5, 0.1 );
00198     BOOST_REQUIRE_CLOSE( timer.occured[1].second, now+0.5, 0.1 );
00199     BOOST_REQUIRE_CLOSE( timer.occured[2].second, now+0.6, 0.1 );
00200     BOOST_REQUIRE_CLOSE( timer.occured[3].second, now+0.9, 0.1 );
00201 
00202     // Test wrong parameters.
00203     BOOST_CHECK( timer.arm(4, -0.1) == false);
00204     BOOST_CHECK( timer.arm(500, 0.1) == false);
00205 
00206     timer.occured.clear();
00207 
00208     // Test resize.
00209     BOOST_CHECK( timer.arm(10, 0.5) );
00210     timer.setMaxTimers( 5 ); // clears the timer
00211     sleep(1);
00212     BOOST_CHECK( timer.occured.size() == 0 );
00213 }
00214 
00215 BOOST_AUTO_TEST_CASE( testTimerPeriod )
00216 {
00217     TestTimer timer;
00218     Seconds now = hbg->secondsSince( 0 );
00219     // Test starting periodics
00220     BOOST_CHECK( timer.startTimer(0, 0.1) );
00221     BOOST_CHECK( timer.startTimer(1, 0.6) );
00222     BOOST_CHECK( timer.startTimer(2, 0.5) );
00223 
00224     BOOST_CHECK( timer.startTimer(3, 0.5) );
00225     BOOST_CHECK( timer.startTimer(3, 0.2) );
00226 
00227     BOOST_CHECK( timer.isArmed( 0 ) );
00228     BOOST_CHECK( timer.isArmed( 1 ) );
00229     BOOST_CHECK( timer.isArmed( 2 ) );
00230     BOOST_CHECK( timer.isArmed( 3 ) );
00231 
00232     sleep(1);
00233 
00234     // Test clearing
00235     BOOST_CHECK( timer.killTimer( 0 ) );
00236     BOOST_CHECK( timer.killTimer( 1 ) );
00237     BOOST_CHECK( timer.killTimer( 2 ) );
00238     BOOST_CHECK( timer.killTimer( 3 ) );
00239     BOOST_CHECK( !timer.isArmed( 0 ) );
00240     BOOST_CHECK( !timer.isArmed( 1 ) );
00241     BOOST_CHECK( !timer.isArmed( 2 ) );
00242     BOOST_CHECK( !timer.isArmed( 3 ) );
00243 
00244     // Test sequence
00245     //BOOST_CHECK( timer.occured.size() == 4 ); hard to estimate
00246     BOOST_CHECK( timer.occured[0].first == 0 );
00247     BOOST_CHECK( timer.occured[1].first == 0 );
00248     BOOST_CHECK( timer.occured[2].first == 3 );
00249     BOOST_CHECK( timer.occured[3].first == 0 );
00250     BOOST_CHECK( timer.occured[4].first == 0 );
00251     BOOST_CHECK( timer.occured[5].first == 3 );
00252 
00253     BOOST_CHECK( timer.occured[6].first == 0 );
00254     BOOST_CHECK( timer.occured[7].first == 2 );
00255 
00256     BOOST_CHECK( timer.occured[8].first == 0 );
00257     BOOST_CHECK( timer.occured[9].first == 1 );
00258     BOOST_CHECK( timer.occured[10].first == 3 );
00259     BOOST_CHECK( timer.occured[11].first == 0 );
00260     BOOST_CHECK( timer.occured[12].first == 0 );
00261     BOOST_CHECK( timer.occured[13].first == 3 );
00262     BOOST_CHECK( timer.occured[14].first == 0 );
00263 
00264     // Test timeliness
00265     BOOST_REQUIRE_CLOSE( timer.occured[0].second, now+0.1, 0.1 );
00266     BOOST_REQUIRE_CLOSE( timer.occured[1].second, now+0.2, 0.1 );
00267     BOOST_REQUIRE_CLOSE( timer.occured[2].second, now+0.2, 0.1 );
00268     BOOST_REQUIRE_CLOSE( timer.occured[3].second, now+0.3, 0.1 );
00269     BOOST_REQUIRE_CLOSE( timer.occured[4].second, now+0.4, 0.1 );
00270     BOOST_REQUIRE_CLOSE( timer.occured[5].second, now+0.4, 0.1 );
00271     BOOST_REQUIRE_CLOSE( timer.occured[6].second, now+0.5, 0.1 );
00272     BOOST_REQUIRE_CLOSE( timer.occured[7].second, now+0.5, 0.1 );
00273     BOOST_REQUIRE_CLOSE( timer.occured[8].second, now+0.6, 0.1 );
00274     BOOST_REQUIRE_CLOSE( timer.occured[9].second, now+0.6, 0.1 );
00275     BOOST_REQUIRE_CLOSE( timer.occured[10].second, now+0.6, 0.1 );
00276     BOOST_REQUIRE_CLOSE( timer.occured[11].second, now+0.7, 0.1 );
00277     BOOST_REQUIRE_CLOSE( timer.occured[12].second, now+0.8, 0.1 );
00278     BOOST_REQUIRE_CLOSE( timer.occured[13].second, now+0.8, 0.1 );
00279     BOOST_REQUIRE_CLOSE( timer.occured[14].second, now+0.9, 0.1 );
00280 
00281     // Test wrong parameters.
00282     BOOST_CHECK( timer.startTimer(4, -0.1) == false);
00283     BOOST_CHECK( timer.startTimer(500, 0.1) == false);
00284 
00285     timer.occured.clear();
00286 
00287     // Test resize.
00288     BOOST_CHECK( timer.startTimer(10, 0.5) );
00289     timer.setMaxTimers( 5 ); // clears the timer
00290     sleep(1);
00291     BOOST_CHECK( timer.occured.size() == 0 );
00292 }
00293 
00294 BOOST_AUTO_TEST_SUITE_END()


rtt
Author(s): RTT Developers
autogenerated on Thu Jan 2 2014 11:35:40