summaryrefslogtreecommitdiff
path: root/src/common/alignment.h
diff options
context:
space:
mode:
authorGravatar Fernando Sahmkow2019-07-18 18:15:53 -0400
committerGravatar FernandoS272019-07-19 10:06:08 -0400
commit9bede4eeed523f9707a989f1297279c006086e76 (patch)
tree2acfabeff5f7f449bcdb22563f5ad66f7fa5f414 /src/common/alignment.h
parentMerge pull request #2687 from lioncash/tls-process (diff)
downloadyuzu-9bede4eeed523f9707a989f1297279c006086e76.tar.gz
yuzu-9bede4eeed523f9707a989f1297279c006086e76.tar.xz
yuzu-9bede4eeed523f9707a989f1297279c006086e76.zip
VM_Manager: Align allocated memory to 256bytes
This commit ensures that all backing memory allocated for the Guest CPU is aligned to 256 bytes. This due to how gpu memory works and the heavy constraints it has in the alignment of physical memory.
Diffstat (limited to 'src/common/alignment.h')
-rw-r--r--src/common/alignment.h79
1 files changed, 79 insertions, 0 deletions
diff --git a/src/common/alignment.h b/src/common/alignment.h
index 617b14d9b..b3fbdfe20 100644
--- a/src/common/alignment.h
+++ b/src/common/alignment.h
@@ -3,7 +3,10 @@
3#pragma once 3#pragma once
4 4
5#include <cstddef> 5#include <cstddef>
6#include <cstdlib>
6#include <type_traits> 7#include <type_traits>
8#include <malloc.h>
9#include <stdlib.h>
7 10
8namespace Common { 11namespace Common {
9 12
@@ -37,4 +40,80 @@ constexpr bool IsWordAligned(T value) {
37 return (value & 0b11) == 0; 40 return (value & 0b11) == 0;
38} 41}
39 42
43template <typename T, std::size_t Align = 16>
44class AlignmentAllocator {
45public:
46 typedef T value_type;
47 typedef std::size_t size_type;
48 typedef std::ptrdiff_t difference_type;
49
50 typedef T* pointer;
51 typedef const T* const_pointer;
52
53 typedef T& reference;
54 typedef const T& const_reference;
55
56public:
57 inline AlignmentAllocator() throw() {}
58
59 template <typename T2>
60 inline AlignmentAllocator(const AlignmentAllocator<T2, Align>&) throw() {}
61
62 inline ~AlignmentAllocator() throw() {}
63
64 inline pointer adress(reference r) {
65 return &r;
66 }
67
68 inline const_pointer adress(const_reference r) const {
69 return &r;
70 }
71
72#if (defined _MSC_VER)
73 inline pointer allocate(size_type n) {
74 return (pointer)_aligned_malloc(n * sizeof(value_type), Align);
75 }
76
77 inline void deallocate(pointer p, size_type) {
78 _aligned_free(p);
79 }
80#else
81 inline pointer allocate(size_type n) {
82 return (pointer)std::aligned_alloc(Align, n * sizeof(value_type));
83 }
84
85 inline void deallocate(pointer p, size_type) {
86 std::free(p);
87 }
88#endif
89
90 inline void construct(pointer p, const value_type& wert) {
91 new (p) value_type(wert);
92 }
93
94 inline void destroy(pointer p) {
95 p->~value_type();
96 }
97
98 inline size_type max_size() const throw() {
99 return size_type(-1) / sizeof(value_type);
100 }
101
102 template <typename T2>
103 struct rebind {
104 typedef AlignmentAllocator<T2, Align> other;
105 };
106
107 bool operator!=(const AlignmentAllocator<T, Align>& other) const {
108 return !(*this == other);
109 }
110
111 // Returns true if and only if storage allocated from *this
112 // can be deallocated from other, and vice versa.
113 // Always returns true for stateless allocators.
114 bool operator==(const AlignmentAllocator<T, Align>& other) const {
115 return true;
116 }
117};
118
40} // namespace Common 119} // namespace Common