LArSoft  v09_90_00
Liquid Argon Software toolkit - https://larsoft.org/
art::Group Class Referencefinal

#include "Group.h"

Inheritance diagram for art::Group:
art::EDProductGetter

Public Types

enum  grouptype { grouptype::normal = 0, grouptype::assns = 1, grouptype::assnsWithData = 2 }
 

Public Member Functions

 ~Group ()
 
 Group (DelayedReader *, BranchDescription const &, std::unique_ptr< RangeSet > &&, grouptype const gt, std::unique_ptr< EDProduct > &&edp=nullptr)
 
EDProduct const * getIt_ () const override
 
EDProduct const * anyProduct () const
 
EDProduct const * uniqueProduct () const
 
EDProduct const * uniqueProduct (TypeID const &) const
 
bool resolveProductIfAvailable (TypeID wanted_wrapper=TypeID{}) const
 
bool tryToResolveProduct (TypeID const &)
 
void removeCachedProduct ()
 
BranchDescription const & productDescription () const noexcept
 
ProductID productID () const
 
RangeSet const & rangeOfValidity () const
 
bool productAvailable () const
 
cet::exempt_ptr< ProductProvenance const > productProvenance () const
 
void setProductProvenance (std::unique_ptr< ProductProvenance const > &&)
 
void setProductAndProvenance (std::unique_ptr< ProductProvenance const > &&, std::unique_ptr< EDProduct > &&, std::unique_ptr< RangeSet > &&)
 
EDProduct const * getIt () const
 

Private Attributes

BranchDescription const & branchDescription_
 
cet::exempt_ptr< DelayedReader const > const delayedReader_
 
std::recursive_mutex mutex_ {}
 
std::atomic< ProductProvenance const * > productProvenance_ {nullptr}
 
std::atomic< EDProduct * > product_
 
std::atomic< RangeSet * > rangeSet_
 
grouptype const grpType_
 
std::atomic< EDProduct * > partnerProduct_ {nullptr}
 
std::atomic< EDProduct * > baseProduct_ {nullptr}
 
std::atomic< EDProduct * > partnerBaseProduct_ {nullptr}
 

Detailed Description

Definition at line 30 of file Group.h.

Member Enumeration Documentation

enum art::Group::grouptype
strong
Enumerator
normal 
assns 
assnsWithData 

Definition at line 34 of file Group.h.

34 { normal = 0, assns = 1, assnsWithData = 2 };

Constructor & Destructor Documentation

art::Group::~Group ( )

Definition at line 20 of file Group.cc.

21  {
22  delete productProvenance_.load();
23  delete product_.load();
24  delete rangeSet_.load();
25  delete partnerProduct_.load();
26  delete baseProduct_.load();
27  delete partnerBaseProduct_.load();
28  }
std::atomic< ProductProvenance const * > productProvenance_
Definition: Group.h:91
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::atomic< EDProduct * > baseProduct_
Definition: Group.h:116
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::atomic< EDProduct * > partnerProduct_
Definition: Group.h:109
std::atomic< EDProduct * > partnerBaseProduct_
Definition: Group.h:120
art::Group::Group ( DelayedReader reader,
BranchDescription const &  bd,
std::unique_ptr< RangeSet > &&  rs,
grouptype const  gt,
std::unique_ptr< EDProduct > &&  edp = nullptr 
)

Definition at line 30 of file Group.cc.

References delayedReader_, grpType_, product_, and rangeSet_.

35  : branchDescription_{bd}
36  , delayedReader_{reader}
37  , product_{edp.release()}
38  , rangeSet_{rs.release()}
39  , grpType_{gt}
40  {}
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::atomic< EDProduct * > product_
Definition: Group.h:96
cet::exempt_ptr< DelayedReader const > const delayedReader_
Definition: Group.h:78
BranchDescription const & branchDescription_
Definition: Group.h:74
grouptype const grpType_
Definition: Group.h:102

