1 // Copyright (C) 2020-2021 Intel Corporation
2 // SPDX-License-Identifier: Apache-2.0
3 
4 #include "gtest/gtest.h"
5 #include "hexl/logging/logging.hpp"
6 #include "hexl/util/aligned-allocator.hpp"
7 #include "hexl/util/defines.hpp"
8 #include "hexl/util/types.hpp"
9 #include "test-util.hpp"
10 
11 namespace intel {
12 namespace hexl {
13 
TEST(AlignedVector64,alloc)14 TEST(AlignedVector64, alloc) {
15   AlignedVector64<uint64_t> x{1, 2, 3, 4};
16   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
17 }
18 
TEST(AlignedVector64,assignment)19 TEST(AlignedVector64, assignment) {
20   AlignedVector64<uint64_t> x{1, 2, 3, 4};
21   AlignedVector64<uint64_t> y = x;
22   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
23   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
24   ASSERT_EQ(x, y);
25 }
26 
TEST(AlignedVector64,move_assignment)27 TEST(AlignedVector64, move_assignment) {
28   AlignedVector64<uint64_t> x{1, 2, 3, 4};
29   AlignedVector64<uint64_t> y = std::move(x);
30   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
31   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
32   ASSERT_EQ(y, (AlignedVector64<uint64_t>{1, 2, 3, 4}));
33 }
34 
TEST(AlignedVector64,copy_constructor)35 TEST(AlignedVector64, copy_constructor) {
36   AlignedVector64<uint64_t> x{1, 2, 3, 4};
37   AlignedVector64<uint64_t> y{x};
38   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
39   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
40   ASSERT_EQ(y, (AlignedVector64<uint64_t>{1, 2, 3, 4}));
41 }
42 
TEST(AlignedVector64,move_constructor)43 TEST(AlignedVector64, move_constructor) {
44   AlignedVector64<uint64_t> x{1, 2, 3, 4};
45   AlignedVector64<uint64_t> y{std::move(x)};
46   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
47   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
48   ASSERT_EQ(y, (AlignedVector64<uint64_t>{1, 2, 3, 4}));
49 }
50 
TEST(AlignedAllocator,assignment)51 TEST(AlignedAllocator, assignment) {
52   AlignedAllocator<uint64_t, 64> x;
53   AlignedAllocator<uint64_t, 64> y = x;
54 }
55 
56 struct CustomAllocator {
57   using T = size_t;
invoke_allocationintel::hexl::CustomAllocator58   T* invoke_allocation(size_t size) { return new T[size]; }
59 
lets_deallocateintel::hexl::CustomAllocator60   void lets_deallocate(T* ptr) { delete[] ptr; }
61 };
62 
63 struct CustomAllocatorAdapter
64     : public AllocatorInterface<CustomAllocatorAdapter> {
CustomAllocatorAdapterintel::hexl::CustomAllocatorAdapter65   explicit CustomAllocatorAdapter(CustomAllocator&& a_) : a(std::move(a_)) {}
66 
67   // interface implementations
allocate_implintel::hexl::CustomAllocatorAdapter68   void* allocate_impl(size_t bytes_count) {
69     return a.invoke_allocation(bytes_count);
70   }
deallocate_implintel::hexl::CustomAllocatorAdapter71   void deallocate_impl(void* p, size_t n) {
72     HEXL_UNUSED(n);
73     a.lets_deallocate(static_cast<CustomAllocator::T*>(p));
74   }
75 
76   CustomAllocator a;
77 };
78 
TEST(AlignedVectorCustomAllocator64,alloc)79 TEST(AlignedVectorCustomAllocator64, alloc) {
80   std::shared_ptr<AllocatorBase> adapter_allocator;
81   {
82     CustomAllocator outer_allocator;
83     adapter_allocator =
84         std::make_shared<CustomAllocatorAdapter>(std::move(outer_allocator));
85   }
86 
87   AlignedAllocator<uint64_t, 64> hexl_alloc(adapter_allocator);
88 
89   AlignedVector64<uint64_t> x({1, 2, 3, 4}, hexl_alloc);
90   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
91 }
92 
TEST(AlignedVectorCustomAllocator64,assignment)93 TEST(AlignedVectorCustomAllocator64, assignment) {
94   std::shared_ptr<AllocatorBase> adapter_allocator;
95   {
96     CustomAllocator outer_allocator;
97     adapter_allocator =
98         std::make_shared<CustomAllocatorAdapter>(std::move(outer_allocator));
99   }
100 
101   AlignedAllocator<uint64_t, 64> hexl_alloc(adapter_allocator);
102 
103   AlignedVector64<uint64_t> x({1, 2, 3, 4}, hexl_alloc);
104   AlignedVector64<uint64_t> y = x;
105   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
106   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
107   ASSERT_EQ(x, y);
108 }
109 
TEST(AlignedVectorCustomAllocator64,move_assignment)110 TEST(AlignedVectorCustomAllocator64, move_assignment) {
111   std::shared_ptr<AllocatorBase> adapter_allocator;
112   {
113     CustomAllocator outer_allocator;
114     adapter_allocator =
115         std::make_shared<CustomAllocatorAdapter>(std::move(outer_allocator));
116   }
117 
118   AlignedAllocator<uint64_t, 64> hexl_alloc(adapter_allocator);
119 
120   AlignedVector64<uint64_t> x({1, 2, 3, 4}, hexl_alloc);
121   AlignedVector64<uint64_t> y = std::move(x);
122   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
123   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
124   ASSERT_EQ(y, (AlignedVector64<uint64_t>({1, 2, 3, 4}, hexl_alloc)));
125 }
126 
TEST(AlignedVectorCustomAllocator64,copy_constructor)127 TEST(AlignedVectorCustomAllocator64, copy_constructor) {
128   std::shared_ptr<AllocatorBase> adapter_allocator;
129   {
130     CustomAllocator outer_allocator;
131     adapter_allocator =
132         std::make_shared<CustomAllocatorAdapter>(std::move(outer_allocator));
133   }
134 
135   AlignedAllocator<uint64_t, 64> hexl_alloc(adapter_allocator);
136   AlignedVector64<uint64_t> x({1, 2, 3, 4}, hexl_alloc);
137   AlignedVector64<uint64_t> y{x};
138   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
139   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
140   ASSERT_EQ(y, (AlignedVector64<uint64_t>({1, 2, 3, 4}, hexl_alloc)));
141 }
142 
TEST(AlignedVectorCustomAllocator64,move_constructor)143 TEST(AlignedVectorCustomAllocator64, move_constructor) {
144   std::shared_ptr<AllocatorBase> adapter_allocator;
145   {
146     CustomAllocator outer_allocator;
147     adapter_allocator =
148         std::make_shared<CustomAllocatorAdapter>(std::move(outer_allocator));
149   }
150 
151   AlignedAllocator<uint64_t, 64> hexl_alloc(adapter_allocator);
152   AlignedVector64<uint64_t> x({1, 2, 3, 4}, hexl_alloc);
153   AlignedVector64<uint64_t> y{std::move(x)};
154   ASSERT_EQ(reinterpret_cast<uintptr_t>(x.data()) % 64, 0);
155   ASSERT_EQ(reinterpret_cast<uintptr_t>(y.data()) % 64, 0);
156   ASSERT_EQ(y, (AlignedVector64<uint64_t>({1, 2, 3, 4}, hexl_alloc)));
157 }
158 }  // namespace hexl
159 }  // namespace intel
160