From 6cbbf9518d4120f9a36b2e006febcfeee78adb88 Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 10:42:18 -0500 Subject: [PATCH 01/13] Better process order handling --- .../Provenance/interface/ProductRegistry.h | 2 ++ DataFormats/Provenance/src/ProductRegistry.cc | 31 ++++++++++++++++--- .../SignallingProductRegistryFiller.h | 2 ++ .../Framework/test/productregistry.cppunit.cc | 1 + .../plugins/PutOrMergeTestSource.cc | 1 + FWCore/Sources/src/PuttableSourceBase.cc | 1 + FWCore/TestProcessor/src/TestProcessor.cc | 6 ++++ 7 files changed, 40 insertions(+), 4 deletions(-) diff --git a/DataFormats/Provenance/interface/ProductRegistry.h b/DataFormats/Provenance/interface/ProductRegistry.h index baf94c53fa80b..d3605fec10854 100644 --- a/DataFormats/Provenance/interface/ProductRegistry.h +++ b/DataFormats/Provenance/interface/ProductRegistry.h @@ -182,6 +182,7 @@ namespace edm { iter->second.merge(prod.second); } } + mergeProcessOrderFromAddInput(iReg.processOrder()); } private: @@ -206,6 +207,7 @@ namespace edm { void checkForDuplicateProcessName(ProductDescription const& desc, std::string const* processName) const; void updateProcessOrder(std::vector const& processOrder); + void mergeProcessOrderFromAddInput(std::vector const& processOrder); void throwIfNotFrozen() const; void throwIfFrozen() const; diff --git a/DataFormats/Provenance/src/ProductRegistry.cc b/DataFormats/Provenance/src/ProductRegistry.cc index c6e0ea6f737c6..a3f2b576346e8 100644 --- a/DataFormats/Provenance/src/ProductRegistry.cc +++ b/DataFormats/Provenance/src/ProductRegistry.cc @@ -218,6 +218,17 @@ namespace edm { processingOrderMerge(processOrder, transient_.processOrder_); } + void ProductRegistry::mergeProcessOrderFromAddInput(std::vector const& processOrder) { + if (processOrder.empty()) + return; + //see if the input already has the current process + if (not transient_.processOrder_.empty() and (transient_.processOrder_[0] != processOrder[0])) { + transient_.processOrder_.insert(transient_.processOrder_.end(), processOrder.begin(), processOrder.end()); + } else { + updateProcessOrder(processOrder); + } + } + void ProductRegistry::setUnscheduledProducts(std::set const& unscheduledLabels) { throwIfFrozen(); @@ -250,9 +261,20 @@ namespace edm { std::string ProductRegistry::merge(ProductRegistry const& other, std::string const& fileName, ProductDescription::MatchMode branchesMustMatch) { - if (branchesMustMatch == ProductDescription::FromInputToCurrent and transient_.processOrder_.size() == 1) { - transient_.processOrder_.insert( - transient_.processOrder_.end(), other.transient_.processOrder_.begin(), other.transient_.processOrder_.end()); + if (branchesMustMatch == ProductDescription::FromInputToCurrent) { + if (processOrder().size() == 1 and not other.processOrder().empty() and + processOrder()[0] != other.processOrder()[0]) { + assert(transient_.processOrder_.size() == 1); + transient_.processOrder_.insert(transient_.processOrder_.end(), + other.transient_.processOrder_.begin(), + other.transient_.processOrder_.end()); + } else { + //the current process must not change + assert(not processOrder().empty()); + auto current = processOrder()[0]; + processingOrderMerge(other.processOrder(), transient_.processOrder_); + assert(current == processOrder()[0]); + } } else { processingOrderMerge(other.processOrder(), transient_.processOrder_); } @@ -310,6 +332,7 @@ namespace edm { std::vector producedTypes; transient_.branchIDToIndex_.clear(); + assert(productList_.empty() or processOrder().size() > 0); std::array, NumBranchTypes> new_productLookups{ {std::make_shared(), @@ -452,7 +475,7 @@ namespace edm { std::string_view processNameSV(processName ? std::string_view(*processName) : std::string_view()); for (auto& iterProductLookup : new_productLookups) { - iterProductLookup->setFrozen(processNameSV); + iterProductLookup->setFrozen(processOrder()); } for (size_t i = 0; i < new_productLookups.size(); ++i) { transient_.productLookups_[i] = std::move(new_productLookups[i]); diff --git a/FWCore/Framework/interface/SignallingProductRegistryFiller.h b/FWCore/Framework/interface/SignallingProductRegistryFiller.h index 566baa0d6118e..c7623647ea695 100644 --- a/FWCore/Framework/interface/SignallingProductRegistryFiller.h +++ b/FWCore/Framework/interface/SignallingProductRegistryFiller.h @@ -80,6 +80,8 @@ namespace edm { registry_.setProcessOrder(std::vector(1, processOrder)); } + void setProcessOrder(std::vector const& processOrder) { registry_.setProcessOrder(processOrder); } + template void watchProductAdditions(const T& iFunc) { serviceregistry::connect_but_block_self(productAddedSignal_, iFunc); diff --git a/FWCore/Framework/test/productregistry.cppunit.cc b/FWCore/Framework/test/productregistry.cppunit.cc index 5cb82cbe678fa..5c4921af26845 100644 --- a/FWCore/Framework/test/productregistry.cppunit.cc +++ b/FWCore/Framework/test/productregistry.cppunit.cc @@ -238,6 +238,7 @@ void testProductRegistry::testAddAlias() { simpleVecBranch_->unwrappedTypeID(), simpleDerivedVecBranch_->unwrappedTypeID()}; std::set elementTypesConsumed{intBranch_->unwrappedTypeID(), edm::TypeID(typeid(edmtest::Simple))}; + reg.setProcessOrder({"PROD"}); reg.setFrozen(productTypesConsumed, elementTypesConsumed, "TEST"); { auto notFound = diff --git a/FWCore/Integration/plugins/PutOrMergeTestSource.cc b/FWCore/Integration/plugins/PutOrMergeTestSource.cc index f996a87421a7b..fbe84369519b3 100644 --- a/FWCore/Integration/plugins/PutOrMergeTestSource.cc +++ b/FWCore/Integration/plugins/PutOrMergeTestSource.cc @@ -78,6 +78,7 @@ void PutOrMergeTestSource::registerProducts() { productRegistryUpdate().copyProduct(thingDesc_); productRegistryUpdate().copyProduct(thingWithMergeDesc_); productRegistryUpdate().copyProduct(thingWithEqualDesc_); + productRegistryUpdate().setProcessOrder({"PROD"}); } InputSource::ItemTypeInfo PutOrMergeTestSource::getNextItemType() { diff --git a/FWCore/Sources/src/PuttableSourceBase.cc b/FWCore/Sources/src/PuttableSourceBase.cc index ee215c3d4c13c..4f0b8db737cae 100644 --- a/FWCore/Sources/src/PuttableSourceBase.cc +++ b/FWCore/Sources/src/PuttableSourceBase.cc @@ -41,6 +41,7 @@ PuttableSourceBase::PuttableSourceBase(ParameterSet const& iPSet, InputSourceDes void PuttableSourceBase::registerProducts() { SignallingProductRegistryFiller reg; + reg.setProcessOrder({moduleDescription().processName()}); //this handled case were Source's construct injects items into the ProductRegistry reg.addFromInput(productRegistryUpdate()); registerProducts(this, ®, moduleDescription()); diff --git a/FWCore/TestProcessor/src/TestProcessor.cc b/FWCore/TestProcessor/src/TestProcessor.cc index 7cd0d4053c309..a4ff547aaa8ee 100644 --- a/FWCore/TestProcessor/src/TestProcessor.cc +++ b/FWCore/TestProcessor/src/TestProcessor.cc @@ -45,6 +45,7 @@ #include "FWCore/ParameterSet/interface/ProcessDesc.h" #include "FWCore/ParameterSet/interface/validateTopLevelParameterSets.h" +#include "DataFormats/Provenance/interface/processingOrderMerge.h" #include "FWCore/Utilities/interface/ExceptionCollector.h" #include "oneTimeInitialization.h" @@ -121,6 +122,11 @@ namespace edm { processHistory_.emplace_back(p, psetid, xstr(PROJECT_VERSION), HardwareResourcesDescription()); processHistoryRegistry_.registerProcessHistory(processHistory_); } + std::vector orderedProcesses; + processingOrderMerge(processHistoryRegistry_, orderedProcesses); + orderedProcesses.insert(orderedProcesses.begin(), processConfiguration_->processName()); + + tempReg->setProcessOrder(orderedProcesses); //setup the products we will be adding to the event for (auto const& produce : iConfig.produceEntries()) { From ee4fd48b33e84e6a0c912173f1f8c17ebaeb20c2 Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 10:43:42 -0500 Subject: [PATCH 02/13] Handle case for empty ROOT file An empty ROOT files contains no ProcessHistory which causes problems when filling the ProductRegistry at construction time. Now skip empty files until we find a file with data. --- IOPool/Input/src/RootFile.cc | 11 ++++++++--- IOPool/Input/src/RootFile.h | 2 ++ IOPool/Input/src/RootPrimaryFileSequence.cc | 2 +- 3 files changed, 11 insertions(+), 4 deletions(-) diff --git a/IOPool/Input/src/RootFile.cc b/IOPool/Input/src/RootFile.cc index 3a792311695c8..6c5b0ebdbb93b 100644 --- a/IOPool/Input/src/RootFile.cc +++ b/IOPool/Input/src/RootFile.cc @@ -563,9 +563,13 @@ namespace edm { processingOrderMerge(*processHistoryRegistry_, processingOrder); newReg->setProcessOrder(processingOrder); - // freeze the product registry - newReg->setFrozen(inputType != InputType::Primary); - productRegistry_.reset(newReg.release()); + if (not processingOrder.empty()) { + // freeze the product registry + newReg->setFrozen(inputType != InputType::Primary); + productRegistry_.reset(newReg.release()); + } else { + productRegistry_ = std::make_shared(); + } } // Set up information from the product registry. @@ -626,6 +630,7 @@ namespace edm { RootFile::~RootFile() {} + bool RootFile::empty() const { return runTree_.entries() == 0; } void RootFile::readEntryDescriptionTree(EntryDescriptionMap& entryDescriptionMap, InputType inputType) { // Called only for old format files. // We use a smart pointer so the tree will be deleted after use, and not kept for the life of the file. diff --git a/IOPool/Input/src/RootFile.h b/IOPool/Input/src/RootFile.h index d038d0061373a..7dc4a6233563e 100644 --- a/IOPool/Input/src/RootFile.h +++ b/IOPool/Input/src/RootFile.h @@ -155,6 +155,8 @@ namespace edm { std::array const& hasNewlyDroppedBranch() const { return hasNewlyDroppedBranch_; } bool branchListIndexesUnchanged() const { return branchListIndexesUnchanged_; } bool modifiedIDs() const { return daqProvenanceHelper_.get() != nullptr; } + //Are there no data stored in the file? + bool empty() const; std::shared_ptr createFileBlock(); void updateFileBlock(FileBlock&); diff --git a/IOPool/Input/src/RootPrimaryFileSequence.cc b/IOPool/Input/src/RootPrimaryFileSequence.cc index 3b5a4b588315b..467039fbc0492 100644 --- a/IOPool/Input/src/RootPrimaryFileSequence.cc +++ b/IOPool/Input/src/RootPrimaryFileSequence.cc @@ -66,7 +66,7 @@ namespace edm { // Open the first file. for (setAtFirstFile(); !noMoreFiles(); setAtNextFile()) { initFile(input_.skipBadFiles()); - if (rootFile()) + if (rootFile() and not rootFile()->empty()) break; } if (rootFile()) { From e8ded6872cb2b3e1a3c06c3fa0582e7ca28ebd2c Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 13:02:58 -0500 Subject: [PATCH 03/13] Set no-process lookup at begin job time Instead of dynamically determining what data product to get at Run/LuminosityBlock/Event transition time, the data product to get is now determined at begin job time. This is done for no-process and the skip current process cases. --- .../interface/ProductResolverIndexHelper.h | 10 +- .../src/ProductResolverIndexHelper.cc | 195 ++++-- .../test/productResolverIndexHelper_t.cpp | 587 ++++++++++++------ .../src/classes_def_others.xml | 2 +- FWCore/Framework/interface/Principal.h | 2 - .../Framework/interface/ProductResolverBase.h | 14 +- .../src/DroppedDataProductResolver.cc | 6 +- .../src/DroppedDataProductResolver.h | 4 +- FWCore/Framework/src/EDConsumerBase.cc | 16 +- FWCore/Framework/src/EDLooperBase.cc | 3 +- FWCore/Framework/src/EventForTransformer.cc | 2 +- FWCore/Framework/src/EventPrincipal.cc | 4 +- FWCore/Framework/src/EventProcessor.cc | 3 +- FWCore/Framework/src/Principal.cc | 25 +- FWCore/Framework/src/PrincipalGetAdapter.cc | 4 +- FWCore/Framework/src/ProductResolvers.cc | 481 +------------- FWCore/Framework/src/ProductResolvers.h | 143 +---- .../Framework/src/ProductResolversFactory.cc | 81 --- FWCore/Framework/src/Worker.cc | 9 +- FWCore/Framework/test/Event_t.cpp | 19 +- .../test/edconsumerbase_t.cppunit.cc | 104 ++-- .../test/event_getrefbeforeput_t.cppunit.cc | 1 + .../test/eventprincipal_t.cppunit.cc | 1 + .../Framework/test/generichandle_t.cppunit.cc | 1 + .../test/testNoProcessFallback3_cfg.py | 8 +- .../testNoProcessFallbackNoCurrent_cfg.py | 2 +- ...estProcessBlockNOMergeOfMergedFiles_cfg.py | 7 +- 27 files changed, 704 insertions(+), 1030 deletions(-) diff --git a/DataFormats/Provenance/interface/ProductResolverIndexHelper.h b/DataFormats/Provenance/interface/ProductResolverIndexHelper.h index 707144625603f..13b1ea7bcc5f5 100644 --- a/DataFormats/Provenance/interface/ProductResolverIndexHelper.h +++ b/DataFormats/Provenance/interface/ProductResolverIndexHelper.h @@ -156,9 +156,6 @@ namespace edm { char const* moduleLabel, char const* instance) const; - // Return indexes for all groups that match the type. - Matches relatedIndexes(KindOfType kindOfType, TypeID const& typeID) const; - // This will throw if called after the object is frozen. // The typeID must be for a type with a dictionary // (the calling function is expected to check that) @@ -196,15 +193,13 @@ namespace edm { // Before the object is frozen the accessors above will // fail to find a match. Once frozen, no more new entries // can be added with insert. - void setFrozen(std::string_view processName); + void setFrozen(std::vector const& orderedProcessNames); /**The list of process names for data products associated to the ProductResolvers. * If no products are associated with a process for this transition, the process name will not be in this list. */ std::vector const& lookupProcessNames() const; - bool producesInCurrentProcess() const { return producesInCurrentProcess_; } - class Range { public: Range(unsigned int begin, unsigned int end) : begin_(begin), end_(end) {} @@ -335,6 +330,7 @@ namespace edm { ProductResolverIndex index() const { return index_; } void clearProcess() { process_.clear(); } + void setSkipCurrentProcess() { process_ = "#"; } void setIndex(ProductResolverIndex v) { index_ = v; } bool operator<(Item const& right) const; @@ -351,8 +347,6 @@ namespace edm { edm::propagate_const>> items_; edm::propagate_const>> processItems_; - - bool producesInCurrentProcess_{false}; }; } // namespace edm #endif diff --git a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc index 4c265aacddcbc..c26b2d603e804 100644 --- a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc +++ b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc @@ -10,7 +10,6 @@ #include #include -#include #include namespace edm { @@ -121,11 +120,12 @@ namespace edm { return index; } //Now check to see if only one process has this type/module/instance name - auto nextIndex = index + 1; + // we need to skip the skipCurrentProcess entry + auto nextIndex = index + 2; while (indexAndNames_.size() > nextIndex && indexAndNames_[nextIndex].startInProcessNames() != 0U) { ++nextIndex; } - return (nextIndex == index + 2) ? index + 1 : index; + return (nextIndex == index + 3) ? index + 2 : index; }; return indexAndNames_[checkForSingleProcess(iToIndexAndNames)].index(); @@ -201,23 +201,6 @@ namespace edm { return Matches(this, startInIndexAndNames, numberOfMatches); } - ProductResolverIndexHelper::Matches ProductResolverIndexHelper::relatedIndexes(KindOfType kindOfType, - TypeID const& typeID) const { - unsigned int startInIndexAndNames = std::numeric_limits::max(); - unsigned int numberOfMatches = 0; - - // Look for the type and check to see if it found it - unsigned iType = indexToType(kindOfType, typeID); - if (iType != std::numeric_limits::max()) { - // Get the range of entries with a matching TypeID - Range const& range = ranges_[iType]; - - startInIndexAndNames = range.begin(); - numberOfMatches = range.end() - range.begin(); - } - return Matches(this, startInIndexAndNames, numberOfMatches); - } - ProductResolverIndex ProductResolverIndexHelper::insert(TypeID const& typeID, char const* moduleLabel, char const* instance, @@ -252,8 +235,11 @@ namespace edm { item.clearProcess(); iter = items_->find(item); if (iter == items_->end()) { - item.setIndex(nextIndexValue_); - ++nextIndexValue_; + item.setIndex(ProductResolverIndexInitializing); + items_->insert(item); + //add entry for skipCurrentProcess + item.setSkipCurrentProcess(); + item.setIndex(ProductResolverIndexInitializing); items_->insert(item); } @@ -273,8 +259,10 @@ namespace edm { containedItem.clearProcess(); iter = items_->find(containedItem); if (iter == items_->end()) { - containedItem.setIndex(nextIndexValue_); - ++nextIndexValue_; + containedItem.setIndex(ProductResolverIndexInitializing); + items_->insert(containedItem); + containedItem.setSkipCurrentProcess(); + containedItem.setIndex(ProductResolverIndexInitializing); items_->insert(containedItem); } @@ -292,8 +280,10 @@ namespace edm { baseItem.clearProcess(); iter = items_->find(baseItem); if (iter == items_->end()) { - baseItem.setIndex(nextIndexValue_); - ++nextIndexValue_; + baseItem.setIndex(ProductResolverIndexInitializing); + items_->insert(baseItem); + baseItem.setSkipCurrentProcess(); + baseItem.setIndex(ProductResolverIndexInitializing); items_->insert(baseItem); } } @@ -317,7 +307,67 @@ namespace edm { return insert(typeID, moduleLabel, instance, process, containedTypeID, baseTypesOfContainedType); } - void ProductResolverIndexHelper::setFrozen(std::string_view processName) { + namespace { + void setNoProcessIndices(std::vector::iterator itBegin, + std::vector::iterator itEnd, + std::vector const& orderedProcessNames, + std::vector const& processNames) { + using IndexAndNames = edm::ProductResolverIndexHelper::IndexAndNames; + assert(itEnd - itBegin > 2); + assert(itBegin->startInProcessNames() == 0U); + assert((itBegin + 1)->startInProcessNames() == 1U); + assert(processNames[(itBegin + 1)->startInProcessNames()] == '#'); + assert(itBegin->index() == edm::ProductResolverIndexInitializing); + assert((itBegin + 1)->index() == edm::ProductResolverIndexInitializing); + if (itEnd - itBegin == 3) { + //only have one actual process + *itBegin = + IndexAndNames((itBegin + 2)->index(), itBegin->startInBigNamesContainer(), itBegin->startInProcessNames()); + //Now handle skipCurrentProcess + if (orderedProcessNames[0] == &processNames[(itBegin + 2)->startInProcessNames()]) { + //the one process is the current process + *(itBegin + 1) = IndexAndNames(ProductResolverIndexInvalid, + (itBegin + 1)->startInBigNamesContainer(), + (itBegin + 1)->startInProcessNames()); + } else { + *(itBegin + 1) = IndexAndNames( + (itBegin + 2)->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + } + } else { + bool foundFirstMatch = false; + for (auto const& proc : orderedProcessNames) { + auto it = itBegin + 2; + while (it != itEnd && proc != &processNames[it->startInProcessNames()]) { + ++it; + } + if (it != itEnd) { + if (not foundFirstMatch) { + foundFirstMatch = true; + //found a process that matches + *itBegin = + IndexAndNames(it->index(), itBegin->startInBigNamesContainer(), itBegin->startInProcessNames()); + //Now handle skipCurrentProcess + if (proc != orderedProcessNames[0]) { + *(itBegin + 1) = IndexAndNames( + it->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + break; + } else { + //this process is the current process + *(itBegin + 1) = IndexAndNames(ProductResolverIndexInvalid, + (itBegin + 1)->startInBigNamesContainer(), + (itBegin + 1)->startInProcessNames()); + } + } else { + *(itBegin + 1) = IndexAndNames( + it->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + break; + } + } + } + } + } + } // namespace + void ProductResolverIndexHelper::setFrozen(std::vector const& orderedProcessNames) { if (!items_) return; @@ -361,6 +411,15 @@ namespace edm { previousInstance = item.instance(); } + //sanity check + for (auto const& p : *processItems_) { + if (p.empty() or p == "#") + continue; + if (orderedProcessNames.end() == std::find(orderedProcessNames.begin(), orderedProcessNames.end(), p)) { + throw Exception(errors::LogicError) + << "ProductResolverIndexHelper::setFrozen process not in ordered list " << p << std::endl; + } + } // Size and fill the process name vector unsigned int processNamesSize = 0; for (auto const& processItem : *processItems_) { @@ -374,9 +433,6 @@ namespace edm { } processNames_.push_back('\0'); lookupProcessNames_.push_back(processItem); - if (processItem == processName) { - producesInCurrentProcess_ = true; - } } // Reserve memory in the vectors @@ -393,9 +449,10 @@ namespace edm { unsigned int iBeginning = 0; iCountCharacters = 0; unsigned int previousCharacterCount = 0; + unsigned int iNoProcessBegin = 0; if (!items_->empty()) { for (auto const& item : *items_) { - if (iFirstThisType || item.typeID() != previousTypeID || item.kindOfType() != previousKindOfType) { + if (iFirstType || item.typeID() != previousTypeID || item.kindOfType() != previousKindOfType) { iFirstThisType = true; sortedTypeIDs_.push_back(item.typeID()); if (iFirstType) { @@ -405,9 +462,15 @@ namespace edm { } iBeginning = iCount; } - ++iCount; if (iFirstThisType || item.moduleLabel() != previousModuleLabel || item.instance() != previousInstance) { + if (iNoProcessBegin != iCount) { + setNoProcessIndices(indexAndNames_.begin() + iNoProcessBegin, + indexAndNames_.begin() + iCount, + orderedProcessNames, + processNames_); + iNoProcessBegin = iCount; + } unsigned int labelSize = item.moduleLabel().size(); for (unsigned int j = 0; j < labelSize; ++j) { bigNamesContainer_.push_back(item.moduleLabel()[j]); @@ -439,8 +502,11 @@ namespace edm { previousKindOfType = item.kindOfType(); previousModuleLabel = item.moduleLabel(); previousInstance = item.instance(); + ++iCount; } ranges_.push_back(Range(iBeginning, iCount)); + setNoProcessIndices( + indexAndNames_.begin() + iNoProcessBegin, indexAndNames_.end(), orderedProcessNames, processNames_); } // Some sanity checks to protect against out of bounds vector accesses @@ -616,30 +682,50 @@ namespace edm { void ProductResolverIndexHelper::sanityCheck() const { bool sanityChecksPass = true; - if (sortedTypeIDs_.size() != ranges_.size()) + std::string errorMessage; + if (sortedTypeIDs_.size() != ranges_.size()) { sanityChecksPass = false; + errorMessage += "sortedTypeIDs_.size() != ranges_.size()\n"; + } unsigned int previousEnd = 0; for (auto const& range : ranges_) { - if (range.begin() != previousEnd) + if (range.begin() != previousEnd) { sanityChecksPass = false; - if (range.begin() >= range.end()) + errorMessage += "ranges_ are not contiguous\n"; + } + if (range.begin() >= range.end()) { sanityChecksPass = false; + errorMessage += "ranges_ are not valid\n"; + } previousEnd = range.end(); } - if (previousEnd != indexAndNames_.size()) + if (previousEnd != indexAndNames_.size()) { sanityChecksPass = false; + errorMessage += "ranges_ do not cover all of indexAndNames_\n"; + } unsigned maxStart = 0; unsigned maxStartProcess = 0; for (auto const& indexAndName : indexAndNames_) { - if (indexAndName.index() >= nextIndexValue_ && indexAndName.index() != ProductResolverIndexAmbiguous) + if (indexAndName.index() >= nextIndexValue_ && (indexAndName.index() != ProductResolverIndexAmbiguous and + indexAndName.index() != ProductResolverIndexInvalid)) { sanityChecksPass = false; + auto startOfModule = indexAndName.startInBigNamesContainer(); + auto startOfInstance = strlen(&bigNamesContainer_[startOfModule]) + 1 + startOfModule; + errorMessage += "indexAndNames_ has invalid index" + std::to_string(indexAndName.index()) + " " + + &bigNamesContainer_[startOfModule] + " " + &bigNamesContainer_[startOfInstance] + " " + + &processNames_[indexAndName.startInProcessNames()] + "\n"; + } - if (indexAndName.startInBigNamesContainer() >= bigNamesContainer_.size()) + if (indexAndName.startInBigNamesContainer() >= bigNamesContainer_.size()) { sanityChecksPass = false; - if (indexAndName.startInProcessNames() >= processNames_.size()) + errorMessage += "indexAndNames_ has invalid startInBigNamesContainer\n"; + } + if (indexAndName.startInProcessNames() >= processNames_.size()) { sanityChecksPass = false; + errorMessage += "indexAndNames_ has invalid startInProcessNames\n"; + } if (indexAndName.startInBigNamesContainer() > maxStart) maxStart = indexAndName.startInBigNamesContainer(); @@ -648,34 +734,47 @@ namespace edm { } if (!indexAndNames_.empty()) { - if (bigNamesContainer_.back() != '\0') + if (bigNamesContainer_.back() != '\0') { sanityChecksPass = false; - if (processNames_.back() != '\0') + errorMessage += "bigNamesContainer_ does not end with null char\n"; + } + if (processNames_.back() != '\0') { sanityChecksPass = false; - if (maxStart >= bigNamesContainer_.size()) + errorMessage += "processNames_ does not end with null char\n"; + } + if (maxStart >= bigNamesContainer_.size()) { sanityChecksPass = false; + errorMessage += "maxStart >= bigNamesContainer_.size()\n"; + } unsigned int countZeroes = 0; for (unsigned j = maxStart; j < bigNamesContainer_.size(); ++j) { if (bigNamesContainer_[j] == '\0') { ++countZeroes; } } - if (countZeroes != 2) + if (countZeroes != 2) { sanityChecksPass = false; - if (maxStartProcess >= processNames_.size()) + errorMessage += "bigNamesContainer_ does not have two null chars\n"; + } + if (maxStartProcess >= processNames_.size()) { sanityChecksPass = false; + errorMessage += "maxStartProcess >= processNames_.size()\n"; + } countZeroes = 0; for (unsigned j = maxStartProcess; j < processNames_.size(); ++j) { if (processNames_[j] == '\0') { ++countZeroes; } } - if (countZeroes != 1) + if (countZeroes != 1) { sanityChecksPass = false; + errorMessage += "processNames_ does not have one null char\n"; + } } if (!sanityChecksPass) { - throw Exception(errors::LogicError) << "ProductResolverIndexHelper::setFrozen - Detected illegal state.\n"; + throw Exception(errors::LogicError) << "ProductResolverIndexHelper::setFrozen - Detected illegal state.\n" + << errorMessage; } } @@ -769,8 +868,8 @@ namespace edm { if (items_) { os << "******* items_ \n"; for (auto const& item : *items_) { - std::cout << item.kindOfType() << " " << item.moduleLabel() << " " << item.instance() << " " << item.process() - << " " << item.index() << " " << item.typeID() << "\n"; + os << item.kindOfType() << " " << item.moduleLabel() << " " << item.instance() << " " << item.process() << " " + << item.index() << " " << item.typeID() << "\n"; } } if (processItems_) { diff --git a/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp b/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp index 204482db41084..c632b8b4bc43e 100644 --- a/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp +++ b/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp @@ -21,7 +21,10 @@ TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { SECTION("CreateEmpty") { edm::ProductResolverIndexHelper helper; - helper.setFrozen("processA"); + { + std::vector processNames = {"processA"}; + helper.setFrozen(processNames); + } REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == ProductResolverIndexInvalid); @@ -33,205 +36,417 @@ TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { edm::ProductResolverIndexHelper::Matches matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "label_A", "instance_A"); REQUIRE(matches.numberOfMatches() == 0); - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID); - REQUIRE(matches.numberOfMatches() == 0); TypeID typeID(typeid(ProductID)); REQUIRE_THROWS_AS(helper.insert(typeID, "labelA", "instanceA", "processA"), cms::Exception); } SECTION("OneEntry") { - edm::ProductResolverIndexHelper helper; - - TypeID typeIDProductID(typeid(ProductID)); - helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); - - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); - - edm::ProductResolverIndexHelper::Matches matches = - helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "label_A", "instance_A"); - REQUIRE(matches.numberOfMatches() == 0); - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID); - REQUIRE(matches.numberOfMatches() == 0); - - helper.setFrozen("processA"); - - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA"); - REQUIRE(matches.numberOfMatches() == 2); - edm::ProductResolverIndex indexEmptyProcess = matches.index(0); - edm::ProductResolverIndex indexWithProcess = matches.index(1); - REQUIRE_THROWS_AS(matches.index(2), cms::Exception); - REQUIRE(indexEmptyProcess < 2); - REQUIRE(indexWithProcess < 2); - REQUIRE(indexEmptyProcess != indexWithProcess); - - //with only one entry, all should resolve to the one with process name - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcess); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcess); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcess); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcess); - - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instance", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceAX", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "label", "instanceA", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelAX", "instanceA", "processA") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "process") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processAX") == - ProductResolverIndexInvalid); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_EventID, "labelA", "instanceA", "processA") == - ProductResolverIndexInvalid); - - REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == - ProductResolverIndexInvalid); - - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID); - REQUIRE(matches.numberOfMatches() == 2); - REQUIRE(matches.index(0) == indexEmptyProcess); - REQUIRE(matches.index(1) == indexWithProcess); - - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID); - REQUIRE(matches.numberOfMatches() == 0); - - matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_ProductID); - REQUIRE(matches.numberOfMatches() == 0); - - matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA"); - REQUIRE(matches.numberOfMatches() == 0); - - { - auto indexToModules = helper.indiciesForModulesInProcess("processA"); - REQUIRE(indexToModules.size() == 1); - REQUIRE(indexToModules.count("labelA") == 1); - auto const& range = indexToModules.equal_range("labelA"); - REQUIRE(std::get<2>(range.first->second) == indexWithProcess); + SECTION("Current process") { + edm::ProductResolverIndexHelper helper; + + TypeID typeIDProductID(typeid(ProductID)); + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); + + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); + + edm::ProductResolverIndexHelper::Matches matches = + helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "label_A", "instance_A"); + REQUIRE(matches.numberOfMatches() == 0); + + { + std::vector processNames = {"processA"}; + helper.setFrozen(processNames); + } + + matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA"); + REQUIRE(matches.numberOfMatches() == 3); + edm::ProductResolverIndex indexEmptyProcess = matches.index(0); + edm::ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + edm::ProductResolverIndex indexWithProcess = matches.index(2); + REQUIRE_THROWS_AS(matches.index(3), cms::Exception); + REQUIRE(indexEmptyProcess < 2); + REQUIRE(indexWithProcess < 2); + REQUIRE(indexEmptyProcess == indexWithProcess); + REQUIRE(indexSkipCurrentProcess == ProductResolverIndexInvalid); + + //with only one entry, all should resolve to the one with process name + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcess); + + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instance", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceAX", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "label", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelAX", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "process") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processAX") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_EventID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + + matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA"); + REQUIRE(matches.numberOfMatches() == 0); + + { + auto indexToModules = helper.indiciesForModulesInProcess("processA"); + REQUIRE(indexToModules.size() == 1); + REQUIRE(indexToModules.count("labelA") == 1); + auto const& range = indexToModules.equal_range("labelA"); + REQUIRE(std::get<2>(range.first->second) == indexWithProcess); + } + + { + auto indexToModules = helper.indiciesForModulesInProcess("processNotHere"); + REQUIRE(indexToModules.size() == 0); + } } - - { - auto indexToModules = helper.indiciesForModulesInProcess("processNotHere"); - REQUIRE(indexToModules.size() == 0); + SECTION("Previous process") { + edm::ProductResolverIndexHelper helper; + + TypeID typeIDProductID(typeid(ProductID)); + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); + + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); + + edm::ProductResolverIndexHelper::Matches matches = + helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "label_A", "instance_A"); + REQUIRE(matches.numberOfMatches() == 0); + + { + std::vector processNames = {"processB", "processA"}; + helper.setFrozen(processNames); + } + + matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA"); + REQUIRE(matches.numberOfMatches() == 3); + edm::ProductResolverIndex indexEmptyProcess = matches.index(0); + edm::ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + edm::ProductResolverIndex indexWithProcess = matches.index(2); + REQUIRE_THROWS_AS(matches.index(3), cms::Exception); + REQUIRE(indexEmptyProcess < 2); + REQUIRE(indexWithProcess < 2); + REQUIRE(indexEmptyProcess == indexWithProcess); + REQUIRE(indexSkipCurrentProcess == indexWithProcess); + + //with only one entry, all should resolve to the one with process name + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcess); + + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instance", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceAX", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "label", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelAX", "instanceA", "processA") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "process") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processAX") == + ProductResolverIndexInvalid); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_EventID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA") == ProductResolverIndexInvalid); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == + ProductResolverIndexInvalid); + + matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_ProductID, "labelA", "instanceA"); + REQUIRE(matches.numberOfMatches() == 0); + + { + auto indexToModules = helper.indiciesForModulesInProcess("processA"); + REQUIRE(indexToModules.size() == 1); + REQUIRE(indexToModules.count("labelA") == 1); + auto const& range = indexToModules.equal_range("labelA"); + REQUIRE(std::get<2>(range.first->second) == indexWithProcess); + } + + { + auto indexToModules = helper.indiciesForModulesInProcess("processNotHere"); + REQUIRE(indexToModules.size() == 0); + } + } + SECTION("current and previous section") { + edm::ProductResolverIndexHelper helper; + + TypeID typeIDProductID(typeid(ProductID)); + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); + helper.insert(typeIDProductID, "labelA", "instanceA", "processB"); + { + std::vector processNames = {"processB", "processA"}; + helper.setFrozen(processNames); + } + auto matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA"); + REQUIRE(matches.numberOfMatches() == 4); + edm::ProductResolverIndex indexEmptyProcess = matches.index(0); + edm::ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + edm::ProductResolverIndex indexWithProcessA = matches.index(2); + edm::ProductResolverIndex indexWithProcessB = matches.index(3); + REQUIRE_THROWS_AS(matches.index(4), cms::Exception); + REQUIRE(indexEmptyProcess == indexWithProcessB); + REQUIRE(indexSkipCurrentProcess == indexWithProcessA); + + //with only one entry, all should resolve to the one with process name + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcessB); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcessB); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcessB); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcessA); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processB") == indexWithProcessB); } } SECTION("ManyEntries") { - edm::ProductResolverIndexHelper helper; - - TypeID typeIDProductID(typeid(ProductID)); - TypeID typeIDEventID(typeid(EventID)); - TypeID typeIDVectorInt(typeid(std::vector)); - TypeID typeIDSetInt(typeid(std::set)); - TypeID typeIDVSimpleDerived(typeid(std::vector)); - - helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0, 1, 2 - helper.insert(typeIDVectorInt, "label", "instance", "process"); // 3, 4, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 6, 7 - helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 8, 9 - helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 10, 11 - helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 12, 13 - helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 14, 15 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 16, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 17, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 18, 5 - helper.insert(typeIDProductID, "label", "instance", "process"); // 19, 20 - helper.insert(typeIDEventID, "label", "instance", "process"); // 21, 22 - helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 23, 24 - REQUIRE_THROWS_AS(helper.insert(typeIDProductID, "labelA", "instanceA", "processA"), cms::Exception); // duplicate - - helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 25, 26 - - helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 27, 28, 29, 30 - - helper.setFrozen("processC"); - - TypeID typeID_int(typeid(int)); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC", "processC") == ProductResolverIndexAmbiguous); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC", "processQ") == ProductResolverIndexInvalid); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC") == ProductResolverIndexAmbiguous); - edm::ProductResolverIndexHelper::Matches matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_int); - REQUIRE(matches.numberOfMatches() == 4); - REQUIRE(matches.index(0) == 5); - REQUIRE(matches.index(1) == 3); - REQUIRE(matches.index(2) == 2); - REQUIRE(matches.index(3) == ProductResolverIndexAmbiguous); - - TypeID typeID_vint(typeid(std::vector)); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC") == 0); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_vint, "labelC", "instanceC") == 0); //only one with no process - - TypeID typeID_sint(typeid(std::set)); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_sint, "labelC", "instanceC", "processC") == 25); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_sint, "labelC", "instanceC") == 25); //only one with no process - - TypeID typeID_Simple(typeid(edmtest::Simple)); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC") == 27); //only one with no process - REQUIRE(helper.index(ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC", "processC") == 27); - - TypeID typeID_SimpleDerived(typeid(edmtest::SimpleDerived)); - REQUIRE(helper.index(ELEMENT_TYPE, typeID_SimpleDerived, "labelC", "instanceC") == 27); //only one with no process - REQUIRE(helper.index(ELEMENT_TYPE, typeID_SimpleDerived, "labelC", "instanceC", "processC") == 27); - - TypeID typeID_VSimpleDerived(typeid(std::vector)); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_VSimpleDerived, "labelC", "instanceC") == 27); //only one with no process - REQUIRE(helper.index(PRODUCT_TYPE, typeID_VSimpleDerived, "labelC", "instanceC", "processC") == 27); - - matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID, "labelB", "instanceB"); - REQUIRE(matches.numberOfMatches() == 5); - ProductResolverIndex indexEmptyProcess = matches.index(0); - ProductResolverIndex indexB = matches.index(1); - ProductResolverIndex indexB1 = matches.index(2); - ProductResolverIndex indexB2 = matches.index(3); - ProductResolverIndex indexB3 = matches.index(4); - REQUIRE_THROWS_AS(matches.index(5), cms::Exception); - REQUIRE(indexEmptyProcess == 7); - REQUIRE(indexB == 6); - REQUIRE(indexB1 == 16); - REQUIRE(indexB2 == 18); - REQUIRE(indexB3 == 17); - - REQUIRE(std::string(matches.moduleLabel(4)) == "labelB"); - REQUIRE(std::string(matches.productInstanceName(4)) == "instanceB"); - REQUIRE(std::string(matches.processName(4)) == "processB3"); - REQUIRE(std::string(matches.processName(0)) == ""); - - matches = helper.relatedIndexes(ELEMENT_TYPE, typeID_Simple); - REQUIRE(matches.numberOfMatches() == 2); - ProductResolverIndex indexC = matches.index(1); - REQUIRE_THROWS_AS(matches.index(2), cms::Exception); - REQUIRE(indexC == 27); - - { - auto indexToModules = helper.indiciesForModulesInProcess("processA"); - REQUIRE(indexToModules.size() == 1); + SECTION("1 simple type not in current process") { + edm::ProductResolverIndexHelper helper; + TypeID typeIDEventID(typeid(EventID)); + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 0, + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 1, + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 2, + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 3, + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 4, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 5, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 6, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 7, + helper.insert(typeIDEventID, "label", "instance", "process"); // 8, + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } + auto matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID, "labelB", "instanceB"); + REQUIRE(matches.numberOfMatches() == 4 + 2); //4 process matches + 1 empty and 1 skip current process + ProductResolverIndex indexEmptyProcess = matches.index(0); + ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + ProductResolverIndex indexB = matches.index(2); + ProductResolverIndex indexB1 = matches.index(3); + ProductResolverIndex indexB2 = matches.index(4); + ProductResolverIndex indexB3 = matches.index(5); + REQUIRE_THROWS_AS(matches.index(6), cms::Exception); + REQUIRE(indexB == 0); + REQUIRE(indexB1 == 5); + REQUIRE(indexB2 == 7); + REQUIRE(indexB3 == 6); + REQUIRE(indexEmptyProcess == indexB); + REQUIRE(indexSkipCurrentProcess == indexB); + + REQUIRE(std::string(matches.moduleLabel(5)) == "labelB"); + REQUIRE(std::string(matches.productInstanceName(5)) == "instanceB"); + REQUIRE(std::string(matches.processName(5)) == "processB3"); + REQUIRE(std::string(matches.processName(0)) == ""); } - { - auto indexToModules = helper.indiciesForModulesInProcess("processB"); - REQUIRE(indexToModules.size() == 5); + SECTION("1 simple type in current process") { + edm::ProductResolverIndexHelper helper; + TypeID typeIDEventID(typeid(EventID)); + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 0, + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 1, + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 2, + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 3, + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 4, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 5, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 6, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 7, + { + std::vector processNames = {"processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } + auto matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID, "labelB", "instanceB"); + REQUIRE(matches.numberOfMatches() == 4 + 2); //4 process matches + 1 empty and 1 skip current process + ProductResolverIndex indexEmptyProcess = matches.index(0); + ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + ProductResolverIndex indexB = matches.index(2); + ProductResolverIndex indexB1 = matches.index(3); + ProductResolverIndex indexB2 = matches.index(4); + ProductResolverIndex indexB3 = matches.index(5); + REQUIRE_THROWS_AS(matches.index(6), cms::Exception); + REQUIRE(indexB == 0); + REQUIRE(indexB1 == 5); + REQUIRE(indexB2 == 7); + REQUIRE(indexB3 == 6); + REQUIRE(indexEmptyProcess == indexB); + REQUIRE(indexSkipCurrentProcess == indexB1); + + REQUIRE(std::string(matches.moduleLabel(5)) == "labelB"); + REQUIRE(std::string(matches.productInstanceName(5)) == "instanceB"); + REQUIRE(std::string(matches.processName(5)) == "processB3"); + REQUIRE(std::string(matches.processName(0)) == ""); } - { - auto indexToModules = helper.indiciesForModulesInProcess("processB1"); - REQUIRE(indexToModules.size() == 1); - } - { - auto indexToModules = helper.indiciesForModulesInProcess("processB2"); - REQUIRE(indexToModules.size() == 1); - } - { - auto indexToModules = helper.indiciesForModulesInProcess("processB3"); - REQUIRE(indexToModules.size() == 1); + + SECTION("2 simple types") { + edm::ProductResolverIndexHelper helper; + TypeID typeIDProductID(typeid(ProductID)); + TypeID typeIDEventID(typeid(EventID)); + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 0, + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 1, + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 2, + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 3, + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 4, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 5, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 6, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 7, + helper.insert(typeIDProductID, "label", "instance", "process"); // 8, + helper.insert(typeIDEventID, "label", "instance", "process"); // 9, + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 10 + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } + auto matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID, "labelB", "instanceB"); + REQUIRE(matches.numberOfMatches() == 4 + 2); + ProductResolverIndex indexEmptyProcess = matches.index(0); + ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + ProductResolverIndex indexB = matches.index(2); + ProductResolverIndex indexB1 = matches.index(3); + ProductResolverIndex indexB2 = matches.index(4); + ProductResolverIndex indexB3 = matches.index(5); + REQUIRE_THROWS_AS(matches.index(6), cms::Exception); + REQUIRE(indexB == 0); + REQUIRE(indexB1 == 5); + REQUIRE(indexB2 == 7); + REQUIRE(indexB3 == 6); + REQUIRE(indexEmptyProcess == indexB); + REQUIRE(indexSkipCurrentProcess == indexB); + + REQUIRE(std::string(matches.moduleLabel(5)) == "labelB"); + REQUIRE(std::string(matches.productInstanceName(5)) == "instanceB"); + REQUIRE(std::string(matches.processName(5)) == "processB3"); + REQUIRE(std::string(matches.processName(0)) == ""); } - { - auto indexToModules = helper.indiciesForModulesInProcess("processC"); - REQUIRE(indexToModules.size() == 3); + SECTION("many types and entries") { + edm::ProductResolverIndexHelper helper; + + TypeID typeIDProductID(typeid(ProductID)); + TypeID typeIDEventID(typeid(EventID)); + TypeID typeIDVectorInt(typeid(std::vector)); + TypeID typeIDSetInt(typeid(std::set)); + TypeID typeIDVSimpleDerived(typeid(std::vector)); + // order of indicies: [ same but for each element type] + helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0, + helper.insert(typeIDVectorInt, "label", "instance", "process"); // 1, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 2, + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 3, + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 4, + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 5, + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 6, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 7, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 8, + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 9, + helper.insert(typeIDProductID, "label", "instance", "process"); // 10, + helper.insert(typeIDEventID, "label", "instance", "process"); // 11, + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 12 + REQUIRE_THROWS_AS(helper.insert(typeIDProductID, "labelA", "instanceA", "processA"), + cms::Exception); // duplicate + + helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 13 + + helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 14 + + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } + + TypeID typeID_int(typeid(int)); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC", "processC") == + ProductResolverIndexAmbiguous); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC", "processQ") == ProductResolverIndexInvalid); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_int, "labelC", "instanceC") == ProductResolverIndexAmbiguous); + + TypeID typeID_vint(typeid(std::vector)); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC") == 0); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_vint, "labelC", "instanceC") == 0); //only one with no process + + TypeID typeID_sint(typeid(std::set)); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_sint, "labelC", "instanceC", "processC") == 13); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_sint, "labelC", "instanceC") == 13); //only one with no process + + TypeID typeID_Simple(typeid(edmtest::Simple)); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC") == 14); //only one with no process + REQUIRE(helper.index(ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC", "processC") == 14); + + TypeID typeID_SimpleDerived(typeid(edmtest::SimpleDerived)); + REQUIRE(helper.index(ELEMENT_TYPE, typeID_SimpleDerived, "labelC", "instanceC") == + 14); //only one with no process + REQUIRE(helper.index(ELEMENT_TYPE, typeID_SimpleDerived, "labelC", "instanceC", "processC") == 14); + + TypeID typeID_VSimpleDerived(typeid(std::vector)); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_VSimpleDerived, "labelC", "instanceC") == + 14); //only one with no process + REQUIRE(helper.index(PRODUCT_TYPE, typeID_VSimpleDerived, "labelC", "instanceC", "processC") == 14); + + auto matches = helper.relatedIndexes(PRODUCT_TYPE, typeID_EventID, "labelB", "instanceB"); + REQUIRE(matches.numberOfMatches() == 4 + 2); //4 process matches + 1 empty and 1 skip current process + ProductResolverIndex indexEmptyProcess = matches.index(0); + ProductResolverIndex indexSkipCurrentProcess = matches.index(1); + ProductResolverIndex indexB = matches.index(2); + ProductResolverIndex indexB1 = matches.index(3); + ProductResolverIndex indexB2 = matches.index(4); + ProductResolverIndex indexB3 = matches.index(5); + REQUIRE_THROWS_AS(matches.index(6), cms::Exception); + REQUIRE(indexEmptyProcess == 2); + REQUIRE(indexSkipCurrentProcess == 2); + REQUIRE(indexB == 2); + REQUIRE(indexB1 == 7); + REQUIRE(indexB2 == 9); + REQUIRE(indexB3 == 8); + + REQUIRE(std::string(matches.moduleLabel(5)) == "labelB"); + REQUIRE(std::string(matches.productInstanceName(5)) == "instanceB"); + REQUIRE(std::string(matches.processName(5)) == "processB3"); + REQUIRE(std::string(matches.processName(0)) == ""); + + { + auto indexToModules = helper.indiciesForModulesInProcess("processA"); + REQUIRE(indexToModules.size() == 1); + } + { + auto indexToModules = helper.indiciesForModulesInProcess("processB"); + REQUIRE(indexToModules.size() == 5); + } + { + auto indexToModules = helper.indiciesForModulesInProcess("processB1"); + REQUIRE(indexToModules.size() == 1); + } + { + auto indexToModules = helper.indiciesForModulesInProcess("processB2"); + REQUIRE(indexToModules.size() == 1); + } + { + auto indexToModules = helper.indiciesForModulesInProcess("processB3"); + REQUIRE(indexToModules.size() == 1); + } + { + auto indexToModules = helper.indiciesForModulesInProcess("processC"); + REQUIRE(indexToModules.size() == 3); + } } } } diff --git a/DataFormats/StdDictionaries/src/classes_def_others.xml b/DataFormats/StdDictionaries/src/classes_def_others.xml index 0af34d7f49dff..8f75efeb4b698 100644 --- a/DataFormats/StdDictionaries/src/classes_def_others.xml +++ b/DataFormats/StdDictionaries/src/classes_def_others.xml @@ -25,5 +25,5 @@ - + diff --git a/FWCore/Framework/interface/Principal.h b/FWCore/Framework/interface/Principal.h index bf8a9bc95dbe1..d6e508df2357d 100644 --- a/FWCore/Framework/interface/Principal.h +++ b/FWCore/Framework/interface/Principal.h @@ -118,14 +118,12 @@ namespace edm { BasicHandle getByToken(KindOfType kindOfType, TypeID const& typeID, ProductResolverIndex index, - bool skipCurrentProcess, bool& ambiguous, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const; void prefetchAsync(WaitingTaskHolder waitTask, ProductResolverIndex index, - bool skipCurrentProcess, ServiceToken const& token, ModuleCallingContext const* mcc) const; diff --git a/FWCore/Framework/interface/ProductResolverBase.h b/FWCore/Framework/interface/ProductResolverBase.h index 5a8bf81b502bc..bf2491498ee67 100644 --- a/FWCore/Framework/interface/ProductResolverBase.h +++ b/FWCore/Framework/interface/ProductResolverBase.h @@ -58,21 +58,19 @@ namespace edm { ProductResolverBase& operator=(ProductResolverBase const&) = delete; // Disallow copying and moving Resolution resolveProduct(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const { - return resolveProduct_(principal, skipCurrentProcess, sra, mcc); + return resolveProduct_(principal, sra, mcc); } /** oDataFetchedIsValid is allowed to be nullptr in which case no value will be assigned */ void prefetchAsync(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - return prefetchAsync_(waitTask, principal, skipCurrentProcess, token, sra, mcc); + return prefetchAsync_(waitTask, principal, token, sra, mcc); } void retrieveAndMerge(Principal const& principal, @@ -99,9 +97,7 @@ namespace edm { // Product was deleted early in order to save memory bool productWasDeleted() const { return productWasDeleted_(); } - bool productWasFetchedAndIsValid(bool iSkipCurrentProcess) const { - return productWasFetchedAndIsValid_(iSkipCurrentProcess); - } + bool productWasFetchedAndIsValid() const { return productWasFetchedAndIsValid_(); } // Retrieves pointer to the per event(lumi)(run) provenance. ProductProvenance const* productProvenancePtr() const { return productProvenancePtr_(); } @@ -164,12 +160,10 @@ namespace edm { private: virtual Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const = 0; virtual void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept = 0; @@ -181,7 +175,7 @@ namespace edm { virtual bool productUnavailable_() const = 0; virtual bool productResolved_() const = 0; virtual bool productWasDeleted_() const = 0; - virtual bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const = 0; + virtual bool productWasFetchedAndIsValid_() const = 0; virtual ProductDescription const& productDescription_() const = 0; virtual void resetProductDescription_(std::shared_ptr bd) = 0; diff --git a/FWCore/Framework/src/DroppedDataProductResolver.cc b/FWCore/Framework/src/DroppedDataProductResolver.cc index e085e13084da4..660aa7b5aa11d 100644 --- a/FWCore/Framework/src/DroppedDataProductResolver.cc +++ b/FWCore/Framework/src/DroppedDataProductResolver.cc @@ -6,15 +6,11 @@ namespace edm { DroppedDataProductResolver::Resolution DroppedDataProductResolver::resolveProduct_( - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const { + Principal const& principal, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const { return Resolution(nullptr); } void DroppedDataProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept {} diff --git a/FWCore/Framework/src/DroppedDataProductResolver.h b/FWCore/Framework/src/DroppedDataProductResolver.h index 7cfe977122b96..1b7de16e71ecd 100644 --- a/FWCore/Framework/src/DroppedDataProductResolver.h +++ b/FWCore/Framework/src/DroppedDataProductResolver.h @@ -19,12 +19,10 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const final; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept final; @@ -34,7 +32,7 @@ namespace edm { bool productUnavailable_() const final { return true; } bool productResolved_() const final { return true; } bool productWasDeleted_() const final { return false; } - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const final { return false; } + bool productWasFetchedAndIsValid_() const final { return false; } bool unscheduledWasNotRun_() const final { return false; } void resetProductData_(bool deleteEarly) final {} ProductDescription const& productDescription_() const final { return m_provenance.productDescription(); } diff --git a/FWCore/Framework/src/EDConsumerBase.cc b/FWCore/Framework/src/EDConsumerBase.cc index 1e67d17d57792..ae763182b3d56 100644 --- a/FWCore/Framework/src/EDConsumerBase.cc +++ b/FWCore/Framework/src/EDConsumerBase.cc @@ -127,12 +127,14 @@ void EDConsumerBase::updateLookup(BranchType iBranchType, if (itInfo->m_branchType == iBranchType) { const unsigned int labelStart = itLabels->m_startOfModuleLabel; const char* moduleLabel = &(m_tokenLabels[labelStart]); - itInfo->m_index = ProductResolverIndexAndSkipBit(iHelper.index(*itKind, - itInfo->m_type, - moduleLabel, - moduleLabel + itLabels->m_deltaToProductInstance, - moduleLabel + itLabels->m_deltaToProcessName), - itInfo->m_index.skipCurrentProcess()); + const char* processName = moduleLabel + itLabels->m_deltaToProcessName; + if (itInfo->m_index.skipCurrentProcess()) { + processName = "#"; + } + itInfo->m_index = ProductResolverIndexAndSkipBit( + iHelper.index( + *itKind, itInfo->m_type, moduleLabel, moduleLabel + itLabels->m_deltaToProductInstance, processName), + itInfo->m_index.skipCurrentProcess()); } } } @@ -268,7 +270,7 @@ ProductResolverIndexAndSkipBit EDConsumerBase::indexFromIfExactMatch(EDGetToken return info.m_index; } } - return ProductResolverIndexAndSkipBit(edm::ProductResolverIndexInvalid, false); + return ProductResolverIndexAndSkipBit(edm::ProductResolverIndexInitializing, false); } EDGetToken EDConsumerBase::getRegisteredToken(TypeID const& typeID, diff --git a/FWCore/Framework/src/EDLooperBase.cc b/FWCore/Framework/src/EDLooperBase.cc index 940aeede76b99..b1df0377c6b38 100644 --- a/FWCore/Framework/src/EDLooperBase.cc +++ b/FWCore/Framework/src/EDLooperBase.cc @@ -201,9 +201,8 @@ namespace edm { for (auto const& item : items) { ProductResolverIndex productResolverIndex = item.productResolverIndex(); - bool skipCurrentProcess = item.skipCurrentProcess(); if (productResolverIndex != ProductResolverIndexAmbiguous) { - iPrincipal.prefetchAsync(iTask, productResolverIndex, skipCurrentProcess, token, &moduleCallingContext_); + iPrincipal.prefetchAsync(iTask, productResolverIndex, token, &moduleCallingContext_); } } } diff --git a/FWCore/Framework/src/EventForTransformer.cc b/FWCore/Framework/src/EventForTransformer.cc index ca836f9d01fe1..0760c9604cfb2 100644 --- a/FWCore/Framework/src/EventForTransformer.cc +++ b/FWCore/Framework/src/EventForTransformer.cc @@ -16,7 +16,7 @@ namespace edm { BasicHandle EventForTransformer::get(edm::TypeID const& iTypeID, ProductResolverIndex iIndex) const { bool amb = false; - return eventPrincipal_.getByToken(PRODUCT_TYPE, iTypeID, iIndex, false, amb, nullptr, &mcc_); + return eventPrincipal_.getByToken(PRODUCT_TYPE, iTypeID, iIndex, amb, nullptr, &mcc_); } void EventForTransformer::put(ProductResolverIndex index, diff --git a/FWCore/Framework/src/EventPrincipal.cc b/FWCore/Framework/src/EventPrincipal.cc index 5f911d0c2ebf8..b97b8c64f4163 100644 --- a/FWCore/Framework/src/EventPrincipal.cc +++ b/FWCore/Framework/src/EventPrincipal.cc @@ -283,7 +283,7 @@ namespace edm { return whyFailed; })); } - auto resolution = phb->resolveProduct(*this, false, nullptr, nullptr); + auto resolution = phb->resolveProduct(*this, nullptr, nullptr); auto data = resolution.data(); if (data) { @@ -370,7 +370,7 @@ namespace edm { << "EventPrincipal::getThinnedAssociation, ThinnedAssociation ProductResolver cannot be found\n" << "This should never happen. Contact a Framework developer"; } - ProductData const* productData = (phb->resolveProduct(*this, false, nullptr, nullptr)).data(); + ProductData const* productData = (phb->resolveProduct(*this, nullptr, nullptr)).data(); if (productData == nullptr) { return nullptr; } diff --git a/FWCore/Framework/src/EventProcessor.cc b/FWCore/Framework/src/EventProcessor.cc index a105406005f50..221fcc035514c 100644 --- a/FWCore/Framework/src/EventProcessor.cc +++ b/FWCore/Framework/src/EventProcessor.cc @@ -1615,8 +1615,7 @@ namespace edm { for (auto const& item : items) { ProductResolverIndex productResolverIndex = item.productResolverIndex(); - bool skipCurrentProcess = item.skipCurrentProcess(); - iPrincipal.prefetchAsync(iTask, productResolverIndex, skipCurrentProcess, iServiceToken, nullptr); + iPrincipal.prefetchAsync(iTask, productResolverIndex, iServiceToken, nullptr); } } } diff --git a/FWCore/Framework/src/Principal.cc b/FWCore/Framework/src/Principal.cc index 4b10a540b69dc..bda15eef94cab 100644 --- a/FWCore/Framework/src/Principal.cc +++ b/FWCore/Framework/src/Principal.cc @@ -142,8 +142,8 @@ namespace edm { size_t Principal::size() const { size_t size = 0U; for (auto const& prod : *this) { - if (prod->singleProduct() && // Not a NoProcessProductResolver - !prod->productUnavailable() && !prod->unscheduledWasNotRun() && !prod->productDescription().dropped()) { + if (prod->singleProduct() && !prod->productUnavailable() && !prod->unscheduledWasNotRun() && + !prod->productDescription().dropped()) { ++size; } } @@ -409,14 +409,13 @@ namespace edm { BasicHandle Principal::getByToken(KindOfType, TypeID const&, ProductResolverIndex index, - bool skipCurrentProcess, bool& ambiguous, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const { assert(index != ProductResolverIndexInvalid); auto& productResolver = productResolvers_[index]; assert(nullptr != productResolver.get()); - auto resolution = productResolver->resolveProduct(*this, skipCurrentProcess, sra, mcc); + auto resolution = productResolver->resolveProduct(*this, sra, mcc); if (resolution.isAmbiguous()) { ambiguous = true; //The caller is looking explicitly for this case @@ -434,12 +433,11 @@ namespace edm { void Principal::prefetchAsync(WaitingTaskHolder task, ProductResolverIndex index, - bool skipCurrentProcess, ServiceToken const& token, ModuleCallingContext const* mcc) const { auto const& productResolver = productResolvers_.at(index); assert(nullptr != productResolver.get()); - productResolver->prefetchAsync(task, *this, skipCurrentProcess, token, nullptr, mcc); + productResolver->prefetchAsync(task, *this, token, nullptr, mcc); } ProductData const* Principal::findProductByLabel(KindOfType kindOfType, @@ -459,6 +457,10 @@ namespace edm { if (inputTag.process() == InputTag::kCurrentProcess) { processName = &processConfiguration_->processName(); } + std::string const kSkipCurrentProcess = "#"; + if (skipCurrentProcess) { + processName = &kSkipCurrentProcess; + } token = consumer->getRegisteredToken( typeID, inputTag.label(), inputTag.instance(), *processName, branchType(), skipCurrentProcess); if (token.isUninitialized()) { @@ -472,11 +474,14 @@ namespace edm { } //check that the InputTag is not being used for a different type/Principal than the first call auto index = consumer ? consumer->indexFromIfExactMatch(token, branchType(), typeID).productResolverIndex() - : ProductResolverIndexInvalid; + : ProductResolverIndexInitializing; if (index == ProductResolverIndexInvalid) { + return nullptr; + } + if (index == ProductResolverIndexInitializing) { char const* processName = inputTag.process().c_str(); if (skipCurrentProcess) { - processName = "\0"; + processName = "#"; } else if (inputTag.process() == InputTag::kCurrentProcess) { processName = processConfiguration_->processName().c_str(); } @@ -514,7 +519,7 @@ namespace edm { auto const& productResolver = productResolvers_[index]; - auto resolution = productResolver->resolveProduct(*this, skipCurrentProcess, sra, mcc); + auto resolution = productResolver->resolveProduct(*this, sra, mcc); if (resolution.isAmbiguous()) { throwAmbiguousException("findProductByLabel", typeID, @@ -558,7 +563,7 @@ namespace edm { auto const& productResolver = productResolvers_[index]; - auto resolution = productResolver->resolveProduct(*this, false, sra, mcc); + auto resolution = productResolver->resolveProduct(*this, sra, mcc); if (resolution.isAmbiguous()) { throwAmbiguousException("findProductByLabel", typeID, label, instance, process); } diff --git a/FWCore/Framework/src/PrincipalGetAdapter.cc b/FWCore/Framework/src/PrincipalGetAdapter.cc index b83afb5df8468..b5154e9f7fe1b 100644 --- a/FWCore/Framework/src/PrincipalGetAdapter.cc +++ b/FWCore/Framework/src/PrincipalGetAdapter.cc @@ -147,7 +147,6 @@ namespace edm { ModuleCallingContext const* mcc) const { ProductResolverIndexAndSkipBit indexAndBit = consumer_->indexFrom(token, branchType(), id); ProductResolverIndex index = indexAndBit.productResolverIndex(); - bool skipCurrentProcess = indexAndBit.skipCurrentProcess(); if (UNLIKELY(index == ProductResolverIndexInvalid)) { return makeFailToGetException(kindOfType, id, token); } else if (UNLIKELY(index == ProductResolverIndexAmbiguous)) { @@ -155,8 +154,7 @@ namespace edm { throwAmbiguousException(id, token); } bool ambiguous = false; - BasicHandle h = - principal_.getByToken(kindOfType, id, index, skipCurrentProcess, ambiguous, resourcesAcquirer_, mcc); + BasicHandle h = principal_.getByToken(kindOfType, id, index, ambiguous, resourcesAcquirer_, mcc); if (ambiguous) { // This deals with ambiguities where the process is not specified throwAmbiguousException(id, token); diff --git a/FWCore/Framework/src/ProductResolvers.cc b/FWCore/Framework/src/ProductResolvers.cc index 0ce78d9a2ed59..7b3a0d28ace97 100644 --- a/FWCore/Framework/src/ProductResolvers.cc +++ b/FWCore/Framework/src/ProductResolvers.cc @@ -170,7 +170,7 @@ namespace edm { } } // namespace ProductResolverBase::Resolution DelayedReaderInputProductResolver::resolveProduct_( - Principal const& principal, bool, SharedResourcesAcquirer*, ModuleCallingContext const* mcc) const { + Principal const& principal, SharedResourcesAcquirer*, ModuleCallingContext const* mcc) const { return resolveProductImpl([this, &principal, mcc]() { auto branchType = principal.branchType(); if (branchType == InLumi || branchType == InRun) { @@ -276,7 +276,6 @@ namespace edm { void DelayedReaderInputProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { @@ -368,7 +367,6 @@ namespace edm { bool PutOnReadInputProductResolver::isFromCurrentProcess() const { return false; } ProductResolverBase::Resolution PutOnReadInputProductResolver::resolveProduct_(Principal const&, - bool skipCurrentProcess, SharedResourcesAcquirer*, ModuleCallingContext const*) const { return resolveProductImpl([]() { return; }); @@ -376,7 +374,6 @@ namespace edm { void PutOnReadInputProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept {} @@ -386,42 +383,34 @@ namespace edm { } ProductResolverBase::Resolution PuttableProductResolver::resolveProduct_(Principal const&, - bool skipCurrentProcess, SharedResourcesAcquirer*, ModuleCallingContext const*) const { - if (!skipCurrentProcess) { - //'false' means never call the lambda function - return resolveProductImpl([]() { return; }); - } - return Resolution(nullptr); + return resolveProductImpl([]() { return; }); } void PuttableProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - if (not skipCurrentProcess) { - if (productDescription().branchType() == InProcess && - mcc->parent().globalContext()->transition() == GlobalContext::Transition::kAccessInputProcessBlock) { - // This is an accessInputProcessBlock transition - // We cannot access produced products in those transitions. + if (productDescription().branchType() == InProcess && + mcc->parent().globalContext()->transition() == GlobalContext::Transition::kAccessInputProcessBlock) { + // This is an accessInputProcessBlock transition + // We cannot access produced products in those transitions. + return; + } + if (productDescription().availableOnlyAtEndTransition() and mcc) { + if (not mcc->parent().isAtEndTransition()) { return; } - if (productDescription().availableOnlyAtEndTransition() and mcc) { - if (not mcc->parent().isAtEndTransition()) { - return; - } - } + } - if (waitingTasks_) { - // using a waiting task to do a callback guarantees that the - // waitingTasks_ list (from the worker) will be released from - // waiting even if the module does not put this data product - // or the module has an exception while running - waitingTasks_->add(waitTask); - } + if (waitingTasks_) { + // using a waiting task to do a callback guarantees that the + // waitingTasks_ list (from the worker) will be released from + // waiting even if the module does not put this data product + // or the module has an exception while running + waitingTasks_->add(waitTask); } } @@ -438,10 +427,9 @@ namespace edm { } ProductResolverBase::Resolution UnscheduledProductResolver::resolveProduct_(Principal const&, - bool skipCurrentProcess, SharedResourcesAcquirer*, ModuleCallingContext const*) const { - if (!skipCurrentProcess and worker_) { + if (worker_) { return resolveProductImpl([] {}); } return Resolution(nullptr); @@ -449,13 +437,9 @@ namespace edm { void UnscheduledProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - if (skipCurrentProcess) { - return; - } assert(worker_); //need to try changing prefetchRequested_ before adding to waitingTasks_ bool expected = false; @@ -512,10 +496,9 @@ namespace edm { } ProductResolverBase::Resolution TransformingProductResolver::resolveProduct_(Principal const&, - bool skipCurrentProcess, SharedResourcesAcquirer*, ModuleCallingContext const*) const { - if (!skipCurrentProcess and worker_) { + if (worker_) { return resolveProductImpl([] {}); } return Resolution(nullptr); @@ -534,13 +517,9 @@ namespace edm { void TransformingProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - if (skipCurrentProcess) { - return; - } assert(worker_ != nullptr); //need to try changing prefetchRequested_ before adding to waitingTasks_ bool expected = false; @@ -653,10 +632,7 @@ namespace edm { // This routine returns true if the product was deleted early in order to save memory bool DataManagingProductResolver::productWasDeleted_() const { return status() == ProductStatus::ProductDeleted; } - bool DataManagingProductResolver::productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const { - if (iSkipCurrentProcess and isFromCurrentProcess()) { - return false; - } + bool DataManagingProductResolver::productWasFetchedAndIsValid_() const { if (status() == ProductStatus::ProductSet) { if (getProductData().wrapper()->isPresent()) { return true; @@ -770,25 +746,19 @@ namespace edm { DataManagingOrAliasProductResolver& realProduct) : SwitchBaseProductResolver(std::move(bd), realProduct), status_(defaultStatus_) {} - ProductResolverBase::Resolution SwitchProducerProductResolver::resolveProduct_(Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const { + ProductResolverBase::Resolution SwitchProducerProductResolver::resolveProduct_( + Principal const& principal, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const { if (status_ == ProductStatus::ResolveFailed) { - return resolveProductImpl(realProduct().resolveProduct(principal, skipCurrentProcess, sra, mcc)); + return resolveProductImpl(realProduct().resolveProduct(principal, sra, mcc)); } return Resolution(nullptr); } void SwitchProducerProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - if (skipCurrentProcess) { - return; - } if (productDescription().availableOnlyAtEndTransition() and mcc and not mcc->parent().isAtEndTransition()) { return; } @@ -847,22 +817,16 @@ namespace edm { } ProductResolverBase::Resolution SwitchAliasProductResolver::resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const { - return resolveProductImpl(realProduct().resolveProduct(principal, skipCurrentProcess, sra, mcc)); + return resolveProductImpl(realProduct().resolveProduct(principal, sra, mcc)); } void SwitchAliasProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept { - if (skipCurrentProcess) { - return; - } - //need to try changing prefetchRequested_ before adding to waitingTasks_ bool expected = false; bool doPrefetchRequested = prefetchRequested().compare_exchange_strong(expected, true); @@ -881,402 +845,7 @@ namespace edm { waitingTasks().doneWaiting(std::exception_ptr()); } }); - realProduct().prefetchAsync( - WaitingTaskHolder(*waitTask.group(), waiting), principal, skipCurrentProcess, token, sra, mcc); - } - } - - NoProcessProductResolver::NoProcessProductResolver(std::vector const& matchingHolders, - std::vector const& ambiguous, - bool madeAtEnd) - : matchingHolders_(matchingHolders), - ambiguous_(ambiguous), - lastCheckIndex_(ambiguous_.size() + kUnsetOffset), - lastSkipCurrentCheckIndex_(lastCheckIndex_.load()), - prefetchRequested_(false), - skippingPrefetchRequested_(false), - madeAtEnd_{madeAtEnd} { - assert(ambiguous_.size() == matchingHolders_.size()); - } - - ProductResolverBase::Resolution NoProcessProductResolver::tryResolver(unsigned int index, - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const { - ProductResolverBase const* productResolver = principal.getProductResolverByIndex(matchingHolders_[index]); - return productResolver->resolveProduct(principal, skipCurrentProcess, sra, mcc); - } - - ProductResolverBase::Resolution NoProcessProductResolver::resolveProduct_(Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const { - //See if we've already cached which Resolver we should call or if - // we know it is ambiguous - const unsigned int choiceSize = ambiguous_.size(); - - //madeAtEnd_==true and not at end transition is the same as skipping the current process - if ((not skipCurrentProcess) and (madeAtEnd_ and mcc)) { - skipCurrentProcess = not mcc->parent().isAtEndTransition(); - } - - unsigned int checkCacheIndex = skipCurrentProcess ? lastSkipCurrentCheckIndex_.load() : lastCheckIndex_.load(); - if (checkCacheIndex != choiceSize + kUnsetOffset) { - if (checkCacheIndex == choiceSize + kAmbiguousOffset) { - return ProductResolverBase::Resolution::makeAmbiguous(); - } else if (checkCacheIndex == choiceSize + kMissingOffset) { - return Resolution(nullptr); - } - return tryResolver(checkCacheIndex, principal, skipCurrentProcess, sra, mcc); - } - - std::atomic& updateCacheIndex = skipCurrentProcess ? lastSkipCurrentCheckIndex_ : lastCheckIndex_; - - std::vector const& lookupProcessOrder = principal.lookupProcessOrder(); - for (unsigned int k : lookupProcessOrder) { - assert(k < ambiguous_.size()); - if (k == 0) - break; // Done - if (ambiguous_[k]) { - updateCacheIndex = choiceSize + kAmbiguousOffset; - return ProductResolverBase::Resolution::makeAmbiguous(); - } - if (matchingHolders_[k] != ProductResolverIndexInvalid) { - auto resolution = tryResolver(k, principal, skipCurrentProcess, sra, mcc); - if (resolution.data() != nullptr) { - updateCacheIndex = k; - return resolution; - } - } - } - - updateCacheIndex = choiceSize + kMissingOffset; - return Resolution(nullptr); - } - - void NoProcessProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, - Principal const& principal, - bool skipCurrentProcess, - ServiceToken const& token, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const noexcept { - bool timeToMakeAtEnd = true; - if (madeAtEnd_ and mcc) { - timeToMakeAtEnd = mcc->parent().isAtEndTransition(); + realProduct().prefetchAsync(WaitingTaskHolder(*waitTask.group(), waiting), principal, token, sra, mcc); } - - //If timeToMakeAtEnd is false, then it is equivalent to skipping the current process - if (not skipCurrentProcess and timeToMakeAtEnd) { - //need to try changing prefetchRequested_ before adding to waitingTasks_ - bool expected = false; - bool prefetchRequested = prefetchRequested_.compare_exchange_strong(expected, true); - waitingTasks_.add(waitTask); - - if (prefetchRequested) { - //we are the first thread to request - tryPrefetchResolverAsync(0, principal, false, sra, mcc, token, waitTask.group()); - } - } else { - skippingWaitingTasks_.add(waitTask); - bool expected = false; - if (skippingPrefetchRequested_.compare_exchange_strong(expected, true)) { - bool producesInCurrentProcess = principal.productLookup().producesInCurrentProcess() and skipCurrentProcess; - auto startIndex = producesInCurrentProcess ? 1U : 0U; - //we are the first thread to request - tryPrefetchResolverAsync(startIndex, principal, true, sra, mcc, token, waitTask.group()); - } - } - } - - void NoProcessProductResolver::setCache(bool iSkipCurrentProcess, - ProductResolverIndex iIndex, - std::exception_ptr iExceptPtr) const { - if (not iSkipCurrentProcess) { - lastCheckIndex_ = iIndex; - waitingTasks_.doneWaiting(iExceptPtr); - } else { - lastSkipCurrentCheckIndex_ = iIndex; - skippingWaitingTasks_.doneWaiting(iExceptPtr); - } - } - - namespace { - class TryNextResolverWaitingTask : public edm::WaitingTask { - public: - TryNextResolverWaitingTask(NoProcessProductResolver const* iResolver, - unsigned int iResolverIndex, - Principal const* iPrincipal, - SharedResourcesAcquirer* iSRA, - ModuleCallingContext const* iMCC, - bool iSkipCurrentProcess, - ServiceToken iToken, - oneapi::tbb::task_group* iGroup) noexcept - : resolver_(iResolver), - principal_(iPrincipal), - sra_(iSRA), - mcc_(iMCC), - group_(iGroup), - serviceToken_(iToken), - index_(iResolverIndex), - skipCurrentProcess_(iSkipCurrentProcess) {} - - void execute() final { - auto exceptPtr = exceptionPtr(); - if (exceptPtr) { - resolver_->prefetchFailed(index_, *principal_, skipCurrentProcess_, exceptPtr); - } else { - if (not resolver_->dataValidFromResolver(index_, *principal_, skipCurrentProcess_)) { - resolver_->tryPrefetchResolverAsync( - index_ + 1, *principal_, skipCurrentProcess_, sra_, mcc_, serviceToken_.lock(), group_); - } - } - } - - private: - NoProcessProductResolver const* resolver_; - Principal const* principal_; - SharedResourcesAcquirer* sra_; - ModuleCallingContext const* mcc_; - oneapi::tbb::task_group* group_; - ServiceWeakToken serviceToken_; - unsigned int index_; - bool skipCurrentProcess_; - }; - } // namespace - - void NoProcessProductResolver::prefetchFailed(unsigned int iProcessingIndex, - Principal const& principal, - bool iSkipCurrentProcess, - std::exception_ptr iExceptPtr) const { - std::vector const& lookupProcessOrder = principal.lookupProcessOrder(); - auto k = lookupProcessOrder[iProcessingIndex]; - - setCache(iSkipCurrentProcess, k, iExceptPtr); - } - - bool NoProcessProductResolver::dataValidFromResolver(unsigned int iProcessingIndex, - Principal const& principal, - bool iSkipCurrentProcess) const { - std::vector const& lookupProcessOrder = principal.lookupProcessOrder(); - auto k = lookupProcessOrder[iProcessingIndex]; - ProductResolverBase const* productResolver = principal.getProductResolverByIndex(matchingHolders_[k]); - - if (productResolver->productWasFetchedAndIsValid(iSkipCurrentProcess)) { - setCache(iSkipCurrentProcess, k, nullptr); - return true; - } - return false; - } - - void NoProcessProductResolver::tryPrefetchResolverAsync(unsigned int iProcessingIndex, - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc, - ServiceToken token, - oneapi::tbb::task_group* group) const noexcept { - std::vector const& lookupProcessOrder = principal.lookupProcessOrder(); - auto index = iProcessingIndex; - - const unsigned int choiceSize = ambiguous_.size(); - unsigned int newCacheIndex = choiceSize + kMissingOffset; - while (index < lookupProcessOrder.size()) { - auto k = lookupProcessOrder[index]; - if (k == 0) { - break; - } - assert(k < ambiguous_.size()); - if (ambiguous_[k]) { - newCacheIndex = choiceSize + kAmbiguousOffset; - break; - } - if (matchingHolders_[k] != ProductResolverIndexInvalid) { - //make new task - - auto task = new TryNextResolverWaitingTask(this, index, &principal, sra, mcc, skipCurrentProcess, token, group); - WaitingTaskHolder hTask(*group, task); - ProductResolverBase const* productResolver = principal.getProductResolverByIndex(matchingHolders_[k]); - - //Make sure the Services are available on this thread - ServiceRegistry::Operate guard(token); - - productResolver->prefetchAsync(hTask, principal, skipCurrentProcess, token, sra, mcc); - return; - } - ++index; - } - //data product unavailable - setCache(skipCurrentProcess, newCacheIndex, nullptr); - } - - void NoProcessProductResolver::setProductProvenanceRetriever_(ProductProvenanceRetriever const*) {} - - void NoProcessProductResolver::setProductID_(ProductID const&) {} - - ProductProvenance const* NoProcessProductResolver::productProvenancePtr_() const { return nullptr; } - - inline unsigned int NoProcessProductResolver::unsetIndexValue() const { return ambiguous_.size() + kUnsetOffset; } - - void NoProcessProductResolver::resetProductData_(bool) { - // This function should never receive 'true'. On the other hand, - // nothing should break if a 'true' is passed, because - // NoProcessProductResolver just forwards the resolve - const auto resetValue = unsetIndexValue(); - lastCheckIndex_ = resetValue; - lastSkipCurrentCheckIndex_ = resetValue; - prefetchRequested_ = false; - skippingPrefetchRequested_ = false; - waitingTasks_.reset(); - skippingWaitingTasks_.reset(); - } - - bool NoProcessProductResolver::singleProduct_() const { return false; } - - bool NoProcessProductResolver::unscheduledWasNotRun_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::unscheduledWasNotRun_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool NoProcessProductResolver::productUnavailable_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::productUnavailable_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool NoProcessProductResolver::productResolved_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::productResolved_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool NoProcessProductResolver::productWasDeleted_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::productWasDeleted_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool NoProcessProductResolver::productWasFetchedAndIsValid_(bool /*iSkipCurrentProcess*/) const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::productWasFetchedAndIsValid_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - ProductDescription const& NoProcessProductResolver::productDescription_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::productDescription_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - void NoProcessProductResolver::resetProductDescription_(std::shared_ptr) { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::resetProductDescription_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - Provenance const* NoProcessProductResolver::provenance_() const { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::provenance_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - void NoProcessProductResolver::connectTo(ProductResolverBase const&, Principal const*) { - throw Exception(errors::LogicError) - << "NoProcessProductResolver::connectTo() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - //---- SingleChoiceNoProcessProductResolver ---------------- - ProductResolverBase::Resolution SingleChoiceNoProcessProductResolver::resolveProduct_( - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const { - //In future changes this class will be removed. Although the class is still being instantiated, it should never be called. - // For now the assert is here to catch any missed cases. - assert(false); - //NOTE: Have to lookup the other ProductResolver each time rather than cache - // it's pointer since it appears the pointer can change at some later stage - return principal.getProductResolverByIndex(realResolverIndex_) - ->resolveProduct(principal, skipCurrentProcess, sra, mcc); - } - - void SingleChoiceNoProcessProductResolver::prefetchAsync_(WaitingTaskHolder waitTask, - Principal const& principal, - bool skipCurrentProcess, - ServiceToken const& token, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const noexcept { - //In future changes this class will be removed. Although the class is still being instantiated, it should never be called. - // For now the assert is here to catch any missed cases. - assert(false); - principal.getProductResolverByIndex(realResolverIndex_) - ->prefetchAsync(waitTask, principal, skipCurrentProcess, token, sra, mcc); } - - void SingleChoiceNoProcessProductResolver::setProductProvenanceRetriever_(ProductProvenanceRetriever const*) {} - - void SingleChoiceNoProcessProductResolver::setProductID_(ProductID const&) {} - - ProductProvenance const* SingleChoiceNoProcessProductResolver::productProvenancePtr_() const { return nullptr; } - - void SingleChoiceNoProcessProductResolver::resetProductData_(bool) {} - - bool SingleChoiceNoProcessProductResolver::singleProduct_() const { return false; } - - bool SingleChoiceNoProcessProductResolver::unscheduledWasNotRun_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::unscheduledWasNotRun_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool SingleChoiceNoProcessProductResolver::productUnavailable_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::productUnavailable_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool SingleChoiceNoProcessProductResolver::productResolved_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::productResolved_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool SingleChoiceNoProcessProductResolver::productWasDeleted_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::productWasDeleted_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - bool SingleChoiceNoProcessProductResolver::productWasFetchedAndIsValid_(bool /*iSkipCurrentProcess*/) const { - throw Exception(errors::LogicError) << "SingleChoiceNoProcessProductResolver::productWasFetchedAndIsValid_() not " - "implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - ProductDescription const& SingleChoiceNoProcessProductResolver::productDescription_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::productDescription_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - void SingleChoiceNoProcessProductResolver::resetProductDescription_(std::shared_ptr) { - throw Exception(errors::LogicError) << "SingleChoiceNoProcessProductResolver::resetProductDescription_() not " - "implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - Provenance const* SingleChoiceNoProcessProductResolver::provenance_() const { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::provenance_() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - - void SingleChoiceNoProcessProductResolver::connectTo(ProductResolverBase const&, Principal const*) { - throw Exception(errors::LogicError) - << "SingleChoiceNoProcessProductResolver::connectTo() not implemented and should never be called.\n" - << "Contact a Framework developer\n"; - } - } // namespace edm diff --git a/FWCore/Framework/src/ProductResolvers.h b/FWCore/Framework/src/ProductResolvers.h index eee108aef75df..8f34282cf0dc4 100644 --- a/FWCore/Framework/src/ProductResolvers.h +++ b/FWCore/Framework/src/ProductResolvers.h @@ -84,7 +84,7 @@ namespace edm { bool productUnavailable_() const final; bool productResolved_() const final; bool productWasDeleted_() const final; - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const final; + bool productWasFetchedAndIsValid_() const final; ProductDescription const& productDescription_() const final { return *getProductData().productDescription(); } void resetProductDescription_(std::shared_ptr bd) final { @@ -130,12 +130,10 @@ namespace edm { bool isFromCurrentProcess() const final; Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const override; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept override; @@ -169,12 +167,10 @@ namespace edm { void putOrMergeProduct(std::unique_ptr prod) const override; Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const final; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept final; @@ -207,12 +203,10 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const override; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept override; @@ -235,12 +229,10 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const override; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept override; @@ -264,12 +256,10 @@ namespace edm { private: void putProduct(std::unique_ptr edp) const override; Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const override; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept override; @@ -298,26 +288,22 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const override { - return realProduct_.resolveProduct(principal, skipCurrentProcess, sra, mcc); + return realProduct_.resolveProduct(principal, sra, mcc); } void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept override { - realProduct_.prefetchAsync(waitTask, principal, skipCurrentProcess, token, sra, mcc); + realProduct_.prefetchAsync(waitTask, principal, token, sra, mcc); } bool unscheduledWasNotRun_() const override { return realProduct_.unscheduledWasNotRun(); } bool productUnavailable_() const override { return realProduct_.productUnavailable(); } bool productResolved_() const final { return realProduct_.productResolved(); } bool productWasDeleted_() const override { return realProduct_.productWasDeleted(); } - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const final { - return realProduct_.productWasFetchedAndIsValid(iSkipCurrentProcess); - } + bool productWasFetchedAndIsValid_() const final { return realProduct_.productWasFetchedAndIsValid(); } ProductDescription const& productDescription_() const override { return *bd_; } void resetProductDescription_(std::shared_ptr bd) override { bd_ = bd; } @@ -357,9 +343,7 @@ namespace edm { private: bool productResolved_() const final; bool productWasDeleted_() const final { return realProduct_.productWasDeleted(); } - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const final { - return realProduct_.productWasFetchedAndIsValid(iSkipCurrentProcess); - } + bool productWasFetchedAndIsValid_() const final { return realProduct_.productWasFetchedAndIsValid(); } ProductDescription const& productDescription_() const final { return *productData_.productDescription(); ; @@ -394,12 +378,10 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const final; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept final; @@ -425,12 +407,10 @@ namespace edm { private: Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const final; void prefetchAsync_(WaitingTaskHolder waitTask, Principal const& principal, - bool skipCurrentProcess, ServiceToken const& token, SharedResourcesAcquirer* sra, ModuleCallingContext const* mcc) const noexcept final; @@ -438,119 +418,6 @@ namespace edm { bool productUnavailable_() const final { return realProduct().productUnavailable(); } }; - class NoProcessProductResolver : public ProductResolverBase { - public: - typedef ProducedProductResolver::ProductStatus ProductStatus; - NoProcessProductResolver(std::vector const& matchingHolders, - std::vector const& ambiguous, - bool madeAtEnd); - - void connectTo(ProductResolverBase const& iOther, Principal const*) final; - - void tryPrefetchResolverAsync(unsigned int iProcessingIndex, - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc, - ServiceToken token, - oneapi::tbb::task_group*) const noexcept; - - bool dataValidFromResolver(unsigned int iProcessingIndex, - Principal const& principal, - bool iSkipCurrentProcess) const; - - void prefetchFailed(unsigned int iProcessingIndex, - Principal const& principal, - bool iSkipCurrentProcess, - std::exception_ptr iExceptPtr) const; - - private: - unsigned int unsetIndexValue() const; - Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const override; - void prefetchAsync_(WaitingTaskHolder waitTask, - Principal const& principal, - bool skipCurrentProcess, - ServiceToken const& token, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const noexcept override; - bool unscheduledWasNotRun_() const override; - bool productUnavailable_() const override; - bool productWasDeleted_() const override; - bool productResolved_() const final; - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const override; - - ProductDescription const& productDescription_() const override; - void resetProductDescription_(std::shared_ptr bd) override; - Provenance const* provenance_() const override; - - std::string const& resolvedModuleLabel_() const override { return moduleLabel(); } - void setProductProvenanceRetriever_(ProductProvenanceRetriever const* provRetriever) override; - void setProductID_(ProductID const& pid) override; - ProductProvenance const* productProvenancePtr_() const override; - void resetProductData_(bool deleteEarly) override; - bool singleProduct_() const override; - - Resolution tryResolver(unsigned int index, - Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const; - - void setCache(bool skipCurrentProcess, ProductResolverIndex index, std::exception_ptr exceptionPtr) const; - - std::vector matchingHolders_; - std::vector ambiguous_; - CMS_THREAD_SAFE mutable WaitingTaskList waitingTasks_; - CMS_THREAD_SAFE mutable WaitingTaskList skippingWaitingTasks_; - mutable std::atomic lastCheckIndex_; - mutable std::atomic lastSkipCurrentCheckIndex_; - mutable std::atomic prefetchRequested_; - mutable std::atomic skippingPrefetchRequested_; - const bool madeAtEnd_; - }; - - class SingleChoiceNoProcessProductResolver : public ProductResolverBase { - public: - typedef ProducedProductResolver::ProductStatus ProductStatus; - SingleChoiceNoProcessProductResolver(ProductResolverIndex iChoice) - : ProductResolverBase(), realResolverIndex_(iChoice) {} - - void connectTo(ProductResolverBase const& iOther, Principal const*) final; - - private: - Resolution resolveProduct_(Principal const& principal, - bool skipCurrentProcess, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const override; - void prefetchAsync_(WaitingTaskHolder waitTask, - Principal const& principal, - bool skipCurrentProcess, - ServiceToken const& token, - SharedResourcesAcquirer* sra, - ModuleCallingContext const* mcc) const noexcept override; - bool unscheduledWasNotRun_() const override; - bool productUnavailable_() const override; - bool productWasDeleted_() const override; - bool productResolved_() const final; - bool productWasFetchedAndIsValid_(bool iSkipCurrentProcess) const override; - - ProductDescription const& productDescription_() const override; - void resetProductDescription_(std::shared_ptr bd) override; - Provenance const* provenance_() const override; - - std::string const& resolvedModuleLabel_() const override { return moduleLabel(); } - void setProductProvenanceRetriever_(ProductProvenanceRetriever const* provRetriever) override; - void setProductID_(ProductID const& pid) override; - ProductProvenance const* productProvenancePtr_() const override; - void resetProductData_(bool deleteEarly) override; - bool singleProduct_() const override; - - ProductResolverIndex realResolverIndex_; - }; - } // namespace edm #endif diff --git a/FWCore/Framework/src/ProductResolversFactory.cc b/FWCore/Framework/src/ProductResolversFactory.cc index 5ca053e90046c..c290256a715d7 100644 --- a/FWCore/Framework/src/ProductResolversFactory.cc +++ b/FWCore/Framework/src/ProductResolversFactory.cc @@ -109,85 +109,6 @@ namespace edm::productResolversFactory { } return makePutOnReadInputProduct(cbd); } - bool isProductMadeAtEnd(edm::BranchIDList const& matchingHolders, - std::vector const& ambiguous, - std::vector> const& productResolvers) { - for (unsigned int j = 0; j < matchingHolders.size(); ++j) { - if ((not ambiguous[j]) and ProductResolverIndexInvalid != matchingHolders[j] and - productResolvers[matchingHolders[j]]->productDescription().availableOnlyAtEndTransition()) { - return true; - } - } - return false; - } - std::shared_ptr makeNoProcess( - unsigned int numberOfMatches, - ProductResolverIndex lastMatchIndex, - edm::BranchIDList const& matchingHolders, - std::vector const& ambiguous, - std::vector> const& productResolvers) { - if ((numberOfMatches == 1) and (lastMatchIndex != ProductResolverIndexAmbiguous)) { - //only one choice so use a special resolver - return std::make_shared(lastMatchIndex); - } - //Need to know if the product from this processes is added at end of transition - bool productMadeAtEnd = isProductMadeAtEnd(matchingHolders, ambiguous, productResolvers); - return std::make_shared(matchingHolders, ambiguous, productMadeAtEnd); - } - - void addUnspecifiedProcess(ProductResolverIndexHelper const& iHelper, - std::vector>& productResolvers) { - // Now create the ProductResolvers that search in reverse process - // order and are used for queries where the process name is the - // empty string - std::vector const& lookupProcessNames = iHelper.lookupProcessNames(); - std::vector matchingHolders(lookupProcessNames.size(), ProductResolverIndexInvalid); - std::vector ambiguous(lookupProcessNames.size(), false); - unsigned int beginElements = iHelper.beginElements(); - std::vector const& sortedTypeIDs = iHelper.sortedTypeIDs(); - std::vector const& ranges = iHelper.ranges(); - std::vector const& indexAndNames = iHelper.indexAndNames(); - std::vector const& processNamesCharArray = iHelper.processNames(); - - unsigned int numberOfMatches = 0; - ProductResolverIndex lastMatchIndex = ProductResolverIndexInvalid; - if (!sortedTypeIDs.empty()) { - ProductResolverIndex productResolverIndex = ProductResolverIndexInvalid; - for (unsigned int k = 0, kEnd = sortedTypeIDs.size(); k < kEnd; ++k) { - ProductResolverIndexHelper::Range const& range = ranges.at(k); - for (unsigned int i = range.begin(); i < range.end(); ++i) { - ProductResolverIndexHelper::IndexAndNames const& product = indexAndNames.at(i); - if (product.startInProcessNames() == 0) { - if (productResolverIndex != ProductResolverIndexInvalid) { - productResolvers.at(productResolverIndex) = - makeNoProcess(numberOfMatches, lastMatchIndex, matchingHolders, ambiguous, productResolvers); - matchingHolders.assign(lookupProcessNames.size(), ProductResolverIndexInvalid); - ambiguous.assign(lookupProcessNames.size(), false); - numberOfMatches = 0; - lastMatchIndex = ProductResolverIndexInvalid; - } - productResolverIndex = product.index(); - } else { - const std::string_view process(&processNamesCharArray.at(product.startInProcessNames())); - auto iter = std::find(lookupProcessNames.begin(), lookupProcessNames.end(), process); - assert(iter != lookupProcessNames.end()); - ProductResolverIndex iMatchingIndex = product.index(); - lastMatchIndex = iMatchingIndex; - assert(iMatchingIndex != ProductResolverIndexInvalid); - ++numberOfMatches; - if (iMatchingIndex == ProductResolverIndexAmbiguous) { - assert(k >= beginElements); - ambiguous.at(iter - lookupProcessNames.begin()) = true; - } else { - matchingHolders.at(iter - lookupProcessNames.begin()) = iMatchingIndex; - } - } - } - } - productResolvers.at(productResolverIndex) = - makeNoProcess(numberOfMatches, lastMatchIndex, matchingHolders, ambiguous, productResolvers); - } - } } // namespace std::vector> make(BranchType bt, @@ -245,8 +166,6 @@ namespace edm::productResolversFactory { } } - addUnspecifiedProcess(*helper, productResolvers); - return productResolvers; } } // namespace edm::productResolversFactory diff --git a/FWCore/Framework/src/Worker.cc b/FWCore/Framework/src/Worker.cc index f63481e40b808..36ca8bb6e7b68 100644 --- a/FWCore/Framework/src/Worker.cc +++ b/FWCore/Framework/src/Worker.cc @@ -136,11 +136,9 @@ namespace edm { for (auto const& item : items) { ProductResolverIndex productResolverIndex = item.productResolverIndex(); - bool skipCurrentProcess = item.skipCurrentProcess(); if (productResolverIndex != ProductResolverIndexAmbiguous and productResolverIndex != ProductResolverIndexInvalid) { - iPrincipal->prefetchAsync( - choiceHolder, productResolverIndex, skipCurrentProcess, token, &moduleCallingContext_); + iPrincipal->prefetchAsync(choiceHolder, productResolverIndex, token, &moduleCallingContext_); } } choiceHolder.doneWaiting(std::exception_ptr{}); @@ -179,9 +177,8 @@ namespace edm { for (auto const& item : items) { ProductResolverIndex productResolverIndex = item.productResolverIndex(); - bool skipCurrentProcess = item.skipCurrentProcess(); if (productResolverIndex != ProductResolverIndexAmbiguous) { - iPrincipal.prefetchAsync(iTask, productResolverIndex, skipCurrentProcess, token, &moduleCallingContext_); + iPrincipal.prefetchAsync(iTask, productResolverIndex, token, &moduleCallingContext_); } } } @@ -213,7 +210,7 @@ namespace edm { //pre prefetch signal actReg_->preModuleTransformPrefetchingSignal_.emit(*mcc.getStreamContext(), mcc); iPrincipal.prefetchAsync( - WaitingTaskHolder(*iTask.group(), task), itemToGetForTransform(iTransformIndex), false, iToken, &mcc); + WaitingTaskHolder(*iTask.group(), task), itemToGetForTransform(iTransformIndex), iToken, &mcc); } void Worker::resetModuleDescription(ModuleDescription const* iDesc) { diff --git a/FWCore/Framework/test/Event_t.cpp b/FWCore/Framework/test/Event_t.cpp index deac0c88a2692..cd88af6cd4b8e 100644 --- a/FWCore/Framework/test/Event_t.cpp +++ b/FWCore/Framework/test/Event_t.cpp @@ -260,6 +260,8 @@ std::unique_ptr testEvent::putProduct(std::unique_ptr product, productInstanceLabel.c_str(), currentModuleDescription_->processName().c_str()); CPPUNIT_ASSERT(index != std::numeric_limits::max()); + CPPUNIT_ASSERT(index != ProductResolverIndexInvalid); + CPPUNIT_ASSERT(index != ProductResolverIndexInitializing); const_cast&>(prod->putTokenIndexToProductResolverIndex()).push_back(index); currentEvent_->setProducer(prod.get(), nullptr); currentEvent_->put(std::move(product), productInstanceLabel); @@ -363,6 +365,7 @@ testEvent::testEvent() availableProducts_->addProduct(branch); // Freeze the product registry before we make the Event. + availableProducts_->setProcessOrder({"CURRENT", "LATE", "EARLY"}); availableProducts_->setFrozen(); branchIDListHelper_->updateFromRegistry(availableProducts_->registry()); } @@ -429,6 +432,7 @@ void testEvent::setUp() { // look up the object. std::shared_ptr preg(std::make_shared(availableProducts_->registry())); + assert(not preg->processOrder().empty()); std::string uuid = createGlobalIdentifier(); Timestamp time = make_timestamp(); EventID id = make_id(); @@ -782,20 +786,10 @@ void testEvent::getByToken() { CPPUNIT_ASSERT(eb->getByToken(modMultiToken, h)); CPPUNIT_ASSERT(h->value == 3); - CPPUNIT_ASSERT(currentEvent_->getByToken(modMultiInt1Token, h)); - CPPUNIT_ASSERT(h->value == 200); - CPPUNIT_ASSERT(eb->getByToken(modMultiInt1Token, h)); - CPPUNIT_ASSERT(h->value == 200); - CPPUNIT_ASSERT(!currentEvent_->getByToken(modMultinomatchToken, h)); CPPUNIT_ASSERT(!h.isValid()); CPPUNIT_ASSERT_THROW(*h, cms::Exception); - CPPUNIT_ASSERT(currentEvent_->getByToken(modMultiInt1Token, h)); - CPPUNIT_ASSERT(h->value == 200); - CPPUNIT_ASSERT(eb->getByToken(modMultiInt1Token, h)); - CPPUNIT_ASSERT(h->value == 200); - CPPUNIT_ASSERT(currentEvent_->getByToken(modMultiInt1EarlyToken, h)); CPPUNIT_ASSERT(h->value == 1); CPPUNIT_ASSERT(eb->getByToken(modMultiInt1EarlyToken, h)); @@ -816,6 +810,11 @@ void testEvent::getByToken() { CPPUNIT_ASSERT(eb->getByToken(modMultiInt2EarlyToken, h)); CPPUNIT_ASSERT(h->value == 2); + CPPUNIT_ASSERT(currentEvent_->getByToken(modMultiInt1Token, h)); + CPPUNIT_ASSERT(h->value == 200); + CPPUNIT_ASSERT(eb->getByToken(modMultiInt1Token, h)); + CPPUNIT_ASSERT(h->value == 200); + CPPUNIT_ASSERT(currentEvent_->getByToken(modOneToken, h)); CPPUNIT_ASSERT(h->value == 4); CPPUNIT_ASSERT(eb->getByToken(modOneToken, h)); diff --git a/FWCore/Framework/test/edconsumerbase_t.cppunit.cc b/FWCore/Framework/test/edconsumerbase_t.cppunit.cc index 90f550a6d0fa2..ab5f79ea19a81 100644 --- a/FWCore/Framework/test/edconsumerbase_t.cppunit.cc +++ b/FWCore/Framework/test/edconsumerbase_t.cppunit.cc @@ -125,27 +125,35 @@ void TestEDConsumerBase::testRegularType() { edm::TypeID typeIDSetInt(typeid(std::set)); edm::TypeID typeIDVSimpleDerived(typeid(std::vector)); - helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0, 1, 2 - helper.insert(typeIDVectorInt, "label", "instance", "process"); // 3, 4, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 6, 7 - helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 8, 9 - helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 10, 11 - helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 12, 13 - helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 14, 15 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 16, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 17, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 18, 5 - helper.insert(typeIDProductID, "label", "instance", "process"); // 19, 20 - helper.insert(typeIDEventID, "label", "instance", "process"); // 21, 22 - helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 23, 24 - helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 25, 26 - helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 27, 28, 29, 30 + //ProductResolverIndex + helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0 + helper.insert(typeIDVectorInt, "label", "instance", "process"); // 1 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 2 + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 3 + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 4 + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 5 + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 6 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 7 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 8 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 9 + helper.insert(typeIDProductID, "label", "instance", "process"); // 10 + helper.insert(typeIDEventID, "label", "instance", "process"); // 11 + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 12 + helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 13 + helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 14 - helper.setFrozen("processC"); + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } edm::TypeID typeID_vint(typeid(std::vector)); const auto vint_c = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC"); + const auto vint_c_skipCurrent = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "#"); + CPPUNIT_ASSERT(edm::ProductResolverIndexInvalid == vint_c_skipCurrent); const auto vint_c_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", 0); + CPPUNIT_ASSERT(vint_c == vint_c_no_proc); const auto vint_blank = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", "process"); const auto vint_blank_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", 0); { @@ -263,7 +271,7 @@ void TestEDConsumerBase::testRegularType() { CPPUNIT_ASSERT(intConsumer.m_tokens[0].index() == 0); CPPUNIT_ASSERT(intConsumer.m_tokens[1].index() == 1); - CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_c_no_proc, true) == + CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_c_skipCurrent, true) == intConsumer.indexFrom(intConsumer.m_tokens[1], edm::InEvent, typeID_vint)); CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_blank_no_proc, false) == intConsumer.indexFrom(intConsumer.m_tokens[0], edm::InEvent, typeID_vint)); @@ -271,10 +279,10 @@ void TestEDConsumerBase::testRegularType() { std::vector indices; intConsumer.itemsToGet(edm::InEvent, indices); - CPPUNIT_ASSERT(2 == indices.size()); - CPPUNIT_ASSERT(indices.end() != std::find(indices.begin(), + CPPUNIT_ASSERT(1 == indices.size()); + CPPUNIT_ASSERT(indices.end() == std::find(indices.begin(), indices.end(), - edm::ProductResolverIndexAndSkipBit(vint_c_no_proc, true))); + edm::ProductResolverIndexAndSkipBit(vint_c_skipCurrent, true))); CPPUNIT_ASSERT(indices.end() != std::find(indices.begin(), indices.end(), edm::ProductResolverIndexAndSkipBit(vint_blank_no_proc, false))); @@ -325,23 +333,27 @@ void TestEDConsumerBase::testViewType() { edm::TypeID typeIDSetInt(typeid(std::set)); edm::TypeID typeIDVSimpleDerived(typeid(std::vector)); - helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0, 1, 2 - helper.insert(typeIDVectorInt, "label", "instance", "process"); // 3, 4, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 6, 7 - helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 8, 9 - helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 10, 11 - helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 12, 13 - helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 14, 15 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 16, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 17, 5 - helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 18, 5 - helper.insert(typeIDProductID, "label", "instance", "process"); // 19, 20 - helper.insert(typeIDEventID, "label", "instance", "process"); // 21, 22 - helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 23, 24 - helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 25, 26 - helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 27, 28, 29, 30 + helper.insert(typeIDVectorInt, "labelC", "instanceC", "processC"); // 0 + helper.insert(typeIDVectorInt, "label", "instance", "process"); // 1 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB"); // 2 + helper.insert(typeIDEventID, "label", "instanceB", "processB"); // 3 + helper.insert(typeIDEventID, "labelX", "instanceB", "processB"); // 4 + helper.insert(typeIDEventID, "labelB", "instance", "processB"); // 5 + helper.insert(typeIDEventID, "labelB", "instanceX", "processB"); // 6 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB1"); // 7 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB3"); // 8 + helper.insert(typeIDEventID, "labelB", "instanceB", "processB2"); // 9 + helper.insert(typeIDProductID, "label", "instance", "process"); // 10 + helper.insert(typeIDEventID, "label", "instance", "process"); // 11 + helper.insert(typeIDProductID, "labelA", "instanceA", "processA"); // 12 + helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 13 + helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 14 - helper.setFrozen("processC"); + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } edm::TypeID typeID_int(typeid(int)); edm::TypeID typeID_Simple(typeid(edmtest::Simple)); @@ -351,6 +363,8 @@ void TestEDConsumerBase::testViewType() { const auto v_int_no_proc = helper.index(edm::ELEMENT_TYPE, typeID_int, "label", "instance"); const auto v_simple_no_proc = helper.index(edm::ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC"); + CPPUNIT_ASSERT(v_simple_no_proc == v_simple); + const auto v_simple_skip = helper.index(edm::ELEMENT_TYPE, typeID_Simple, "labelC", "#"); { std::vector> vT = { @@ -390,19 +404,19 @@ void TestEDConsumerBase::testViewType() { CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(v_int_no_proc, false) == consumer.indexFrom(consumer.m_tokens[0], edm::InEvent, typeID_int)); - CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(v_simple_no_proc, true) == + CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(v_simple_skip, true) == consumer.indexFrom(consumer.m_tokens[1], edm::InEvent, typeID_Simple)); { std::vector indices; consumer.itemsToGet(edm::InEvent, indices); - CPPUNIT_ASSERT(2 == indices.size()); + CPPUNIT_ASSERT(1 == indices.size()); CPPUNIT_ASSERT(indices.end() != std::find(indices.begin(), indices.end(), edm::ProductResolverIndexAndSkipBit(v_int_no_proc, false))); - CPPUNIT_ASSERT(indices.end() != std::find(indices.begin(), + CPPUNIT_ASSERT(indices.end() == std::find(indices.begin(), indices.end(), - edm::ProductResolverIndexAndSkipBit(v_simple_no_proc, true))); + edm::ProductResolverIndexAndSkipBit(v_simple_skip, true))); std::vector indicesMay; consumer.itemsMayGet(edm::InEvent, indicesMay); @@ -454,10 +468,16 @@ void TestEDConsumerBase::testMay() { helper.insert(typeIDSetInt, "labelC", "instanceC", "processC"); // 25, 26 helper.insert(typeIDVSimpleDerived, "labelC", "instanceC", "processC"); // 27, 28, 29, 30 - helper.setFrozen("processC"); + { + std::vector processNames = { + "processC", "process", "processB", "processB1", "processB2", "processB3", "processA"}; + helper.setFrozen(processNames); + } edm::TypeID typeID_vint(typeid(std::vector)); const auto vint_c = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC"); const auto vint_c_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", 0); + CPPUNIT_ASSERT(vint_c_no_proc == vint_c); + const auto vint_c_skip = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "#"); const auto vint_blank = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", "process"); const auto vint_blank_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", 0); { @@ -559,7 +579,7 @@ void TestEDConsumerBase::testMay() { CPPUNIT_ASSERT(consumer.m_mayTokens[1].index() == 1); CPPUNIT_ASSERT(consumer.m_tokens.size() == 0); - CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_c_no_proc, true) == + CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_c_skip, true) == consumer.indexFrom(consumer.m_mayTokens[1], edm::InEvent, typeID_vint)); CPPUNIT_ASSERT(edm::ProductResolverIndexAndSkipBit(vint_blank_no_proc, false) == consumer.indexFrom(consumer.m_mayTokens[0], edm::InEvent, typeID_vint)); diff --git a/FWCore/Framework/test/event_getrefbeforeput_t.cppunit.cc b/FWCore/Framework/test/event_getrefbeforeput_t.cppunit.cc index 543e2d143e7f9..ca190de623a54 100644 --- a/FWCore/Framework/test/event_getrefbeforeput_t.cppunit.cc +++ b/FWCore/Framework/test/event_getrefbeforeput_t.cppunit.cc @@ -156,6 +156,7 @@ void testEventGetRefBeforePut::getRefTest() { auto preg = std::make_unique(); preg->addProduct(product); + preg->setCurrentProcess(processName); preg->setFrozen(); auto branchIDListHelper = std::make_shared(); branchIDListHelper->updateFromRegistry(preg->registry()); diff --git a/FWCore/Framework/test/eventprincipal_t.cppunit.cc b/FWCore/Framework/test/eventprincipal_t.cppunit.cc index f403b6c99387a..9939c3b6994b4 100644 --- a/FWCore/Framework/test/eventprincipal_t.cppunit.cc +++ b/FWCore/Framework/test/eventprincipal_t.cppunit.cc @@ -131,6 +131,7 @@ void test_ep::setUp() { pProductRegistry_->addProduct(*fake_single_process_branch("test", "TEST")); pProductRegistry_->addProduct(*fake_single_process_branch("user", "USER")); pProductRegistry_->addProduct(*fake_single_process_branch("rick", "USER2", "rick")); + pProductRegistry_->setProcessOrder({"USER2", "USER", "TEST", "PROD", "HLT"}); pProductRegistry_->setFrozen(); auto branchIDListHelper = std::make_shared(); branchIDListHelper->updateFromRegistry(pProductRegistry_->registry()); diff --git a/FWCore/Framework/test/generichandle_t.cppunit.cc b/FWCore/Framework/test/generichandle_t.cppunit.cc index 892ef9444bc84..5eec5ea66efbc 100644 --- a/FWCore/Framework/test/generichandle_t.cppunit.cc +++ b/FWCore/Framework/test/generichandle_t.cppunit.cc @@ -150,6 +150,7 @@ void testGenericHandle::getbyLabelTest() { auto preg = std::make_unique(); preg->addProduct(product); + preg->setCurrentProcess(processName); preg->setFrozen(); auto branchIDListHelper = std::make_shared(); branchIDListHelper->updateFromRegistry(preg->registry()); diff --git a/FWCore/Integration/test/testNoProcessFallback3_cfg.py b/FWCore/Integration/test/testNoProcessFallback3_cfg.py index f1581aab09099..7193caaf0e1bd 100644 --- a/FWCore/Integration/test/testNoProcessFallback3_cfg.py +++ b/FWCore/Integration/test/testNoProcessFallback3_cfg.py @@ -69,7 +69,7 @@ process.keeper2 = EventIDFilter( eventsToPass = [cms.EventID(1,1,2)] ) -process.p2 = cms.Path(process.keeper2 + process.testerNoProcess1 + process.testerSkipCurrentProcess1 + process.testerCurrentProcessMissing) +process.p2 = cms.Path(process.keeper2 + process.testerNoProcessMissing + process.testerSkipCurrentProcessMissing + process.testerCurrentProcessMissing) process.keeper3 = EventIDFilter( eventsToPass = [cms.EventID(1,1,3)] @@ -87,12 +87,12 @@ valueMustBeMissing = cms.untracked.bool(False) ) -process.p3 = cms.Path(process.keeper3 + process.testerNoProcess2 + process.testerSkipCurrentProcess2 + process.testerCurrentProcessMissing) +process.p3 = cms.Path(process.keeper3 + process.testerNoProcessMissing + process.testerSkipCurrentProcess2 + process.testerCurrentProcessMissing) process.keeper4 = EventIDFilter( eventsToPass = [cms.EventID(1,1,4)] ) -process.p4 = cms.Path(process.keeper4 + process.testerNoProcess2 + process.testerSkipCurrentProcess2 + process.testerCurrentProcessMissing) +process.p4 = cms.Path(process.keeper4 + process.testerNoProcessMissing + process.testerSkipCurrentProcess2 + process.testerCurrentProcessMissing) process.testerNoProcess3 = cms.EDAnalyzer("BuiltinIntTestAnalyzer", moduleLabel = cms.untracked.InputTag("intProducer"), @@ -114,7 +114,7 @@ process.keeper6 = EventIDFilter( eventsToPass = [cms.EventID(1,1,6)] ) -process.p6 = cms.Path(process.keeper6 + process.testerNoProcess3 + process.testerSkipCurrentProcess1 + process.testerCurrentProcess3) +process.p6 = cms.Path(process.keeper6 + process.testerNoProcess3 + process.testerSkipCurrentProcessMissing + process.testerCurrentProcess3) process.keeper7 = EventIDFilter( eventsToPass = [cms.EventID(1,1,7)] diff --git a/FWCore/Integration/test/testNoProcessFallbackNoCurrent_cfg.py b/FWCore/Integration/test/testNoProcessFallbackNoCurrent_cfg.py index 111c4c5e49149..cf3fa67603a31 100644 --- a/FWCore/Integration/test/testNoProcessFallbackNoCurrent_cfg.py +++ b/FWCore/Integration/test/testNoProcessFallbackNoCurrent_cfg.py @@ -59,7 +59,7 @@ process.keeper2 = EventIDFilter( eventsToPass = [cms.EventID(1,1,2)] ) -process.p2 = cms.Path(process.keeper2 + process.testerNoProcess1 + process.testerSkipCurrentProcess1 + process.testerCurrentProcessMissing) +process.p2 = cms.Path(process.keeper2 + process.testerNoProcessMissing + process.testerSkipCurrentProcessMissing + process.testerCurrentProcessMissing) process.keeper3 = EventIDFilter( eventsToPass = [cms.EventID(1,1,3)] diff --git a/FWCore/Integration/test/testProcessBlockNOMergeOfMergedFiles_cfg.py b/FWCore/Integration/test/testProcessBlockNOMergeOfMergedFiles_cfg.py index 7a4356b6f56a1..49f82b1115847 100644 --- a/FWCore/Integration/test/testProcessBlockNOMergeOfMergedFiles_cfg.py +++ b/FWCore/Integration/test/testProcessBlockNOMergeOfMergedFiles_cfg.py @@ -34,12 +34,15 @@ # # TOTAL 8221 +#must use skipCurrentProcess as all ProcessBlocks use the same lookups and +# the current process contains a module with the same label that makes the +# same product as is found in the 'MERGE' process block process.readProcessBlocksOneAnalyzer = cms.EDAnalyzer("edmtest::one::InputProcessBlockIntAnalyzer", transitions = cms.int32(30), consumesBeginProcessBlock = cms.InputTag("intProducerBeginProcessBlock", ""), consumesEndProcessBlock = cms.InputTag("intProducerEndProcessBlock", ""), - consumesBeginProcessBlockM = cms.InputTag("intProducerBeginProcessBlockM", ""), - consumesEndProcessBlockM = cms.InputTag("intProducerEndProcessBlockM", ""), + consumesBeginProcessBlockM = cms.InputTag("intProducerBeginProcessBlockM", "", cms.InputTag.skipCurrentProcess()), + consumesEndProcessBlockM = cms.InputTag("intProducerEndProcessBlockM", "", cms.InputTag.skipCurrentProcess()), expectedByRun = cms.vint32(11, 22, 3300, 4400), expectedSum = cms.int32(8221) ) From 2a4044892bd6dd96f3ad073771fa09de86afef43 Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 14:23:44 -0500 Subject: [PATCH 04/13] apply result of code checks --- DataFormats/Provenance/src/ProductRegistry.cc | 2 +- FWCore/Framework/src/DroppedDataProductResolver.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/DataFormats/Provenance/src/ProductRegistry.cc b/DataFormats/Provenance/src/ProductRegistry.cc index a3f2b576346e8..86420c0bd10d1 100644 --- a/DataFormats/Provenance/src/ProductRegistry.cc +++ b/DataFormats/Provenance/src/ProductRegistry.cc @@ -332,7 +332,7 @@ namespace edm { std::vector producedTypes; transient_.branchIDToIndex_.clear(); - assert(productList_.empty() or processOrder().size() > 0); + assert(productList_.empty() or !processOrder().empty()); std::array, NumBranchTypes> new_productLookups{ {std::make_shared(), diff --git a/FWCore/Framework/src/DroppedDataProductResolver.h b/FWCore/Framework/src/DroppedDataProductResolver.h index 1b7de16e71ecd..f446c60a45810 100644 --- a/FWCore/Framework/src/DroppedDataProductResolver.h +++ b/FWCore/Framework/src/DroppedDataProductResolver.h @@ -13,7 +13,7 @@ namespace edm { class DroppedDataProductResolver : public ProductResolverBase { public: DroppedDataProductResolver(std::shared_ptr bd) - : ProductResolverBase(), m_provenance(std::move(bd), {}) {} + : ProductResolverBase(), m_provenance(bd, {}) {} void connectTo(ProductResolverBase const&, Principal const*) final {} From c36be5849354e8a334482062caae1faf0d035fbf Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 14:25:52 -0500 Subject: [PATCH 05/13] Define skippCurrentProcessLabel in one place --- .../interface/ProductResolverIndexHelper.h | 6 +++++- .../Provenance/src/ProductResolverIndexHelper.cc | 2 +- .../Provenance/test/productResolverIndexHelper_t.cpp | 12 +++++++++--- FWCore/Framework/src/EDConsumerBase.cc | 2 +- FWCore/Framework/src/Principal.cc | 4 ++-- FWCore/Framework/test/edconsumerbase_t.cppunit.cc | 8 +++++--- 6 files changed, 23 insertions(+), 11 deletions(-) diff --git a/DataFormats/Provenance/interface/ProductResolverIndexHelper.h b/DataFormats/Provenance/interface/ProductResolverIndexHelper.h index 13b1ea7bcc5f5..b96b1e4005203 100644 --- a/DataFormats/Provenance/interface/ProductResolverIndexHelper.h +++ b/DataFormats/Provenance/interface/ProductResolverIndexHelper.h @@ -258,6 +258,10 @@ namespace edm { // For debugging only void print(std::ostream& os) const; + //ProcessName label used to denote the current process should be skipped + //used by all methods of this class that accept the process name + static constexpr char const* const skipCurrentProcessLabel() { return "#"; } + private: // Next available value for a ProductResolverIndex. This just // increments by one each time a new value is assigned. @@ -330,7 +334,7 @@ namespace edm { ProductResolverIndex index() const { return index_; } void clearProcess() { process_.clear(); } - void setSkipCurrentProcess() { process_ = "#"; } + void setSkipCurrentProcess() { process_ = ProductResolverIndexHelper::skipCurrentProcessLabel(); } void setIndex(ProductResolverIndex v) { index_ = v; } bool operator<(Item const& right) const; diff --git a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc index c26b2d603e804..94a5cdad76143 100644 --- a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc +++ b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc @@ -413,7 +413,7 @@ namespace edm { //sanity check for (auto const& p : *processItems_) { - if (p.empty() or p == "#") + if (p.empty() or p == skipCurrentProcessLabel()) continue; if (orderedProcessNames.end() == std::find(orderedProcessNames.begin(), orderedProcessNames.end(), p)) { throw Exception(errors::LogicError) diff --git a/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp b/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp index c632b8b4bc43e..765e0dcd6929c 100644 --- a/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp +++ b/DataFormats/Provenance/test/productResolverIndexHelper_t.cpp @@ -14,6 +14,9 @@ #include using namespace edm; +namespace { + constexpr auto skipCurrentProcessLabel = edm::ProductResolverIndexHelper::skipCurrentProcessLabel(); +} TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { TypeID typeID_ProductID(typeid(ProductID)); @@ -79,7 +82,8 @@ TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcess); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", skipCurrentProcessLabel) == + indexSkipCurrentProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instance", "processA") == @@ -154,7 +158,8 @@ TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcess); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", skipCurrentProcessLabel) == + indexSkipCurrentProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instance", "processA") == @@ -216,7 +221,8 @@ TEST_CASE("ProductResolverIndexHelper", "[ProductResolverIndexHelper]") { REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA") == indexWithProcessB); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "") == indexWithProcessB); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", 0) == indexWithProcessB); - REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "#") == indexSkipCurrentProcess); + REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", skipCurrentProcessLabel) == + indexSkipCurrentProcess); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processA") == indexWithProcessA); REQUIRE(helper.index(PRODUCT_TYPE, typeID_ProductID, "labelA", "instanceA", "processB") == indexWithProcessB); } diff --git a/FWCore/Framework/src/EDConsumerBase.cc b/FWCore/Framework/src/EDConsumerBase.cc index ae763182b3d56..efa1393047d2f 100644 --- a/FWCore/Framework/src/EDConsumerBase.cc +++ b/FWCore/Framework/src/EDConsumerBase.cc @@ -129,7 +129,7 @@ void EDConsumerBase::updateLookup(BranchType iBranchType, const char* moduleLabel = &(m_tokenLabels[labelStart]); const char* processName = moduleLabel + itLabels->m_deltaToProcessName; if (itInfo->m_index.skipCurrentProcess()) { - processName = "#"; + processName = iHelper.skipCurrentProcessLabel(); } itInfo->m_index = ProductResolverIndexAndSkipBit( iHelper.index( diff --git a/FWCore/Framework/src/Principal.cc b/FWCore/Framework/src/Principal.cc index bda15eef94cab..6bc48f1492127 100644 --- a/FWCore/Framework/src/Principal.cc +++ b/FWCore/Framework/src/Principal.cc @@ -457,7 +457,7 @@ namespace edm { if (inputTag.process() == InputTag::kCurrentProcess) { processName = &processConfiguration_->processName(); } - std::string const kSkipCurrentProcess = "#"; + std::string const kSkipCurrentProcess = ProductResolverIndexHelper::skipCurrentProcessLabel(); if (skipCurrentProcess) { processName = &kSkipCurrentProcess; } @@ -481,7 +481,7 @@ namespace edm { if (index == ProductResolverIndexInitializing) { char const* processName = inputTag.process().c_str(); if (skipCurrentProcess) { - processName = "#"; + processName = ProductResolverIndexHelper::skipCurrentProcessLabel(); } else if (inputTag.process() == InputTag::kCurrentProcess) { processName = processConfiguration_->processName().c_str(); } diff --git a/FWCore/Framework/test/edconsumerbase_t.cppunit.cc b/FWCore/Framework/test/edconsumerbase_t.cppunit.cc index ab5f79ea19a81..7b466dcfc54d4 100644 --- a/FWCore/Framework/test/edconsumerbase_t.cppunit.cc +++ b/FWCore/Framework/test/edconsumerbase_t.cppunit.cc @@ -114,6 +114,7 @@ namespace { std::vector>> m_tokens; }; + constexpr const auto skipCurrentProcessLabel = edm::ProductResolverIndexHelper::skipCurrentProcessLabel(); } // namespace void TestEDConsumerBase::testRegularType() { @@ -150,7 +151,8 @@ void TestEDConsumerBase::testRegularType() { edm::TypeID typeID_vint(typeid(std::vector)); const auto vint_c = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC"); - const auto vint_c_skipCurrent = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "#"); + const auto vint_c_skipCurrent = + helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", skipCurrentProcessLabel); CPPUNIT_ASSERT(edm::ProductResolverIndexInvalid == vint_c_skipCurrent); const auto vint_c_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", 0); CPPUNIT_ASSERT(vint_c == vint_c_no_proc); @@ -364,7 +366,7 @@ void TestEDConsumerBase::testViewType() { const auto v_int_no_proc = helper.index(edm::ELEMENT_TYPE, typeID_int, "label", "instance"); const auto v_simple_no_proc = helper.index(edm::ELEMENT_TYPE, typeID_Simple, "labelC", "instanceC"); CPPUNIT_ASSERT(v_simple_no_proc == v_simple); - const auto v_simple_skip = helper.index(edm::ELEMENT_TYPE, typeID_Simple, "labelC", "#"); + const auto v_simple_skip = helper.index(edm::ELEMENT_TYPE, typeID_Simple, "labelC", skipCurrentProcessLabel); { std::vector> vT = { @@ -477,7 +479,7 @@ void TestEDConsumerBase::testMay() { const auto vint_c = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "processC"); const auto vint_c_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", 0); CPPUNIT_ASSERT(vint_c_no_proc == vint_c); - const auto vint_c_skip = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", "#"); + const auto vint_c_skip = helper.index(edm::PRODUCT_TYPE, typeID_vint, "labelC", "instanceC", skipCurrentProcessLabel); const auto vint_blank = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", "process"); const auto vint_blank_no_proc = helper.index(edm::PRODUCT_TYPE, typeID_vint, "label", "instance", 0); { From 8b3e1f845299ceeaf61fd5592ea534329362edd6 Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Tue, 26 Aug 2025 15:13:59 -0500 Subject: [PATCH 06/13] Add back in commented out class --- DataFormats/StdDictionaries/src/classes_def_others.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DataFormats/StdDictionaries/src/classes_def_others.xml b/DataFormats/StdDictionaries/src/classes_def_others.xml index 8f75efeb4b698..3d011b7586cd8 100644 --- a/DataFormats/StdDictionaries/src/classes_def_others.xml +++ b/DataFormats/StdDictionaries/src/classes_def_others.xml @@ -25,5 +25,5 @@ - + From a26fcac00cd6b644a2a9a4e5f5c5f98530ccf15e Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Wed, 27 Aug 2025 09:15:56 -0500 Subject: [PATCH 07/13] Removed unused variables --- DataFormats/Provenance/src/ProductRegistry.cc | 1 - FWCore/Framework/src/ProductResolvers.cc | 4 ---- 2 files changed, 5 deletions(-) diff --git a/DataFormats/Provenance/src/ProductRegistry.cc b/DataFormats/Provenance/src/ProductRegistry.cc index 86420c0bd10d1..5fe2848d99897 100644 --- a/DataFormats/Provenance/src/ProductRegistry.cc +++ b/DataFormats/Provenance/src/ProductRegistry.cc @@ -473,7 +473,6 @@ namespace edm { throwMissingDictionariesException(missingDictionaries, context, producedTypes, branchNamesForMissing); } - std::string_view processNameSV(processName ? std::string_view(*processName) : std::string_view()); for (auto& iterProductLookup : new_productLookups) { iterProductLookup->setFrozen(processOrder()); } diff --git a/FWCore/Framework/src/ProductResolvers.cc b/FWCore/Framework/src/ProductResolvers.cc index 7b3a0d28ace97..17d1a87783880 100644 --- a/FWCore/Framework/src/ProductResolvers.cc +++ b/FWCore/Framework/src/ProductResolvers.cc @@ -26,10 +26,6 @@ #include #include -static constexpr unsigned int kUnsetOffset = 0; -static constexpr unsigned int kAmbiguousOffset = 1; -static constexpr unsigned int kMissingOffset = 2; - namespace edm { void DataManagingProductResolver::throwProductDeletedException() const { From e9f46ccf0f80912062ec1f8ff1822e29a6ca5866 Mon Sep 17 00:00:00 2001 From: Christopher Jones Date: Wed, 27 Aug 2025 15:30:34 -0500 Subject: [PATCH 08/13] Improve exception message from GenParticleProducer --- .../HepMCCandAlgos/plugins/GenParticleProducer.cc | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/PhysicsTools/HepMCCandAlgos/plugins/GenParticleProducer.cc b/PhysicsTools/HepMCCandAlgos/plugins/GenParticleProducer.cc index df5ee966a6104..95009ff8ad03e 100644 --- a/PhysicsTools/HepMCCandAlgos/plugins/GenParticleProducer.cc +++ b/PhysicsTools/HepMCCandAlgos/plugins/GenParticleProducer.cc @@ -235,8 +235,14 @@ void GenParticleProducer::produce(StreamID, Event& evt, const EventSetup& es) co } else { Handle mcp3; bool found = evt.getByToken(srcToken3_, mcp3); - if (!found) - throw cms::Exception("ProductAbsent") << "No HepMCProduct, tried to get HepMC3Product, but it is also absent."; + if (!found) { + try { + *mcp3; + } catch (cms::Exception& iExcept) { + iExcept.addContext("No HepMCProduct, tried to get HepMC3Product, but it is also absent."); + throw; + } + } ivhepmc = 3; mc3 = new HepMC3::GenEvent(); mc3->read_data(*mcp3->GetEvent()); From f046846ef1336bcf99749a5ce7c39602fbcf0e08 Mon Sep 17 00:00:00 2001 From: Christopher Jones Date: Wed, 27 Aug 2025 15:31:11 -0500 Subject: [PATCH 09/13] Conditionally produce/consume in GeneratorSmearedProducer Only call produces and consumes if the data products the module want appear to be in the job. This solves the case where the module has been added to a job just on the remote possibility it might be needed but infact the values which are actually wanted come from the source. --- .../Core/plugins/GeneratorSmearedProducer.cc | 73 +++++++++++++++---- 1 file changed, 57 insertions(+), 16 deletions(-) diff --git a/GeneratorInterface/Core/plugins/GeneratorSmearedProducer.cc b/GeneratorInterface/Core/plugins/GeneratorSmearedProducer.cc index 7eb2981fcf34b..c9ce7c305f938 100644 --- a/GeneratorInterface/Core/plugins/GeneratorSmearedProducer.cc +++ b/GeneratorInterface/Core/plugins/GeneratorSmearedProducer.cc @@ -27,27 +27,66 @@ class GeneratorSmearedProducer : public edm::global::EDProducer<> { static void fillDescriptions(edm::ConfigurationDescriptions& descriptions); private: - const edm::EDGetTokenT newToken_; - const edm::EDGetTokenT oldToken_; - const edm::EDGetTokenT Token3_; + edm::EDGetTokenT newToken_; + edm::EDGetTokenT oldToken_; + edm::EDGetTokenT Token3_; }; -GeneratorSmearedProducer::GeneratorSmearedProducer(edm::ParameterSet const& ps) - : newToken_(consumes(ps.getUntrackedParameter("currentTag"))), - oldToken_(consumes(ps.getUntrackedParameter("previousTag"))), - Token3_(consumes(ps.getUntrackedParameter("currentTag"))) { +namespace { + template + bool match(edm::InputTag const& iTag, edm::ProductDescription const& iDesc) { + if (iDesc.unwrappedTypeID() == edm::TypeID(typeid(T))) { + if (iDesc.moduleLabel() == iTag.label() and iDesc.productInstanceName() == iTag.instance()) { + if (iTag.process().empty() or iTag.willSkipCurrentProcess() or + iTag.process() == edm::InputTag::kCurrentProcess) { + return true; + } + } else { + return iTag.process() == iDesc.processName(); + } + } + return false; + } +} // namespace + +GeneratorSmearedProducer::GeneratorSmearedProducer(edm::ParameterSet const& ps) { // This producer produces a HepMCProduct, a copy of the original one // It is used for backward compatibility // If HepMC3Product exists, it produces its copy // It adds "generatorSmeared" to description, which is needed for further processing - produces(); - produces(); + auto currentTag = ps.getUntrackedParameter("currentTag"); + auto previousTag = ps.getUntrackedParameter("previousTag"); + callWhenNewProductsRegistered([this, currentTag, previousTag](edm::ProductDescription const& desc) { + bool oldHep = false; + if (match(currentTag, desc)) { + if (newToken_.isUninitialized()) { + newToken_ = consumes(currentTag); + oldHep = true; + } + } + if (match(previousTag, desc)) { + if (oldToken_.isUninitialized()) { + oldToken_ = consumes(previousTag); + oldHep = true; + } + } + if (oldHep) { + produces(); + } + if (match(currentTag, desc)) { + Token3_ = consumes(currentTag); + produces(); + } + }); } void GeneratorSmearedProducer::produce(edm::StreamID, edm::Event& iEvent, const edm::EventSetup& es) const { edm::Handle theHepMCProduct; - bool found = iEvent.getByToken(newToken_, theHepMCProduct); - if (!found) { + bool found = false; + if (not newToken_.isUninitialized()) { + found = iEvent.getByToken(newToken_, theHepMCProduct); + } + if (!found and not oldToken_.isUninitialized()) { found = iEvent.getByToken(oldToken_, theHepMCProduct); } if (found) { @@ -55,11 +94,13 @@ void GeneratorSmearedProducer::produce(edm::StreamID, edm::Event& iEvent, const iEvent.put(std::move(theCopy)); } - edm::Handle theHepMC3Product; - found = iEvent.getByToken(Token3_, theHepMC3Product); - if (found) { - std::unique_ptr theCopy3(new edm::HepMC3Product(*theHepMC3Product)); - iEvent.put(std::move(theCopy3)); + if (not Token3_.isUninitialized()) { + edm::Handle theHepMC3Product; + found = iEvent.getByToken(Token3_, theHepMC3Product); + if (found) { + std::unique_ptr theCopy3(new edm::HepMC3Product(*theHepMC3Product)); + iEvent.put(std::move(theCopy3)); + } } } From eaa09a3ffc9c6a5e255c96efc2b8dbc9594642b8 Mon Sep 17 00:00:00 2001 From: Christopher Jones Date: Wed, 27 Aug 2025 16:39:38 -0500 Subject: [PATCH 10/13] Call ProductRegistry::setProcessOrder from sources --- FWCore/Sources/src/DaqProvenanceHelper.cc | 1 + GeneratorInterface/LHEInterface/plugins/LHEProvenanceHelper.cc | 1 + 2 files changed, 2 insertions(+) diff --git a/FWCore/Sources/src/DaqProvenanceHelper.cc b/FWCore/Sources/src/DaqProvenanceHelper.cc index f133b9355b176..75a7fd42e78d0 100644 --- a/FWCore/Sources/src/DaqProvenanceHelper.cc +++ b/FWCore/Sources/src/DaqProvenanceHelper.cc @@ -85,6 +85,7 @@ namespace edm { // Now we need to set all the metadata // Add the product to the product registry productRegistry.copyProduct(constProductDescription_); + productRegistry.setProcessOrder({constProductDescription_.processName()}); // Insert an entry for this process in the process history registry // This process is about the data from LHC, and has thus no diff --git a/GeneratorInterface/LHEInterface/plugins/LHEProvenanceHelper.cc b/GeneratorInterface/LHEInterface/plugins/LHEProvenanceHelper.cc index 7306de3fb53b6..acce74a5b39a2 100644 --- a/GeneratorInterface/LHEInterface/plugins/LHEProvenanceHelper.cc +++ b/GeneratorInterface/LHEInterface/plugins/LHEProvenanceHelper.cc @@ -48,6 +48,7 @@ namespace edm { auto rp = runProductProductDescription_; rp.setIsProvenanceSetOnRead(); productRegistry.copyProduct(rp); + productRegistry.setProcessOrder({eventProductProductDescription_.processName()}); BranchIDList bli(1UL, ep.branchID().id()); branchIDListHelper.updateFromInput({{bli}}); } From f0ae55963d5673ffc9d17b81a384d20ccbcd65ab Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Wed, 27 Aug 2025 16:43:39 -0500 Subject: [PATCH 11/13] fixed indention --- DataFormats/StdDictionaries/src/classes_def_others.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DataFormats/StdDictionaries/src/classes_def_others.xml b/DataFormats/StdDictionaries/src/classes_def_others.xml index 3d011b7586cd8..0af34d7f49dff 100644 --- a/DataFormats/StdDictionaries/src/classes_def_others.xml +++ b/DataFormats/StdDictionaries/src/classes_def_others.xml @@ -25,5 +25,5 @@ - + From f8cd6dc16cf645cd296706badcd33c4d3856de30 Mon Sep 17 00:00:00 2001 From: Chris Jones Date: Wed, 27 Aug 2025 16:44:06 -0500 Subject: [PATCH 12/13] Improved code clarity based on code review --- .../src/ProductResolverIndexHelper.cc | 125 +++++++++--------- 1 file changed, 60 insertions(+), 65 deletions(-) diff --git a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc index 94a5cdad76143..5345b9bde3c84 100644 --- a/DataFormats/Provenance/src/ProductResolverIndexHelper.cc +++ b/DataFormats/Provenance/src/ProductResolverIndexHelper.cc @@ -232,60 +232,44 @@ namespace edm { // Put in an entry for the product with an empty process name // if it is not already there - item.clearProcess(); - iter = items_->find(item); - if (iter == items_->end()) { - item.setIndex(ProductResolverIndexInitializing); - items_->insert(item); - //add entry for skipCurrentProcess - item.setSkipCurrentProcess(); - item.setIndex(ProductResolverIndexInitializing); - items_->insert(item); - } + auto insertNoProcessCase = [](Item& item, std::set& container) { + item.clearProcess(); + auto iter = container.find(item); + if (iter == container.end()) { + item.setIndex(ProductResolverIndexInitializing); + container.insert(item); + //add entry for skipCurrentProcess + item.setSkipCurrentProcess(); + item.setIndex(ProductResolverIndexInitializing); + container.insert(item); + } + }; + insertNoProcessCase(item, *items_); // Now put in entries for a contained class if this is a // recognized container. if (containedTypeID != TypeID(typeid(void)) && containedTypeID != TypeID()) { TypeWithDict containedType(containedTypeID.typeInfo()); - Item containedItem(ELEMENT_TYPE, containedTypeID, moduleLabel, instance, process, savedProductIndex); - iter = items_->find(containedItem); - if (iter != items_->end()) { - containedItem.setIndex(ProductResolverIndexAmbiguous); - items_->erase(iter); - } - items_->insert(containedItem); + auto insertAndCheckForAmbiguous = [](Item& item, std::set& container) { + auto iter = container.find(item); + if (iter != container.end()) { + item.setIndex(ProductResolverIndexAmbiguous); + container.erase(iter); + } + container.insert(item); + }; - containedItem.clearProcess(); - iter = items_->find(containedItem); - if (iter == items_->end()) { - containedItem.setIndex(ProductResolverIndexInitializing); - items_->insert(containedItem); - containedItem.setSkipCurrentProcess(); - containedItem.setIndex(ProductResolverIndexInitializing); - items_->insert(containedItem); - } + Item containedItem(ELEMENT_TYPE, containedTypeID, moduleLabel, instance, process, savedProductIndex); + insertAndCheckForAmbiguous(containedItem, *items_); + insertNoProcessCase(containedItem, *items_); // Repeat this for all public base classes of the contained type if (baseTypesOfContainedType) { for (TypeID const& baseTypeID : *baseTypesOfContainedType) { Item baseItem(ELEMENT_TYPE, baseTypeID, moduleLabel, instance, process, savedProductIndex); - iter = items_->find(baseItem); - if (iter != items_->end()) { - baseItem.setIndex(ProductResolverIndexAmbiguous); - items_->erase(iter); - } - items_->insert(baseItem); - - baseItem.clearProcess(); - iter = items_->find(baseItem); - if (iter == items_->end()) { - baseItem.setIndex(ProductResolverIndexInitializing); - items_->insert(baseItem); - baseItem.setSkipCurrentProcess(); - baseItem.setIndex(ProductResolverIndexInitializing); - items_->insert(baseItem); - } + insertAndCheckForAmbiguous(baseItem, *items_); + insertNoProcessCase(baseItem, *items_); } } } @@ -312,31 +296,40 @@ namespace edm { std::vector::iterator itEnd, std::vector const& orderedProcessNames, std::vector const& processNames) { + /*The order of the iterators should be + 0 : the empty process name case -> '' + 1 : the skip current process case -> '#' + 2+: the cases with a specific process name*/ using IndexAndNames = edm::ProductResolverIndexHelper::IndexAndNames; assert(itEnd - itBegin > 2); - assert(itBegin->startInProcessNames() == 0U); - assert((itBegin + 1)->startInProcessNames() == 1U); - assert(processNames[(itBegin + 1)->startInProcessNames()] == '#'); - assert(itBegin->index() == edm::ProductResolverIndexInitializing); - assert((itBegin + 1)->index() == edm::ProductResolverIndexInitializing); + const auto itNoProcess = itBegin; + const auto itSkipCurrentProcess = itBegin + 1; + const auto itFirstWithSetProcess = itBegin + 2; + assert(itNoProcess->startInProcessNames() == 0U); + assert(itSkipCurrentProcess->startInProcessNames() == 1U); + assert(processNames[itSkipCurrentProcess->startInProcessNames()] == '#'); + assert(itNoProcess->index() == edm::ProductResolverIndexInitializing); + assert(itSkipCurrentProcess->index() == edm::ProductResolverIndexInitializing); if (itEnd - itBegin == 3) { //only have one actual process - *itBegin = - IndexAndNames((itBegin + 2)->index(), itBegin->startInBigNamesContainer(), itBegin->startInProcessNames()); + *itNoProcess = IndexAndNames(itFirstWithSetProcess->index(), + itNoProcess->startInBigNamesContainer(), + itNoProcess->startInProcessNames()); //Now handle skipCurrentProcess - if (orderedProcessNames[0] == &processNames[(itBegin + 2)->startInProcessNames()]) { + if (orderedProcessNames[0] == &processNames[itFirstWithSetProcess->startInProcessNames()]) { //the one process is the current process - *(itBegin + 1) = IndexAndNames(ProductResolverIndexInvalid, - (itBegin + 1)->startInBigNamesContainer(), - (itBegin + 1)->startInProcessNames()); + *itSkipCurrentProcess = IndexAndNames(ProductResolverIndexInvalid, + itSkipCurrentProcess->startInBigNamesContainer(), + itSkipCurrentProcess->startInProcessNames()); } else { - *(itBegin + 1) = IndexAndNames( - (itBegin + 2)->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + *itSkipCurrentProcess = IndexAndNames(itFirstWithSetProcess->index(), + itSkipCurrentProcess->startInBigNamesContainer(), + itSkipCurrentProcess->startInProcessNames()); } } else { bool foundFirstMatch = false; for (auto const& proc : orderedProcessNames) { - auto it = itBegin + 2; + auto it = itFirstWithSetProcess; while (it != itEnd && proc != &processNames[it->startInProcessNames()]) { ++it; } @@ -344,22 +337,24 @@ namespace edm { if (not foundFirstMatch) { foundFirstMatch = true; //found a process that matches - *itBegin = - IndexAndNames(it->index(), itBegin->startInBigNamesContainer(), itBegin->startInProcessNames()); + *itNoProcess = IndexAndNames( + it->index(), itNoProcess->startInBigNamesContainer(), itNoProcess->startInProcessNames()); //Now handle skipCurrentProcess if (proc != orderedProcessNames[0]) { - *(itBegin + 1) = IndexAndNames( - it->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + *itSkipCurrentProcess = IndexAndNames(it->index(), + itSkipCurrentProcess->startInBigNamesContainer(), + itSkipCurrentProcess->startInProcessNames()); break; } else { //this process is the current process - *(itBegin + 1) = IndexAndNames(ProductResolverIndexInvalid, - (itBegin + 1)->startInBigNamesContainer(), - (itBegin + 1)->startInProcessNames()); + *itSkipCurrentProcess = IndexAndNames(ProductResolverIndexInvalid, + itSkipCurrentProcess->startInBigNamesContainer(), + itSkipCurrentProcess->startInProcessNames()); } } else { - *(itBegin + 1) = IndexAndNames( - it->index(), (itBegin + 1)->startInBigNamesContainer(), (itBegin + 1)->startInProcessNames()); + *itSkipCurrentProcess = IndexAndNames(it->index(), + itSkipCurrentProcess->startInBigNamesContainer(), + itSkipCurrentProcess->startInProcessNames()); break; } } From 857254111ff82da5cc05e9e451a0a55f6e3d4d0d Mon Sep 17 00:00:00 2001 From: Christopher Jones Date: Thu, 28 Aug 2025 15:08:36 -0500 Subject: [PATCH 13/13] Fix getting data from MixingModule The MixingModule does not use consumes when getting data from the mixing files. --- FWCore/Framework/src/Principal.cc | 3 +++ Mixing/Base/src/PileUp.cc | 1 + 2 files changed, 4 insertions(+) diff --git a/FWCore/Framework/src/Principal.cc b/FWCore/Framework/src/Principal.cc index 6bc48f1492127..3a893b111b3c3 100644 --- a/FWCore/Framework/src/Principal.cc +++ b/FWCore/Framework/src/Principal.cc @@ -495,6 +495,9 @@ namespace edm { inputTag.instance(), appendCurrentProcessIfAlias(inputTag.process(), processConfiguration_->processName())); } else if (index == ProductResolverIndexInvalid) { + if (not consumer) { + return nullptr; + } // can occur because of missing consumes if nothing else in the process consumes the product for (auto const& item : preg_->productList()) { auto const& bd = item.second; diff --git a/Mixing/Base/src/PileUp.cc b/Mixing/Base/src/PileUp.cc index d289cc0619f33..3ad58d69ab779 100644 --- a/Mixing/Base/src/PileUp.cc +++ b/Mixing/Base/src/PileUp.cc @@ -124,6 +124,7 @@ namespace edm { provider_ = std::make_unique(producers, filler, processConfiguration_); } + filler.setCurrentProcess(processConfiguration_->processName()); filler.addFromInput(*input_->productRegistry()); filler.setFrozen(); productRegistry_ = std::make_shared(filler.moveTo());