sessiond: validate existence of field reference received from LTTng-UST
[lttng-tools.git] / src / bin / lttng-sessiond / field.cpp
CommitLineData
0220be14
JG
1/*
2 * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 */
7
8#include "field.hpp"
9
10#include <common/exception.hpp>
11#include <common/format.hpp>
12
d7bfb9b0
JG
13#include <set>
14
0220be14
JG
15namespace lst = lttng::sessiond::trace;
16
17namespace {
18template <class FieldTypeSet>
19bool fields_are_equal(const FieldTypeSet& a, const FieldTypeSet& b)
20{
21 if (a.size() != b.size()) {
22 return false;
23 }
24
25 return std::equal(a.cbegin(), a.cend(), b.cbegin(),
26 [](typename FieldTypeSet::const_reference field_a,
27 typename FieldTypeSet::const_reference field_b) {
28 return *field_a == *field_b;
29 });
30}
31} /* namespace */
32
eda1aa02
JG
33lst::field_location::field_location(lst::field_location::root in_lookup_root,
34 lst::field_location::elements in_elements) :
35 root_{in_lookup_root}, elements_{std::move(in_elements)}
36{
37}
38
39bool lst::field_location::operator==(const lst::field_location& other) const noexcept
40{
41 return root_ == other.root_ &&
42 elements_ == other.elements_;
43}
44
0220be14
JG
45lst::type::type(unsigned int in_alignment) : alignment{in_alignment}
46{
47}
48
49lst::type::~type()
50{
51}
52
53bool lst::type::operator==(const lst::type& other) const noexcept
54{
55 return typeid(*this) == typeid(other) &&
56 alignment == other.alignment &&
57 /* defer to concrete type comparison */
58 this->_is_equal(other);
59}
60
61bool lst::type::operator!=(const lst::type& other) const noexcept
62{
63 return !(*this == other);
64}
65
66lst::field::field(std::string in_name, lst::type::cuptr in_type) :
67 name{std::move(in_name)}, _type{std::move(in_type)}
68{
69}
70
71void lst::field::accept(lst::field_visitor& visitor) const
72{
73 visitor.visit(*this);
74}
75
76bool lst::field::operator==(const lst::field& other) const noexcept
77{
78 return name == other.name && *_type == *other._type;
79}
80
81lst::integer_type::integer_type(unsigned int in_alignment,
82 enum lst::byte_order in_byte_order,
83 unsigned int in_size,
84 enum lst::integer_type::signedness in_signedness,
e7360180
JG
85 enum lst::integer_type::base in_base,
86 roles in_roles) :
0220be14
JG
87 type(in_alignment),
88 byte_order{in_byte_order},
89 size{in_size},
65cd3c0c 90 signedness_{in_signedness},
e7360180
JG
91 base_{in_base},
92 roles_{std::move(in_roles)}
0220be14
JG
93{
94}
95
96bool lst::integer_type::_is_equal(const type &base_other) const noexcept
97{
98 const auto& other = static_cast<decltype(*this)&>(base_other);
99
100 return this->byte_order == other.byte_order &&
101 this->size == other.size &&
65cd3c0c 102 this->signedness_ == other.signedness_ &&
e7360180
JG
103 this->base_ == other.base_ &&
104 this->roles_ == other.roles_;
0220be14
JG
105}
106
107void lst::integer_type::accept(type_visitor& visitor) const
108{
109 visitor.visit(*this);
110}
111
112lst::byte_order lst::type::reverse_byte_order(lst::byte_order byte_order) noexcept
113{
114 if (byte_order == lst::byte_order::BIG_ENDIAN_) {
115 return lst::byte_order::LITTLE_ENDIAN_;
116 } else {
117 return lst::byte_order::BIG_ENDIAN_;
118 }
119}
120
121lst::floating_point_type::floating_point_type(unsigned int in_alignment,
122 lst::byte_order in_byte_order,
123 unsigned int in_exponent_digits,
124 unsigned int in_mantissa_digits) :
125 type(in_alignment),
126 byte_order(in_byte_order),
127 exponent_digits{in_exponent_digits},
128 mantissa_digits(in_mantissa_digits)
129{
130 /* Allowed (exponent, mantissa) pairs. */
d7bfb9b0 131 static const std::set<std::pair<unsigned int, unsigned int>> allowed_pairs{
0220be14
JG
132 {5, 11}, /* binary16 */
133 {8, 24}, /* binary32 */
134 {11, 53}, /* binary64 */
135 {15, 113}, /* binary128 */
136 };
137
d7bfb9b0
JG
138 if (allowed_pairs.find({exponent_digits, mantissa_digits}) != allowed_pairs.end()) {
139 /* mantissa and exponent digits is a valid pair. */
140 return;
0220be14
JG
141 }
142
143 LTTNG_THROW_INVALID_ARGUMENT_ERROR(
144 fmt::format("Invalid exponent/mantissa values provided while creating {}",
145 typeid(*this)));
146}
147
148void lst::floating_point_type::accept(type_visitor& visitor) const
149{
150 visitor.visit(*this);
151}
152
153bool lst::floating_point_type::_is_equal(const type& base_other) const noexcept
154{
155 const auto& other = static_cast<decltype(*this)&>(base_other);
156
157 return this->byte_order == other.byte_order &&
158 this->exponent_digits == other.exponent_digits &&
159 this->mantissa_digits == other.mantissa_digits;
160}
161
162lst::enumeration_type::enumeration_type(unsigned int in_alignment,
163 enum lst::byte_order in_byte_order,
164 unsigned int in_size,
165 enum signedness in_signedness,
e7360180
JG
166 enum base in_base,
167 lst::integer_type::roles in_roles) :
168 integer_type(in_alignment,
169 in_byte_order,
170 in_size,
171 in_signedness,
172 in_base,
173 std::move(in_roles))
0220be14
JG
174{
175}
176
e2c2bec2
JR
177namespace lttng {
178namespace sessiond {
179namespace trace {
0220be14
JG
180template <>
181void lst::signed_enumeration_type::accept(type_visitor& visitor) const
182{
183 visitor.visit(*this);
184}
185
186template <>
187void lst::unsigned_enumeration_type::accept(type_visitor& visitor) const
188{
189 visitor.visit(*this);
190}
e2c2bec2
JR
191} /* namespace trace */
192} /* namespace sessiond */
193} /* namespace lttng */
0220be14
JG
194
195lst::array_type::array_type(unsigned int in_alignment, type::cuptr in_element_type) :
196 type(in_alignment), element_type{std::move(in_element_type)}
197{
198}
199
200bool lst::array_type::_is_equal(const type& base_other) const noexcept
201{
202 const auto& other = static_cast<decltype(*this)&>(base_other);
203
204 return *this->element_type == *other.element_type;
205}
206
207lst::static_length_array_type::static_length_array_type(unsigned int in_alignment,
208 type::cuptr in_element_type,
209 uint64_t in_length) :
210 array_type(in_alignment, std::move(in_element_type)),
211 length{in_length}
212{
213}
214
215bool lst::static_length_array_type::_is_equal(const type& base_other) const noexcept
216{
217 const auto& other = static_cast<decltype(*this)&>(base_other);
218
219 return array_type::_is_equal(base_other) && this->length == other.length;
220}
221
222void lst::static_length_array_type::accept(type_visitor& visitor) const
223{
224 visitor.visit(*this);
225}
226
227lst::dynamic_length_array_type::dynamic_length_array_type(unsigned int in_alignment,
228 type::cuptr in_element_type,
eda1aa02 229 lst::field_location in_length_field_location) :
0220be14 230 array_type(in_alignment, std::move(in_element_type)),
eda1aa02 231 length_field_location{std::move(in_length_field_location)}
0220be14
JG
232{
233}
234
235bool lst::dynamic_length_array_type::_is_equal(const type& base_other) const noexcept
236{
237 const auto& other = static_cast<decltype(*this)&>(base_other);
238
239 return array_type::_is_equal(base_other) &&
eda1aa02 240 this->length_field_location == other.length_field_location;
0220be14
JG
241}
242
243void lst::dynamic_length_array_type::accept(type_visitor& visitor) const
244{
245 visitor.visit(*this);
246}
247
e7360180
JG
248lst::static_length_blob_type::static_length_blob_type(
249 unsigned int in_alignment, uint64_t in_length_bytes, roles in_roles) :
250 type(in_alignment), length_bytes{in_length_bytes}, roles_{std::move(in_roles)}
251{
252}
253
254bool lst::static_length_blob_type::_is_equal(const type& base_other) const noexcept
255{
256 const auto& other = static_cast<decltype(*this)&>(base_other);
257
258 return length_bytes == other.length_bytes && roles_ == other.roles_;
259}
260
261void lst::static_length_blob_type::accept(type_visitor& visitor) const
262{
263 visitor.visit(*this);
264}
265
266lst::dynamic_length_blob_type::dynamic_length_blob_type(
eda1aa02
JG
267 unsigned int in_alignment, lst::field_location in_length_field_location) :
268 type(in_alignment), length_field_location{std::move(in_length_field_location)}
e7360180
JG
269{
270}
271
272bool lst::dynamic_length_blob_type::_is_equal(const type& base_other) const noexcept
273{
274 const auto& other = dynamic_cast<decltype(*this)&>(base_other);
275
eda1aa02 276 return length_field_location == other.length_field_location;
e7360180
JG
277}
278
279void lst::dynamic_length_blob_type::accept(type_visitor& visitor) const
280{
281 visitor.visit(*this);
282}
283
0220be14 284lst::string_type::string_type(unsigned int in_alignment, enum encoding in_encoding) :
65cd3c0c 285 type(in_alignment), encoding_{in_encoding}
0220be14
JG
286{
287}
288
289bool lst::string_type::_is_equal(const type& base_other) const noexcept
290{
291 const auto& other = static_cast<decltype(*this)&>(base_other);
292
65cd3c0c 293 return this->encoding_ == other.encoding_;
0220be14
JG
294}
295
296lst::static_length_string_type::static_length_string_type(
297 unsigned int in_alignment, enum encoding in_encoding, uint64_t in_length) :
298 string_type(in_alignment, in_encoding), length{in_length}
299{
300}
301
302bool lst::static_length_string_type::_is_equal(const type& base_other) const noexcept
303{
304 const auto& other = static_cast<decltype(*this)&>(base_other);
305
306 return string_type::_is_equal(base_other) && this->length == other.length;
307}
308
309void lst::static_length_string_type::accept(type_visitor& visitor) const
310{
311 visitor.visit(*this);
312}
313
314lst::dynamic_length_string_type::dynamic_length_string_type(unsigned int in_alignment,
315 enum encoding in_encoding,
eda1aa02
JG
316 field_location in_length_field_location) :
317 string_type(in_alignment, in_encoding),
318 length_field_location{std::move(in_length_field_location)}
0220be14
JG
319{
320}
321
322bool lst::dynamic_length_string_type::_is_equal(const type& base_other) const noexcept
323{
324 const auto& other = static_cast<decltype(*this)&>(base_other);
325
326 return string_type::_is_equal(base_other) &&
eda1aa02 327 this->length_field_location == other.length_field_location;
0220be14
JG
328}
329
330void lst::dynamic_length_string_type::accept(type_visitor& visitor) const
331{
332 visitor.visit(*this);
333}
334
335lst::null_terminated_string_type::null_terminated_string_type(unsigned int in_alignment,
336 enum encoding in_encoding) :
337 string_type(in_alignment, in_encoding)
338{
339}
340
341void lst::null_terminated_string_type::accept(type_visitor& visitor) const
342{
343 visitor.visit(*this);
344}
345
346lst::structure_type::structure_type(unsigned int in_alignment, fields in_fields) :
347 type(in_alignment), _fields{std::move(in_fields)}
348{
349}
350
351bool lst::structure_type::_is_equal(const type& base_other) const noexcept
352{
353 const auto &other = static_cast<decltype(*this)&>(base_other);
354
355 return fields_are_equal(this->_fields, other._fields);
356}
357
358void lst::structure_type::accept(type_visitor& visitor) const
359{
360 visitor.visit(*this);
361}
362
363lst::variant_type::variant_type(unsigned int in_alignment,
eda1aa02 364 field_location in_selector_field_location,
0220be14
JG
365 choices in_choices) :
366 type(in_alignment),
eda1aa02
JG
367 selector_field_location{std::move(in_selector_field_location)},
368 _choices
369{std::move(in_choices)}
0220be14
JG
370{
371}
372
373bool lst::variant_type::_is_equal(const type& base_other) const noexcept
374{
375 const auto &other = static_cast<decltype(*this)&>(base_other);
376
eda1aa02
JG
377 return this->selector_field_location == other.selector_field_location &&
378 fields_are_equal(this->_choices
379, other._choices
380);
0220be14
JG
381}
382
383void lst::variant_type::accept(type_visitor& visitor) const
384{
385 visitor.visit(*this);
d7bfb9b0 386}
This page took 0.039724 seconds and 4 git commands to generate.