Member Function Documentation

EDProduct const * art::Group::anyProduct ( ) const

Definition at line 54 of file Group.cc.

References assns, baseProduct_, grpType_, mutex_, normal, partnerBaseProduct_, partnerProduct_, and product_.

Referenced by art::detail::PrincipalProcessor< DETAIL >::operator()().

55  {
56  std::lock_guard sentry{mutex_};
57  if (grpType_ == grouptype::normal) {
58  return product_.load();
59  }
60  EDProduct* result = product_.load();
61  if (result == nullptr) {
62  result = partnerProduct_.load();
63  }
64  if (grpType_ == grouptype::assns) {
65  return result;
66  }
67  if (result != nullptr) {
68  return result;
69  }
70  result = baseProduct_.load();
71  if (result == nullptr) {
72  result = partnerBaseProduct_.load();
73  }
74  return result;
75  }
std::atomic< EDProduct * > baseProduct_
Definition: Group.h:116
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
std::atomic< EDProduct * > partnerProduct_
Definition: Group.h:109
std::atomic< EDProduct * > partnerBaseProduct_
Definition: Group.h:120
grouptype const grpType_
Definition: Group.h:102
EDProduct const * art::EDProductGetter::getIt ( ) const
inherited

Definition at line 10 of file EDProductGetter.cc.

References art::EDProductGetter::getIt_().

Referenced by art::RefCore::isAvailable(), and art::ProductPtr< T >::product_().

11  {
12  return getIt_();
13  }
virtual EDProduct const * getIt_() const
EDProduct const * art::Group::getIt_ ( ) const
overridevirtual

Reimplemented from art::EDProductGetter.

Definition at line 43 of file Group.cc.

References grpType_, mutex_, normal, product_, resolveProductIfAvailable(), and uniqueProduct().

44  {
45  std::lock_guard sentry{mutex_};
46  if (grpType_ == grouptype::normal) {
48  return product_.load();
49  }
50  return uniqueProduct();
51  }
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
bool resolveProductIfAvailable(TypeID wanted_wrapper=TypeID{}) const
Definition: Group.cc:286
grouptype const grpType_
Definition: Group.h:102
EDProduct const * uniqueProduct() const
Definition: Group.cc:78
bool art::Group::productAvailable ( ) const

Definition at line 206 of file Group.cc.

References branchDescription_, art::BranchDescription::branchType(), delayedReader_, art::BranchDescription::dropped(), art::productstatus::dummyToPreventDoubleCount(), art::InRun, art::InSubRun, art::errors::LogicError, mutex_, art::productstatus::neverCreated(), art::productstatus::present(), art::BranchDescription::present(), art::BranchDescription::produced(), product_, art::BranchDescription::productID(), productProvenance_, and art::productstatus::uninitialized().

Referenced by resolveProductIfAvailable(), and tryToResolveProduct().

