diff options
Diffstat (limited to 'src/lib/netlist/plib')
-rw-r--r-- | src/lib/netlist/plib/gmres.h | 12 | ||||
-rw-r--r-- | src/lib/netlist/plib/mat_cr.h | 2 | ||||
-rw-r--r-- | src/lib/netlist/plib/palloc.h | 83 | ||||
-rw-r--r-- | src/lib/netlist/plib/parray.h | 5 | ||||
-rw-r--r-- | src/lib/netlist/plib/pconfig.h | 14 | ||||
-rw-r--r-- | src/lib/netlist/plib/pmempool.h | 102 |
6 files changed, 164 insertions, 54 deletions
diff --git a/src/lib/netlist/plib/gmres.h b/src/lib/netlist/plib/gmres.h index 9be0dd99a96..ecdc093ff17 100644 --- a/src/lib/netlist/plib/gmres.h +++ b/src/lib/netlist/plib/gmres.h @@ -75,11 +75,13 @@ namespace plib } } - mat_type m_mat; - mat_type m_LU; - bool m_use_iLU_preconditioning; - std::size_t m_ILU_scale; - std::size_t m_band_width; + PALIGNAS_VECTOROPT() + mat_type m_mat; + PALIGNAS_VECTOROPT() + mat_type m_LU; + bool m_use_iLU_preconditioning; + std::size_t m_ILU_scale; + std::size_t m_band_width; }; template <typename FT, int SIZE> diff --git a/src/lib/netlist/plib/mat_cr.h b/src/lib/netlist/plib/mat_cr.h index be2d730b215..3cf2570b725 100644 --- a/src/lib/netlist/plib/mat_cr.h +++ b/src/lib/netlist/plib/mat_cr.h @@ -72,7 +72,7 @@ namespace plib ~matrix_compressed_rows_t() = default; - constexpr index_type size() const { return (N>0) ? N : m_size; } + constexpr index_type size() const { return static_cast<index_type>((N>0) ? N : m_size); } void set_scalar(const T scalar) { diff --git a/src/lib/netlist/plib/palloc.h b/src/lib/netlist/plib/palloc.h index da404be279f..793ad1ce553 100644 --- a/src/lib/netlist/plib/palloc.h +++ b/src/lib/netlist/plib/palloc.h @@ -46,40 +46,37 @@ namespace plib { delete [] ptr; } - template<typename T, typename... Args> - std::unique_ptr<T> make_unique(Args&&... args) - { - return std::unique_ptr<T>(new T(std::forward<Args>(args)...)); - } - - template<typename BC, typename DC, typename... Args> - std::unique_ptr<BC> make_unique_base(Args&&... args) - { - std::unique_ptr<BC> ret(new DC(std::forward<Args>(args)...)); - return ret; - } - - template <typename SC> + template <typename SC, typename D = std::default_delete<SC>> class owned_ptr { - private: + public: owned_ptr() : m_ptr(nullptr), m_is_owned(true) { } - public: + + template <typename, typename> + friend class owned_ptr; + owned_ptr(SC *p, bool owned) noexcept - : m_ptr(p), m_is_owned(owned) + : m_ptr(p), m_deleter(), m_is_owned(owned) + { } + + owned_ptr(SC *p, bool owned, D deleter) noexcept + : m_ptr(p), m_deleter(deleter), m_is_owned(owned) { } + owned_ptr(const owned_ptr &r) = delete; owned_ptr & operator =(owned_ptr &r) = delete; - template<typename DC> - owned_ptr & operator =(owned_ptr<DC> &&r) + template<typename DC, typename DC_D> + owned_ptr & operator =(owned_ptr<DC, DC_D> &&r) { if (m_is_owned && (m_ptr != nullptr)) - delete m_ptr; + //delete m_ptr; + m_deleter(m_ptr); m_is_owned = r.m_is_owned; m_ptr = r.m_ptr; + m_deleter = r.m_deleter; r.m_is_owned = false; r.m_ptr = nullptr; return *this; @@ -89,50 +86,43 @@ namespace plib { { m_is_owned = r.m_is_owned; m_ptr = r.m_ptr; + m_deleter = r.m_deleter; r.m_is_owned = false; r.m_ptr = nullptr; } owned_ptr &operator=(owned_ptr &&r) noexcept { + if (m_is_owned && (m_ptr != nullptr)) + //delete m_ptr; + m_deleter(m_ptr); m_is_owned = r.m_is_owned; m_ptr = r.m_ptr; + m_deleter = r.m_deleter; r.m_is_owned = false; r.m_ptr = nullptr; return *this; } - template<typename DC> - owned_ptr(owned_ptr<DC> &&r) noexcept + template<typename DC, typename DC_D> + owned_ptr(owned_ptr<DC, DC_D> &&r) noexcept { m_ptr = static_cast<SC *>(r.get()); m_is_owned = r.is_owned(); + m_deleter = r.m_deleter; r.release(); } ~owned_ptr() { if (m_is_owned && (m_ptr != nullptr)) - delete m_ptr; + { + //delete m_ptr; + m_deleter(m_ptr); + } m_is_owned = false; m_ptr = nullptr; } - template<typename DC, typename... Args> - static owned_ptr Create(Args&&... args) - { - owned_ptr a; - auto *x = new DC(std::forward<Args>(args)...); - a.m_ptr = static_cast<SC *>(x); - return std::move(a); - } - - template<typename... Args> - static owned_ptr Create(Args&&... args) - { - owned_ptr a; - a.m_ptr = new SC(std::forward<Args>(args)...); - return std::move(a); - } SC * release() { SC *tmp = m_ptr; @@ -148,9 +138,24 @@ namespace plib { SC * get() const { return m_ptr; } private: SC *m_ptr; + D m_deleter; bool m_is_owned; }; + + template<typename T, typename... Args> + std::unique_ptr<T> make_unique(Args&&... args) + { + return std::unique_ptr<T>(new T(std::forward<Args>(args)...)); + } + + template<typename T, typename... Args> + static owned_ptr<T> make_owned(Args&&... args) + { + owned_ptr<T> a(new T(std::forward<Args>(args)...), true); + return std::move(a); + } + } // namespace plib #endif /* PALLOC_H_ */ diff --git a/src/lib/netlist/plib/parray.h b/src/lib/netlist/plib/parray.h index e3e15df5539..5fded97d1e9 100644 --- a/src/lib/netlist/plib/parray.h +++ b/src/lib/netlist/plib/parray.h @@ -109,8 +109,9 @@ namespace plib { const FT * data() const noexcept { return m_a.data(); } private: - base_type m_a; - size_type m_size; + PALIGNAS_VECTOROPT() + base_type m_a; + size_type m_size; }; } // namespace plib diff --git a/src/lib/netlist/plib/pconfig.h b/src/lib/netlist/plib/pconfig.h index 71a5f25e0e8..cc92a42c827 100644 --- a/src/lib/netlist/plib/pconfig.h +++ b/src/lib/netlist/plib/pconfig.h @@ -33,6 +33,20 @@ #define PHAS_INT128 (0) #endif +/* + * Standard alignment macros + */ + +#define PALIGNAS_CACHELINE() PALIGNAS(64) +#define PALIGNAS_VECTOROPT() PALIGNAS(64) + +/* Breaks mame build on windows due to -Wattribute */ +#if defined(_WIN32) && defined(__GNUC__) +#define PALIGNAS(x) +#else +#define PALIGNAS(x) alignas(x) +#endif + /*============================================================ * Check for CPP Version * diff --git a/src/lib/netlist/plib/pmempool.h b/src/lib/netlist/plib/pmempool.h index 2e15076b477..f5691aa2c43 100644 --- a/src/lib/netlist/plib/pmempool.h +++ b/src/lib/netlist/plib/pmempool.h @@ -1,7 +1,7 @@ // license:GPL-2.0+ // copyright-holders:Couriersud /* - * palloc.h + * pmempool.h * */ @@ -89,25 +89,28 @@ namespace plib { { } - COPYASSIGNMOVE(mempool, delete) ~mempool() { + for (auto & b : m_blocks) { if (b->m_num_alloc != 0) { + plib::perrlogger("Found {} info blocks\n", sinfo().size()); plib::perrlogger("Found block with {} dangling allocations\n", b->m_num_alloc); } ::operator delete(b->m_data); } } - - void *alloc(size_t size) + void *alloc(size_t size, size_t align) { - size_t rs = (size + m_min_align - 1) & ~(m_min_align - 1); + if (align < m_min_align) + align = m_min_align; + + size_t rs = (size + align - 1) & ~(align - 1); for (auto &b : m_blocks) { if (b->m_free > rs) @@ -115,8 +118,11 @@ namespace plib { b->m_free -= rs; b->m_num_alloc++; auto ret = reinterpret_cast<void *>(b->m_data + b->m_cur); + auto capacity(rs); + std::align(align, size, ret, capacity); sinfo().insert({ ret, info(b, b->m_cur)}); b->m_cur += rs; + return ret; } } @@ -125,15 +131,20 @@ namespace plib { b->m_num_alloc = 1; b->m_free = m_min_alloc - rs; auto ret = reinterpret_cast<void *>(b->m_data + b->m_cur); + auto capacity(rs); + std::align(align, size, ret, capacity); sinfo().insert({ ret, info(b, b->m_cur)}); b->m_cur += rs; return ret; } } - void free(void *ptr) + static void free(void *ptr) { - info i = sinfo().find(ptr)->second; + auto it = sinfo().find(ptr); + if (it == sinfo().end()) + printf("pointer not found\n"); + info i = it->second; block *b = i.m_block; if (b->m_num_alloc == 0) throw plib::pexception("mempool::free - double free was called\n"); @@ -143,11 +154,88 @@ namespace plib { //b->cur_ptr = b->data; } b->m_num_alloc--; + //printf("Freeing in block %p %lu\n", b, b->m_num_alloc); + sinfo().erase(it); } + template <typename T> + struct pool_deleter + { + constexpr pool_deleter() noexcept = default; + + template<typename U, typename = typename + std::enable_if<std::is_convertible< U*, T*>::value>::type> + pool_deleter(const pool_deleter<U>&) noexcept { } + + void operator()(T *p) const + { + p->~T(); + mempool::free(p); + } + }; + + template <typename T> + using poolptr = plib::owned_ptr<T, pool_deleter<T>>; + + template<typename T, typename... Args> + poolptr<T> make_poolptr(Args&&... args) + { + auto mem = this->alloc(sizeof(T), alignof(T)); + auto *obj = new (mem) T(std::forward<Args>(args)...); + poolptr<T> a(obj, true); + return std::move(a); + } }; + class mempool_default + { + private: + + size_t m_min_alloc; + size_t m_min_align; + + public: + + mempool_default(size_t min_alloc, size_t min_align) + : m_min_alloc(min_alloc), m_min_align(min_align) + { + } + + COPYASSIGNMOVE(mempool_default, delete) + + ~mempool_default() + { + } + + void *alloc(size_t size) + { + plib::unused_var(m_min_alloc); // -Wunused-private-field fires without + plib::unused_var(m_min_align); + + return ::operator new(size); + } + + static void free(void *ptr) + { + ::operator delete(ptr); + } + + template <typename T> + using poolptr = plib::owned_ptr<T>; + + template<typename T, typename... Args> + poolptr<T> make_poolptr(Args&&... args) + { + auto mem(alloc(sizeof(T))); + auto *obj = new (mem) T(std::forward<Args>(args)...); + poolptr<T> a(obj, true); + return std::move(a); + } + + }; + + } // namespace plib #endif /* PMEMPOOL_H_ */ |