DataViewImpl.cc
Go to the documentation of this file.
2 // vim: set sw=2 expandtab :
3 
12 #include "cetlib/HorizontalRule.h"
13 #include "cetlib/exempt_ptr.h"
14 #include "cetlib_except/exception.h"
16 #include "fhiclcpp/fwd.h"
17 
18 #include <algorithm>
19 #include <map>
20 #include <memory>
21 #include <ostream>
22 #include <set>
23 #include <string>
24 #include <utility>
25 #include <vector>
26 
27 using namespace cet;
28 using namespace std;
29 
30 namespace art {
31 
32  class EDProductGetter;
33 
34  DataViewImpl::~DataViewImpl() = default;
35 
36  DataViewImpl::DataViewImpl(BranchType const bt,
37  Principal const& principal,
38  ModuleContext const& mc,
39  bool const recordParents,
40  RangeSet const& rs /* = RangeSet::invalid() */)
41  : branchType_{bt}
42  , principal_{principal}
43  , mc_{mc}
44  , md_{mc.moduleDescription()}
45  , recordParents_{recordParents}
46  , rangeSet_{rs}
47  {}
48 
49  RunID
51  {
52  std::lock_guard lock{mutex_};
53  return principal_.runID();
54  }
55 
56  SubRunID
58  {
59  std::lock_guard lock{mutex_};
60  return principal_.subRunID();
61  }
62 
63  EventID
65  {
66  std::lock_guard lock{mutex_};
67  return principal_.eventID();
68  }
69 
72  {
73  std::lock_guard lock{mutex_};
74  return principal_.run();
75  }
76 
79  {
80  std::lock_guard lock{mutex_};
81  return principal_.subRun();
82  }
83 
86  {
87  std::lock_guard lock{mutex_};
88  return principal_.event();
89  }
90 
91  Timestamp const&
93  {
94  std::lock_guard lock{mutex_};
95  return principal_.beginTime();
96  }
97 
98  Timestamp const&
100  {
101  std::lock_guard lock{mutex_};
102  return principal_.endTime();
103  }
104 
105  Timestamp
107  {
108  std::lock_guard lock{mutex_};
109  return principal_.time();
110  }
111 
112  bool
114  {
115  std::lock_guard lock{mutex_};
116  return principal_.isReal();
117  }
118 
121  {
122  std::lock_guard lock{mutex_};
123  return principal_.ExperimentType();
124  }
125 
126  History const&
128  {
129  std::lock_guard lock{mutex_};
130  return principal_.history();
131  }
132 
133  ProcessHistoryID const&
135  {
136  std::lock_guard lock{mutex_};
138  }
139 
140  ProcessHistory const&
142  {
143  std::lock_guard lock{mutex_};
144  return principal_.processHistory();
145  }
146 
147  EDProductGetter const*
149  {
150  std::lock_guard lock{mutex_};
151  return principal_.productGetter(pid);
152  }
153 
154  bool
155  DataViewImpl::getProcessParameterSet(string const& processName,
156  fhicl::ParameterSet& ps) const
157  {
158  std::lock_guard lock{mutex_};
159  if (branchType_ != InEvent) {
160  return false;
161  }
162  ProcessHistory ph;
164  ph)) {
166  << "ProcessHistoryID " << principal_.history().processHistoryID()
167  << " is not found in the ProcessHistoryRegistry.\n"
168  << "This file is malformed.\n";
169  }
170  auto const config = ph.getConfigurationForProcess(processName);
171  if (config) {
172  fhicl::ParameterSetRegistry::get(config->parameterSetID(), ps);
173  }
174  return config.has_value();
175  }
176 
179  {
180  return principal_.getProductDescription(pid);
181  }
182 
183  void
185  Principal& principal,
186  bool const checkProducts,
187  map<TypeLabel, BranchDescription> const* expectedProducts)
188  {
189  std::lock_guard lock{mutex_};
190  if (checkProducts) {
191  vector<string> missing;
192  for (auto const& typeLabel_and_bd : *expectedProducts) {
193  if (putProducts_.find(typeLabel_and_bd.first) != putProducts_.cend()) {
194  continue;
195  }
196  ostringstream desc;
197  desc << typeLabel_and_bd.second;
198  missing.emplace_back(desc.str());
199  }
200  if (!missing.empty()) {
201  ostringstream errmsg;
202  HorizontalRule rule{25};
203  errmsg << "The following products have been declared with 'produces',\n"
204  << "but they have not been placed onto the event:\n"
205  << rule('=') << '\n';
206  for (auto const& desc : missing) {
207  errmsg << desc << rule('=') << '\n';
208  }
209  throw Exception{errors::LogicError, "DataViewImpl::checkPutProducts"}
210  << errmsg.str();
211  }
212  }
213  for (auto& type_label_and_pmvalue : putProducts_) {
214  auto& pmvalue = type_label_and_pmvalue.second;
215  unique_ptr<ProductProvenance const> pp;
216  if (branchType_ == InEvent) {
217  vector<ProductID> gotPIDs;
218  if (!retrievedProducts_.empty()) {
219  gotPIDs.reserve(retrievedProducts_.size());
220  gotPIDs.assign(retrievedProducts_.begin(), retrievedProducts_.end());
221  }
222  pp = make_unique<ProductProvenance const>(
223  pmvalue.bd_.productID(), productstatus::present(), gotPIDs);
224  } else {
225  pp = make_unique<ProductProvenance const>(pmvalue.bd_.productID(),
227  }
229  make_unique<RangeSet>(pmvalue.rs_) :
230  make_unique<RangeSet>();
231  principal.put(pmvalue.bd_, move(pp), move(pmvalue.prod_), move(rs));
232  };
233  putProducts_.clear();
234  }
235 
236  void
238  {
239  std::lock_guard lock{mutex_};
240  for (auto& type_label_and_pmvalue : putProducts_) {
241  auto& pmvalue = type_label_and_pmvalue.second;
242  unique_ptr<ProductProvenance const> pp =
243  make_unique<ProductProvenance const>(pmvalue.bd_.productID(),
245  if ((branchType_ == InRun) || (branchType_ == InSubRun)) {
246  principal.put(pmvalue.bd_,
247  move(pp),
248  move(pmvalue.prod_),
249  make_unique<RangeSet>(pmvalue.rs_));
250  } else {
251  principal.put(
252  pmvalue.bd_, move(pp), move(pmvalue.prod_), make_unique<RangeSet>());
253  }
254  };
255  putProducts_.clear();
256  }
257 
258  string const&
259  DataViewImpl::getProcessName_(std::string const& specifiedProcessName) const
260  {
261  return specifiedProcessName == "current_process"s ? md_.processName() :
262  specifiedProcessName;
263  }
264 
265  BranchDescription const&
267  TypeID const& type,
268  string const& instance,
269  bool const alwaysEnableLookupOfProducedProducts /*= false*/) const
270  {
271  std::lock_guard lock{mutex_};
272  auto const& product_name = canonicalProductName(
274  ProductID const pid{product_name};
276  pid, alwaysEnableLookupOfProducedProducts);
277  if (!bd || (bd->producedClassName() != type.className())) {
278  // Either we did not find the product, or the product we
279  // did find does not match (which can happen with Assns
280  // since Assns(A,B) and Assns(B,A) have the same ProductID
281  // but not the same class name.
283  "DataViewImpl::getProductDescription_: error while "
284  "trying to retrieve product description:\n")
285  << "No product is registered for\n"
286  << " process name: '" << md_.processName() << "'\n"
287  << " module label: '" << md_.moduleLabel() << "'\n"
288  << " product class name: '" << type.className() << "'\n"
289  << " product friendly class name: '" << type.friendlyClassName()
290  << "'\n"
291  << " product instance name: '" << instance << "'\n"
292  << " branch type: '" << branchType_ << "'\n";
293  }
294  // The description object is owned by either the source or the
295  // event processor, whose lifetimes exceed that of the
296  // DataViewImpl object. It is therefore safe to dereference.
297  return *bd;
298  }
299 
300  void
302  {
303  if (grp->productDescription().transient()) {
304  // If the product retrieved is transient, don't use its
305  // ProductID; use the ProductID's of its parents.
306  auto const& parents = grp->productProvenance()->parentage().parents();
307  retrievedProducts_.insert(cbegin(parents), cend(parents));
308  } else {
309  retrievedProducts_.insert(grp->productDescription().productID());
310  }
311  }
312 
315  string const& moduleLabel,
316  string const& productInstanceName,
317  ProcessTag const& processTag) const
318  {
319  // Check that the consumesView<ELEMENT, BT>(InputTag),
320  // or the mayConsumeView<ELEMENT, BT>(InputTag)
321  // is actually present.
323  branchType_,
324  md_,
326  typeID,
327  moduleLabel,
328  productInstanceName,
329  processTag});
330  // Fetch the specified data products, which must be containers.
331  auto const groups = principal_.getMatchingSequence(
332  mc_,
333  Selector{ModuleLabelSelector{moduleLabel} &&
334  ProductInstanceNameSelector{productInstanceName} &&
335  ProcessNameSelector{processTag.name()}},
336  processTag);
337  auto qrs = resolve_products(groups, TypeID{});
338  // Remove any containers that do not allow upcasting of their
339  // elements to the desired element type.
340  auto new_end =
341  remove_if(qrs.begin(), qrs.end(), [&typeID](auto const& gqr) {
342  auto const group = gqr.result();
343  assert(group->productDescription().supportsView());
344  return !detail::upcastAllowed(*group->uniqueProduct()->typeInfo(),
345  typeID.typeInfo());
346  });
347  qrs.erase(new_end, qrs.end());
348  // Throw if there is not one and only one container to return.
349  if (qrs.size() != 1) {
351  e << "getView: Found "
352  << (qrs.empty() ? "no products" : "more than one product")
353  << " matching all criteria\n"
354  << "Looking for sequence of type: " << typeID << "\n"
355  << "Looking for module label: " << moduleLabel << "\n"
356  << "Looking for productInstanceName: " << productInstanceName << "\n";
357  if (!processTag.name().empty()) {
358  e << "Looking for processName: " << processTag.name() << "\n";
359  }
360  throw e;
361  }
362  // And return the single result.
363  return qrs[0].result();
364  }
365 } // namespace art
RunNumber_t run() const
Definition: Principal.cc:1070
EventID const & eventID() const
Definition: Principal.cc:1064
Principal const & principal_
Definition: DataViewImpl.h:307
SubRunID subRunID() const
Definition: DataViewImpl.cc:57
EventNumber_t event() const
Definition: DataViewImpl.cc:85
EDProductGetter const * productGetter(ProductID const &pid) const
Definition: Principal.cc:297
RunID const & runID() const
Definition: Principal.cc:1052
decltype(auto) constexpr cend(T &&obj)
ADL-aware version of std::cend.
Definition: StdUtils.h:87
static ConsumesInfo * instance()
Definition: ConsumesInfo.cc:24
std::string friendlyClassName() const
Definition: TypeID.cc:61
std::string const & getProcessName_(std::string const &) const
Timestamp const & time() const
Definition: Principal.cc:1125
std::string string
Definition: nybbler.cc:12
Timestamp const & beginTime() const
Definition: Principal.cc:1097
std::string const & moduleLabel() const
EventAuxiliary::ExperimentType ExperimentType() const
Definition: Principal.cc:896
ProcessHistory const & processHistory() const
static collection_type const & get() noexcept
const std::string instance
Timestamp const & endTime() const
Definition: DataViewImpl.cc:99
STL namespace.
History const & history() const
Definition: Principal.cc:902
EventID eventID() const
Definition: DataViewImpl.cc:64
bool getProcessParameterSet(std::string const &process, fhicl::ParameterSet &) const
BranchType const branchType_
Definition: DataViewImpl.h:304
void movePutProductsToPrincipal(Principal &principal)
EventAuxiliary::ExperimentType experimentType() const
std::string const & processName() const
EventNumber_t event() const
Definition: Principal.cc:1091
bool isRealData() const
RunID runID() const
Definition: DataViewImpl.cc:50
const double e
static collection_type const & get()
Timestamp time() const
bt
Definition: tracks.py:83
History const & history() const
cet::exempt_ptr< BranchDescription const > getProductDescription(ProductID const pid, bool const alwaysEnableLookupOfProducedProducts=false) const
Definition: Principal.cc:994
static Config * config
Definition: config.cpp:1054
def move(depos, offset)
Definition: depos.py:107
EDProductGetter const * productGetter(ProductID const pid) const
std::set< ProductID > retrievedProducts_
Definition: DataViewImpl.h:329
SubRunID subRunID() const
Definition: Principal.cc:1058
void put(BranchDescription const &, std::unique_ptr< ProductProvenance const > &&, std::unique_ptr< EDProduct > &&, std::unique_ptr< RangeSet > &&)
Definition: Principal.cc:930
IDNumber_t< Level::SubRun > SubRunNumber_t
Definition: IDNumber.h:119
ModuleDescription const & md_
Definition: DataViewImpl.h:313
SubRunNumber_t subRun() const
Definition: DataViewImpl.cc:78
std::string className() const
Definition: TypeID.cc:48
cet::exempt_ptr< BranchDescription const > getProductDescription(ProductID) const
RunNumber_t run() const
Definition: DataViewImpl.cc:71
std::string canonicalProductName(std::string const &friendlyClassName, std::string const &moduleLabel, std::string const &productInstanceName, std::string const &processName)
static constexpr double ps
Definition: Units.h:99
std::vector< cet::exempt_ptr< Group > > getMatchingSequence(ModuleContext const &, SelectorBase const &, ProcessTag const &) const
Definition: Principal.cc:696
void validateConsumedProduct(BranchType const, ModuleDescription const &, ProductInfo const &productInfo)
ProcessHistory const & processHistory() const
Definition: Principal.cc:363
cet::coded_exception< errors::ErrorCodes, ExceptionDetail::translate > Exception
Definition: Exception.h:66
std::recursive_mutex mutex_
Definition: DataViewImpl.h:301
std::optional< ProcessConfiguration > getConfigurationForProcess(std::string const &name) const
auto const & name() const
Definition: ProcessTag.h:23
void recordAsParent_(cet::exempt_ptr< Group const > grp) const
std::map< TypeLabel, PMValue > putProducts_
Definition: DataViewImpl.h:333
cet::exempt_ptr< Group const > getContainerForView_(TypeID const &, std::string const &moduleLabel, std::string const &productInstanceName, ProcessTag const &processTag) const
ProcessHistoryID const & processHistoryID() const noexcept
Definition: History.cc:31
bool isReal() const
Definition: Principal.cc:890
BranchDescription const & getProductDescription_(TypeID const &type, std::string const &instance, bool const alwaysEnableLookupOfProducedProducts=false) const
ProcessHistoryID const & processHistoryID() const
IDNumber_t< Level::Event > EventNumber_t
Definition: IDNumber.h:118
BranchType
Definition: BranchType.h:20
decltype(auto) constexpr cbegin(T &&obj)
ADL-aware version of std::cbegin.
Definition: StdUtils.h:82
bool upcastAllowed(std::type_info const &tiFrom, std::type_info const &tiTo)
ModuleContext const & mc_
Definition: DataViewImpl.h:310
constexpr bool range_sets_supported(BranchType const bt)
Timestamp const & endTime() const
Definition: Principal.cc:1106
static QCString * s
Definition: config.cpp:1042
constexpr ProductStatus present() noexcept
Definition: ProductStatus.h:10
Timestamp const & beginTime() const
Definition: DataViewImpl.cc:92
SubRunNumber_t subRun() const
Definition: Principal.cc:1082
std::type_info const & typeInfo() const
Definition: TypeID.cc:36
bool const recordParents_
Definition: DataViewImpl.h:320
IDNumber_t< Level::Run > RunNumber_t
Definition: IDNumber.h:120
std::vector< GroupQueryResult > resolve_products(std::vector< cet::exempt_ptr< art::Group >> const &groups, art::TypeID const &wrapped_type)
Definition: Group.cc:428