+2016-05-04 Jonathan Wakely <jwakely@redhat.com>
+
+ PR libstdc++/70940
+ * include/experimental/memory_resource
+ (__resource_adaptor_imp::do_allocate): Do not default-construct
+ rebound allocator.
+ (__resource_adaptor_imp::do_deallocate): Likewise. Use
+ allocator_traits to get pointer type.
+ (__null_memory_resource::do_allocate): Remove unused parameters.
+ (__null_memory_resource::do_deallocate): Likewise.
+ (__null_memory_resource::do_is_equal): Likewise. Add return statement.
+ * testsuite/experimental/type_erased_allocator/1.cc: Combine with ...
+ * testsuite/experimental/type_erased_allocator/1_neg.cc: This, and
+ move to ...
+ * testsuite/experimental/memory_resource/1.cc: Here.
+ * testsuite/experimental/memory_resource/null_memory_resource.cc: New.
+ * testsuite/experimental/memory_resource/resource_adaptor.cc: New.
+
2016-04-29 Chris Gregory <czipperz@gmail.com>
* config/*: Remove trailing whitespace.
size_t __new_size = _S_aligned_size(__bytes,
_S_supported(__alignment) ?
__alignment : _S_max_align);
- return _Aligned_alloc().allocate(__new_size);
+ return _Aligned_alloc(_M_alloc).allocate(__new_size);
}
virtual void
size_t __new_size = _S_aligned_size(__bytes,
_S_supported(__alignment) ?
__alignment : _S_max_align);
- _Aligned_alloc().deallocate(static_cast<typename
- _Aligned_alloc::pointer>(__p),
- __new_size);
+ using _Ptr = typename allocator_traits<_Aligned_alloc>::pointer;
+ _Aligned_alloc(_M_alloc).deallocate(static_cast<_Ptr>(__p),
+ __new_size);
}
virtual bool
private:
// Calculate Aligned Size
- // Returns a size that is larger than or equal to __size and divided by
- // __alignment, where __alignment is required to be the power of 2.
+ // Returns a size that is larger than or equal to __size and divisible
+ // by __alignment, where __alignment is required to be the power of 2.
static size_t
_S_aligned_size(size_t __size, size_t __alignment)
{ return ((__size - 1)|(__alignment - 1)) + 1; }
{
protected:
void*
- do_allocate(size_t __bytes, size_t __alignment)
+ do_allocate(size_t, size_t)
{ std::__throw_bad_alloc(); }
void
- do_deallocate(void* __p, size_t __bytes, size_t __alignment)
+ do_deallocate(void*, size_t, size_t) noexcept
{ }
bool
do_is_equal(const memory_resource& __other) const noexcept
- { }
+ { return this == &__other; }
friend memory_resource* null_memory_resource() noexcept;
};
--- /dev/null
+// { dg-options "-std=gnu++14" }
+
+// Copyright (C) 2015-2016 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#include <experimental/memory_resource>
+#include <vector>
+#include <cstdlib>
+#include <testsuite_hooks.h>
+#include <testsuite_allocator.h>
+
+using std::experimental::pmr::polymorphic_allocator;
+using std::experimental::pmr::memory_resource;
+using std::experimental::pmr::new_delete_resource;
+using std::experimental::pmr::get_default_resource;
+using std::experimental::pmr::set_default_resource;
+
+struct A
+{
+ A() { ++ctor_count; }
+ ~A() { ++dtor_count; }
+ static int ctor_count;
+ static int dtor_count;
+};
+
+int A::ctor_count = 0;
+int A::dtor_count = 0;
+
+struct CountedResource : public memory_resource
+{
+public:
+ CountedResource() = default;
+ ~CountedResource() = default;
+
+ static size_t get_alloc_count() { return alloc_count; }
+ static size_t get_dalloc_count() { return dalloc_count; }
+
+ static size_t alloc_count;
+ static size_t dalloc_count;
+protected:
+ void* do_allocate(size_t bytes, size_t alignment)
+ {
+ alloc_count += bytes;
+ if (auto ptr = std::malloc(bytes))
+ return ptr;
+ throw std::bad_alloc();
+ }
+
+ void do_deallocate(void *p, size_t bytes, size_t alignment)
+ {
+ dalloc_count += bytes;
+ std::free(p);
+ }
+
+ bool do_is_equal(const memory_resource& __other) const noexcept
+ { return this == &__other; }
+};
+
+size_t CountedResource::alloc_count = 0;
+size_t CountedResource::dalloc_count = 0;
+
+void clear()
+{
+ CountedResource::alloc_count = 0;
+ CountedResource::dalloc_count = 0;
+ A::ctor_count = 0;
+ A::dtor_count = 0;
+}
+
+// memory resource
+void
+test01()
+{
+ bool test __attribute((unused)) = false;
+
+ memory_resource* r = new_delete_resource();
+ VERIFY(get_default_resource() == r);
+ void *p = get_default_resource()->allocate(5);
+ VERIFY(p);
+ get_default_resource()->deallocate(p, 5);
+
+ clear();
+ CountedResource* cr = new CountedResource();
+ set_default_resource(cr);
+ VERIFY(get_default_resource() == cr);
+ void *pc = get_default_resource()->allocate(5);
+ VERIFY(pc);
+ get_default_resource()->deallocate(pc, 5);
+ VERIFY(CountedResource::get_alloc_count() == 5);
+ VERIFY(CountedResource::get_dalloc_count() == 5);
+}
+
+// polymorphic_allocator
+void
+test02()
+{
+ bool test __attribute((unused)) = false;
+
+ clear();
+ {
+ CountedResource cr;
+ polymorphic_allocator<A> pa(&cr);
+ std::vector<A, polymorphic_allocator<A>> v(5, A(), pa);
+ }
+ VERIFY(A::ctor_count == 1);
+ VERIFY(A::dtor_count == 6);
+ VERIFY(CountedResource::get_alloc_count() == 5);
+ VERIFY(CountedResource::get_dalloc_count() == 5);
+}
+
+void
+test03()
+{
+ bool test __attribute((unused)) = false;
+
+ clear();
+ CountedResource cr;
+ polymorphic_allocator<A> pa(&cr);
+ A* p = pa.allocate(1);
+ pa.construct(p);
+ pa.destroy(p);
+ pa.deallocate(p, 1);
+ VERIFY(A::ctor_count == 1);
+ VERIFY(A::dtor_count == 1);
+ VERIFY(CountedResource::get_alloc_count() == 1);
+ VERIFY(CountedResource::get_dalloc_count() == 1);
+}
+
+void
+test04()
+{
+ bool test __attribute((unused)) = false;
+
+ polymorphic_allocator<A> pa1(get_default_resource());
+ polymorphic_allocator<A> pa2(get_default_resource());
+ VERIFY(pa1 == pa2);
+ polymorphic_allocator<A> pa3 = pa2.select_on_container_copy_construction();
+ VERIFY(pa1 == pa3);
+}
+
+int main()
+{
+ test01();
+ test02();
+ test03();
+ test04();
+}
--- /dev/null
+// { dg-options "-std=gnu++14" }
+
+// Copyright (C) 2016 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#include <experimental/memory_resource>
+#include <testsuite_hooks.h>
+
+using std::experimental::pmr::memory_resource;
+using std::experimental::pmr::null_memory_resource;
+using std::experimental::pmr::new_delete_resource;
+
+// null_memory_resource
+void
+test06()
+{
+ bool test __attribute((unused)) = false;
+
+ memory_resource* r = null_memory_resource();
+ bool caught = false;
+
+ void* p = nullptr;
+ try {
+ p = r->allocate(1);
+ } catch (const std::bad_alloc&) {
+ caught = true;
+ }
+ VERIFY( caught );
+
+ VERIFY( *r == *r );
+ VERIFY( r->is_equal(*r) );
+ VERIFY( !r->is_equal(*new_delete_resource()) );
+}
+
+int main()
+{
+ test06();
+}
--- /dev/null
+// { dg-options "-std=gnu++14" }
+
+// Copyright (C) 2016 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#include <experimental/memory_resource>
+#include <testsuite_hooks.h>
+#include <testsuite_allocator.h>
+
+using std::experimental::pmr::memory_resource;
+using std::experimental::pmr::resource_adaptor;
+
+template<typename T>
+ struct Allocator : __gnu_test::SimpleAllocator<T>
+ {
+ Allocator(int) { } // not default constructible
+
+ template<typename U>
+ Allocator(const Allocator<U>&) { }
+ };
+
+template<typename T>
+ bool aligned(void* p)
+ {
+ return (reinterpret_cast<std::uintptr_t>(p) % alignof(T)) == 0;
+ }
+
+// resource_adaptor
+void
+test05()
+{
+ bool test __attribute((unused)) = false;
+ using std::max_align_t;
+ using std::uintptr_t;
+ void* p = nullptr;
+
+ Allocator<int> a1(1), a2(2); // minimal interface allocators
+ resource_adaptor<decltype(a1)> r1(a1), r2(a2);
+ VERIFY( r1 == r1 );
+ VERIFY( r1 == r2 );
+ p = r1.allocate(1);
+ VERIFY( aligned<max_align_t>(p) );
+ r1.deallocate(p, 1);
+ p = r1.allocate(1, alignof(short));
+ VERIFY( aligned<short>(p) );
+ r1.deallocate(p, 1, alignof(short));
+ p = r1.allocate(1, alignof(long));
+ VERIFY( aligned<long>(p) );
+ r1.deallocate(p, 1, alignof(long));
+
+ __gnu_test::uneq_allocator<double> a3(3), a4(4); // non-equal allocators
+ resource_adaptor<decltype(a3)> r3(a3), r4(a4);
+ VERIFY( r3 == r3 );
+ VERIFY( r4 == r4 );
+ VERIFY( r3 != r4 );
+ p = r3.allocate(1);
+ VERIFY( aligned<max_align_t>(p) );
+ r3.deallocate(p, 1);
+ p = r3.allocate(1, alignof(short));
+ VERIFY( aligned<short>(p) );
+ r3.deallocate(p, 1, alignof(short));
+ p = r3.allocate(1, alignof(long));
+ VERIFY( aligned<long>(p) );
+ r3.deallocate(p, 1, alignof(long));
+
+ // TODO test with an allocator that doesn't use new or malloc, so
+ // returns pointers that are not suitably aligned for any type.
+}
+
+int main()
+{
+ test05();
+}
+++ /dev/null
-// { dg-options "-std=gnu++14" }
-
-// Copyright (C) 2015-2016 Free Software Foundation, Inc.
-//
-// This file is part of the GNU ISO C++ Library. This library is free
-// software; you can redistribute it and/or modify it under the
-// terms of the GNU General Public License as published by the
-// Free Software Foundation; either version 3, or (at your option)
-// any later version.
-
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-// GNU General Public License for more details.
-
-// You should have received a copy of the GNU General Public License along
-// with this library; see the file COPYING3. If not see
-// <http://www.gnu.org/licenses/>.
-
-#include <memory>
-#include <experimental/memory_resource>
-#include <vector>
-#include <testsuite_hooks.h>
-#include <testsuite_allocator.h>
-
-using std::experimental::pmr::polymorphic_allocator;
-using std::experimental::pmr::memory_resource;
-using std::experimental::pmr::new_delete_resource;
-using std::experimental::pmr::get_default_resource;
-using std::experimental::pmr::set_default_resource;
-
-struct A
-{
- A() { ++ctor_count; }
- ~A() { ++dtor_count; }
- static int ctor_count;
- static int dtor_count;
-};
-int A::ctor_count = 0;
-int A::dtor_count = 0;
-
-struct CountedResource : public memory_resource
-{
-public:
- CountedResource() = default;
- ~ CountedResource() = default;
-
- static size_t get_alloc_count() { return alloc_count; }
- static size_t get_dalloc_count() { return dalloc_count; }
-
- static size_t alloc_count;
- static size_t dalloc_count;
-protected:
- void* do_allocate(size_t bytes, size_t alignment)
- {
- alloc_count += bytes;
- if (auto ptr = std::malloc(bytes)) {
- return ptr;
- }
- throw std::bad_alloc();
- }
-
- void do_deallocate(void *p, size_t bytes, size_t alignment)
- {
- dalloc_count += bytes;
- free(p);
- }
-
- bool do_is_equal(const memory_resource& __other) const noexcept
- { return this == &__other; }
-};
- size_t CountedResource::alloc_count = 0;
- size_t CountedResource::dalloc_count = 0;
-
-void clear()
-{
- CountedResource::alloc_count = 0;
- CountedResource::dalloc_count = 0;
- A::ctor_count = 0;
- A::dtor_count = 0;
-}
-
-// memory resource
-void test01()
-{
- memory_resource* r = new_delete_resource();
- VERIFY(get_default_resource() == r);
- void *p = get_default_resource()->allocate(5);
- VERIFY(p);
- get_default_resource()->deallocate(p, 5);
-
- clear();
- CountedResource* cr = new CountedResource();
- set_default_resource(cr);
- VERIFY(get_default_resource() == cr);
- void *pc = get_default_resource()->allocate(5);
- VERIFY(pc);
- get_default_resource()->deallocate(pc, 5);
- VERIFY(CountedResource::get_alloc_count() == 5);
- VERIFY(CountedResource::get_dalloc_count() == 5);
-}
-
-// polymorphic_allocator
-void test02()
-{
- clear();
- {
- CountedResource cr;
- polymorphic_allocator<A> pa(&cr);
- std::vector<A, polymorphic_allocator<A>> v(5, A(), pa);
- }
- VERIFY(A::ctor_count == 1);
- VERIFY(A::dtor_count == 6);
- VERIFY(CountedResource::get_alloc_count() == 5);
- VERIFY(CountedResource::get_dalloc_count() == 5);
-}
-
-void test03() {
- clear();
- CountedResource cr;
- polymorphic_allocator<A> pa(&cr);
- A* p = pa.allocate(1);
- pa.construct(p);
- pa.destroy(p);
- pa.deallocate(p, 1);
- VERIFY(A::ctor_count == 1);
- VERIFY(A::dtor_count == 1);
- VERIFY(CountedResource::get_alloc_count() == 1);
- VERIFY(CountedResource::get_dalloc_count() == 1);
-}
-
-void test04() {
- polymorphic_allocator<A> pa1(get_default_resource());
- polymorphic_allocator<A> pa2(get_default_resource());
- VERIFY(pa1 == pa2);
- polymorphic_allocator<A> pa3 = pa2.select_on_container_copy_construction();
- VERIFY(pa1 == pa3);
-}
-
-int main() {
- test01();
- test02();
- test03();
- test04();
- return 0;
-}
+++ /dev/null
-// { dg-do run { xfail *-*-* } }
-// { dg-options "-std=gnu++14" }
-
-// Copyright (C) 2015-2016 Free Software Foundation, Inc.
-//
-// This file is part of the GNU ISO C++ Library. This library is free
-// software; you can redistribute it and/or modify it under the
-// terms of the GNU General Public License as published by the
-// Free Software Foundation; either version 3, or (at your option)
-// any later version.
-
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-// GNU General Public License for more details.
-
-// You should have received a copy of the GNU General Public License along
-// with this library; see the file COPYING3. If not see
-// <http://www.gnu.org/licenses/>.
-
-#include <experimental/memory_resource>
-#include <testsuite_hooks.h>
-#include <testsuite_allocator.h>
-
-using std::experimental::pmr::polymorphic_allocator;
-using std::experimental::pmr::null_memory_resource;
-using std::experimental::pmr::memory_resource;
-
-void test01() {
- memory_resource* r = null_memory_resource();
- auto p = r->allocate(1);
-}
-
-int main() {
- test01();
-}