From 548496fa2e5edb915f276d48bfcdb7d2c70da328 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ion=20Gazta=C3=B1aga?= Date: Wed, 21 Jan 2026 13:43:31 +0100 Subject: [PATCH] Fixes #328 ("boost::container::deque stores a redundant copy of the allocator, increasing size") --- doc/container.qbk | 2 ++ include/boost/container/deque.hpp | 37 +++++++++---------------------- 2 files changed, 12 insertions(+), 27 deletions(-) diff --git a/doc/container.qbk b/doc/container.qbk index d20b256..7d0a249 100644 --- a/doc/container.qbk +++ b/doc/container.qbk @@ -1458,9 +1458,11 @@ use [*Boost.Container]? There are several reasons for that: * Implemented overaligned allocation support for `new_allocator` and `pmr::new_delete_resource()`: * If available, uses C++17's utilities under the `__cpp_aligned_new` feature. * Uses alternative aligned allocation functions (`posix_memalign`, `aligned_alloc`, `_aligned_malloc`...) otherwise. +* Implemented overaligned allocation support for `adaptive_pool`and `node_allocator` * Updated `basic_string` to the latest standard API: Added missing `string_view` members and updated `operator[]` to be able to return the terminating null. * Fixed bugs/issues: * [@https://github.com/boostorg/container/issues/323 GitHub #323: ['"flat_tree::try_emplace UB"]]. + * [@https://github.com/boostorg/container/issues/328 GitHub #328: ['"boost::container::deque stores a redundant copy of the allocator, increasing size"]]. [endsect] diff --git a/include/boost/container/deque.hpp b/include/boost/container/deque.hpp index 87cf8f2..ac5935a 100644 --- a/include/boost/container/deque.hpp +++ b/include/boost/container/deque.hpp @@ -420,7 +420,6 @@ class deque_base { return deque_block_traits::value; } typedef deque_value_traits traits_t; - typedef ptr_alloc_t map_allocator_type; inline val_alloc_ptr prot_allocate_node() { @@ -434,12 +433,14 @@ class deque_base inline ptr_alloc_ptr prot_allocate_map(size_type n) { - return this->ptr_alloc().allocate(n); + ptr_alloc_t palloc(this->alloc()); + return palloc.allocate(n); } inline void prot_deallocate_map(ptr_alloc_ptr p, size_type n) BOOST_NOEXCEPT_OR_NOTHROW { - this->ptr_alloc().deallocate(p, n); + ptr_alloc_t palloc(this->alloc()); + return palloc.deallocate(p, n); } inline deque_base(size_type num_elements, const allocator_type& a) @@ -455,8 +456,7 @@ class deque_base {} inline explicit deque_base(BOOST_RV_REF(deque_base) x) - : members_( boost::move(x.ptr_alloc()) - , boost::move(x.alloc()) ) + : members_( boost::move(x.alloc()) ) {} ~deque_base() @@ -714,26 +714,18 @@ class deque_base protected: struct members_holder - : public ptr_alloc_t - , public allocator_type + : public allocator_type { friend class deque_base; members_holder() - : map_allocator_type(), allocator_type() + : allocator_type() , m_map(), m_map_size() , m_start_off(), m_finish_off() {} - explicit members_holder(const allocator_type &a) - : map_allocator_type(a), allocator_type(a) - , m_map(), m_map_size() - , m_start_off(), m_finish_off() - {} - - template - members_holder(BOOST_FWD_REF(PtrAllocConvertible) pa, BOOST_FWD_REF(ValAllocConvertible) va) - : map_allocator_type(boost::forward(pa)) - , allocator_type (boost::forward(va)) + template + explicit members_holder(BOOST_FWD_REF(ValAllocConvertible) va) + : allocator_type(boost::forward(va)) , m_map(), m_map_size() , m_start_off(), m_finish_off() {} @@ -753,12 +745,6 @@ class deque_base stored_size_type m_finish_off; } members_; - inline ptr_alloc_t &ptr_alloc() BOOST_NOEXCEPT_OR_NOTHROW - { return members_; } - - inline const ptr_alloc_t &ptr_alloc() const BOOST_NOEXCEPT_OR_NOTHROW - { return members_; } - inline allocator_type &alloc() BOOST_NOEXCEPT_OR_NOTHROW { return members_; } @@ -1335,7 +1321,6 @@ class deque : protected deque_base::type, this->shrink_to_fit(); } dtl::assign_alloc(this->alloc(), x.alloc(), flag); - dtl::assign_alloc(this->ptr_alloc(), x.ptr_alloc(), flag); this->assign(x.cbegin(), x.cend()); } return *this; @@ -2400,7 +2385,6 @@ class deque : protected deque_base::type, this->swap_members(x); dtl::bool_ flag; dtl::swap_alloc(this->alloc(), x.alloc(), flag); - dtl::swap_alloc(this->ptr_alloc(), x.ptr_alloc(), flag); } //! Effects: Erases all the elements of the deque. @@ -2504,7 +2488,6 @@ class deque : protected deque_base::type, //Move allocator if needed dtl::bool_ flag; dtl::move_alloc(this->alloc(), x.alloc(), flag); - dtl::move_alloc(this->ptr_alloc(), x.ptr_alloc(), flag); //Nothrow swap this->swap_members(x); }