eive-obsw/linux/devices/devicedefinitions/PlocMPSoCDefinitions.h

777 lines
26 KiB
C
Raw Normal View History

#ifndef MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_
#define MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_
2021-04-11 12:04:13 +02:00
2022-03-27 13:07:18 +02:00
#include "MPSoCReturnValuesIF.h"
#include "OBSWConfig.h"
#include "eive/definitions.h"
2022-03-27 10:44:32 +02:00
#include "fsfw/globalfunctions/CRC.h"
#include "fsfw/serialize/SerializeAdapter.h"
#include "mission/devices/devicedefinitions/SpBase.h"
2021-04-11 12:04:13 +02:00
2022-01-05 11:26:01 +01:00
namespace mpsoc {
2021-04-11 12:04:13 +02:00
2022-01-05 11:26:01 +01:00
static const DeviceCommandId_t NONE = 0;
static const DeviceCommandId_t TC_MEM_WRITE = 1;
static const DeviceCommandId_t TC_MEM_READ = 2;
static const DeviceCommandId_t ACK_REPORT = 3;
static const DeviceCommandId_t EXE_REPORT = 5;
static const DeviceCommandId_t TM_MEMORY_READ_REPORT = 6;
static const DeviceCommandId_t TC_FLASHFOPEN = 7;
2022-01-06 10:12:08 +01:00
static const DeviceCommandId_t TC_FLASHFCLOSE = 8;
2022-01-06 18:05:21 +01:00
static const DeviceCommandId_t TC_FLASHWRITE = 9;
2022-03-21 08:35:28 +01:00
static const DeviceCommandId_t TC_FLASHDELETE = 10;
static const DeviceCommandId_t TC_REPLAY_START = 11;
static const DeviceCommandId_t TC_REPLAY_STOP = 12;
static const DeviceCommandId_t TC_REPLAY_WRITE_SEQUENCE = 13;
static const DeviceCommandId_t TC_DOWNLINK_PWR_ON = 14;
static const DeviceCommandId_t TC_DOWNLINK_PWR_OFF = 15;
2022-03-24 17:39:50 +01:00
static const DeviceCommandId_t TC_MODE_REPLAY = 16;
2022-04-20 21:33:39 +02:00
static const DeviceCommandId_t TC_CAM_CMD_SEND = 17;
static const DeviceCommandId_t TC_MODE_IDLE = 18;
static const DeviceCommandId_t TM_CAM_CMD_RPT = 19;
2022-04-29 22:55:01 +02:00
static const DeviceCommandId_t SET_UART_TX_TRISTATE = 20;
static const DeviceCommandId_t RELEASE_UART_TX = 21;
static const DeviceCommandId_t TC_CAM_TAKE_PIC = 22;
static const DeviceCommandId_t TC_SIMPLEX_SEND_FILE = 23;
static const DeviceCommandId_t TC_DOWNLINK_DATA_MODULATE = 24;
2023-02-14 14:00:53 +01:00
static const DeviceCommandId_t TC_MODE_SNAPSHOT = 25;
2022-04-29 22:55:01 +02:00
2022-03-25 09:08:01 +01:00
// Will reset the sequence count of the OBSW
static const DeviceCommandId_t OBSW_RESET_SEQ_COUNT = 50;
2022-01-03 08:01:55 +01:00
static const uint16_t SIZE_ACK_REPORT = 14;
static const uint16_t SIZE_EXE_REPORT = 14;
static const uint16_t SIZE_TM_MEM_READ_REPORT = 18;
2022-04-20 21:33:39 +02:00
static const uint16_t SIZE_TM_CAM_CMD_RPT = 18;
2022-01-03 08:01:55 +01:00
/**
* SpacePacket apids of PLOC telecommands and telemetry.
*/
2022-01-05 11:26:01 +01:00
namespace apid {
2022-03-26 20:47:25 +01:00
static const uint16_t TC_REPLAY_START = 0x110;
static const uint16_t TC_REPLAY_STOP = 0x111;
static const uint16_t TC_REPLAY_WRITE_SEQUENCE = 0x112;
static const uint16_t TC_DOWNLINK_PWR_ON = 0x113;
static const uint16_t TC_MEM_WRITE = 0x114;
static const uint16_t TC_MEM_READ = 0x115;
static const uint16_t TC_CAM_TAKE_PIC = 0x116;
2022-03-26 20:47:25 +01:00
static const uint16_t TC_FLASHWRITE = 0x117;
static const uint16_t TC_FLASHFOPEN = 0x119;
static const uint16_t TC_FLASHFCLOSE = 0x11A;
static const uint16_t TC_FLASHDELETE = 0x11C;
2022-04-20 21:33:39 +02:00
static const uint16_t TC_MODE_IDLE = 0x11E;
static const uint16_t TC_MODE_REPLAY = 0x11F;
static const uint16_t TC_MODE_SNAPSHOT = 0x120;
static const uint16_t TC_DOWNLINK_DATA_MODULATE = 0x121;
2022-03-26 20:47:25 +01:00
static const uint16_t TC_DOWNLINK_PWR_OFF = 0x124;
2022-04-20 21:33:39 +02:00
static const uint16_t TC_CAM_CMD_SEND = 0x12C;
static const uint16_t TC_SIMPLEX_SEND_FILE = 0x130;
2022-03-26 20:47:25 +01:00
static const uint16_t TM_MEMORY_READ_REPORT = 0x404;
static const uint16_t ACK_SUCCESS = 0x400;
static const uint16_t ACK_FAILURE = 0x401;
static const uint16_t EXE_SUCCESS = 0x402;
static const uint16_t EXE_FAILURE = 0x403;
2022-04-20 21:33:39 +02:00
static const uint16_t TM_CAM_CMD_RPT = 0x407;
2022-03-26 20:47:25 +01:00
} // namespace apid
2022-01-05 11:26:01 +01:00
/** Offset from first byte in space packet to first byte of data field */
2022-01-03 08:01:55 +01:00
static const uint8_t DATA_FIELD_OFFSET = 6;
static const size_t MEM_READ_RPT_LEN_OFFSET = 10;
2022-03-26 20:47:25 +01:00
static const char NULL_TERMINATOR = '\0';
2022-04-20 21:33:39 +02:00
static const uint8_t MIN_SPACE_PACKET_LENGTH = 7;
static const uint8_t SPACE_PACKET_HEADER_SIZE = 6;
2022-01-03 08:01:55 +01:00
static constexpr size_t CRC_SIZE = 2;
2022-01-03 08:01:55 +01:00
/**
* The size of payload data which will be forwarded to the requesting object. e.g. PUS Service
* 8.
*/
static const uint8_t SIZE_MEM_READ_RPT_FIX = 6;
2022-01-03 08:01:55 +01:00
2022-01-05 11:26:01 +01:00
static const size_t MAX_FILENAME_SIZE = 256;
2022-01-03 08:01:55 +01:00
/**
* PLOC space packet length for fixed size packets. This is the size of the whole packet data
* field. For the length field in the space packet this size will be substracted by one.
*/
static const uint16_t LENGTH_TC_MEM_WRITE = 12;
static const uint16_t LENGTH_TC_MEM_READ = 8;
/**
2022-08-16 18:41:50 +02:00
* Maximum SP packet size as specified in the TAS Supversior ICD.
* https://eive-cloud.irs.uni-stuttgart.de/index.php/apps/files/?dir=/EIVE_TAS-ILH-IRS/ICD-PLOC/TAS&fileid=942896
* at sheet README
*/
static constexpr size_t SP_MAX_SIZE = 1024;
static const size_t MAX_REPLY_SIZE = SP_MAX_SIZE * 3;
static const size_t MAX_COMMAND_SIZE = SP_MAX_SIZE;
2022-01-06 18:05:21 +01:00
static const size_t MAX_DATA_SIZE = 1016;
2022-01-03 08:01:55 +01:00
2022-01-05 11:26:01 +01:00
/**
2022-03-21 16:21:51 +01:00
* The replay write sequence command has a maximum delay for the execution report which amounts to
2022-03-26 20:47:25 +01:00
* 30 seconds. (80 cycles * 0.5 seconds = 40 seconds).
2022-03-21 16:21:51 +01:00
*/
2022-03-26 20:47:25 +01:00
static const uint16_t TC_WRITE_SEQ_EXECUTION_DELAY = 80;
// Requires approx. 2 seconds for execution. 8 => 4 seconds
static const uint16_t TC_DOWNLINK_PWR_ON_EXECUTION_DELAY = 8;
static const uint16_t TC_CAM_TAKE_PIC_EXECUTION_DELAY = 20;
2022-03-21 16:21:51 +01:00
namespace status_code {
static const uint16_t DEFAULT_ERROR_CODE = 0x1;
2022-06-17 08:31:36 +02:00
static const uint16_t UNKNOWN_APID = 0x5DD;
static const uint16_t INCORRECT_LENGTH = 0x5DE;
static const uint16_t INCORRECT_CRC = 0x5DF;
static const uint16_t INCORRECT_PKT_SEQ_CNT = 0x5E0;
static const uint16_t TC_NOT_ALLOWED_IN_MODE = 0x5E1;
static const uint16_t TC_EXEUTION_DISABLED = 0x5E2;
static const uint16_t FLASH_MOUNT_FAILED = 0x5E3;
static const uint16_t FLASH_FILE_ALREADY_CLOSED = 0x5E4;
static const uint16_t FLASH_FILE_OPEN_FAILED = 0x5E5;
static const uint16_t FLASH_FILE_ALREDY_OPEN = 0x5E6;
static const uint16_t FLASH_FILE_NOT_OPEN = 0x5E7;
static const uint16_t FLASH_UNMOUNT_FAILED = 0x5E8;
static const uint16_t HEAP_ALLOCATION_FAILED = 0x5E9;
static const uint16_t INVALID_PARAMETER = 0x5EA;
static const uint16_t NOT_INITIALIZED = 0x5EB;
static const uint16_t REBOOT_IMMINENT = 0x5EC;
static const uint16_t CORRUPT_DATA = 0x5ED;
static const uint16_t FLASH_CORRECTABLE_MISMATCH = 0x5EE;
static const uint16_t FLASH_UNCORRECTABLE_MISMATCH = 0x5EF;
static const uint16_t RESERVED_0 = 0x5F0;
static const uint16_t RESERVED_1 = 0x5F1;
static const uint16_t RESERVED_2 = 0x5F2;
static const uint16_t RESERVED_3 = 0x5F3;
static const uint16_t RESERVED_4 = 0x5F4;
} // namespace status_code
2022-03-21 16:21:51 +01:00
/**
* @brief Abstract base class for TC space packet of MPSoC.
2022-01-05 11:26:01 +01:00
*/
2022-08-15 18:34:26 +02:00
class TcBase : public ploc::SpTcBase, public MPSoCReturnValuesIF {
2022-03-26 20:47:25 +01:00
public:
virtual ~TcBase() = default;
2022-03-26 20:47:25 +01:00
// Initial length field of space packet. Will always be updated when packet is created.
2022-08-19 15:49:22 +02:00
static const uint16_t INIT_LENGTH = 2;
2022-03-26 20:47:25 +01:00
/**
* @brief Constructor
*
* @param sequenceCount Sequence count of space packet which will be incremented with each
* sent and received packets.
*/
2022-08-15 18:34:26 +02:00
TcBase(ploc::SpTcParams params, uint16_t apid, uint16_t sequenceCount)
2022-12-22 17:17:23 +01:00
: ploc::SpTcBase(params, apid, 0, sequenceCount) {
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(INIT_LENGTH);
}
ReturnValue_t buildPacket() { return buildPacket(nullptr, 0); }
2022-03-26 20:47:25 +01:00
/**
* @brief Function to initialize the space packet
*
* @param commandData Pointer to command specific data
* @param commandDataLen Length of command data
*
2022-08-24 17:27:47 +02:00
* @return returnvalue::OK if packet creation was successful, otherwise error return value
2022-03-26 20:47:25 +01:00
*/
ReturnValue_t buildPacket(const uint8_t* commandData, size_t commandDataLen) {
payloadStart = spParams.buf + ccsds::HEADER_LEN;
ReturnValue_t res;
if (commandData != nullptr and commandDataLen > 0) {
res = initPacket(commandData, commandDataLen);
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
return res;
}
}
2022-08-15 18:58:56 +02:00
updateSpFields();
res = checkSizeAndSerializeHeader();
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
return res;
}
2022-11-07 10:30:09 +01:00
return calcAndSetCrc();
2022-03-26 20:47:25 +01:00
}
protected:
/**
* @brief Must be overwritten by the child class to define the command specific parameters
*
* @param commandData Pointer to received command data
* @param commandDataLen Length of received command data
*/
virtual ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-01-05 11:26:01 +01:00
};
2022-01-03 08:01:55 +01:00
/**
* @brief This class helps to build the memory read command for the PLOC.
*/
2022-03-26 20:47:25 +01:00
class TcMemRead : public TcBase {
public:
/**
* @brief Constructor
*/
2022-08-15 18:34:26 +02:00
TcMemRead(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_MEM_READ, sequenceCount) {
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(COMMAND_LENGTH + CRC_SIZE);
2022-03-26 20:47:25 +01:00
}
2021-04-11 12:04:13 +02:00
2022-03-26 20:47:25 +01:00
uint16_t getMemLen() const { return memLen; }
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-03-26 20:47:25 +01:00
result = lengthCheck(commandDataLen);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
std::memcpy(payloadStart, commandData, MEM_ADDRESS_SIZE);
std::memcpy(payloadStart + MEM_ADDRESS_SIZE, commandData + MEM_ADDRESS_SIZE, MEM_LEN_SIZE);
2022-03-26 20:47:25 +01:00
size_t size = sizeof(memLen);
const uint8_t* memLenPtr = commandData + MEM_ADDRESS_SIZE;
result =
SerializeAdapter::deSerialize(&memLen, &memLenPtr, &size, SerializeIF::Endianness::BIG);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
return result;
}
2022-03-26 20:47:25 +01:00
private:
static const size_t COMMAND_LENGTH = 6;
static const size_t MEM_ADDRESS_SIZE = 4;
static const size_t MEM_LEN_SIZE = 2;
static const uint16_t PACKET_LENGTH = 7;
2022-03-26 20:47:25 +01:00
uint16_t memLen = 0;
2022-03-26 20:47:25 +01:00
ReturnValue_t lengthCheck(size_t commandDataLen) {
2022-08-24 17:27:47 +02:00
if (commandDataLen != COMMAND_LENGTH or checkPayloadLen() != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return INVALID_LENGTH;
2022-01-03 08:01:55 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-01-03 08:01:55 +01:00
};
/**
2022-01-06 10:12:08 +01:00
* @brief This class helps to generate the space packet to write data to a memory address within
2022-01-03 08:01:55 +01:00
* the PLOC.
*/
2022-03-26 20:47:25 +01:00
class TcMemWrite : public TcBase {
public:
/**
* @brief Constructor
*/
2022-08-15 18:34:26 +02:00
TcMemWrite(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_MEM_WRITE, sequenceCount) {}
2022-03-26 20:47:25 +01:00
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-03-26 20:47:25 +01:00
result = lengthCheck(commandDataLen);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
uint16_t memLen =
*(commandData + MEM_ADDRESS_SIZE) << 8 | *(commandData + MEM_ADDRESS_SIZE + 1);
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(MIN_FIXED_PAYLOAD_LENGTH + memLen * 4 + CRC_SIZE);
2022-08-16 18:37:51 +02:00
result = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return result;
}
std::memcpy(payloadStart, commandData, commandDataLen);
2022-03-26 20:47:25 +01:00
return result;
}
private:
2022-08-16 18:02:32 +02:00
// 4 byte address, 2 byte mem length field
2022-03-26 20:47:25 +01:00
static const size_t MEM_ADDRESS_SIZE = 4;
2022-08-16 18:02:32 +02:00
static const size_t MIN_FIXED_PAYLOAD_LENGTH = MEM_ADDRESS_SIZE + 2;
// Min length consists of 4 byte address, 2 byte mem length field, 4 byte data (1 word)
static const size_t MIN_COMMAND_DATA_LENGTH = MIN_FIXED_PAYLOAD_LENGTH + 4;
2022-03-26 20:47:25 +01:00
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen < MIN_COMMAND_DATA_LENGTH) {
2022-08-18 15:32:24 +02:00
sif::warning << "TcMemWrite: Length " << commandDataLen << " smaller than minimum "
<< MIN_COMMAND_DATA_LENGTH << std::endl;
2022-08-16 18:02:32 +02:00
return INVALID_LENGTH;
}
2022-08-18 15:32:24 +02:00
if (commandDataLen + CRC_SIZE > spParams.maxSize) {
sif::warning << "TcMemWrite: Length " << commandDataLen << " larger than allowed "
<< spParams.maxSize - CRC_SIZE << std::endl;
2022-03-26 20:47:25 +01:00
return INVALID_LENGTH;
2022-01-03 08:01:55 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-01-05 11:26:01 +01:00
};
2021-04-11 12:04:13 +02:00
2022-01-05 11:26:01 +01:00
/**
2022-01-06 10:12:08 +01:00
* @brief Class to help creation of flash fopen command.
2022-01-05 11:26:01 +01:00
*/
2022-08-15 18:34:26 +02:00
class FlashFopen : public ploc::SpTcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
FlashFopen(ploc::SpTcParams params, uint16_t sequenceCount)
: ploc::SpTcBase(params, apid::TC_FLASHFOPEN, sequenceCount) {}
2022-03-26 20:47:25 +01:00
static const char APPEND = 'a';
static const char WRITE = 'w';
static const char READ = 'r';
ReturnValue_t createPacket(std::string filename, char accessMode_) {
accessMode = accessMode_;
size_t nameSize = filename.size();
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(nameSize + sizeof(NULL_TERMINATOR) + sizeof(accessMode) + CRC_SIZE);
2022-08-16 18:37:51 +02:00
ReturnValue_t result = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return result;
}
std::memcpy(payloadStart, filename.c_str(), nameSize);
*(spParams.buf + nameSize) = NULL_TERMINATOR;
std::memcpy(payloadStart + nameSize + sizeof(NULL_TERMINATOR), &accessMode, sizeof(accessMode));
2022-08-15 18:58:56 +02:00
updateSpFields();
2022-11-07 10:30:09 +01:00
return calcAndSetCrc();
2022-03-26 20:47:25 +01:00
}
private:
char accessMode = APPEND;
2022-01-03 08:01:55 +01:00
};
2021-04-11 12:04:13 +02:00
2022-01-06 10:12:08 +01:00
/**
* @brief Class to help creation of flash fclose command.
*/
2022-08-16 18:37:51 +02:00
class FlashFclose : public ploc::SpTcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
FlashFclose(ploc::SpTcParams params, uint16_t sequenceCount)
2022-08-16 18:37:51 +02:00
: ploc::SpTcBase(params, apid::TC_FLASHFCLOSE, sequenceCount) {}
2022-03-26 20:47:25 +01:00
ReturnValue_t createPacket(std::string filename) {
size_t nameSize = filename.size();
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE);
2022-08-16 18:37:51 +02:00
ReturnValue_t result = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return result;
}
std::memcpy(payloadStart, filename.c_str(), nameSize);
*(payloadStart + nameSize) = NULL_TERMINATOR;
2022-11-07 10:30:09 +01:00
return calcAndSetCrc();
2022-03-26 20:47:25 +01:00
}
2022-03-21 08:35:28 +01:00
};
2022-03-21 16:21:51 +01:00
/**
* @brief Class to build flash write space packet.
*/
2022-08-15 18:34:26 +02:00
class TcFlashWrite : public ploc::SpTcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
TcFlashWrite(ploc::SpTcParams params, uint16_t sequenceCount)
: ploc::SpTcBase(params, apid::TC_FLASHWRITE, sequenceCount) {}
2022-03-26 20:47:25 +01:00
2022-08-15 18:34:26 +02:00
ReturnValue_t buildPacket(const uint8_t* writeData, uint32_t writeLen_) {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-03-26 20:47:25 +01:00
writeLen = writeLen_;
if (writeLen > MAX_DATA_SIZE) {
sif::debug << "FlashWrite::createPacket: Command data too big" << std::endl;
2022-08-24 17:27:47 +02:00
return returnvalue::FAILED;
2022-03-26 20:47:25 +01:00
}
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(static_cast<uint16_t>(writeLen) + 4 + CRC_SIZE);
2022-08-16 18:37:51 +02:00
result = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return result;
}
2022-08-20 12:11:08 +02:00
size_t serializedSize = ccsds::HEADER_LEN;
result = SerializeAdapter::serialize(&writeLen, payloadStart, &serializedSize, spParams.maxSize,
SerializeIF::Endianness::BIG);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
std::memcpy(payloadStart + sizeof(writeLen), writeData, writeLen);
2022-08-15 18:58:56 +02:00
updateSpFields();
auto res = checkSizeAndSerializeHeader();
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
return res;
2022-03-21 16:21:51 +01:00
}
2022-11-07 10:30:09 +01:00
return calcAndSetCrc();
2022-03-26 20:47:25 +01:00
}
private:
uint32_t writeLen = 0;
2022-03-21 16:21:51 +01:00
};
2022-03-21 08:35:28 +01:00
/**
2022-03-21 08:53:55 +01:00
* @brief Class to help creation of flash delete command.
2022-03-21 08:35:28 +01:00
*/
2022-08-15 18:34:26 +02:00
class TcFlashDelete : public ploc::SpTcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
TcFlashDelete(ploc::SpTcParams params, uint16_t sequenceCount)
: ploc::SpTcBase(params, apid::TC_FLASHDELETE, sequenceCount) {}
2022-03-26 20:47:25 +01:00
ReturnValue_t buildPacket(std::string filename) {
2022-03-26 20:47:25 +01:00
size_t nameSize = filename.size();
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE);
2022-08-16 18:37:51 +02:00
auto res = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return res;
}
std::memcpy(payloadStart, filename.c_str(), nameSize);
*(payloadStart + nameSize) = NULL_TERMINATOR;
2022-08-16 18:37:51 +02:00
2022-08-15 18:58:56 +02:00
updateSpFields();
2022-08-16 18:37:51 +02:00
res = checkSizeAndSerializeHeader();
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
return res;
}
2022-11-07 10:30:09 +01:00
return calcAndSetCrc();
2022-03-26 20:47:25 +01:00
}
2022-01-06 10:12:08 +01:00
};
2022-01-06 18:05:21 +01:00
/**
2022-03-21 16:21:51 +01:00
* @brief Class to build replay stop space packet.
2022-01-06 18:05:21 +01:00
*/
2022-03-21 16:21:51 +01:00
class TcReplayStop : public TcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
TcReplayStop(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_REPLAY_STOP, sequenceCount) {}
2022-01-06 18:05:21 +01:00
};
2022-03-21 11:05:41 +01:00
/**
* @brief This class helps to build the replay start command.
*/
2022-03-26 20:47:25 +01:00
class TcReplayStart : public TcBase {
public:
/**
* @brief Constructor
*/
2022-08-15 18:34:26 +02:00
TcReplayStart(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_REPLAY_START, sequenceCount) {}
2022-03-26 20:47:25 +01:00
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(commandDataLen + CRC_SIZE);
2022-03-26 20:47:25 +01:00
result = lengthCheck(commandDataLen);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
result = checkData(*commandData);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
std::memcpy(payloadStart, commandData, commandDataLen);
2022-03-26 20:47:25 +01:00
return result;
}
private:
static const size_t COMMAND_DATA_LENGTH = 1;
static const uint8_t REPEATING = 0;
static const uint8_t ONCE = 1;
ReturnValue_t lengthCheck(size_t commandDataLen) {
2022-08-26 14:28:06 +02:00
if (commandDataLen != COMMAND_DATA_LENGTH or checkPayloadLen() != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
sif::warning << "TcReplayStart: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
2022-03-21 11:05:41 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
ReturnValue_t checkData(uint8_t replay) {
if (replay != REPEATING && replay != ONCE) {
sif::warning << "TcReplayStart::checkData: Invalid replay value" << std::endl;
return INVALID_PARAMETER;
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-03-21 11:05:41 +01:00
};
/**
2022-03-21 16:21:51 +01:00
* @brief This class helps to build downlink power on command.
2022-03-21 11:05:41 +01:00
*/
2022-03-26 20:47:25 +01:00
class TcDownlinkPwrOn : public TcBase {
public:
/**
* @brief Constructor
*/
2022-08-15 18:34:26 +02:00
TcDownlinkPwrOn(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_DOWNLINK_PWR_ON, sequenceCount) {}
2022-03-26 20:47:25 +01:00
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-03-26 20:47:25 +01:00
result = lengthCheck(commandDataLen);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
result = modeCheck(*commandData);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
result = laneRateCheck(*(commandData + 1));
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(commandDataLen + sizeof(MAX_AMPLITUDE) + CRC_SIZE);
2022-08-16 18:37:51 +02:00
result = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return result;
}
std::memcpy(payloadStart, commandData, commandDataLen);
std::memcpy(payloadStart + commandDataLen, &MAX_AMPLITUDE, sizeof(MAX_AMPLITUDE));
2022-03-26 20:47:25 +01:00
return result;
}
private:
static const uint8_t INTERFACE_ID = CLASS_ID::DWLPWRON_CMD;
//! [EXPORT] : [COMMENT] Received command has invalid JESD mode (valid modes are 0 - 5)
static const ReturnValue_t INVALID_MODE = MAKE_RETURN_CODE(0xE0);
//! [EXPORT] : [COMMENT] Received command has invalid lane rate (valid lane rate are 0 - 9)
static const ReturnValue_t INVALID_LANE_RATE = MAKE_RETURN_CODE(0xE1);
static const size_t COMMAND_DATA_LENGTH = 2;
static const uint8_t MAX_MODE = 5;
static const uint8_t MAX_LANE_RATE = 9;
static const uint16_t MAX_AMPLITUDE = 0;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_DATA_LENGTH) {
sif::warning << "TcDownlinkPwrOn: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
ReturnValue_t modeCheck(uint8_t mode) {
if (mode > MAX_MODE) {
sif::warning << "TcDwonlinkPwrOn::modeCheck: Invalid JESD mode" << std::endl;
return INVALID_MODE;
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
ReturnValue_t laneRateCheck(uint8_t laneRate) {
if (laneRate > MAX_LANE_RATE) {
sif::warning << "TcReplayStart::laneRateCheck: Invalid lane rate" << std::endl;
return INVALID_LANE_RATE;
2022-03-21 16:21:51 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-03-21 16:21:51 +01:00
};
/**
* @brief Class to build replay stop space packet.
*/
class TcDownlinkPwrOff : public TcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
TcDownlinkPwrOff(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_DOWNLINK_PWR_OFF, sequenceCount) {}
2022-03-21 16:21:51 +01:00
};
/**
* @brief This class helps to build the replay start command.
*/
2022-03-26 20:47:25 +01:00
class TcReplayWriteSeq : public TcBase {
public:
/**
* @brief Constructor
*/
2022-08-15 18:34:26 +02:00
TcReplayWriteSeq(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_REPLAY_WRITE_SEQUENCE, sequenceCount) {}
2022-03-26 20:47:25 +01:00
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-08-24 17:27:47 +02:00
ReturnValue_t result = returnvalue::OK;
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(commandDataLen + sizeof(NULL_TERMINATOR) + CRC_SIZE);
2022-03-26 20:47:25 +01:00
result = lengthCheck(commandDataLen);
2022-08-24 17:27:47 +02:00
if (result != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
return result;
}
std::memcpy(payloadStart, commandData, commandDataLen);
*(payloadStart + commandDataLen) = NULL_TERMINATOR;
2022-03-26 20:47:25 +01:00
return result;
}
2022-03-21 16:21:51 +01:00
2022-03-26 20:47:25 +01:00
private:
static const size_t USE_DECODING_LENGTH = 1;
2022-03-21 16:21:51 +01:00
2022-03-26 20:47:25 +01:00
ReturnValue_t lengthCheck(size_t commandDataLen) {
2022-08-16 18:37:51 +02:00
if (commandDataLen > USE_DECODING_LENGTH + MAX_FILENAME_SIZE or
2022-08-24 17:27:47 +02:00
checkPayloadLen() != returnvalue::OK) {
2022-03-26 20:47:25 +01:00
sif::warning << "TcReplayWriteSeq: Command has invalid length " << commandDataLen
<< std::endl;
return INVALID_LENGTH;
2022-03-21 16:21:51 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-26 20:47:25 +01:00
}
2022-03-21 11:05:41 +01:00
};
2022-04-10 18:46:39 +02:00
/**
* @brief Helps to extract the fields of the flash write command from the PUS packet.
*/
2022-03-22 11:35:44 +01:00
class FlashWritePusCmd : public MPSoCReturnValuesIF {
public:
FlashWritePusCmd(){};
ReturnValue_t extractFields(const uint8_t* commandData, size_t commandDataLen) {
if (commandDataLen > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE + MAX_FILENAME_SIZE)) {
2022-03-26 20:47:25 +01:00
return INVALID_LENGTH;
2022-03-22 11:35:44 +01:00
}
obcFile = std::string(reinterpret_cast<const char*>(commandData));
if (obcFile.size() > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE)) {
2022-03-26 20:47:25 +01:00
return FILENAME_TOO_LONG;
2022-03-22 11:35:44 +01:00
}
mpsocFile = std::string(
reinterpret_cast<const char*>(commandData + obcFile.size() + SIZE_NULL_TERMINATOR));
2022-03-22 11:35:44 +01:00
if (mpsocFile.size() > MAX_FILENAME_SIZE) {
2022-03-26 20:47:25 +01:00
return MPSOC_FILENAME_TOO_LONG;
2022-03-22 11:35:44 +01:00
}
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-03-22 11:35:44 +01:00
}
2022-03-26 20:47:25 +01:00
std::string getObcFile() { return obcFile; }
2022-03-22 11:35:44 +01:00
2022-03-26 20:47:25 +01:00
std::string getMPSoCFile() { return mpsocFile; }
2022-03-22 11:35:44 +01:00
private:
static const size_t SIZE_NULL_TERMINATOR = 1;
2022-03-22 11:35:44 +01:00
std::string obcFile = "";
std::string mpsocFile = "";
};
2022-03-24 17:39:50 +01:00
/**
* @brief Class to build replay stop space packet.
*/
class TcModeReplay : public TcBase {
2022-03-26 20:47:25 +01:00
public:
2022-08-15 18:34:26 +02:00
TcModeReplay(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_MODE_REPLAY, sequenceCount) {}
2022-03-24 17:39:50 +01:00
};
2022-04-20 21:33:39 +02:00
/**
* @brief Class to build mode idle command
*/
class TcModeIdle : public TcBase {
public:
2022-08-15 18:34:26 +02:00
TcModeIdle(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_MODE_IDLE, sequenceCount) {}
2022-04-20 21:33:39 +02:00
};
2023-02-14 14:00:53 +01:00
/**
* @brief Class to build mode idle command
*/
class TcModeSnapshot : public TcBase {
public:
TcModeSnapshot(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_MODE_SNAPSHOT, sequenceCount) {}
};
/**
* @brief Class to build camera take picture command
*/
class TcCamTakePic : public TcBase {
public:
TcCamTakePic(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_CAM_TAKE_PIC, sequenceCount) {}
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
std::string fileName(reinterpret_cast<const char*>(commandData));
if (fileName.size() + sizeof(NULL_TERMINATOR) > MAX_FILENAME_SIZE) {
return FILENAME_TOO_LONG;
}
if (commandDataLen - (fileName.size() + sizeof(NULL_TERMINATOR)) != PARAMETER_SIZE) {
return INVALID_LENGTH;
}
spParams.setFullPayloadLen(commandDataLen);
std::memcpy(payloadStart, commandData, commandDataLen);
return returnvalue::OK;
}
private:
static const size_t MAX_DATA_LENGTH = 286;
2023-02-28 09:13:41 +01:00
static const size_t PARAMETER_SIZE = 28;
};
/**
* @brief Class to build simplex send file command
*/
class TcSimplexSendFile : public TcBase {
public:
TcSimplexSendFile(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_SIMPLEX_SEND_FILE, sequenceCount) {}
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
std::string fileName(reinterpret_cast<const char*>(commandData));
if (fileName.size() + sizeof(NULL_TERMINATOR) > MAX_FILENAME_SIZE) {
return FILENAME_TOO_LONG;
}
spParams.setFullPayloadLen(commandDataLen);
std::memcpy(payloadStart, commandData, commandDataLen);
return returnvalue::OK;
}
private:
static const size_t MAX_DATA_LENGTH = 256;
};
/**
* @brief Class to build downlink data modulate command
*/
class TcDownlinkDataModulate : public TcBase {
public:
TcDownlinkDataModulate(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_DOWNLINK_DATA_MODULATE, sequenceCount) {}
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
spParams.setFullPayloadLen(commandDataLen);
std::memcpy(payloadStart, commandData, commandDataLen);
return returnvalue::OK;
}
private:
static const size_t MAX_DATA_LENGTH = 11;
};
2022-04-20 21:33:39 +02:00
class TcCamcmdSend : public TcBase {
2022-04-22 14:09:08 +02:00
public:
2022-08-15 18:34:26 +02:00
TcCamcmdSend(ploc::SpTcParams params, uint16_t sequenceCount)
: TcBase(params, apid::TC_CAM_CMD_SEND, sequenceCount) {}
2022-04-20 21:33:39 +02:00
2022-04-22 14:09:08 +02:00
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) override {
2022-04-22 14:09:08 +02:00
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
uint16_t dataLen = static_cast<uint16_t>(commandDataLen + sizeof(CARRIAGE_RETURN));
2022-11-07 10:30:09 +01:00
spParams.setFullPayloadLen(sizeof(dataLen) + commandDataLen + sizeof(CARRIAGE_RETURN) +
CRC_SIZE);
2022-08-16 18:37:51 +02:00
auto res = checkPayloadLen();
2022-08-24 17:27:47 +02:00
if (res != returnvalue::OK) {
2022-08-16 18:37:51 +02:00
return res;
}
2022-08-20 12:11:08 +02:00
size_t size = ccsds::HEADER_LEN;
SerializeAdapter::serialize(&dataLen, payloadStart, &size, spParams.maxSize,
SerializeIF::Endianness::BIG);
std::memcpy(payloadStart + sizeof(dataLen), commandData, commandDataLen);
*(payloadStart + sizeof(dataLen) + commandDataLen) = CARRIAGE_RETURN;
2022-08-16 18:37:51 +02:00
2022-08-24 17:27:47 +02:00
return returnvalue::OK;
2022-04-22 14:09:08 +02:00
}
2022-04-20 21:33:39 +02:00
2022-04-22 14:09:08 +02:00
private:
static const uint8_t MAX_DATA_LENGTH = 10;
static const uint8_t CARRIAGE_RETURN = 0xD;
2022-04-20 21:33:39 +02:00
};
2022-03-26 20:47:25 +01:00
} // namespace mpsoc
2022-03-24 17:39:50 +01:00
#endif /* MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_ */