OpenVPN 3 Core Library
Loading...
Searching...
No Matches
test_pktid_data.cpp
Go to the documentation of this file.
1#include "test_common.hpp"
2
5
6using namespace openvpn;
7
9{
12 {
13 id = v_id;
14 }
15};
16
17template <typename PIDRecv>
18void testcase(PIDRecv &pr,
19 const std::time_t t,
20 const PacketIDData::data_id_t pkt_id,
21 const Error::Type expected_status)
22{
23 bool wide = pr.length() > 4;
24 const PacketIDDataConstruct pid(pkt_id, wide);
25 const Error::Type status = pr.do_test_add(pid, t);
26 // OPENVPN_LOG("[" << t << "] id=" << pkt_id << ' ' << Error::name(status));
27 ASSERT_EQ(status, expected_status);
28}
29
31{
32 typedef PacketIDDataReceiveType<3, 5> PIDRecv;
34 PIDRecv pr;
35 pr.init("test", 0, usewide);
36
38 testcase(pr, 1, 1, Error::SUCCESS);
39 testcase(pr, 1, 1, Error::PKTID_REPLAY); /* replay */
40 testcase(pr, 2, 2, Error::SUCCESS);
41 testcase(pr, 3, 4, Error::SUCCESS);
42 testcase(pr, 4, 1, Error::PKTID_REPLAY); /* replay */
43 testcase(pr, 5, 3, Error::SUCCESS);
44
45 testcase(pr, 6, 8, Error::SUCCESS);
46 testcase(pr, 10, 5, Error::SUCCESS);
47 testcase(pr, 15, 7, Error::PKTID_EXPIRE); /* expire backtrack */
48
49 testcase(pr, 20, 127, Error::SUCCESS);
50 testcase(pr, 20, 127, Error::PKTID_REPLAY);
51 testcase(pr, 21, 128, Error::SUCCESS);
52 testcase(pr, 22, 64, Error::PKTID_BACKTRACK); /* large backtrack */
53 testcase(pr, 23, 65, Error::SUCCESS);
54 testcase(pr, 24, 66, Error::SUCCESS);
55
57 testcase(pr, 33, 3, Error::PKTID_BACKTRACK); /* time backtrack */
58
59 testcase(pr, 40, 0xfffffffe, Error::SUCCESS);
60 testcase(pr, 41, 0xffffffff, Error::SUCCESS);
61}
62
63TEST(misc, do_packet_id_recv_test_long_ids)
64{
65 typedef PacketIDDataReceiveType<3, 5> PIDRecv;
66 PIDRecv pr;
68 pr.init("test", 0, true);
69
70 testcase(pr, 40, 0xfffffffe, Error::SUCCESS);
71 testcase(pr, 41, 0xffffffff, Error::SUCCESS);
72 testcase(pr, 42, 0x100000001, Error::SUCCESS);
73 testcase(pr, 42, 0xffffff0d, Error::PKTID_BACKTRACK);
74 testcase(pr, 50, 0x200000000, Error::SUCCESS);
75 testcase(pr, 50, 0x500000000, Error::SUCCESS);
76 testcase(pr, 50, 0x400000000, Error::PKTID_BACKTRACK);
77 testcase(pr, 50, 0x399999999, Error::PKTID_BACKTRACK);
78 testcase(pr, 50, 0x3ffffffff, Error::PKTID_BACKTRACK);
79 testcase(pr, 50, 0x4ffffffff, Error::SUCCESS);
80}
81
82
83TEST(misc, pktid_test_data_32bit)
84{
86}
87
88TEST(misc, pktid_test_data_64bit)
89{
91}
92
93
94template <unsigned int ORDER, unsigned int EXPIRE>
95void perfiter(const long n,
96 const long range,
97 const long step,
98 const long iter_per_step_pre,
99 long &count)
100{
102
103 const long iter_per_step = iter_per_step_pre * step;
104 // OPENVPN_LOG("ITER order=" << ORDER << " n=" << n << " range=" << range << " step=" << step << " iter_per_step="
105 // << iter_per_step);
106
107 constexpr std::time_t pkt_time = 1234;
108
109 MTRand urand;
110 std::vector<bool> bv(n);
111 long high = 0;
112 SessionStats::Ptr stats(new SessionStats());
113 PIDRecv pr;
114 pr.init("test", 0, false);
115
116 for (long i = 1; i < n; i += step)
117 {
118 for (long j = 0; j < iter_per_step; ++j)
119 {
120 const long delta = long(urand.randrange32(static_cast<uint32_t>(range))) - range / 2;
121 const long id = i + delta;
122 if (id >= 0 && id < n)
123 {
124 if (id > high)
125 high = id;
127 if (!id)
129 else if (high - id >= (const long)PIDRecv::REPLAY_WINDOW_SIZE)
131 else if (bv[id])
133 const PacketIDDataConstruct pid(id);
134 const Error::Type result = pr.do_test_add(pid, pkt_time);
135 ++count;
136#define INFO "i=" << i << " id=" << id << " high=" << high << " result=" << Error::name(result) << " expected=" << Error::name(expected)
137 // OPENVPN_LOG(INFO);
138 ASSERT_EQ(result, expected) << INFO;
140 bv[id] = true;
141 }
142 }
143 }
144}
145
146template <unsigned int ORDER, unsigned int EXPIRE>
147void perf(long &count)
148{
150
151 perfiter<ORDER, EXPIRE>(20000, PIDRecv::REPLAY_WINDOW_SIZE * 3, 1, 10, count);
152 perfiter<ORDER, EXPIRE>(20000, PIDRecv::REPLAY_WINDOW_SIZE * 3, PIDRecv::REPLAY_WINDOW_SIZE / 2, 10, count);
153 perfiter<ORDER, EXPIRE>(20000, PIDRecv::REPLAY_WINDOW_SIZE * 2, 1, 10, count);
154 perfiter<ORDER, EXPIRE>(20000, PIDRecv::REPLAY_WINDOW_SIZE * 2, PIDRecv::REPLAY_WINDOW_SIZE / 2, 10, count);
155 perfiter<ORDER, EXPIRE>(20000, 16, 1, 10, count);
156 perfiter<ORDER, EXPIRE>(20000, 16, PIDRecv::REPLAY_WINDOW_SIZE / 2, 10, count);
157 perfiter<ORDER, EXPIRE>(20000, 4, 1, 10, count);
158 perfiter<ORDER, EXPIRE>(20000, 4, PIDRecv::REPLAY_WINDOW_SIZE / 2, 10, count);
159}
160
161
163{
164 public:
165 PacketIDDataSendTest(bool wide, std::uint64_t start)
166 : openvpn::PacketIDDataSend(wide, 0)
167 {
168 pid_ = PacketIDDataConstruct{start, wide};
169 }
170};
171
172TEST(misc, pktid_32_bit_overrun_32bit_counter)
173{
174 PacketIDDataSendTest pidsend{false, 0xfffffffc};
175
176 auto ret = pidsend.next();
177 EXPECT_EQ(ret.str(), "[0xfffffffd]");
178
179 ret = pidsend.next();
180 EXPECT_EQ(ret.str(), "[0xfffffffe]");
181
182 EXPECT_THROW(ret = pidsend.next(), PacketIDDataSend::packet_id_wrap);
183}
184
185
186TEST(misc, pktid_32_bit_overrun_64bit_counter)
187{
188 PacketIDDataSendTest pidsend{true, 0xfffffffd};
189
190 auto ret = pidsend.next();
191 EXPECT_EQ(ret.str(), "[0xfffffffe]");
192
193 ret = pidsend.next();
194 EXPECT_EQ(ret.str(), "[0xffffffff]");
195
196 ret = pidsend.next();
197 EXPECT_EQ(ret.str(), "[0x100000000]");
198
199 ret = pidsend.next();
200 EXPECT_EQ(ret.str(), "[0x100000001]");
201}
202
203
204TEST(misc, pktid_64_bit_overrun_64bit_counter)
205{
206 PacketIDDataSendTest pidsend{true, 0xfffffffffffffffc};
207
208 auto ret = pidsend.next();
209 EXPECT_EQ(ret.str(), "[0xfffffffffffffffd]");
210
211 ret = pidsend.next();
212 EXPECT_EQ(ret.str(), "[0xfffffffffffffffe]");
213
214 EXPECT_THROW(ret = pidsend.next(), PacketIDDataSend::packet_id_wrap);
215}
216
217TEST(misc, pktid_32_bit_warn)
218{
219 PacketIDDataSendTest pidsend{false, 0xfefffffe};
220
221 EXPECT_FALSE(pidsend.wrap_warning());
222 auto ret = pidsend.next();
223 EXPECT_EQ(ret.str(), "[0xfeffffff]");
224 EXPECT_FALSE(pidsend.wrap_warning());
225
226 ret = pidsend.next();
227 EXPECT_EQ(ret.str(), "[0xff000000]");
228 EXPECT_TRUE(pidsend.wrap_warning());
229
230 ret = pidsend.next();
231 EXPECT_EQ(ret.str(), "[0xff000001]");
232 EXPECT_TRUE(pidsend.wrap_warning());
233}
234
235TEST(misc, pktid_64_bit_warn_32bit)
236{
237 // Test we are not warning at 32bit
238 PacketIDDataSendTest pidsend{true, 0xfefffffe};
239
240 EXPECT_FALSE(pidsend.wrap_warning());
241 auto ret = pidsend.next();
242 EXPECT_EQ(ret.str(), "[0xfeffffff]");
243 EXPECT_FALSE(pidsend.wrap_warning());
244
245 ret = pidsend.next();
246 EXPECT_EQ(ret.str(), "[0xff000000]");
247 EXPECT_FALSE(pidsend.wrap_warning());
248
249 ret = pidsend.next();
250 EXPECT_EQ(ret.str(), "[0xff000001]");
251 EXPECT_FALSE(pidsend.wrap_warning());
252}
253
254
255TEST(misc, pktid_data_perf)
256{
257 {
258 long count = 0;
259 perf<3, 5>(count);
260 perf<6, 5>(count);
261 perf<8, 5>(count);
262 // ASSERT_EQ(4746439, count);
263 }
264}
PacketIDDataSendTest(bool wide, std::uint64_t start)
std::uint32_t randrange32(const std::uint32_t end)
Return a uniformly distributed random number in the range [0, end)
Definition randapi.hpp:147
PacketIDDataConstruct(const PacketIDData::data_id_t v_id=PacketIDData::data_id_t{0}, bool wide=false)
std::string ret
const std::string expected
void perf()
void testcase(PIDRecv &pr, const std::time_t t, const PacketIDData::data_id_t pkt_id, const Error::Type expected_status)
void do_packet_id_recv_test_short_ids(bool usewide)
TEST(misc, do_packet_id_recv_test_long_ids)
void perfiter(const long n, const long range, const long step, const long iter_per_step_pre, long &count)
#define INFO