blob: 2e054bca624536432ad93eeadd7a24769ab38a88 [file] [log] [blame]
William A. Kennington IIIe0990382019-10-18 02:10:25 -07001#include <catch2/catch.hpp>
2#include <endian.h>
3#include <stdexcept>
4#include <stdplus/raw.hpp>
5#include <string_view>
6#include <vector>
7
8namespace stdplus
9{
10namespace raw
11{
12namespace
13{
14
William A. Kennington III3b35fcf2020-06-13 18:42:39 -070015TEST_CASE("Equal", "[Equal]")
16{
17 int a = 4;
18 unsigned b = 4;
19 CHECK(equal(a, b));
20 b = 5;
21 CHECK(!equal(a, b));
22}
23
William A. Kennington IIIe0990382019-10-18 02:10:25 -070024TEST_CASE("Copy From Empty", "[CopyFrom]")
25{
William A. Kennington III5c99ff42020-07-19 02:29:26 -070026 const std::string_view cs;
27 CHECK_THROWS_AS(copyFrom<int>(cs), std::runtime_error);
28 std::string_view s;
William A. Kennington IIIe0990382019-10-18 02:10:25 -070029 CHECK_THROWS_AS(copyFrom<int>(s), std::runtime_error);
William A. Kennington IIIe0990382019-10-18 02:10:25 -070030}
31
32TEST_CASE("Copy From Basic", "[CopyFrom]")
33{
34 int a = 4;
35 const std::string_view s(reinterpret_cast<char*>(&a), sizeof(a));
36 CHECK(a == copyFrom<int>(s));
37}
38
39TEST_CASE("Copy From Partial", "[CopyFrom]")
40{
41 const std::vector<char> s = {'a', 'b', 'c'};
42 CHECK('a' == copyFrom<char>(s));
43 const char s2[] = "def";
44 CHECK('d' == copyFrom<char>(s2));
45}
46
William A. Kennington III5c99ff42020-07-19 02:29:26 -070047struct Int
48{
49 uint8_t data[sizeof(int)];
50
51 inline bool operator==(const Int& other) const
52 {
53 return memcmp(data, other.data, sizeof(data)) == 0;
54 }
55};
56
57TEST_CASE("Ref From Empty", "[RefFrom]")
58{
59 const std::string_view cs;
60 CHECK_THROWS_AS(refFrom<Int>(cs), std::runtime_error);
61 std::string_view s;
62 CHECK_THROWS_AS(refFrom<Int>(s), std::runtime_error);
63}
64
65TEST_CASE("Ref From Basic", "[RefFrom]")
66{
67 Int a = {4, 0, 0, 4};
68 const std::string_view s(reinterpret_cast<char*>(&a), sizeof(a));
69 CHECK(a == refFrom<Int>(s));
70}
71
72TEST_CASE("Ref From Partial", "[RefFrom]")
73{
74 const std::vector<char> s = {'a', 'b', 'c'};
75 CHECK('a' == refFrom<char>(s));
76 const char s2[] = "def";
77 CHECK('d' == refFrom<char>(s2));
78}
79
William A. Kennington IIIe0990382019-10-18 02:10:25 -070080TEST_CASE("Extract Too Small", "[Extract]")
81{
82 std::string_view s("a");
83 CHECK_THROWS_AS(extract<int>(s), std::runtime_error);
84 CHECK(1 == s.size());
85}
86
87TEST_CASE("Extract Basic", "[Extract]")
88{
89 int a = 4;
90 std::string_view s(reinterpret_cast<char*>(&a), sizeof(a));
91 CHECK(a == extract<int>(s));
92 CHECK(s.empty());
93}
94
95TEST_CASE("Extract Partial", "[Extract]")
96{
97 std::string_view s("abc");
98 CHECK('a' == extract<char>(s));
99 CHECK(2 == s.size());
100}
101
William A. Kennington III5c99ff42020-07-19 02:29:26 -0700102TEST_CASE("Extract Ref Too Small", "[ExtractRef]")
103{
104 std::string_view s("a");
105 CHECK_THROWS_AS(extractRef<Int>(s), std::runtime_error);
106 CHECK(1 == s.size());
107}
108
109TEST_CASE("Extract Ref Basic", "[ExtractRef]")
110{
111 Int a = {4, 0, 0, 4};
112 std::string_view s(reinterpret_cast<char*>(&a), sizeof(a));
113 CHECK(a == extractRef<Int>(s));
114 CHECK(s.empty());
115}
116
117TEST_CASE("Extract Ref Partial", "[ExtractRef]")
118{
119 std::string_view s("abc");
120 CHECK('a' == extractRef<char>(s));
121 CHECK(2 == s.size());
122}
123
William A. Kennington IIIe0990382019-10-18 02:10:25 -0700124TEST_CASE("As View Byte", "[AsView]")
125{
126 int32_t a = 4;
127 auto s = asView<uint8_t>(a);
128 CHECK(a == copyFrom<int>(s));
129}
130
131TEST_CASE("As View Int", "[AsView]")
132{
133 int32_t a = 4;
134 auto s = asView<char16_t>(a);
135 CHECK(a == copyFrom<int>(s));
136}
137
138TEST_CASE("As View Arr", "[AsView]")
139{
140 std::vector<uint32_t> arr = {htole32(1), htole32(2)};
141 auto s = asView<char16_t>(arr);
142 REQUIRE(4 == s.size());
143 CHECK(htole16(1) == s[0]);
144 CHECK(htole16(0) == s[1]);
145 CHECK(htole16(2) == s[2]);
146 CHECK(htole16(0) == s[3]);
147}
148
William A. Kennington IIIba7d7542020-07-19 20:04:44 -0700149TEST_CASE("As View View", "[AsView]")
150{
151 std::string_view sv = "ab";
152 auto s = asView<uint8_t>(sv);
153 REQUIRE(s.size() == 2);
154 CHECK(s[0] == sv[0]);
155 CHECK(s[1] == sv[1]);
156}
157
William A. Kennington IIIe0990382019-10-18 02:10:25 -0700158#ifdef STDPLUS_SPAN_TYPE
159TEST_CASE("Span Extract TooSmall", "[Extract]")
160{
161 const std::vector<char> v = {'c'};
162 span<const char> s = v;
163 CHECK_THROWS_AS(extract<int>(s), std::runtime_error);
164 CHECK(1 == s.size());
165}
166
167TEST_CASE("Span Extract Basic", "[Extract]")
168{
169 const std::vector<int> v = {4};
170 span<const int> s = v;
171 CHECK(v[0] == extract<int>(s));
172 CHECK(s.empty());
173}
174
175TEST_CASE("Span Extract Larger", "[Extract]")
176{
177 const std::vector<int> v{3, 4, 5};
178 span<const int> s = v;
179 CHECK(v[0] == extract<int>(s));
180 CHECK(v.size() - 1 == s.size());
181}
182
William A. Kennington III5c99ff42020-07-19 02:29:26 -0700183TEST_CASE("Span Extract Ref TooSmall", "[ExtractRef]")
184{
185 const std::vector<char> v = {'c'};
186 span<const char> s = v;
187 CHECK_THROWS_AS(extractRef<Int>(s), std::runtime_error);
188 CHECK(1 == s.size());
189}
190
191TEST_CASE("Span Extract Ref Basic", "[ExtractRef]")
192{
193 const std::vector<Int> v = {{4, 0, 0, 4}};
194 span<const Int> s = v;
195 CHECK(v[0] == extractRef<Int>(s));
196 CHECK(s.empty());
197}
198
199TEST_CASE("Span Extract Ref Larger", "[ExtractRef]")
200{
201 const std::vector<Int> v{{3}, {4}, {5}};
202 span<const Int> s = v;
203 CHECK(v[0] == extractRef<Int>(s));
204 CHECK(v.size() - 1 == s.size());
205}
206
William A. Kennington IIIe0990382019-10-18 02:10:25 -0700207TEST_CASE("As Span const", "[AsSpan]")
208{
209 const uint64_t data = htole64(0xffff0000);
210 auto s = asSpan<uint32_t>(data);
211 CHECK(s.size() == 2);
212 CHECK(s[0] == htole32(0xffff0000));
213 CHECK(s[1] == htole32(0x00000000));
214}
215
216TEST_CASE("As Span Arr const", "[AsSpan]")
217{
218 const std::vector<uint32_t> arr = {htole32(1), htole32(2)};
219 auto s = asSpan<uint16_t>(arr);
220 REQUIRE(4 == s.size());
221 CHECK(htole16(1) == s[0]);
222 CHECK(htole16(0) == s[1]);
223 CHECK(htole16(2) == s[2]);
224 CHECK(htole16(0) == s[3]);
225}
226
227TEST_CASE("As Span", "[AsSpan]")
228{
229 uint64_t data = htole64(0xffff0000);
230 auto s = asSpan<uint16_t>(data);
231 CHECK(s.size() == 4);
232 s[2] = 0xfefe;
233 CHECK(s[0] == htole16(0x0000));
234 CHECK(s[1] == htole16(0xffff));
235 CHECK(s[2] == htole16(0xfefe));
236 CHECK(s[3] == htole16(0x0000));
237}
238
239TEST_CASE("As Span Arr", "[AsSpan]")
240{
241 std::vector<uint32_t> arr = {htole32(1), htole32(2)};
242 auto s = asSpan<uint16_t>(arr);
243 REQUIRE(4 == s.size());
244 CHECK(htole16(1) == s[0]);
245 CHECK(htole16(0) == s[1]);
246 CHECK(htole16(2) == s[2]);
247 CHECK(htole16(0) == s[3]);
248}
249
William A. Kennington IIIba7d7542020-07-19 20:04:44 -0700250TEST_CASE("As Span Span", "[AsSpan]")
251{
252 std::array<char, 2> arr = {'a', 'b'};
253 auto sp1 = span<const char>(arr);
254 auto s1 = asSpan<uint8_t>(sp1);
255 REQUIRE(s1.size() == 2);
256 CHECK(s1[0] == arr[0]);
257 CHECK(s1[1] == arr[1]);
258 auto sp2 = span<char>(arr);
259 auto s2 = asSpan<uint8_t>(sp2);
260 REQUIRE(s2.size() == 2);
261 CHECK(s2[0] == arr[0]);
262 CHECK(s2[1] == arr[1]);
263}
264
William A. Kennington IIIe0990382019-10-18 02:10:25 -0700265#endif
266
267} // namespace
268} // namespace raw
269} // namespace stdplus