2 * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
4 * SPDX-License-Identifier: GPL-2.0-only
10 #include <common/exception.hpp>
11 #include <common/format.hpp>
15 namespace lst
= lttng::sessiond::trace
;
18 template <class FieldTypeSet
>
19 bool fields_are_equal(const FieldTypeSet
& a
, const FieldTypeSet
& b
)
21 if (a
.size() != b
.size()) {
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
;
33 lst::type::type(unsigned int in_alignment
) : alignment
{in_alignment
}
41 bool lst::type::operator==(const lst::type
& other
) const noexcept
43 return typeid(*this) == typeid(other
) &&
44 alignment
== other
.alignment
&&
45 /* defer to concrete type comparison */
46 this->_is_equal(other
);
49 bool lst::type::operator!=(const lst::type
& other
) const noexcept
51 return !(*this == other
);
54 lst::field::field(std::string in_name
, lst::type::cuptr in_type
) :
55 name
{std::move(in_name
)}, _type
{std::move(in_type
)}
59 void lst::field::accept(lst::field_visitor
& visitor
) const
64 bool lst::field::operator==(const lst::field
& other
) const noexcept
66 return name
== other
.name
&& *_type
== *other
._type
;
69 lst::integer_type::integer_type(unsigned int in_alignment
,
70 enum lst::byte_order in_byte_order
,
72 enum lst::integer_type::signedness in_signedness
,
73 enum lst::integer_type::base in_base
,
76 byte_order
{in_byte_order
},
78 signedness_
{in_signedness
},
80 roles_
{std::move(in_roles
)}
84 bool lst::integer_type::_is_equal(const type
&base_other
) const noexcept
86 const auto& other
= static_cast<decltype(*this)&>(base_other
);
88 return this->byte_order
== other
.byte_order
&&
89 this->size
== other
.size
&&
90 this->signedness_
== other
.signedness_
&&
91 this->base_
== other
.base_
&&
92 this->roles_
== other
.roles_
;
95 void lst::integer_type::accept(type_visitor
& visitor
) const
100 lst::byte_order
lst::type::reverse_byte_order(lst::byte_order byte_order
) noexcept
102 if (byte_order
== lst::byte_order::BIG_ENDIAN_
) {
103 return lst::byte_order::LITTLE_ENDIAN_
;
105 return lst::byte_order::BIG_ENDIAN_
;
109 lst::floating_point_type::floating_point_type(unsigned int in_alignment
,
110 lst::byte_order in_byte_order
,
111 unsigned int in_exponent_digits
,
112 unsigned int in_mantissa_digits
) :
114 byte_order(in_byte_order
),
115 exponent_digits
{in_exponent_digits
},
116 mantissa_digits(in_mantissa_digits
)
118 /* Allowed (exponent, mantissa) pairs. */
119 static const std::set
<std::pair
<unsigned int, unsigned int>> allowed_pairs
{
120 {5, 11}, /* binary16 */
121 {8, 24}, /* binary32 */
122 {11, 53}, /* binary64 */
123 {15, 113}, /* binary128 */
126 if (allowed_pairs
.find({exponent_digits
, mantissa_digits
}) != allowed_pairs
.end()) {
127 /* mantissa and exponent digits is a valid pair. */
131 LTTNG_THROW_INVALID_ARGUMENT_ERROR(
132 fmt::format("Invalid exponent/mantissa values provided while creating {}",
136 void lst::floating_point_type::accept(type_visitor
& visitor
) const
138 visitor
.visit(*this);
141 bool lst::floating_point_type::_is_equal(const type
& base_other
) const noexcept
143 const auto& other
= static_cast<decltype(*this)&>(base_other
);
145 return this->byte_order
== other
.byte_order
&&
146 this->exponent_digits
== other
.exponent_digits
&&
147 this->mantissa_digits
== other
.mantissa_digits
;
150 lst::enumeration_type::enumeration_type(unsigned int in_alignment
,
151 enum lst::byte_order in_byte_order
,
152 unsigned int in_size
,
153 enum signedness in_signedness
,
155 lst::integer_type::roles in_roles
) :
156 integer_type(in_alignment
,
169 void lst::signed_enumeration_type::accept(type_visitor
& visitor
) const
171 visitor
.visit(*this);
175 void lst::unsigned_enumeration_type::accept(type_visitor
& visitor
) const
177 visitor
.visit(*this);
179 } /* namespace trace */
180 } /* namespace sessiond */
181 } /* namespace lttng */
183 lst::array_type::array_type(unsigned int in_alignment
, type::cuptr in_element_type
) :
184 type(in_alignment
), element_type
{std::move(in_element_type
)}
188 bool lst::array_type::_is_equal(const type
& base_other
) const noexcept
190 const auto& other
= static_cast<decltype(*this)&>(base_other
);
192 return *this->element_type
== *other
.element_type
;
195 lst::static_length_array_type::static_length_array_type(unsigned int in_alignment
,
196 type::cuptr in_element_type
,
197 uint64_t in_length
) :
198 array_type(in_alignment
, std::move(in_element_type
)),
203 bool lst::static_length_array_type::_is_equal(const type
& base_other
) const noexcept
205 const auto& other
= static_cast<decltype(*this)&>(base_other
);
207 return array_type::_is_equal(base_other
) && this->length
== other
.length
;
210 void lst::static_length_array_type::accept(type_visitor
& visitor
) const
212 visitor
.visit(*this);
215 lst::dynamic_length_array_type::dynamic_length_array_type(unsigned int in_alignment
,
216 type::cuptr in_element_type
,
217 std::string in_length_field_name
) :
218 array_type(in_alignment
, std::move(in_element_type
)),
219 length_field_name
{std::move(in_length_field_name
)}
223 bool lst::dynamic_length_array_type::_is_equal(const type
& base_other
) const noexcept
225 const auto& other
= static_cast<decltype(*this)&>(base_other
);
227 return array_type::_is_equal(base_other
) &&
228 this->length_field_name
== other
.length_field_name
;
231 void lst::dynamic_length_array_type::accept(type_visitor
& visitor
) const
233 visitor
.visit(*this);
236 lst::static_length_blob_type::static_length_blob_type(
237 unsigned int in_alignment
, uint64_t in_length_bytes
, roles in_roles
) :
238 type(in_alignment
), length_bytes
{in_length_bytes
}, roles_
{std::move(in_roles
)}
242 bool lst::static_length_blob_type::_is_equal(const type
& base_other
) const noexcept
244 const auto& other
= static_cast<decltype(*this)&>(base_other
);
246 return length_bytes
== other
.length_bytes
&& roles_
== other
.roles_
;
249 void lst::static_length_blob_type::accept(type_visitor
& visitor
) const
251 visitor
.visit(*this);
254 lst::dynamic_length_blob_type::dynamic_length_blob_type(
255 unsigned int in_alignment
, std::string in_length_field_name
) :
256 type(in_alignment
), length_field_name
{std::move(in_length_field_name
)}
260 bool lst::dynamic_length_blob_type::_is_equal(const type
& base_other
) const noexcept
262 const auto& other
= dynamic_cast<decltype(*this)&>(base_other
);
264 return length_field_name
== other
.length_field_name
;
267 void lst::dynamic_length_blob_type::accept(type_visitor
& visitor
) const
269 visitor
.visit(*this);
272 lst::string_type::string_type(unsigned int in_alignment
, enum encoding in_encoding
) :
273 type(in_alignment
), encoding_
{in_encoding
}
277 bool lst::string_type::_is_equal(const type
& base_other
) const noexcept
279 const auto& other
= static_cast<decltype(*this)&>(base_other
);
281 return this->encoding_
== other
.encoding_
;
284 lst::static_length_string_type::static_length_string_type(
285 unsigned int in_alignment
, enum encoding in_encoding
, uint64_t in_length
) :
286 string_type(in_alignment
, in_encoding
), length
{in_length
}
290 bool lst::static_length_string_type::_is_equal(const type
& base_other
) const noexcept
292 const auto& other
= static_cast<decltype(*this)&>(base_other
);
294 return string_type::_is_equal(base_other
) && this->length
== other
.length
;
297 void lst::static_length_string_type::accept(type_visitor
& visitor
) const
299 visitor
.visit(*this);
302 lst::dynamic_length_string_type::dynamic_length_string_type(unsigned int in_alignment
,
303 enum encoding in_encoding
,
304 std::string in_length_field_name
) :
305 string_type(in_alignment
, in_encoding
), length_field_name
{std::move(in_length_field_name
)}
309 bool lst::dynamic_length_string_type::_is_equal(const type
& base_other
) const noexcept
311 const auto& other
= static_cast<decltype(*this)&>(base_other
);
313 return string_type::_is_equal(base_other
) &&
314 this->length_field_name
== other
.length_field_name
;
317 void lst::dynamic_length_string_type::accept(type_visitor
& visitor
) const
319 visitor
.visit(*this);
322 lst::null_terminated_string_type::null_terminated_string_type(unsigned int in_alignment
,
323 enum encoding in_encoding
) :
324 string_type(in_alignment
, in_encoding
)
328 void lst::null_terminated_string_type::accept(type_visitor
& visitor
) const
330 visitor
.visit(*this);
333 lst::structure_type::structure_type(unsigned int in_alignment
, fields in_fields
) :
334 type(in_alignment
), _fields
{std::move(in_fields
)}
338 bool lst::structure_type::_is_equal(const type
& base_other
) const noexcept
340 const auto &other
= static_cast<decltype(*this)&>(base_other
);
342 return fields_are_equal(this->_fields
, other
._fields
);
345 void lst::structure_type::accept(type_visitor
& visitor
) const
347 visitor
.visit(*this);
350 lst::variant_type::variant_type(unsigned int in_alignment
,
351 std::string in_tag_name
,
352 choices in_choices
) :
354 tag_name
{std::move(in_tag_name
)},
355 _choices
{std::move(in_choices
)}
359 bool lst::variant_type::_is_equal(const type
& base_other
) const noexcept
361 const auto &other
= static_cast<decltype(*this)&>(base_other
);
363 return this->tag_name
== other
.tag_name
&&
364 fields_are_equal(this->_choices
, other
._choices
);
367 void lst::variant_type::accept(type_visitor
& visitor
) const
369 visitor
.visit(*this);