continue dest handler

This commit is contained in:
Robin Müller 2022-08-23 19:37:30 +02:00
parent 95457b1760
commit 9441b4a70e
No known key found for this signature in database
GPG Key ID: 71B58F8A3CDFA9AC
6 changed files with 148 additions and 52 deletions

View File

@ -2,16 +2,32 @@
#include <utility> #include <utility>
#include "fsfw/cfdp/pdu/HeaderReader.h"
#include "fsfw/cfdp/pdu/MetadataPduReader.h"
#include "fsfw/objectmanager.h" #include "fsfw/objectmanager.h"
#include "fsfw/serviceinterface.h"
cfdp::DestHandler::DestHandler(DestHandlerParams params) : p(std::move(params)) {} using namespace returnvalue;
cfdp::DestHandler::DestHandler(DestHandlerParams params, FsfwParams fsfwParams)
: dp(std::move(params)), fp(fsfwParams), tlvVec(params.maxTlvsInOnePdu) {}
ReturnValue_t cfdp::DestHandler::performStateMachine() { ReturnValue_t cfdp::DestHandler::performStateMachine() {
switch (step) { switch (step) {
case TransactionStep::IDLE: { case TransactionStep::IDLE: {
for (const auto& info : p.packetListRef) { ReturnValue_t status = returnvalue::OK;
ReturnValue_t result;
for (const auto& info : dp.packetListRef) {
if (info.pduType == PduType::FILE_DIRECTIVE and
info.directiveType == FileDirectives::METADATA) {
result = handleMetadataPdu(info);
if (result != OK) {
status = result;
} }
} }
}
return status;
}
case TransactionStep::TRANSACTION_START: case TransactionStep::TRANSACTION_START:
break; break;
case TransactionStep::RECEIVING_FILE_DATA_PDUS: case TransactionStep::RECEIVING_FILE_DATA_PDUS:
@ -27,26 +43,86 @@ ReturnValue_t cfdp::DestHandler::performStateMachine() {
} }
ReturnValue_t cfdp::DestHandler::passPacket(PacketInfo packet) { ReturnValue_t cfdp::DestHandler::passPacket(PacketInfo packet) {
if (p.packetListRef.full()) { if (dp.packetListRef.full()) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
p.packetListRef.push_back(packet); dp.packetListRef.push_back(packet);
return returnvalue::OK; return returnvalue::OK;
} }
ReturnValue_t cfdp::DestHandler::initialize() { ReturnValue_t cfdp::DestHandler::initialize() {
if (p.tmStore == nullptr) { if (fp.tmStore == nullptr) {
p.tmStore = ObjectManager::instance()->get<StorageManagerIF>(objects::TM_STORE); fp.tmStore = ObjectManager::instance()->get<StorageManagerIF>(objects::TM_STORE);
if (p.tmStore == nullptr) { if (fp.tmStore == nullptr) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
} }
if (p.tcStore == nullptr) { if (fp.tcStore == nullptr) {
p.tcStore = ObjectManager::instance()->get<StorageManagerIF>(objects::TC_STORE); fp.tcStore = ObjectManager::instance()->get<StorageManagerIF>(objects::TC_STORE);
if (p.tcStore == nullptr) { if (fp.tcStore == nullptr) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
} }
return returnvalue::OK; return returnvalue::OK;
} }
ReturnValue_t cfdp::DestHandler::handleMetadataPdu(const PacketInfo& info) {
// Process metadata PDU
auto constAccessorPair = fp.tcStore->getData(info.storeId);
if (constAccessorPair.first != OK) {
// TODO: This is not a CFDP error. Event and/or warning?
return constAccessorPair.first;
}
cfdp::FileSize fileSize;
cfdp::StringLv sourceFileName;
cfdp::StringLv destFileName;
MetadataInfo metadataInfo(fileSize, sourceFileName, destFileName);
cfdp::Tlv* tlvArrayAsPtr = tlvVec.data();
metadataInfo.setOptionsArray(&tlvArrayAsPtr, std::nullopt, tlvVec.size());
MetadataPduReader reader(constAccessorPair.second.data(), constAccessorPair.second.size(),
metadataInfo);
ReturnValue_t result = reader.parseData();
// TODO: The standard does not really specify what happens if this kind of error happens
// I think it might be a good idea to cache some sort of error code, which
// is translated into a warning and/or event by an upper layer
if (result != OK) {
return handleMetadataParseError(constAccessorPair.second.data(),
constAccessorPair.second.size());
}
return result;
}
ReturnValue_t cfdp::DestHandler::handleMetadataParseError(const uint8_t* rawData, size_t maxSize) {
// TODO: try to extract destination ID for error
// TODO: Invalid metadata PDU.
#if FSFW_CPP_OSTREAM_ENABLED == 1
sif::warning << "Parsing Metadata PDU failed with code " << result << std::endl;
#else
#endif
HeaderReader headerReader(rawData, maxSize);
ReturnValue_t result = headerReader.parseData();
if (result != OK) {
// TODO: Now this really should not happen. Warning or error,
// yield or cache appropriate returnvalue
#if FSFW_CPP_OSTREAM_ENABLED == 1
sif::warning << "Parsing Header failed" << std::endl;
#else
#endif
// TODO: Trigger appropriate event
return result;
}
cfdp::EntityId destId;
headerReader.getDestId(destId);
RemoteEntityCfg* remoteCfg;
if (not dp.remoteCfgTable.getRemoteCfg(destId, &remoteCfg)) {
// TODO: No remote config for dest ID. I consider this a configuration error.
// Warning or error, yield or cache appropriate returnvalue
#if FSFW_CPP_OSTREAM_ENABLED == 1
sif::warning << "No remote config exists for destination ID" << std::endl;
#else
#endif
// TODO: Trigger appropriate event
}
// TODO: Appropriate returnvalue?
return returnvalue::FAILED;
}

View File

@ -28,28 +28,34 @@ struct PacketInfo {
struct DestHandlerParams { struct DestHandlerParams {
DestHandlerParams(LocalEntityCfg cfg, UserBase& user, RemoteConfigTableIF& remoteCfgTable, DestHandlerParams(LocalEntityCfg cfg, UserBase& user, RemoteConfigTableIF& remoteCfgTable,
AcceptsTelemetryIF& packetDest, MessageQueueIF& msgQueue, etl::ilist<PacketInfo>& packetList, uint8_t maxTlvsInOnePdu)
etl::ilist<PacketInfo>& packetList)
: cfg(std::move(cfg)), : cfg(std::move(cfg)),
user(user), user(user),
remoteCfgTable(remoteCfgTable), remoteCfgTable(remoteCfgTable),
packetDest(packetDest),
msgQueue(msgQueue),
packetListRef(packetList) {} packetListRef(packetList) {}
LocalEntityCfg cfg; LocalEntityCfg cfg;
UserBase& user; UserBase& user;
RemoteConfigTableIF& remoteCfgTable; RemoteConfigTableIF& remoteCfgTable;
etl::ilist<PacketInfo>& packetListRef;
uint8_t maxTlvsInOnePdu;
};
struct FsfwParams {
FsfwParams(AcceptsTelemetryIF& packetDest, MessageQueueIF& msgQueue,
EventReportingProxyIF& eventReporter)
: packetDest(packetDest), msgQueue(msgQueue), eventReporter(eventReporter) {}
AcceptsTelemetryIF& packetDest; AcceptsTelemetryIF& packetDest;
MessageQueueIF& msgQueue; MessageQueueIF& msgQueue;
EventReportingProxyIF& eventReporter;
StorageManagerIF* tcStore = nullptr; StorageManagerIF* tcStore = nullptr;
StorageManagerIF* tmStore = nullptr; StorageManagerIF* tmStore = nullptr;
etl::ilist<PacketInfo>& packetListRef;
}; };
class DestHandler { class DestHandler {
public: public:
explicit DestHandler(DestHandlerParams params); explicit DestHandler(DestHandlerParams handlerParams, FsfwParams fsfwParams);
ReturnValue_t performStateMachine(); ReturnValue_t performStateMachine();
@ -57,8 +63,12 @@ class DestHandler {
ReturnValue_t initialize(); ReturnValue_t initialize();
ReturnValue_t handleMetadataPdu(const PacketInfo& info);
ReturnValue_t handleMetadataParseError(const uint8_t* rawData, size_t maxSize);
private: private:
DestHandlerParams p; DestHandlerParams dp;
FsfwParams fp;
enum class TransactionStep { enum class TransactionStep {
IDLE = 0, IDLE = 0,
TRANSACTION_START = 1, TRANSACTION_START = 1,
@ -68,6 +78,7 @@ class DestHandler {
SENDING_FINISHED_PDU = 5 SENDING_FINISHED_PDU = 5
}; };
TransactionStep step = TransactionStep::IDLE; TransactionStep step = TransactionStep::IDLE;
std::vector<cfdp::Tlv> tlvVec;
}; };
} // namespace cfdp } // namespace cfdp

View File

@ -1,22 +1,25 @@
#include "MetadataInfo.h" #include "MetadataInfo.h"
MetadataInfo::MetadataInfo(bool closureRequested, cfdp::ChecksumType checksumType, MetadataInfo::MetadataInfo(bool closureRequested, cfdp::ChecksumType checksumType,
cfdp::FileSize& fileSize, cfdp::Lv& sourceFileName, cfdp::FileSize& fileSize, cfdp::StringLv& sourceFileName,
cfdp::Lv& destFileName) cfdp::StringLv& destFileName)
: closureRequested(closureRequested), : MetadataInfo(fileSize, sourceFileName, destFileName) {
checksumType(checksumType), this->closureRequested = closureRequested;
fileSize(fileSize), this->checksumType = checksumType;
sourceFileName(sourceFileName),
destFileName(destFileName) {}
void MetadataInfo::setOptionsArray(cfdp::Tlv** optionsArray_, const size_t* optionsLen_,
const size_t* maxOptionsLen_) {
this->optionsArray = optionsArray_;
if (maxOptionsLen_ != nullptr) {
this->maxOptionsLen = *maxOptionsLen_;
} }
if (optionsLen_ != nullptr) {
this->optionsLen = *optionsLen_; MetadataInfo::MetadataInfo(cfdp::FileSize& fileSize, cfdp::StringLv& sourceFileName,
cfdp::StringLv& destFileName)
: fileSize(fileSize), sourceFileName(sourceFileName), destFileName(destFileName) {}
void MetadataInfo::setOptionsArray(cfdp::Tlv** optionsArray_, std::optional<size_t> optionsLen_,
std::optional<size_t> maxOptionsLen_) {
this->optionsArray = optionsArray_;
if (maxOptionsLen_) {
this->maxOptionsLen = maxOptionsLen_.value();
}
if (optionsLen_) {
this->optionsLen = optionsLen_.value();
} }
} }
@ -32,7 +35,7 @@ void MetadataInfo::setClosureRequested(bool closureRequested_) {
closureRequested = closureRequested_; closureRequested = closureRequested_;
} }
cfdp::Lv& MetadataInfo::getDestFileName() { return destFileName; } cfdp::StringLv& MetadataInfo::getDestFileName() { return destFileName; }
cfdp::FileSize& MetadataInfo::getFileSize() { return fileSize; } cfdp::FileSize& MetadataInfo::getFileSize() { return fileSize; }
@ -81,9 +84,11 @@ size_t MetadataInfo::getSerializedSize(bool fssLarge) {
return size; return size;
} }
void MetadataInfo::setDestFileName(cfdp::Lv& destFileName_) { this->destFileName = destFileName_; } void MetadataInfo::setDestFileName(cfdp::StringLv& destFileName_) {
this->destFileName = destFileName_;
}
void MetadataInfo::setSourceFileName(cfdp::Lv& sourceFileName_) { void MetadataInfo::setSourceFileName(cfdp::StringLv& sourceFileName_) {
this->sourceFileName = sourceFileName_; this->sourceFileName = sourceFileName_;
} }
@ -95,4 +100,4 @@ size_t MetadataInfo::getOptionsLen() const { return optionsLen; }
void MetadataInfo::setOptionsLen(size_t optionsLen_) { this->optionsLen = optionsLen_; } void MetadataInfo::setOptionsLen(size_t optionsLen_) { this->optionsLen = optionsLen_; }
cfdp::Lv& MetadataInfo::getSourceFileName() { return sourceFileName; } cfdp::StringLv& MetadataInfo::getSourceFileName() { return sourceFileName; }

View File

@ -1,30 +1,35 @@
#ifndef FSFW_SRC_FSFW_CFDP_PDU_METADATAINFO_H_ #ifndef FSFW_SRC_FSFW_CFDP_PDU_METADATAINFO_H_
#define FSFW_SRC_FSFW_CFDP_PDU_METADATAINFO_H_ #define FSFW_SRC_FSFW_CFDP_PDU_METADATAINFO_H_
#include <optional>
#include "fsfw/cfdp/FileSize.h" #include "fsfw/cfdp/FileSize.h"
#include "fsfw/cfdp/definitions.h" #include "fsfw/cfdp/definitions.h"
#include "fsfw/cfdp/tlv/Lv.h" #include "fsfw/cfdp/tlv/Lv.h"
#include "fsfw/cfdp/tlv/StringLv.h"
#include "fsfw/cfdp/tlv/Tlv.h" #include "fsfw/cfdp/tlv/Tlv.h"
class MetadataInfo { class MetadataInfo {
public: public:
MetadataInfo(cfdp::FileSize& fileSize, cfdp::StringLv& sourceFileName,
cfdp::StringLv& destFileName);
MetadataInfo(bool closureRequested, cfdp::ChecksumType checksumType, cfdp::FileSize& fileSize, MetadataInfo(bool closureRequested, cfdp::ChecksumType checksumType, cfdp::FileSize& fileSize,
cfdp::Lv& sourceFileName, cfdp::Lv& destFileName); cfdp::StringLv& sourceFileName, cfdp::StringLv& destFileName);
size_t getSerializedSize(bool fssLarge = false); size_t getSerializedSize(bool fssLarge = false);
void setOptionsArray(cfdp::Tlv** optionsArray, const size_t* optionsLen, void setOptionsArray(cfdp::Tlv** optionsArray, std::optional<size_t> optionsLen,
const size_t* maxOptionsLen); std::optional<size_t> maxOptionsLen);
[[nodiscard]] cfdp::ChecksumType getChecksumType() const; [[nodiscard]] cfdp::ChecksumType getChecksumType() const;
void setChecksumType(cfdp::ChecksumType checksumType); void setChecksumType(cfdp::ChecksumType checksumType);
[[nodiscard]] bool isClosureRequested() const; [[nodiscard]] bool isClosureRequested() const;
void setClosureRequested(bool closureRequested = false); void setClosureRequested(bool closureRequested = false);
void setDestFileName(cfdp::Lv& destFileName); void setDestFileName(cfdp::StringLv& destFileName);
void setSourceFileName(cfdp::Lv& sourceFileName); void setSourceFileName(cfdp::StringLv& sourceFileName);
cfdp::Lv& getDestFileName(); cfdp::StringLv& getDestFileName();
cfdp::Lv& getSourceFileName(); cfdp::StringLv& getSourceFileName();
cfdp::FileSize& getFileSize(); cfdp::FileSize& getFileSize();
[[nodiscard]] bool hasOptions() const; [[nodiscard]] bool hasOptions() const;
@ -37,10 +42,10 @@ class MetadataInfo {
private: private:
bool closureRequested = false; bool closureRequested = false;
cfdp::ChecksumType checksumType; cfdp::ChecksumType checksumType = cfdp::ChecksumType::NULL_CHECKSUM;
cfdp::FileSize& fileSize; cfdp::FileSize& fileSize;
cfdp::Lv& sourceFileName; cfdp::StringLv& sourceFileName;
cfdp::Lv& destFileName; cfdp::StringLv& destFileName;
cfdp::Tlv** optionsArray = nullptr; cfdp::Tlv** optionsArray = nullptr;
size_t optionsLen = 0; size_t optionsLen = 0;

View File

@ -5,7 +5,7 @@
class EventReportingProxyIF { class EventReportingProxyIF {
public: public:
virtual ~EventReportingProxyIF() {} virtual ~EventReportingProxyIF() = default;
virtual void forwardEvent(Event event, uint32_t parameter1 = 0, virtual void forwardEvent(Event event, uint32_t parameter1 = 0,
uint32_t parameter2 = 0) const = 0; uint32_t parameter2 = 0) const = 0;

View File

@ -21,7 +21,7 @@ TEST_CASE("Metadata PDU", "[cfdp][pdu]") {
std::string firstFileName = "hello.txt"; std::string firstFileName = "hello.txt";
cfdp::StringLv sourceFileName(firstFileName); cfdp::StringLv sourceFileName(firstFileName);
cfdp::Lv destFileName; cfdp::StringLv destFileName;
FileSize fileSize(35); FileSize fileSize(35);
MetadataInfo info(false, ChecksumType::MODULAR, fileSize, sourceFileName, destFileName); MetadataInfo info(false, ChecksumType::MODULAR, fileSize, sourceFileName, destFileName);
@ -67,11 +67,10 @@ TEST_CASE("Metadata PDU", "[cfdp][pdu]") {
REQUIRE(mdBuffer[26] == 0); REQUIRE(mdBuffer[26] == 0);
std::string otherFileName = "hello2.txt"; std::string otherFileName = "hello2.txt";
cfdp::Lv otherFileNameLv(reinterpret_cast<const uint8_t*>(otherFileName.data()), cfdp::StringLv otherFileNameLv(otherFileName.data(), otherFileName.size());
otherFileName.size());
info.setSourceFileName(otherFileNameLv); info.setSourceFileName(otherFileNameLv);
size_t sizeOfOptions = options.size(); size_t sizeOfOptions = options.size();
info.setOptionsArray(options.data(), &sizeOfOptions, &sizeOfOptions); info.setOptionsArray(options.data(), sizeOfOptions, sizeOfOptions);
REQUIRE(info.getMaxOptionsLen() == 2); REQUIRE(info.getMaxOptionsLen() == 2);
info.setMaxOptionsLen(3); info.setMaxOptionsLen(3);
REQUIRE(info.getMaxOptionsLen() == 3); REQUIRE(info.getMaxOptionsLen() == 3);
@ -129,7 +128,7 @@ TEST_CASE("Metadata PDU", "[cfdp][pdu]") {
} }
size_t sizeOfOptions = options.size(); size_t sizeOfOptions = options.size();
size_t maxSize = 4; size_t maxSize = 4;
info.setOptionsArray(options.data(), &sizeOfOptions, &maxSize); info.setOptionsArray(options.data(), sizeOfOptions, maxSize);
REQUIRE(info.getOptionsLen() == 2); REQUIRE(info.getOptionsLen() == 2);
info.setChecksumType(cfdp::ChecksumType::CRC_32C); info.setChecksumType(cfdp::ChecksumType::CRC_32C);
info.setClosureRequested(true); info.setClosureRequested(true);
@ -166,9 +165,9 @@ TEST_CASE("Metadata PDU", "[cfdp][pdu]") {
} }
mdBuffer[1] = (36 >> 8) & 0xff; mdBuffer[1] = (36 >> 8) & 0xff;
mdBuffer[2] = 36 & 0xff; mdBuffer[2] = 36 & 0xff;
info.setOptionsArray(nullptr, nullptr, nullptr); info.setOptionsArray(nullptr, std::nullopt, std::nullopt);
REQUIRE(deserializer2.parseData() == cfdp::METADATA_CANT_PARSE_OPTIONS); REQUIRE(deserializer2.parseData() == cfdp::METADATA_CANT_PARSE_OPTIONS);
info.setOptionsArray(options.data(), &sizeOfOptions, nullptr); info.setOptionsArray(options.data(), sizeOfOptions, std::nullopt);
for (size_t maxSz = 0; maxSz < 46; maxSz++) { for (size_t maxSz = 0; maxSz < 46; maxSz++) {
MetadataPduReader invalidSzDeser(mdBuffer.data(), maxSz, info); MetadataPduReader invalidSzDeser(mdBuffer.data(), maxSz, info);
if (not invalidSzDeser.isNull()) { if (not invalidSzDeser.isNull()) {