ATLAS Offline Software
Loading...
Searching...
No Matches
EvtIdModifierSvc.cxx
Go to the documentation of this file.
1
2
3/*
4 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
5*/
6
7// EvtIdModifierSvc.cxx
8// Implementation file for class EvtIdModifierSvc
9// Author: S.Binet<binet@cern.ch>
11
12// AthenaServices includes
13#include "EvtIdModifierSvc.h"
14
15// STL includes
16#include <algorithm>
17#include <set>
18
19// FrameWork includes
21
22// EventInfo includes
23#include "EventInfo/EventID.h"
24
25
26namespace {
27constexpr int prop_per_nplet{6};
28
29enum ModFlag {
30 RUNNBR = 1 << 0,
31 EVTNBR = 1 << 1,
32 TIMESTAMP = 1 << 2,
33 LBKNBR = 1 << 3
34};
35
37
38} // namespace
39
41// Public methods:
43
44// Constructors
46EvtIdModifierSvc::EvtIdModifierSvc(const std::string& name,
47 ISvcLocator* pSvcLocator)
48 : base_class(name, pSvcLocator) {
49
50 declareProperty("Modifiers", m_evtNpletsProp,
51 "A list of n-uplets "
52 "(RunNumber,EvtNbr,TimeStamp,LumiBlock,Nevents,ModBit).");
53
54 declareProperty("EvtStoreName", m_evtStoreName = "StoreGateSvc",
55 "Name of the event store whose EventIDs will be modified.");
56
57 declareProperty("SkipEvents", m_firstEvtIdx = 0,
58 "Number of events to skip before modifying EventIDs.");
59 declareProperty("SkippedEvents", m_skippedEvents = 0,
60 "Number of events skipped in the EventSelector.");
61}
62
63// Athena Service's Hooks
66 ATH_MSG_INFO("Initializing " << name() << "...");
67
68 if (const auto nplets_prop_count = m_evtNpletsProp.size();
69 nplets_prop_count > 0) {
70 // they should be Nplets...
71 if (nplets_prop_count % prop_per_nplet != 0) {
72 ATH_MSG_ERROR("invalid list of n-plets (not divisible by "
73 << prop_per_nplet << ")" << endmsg << "check your joboptions !");
74 return StatusCode::FAILURE;
75 }
76
77 m_evtNplets.reserve(nplets_prop_count / prop_per_nplet);
78 for (std::size_t i = 0; i < nplets_prop_count; i += prop_per_nplet) {
79 m_evtNplets.push_back({
80 // clang-format off
81 .runnbr = static_cast<number_type>( m_evtNpletsProp[i + 0]),
82 .evtnbr = static_cast<event_number_t>(m_evtNpletsProp[i + 1]),
83 .timestamp = static_cast<number_type>( m_evtNpletsProp[i + 2]),
84 .lbknbr = static_cast<number_type>( m_evtNpletsProp[i + 3]),
85 .nevts = static_cast<event_number_t>(m_evtNpletsProp[i + 4]),
86 .flags = static_cast<int>( m_evtNpletsProp[i + 5])
87 // clang-format on
88 });
89 }
90 }
91
92 // initialize running total of nevts
93 m_numEvtTotals.clear();
94 event_number_t sum = 0;
95 for (const ItemModifier& elem : m_evtNplets) {
96 sum += elem.nevts;
97 m_numEvtTotals.push_back(sum);
98 }
99
100 if (msgLvl(MSG::DEBUG)) {
101 msg(MSG::DEBUG) << "store being modified: [" << m_evtStoreName << "]"
102 << endmsg << "evtid-modifiers: [ ";
103 for (const ItemModifier& elem : m_evtNplets) {
104 msg(MSG::DEBUG) << "[" << elem.runnbr << ", " << elem.evtnbr << ", "
105 << elem.timestamp << ", " << elem.lbknbr << ", "
106 << elem.nevts << ", flags=0x" << std::hex << elem.flags
107 << std::dec << "], ";
108 }
109 msg(MSG::DEBUG) << "]" << endmsg;
110 }
111
112 return StatusCode::SUCCESS;
113}
114
116// Const methods:
118
121std::vector<number_type> EvtIdModifierSvc::run_number_list() const {
122 std::set<number_type> runs;
123
124 for (const ItemModifier& elem : m_evtNplets) {
125 if (elem.flags & ModFlag::RUNNBR) {
126 runs.insert(elem.runnbr);
127 }
128 }
129 return std::vector(runs.begin(), runs.end());
130}
131
133// Non-const methods:
135
139 bool consume_stream) {
140 // Left in to match old observable behaviour:
141 // only when consuming stream is required do we check for a matching
142 // current StoreGate name (ie: typically the case of being called from a T/P
143 // cnv)
144 if (consume_stream) {
146 if (!active) {
147 ATH_MSG_INFO("could not retrieve the active evtstore - bailing out");
148 return;
149 }
150
151 const std::string& evtStoreName = active->name();
152 ATH_MSG_DEBUG("active store: [" << evtStoreName << "]");
153 if (evtStoreName != m_evtStoreName) {
154 return;
155 }
156 }
157
158 ATH_MSG_DEBUG("evtid before massaging: " << "(" << evt_id.run_number() << ", "
159 << evt_id.event_number() << ", "
160 << evt_id.time_stamp() << ", "
161 << evt_id.lumi_block() << ")");
162
163 // event skipping
164 std::int64_t idx =
165 std::int64_t(evt_index) + m_skippedEvents - std::int64_t(m_firstEvtIdx);
166 std::int64_t idx_looped = idx % m_numEvtTotals.back();
167 ATH_MSG_DEBUG("Got event idx " << evt_index << " --(account for skipping)--> "
168 << idx << " --(modulo #modifiers)--> "
169 << idx_looped);
170 if (idx < 0) {
171 ATH_MSG_DEBUG("skip event");
172 return;
173 }
174
175 // Account for events skipped in
176 std::size_t mod_idx = std::upper_bound(m_numEvtTotals.cbegin(),
177 m_numEvtTotals.cend(), idx_looped) -
178 m_numEvtTotals.cbegin();
179 ItemModifier current = m_evtNplets[mod_idx];
180 ATH_MSG_DEBUG("Unique modifier index " << mod_idx
181 << " (LB: " << current.lbknbr << ")");
182 if (mod_idx >= m_numEvtTotals.size()) {
183 // Shouldn't happen
184 ATH_MSG_ERROR("Somehow run out of modifiers");
185 return;
186 }
187
188 if (current.flags & ModFlag::RUNNBR) {
189 evt_id.set_run_number(current.runnbr);
190 }
191 if (current.flags & ModFlag::EVTNBR) {
192 evt_id.set_event_number(current.evtnbr);
193 }
194 if (current.flags & ModFlag::TIMESTAMP) {
195 evt_id.set_time_stamp(current.timestamp);
196 }
197 if (current.flags & ModFlag::LBKNBR) {
198 evt_id.set_lumi_block(current.lbknbr);
199 }
200
201 ATH_MSG_DEBUG("evtid after massaging: " << "(" << evt_id.run_number() << ", "
202 << evt_id.event_number() << ", "
203 << evt_id.time_stamp() << ", "
204 << evt_id.lumi_block() << ")");
205}
#define endmsg
#define ATH_MSG_ERROR(x)
#define ATH_MSG_INFO(x)
#define ATH_MSG_DEBUG(x)
This class provides a unique identification for each event, in terms of run/event number and/or a tim...
EventIDBase::event_number_t event_number_t
This class provides a unique identification for each event, in terms of run/event number and/or a tim...
Definition EventID.h:35
event_number_t m_firstEvtIdx
(prop) first event number at which we begin to modify event ids
EvtIdModifierSvc()
Default constructor:
event_number_t m_skippedEvents
(prop) number of events skipped in the event selector
virtual void modify_evtid(EventID &evt_id, event_number_t evt_index, bool consume_stream) override
modify an EventID's lumi block content.
std::vector< uint64_t > m_evtNpletsProp
(prop) list of n-plets (run-nbr, evt-nbr, time-stamp, lbk-nbr, nbr-of-events-per-lbk,...
std::vector< event_number_t > m_numEvtTotals
Running total of numEvts before each modifier.
virtual StatusCode initialize() override
Gaudi Service Implementation.
std::vector< ItemModifier > m_evtNplets
db of list of ItemModifiers: (run-nbr, evt-nbr, time-stamp, lbk-nbr, nbr-of-events-per-lbk,...
std::string m_evtStoreName
(prop) Name of the event store whose EventIDs will be modified.
virtual std::vector< number_type > run_number_list() const override
return the (sorted) list of run-numbers which will be modified.
EventIDBase::number_type number_type
The Athena Transient Store API.
static StoreGateSvc * currentStoreGate()
get current StoreGate
unsigned int number_type
MsgStream & msg
Definition testRead.cxx:32