DCCL v4
Loading...
Searching...
No Matches
test.cpp
1// Copyright 2023:
2// GobySoft, LLC (2013-)
3// Community contributors (see AUTHORS file)
4// File authors:
5// Toby Schneider <toby@gobysoft.org>
6//
7//
8// This file is part of the Dynamic Compact Control Language Library
9// ("DCCL").
10//
11// DCCL is free software: you can redistribute it and/or modify
12// it under the terms of the GNU Lesser General Public License as published by
13// the Free Software Foundation, either version 2.1 of the License, or
14// (at your option) any later version.
15//
16// DCCL is distributed in the hope that it will be useful,
17// but WITHOUT ANY WARRANTY; without even the implied warranty of
18// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19// GNU Lesser General Public License for more details.
20//
21// You should have received a copy of the GNU Lesser General Public License
22// along with DCCL. If not, see <http://www.gnu.org/licenses/>.
23// tests all protobuf types with _default codecs, repeat and non repeat
24
25#include <thread>
26
27#include "../../arithmetic/field_codec_arithmetic.h"
28#include "../../codec.h"
29#include "test.pb.h"
30#include "test_arithmetic.pb.h"
31
32using namespace dccl::test;
33
34void arithmetic_run_test(dccl::Codec& codec, dccl::arith::protobuf::ArithmeticModel& model,
35 const google::protobuf::Message& msg_in, bool set_model = true)
36{
37 if (set_model)
38 {
39 model.set_name("model");
40 dccl::arith::ModelManager::set_model(codec, model);
41 }
42
43 codec.load(msg_in.GetDescriptor());
44 codec.info(msg_in.GetDescriptor());
45
46 // std::cout << "Message in:\n" << msg_in.DebugString() << std::endl;
47
48 // std::cout << "Try encode..." << std::endl;
49 std::string bytes;
50 codec.encode(&bytes, msg_in);
51 // std::cout << "... got bytes (hex): " << dccl::hex_encode(bytes) << std::endl;
52
53 // std::cout << "Try decode..." << std::endl;
54
55 std::shared_ptr<google::protobuf::Message> msg_out(msg_in.New());
56 codec.decode(bytes, msg_out.get());
57
58 // std::cout << "... got Message out:\n" << msg_out->DebugString() << std::endl;
59
60 assert(msg_in.SerializeAsString() == msg_out->SerializeAsString());
61}
62
63void decode_check(dccl::Codec& codec, const std::string& encoded, TestMsg msg_in);
64void run(int thread, int num_iterations);
65int main(int /*argc*/, char* /*argv*/ [])
66{
67 {
68 std::thread t1([]() { run(1, 100); });
69 std::thread t2([]() { run(2, 100); });
70 std::thread t3([]() { run(3, 100); });
71 std::thread t4([]() { run(4, 100); });
72 std::thread t5([]() { run(5, 100); });
73 std::thread t6([]() { run(6, 100); });
74 std::thread t7([]() { run(7, 100); });
75 std::thread t8([]() { run(8, 100); });
76 std::thread t9([]() { run(9, 100); });
77 std::thread t10([]() { run(10, 100); });
78 t1.join();
79 t2.join();
80 t3.join();
81 t4.join();
82 t5.join();
83 t6.join();
84 t7.join();
85 t8.join();
86 t9.join();
87 t10.join();
88 }
89
90 dccl::dlog.connect(dccl::logger::ALL, &std::cerr);
91 {
92 std::thread t1([]() { run(1, 10); });
93 std::thread t2([]() { run(2, 10); });
94 std::thread t3([]() { run(3, 10); });
95 std::thread t4([]() { run(4, 10); });
96 std::thread t5([]() { run(5, 10); });
97 std::thread t6([]() { run(6, 10); });
98 std::thread t7([]() { run(7, 10); });
99 std::thread t8([]() { run(8, 10); });
100 std::thread t9([]() { run(9, 10); });
101 std::thread t10([]() { run(10, 10); });
102 t1.join();
103 t2.join();
104 t3.join();
105 t4.join();
106 t5.join();
107 t6.join();
108 t7.join();
109 t8.join();
110 t9.join();
111 t10.join();
112 }
113
114 std::cout << "all tests passed" << std::endl;
115}
116
117void run(int thread, int num_iterations)
118{
119 dccl::Codec codec;
120 codec.load_library(DCCL_ARITHMETIC_NAME);
121 codec.load<TestMsg>();
122 for (int m = 0; m < num_iterations; ++m)
123 {
124 std::cout << "Thread " << thread << ", it: " << m << std::endl;
125 codec.info<TestMsg>();
126 TestMsg msg_in;
127 int i = 0;
128 msg_in.set_double_default_optional(++i + 0.1);
129 msg_in.set_float_default_optional(++i + 0.2);
130
131 msg_in.set_int32_default_optional(++i);
132 msg_in.set_int64_default_optional(-++i);
133 msg_in.set_uint32_default_optional(++i);
134 msg_in.set_uint64_default_optional(++i);
135 msg_in.set_sint32_default_optional(-++i);
136 msg_in.set_sint64_default_optional(++i);
137 msg_in.set_fixed32_default_optional(++i);
138 msg_in.set_fixed64_default_optional(++i);
139 msg_in.set_sfixed32_default_optional(++i);
140 msg_in.set_sfixed64_default_optional(-++i);
141
142 msg_in.set_bool_default_optional(true);
143
144 msg_in.set_string_default_optional("abc123");
145 msg_in.set_bytes_default_optional(dccl::hex_decode("00112233aabbcc1234"));
146
147 msg_in.set_enum_default_optional(ENUM_C);
148 msg_in.mutable_msg_default_optional()->set_val(++i + 0.3);
149 msg_in.mutable_msg_default_optional()->mutable_msg()->set_val(++i);
150
151 msg_in.set_double_default_required(++i + 0.1);
152 msg_in.set_float_default_required(++i + 0.2);
153
154 msg_in.set_int32_default_required(++i);
155 msg_in.set_int64_default_required(-++i);
156 msg_in.set_uint32_default_required(++i);
157 msg_in.set_uint64_default_required(++i);
158 msg_in.set_sint32_default_required(-++i);
159 msg_in.set_sint64_default_required(++i);
160 msg_in.set_fixed32_default_required(++i);
161 msg_in.set_fixed64_default_required(++i);
162 msg_in.set_sfixed32_default_required(++i);
163 msg_in.set_sfixed64_default_required(-++i);
164
165 msg_in.set_bool_default_required(true);
166
167 msg_in.set_string_default_required("abc123");
168 msg_in.set_bytes_default_required(dccl::hex_decode("00112233aabbcc1234"));
169
170 msg_in.set_enum_default_required(ENUM_C);
171 msg_in.mutable_msg_default_required()->set_val(++i + 0.3);
172 msg_in.mutable_msg_default_required()->mutable_msg()->set_val(++i);
173
174 for (int j = 0; j < 2; ++j)
175 {
176 msg_in.add_double_default_repeat(++i + 0.1);
177 msg_in.add_float_default_repeat(++i + 0.2);
178
179 msg_in.add_int32_default_repeat(++i);
180 msg_in.add_int64_default_repeat(-++i);
181 msg_in.add_uint32_default_repeat(++i);
182 msg_in.add_uint64_default_repeat(++i);
183 msg_in.add_sint32_default_repeat(-++i);
184 msg_in.add_sint64_default_repeat(++i);
185 msg_in.add_fixed32_default_repeat(++i);
186 msg_in.add_fixed64_default_repeat(++i);
187 msg_in.add_sfixed32_default_repeat(++i);
188 msg_in.add_sfixed64_default_repeat(-++i);
189
190 msg_in.add_bool_default_repeat(true);
191
192 msg_in.add_string_default_repeat("abc123");
193
194 if (j)
195 msg_in.add_bytes_default_repeat(dccl::hex_decode("00aabbcc"));
196 else
197 msg_in.add_bytes_default_repeat(dccl::hex_decode("ffeedd12"));
198
199 msg_in.add_enum_default_repeat(static_cast<Enum1>((++i % 3) + 1));
200 EmbeddedMsg1* em_msg = msg_in.add_msg_default_repeat();
201 em_msg->set_val(++i + 0.3);
202 em_msg->mutable_msg()->set_val(++i);
203 }
204
205 std::string bytes;
206 codec.encode(&bytes, msg_in);
207
208 decode_check(codec, bytes, msg_in);
209
210 // test case from Practical Implementations of Arithmetic Coding by Paul G. Howard and Je rey Scott Vitter
211 {
213
214 model.set_eof_frequency(4); // "a"
215
216 model.add_value_bound(0);
217 model.add_frequency(5); // "b"
218
219 model.add_value_bound(1);
220 model.add_frequency(1); // "EOF"
221
222 model.add_value_bound(2);
223
224 model.set_out_of_range_frequency(0);
225
226 dccl::test::arith::ArithmeticDoubleTestMsg msg_in;
227
228 msg_in.add_value(0); // b
229 msg_in.add_value(0); // b
230 msg_in.add_value(0); // b
231 msg_in.add_value(1); // "EOF"
232
233 arithmetic_run_test(codec, model, msg_in);
234 }
235 }
236}
237
238void decode_check(dccl::Codec& codec, const std::string& encoded, TestMsg msg_in)
239{
240 TestMsg msg_out;
241 codec.decode(encoded, &msg_out);
242
243 // std::cout << "... got Message out:\n" << msg_out.DebugString() << std::endl;
244
245 // truncate to "max_length" as codec should do
246 msg_in.set_string_default_repeat(0, "abc1");
247 msg_in.set_string_default_repeat(1, "abc1");
248
249 assert(msg_in.SerializeAsString() == msg_out.SerializeAsString());
250}
The Dynamic CCL enCODer/DECoder. This is the main class you will use to load, encode and decode DCCL ...
Definition codec.h:63
void connect(int verbosity_mask, Slot slot)
Connect the output of one or more given verbosities to a slot (function pointer or similar)
Definition logger.h:214
Unit test namespace.
Definition test.cpp:45
void hex_decode(const std::string &in, std::string *out)
Decodes a (little-endian) hexadecimal string to a byte string. Index 0 and 1 (first byte) of in are w...
Definition binary.h:51