Index: denali.pro =================================================================== diff -u -r61bc469fa3c4bd400c6cbf71f2a78d65f075063f -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- denali.pro (.../denali.pro) (revision 61bc469fa3c4bd400c6cbf71f2a78d65f075063f) +++ denali.pro (.../denali.pro) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -14,6 +14,12 @@ DEFINES += DISABLE_KEEP_ALIVE } +#CONFIG += disable_sequence +disable_sequence { + message( *** IMPORTANT : DISABLED SEQUENCE *** ) + DEFINES += DISABLE_SEQUENCE +} + # The following define makes your compiler emit warnings if you use # any Qt feature that has been marked deprecated (the exact warnings # depend on your compiler). Refer to the documentation for the Index: denali.pro.user =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- denali.pro.user (.../denali.pro.user) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ denali.pro.user (.../denali.pro.user) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -1,14 +1,14 @@ - + EnvironmentId {67370740-e20f-4fc6-be45-6652e866a8bf} ProjectExplorer.Project.ActiveTarget - 0 + 1 ProjectExplorer.Project.EditorSettings @@ -68,7 +68,7 @@ Desktop Qt 5.12.5 GCC 64bit Desktop Qt 5.12.5 GCC 64bit qt.qt5.5125.gcc_64_kit - 1 + 0 0 0 @@ -600,7 +600,7 @@ true false - /home/denali/Project/tmp/build/denali-Desktop_Qt_5_12_5_GCC_64bit-Release + /home/denali/Project/tmp/build/denali-Desktop_Qt_5_12_5_GCC_64bit-Debug 1 Index: main.cpp =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- main.cpp (.../main.cpp) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ main.cpp (.../main.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -38,6 +38,8 @@ #include "usbwatcher.h" #include "threads.h" +#include + #ifdef UNIT_TEST #include TEST_CLASS_INCLUDE QTEST_MAIN(TEST_CLASS_NAME) @@ -51,8 +53,6 @@ { //! - Qt Application initialization and parameters settings // Qt Core Application parameters settings - - QApplication::setApplicationName(QLatin1String("Denali")); QApplication::setOrganizationName(QLatin1String("Diality Inc.")); Index: scripts/run.sh =================================================================== diff -u -rd68767b00e162186262be1eac0b9071bc2257d0d -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- scripts/run.sh (.../run.sh) (revision d68767b00e162186262be1eac0b9071bc2257d0d) +++ scripts/run.sh (.../run.sh) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -30,6 +30,8 @@ #setting up can interface ip link set can0 up type can bitrate 250000 +ifconfig can0 txqueuelen 4000 +sysctl net/core/netdev_max_backlog=4000 if [ $? -eq 0 ]; then echo ":: Can interface setup" fi Index: sources/canbus/caninterface.cpp =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/caninterface.cpp (.../caninterface.cpp) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/caninterface.cpp (.../caninterface.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -29,7 +29,10 @@ * \brief Caninterface Constructor * \param parent object */ -CanInterface::CanInterface(QObject *parent) : QObject(parent) { } +CanInterface::CanInterface(QObject *parent) : QObject(parent) { + FrameCount _rxFrameCountMax = pow(2, 8 * sizeof(FrameCount)) - 1;; + FrameCount _txFrameCountMax = pow(2, 8 * sizeof(FrameCount)) - 1;; +} /*! * \brief CanInterface Initialization @@ -231,7 +234,7 @@ * for debugging purposes. * \param vFrame - The CANBUS frame to be sent out */ -void CanInterface::consoleOut(const QCanBusFrame &vFrame) +void CanInterface::consoleOut(const QCanBusFrame &vFrame, QString vFrameCount) { if ( ! _enableConsoleOut ) return; @@ -248,10 +251,40 @@ else { view = vFrame.payload().toHex('.').replace(QByteArray("a5"),QByteArray("\033[1;33mA5\033[0m")); } - fprintf(stderr, "%s %s %i %s\n", time.toLatin1().constData(), flags.toLatin1().constData(), vFrame.frameId(), view.toLatin1().constData()); + fprintf(stderr, "%s %s %s %i %s\n", vFrameCount.toLatin1(), time.toLatin1().constData(), flags.toLatin1().constData(), vFrame.frameId(), view.toLatin1().constData()); } /*! + * \brief CanInterface::rxCount + * \details count received frames up the size of the FrameCount type size + * \return frame count + */ +CanInterface::FrameCount CanInterface::rxCount() +{ + if ( _rxFrameCount <= _rxFrameCountMax) { + ++_rxFrameCount; + } else { + _rxFrameCount = 1; + } + return _rxFrameCount; +} + +/*! + * \brief CanInterface::txCount + * \details count transmitted frames up the size of the FrameCount type size + * \return frame count + */ +CanInterface::FrameCount CanInterface::txCount() +{ + if ( _txFrameCount <= _rxFrameCountMax) { + ++_txFrameCount; + } else { + _txFrameCount = 1; + } + return _txFrameCount; +} + +/*! * \brief frameFlags * \details CANBUS message frame type as flags * \param vFrame - CANBUS message frame @@ -315,10 +348,10 @@ if (!_canDevice) return; while (_canDevice->framesAvailable()) { - //int i = _canDevice->framesAvailable(); const QCanBusFrame frame = _canDevice->readFrame(); - //qDebug() << "frame: #" << i << frame.toString(); - consoleOut(frame); + rxCount(); + if ( _enableConsoleOut ) + consoleOut(frame, QString("Rx:%1").arg(_rxFrameCount)); emit didFrameReceive(frame); } } @@ -332,6 +365,8 @@ void CanInterface::onFrameTransmit(const QCanBusFrame &vFrame) { bool ok = transmit(vFrame); - consoleOut(vFrame); + rxCount(); + if ( _enableConsoleOut ) + consoleOut(vFrame, QString("Tx:%1").arg(_txFrameCount)); emit didFrameTransmit(ok); } Index: sources/canbus/caninterface.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/caninterface.h (.../caninterface.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/caninterface.h (.../caninterface.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -59,6 +59,12 @@ QThread *_thread = nullptr; bool _init = false; + typedef quint16 FrameCount; + FrameCount _rxFrameCount = 0; + FrameCount _rxFrameCountMax = 0; + FrameCount _txFrameCount = 0; + FrameCount _txFrameCountMax = 0; + // Singleton SINGLETON(CanInterface) @@ -85,8 +91,11 @@ void status (const QString &vDescription, QString vError = ""); bool transmit (const QCanBusFrame &vFrame); - void consoleOut (const QCanBusFrame &vFrame); + void consoleOut (const QCanBusFrame &vFrame, QString vFrameCount); + FrameCount rxCount(); + FrameCount txCount(); + static QString frameFlags(const QCanBusFrame &vFrame); signals: Index: sources/canbus/messagebuilder.cpp =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messagebuilder.cpp (.../messagebuilder.cpp) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messagebuilder.cpp (.../messagebuilder.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -19,6 +19,7 @@ #include "logger.h" #include "crc.h" #include "format.h" +#include "types.h" // namespace using namespace Can; @@ -191,6 +192,27 @@ } /*! + * \brief MessageBuilder::checkCRC + * \details Overloaded CheckCRC which checks the CRC and Log the error if there is. + * \param vMessage + * \return + */ +bool MessageBuilder::checkCRC(const Message &vMessage) +{ + consoleOut("", false, Can_Id::eChlid_NONE); + QByteArray crcData = vMessage.head + vMessage.data; + quint8 mExpected = 0; + quint8 mBeenRead = 0; + if ( ! checkCRC(crcData, mExpected, mBeenRead ) ) { // CRC is always next byte after Data + LOG_ERROR(tr("CRC error, expected %1 but got %2") + .arg(Format::toHexString(mExpected, true, eLenCRCDigits)) + .arg(Format::toHexString(mBeenRead, true, eLenCRCDigits))); + return false; + } + return true; +} + +/*! * \brief MessageBuilder::buildMessage * \details Builds Message out of vPayload of type QByteArray * by adding Sync byte, ActionID(MessageID), data length, data, CANBUS channel id for header @@ -208,6 +230,9 @@ consoleOut(vPayload, true, vCan_Id); vMessage.can_id = vCan_Id; vMessage.head = getHeader (mPayload); // keep header before taking it out of the payload. doesn't affect payload +#ifndef DISABLE_SEQUENCE + vMessage.sequence = getSequence (mPayload); +#endif vMessage.actionId = getActionId (mPayload); vMessage.length = getLength (mPayload); vMessage.data = getData (mPayload, vMessage.length); @@ -226,16 +251,8 @@ // and when Message model identifies the message is complete // will SIGNAL builder to check for crc. if (vMessage.isComplete()) { - consoleOut("", false, Can_Id::eChlid_NONE); - QByteArray crcData = vMessage.head + vMessage.data; - quint8 mExpected = 0; - quint8 mBeenRead = 0; - if ( ! checkCRC(crcData, mExpected, mBeenRead ) ) { // CRC is always next byte after Data - LOG_ERROR(tr("CRC error, expected %1 but got %2") - .arg(Format::toHexString(mExpected, true, eLenCRCDigits)) - .arg(Format::toHexString(mBeenRead, true, eLenCRCDigits))); - return false; - } + bool ok = checkCRC(vMessage); + if (!ok) return false; } return true; @@ -261,6 +278,24 @@ } /*! + * \brief MessageBuilder::getSequence + * \details Extract the 2 bytes of the sequence + * out of the vPayload of type QByteArray + * \param vPayload - The payload of the CANBUS message + * \return Returns ActionId of type GuiActionType + * \note Removes the 2 bytes of ActionID from vPayload + * It starts from the first byte so those 2 bytes should be the first 2 bytes. + */ +qint16 MessageBuilder::getSequence(QByteArray &vPayload) +{ + Types::S16 mSequence; + int index = 0; + Types::getValue<>(vPayload, index, mSequence); + vPayload = vPayload.mid(eLenSequence); + return mSequence.value; +} + +/*! * \brief MessageBuilder::getHeader * \details Collect the 3 bytes (Frame_Data::eLenHeaderInfo) * as header portion of the payload @@ -277,6 +312,10 @@ QByteArray MessageBuilder::getHeader(const QByteArray &vPayload) { QByteArray headInfo; + if (vPayload.length() < eLenHeaderInfo) { + LOG_ERROR("Incorrect Message Header"); + return headInfo; + } for (int i = 0; i < eLenHeaderInfo; i++) { headInfo += vPayload[i]; } @@ -296,10 +335,6 @@ { quint16 mActionId; mActionId = (vPayload[0] << 8) | vPayload[1]; - - //TODO : It needs to be checked that the ActionID is Correct. - //return GuiActionType::Unknown; - vPayload = vPayload.mid(eLenActionId); return static_cast(mActionId); } Index: sources/canbus/messagebuilder.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messagebuilder.h (.../messagebuilder.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messagebuilder.h (.../messagebuilder.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -29,10 +29,10 @@ * \details This class is handling the can message by building and striping it. * \n * // -- CAN PAYLOAD STRUCTURE -- \n - * #0 #1 #2 #3 #4 #5 #6 #7 \n - * +---+---+---+---+---+---+---+---+--.......--+ \n - * | A5| MsgId |Len| Data |CRC|..padding..| \n - * +---+---+---+---+---+---+---+---+--.......--+ \n + * #0 #1 #2 #3 #4 #5 #6 #7 #8 #9 \n + * +---+---+---+---+---+---+---+---+---+---+--.......--+ \n + * | A5| Seq# | MsgId |Len| Data |CRC|..padding..| \n + * +---+---+---+---+---+---+---+---+---+---+--.......--+ \n * \n * Header Frame: \n * 1 - CRC is last after payload \n @@ -59,8 +59,10 @@ quint8 calcCRC (const QByteArray &vData ); bool checkCRC (const QByteArray &vData , quint8 &vExpected, quint8 &vBeenRead); + bool checkCRC (const Message &vMessage); bool hasSyncByte ( QByteArray &vPayload); + qint16 getSequence(QByteArray &vPayload); QByteArray getHeader (const QByteArray &vPayload); Gui::GuiActionType getActionId ( QByteArray &vPayload); int getLength ( QByteArray &vPayload); Index: sources/canbus/messagedispatcher.cpp =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messagedispatcher.cpp (.../messagedispatcher.cpp) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messagedispatcher.cpp (.../messagedispatcher.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -133,28 +133,16 @@ // Append a message to the list if (_messageList[vCanId].isEmpty() || _messageList[vCanId].last().isComplete()) { _messageList[vCanId].append(Message()); - //qDebug() << tr("Created a message for channel %1#%2").arg(vCanId).arg(Format::toHexString(vPayload)); - } /*else { - qDebug() << tr("Data for message on channel %1#%2").arg(vCanId).arg(Format::toHexString(vPayload)); - }*/ - //for (int i = 0; i < _messageList[vCanId].count(); ++i) { - // qDebug() << _messageList[vCanId][i].data.toHex('.'); - //} - // build the message - if (! _builder.buildMessage(vPayload, _messageList[vCanId].last(), vCanId)) { - _messageList[vCanId].removeLast(); - return; } + + // build the message and check. + if (! buildMessage(vCanId, vPayload)) + return; Message mMessage = _messageList[vCanId].last(); // TODO : must be moved to a MessageModel class if (mMessage.isComplete()) { - GuiActionType mActionId; - QVariantList mData; - if (_interpreter.interpretMessage(vCanId, mMessage, mActionId, mData)) { - emit didActionReceive(mActionId, mData); - } - _messageList[vCanId].removeLast(); + interpretMessage(mMessage); } } @@ -196,3 +184,55 @@ } } +/*! + * \brief MessageDispatcher::buildMessage + * \details Calls the messageBuilder buildMessage method. + * \param vCanId - CANBUS channel of the frame + * \param vPayload - Payload of the frame + * \return false on error + */ +bool MessageDispatcher::buildMessage(Can_Id vCanId, const QByteArray &vPayload) +{ + if (vPayload.length() < eLenCanFrame) { + LOG_ERROR(tr("Incorrect frame length. Exp:%1,got:%2").arg(eLenCanFrame).arg(vPayload.length())); + return false; + } + if (! _builder.buildMessage(vPayload, _messageList[vCanId].last(), vCanId)) { + _messageList[vCanId].removeLast(); + return false; + } + return true; +} + +/*! + * \brief MessageDispatcher::interpretMessage + * \details Calls the MessageInterpreter interpretMessage method + * Regarding the Message Id and the sequence emit different signals + * to handle the normal or acknowledge messages. + * \param vMessage - The Message + * \return false on error + */ +bool MessageDispatcher::interpretMessage(const Message &vMessage) +{ + bool ok = false; + QVariantList mData; + if (_interpreter.interpretMessage(vMessage, mData)) { + ok = true; + GuiActionType mActionId = vMessage.actionId; + switch (mActionId) { + case GuiActionType::Acknow: + emit didAcknowReceive(mData); + break; + default: + if (vMessage.sequence < 0) { + // actionTransmit(-vMessage.sequence, GuiActionType::Acknow,{}); + } + emit didActionReceive(mActionId, mData); + break; + } + } + _messageList[vMessage.can_id].removeLast(); + return ok; + +} + Index: sources/canbus/messagedispatcher.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messagedispatcher.h (.../messagedispatcher.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messagedispatcher.h (.../messagedispatcher.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -115,6 +115,8 @@ void actionTransmit(GuiActionType vActionId, const QVariantList &vData); + bool buildMessage (Can_Id vCanId, const QByteArray &vPayload); + bool interpretMessage(const Message &vMessage); signals: /*! * \brief didActionReceive @@ -125,7 +127,23 @@ * \param vData - The data has been collected from CANBUS frame(s) */ void didActionReceive(GuiActionType vAction , const QVariantList &vData); + /*! + * \brief didActionReceive + * \details Emits when a message requires + * \param vData + */ + void didActionReceive(const Message &vMessage); + + /** + * @brief didAcknowReceive + * @details if the type the received message id is and Acknow this signal will be emitted + * @param vData - the data of the Acknow message which is the message Sequence + * which we got the Ack for. + */ + void didAcknowReceive(const QVariantList &vData); + + /*! * \brief didFrameTransmit * \details When a message is requested to be transmitted this signal is emitted * on successful interpretation and building the message into frames Index: sources/canbus/messageglobals.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messageglobals.h (.../messageglobals.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messageglobals.h (.../messageglobals.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -29,9 +29,10 @@ const QHash payloadLen { {Gui::GuiActionType::PowerOff , 1 }, {Gui::GuiActionType::KeepAlive , 0 }, - {Gui::GuiActionType::BloodFlow , 7 * 4 } , // 7 parameters each 4bytes - {Gui::GuiActionType::DialysateFlow , 7 * 4 } , // 7 parameters each 4bytes + {Gui::GuiActionType::BloodFlow , 7 * 4 }, // 7 parameters each 4bytes + {Gui::GuiActionType::DialysateFlow , 7 * 4 }, // 7 parameters each 4bytes {Gui::GuiActionType::String , 255 }, + {Gui::GuiActionType::Acknow , 0 }, }; /*! @@ -49,12 +50,17 @@ */ enum Frame_Data : quint8 { eLenCanFrame = 8, ///< The length of each can frame. Should be padded by 0x00 if is less. +#ifdef DISABLE_SEQUENCE eLenHeaderInfo = 3, ///< The Header length witch is included in CRC after Sync byte +#else + eLenHeaderInfo = 5, ///< The Header length witch is included in CRC after Sync byte (it's the sum of eLenSequence + eLenActionId + eLenLength) +#endif eLenMaxHeaderData = 3, ///< Maximum data byte can be in one frame as header data portion eLenMaxData = 255, ///< Maximum data length in a Can Message since data length value kept in one byte eLenSyncByte = 1, ///< The length of Sync byte at the beginning of each header frame - eLenActionId = 2, ///< The length of MessageID bytes (2) at the beginning of each header frame after sync + eLenSequence = 2, ///< The length of Sequence number bytes (2) at the beginning of each header frame after sync + eLenActionId = 2, ///< The length of MessageID bytes eLenLength = 1, ///< The length of data length value byte at the beginning of each header frame after MessageID eLenCRCDigits = 2, @@ -98,6 +104,7 @@ */ struct Message { // TODO : Should be converted to MessageModel class // no time left for now !!! Can_Id can_id; + qint16 sequence = 0; // seq 0 is invalid Gui::GuiActionType actionId = Gui::GuiActionType::Unknown; int length = 0; QByteArray head; Index: sources/canbus/messageinterpreter.cpp =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messageinterpreter.cpp (.../messageinterpreter.cpp) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messageinterpreter.cpp (.../messageinterpreter.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -90,14 +90,14 @@ * \return true if the message channel is in the range which can be interpreted, false otherwise. * This return value will be used later to emit MessageDispatcher::didActionReceive signal or not */ -bool MessageInterpreter::interpretMessage(const Can_Id vCan_Id, const Message &vMessage, Gui::GuiActionType &vActionId, QVariantList &vData) +bool MessageInterpreter::interpretMessage(const Message &vMessage, QVariantList &vData) { bool ok = false; - switch (vCan_Id) { + switch (vMessage.can_id) { case eChlid_HD: case eChlid_HD_Alarm: case eChlid_HD_Sync: - ok = interpretMessage_HD(vMessage, vActionId, vData); + ok = interpretMessage_HD(vMessage, vData); break; default: break; @@ -133,13 +133,12 @@ * \return true if the message CANBUS channel is in the range which can be interpreted, false otherwise. * This return value will be used later to emit MessageDispatcher::didActionReceive signal or not */ -bool MessageInterpreter::interpretMessage_HD(const Message &vMessage, Gui::GuiActionType &vActionId, QVariantList &vData) +bool MessageInterpreter::interpretMessage_HD(const Message &vMessage, QVariantList &vData) { bool ok = true; - vActionId = vMessage.actionId; vData.clear(); - switch (vActionId) { // notice we are in receive mode + switch (vMessage.actionId) { // notice we are in receive mode case Gui::GuiActionType::PowerOff: { quint8 mShowHide; ok = getPowerOffData(vMessage, mShowHide); @@ -190,7 +189,7 @@ * \return true if the message CANBUS channel is in the range which can be interpreted, false otherwise. * This return value will be used later to emit MessageDispatcher::didActionReceive signal or not */ -bool MessageInterpreter::interpretMessage_DG(const Message &vMessage, Gui::GuiActionType &vActionId, QVariantList &vData) +bool MessageInterpreter::interpretMessage_DG(const Message &vMessage, Gui::GuiActionType vActionId, QVariantList &vData) { Q_UNUSED(vMessage ); Q_UNUSED(vActionId); Index: sources/canbus/messageinterpreter.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/canbus/messageinterpreter.h (.../messageinterpreter.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/canbus/messageinterpreter.h (.../messageinterpreter.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -35,8 +35,8 @@ void printUnhandled (const Message &vMessage); - bool interpretMessage_HD (const Message &vMessage , Gui::GuiActionType &vActionId, QVariantList &vData) __attribute_warn_unused_result__; - bool interpretMessage_DG (const Message &vMessage , Gui::GuiActionType &vActionId, QVariantList &vData) __attribute_warn_unused_result__; + bool interpretMessage_HD (const Message &vMessage , QVariantList &vData) __attribute_warn_unused_result__; + bool interpretMessage_DG (const Message &vMessage , Gui::GuiActionType vActionId, QVariantList &vData) __attribute_warn_unused_result__; bool getPowerOffData (const Message &vMessage , quint8 &vShowHide) __attribute_warn_unused_result__; @@ -67,8 +67,8 @@ explicit MessageInterpreter(QObject *parent = nullptr); // interpret the data into GUI understandable Actions/Data - bool interpretMessage(const Can_Id vCan_Id, const Message &vMessage, Gui::GuiActionType &vActionId, QVariantList &vData) __attribute_warn_unused_result__; - bool interpretMessage(const Gui::GuiActionType &vActionId, const QVariantList &vData, QByteArray &vPayload) __attribute_warn_unused_result__; + bool interpretMessage(const Message &vMessage, QVariantList &vData) __attribute_warn_unused_result__; + bool interpretMessage(const Gui::GuiActionType &vActionId, const QVariantList &vData, QByteArray &vPayload) __attribute_warn_unused_result__; signals: Index: sources/gui/guiglobals.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/gui/guiglobals.h (.../guiglobals.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/gui/guiglobals.h (.../guiglobals.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -39,7 +39,9 @@ AlarmTriggered = 0x0300, AlarmCleared = 0x0400, - String = 0xFFFF, + String = 0xFFFE, + + Acknow = 0xFFFF, }; enum class GuiActionsIndx_Enum { Index: sources/storage/logger.cpp =================================================================== diff -u -re663ffa6157024ed326f2db445982ff150f9aa72 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/storage/logger.cpp (.../logger.cpp) (revision e663ffa6157024ed326f2db445982ff150f9aa72) +++ sources/storage/logger.cpp (.../logger.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -245,6 +245,7 @@ QString mDestination = Storage::USB_Mount_Point; QFuture future = QtConcurrent::run(&FileHandler::copyFolder, mSource, mDestination); _exportWatcher.setFuture(future); + future.waitForFinished(); return true; } Index: sources/storage/usbwatcher.cpp =================================================================== diff -u -r862dc0590b73c618fac73dce2c976e3526e0404a -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/storage/usbwatcher.cpp (.../usbwatcher.cpp) (revision 862dc0590b73c618fac73dce2c976e3526e0404a) +++ sources/storage/usbwatcher.cpp (.../usbwatcher.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -99,6 +99,7 @@ _thread->setObjectName(QString("%1_Thread").arg(metaObject()->className())); connect(qApp, SIGNAL(aboutToQuit()), this, SLOT(quit())); _thread->start(); + _thread->setPriority(QThread::LowestPriority); moveToThread(_thread); } @@ -240,7 +241,7 @@ bool USBWatcher::usbUmount(const QString &vDevice) { bool ok; - ok = umount(vDevice.toLatin1().constData()) == 0; + ok = ::umount(vDevice.toLatin1().constData()) == 0; if (ok) { _mounted = false; LOG_EVENT(tr("USB drive unmounted")); Index: sources/utility/types.h =================================================================== diff -u -r227f28b202f81ab3dd04a81868697025ccab6220 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- sources/utility/types.h (.../types.h) (revision 227f28b202f81ab3dd04a81868697025ccab6220) +++ sources/utility/types.h (.../types.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -81,6 +81,16 @@ * \details This is the union which will be used to extract the bytes of an signed int type value * 4 bytes */ +union S16 { + qint16 value = 0; + quint8 bytes[sizeof(qint16)]; +}; + +/*! + * \brief The S32 union + * \details This is the union which will be used to extract the bytes of an signed int type value + * 4 bytes + */ union S32 { qint32 value = 0; quint8 bytes[sizeof(qint32)]; Index: unittests/tst_canbus.cpp =================================================================== diff -u -re02b2d465b145702dc41965b2e7da154857eea75 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- unittests/tst_canbus.cpp (.../tst_canbus.cpp) (revision e02b2d465b145702dc41965b2e7da154857eea75) +++ unittests/tst_canbus.cpp (.../tst_canbus.cpp) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -67,6 +67,7 @@ _emited = true; QCOMPARE(Format::toHexString(vPayload), _expected); }); + connect(&_MessageDispatcher, &MessageDispatcher::didActionReceive, [=](Gui::GuiActionType vAction , const QVariantList &vData ) { _emited = true; QVERIFY(vAction == _action); @@ -126,11 +127,12 @@ QVERIFY(_emited); } -void tst_canbus::tst_FrameInterface_ActionTransmit_LongFF() +void tst_canbus::tst_FrameInterface_ActionTransmit_Raw() { // An example of longest data transmission by Gui::GuiActionType::String // which can be as long as 255 byte. - _expected = "A5.FF.FF.03.41.42.43.EF"; + _expected = "A5.FF.FE.03.41.42.43.3C"; + // A. B. C QVariantList mData {"ABC"}; _MessageDispatcher.onActionTransmit(Gui::GuiActionType::String, mData); QVERIFY(_emited); @@ -218,7 +220,7 @@ mPayload = "A5.01.00.01.00.6F"; mFrame.setPayload(QByteArray::fromHex(mPayload.remove(QLatin1Char('.')).toLatin1())); emit _CanInterface.didFrameReceive(mFrame); - QVERIFY(_emited); // Should not emit due to crc error + QVERIFY( ! _emited); // Should not emit due to frame length less than 8 } void tst_canbus::tst_FrameInterface_FrameReceived_LongFrame_Error() Index: unittests/tst_canbus.h =================================================================== diff -u -re02b2d465b145702dc41965b2e7da154857eea75 -re58b907a69d4ca7daa77d69791593b886d1b80e8 --- unittests/tst_canbus.h (.../tst_canbus.h) (revision e02b2d465b145702dc41965b2e7da154857eea75) +++ unittests/tst_canbus.h (.../tst_canbus.h) (revision e58b907a69d4ca7daa77d69791593b886d1b80e8) @@ -46,7 +46,7 @@ void tst_FrameInterface_ActionTransmit_PowerOff_Accepted(); void tst_FrameInterface_ActionTransmit_PowerOff_Rejected(); void tst_FrameInterface_ActionTransmit_PowerOff(); - void tst_FrameInterface_ActionTransmit_LongFF(); + void tst_FrameInterface_ActionTransmit_Raw(); void tst_FrameInterface_ActionTransmit_Unknown (); void tst_FrameInterface_FrameReceived_PowerOff(); void tst_FrameInterface_FrameReceived_PowerOff_Timeout();