sessiond: ust: conditionally enable the underscore prefix variant quirk
[lttng-tools.git] / src / bin / lttng-sessiond / field.cpp
index d81cf02c736ccb9f061fdacdf1dcf33cc2ebd66b..e46e06631eae121b4736547b31995839783bd381 100644 (file)
@@ -30,6 +30,18 @@ bool fields_are_equal(const FieldTypeSet& a, const FieldTypeSet& b)
 }
 } /* namespace */
 
+lst::field_location::field_location(lst::field_location::root in_lookup_root,
+               lst::field_location::elements in_elements) :
+       root_{in_lookup_root}, elements_{std::move(in_elements)}
+{
+}
+
+bool lst::field_location::operator==(const lst::field_location& other) const noexcept
+{
+       return root_ == other.root_ &&
+                       elements_ == other.elements_;
+}
+
 lst::type::type(unsigned int in_alignment) : alignment{in_alignment}
 {
 }
@@ -54,6 +66,9 @@ bool lst::type::operator!=(const lst::type& other) const noexcept
 lst::field::field(std::string in_name, lst::type::cuptr in_type) :
        name{std::move(in_name)}, _type{std::move(in_type)}
 {
+       if (!_type) {
+               LTTNG_THROW_ERROR(fmt::format("Invalid type used to create field: field name = `{}`", name));
+       }
 }
 
 void lst::field::accept(lst::field_visitor& visitor) const
@@ -66,6 +81,20 @@ bool lst::field::operator==(const lst::field& other) const noexcept
        return name == other.name && *_type == *other._type;
 }
 
+lst::type::cuptr lst::field::move_type() noexcept
+{
+       return std::move(_type);
+}
+
+const lst::type &lst::field::get_type() const
+{
+       if (_type) {
+               return *_type;
+       } else {
+               LTTNG_THROW_ERROR(fmt::format("Invalid attempt to access field type after transfer: field name = `{}`", name));
+       }
+}
+
 lst::integer_type::integer_type(unsigned int in_alignment,
                enum lst::byte_order in_byte_order,
                unsigned int in_size,
@@ -81,6 +110,12 @@ lst::integer_type::integer_type(unsigned int in_alignment,
 {
 }
 
+lst::type::cuptr lst::integer_type::copy() const
+{
+       return lttng::make_unique<integer_type>(
+                       alignment, byte_order, size, signedness_, base_, roles_);
+}
+
 bool lst::integer_type::_is_equal(const type &base_other) const noexcept
 {
        const auto& other = static_cast<decltype(*this)&>(base_other);
@@ -133,6 +168,12 @@ lst::floating_point_type::floating_point_type(unsigned int in_alignment,
                                        typeid(*this)));
 }
 
+lst::type::cuptr lst::floating_point_type::copy() const
+{
+       return lttng::make_unique<floating_point_type>(
+                       alignment, byte_order, exponent_digits, mantissa_digits);
+}
+
 void lst::floating_point_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
@@ -162,17 +203,36 @@ lst::enumeration_type::enumeration_type(unsigned int in_alignment,
 {
 }
 
+/*
+ * Due to a bug in g++ < 7.1, these specializations must be enclosed in the namespaces
+ * rather than using the usual `namespace::namespace::function` notation:
+ * see https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56480.
+ */
 namespace lttng {
 namespace sessiond {
 namespace trace {
 template <>
-void lst::signed_enumeration_type::accept(type_visitor& visitor) const
+void signed_enumeration_type::accept(type_visitor& visitor) const
+{
+       visitor.visit(*this);
+}
+
+template <>
+void unsigned_enumeration_type::accept(type_visitor& visitor) const
+{
+       visitor.visit(*this);
+}
+
+template <>
+void variant_type<lst::signed_enumeration_type::mapping::range_t::range_integer_t>::accept(
+               lst::type_visitor& visitor) const
 {
        visitor.visit(*this);
 }
 
 template <>
-void lst::unsigned_enumeration_type::accept(type_visitor& visitor) const
+void variant_type<lst::unsigned_enumeration_type::mapping::range_t::range_integer_t>::accept(
+               lst::type_visitor& visitor) const
 {
        visitor.visit(*this);
 }
@@ -207,6 +267,12 @@ bool lst::static_length_array_type::_is_equal(const type& base_other) const noex
        return array_type::_is_equal(base_other) && this->length == other.length;
 }
 
+lst::type::cuptr lst::static_length_array_type::copy() const
+{
+       return lttng::make_unique<static_length_array_type>(
+                       alignment, element_type->copy(), length);
+}
+
 void lst::static_length_array_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
@@ -214,9 +280,9 @@ void lst::static_length_array_type::accept(type_visitor& visitor) const
 
 lst::dynamic_length_array_type::dynamic_length_array_type(unsigned int in_alignment,
                type::cuptr in_element_type,
-               std::string in_length_field_name) :
+               lst::field_location in_length_field_location) :
        array_type(in_alignment, std::move(in_element_type)),
-       length_field_name{std::move(in_length_field_name)}
+       length_field_location{std::move(in_length_field_location)}
 {
 }
 
@@ -225,7 +291,13 @@ bool lst::dynamic_length_array_type::_is_equal(const type& base_other) const noe
        const auto& other = static_cast<decltype(*this)&>(base_other);
 
        return array_type::_is_equal(base_other) &&
-                       this->length_field_name == other.length_field_name;
+                       this->length_field_location == other.length_field_location;
+}
+
+lst::type::cuptr lst::dynamic_length_array_type::copy() const
+{
+       return lttng::make_unique<dynamic_length_array_type>(
+                       alignment, element_type->copy(), length_field_location);
 }
 
 void lst::dynamic_length_array_type::accept(type_visitor& visitor) const
@@ -246,14 +318,19 @@ bool lst::static_length_blob_type::_is_equal(const type& base_other) const noexc
        return length_bytes == other.length_bytes && roles_ == other.roles_;
 }
 
+lst::type::cuptr lst::static_length_blob_type::copy() const
+{
+       return lttng::make_unique<static_length_blob_type>(alignment, length_bytes, roles_);
+}
+
 void lst::static_length_blob_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
 }
 
 lst::dynamic_length_blob_type::dynamic_length_blob_type(
-               unsigned int in_alignment, std::string in_length_field_name) :
-       type(in_alignment), length_field_name{std::move(in_length_field_name)}
+               unsigned int in_alignment, lst::field_location in_length_field_location) :
+       type(in_alignment), length_field_location{std::move(in_length_field_location)}
 {
 }
 