207  {
208  if (branchDescription_.dropped()) {
209  // Not a product we are producing this time around, and it is not
210  // present in any of the input files we have opened so far.
211  return false;
212  }
214  std::lock_guard sentry{mutex_};
215  bool availableAfterCombine{false};
218  availableAfterCombine =
219  delayedReader_->isAvailableAfterCombine(branchDescription_.productID());
220  }
221  auto status = productstatus::uninitialized();
222  if (productProvenance_.load() == nullptr) {
223  // No provenance, must be a produced product which has not been
224  // put yet, or a non-produced product that is available after
225  // combine (agggregation) and not yet read, or a non-produced
226  // product in a secondary file that has not yet been opened.
227  if (!branchDescription_.produced()) {
228  if (availableAfterCombine) {
229  // No provenance, not produced, but we can get it from the
230  // input, we just have not done so yet. Claim the product is
231  // available.
232  return true;
233  }
234  // Not produced, not availableAfterCombine, must be in a
235  // secondary file that has not yet been opened. We report it as
236  // not available so that the Principal getBy* routines will try
237  // the next secondary file.
238  return false;
239  }
240  if (product_.load()) {
241  throw Exception(errors::LogicError, "Group::status():")
242  << "We have a produced product, the product has been put(), but "
243  "there is no provenance!\n";
244  }
245  // We have a product product which has not been put(), and has no
246  // provenance (as it should be).
247  status = productstatus::neverCreated();
248  } else {
249  // Not a produced product, and not yet delay read, use the status
250  // from the on-file provenance.
251  status = productProvenance_.load()->productStatus();
252  }
255  if (!availableAfterCombine) {
256  // We know this is a produced run or subrun product which is not
257  // present in any fragments.
258  return status == productstatus::present();
259  }
260  }
261  // We now know we are either an event or results product, or we are
262  // a run or subrun product that can become valid through product
263  // combination (aggregation).
265  // We now know that we are a run or subrun product that can become
266  // valid through product combination (aggregation). Special case
267  // this and report the product as available even though the the
268  // provenance product status is a special flag that is not the
269  // present status.
270  // This is here to allow fetching of a product specially marked by
271  // RootOutputFile as a dummy with an invalid range set created to
272  // prevent double-counting when combining run/subrun products. We
273  // allow the fetch to happen because the call to
274  // isPossiblyAvailable above determined that the fetch will result
275  // in a valid and present product, even though this particular
276  // dummy one is not.
277  return true;
278  }
279  // Note: Technically this is not necessary since the Wrapper present
280  // flag covers this case, but this way we never do the I/O on
281  // the product if we already have the provenance.
282  return status == productstatus::present();
283  }
bool produced() const noexcept
constexpr ProductStatus dummyToPreventDoubleCount() noexcept
Definition: ProductStatus.h:25
bool present() const noexcept
std::atomic< ProductProvenance const * > productProvenance_
Definition: Group.h:91
BranchType branchType() const noexcept
constexpr ProductStatus uninitialized() noexcept
Definition: ProductStatus.h:36
bool dropped() const noexcept
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
cet::exempt_ptr< DelayedReader const > const delayedReader_
Definition: Group.h:78
cet::coded_exception< errors::ErrorCodes, ExceptionDetail::translate > Exception
Definition: Exception.h:66
constexpr ProductStatus neverCreated() noexcept
Definition: ProductStatus.h:15
BranchDescription const & branchDescription_
Definition: Group.h:74
constexpr ProductStatus present() noexcept
Definition: ProductStatus.h:10
ProductID productID() const noexcept
BranchDescription const & art::Group::productDescription ( ) const
noexcept

Definition at line 126 of file Group.cc.

References branchDescription_.

127  {
128  return branchDescription_;
129  }
BranchDescription const & branchDescription_
Definition: Group.h:74
ProductID art::Group::productID ( ) const

Definition at line 132 of file Group.cc.

References branchDescription_, and art::BranchDescription::productID().

133  {
134  return branchDescription_.productID();
135  }
BranchDescription const & branchDescription_
Definition: Group.h:74
ProductID productID() const noexcept
cet::exempt_ptr< ProductProvenance const > art::Group::productProvenance ( ) const

Definition at line 145 of file Group.cc.

References mutex_, and productProvenance_.

Referenced by art::detail::PrincipalProcessor< DETAIL >::operator()().

146  {
147  std::lock_guard sentry{mutex_};
148  return productProvenance_.load();
149  }
std::atomic< ProductProvenance const * > productProvenance_
Definition: Group.h:91
std::recursive_mutex mutex_
Definition: Group.h:87
RangeSet const & art::Group::rangeOfValidity ( ) const

Definition at line 138 of file Group.cc.

References mutex_, and rangeSet_.

139  {
140  std::lock_guard sentry{mutex_};
141  return *rangeSet_.load();
142  }
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::recursive_mutex mutex_
Definition: Group.h:87
void art::Group::removeCachedProduct ( )

