Esempio n. 1
0
// Otherwise, if uses_allocator_v<T, inner_allocator_type> is true and
// is_constructible_v<T, Args..., inner_allocator_type&> is true, calls
// OUTERMOST_ALLOC_TRAITS(*this)::construct(OUTERMOST (*this), p,
//   std::forward<Args>(args)..., inner_allocator()).
void test_bullet_three() {
    using VoidAlloc2 = CountingAllocator<void, 2>;

    AllocController POuter;
    AllocController PInner;
    {
        using T = UsesAllocatorV2<VoidAlloc2, 3>;
        using Outer = CountingAllocator<T, 1>;
        using Inner = CountingAllocator<T, 2>;
        using SA = std::scoped_allocator_adaptor<Outer, Inner>;
        static_assert(!std::uses_allocator<T, Outer>::value, "");
        static_assert(std::uses_allocator<T, Inner>::value, "");
        T* ptr = (T*)::operator new(sizeof(T));
        Outer O(POuter);
        Inner I(PInner);
        SA A(O, I);
        int x = 42;
        int const& cx = x;
        A.construct(ptr, x, cx, std::move(x));
        assert((checkConstruct<int&, int const&, int&&>(*ptr, UA_AllocLast, I)));
        assert((POuter.checkConstruct<
                   int&, int const&, int&&,
                   SA::inner_allocator_type&>(O, ptr)));
        A.destroy(ptr);
        ::operator delete((void*)ptr);
    }
    PInner.reset();
    POuter.reset();
}
void test_with_inner_alloc()
{
    using VoidAlloc2 = CountingAllocator<void, 2>;

    AllocController POuter;
    AllocController PInner;
    {
        using T = UsesAllocatorV1<VoidAlloc2, 0>;
        using U = UsesAllocatorV2<VoidAlloc2, 0>;
        using Pair = std::pair<T, U>;
        using Outer = CountingAllocator<Pair, 1>;
        using Inner = CountingAllocator<Pair, 2>;
        using SA = std::scoped_allocator_adaptor<Outer, Inner>;
        using SAInner = std::scoped_allocator_adaptor<Inner>;
        static_assert(!std::uses_allocator<T, Outer>::value, "");
        static_assert(std::uses_allocator<T, Inner>::value, "");
        Pair * ptr = (Pair*)std::malloc(sizeof(Pair));
        assert(ptr);
        Outer O(POuter);
        Inner I(PInner);
        SA A(O, I);
        A.construct(ptr);
        assert(checkConstruct<>(ptr->first, UA_AllocArg, I));
        assert(checkConstruct<>(ptr->second, UA_AllocLast));
        assert((POuter.checkConstruct<std::piecewise_construct_t const&,
                                 std::tuple<std::allocator_arg_t, SAInner&>&&,
                                 std::tuple<SAInner&>&&
              >(O, ptr)));
        A.destroy(ptr);
        std::free(ptr);
    }
    PInner.reset();
    POuter.reset();
    {
        using T = UsesAllocatorV3<VoidAlloc2, 0>;
        using U = NotUsesAllocator<VoidAlloc2, 0>;
        using Pair = std::pair<T, U>;
        using Outer = CountingAllocator<Pair, 1>;
        using Inner = CountingAllocator<Pair, 2>;
        using SA = std::scoped_allocator_adaptor<Outer, Inner>;
        using SAInner = std::scoped_allocator_adaptor<Inner>;
        static_assert(!std::uses_allocator<T, Outer>::value, "");
        static_assert(std::uses_allocator<T, Inner>::value, "");
        Pair * ptr = (Pair*)std::malloc(sizeof(Pair));
        assert(ptr);
        Outer O(POuter);
        Inner I(PInner);
        SA A(O, I);
        A.construct(ptr);
        assert(checkConstruct<>(ptr->first, UA_AllocArg, I));
        assert(checkConstruct<>(ptr->second, UA_None));
        assert((POuter.checkConstruct<std::piecewise_construct_t const&,
                                 std::tuple<std::allocator_arg_t, SAInner&>&&,
                                 std::tuple<>&&
              >(O, ptr)));
        A.destroy(ptr);
        std::free(ptr);
    }
}
void test_no_inner_alloc()
{
    using VoidAlloc = CountingAllocator<void>;
    AllocController P;
    {
        using T = UsesAllocatorV1<VoidAlloc, 1>;
        using U = UsesAllocatorV2<VoidAlloc, 1>;
        using Pair = std::pair<T, U>;
        using PairIn = std::pair<int&, int const&&>;
        int x = 42;
        const int y = 101;
        using Alloc = CountingAllocator<Pair>;
        using SA = std::scoped_allocator_adaptor<Alloc>;
        static_assert(std::uses_allocator<T, CountingAllocator<T> >::value, "");
        Pair * ptr = (Pair*)std::malloc(sizeof(Pair));
        assert(ptr != nullptr);
        Alloc CA(P);
        SA A(CA);
        PairIn in(x, std::move(y));
        A.construct(ptr, std::move(in));
        assert(checkConstruct<int&>(ptr->first, UA_AllocArg, CA));
        assert(checkConstruct<int const&&>(ptr->second, UA_AllocLast, CA));
        assert((P.checkConstruct<std::piecewise_construct_t const&,
                                 std::tuple<std::allocator_arg_t, SA&, int&>&&,
                                 std::tuple<int const&&, SA&>&&
              >(CA, ptr)));
        A.destroy(ptr);
        std::free(ptr);

    }
    P.reset();
    {
        using T = UsesAllocatorV3<VoidAlloc, 1>;
        using U = NotUsesAllocator<VoidAlloc, 1>;
        using Pair = std::pair<T, U>;
        using PairIn = std::pair<int, int const&>;
        int x = 42;
        const int y = 101;
        using Alloc = CountingAllocator<Pair>;
        using SA = std::scoped_allocator_adaptor<Alloc>;
        static_assert(std::uses_allocator<T, CountingAllocator<T> >::value, "");
        Pair * ptr = (Pair*)std::malloc(sizeof(Pair));
        assert(ptr != nullptr);
        Alloc CA(P);
        SA A(CA);
        PairIn in(x, y);
        A.construct(ptr, std::move(in));
        assert(checkConstruct<int&&>(ptr->first, UA_AllocArg, CA));
        assert(checkConstruct<int const&>(ptr->second, UA_None));
        assert((P.checkConstruct<std::piecewise_construct_t const&,
                                 std::tuple<std::allocator_arg_t, SA&, int&&>&&,
                                 std::tuple<int const&>&&
                   >(CA, ptr)));
        A.destroy(ptr);
        std::free(ptr);
    }
}