Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-05-11 03:34:14

0001 // -*- C++ -*-
0002 //
0003 // Package:     Framework
0004 // Class  :     ESProductResolver
0005 //
0006 // Implementation:
0007 //     <Notes on implementation>
0008 //
0009 // Author:      Chris Jones
0010 // Created:     Thu Mar 31 12:49:19 EST 2005
0011 //
0012 
0013 #include "FWCore/Framework/interface/ESProductResolver.h"
0014 #include "FWCore/Framework/interface/ComponentDescription.h"
0015 #include "FWCore/Framework/interface/MakeDataException.h"
0016 #include "FWCore/Framework/interface/EventSetupRecordImpl.h"
0017 #include "FWCore/Utilities/interface/Likely.h"
0018 
0019 namespace edm {
0020   namespace eventsetup {
0021 
0022     static const ComponentDescription* dummyDescription() {
0023       static const ComponentDescription s_desc;
0024       return &s_desc;
0025     }
0026 
0027     ESProductResolver::ESProductResolver()
0028         : description_(dummyDescription()),
0029           cache_(nullptr),
0030           cacheIsValid_(false),
0031           nonTransientAccessRequested_(false) {}
0032 
0033     ESProductResolver::~ESProductResolver() {}
0034 
0035     void ESProductResolver::clearCacheIsValid() {
0036       nonTransientAccessRequested_.store(false, std::memory_order_release);
0037       cache_ = nullptr;
0038       cacheIsValid_.store(false, std::memory_order_release);
0039     }
0040 
0041     void ESProductResolver::resetIfTransient() {
0042       if (!nonTransientAccessRequested_.load(std::memory_order_acquire)) {
0043         clearCacheIsValid();
0044         invalidateTransientCache();
0045       }
0046     }
0047 
0048     void ESProductResolver::invalidateTransientCache() { invalidateCache(); }
0049 
0050     namespace {
0051       void throwMakeException(const EventSetupRecordImpl& iRecord, const DataKey& iKey) {
0052         throw MakeDataException(iRecord.key(), iKey);
0053       }
0054 
0055     }  // namespace
0056 
0057     void ESProductResolver::prefetchAsync(WaitingTaskHolder iTask,
0058                                           EventSetupRecordImpl const& iRecord,
0059                                           DataKey const& iKey,
0060                                           EventSetupImpl const* iEventSetupImpl,
0061                                           ServiceToken const& iToken,
0062                                           ESParentContext const& iParent) const noexcept {
0063       const_cast<ESProductResolver*>(this)->prefetchAsyncImpl(iTask, iRecord, iKey, iEventSetupImpl, iToken, iParent);
0064     }
0065 
0066     void const* ESProductResolver::getAfterPrefetch(const EventSetupRecordImpl& iRecord,
0067                                                     const DataKey& iKey,
0068                                                     bool iTransiently) const {
0069       //We need to set the AccessType for each request so this can't be called in an earlier function in the stack.
0070       //This also must be before the cache_ check since we want to setCacheIsValid before a possible
0071       // exception throw. If we don't, 'getImpl' will be called again on a second request for the data.
0072 
0073       if LIKELY (!iTransiently) {
0074         nonTransientAccessRequested_.store(true, std::memory_order_release);
0075       }
0076 
0077       if UNLIKELY (!cacheIsValid()) {
0078         cache_ = getAfterPrefetchImpl();
0079         cacheIsValid_.store(true, std::memory_order_release);
0080       }
0081 
0082       if UNLIKELY (nullptr == cache_) {
0083         throwMakeException(iRecord, iKey);
0084       }
0085       return cache_;
0086     }
0087 
0088   }  // namespace eventsetup
0089 }  // namespace edm