Definition at line 178 of file Group.cc.

References assns, baseProduct_, branchDescription_, grpType_, art::RangeSet::invalid(), art::errors::LogicError, mutex_, normal, partnerBaseProduct_, partnerProduct_, art::BranchDescription::produced(), product_, and rangeSet_.

179  {
180  std::lock_guard sentry{mutex_};
182  throw Exception(errors::LogicError, "Group::removeCachedProduct():")
183  << "Attempt to remove a produced product!\n"
184  << "This routine should only be used to remove large data products "
185  << "read from disk (like raw digits).\n";
186  }
187  delete product_.load();
188  product_ = nullptr;
189  if (grpType_ == grouptype::normal) {
190  return;
191  }
192  delete partnerProduct_.load();
193  partnerProduct_ = nullptr;
194  if (grpType_ == grouptype::assns) {
195  return;
196  }
197  delete baseProduct_.load();
198  baseProduct_ = nullptr;
199  delete partnerBaseProduct_.load();
200  partnerBaseProduct_ = nullptr;
201  delete rangeSet_.load();
202  rangeSet_ = new RangeSet{RangeSet::invalid()};
203  }
bool produced() const noexcept
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::atomic< EDProduct * > baseProduct_
Definition: Group.h:116
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
cet::coded_exception< errors::ErrorCodes, ExceptionDetail::translate > Exception
Definition: Exception.h:66
std::atomic< EDProduct * > partnerProduct_
Definition: Group.h:109
BranchDescription const & branchDescription_
Definition: Group.h:74
static RangeSet invalid()
Definition: RangeSet.cc:45
std::atomic< EDProduct * > partnerBaseProduct_
Definition: Group.h:120
grouptype const grpType_
Definition: Group.h:102
bool art::Group::resolveProductIfAvailable ( TypeID  wanted_wrapper = TypeID{}) const

Definition at line 286 of file Group.cc.

References assns, assnsWithData, baseProduct_, branchDescription_, delayedReader_, grpType_, art::LeftRight, art::LeftRightData, mutex_, normal, partnerBaseProduct_, partnerProduct_, art::BranchDescription::produced(), product_, productAvailable(), art::BranchDescription::productID(), rangeSet_, art::RightLeft, art::RightLeftData, and art::TypeID::typeInfo().

Referenced by getIt_(), art::detail::PrincipalProcessor< DETAIL >::operator()(), and tryToResolveProduct().

