diff options
Diffstat (limited to 'intern/cycles/util/util_vector.h')
-rw-r--r-- | intern/cycles/util/util_vector.h | 93 |
1 files changed, 66 insertions, 27 deletions
diff --git a/intern/cycles/util/util_vector.h b/intern/cycles/util/util_vector.h index cc6e8a371ed..92c3f116c69 100644 --- a/intern/cycles/util/util_vector.h +++ b/intern/cycles/util/util_vector.h @@ -11,7 +11,7 @@ * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and - * limitations under the License + * limitations under the License. */ #ifndef __UTIL_VECTOR_H__ @@ -22,31 +22,73 @@ #include <string.h> #include <vector> +#include "util_aligned_malloc.h" #include "util_types.h" -CCL_NAMESPACE_BEGIN +#ifdef WITH_CYCLES_DEBUG +# include "util_guarded_allocator.h" +#endif -using std::vector; +CCL_NAMESPACE_BEGIN -static inline void *malloc_aligned(size_t size, size_t alignment) +/* Vector + * + * Own subclass-ed vestion of std::vector. Subclass is needed because: + * + * - When building with WITH_CYCLES_DEBUG we need to use own allocator which + * keeps track of used/peak memory. + * + * - Have method to ensure capacity is re-set to 0. + */ +template<typename value_type> +class vector : public std::vector<value_type +#ifdef WITH_CYCLES_DEBUG + , GuardedAllocator<value_type> +#endif + > { - void *data = (void*)malloc(size + sizeof(void*) + alignment - 1); +public: +#ifdef WITH_CYCLES_DEBUG + typedef GuardedAllocator<value_type> allocator_type; +#else + typedef std::allocator<value_type> allocator_type; +#endif - union { void *ptr; size_t offset; } u; - u.ptr = (char*)data + sizeof(void*); - u.offset = (u.offset + alignment - 1) & ~(alignment - 1); - *(((void**)u.ptr) - 1) = data; + /* Default constructor. */ + explicit vector() : std::vector<value_type, allocator_type>() { } - return u.ptr; -} + /* Fill constructor. */ + explicit vector(size_t n, const value_type& val = value_type()) + : std::vector<value_type, allocator_type>(n, val) { } -static inline void free_aligned(void *ptr) -{ - if(ptr) { - void *data = *(((void**)ptr) - 1); - free(data); + /* Range constructor. */ + template <class InputIterator> + vector (InputIterator first, InputIterator last) + : std::vector<value_type, allocator_type>(first, last) { } + + /* Copy constructor. */ + vector(const vector &x) : std::vector<value_type, allocator_type>(x) { } + + void shrink_to_fit(void) + { +#if __cplusplus < 201103L + vector<value_type>().swap(*this); +#else + std::vector<value_type, allocator_type>::shrink_to_fit(); +#endif } -} + + void free_memory(void) { + std::vector<value_type, allocator_type>::resize(0); + shrink_to_fit(); + } + + /* Some external API might demand working with std::vector. */ + operator std::vector<value_type>() + { + return std::vector<value_type>(*this); + } +}; /* Array * @@ -74,7 +116,7 @@ public: datasize = 0; } else { - data = (T*)malloc_aligned(sizeof(T)*newsize, alignment); + data = (T*)util_aligned_malloc(sizeof(T)*newsize, alignment); datasize = newsize; } } @@ -91,7 +133,7 @@ public: datasize = 0; } else { - data = (T*)malloc_aligned(sizeof(T)*from.datasize, alignment); + data = (T*)util_aligned_malloc(sizeof(T)*from.datasize, alignment); memcpy(data, from.data, from.datasize*sizeof(T)); datasize = from.datasize; } @@ -105,10 +147,7 @@ public: data = NULL; if(datasize > 0) { - data = (T*)malloc_aligned(sizeof(T)*datasize, alignment); - memcpy(data, &from[0], datasize*sizeof(T)); - free_aligned(data); - data = (T*)malloc_aligned(sizeof(T)*datasize, alignment); + data = (T*)util_aligned_malloc(sizeof(T)*datasize, alignment); memcpy(data, &from[0], datasize*sizeof(T)); } @@ -117,7 +156,7 @@ public: ~array() { - free_aligned(data); + util_aligned_free(data); } void resize(size_t newsize) @@ -126,10 +165,10 @@ public: clear(); } else if(newsize != datasize) { - T *newdata = (T*)malloc_aligned(sizeof(T)*newsize, alignment); + T *newdata = (T*)util_aligned_malloc(sizeof(T)*newsize, alignment); if(data) { memcpy(newdata, data, ((datasize < newsize)? datasize: newsize)*sizeof(T)); - free_aligned(data); + util_aligned_free(data); } data = newdata; @@ -139,7 +178,7 @@ public: void clear() { - free_aligned(data); + util_aligned_free(data); data = NULL; datasize = 0; } |