Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2021-05-17 03:00:11

0001 #include "DataFormats/Provenance/interface/ProductProvenanceLookup.h"
0002 #include "DataFormats/Provenance/interface/ProductRegistry.h"
0003 #include "FWCore/Utilities/interface/EDMException.h"
0004 
0005 #include <algorithm>
0006 
0007 /*
0008  ProductProvenanceLookup
0009 */
0010 
0011 namespace edm {
0012   ProductProvenanceLookup::ProductProvenanceLookup()
0013       : entryInfoSet_(), readEntryInfoSet_(), parentProcessRetriever_(nullptr) {}
0014 
0015   ProductProvenanceLookup::ProductProvenanceLookup(edm::ProductRegistry const& iReg)
0016       : entryInfoSet_(), readEntryInfoSet_(), parentProcessRetriever_(nullptr) {
0017     setupEntryInfoSet(iReg);
0018   }
0019 
0020   ProductProvenanceLookup::~ProductProvenanceLookup() { delete readEntryInfoSet_.load(); }
0021 
0022   void ProductProvenanceLookup::setupEntryInfoSet(edm::ProductRegistry const& iReg) {
0023     std::set<BranchID> ids;
0024     for (auto const& p : iReg.productList()) {
0025       if (p.second.branchType() == edm::InEvent) {
0026         if (p.second.produced() or p.second.isProvenanceSetOnRead()) {
0027           ids.insert(p.second.branchID());
0028         }
0029       }
0030     }
0031     entryInfoSet_.reserve(ids.size());
0032     for (auto const& b : ids) {
0033       entryInfoSet_.emplace_back(b);
0034     }
0035   }
0036 
0037   void ProductProvenanceLookup::update(edm::ProductRegistry const& iReg) {
0038     entryInfoSet_.clear();
0039     setupEntryInfoSet(iReg);
0040   }
0041 
0042   void ProductProvenanceLookup::insertIntoSet(ProductProvenance entryInfo) const {
0043     //NOTE:do not read provenance here because we only need the full
0044     // provenance when someone tries to access it not when doing the insert
0045     // doing the delay saves 20% of time when doing an analysis job
0046     //readProvenance();
0047     auto itFound =
0048         std::lower_bound(entryInfoSet_.begin(),
0049                          entryInfoSet_.end(),
0050                          entryInfo.branchID(),
0051                          [](auto const& iEntry, edm::BranchID const& iValue) { return iEntry.branchID() < iValue; });
0052     if UNLIKELY (itFound == entryInfoSet_.end() or itFound->branchID() != entryInfo.branchID()) {
0053       throw edm::Exception(edm::errors::LogicError) << "ProductProvenanceLookup::insertIntoSet passed a BranchID "
0054                                                     << entryInfo.branchID().id() << " that has not been pre-registered";
0055     }
0056     itFound->threadsafe_set(entryInfo.moveParentageID());
0057   }
0058 
0059   ProductProvenance const* ProductProvenanceLookup::branchIDToProvenance(BranchID const& bid) const {
0060     auto itFound = std::lower_bound(
0061         entryInfoSet_.begin(), entryInfoSet_.end(), bid, [](auto const& iEntry, edm::BranchID const& iValue) {
0062           return iEntry.branchID() < iValue;
0063         });
0064     if (itFound != entryInfoSet_.end() and itFound->branchID() == bid) {
0065       if (auto p = itFound->productProvenance()) {
0066         return p;
0067       }
0068     }
0069     if (parentProcessRetriever_) {
0070       return parentProcessRetriever_->branchIDToProvenance(bid);
0071     }
0072     //check in source
0073     if (nullptr == readEntryInfoSet_.load()) {
0074       auto readProv = readProvenance();
0075       std::set<ProductProvenance> const* expected = nullptr;
0076       if (readEntryInfoSet_.compare_exchange_strong(expected, readProv.get())) {
0077         readProv.release();
0078       }
0079     }
0080     auto ptr = readEntryInfoSet_.load();
0081     if (ptr) {
0082       ProductProvenance ei(bid);
0083       auto itRead = ptr->find(ei);
0084       if (itRead != ptr->end()) {
0085         return &*itRead;
0086       }
0087     }
0088     auto nr = nextRetriever();
0089     if (nr) {
0090       return nr->branchIDToProvenance(bid);
0091     }
0092     return nullptr;
0093   }
0094 
0095   ProductProvenance const* ProductProvenanceLookup::branchIDToProvenanceForProducedOnly(BranchID const& bid) const {
0096     auto itFound = std::lower_bound(
0097         entryInfoSet_.begin(), entryInfoSet_.end(), bid, [](auto const& iEntry, edm::BranchID const& iValue) {
0098           return iEntry.branchID() < iValue;
0099         });
0100     if (itFound != entryInfoSet_.end() and itFound->branchID() == bid) {
0101       if (auto p = itFound->productProvenance()) {
0102         return p;
0103       }
0104     }
0105     if (parentProcessRetriever_) {
0106       return parentProcessRetriever_->branchIDToProvenanceForProducedOnly(bid);
0107     }
0108     auto nr = nextRetriever();
0109     if (nr) {
0110       return nr->branchIDToProvenanceForProducedOnly(bid);
0111     }
0112     return nullptr;
0113   }
0114 
0115 }  // namespace edm