288  {
289  std::lock_guard sentry{mutex_};
290  // Now try to get the master product.
291  if (product_.load() == nullptr) {
292  // Not already resolved.
294  // Never produced, hopeless.
295  return false;
296  }
297  if (!productAvailable()) {
298  // Not possible to get it, hopeless.
299  return false;
300  }
301  // Now try to read it.
302  // Note: This may call back to us to update the product
303  // provenance if run or subRun data product merging creates a
304  // new provenance.
305  product_ =
307  ->getProduct(this, branchDescription_.productID(), *rangeSet_.load())
308  .release();
309  if (product_.load() == nullptr) {
310  // We failed to get the master product, hopeless.
311  return false;
312  }
313  }
314 
315  if (!wanted_wrapper_type) {
316  // The type of the product is not known, therefore the on-disk
317  // representation is sufficient.
318  return true;
319  }
320 
321  if (grpType_ == grouptype::normal) {
322  // If we get here, we have successfully read a normal product.
323  return true;
324  }
325 
326  assert(grpType_ != grouptype::normal);
327  auto normal_metatype = (grpType_ == grouptype::assns) ?
330 
331  auto assns_type_ids = product_.load()->getTypeIDs();
332  assert(!assns_type_ids.empty());
333 
334  if (wanted_wrapper_type == assns_type_ids.at(normal_metatype)) {
335  return true;
336  }
337 
338  auto partner_metatype = (grpType_ == grouptype::assns) ?
341  if (wanted_wrapper_type == assns_type_ids.at(partner_metatype)) {
342  if (partnerProduct_.load() != nullptr) {
343  // They wanted the partner product, and we have already made it, done.
344  return true;
345  }
346  // They want the partner product, ask the wrapper to make it for us,
347  // who ends up asking the assns to do it.
349  product_.load()->makePartner(wanted_wrapper_type.typeInfo()).release();
350  return partnerProduct_.load() != nullptr;
351  }
352 
354 
355  if (wanted_wrapper_type == assns_type_ids.at(product_metatype::LeftRight)) {
356  if (baseProduct_.load() != nullptr) {
357  // They wanted the base product, and we have already made it, done.
358  return true;
359  }
360  // They want the base, ask the wrapper to make it for us,
361  // who ends up asking the assns to do it.
362  baseProduct_ =
363  product_.load()->makePartner(wanted_wrapper_type.typeInfo()).release();
364  return baseProduct_.load() != nullptr;
365  }
366  if (partnerBaseProduct_.load() != nullptr) {
367  // They wanted the partner base product, and we have already made it,
368  // done.
369  return true;
370  }
372  product_.load()->makePartner(wanted_wrapper_type.typeInfo()).release();
373  return partnerBaseProduct_.load() != nullptr;
374  }
bool produced() const noexcept
bool productAvailable() const
Definition: Group.cc:206
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::atomic< EDProduct * > baseProduct_
Definition: Group.h:116
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
cet::exempt_ptr< DelayedReader const > const delayedReader_
Definition: Group.h:78
std::atomic< EDProduct * > partnerProduct_
Definition: Group.h:109
BranchDescription const & branchDescription_
Definition: Group.h:74
std::atomic< EDProduct * > partnerBaseProduct_
Definition: Group.h:120
grouptype const grpType_
Definition: Group.h:102
ProductID productID() const noexcept
void art::Group::setProductAndProvenance ( std::unique_ptr< ProductProvenance const > &&  pp,
std::unique_ptr< EDProduct > &&  edp,
std::unique_ptr< RangeSet > &&  rs 
)

Definition at line 164 of file Group.cc.

References mutex_, product_, productProvenance_, and rangeSet_.

167  {
168  std::lock_guard sentry{mutex_};
169  delete productProvenance_.load();
170  productProvenance_ = pp.release();
171  delete product_.load();
172  product_ = edp.release();
173  delete rangeSet_.load();
174  rangeSet_ = rs.release();
175  }
std::atomic< ProductProvenance const * > productProvenance_
Definition: Group.h:91
std::atomic< RangeSet * > rangeSet_
Definition: Group.h:100
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
void art::Group::setProductProvenance ( std::unique_ptr< ProductProvenance const > &&  pp)

Definition at line 155 of file Group.cc.

References mutex_, and productProvenance_.

156  {
157  std::lock_guard sentry{mutex_};
158  delete productProvenance_.load();
159  productProvenance_ = pp.release();
160  }
std::atomic< ProductProvenance const * > productProvenance_
Definition: Group.h:91
std::recursive_mutex mutex_
Definition: Group.h:87
bool art::Group::tryToResolveProduct ( TypeID const &  wanted_wrapper)

Definition at line 377 of file Group.cc.

References mutex_, productAvailable(), and resolveProductIfAvailable().

378  {
379  std::lock_guard sentry{mutex_};
380  resolveProductIfAvailable(wanted_wrapper);
381 
382  // If the product is a dummy filler, it will now be marked unavailable.
383  return productAvailable();
384  }
bool productAvailable() const
Definition: Group.cc:206
std::recursive_mutex mutex_
Definition: Group.h:87
bool resolveProductIfAvailable(TypeID wanted_wrapper=TypeID{}) const
Definition: Group.cc:286
EDProduct const * art::Group::uniqueProduct ( ) const

Definition at line 78 of file Group.cc.

References grpType_, art::errors::LogicError, mutex_, normal, and product_.

