Go to the documentation of this file.00001 #ifndef FWCore_Framework_Path_h
00002 #define FWCore_Framework_Path_h
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014 #include "FWCore/Framework/interface/CurrentProcessingContext.h"
00015 #include "FWCore/Framework/src/WorkerInPath.h"
00016 #include "FWCore/Framework/src/Worker.h"
00017 #include "DataFormats/Common/interface/HLTenums.h"
00018 #include "DataFormats/Common/interface/TriggerResults.h"
00019
00020 #include "boost/shared_ptr.hpp"
00021
00022 #include <string>
00023 #include <vector>
00024
00025 #include "FWCore/Framework/src/RunStopwatch.h"
00026
00027 namespace edm {
00028
00029 class Path {
00030 public:
00031 typedef hlt::HLTState State;
00032
00033 typedef std::vector<WorkerInPath> WorkersInPath;
00034 typedef WorkersInPath::size_type size_type;
00035 typedef boost::shared_ptr<HLTGlobalStatus> TrigResPtr;
00036
00037 Path(int bitpos, std::string const& path_name,
00038 WorkersInPath const& workers,
00039 TrigResPtr trptr,
00040 ActionTable const& actions,
00041 boost::shared_ptr<ActivityRegistry> reg,
00042 bool isEndPath);
00043
00044 template <typename T>
00045 void processOneOccurrence(typename T::MyPrincipal&, EventSetup const&);
00046
00047 int bitPosition() const { return bitpos_; }
00048 std::string const& name() const { return name_; }
00049
00050 std::pair<double, double> timeCpuReal() const {
00051 if(stopwatch_) {
00052 return std::pair<double, double>(stopwatch_->cpuTime(), stopwatch_->realTime());
00053 }
00054 return std::pair<double, double>(0., 0.);
00055 }
00056
00057 std::pair<double, double> timeCpuReal(unsigned int const i) const {
00058 return workers_.at(i).timeCpuReal();
00059 }
00060
00061 void clearCounters();
00062
00063 int timesRun() const { return timesRun_; }
00064 int timesPassed() const { return timesPassed_; }
00065 int timesFailed() const { return timesFailed_; }
00066 int timesExcept() const { return timesExcept_; }
00067
00068 State state() const { return state_; }
00069
00070 size_type size() const { return workers_.size(); }
00071 int timesVisited(size_type i) const { return workers_.at(i).timesVisited(); }
00072 int timesPassed (size_type i) const { return workers_.at(i).timesPassed() ; }
00073 int timesFailed (size_type i) const { return workers_.at(i).timesFailed() ; }
00074 int timesExcept (size_type i) const { return workers_.at(i).timesExcept() ; }
00075 Worker const* getWorker(size_type i) const { return workers_.at(i).getWorker(); }
00076
00077 void useStopwatch();
00078 private:
00079 RunStopwatch::StopwatchPointer stopwatch_;
00080 int timesRun_;
00081 int timesPassed_;
00082 int timesFailed_;
00083 int timesExcept_;
00084
00085 State state_;
00086
00087 int bitpos_;
00088 std::string name_;
00089 TrigResPtr trptr_;
00090 boost::shared_ptr<ActivityRegistry> actReg_;
00091 ActionTable const* act_table_;
00092
00093 WorkersInPath workers_;
00094
00095 bool isEndPath_;
00096
00097
00098
00099 bool handleWorkerFailure(cms::Exception const& e, int nwrwue, bool isEvent);
00100 void recordUnknownException(int nwrwue, bool isEvent);
00101 void recordStatus(int nwrwue, bool isEvent);
00102 void updateCounters(bool succeed, bool isEvent);
00103 };
00104
00105 namespace {
00106 template <typename T>
00107 class PathSignalSentry {
00108 public:
00109 PathSignalSentry(ActivityRegistry *a,
00110 std::string const& name,
00111 int const& nwrwue,
00112 hlt::HLTState const& state) :
00113 a_(a), name_(name), nwrwue_(nwrwue), state_(state) {
00114 if (a_) T::prePathSignal(a_, name_);
00115 }
00116 ~PathSignalSentry() {
00117 HLTPathStatus status(state_, nwrwue_);
00118 if(a_) T::postPathSignal(a_, name_, status);
00119 }
00120 private:
00121 ActivityRegistry* a_;
00122 std::string const& name_;
00123 int const& nwrwue_;
00124 hlt::HLTState const& state_;
00125 };
00126 }
00127
00128 template <typename T>
00129 void Path::processOneOccurrence(typename T::MyPrincipal& ep, EventSetup const& es) {
00130
00131
00132
00133 int nwrwue = -1;
00134 std::auto_ptr<PathSignalSentry<T> > signaler(new PathSignalSentry<T>(actReg_.get(), name_, nwrwue, state_));
00135
00136
00137 RunStopwatch stopwatch(T::isEvent_ ? stopwatch_ : RunStopwatch::StopwatchPointer());
00138
00139 if (T::isEvent_) {
00140 ++timesRun_;
00141 }
00142 state_ = hlt::Ready;
00143
00144
00145 bool should_continue = true;
00146 CurrentProcessingContext cpc(&name_, bitPosition(), isEndPath_);
00147
00148 WorkersInPath::size_type idx = 0;
00149
00150
00151 for (WorkersInPath::iterator i = workers_.begin(), end = workers_.end();
00152 i != end && should_continue;
00153 ++i, ++idx) {
00154 ++nwrwue;
00155 assert (static_cast<int>(idx) == nwrwue);
00156 try {
00157 cpc.activate(idx, i->getWorker()->descPtr());
00158 should_continue = i->runWorker<T>(ep, es, &cpc);
00159 }
00160 catch(cms::Exception& e) {
00161
00162 should_continue = handleWorkerFailure(e, nwrwue, T::isEvent_);
00163 }
00164 catch(...) {
00165 recordUnknownException(nwrwue, T::isEvent_);
00166 throw;
00167 }
00168 }
00169 updateCounters(should_continue, T::isEvent_);
00170 recordStatus(nwrwue, T::isEvent_);
00171 }
00172
00173 }
00174
00175 #endif