CMS 3D CMS Logo

DataProxy.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: Framework
4 // Class : DataProxy
5 //
6 // Implementation:
7 // <Notes on implementation>
8 //
9 // Author: Chris Jones
10 // Created: Thu Mar 31 12:49:19 EST 2005
11 //
12 
13 // system include files
14 #include <mutex>
15 
16 // user include files
22 
23 //
24 // constants, enums and typedefs
25 //
26 namespace edm {
27  namespace eventsetup {
28  static std::recursive_mutex s_esGlobalMutex;
29  //
30  // static data member definitions
31  //
33  static ComponentDescription s_desc;
34  return &s_desc;
35  }
36  //
37  // constructors and destructor
38  //
40  : cache_(nullptr),
41  cacheIsValid_(false),
42  nonTransientAccessRequested_(false),
43  description_(dummyDescription()) {}
44 
45  // DataProxy::DataProxy(const DataProxy& rhs)
46  // {
47  // // do actual copying here;
48  // }
49 
51 
52  //
53  // assignment operators
54  //
55  // const DataProxy& DataProxy::operator=(const DataProxy& rhs)
56  // {
57  // //An exception safe implementation is
58  // DataProxy temp(rhs);
59  // swap(rhs);
60  //
61  // return *this;
62  // }
63 
64  //
65  // member functions
66  //
68  cacheIsValid_.store(false, std::memory_order_release);
69  nonTransientAccessRequested_.store(false, std::memory_order_release);
70  cache_ = nullptr;
71  }
72 
74  if (!nonTransientAccessRequested_.load(std::memory_order_acquire)) {
77  }
78  }
79 
81  //
82  // const member functions
83  //
84  namespace {
85  void throwMakeException(const EventSetupRecordImpl& iRecord, const DataKey& iKey) {
86  throw MakeDataException(iRecord.key(), iKey);
87  }
88 
89  class ESSignalSentry {
90  public:
91  ESSignalSentry(const EventSetupRecordImpl& iRecord,
92  const DataKey& iKey,
93  ComponentDescription const* componentDescription,
94  ActivityRegistry const* activityRegistry)
95  : eventSetupRecord_(iRecord),
96  dataKey_(iKey),
97  componentDescription_(componentDescription),
98  calledPostLock_(false),
99  activityRegistry_(activityRegistry) {
101  }
102  void sendPostLockSignal() {
103  calledPostLock_ = true;
104  activityRegistry_->postLockEventSetupGetSignal_(componentDescription_, eventSetupRecord_.key(), dataKey_);
105  }
106  ~ESSignalSentry() noexcept(false) {
107  if (!calledPostLock_) {
108  activityRegistry_->postLockEventSetupGetSignal_(componentDescription_, eventSetupRecord_.key(), dataKey_);
109  }
110  activityRegistry_->postEventSetupGetSignal_(componentDescription_, eventSetupRecord_.key(), dataKey_);
111  }
112 
113  private:
116  ComponentDescription const* componentDescription_;
119  };
120  } // namespace
121 
122  const void* DataProxy::get(const EventSetupRecordImpl& iRecord,
123  const DataKey& iKey,
124  bool iTransiently,
125  ActivityRegistry const* activityRegistry) const {
126  if (!cacheIsValid()) {
127  ESSignalSentry signalSentry(iRecord, iKey, providerDescription(), activityRegistry);
128  std::lock_guard<std::recursive_mutex> guard(s_esGlobalMutex);
129  signalSentry.sendPostLockSignal();
130  if (!cacheIsValid()) {
131  cache_ = const_cast<DataProxy*>(this)->getImpl(iRecord, iKey);
132  cacheIsValid_.store(true, std::memory_order_release);
133  }
134  }
135  //We need to set the AccessType for each request so this can't be called in the if block above.
136  //This also must be before the cache_ check since we want to setCacheIsValid before a possible
137  // exception throw. If we don't, 'getImpl' will be called again on a second request for the data.
138  if (!iTransiently) {
139  nonTransientAccessRequested_.store(true, std::memory_order_release);
140  }
141 
142  if (nullptr == cache_) {
143  throwMakeException(iRecord, iKey);
144  }
145  return cache_;
146  }
147 
149  const DataKey& iKey,
150  bool iTransiently,
151  ActivityRegistry const* activityRegistry) const {
152  get(iRecord, iKey, iTransiently, activityRegistry);
153  }
154 
155  //
156  // static member functions
157  //
158  } // namespace eventsetup
159 } // namespace edm
ActivityRegistry const * activityRegistry_
Definition: DataProxy.cc:118
bool cacheIsValid() const
Definition: DataProxy.h:43
void const * get(EventSetupRecordImpl const &, DataKey const &iKey, bool iTransiently, ActivityRegistry const *) const
Definition: DataProxy.cc:122
ComponentDescription const * componentDescription_
Definition: DataProxy.cc:116
#define nullptr
virtual void invalidateTransientCache()
Definition: DataProxy.cc:80
DataKey const & dataKey_
Definition: DataProxy.cc:115
std::atomic< bool > nonTransientAccessRequested_
Definition: DataProxy.h:99
PreLockEventSetupGet preLockEventSetupGetSignal_
signal is emitted before lock taken in EventSetup DataProxy::get function
void doGet(EventSetupRecordImpl const &iRecord, DataKey const &iKey, bool iTransiently, ActivityRegistry const *) const
Definition: DataProxy.cc:148
bool calledPostLock_
Definition: DataProxy.cc:117
std::atomic< bool > cacheIsValid_
Definition: DataProxy.h:98
virtual void const * getImpl(EventSetupRecordImpl const &, DataKey const &iKey)=0
#define noexcept
ComponentDescription const * providerDescription() const
returns the description of the DataProxyProvider which owns this Proxy
Definition: DataProxy.h:55
HLT enums.
EventSetupRecordImpl const & eventSetupRecord_
Definition: DataProxy.cc:114
static std::recursive_mutex s_esGlobalMutex
Definition: DataProxy.cc:28
static const ComponentDescription * dummyDescription()
Definition: DataProxy.cc:32
virtual void invalidateCache()=0
EventSetupRecordKey const & key() const