diff options
author | Romain Forlot <romain.forlot@iot.bzh> | 2017-02-22 17:47:39 +0100 |
---|---|---|
committer | Romain Forlot <romain.forlot@iot.bzh> | 2017-02-22 17:47:39 +0100 |
commit | 7a570f951d151a73ee9e0755c263c9a8eb8eb806 (patch) | |
tree | b67cfd85bc3ef1962189a29072c508a2f5940275 | |
parent | 836feaecd602e86ea6d954ae018a2d7bbc04aa7a (diff) |
Enhance error handling about can_message_t class
Change-Id: I9fbda1110eea7a3bd7e5855739280aa10bce5a6b
Signed-off-by: Romain Forlot <romain.forlot@iot.bzh>
-rw-r--r-- | src/can-utils.cpp | 54 | ||||
-rw-r--r-- | src/can-utils.hpp | 126 |
2 files changed, 145 insertions, 35 deletions
diff --git a/src/can-utils.cpp b/src/can-utils.cpp index fb6025ce..42763b8f 100644 --- a/src/can-utils.cpp +++ b/src/can-utils.cpp @@ -24,32 +24,42 @@ *********************************************************************************/ can_message_t::can_message_t(const struct afb_binding_interface* interface) - : interface_{interface} + : interface_{interface}, id_{0}, length_{0}, format_{CanMessageFormat::ERROR}, data_{0,0,0,0,0,0,0,0} {} uint32_t can_message_t::get_id() const { - if (id_ != 0) - return id_; - return 0; + return id_; } int can_message_t::get_format() const { if (format_ != CanMessageFormat::STANDARD || format_ != CanMessageFormat::EXTENDED) - return -1; + return CanMessageFormat::ERROR; return format_; } const uint8_t* can_message_t::get_data() const { - return &data_; + return data_; } uint8_t can_message_t::get_length() const { return length_; } +bool can_message_t::is_correct_to_send() +{ + if (id_ != 0 && length_ != 0 && format_ != CanMessageFormat::ERROR) + { + int i; + for(i=0;i<CAN_MESSAGE_SIZE;i++) + if(data_[i] != 0) + return true; + } + return false; +} + void can_message_t::set_id(const uint32_t new_id) { switch(format_) @@ -76,23 +86,25 @@ void can_message_t::set_format(const CanMessageFormat new_format) void can_message_t::set_data(const uint8_t new_data) { - ::memcpy(&data_, &new_data, sizeof(new_data)); - length_ = sizeof(new_data); + if ((sizeof(new_data) / sizeof(uint8_t) > CAN_MESSAGE_SIZE)) + ERROR(interface_, "Can set data, your data array is too big"); + else + { + ::memcpy(&data_, &new_data, sizeof(new_data)); + length_ = sizeof(new_data); + } } -/* - * @brief This is the preferred way to initialize a CanMessage object - * from a read canfd_frame message. - * - * @param: canfd_frame pointer - */ void can_message_t::convert_from_canfd_frame(const canfd_frame& frame) { length_ = (frame.len > CAN_MAX_DLEN) ? (uint8_t)CAN_MAX_DLEN : frame.len; length_ = (frame.len > CANFD_MAX_DLEN) ? (uint8_t)CANFD_MAX_DLEN : frame.len; if (frame.can_id & CAN_ERR_FLAG) + { id_ = frame.can_id & (CAN_ERR_MASK|CAN_ERR_FLAG); + format_ = CanMessageFormat::ERROR; + } else if (frame.can_id & CAN_EFF_FLAG) { id_ = frame.can_id & CAN_EFF_MASK; @@ -114,12 +126,18 @@ canfd_frame can_message_t::convert_to_canfd_frame() { canfd_frame frame; - frame.can_id = get_id(); - frame.len = get_length(); - ::memcpy(frame.data, get_data(), length_); - + if(is_correct_to_send()) + { + frame.can_id = get_id(); + frame.len = get_length(); + ::memcpy(frame.data, get_data(), length_); + } + else + ERROR(interface_, "can_message_t not correctly initialized to be sent"); + return frame; } + /******************************************************************************** * * can_bus_dev_t method implementation diff --git a/src/can-utils.hpp b/src/can-utils.hpp index d945be4c..1fac69e9 100644 --- a/src/can-utils.hpp +++ b/src/can-utils.hpp @@ -84,28 +84,31 @@ typedef uint64_t (*SignalEncoder)(struct CanSignal* signal, openxc_DynamicField* value, bool* send); /** + * @enum CanMessageFormat * @brief The ID format for a CAN message. - * - * STANDARD - standard 11-bit CAN arbitration ID. - * EXTENDED - an extended frame, with a 29-bit arbitration ID. */ enum CanMessageFormat { - STANDARD, - EXTENDED, + STANDARD, /*!< STANDARD - standard 11-bit CAN arbitration ID. */ + EXTENDED, /*!< EXTENDED - an extended frame, with a 29-bit arbitration ID. */ + ERROR, /*!< ERROR - ERROR code used at initialization to signify that it isn't usable'*/ }; typedef enum CanMessageFormat CanMessageFormat; /** + * @class can_message_t + * * @brief A compact representation of a single CAN message, meant to be used in in/out * buffers. * - * param[in] uint32_t id - The ID of the message. - * param[in] CanMessageFormat format - the format of the message's ID. - * param[in] uint8_t data - The message's data field. - * @param[in] uint8_t length - the length of the data array (max 8). -************************* -* old CanMessage struct * -************************* + * param[in] + * param[in] + * param[in] + * @param[in] + */ + +/************************* + * old CanMessage struct * + ************************* struct CanMessage { uint32_t id; CanMessageFormat format; @@ -116,26 +119,115 @@ typedef struct CanMessage CanMessage; */ class can_message_t { private: - const struct afb_binding_interface* interface_; - uint32_t id_; - CanMessageFormat format_; - uint8_t data_; - uint8_t length_; + const struct afb_binding_interface* interface_; /*!< afb_binding_interface interface between daemon and binding */ + + uint32_t id_; /*!< uint32_t id - The ID of the message. */ + uint8_t length_; /*!< uint8_t length - the length of the data array (max 8). */ + CanMessageFormat format_; /*!< CanMessageFormat format - the format of the message's ID.*/ + uint8_t data_[CAN_MESSAGE_SIZE]; /*!< uint8_t data - The message's data field with a size of 8 which is the standard about CAN bus messages.*/ public: + /** + * @brief Class constructor + * + * Constructor about can_message_t class. + * + * @param interface - const structafb_binding_interface pointer + */ can_message_t(const struct afb_binding_interface* interface); + /** + * @brief Retrieve id_ member value. + * + * @return uint32_t id_ class member + */ uint32_t get_id() const; + + /** + * @brief Retrieve format_ member value. + * + * @return CanMessageFormat format_ class member + */ int get_format() const; + + /** + * @brief Retrieve data_ member value. + * + * @return uint8_t data_ pointer class member + */ const uint8_t* get_data() const; + + /** + * @brief Retrieve length_ member value. + * + * @return uint8_t length_ class member + */ uint8_t get_length() const; + /** + * @brief Control whether the object is correctly initialized + * to be sent over the CAN bus + * + * @return true if object correctly initialized and false if not... + */ + bool is_correct_to_send(); + + /** + * @brief Set id_ member value. + * + * Preferred way to initialize these members by using + * convert_from_canfd_frame method. + * + * @param uint32_t id_ class member + */ void set_id(const uint32_t new_id); + + /** + * @brief Set format_ member value. + * + * Preferred way to initialize these members by using + * convert_from_canfd_frame method. + * + * @param CanMessageFormat format_ class member + */ void set_format(const CanMessageFormat format); + + /** + * @brief Set data_ member value. + * + * Preferred way to initialize these members by using + * convert_from_canfd_frame method. + * + * @param uint8_t data_ array with a max size of 8 elements. + */ void set_data(const uint8_t new_data); + + /** + * @brief Set length_ member value. + * + * Preferred way to initialize these members by using + * convert_from_canfd_frame method. + * + * @param uint8_t length_ array with a max size of 8 elements. + */ void set_length(const uint8_t new_length); + /** + * @brief Take a canfd_frame struct to initialize class members + * + * This is the preferred way to initialize class members. + * + * @param canfd_frame struct read from can bus device. + */ void convert_from_canfd_frame(const canfd_frame& frame); + + /** + * @brief Take all initialized class's members and build an + * canfd_frame struct that can be use to send a CAN message over + * the bus. + * + * @return canfd_frame struct built from class members. + */ canfd_frame convert_to_canfd_frame(); }; |