libvisiontransfer  4.1.5
alignedallocator.h
1 /*******************************************************************************
2  * Copyright (c) 2017 Nerian Vision Technologies
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a copy
5  * of this software and associated documentation files (the "Software"), to deal
6  * in the Software without restriction, including without limitation the rights
7  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8  * copies of the Software, and to permit persons to whom the Software is
9  * furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice shall be included in
12  * all copies or substantial portions of the Software.
13  *******************************************************************************/
14 
15 #ifndef ALIGNEDALLOCATOR_H
16 #define ALIGNEDALLOCATOR_H
17 
18 #include <cstdlib>
19 #include <memory>
20 #include <limits>
21 
28 template<typename T, int alignment = 32>
30 public :
31  // Typedefs
32  typedef T value_type;
33  typedef value_type* pointer;
34  typedef const value_type* const_pointer;
35  typedef value_type& reference;
36  typedef const value_type& const_reference;
37  typedef std::size_t size_type;
38  typedef std::ptrdiff_t difference_type;
39 
40  // convert an allocator<T> to allocator<U>
41  template<typename U>
42  struct rebind {
43  typedef AlignedAllocator<U> other;
44  };
45 
46  explicit AlignedAllocator() {}
47  ~AlignedAllocator() {}
48  explicit AlignedAllocator(AlignedAllocator const&) {}
49  template<typename U>
50  explicit AlignedAllocator(AlignedAllocator<U> const&) {}
51 
52  // Address
53  inline pointer address(reference r) { return &r; }
54  inline const_pointer address(const_reference r) { return &r; }
55 
56  // Memory allocation
57  pointer allocate(size_type cnt, typename std::allocator<void>::const_pointer = 0) {
58  // Allocate memory and align it
59  unsigned char* ptr = new unsigned char[sizeof(T) * cnt + (alignment-1) + 1];
60  unsigned char* alignedPtr = reinterpret_cast<unsigned char*>((size_t(ptr + 1) + alignment-1) & -alignment);
61 
62  // Store offset in allocated memory area
63  alignedPtr[-1] = static_cast<unsigned char>(alignedPtr - ptr);
64 
65  return reinterpret_cast<pointer>(alignedPtr);
66  }
67 
68  void deallocate(pointer p, size_type) {
69  // Get address of unaligned pointer
70  unsigned char* alignedPtr = reinterpret_cast<unsigned char*>(p);
71  unsigned char* unalignedPtr = alignedPtr - alignedPtr[-1];
72 
73  // Delete it
74  ::operator delete[](unalignedPtr);
75  }
76 
77  // Size
78  size_type max_size() const {
79  return std::numeric_limits<size_type>::max() / sizeof(T);
80  }
81 
82  // Construction
83  void construct(pointer p, const T& t) {
84  new(p) T(t);
85  }
86 
87  // Destruction
88  void destroy(pointer p) {
89  p->~T();
90  }
91 };
92 
93 #endif
STL-compatible allocator for memory-aligned allocations.
Nerian Vision Technologies