Field3D
FieldCache.h
Go to the documentation of this file.
1 //----------------------------------------------------------------------------//
2 
3 /*
4  * Copyright (c) 2011 Sony Pictures Imageworks Inc
5  *
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  *
12  * Redistributions of source code must retain the above copyright
13  * notice, this list of conditions and the following disclaimer.
14  * Redistributions in binary form must reproduce the above copyright
15  * notice, this list of conditions and the following disclaimer in the
16  * documentation and/or other materials provided with the
17  * distribution. Neither the name of Sony Pictures Imageworks nor the
18  * names of its contributors may be used to endorse or promote
19  * products derived from this software without specific prior written
20  * permission.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
24  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
25  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
26  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
27  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
28  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
29  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
31  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
32  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
33  * OF THE POSSIBILITY OF SUCH DAMAGE.
34  */
35 
36 //----------------------------------------------------------------------------//
37 
42 //----------------------------------------------------------------------------//
43 
44 #ifndef _INCLUDED_Field3D_FieldCache_H_
45 #define _INCLUDED_Field3D_FieldCache_H_
46 
47 //----------------------------------------------------------------------------//
48 
49 #include <boost/thread/mutex.hpp>
50 #include <boost/foreach.hpp>
51 
52 #include "Field.h"
53 
54 //----------------------------------------------------------------------------//
55 
56 #include "ns.h"
57 
59 
60 //----------------------------------------------------------------------------//
61 // FieldCache
62 //----------------------------------------------------------------------------//
63 
64 /* \class FieldCache
65 
66  This class is used by Field3DInputFile::readField() to see if the
67  field being loaded already exists in memory. It uses the weak pointer
68  system in RefBase to check if a previously loaded field still resides
69  in memory. If it is, then readField() returns a pointer rather than
70  reading the data again from disk.
71 
72  \note FieldCache does not increment the reference count of cached fields,
73  so objects will be deallocated naturally.
74  */
75 
76 //----------------------------------------------------------------------------//
77 
78 template <typename Data_T>
80 {
81 public:
82 
83  // Typedefs ------------------------------------------------------------------
84 
86  typedef typename Field_T::Ptr FieldPtr;
87  typedef typename Field_T::WeakPtr WeakPtr;
88  typedef std::pair<WeakPtr, Field_T*> CacheEntry;
89  typedef std::map<std::string, CacheEntry> Cache;
90 
91  // Access to singleton -------------------------------------------------------
92 
94  static FieldCache& singleton();
95 
96  // Main methods --------------------------------------------------------------
97 
101  FieldPtr getCachedField(const std::string &filename,
102  const std::string &layerPath);
104  void cacheField(FieldPtr field, const std::string &filename,
105  const std::string &layerPath);
107  long long int memSize() const;
108 
109 private:
110 
111  // Utility functions --------------------------------------------------------
112 
114  std::string key(const std::string &filename,
115  const std::string &layerPath);
116 
117  // Data members -------------------------------------------------------------
118 
124  static boost::mutex ms_creationMutex;
126  static boost::mutex ms_accessMutex;
127 };
128 
129 //----------------------------------------------------------------------------//
130 // Implementations
131 //----------------------------------------------------------------------------//
132 
133 template <typename Data_T>
135 {
136  boost::mutex::scoped_lock lock(ms_creationMutex);
137  if (!ms_singleton) {
138  ms_singleton = new FieldCache;
139  }
140  return *ms_singleton;
141 }
142 
143 //----------------------------------------------------------------------------//
144 
145 template <typename Data_T>
147 FieldCache<Data_T>::getCachedField(const std::string &filename,
148  const std::string &layerPath)
149 {
150  boost::mutex::scoped_lock lock(ms_accessMutex);
151  // First see if the request has ever been processed
152  typename Cache::iterator i = m_cache.find(key(filename, layerPath));
153  if (i == m_cache.end()) {
154  return FieldPtr();
155  }
156  // Next, check if all weak_ptrs are valid
157  CacheEntry &entry = i->second;
158  WeakPtr weakPtr = entry.first;
159  if (weakPtr.expired()) {
160  return FieldPtr();
161  }
162  return FieldPtr(entry.second);
163 }
164 
165 //----------------------------------------------------------------------------//
166 
167 template <typename Data_T>
168 void FieldCache<Data_T>::cacheField(FieldPtr field, const std::string &filename,
169  const std::string &layerPath)
170 {
171  boost::mutex::scoped_lock lock(ms_accessMutex);
172  m_cache[key(filename, layerPath)] =
173  std::make_pair(field->weakPtr(), field.get());
174 }
175 
176 //----------------------------------------------------------------------------//
177 
178 template <typename Data_T>
179 long long int FieldCache<Data_T>::memSize() const
180 {
181  boost::mutex::scoped_lock lock(ms_accessMutex);
182 
183  long long int memSize = 0;
184 
185  BOOST_FOREACH (const typename Cache::value_type &i, m_cache) {
186  // Check if pointer is valid
187  WeakPtr weakPtr = i.second.first;
188  if (weakPtr.expired()) {
189  continue;
190  } else {
191  // If valid, accumulate memory
192  memSize += i.second.second->memSize();
193  }
194  }
195 
196  return memSize;
197 }
198 
199 //----------------------------------------------------------------------------//
200 
201 template <typename Data_T>
202 std::string FieldCache<Data_T>::key(const std::string &filename,
203  const std::string &layerPath)
204 {
205  return filename + "/" + layerPath;
206 }
207 
208 //----------------------------------------------------------------------------//
209 
211 
212 //----------------------------------------------------------------------------//
213 
214 #endif
FIELD3D_NAMESPACE_HEADER_CLOSE
#define FIELD3D_NAMESPACE_HEADER_CLOSE
Definition: ns.h:58
FieldCache::ms_accessMutex
static boost::mutex ms_accessMutex
Mutex to prevent reading from and writing to the cache concurrently.
Definition: FieldCache.h:126
Field::Ptr
boost::intrusive_ptr< Field > Ptr
Definition: Field.h:395
FieldCache::singleton
static FieldCache & singleton()
Returns a reference to the FieldCache singleton.
Definition: FieldCache.h:134
FieldCache::memSize
long long int memSize() const
Returns the memory use of all currently loaded fields.
Definition: FieldCache.h:179
FieldCache::key
std::string key(const std::string &filename, const std::string &layerPath)
Constructs the cache key for a given file and layer path.
Definition: FieldCache.h:202
FieldCache::CacheEntry
std::pair< WeakPtr, Field_T * > CacheEntry
Definition: FieldCache.h:88
FieldCache::m_cache
Cache m_cache
The cache itself. Maps a 'key' to a weak pointer and a raw pointer.
Definition: FieldCache.h:120
ns.h
FieldCache::WeakPtr
Field_T::WeakPtr WeakPtr
Definition: FieldCache.h:87
FieldCache::FieldPtr
Field_T::Ptr FieldPtr
Definition: FieldCache.h:86
Field.h
Contains Field, WritableField and ResizableField classes.
FieldCache::Field_T
Field< Data_T > Field_T
Definition: FieldCache.h:85
FieldCache::Cache
std::map< std::string, CacheEntry > Cache
Definition: FieldCache.h:89
FieldCache::getCachedField
FieldPtr getCachedField(const std::string &filename, const std::string &layerPath)
Checks the cache for a previously loaded field.
Definition: FieldCache.h:147
FieldCache::ms_creationMutex
static boost::mutex ms_creationMutex
Mutex to prevent multiple allocaation of the singleton.
Definition: FieldCache.h:124
FIELD3D_NAMESPACE_OPEN
Definition: FieldMapping.cpp:74
RefBase::WeakPtr
boost::weak_ptr< RefBase > WeakPtr
Definition: RefCount.h:113
FieldCache::cacheField
void cacheField(FieldPtr field, const std::string &filename, const std::string &layerPath)
Adds the given field to the cache.
Definition: FieldCache.h:168
FieldCache::ms_singleton
static FieldCache * ms_singleton
The singleton instance.
Definition: FieldCache.h:122
Field
Definition: Field.h:389
FieldCache
Definition: FieldCache.h:79