6 #include <GaudiKernel/DataIncident.h>   
    7 #include <GaudiKernel/IEvtSelector.h> 
    8 #include <GaudiKernel/IIncidentSvc.h> 
   10 #include <boost/core/typeinfo.hpp> 
   11 #include <range/v3/to_container.hpp> 
   12 #include <range/v3/view.hpp> 
   19 using namespace std::literals;
 
   20 namespace rv = ranges::views;
 
   23 template <
typename propType, 
typename T>
 
   24 const Gaudi::Property<propType>&
 
   25 getProp(SmartIF<T>& iface, 
const std::string& 
name)
 
   27   auto prop_iface = iface.template as<IProperty>();
 
   28   const auto& prop = prop_iface->getProperty(
name);
 
   30     const auto& conv_prop =
 
   31         dynamic_cast<const Gaudi::Property<propType>&
>(prop);
 
   33   } 
catch (
const std::bad_cast&) {
 
   34     std::string if_name = 
"UNKNOWN";
 
   36       if_name = iface.template as<INamedInterface>()->name();
 
   40         "The {} object's {} property has type {} not Gaudi::Property<{}>",
 
   41         if_name, 
name, boost::core::demangled_name(
typeid(prop)),
 
   42         boost::core::demangled_name(
typeid(propType)));
 
   43     throw std::logic_error(
what);
 
   49                    const std::string& 
val) {
 
   50   auto prop_iface = iface.template as<IProperty>();
 
   51   return prop_iface->setProperty(
name, 
val);
 
   62   SmartIF<IProperty> propMgr(serviceLocator());
 
   63   std::string evt_sel_name{};
 
   64   ATH_CHECK(propMgr->getProperty(
"EvtSel", evt_sel_name));
 
   65   if (evt_sel_name.empty()) {
 
   70     return StatusCode::SUCCESS;
 
   72   auto sg = serviceLocator()->service<
StoreGateSvc>(
"StoreGateSvc/StoreGateSvc",
 
   74   auto evtSel = serviceLocator()->service<IEvtSelector>(std::move(evt_sel_name), 
false);
 
   75   if (!sg.isValid() || !evtSel.isValid()) {
 
   77     return StatusCode::FAILURE;
 
   81       "EvtIdModifierSvc/EvtIdModifierSvc", 
false);
 
   83   std::vector<EvtId> modifier_evts{};
 
   84   if (modSvc.isValid()) {
 
   87       evts_skipped_before_mod =
 
   88           getProp<std::uint64_t&>(modSvc, 
"SkipEvents").value();
 
   90                                << 
" events before modifying");
 
   91       std::vector<std::uint64_t> 
lst = 
 
   92         getProp<std::vector<std::uint64_t>&>(modSvc, 
"Modifiers").
value();
 
   94                    << 
lst.size() / 6 << 
" entries.");
 
   95       std::string config_str{};
 
   96       auto config_str_iter = std::back_inserter(config_str);
 
   99           rv::for_each([&config_str_iter](
const auto& rec) {
 
  100             const int mod_bitset = rec[5];
 
  101             const bool mod_run_num = mod_bitset & 1;
 
  102             const bool mod_evt_num = mod_bitset & (1 << 1);
 
  103             const bool mod_lb_num = mod_bitset & (1 << 3);
 
  110             std::format_to(config_str_iter,
 
  111                            "Run: {} [{:c}] LB: {} [{:c}] EVT: {} [{:c}] " 
  113                            runNum, mod_run_num ? 
'Y' : 
'N', lbNum,
 
  114                            mod_lb_num ? 
'Y' : 
'N', evtNum,
 
  115                            mod_evt_num ? 
'Y' : 
'N', numEvts);
 
  116             return ranges::yield_from(
 
  118                                    static_cast<uint32_t>(lbNum), evtNum},
 
  123     } 
catch (
const std::bad_cast&) {
 
  124       ATH_MSG_ERROR(
"Wrong type for property of EvtIdModifierSvc.");
 
  131   ATH_CHECK(setProp(evtSel, 
"SkipEvents", 
"0"));
 
  132   IEvtSelector::Context* ctx = 
nullptr;
 
  137   Service* evtSelSvc = 
dynamic_cast<Service*
>(evtSel.get());
 
  140     return StatusCode::FAILURE;
 
  143   while (evtSel->next(*ctx).isSuccess()) {
 
  146     IOpaqueAddress* addr = 
nullptr;
 
  147     ATH_CHECK(evtSel->createAddress(*ctx, addr));
 
  154     std::vector<std::string> attr_lists;
 
  156     const auto* attr_list_p =
 
  158     if (attr_list_p != 
nullptr && attr_list_p->size() > 6) {
 
  161         const auto runNum = attr_list[
"RunNumber"].data<
unsigned>();
 
  162         const auto evtNum = attr_list[
"EventNumber"].data<
unsigned long long>();
 
  163         const auto lbNum = attr_list[
"LumiBlockN"].data<
unsigned>();
 
  164         evt_id = EvtId{
runNum, lbNum, evtNum};
 
  169     if (
idx >= evts_skipped_before_mod && !modifier_evts.empty()) {
 
  170       const std::size_t mod_idx =
 
  171           (
idx - evts_skipped_before_mod) % modifier_evts.size();
 
  172       evt_id.runNum = modifier_evts[mod_idx].runNum != 0U
 
  173                           ? modifier_evts[mod_idx].runNum
 
  175       evt_id.lbNum = modifier_evts[mod_idx].lbNum != 0U
 
  176                          ? modifier_evts[mod_idx].lbNum
 
  178       evt_id.evtNum = modifier_evts[mod_idx].evtNum != 0U
 
  179                           ? modifier_evts[mod_idx].evtNum
 
  189                                              << 
" and rewinding");
 
  198   incident_svc->addListener(
this, 
"BeginRun");
 
  199   incident_svc->addListener(
this, 
"SkipEvents");
 
  200   return StatusCode::SUCCESS;
 
  212   return StatusCode::SUCCESS;
 
  226   return StatusCode::SUCCESS;
 
  230   if (inc.type() != 
"BeginRun"s && inc.type() != 
"SkipEvents"s) {
 
  233   ATH_MSG_DEBUG(
"Received incident of type " << inc.type() << 
" from " 
  235   if (inc.type() == 
"SkipEvents"s) {
 
  238         dynamic_cast<const ContextIncident<std::tuple<int, int>
>&>(inc);
 
  240     auto end = 
m_events.cbegin() + std::get<1>(cInc.tag()) +
 
  243       if (!std::invoke(
fn, 
begin, 
end).isSuccess()) {
 
  244         throw std::runtime_error(
 
  245             "A skipEvent callback returned a failure error code!");