00001
00002 #include "artdaq/DAQdata/Globals.hh"
00003 #include "artdaq/ArtModules/detail/RawEventQueueReader.hh"
00004
00005 #include "art/Framework/IO/Sources/put_product_in_principal.h"
00006 #include "canvas/Persistency/Provenance/FileFormatVersion.h"
00007 #include "canvas/Utilities/Exception.h"
00008 #include "artdaq-core/Data/Fragment.hh"
00009 #include <sys/time.h>
00010
00011 using std::string;
00012
00013 artdaq::detail::RawEventQueueReader::RawEventQueueReader(fhicl::ParameterSet const& ps,
00014 art::ProductRegistryHelper& help,
00015 art::SourceHelper const& pm) :
00016 pmaker(pm)
00017 , incoming_events(getGlobalQueue())
00018 , waiting_time(ps.get<double>("waiting_time", 86400.0))
00019 , resume_after_timeout(ps.get<bool>("resume_after_timeout", true))
00020 , pretend_module_name(ps.get<std::string>("raw_data_label","daq"))
00021 , unidentified_instance_name("unidentified")
00022 , shutdownMsgReceived(false)
00023 , outputFileCloseNeeded(false)
00024 , fragment_type_map_(Fragment::MakeSystemTypeMap())
00025 , readNext_calls_(0)
00026 {
00027 help.reconstitutes<Fragments, art::InEvent>(pretend_module_name,
00028 unidentified_instance_name);
00029 for (auto it = fragment_type_map_.begin(); it != fragment_type_map_.end(); ++it)
00030 {
00031 help.reconstitutes<Fragments, art::InEvent>(pretend_module_name, it->second);
00032 }
00033 }
00034
00035 void artdaq::detail::RawEventQueueReader::closeCurrentFile() {}
00036
00037 void artdaq::detail::RawEventQueueReader::readFile(string const&,
00038 art::FileBlock*& fb)
00039 {
00040 fb = new art::FileBlock(art::FileFormatVersion(1, "RawEvent2011"), "nothing");
00041 }
00042
00043 bool artdaq::detail::RawEventQueueReader::readNext(art::RunPrincipal* const & inR,
00044 art::SubRunPrincipal* const & inSR,
00045 art::RunPrincipal*& outR,
00046 art::SubRunPrincipal*& outSR,
00047 art::EventPrincipal*& outE)
00048 {
00049
00050
00051
00052
00053 if (readNext_calls_++ == 0)
00054 {
00055 incoming_events.setReaderIsReady();
00056 TRACE(50, "RawEventQueueReader::readNext after incoming_events.setReaderIsReady()");
00057 }
00058
00059 outR = 0;
00060 outSR = 0;
00061 outE = 0;
00062 RawEvent_ptr popped_event;
00063
00064
00065
00066
00067
00068 bool keep_looping = true;
00069 bool got_event = false;
00070 while (keep_looping)
00071 {
00072 keep_looping = false;
00073 got_event = incoming_events.deqTimedWait(popped_event, waiting_time);
00074 if (!got_event)
00075 {
00076 TLOG_INFO("RawEventQueueReader")
00077 << "InputFailure: Reading timed out in RawEventQueueReader::readNext()" << TLOG_ENDL;
00078 keep_looping = resume_after_timeout;
00079 }
00080 }
00081
00082
00083
00084
00085
00086 if (!got_event || !popped_event)
00087 {
00088 TLOG_DEBUG("RawEventQueueReader") << "Received shutdown message, returning false" << TLOG_ENDL;
00089 shutdownMsgReceived = true;
00090 return false;
00091 }
00092
00093
00094
00095
00096 art::Timestamp currentTime = time(0);
00097
00098
00099 if (inR == 0 || inR->run() != popped_event->runID())
00100 {
00101 outR = pmaker.makeRunPrincipal(popped_event->runID(),
00102 currentTime);
00103 }
00104
00105 if (popped_event->numFragments() == 1)
00106 {
00107 if (popped_event->releaseProduct(Fragment::EndOfRunFragmentType)->size() == 1)
00108 {
00109 art::EventID const evid(art::EventID::flushEvent());
00110 outR = pmaker.makeRunPrincipal(evid.runID(), currentTime);
00111 outSR = pmaker.makeSubRunPrincipal(evid.subRunID(), currentTime);
00112 outE = pmaker.makeEventPrincipal(evid, currentTime);
00113 return true;
00114 }
00115 else if (popped_event->releaseProduct(Fragment::EndOfSubrunFragmentType)->size() == 1)
00116 {
00117
00118 if (inR == 0 || inR->run() != popped_event->runID())
00119 {
00120 outSR = pmaker.makeSubRunPrincipal(popped_event->runID(),
00121 popped_event->subrunID(),
00122 currentTime);
00123 #ifdef ARTDAQ_ART_EVENTID_HAS_EXPLICIT_RUNID
00124 art::EventID const evid(art::EventID::flushEvent(outR->id(), outSR->id()));
00125 #else
00126 art::EventID const evid(art::EventID::flushEvent(outSR->id()));
00127 #endif
00128 outE = pmaker.makeEventPrincipal(evid, currentTime);
00129 }
00130 else
00131 {
00132
00133
00134
00135
00136 if (inSR != 0 && !inSR->id().isFlush() && inSR->subRun() == popped_event->subrunID())
00137 {
00138 art::EventID const evid(art::EventID::flushEvent(inR->id()));
00139 outSR = pmaker.makeSubRunPrincipal(evid.subRunID(), currentTime);
00140 outE = pmaker.makeEventPrincipal(evid, currentTime);
00141
00142
00143
00144 }
00145 else
00146 {
00147 outSR = pmaker.makeSubRunPrincipal(popped_event->runID(),
00148 popped_event->subrunID(),
00149 currentTime);
00150 #ifdef ARTDAQ_ART_EVENTID_HAS_EXPLICIT_RUNID
00151 art::EventID const evid(art::EventID::flushEvent(inR->id(), outSR->id()));
00152 #else
00153 art::EventID const evid(art::EventID::flushEvent(outSR->id()));
00154 #endif
00155 outE = pmaker.makeEventPrincipal(evid, currentTime);
00156
00157
00158 }
00159 outR = 0;
00160 }
00161
00162 return true;
00163 }
00164 }
00165
00166
00167 art::SubRunID subrun_check(popped_event->runID(), popped_event->subrunID());
00168 if (inSR == 0 || subrun_check != inSR->id())
00169 {
00170 outSR = pmaker.makeSubRunPrincipal(popped_event->runID(),
00171 popped_event->subrunID(),
00172 currentTime);
00173 }
00174 outE = pmaker.makeEventPrincipal(popped_event->runID(),
00175 popped_event->subrunID(),
00176 popped_event->sequenceID(),
00177 currentTime);
00178
00179 std::vector<Fragment::type_t> type_list;
00180 popped_event->fragmentTypes(type_list);
00181
00182 std::map<Fragment::type_t, std::string>::const_iterator iter_end =
00183 fragment_type_map_.end();
00184 for (size_t idx = 0; idx < type_list.size(); ++idx)
00185 {
00186 std::map<Fragment::type_t, std::string>::const_iterator iter =
00187 fragment_type_map_.find(type_list[idx]);
00188 if (iter != iter_end)
00189 {
00190 put_product_in_principal(popped_event->releaseProduct(type_list[idx]),
00191 *outE,
00192 pretend_module_name,
00193 iter->second);
00194 }
00195 else
00196 {
00197 put_product_in_principal(popped_event->releaseProduct(type_list[idx]),
00198 *outE,
00199 pretend_module_name,
00200 unidentified_instance_name);
00201 TLOG_WARNING("RawEventQueueReader")
00202 << "UnknownFragmentType: The product instance name mapping for fragment type \""
00203 << ((int)type_list[idx]) << "\" is not known. Fragments of this "
00204 << "type will be stored in the event with an instance name of \""
00205 << unidentified_instance_name << "\"." << TLOG_ENDL;
00206 }
00207 }
00208
00209 return true;
00210 }