|
Teuchos Package Browser (Single Doxygen Collection)
Version of the Day
|
00001 // @HEADER 00002 // *********************************************************************** 00003 // 00004 // Teuchos: Common Tools Package 00005 // Copyright (2004) Sandia Corporation 00006 // 00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive 00008 // license for use of this work by or on behalf of the U.S. Government. 00009 // 00010 // Redistribution and use in source and binary forms, with or without 00011 // modification, are permitted provided that the following conditions are 00012 // met: 00013 // 00014 // 1. Redistributions of source code must retain the above copyright 00015 // notice, this list of conditions and the following disclaimer. 00016 // 00017 // 2. Redistributions in binary form must reproduce the above copyright 00018 // notice, this list of conditions and the following disclaimer in the 00019 // documentation and/or other materials provided with the distribution. 00020 // 00021 // 3. Neither the name of the Corporation nor the names of the 00022 // contributors may be used to endorse or promote products derived from 00023 // this software without specific prior written permission. 00024 // 00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY 00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE 00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00036 // 00037 // Questions? Contact Michael A. Heroux (maherou@sandia.gov) 00038 // 00039 // *********************************************************************** 00040 // @HEADER 00041 00042 #ifndef TEUCHOS_PERFORMANCEMONITORBASE_H 00043 #define TEUCHOS_PERFORMANCEMONITORBASE_H 00044 00050 #include "Teuchos_ConfigDefs.hpp" 00051 #include "Teuchos_Array.hpp" 00052 #include "Teuchos_Comm.hpp" 00053 #include "Teuchos_RCP.hpp" 00054 #include "Teuchos_TableFormat.hpp" 00055 00056 namespace Teuchos 00057 { 00065 enum ECounterSetOp { Intersection, Union }; 00066 00091 void 00092 mergeCounterNames (const Comm<int>& comm, 00093 const Array<std::string>& localNames, 00094 Array<std::string>& globalNames, 00095 const ECounterSetOp setOp); 00096 00140 template <class T> 00141 class PerformanceMonitorBase 00142 { 00143 public: 00145 PerformanceMonitorBase(T& counter_in, bool reset=false) 00146 : counter_(counter_in), isRecursiveCall_(counter_.isRunning()) 00147 { 00148 (void) reset; // get rid of "unused parameter" warning 00149 counter_.incrementNumCalls (); 00150 } 00151 00156 virtual ~PerformanceMonitorBase() {} 00157 00172 static RCP<T> getNewCounter (const std::string& name); 00173 00175 static TableFormat& format() 00176 { 00177 // WARNING This is not thread safe! In particular, if multiple 00178 // threads call this method for the "first time" at the same 00179 // time, the RCP may be initialized incorrectly. 00180 static RCP<TableFormat> rtn=rcp(new TableFormat()); 00181 return *rtn; 00182 } 00183 00191 static RCP<T> 00192 lookupCounter (const std::string& name); 00193 00198 static void clearCounters (); 00199 00209 static TEUCHOS_DEPRECATED void clearTimers (); 00210 00216 static void clearCounter (const std::string& name); 00217 00228 static TEUCHOS_DEPRECATED void clearTimer (const std::string& name); 00229 00230 protected: 00231 00233 const T& counter() const { return counter_; } 00234 00236 T& counter() { return counter_; } 00237 00244 bool isRecursiveCall() const { return isRecursiveCall_; } 00245 00247 static std::map<std::string, RCP<T> >& counters() 00248 { 00249 // Use the "Meyers Trick" to create static data safely. 00250 // 00251 // WARNING This is not thread safe! In particular, if multiple 00252 // threads call counters() for the "first time" at the same 00253 // time, the array may be initialized incorrectly. 00254 static std::map<std::string, RCP<T> > theCounters; 00255 static int initialized; 00256 if (! initialized) { 00257 theCounters.clear (); 00258 initialized = 1; 00259 } 00260 return theCounters; 00261 } 00262 00263 private: 00264 00266 T& counter_; 00267 00269 bool isRecursiveCall_; 00270 }; 00271 00272 template<class T> 00273 RCP<T> 00274 PerformanceMonitorBase<T>::getNewCounter (const std::string& name) 00275 { 00276 typedef std::map<std::string, RCP<T> > map_type; 00277 typedef typename map_type::iterator iter_type; 00278 00279 map_type& ctrs = counters (); 00280 iter_type it = ctrs.find (name); 00281 RCP<T> newCounter = null; 00282 if (it == ctrs.end ()) { 00283 newCounter = rcp (new T (name)); 00284 #ifdef HAVE_TEUCHOS_DEBUG 00285 const bool wasNotThere = ctrs.insert (std::make_pair (name, newCounter)).second; 00286 TEUCHOS_TEST_FOR_EXCEPTION( 00287 ! wasNotThere, std::logic_error, 00288 "getNewCounter: insert() claims that timer \"" << name << "\" was " 00289 "already there in the map, even though find() claims that it was not. " 00290 "Please report this bug to the Teuchos developers."); 00291 #else 00292 // Use the returned iterator to optimize insertion. 00293 ctrs.insert (it, std::make_pair (name, newCounter)); 00294 #endif // HAVE_TEUCHOS_DEBUG 00295 } else { 00296 newCounter = it->second; 00297 #ifdef HAVE_TEUCHOS_DEBUG 00298 TEUCHOS_TEST_FOR_EXCEPTION( 00299 it->second.is_null (), std::logic_error, 00300 "getNewCounter: Timer \"" << name << "\" was already there in the map, " 00301 "but looking it up by name resulted in a null timer. " 00302 "Please report this bug to the Teuchos developers."); 00303 TEUCHOS_TEST_FOR_EXCEPTION( 00304 name != it->second->name (), std::logic_error, 00305 "getNewCounter: Timer \"" << name << "\" was already there in the map, " 00306 "but looking it up by name resulted in a timer with a different name \"" 00307 << it->second->name () << "\". Please report this bug to the Teuchos " 00308 "developers."); 00309 #endif // HAVE_TEUCHOS_DEBUG 00310 } 00311 00312 #ifdef HAVE_TEUCHOS_DEBUG 00313 TEUCHOS_TEST_FOR_EXCEPTION( 00314 newCounter.is_null (), std::logic_error, 00315 "getNewCounter: At end of method, when creating timer \"" << name 00316 << "\", newCounter is null. Please report this bug to the Teuchos " 00317 "developers."); 00318 #endif // HAVE_TEUCHOS_DEBUG 00319 return newCounter; 00320 } 00321 00322 template<class T> 00323 RCP<T> 00324 PerformanceMonitorBase<T>::lookupCounter (const std::string& name) 00325 { 00326 typedef std::map<std::string, RCP<T> > map_type; 00327 typedef typename map_type::iterator iter_type; 00328 00329 map_type& ctrs = counters (); 00330 iter_type it = ctrs.find (name); 00331 if (it == ctrs.end ()) { 00332 return null; 00333 } else { 00334 return it->second; 00335 } 00336 } 00337 00338 template<class T> 00339 void 00340 PerformanceMonitorBase<T>::clearCounter (const std::string& name) 00341 { 00342 counters ().erase (name); 00343 } 00344 00345 template<class T> 00346 void 00347 PerformanceMonitorBase<T>::clearTimer (const std::string& name) 00348 { 00349 clearCounter (name); 00350 } 00351 00352 template<class T> 00353 void 00354 PerformanceMonitorBase<T>::clearTimers () 00355 { 00356 clearCounters (); 00357 } 00358 00359 template<class T> 00360 void 00361 PerformanceMonitorBase<T>::clearCounters () 00362 { 00363 counters ().clear (); 00364 } 00365 00366 } // namespace Teuchos 00367 00368 #endif // TEUCHOS_PERFORMANCEMONITORBASE_H
1.7.6.1