Referenced by getIt_().

79  {
80  std::lock_guard sentry{mutex_};
81  if (grpType_ == grouptype::normal) {
82  return product_.load();
83  }
84  throw Exception(errors::LogicError, "AmbiguousProduct")
85  << cet::demangle_symbol(typeid(*this).name())
86  << " was asked for a held product (uniqueProduct()) "
87  << "without specifying which one was wanted.\n";
88  }
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
cet::coded_exception< errors::ErrorCodes, ExceptionDetail::translate > Exception
Definition: Exception.h:66
grouptype const grpType_
Definition: Group.h:102
EDProduct const * art::Group::uniqueProduct ( TypeID const &  wanted_wrapper_type) const

Definition at line 91 of file Group.cc.

References assns, baseProduct_, grpType_, art::LeftRight, mutex_, normal, partnerBaseProduct_, partnerProduct_, product_, art::RightLeft, and art::RightLeftData.

92  {
93  std::lock_guard sentry{mutex_};
94  if (product_.load() == nullptr) {
95  return nullptr;
96  }
97  if (grpType_ == grouptype::normal) {
98  return product_.load();
99  }
100 
101  auto assns_type_ids = product_.load()->getTypeIDs();
102  if (grpType_ == grouptype::assns) {
103  assert(assns_type_ids.size() == 2ull);
104  if (wanted_wrapper_type ==
105  assns_type_ids.at(product_metatype::RightLeft)) {
106  return partnerProduct_.load();
107  }
108  return product_.load();
109  }
110 
111  assert(assns_type_ids.size() == 4ull);
112  if (wanted_wrapper_type == assns_type_ids.at(product_metatype::RightLeft)) {
113  return partnerBaseProduct_.load();
114  }
115  if (wanted_wrapper_type == assns_type_ids.at(product_metatype::LeftRight)) {
116  return baseProduct_.load();
117  }
118  if (wanted_wrapper_type ==
119  assns_type_ids.at(product_metatype::RightLeftData)) {
120  return partnerProduct_.load();
121  }
122  return product_.load();
123  }
std::atomic< EDProduct * > baseProduct_
Definition: Group.h:116
std::atomic< EDProduct * > product_
Definition: Group.h:96
std::recursive_mutex mutex_
Definition: Group.h:87
std::atomic< EDProduct * > partnerProduct_
Definition: Group.h:109
std::atomic< EDProduct * > partnerBaseProduct_
Definition: Group.h:120
grouptype const grpType_
Definition: Group.h:102

Member Data Documentation

std::atomic<EDProduct*> art::Group::baseProduct_ {nullptr}
mutableprivate

Definition at line 116 of file Group.h.

Referenced by anyProduct(), removeCachedProduct(), resolveProductIfAvailable(), and uniqueProduct().

BranchDescription const& art::Group::branchDescription_
private
cet::exempt_ptr<DelayedReader const> const art::Group::delayedReader_
private

Definition at line 78 of file Group.h.

Referenced by Group(), productAvailable(), and resolveProductIfAvailable().

grouptype const art::Group::grpType_
private
std::atomic<EDProduct*> art::Group::partnerBaseProduct_ {nullptr}
mutableprivate

Definition at line 120 of file Group.h.

Referenced by anyProduct(), removeCachedProduct(), resolveProductIfAvailable(), and uniqueProduct().

std::atomic<EDProduct*> art::Group::partnerProduct_ {nullptr}
mutableprivate

Definition at line 109 of file Group.h.

Referenced by anyProduct(), removeCachedProduct(), resolveProductIfAvailable(), and uniqueProduct().

std::atomic<EDProduct*> art::Group::product_
mutableprivate
std::atomic<ProductProvenance const*> art::Group::productProvenance_ {nullptr}
private
std::atomic<RangeSet*> art::Group::rangeSet_
mutableprivate

The documentation for this class was generated from the following files: