9#include "Gaudi/Interfaces/IOptionsSvc.h"
12#include "hltinterface/DataCollector.h"
15#include "eformat/Status.h"
26 base_class(name, pSvcLocator)
32 ATH_MSG_INFO(
"HltROBDataProviderSvc::" << __FUNCTION__ <<
": name = " << name());
64 if (tmpsrc.human_detector() !=
"UNKNOWN") {
72 if (tmpsrc.human_detector() !=
"UNKNOWN") {
81 eformat::helper::SourceIdentifier tmpsrc(it.first);
82 ATH_MSG_INFO(
" RobId=0x" << MSG::hex << it.first <<
" -> in Sub Det = " << tmpsrc.human_detector());
84 for (
auto it_status: it.second) {
85 eformat::helper::Status tmpstatus(it_status);
87 << MSG::hex << std::setfill(
'0' ) << std::setw(8) << tmpstatus.code()
88 <<
" Generic Part=0x" << std::setw(4) << tmpstatus.generic()
89 <<
" Specific Part=0x" << std::setw(4) << tmpstatus.specific() << MSG::dec);
96 eformat::helper::SourceIdentifier tmpsrc(it.first, 0);
97 ATH_MSG_INFO(
" SubDetId=0x" << MSG::hex << it.first <<
" -> " << tmpsrc.human_detector());
98 for (
auto it_status : it.second) {
99 eformat::helper::Status tmpstatus(it_status);
101 << MSG::hex << std::setfill(
'0' ) << std::setw(8) << tmpstatus.code()
102 <<
" Generic Part=0x" << std::setw(4) << tmpstatus.generic()
103 <<
" Specific Part=0x" << std::setw(4) << tmpstatus.specific() << MSG::dec);
108 bool robOKSconfigFound =
false;
112 if ((jobOptionsSvc.retrieve()).isFailure()) {
115 if (jobOptionsSvc->has(
"DataFlowConfig.DF_Enabled_ROB_IDs") &&
116 m_enabledROBs.fromString(jobOptionsSvc->get(
"DataFlowConfig.DF_Enabled_ROB_IDs")).isSuccess()) {
117 robOKSconfigFound =
true;
119 << MSG::dec <<
m_enabledROBs.value().size() <<
" enabled ROB IDs.");
129 ATH_MSG_INFO(
" ---> The list of enabled ROBs has size = 0. No check will be performed ");
133 <<
". It was read from the partition database." );
136 <<
". It was read from job options." );
152 ATH_MSG_INFO(
" The following sub-detectors or sub-detector groups are configured for prefetching : Number = "
156 eformat::SubDetector sd(
static_cast<eformat::SubDetector
>(it));
157 eformat::helper::SourceIdentifier tmpsrc(sd, 0);
158 ATH_MSG_INFO(
" SubDetId = 0x" << MSG::hex << std::setw(2) << (
int)it << MSG::dec <<
" -> Group : "
159 << tmpsrc.human_group()
160 <<
" -> SubDetector : " << tmpsrc.human_detector() );
162 eformat::SubDetectorGroup sg(
static_cast<eformat::SubDetectorGroup
>(it));
163 ATH_MSG_INFO(
" SubDetGroup = 0x" << MSG::hex << std::setw(1) << (
int)it << MSG::dec <<
" -> Group : "
164 << eformat::helper::SubDetectorGroupDictionary.
string(sg));
170 eformat::helper::SourceIdentifier tmpsrc(rob);
189 return(StatusCode::SUCCESS);
195 return StatusCode::SUCCESS;
202 const std::string_view callerName)
204 ATH_MSG_VERBOSE(
"start of " << __FUNCTION__ <<
": Number of ROB Ids to add = " << robIds.size()
205 <<
" caller name = " << callerName);
209 std::vector<uint32_t> robIds_missing ;
212 std::vector<const ROBF*> robFragments_inCache ;
218 if (!robIds_missing.empty()) {
219 ATH_MSG_DEBUG( __FUNCTION__ <<
": Number of ROB Ids to reserve with DCM = " << robIds_missing.size());
223 hltinterface::DataCollector::instance()->reserveROBData(cache->globalEventNumber, robIds_missing);
226 auto mon_robres_nROBs =
Monitored::Scalar(
"NUMBER_ROBReserveData",robIds_missing.size());
228 }
catch (
const std::exception& ex) {
230 <<
"Failed to reserve ROB data, caught an unexpected exception: " << ex.what());
233 <<
"Failed to reserve ROB data, caught an unexpected exception.");
241 ATH_MSG_FATAL(
"Obsolete method HltROBDataProviderSvc::setNextEvent(const EventContext& context, const std::vector<ROBF>& result) called "
242 <<
"\n context = " << context <<
" number of ROB fragments = " << result.size() );
261 cache->currentLvl1ID =
re->lvl1_id();
263 cache->globalEventNumber =
re->global_id();
271 std::vector<ROBF> rob_fragments;
277 auto iter =
re->child_iter();
279 rob_fragments.emplace_back(fp);
282 const size_t nRobs = rob_fragments.size();
286 ATH_MSG_DEBUG(
" current [global id, LVL1 id] = [" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
"]" );
288 ATH_MSG_DEBUG(
" size of ROB cache = " << cache->robmap.size() );
303 const std::vector<uint32_t>& robIds, std::vector<const ROBF*>& robFragments,
304 const std::string_view callerName)
309 std::lock_guard<std::mutex>
lock( cache->eventCache_mtx );
313 ATH_MSG_VERBOSE(
"start of " << __FUNCTION__ <<
": Number of ROB Ids to get = " << robIds.size()
314 <<
" caller name = " << callerName);
317 std::vector<uint32_t> robIds_missing ;
323 if (robIds_missing.empty()) {
324 ATH_MSG_DEBUG( __FUNCTION__ <<
": All requested ROB Ids were found in the cache. ");
329 ATH_MSG_DEBUG( __FUNCTION__ <<
": Number of ROB Ids to retrieve with DCM = " << robIds_missing.size());
331 typedef std::vector<hltinterface::DCM_ROBInfo> ROBInfoVec;
332 ROBInfoVec vRobInfos;
335 vRobInfos.reserve( robIds_missing.size() ) ;
338 hltinterface::DataCollector::instance()->collect(vRobInfos, cache->globalEventNumber, robIds_missing);
343 }
catch (
const std::exception& ex) {
345 <<
"Failed to collect ROBs, caught an unexpected exception: " << ex.what()
346 <<
". Throwing hltonl::Exception::EventSourceCorrupted" );
350 <<
"Failed to collect ROBs, caught an unexpected exception. "
351 <<
"Throwing hltonl::Exception::EventSourceCorrupted" );
356 std::vector<ROBF> robFragments_missing;
357 robFragments_missing.reserve( vRobInfos.size() );
358 for(ROBInfoVec::const_iterator it=vRobInfos.begin(); it!=vRobInfos.end(); ++it) {
359 ATH_MSG_DEBUG(__FUNCTION__ <<
" ROB Id = 0x" << MSG::hex << it->robFragment.source_id() << MSG::dec
360 <<
" retrieved from DCM for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
361 robFragments_missing.push_back( it->robFragment );
368 for (
const ROBF* robFrag : robFragments) {
373 std::set<uint32_t> robIds_ignored;
377 for (
const hltinterface::DCM_ROBInfo& robInfo : vRobInfos) {
381 if (robIds_ignored.find(robInfo.robFragment.source_id()) != robIds_ignored.end()) {
388 monitorData.requested_ROBs[robInfo.robFragment.source_id()] =
robmap_getRobData(robInfo.robFragment, status);
392 std::set<uint32_t> robIds_disabled;
396 for (uint32_t robId : robIds_disabled) {
417 static_assert(std::is_nothrow_move_constructible<robmonitor::ROBDataMonitorStruct>::value);
427 robData.rob_size = robFrag.fragment_size_word();
428 robData.rob_status_word = robFrag.nstatus() ? robFrag.status()[0] : 0;
429 robData.rob_history = robStatus;
459 for (
const auto& el :
m_eventsCache.get( context )->robmap )
475 ATH_MSG_VERBOSE(
"start of " << __FUNCTION__ <<
" caller name = " << callerName);
480 std::lock_guard<std::mutex>
lock( cache->eventCache_mtx );
483 if (cache->isEventComplete)
return 0;
485 typedef std::vector<hltinterface::DCM_ROBInfo> ROBInfoVec;
486 ROBInfoVec vRobInfos ;
496 hltinterface::DataCollector::instance()->collect(vRobInfos, cache->globalEventNumber);
498 ATH_MSG_DEBUG( __FUNCTION__ <<
": Number of received ROB Ids = " << vRobInfos.size() );
500 auto mon_col_nROBs =
Monitored::Scalar(
"NUMBER_CollectAllROBs",vRobInfos.size());
502 }
catch (
const std::exception& ex) {
504 <<
"Failed to collect complete event, caught an unexpected exception: " << ex.what()
505 <<
". Throwing hltonl::Exception::EventSourceCorrupted" );
509 <<
"Failed to collect complete event, caught an unexpected exception. "
510 <<
"Throwing hltonl::Exception::EventSourceCorrupted" );
515 std::vector<ROBF> robFragments_missing;
516 robFragments_missing.reserve( vRobInfos.size() );
517 for(ROBInfoVec::const_iterator it=vRobInfos.begin(); it!=vRobInfos.end(); ++it) {
518 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id = 0x" << MSG::hex << it->robFragment.source_id() << MSG::dec
519 <<
" retrieved from DCM for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
520 robFragments_missing.push_back( it->robFragment );
526 cache->isEventComplete =
true;
528 return vRobInfos.size();
542 const uint32_t* rob_it_status;
543 const uint32_t null_status(0);
545 if (rob->nstatus() == 0) {
546 rob_it_status = &null_status;
549 rob->status(rob_it_status);
553 eformat::helper::SourceIdentifier tmpsrc(rob->rob_source_id());
556 FilterRobMap::iterator map_it_rob =
m_filterRobMap.find(tmpsrc.code());
558 for (
auto it_status: (*map_it_rob).second) {
559 if (*rob_it_status == it_status) {
560 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id = 0x" << MSG::hex << tmpsrc.code()
561 <<
" with status = 0x" << *rob_it_status << MSG::dec
562 <<
" removed due to ROB filter rule.");
569 FilterSubDetMap::iterator map_it_subdet =
m_filterSubDetMap.find(tmpsrc.subdetector_id());
571 for (
auto it_status: (*map_it_subdet).second) {
572 if (*rob_it_status == it_status) {
573 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id = 0x" << MSG::hex << tmpsrc.code()
574 <<
" with status = 0x" << *rob_it_status << MSG::dec
575 <<
" removed due to SubDet filter rule.");
586 cache->event =
nullptr;
587 cache->currentLvl1ID = 0;
588 cache->globalEventNumber = 0;
589 cache->eventStatus = 0;
590 cache->isEventComplete =
false;
591 { cache->robmap.clear(); }
595 std::vector<const ROBF*>& robFragments_inCache,
596 std::vector<uint32_t>& robIds_missing,
597 std::optional<std::reference_wrapper<std::set<uint32_t>>> robIds_disabled )
599 ATH_MSG_VERBOSE(
"start of " << __FUNCTION__ <<
" number of ROB Ids to check = " << robIds_toCheck.size());
602 robFragments_inCache.clear();
603 robIds_missing.clear();
606 robFragments_inCache.reserve( robIds_toCheck.size() );
607 robIds_missing.reserve( robIds_toCheck.size() );
610 for (uint32_t
id : robIds_toCheck) {
613 std::vector<uint32_t>::iterator missing_it = std::find(robIds_missing.begin(), robIds_missing.end(),
id);
614 if (missing_it != robIds_missing.end()) {
615 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id : 0x" << MSG::hex <<
id << MSG::dec <<
" is already on the list of missing IDs.");
620 { ROBMAP::const_iterator map_it = cache->robmap.find(
id);
621 if (map_it != cache->robmap.end()) {
622 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id 0x" << MSG::hex <<
id << MSG::dec
623 <<
" found for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
624 robFragments_inCache.push_back( &(map_it->second) );
631 std::vector<uint32_t>::const_iterator rob_enabled_it =
634 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id : 0x" << MSG::hex <<
id << MSG::dec
635 <<
" will be not added, since it is not on the list of enabled ROBs.");
636 if (robIds_disabled) {
637 robIds_disabled->get().insert(
id);
644 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id : 0x" << MSG::hex <<
id << MSG::dec <<
" is missing ");
645 robIds_missing.push_back(
id ) ;
650 std::optional<std::reference_wrapper<std::set<uint32_t>>> robIds_ignored)
652 ATH_MSG_VERBOSE(
"start of " << __FUNCTION__ <<
" number of ROB fragments to add = " << robFragments.size());
654 for (
const ROBF& rob : robFragments) {
657 uint32_t
id = rob.source_id();
658 ATH_MSG_VERBOSE(__FUNCTION__ <<
" Id = 0x" << std::hex <<
id << std::dec );
661 if ( (eformat::helper::SourceIdentifier(
id).module_id() != 0) &&
662 (eformat::helper::SourceIdentifier(
id).subdetector_id() == eformat::TDAQ_LVL2) ) {
663 id = eformat::helper::SourceIdentifier(eformat::helper::SourceIdentifier(
id).subdetector_id(),0).code();
665 ATH_MSG_ERROR(__FUNCTION__ <<
" Inconsistent flag for masking L2/EF module IDs");
668 }
else if ( (eformat::helper::SourceIdentifier(
id).module_id() != 0) &&
669 (eformat::helper::SourceIdentifier(
id).subdetector_id() == eformat::TDAQ_EVENT_FILTER) &&
671 id = eformat::helper::SourceIdentifier(eformat::helper::SourceIdentifier(
id).subdetector_id(),0).code();
675 { ROBMAP::const_iterator it = cache->robmap.find(
id);
676 if (it != cache->robmap.end()) {
677 ATH_MSG_VERBOSE(__FUNCTION__ <<
" Duplicate ROB Id 0x" << MSG::hex <<
id << MSG::dec
678 <<
" found for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
685 if (rob.nstatus() > 0) {
686 const uint32_t* it_status;
687 rob.status(it_status);
688 eformat::helper::Status tmpstatus(*it_status);
689 ATH_MSG_VERBOSE(__FUNCTION__ <<
" ROB Id = 0x" << MSG::hex <<
id << std::setfill(
'0')
690 <<
" with Generic Status Code = 0x" << std::setw(4) << tmpstatus.generic()
691 <<
" and Specific Status Code = 0x" << std::setw(4) << tmpstatus.specific() << MSG::dec
692 <<
" removed for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
694 if (robIds_ignored) {
695 robIds_ignored->get().insert(
id);
702 ATH_MSG_VERBOSE(__FUNCTION__ <<
" Empty ROB Id = 0x" << MSG::hex <<
id << MSG::dec
703 <<
" removed for (global Id, L1 Id) = (" << cache->globalEventNumber <<
"," << cache->currentLvl1ID <<
")" );
708 { cache->robmap.insert(std::make_pair(
id,std::move(rob))); }
const boost::regex re(r_e)
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
static const size_t MAX_ROBFRAGMENTS_GUESS
Service to serve ROB data in online environment.
virtual void lock()=0
Interface to allow an object to lock itself when made const in SG.
OFFLINE_FRAGMENTS_NAMESPACE::FullEventFragment RawEvent
data type for reading raw event
size_t size() const
Number of registered mappings.
std::vector< uint32_t > m_prefetchWholeROSList
virtual uint32_t getEventStatus(const EventContext &) override
Retrieve the status for the event.
virtual void setEventStatus(const EventContext &, uint32_t) override
Store the status for the event.
virtual void setNextEvent(const EventContext &, const std::vector< ROBF > &) override
Start a new event with a set of ROB fragments, e.g. from LVL1 result, in online and add the fragments...
Gaudi::Property< std::vector< uint32_t > > m_enabledROBs
ServiceHandle< ITrigCostSvc > m_trigCostSvcHandle
HltROBDataProviderSvc(const std::string &name, ISvcLocator *pSvcLocator)
OFFLINE_FRAGMENTS_NAMESPACE::ROBFragment ROBF
ROB Fragment class.
robmonitor::ROBDataStruct robmap_getRobData(const ROBF &, robmonitor::ROBHistory)
method to get ROB fragment from ROBF input: context ROB fragment to be parsed ROB history status
void eventCache_clear(EventCache *)
method to clear an event cache in a slot input: pointer to cache
Gaudi::Property< ArrayPairIntType > m_filterRobWithStatus
bool robmap_filterRobWithStatus(const ROBF *)
method to filter ROBs with given Status code
void eventCache_checkRobListToCache(EventCache *, const std::vector< uint32_t > &, std::vector< const ROBF * > &, std::vector< uint32_t > &, std::optional< std::reference_wrapper< std::set< uint32_t > > > robIds_disabled=std::nullopt)
method to compare a list of ROB Ids to the ones in an event cache in a slot input: pointer to cache v...
virtual void addROBData(const EventContext &, const std::vector< uint32_t > &, const std::string_view callerName="UNKNOWN") override
Signal ROB fragments which should be considered for prefetching in online running.
virtual void getROBData(const EventContext &, const std::vector< uint32_t > &, std::vector< const ROBF * > &, const std::string_view callerName="UNKNOWN") override
Retrieve ROB fragments for given ROB ids from the ROB cache.
virtual StatusCode finalize() override
Gaudi::Property< bool > m_prefetchAllROBsfromROS
FilterSubDetMap m_filterSubDetMap
virtual StatusCode initialize() override
void eventCache_addRobData(EventCache *, std::vector< ROBF > &&, std::optional< std::reference_wrapper< std::set< uint32_t > > > robIds_ignored=std::nullopt)
method to add ROB fragments to an event cache in a slot input: pointer to cache vector of ROB fragmen...
virtual int collectCompleteEventData(const EventContext &, const std::string_view callerName="UNKNOWN") override
retrieve in online running all ROBs for the event from the readout system. Only those ROBs are retrie...
Gaudi::Property< ArrayPairIntType > m_filterSubDetWithStatus
virtual bool isEventComplete(const EventContext &) const override
Flag to check if all event data have been retrieved.
virtual void processCachedROBs(const EventContext &, const std::function< void(const ROBF *)> &) const override
Apply a function to all ROBs in the cache.
ToolHandle< GenericMonitoringTool > m_monTool
Monitoring tool.
virtual const RawEvent * getEvent(const EventContext &) override
Retrieve the full event fragment.
Gaudi::Property< std::vector< uint8_t > > m_prefetchSubDetROS
FilterRobMap m_filterRobMap
SG::SlotSpecificObj< EventCache > m_eventsCache
An event cache for each slot.
Gaudi::Property< bool > m_filterEmptyROB
Filter out empty ROB fragments which are send by the ROS.
Gaudi::Property< bool > m_readROBfromOKS
Gaudi::Property< bool > m_doCostMonitoring
bool m_maskL2EFModuleID
For Run 1 the module ID for the Lvl2/EF result contained the machine ID and needed to be filtered out...
Group of local monitoring quantities and retain correlation when filling histograms
Declare a monitored scalar variable.
Maintain a set of objects, one per slot.
utility class to measure time duration in AthenaMT The pattern when it is useful: AlgA tags the begin...
uint64_t microsecondsSinceEpoch() const
Thrown if event source throws an exception when new event is requested.
The structure which is used to monitor the ROB data request in L2 It is created for every addROBData ...
A structure with data about ROB properties.
const DataType * PointerType
size_t getNSlots()
Return the number of event slots.
ROBHistory
A structure with data about ROB properties.
struct which provides the event cache for each slot