OPeNDAP Hyrax Back End Server (BES) Updated for version 3.8.3
BESStopWatch.cc
Go to the documentation of this file.
00001 // BESStopWatch.cc
00002 
00003 // This file is part of bes, A C++ back-end server implementation framework
00004 // for the OPeNDAP Data Access Protocol.
00005 
00006 // Copyright (c) 2004-2009 University Corporation for Atmospheric Research
00007 // Author: Patrick West <pwest@ucar.edu> and Jose Garcia <jgarcia@ucar.edu>
00008 //
00009 // This library is free software; you can redistribute it and/or
00010 // modify it under the terms of the GNU Lesser General Public
00011 // License as published by the Free Software Foundation; either
00012 // version 2.1 of the License, or (at your option) any later version.
00013 // 
00014 // This library is distributed in the hope that it will be useful,
00015 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00016 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00017 // Lesser General Public License for more details.
00018 // 
00019 // You should have received a copy of the GNU Lesser General Public
00020 // License along with this library; if not, write to the Free Software
00021 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00022 //
00023 // You can contact University Corporation for Atmospheric Research at
00024 // 3080 Center Green Drive, Boulder, CO 80301
00025  
00026 // (c) COPYRIGHT University Corporation for Atmospheric Research 2004-2005
00027 // Please read the full copyright statement in the file COPYRIGHT_UCAR.
00028 //
00029 // Authors:
00030 //      pwest       Patrick West <pwest@ucar.edu>
00031 //      jgarcia     Jose Garcia <jgarcia@ucar.edu>
00032 
00033 #include <cerrno>
00034 #include <string>
00035 #include <iostream>
00036 #include <cstring>
00037 
00038 using std::string ;
00039 using std::endl ;
00040 
00041 #include "BESStopWatch.h"
00042 #include "BESDebug.h"
00043 
00044 bool
00045 BESStopWatch::start()
00046 {
00047     // get timer for current usage
00048     if( getrusage( RUSAGE_SELF, &_start_usage ) != 0 )
00049     {
00050         int myerrno = errno ;
00051         char *c_err = strerror( myerrno ) ;
00052         string err = "getrusage failed in start: " ;
00053         if( c_err )
00054         {
00055             err += c_err ;
00056         }
00057         else
00058         {
00059             err += "unknown error" ;
00060         }
00061         BESDEBUG( "timing", err ) ;
00062         _started = false ;
00063     }
00064     else
00065     {
00066         _started = true ;
00067     }
00068 
00069     // either we started the stop watch, or failed to start it. Either way,
00070     // no timings are available, so set stopped to false.
00071     _stopped = false ;
00072 
00073     return _started ;
00074 }
00075 
00076 bool
00077 BESStopWatch::stop()
00078 {
00079     // if we have started, the we can stop. Otherwise just fall through.
00080     if( _started )
00081     {
00082         // get timer for current usage
00083         if( getrusage( RUSAGE_SELF, &_stop_usage ) != 0 )
00084         {
00085             int myerrno = errno ;
00086             char *c_err = strerror( myerrno ) ;
00087             string err = "getrusage failed in stop: " ;
00088             if( c_err )
00089             {
00090                 err += c_err ;
00091             }
00092             else
00093             {
00094                 err += "unknown error" ;
00095             }
00096             BESDEBUG( "timing", err ) ;
00097             _started = false ;
00098             _stopped = false ;
00099         }
00100         else
00101         {
00102             // get the difference between the _start_usage and the
00103             // _stop_usage and save the difference.
00104             bool success = timeval_subtract() ;
00105             if( !success )
00106             {
00107                 BESDEBUG( "timing", "failed to get timing" ) ;
00108                 _started = false ;
00109                 _stopped = false ;
00110             }
00111             else
00112             {
00113                 _stopped = true ;
00114             }
00115         }
00116     }
00117     
00118     return _stopped ;
00119 }
00120 
00121 bool
00122 BESStopWatch::timeval_subtract()
00123 {
00124     struct timeval &start = _start_usage.ru_utime ;
00125     struct timeval &stop = _stop_usage.ru_utime ;
00126 
00127     /* Perform the carry for the later subtraction by updating y. */
00128     if( stop.tv_usec < start.tv_usec )
00129     {
00130         int nsec = (start.tv_usec - stop.tv_usec) / 1000000 + 1 ;
00131         start.tv_usec -= 1000000 * nsec ;
00132         start.tv_sec += nsec ;
00133     }
00134     if( stop.tv_usec - start.tv_usec > 1000000 )
00135     {
00136         int nsec = (start.tv_usec - stop.tv_usec) / 1000000 ;
00137         start.tv_usec += 1000000 * nsec ;
00138         start.tv_sec -= nsec ;
00139     }
00140 
00141     /* Compute the time remaining to wait.
00142     tv_usec  is certainly positive. */
00143     _result.tv_sec = stop.tv_sec - start.tv_sec ;
00144     _result.tv_usec = stop.tv_usec - start.tv_usec ;
00145 
00146     /* Return 1 if result is negative. */
00147     return !(stop.tv_sec < start.tv_sec) ;
00148 }
00149 
00156 void
00157 BESStopWatch::dump( ostream &strm ) const
00158 {
00159     strm << BESIndent::LMarg << "BESStopWatch::dump - ("
00160                              << (void *)this << ")" << endl ;
00161 }
00162