From 2cbbc4a8a97cd69e66de497cc9672f97594c06aa Mon Sep 17 00:00:00 2001 From: Antonio Cuadros <49162117+Acuadros95@users.noreply.github.com> Date: Tue, 25 Jul 2023 10:06:29 +0200 Subject: [PATCH] Fix deserialization endianness (#336) * Fix deserialization endianness Signed-off-by: acuadros95 * Update doxy Signed-off-by: acuadros95 * Add XRCE Endianness enum Signed-off-by: acuadros95 --------- Signed-off-by: acuadros95 --- include/uxr/agent/message/InputMessage.hpp | 7 ++ include/uxr/agent/types/XRCETypes.hpp | 81 +++++++++++++++++++++- src/cpp/datareader/DataReader.cpp | 6 +- src/cpp/datawriter/DataWriter.cpp | 6 +- src/cpp/participant/Participant.cpp | 6 +- src/cpp/processor/Processor.cpp | 3 + src/cpp/publisher/Publisher.cpp | 3 +- src/cpp/replier/Replier.cpp | 6 +- src/cpp/requester/Requester.cpp | 6 +- src/cpp/subscriber/Subscriber.cpp | 3 +- src/cpp/topic/Topic.cpp | 6 +- 11 files changed, 116 insertions(+), 17 deletions(-) diff --git a/include/uxr/agent/message/InputMessage.hpp b/include/uxr/agent/message/InputMessage.hpp index 8533fdb9..fbb9c331 100644 --- a/include/uxr/agent/message/InputMessage.hpp +++ b/include/uxr/agent/message/InputMessage.hpp @@ -100,6 +100,13 @@ inline bool InputMessage::prepare_next_submessage() if (fastbuffer_.getBufferSize() > deserializer_.getSerializedDataLength()) { rv = deserialize(subheader_); + + // Check submessage endianness + fastcdr::Cdr::Endianness endianness = static_cast(subheader_.flags() & 0x01); + if (endianness != deserializer_.endianness()) + { + deserializer_.changeEndianness(endianness); + } } return rv; } diff --git a/include/uxr/agent/types/XRCETypes.hpp b/include/uxr/agent/types/XRCETypes.hpp index 404057a6..7d58e476 100644 --- a/include/uxr/agent/types/XRCETypes.hpp +++ b/include/uxr/agent/types/XRCETypes.hpp @@ -91,6 +91,15 @@ const XrceVersion XRCE_VERSION = {XRCE_VERSION_MAJOR, XRCE_VERSION_MINOR}; const uint8_t XRCE_VENDOR_INVALID1 = 0x00; const uint8_t XRCE_VENDOR_INVALID2 = 0x00; +//! @brief This enumeration represents the two posible values of the SubMessage endianness flag. +typedef enum Endianness +{ + //! @brief Big endianness. + BIG_ENDIANNESS = 0x0, + //! @brief Little endianness. + LITTLE_ENDIANNESS = 0x1 +} Endianness; + /*! * @brief This class represents the structure Time_t defined by the user in the IDL file. * @ingroup TYPESMOD @@ -2364,6 +2373,24 @@ class OBJK_RepresentationBinAndXML_Base return m_representation; } + /*! + * @brief This function updates the value in representation endianness + * @param endianness New value of representation endianness + */ + inline void endianness(Endianness endianness) + { + m_endianness = endianness; + } + + /*! + * @brief This function returns a copy to the representation endianness + * @return Representation endianness + */ + inline Endianness endianness() const + { + return m_endianness; + } + /*! * @brief This function returns the maximum serialized size of an object * depending on the buffer alignment. @@ -2395,6 +2422,7 @@ class OBJK_RepresentationBinAndXML_Base private: OBJK_RepresentationBinAndXMLFormats m_representation; + Endianness m_endianness; }; /*! @@ -2474,7 +2502,25 @@ class OBJK_Representation3_Base { return m_representation; } - + + /*! + * @brief This function updates the value in representation endianness + * @param endianness New value of representation endianness + */ + inline void endianness(Endianness endianness) + { + m_endianness = endianness; + } + + /*! + * @brief This function returns a copy to the representation endianness + * @return Representation endianness + */ + inline Endianness endianness() const + { + return m_endianness; + } + /*! * @brief This function returns the maximum serialized size of an object * depending on the buffer alignment. @@ -2505,6 +2551,7 @@ class OBJK_Representation3_Base private: OBJK_Representation3Formats m_representation; + Endianness m_endianness; }; /*! @@ -5902,7 +5949,34 @@ class ObjectVariant * @exception dds::xrce::XRCETypesException This exception is thrown if the requested union member is not the current selection. */ REPLIER_Representation& replier(); - + + /*! + * @brief This function updates the value in representation endianness + * @param endianness New value of representation endianness + */ + inline void endianness(Endianness endianness) + { + m_endianness = endianness; + + m_participant.endianness(m_endianness); + m_topic.endianness(m_endianness); + m_publisher.endianness(m_endianness); + m_subscriber.endianness(m_endianness); + m_data_writer.endianness(m_endianness); + m_data_reader.endianness(m_endianness); + m_requester.endianness(m_endianness); + m_replier.endianness(m_endianness); + } + + /*! + * @brief This function returns a copy to the representation endianness + * @return Representation endianness + */ + inline Endianness endianness() const + { + return m_endianness; + } + /*! * @brief This function returns the maximum serialized size of an object * depending on the buffer alignment. @@ -5933,7 +6007,8 @@ class ObjectVariant private: ObjectKind m__d; - + Endianness m_endianness; + AGENT_Representation m_agent; CLIENT_Representation m_client; OBJK_APPLICATION_Representation m_application; diff --git a/src/cpp/datareader/DataReader.cpp b/src/cpp/datareader/DataReader.cpp index 97b875fc..4dfcea17 100644 --- a/src/cpp/datareader/DataReader.cpp +++ b/src/cpp/datareader/DataReader.cpp @@ -54,7 +54,8 @@ std::unique_ptr DataReader::create( dds::xrce::OBJK_DataReader_Binary datareader_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); datareader_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_datareader_by_bin(raw_object_id, subscriber_id, datareader_xrce); @@ -111,7 +112,8 @@ bool DataReader::matched( dds::xrce::OBJK_DataReader_Binary datareader_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); datareader_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_datareader_from_bin(get_raw_id(), datareader_xrce); diff --git a/src/cpp/datawriter/DataWriter.cpp b/src/cpp/datawriter/DataWriter.cpp index b47326cc..9423deb4 100644 --- a/src/cpp/datawriter/DataWriter.cpp +++ b/src/cpp/datawriter/DataWriter.cpp @@ -52,7 +52,8 @@ std::unique_ptr DataWriter::create( dds::xrce::OBJK_DataWriter_Binary datawriter_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); datawriter_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_datawriter_by_bin(raw_object_id, publisher_id, datawriter_xrce); @@ -105,7 +106,8 @@ bool DataWriter::matched(const dds::xrce::ObjectVariant& new_object_rep) const dds::xrce::OBJK_DataWriter_Binary datawriter_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); datawriter_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_datawriter_from_bin(get_raw_id(), datawriter_xrce); diff --git a/src/cpp/participant/Participant.cpp b/src/cpp/participant/Participant.cpp index 2b49ea86..45d6c63f 100644 --- a/src/cpp/participant/Participant.cpp +++ b/src/cpp/participant/Participant.cpp @@ -48,7 +48,8 @@ std::unique_ptr Participant::create( participant_xrce.domain_id(representation.domain_id()); fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); participant_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_participant_by_bin(raw_object_id, participant_xrce); @@ -106,7 +107,8 @@ bool Participant::matched(const dds::xrce::ObjectVariant& new_object_rep) const participant_xrce.domain_id(domain_id); fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); participant_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_participant_from_bin(get_raw_id(), domain_id, participant_xrce); diff --git a/src/cpp/processor/Processor.cpp b/src/cpp/processor/Processor.cpp index 14a3b410..8133d7f7 100644 --- a/src/cpp/processor/Processor.cpp +++ b/src/cpp/processor/Processor.cpp @@ -332,6 +332,9 @@ bool Processor::process_create_submessage( dds::xrce::CREATE_Payload create_payload; if (input_packet.message->get_payload(create_payload)) { + dds::xrce::Endianness endianness = static_cast(input_packet.message->get_subheader().flags() & 0x01); + create_payload.object_representation().endianness(endianness); + dds::xrce::STATUS_Payload status_payload; status_payload.related_request().request_id(create_payload.request_id()); status_payload.related_request().object_id(create_payload.object_id()); diff --git a/src/cpp/publisher/Publisher.cpp b/src/cpp/publisher/Publisher.cpp index 0a47a9b1..078b3382 100644 --- a/src/cpp/publisher/Publisher.cpp +++ b/src/cpp/publisher/Publisher.cpp @@ -42,7 +42,8 @@ std::unique_ptr Publisher::create( dds::xrce::OBJK_Publisher_Binary publisher_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); publisher_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_publisher_by_bin(raw_object_id, participant_id, publisher_xrce); diff --git a/src/cpp/replier/Replier.cpp b/src/cpp/replier/Replier.cpp index c6010caa..e1bbb642 100644 --- a/src/cpp/replier/Replier.cpp +++ b/src/cpp/replier/Replier.cpp @@ -52,7 +52,8 @@ std::unique_ptr Replier::create( dds::xrce::OBJK_Replier_Binary replier_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); replier_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_replier_by_bin(raw_object_id, participant_id, replier_xrce); @@ -108,7 +109,8 @@ bool Replier::matched( dds::xrce::OBJK_Replier_Binary replier_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); replier_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_replier_from_bin(get_raw_id(), replier_xrce); diff --git a/src/cpp/requester/Requester.cpp b/src/cpp/requester/Requester.cpp index d747f0ed..e1dddb75 100644 --- a/src/cpp/requester/Requester.cpp +++ b/src/cpp/requester/Requester.cpp @@ -54,7 +54,8 @@ std::unique_ptr Requester::create( dds::xrce::OBJK_Requester_Binary request_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); request_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_requester_by_bin(raw_object_id, participant_id, request_xrce); @@ -110,7 +111,8 @@ bool Requester::matched( dds::xrce::OBJK_Requester_Binary request_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); request_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_requester_from_bin(get_raw_id(), request_xrce); diff --git a/src/cpp/subscriber/Subscriber.cpp b/src/cpp/subscriber/Subscriber.cpp index ff0cdecb..409c0ad0 100644 --- a/src/cpp/subscriber/Subscriber.cpp +++ b/src/cpp/subscriber/Subscriber.cpp @@ -42,7 +42,8 @@ std::unique_ptr Subscriber::create( dds::xrce::OBJK_Subscriber_Binary subscriber_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); subscriber_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_subscriber_by_bin(raw_object_id, participant_id, subscriber_xrce); diff --git a/src/cpp/topic/Topic.cpp b/src/cpp/topic/Topic.cpp index 5c587131..8a77183b 100644 --- a/src/cpp/topic/Topic.cpp +++ b/src/cpp/topic/Topic.cpp @@ -49,7 +49,8 @@ std::unique_ptr Topic::create( dds::xrce::OBJK_Topic_Binary topic_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(representation.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); topic_xrce.deserialize(cdr); created_entity = proxy_client->get_middleware().create_topic_by_bin(raw_object_id, participant_id, topic_xrce); @@ -103,7 +104,8 @@ bool Topic::matched(const dds::xrce::ObjectVariant& new_object_rep) const dds::xrce::OBJK_Topic_Binary topic_xrce; fastcdr::FastBuffer fastbuffer{reinterpret_cast(const_cast(rep.binary_representation().data())), rep.binary_representation().size()}; - eprosima::fastcdr::Cdr cdr(fastbuffer); + eprosima::fastcdr::Cdr::Endianness endianness = static_cast(new_object_rep.endianness()); + eprosima::fastcdr::Cdr cdr(fastbuffer, endianness); topic_xrce.deserialize(cdr); rv = proxy_client_->get_middleware().matched_topic_from_bin(get_raw_id(), topic_xrce);