├── CTO.h ├── CmdPacket.h ├── CmdPacketConnect.cpp ├── CmdPacketConnect.h ├── CmdPacketDisconnect.cpp ├── CmdPacketDisconnect.h ├── CmdPacketDownload.cpp ├── CmdPacketDownload.h ├── CmdPacketGetSeed.cpp ├── CmdPacketGetSeed.h ├── CmdPacketGetStatus.cpp ├── CmdPacketGetStatus.h ├── CmdPacketSetMta.cpp ├── CmdPacketSetMta.h ├── CmdPacketShortUpload.cpp ├── CmdPacketShortUpload.h ├── CmdPacketSync.cpp ├── CmdPacketSync.h ├── CmdPacketUnlock.cpp ├── CmdPacketUnlock.h ├── CmdPacketUpload.cpp ├── CmdPacketUpload.h ├── DAQ.cpp ├── DAQ.h ├── DAQPackets.cpp ├── DAQPackets.h ├── DTO.cpp ├── DTO.h ├── ErrorPacket.h ├── ErrorPacketAccessLocked.cpp ├── ErrorPacketAccessLocked.h ├── ErrorPacketCmdUnknown.cpp ├── ErrorPacketCmdUnknown.h ├── ErrorPacketMemoryOverflow.cpp ├── ErrorPacketMemoryOverflow.h ├── ErrorPacketOutOfRange.cpp ├── ErrorPacketOutOfRange.h ├── ErrorPacketSequence.cpp ├── ErrorPacketSequence.h ├── ErrorPacketSync.cpp ├── ErrorPacketSync.h ├── EventPacket.h ├── IncomingPacketHandler.cpp ├── IncomingPacketHandler.h ├── LICENSE ├── MessageFactory.h ├── PacketFactory.cpp ├── PacketFactory.h ├── README.md ├── ResPacket.h ├── ResPacketConnect.cpp ├── ResPacketConnect.h ├── ResPacketGetSeed.cpp ├── ResPacketGetSeed.h ├── ResPacketGetStatus.cpp ├── ResPacketGetStatus.h ├── ResPacketUnlock.cpp ├── ResPacketUnlock.h ├── ResPacketUpload.cpp ├── ResPacketUpload.h ├── XcpHeader.h ├── XcpMaster.cpp ├── XcpMaster.h ├── XcpMessage.cpp ├── XcpMessage.h ├── XcpPacket.h ├── XcpTail.h └── transport ├── can ├── CanHeader.cpp ├── CanHeader.h ├── CanMessage.cpp ├── CanMessage.h ├── CanMessageFactory.cpp ├── CanMessageFactory.h ├── CanTail.cpp └── CanTail.h └── ethernet ├── EthernetHeader.cpp ├── EthernetHeader.h ├── EthernetMessage.cpp ├── EthernetMessage.h ├── EthernetMessageFactory.cpp ├── EthernetMessageFactory.h ├── EthernetTail.cpp └── EthernetTail.h /CTO.h: -------------------------------------------------------------------------------- 1 | #ifndef CTO_H 2 | #define CTO_H 3 | 4 | #include "XcpPacket.h" 5 | 6 | class CTO : public XcpPacket 7 | { 8 | public: 9 | enum SlaveToMasterPacketTypes 10 | { 11 | RES = 0xFF, 12 | ERR = 0xFE, 13 | EV = 0xFD, 14 | SERV = 0xFC, 15 | }; 16 | 17 | enum MasterToSlaveCommands 18 | { 19 | //Standard Commands: 20 | CONNECT = 0xFF, 21 | DISCONNECT = 0xFE, 22 | GET_STATUS = 0xFD, 23 | SYNCH = 0xFC, 24 | GET_COMM_MODE_INFO = 0xFB, 25 | GET_ID = 0xFA, 26 | SET_REQUEST = 0xF9, 27 | GET_SEED = 0xF8, 28 | UNLOCK = 0xF7, 29 | SET_MTA = 0xF6, 30 | UPLOAD = 0xF5, 31 | SHORT_UPLOAD = 0xF4, 32 | BUILD_CHECKSUM = 0xF3, 33 | TRANSPORT_LAYER_CMD = 0xF2, 34 | USER_CMD = 0xF1, 35 | 36 | //Calibration commands: 37 | DOWNLOAD = 0xF0, 38 | 39 | //Page switching commands: 40 | 41 | //Basic data acquisition and stimulation commands: 42 | SET_DAQ_PTR = 0xE2, 43 | WRITE_DAQ = 0xE1, 44 | SET_DAQ_LIST_MODE = 0xE0, 45 | START_STOP_DAQ_LIST = 0xDE, 46 | START_STOP_SYNCH = 0xDD, 47 | WRITE_DAQ_MULTIPLE = 0xC7, 48 | READ_DAQ = 0xDB, 49 | GET_DAQ_CLOCK = 0xDC, 50 | GET_DAQ_PROCESSOR_INFO = 0xDA, 51 | GET_DAQ_RESOLUTION_INFO = 0xD9, 52 | GET_DAQ_LIST_MODE = 0xDF, 53 | GET_DAQ_EVENT_INFO = 0xD7, 54 | DTO_CTR_PROPERTIES = 0xC5, 55 | 56 | //Static data acquisition and stim commands: 57 | CLEAR_DAQ_LIST = 0xE3, 58 | GET_DAQ_LIST_INFO = 0xD8, 59 | 60 | //Dynamic data acquisition and stim commands: 61 | FREE_DAQ = 0xD6, 62 | ALLOC_DAQ = 0xD5, 63 | ALLOC_ODT = 0xD4, 64 | ALLOC_ODT_ENTRY = 0xD3, 65 | 66 | //Non-volatile memory programming commands: 67 | 68 | //Time sync commands: 69 | }; 70 | 71 | public: 72 | CTO() : XcpPacket() {} 73 | virtual ~CTO() {} 74 | }; 75 | 76 | #endif // CTO_H 77 | -------------------------------------------------------------------------------- /CmdPacket.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKET_H 2 | #define CMDPACKET_H 3 | 4 | #include "CTO.h" 5 | 6 | class CmdPacket : public CTO 7 | { 8 | public: 9 | CmdPacket() : CTO() {} 10 | virtual ~CmdPacket() {} 11 | }; 12 | 13 | #endif // CMDPACKET_H 14 | -------------------------------------------------------------------------------- /CmdPacketConnect.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketConnect.h" 2 | 3 | CmdPacketConnect::CmdPacketConnect(CmdPacketConnect::ConnectMode a_eMode) 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::CONNECT); 7 | m_dataField.append(a_eMode); 8 | } 9 | -------------------------------------------------------------------------------- /CmdPacketConnect.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETCONNECT_H 2 | #define CMDPACKETCONNECT_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketConnect : public CmdPacket 7 | { 8 | public: 9 | enum ConnectMode 10 | { 11 | NORMAL = 0x00, 12 | USER_DEFINED = 0x01 13 | }; 14 | 15 | public: 16 | CmdPacketConnect(ConnectMode a_eMode); 17 | }; 18 | 19 | #endif // CMDPACKETCONNECT_H 20 | -------------------------------------------------------------------------------- /CmdPacketDisconnect.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketDisconnect.h" 2 | 3 | CmdPacketDisconnect::CmdPacketDisconnect() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::DISCONNECT); 7 | } 8 | -------------------------------------------------------------------------------- /CmdPacketDisconnect.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETDISCONNECT_H 2 | #define CMDPACKETDISCONNECT_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketDisconnect : public CmdPacket 7 | { 8 | public: 9 | CmdPacketDisconnect(); 10 | }; 11 | 12 | #endif // CMDPACKETDISCONNECT_H 13 | -------------------------------------------------------------------------------- /CmdPacketDownload.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketDownload.h" 2 | 3 | CmdPacketDownload::CmdPacketDownload() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::DOWNLOAD); 7 | m_dataField.resize(5); 8 | } 9 | 10 | void CmdPacketDownload::setNumberOfDataElements(uint8_t a_byNum) 11 | { 12 | m_dataField[0] = a_byNum; 13 | } 14 | 15 | uint8_t CmdPacketDownload::getNumberOfDataElements() 16 | { 17 | return m_dataField[0]; 18 | } 19 | 20 | uint32_t CmdPacketDownload::getDataElements(bool a_bIsLittleEndian) 21 | { 22 | if(a_bIsLittleEndian) { 23 | return (((uint32_t)m_dataField[4]) << 24) | (((uint32_t)m_dataField[3]) << 16) | (((uint32_t)m_dataField[2]) << 8) | m_dataField[1]; 24 | } 25 | else { 26 | //do byte-swap 27 | return (((uint32_t)m_dataField[1]) << 24) | (((uint32_t)m_dataField[2]) << 16) | (((uint32_t)m_dataField[3]) << 8) | m_dataField[4]; 28 | } 29 | } 30 | 31 | void CmdPacketDownload::setDataElements(uint32_t a_dwData, bool a_bIsLittleEndian) 32 | { 33 | uint8_t i1, i2, i3, i4; 34 | i1 = a_dwData & 0xFF; 35 | i2 = (a_dwData >> 8) & 0xFF; 36 | i3 = (a_dwData >> 16) & 0xFF; 37 | i4 = (a_dwData >> 24) & 0xFF; 38 | 39 | if(a_bIsLittleEndian) { 40 | if(m_dataField[0] == 4) { 41 | m_dataField[1] = i1; 42 | m_dataField[2] = i2; 43 | m_dataField[3] = i3; 44 | m_dataField[4] = i4; 45 | } 46 | else if(m_dataField[0] == 2) { 47 | m_dataField[1] = i1; 48 | m_dataField[2] = i2; 49 | m_dataField[3] = 0; 50 | m_dataField[4] = 0; 51 | } 52 | else if(m_dataField[0] == 1) { 53 | m_dataField[1] = i1; 54 | m_dataField[2] = 0; 55 | m_dataField[3] = 0; 56 | m_dataField[4] = 0; 57 | } 58 | } 59 | else { 60 | if(m_dataField[0] == 4) { 61 | m_dataField[1] = i4; 62 | m_dataField[2] = i3; 63 | m_dataField[3] = i2; 64 | m_dataField[4] = i1; 65 | } 66 | else if(m_dataField[0] == 2) { 67 | m_dataField[1] = i2; 68 | m_dataField[2] = i1; 69 | m_dataField[3] = 0; 70 | m_dataField[4] = 0; 71 | } 72 | else if(m_dataField[0] == 1) { 73 | m_dataField[1] = i1; 74 | m_dataField[2] = 0; 75 | m_dataField[3] = 0; 76 | m_dataField[4] = 0; 77 | } 78 | } 79 | } 80 | -------------------------------------------------------------------------------- /CmdPacketDownload.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETDOWNLOAD_H 2 | #define CMDPACKETDOWNLOAD_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketDownload : public CmdPacket 7 | { 8 | public: 9 | CmdPacketDownload(); 10 | 11 | void setNumberOfDataElements(uint8_t a_byNum); 12 | uint8_t getNumberOfDataElements(); 13 | 14 | uint32_t getDataElements(bool a_bIsLittleEndian); 15 | void setDataElements(uint32_t a_dwData, bool a_bIsLittleEndian); 16 | }; 17 | 18 | #endif // CMDPACKETDOWNLOAD_H 19 | -------------------------------------------------------------------------------- /CmdPacketGetSeed.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketGetSeed.h" 2 | 3 | CmdPacketGetSeed::CmdPacketGetSeed() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::GET_SEED); 7 | m_dataField.resize(2); // Reserve 2 element in data field 8 | } 9 | 10 | CmdPacketGetSeed::CmdPacketGetSeed(CmdPacketGetSeed::Mode a_eMode, CmdPacketGetSeed::Resource a_eResource) 11 | : CmdPacketGetSeed() 12 | { 13 | setMode(a_eMode); 14 | setResource(a_eResource); 15 | } 16 | 17 | void CmdPacketGetSeed::setMode(CmdPacketGetSeed::Mode a_eMode) 18 | { 19 | m_dataField[0] = a_eMode; 20 | } 21 | 22 | void CmdPacketGetSeed::setResource(CmdPacketGetSeed::Resource a_eResource) 23 | { 24 | m_dataField[1] = a_eResource; 25 | } 26 | 27 | uint8_t CmdPacketGetSeed::getResource() 28 | { 29 | return m_dataField[1]; 30 | } 31 | -------------------------------------------------------------------------------- /CmdPacketGetSeed.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETGETSEED_H 2 | #define CMDPACKETGETSEED_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketGetSeed : public CmdPacket 7 | { 8 | public: 9 | enum Mode 10 | { 11 | FIRST_PART = 0x00, 12 | REMAINING_PART = 0x01 13 | }; 14 | 15 | enum Resource 16 | { 17 | CAL_PG = 0x01, 18 | DAQ = 0x04, 19 | STIM = 0x08, 20 | PGM = 0x10, 21 | }; 22 | 23 | public: 24 | CmdPacketGetSeed(); 25 | CmdPacketGetSeed(Mode a_eMode, Resource a_eResource); 26 | void setMode(Mode a_eMode); 27 | void setResource(Resource a_eResource); 28 | uint8_t getResource(); 29 | }; 30 | 31 | #endif // CMDPACKETGETSEED_H 32 | -------------------------------------------------------------------------------- /CmdPacketGetStatus.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketGetStatus.h" 2 | 3 | CmdPacketGetStatus::CmdPacketGetStatus() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::GET_STATUS); 7 | } 8 | -------------------------------------------------------------------------------- /CmdPacketGetStatus.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETGETSTATUS_H 2 | #define CMDPACKETGETSTATUS_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketGetStatus : public CmdPacket 7 | { 8 | public: 9 | CmdPacketGetStatus(); 10 | }; 11 | 12 | #endif // CMDPACKETGETSTATUS_H 13 | -------------------------------------------------------------------------------- /CmdPacketSetMta.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketSetMta.h" 2 | 3 | CmdPacketSetMta::CmdPacketSetMta() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::SET_MTA); 7 | m_dataField.resize(7); // Reserve 7 element in data field 8 | m_dataField[0] = 0; // Unused 9 | m_dataField[1] = 0; // Unused 10 | } 11 | 12 | uint8_t CmdPacketSetMta::getAddressExtension() 13 | { 14 | return m_dataField[2]; 15 | } 16 | 17 | void CmdPacketSetMta::setAddressExtension(uint8_t a_byAddressExtension) 18 | { 19 | m_dataField[2] = a_byAddressExtension; 20 | } 21 | 22 | uint32_t CmdPacketSetMta::getAddress(bool a_bIsLittleEndian) 23 | { 24 | if(a_bIsLittleEndian) { 25 | return (((uint32_t)m_dataField[6]) << 24) | (((uint32_t)m_dataField[5]) << 16) | (((uint32_t)m_dataField[4]) << 8) | m_dataField[3]; 26 | } 27 | else { 28 | //do byte-swap 29 | return (((uint32_t)m_dataField[3]) << 24) | (((uint32_t)m_dataField[4]) << 16) | (((uint32_t)m_dataField[5]) << 8) | m_dataField[6]; 30 | } 31 | } 32 | 33 | void CmdPacketSetMta::setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian) 34 | { 35 | uint8_t i1, i2, i3, i4; 36 | i1 = a_dwAddress & 0xFF; 37 | i2 = (a_dwAddress >> 8) & 0xFF; 38 | i3 = (a_dwAddress >> 16) & 0xFF; 39 | i4 = (a_dwAddress >> 24) & 0xFF; 40 | 41 | if(a_bIsLittleEndian) { 42 | m_dataField[3] = i1; 43 | m_dataField[4] = i2; 44 | m_dataField[5] = i3; 45 | m_dataField[6] = i4; 46 | } 47 | else { 48 | m_dataField[3] = i4; 49 | m_dataField[4] = i3; 50 | m_dataField[5] = i2; 51 | m_dataField[6] = i1; 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /CmdPacketSetMta.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETSETMTA_H 2 | #define CMDPACKETSETMTA_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketSetMta : public CmdPacket 7 | { 8 | public: 9 | CmdPacketSetMta(); 10 | 11 | uint8_t getAddressExtension(); 12 | void setAddressExtension(uint8_t a_byAddressExtension); 13 | 14 | uint32_t getAddress(bool a_bIsLittleEndian); 15 | void setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian); 16 | }; 17 | 18 | #endif // CMDPACKETSETMTA_H 19 | -------------------------------------------------------------------------------- /CmdPacketShortUpload.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketShortUpload.h" 2 | 3 | CmdPacketShortUpload::CmdPacketShortUpload() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::SHORT_UPLOAD); 7 | m_dataField.resize(7); // Reserve 7 element in data field 8 | m_dataField[1] = 0; // Unused 9 | } 10 | 11 | void CmdPacketShortUpload::setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian) 12 | { 13 | uint8_t i1, i2, i3, i4; 14 | i1 = a_dwAddress & 0xFF; 15 | i2 = (a_dwAddress >> 8) & 0xFF; 16 | i3 = (a_dwAddress >> 16) & 0xFF; 17 | i4 = (a_dwAddress >> 24) & 0xFF; 18 | 19 | if(a_bIsLittleEndian) { 20 | m_dataField[3] = i1; 21 | m_dataField[4] = i2; 22 | m_dataField[5] = i3; 23 | m_dataField[6] = i4; 24 | } 25 | else { 26 | m_dataField[3] = i4; 27 | m_dataField[4] = i3; 28 | m_dataField[5] = i2; 29 | m_dataField[6] = i1; 30 | } 31 | } 32 | 33 | uint32_t CmdPacketShortUpload::getAddress(bool a_bIsLittleEndian) 34 | { 35 | if(a_bIsLittleEndian) { 36 | return (((uint32_t)m_dataField[6]) << 24) | (((uint32_t)m_dataField[5]) << 16) | (((uint32_t)m_dataField[4]) << 8) | m_dataField[3]; 37 | } 38 | else { 39 | //do byte-swap 40 | return (((uint32_t)m_dataField[3]) << 24) | (((uint32_t)m_dataField[4]) << 16) | (((uint32_t)m_dataField[5]) << 8) | m_dataField[6]; 41 | } 42 | } 43 | 44 | void CmdPacketShortUpload::setAddressExtension(uint8_t a_byAddressExtension) 45 | { 46 | m_dataField[2] = a_byAddressExtension; 47 | } 48 | 49 | uint8_t CmdPacketShortUpload::getAddressExtension() 50 | { 51 | return m_dataField[2]; 52 | } 53 | 54 | void CmdPacketShortUpload::setNumberOfDataElements(uint8_t a_byNumberOfDataElements) 55 | { 56 | m_dataField[0] = a_byNumberOfDataElements; 57 | } 58 | 59 | uint8_t CmdPacketShortUpload::getNumberOfDataElements() 60 | { 61 | return m_dataField[0]; 62 | } 63 | -------------------------------------------------------------------------------- /CmdPacketShortUpload.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETSHORTUPLOAD_H 2 | #define CMDPACKETSHORTUPLOAD_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketShortUpload : public CmdPacket 7 | { 8 | public: 9 | CmdPacketShortUpload(); 10 | 11 | void setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian); 12 | uint32_t getAddress(bool a_bIsLittleEndian); 13 | 14 | void setAddressExtension(uint8_t a_byAddressExtension); 15 | uint8_t getAddressExtension(); 16 | 17 | void setNumberOfDataElements(uint8_t a_byNumberOfDataElements); 18 | uint8_t getNumberOfDataElements(); 19 | }; 20 | 21 | #endif // CMDPACKETSHORTUPLOAD_H 22 | -------------------------------------------------------------------------------- /CmdPacketSync.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketSync.h" 2 | 3 | CmdPacketSync::CmdPacketSync() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::SYNCH); 7 | } 8 | -------------------------------------------------------------------------------- /CmdPacketSync.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETSYNC_H 2 | #define CMDPACKETSYNC_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketSync : public CmdPacket 7 | { 8 | public: 9 | CmdPacketSync(); 10 | }; 11 | 12 | #endif // CMDPACKETSYNC_H 13 | -------------------------------------------------------------------------------- /CmdPacketUnlock.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketUnlock.h" 2 | 3 | CmdPacketUnlock::CmdPacketUnlock(const QVector &a_rKey, uint8_t a_byStartIndex, uint8_t a_byMaxCto) 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::UNLOCK); 7 | 8 | uint8_t byDataLength = 0; 9 | if((uint8_t)a_rKey.size() - a_byStartIndex >= a_byMaxCto - 2) { 10 | byDataLength = a_byMaxCto - 2; 11 | } 12 | else { 13 | byDataLength = (uint32_t)a_rKey.size() + 1; 14 | } 15 | 16 | m_dataField.resize(byDataLength); 17 | m_dataField[0] = (uint8_t)a_rKey.size() - a_byStartIndex; 18 | for(unsigned int i = 0; i < byDataLength-1; i++) { 19 | m_dataField[1 + i] = a_rKey[a_byStartIndex + i]; 20 | } 21 | } 22 | 23 | QVector CmdPacketUnlock::createUnlockPackets(const QVector &a_rKey, uint8_t a_byMaxCto) 24 | { 25 | QVector retval; 26 | uint8_t byRemainingKeyLength = (uint8_t)a_rKey.size(); 27 | do { 28 | CmdPacketUnlock* pToAdd = new CmdPacketUnlock(a_rKey, 0, a_byMaxCto); 29 | byRemainingKeyLength -= pToAdd->getRemainingKeyLength(); 30 | retval.push_back(pToAdd); 31 | } while(byRemainingKeyLength); 32 | 33 | return retval; 34 | } 35 | 36 | uint8_t CmdPacketUnlock::getRemainingKeyLength() 37 | { 38 | return m_dataField[0]; 39 | } 40 | -------------------------------------------------------------------------------- /CmdPacketUnlock.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETUNLOCK_H 2 | #define CMDPACKETUNLOCK_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketUnlock : public CmdPacket 7 | { 8 | public: 9 | CmdPacketUnlock(const QVector &a_rKey, uint8_t a_byStartIndex, uint8_t a_byMaxCto); 10 | 11 | static QVector createUnlockPackets(const QVector& a_rKey, uint8_t a_byMaxCto); 12 | 13 | uint8_t getRemainingKeyLength(); 14 | }; 15 | 16 | #endif // CMDPACKETUNLOCK_H 17 | -------------------------------------------------------------------------------- /CmdPacketUpload.cpp: -------------------------------------------------------------------------------- 1 | #include "CmdPacketUpload.h" 2 | 3 | CmdPacketUpload::CmdPacketUpload(uint8_t a_byNumberOfDataElements) 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::UPLOAD); 7 | m_dataField.resize(1); // Reserve 1 element in data field 8 | m_dataField[0] = a_byNumberOfDataElements; 9 | } 10 | 11 | void CmdPacketUpload::setNumberOfDataElements(uint8_t a_byNum) 12 | { 13 | m_dataField[0] = a_byNum; 14 | } 15 | 16 | uint8_t CmdPacketUpload::getNumberOfDataElements() 17 | { 18 | return m_dataField[0]; 19 | } 20 | -------------------------------------------------------------------------------- /CmdPacketUpload.h: -------------------------------------------------------------------------------- 1 | #ifndef CMDPACKETUPLOAD_H 2 | #define CMDPACKETUPLOAD_H 3 | 4 | #include "CmdPacket.h" 5 | 6 | class CmdPacketUpload : public CmdPacket 7 | { 8 | public: 9 | //Number of dataelements: 1..[MAXCTO/AG - 1] in standardmode, 1..255 in block mode 10 | CmdPacketUpload(uint8_t a_byNumberOfDataElements); 11 | 12 | void setNumberOfDataElements(uint8_t a_byNum); 13 | uint8_t getNumberOfDataElements(); 14 | }; 15 | 16 | #endif // CMDPACKETUPLOAD_H 17 | -------------------------------------------------------------------------------- /DAQ.cpp: -------------------------------------------------------------------------------- 1 | #include "DAQ.h" 2 | 3 | #include 4 | 5 | OdtEntry::OdtEntry() 6 | { 7 | m_dwAddress = 0; 8 | m_byAddressExtension = 0; 9 | m_byLength = 0; 10 | m_byDataType = 0; 11 | } 12 | 13 | OdtEntry::OdtEntry(uint32_t a_dwAddress, uint8_t a_byAddressExtension, uint8_t a_byLength) 14 | { 15 | m_dwAddress = a_dwAddress; 16 | m_byAddressExtension = a_byAddressExtension; 17 | m_byLength = a_byLength; 18 | } 19 | 20 | OdtEntry::OdtEntry(const OdtEntry &other) 21 | { 22 | m_dwAddress = other.m_dwAddress; 23 | m_byAddressExtension = other.m_byAddressExtension; 24 | m_byLength = other.m_byLength; 25 | m_byDataType = other.m_byDataType; 26 | } 27 | 28 | void OdtEntry::setDataType(uint8_t a_byDataType) 29 | { 30 | m_byDataType = a_byDataType; 31 | switch (m_byDataType) 32 | { 33 | case MeasurementDataTypes::eInt8: 34 | case MeasurementDataTypes::eUint8: 35 | m_byLength = 1; 36 | break; 37 | case MeasurementDataTypes::eInt16: 38 | case MeasurementDataTypes::eUint16: 39 | m_byLength = 2; 40 | break; 41 | case MeasurementDataTypes::eInt32: 42 | case MeasurementDataTypes::eUint32: 43 | case MeasurementDataTypes::eFloat: 44 | m_byLength = 4; 45 | break; 46 | case MeasurementDataTypes::eDouble: 47 | case MeasurementDataTypes::eInt64: 48 | case MeasurementDataTypes::eUint64: 49 | m_byLength = 8; 50 | break; 51 | default: 52 | m_byLength = 0; //undefined data type = error 53 | break; 54 | } 55 | } 56 | 57 | ODT::ODT() 58 | { 59 | m_bIsFirst = false; 60 | } 61 | 62 | ODT::ODT(const ODT &other) 63 | : m_listEntry(other.m_listEntry) 64 | { 65 | m_bIsFirst = other.m_bIsFirst; 66 | } 67 | 68 | ODT::~ODT() 69 | { 70 | m_listEntry.clear(); 71 | } 72 | 73 | void ODT::addEntry(OdtEntry a_rEntry) 74 | { 75 | m_listEntry.push_back(a_rEntry); 76 | } 77 | 78 | OdtEntry &ODT::getEntry(uint32_t a_dwIndex) 79 | { 80 | return m_listEntry[a_dwIndex]; 81 | } 82 | 83 | uint32_t ODT::getOdtSize() const 84 | { 85 | uint32_t dwSize = 0; 86 | foreach(OdtEntry odtEntry, m_listEntry) { 87 | dwSize += odtEntry.getLength(); 88 | } 89 | return dwSize; 90 | } 91 | 92 | uint32_t ODT::getNumberOfEntries() const 93 | { 94 | return (uint32_t)m_listEntry.size(); 95 | } 96 | 97 | bool ODT::isFirst() const 98 | { 99 | return m_bIsFirst; 100 | } 101 | 102 | void ODT::setFirst(bool a_bIsFirst) 103 | { 104 | m_bIsFirst = a_bIsFirst; 105 | } 106 | 107 | DAQ::DAQ(const DAQ &other) 108 | : DTO(), 109 | m_listOdt(other.m_listOdt) 110 | { 111 | m_byMode = other.m_byMode; 112 | m_wEventChannel = other.m_wEventChannel; 113 | m_byPrescaler = other.m_byPrescaler; 114 | m_byPriority = other.m_byPriority; 115 | m_byFirstPid = other.m_byFirstPid; 116 | m_dwLastTimestamp = other.m_dwLastTimestamp; 117 | } 118 | 119 | DAQ::~DAQ() 120 | { 121 | m_listOdt.clear(); 122 | } 123 | 124 | void DAQ::addOdt(ODT a_Odt) 125 | { 126 | if (m_listOdt.size() == 0) 127 | { 128 | a_Odt.setFirst(true); 129 | } 130 | m_listOdt.push_back(a_Odt); 131 | } 132 | 133 | ODT &DAQ::getOdt(uint32_t a_dwIndex) 134 | { 135 | return m_listOdt[a_dwIndex]; 136 | } 137 | 138 | DaqLayout::DaqLayout(const DaqLayout &other) 139 | : m_listDaq(other.m_listDaq) 140 | { 141 | m_bInitialized = other.m_bInitialized; 142 | } 143 | 144 | DaqLayout::~DaqLayout() 145 | { 146 | m_listDaq.clear(); 147 | } 148 | 149 | void DaqLayout::setDaq(unsigned int a_nId, DAQ a_daq) 150 | { 151 | if(a_nId < m_listDaq.size()) { 152 | m_listDaq[a_nId] = a_daq; 153 | } 154 | } 155 | 156 | bool DaqLayout::calcDaqNumberFromAbsPid(uint8_t a_byPid, uint16_t &a_rDaqNumber) 157 | { 158 | for(int i=0; i 5 | #include "DTO.h" 6 | 7 | enum MeasurementDataTypes 8 | { 9 | eInt8 = 0, 10 | eUint8, 11 | eInt16, 12 | eUint16, 13 | eInt32, 14 | eUint32, 15 | eFloat, 16 | eDouble, 17 | eInt64, 18 | eUint64, 19 | }; 20 | 21 | class OdtEntry 22 | { 23 | public: 24 | OdtEntry(); 25 | OdtEntry(uint32_t a_dwAddress, uint8_t a_byAddressExtension, uint8_t a_byLength); 26 | OdtEntry(const OdtEntry& other); 27 | uint32_t getAddress() const {return m_dwAddress;} 28 | void setAddress(uint32_t a_dwAddress) {m_dwAddress = a_dwAddress;} 29 | uint8_t getAddressExtension() const {return m_byAddressExtension;} 30 | void setAddressExtension(uint8_t a_byAddressExtension) {m_byAddressExtension = a_byAddressExtension;} 31 | uint8_t getLength() const {return m_byLength;} 32 | void setDataType(uint8_t a_byDataType); 33 | uint8_t getDataType() const {return m_byDataType;} 34 | 35 | private: 36 | uint32_t m_dwAddress; 37 | uint8_t m_byAddressExtension; 38 | uint8_t m_byLength; 39 | uint8_t m_byDataType; 40 | }; 41 | 42 | class ODT 43 | { 44 | public: 45 | ODT(); 46 | ODT(const ODT& other); 47 | ~ODT(); 48 | void addEntry(OdtEntry a_rEntry); 49 | OdtEntry& getEntry(uint32_t a_dwIndex); 50 | uint32_t getOdtSize() const; 51 | uint32_t getNumberOfEntries() const; 52 | bool isFirst() const; 53 | void setFirst(bool a_bIsFirst); 54 | 55 | private: 56 | QVector m_listEntry; 57 | bool m_bIsFirst; 58 | }; 59 | 60 | class DAQ : public DTO 61 | { 62 | public: 63 | DAQ() : DTO() {} 64 | DAQ(const DAQ& other); 65 | virtual ~DAQ(); 66 | void addOdt(ODT a_Odt); 67 | ODT& getOdt(uint32_t a_dwIndex); 68 | void setMode(uint8_t a_byMode) {m_byMode = a_byMode;} 69 | uint8_t getMode() const {return m_byMode;} 70 | uint16_t getEventChannel() const {return m_wEventChannel;} 71 | uint8_t getPrescaler() const {return m_byPrescaler;} 72 | uint8_t getPriority() const {return m_byPriority;} 73 | void setEventChannel(uint16_t a_wEventChannel) {m_wEventChannel = a_wEventChannel;} 74 | void setPrescaler(uint8_t a_byPrescaler) {m_byPrescaler = a_byPrescaler;} 75 | void setPriority(uint8_t a_byPriority) {m_byPriority = a_byPriority;} 76 | uint16_t getNumberOfOdts() const {return (uint16_t)m_listOdt.size();} 77 | uint8_t getFirstPid() {return m_byFirstPid;} 78 | void setFirstPid(uint8_t a_byFirstPid) {m_byFirstPid = a_byFirstPid;} 79 | void setLastTimestamp(uint32_t a_dwTimestamp) {m_dwLastTimestamp = a_dwTimestamp;} 80 | uint32_t getLastTimestamp() {return m_dwLastTimestamp;} 81 | 82 | private: 83 | QVector m_listOdt; 84 | uint8_t m_byMode; 85 | uint16_t m_wEventChannel; 86 | uint8_t m_byPrescaler; 87 | uint8_t m_byPriority; 88 | uint8_t m_byFirstPid; 89 | uint32_t m_dwLastTimestamp; 90 | }; 91 | 92 | class DaqLayout 93 | { 94 | public: 95 | DaqLayout() : m_bInitialized(false) {} 96 | DaqLayout(const DaqLayout &other); 97 | ~DaqLayout(); 98 | void addDaq(DAQ a_daq) {m_listDaq.push_back(a_daq);} 99 | void setDaq(unsigned int a_nId, DAQ a_daq); 100 | DAQ& getDaq(uint32_t a_dwIndex) {return m_listDaq[a_dwIndex];} 101 | uint16_t getNumberOfDaqLists() const {return (uint16_t)m_listDaq.size();} 102 | bool calcDaqNumberFromAbsPid(uint8_t a_byPid, uint16_t &a_rDaqNumber); 103 | bool calcOdtNumberFromAbsPid(uint8_t a_byPid, uint8_t &a_rOdtNumber); 104 | bool getOdtFromAbsolutePid(uint8_t a_byPid, ODT &a_rOdt); 105 | bool isInitialized() const {return m_bInitialized;} 106 | void setInitialized(bool a_bInitialized) {m_bInitialized = a_bInitialized;} 107 | 108 | private: 109 | QVector m_listDaq; 110 | bool m_bInitialized; 111 | }; 112 | 113 | #endif // DAQ_H 114 | -------------------------------------------------------------------------------- /DAQPackets.cpp: -------------------------------------------------------------------------------- 1 | #include "DAQPackets.h" 2 | 3 | FreeDaqPacket::FreeDaqPacket() 4 | : CmdPacket() 5 | { 6 | m_idField.append(CTO::FREE_DAQ); 7 | } 8 | 9 | AllocDaqPacket::AllocDaqPacket() 10 | : CmdPacket() 11 | { 12 | m_idField.append(CTO::ALLOC_DAQ); 13 | m_dataField.resize(3); // Reserve 3 element in data field 14 | m_dataField[0] = 0; 15 | } 16 | 17 | void AllocDaqPacket::setDaqCount(uint16_t a_wDaqCount, bool a_bIsLittleEndian) 18 | { 19 | uint8_t t1, t2; 20 | t1 = a_wDaqCount & 0xFF; 21 | t2 = (a_wDaqCount >> 8) & 0xFF; 22 | 23 | if(a_bIsLittleEndian) { 24 | m_dataField[1] = t1; 25 | m_dataField[2] = t2; 26 | } 27 | else { 28 | m_dataField[1] = t2; 29 | m_dataField[2] = t1; 30 | } 31 | } 32 | 33 | uint16_t AllocDaqPacket::getDaqCount(bool a_bIsLittleEndian) 34 | { 35 | uint16_t retval; 36 | uint16_t t1, t2; 37 | t1 = m_dataField[1]; 38 | t2 = m_dataField[2]; 39 | 40 | if(a_bIsLittleEndian) { 41 | retval = (t2 << 8) | t1; 42 | } 43 | else { 44 | retval = (t1 << 8) | t2; 45 | } 46 | 47 | return retval; 48 | } 49 | 50 | AllocOdtPacket::AllocOdtPacket() 51 | : CmdPacket() 52 | { 53 | m_idField.append(CTO::ALLOC_ODT); 54 | m_dataField.resize(4); // Reserve 4 element in data field 55 | m_dataField[0] = 0; 56 | } 57 | 58 | void AllocOdtPacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 59 | { 60 | uint8_t t1, t2; 61 | t1 = a_wDaqListNumber & 0xFF; 62 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 63 | 64 | if(a_bIsLittleEndian) { 65 | m_dataField[1] = t1; 66 | m_dataField[2] = t2; 67 | } 68 | else { 69 | m_dataField[1] = t2; 70 | m_dataField[2] = t1; 71 | } 72 | } 73 | 74 | void AllocOdtPacket::setOdtCount(uint8_t a_byOdtCount) 75 | { 76 | m_dataField[3] = a_byOdtCount; 77 | } 78 | 79 | AllocOdtEntryPacket::AllocOdtEntryPacket() 80 | : CmdPacket() 81 | { 82 | m_idField.append(CTO::ALLOC_ODT_ENTRY); 83 | m_dataField.resize(5); // Reserve 5 element in data field 84 | m_dataField[0] = 0; 85 | } 86 | 87 | void AllocOdtEntryPacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 88 | { 89 | uint8_t t1, t2; 90 | t1 = a_wDaqListNumber & 0xFF; 91 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 92 | 93 | if(a_bIsLittleEndian) { 94 | m_dataField[1] = t1; 95 | m_dataField[2] = t2; 96 | } 97 | else { 98 | m_dataField[1] = t2; 99 | m_dataField[2] = t1; 100 | } 101 | } 102 | 103 | void AllocOdtEntryPacket::setOdtNumber(uint8_t a_byOdtNumber) 104 | { 105 | m_dataField[3] = a_byOdtNumber; 106 | } 107 | 108 | void AllocOdtEntryPacket::setOdtEntriesCount(uint8_t a_byOdtEntriesCount) 109 | { 110 | m_dataField[4] = a_byOdtEntriesCount; 111 | } 112 | 113 | SetDaqPtrPacket::SetDaqPtrPacket() 114 | : CmdPacket() 115 | { 116 | m_idField.append(CTO::SET_DAQ_PTR); 117 | m_dataField.resize(5); // Reserve 5 element in data field 118 | m_dataField[0] = 0; 119 | } 120 | 121 | void SetDaqPtrPacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 122 | { 123 | uint8_t t1, t2; 124 | t1 = a_wDaqListNumber & 0xFF; 125 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 126 | 127 | if(a_bIsLittleEndian) { 128 | m_dataField[1] = t1; 129 | m_dataField[2] = t2; 130 | } 131 | else { 132 | m_dataField[1] = t2; 133 | m_dataField[2] = t1; 134 | } 135 | } 136 | 137 | void SetDaqPtrPacket::setOdtNumber(uint8_t a_byOdtNumber) 138 | { 139 | m_dataField[3] = a_byOdtNumber; 140 | } 141 | 142 | void SetDaqPtrPacket::setOdtEntryNumber(uint8_t a_byOdtEntryNumber) 143 | { 144 | m_dataField[4] = a_byOdtEntryNumber; 145 | } 146 | 147 | WriteDaqPacket::WriteDaqPacket() 148 | : CmdPacket() 149 | { 150 | m_idField.append(CTO::WRITE_DAQ); 151 | m_dataField.resize(7); // Reserve 7 element in data field 152 | } 153 | 154 | void WriteDaqPacket::setBitOffset(uint8_t a_byOffset) 155 | { 156 | m_dataField[0] = a_byOffset; 157 | } 158 | 159 | void WriteDaqPacket::setElementSize(uint8_t a_bySize) 160 | { 161 | m_dataField[1] = a_bySize; 162 | } 163 | 164 | void WriteDaqPacket::setAddressExtension(uint8_t a_byAddressExtension) 165 | { 166 | m_dataField[2] = a_byAddressExtension; 167 | } 168 | 169 | void WriteDaqPacket::setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian) 170 | { 171 | uint8_t i1, i2, i3, i4; 172 | i1 = a_dwAddress & 0xFF; 173 | i2 = (a_dwAddress >> 8) & 0xFF; 174 | i3 = (a_dwAddress >> 16) & 0xFF; 175 | i4 = (a_dwAddress >> 24) & 0xFF; 176 | 177 | if(a_bIsLittleEndian) { 178 | m_dataField[3] = i1; 179 | m_dataField[4] = i2; 180 | m_dataField[5] = i3; 181 | m_dataField[6] = i4; 182 | } 183 | else { 184 | m_dataField[3] = i4; 185 | m_dataField[4] = i3; 186 | m_dataField[5] = i2; 187 | m_dataField[6] = i1; 188 | } 189 | } 190 | 191 | SetDaqListModePacket::SetDaqListModePacket() 192 | : CmdPacket() 193 | { 194 | m_idField.append(CTO::SET_DAQ_LIST_MODE); 195 | m_dataField.resize(7); // Reserve 7 element in data field 196 | } 197 | 198 | SetDaqListModePacket::SetDaqListModePacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority, bool a_bIsLittleEndian) 199 | : CmdPacket() 200 | { 201 | m_idField.resize(1); 202 | m_idField[0] = CTO::SET_DAQ_LIST_MODE; 203 | m_dataField.resize(7); // Reserve 7 element in data field 204 | 205 | setMode(a_byMode); 206 | setDaqListNumber(a_wDaqListNumber,a_bIsLittleEndian); 207 | setEventChannel(a_wEventChannel, a_bIsLittleEndian); 208 | setTransmissionRatePrescaler(a_byPrescaler); 209 | setDaqListPriority(a_byPriority); 210 | } 211 | 212 | void SetDaqListModePacket::setMode(uint8_t a_byMode) 213 | { 214 | m_dataField[0] = a_byMode; 215 | } 216 | 217 | void SetDaqListModePacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 218 | { 219 | uint8_t t1, t2; 220 | t1 = a_wDaqListNumber & 0xFF; 221 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 222 | 223 | if(a_bIsLittleEndian) { 224 | m_dataField[1] = t1; 225 | m_dataField[2] = t2; 226 | } 227 | else { 228 | m_dataField[1] = t2; 229 | m_dataField[2] = t1; 230 | } 231 | } 232 | 233 | void SetDaqListModePacket::setEventChannel(uint16_t a_wEventChannel, bool a_bIsLittleEndian) 234 | { 235 | uint8_t t1, t2; 236 | t1 = a_wEventChannel & 0xFF; 237 | t2 = (a_wEventChannel >> 8) & 0xFF; 238 | 239 | if(a_bIsLittleEndian) { 240 | m_dataField[3] = t1; 241 | m_dataField[4] = t2; 242 | } 243 | else { 244 | m_dataField[3] = t2; 245 | m_dataField[4] = t1; 246 | } 247 | } 248 | 249 | void SetDaqListModePacket::setTransmissionRatePrescaler(uint8_t a_byPrescaler) 250 | { 251 | m_dataField[5] = a_byPrescaler; 252 | } 253 | 254 | void SetDaqListModePacket::setDaqListPriority(uint8_t a_byPriority) 255 | { 256 | m_dataField[6] = a_byPriority; 257 | } 258 | 259 | StartStopDaqListPacket::StartStopDaqListPacket() 260 | : CmdPacket() 261 | { 262 | m_idField.append(CTO::START_STOP_DAQ_LIST); 263 | m_dataField.resize(3); // Reserve 3 element in data field 264 | } 265 | 266 | StartStopDaqListPacket::StartStopDaqListPacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 267 | : CmdPacket() 268 | { 269 | m_idField.append(CTO::START_STOP_DAQ_LIST); 270 | m_dataField.resize(3); // Reserve 3 element in data field 271 | setMode(a_byMode); 272 | setDaqListNumber(a_wDaqListNumber, a_bIsLittleEndian); 273 | } 274 | 275 | void StartStopDaqListPacket::setMode(uint8_t a_byMode) 276 | { 277 | m_dataField[0] = a_byMode; 278 | } 279 | 280 | void StartStopDaqListPacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 281 | { 282 | uint8_t t1, t2; 283 | t1 = a_wDaqListNumber & 0xFF; 284 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 285 | 286 | if(a_bIsLittleEndian) { 287 | m_dataField[1] = t1; 288 | m_dataField[2] = t2; 289 | } 290 | else { 291 | m_dataField[1] = t2; 292 | m_dataField[2] = t1; 293 | } 294 | } 295 | 296 | uint16_t StartStopDaqListPacket::getDaqListNumber(bool a_bIsLittleEndian) 297 | { 298 | uint16_t retval; 299 | if(a_bIsLittleEndian) { 300 | retval = m_dataField[1]; 301 | retval |= (((uint16_t)m_dataField[2])<<8); 302 | } 303 | else { 304 | retval = m_dataField[2]; 305 | retval |= (((uint16_t)m_dataField[1]) << 8); 306 | } 307 | return retval; 308 | } 309 | 310 | StartStopDaqListPositiveResponse::StartStopDaqListPositiveResponse(const QVector &a_rData) 311 | : ResPacket() 312 | { 313 | m_dataField.resize(1); 314 | for(int i=0; i &a_rData) 326 | { 327 | return new StartStopDaqListPositiveResponse(a_rData); 328 | } 329 | 330 | StartStopSynchPacket::StartStopSynchPacket(StartStopSynchPacket::Mode a_eMode) 331 | : CmdPacket() 332 | { 333 | m_idField.append(CTO::START_STOP_SYNCH); 334 | m_dataField.resize(1); // Reserve 1 element in data field 335 | setMode(a_eMode); 336 | } 337 | 338 | void StartStopSynchPacket::setMode(uint8_t a_byMode) 339 | { 340 | m_dataField[0] = a_byMode; 341 | } 342 | 343 | GetDaqProcessorInfo::GetDaqProcessorInfo() 344 | : CmdPacket() 345 | { 346 | m_idField.append(CTO::GET_DAQ_PROCESSOR_INFO); 347 | } 348 | 349 | GetDaqProcessorInfoResponse::GetDaqProcessorInfoResponse(const QVector &a_rData) 350 | : ResPacket() 351 | { 352 | m_dataField.resize(7); 353 | for(int i=0; i &a_rData) 359 | { 360 | return new GetDaqProcessorInfoResponse(a_rData); 361 | } 362 | 363 | uint8_t GetDaqProcessorInfoResponse::getDaqProperties() 364 | { 365 | return m_dataField[0]; 366 | } 367 | 368 | uint16_t GetDaqProcessorInfoResponse::getMaxDaq(bool a_bIsLittleEndian) 369 | { 370 | if(a_bIsLittleEndian) { 371 | return (((uint16_t)m_dataField[2]) << 8) | m_dataField[1]; 372 | } 373 | else { 374 | //do byte-swap 375 | return (((uint16_t)m_dataField[1]) << 8) | m_dataField[2]; 376 | } 377 | } 378 | 379 | uint16_t GetDaqProcessorInfoResponse::getMaxEventChannel(bool a_bIsLittleEndian) 380 | { 381 | if(a_bIsLittleEndian) { 382 | return (((uint16_t)m_dataField[4]) << 8) | m_dataField[3]; 383 | } 384 | else { 385 | //do byte-swap 386 | return (((uint16_t)m_dataField[3]) << 8) | m_dataField[4]; 387 | } 388 | } 389 | 390 | uint8_t GetDaqProcessorInfoResponse::getMinDaq() 391 | { 392 | return m_dataField[5]; 393 | } 394 | 395 | uint8_t GetDaqProcessorInfoResponse::getDaqKeyByte() 396 | { 397 | return m_dataField[6]; 398 | } 399 | 400 | ClearDAQListPacket::ClearDAQListPacket(uint16_t a_wDAQListNumber, bool a_bIsLittleEndian) 401 | : CmdPacket() 402 | { 403 | m_idField.append(CTO::CLEAR_DAQ_LIST); 404 | m_dataField.resize(3); // Reserve 3 element in data field 405 | m_dataField[0] = 0; //Reserved 406 | setDaqListNumber(a_wDAQListNumber, a_bIsLittleEndian); 407 | } 408 | 409 | void ClearDAQListPacket::setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 410 | { 411 | uint8_t t1, t2; 412 | t1 = a_wDaqListNumber & 0xFF; 413 | t2 = (a_wDaqListNumber >> 8) & 0xFF; 414 | 415 | if(a_bIsLittleEndian) { 416 | m_dataField[1] = t1; 417 | m_dataField[2] = t2; 418 | } 419 | else { 420 | m_dataField[1] = t2; 421 | m_dataField[2] = t1; 422 | } 423 | } 424 | 425 | uint16_t ClearDAQListPacket::getDaqListNumber(bool a_bIsLittleEndian) 426 | { 427 | if(a_bIsLittleEndian) { 428 | return (((uint16_t)m_dataField[2]) << 8) | m_dataField[1]; 429 | } 430 | else { 431 | //do byte-swap 432 | return (((uint16_t)m_dataField[1]) << 8) | m_dataField[2]; 433 | } 434 | } 435 | -------------------------------------------------------------------------------- /DAQPackets.h: -------------------------------------------------------------------------------- 1 | #ifndef DAQPACKETS_H 2 | #define DAQPACKETS_H 3 | 4 | #include "CmdPacket.h" 5 | #include "ResPacket.h" 6 | 7 | class FreeDaqPacket final : public CmdPacket 8 | { 9 | public: 10 | FreeDaqPacket(); 11 | }; 12 | 13 | 14 | class AllocDaqPacket final : public CmdPacket 15 | { 16 | public: 17 | AllocDaqPacket(); 18 | void setDaqCount(uint16_t a_wDaqCount, bool a_bIsLittleEndian); 19 | uint16_t getDaqCount(bool a_bIsLittleEndian); 20 | }; 21 | 22 | 23 | class AllocOdtPacket final : public CmdPacket 24 | { 25 | public: 26 | AllocOdtPacket(); 27 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 28 | void setOdtCount(uint8_t a_byOdtCount); 29 | }; 30 | 31 | 32 | class AllocOdtEntryPacket final : public CmdPacket 33 | { 34 | public: 35 | AllocOdtEntryPacket(); 36 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 37 | void setOdtNumber(uint8_t a_byOdtNumber); 38 | void setOdtEntriesCount(uint8_t a_byOdtEntriesCount); 39 | }; 40 | 41 | 42 | class SetDaqPtrPacket final : public CmdPacket 43 | { 44 | public: 45 | SetDaqPtrPacket(); 46 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 47 | void setOdtNumber(uint8_t a_byOdtNumber); 48 | void setOdtEntryNumber(uint8_t a_byOdtEntryNumber); 49 | }; 50 | 51 | 52 | class WriteDaqPacket final : public CmdPacket 53 | { 54 | public: 55 | WriteDaqPacket(); 56 | // For DAQ diresction it is a bitmask, for STIM direction it is the position of the bit to be manipulated. 57 | // The DAQ pointer is auto post incremented within an ODT. 58 | // After the last ODT entry the pointer value is undefined. 59 | void setBitOffset(uint8_t a_byOffset); 60 | void setElementSize(uint8_t a_bySize); 61 | void setAddressExtension(uint8_t a_byAddressExtension); 62 | void setAddress(uint32_t a_dwAddress, bool a_bIsLittleEndian); 63 | }; 64 | 65 | 66 | class SetDaqListModePacket final : public CmdPacket 67 | { 68 | public: 69 | enum ModeFieldBits 70 | { 71 | ALTERNATING = 0x01, //0: disable alternating display mode, 1: enable 72 | DIRECTION = 0x02, //0: DAQ direction, 1: STIM direction 73 | DTO_CTR = 0x08, //0: do not use DTO ctr field, 1: use ctr 74 | TIMESTAMP = 0x10, //0: disable timestamp, 1: enable 75 | PID_OFF = 0x20, //0: transmit DTO with identification field, 1: transmit DTO WITHOUT identifictation field 76 | }; 77 | 78 | public: 79 | SetDaqListModePacket(); 80 | SetDaqListModePacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority, bool a_bIsLittleEndian); 81 | void setMode(uint8_t a_byMode); 82 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 83 | void setEventChannel(uint16_t a_wEventChannel, bool a_bIsLittleEndian); 84 | void setTransmissionRatePrescaler(uint8_t a_byPrescaler); 85 | void setDaqListPriority(uint8_t a_byPriority); 86 | }; 87 | 88 | 89 | class StartStopDaqListPacket final : public CmdPacket 90 | { 91 | public: 92 | enum Mode 93 | { 94 | STOP = 0x0, 95 | START = 0x1, 96 | SELECT = 0x2, 97 | }; 98 | 99 | public: 100 | StartStopDaqListPacket(); 101 | //Mode: 0 stop, 1 start, 2 select 102 | StartStopDaqListPacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 103 | void setMode(uint8_t a_byMode); 104 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 105 | uint16_t getDaqListNumber(bool a_bIsLittleEndian); 106 | }; 107 | 108 | 109 | class StartStopDaqListPositiveResponse final : public ResPacket 110 | { 111 | public: 112 | StartStopDaqListPositiveResponse(const QVector& a_rData); 113 | uint8_t getFirstPid(); 114 | static StartStopDaqListPositiveResponse* deserialize(const QVector& a_rData); 115 | }; 116 | 117 | 118 | class StartStopSynchPacket final : public CmdPacket 119 | { 120 | public: 121 | enum Mode 122 | { 123 | STOP_ALL = 0x00, 124 | START_SELECTED = 0x01, 125 | STOP_SELECTED = 0x02, 126 | }; 127 | StartStopSynchPacket(Mode a_eMode); 128 | void setMode(uint8_t a_byMode); 129 | }; 130 | 131 | 132 | class GetDaqProcessorInfo final : public CmdPacket 133 | { 134 | public: 135 | GetDaqProcessorInfo(); 136 | }; 137 | 138 | 139 | class GetDaqProcessorInfoResponse final : public ResPacket 140 | { 141 | public: 142 | enum DaqPropertiesBits 143 | { 144 | DAQ_CONFIG_TYPE = 0x01, //0: Static DAQ list configuration, 1: dynamic daq list configuration 145 | PRESCALER_SUPPORTED = 0x02, //0: prescaler not supported, 1: prescaler supported 146 | RESUME_SUPPORTED = 0x04, //0: DAQ list can not be set to resume mode, 1: Daq list can be set to resume mode 147 | BIT_STIM_SUPPORTED = 0x08, //0: bitwise datastimulation not supported, 1: supported 148 | TIMESTAMP_SUPPORTED = 0x10, //0: timestamped mode not supported, 1: supported 149 | PID_OFF_SUPPORTED = 0x20, //0: Identification field can not be switched off, 1: Identification field may be switched off 150 | OVERLOAD_MSB = 0x40, 151 | OVERLOAD_EVENT = 0x80, //OE-OM: 0-0:No overload indication | 0-1:overload indication in MSB of PID | 1-0: overload indication by Event Packet | 1-1: not allowed 152 | 153 | OVERLOAD_INDICATION_MODE = 0xC0, //the 2 before, only combined 154 | }; 155 | 156 | enum DaqKeyByteBits 157 | { 158 | OPTIMISATION_TYPE_0 = 0x01, //The Optimisation_Type flags indicate the type of Optimisation Method the master preferably should use. 159 | OPTIMISATION_TYPE_1 = 0x02, 160 | OPTIMISATION_TYPE_2 = 0x04, 161 | OPTIMISATION_TYPE_3 = 0x08, //OT3-2-1-0: 0000: OM_DEFAULT | 0001: OM_ODT_TYPE_16 | 0010: OM_ODT_TYPE_32 | 0011: OM_ODT_TYPE_64 | 0100: OM_ODT_TYPE_ALIGNMENT | 0101: OM_MAX_ENTRY_SIZE 162 | 163 | OPTIMISATION_TYPE = 0x0F, ////the 4 entries before this one, only that it is combined into one 164 | 165 | ADDRESS_EXTENSION_ODT = 0x10, //The ADDR_EXTENSION flag indicates whether the address extension of all entries within one ODT or within one DAQ must be the same. 166 | ADDRESS_EXTENSION_DAQ = 0x20, //AEDAQ-AEODT: 00: address extension can be different within one and the same ODT | 01: 0 1 address extension to be the same for all entries within one ODT | 10: not allowed | 11: address extension to be the same for all entries within one DAQ 167 | 168 | ADDRESS_EXTENSION = 0x30, 169 | 170 | IDENTIFICATION_FIELD_TYPE_0 = 0x40, 171 | IDENTIFICATION_FIELD_TYPE_1 = 0x80, //00: absoulute odt number | 01: Relative ODT number, absolute DAQ list number (BYTE) | Relative ODT number, absolute DAQ list number (WORD) | 11: Relative ODT number, absolute DAQ list number (WORD, aligned) 172 | 173 | IDENTIFICATION_FIELD_TYPE = 0xC0, //the two entries before this one, only that it is combined into one 174 | }; 175 | 176 | enum OverloadIndicationMode 177 | { 178 | NO_INDICATION = 0x00, 179 | MSB_PID = 0x40, 180 | EVENT_PACKET = 0x80, 181 | NOT_ALLOWED = 0xC0, 182 | }; 183 | 184 | enum OptimisationMode 185 | { 186 | OM_DEFAULT = 0x00, 187 | OM_ODT_TYPE_16 = 0x01, 188 | OM_ODT_TYPE_32 = 0x02, 189 | OM_ODT_TYPE_64 = 0x03, 190 | OM_ODT_TYPE_ALIGNMENT = 0x04, 191 | OM_MAX_ENTRY_SIZE = 0x05, 192 | }; 193 | 194 | enum AddressExtensionType 195 | { 196 | CAN_BE_DIFFERENT = 0x00, 197 | SAME_FOR_ALL_ENTRIES_ODT = 0x10, 198 | // NOT_ALLOWED = 0x20, 199 | SAME_FOR_ALL_ENTRIES_DAQ = 0x30 200 | }; 201 | 202 | enum IdentificationFieldType 203 | { 204 | ABSOLUTE_ODT_NUMBER = 0x00, 205 | RELATIVE_ODT_ABSOLUTE_DAQ_BYTE = 0x40, 206 | RELATIVE_ODT_ABSOLUTE_DAQ_WORD = 0x80, 207 | RELATIVE_ODT_ABSOLUTE_DAQ_WORD_ALIGNED = 0xC0, 208 | }; 209 | 210 | GetDaqProcessorInfoResponse(const QVector& a_rData); 211 | static GetDaqProcessorInfoResponse* deserialize(const QVector& a_rData); 212 | uint8_t getDaqProperties(); 213 | //total number of DAQ lists available in the slave device. If DAQ_CONFIG_TYPE = dynamic, MAX_DAQ equals MIN_DAQ + DAQ_COUNT 214 | uint16_t getMaxDaq(bool a_bIsLittleEndian); 215 | //MAX_EVENT_CHANNEL is the number of available event channels. MAX_EVENT_CHANNEL = 0x00 means that the number of events in the slave is unknown. 216 | uint16_t getMaxEventChannel(bool a_bIsLittleEndian); 217 | //MIN_DAQ is the number of predefined DAQ lists. 218 | uint8_t getMinDaq(); 219 | uint8_t getDaqKeyByte(); 220 | }; 221 | 222 | 223 | class ClearDAQListPacket final : public CmdPacket 224 | { 225 | public: 226 | ClearDAQListPacket(uint16_t a_wDAQListNumber, bool a_bIsLittleEndian); 227 | void setDaqListNumber(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 228 | uint16_t getDaqListNumber(bool a_bIsLittleEndian); 229 | }; 230 | 231 | #endif // DAQPACKETS_H 232 | -------------------------------------------------------------------------------- /DTO.cpp: -------------------------------------------------------------------------------- 1 | #include "DTO.h" 2 | #include 3 | #include "DAQ.h" 4 | #include "DAQPackets.h" 5 | 6 | DTO::DTO() 7 | : XcpPacket () 8 | { 9 | 10 | } 11 | 12 | DTO::DTO(const QVector &a_rData, uint8_t TimestampSize, bool TimestampFixed, uint8_t IdentificationFieldType, DaqLayout &a_rDaqLayout) 13 | : XcpPacket () 14 | { 15 | m_bIsTimestamped = false; 16 | m_dwTimestamp = 0; 17 | m_bIsCTRed = false; 18 | m_byCtr = 0; 19 | m_byFill = 0; 20 | m_wDaq = 0; 21 | m_wDaqIndex = 0; 22 | m_byOdtIndex = 0; 23 | uint8_t Mode = 0; 24 | ODT currentOdtLayout; 25 | 26 | uint32_t ptr = 0; 27 | setPid(a_rData[ptr]); //between 0x00-0xFB 28 | ptr++; 29 | if (IdentificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::ABSOLUTE_ODT_NUMBER) { 30 | if(!a_rDaqLayout.calcDaqNumberFromAbsPid(getPid(), m_wDaqIndex)) return; 31 | if(!a_rDaqLayout.calcOdtNumberFromAbsPid(getPid(), m_byOdtIndex)) return; 32 | Mode = a_rDaqLayout.getDaq(m_wDaqIndex).getMode(); 33 | if(!a_rDaqLayout.getOdtFromAbsolutePid(getPid(), currentOdtLayout)) return; 34 | if (currentOdtLayout.isFirst() && (SetDaqListModePacket::ModeFieldBits::DTO_CTR&Mode)) 35 | { 36 | m_byCtr = a_rData[ptr]; 37 | ptr++; 38 | } 39 | } 40 | else if (IdentificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_BYTE) 41 | { 42 | m_wDaq = a_rData[ptr]; 43 | m_wDaqIndex = m_wDaq; 44 | m_byOdtIndex = getPid(); 45 | ptr++; 46 | Mode = a_rDaqLayout.getDaq(m_wDaq).getMode(); 47 | currentOdtLayout = a_rDaqLayout.getDaq(m_wDaq).getOdt(getPid()); 48 | if (currentOdtLayout.isFirst() && (SetDaqListModePacket::ModeFieldBits::DTO_CTR&Mode)) 49 | { 50 | m_byCtr = a_rData[ptr]; 51 | ptr++; 52 | } 53 | } 54 | else if (IdentificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_WORD) 55 | { 56 | uint16_t t1 = a_rData[ptr]; 57 | uint16_t t2 = a_rData[ptr + 1]; 58 | m_wDaq = t1 & 0xFF; 59 | m_wDaq |= (t2 << 8) & 0xFF00; 60 | m_wDaqIndex = m_wDaq; 61 | m_byOdtIndex = getPid(); 62 | Mode = a_rDaqLayout.getDaq(m_wDaq).getMode(); 63 | currentOdtLayout = a_rDaqLayout.getDaq(m_wDaq).getOdt(getPid()); 64 | if (currentOdtLayout.isFirst() && (SetDaqListModePacket::ModeFieldBits::DTO_CTR&Mode)) 65 | { 66 | m_byCtr = a_rData[ptr]; 67 | ptr += 3; 68 | } 69 | else 70 | { 71 | ptr += 2; 72 | } 73 | } 74 | else if (IdentificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_WORD_ALIGNED) 75 | { 76 | m_byFill = a_rData[ptr]; 77 | uint16_t t1 = a_rData[ptr + 1]; 78 | uint16_t t2 = a_rData[ptr + 2]; 79 | m_wDaq = t1 & 0xFF; 80 | m_wDaq |= (t2 << 8) & 0xFF00; 81 | m_wDaqIndex = m_wDaq; 82 | m_byOdtIndex = getPid(); 83 | Mode = a_rDaqLayout.getDaq(m_wDaq).getMode(); 84 | ptr += 3; 85 | } 86 | 87 | 88 | if (Mode&SetDaqListModePacket::ModeFieldBits::DTO_CTR) 89 | { 90 | m_bIsCTRed = true; 91 | } 92 | 93 | if ((Mode&SetDaqListModePacket::ModeFieldBits::TIMESTAMP || TimestampFixed) && currentOdtLayout.isFirst()) 94 | { 95 | m_bIsTimestamped = true; 96 | if (TimestampSize == 1) 97 | { 98 | m_dwTimestamp = a_rData[ptr]; 99 | ptr++; 100 | } 101 | else if (TimestampSize == 2) 102 | { 103 | uint32_t t1, t2; 104 | t1 = a_rData[ptr]; 105 | t2 = a_rData[ptr + 1]; 106 | ptr += 2; 107 | m_dwTimestamp = t1 & 0xFF; 108 | m_dwTimestamp |= ((t2 << 8) & 0xFF00); 109 | } 110 | else if (TimestampSize == 4) 111 | { 112 | uint32_t t1, t2, t3, t4; 113 | t1 = a_rData[ptr]; 114 | t2 = a_rData[ptr + 1]; 115 | t3 = a_rData[ptr + 2]; 116 | t4 = a_rData[ptr + 3]; 117 | ptr += 4; 118 | m_dwTimestamp = t1 & 0xFF; 119 | m_dwTimestamp |= ((t2 << 8) & 0x0000FF00); 120 | m_dwTimestamp |= ((t3 << 16) & 0x00FF0000); 121 | m_dwTimestamp |= ((t4 << 24) & 0xFF000000); 122 | } 123 | } 124 | 125 | uint32_t dwDataLength = currentOdtLayout.getOdtSize(); 126 | m_dataField.resize(dwDataLength); 127 | for (uint32_t i = 0; i < dwDataLength; i++) 128 | { 129 | m_dataField[i] = a_rData[i + ptr]; 130 | } 131 | } 132 | 133 | DTO::~DTO() 134 | { 135 | 136 | } 137 | -------------------------------------------------------------------------------- /DTO.h: -------------------------------------------------------------------------------- 1 | #ifndef DTO_H 2 | #define DTO_H 3 | 4 | #include "XcpPacket.h" 5 | 6 | class DaqLayout; 7 | 8 | class DTO : public XcpPacket 9 | { 10 | public: 11 | DTO(); 12 | DTO(const QVector& a_rData, uint8_t TimestampSize, bool TimestampFixed, uint8_t IdentificationFieldType, DaqLayout& a_rDaqLayout); 13 | virtual ~DTO(); 14 | uint16_t getDaqField() {return m_wDaq;} 15 | uint8_t getCtrField() {return m_byCtr;} 16 | uint8_t getFillField() {return m_byFill;} 17 | uint32_t getTimestamp() {return m_dwTimestamp;} 18 | bool isTimestamped() {return m_bIsTimestamped;} 19 | bool isCTRed() {return m_bIsCTRed;} 20 | //Gets the index of the packet in the DAQList int the DAQLayout descriptor. It is already calculated, so no more transformations needed. (Absolute ODT, relative odt abs DAQ) 21 | uint16_t getDaqIndex() {return m_wDaqIndex;} 22 | //Gets the index of the packet in the ODTList int the DAQLayout descriptor. It is already calculated, so no more transformations needed. (Absolute ODT, relative odt abs DAQ) 23 | uint8_t getOdtIndex() {return m_byOdtIndex;} 24 | 25 | private: 26 | uint16_t m_wDaq; 27 | uint8_t m_byFill; //If in aligned DAQ mode, this is the ctr field 28 | uint8_t m_byCtr; 29 | uint32_t m_dwTimestamp; 30 | bool m_bIsTimestamped; 31 | bool m_bIsCTRed; 32 | uint16_t m_wDaqIndex; //Index of the packet in the DAQList DaqLayout descriptor 33 | uint8_t m_byOdtIndex; //Index of the packet in the ODTList in the DaqLayout descriptor 34 | 35 | }; 36 | 37 | #endif // DTO_H 38 | -------------------------------------------------------------------------------- /ErrorPacket.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKET_H 2 | #define ERRORPACKET_H 3 | 4 | #include "CTO.h" 5 | 6 | class ErrorPacket : public CTO 7 | { 8 | public: 9 | enum ErrorCodes 10 | { 11 | ERR_CMD_SYNCH = 0x00, 12 | ERR_CMD_BUSY = 0x10, 13 | ERR_DAQ_ACTIVE = 0x11, 14 | ERR_PGM_ACTIVE = 0x12, 15 | ERR_CMD_UNKNOWN = 0x20, 16 | ERR_CMD_SYNTAX = 0x21, 17 | ERR_OUT_OF_RANGE = 0x22, 18 | ERR_WRITE_PROTECTED = 0x23, 19 | ERR_ACCESS_DENIED = 0x24, 20 | ERR_ACCESS_LOCKED = 0x25, 21 | ERR_PAGE_NOT_VALID = 0x26, 22 | ERR_MODE_NOT_VALID = 0x27, 23 | ERR_SEGMENT_NOT_VALID = 0x28, 24 | ERR_SEQUENCE = 0x29, 25 | ERR_DAQ_CONFIG = 0x2A, 26 | ERR_MEMORY_OVERFLOW = 0x30, 27 | ERR_GENERIC = 0x31, 28 | ERR_VERIFY = 0x32, 29 | ERR_RESOURCE_TEMPORARY_NOT_ACCESSIBLE = 0x33, 30 | ERR_SUBCMD_UNKNOWN = 0x34, 31 | }; 32 | 33 | public: 34 | ErrorPacket() : CTO() 35 | { 36 | m_idField.resize(1); 37 | m_idField[0] = CTO::ERR; 38 | } 39 | virtual ~ErrorPacket() {} 40 | 41 | virtual void setErrorCode(uint8_t a_byErrorCode) 42 | { 43 | m_dataField[0] = a_byErrorCode; // Must available 44 | } 45 | 46 | virtual uint8_t getErrorCode() 47 | { 48 | return m_dataField[0]; // Must available 49 | } 50 | }; 51 | 52 | #endif // ERRORPACKET_H 53 | -------------------------------------------------------------------------------- /ErrorPacketAccessLocked.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketAccessLocked.h" 2 | 3 | ErrorPacketAccessLocked::ErrorPacketAccessLocked() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_ACCESS_LOCKED; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketAccessLocked.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETACCESSLOCKED_H 2 | #define ERRORPACKETACCESSLOCKED_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketAccessLocked : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketAccessLocked(); 10 | }; 11 | 12 | #endif // ERRORPACKETACCESSLOCKED_H 13 | -------------------------------------------------------------------------------- /ErrorPacketCmdUnknown.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketCmdUnknown.h" 2 | 3 | ErrorPacketCmdUnknown::ErrorPacketCmdUnknown() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_CMD_UNKNOWN; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketCmdUnknown.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETCMDUNKNOWN_H 2 | #define ERRORPACKETCMDUNKNOWN_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketCmdUnknown : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketCmdUnknown(); 10 | }; 11 | 12 | #endif // ERRORPACKETCMDUNKNOWN_H 13 | -------------------------------------------------------------------------------- /ErrorPacketMemoryOverflow.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketMemoryOverflow.h" 2 | 3 | ErrorPacketMemoryOverflow::ErrorPacketMemoryOverflow() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_MEMORY_OVERFLOW; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketMemoryOverflow.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETMEMORYOVERFLOW_H 2 | #define ERRORPACKETMEMORYOVERFLOW_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketMemoryOverflow : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketMemoryOverflow(); 10 | }; 11 | 12 | #endif // ERRORPACKETMEMORYOVERFLOW_H 13 | -------------------------------------------------------------------------------- /ErrorPacketOutOfRange.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketOutOfRange.h" 2 | 3 | ErrorPacketOutOfRange::ErrorPacketOutOfRange() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_OUT_OF_RANGE; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketOutOfRange.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETOUTOFRANGE_H 2 | #define ERRORPACKETOUTOFRANGE_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketOutOfRange : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketOutOfRange(); 10 | }; 11 | 12 | #endif // ERRORPACKETOUTOFRANGE_H 13 | -------------------------------------------------------------------------------- /ErrorPacketSequence.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketSequence.h" 2 | 3 | ErrorPacketSequence::ErrorPacketSequence() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_SEQUENCE; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketSequence.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETSEQUENCE_H 2 | #define ERRORPACKETSEQUENCE_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketSequence : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketSequence(); 10 | }; 11 | 12 | #endif // ERRORPACKETSEQUENCE_H 13 | -------------------------------------------------------------------------------- /ErrorPacketSync.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorPacketSync.h" 2 | 3 | ErrorPacketSync::ErrorPacketSync() 4 | : ErrorPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = ErrorCodes::ERR_CMD_SYNCH; 8 | } 9 | -------------------------------------------------------------------------------- /ErrorPacketSync.h: -------------------------------------------------------------------------------- 1 | #ifndef ERRORPACKETSYNC_H 2 | #define ERRORPACKETSYNC_H 3 | 4 | #include "ErrorPacket.h" 5 | 6 | class ErrorPacketSync : public ErrorPacket 7 | { 8 | public: 9 | ErrorPacketSync(); 10 | }; 11 | 12 | #endif // ERRORPACKETSYNC_H 13 | -------------------------------------------------------------------------------- /EventPacket.h: -------------------------------------------------------------------------------- 1 | #ifndef EVENTPACKET_H 2 | #define EVENTPACKET_H 3 | 4 | #include "CTO.h" 5 | 6 | class ErrorPacket : public CTO 7 | { 8 | public: 9 | ErrorPacket(); 10 | }; 11 | 12 | #endif // EVENTPACKET_H 13 | -------------------------------------------------------------------------------- /IncomingPacketHandler.cpp: -------------------------------------------------------------------------------- 1 | #include "IncomingPacketHandler.h" 2 | 3 | #include 4 | #include 5 | 6 | IncomingPacketHandler::IncomingPacketHandler(XcpMaster &a_rMaster) 7 | : m_rMaster(a_rMaster) 8 | { 9 | m_dwReceivedDtoCount = 0; 10 | resetSeedAndKey(); 11 | } 12 | 13 | IncomingPacketHandler::~IncomingPacketHandler() 14 | { 15 | 16 | } 17 | 18 | void IncomingPacketHandler::handle(XcpPacket *a_pPacket) 19 | { 20 | ResPacketConnect *pResPacketConnect = dynamic_cast(a_pPacket); 21 | if(pResPacketConnect) { 22 | handle(*pResPacketConnect); 23 | return; 24 | } 25 | ResPacketGetStatus *pResPacketGetStatus = dynamic_cast(a_pPacket); 26 | if(pResPacketGetStatus) { 27 | handle(*pResPacketGetStatus); 28 | return; 29 | } 30 | ResPacketUpload *pResPacketUpload = dynamic_cast(a_pPacket); 31 | if(pResPacketUpload) { 32 | handle(*pResPacketUpload); 33 | return; 34 | } 35 | StartStopDaqListPositiveResponse *pStartStopDaqListPositiveResponse = dynamic_cast(a_pPacket); 36 | if(pStartStopDaqListPositiveResponse) { 37 | handle(*pStartStopDaqListPositiveResponse); 38 | return; 39 | } 40 | ResPacketGetSeed *pResPacketGetSeed = dynamic_cast(a_pPacket); 41 | if(pResPacketGetSeed) { 42 | handle(*pResPacketGetSeed); 43 | return; 44 | } 45 | ResPacketUnlock *pResPacketUnlock = dynamic_cast(a_pPacket); 46 | if(pResPacketUnlock) { 47 | handle(*pResPacketUnlock); 48 | return; 49 | } 50 | GetDaqProcessorInfoResponse *pGetDaqProcessorInfoResponse = dynamic_cast(a_pPacket); 51 | if(pGetDaqProcessorInfoResponse) { 52 | handle(*pGetDaqProcessorInfoResponse); 53 | return; 54 | } 55 | // Put ResPacket after all RES packets 56 | ResPacket *pResPacket = dynamic_cast(a_pPacket); 57 | if(pResPacket) { 58 | handle(*pResPacket); 59 | } 60 | 61 | ErrorPacketSync *pErrorPacketSync = dynamic_cast(a_pPacket); 62 | if(pErrorPacketSync) { 63 | handle(*pErrorPacketSync); 64 | return; 65 | } 66 | 67 | ErrorPacketAccessLocked *pErrorPacketAccessLocked = dynamic_cast(a_pPacket); 68 | if(pErrorPacketAccessLocked) { 69 | handle(*pErrorPacketAccessLocked); 70 | return; 71 | } 72 | 73 | ErrorPacketOutOfRange *pErrorPacketOutOfRange = dynamic_cast(a_pPacket); 74 | if(pErrorPacketOutOfRange) { 75 | handle(*pErrorPacketOutOfRange); 76 | return; 77 | } 78 | 79 | ErrorPacketSequence *pErrorPacketSequence = dynamic_cast(a_pPacket); 80 | if(pErrorPacketSequence) { 81 | handle(*pErrorPacketSequence); 82 | return; 83 | } 84 | 85 | ErrorPacketMemoryOverflow *pErrorPacketMemoryOverflow = dynamic_cast(a_pPacket); 86 | if(pErrorPacketMemoryOverflow) { 87 | handle(*pErrorPacketMemoryOverflow); 88 | return; 89 | } 90 | 91 | ErrorPacketCmdUnknown *pErrorPacketCmdUnknown = dynamic_cast(a_pPacket); 92 | if(pErrorPacketCmdUnknown) { 93 | handle(*pErrorPacketCmdUnknown); 94 | return; 95 | } 96 | 97 | DTO *pDTO = dynamic_cast(a_pPacket); 98 | if(pDTO) { 99 | handle(*pDTO); 100 | return; 101 | } 102 | } 103 | 104 | void IncomingPacketHandler::handle(ResPacket &a_rPacket) 105 | { 106 | qDebug() << "General Ack packet received (or an unhandled packet format) PID: " << (int)a_rPacket.getPid(); 107 | } 108 | 109 | void IncomingPacketHandler::handle(ResPacketConnect &a_rPacket) 110 | { 111 | XcpMaster::SlaveProperties properties = m_rMaster.getSlaveProperties(); 112 | 113 | properties.CAL_PG = ((a_rPacket.getResource()&ResPacketConnect::ResourceParameterBits::CAL_PG) != 0); 114 | properties.DAQ = ((a_rPacket.getResource()&ResPacketConnect::ResourceParameterBits::DAQ) != 0); 115 | properties.PGM = ((a_rPacket.getResource()&ResPacketConnect::ResourceParameterBits::PGM) != 0); 116 | properties.STIM = ((a_rPacket.getResource()&ResPacketConnect::ResourceParameterBits::STIM) != 0); 117 | 118 | properties.byteOrder = ((a_rPacket.getCommModeBasic()&ResPacketConnect::CommModeBasicBits::BYTE_ORDER) != 0); 119 | properties.addressGranularity = ((a_rPacket.getCommModeBasic()&ResPacketConnect::CommModeBasicBits::ADDRESS_GRANULARITY_BOTH) >> 1); 120 | properties.slaveBlockMode = ((a_rPacket.getCommModeBasic()&ResPacketConnect::CommModeBasicBits::SLAVE_BLOCK_MODE) != 0); 121 | properties.optionalData = ((a_rPacket.getCommModeBasic()&ResPacketConnect::CommModeBasicBits::OPTIONAL) != 0); 122 | 123 | properties.maxCto = a_rPacket.getMaxCto(); 124 | properties.maxDto = a_rPacket.getMaxDto(!properties.byteOrder); //at this point we have already set the ByteOrder, true for little endian and false for big 125 | properties.transportLayerVersion = a_rPacket.getTransportLayerVersion(); 126 | properties.protocolLayerVersion = a_rPacket.getProtocolLayerVersion(); 127 | 128 | m_rMaster.setSlaveProperties(properties); //write back Slave properties to the Master 129 | 130 | qDebug() 131 | << "PID: " << (int)a_rPacket.getPid() 132 | << " | Resource:" << (int)a_rPacket.getResource() 133 | << " (CAL/PG: " << properties.CAL_PG << ", " 134 | << "DAQ: " << properties.DAQ << ", " 135 | << "STIM: " << properties.STIM << ", " 136 | << "PGM: " << properties.PGM << ") " 137 | << " | CommMode:" << (int)a_rPacket.getCommModeBasic() 138 | << " | MaxCTO:" << (int)properties.maxCto 139 | << " | MaxDTO:" << (int)properties.maxDto 140 | << " | ProtocolLayer version:" << (int)properties.protocolLayerVersion 141 | << " | Transport Layer version:" << (int)properties.transportLayerVersion << "\n"; 142 | 143 | qDebug() << "Byte order: " << properties.byteOrder << "\n"; 144 | qDebug() << "Address granularity: " << (int)properties.addressGranularity << "\n"; 145 | qDebug() << "Slave block mode: " << properties.slaveBlockMode << "\n"; 146 | qDebug() << "Optional data: " << properties.optionalData << "\n"; 147 | } 148 | 149 | void IncomingPacketHandler::handle(ResPacketGetStatus &a_rPacket) 150 | { 151 | qDebug() << "Receive get status resonse packet"; 152 | } 153 | 154 | void IncomingPacketHandler::handle(ErrorPacketSync &a_rPacket) 155 | { 156 | qDebug() << "Receive Sync Error packet"; 157 | } 158 | 159 | void IncomingPacketHandler::handle(ResPacketUpload &a_rPacket) 160 | { 161 | qDebug() << "Receive Upload packet"; 162 | 163 | m_rMaster.emitSendUploadByteArray(a_rPacket.getDataBytes()); 164 | } 165 | 166 | void IncomingPacketHandler::handle(ErrorPacketAccessLocked &a_rPacket) 167 | { 168 | qDebug() << "Error, Access Denied, Seed & Key is required"; 169 | } 170 | 171 | void IncomingPacketHandler::handle(ErrorPacketOutOfRange &a_rPacket) 172 | { 173 | qDebug() << a_rPacket.getErrorCode(); 174 | qDebug() << "Error: OUT_OF_RANGE"; 175 | } 176 | 177 | void IncomingPacketHandler::handle(ErrorPacketSequence &a_rPacket) 178 | { 179 | qDebug() << "Error: ERR_SEQUENCE"; 180 | } 181 | 182 | void IncomingPacketHandler::handle(ErrorPacketMemoryOverflow &a_rPacket) 183 | { 184 | qDebug() << "Error: Memory overflow"; 185 | } 186 | 187 | void IncomingPacketHandler::handle(StartStopDaqListPositiveResponse &a_rPacket) 188 | { 189 | if(m_rMaster.getDaqLayout().isInitialized()) { 190 | qDebug() << "Start/Stop Daq list response | FIRST PID: 0x" + QString::number(a_rPacket.getFirstPid(), 16); 191 | StartStopDaqListPacket* command = dynamic_cast(m_rMaster.getLastSentCmd()); 192 | if(command) { 193 | DaqLayout& dl = m_rMaster.getDaqLayout(); 194 | DAQ& d = dl.getDaq(command->getDaqListNumber(m_rMaster.getSlaveProperties().byteOrder == 0)); 195 | d.setFirstPid(a_rPacket.getFirstPid()); 196 | } 197 | else { 198 | qDebug() << "There was an error while setting the first PID on the DAQListDescriptor"; 199 | } 200 | } 201 | else { 202 | qDebug() << "Warning! Daq layout was not initialized before starting daq transfer."; 203 | } 204 | } 205 | 206 | void IncomingPacketHandler::handle(ResPacketGetSeed &a_rPacket) 207 | { 208 | qDebug() << "GetSeedResponse"; 209 | if (m_baSeed.size() == 0) //Mode 0 210 | { 211 | m_lRemainingSeedLength = a_rPacket.getLengthField(); 212 | } 213 | 214 | unsigned int nSeedPartSize = a_rPacket.getSeedPartSize(); 215 | for (unsigned int i = 0; i < nSeedPartSize; i++) 216 | { 217 | m_baSeed.push_back(a_rPacket.getSeedPart(i)); 218 | } 219 | 220 | m_dwProcessedSeedLength += nSeedPartSize; 221 | m_lRemainingSeedLength -= nSeedPartSize; 222 | CmdPacketGetSeed* pLastPacket = dynamic_cast(m_rMaster.getLastSentCmd()); 223 | if(m_lRemainingSeedLength == 0) { 224 | XCP_ComputeKeyFromSeedPtr_t ptr = m_rMaster.getComputeKeyPtr(); 225 | if(pLastPacket && ptr) { 226 | ptr(pLastPacket->getResource(), a_rPacket.getLengthField(), m_baSeed.data(), &m_byKeyLength, m_baKey.data()); 227 | m_baKey.resize(m_byKeyLength); 228 | } 229 | } 230 | } 231 | 232 | void IncomingPacketHandler::handle(ResPacketUnlock &a_rPacket) 233 | { 234 | qDebug() << "UnlockResponse packet"; 235 | XcpMaster::SlaveProperties properties = m_rMaster.getSlaveProperties(); 236 | properties.CAL_PG = ((a_rPacket.getCurrentResourceProtection()&ResPacketConnect::ResourceParameterBits::CAL_PG) != 0); 237 | properties.DAQ = ((a_rPacket.getCurrentResourceProtection()&ResPacketConnect::ResourceParameterBits::DAQ) != 0); 238 | properties.PGM = ((a_rPacket.getCurrentResourceProtection()&ResPacketConnect::ResourceParameterBits::PGM) != 0); 239 | properties.STIM = ((a_rPacket.getCurrentResourceProtection()&ResPacketConnect::ResourceParameterBits::STIM) != 0); 240 | m_rMaster.setSlaveProperties(properties); 241 | 242 | qDebug() << "(CAL/PG: " << properties.CAL_PG << ", " 243 | << "DAQ: " << properties.DAQ << ", " 244 | << "STIM: " << properties.STIM << ", " 245 | << "PGM: " << properties.PGM << ") \n"; 246 | resetSeedAndKey(); 247 | } 248 | 249 | void IncomingPacketHandler::handle(GetDaqProcessorInfoResponse &a_rPacket) 250 | { 251 | qDebug() << "GetDaqProcessorInfoResponsePacket\n"; 252 | XcpMaster::SlaveProperties properties = m_rMaster.getSlaveProperties(); 253 | properties.DaqProperties.configType = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::DAQ_CONFIG_TYPE) != 0); 254 | properties.DaqProperties.prescalerSupported = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::PRESCALER_SUPPORTED) != 0); 255 | properties.DaqProperties.resumeSupported = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::RESUME_SUPPORTED) != 0); 256 | properties.DaqProperties.bitStimSupported = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::BIT_STIM_SUPPORTED) != 0); 257 | properties.DaqProperties.timeStampSupported = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::TIMESTAMP_SUPPORTED) != 0); 258 | properties.DaqProperties.pidOffSupported = ((a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::PID_OFF_SUPPORTED) != 0); 259 | 260 | properties.DaqProperties.overloadIndicationMode = a_rPacket.getDaqProperties()&GetDaqProcessorInfoResponse::DaqPropertiesBits::OVERLOAD_INDICATION_MODE; 261 | properties.DaqProperties.optimisationType = a_rPacket.getDaqKeyByte()&GetDaqProcessorInfoResponse::DaqKeyByteBits::OPTIMISATION_TYPE; 262 | properties.DaqProperties.addressExtensionType = a_rPacket.getDaqKeyByte()&GetDaqProcessorInfoResponse::DaqKeyByteBits::ADDRESS_EXTENSION; 263 | properties.DaqProperties.identificationFieldType = a_rPacket.getDaqKeyByte()&GetDaqProcessorInfoResponse::DaqKeyByteBits::IDENTIFICATION_FIELD_TYPE; 264 | 265 | properties.DaqProperties.maxDaq = a_rPacket.getMaxDaq(properties.byteOrder==0); 266 | properties.DaqProperties.minDaq = a_rPacket.getMinDaq(); 267 | properties.DaqProperties.maxEventChannel = a_rPacket.getMaxEventChannel(properties.byteOrder==0); 268 | 269 | m_rMaster.setSlaveProperties(properties); 270 | 271 | qDebug() << "Config type: "; 272 | if (properties.DaqProperties.configType == 0) 273 | { 274 | qDebug() << "Static DAQ\n"; 275 | } 276 | else 277 | { 278 | qDebug() << "Dynamic DAQ\n"; 279 | } 280 | qDebug() << "Prescaler supported: " << properties.DaqProperties.prescalerSupported << "\n"; 281 | qDebug() << "Resume supported: " << properties.DaqProperties.resumeSupported << "\n"; 282 | qDebug() << "BitStim supported: " << properties.DaqProperties.bitStimSupported << "\n"; 283 | qDebug() << "Timestamp supported: " << properties.DaqProperties.timeStampSupported << "\n"; 284 | qDebug() << "Pid off supported: " << properties.DaqProperties.pidOffSupported << "\n"; 285 | qDebug() << "Overload indication mode: "; 286 | if (properties.DaqProperties.overloadIndicationMode == GetDaqProcessorInfoResponse::OverloadIndicationMode::EVENT_PACKET) 287 | { 288 | qDebug() << "Event Packet"; 289 | } 290 | else if (properties.DaqProperties.overloadIndicationMode == GetDaqProcessorInfoResponse::OverloadIndicationMode::MSB_PID) 291 | { 292 | qDebug() << "MSB PID"; 293 | } 294 | else if (properties.DaqProperties.overloadIndicationMode == GetDaqProcessorInfoResponse::OverloadIndicationMode::NO_INDICATION) 295 | { 296 | qDebug() << "No indication"; 297 | } 298 | qDebug() << "\n"; 299 | qDebug() << "Optimisation type: "; 300 | if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_DEFAULT) 301 | { 302 | qDebug() << "Default"; 303 | } 304 | else if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_ODT_TYPE_16) 305 | { 306 | qDebug() << "OM_ODT_TYPE_16"; 307 | } 308 | else if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_ODT_TYPE_32) 309 | { 310 | qDebug() << "OM_ODT_TYPE_32"; 311 | } 312 | else if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_ODT_TYPE_64) 313 | { 314 | qDebug() << "OM_ODT_TYPE_64"; 315 | } 316 | else if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_MAX_ENTRY_SIZE) 317 | { 318 | qDebug() << "OM_MAX_ENTRY_SIZE"; 319 | } 320 | else if (properties.DaqProperties.optimisationType == GetDaqProcessorInfoResponse::OptimisationMode::OM_ODT_TYPE_ALIGNMENT) 321 | { 322 | qDebug() << "OM_ODT_TYPE_ALIGNMENT"; 323 | } 324 | else 325 | { 326 | qDebug() << "Unknown mode: " << QString::number(properties.DaqProperties.optimisationType, 16); 327 | } 328 | qDebug() << "\n"; 329 | 330 | qDebug() << "Address Extension type: "; 331 | if (properties.DaqProperties.addressExtensionType == GetDaqProcessorInfoResponse::AddressExtensionType::CAN_BE_DIFFERENT) 332 | { 333 | qDebug() << "address extension can be different within one and the same ODT"; 334 | } 335 | else if (properties.DaqProperties.addressExtensionType == GetDaqProcessorInfoResponse::AddressExtensionType::SAME_FOR_ALL_ENTRIES_ODT) 336 | { 337 | qDebug() << "address extension to be the same for all entries within one ODT"; 338 | } 339 | else if (properties.DaqProperties.addressExtensionType == GetDaqProcessorInfoResponse::AddressExtensionType::SAME_FOR_ALL_ENTRIES_DAQ) 340 | { 341 | qDebug() << "address extension to be the same for all entries within one DAQ"; 342 | } 343 | else 344 | { 345 | qDebug() << "unknown: 0x" << QString::number(properties.DaqProperties.addressExtensionType, 16); 346 | } 347 | qDebug() << "\n"; 348 | qDebug() << "Identification field type: "; 349 | if (properties.DaqProperties.identificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::ABSOLUTE_ODT_NUMBER) 350 | { 351 | qDebug() << "Absolute ODT number"; 352 | } 353 | else if (properties.DaqProperties.identificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_BYTE) 354 | { 355 | qDebug() << "Relative ODT number, absolute DAQ list number (byte)"; 356 | } 357 | else if (properties.DaqProperties.identificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_WORD) 358 | { 359 | qDebug() << "Relative ODT number, absolute DAQ list number (word)"; 360 | } 361 | else if (properties.DaqProperties.identificationFieldType == GetDaqProcessorInfoResponse::IdentificationFieldType::RELATIVE_ODT_ABSOLUTE_DAQ_WORD_ALIGNED) 362 | { 363 | qDebug() << "Relative ODT number, absolute DAQ list number (word-aligned)"; 364 | } 365 | qDebug() << "\n"; 366 | qDebug() << "Max DAQ: " << (int)properties.DaqProperties.maxDaq<<"\n"; 367 | qDebug() << "Max Event channel: " << (int)properties.DaqProperties.maxEventChannel<<"\n"; 368 | qDebug() << "Min DAQ: " << (int)properties.DaqProperties.minDaq << "\n"; 369 | } 370 | 371 | void IncomingPacketHandler::handle(DTO &a_rPacket) 372 | { 373 | qDebug() << "DAQ packet:\n"; 374 | qDebug() << a_rPacket.getDaqField()<<"\n"; 375 | DaqLayout& daqlayout = m_rMaster.getDaqLayout(); 376 | qDebug() << a_rPacket.getDaqIndex(); 377 | DAQ& daq = daqlayout.getDaq(a_rPacket.getDaqIndex()); 378 | uint32_t dwLastTimestamp = m_rMaster.getDaqLayout().getDaq(a_rPacket.getDaqIndex()).getLastTimestamp(); 379 | if (a_rPacket.isTimestamped()) { 380 | qDebug() << a_rPacket.getTimestamp() << "\n"; 381 | daq.setLastTimestamp(a_rPacket.getTimestamp()); 382 | } 383 | 384 | ODT& odt = daq.getOdt(a_rPacket.getOdtIndex()); 385 | uint32_t dwByteIndex = 0; 386 | for (uint32_t i=0; i= 1+dwByteIndex) { 393 | int8_t value = (int8_t)a_rPacket.getDataBytes()[dwByteIndex]; 394 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 395 | } 396 | break; 397 | } 398 | case MeasurementDataTypes::eUint8: 399 | { 400 | if(a_rPacket.getDataBytes().size() >= 1+dwByteIndex) { 401 | uint8_t value = (uint8_t)a_rPacket.getDataBytes()[dwByteIndex]; 402 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 403 | } 404 | break; 405 | } 406 | case MeasurementDataTypes::eInt16: 407 | { 408 | if(a_rPacket.getDataBytes().size() >= 2+dwByteIndex) { 409 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 410 | int16_t value = ((((uint32_t)bytes[0])<<8)&0xFF00)+((((uint32_t)bytes[1])<<0)&0xFF); 411 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 412 | } 413 | break; 414 | } 415 | case MeasurementDataTypes::eUint16: 416 | { 417 | if(a_rPacket.getDataBytes().size() >= 2+dwByteIndex) { 418 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 419 | uint16_t value = ((((uint32_t)bytes[0])<<8)&0xFF00)+((((uint32_t)bytes[1])<<0)&0xFF); 420 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 421 | } 422 | break; 423 | } 424 | case MeasurementDataTypes::eInt32: 425 | { 426 | if(a_rPacket.getDataBytes().size() >= 4+dwByteIndex) { 427 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 428 | int32_t value = ((((uint32_t)bytes[0])<<24)&0xFF000000)+((((uint32_t)bytes[1])<<16)&0xFF0000)+((((uint32_t)bytes[2])<<8)&0xFF00)+((((uint32_t)bytes[3])<<0)&0xFF); 429 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 430 | } 431 | break; 432 | } 433 | case MeasurementDataTypes::eUint32: 434 | { 435 | if(a_rPacket.getDataBytes().size() >= 4+dwByteIndex) { 436 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 437 | uint32_t value = ((((uint32_t)bytes[0])<<24)&0xFF000000)+((((uint32_t)bytes[1])<<16)&0xFF0000)+((((uint32_t)bytes[2])<<8)&0xFF00)+((((uint32_t)bytes[3])<<0)&0xFF); 438 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 439 | } 440 | break; 441 | } 442 | case MeasurementDataTypes::eFloat: 443 | { 444 | if(a_rPacket.getDataBytes().size() >= 4+dwByteIndex) { 445 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 446 | uint32_t value = ((((uint32_t)bytes[0])<<24)&0xFF000000)+((((uint32_t)bytes[1])<<16)&0xFF0000)+((((uint32_t)bytes[2])<<8)&0xFF00)+((((uint32_t)bytes[3])<<0)&0xFF); 447 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)(*((float*)&value))); 448 | } 449 | break; 450 | } 451 | case MeasurementDataTypes::eInt64: 452 | { 453 | if(a_rPacket.getDataBytes().size() >= 8+dwByteIndex) { 454 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 455 | int64_t value = ((((uint64_t)bytes[0])<<56)&0xFF00000000000000) 456 | +((((uint64_t)bytes[1])<<48)&0xFF000000000000) 457 | +((((uint64_t)bytes[2])<<40)&0xFF0000000000) 458 | +((((uint64_t)bytes[3])<<32)&0xFF00000000) 459 | +((((uint64_t)bytes[4])<<24)&0xFF000000) 460 | +((((uint64_t)bytes[5])<<16)&0xFF0000) 461 | +((((uint64_t)bytes[6])<<8 )&0xFF00) 462 | +((((uint64_t)bytes[7])<<0 )&0xFF); 463 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 464 | } 465 | break; 466 | } 467 | case MeasurementDataTypes::eUint64: 468 | { 469 | if(a_rPacket.getDataBytes().size() >= 8+dwByteIndex) { 470 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 471 | uint64_t value = ((((uint64_t)bytes[0])<<56)&0xFF00000000000000) 472 | +((((uint64_t)bytes[1])<<48)&0xFF000000000000) 473 | +((((uint64_t)bytes[2])<<40)&0xFF0000000000) 474 | +((((uint64_t)bytes[3])<<32)&0xFF00000000) 475 | +((((uint64_t)bytes[4])<<24)&0xFF000000) 476 | +((((uint64_t)bytes[5])<<16)&0xFF0000) 477 | +((((uint64_t)bytes[6])<<8 )&0xFF00) 478 | +((((uint64_t)bytes[7])<<0 )&0xFF); 479 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (double)value); 480 | } 481 | break; 482 | } 483 | case MeasurementDataTypes::eDouble: 484 | { 485 | if(a_rPacket.getDataBytes().size() >= 8+dwByteIndex) { 486 | QVector bytes = a_rPacket.getDataBytes().mid(dwByteIndex); 487 | uint64_t value = ((((uint64_t)bytes[0])<<56)&0xFF00000000000000) 488 | +((((uint64_t)bytes[1])<<48)&0xFF000000000000) 489 | +((((uint64_t)bytes[2])<<40)&0xFF0000000000) 490 | +((((uint64_t)bytes[3])<<32)&0xFF00000000) 491 | +((((uint64_t)bytes[4])<<24)&0xFF000000) 492 | +((((uint64_t)bytes[5])<<16)&0xFF0000) 493 | +((((uint64_t)bytes[6])<<8 )&0xFF00) 494 | +((((uint64_t)bytes[7])<<0 )&0xFF); 495 | m_rMaster.emitSendOdtEntryValue(a_rPacket.getDaqIndex(), a_rPacket.getOdtIndex(), i, dwLastTimestamp, (*((double*)&value))); 496 | } 497 | break; 498 | } 499 | 500 | } 501 | dwByteIndex += odt.getEntry(i).getLength(); 502 | } 503 | 504 | m_dwReceivedDtoCount++; 505 | } 506 | 507 | void IncomingPacketHandler::handle(ErrorPacketCmdUnknown &a_rPacket) 508 | { 509 | qDebug() << "ERROR: Unknown command\n"; 510 | } 511 | 512 | const QVector &IncomingPacketHandler::getUnlockKey() const 513 | { 514 | return m_baKey; 515 | } 516 | 517 | void IncomingPacketHandler::resetSeedAndKey() 518 | { 519 | m_dwProcessedSeedLength = 0; 520 | m_lRemainingSeedLength = -1; 521 | m_baKey.clear(); 522 | m_baKey.resize(255); 523 | m_byKeyLength = 255; 524 | m_baSeed.clear(); 525 | } 526 | -------------------------------------------------------------------------------- /IncomingPacketHandler.h: -------------------------------------------------------------------------------- 1 | #ifndef INCOMINGPACKETHANDLER_H 2 | #define INCOMINGPACKETHANDLER_H 3 | 4 | #include 5 | #include "XcpMaster.h" 6 | #include "ResPacket.h" 7 | #include "ResPacketConnect.h" 8 | #include "ResPacketGetStatus.h" 9 | #include "ErrorPacketSync.h" 10 | #include "ResPacketUpload.h" 11 | #include "ErrorPacketAccessLocked.h" 12 | #include "ErrorPacketOutOfRange.h" 13 | #include "ErrorPacketSequence.h" 14 | #include "ErrorPacketMemoryOverflow.h" 15 | #include "DAQPackets.h" 16 | #include "ResPacketGetSeed.h" 17 | #include "ResPacketUnlock.h" 18 | #include "DAQPackets.h" 19 | #include "DTO.h" 20 | #include "ErrorPacketCmdUnknown.h" 21 | 22 | class IncomingPacketHandler 23 | { 24 | public: 25 | IncomingPacketHandler(XcpMaster &a_rMaster); 26 | ~IncomingPacketHandler(); 27 | 28 | void handle(XcpPacket *a_pPacket); 29 | 30 | void handle(ResPacket& a_rPacket); 31 | void handle(ResPacketConnect& a_rPacket); 32 | void handle(ResPacketGetStatus& a_rPacket); 33 | void handle(ErrorPacketSync& a_rPacket); 34 | void handle(ResPacketUpload& a_rPacket); 35 | void handle(ErrorPacketAccessLocked& a_rPacket); 36 | void handle(ErrorPacketOutOfRange& a_rPacket); 37 | void handle(ErrorPacketSequence& a_rPacket); 38 | void handle(ErrorPacketMemoryOverflow& a_rPacket); 39 | void handle(StartStopDaqListPositiveResponse& a_rPacket); 40 | void handle(ResPacketGetSeed& a_rPacket); 41 | void handle(ResPacketUnlock& a_rPacket); 42 | void handle(GetDaqProcessorInfoResponse& a_rPacket); 43 | void handle(DTO& a_rPacket); 44 | void handle(ErrorPacketCmdUnknown& a_rPacket); 45 | 46 | const QVector& getUnlockKey() const; 47 | 48 | private: 49 | void resetSeedAndKey(); 50 | 51 | private: 52 | XcpMaster &m_rMaster; 53 | QVector m_baKey; 54 | QVector m_baSeed; 55 | uint8_t m_byKeyLength; 56 | uint32_t m_dwProcessedSeedLength; 57 | int32_t m_lRemainingSeedLength; 58 | uint32_t m_dwReceivedDtoCount; 59 | }; 60 | 61 | #endif // INCOMINGPACKETHANDLER_H 62 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021 Steve Cai 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /MessageFactory.h: -------------------------------------------------------------------------------- 1 | #ifndef MESSAGEFACTORY_H 2 | #define MESSAGEFACTORY_H 3 | 4 | #include "XcpMessage.h" 5 | 6 | class MessageFactory 7 | { 8 | public: 9 | MessageFactory() {} 10 | virtual ~MessageFactory() {} 11 | 12 | virtual XcpMessage* createMessage(XcpPacket* a_pPacket) = 0; 13 | 14 | virtual QVector getPacketBytes(const QVector& a_rMsgBytes) = 0; 15 | }; 16 | 17 | #endif // MESSAGEFACTORY_H 18 | -------------------------------------------------------------------------------- /PacketFactory.cpp: -------------------------------------------------------------------------------- 1 | #include "PacketFactory.h" 2 | 3 | #include 4 | #include "DTO.h" 5 | #include "ResPacketConnect.h" 6 | #include "ResPacketGetSeed.h" 7 | #include "ResPacketGetStatus.h" 8 | #include "ResPacketUpload.h" 9 | #include "ResPacketUnlock.h" 10 | #include "DAQPackets.h" 11 | #include "ErrorPacket.h" 12 | #include "ErrorPacketSync.h" 13 | #include "ErrorPacketAccessLocked.h" 14 | #include "ErrorPacketCmdUnknown.h" 15 | #include "ErrorPacketMemoryOverflow.h" 16 | #include "ErrorPacketOutOfRange.h" 17 | #include "ErrorPacketSequence.h" 18 | #include "CmdPacketDisconnect.h" 19 | #include "CmdPacketGetStatus.h" 20 | #include "CmdPacketSync.h" 21 | #include "CmdPacketSetMta.h" 22 | #include "CmdPacketUpload.h" 23 | #include "CmdPacketUnlock.h" 24 | #include "CmdPacketShortUpload.h" 25 | #include "CmdPacketDownload.h" 26 | 27 | 28 | PacketFactory::PacketFactory(XcpMaster &a_rMaster) 29 | : m_rMaster(a_rMaster) 30 | { 31 | 32 | } 33 | 34 | PacketFactory::~PacketFactory() 35 | { 36 | 37 | } 38 | 39 | XcpPacket *PacketFactory::createConnectPacket(CmdPacketConnect::ConnectMode a_eMode) 40 | { 41 | return new CmdPacketConnect(a_eMode); 42 | } 43 | 44 | XcpPacket *PacketFactory::createDisconnectPacket() 45 | { 46 | return new CmdPacketDisconnect(); 47 | } 48 | 49 | XcpPacket *PacketFactory::createGetStatusPacket() 50 | { 51 | return new CmdPacketGetStatus(); 52 | } 53 | 54 | XcpPacket *PacketFactory::createSynchPacket() 55 | { 56 | return new CmdPacketSync(); 57 | } 58 | 59 | XcpPacket *PacketFactory::createSetMtaPacket(uint32_t a_dwAddress, uint8_t a_byExtension, bool a_bIsLittleEndian) 60 | { 61 | CmdPacketSetMta* pPacket = new CmdPacketSetMta(); 62 | pPacket->setAddress(a_dwAddress, a_bIsLittleEndian); 63 | pPacket->setAddressExtension(a_byExtension); 64 | return pPacket; 65 | } 66 | 67 | XcpPacket *PacketFactory::createUploadPacket(uint8_t a_byNumberOfElements) 68 | { 69 | return new CmdPacketUpload(a_byNumberOfElements); 70 | } 71 | 72 | XcpPacket *PacketFactory::createShortUploadPacket(uint8_t a_byNumberOfElements, uint32_t a_dwAddress, uint8_t a_byAddressExtension, bool a_bIsLittleEndian) 73 | { 74 | CmdPacketShortUpload* pPacket = new CmdPacketShortUpload(); 75 | pPacket->setAddress(a_dwAddress, a_bIsLittleEndian); 76 | pPacket->setAddressExtension(a_byAddressExtension); 77 | pPacket->setNumberOfDataElements(a_byNumberOfElements); 78 | return pPacket; 79 | } 80 | 81 | XcpPacket *PacketFactory::createFreeDaqPacket() 82 | { 83 | return new FreeDaqPacket(); 84 | } 85 | 86 | XcpPacket *PacketFactory::createAllocDaqPacket(uint16_t a_wDaqCount, bool a_bIsLittleEndian) 87 | { 88 | AllocDaqPacket* pPacket = new AllocDaqPacket(); 89 | pPacket->setDaqCount(a_wDaqCount, a_bIsLittleEndian); 90 | return pPacket; 91 | } 92 | 93 | XcpPacket *PacketFactory::createAllocOdtPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtCount, bool a_bIsLittleEndian) 94 | { 95 | AllocOdtPacket* pPacket = new AllocOdtPacket(); 96 | pPacket->setDaqListNumber(a_wDaqListNumber, a_bIsLittleEndian); 97 | pPacket->setOdtCount(a_byOdtCount); 98 | return pPacket; 99 | } 100 | 101 | XcpPacket *PacketFactory::createAllocOdtEntryPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntriesCount, bool a_bIsLittleEndian) 102 | { 103 | AllocOdtEntryPacket* pPacket = new AllocOdtEntryPacket(); 104 | pPacket->setDaqListNumber(a_wDaqListNumber, a_bIsLittleEndian); 105 | pPacket->setOdtNumber(a_byOdtNumber); 106 | pPacket->setOdtEntriesCount(a_byOdtEntriesCount); 107 | return pPacket; 108 | } 109 | 110 | XcpPacket *PacketFactory::createSetDaqPtrPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryNumber, bool a_bIsLittleEndian) 111 | { 112 | SetDaqPtrPacket* pPacket = new SetDaqPtrPacket(); 113 | pPacket->setDaqListNumber(a_wDaqListNumber, a_bIsLittleEndian); 114 | pPacket->setOdtNumber(a_byOdtNumber); 115 | pPacket->setOdtEntryNumber(a_byOdtEntryNumber); 116 | return pPacket; 117 | } 118 | 119 | XcpPacket *PacketFactory::createWriteDaqPacket(uint8_t a_byBitOffset, uint8_t a_bySize, uint8_t a_byAddressExtension, uint32_t a_dwAddress, bool a_bIsLittleEndian) 120 | { 121 | WriteDaqPacket* pPacket = new WriteDaqPacket(); 122 | pPacket->setBitOffset(a_byBitOffset); 123 | pPacket->setElementSize(a_bySize); 124 | pPacket->setAddressExtension(a_byAddressExtension); 125 | pPacket->setAddress(a_dwAddress, a_bIsLittleEndian); 126 | return pPacket; 127 | } 128 | 129 | XcpPacket *PacketFactory::createSetDaqListModePacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority, bool a_bIsLittleEndian) 130 | { 131 | return new SetDaqListModePacket(a_byMode, a_wDaqListNumber, a_wEventChannel, a_byPrescaler, a_byPriority, a_bIsLittleEndian); 132 | } 133 | 134 | XcpPacket *PacketFactory::createStartStopDaqListPacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 135 | { 136 | return new StartStopDaqListPacket(a_byMode, a_wDaqListNumber, a_bIsLittleEndian); 137 | } 138 | 139 | XcpPacket *PacketFactory::createStartStopSyncPacket(StartStopSynchPacket::Mode a_eMode) 140 | { 141 | return new StartStopSynchPacket(a_eMode); 142 | } 143 | 144 | XcpPacket *PacketFactory::createGetSeedPacket(CmdPacketGetSeed::Mode a_eMode, CmdPacketGetSeed::Resource a_eResource) 145 | { 146 | return new CmdPacketGetSeed(a_eMode, a_eResource); 147 | } 148 | 149 | XcpPacket *PacketFactory::createGetDaqProcessorInfoPacket() 150 | { 151 | return new GetDaqProcessorInfo(); 152 | } 153 | 154 | XcpPacket *PacketFactory::createClearDaqListPacket(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian) 155 | { 156 | return new ClearDAQListPacket(a_wDaqListNumber, a_bIsLittleEndian); 157 | } 158 | 159 | XcpPacket *PacketFactory::createDownloadPacket(uint8_t a_byNumOfDataElements, uint32_t a_dwData, bool a_bIsLittleEndian) 160 | { 161 | CmdPacketDownload* pPacket = new CmdPacketDownload(); 162 | pPacket->setNumberOfDataElements(a_byNumOfDataElements); 163 | pPacket->setDataElements(a_dwData, a_bIsLittleEndian); 164 | return pPacket; 165 | } 166 | 167 | QVector PacketFactory::createUnlockPackets(const QVector &a_rKey) 168 | { 169 | return CmdPacketUnlock::createUnlockPackets(a_rKey, m_rMaster.getSlaveProperties().maxCto); 170 | } 171 | 172 | XcpPacket *PacketFactory::deserializeIncomingFromSlave(const QVector &a_rData, CmdPacket *a_pLastSentCommand) 173 | { 174 | if (a_rData.size() > 0) { //Handle empty messages 175 | uint8_t byPid = a_rData[0]; 176 | switch (byPid) 177 | { 178 | case CTO::RES: 179 | return createResponsePacket(a_rData, a_pLastSentCommand); 180 | case CTO::EV: 181 | break; 182 | case CTO::ERR: 183 | return createErrorPacket(a_rData, a_pLastSentCommand); 184 | case CTO::SERV: 185 | break; 186 | default: 187 | if (byPid >= 0x00 && byPid <= 0xFB) 188 | { 189 | return deserializeIncomingDaq(a_rData); 190 | } 191 | break; 192 | } 193 | } 194 | return nullptr; 195 | } 196 | 197 | XcpPacket *PacketFactory::createResponsePacket(const QVector &a_rData, CmdPacket *a_pLastSentCommand) 198 | { 199 | if(a_pLastSentCommand) { 200 | uint8_t byLastCommandPID = a_pLastSentCommand->getPid(); 201 | switch (byLastCommandPID) 202 | { 203 | case CTO::CONNECT: 204 | return ResPacketConnect::deserialize(a_rData); 205 | case CTO::DISCONNECT: 206 | return new ResPacket(); 207 | case CTO::GET_STATUS: 208 | return ResPacketGetStatus::deserialize(a_rData); 209 | case CTO::UPLOAD: 210 | return ResPacketUpload::deserialize(a_rData, m_rMaster.getSlaveProperties().addressGranularity); 211 | case CTO::SHORT_UPLOAD: 212 | return ResPacketUpload::deserialize(a_rData, m_rMaster.getSlaveProperties().addressGranularity); 213 | case CTO::SET_MTA: 214 | return new ResPacket(); 215 | case CTO::START_STOP_DAQ_LIST: 216 | return StartStopDaqListPositiveResponse::deserialize(a_rData); 217 | case CTO::GET_SEED: 218 | return ResPacketGetSeed::deserialize(a_rData); 219 | case CTO::UNLOCK: 220 | return ResPacketUnlock::deserialize(a_rData); 221 | case CTO::GET_DAQ_PROCESSOR_INFO: 222 | return GetDaqProcessorInfoResponse::deserialize(a_rData); 223 | default: 224 | return new ResPacket(); 225 | } 226 | } 227 | qDebug() << "Internal error: Last sent command is a nullptr\a\n"; 228 | return nullptr; 229 | } 230 | 231 | XcpPacket *PacketFactory::createErrorPacket(const QVector &a_rData, CmdPacket *a_pLastSentCommand) 232 | { 233 | if(a_pLastSentCommand) { 234 | uint8_t byErrorCode = a_rData[1]; 235 | uint8_t byLastCommandPID = a_pLastSentCommand->getPid(); 236 | switch (byLastCommandPID) 237 | { 238 | case ErrorPacket::ErrorCodes::ERR_CMD_SYNCH: 239 | return new ErrorPacketSync(); 240 | case ErrorPacket::ErrorCodes::ERR_ACCESS_LOCKED: 241 | return new ErrorPacketAccessLocked(); 242 | case ErrorPacket::ErrorCodes::ERR_OUT_OF_RANGE: 243 | return new ErrorPacketOutOfRange(); 244 | case ErrorPacket::ErrorCodes::ERR_SEQUENCE: 245 | return new ErrorPacketSequence(); 246 | case ErrorPacket::ErrorCodes::ERR_MEMORY_OVERFLOW: 247 | return new ErrorPacketMemoryOverflow(); 248 | case ErrorPacket::ErrorCodes::ERR_CMD_UNKNOWN: 249 | return new ErrorPacketCmdUnknown(); 250 | default: 251 | qDebug() << "Deserialization error: Unhandled errorcode\n"; 252 | return nullptr; 253 | } 254 | } 255 | qDebug() << "Internal error: Last sent command is a nullptr\a\n"; 256 | return nullptr; 257 | } 258 | 259 | XcpPacket *PacketFactory::deserializeIncomingDaq(const QVector &a_rData) 260 | { 261 | return new DTO(a_rData, m_rMaster.getSlaveProperties().DaqProperties.timestampSize, false, m_rMaster.getSlaveProperties().DaqProperties.identificationFieldType, m_rMaster.getDaqLayout()); 262 | } 263 | -------------------------------------------------------------------------------- /PacketFactory.h: -------------------------------------------------------------------------------- 1 | #ifndef PACKETFACTORY_H 2 | #define PACKETFACTORY_H 3 | 4 | #include 5 | #include "XcpMaster.h" 6 | #include "XcpPacket.h" 7 | #include "CmdPacket.h" 8 | #include "CmdPacketConnect.h" 9 | #include "DAQPackets.h" 10 | #include "CmdPacketGetSeed.h" 11 | 12 | class PacketFactory 13 | { 14 | public: 15 | PacketFactory(XcpMaster &a_rMaster); 16 | virtual ~PacketFactory(); 17 | 18 | XcpPacket* createConnectPacket(CmdPacketConnect::ConnectMode a_eMode); 19 | XcpPacket* createDisconnectPacket(); 20 | XcpPacket* createGetStatusPacket(); 21 | XcpPacket* createSynchPacket(); 22 | XcpPacket* createSetMtaPacket(uint32_t a_dwAddress, uint8_t a_byExtension, bool a_bIsLittleEndian); 23 | XcpPacket* createUploadPacket(uint8_t a_byNumberOfElements); 24 | XcpPacket* createShortUploadPacket(uint8_t a_byNumberOfElements, uint32_t a_dwAddress, uint8_t a_byAddressExtension, bool a_bIsLittleEndian); 25 | XcpPacket* createFreeDaqPacket(); 26 | XcpPacket* createAllocDaqPacket(uint16_t a_wDaqCount, bool a_bIsLittleEndian); 27 | XcpPacket* createAllocOdtPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtCount, bool a_bIsLittleEndian); 28 | XcpPacket* createAllocOdtEntryPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntriesCount, bool a_bIsLittleEndian); 29 | XcpPacket* createSetDaqPtrPacket(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryNumber, bool a_bIsLittleEndian); 30 | XcpPacket* createWriteDaqPacket(uint8_t a_byBitOffset, uint8_t a_bySize, uint8_t a_byAddressExtension, uint32_t a_dwAddress, bool a_bIsLittleEndian); 31 | XcpPacket* createSetDaqListModePacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority, bool a_bIsLittleEndian); 32 | XcpPacket* createStartStopDaqListPacket(uint8_t a_byMode, uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 33 | XcpPacket* createStartStopSyncPacket(StartStopSynchPacket::Mode a_eMode); 34 | XcpPacket* createGetSeedPacket(CmdPacketGetSeed::Mode a_eMode, CmdPacketGetSeed::Resource a_eResource); 35 | XcpPacket* createGetDaqProcessorInfoPacket(); 36 | XcpPacket* createClearDaqListPacket(uint16_t a_wDaqListNumber, bool a_bIsLittleEndian); 37 | XcpPacket* createDownloadPacket(uint8_t a_byNumOfDataElements, uint32_t a_dwData, bool a_bIsLittleEndian); 38 | QVector createUnlockPackets(const QVector& a_rKey); 39 | 40 | 41 | XcpPacket* deserializeIncomingFromSlave(const QVector& a_rData, CmdPacket* a_pLastSentCommand); 42 | 43 | private: 44 | XcpPacket* createResponsePacket(const QVector& a_rData, CmdPacket* a_pLastSentCommand); 45 | XcpPacket* createErrorPacket(const QVector& a_rData, CmdPacket* a_pLastSentCommand); 46 | XcpPacket* deserializeIncomingDaq(const QVector& a_rData); 47 | 48 | private: 49 | XcpMaster &m_rMaster; 50 | }; 51 | 52 | #endif // PACKETFACTORY_H 53 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # XcpMaster 2 | The master node of XCP (Universal Measurement and Calibration Protocol) protocol. It'a Qt refactoring version referring to the [@robotjatek XCP repo](https://github.com/robotjatek/XCP). I made some modifications to fit my project. 3 | 4 | This repo is mainly for my [CCP (XCP on CAN) plugin](https://github.com/lotusczp/CCP-Plugin) of [Lobster](https://github.com/lotusczp/Lobster). And also XCP on Ethernet plugin. 5 | 6 | ## Todo 7 | - Need to support timestamp in the near future. 8 | 9 | -------------------------------------------------------------------------------- /ResPacket.h: -------------------------------------------------------------------------------- 1 | #ifndef RESPACKET_H 2 | #define RESPACKET_H 3 | 4 | #include "CTO.h" 5 | 6 | class ResPacket : public CTO 7 | { 8 | public: 9 | ResPacket() : CTO() 10 | { 11 | m_idField.resize(1); 12 | m_idField[0] = CTO::RES; 13 | } 14 | virtual ~ResPacket() {} 15 | }; 16 | 17 | #endif // RESPACKET_H 18 | -------------------------------------------------------------------------------- /ResPacketConnect.cpp: -------------------------------------------------------------------------------- 1 | #include "ResPacketConnect.h" 2 | 3 | ResPacketConnect::ResPacketConnect(uint8_t a_byResource, uint8_t a_byCommModeBasic, uint8_t a_byMaxCto, uint16_t a_wMaxDto, uint8_t a_byProtocolLayerVersion, uint8_t a_byTransportLayerVersion) 4 | : ResPacket () 5 | { 6 | m_dataField.resize(7); 7 | 8 | setResource(a_byResource); 9 | setCommModeBasic(a_byCommModeBasic); 10 | setMaxCto(a_byMaxCto); 11 | setMaxDto(a_wMaxDto); 12 | setProtocolLayerVersion(a_byProtocolLayerVersion); 13 | setTransportLayerVersion(a_byTransportLayerVersion); 14 | } 15 | 16 | uint8_t ResPacketConnect::getResource() 17 | { 18 | return m_dataField[0]; 19 | } 20 | 21 | uint8_t ResPacketConnect::getCommModeBasic() 22 | { 23 | return m_dataField[1]; 24 | } 25 | 26 | uint8_t ResPacketConnect::getMaxCto() 27 | { 28 | return m_dataField[2]; 29 | } 30 | 31 | uint16_t ResPacketConnect::getMaxDto(bool a_bIsLittleEndian) 32 | { 33 | if(a_bIsLittleEndian) { 34 | return (((uint16_t)m_dataField[4]) << 8) | m_dataField[3]; 35 | } 36 | else { 37 | //do byte-swap 38 | return (((uint16_t)m_dataField[3]) << 8) | m_dataField[4]; 39 | } 40 | } 41 | 42 | uint8_t ResPacketConnect::getProtocolLayerVersion() 43 | { 44 | return m_dataField[5]; 45 | } 46 | 47 | uint8_t ResPacketConnect::getTransportLayerVersion() 48 | { 49 | return m_dataField[6]; 50 | } 51 | 52 | void ResPacketConnect::setResource(uint8_t a_byResource) 53 | { 54 | m_dataField[0] = a_byResource; 55 | } 56 | 57 | void ResPacketConnect::setCommModeBasic(uint8_t a_byCommModeBasic) 58 | { 59 | m_dataField[1] = a_byCommModeBasic; 60 | } 61 | 62 | void ResPacketConnect::setMaxCto(uint8_t a_byCto) 63 | { 64 | m_dataField[2] = a_byCto; 65 | } 66 | 67 | void ResPacketConnect::setMaxDto(uint16_t a_wDto) 68 | { 69 | m_dataField[3] = a_wDto & 0xFF; 70 | m_dataField[4] = (a_wDto & 0xFF00) >> 8; 71 | } 72 | 73 | void ResPacketConnect::setProtocolLayerVersion(uint8_t a_byVersion) 74 | { 75 | m_dataField[5] = a_byVersion; 76 | } 77 | 78 | void ResPacketConnect::setTransportLayerVersion(uint8_t a_byVersion) 79 | { 80 | m_dataField[6] = a_byVersion; 81 | } 82 | 83 | ResPacketConnect *ResPacketConnect::deserialize(const QVector &a_rPacketBytes) 84 | { 85 | return new ResPacketConnect(a_rPacketBytes); 86 | } 87 | 88 | ResPacketConnect::ResPacketConnect(const QVector &a_rPacketBytes) 89 | : ResPacket () 90 | { 91 | m_dataField.resize(7); 92 | 93 | for (int i=0; i<7; i++) { 94 | m_dataField[i] = a_rPacketBytes[i+1]; 95 | } 96 | 97 | } 98 | -------------------------------------------------------------------------------- /ResPacketConnect.h: -------------------------------------------------------------------------------- 1 | #ifndef RESPACKETCONNECT_H 2 | #define RESPACKETCONNECT_H 3 | 4 | #include "ResPacket.h" 5 | 6 | class ResPacketConnect : public ResPacket 7 | { 8 | public: 9 | //If a resource is available the mandatory commands of this resource must be supported 10 | enum ResourceParameterBits 11 | { 12 | CAL_PG = 0x1, //Calibration and Paging: 0 = not available , 1 = avilable 13 | DAQ = 0x4, //DAQ list supported: 0 = not avaliable, 1 = available 14 | STIM = 0x8, //STIM - Data stimulation of a daq list: 0 = not available, 1 = available 15 | PGM = 0x10, //Programming: 0 = flash programming not available, 1 = available 16 | }; 17 | 18 | enum CommModeBasicBits 19 | { 20 | BYTE_ORDER = 0x1, //Byte order for multibyte parameters. 0 = Little endian (Intel format), 1 = Big Endian (Motorola format) 21 | ADDRESS_GRANULARITY_0 = 0x2, //The address granularity indicates the size of an element 22 | ADDRESS_GRANULARITY_1 = 0x4, //The address granularity indicates the size of an element: 00-byte, 01-word, 10-DWORD, 11-reserved 23 | ADDRESS_GRANULARITY_BOTH = 0x6, 24 | SLAVE_BLOCK_MODE = 0x40, //Inidicates if slave block mode is available 25 | OPTIONAL = 0x80, //The OPTIONAL flag indicates whether additional information on supported types of Communication mode is available.The master can get that additional information with GET_COMM_MODE_INFO. 26 | }; 27 | 28 | public: 29 | ResPacketConnect(uint8_t a_byResource, uint8_t a_byCommModeBasic, uint8_t a_byMaxCto, uint16_t a_wMaxDto, uint8_t a_byProtocolLayerVersion, uint8_t a_byTransportLayerVersion); 30 | uint8_t getResource(); 31 | uint8_t getCommModeBasic(); 32 | uint8_t getMaxCto(); 33 | uint16_t getMaxDto(bool a_bIsLittleEndian); 34 | uint8_t getProtocolLayerVersion(); 35 | uint8_t getTransportLayerVersion(); 36 | void setResource(uint8_t a_byResource); 37 | void setCommModeBasic(uint8_t a_byCommModeBasic); 38 | void setMaxCto(uint8_t a_byCto); 39 | void setMaxDto(uint16_t a_wDto); 40 | void setProtocolLayerVersion(uint8_t a_byVersion); 41 | void setTransportLayerVersion(uint8_t a_byVersion); 42 | 43 | static ResPacketConnect* deserialize(const QVector& a_rPacketBytes); 44 | 45 | private: 46 | ResPacketConnect(const QVector& a_rPacketBytes); 47 | }; 48 | 49 | #endif // RESPACKETCONNECT_H 50 | -------------------------------------------------------------------------------- /ResPacketGetSeed.cpp: -------------------------------------------------------------------------------- 1 | #include "ResPacketGetSeed.h" 2 | 3 | 4 | ResPacketGetSeed::ResPacketGetSeed(const QVector &a_rPacketBytes) 5 | : ResPacket() 6 | { 7 | int iDataLength = a_rPacketBytes.size() - 1; 8 | m_dataField.resize(iDataLength); 9 | for(int i = 0; i &a_rPacketBytes) 30 | { 31 | return new ResPacketGetSeed(a_rPacketBytes); 32 | } 33 | -------------------------------------------------------------------------------- /ResPacketGetSeed.h: -------------------------------------------------------------------------------- 1 | #ifndef RESPACKETGETSEED_H 2 | #define RESPACKETGETSEED_H 3 | 4 | #include 5 | #include "ResPacket.h" 6 | 7 | class ResPacketGetSeed : public ResPacket 8 | { 9 | public: 10 | ResPacketGetSeed(const QVector& a_rPacketBytes); 11 | uint8_t getLengthField(); 12 | uint8_t getSeedPart(uint8_t a_byElement); 13 | uint8_t getSeedPartSize(); 14 | static ResPacketGetSeed* deserialize(const QVector& a_rPacketBytes); 15 | }; 16 | 17 | #endif // RESPACKETGETSEED_H 18 | -------------------------------------------------------------------------------- /ResPacketGetStatus.cpp: -------------------------------------------------------------------------------- 1 | #include "ResPacketGetStatus.h" 2 | 3 | ResPacketGetStatus::ResPacketGetStatus(const QVector &a_rPacketBytes) 4 | : ResPacket() 5 | { 6 | m_dataField.resize(5); 7 | for(int i=0; i<5; i++) { 8 | m_dataField[i] = a_rPacketBytes[i+1]; 9 | } 10 | } 11 | 12 | ResPacketGetStatus *ResPacketGetStatus::deserialize(const QVector &a_rPacketBytes) 13 | { 14 | return new ResPacketGetStatus(a_rPacketBytes); 15 | } 16 | 17 | uint8_t ResPacketGetStatus::getCurrentSessionStatus() 18 | { 19 | return m_dataField[0]; 20 | } 21 | 22 | void ResPacketGetStatus::setCurrentSessionStatus(uint8_t a_bySessionStatus) 23 | { 24 | m_dataField[0] = a_bySessionStatus; 25 | } 26 | 27 | uint8_t ResPacketGetStatus::getCurrentResourceProtection() 28 | { 29 | return m_dataField[1]; 30 | } 31 | 32 | void ResPacketGetStatus::setCurrentResourceProtection(uint8_t a_byResourceProtection) 33 | { 34 | m_dataField[0] = a_byResourceProtection; 35 | } 36 | 37 | uint8_t ResPacketGetStatus::getStateNumber() 38 | { 39 | return m_dataField[2]; 40 | } 41 | 42 | void ResPacketGetStatus::setStateNumber(uint8_t a_byState) 43 | { 44 | m_dataField[2] = a_byState; 45 | } 46 | 47 | uint16_t ResPacketGetStatus::getSessionConfigurationId(bool a_bIsLittleEndian) 48 | { 49 | if(a_bIsLittleEndian) { 50 | return (((uint16_t)m_dataField[4]) << 8) | m_dataField[3]; 51 | } 52 | else { 53 | //do byte-swap 54 | return (((uint16_t)m_dataField[3]) << 8) | m_dataField[4]; 55 | } 56 | } 57 | 58 | void ResPacketGetStatus::setSessionConfigurationId(uint16_t a_wSessionConfigurationId, bool a_bIsLittleEndian) 59 | { 60 | uint8_t i1, i2; 61 | i1 = a_wSessionConfigurationId & 0xFF; 62 | i2 = (a_wSessionConfigurationId >> 8) & 0xFF; 63 | 64 | if(a_bIsLittleEndian) { 65 | m_dataField[3] = i1; 66 | m_dataField[4] = i2; 67 | } 68 | else { 69 | m_dataField[3] = i2; 70 | m_dataField[4] = i1; 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /ResPacketGetStatus.h: -------------------------------------------------------------------------------- 1 | #ifndef RESPACKETGETSTATUS_H 2 | #define RESPACKETGETSTATUS_H 3 | 4 | #include 5 | #include "ResPacket.h" 6 | 7 | class ResPacketGetStatus : public ResPacket 8 | { 9 | public: 10 | enum CurrentSessionStatusBits 11 | { 12 | STORE_CAL_REQ = 0x01, //Pending request to store data into non-volatile memory 13 | STORE_DAQ_REQ = 0x04, //Pending request to save daq list into non-volatile memory 14 | CLEAR_DAQ_REQ = 0x08, //pending request to clear all daq list in non-volatile memory 15 | DAQ_RUNNING = 0x40, //at least one daq list has been started and is in running mode 16 | RESUME = 0x80, //slave is in resume mode 17 | }; 18 | 19 | enum CurrentResourceProtectionBits //The given resorce is protected with Seed&key. If a resource is protected, an attempt to exectue a command on it before a successful GET_SEED/UNLOCK sequence will result in ERR_ACCESS_LOCKED 20 | { 21 | CAL_PG = 0x01, 22 | DAQ = 0x04, 23 | STIM = 0x08, 24 | PGM = 0x10, 25 | }; 26 | 27 | public: 28 | ResPacketGetStatus(const QVector& a_rPacketBytes); 29 | 30 | static ResPacketGetStatus* deserialize(const QVector& a_rPacketBytes); 31 | 32 | uint8_t getCurrentSessionStatus(); 33 | void setCurrentSessionStatus(uint8_t a_bySessionStatus); 34 | 35 | uint8_t getCurrentResourceProtection(); 36 | void setCurrentResourceProtection(uint8_t a_byResourceProtection); 37 | 38 | uint8_t getStateNumber(); //If the XCP slave supports ECU_STATES the current STATE_NUMBER will be given to the XCP master in the response of GET_STATUS. 39 | void setStateNumber(uint8_t a_byState); 40 | 41 | uint16_t getSessionConfigurationId(bool a_bIsLittleEndian); 42 | void setSessionConfigurationId(uint16_t a_wSessionConfigurationId, bool a_bIsLittleEndian); 43 | }; 44 | 45 | #endif // RESPACKETGETSTATUS_H 46 | -------------------------------------------------------------------------------- /ResPacketUnlock.cpp: -------------------------------------------------------------------------------- 1 | #include "ResPacketUnlock.h" 2 | 3 | ResPacketUnlock::ResPacketUnlock(const QVector &a_rPacketBytes) 4 | : ResPacket() 5 | { 6 | m_dataField.resize(1); 7 | m_dataField[0] = a_rPacketBytes[1]; 8 | } 9 | 10 | void ResPacketUnlock::setCurrentResourceProtection(uint8_t a_byCurrentProection) 11 | { 12 | m_dataField[0] = a_byCurrentProection; 13 | } 14 | 15 | uint8_t ResPacketUnlock::getCurrentResourceProtection() 16 | { 17 | return m_dataField[0]; 18 | } 19 | 20 | ResPacketUnlock *ResPacketUnlock::deserialize(const QVector &a_rPacketBytes) 21 | { 22 | return new ResPacketUnlock(a_rPacketBytes); 23 | } 24 | -------------------------------------------------------------------------------- /ResPacketUnlock.h: -------------------------------------------------------------------------------- 1 | #ifndef RESPACKETUNLOCK_H 2 | #define RESPACKETUNLOCK_H 3 | 4 | #include 5 | #include "ResPacket.h" 6 | 7 | class ResPacketUnlock : public ResPacket 8 | { 9 | public: 10 | ResPacketUnlock(const QVector& a_rPacketBytes); 11 | 12 | void setCurrentResourceProtection(uint8_t a_byCurrentProection); 13 | uint8_t getCurrentResourceProtection(); 14 | 15 | static ResPacketUnlock* deserialize(const QVector& a_rPacketBytes); 16 | 17 | }; 18 | 19 | #endif // RESPACKETUNLOCK_H 20 | -------------------------------------------------------------------------------- /ResPacketUpload.cpp: -------------------------------------------------------------------------------- 1 | #include "ResPacketUpload.h" 2 | 3 | ResPacketUpload *ResPacketUpload::deserialize(const QVector &a_rPacketBytes, uint8_t a_byAG) 4 | { 5 | return new ResPacketUpload(a_rPacketBytes, a_byAG); 6 | } 7 | 8 | ResPacketUpload::ResPacketUpload(const QVector &a_rPacketBytes, uint8_t a_byAG) 9 | { 10 | int iDataLength = a_rPacketBytes.size() - 1; // size - PID fieldsize 11 | m_dataField.resize(iDataLength); 12 | for(int i=0; i 5 | #include "ResPacket.h" 6 | 7 | class ResPacketUpload : public ResPacket 8 | { 9 | public: 10 | static ResPacketUpload* deserialize(const QVector& a_rPacketBytes, uint8_t a_byAG); 11 | 12 | uint8_t getNumberOfElements() {return m_byNumberOfElements;} 13 | 14 | private: 15 | ResPacketUpload(const QVector& a_rPacketBytes, uint8_t a_byAG); 16 | 17 | private: 18 | uint8_t m_byElementSizeInBytes; 19 | uint8_t m_byNumberOfElements; 20 | }; 21 | 22 | #endif // RESPACKETUPLOAD_H 23 | -------------------------------------------------------------------------------- /XcpHeader.h: -------------------------------------------------------------------------------- 1 | #ifndef XCPHEADER_H 2 | #define XCPHEADER_H 3 | 4 | #include 5 | 6 | class XcpHeader 7 | { 8 | public: 9 | XcpHeader () {} 10 | virtual ~XcpHeader() {} 11 | virtual QVector getByteArray() = 0; 12 | }; 13 | 14 | #endif // XCPHEADER_H 15 | -------------------------------------------------------------------------------- /XcpMaster.cpp: -------------------------------------------------------------------------------- 1 | #include "XcpMaster.h" 2 | #include 3 | #include "IncomingPacketHandler.h" 4 | #include "PacketFactory.h" 5 | #include "transport/can/CanMessageFactory.h" 6 | #include "transport/ethernet/EthernetMessageFactory.h" 7 | 8 | XcpMaster::XcpMaster(XcpMaster::TransportLayer a_eTransportlayer) 9 | { 10 | switch (a_eTransportlayer) 11 | { 12 | case TransportLayer::ETHERNET: 13 | m_pMessageFactory = new EthernetMessageFactory(); 14 | break; 15 | case TransportLayer::CAN: 16 | m_pMessageFactory = new CanMessageFactory(); 17 | break; 18 | default: 19 | m_pMessageFactory = nullptr; 20 | break; 21 | } 22 | 23 | m_pPacketFactory = new PacketFactory(*this); 24 | m_pIncomingPacketHandler = new IncomingPacketHandler(*this); 25 | 26 | m_getAvailablePrivileges = nullptr; 27 | m_computeKeyFromSeed = nullptr; 28 | } 29 | 30 | XcpMaster::~XcpMaster() 31 | { 32 | qDeleteAll(m_queueSentCommand); 33 | m_queueSentCommand.clear(); 34 | 35 | delete m_pIncomingPacketHandler; 36 | delete m_pPacketFactory; 37 | delete m_pMessageFactory; 38 | } 39 | 40 | const XcpMaster::SlaveProperties &XcpMaster::getSlaveProperties() const 41 | { 42 | return m_slaveProperties; 43 | } 44 | 45 | void XcpMaster::setSlaveProperties(const XcpMaster::SlaveProperties &a_rProperties) 46 | { 47 | m_slaveProperties = a_rProperties; 48 | } 49 | 50 | XcpMessage *XcpMaster::createConnectMessage(CmdPacketConnect::ConnectMode a_eMode) 51 | { 52 | return m_pMessageFactory->createMessage(m_pPacketFactory->createConnectPacket(a_eMode)); 53 | } 54 | 55 | XcpMessage *XcpMaster::createDisconnectMessage() 56 | { 57 | return m_pMessageFactory->createMessage(m_pPacketFactory->createDisconnectPacket()); 58 | } 59 | 60 | XcpMessage *XcpMaster::createSynchMessage() 61 | { 62 | return m_pMessageFactory->createMessage(m_pPacketFactory->createSynchPacket()); 63 | } 64 | 65 | XcpMessage *XcpMaster::createSetMtaMessage(uint32_t a_dwAddress, uint8_t a_byExtension) 66 | { 67 | return m_pMessageFactory->createMessage(m_pPacketFactory->createSetMtaPacket(a_dwAddress, a_byExtension, m_slaveProperties.byteOrder==0)); 68 | } 69 | 70 | XcpMessage *XcpMaster::createUploadMessage(uint8_t a_byNumberOfElements) 71 | { 72 | return m_pMessageFactory->createMessage(m_pPacketFactory->createUploadPacket(a_byNumberOfElements)); 73 | } 74 | 75 | XcpMessage *XcpMaster::createShortUploadMessage(uint8_t a_byNumberOfElements, uint32_t a_dwAddress, uint8_t a_byAddressExtension) 76 | { 77 | return m_pMessageFactory->createMessage(m_pPacketFactory->createShortUploadPacket(a_byNumberOfElements, a_dwAddress, a_byAddressExtension, m_slaveProperties.byteOrder==0)); 78 | } 79 | 80 | XcpMessage *XcpMaster::createFreeDaqMessage() 81 | { 82 | return m_pMessageFactory->createMessage(m_pPacketFactory->createFreeDaqPacket()); 83 | } 84 | 85 | XcpMessage *XcpMaster::createAllocDaqMessage(uint16_t a_wDaqCount) 86 | { 87 | return m_pMessageFactory->createMessage(m_pPacketFactory->createAllocDaqPacket(a_wDaqCount, m_slaveProperties.byteOrder==0)); 88 | } 89 | 90 | XcpMessage *XcpMaster::createAllocOdtMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtCount) 91 | { 92 | return m_pMessageFactory->createMessage(m_pPacketFactory->createAllocOdtPacket(a_wDaqListNumber, a_byOdtCount, m_slaveProperties.byteOrder==0)); 93 | } 94 | 95 | XcpMessage *XcpMaster::createAllocOdtEntryMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryCount) 96 | { 97 | return m_pMessageFactory->createMessage(m_pPacketFactory->createAllocOdtEntryPacket(a_wDaqListNumber, a_byOdtNumber, a_byOdtEntryCount, m_slaveProperties.byteOrder==0)); 98 | } 99 | 100 | XcpMessage *XcpMaster::createSetDaqPtrMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryNumber) 101 | { 102 | return m_pMessageFactory->createMessage(m_pPacketFactory->createSetDaqPtrPacket(a_wDaqListNumber, a_byOdtNumber, a_byOdtEntryNumber, m_slaveProperties.byteOrder==0)); 103 | } 104 | 105 | XcpMessage *XcpMaster::createWriteDaqMessage(uint8_t a_byBitOffset, uint8_t a_byElementSize, uint8_t a_byAddressExtension, uint32_t a_dwAddress) 106 | { 107 | return m_pMessageFactory->createMessage(m_pPacketFactory->createWriteDaqPacket(a_byBitOffset, a_byElementSize, a_byAddressExtension, a_dwAddress, m_slaveProperties.byteOrder==0)); 108 | } 109 | 110 | XcpMessage *XcpMaster::createSetDaqListModeMessage(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority) 111 | { 112 | return m_pMessageFactory->createMessage(m_pPacketFactory->createSetDaqListModePacket(a_byMode, a_wDaqListNumber, a_wEventChannel, a_byPrescaler, a_byPriority, m_slaveProperties.byteOrder==0)); 113 | } 114 | 115 | XcpMessage *XcpMaster::createStartStopDaqListMessage(StartStopDaqListPacket::Mode a_eMode, uint16_t a_wDaqListNumber) 116 | { 117 | return m_pMessageFactory->createMessage(m_pPacketFactory->createStartStopDaqListPacket(a_eMode, a_wDaqListNumber, m_slaveProperties.byteOrder==0)); 118 | } 119 | 120 | XcpMessage *XcpMaster::createStartStopSynchMessage(StartStopSynchPacket::Mode a_eMode) 121 | { 122 | return m_pMessageFactory->createMessage(m_pPacketFactory->createStartStopSyncPacket(a_eMode)); 123 | } 124 | 125 | XcpMessage *XcpMaster::createGetSeedMessage(CmdPacketGetSeed::Mode a_eMode, CmdPacketGetSeed::Resource a_eResource) 126 | { 127 | return m_pMessageFactory->createMessage(m_pPacketFactory->createGetSeedPacket(a_eMode, a_eResource)); 128 | } 129 | 130 | XcpMessage *XcpMaster::createGetDaqProcessorInfoMessage() 131 | { 132 | return m_pMessageFactory->createMessage(m_pPacketFactory->createGetDaqProcessorInfoPacket()); 133 | } 134 | 135 | XcpMessage *XcpMaster::createClearDaqListMessage(uint16_t a_wDaqListNumber) 136 | { 137 | return m_pMessageFactory->createMessage(m_pPacketFactory->createClearDaqListPacket(a_wDaqListNumber, m_slaveProperties.byteOrder==0)); 138 | } 139 | 140 | XcpMessage *XcpMaster::createDownloadMessage(uint8_t a_byNumOfDataElements, uint32_t a_dwData) 141 | { 142 | return m_pMessageFactory->createMessage(m_pPacketFactory->createDownloadPacket(a_byNumOfDataElements, a_dwData, m_slaveProperties.byteOrder==0)); 143 | } 144 | 145 | QVector XcpMaster::createUnlockMessages() 146 | { 147 | QVector retval; 148 | QVector packets = m_pPacketFactory->createUnlockPackets(m_pIncomingPacketHandler->getUnlockKey()); 149 | foreach(XcpPacket* pPacket, packets) { 150 | retval.append(m_pMessageFactory->createMessage(pPacket)); 151 | } 152 | 153 | return retval; 154 | } 155 | 156 | void XcpMaster::deserializeMessage(const QVector &a_rData) 157 | { 158 | CmdPacket* LastCommand = nullptr; 159 | if (m_queueSentCommand.size() > 0) 160 | { 161 | LastCommand = m_queueSentCommand.front(); 162 | } 163 | 164 | QVector packetBytes = m_pMessageFactory->getPacketBytes(a_rData); 165 | 166 | XcpPacket* pPacket = m_pPacketFactory->deserializeIncomingFromSlave(packetBytes, LastCommand); 167 | 168 | if(pPacket) { 169 | m_pIncomingPacketHandler->handle(pPacket); 170 | qDebug() << "---------------------------------------------\n"; 171 | if (m_queueSentCommand.size() > 0 && pPacket->getPid() > 0xFB) //do not pop if this was a DAQ packet 172 | { 173 | CmdPacket *pCmdPacket = m_queueSentCommand[0]; 174 | m_queueSentCommand.pop_front(); 175 | delete pCmdPacket; 176 | } 177 | delete pPacket; 178 | return; 179 | } 180 | qDebug() << "couldnt deserialise the message\n"; 181 | qDebug() << "---------------------------------------------\n"; 182 | if (m_queueSentCommand.size() > 0) 183 | { 184 | CmdPacket *pCmdPacket = m_queueSentCommand[0]; 185 | m_queueSentCommand.pop_front(); 186 | delete pCmdPacket; 187 | } 188 | 189 | return; 190 | } 191 | 192 | DaqLayout &XcpMaster::getDaqLayout() 193 | { 194 | return m_DaqLayout; 195 | } 196 | 197 | void XcpMaster::setDaqLayout(const DaqLayout &a_rDaqLayout) 198 | { 199 | m_DaqLayout = a_rDaqLayout; 200 | } 201 | 202 | void XcpMaster::handleSentMessage(XcpMessage *a_pMessage) 203 | { 204 | CmdPacket* pToAdd = dynamic_cast(a_pMessage->getPacket()); 205 | if(pToAdd) { 206 | m_queueSentCommand.push_back(pToAdd); 207 | } 208 | else { 209 | // Won't need any more, delete it 210 | if(a_pMessage) delete a_pMessage; 211 | } 212 | } 213 | 214 | CmdPacket *XcpMaster::getLastSentCmd() 215 | { 216 | if(m_queueSentCommand.isEmpty()) return nullptr; 217 | return m_queueSentCommand.front(); 218 | } 219 | 220 | bool XcpMaster::isCommandQueueEmpty() const 221 | { 222 | return m_queueSentCommand.isEmpty(); 223 | } 224 | 225 | void XcpMaster::emitSendUploadByteArray(const QVector &a_rBytes) 226 | { 227 | emit sendUploadByteArray(a_rBytes); 228 | } 229 | 230 | void XcpMaster::emitSendOdtEntryValue(uint16_t a_wDaqIndex, uint8_t a_byOdtIndex, uint32_t a_dwOdtEntryIndex, qint64 a_timestamp, double value) 231 | { 232 | emit sendOdtEntryValue(a_wDaqIndex, a_byOdtIndex, a_dwOdtEntryIndex, a_timestamp, value); 233 | } 234 | 235 | void XcpMaster::setSeedAndKeyFunctions(XCP_GetAvailablePrivilegesPtr_t GetAvailablePrivilegesPtr, XCP_ComputeKeyFromSeedPtr_t ComputeKeyPtr) 236 | { 237 | m_getAvailablePrivileges = GetAvailablePrivilegesPtr; 238 | m_computeKeyFromSeed = ComputeKeyPtr; 239 | } 240 | 241 | XCP_ComputeKeyFromSeedPtr_t XcpMaster::getComputeKeyPtr() 242 | { 243 | return m_computeKeyFromSeed; 244 | } 245 | 246 | XCP_GetAvailablePrivilegesPtr_t XcpMaster::getAvailablePrivilegesPtr() 247 | { 248 | return m_getAvailablePrivileges; 249 | } 250 | -------------------------------------------------------------------------------- /XcpMaster.h: -------------------------------------------------------------------------------- 1 | #ifndef XCPMASTER_H 2 | #define XCPMASTER_H 3 | 4 | #include 5 | #include 6 | 7 | #include "XcpMessage.h" 8 | #include "CmdPacket.h" 9 | #include "XcpMessage.h" 10 | #include "CmdPacketConnect.h" 11 | #include "DAQ.h" 12 | #include "DAQPackets.h" 13 | #include "CmdPacketGetSeed.h" 14 | #include "MessageFactory.h" 15 | 16 | typedef uint32_t(*XCP_GetAvailablePrivilegesPtr_t)(uint8_t* AvailablePrivilege); 17 | typedef uint32_t(*XCP_ComputeKeyFromSeedPtr_t)(uint8_t RequestedPrivilege, uint8_t ByteLenghtSeed, uint8_t* PointerToSeed, uint8_t* ByteLengthKey, uint8_t* PointerToKey); 18 | 19 | class IncomingPacketHandler; 20 | class PacketFactory; 21 | 22 | class XcpMaster : public QObject 23 | { 24 | Q_OBJECT 25 | 26 | public: 27 | enum TransportLayer 28 | { 29 | CAN, 30 | ETHERNET, 31 | USB, 32 | FLEXRAY 33 | }; 34 | 35 | struct SlaveProperties 36 | { 37 | bool CAL_PG; 38 | bool DAQ; 39 | bool STIM; 40 | bool PGM; 41 | 42 | bool byteOrder; 43 | uint8_t addressGranularity; 44 | bool slaveBlockMode; 45 | bool optionalData; 46 | 47 | uint16_t maxDto; 48 | uint8_t maxCto; 49 | uint8_t protocolLayerVersion; 50 | uint8_t transportLayerVersion; 51 | 52 | struct 53 | { 54 | bool configType; 55 | bool prescalerSupported; 56 | bool resumeSupported; 57 | bool bitStimSupported; 58 | bool timeStampSupported; 59 | bool pidOffSupported; 60 | uint8_t overloadIndicationMode; 61 | uint8_t optimisationType; 62 | uint8_t addressExtensionType; 63 | uint8_t identificationFieldType; 64 | uint16_t maxDaq; 65 | uint8_t minDaq; 66 | uint16_t maxEventChannel; 67 | uint8_t timestampSize; 68 | 69 | } DaqProperties; 70 | }; 71 | 72 | public: 73 | XcpMaster(TransportLayer a_eTransportlayer); 74 | virtual ~XcpMaster(); 75 | 76 | const SlaveProperties& getSlaveProperties() const; 77 | void setSlaveProperties(const SlaveProperties& a_rProperties); 78 | 79 | XcpMessage* createConnectMessage(CmdPacketConnect::ConnectMode a_eMode); 80 | XcpMessage* createDisconnectMessage(); 81 | XcpMessage* createGetStatusMessage(); 82 | XcpMessage* createSynchMessage(); 83 | XcpMessage* createSetMtaMessage(uint32_t a_dwAddress, uint8_t a_byExtension); 84 | XcpMessage* createUploadMessage(uint8_t a_byNumberOfElements); 85 | XcpMessage* createShortUploadMessage(uint8_t a_byNumberOfElements, uint32_t a_dwAddress, uint8_t a_byAddressExtension); 86 | XcpMessage* createFreeDaqMessage(); 87 | XcpMessage* createAllocDaqMessage(uint16_t a_wDaqCount); 88 | XcpMessage* createAllocOdtMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtCount); 89 | XcpMessage* createAllocOdtEntryMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryCount); 90 | XcpMessage* createSetDaqPtrMessage(uint16_t a_wDaqListNumber, uint8_t a_byOdtNumber, uint8_t a_byOdtEntryNumber); 91 | XcpMessage* createWriteDaqMessage(uint8_t a_byBitOffset, uint8_t a_byElementSize, uint8_t a_byAddressExtension, uint32_t a_dwAddress); 92 | XcpMessage* createSetDaqListModeMessage(uint8_t a_byMode, uint16_t a_wDaqListNumber, uint16_t a_wEventChannel, uint8_t a_byPrescaler, uint8_t a_byPriority); 93 | XcpMessage* createStartStopDaqListMessage(StartStopDaqListPacket::Mode a_eMode, uint16_t a_wDaqListNumber); 94 | XcpMessage* createStartStopSynchMessage(StartStopSynchPacket::Mode a_eMode); 95 | XcpMessage* createGetSeedMessage(CmdPacketGetSeed::Mode a_eMode, CmdPacketGetSeed::Resource a_eResource); 96 | XcpMessage* createGetDaqProcessorInfoMessage(); 97 | XcpMessage* createClearDaqListMessage(uint16_t a_wDaqListNumber); 98 | XcpMessage* createDownloadMessage(uint8_t a_byNumOfDataElements, uint32_t a_dwData); 99 | QVector createUnlockMessages(); 100 | 101 | void deserializeMessage(const QVector &a_rData); 102 | 103 | DaqLayout& getDaqLayout(); 104 | void setDaqLayout(const DaqLayout &a_rDaqLayout); 105 | 106 | void handleSentMessage(XcpMessage *a_pMessage); 107 | CmdPacket* getLastSentCmd(); 108 | bool isCommandQueueEmpty() const; 109 | 110 | void emitSendUploadByteArray(const QVector &a_rBytes); 111 | void emitSendOdtEntryValue(uint16_t a_wDaqIndex, uint8_t a_byOdtIndex, uint32_t a_dwOdtEntryIndex, qint64 a_timestamp, double value); 112 | 113 | void setSeedAndKeyFunctions(XCP_GetAvailablePrivilegesPtr_t GetAvailablePrivilegesPtr, XCP_ComputeKeyFromSeedPtr_t ComputeKeyPtr); 114 | XCP_ComputeKeyFromSeedPtr_t getComputeKeyPtr(); 115 | XCP_GetAvailablePrivilegesPtr_t getAvailablePrivilegesPtr(); 116 | 117 | signals: 118 | void sendUploadByteArray(QVector bytes); 119 | void sendOdtEntryValue(uint16_t a_wDaqIndex, uint8_t a_byOdtIndex, uint32_t a_dwOdtEntryIndex, qint64 a_timestamp, double value); 120 | 121 | private: 122 | XcpMaster() {} 123 | 124 | private: 125 | QVector m_queueSentCommand; 126 | IncomingPacketHandler *m_pIncomingPacketHandler; 127 | PacketFactory *m_pPacketFactory; 128 | MessageFactory *m_pMessageFactory; 129 | SlaveProperties m_slaveProperties; 130 | DaqLayout m_DaqLayout; 131 | XCP_GetAvailablePrivilegesPtr_t m_getAvailablePrivileges; 132 | XCP_ComputeKeyFromSeedPtr_t m_computeKeyFromSeed; 133 | }; 134 | 135 | #endif // XCPMASTER_H 136 | -------------------------------------------------------------------------------- /XcpMessage.cpp: -------------------------------------------------------------------------------- 1 | #include "XcpMessage.h" 2 | 3 | 4 | QVector XcpMessage::getByteArray() const 5 | { 6 | if(m_pHeader != nullptr 7 | && m_pPacket != nullptr 8 | && m_pTail != nullptr) { 9 | return m_pHeader->getByteArray() + m_pPacket->getByteArray() + m_pTail->getByteArray(); 10 | } 11 | else { 12 | return QVector(); 13 | } 14 | } 15 | 16 | XcpPacket *XcpMessage::getPacket() 17 | { 18 | return m_pPacket; 19 | } 20 | -------------------------------------------------------------------------------- /XcpMessage.h: -------------------------------------------------------------------------------- 1 | #ifndef XCPMESSAGE_H 2 | #define XCPMESSAGE_H 3 | 4 | #include "XcpHeader.h" 5 | #include "XcpPacket.h" 6 | #include "XcpTail.h" 7 | 8 | class XcpMessage 9 | { 10 | public: 11 | XcpMessage(XcpPacket* a_pPacket) {m_pPacket = a_pPacket;} 12 | 13 | QVector getByteArray() const; 14 | 15 | XcpPacket* getPacket(); 16 | 17 | protected: 18 | XcpHeader *m_pHeader; 19 | XcpPacket *m_pPacket; 20 | XcpTail *m_pTail; 21 | }; 22 | 23 | #endif // XCPMESSAGE_H 24 | -------------------------------------------------------------------------------- /XcpPacket.h: -------------------------------------------------------------------------------- 1 | #ifndef XCPPACKET_H 2 | #define XCPPACKET_H 3 | 4 | #include 5 | 6 | class XcpPacket 7 | { 8 | public: 9 | XcpPacket() {} 10 | virtual ~XcpPacket() {} 11 | 12 | quint8 getPid() const 13 | { 14 | if(m_idField.isEmpty()) { 15 | return 0; 16 | } 17 | return m_idField[0]; // Must available 18 | } 19 | 20 | void setPid(quint8 a_byPid) 21 | { 22 | if(m_idField.isEmpty()) { 23 | m_idField.append(a_byPid); 24 | } 25 | m_idField[0] = a_byPid; 26 | } 27 | 28 | QVector getByteArray() const {return m_idField+m_timestampField+m_dataField;} 29 | 30 | QVector getDataBytes() const {return m_dataField;} 31 | 32 | protected: 33 | QVector m_idField; 34 | QVector m_timestampField; 35 | QVector m_dataField; 36 | }; 37 | 38 | #endif // XCPPACKET_H 39 | -------------------------------------------------------------------------------- /XcpTail.h: -------------------------------------------------------------------------------- 1 | #ifndef XCPTAIL_H 2 | #define XCPTAIL_H 3 | 4 | #include 5 | 6 | class XcpTail 7 | { 8 | public: 9 | XcpTail () {} 10 | virtual ~XcpTail() {} 11 | virtual QVector getByteArray() = 0; 12 | }; 13 | 14 | #endif // XCPTAIL_H 15 | -------------------------------------------------------------------------------- /transport/can/CanHeader.cpp: -------------------------------------------------------------------------------- 1 | #include "CanHeader.h" 2 | 3 | CanHeader::CanHeader() 4 | : XcpHeader() 5 | { 6 | 7 | } 8 | 9 | CanHeader::~CanHeader() 10 | { 11 | 12 | } 13 | 14 | QVector CanHeader::getByteArray() 15 | { 16 | return QVector(); 17 | } 18 | -------------------------------------------------------------------------------- /transport/can/CanHeader.h: -------------------------------------------------------------------------------- 1 | #ifndef CANHEADER_H 2 | #define CANHEADER_H 3 | 4 | #include "XcpHeader.h" 5 | 6 | class CanHeader : public XcpHeader 7 | { 8 | public: 9 | CanHeader(); 10 | virtual ~CanHeader(); 11 | 12 | virtual QVector getByteArray(); 13 | }; 14 | 15 | #endif // CANHEADER_H 16 | -------------------------------------------------------------------------------- /transport/can/CanMessage.cpp: -------------------------------------------------------------------------------- 1 | #include "CanMessage.h" 2 | 3 | #include "CanHeader.h" 4 | #include "CanTail.h" 5 | 6 | CanMessage::CanMessage(XcpPacket *a_pPacket) 7 | : XcpMessage(a_pPacket) 8 | { 9 | m_pHeader = new CanHeader; 10 | m_pTail = new CanTail; 11 | } 12 | -------------------------------------------------------------------------------- /transport/can/CanMessage.h: -------------------------------------------------------------------------------- 1 | #ifndef CANMESSAGE_H 2 | #define CANMESSAGE_H 3 | 4 | #include "XcpMessage.h" 5 | 6 | class CanMessage : public XcpMessage 7 | { 8 | public: 9 | CanMessage(XcpPacket* a_pPacket); 10 | }; 11 | 12 | #endif // CANMESSAGE_H 13 | -------------------------------------------------------------------------------- /transport/can/CanMessageFactory.cpp: -------------------------------------------------------------------------------- 1 | #include "CanMessageFactory.h" 2 | 3 | #include "CanMessage.h" 4 | 5 | CanMessageFactory::CanMessageFactory() 6 | : MessageFactory() 7 | { 8 | 9 | } 10 | 11 | CanMessageFactory::~CanMessageFactory() 12 | { 13 | 14 | } 15 | 16 | XcpMessage *CanMessageFactory::createMessage(XcpPacket *a_pPacket) 17 | { 18 | return new CanMessage(a_pPacket); 19 | } 20 | 21 | QVector CanMessageFactory::getPacketBytes(const QVector &a_rMsgBytes) 22 | { 23 | QVector retval = a_rMsgBytes; 24 | 25 | // CAN message has no header nor tail 26 | return retval; 27 | } 28 | -------------------------------------------------------------------------------- /transport/can/CanMessageFactory.h: -------------------------------------------------------------------------------- 1 | #ifndef CANMESSAGEFACTORY_H 2 | #define CANMESSAGEFACTORY_H 3 | 4 | #include "MessageFactory.h" 5 | 6 | class CanMessageFactory : public MessageFactory 7 | { 8 | public: 9 | CanMessageFactory(); 10 | ~CanMessageFactory(); 11 | 12 | virtual XcpMessage* createMessage(XcpPacket* a_pPacket); 13 | 14 | virtual QVector getPacketBytes(const QVector& a_rMsgBytes); 15 | }; 16 | 17 | #endif // CANMESSAGEFACTORY_H 18 | -------------------------------------------------------------------------------- /transport/can/CanTail.cpp: -------------------------------------------------------------------------------- 1 | #include "CanTail.h" 2 | 3 | CanTail::CanTail() 4 | : XcpTail() 5 | { 6 | 7 | } 8 | 9 | CanTail::~CanTail() 10 | { 11 | 12 | } 13 | 14 | QVector CanTail::getByteArray() 15 | { 16 | return QVector(); 17 | } 18 | -------------------------------------------------------------------------------- /transport/can/CanTail.h: -------------------------------------------------------------------------------- 1 | #ifndef CANTAIL_H 2 | #define CANTAIL_H 3 | 4 | #include "XcpTail.h" 5 | 6 | class CanTail : public XcpTail 7 | { 8 | public: 9 | CanTail(); 10 | virtual ~CanTail(); 11 | 12 | virtual QVector getByteArray(); 13 | }; 14 | 15 | #endif // CANTAIL_H 16 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetHeader.cpp: -------------------------------------------------------------------------------- 1 | #include "EthernetHeader.h" 2 | 3 | EthernetHeader::EthernetHeader(uint16_t a_wLen, uint16_t a_wCtr) 4 | : XcpHeader() 5 | { 6 | m_wLength = a_wLen; 7 | m_wCtr = a_wCtr; 8 | } 9 | 10 | EthernetHeader::~EthernetHeader() 11 | { 12 | 13 | } 14 | 15 | QVector EthernetHeader::getByteArray() 16 | { 17 | QVector retval; 18 | 19 | retval.push_back((uint8_t)(m_wLength) & 0xFF); 20 | retval.push_back((uint8_t)(((m_wLength) & 0xFF00)>>8)); 21 | retval.push_back((uint8_t)(m_wCtr) & 0xFF); 22 | retval.push_back((uint8_t)(((m_wCtr) & 0xFF00) >> 8)); 23 | 24 | return retval; 25 | } 26 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetHeader.h: -------------------------------------------------------------------------------- 1 | #ifndef ETHERNETHEADER_H 2 | #define ETHERNETHEADER_H 3 | 4 | #include "XcpHeader.h" 5 | 6 | class EthernetHeader : public XcpHeader 7 | { 8 | public: 9 | EthernetHeader(uint16_t a_wLen, uint16_t a_wCtr); 10 | virtual ~EthernetHeader(); 11 | 12 | virtual QVector getByteArray(); 13 | 14 | void setLength(uint16_t a_wLen) {m_wLength = a_wLen;} 15 | uint16_t getLength() {return m_wLength;} 16 | void setCtr(uint16_t a_wCtr) {m_wCtr = a_wCtr;} 17 | uint16_t getCtr() {return m_wCtr;} 18 | 19 | private: 20 | uint16_t m_wLength; 21 | uint16_t m_wCtr; 22 | }; 23 | 24 | #endif // ETHERNETHEADER_H 25 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetMessage.cpp: -------------------------------------------------------------------------------- 1 | #include "EthernetMessage.h" 2 | 3 | #include "EthernetHeader.h" 4 | #include "EthernetTail.h" 5 | 6 | EthernetMessage::EthernetMessage(XcpPacket *a_pPacket, uint16_t a_wCtr) 7 | : XcpMessage(a_pPacket) 8 | { 9 | m_pHeader = new EthernetHeader(a_pPacket->getByteArray().size(), a_wCtr); 10 | m_pTail = new EthernetTail; 11 | } 12 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetMessage.h: -------------------------------------------------------------------------------- 1 | #ifndef ETHERNETMESSAGE_H 2 | #define ETHERNETMESSAGE_H 3 | 4 | #include "XcpMessage.h" 5 | 6 | class EthernetMessage : public XcpMessage 7 | { 8 | public: 9 | EthernetMessage(XcpPacket* a_pPacket, uint16_t a_wCtr); 10 | }; 11 | 12 | #endif // ETHERNETMESSAGE_H 13 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetMessageFactory.cpp: -------------------------------------------------------------------------------- 1 | #include "EthernetMessageFactory.h" 2 | 3 | #include "EthernetMessage.h" 4 | 5 | EthernetMessageFactory::EthernetMessageFactory() 6 | { 7 | m_wNumberOfCreatedMessages = 0; 8 | } 9 | 10 | EthernetMessageFactory::~EthernetMessageFactory() 11 | { 12 | 13 | } 14 | 15 | XcpMessage *EthernetMessageFactory::createMessage(XcpPacket *a_pPacket) 16 | { 17 | return new EthernetMessage(a_pPacket, m_wNumberOfCreatedMessages++); 18 | } 19 | 20 | QVector EthernetMessageFactory::getPacketBytes(const QVector &a_rMsgBytes) 21 | { 22 | QVector retval = a_rMsgBytes; 23 | 24 | // Ethernet message has 4-byte header and no tail 25 | retval.removeAt(0); 26 | retval.removeAt(1); 27 | retval.removeAt(2); 28 | retval.removeAt(3); 29 | 30 | return retval; 31 | } 32 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetMessageFactory.h: -------------------------------------------------------------------------------- 1 | #ifndef ETHERNETMESSAGEFACTORY_H 2 | #define ETHERNETMESSAGEFACTORY_H 3 | 4 | #include "MessageFactory.h" 5 | 6 | class EthernetMessageFactory : public MessageFactory 7 | { 8 | public: 9 | EthernetMessageFactory(); 10 | ~EthernetMessageFactory(); 11 | 12 | virtual XcpMessage* createMessage(XcpPacket* a_pPacket); 13 | 14 | virtual QVector getPacketBytes(const QVector& a_rMsgBytes); 15 | 16 | private: 17 | uint16_t m_wNumberOfCreatedMessages; 18 | }; 19 | 20 | #endif // ETHERNETMESSAGEFACTORY_H 21 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetTail.cpp: -------------------------------------------------------------------------------- 1 | #include "EthernetTail.h" 2 | 3 | EthernetTail::EthernetTail() 4 | : XcpTail() 5 | { 6 | 7 | } 8 | 9 | EthernetTail::~EthernetTail() 10 | { 11 | 12 | } 13 | 14 | QVector EthernetTail::getByteArray() 15 | { 16 | return QVector(); 17 | } 18 | -------------------------------------------------------------------------------- /transport/ethernet/EthernetTail.h: -------------------------------------------------------------------------------- 1 | #ifndef ETHERNETTAIL_H 2 | #define ETHERNETTAIL_H 3 | 4 | #include "XcpTail.h" 5 | 6 | class EthernetTail : public XcpTail 7 | { 8 | public: 9 | EthernetTail(); 10 | virtual ~EthernetTail(); 11 | 12 | virtual QVector getByteArray(); 13 | }; 14 | 15 | #endif // ETHERNETTAIL_H 16 | --------------------------------------------------------------------------------