@@ -261,7 +338,12 @@ bool lst::dynamic_length_blob_type::_is_equal(const type& base_other) const noex
 {
        const auto& other = dynamic_cast<decltype(*this)&>(base_other);
 
-       return length_field_name == other.length_field_name;
+       return length_field_location == other.length_field_location;
+}
+
+lst::type::cuptr lst::dynamic_length_blob_type::copy() const
+{
+       return lttng::make_unique<dynamic_length_blob_type>(alignment, length_field_location);
 }
 
 void lst::dynamic_length_blob_type::accept(type_visitor& visitor) const
@@ -294,6 +376,11 @@ bool lst::static_length_string_type::_is_equal(const type& base_other) const noe
        return string_type::_is_equal(base_other) && this->length == other.length;
 }
 
+lst::type::cuptr lst::static_length_string_type::copy() const
+{
+       return lttng::make_unique<static_length_string_type>(alignment, encoding_, length);
+}
+
 void lst::static_length_string_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
@@ -301,8 +388,9 @@ void lst::static_length_string_type::accept(type_visitor& visitor) const
 
 lst::dynamic_length_string_type::dynamic_length_string_type(unsigned int in_alignment,
                enum encoding in_encoding,
-               std::string in_length_field_name) :
-       string_type(in_alignment, in_encoding), length_field_name{std::move(in_length_field_name)}
+               field_location in_length_field_location) :
+       string_type(in_alignment, in_encoding),
+       length_field_location{std::move(in_length_field_location)}
 {
 }
 
@@ -311,7 +399,13 @@ bool lst::dynamic_length_string_type::_is_equal(const type& base_other) const no
        const auto& other = static_cast<decltype(*this)&>(base_other);
 
        return string_type::_is_equal(base_other) &&
-                       this->length_field_name == other.length_field_name;
+                       this->length_field_location == other.length_field_location;
+}
+
+lst::type::cuptr lst::dynamic_length_string_type::copy() const
+{
+       return lttng::make_unique<dynamic_length_string_type>(
+                       alignment, encoding_, length_field_location);
 }
 
 void lst::dynamic_length_string_type::accept(type_visitor& visitor) const
@@ -325,13 +419,18 @@ lst::null_terminated_string_type::null_terminated_string_type(unsigned int in_al
 {
 }
 
+lst::type::cuptr lst::null_terminated_string_type::copy() const
+{
+       return lttng::make_unique<null_terminated_string_type>(alignment, encoding_);
+}
+
 void lst::null_terminated_string_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
 }
 
 lst::structure_type::structure_type(unsigned int in_alignment, fields in_fields) :
-       type(in_alignment), _fields{std::move(in_fields)}
+       type(in_alignment), fields_{std::move(in_fields)}
 {
 }
 
@@ -339,32 +438,23 @@ bool lst::structure_type::_is_equal(const type& base_other) const noexcept
 {
        const auto &other = static_cast<decltype(*this)&>(base_other);
 
-       return fields_are_equal(this->_fields, other._fields);
-}
-
-void lst::structure_type::accept(type_visitor& visitor) const
-{
-       visitor.visit(*this);
+       return fields_are_equal(this->fields_, other.fields_);
 }
 
-lst::variant_type::variant_type(unsigned int in_alignment,
-               std::string in_tag_name,
-               choices in_choices) :
-       type(in_alignment),
-       tag_name{std::move(in_tag_name)},
-       _choices{std::move(in_choices)}
+lst::type::cuptr lst::structure_type::copy() const
 {
-}
+       structure_type::fields copy_of_fields;
 
-bool lst::variant_type::_is_equal(const type& base_other) const noexcept
-{
-       const auto &other = static_cast<decltype(*this)&>(base_other);
+       copy_of_fields.reserve(fields_.size());
+       for (const auto& field : fields_) {
+               copy_of_fields.emplace_back(lttng::make_unique<lst::field>(
+                               field->name, field->get_type().copy()));
+       }
 
-       return this->tag_name == other.tag_name &&
-                       fields_are_equal(this->_choices, other._choices);
+       return lttng::make_unique<structure_type>(alignment, std::move(copy_of_fields));
 }
 
-void lst::variant_type::accept(type_visitor& visitor) const
+void lst::structure_type::accept(type_visitor& visitor) const
 {
        visitor.visit(*this);
 }
This page took 0.026559 seconds and 4 git commands to generate.