From 55a663beb20ff5b9435b3dc358e6b869d8353ef8 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:14:38 +0100 Subject: [PATCH 01/26] unittest update --- unittest/testcfg/CatchFactory.cpp | 60 ------------------- unittest/testcfg/FSFWConfig.h | 4 +- unittest/testcfg/objects/CatchFactory.cpp | 56 +++++++++++++++++ unittest/testcfg/{ => objects}/CatchFactory.h | 0 4 files changed, 57 insertions(+), 63 deletions(-) delete mode 100644 unittest/testcfg/CatchFactory.cpp create mode 100644 unittest/testcfg/objects/CatchFactory.cpp rename unittest/testcfg/{ => objects}/CatchFactory.h (100%) diff --git a/unittest/testcfg/CatchFactory.cpp b/unittest/testcfg/CatchFactory.cpp deleted file mode 100644 index c74a8126..00000000 --- a/unittest/testcfg/CatchFactory.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include "CatchFactory.h" - -#include -#include - -#include -#include -#include - -/** - * @brief Produces system objects. - * @details - * Build tasks by using SystemObject Interface (Interface). - * Header files of all tasks must be included - * Please note that an object has to implement the system object interface - * if the interface validity is checked or retrieved later by using the - * get(object_id) function from the ObjectManagerIF. - * - * Framework objects are created first. - * - * @ingroup init - */ -void Factory::produce(void) { - setStaticFrameworkObjectIds(); - new EventManager(objects::EVENT_MANAGER); - new HealthTable(objects::HEALTH_TABLE); - //new InternalErrorReporter(objects::INTERNAL_ERROR_REPORTER); - - { - static constexpr uint8_t NUMBER_OF_POOLS = 5; - const uint16_t element_sizes[NUMBER_OF_POOLS] = {16, 32, 64, 128, 1024}; - const uint16_t n_elements[NUMBER_OF_POOLS] = {100, 50, 25, 15, 5}; - new PoolManager(objects::TC_STORE, element_sizes, - n_elements); - } - - { - static constexpr uint8_t NUMBER_OF_POOLS = 5; - const uint16_t element_sizes[NUMBER_OF_POOLS] = {16, 32, 64, 128, 1024}; - const uint16_t n_elements[NUMBER_OF_POOLS] = {100, 50, 25, 15, 5}; - new PoolManager(objects::TM_STORE, element_sizes, - n_elements); - } - - { - static constexpr uint8_t NUMBER_OF_POOLS = 6; - const uint16_t element_sizes[NUMBER_OF_POOLS] = {32, 64, 512, - 1024, 2048, 4096}; - const uint16_t n_elements[NUMBER_OF_POOLS] = {200, 100, 50, 25, 15, 5}; - new PoolManager(objects::IPC_STORE, element_sizes, - n_elements); - } - -} - -void Factory::setStaticFrameworkObjectIds() { - -} - - diff --git a/unittest/testcfg/FSFWConfig.h b/unittest/testcfg/FSFWConfig.h index 4fb224c1..59934560 100644 --- a/unittest/testcfg/FSFWConfig.h +++ b/unittest/testcfg/FSFWConfig.h @@ -29,13 +29,11 @@ //! additional output which requires the translation files translateObjects //! and translateEvents (and their compiles source files) #if FSFW_OBJ_EVENT_TRANSLATION == 1 -#define FSFW_DEBUG_OUTPUT 1 //! Specify whether info events are printed too. -#define FSFW_DEBUG_INFO 1 +#define FSFW_DEBUG_INFO 1 #include #include #else -#define FSFW_DEBUG_OUTPUT 0 #endif //! When using the newlib nano library, C99 support for stdio facilities diff --git a/unittest/testcfg/objects/CatchFactory.cpp b/unittest/testcfg/objects/CatchFactory.cpp new file mode 100644 index 00000000..3177212f --- /dev/null +++ b/unittest/testcfg/objects/CatchFactory.cpp @@ -0,0 +1,56 @@ +#include "CatchFactory.h" + +#include +#include + +#include +#include +#include + +/** + * @brief Produces system objects. + * @details + * Build tasks by using SystemObject Interface (Interface). + * Header files of all tasks must be included + * Please note that an object has to implement the system object interface + * if the interface validity is checked or retrieved later by using the + * get(object_id) function from the ObjectManagerIF. + * + * Framework objects are created first. + * + * @ingroup init + */ +void Factory::produce(void) { + setStaticFrameworkObjectIds(); + new EventManager(objects::EVENT_MANAGER); + new HealthTable(objects::HEALTH_TABLE); + new InternalErrorReporter(objects::INTERNAL_ERROR_REPORTER); + + { + PoolManager::LocalPoolConfig poolCfg = { + {100, 16}, {50, 32}, {25, 64} , {15, 128}, {5, 1024} + }; + new PoolManager(objects::TC_STORE, poolCfg); + } + + { + PoolManager::LocalPoolConfig poolCfg = { + {100, 16}, {50, 32}, {25, 64} , {15, 128}, {5, 1024} + }; + new PoolManager(objects::TM_STORE, poolCfg); + } + + { + PoolManager::LocalPoolConfig poolCfg = { + {100, 16}, {50, 32}, {25, 64} , {15, 128}, {5, 1024} + }; + new PoolManager(objects::IPC_STORE, poolCfg); + } + +} + +void Factory::setStaticFrameworkObjectIds() { + +} + + diff --git a/unittest/testcfg/CatchFactory.h b/unittest/testcfg/objects/CatchFactory.h similarity index 100% rename from unittest/testcfg/CatchFactory.h rename to unittest/testcfg/objects/CatchFactory.h From 25db9bc9ed8bb53b211d1e0ea5b46ed6967888c6 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:30:39 +0100 Subject: [PATCH 02/26] tmtcservices update --- pus/servicepackets/Service1Packets.h | 8 ++--- tcdistribution/PUSDistributor.cpp | 4 +-- tmtcservices/AcceptsTelecommandsIF.h | 12 +++---- tmtcservices/AcceptsTelemetryIF.h | 9 ++--- tmtcservices/AcceptsVerifyMessageIF.h | 6 ++-- tmtcservices/CommandingServiceBase.cpp | 40 +++++++++++----------- tmtcservices/CommandingServiceBase.h | 10 +++--- tmtcservices/PusServiceBase.cpp | 47 ++++++++++++++------------ tmtcservices/PusServiceBase.h | 13 +++---- tmtcservices/PusVerificationReport.cpp | 2 +- tmtcservices/PusVerificationReport.h | 2 -- tmtcservices/ServiceTypes.h | 8 +---- tmtcservices/SourceSequenceCounter.h | 12 ++----- tmtcservices/TmTcBridge.cpp | 8 ++--- tmtcservices/TmTcBridge.h | 10 +++--- tmtcservices/TmTcMessage.cpp | 11 +++--- tmtcservices/TmTcMessage.h | 16 ++++----- tmtcservices/VerificationCodes.h | 2 +- 18 files changed, 107 insertions(+), 113 deletions(-) diff --git a/pus/servicepackets/Service1Packets.h b/pus/servicepackets/Service1Packets.h index ecb62693..2249b4b0 100644 --- a/pus/servicepackets/Service1Packets.h +++ b/pus/servicepackets/Service1Packets.h @@ -49,7 +49,7 @@ public: if (result != HasReturnvaluesIF::RETURN_OK) { return result; } - if (failureSubtype == TC_VERIFY::PROGRESS_FAILURE) { + if (failureSubtype == tc_verification::PROGRESS_FAILURE) { result = SerializeAdapter::serialize(&stepNumber, buffer, size, maxSize, streamEndianness); if (result != HasReturnvaluesIF::RETURN_OK) { @@ -77,7 +77,7 @@ public: size_t size = 0; size += SerializeAdapter::getSerializedSize(&packetId); size += sizeof(packetSequenceControl); - if(failureSubtype==TC_VERIFY::PROGRESS_FAILURE){ + if(failureSubtype==tc_verification::PROGRESS_FAILURE){ size += SerializeAdapter::getSerializedSize(&stepNumber); } size += SerializeAdapter::getSerializedSize(&errorCode); @@ -131,7 +131,7 @@ public: if (result != HasReturnvaluesIF::RETURN_OK) { return result; } - if (subtype == TC_VERIFY::PROGRESS_SUCCESS) { + if (subtype == tc_verification::PROGRESS_SUCCESS) { result = SerializeAdapter::serialize(&stepNumber, buffer, size, maxSize, streamEndianness); if (result != HasReturnvaluesIF::RETURN_OK) { @@ -145,7 +145,7 @@ public: size_t size = 0; size += SerializeAdapter::getSerializedSize(&packetId); size += sizeof(packetSequenceControl); - if(subtype == TC_VERIFY::PROGRESS_SUCCESS){ + if(subtype == tc_verification::PROGRESS_SUCCESS){ size += SerializeAdapter::getSerializedSize(&stepNumber); } return size; diff --git a/tcdistribution/PUSDistributor.cpp b/tcdistribution/PUSDistributor.cpp index d964202f..8e5b94cc 100644 --- a/tcdistribution/PUSDistributor.cpp +++ b/tcdistribution/PUSDistributor.cpp @@ -77,14 +77,14 @@ ReturnValue_t PUSDistributor::callbackAfterSending(ReturnValue_t queueStatus) { tcStatus = queueStatus; } if (tcStatus != RETURN_OK) { - this->verifyChannel.sendFailureReport(TC_VERIFY::ACCEPTANCE_FAILURE, + this->verifyChannel.sendFailureReport(tc_verification::ACCEPTANCE_FAILURE, currentPacket, tcStatus); // A failed packet is deleted immediately after reporting, // otherwise it will block memory. currentPacket->deletePacket(); return RETURN_FAILED; } else { - this->verifyChannel.sendSuccessReport(TC_VERIFY::ACCEPTANCE_SUCCESS, + this->verifyChannel.sendSuccessReport(tc_verification::ACCEPTANCE_SUCCESS, currentPacket); return RETURN_OK; } diff --git a/tmtcservices/AcceptsTelecommandsIF.h b/tmtcservices/AcceptsTelecommandsIF.h index 76d10a59..bff0e955 100644 --- a/tmtcservices/AcceptsTelecommandsIF.h +++ b/tmtcservices/AcceptsTelecommandsIF.h @@ -1,5 +1,5 @@ -#ifndef ACCEPTSTELECOMMANDSIF_H_ -#define ACCEPTSTELECOMMANDSIF_H_ +#ifndef FRAMEWORK_TMTCSERVICES_ACCEPTSTELECOMMANDSIF_H_ +#define FRAMEWORK_TMTCSERVICES_ACCEPTSTELECOMMANDSIF_H_ #include "../ipc/MessageQueueSenderIF.h" @@ -12,7 +12,7 @@ class AcceptsTelecommandsIF { public: static const uint8_t INTERFACE_ID = CLASS_ID::ACCEPTS_TELECOMMANDS_IF; - static const ReturnValue_t ACTIVITY_STARTED = MAKE_RETURN_CODE(1); + static const ReturnValue_t ACTIVITY_STARTED = MAKE_RETURN_CODE(1); // is this used anywhere or can it be removed? static const ReturnValue_t INVALID_SUBSERVICE = MAKE_RETURN_CODE(2); static const ReturnValue_t ILLEGAL_APPLICATION_DATA = MAKE_RETURN_CODE(3); static const ReturnValue_t SEND_TM_FAILED = MAKE_RETURN_CODE(4); @@ -26,9 +26,9 @@ public: /** * @brief Getter for the service id. * @details Any receiving service (at least any PUS service) shall have a - * service id. If the receiver can handle Telecommands, but for + * service ID. If the receiver can handle Telecommands, but for * some reason has no service id, it shall return 0. - * @return The service id or 0. + * @return The service ID or 0. */ virtual uint16_t getIdentifier() = 0; /** @@ -40,4 +40,4 @@ public: }; -#endif /* ACCEPTSTELECOMMANDSIF_H_ */ +#endif /* FRAMEWORK_TMTCSERVICES_ACCEPTSTELECOMMANDSIF_H_ */ diff --git a/tmtcservices/AcceptsTelemetryIF.h b/tmtcservices/AcceptsTelemetryIF.h index 2325dbe0..43173d89 100644 --- a/tmtcservices/AcceptsTelemetryIF.h +++ b/tmtcservices/AcceptsTelemetryIF.h @@ -1,5 +1,5 @@ -#ifndef ACCEPTSTELEMETRYIF_H_ -#define ACCEPTSTELEMETRYIF_H_ +#ifndef FSFW_TMTCSERVICES_ACCEPTSTELEMETRYIF_H_ +#define FSFW_TMTCSERVICES_ACCEPTSTELEMETRYIF_H_ #include "../ipc/MessageQueueSenderIF.h" /** @@ -20,7 +20,8 @@ public: * receiving message queue. * @return The telemetry reception message queue id. */ - virtual MessageQueueId_t getReportReceptionQueue(uint8_t virtualChannel = 0) = 0; + virtual MessageQueueId_t getReportReceptionQueue( + uint8_t virtualChannel = 0) = 0; }; -#endif /* ACCEPTSTELEMETRYIF_H_ */ +#endif /* FSFW_TMTCSERVICES_ACCEPTSTELEMETRYIF_H_ */ diff --git a/tmtcservices/AcceptsVerifyMessageIF.h b/tmtcservices/AcceptsVerifyMessageIF.h index c9318ab0..d16def4d 100644 --- a/tmtcservices/AcceptsVerifyMessageIF.h +++ b/tmtcservices/AcceptsVerifyMessageIF.h @@ -1,5 +1,5 @@ -#ifndef ACCEPTSVERIFICATIONMESSAGEIF_H_ -#define ACCEPTSVERIFICATIONMESSAGEIF_H_ +#ifndef FSFW_TMTCSERVICES_ACCEPTSVERIFICATIONMESSAGEIF_H_ +#define FSFW_TMTCSERVICES_ACCEPTSVERIFICATIONMESSAGEIF_H_ #include "../ipc/MessageQueueSenderIF.h" @@ -12,4 +12,4 @@ public: }; -#endif /* ACCEPTSVERIFICATIONMESSAGEIF_H_ */ +#endif /* FSFW_TMTCSERVICES_ACCEPTSVERIFICATIONMESSAGEIF_H_ */ diff --git a/tmtcservices/CommandingServiceBase.cpp b/tmtcservices/CommandingServiceBase.cpp index 0ebc3944..ed765ecc 100644 --- a/tmtcservices/CommandingServiceBase.cpp +++ b/tmtcservices/CommandingServiceBase.cpp @@ -1,9 +1,9 @@ -#include "../tcdistribution/PUSDistributorIF.h" #include "AcceptsTelemetryIF.h" -#include "../objectmanager/ObjectManagerIF.h" - #include "CommandingServiceBase.h" #include "TmTcMessage.h" + +#include "../tcdistribution/PUSDistributorIF.h" +#include "../objectmanager/ObjectManagerIF.h" #include "../ipc/QueueFactory.h" #include "../tmtcpacket/pus/TcPacketStored.h" #include "../tmtcpacket/pus/TmPacketStored.h" @@ -149,13 +149,13 @@ void CommandingServiceBase::handleCommandMessage(CommandMessage* reply) { default: if (isStep) { verificationReporter.sendFailureReport( - TC_VERIFY::PROGRESS_FAILURE, iter->second.tcInfo.ackFlags, + tc_verification::PROGRESS_FAILURE, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, result, ++iter->second.step, failureParameter1, failureParameter2); } else { verificationReporter.sendFailureReport( - TC_VERIFY::COMPLETION_FAILURE, iter->second.tcInfo.ackFlags, + tc_verification::COMPLETION_FAILURE, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, result, 0, failureParameter1, failureParameter2); } @@ -184,13 +184,13 @@ void CommandingServiceBase::handleReplyHandlerResult(ReturnValue_t result, if (sendResult == RETURN_OK) { if (isStep and result != NO_STEP_MESSAGE) { verificationReporter.sendSuccessReport( - TC_VERIFY::PROGRESS_SUCCESS, + tc_verification::PROGRESS_SUCCESS, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, ++iter->second.step); } else { verificationReporter.sendSuccessReport( - TC_VERIFY::COMPLETION_SUCCESS, + tc_verification::COMPLETION_SUCCESS, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, 0); checkAndExecuteFifo(iter); @@ -200,14 +200,14 @@ void CommandingServiceBase::handleReplyHandlerResult(ReturnValue_t result, if (isStep) { nextCommand->clearCommandMessage(); verificationReporter.sendFailureReport( - TC_VERIFY::PROGRESS_FAILURE, iter->second.tcInfo.ackFlags, + tc_verification::PROGRESS_FAILURE, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, sendResult, ++iter->second.step, failureParameter1, failureParameter2); } else { nextCommand->clearCommandMessage(); verificationReporter.sendFailureReport( - TC_VERIFY::COMPLETION_FAILURE, + tc_verification::COMPLETION_FAILURE, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, sendResult, 0, failureParameter1, failureParameter2); @@ -232,14 +232,14 @@ void CommandingServiceBase::handleRequestQueue() { if ((packet.getSubService() == 0) or (isValidSubservice(packet.getSubService()) != RETURN_OK)) { - rejectPacket(TC_VERIFY::START_FAILURE, &packet, INVALID_SUBSERVICE); + rejectPacket(tc_verification::START_FAILURE, &packet, INVALID_SUBSERVICE); continue; } result = getMessageQueueAndObject(packet.getSubService(), packet.getApplicationData(), packet.getApplicationDataSize(), &queue, &objectId); if (result != HasReturnvaluesIF::RETURN_OK) { - rejectPacket(TC_VERIFY::START_FAILURE, &packet, result); + rejectPacket(tc_verification::START_FAILURE, &packet, result); continue; } @@ -250,14 +250,14 @@ void CommandingServiceBase::handleRequestQueue() { if (iter != commandMap.end()) { result = iter->second.fifo.insert(address); if (result != RETURN_OK) { - rejectPacket(TC_VERIFY::START_FAILURE, &packet, OBJECT_BUSY); + rejectPacket(tc_verification::START_FAILURE, &packet, OBJECT_BUSY); } } else { CommandInfo newInfo; //Info will be set by startExecution if neccessary newInfo.objectId = objectId; result = commandMap.insert(queue, newInfo, &iter); if (result != RETURN_OK) { - rejectPacket(TC_VERIFY::START_FAILURE, &packet, BUSY); + rejectPacket(tc_verification::START_FAILURE, &packet, BUSY); } else { startExecution(&packet, iter); } @@ -338,10 +338,10 @@ void CommandingServiceBase::startExecution(TcPacketStored *storedPacket, iter->second.tcInfo.tcPacketId = storedPacket->getPacketId(); iter->second.tcInfo.tcSequenceControl = storedPacket->getPacketSequenceControl(); - acceptPacket(TC_VERIFY::START_SUCCESS, storedPacket); + acceptPacket(tc_verification::START_SUCCESS, storedPacket); } else { command.clearCommandMessage(); - rejectPacket(TC_VERIFY::START_FAILURE, storedPacket, sendResult); + rejectPacket(tc_verification::START_FAILURE, storedPacket, sendResult); checkAndExecuteFifo(iter); } break; @@ -352,18 +352,18 @@ void CommandingServiceBase::startExecution(TcPacketStored *storedPacket, &command); } if (sendResult == RETURN_OK) { - verificationReporter.sendSuccessReport(TC_VERIFY::START_SUCCESS, + verificationReporter.sendSuccessReport(tc_verification::START_SUCCESS, storedPacket); - acceptPacket(TC_VERIFY::COMPLETION_SUCCESS, storedPacket); + acceptPacket(tc_verification::COMPLETION_SUCCESS, storedPacket); checkAndExecuteFifo(iter); } else { command.clearCommandMessage(); - rejectPacket(TC_VERIFY::START_FAILURE, storedPacket, sendResult); + rejectPacket(tc_verification::START_FAILURE, storedPacket, sendResult); checkAndExecuteFifo(iter); } break; default: - rejectPacket(TC_VERIFY::START_FAILURE, storedPacket, result); + rejectPacket(tc_verification::START_FAILURE, storedPacket, result); checkAndExecuteFifo(iter); break; } @@ -414,7 +414,7 @@ void CommandingServiceBase::checkTimeout() { for (iter = commandMap.begin(); iter != commandMap.end(); ++iter) { if ((iter->second.uptimeOfStart + (timeoutSeconds * 1000)) < uptime) { verificationReporter.sendFailureReport( - TC_VERIFY::COMPLETION_FAILURE, iter->second.tcInfo.ackFlags, + tc_verification::COMPLETION_FAILURE, iter->second.tcInfo.ackFlags, iter->second.tcInfo.tcPacketId, iter->second.tcInfo.tcSequenceControl, TIMEOUT); checkAndExecuteFifo(iter); diff --git a/tmtcservices/CommandingServiceBase.h b/tmtcservices/CommandingServiceBase.h index 252b6943..3611d7c6 100644 --- a/tmtcservices/CommandingServiceBase.h +++ b/tmtcservices/CommandingServiceBase.h @@ -1,18 +1,20 @@ #ifndef FSFW_TMTCSERVICES_COMMANDINGSERVICEBASE_H_ #define FSFW_TMTCSERVICES_COMMANDINGSERVICEBASE_H_ +#include "AcceptsTelecommandsIF.h" +#include "VerificationReporter.h" + #include "../objectmanager/SystemObject.h" #include "../storagemanager/StorageManagerIF.h" #include "../tasks/ExecutableObjectIF.h" #include "../ipc/MessageQueueIF.h" -#include "AcceptsTelecommandsIF.h" - -#include "VerificationReporter.h" #include "../ipc/CommandMessage.h" #include "../container/FixedMap.h" #include "../container/FIFO.h" #include "../serialize/SerializeIF.h" +#include + class TcPacketStored; namespace Factory{ @@ -40,7 +42,7 @@ class CommandingServiceBase: public SystemObject, friend void (Factory::setStaticFrameworkObjectIds)(); public: // We could make this configurable via preprocessor and the FSFWConfig file. - static constexpr uint8_t COMMAND_INFO_FIFO_DEPTH = 3; + static constexpr uint8_t COMMAND_INFO_FIFO_DEPTH = FSFW_CSB_FIFO_DEPTH; static const uint8_t INTERFACE_ID = CLASS_ID::COMMAND_SERVICE_BASE; diff --git a/tmtcservices/PusServiceBase.cpp b/tmtcservices/PusServiceBase.cpp index d35944a4..cb5a1247 100644 --- a/tmtcservices/PusServiceBase.cpp +++ b/tmtcservices/PusServiceBase.cpp @@ -1,9 +1,10 @@ -#include "../serviceinterface/ServiceInterfaceStream.h" -#include "../tcdistribution/PUSDistributorIF.h" -#include "AcceptsTelemetryIF.h" #include "PusServiceBase.h" +#include "AcceptsTelemetryIF.h" #include "PusVerificationReport.h" #include "TmTcMessage.h" + +#include "../serviceinterface/ServiceInterfaceStream.h" +#include "../tcdistribution/PUSDistributorIF.h" #include "../ipc/QueueFactory.h" object_id_t PusServiceBase::packetSource = 0; @@ -41,9 +42,14 @@ void PusServiceBase::handleRequestQueue() { ReturnValue_t result = RETURN_FAILED; for (uint8_t count = 0; count < PUS_SERVICE_MAX_RECEPTION; count++) { ReturnValue_t status = this->requestQueue->receiveMessage(&message); - // debug << "PusServiceBase::performOperation: Receiving from MQ ID: " - // << std::hex << this->requestQueue.getId() - // << std::dec << " returned: " << status << std::endl; +// if(status != MessageQueueIF::EMPTY) { +// sif::debug << "PusServiceBase::performOperation: Receiving from " +// << "MQ ID: " << std::hex << "0x" << std::setw(8) +// << std::setfill('0') << this->requestQueue->getId() +// << std::dec << " returned: " << status << std::setfill(' ') +// << std::endl; +// } + if (status == RETURN_OK) { this->currentPacket.setStoreAddress(message.getStorageId()); //info << "Service " << (uint16_t) this->serviceId << @@ -55,11 +61,11 @@ void PusServiceBase::handleRequestQueue() { // ": handleRequest returned: " << (int)return_code << std::endl; if (result == RETURN_OK) { this->verifyReporter.sendSuccessReport( - TC_VERIFY::COMPLETION_SUCCESS, &this->currentPacket); + tc_verification::COMPLETION_SUCCESS, &this->currentPacket); } else { this->verifyReporter.sendFailureReport( - TC_VERIFY::COMPLETION_FAILURE, &this->currentPacket, + tc_verification::COMPLETION_FAILURE, &this->currentPacket, result, 0, errorParameter1, errorParameter2); } this->currentPacket.deletePacket(); @@ -74,9 +80,8 @@ void PusServiceBase::handleRequestQueue() { } else { sif::error << "PusServiceBase::performOperation: Service " - << (uint16_t) this->serviceId - << ": Error receiving packet. Code: " << std::hex << status - << std::dec << std::endl; + << this->serviceId << ": Error receiving packet. Code: " + << std::hex << status << std::dec << std::endl; } } } @@ -98,19 +103,17 @@ ReturnValue_t PusServiceBase::initialize() { packetDestination); PUSDistributorIF* distributor = objectManager->get( packetSource); - if ((destService != nullptr) && (distributor != nullptr)) { - this->requestQueue->setDefaultDestination( - destService->getReportReceptionQueue()); - distributor->registerService(this); - return RETURN_OK; - } - else { + if (destService == nullptr or distributor == nullptr) { sif::error << "PusServiceBase::PusServiceBase: Service " - << (uint32_t) this->serviceId << ": Configuration error." - << " Make sure packetSource and packetDestination are defined " - "correctly" << std::endl; - return RETURN_FAILED; + << this->serviceId << ": Configuration error. Make sure " + << "packetSource and packetDestination are defined correctly" + << std::endl; + return ObjectManagerIF::CHILD_INIT_FAILED; } + this->requestQueue->setDefaultDestination( + destService->getReportReceptionQueue()); + distributor->registerService(this); + return HasReturnvaluesIF::RETURN_OK; } ReturnValue_t PusServiceBase::initializeAfterTaskCreation() { diff --git a/tmtcservices/PusServiceBase.h b/tmtcservices/PusServiceBase.h index 98d65efb..4d3d99bc 100644 --- a/tmtcservices/PusServiceBase.h +++ b/tmtcservices/PusServiceBase.h @@ -1,14 +1,15 @@ -#ifndef FRAMEWORK_TMTCSERVICES_PUSSERVICEBASE_H_ -#define FRAMEWORK_TMTCSERVICES_PUSSERVICEBASE_H_ +#ifndef FSFW_TMTCSERVICES_PUSSERVICEBASE_H_ +#define FSFW_TMTCSERVICES_PUSSERVICEBASE_H_ + +#include "AcceptsTelecommandsIF.h" +#include "VerificationCodes.h" +#include "VerificationReporter.h" #include "../objectmanager/ObjectManagerIF.h" #include "../objectmanager/SystemObject.h" #include "../returnvalues/HasReturnvaluesIF.h" #include "../tasks/ExecutableObjectIF.h" #include "../tmtcpacket/pus/TcPacketStored.h" -#include "AcceptsTelecommandsIF.h" -#include "VerificationCodes.h" -#include "VerificationReporter.h" #include "../ipc/MessageQueueIF.h" namespace Factory{ @@ -156,4 +157,4 @@ private: void handleRequestQueue(); }; -#endif /* PUSSERVICEBASE_H_ */ +#endif /* FSFW_TMTCSERVICES_PUSSERVICEBASE_H_ */ diff --git a/tmtcservices/PusVerificationReport.cpp b/tmtcservices/PusVerificationReport.cpp index bfad9ec5..c64e5feb 100644 --- a/tmtcservices/PusVerificationReport.cpp +++ b/tmtcservices/PusVerificationReport.cpp @@ -1,5 +1,5 @@ #include "../serialize/SerializeAdapter.h" -#include "PusVerificationReport.h" +#include "../tmtcservices/PusVerificationReport.h" PusVerificationMessage::PusVerificationMessage() { } diff --git a/tmtcservices/PusVerificationReport.h b/tmtcservices/PusVerificationReport.h index 88954cfd..9dce95ac 100644 --- a/tmtcservices/PusVerificationReport.h +++ b/tmtcservices/PusVerificationReport.h @@ -7,8 +7,6 @@ #include "../tmtcpacket/pus/TcPacketBase.h" #include "../returnvalues/HasReturnvaluesIF.h" -#include - class PusVerificationMessage: public MessageQueueMessage { private: struct verifciationMessageContent { diff --git a/tmtcservices/ServiceTypes.h b/tmtcservices/ServiceTypes.h index 1f5bff42..552601f9 100644 --- a/tmtcservices/ServiceTypes.h +++ b/tmtcservices/ServiceTypes.h @@ -1,13 +1,7 @@ -/** - * @file ServiceTypes.h - * @brief This file defines the ServiceTypes class. - * @date 11.04.2013 - * @author baetz - */ - #ifndef SERVICETYPES_H_ #define SERVICETYPES_H_ +// SHOULDDO: This is a duplication of existing configuration structures. Delete it? namespace SERVICE { enum ServiceTypes { TELECOMMAND_VERIFICATION = 1, diff --git a/tmtcservices/SourceSequenceCounter.h b/tmtcservices/SourceSequenceCounter.h index 1cc58758..2b30a53f 100644 --- a/tmtcservices/SourceSequenceCounter.h +++ b/tmtcservices/SourceSequenceCounter.h @@ -1,12 +1,6 @@ -/** - * @file SourceSequenceCounter.h - * @brief This file defines the SourceSequenceCounter class. - * @date 04.02.2013 - * @author baetz - */ +#ifndef FSFW_TMTCSERVICES_SOURCESEQUENCECOUNTER_H_ +#define FSFW_TMTCSERVICES_SOURCESEQUENCECOUNTER_H_ -#ifndef SOURCESEQUENCECOUNTER_H_ -#define SOURCESEQUENCECOUNTER_H_ #include "../tmtcpacket/SpacePacketBase.h" class SourceSequenceCounter { @@ -27,4 +21,4 @@ public: }; -#endif /* SOURCESEQUENCECOUNTER_H_ */ +#endif /* FSFW_TMTCSERVICES_SOURCESEQUENCECOUNTER_H_ */ diff --git a/tmtcservices/TmTcBridge.cpp b/tmtcservices/TmTcBridge.cpp index 8c2f15e5..b4e9967b 100644 --- a/tmtcservices/TmTcBridge.cpp +++ b/tmtcservices/TmTcBridge.cpp @@ -1,7 +1,6 @@ -#include "../tmtcservices/TmTcBridge.h" +#include "TmTcBridge.h" #include "../ipc/QueueFactory.h" -#include "../tmtcservices/AcceptsTelecommandsIF.h" #include "../serviceinterface/ServiceInterfaceStream.h" #include "../globalfunctions/arrayprinter.h" @@ -95,8 +94,9 @@ ReturnValue_t TmTcBridge::handleTm() { ReturnValue_t status = HasReturnvaluesIF::RETURN_OK; ReturnValue_t result = handleTmQueue(); if(result != RETURN_OK) { - sif::error << "TmTcBridge::handleTm: Error handling TM queue!" - << std::endl; + sif::error << "TmTcBridge::handleTm: Error handling TM queue with " + << "error code 0x" << std::hex << result << std::dec + << "!" << std::endl; status = result; } diff --git a/tmtcservices/TmTcBridge.h b/tmtcservices/TmTcBridge.h index 62cfdaac..0177648c 100644 --- a/tmtcservices/TmTcBridge.h +++ b/tmtcservices/TmTcBridge.h @@ -1,13 +1,13 @@ -#ifndef FRAMEWORK_TMTCSERVICES_TMTCBRIDGE_H_ -#define FRAMEWORK_TMTCSERVICES_TMTCBRIDGE_H_ +#ifndef FSFW_TMTCSERVICES_TMTCBRIDGE_H_ +#define FSFW_TMTCSERVICES_TMTCBRIDGE_H_ +#include "AcceptsTelemetryIF.h" +#include "AcceptsTelecommandsIF.h" #include "../objectmanager/SystemObject.h" -#include "../tmtcservices/AcceptsTelemetryIF.h" #include "../tasks/ExecutableObjectIF.h" #include "../ipc/MessageQueueIF.h" #include "../storagemanager/StorageManagerIF.h" -#include "../tmtcservices/AcceptsTelecommandsIF.h" #include "../container/DynamicFIFO.h" #include "../tmtcservices/TmTcMessage.h" @@ -159,4 +159,4 @@ protected: }; -#endif /* FRAMEWORK_TMTCSERVICES_TMTCBRIDGE_H_ */ +#endif /* FSFW_TMTCSERVICES_TMTCBRIDGE_H_ */ diff --git a/tmtcservices/TmTcMessage.cpp b/tmtcservices/TmTcMessage.cpp index 987bd232..ae028315 100644 --- a/tmtcservices/TmTcMessage.cpp +++ b/tmtcservices/TmTcMessage.cpp @@ -1,5 +1,6 @@ #include "TmTcMessage.h" -#include + +#include TmTcMessage::TmTcMessage() { @@ -15,15 +16,15 @@ store_address_t TmTcMessage::getStorageId() { return temp_id; } -TmTcMessage::TmTcMessage(store_address_t store_id) { +TmTcMessage::TmTcMessage(store_address_t storeId) { this->messageSize += sizeof(store_address_t); - this->setStorageId(store_id); + this->setStorageId(storeId); } size_t TmTcMessage::getMinimumMessageSize() { return this->HEADER_SIZE + sizeof(store_address_t); } -void TmTcMessage::setStorageId(store_address_t store_id) { - memcpy(this->getData(), &store_id, sizeof(store_address_t) ); +void TmTcMessage::setStorageId(store_address_t storeId) { + memcpy(this->getData(), &storeId, sizeof(store_address_t) ); } diff --git a/tmtcservices/TmTcMessage.h b/tmtcservices/TmTcMessage.h index b5e1ff8d..41fe198a 100644 --- a/tmtcservices/TmTcMessage.h +++ b/tmtcservices/TmTcMessage.h @@ -1,5 +1,5 @@ -#ifndef TMTCMESSAGE_H_ -#define TMTCMESSAGE_H_ +#ifndef FSFW_TMTCSERVICES_TMTCMESSAGE_H_ +#define FSFW_TMTCSERVICES_TMTCMESSAGE_H_ #include "../ipc/MessageQueueMessage.h" #include "../storagemanager/StorageManagerIF.h" @@ -10,13 +10,13 @@ * a packet stored in one of the IPC stores (typically a special TM and * a special TC store). This makes passing commands very simple and * efficient. - * \ingroup message_queue + * @ingroup message_queue */ class TmTcMessage : public MessageQueueMessage { protected: /** * @brief This call always returns the same fixed size of the message. - * @return Returns HEADER_SIZE + \c sizeof(store_address_t). + * @return Returns HEADER_SIZE + @c sizeof(store_address_t). */ size_t getMinimumMessageSize(); public: @@ -29,7 +29,7 @@ public: * into the message. * @param packet_id The packet id to put into the message. */ - TmTcMessage( store_address_t packet_id ); + TmTcMessage( store_address_t packetId ); /** * @brief The class's destructor is empty. */ @@ -42,9 +42,9 @@ public: /** * @brief In some cases it might be useful to have a setter for packet id * as well. - * @param packet_id The packet id to put into the message. + * @param packetId The packet id to put into the message. */ - void setStorageId( store_address_t packet_id ); + void setStorageId( store_address_t packetId ); }; -#endif /* TMTCMESSAGE_H_ */ +#endif /* FSFW_TMTCSERVICES_TMTCMESSAGE_H_ */ diff --git a/tmtcservices/VerificationCodes.h b/tmtcservices/VerificationCodes.h index e3e89b5a..35ad6819 100644 --- a/tmtcservices/VerificationCodes.h +++ b/tmtcservices/VerificationCodes.h @@ -1,7 +1,7 @@ #ifndef VERIFICATIONCODES_H_ #define VERIFICATIONCODES_H_ -namespace TC_VERIFY { +namespace tc_verification { enum verification_flags { NONE = 0b0000, From 336b43572f1bb928be5475c2eabebdfa6d53a587 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:46:33 +0100 Subject: [PATCH 03/26] linux update --- ipc/MutexFactory.h | 6 +++--- osal/linux/BinarySemaphore.cpp | 2 +- osal/linux/Clock.cpp | 14 +++++++------- osal/linux/MessageQueue.cpp | 1 + osal/linux/Mutex.h | 5 ++--- osal/linux/MutexFactory.cpp | 3 ++- osal/linux/PosixThread.cpp | 10 +++++++--- osal/linux/SemaphoreFactory.cpp | 3 ++- osal/linux/TaskFactory.cpp | 1 + osal/linux/Timer.cpp | 3 ++- tasks/TaskFactory.h | 8 ++++---- 11 files changed, 32 insertions(+), 24 deletions(-) diff --git a/ipc/MutexFactory.h b/ipc/MutexFactory.h index f8133d81..db505ff9 100644 --- a/ipc/MutexFactory.h +++ b/ipc/MutexFactory.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_IPC_MUTEXFACTORY_H_ -#define FRAMEWORK_IPC_MUTEXFACTORY_H_ +#ifndef FSFW_IPC_MUTEXFACTORY_H_ +#define FSFW_IPC_MUTEXFACTORY_H_ #include "MutexIF.h" /** @@ -31,4 +31,4 @@ private: -#endif /* FRAMEWORK_IPC_MUTEXFACTORY_H_ */ +#endif /* FSFW_IPC_MUTEXFACTORY_H_ */ diff --git a/osal/linux/BinarySemaphore.cpp b/osal/linux/BinarySemaphore.cpp index 8c0eeae7..b81fa109 100644 --- a/osal/linux/BinarySemaphore.cpp +++ b/osal/linux/BinarySemaphore.cpp @@ -1,4 +1,4 @@ -#include "../../osal/linux/BinarySemaphore.h" +#include "BinarySemaphore.h" #include "../../serviceinterface/ServiceInterfaceStream.h" extern "C" { diff --git a/osal/linux/Clock.cpp b/osal/linux/Clock.cpp index 4de18f83..6cddda35 100644 --- a/osal/linux/Clock.cpp +++ b/osal/linux/Clock.cpp @@ -76,25 +76,25 @@ timeval Clock::getUptime() { ReturnValue_t Clock::getUptime(timeval* uptime) { //TODO This is not posix compatible and delivers only seconds precision - // is the OS not called Linux? - //Linux specific file read but more precise + // Linux specific file read but more precise. double uptimeSeconds; if(std::ifstream("/proc/uptime",std::ios::in) >> uptimeSeconds){ uptime->tv_sec = uptimeSeconds; uptime->tv_usec = uptimeSeconds *(double) 1e6 - (uptime->tv_sec *1e6); } + return HasReturnvaluesIF::RETURN_OK; +} - //TODO This is not posix compatible and delivers only seconds precision - // I suggest this is moved into another clock function which will - // deliver second precision later. +// Wait for new FSFW Clock function delivering seconds uptime. +//uint32_t Clock::getUptimeSeconds() { +// //TODO This is not posix compatible and delivers only seconds precision // struct sysinfo sysInfo; // int result = sysinfo(&sysInfo); // if(result != 0){ // return HasReturnvaluesIF::RETURN_FAILED; // } // return sysInfo.uptime; - return HasReturnvaluesIF::RETURN_OK; -} +//} ReturnValue_t Clock::getUptime(uint32_t* uptimeMs) { timeval uptime; diff --git a/osal/linux/MessageQueue.cpp b/osal/linux/MessageQueue.cpp index bc14374a..cfadb793 100644 --- a/osal/linux/MessageQueue.cpp +++ b/osal/linux/MessageQueue.cpp @@ -3,6 +3,7 @@ #include "../../objectmanager/ObjectManagerIF.h" #include + #include /* For O_* constants */ #include /* For mode constants */ #include diff --git a/osal/linux/Mutex.h b/osal/linux/Mutex.h index ecb47a33..cfce407f 100644 --- a/osal/linux/Mutex.h +++ b/osal/linux/Mutex.h @@ -1,10 +1,9 @@ -#ifndef OS_LINUX_MUTEX_H_ -#define OS_LINUX_MUTEX_H_ +#ifndef FSFW_OSAL_LINUX_MUTEX_H_ +#define FSFW_OSAL_LINUX_MUTEX_H_ #include "../../ipc/MutexIF.h" #include - class Mutex : public MutexIF { public: Mutex(); diff --git a/osal/linux/MutexFactory.cpp b/osal/linux/MutexFactory.cpp index 8c2faf88..80211f8b 100644 --- a/osal/linux/MutexFactory.cpp +++ b/osal/linux/MutexFactory.cpp @@ -1,6 +1,7 @@ -#include "../../ipc/MutexFactory.h" #include "Mutex.h" +#include "../../ipc/MutexFactory.h" + //TODO: Different variant than the lazy loading in QueueFactory. What's better and why? MutexFactory* MutexFactory::factoryInstance = new MutexFactory(); diff --git a/osal/linux/PosixThread.cpp b/osal/linux/PosixThread.cpp index ddb1f74f..55d74de3 100644 --- a/osal/linux/PosixThread.cpp +++ b/osal/linux/PosixThread.cpp @@ -1,5 +1,7 @@ -#include "../../serviceinterface/ServiceInterfaceStream.h" #include "PosixThread.h" + +#include "../../serviceinterface/ServiceInterfaceStream.h" + #include #include @@ -149,8 +151,10 @@ void PosixThread::createTask(void* (*fnc_)(void*), void* arg_) { status = pthread_attr_setstack(&attributes, stackPointer, stackSize); if(status != 0){ - sif::error << "Posix Thread attribute setStack failed with: " << - strerror(status) << std::endl; + sif::error << "PosixThread::createTask: pthread_attr_setstack " + " failed with: " << strerror(status) << std::endl; + sif::error << "Make sure the specified stack size is valid and is " + "larger than the minimum allowed stack size." << std::endl; } status = pthread_attr_setinheritsched(&attributes, PTHREAD_EXPLICIT_SCHED); diff --git a/osal/linux/SemaphoreFactory.cpp b/osal/linux/SemaphoreFactory.cpp index e4710933..cfb5f12d 100644 --- a/osal/linux/SemaphoreFactory.cpp +++ b/osal/linux/SemaphoreFactory.cpp @@ -1,6 +1,7 @@ -#include "../../tasks/SemaphoreFactory.h" #include "BinarySemaphore.h" #include "CountingSemaphore.h" + +#include "../../tasks/SemaphoreFactory.h" #include "../../serviceinterface/ServiceInterfaceStream.h" SemaphoreFactory* SemaphoreFactory::factoryInstance = nullptr; diff --git a/osal/linux/TaskFactory.cpp b/osal/linux/TaskFactory.cpp index f507c767..d18a0316 100644 --- a/osal/linux/TaskFactory.cpp +++ b/osal/linux/TaskFactory.cpp @@ -1,5 +1,6 @@ #include "FixedTimeslotTask.h" #include "PeriodicPosixTask.h" + #include "../../tasks/TaskFactory.h" #include "../../returnvalues/HasReturnvaluesIF.h" diff --git a/osal/linux/Timer.cpp b/osal/linux/Timer.cpp index ee964baa..bae631d7 100644 --- a/osal/linux/Timer.cpp +++ b/osal/linux/Timer.cpp @@ -1,6 +1,7 @@ +#include "Timer.h" #include "../../serviceinterface/ServiceInterfaceStream.h" #include -#include "Timer.h" + Timer::Timer() { sigevent sigEvent; diff --git a/tasks/TaskFactory.h b/tasks/TaskFactory.h index cbf2272c..404dd2a8 100644 --- a/tasks/TaskFactory.h +++ b/tasks/TaskFactory.h @@ -1,9 +1,9 @@ -#ifndef FRAMEWORK_TASKS_TASKFACTORY_H_ -#define FRAMEWORK_TASKS_TASKFACTORY_H_ +#ifndef FSFW_TASKS_TASKFACTORY_H_ +#define FSFW_TASKS_TASKFACTORY_H_ -#include #include "FixedTimeslotTaskIF.h" #include "Typedef.h" +#include /** * Singleton Class that produces Tasks. @@ -69,4 +69,4 @@ private: }; -#endif /* FRAMEWORK_TASKS_TASKFACTORY_H_ */ +#endif /* FSFW_TASKS_TASKFACTORY_H_ */ From 4f2470b93f8947fafb4e5f2ea4323a30ed3fd5ff Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:48:12 +0100 Subject: [PATCH 04/26] task factory --- tasks/TaskFactory.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/tasks/TaskFactory.h b/tasks/TaskFactory.h index 404dd2a8..85cdda90 100644 --- a/tasks/TaskFactory.h +++ b/tasks/TaskFactory.h @@ -3,6 +3,7 @@ #include "FixedTimeslotTaskIF.h" #include "Typedef.h" + #include /** @@ -48,10 +49,11 @@ public: /** * Function to be called to delete a task - * @param task The pointer to the task that shall be deleted, NULL specifies current Task + * @param task The pointer to the task that shall be deleted, + * nullptr specifies current Task * @return Success of deletion */ - static ReturnValue_t deleteTask(PeriodicTaskIF* task = NULL); + static ReturnValue_t deleteTask(PeriodicTaskIF* task = nullptr); /** * Function to be called to delay current task From 93842bb91315e53deee34c577912b279676b32b1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 22:56:30 +0100 Subject: [PATCH 05/26] using long name now --- datapoollocal/LocalDataPoolManager.h | 2 +- datapoollocal/LocalPoolVariable.h | 50 ++++++++++++++-------------- datapoollocal/LocalPoolVariable.tpp | 46 ++++++++++++------------- monitoring/MonitorBase.h | 2 +- 4 files changed, 50 insertions(+), 50 deletions(-) diff --git a/datapoollocal/LocalDataPoolManager.h b/datapoollocal/LocalDataPoolManager.h index 95d48303..c4024cf9 100644 --- a/datapoollocal/LocalDataPoolManager.h +++ b/datapoollocal/LocalDataPoolManager.h @@ -48,7 +48,7 @@ class HousekeepingPacketUpdate; * @author R. Mueller */ class LocalDataPoolManager { - template friend class LocalPoolVar; + template friend class LocalPoolVariable; template friend class LocalPoolVector; friend class LocalPoolDataSetBase; friend void (Factory::setStaticFrameworkObjectIds)(); diff --git a/datapoollocal/LocalPoolVariable.h b/datapoollocal/LocalPoolVariable.h index c18d5443..7b7e443e 100644 --- a/datapoollocal/LocalPoolVariable.h +++ b/datapoollocal/LocalPoolVariable.h @@ -22,10 +22,10 @@ * @ingroup data_pool */ template -class LocalPoolVar: public LocalPoolObjectBase { +class LocalPoolVariable: public LocalPoolObjectBase { public: //! Default ctor is forbidden. - LocalPoolVar() = delete; + LocalPoolVariable() = delete; /** * This constructor is used by the data creators to have pool variable @@ -43,7 +43,7 @@ public: * If nullptr, the variable is not registered. * @param setReadWriteMode Specify the read-write mode of the pool variable. */ - LocalPoolVar(HasLocalDataPoolIF* hkOwner, lp_id_t poolId, + LocalPoolVariable(HasLocalDataPoolIF* hkOwner, lp_id_t poolId, DataSetIF* dataSet = nullptr, pool_rwm_t setReadWriteMode = pool_rwm_t::VAR_READ_WRITE); @@ -64,7 +64,7 @@ public: * @param setReadWriteMode Specify the read-write mode of the pool variable. * */ - LocalPoolVar(object_id_t poolOwner, lp_id_t poolId, + LocalPoolVariable(object_id_t poolOwner, lp_id_t poolId, DataSetIF* dataSet = nullptr, pool_rwm_t setReadWriteMode = pool_rwm_t::VAR_READ_WRITE); /** @@ -73,10 +73,10 @@ public: * @param dataSet * @param setReadWriteMode */ - LocalPoolVar(gp_id_t globalPoolId, DataSetIF* dataSet = nullptr, + LocalPoolVariable(gp_id_t globalPoolId, DataSetIF* dataSet = nullptr, pool_rwm_t setReadWriteMode = pool_rwm_t::VAR_READ_WRITE); - virtual~ LocalPoolVar() {}; + virtual~ LocalPoolVariable() {}; /** * @brief This is the local copy of the data pool entry. @@ -118,23 +118,23 @@ public: ReturnValue_t commit(dur_millis_t lockTimeout = MutexIF::BLOCKING) override; - LocalPoolVar &operator=(const T& newValue); - LocalPoolVar &operator=(const LocalPoolVar& newPoolVariable); + LocalPoolVariable &operator=(const T& newValue); + LocalPoolVariable &operator=(const LocalPoolVariable& newPoolVariable); //! Explicit type conversion operator. Allows casting the class to //! its template type to perform operations on value. explicit operator T() const; - bool operator==(const LocalPoolVar& other) const; + bool operator==(const LocalPoolVariable& other) const; bool operator==(const T& other) const; - bool operator!=(const LocalPoolVar& other) const; + bool operator!=(const LocalPoolVariable& other) const; bool operator!=(const T& other) const; - bool operator<(const LocalPoolVar& other) const; + bool operator<(const LocalPoolVariable& other) const; bool operator<(const T& other) const; - bool operator>(const LocalPoolVar& other) const; + bool operator>(const LocalPoolVariable& other) const; bool operator>(const T& other) const; protected: @@ -160,7 +160,7 @@ protected: // std::ostream is the type for object std::cout template friend std::ostream& operator<< (std::ostream &out, - const LocalPoolVar &var); + const LocalPoolVariable &var); private: }; @@ -168,18 +168,18 @@ private: #include "LocalPoolVariable.tpp" template -using lp_var_t = LocalPoolVar; +using lp_var_t = LocalPoolVariable; -using lp_bool_t = LocalPoolVar; -using lp_uint8_t = LocalPoolVar; -using lp_uint16_t = LocalPoolVar; -using lp_uint32_t = LocalPoolVar; -using lp_uint64_t = LocalPoolVar; -using lp_int8_t = LocalPoolVar; -using lp_int16_t = LocalPoolVar; -using lp_int32_t = LocalPoolVar; -using lp_int64_t = LocalPoolVar; -using lp_float_t = LocalPoolVar; -using lp_double_t = LocalPoolVar; +using lp_bool_t = LocalPoolVariable; +using lp_uint8_t = LocalPoolVariable; +using lp_uint16_t = LocalPoolVariable; +using lp_uint32_t = LocalPoolVariable; +using lp_uint64_t = LocalPoolVariable; +using lp_int8_t = LocalPoolVariable; +using lp_int16_t = LocalPoolVariable; +using lp_int32_t = LocalPoolVariable; +using lp_int64_t = LocalPoolVariable; +using lp_float_t = LocalPoolVariable; +using lp_double_t = LocalPoolVariable; #endif /* FSFW_DATAPOOLLOCAL_LOCALPOOLVARIABLE_H_ */ diff --git a/datapoollocal/LocalPoolVariable.tpp b/datapoollocal/LocalPoolVariable.tpp index b9f7b906..48649ad5 100644 --- a/datapoollocal/LocalPoolVariable.tpp +++ b/datapoollocal/LocalPoolVariable.tpp @@ -6,32 +6,32 @@ #endif template -inline LocalPoolVar::LocalPoolVar(HasLocalDataPoolIF* hkOwner, +inline LocalPoolVariable::LocalPoolVariable(HasLocalDataPoolIF* hkOwner, lp_id_t poolId, DataSetIF* dataSet, pool_rwm_t setReadWriteMode): LocalPoolObjectBase(poolId, hkOwner, dataSet, setReadWriteMode) {} template -inline LocalPoolVar::LocalPoolVar(object_id_t poolOwner, lp_id_t poolId, +inline LocalPoolVariable::LocalPoolVariable(object_id_t poolOwner, lp_id_t poolId, DataSetIF *dataSet, pool_rwm_t setReadWriteMode): LocalPoolObjectBase(poolOwner, poolId, dataSet, setReadWriteMode) {} template -inline LocalPoolVar::LocalPoolVar(gp_id_t globalPoolId, DataSetIF *dataSet, +inline LocalPoolVariable::LocalPoolVariable(gp_id_t globalPoolId, DataSetIF *dataSet, pool_rwm_t setReadWriteMode): LocalPoolObjectBase(globalPoolId.objectId, globalPoolId.localPoolId, dataSet, setReadWriteMode){} template -inline ReturnValue_t LocalPoolVar::read(dur_millis_t lockTimeout) { +inline ReturnValue_t LocalPoolVariable::read(dur_millis_t lockTimeout) { MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING, lockTimeout); return readWithoutLock(); } template -inline ReturnValue_t LocalPoolVar::readWithoutLock() { +inline ReturnValue_t LocalPoolVariable::readWithoutLock() { if(readWriteMode == pool_rwm_t::VAR_WRITE) { sif::debug << "LocalPoolVar: Invalid read write " "mode for read() call." << std::endl; @@ -53,14 +53,14 @@ inline ReturnValue_t LocalPoolVar::readWithoutLock() { } template -inline ReturnValue_t LocalPoolVar::commit(dur_millis_t lockTimeout) { +inline ReturnValue_t LocalPoolVariable::commit(dur_millis_t lockTimeout) { MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING, lockTimeout); return commitWithoutLock(); } template -inline ReturnValue_t LocalPoolVar::commitWithoutLock() { +inline ReturnValue_t LocalPoolVariable::commitWithoutLock() { if(readWriteMode == pool_rwm_t::VAR_READ) { sif::debug << "LocalPoolVar: Invalid read write " "mode for commit() call." << std::endl; @@ -81,88 +81,88 @@ inline ReturnValue_t LocalPoolVar::commitWithoutLock() { } template -inline ReturnValue_t LocalPoolVar::serialize(uint8_t** buffer, size_t* size, +inline ReturnValue_t LocalPoolVariable::serialize(uint8_t** buffer, size_t* size, const size_t max_size, SerializeIF::Endianness streamEndianness) const { return SerializeAdapter::serialize(&value, buffer, size ,max_size, streamEndianness); } template -inline size_t LocalPoolVar::getSerializedSize() const { +inline size_t LocalPoolVariable::getSerializedSize() const { return SerializeAdapter::getSerializedSize(&value); } template -inline ReturnValue_t LocalPoolVar::deSerialize(const uint8_t** buffer, +inline ReturnValue_t LocalPoolVariable::deSerialize(const uint8_t** buffer, size_t* size, SerializeIF::Endianness streamEndianness) { return SerializeAdapter::deSerialize(&value, buffer, size, streamEndianness); } template inline std::ostream& operator<< (std::ostream &out, - const LocalPoolVar &var) { + const LocalPoolVariable &var) { out << var.value; return out; } template -inline LocalPoolVar::operator T() const { +inline LocalPoolVariable::operator T() const { return value; } template -inline LocalPoolVar & LocalPoolVar::operator=(const T& newValue) { +inline LocalPoolVariable & LocalPoolVariable::operator=(const T& newValue) { value = newValue; return *this; } template -inline LocalPoolVar& LocalPoolVar::operator =( - const LocalPoolVar& newPoolVariable) { +inline LocalPoolVariable& LocalPoolVariable::operator =( + const LocalPoolVariable& newPoolVariable) { value = newPoolVariable.value; return *this; } template -inline bool LocalPoolVar::operator ==(const LocalPoolVar &other) const { +inline bool LocalPoolVariable::operator ==(const LocalPoolVariable &other) const { return this->value == other.value; } template -inline bool LocalPoolVar::operator ==(const T &other) const { +inline bool LocalPoolVariable::operator ==(const T &other) const { return this->value == other; } template -inline bool LocalPoolVar::operator !=(const LocalPoolVar &other) const { +inline bool LocalPoolVariable::operator !=(const LocalPoolVariable &other) const { return not (*this == other); } template -inline bool LocalPoolVar::operator !=(const T &other) const { +inline bool LocalPoolVariable::operator !=(const T &other) const { return not (*this == other); } template -inline bool LocalPoolVar::operator <(const LocalPoolVar &other) const { +inline bool LocalPoolVariable::operator <(const LocalPoolVariable &other) const { return this->value < other.value; } template -inline bool LocalPoolVar::operator <(const T &other) const { +inline bool LocalPoolVariable::operator <(const T &other) const { return this->value < other; } template -inline bool LocalPoolVar::operator >(const LocalPoolVar &other) const { +inline bool LocalPoolVariable::operator >(const LocalPoolVariable &other) const { return not (*this < other); } template -inline bool LocalPoolVar::operator >(const T &other) const { +inline bool LocalPoolVariable::operator >(const T &other) const { return not (*this < other); } diff --git a/monitoring/MonitorBase.h b/monitoring/MonitorBase.h index 530a3840..967f0f62 100644 --- a/monitoring/MonitorBase.h +++ b/monitoring/MonitorBase.h @@ -72,7 +72,7 @@ protected: return HasReturnvaluesIF::RETURN_OK; } - LocalPoolVar poolVariable; + LocalPoolVariable poolVariable; }; #endif /* FSFW_MONITORING_MONITORBASE_H_ */ From 703d2590ffbf21603e37a2ecad50e3a7d1a767ec Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:20:08 +0100 Subject: [PATCH 06/26] update csb --- CHANGELOG | 4 ++++ tmtcservices/CommandingServiceBase.h | 3 ++- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/CHANGELOG b/CHANGELOG index 7b07db08..2ddd7673 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -60,3 +60,7 @@ that DHB users adapt their polling sequence tables to perform this step. This st allows setting a unique ID. Event.cpp source file removed, functions now defined in header directly. Namespaces renamed. Functions declared `constexpr` now + +### Commanding Service Base + +- CSB uses the diff --git a/tmtcservices/CommandingServiceBase.h b/tmtcservices/CommandingServiceBase.h index 3611d7c6..e10f2ddd 100644 --- a/tmtcservices/CommandingServiceBase.h +++ b/tmtcservices/CommandingServiceBase.h @@ -42,7 +42,8 @@ class CommandingServiceBase: public SystemObject, friend void (Factory::setStaticFrameworkObjectIds)(); public: // We could make this configurable via preprocessor and the FSFWConfig file. - static constexpr uint8_t COMMAND_INFO_FIFO_DEPTH = FSFW_CSB_FIFO_DEPTH; + static constexpr uint8_t COMMAND_INFO_FIFO_DEPTH = + fsfwconfig::FSFW_CSB_FIFO_DEPTH; static const uint8_t INTERFACE_ID = CLASS_ID::COMMAND_SERVICE_BASE; From 72c54d59fac16ceaeb3d32458c6de5e28f60c18e Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:32:56 +0100 Subject: [PATCH 07/26] fsfw config --- defaultcfg/fsfwconfig/FSFWConfig.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/defaultcfg/fsfwconfig/FSFWConfig.h b/defaultcfg/fsfwconfig/FSFWConfig.h index 1386bf66..334f352a 100644 --- a/defaultcfg/fsfwconfig/FSFWConfig.h +++ b/defaultcfg/fsfwconfig/FSFWConfig.h @@ -15,12 +15,6 @@ //! Can be used to enable additional debugging printouts for developing the FSFW #define FSFW_PRINT_VERBOSITY_LEVEL 0 -//! Defines the FIFO depth of each commanding service base which -//! also determines how many commands a CSB service can handle in one cycle -//! simulataneously. This will increase the required RAM for -//! each CSB service ! -#define FSFW_CSB_FIFO_DEPTH 6 - //! If FSFW_OBJ_EVENT_TRANSLATION is set to one, //! additional output which requires the translation files translateObjects //! and translateEvents (and their compiled source files) @@ -52,6 +46,12 @@ static constexpr uint8_t FSFW_MISSION_TIMESTAMP_SIZE = 8; static constexpr size_t FSFW_EVENTMGMR_MATCHTREE_NODES = 240; static constexpr size_t FSFW_EVENTMGMT_EVENTIDMATCHERS = 120; static constexpr size_t FSFW_EVENTMGMR_RANGEMATCHERS = 120; + +//! Defines the FIFO depth of each commanding service base which +//! also determines how many commands a CSB service can handle in one cycle +//! simulataneously. This will increase the required RAM for +//! each CSB service ! +static constexpr uint8_t FSFW_CSB_FIFO_DEPTH = 6; } #endif /* CONFIG_FSFWCONFIG_H_ */ From 82a83a50ee01613c4227407b846173555015b4b4 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:39:33 +0100 Subject: [PATCH 08/26] change log update --- CHANGELOG | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG b/CHANGELOG index 2ddd7673..68b457f4 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -63,4 +63,4 @@ now ### Commanding Service Base -- CSB uses the +- CSB uses the new fsfwconfig::FSFW_CSB_FIFO_DEPTH variable to determine the FIFO depth for each CSB instance. This variable has to be set in the FSFWConfig.h file From e39c4fe2a862706f5be1a00fb14b21daa9f097da Mon Sep 17 00:00:00 2001 From: Spacefish Date: Tue, 15 Dec 2020 22:42:50 +0100 Subject: [PATCH 09/26] added hk service 3 --- pus/Service3Housekeeping.cpp | 295 +++++++++++++++++++++++++++ pus/Service3Housekeeping.h | 105 ++++++++++ pus/servicepackets/Service3Packets.h | 21 ++ 3 files changed, 421 insertions(+) create mode 100644 pus/Service3Housekeeping.cpp create mode 100644 pus/Service3Housekeeping.h create mode 100644 pus/servicepackets/Service3Packets.h diff --git a/pus/Service3Housekeeping.cpp b/pus/Service3Housekeeping.cpp new file mode 100644 index 00000000..175af026 --- /dev/null +++ b/pus/Service3Housekeeping.cpp @@ -0,0 +1,295 @@ +#include "Service3Housekeeping.h" +#include "servicepackets/Service3Packets.h" +#include "../datapoollocal/HasLocalDataPoolIF.h" + + +Service3Housekeeping::Service3Housekeeping(object_id_t objectId, uint16_t apid, + uint8_t serviceId): + CommandingServiceBase(objectId, apid, serviceId, + NUM_OF_PARALLEL_COMMANDS, COMMAND_TIMEOUT_SECONDS) {} + +Service3Housekeeping::~Service3Housekeeping() {} + +ReturnValue_t Service3Housekeeping::isValidSubservice(uint8_t subservice) { + switch(static_cast(subservice)) { + case Subservice::ENABLE_PERIODIC_HK_REPORT_GENERATION: + case Subservice::DISABLE_PERIODIC_HK_REPORT_GENERATION: + case Subservice::ENABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION: + case Subservice::DISABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION: + case Subservice::REPORT_HK_REPORT_STRUCTURES: + case Subservice::REPORT_DIAGNOSTICS_REPORT_STRUCTURES : + case Subservice::GENERATE_ONE_PARAMETER_REPORT: + case Subservice::GENERATE_ONE_DIAGNOSTICS_REPORT: + case Subservice::MODIFY_PARAMETER_REPORT_COLLECTION_INTERVAL: + case Subservice::MODIFY_DIAGNOSTICS_REPORT_COLLECTION_INTERVAL: + return HasReturnvaluesIF::RETURN_OK; + // Telemetry or invalid subservice. + case Subservice::HK_DEFINITIONS_REPORT: + case Subservice::DIAGNOSTICS_DEFINITION_REPORT: + case Subservice::HK_REPORT: + case Subservice::DIAGNOSTICS_REPORT: + default: + return AcceptsTelecommandsIF::INVALID_SUBSERVICE; + } +} + +ReturnValue_t Service3Housekeeping::getMessageQueueAndObject(uint8_t subservice, + const uint8_t *tcData, size_t tcDataLen, + MessageQueueId_t *id, object_id_t *objectId) { + ReturnValue_t result = checkAndAcquireTargetID(objectId,tcData,tcDataLen); + if(result != RETURN_OK) { + return result; + } + return checkInterfaceAndAcquireMessageQueue(id,objectId); +} + +ReturnValue_t Service3Housekeeping::checkAndAcquireTargetID( + object_id_t* objectIdToSet, const uint8_t* tcData, size_t tcDataLen) { + if(SerializeAdapter::deSerialize(objectIdToSet, &tcData, &tcDataLen, + SerializeIF::Endianness::BIG) != HasReturnvaluesIF::RETURN_OK) { + return CommandingServiceBase::INVALID_TC; + } + return HasReturnvaluesIF::RETURN_OK; +} + +ReturnValue_t Service3Housekeeping::checkInterfaceAndAcquireMessageQueue( + MessageQueueId_t* messageQueueToSet, object_id_t* objectId) { + // check HasLocalDataPoolIF property of target + HasLocalDataPoolIF* possibleTarget = + objectManager->get(*objectId); + if(possibleTarget == nullptr){ + return CommandingServiceBase::INVALID_OBJECT; + } + *messageQueueToSet = possibleTarget->getCommandQueue(); + return HasReturnvaluesIF::RETURN_OK; +} + + +ReturnValue_t Service3Housekeeping::prepareCommand(CommandMessage* message, + uint8_t subservice, const uint8_t *tcData, size_t tcDataLen, + uint32_t *state, object_id_t objectId) { + switch(static_cast(subservice)) { + case Subservice::ENABLE_PERIODIC_HK_REPORT_GENERATION: + return prepareReportingTogglingCommand(message, objectId, true, false, + tcData, tcDataLen); + case Subservice::DISABLE_PERIODIC_HK_REPORT_GENERATION: + return prepareReportingTogglingCommand(message, objectId, false, false, + tcData, tcDataLen); + case Subservice::ENABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION: + return prepareReportingTogglingCommand(message, objectId, true, true, + tcData, tcDataLen); + case Subservice::DISABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION: + return prepareReportingTogglingCommand(message, objectId, false, true, + tcData, tcDataLen); + case Subservice::REPORT_HK_REPORT_STRUCTURES: + return prepareStructureReportingCommand(message, objectId, false, tcData, + tcDataLen); + case Subservice::REPORT_DIAGNOSTICS_REPORT_STRUCTURES: + return prepareStructureReportingCommand(message, objectId, true, tcData, + tcDataLen); + case Subservice::GENERATE_ONE_PARAMETER_REPORT: + return prepareOneShotReportCommand(message, objectId, false, + tcData, tcDataLen); + case Subservice::GENERATE_ONE_DIAGNOSTICS_REPORT: + return prepareOneShotReportCommand(message, objectId, true, + tcData, tcDataLen); + case Subservice::MODIFY_PARAMETER_REPORT_COLLECTION_INTERVAL: + return prepareCollectionIntervalModificationCommand(message, objectId, + false, tcData, tcDataLen); + case Subservice::MODIFY_DIAGNOSTICS_REPORT_COLLECTION_INTERVAL: + return prepareCollectionIntervalModificationCommand(message, objectId, + true, tcData, tcDataLen); + case Subservice::HK_DEFINITIONS_REPORT: + case Subservice::DIAGNOSTICS_DEFINITION_REPORT: + case Subservice::HK_REPORT: + case Subservice::DIAGNOSTICS_REPORT: + // Those are telemetry packets. + return CommandingServiceBase::INVALID_TC; + default: + // should never happen, subservice was already checked. + return HasReturnvaluesIF::RETURN_FAILED; + } + return HasReturnvaluesIF::RETURN_OK; +} + +ReturnValue_t Service3Housekeeping::prepareReportingTogglingCommand( + CommandMessage *command, object_id_t objectId, + bool enableReporting, bool isDiagnostics, + const uint8_t* tcData, size_t tcDataLen) { + if(tcDataLen < sizeof(sid_t)) { + // TC data should consist of object ID and set ID. + return CommandingServiceBase::INVALID_TC; + } + + sid_t targetSid = buildSid(objectId, &tcData, &tcDataLen); + HousekeepingMessage::setToggleReportingCommand(command, targetSid, + enableReporting, isDiagnostics); + return HasReturnvaluesIF::RETURN_OK; +} + +ReturnValue_t Service3Housekeeping::prepareStructureReportingCommand( + CommandMessage *command, object_id_t objectId, bool isDiagnostics, + const uint8_t* tcData, size_t tcDataLen) { + if(tcDataLen < sizeof(sid_t)) { + // TC data should consist of object ID and set ID. + return CommandingServiceBase::INVALID_TC; + } + + sid_t targetSid = buildSid(objectId, &tcData, &tcDataLen); + HousekeepingMessage::setStructureReportingCommand(command, targetSid, + isDiagnostics); + return HasReturnvaluesIF::RETURN_OK; +} + +ReturnValue_t Service3Housekeeping::prepareOneShotReportCommand( + CommandMessage *command, object_id_t objectId, bool isDiagnostics, + const uint8_t *tcData, size_t tcDataLen) { + if(tcDataLen < sizeof(sid_t)) { + // TC data should consist of object ID and set ID. + return CommandingServiceBase::INVALID_TC; + } + + sid_t targetSid = buildSid(objectId, &tcData, &tcDataLen); + HousekeepingMessage::setOneShotReportCommand(command, targetSid, + isDiagnostics); + return HasReturnvaluesIF::RETURN_OK; +} + +ReturnValue_t Service3Housekeeping::prepareCollectionIntervalModificationCommand( + CommandMessage *command, object_id_t objectId, bool isDiagnostics, + const uint8_t *tcData, size_t tcDataLen) { + if(tcDataLen < sizeof(sid_t) + sizeof(float)) { + // SID plus the size of the new collection intervL. + return CommandingServiceBase::INVALID_TC; + } + + sid_t targetSid = buildSid(objectId, &tcData, &tcDataLen); + float newCollectionInterval = 0; + SerializeAdapter::deSerialize(&newCollectionInterval, &tcData, &tcDataLen, + SerializeIF::Endianness::BIG); + HousekeepingMessage::setCollectionIntervalModificationCommand(command, + targetSid, newCollectionInterval, isDiagnostics); + return HasReturnvaluesIF::RETURN_OK; +} + + +ReturnValue_t Service3Housekeeping::handleReply(const CommandMessage* reply, + Command_t previousCommand, uint32_t *state, + CommandMessage* optionalNextCommand, object_id_t objectId, + bool *isStep) { + Command_t command = reply->getCommand(); + switch(command) { + + case(HousekeepingMessage::HK_REPORT): { + ReturnValue_t result = generateHkReply(reply, + static_cast(Subservice::HK_REPORT)); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + return CommandingServiceBase::EXECUTION_COMPLETE; + } + + case(HousekeepingMessage::DIAGNOSTICS_REPORT): { + ReturnValue_t result = generateHkReply(reply, + static_cast(Subservice::DIAGNOSTICS_REPORT)); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + return CommandingServiceBase::EXECUTION_COMPLETE; + } + + case(HousekeepingMessage::HK_DEFINITIONS_REPORT): { + return generateHkReply(reply, static_cast( + Subservice::HK_DEFINITIONS_REPORT)); + break; + } + case(HousekeepingMessage::DIAGNOSTICS_DEFINITION_REPORT): { + return generateHkReply(reply, static_cast( + Subservice::DIAGNOSTICS_DEFINITION_REPORT)); + break; + } + + case(HousekeepingMessage::HK_REQUEST_SUCCESS): { + return CommandingServiceBase::EXECUTION_COMPLETE; + } + + case(HousekeepingMessage::HK_REQUEST_FAILURE): { + failureParameter1 = objectId; + ReturnValue_t error = HasReturnvaluesIF::RETURN_FAILED; + HousekeepingMessage::getHkRequestFailureReply(reply,&error); + failureParameter2 = error; + return CommandingServiceBase::EXECUTION_COMPLETE; + } + + default: + sif::error << "Service3Housekeeping::handleReply: Invalid reply with " + << "reply command " << command << "!" << std::endl; + return CommandingServiceBase::INVALID_REPLY; + } + return HasReturnvaluesIF::RETURN_OK; +} + +void Service3Housekeeping::handleUnrequestedReply( + CommandMessage* reply) { + ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; + Command_t command = reply->getCommand(); + + switch(command) { + + case(HousekeepingMessage::DIAGNOSTICS_REPORT): { + result = generateHkReply(reply, + static_cast(Subservice::DIAGNOSTICS_REPORT)); + break; + } + + case(HousekeepingMessage::HK_REPORT): { + result = generateHkReply(reply, + static_cast(Subservice::HK_REPORT)); + break; + } + + default: + sif::error << "Service3Housekeeping::handleUnrequestedReply: Invalid " + << "reply with " << "reply command " << command << "!" + << std::endl; + return; + } + + if(result != HasReturnvaluesIF::RETURN_OK) { + // Configuration error + sif::debug << "Service3Housekeeping::handleUnrequestedReply:" + << "Could not generate reply!" << std::endl; + } +} + +MessageQueueId_t Service3Housekeeping::getHkQueue() const { + return commandQueue->getId(); +} + +ReturnValue_t Service3Housekeeping::generateHkReply( + const CommandMessage* hkMessage, uint8_t subserviceId) { + store_address_t storeId; + + sid_t sid = HousekeepingMessage::getHkDataReply(hkMessage, &storeId); + auto resultPair = IPCStore->getData(storeId); + if(resultPair.first != HasReturnvaluesIF::RETURN_OK) { + return resultPair.first; + } + + HkPacket hkPacket(sid, resultPair.second.data(), resultPair.second.size()); + return sendTmPacket(static_cast(subserviceId), + hkPacket.hkData, hkPacket.hkSize, nullptr, 0); +} + +sid_t Service3Housekeeping::buildSid(object_id_t objectId, + const uint8_t** tcData, size_t* tcDataLen) { + sid_t targetSid; + targetSid.objectId = objectId; + // skip deserialization of object ID, was already done. + *tcData += sizeof(object_id_t); + *tcDataLen -= sizeof(object_id_t); + // size check is expected to be performed beforehand! + SerializeAdapter::deSerialize(&targetSid.ownerSetId, tcData, tcDataLen, + SerializeIF::Endianness::BIG); + return targetSid; +} diff --git a/pus/Service3Housekeeping.h b/pus/Service3Housekeeping.h new file mode 100644 index 00000000..269710ef --- /dev/null +++ b/pus/Service3Housekeeping.h @@ -0,0 +1,105 @@ +#ifndef FSFW_PUS_SERVICE3HOUSEKEEPINGSERVICE_H_ +#define FSFW_PUS_SERVICE3HOUSEKEEPINGSERVICE_H_ + +#include "../housekeeping/AcceptsHkPacketsIF.h" +#include "../housekeeping/HousekeepingMessage.h" +#include "../tmtcservices/CommandingServiceBase.h" + +/** + * @brief Manges spacecraft housekeeping reports and + * sends pool variables (temperature, GPS data ...) to ground. + * + * @details Full Documentation: ECSS-E70-41A or ECSS-E-ST-70-41C. + * Implementation based on PUS-C + * + * The housekeeping service type provides means to control and adapt the + * spacecraft reporting plan according to the mission phases. + * The housekeeping service type provides the visibility of any + * on-board parameters assembled in housekeeping parameter report structures + * or diagnostic parameter report structures as required for the mission. + * The parameter report structures used by the housekeeping service can + * be predefined on-board or created when needed. + * + * @author R. Mueller + * @ingroup pus_services + */ +class Service3Housekeeping: public CommandingServiceBase, + public AcceptsHkPacketsIF { +public: + static constexpr uint8_t NUM_OF_PARALLEL_COMMANDS = 4; + static constexpr uint16_t COMMAND_TIMEOUT_SECONDS = 60; + + Service3Housekeeping(object_id_t objectId, uint16_t apid, uint8_t serviceId); + virtual~ Service3Housekeeping(); +protected: + /* CSB abstract functions implementation . See CSB documentation. */ + ReturnValue_t isValidSubservice(uint8_t subservice) override; + ReturnValue_t getMessageQueueAndObject(uint8_t subservice, + const uint8_t *tcData, size_t tcDataLen, MessageQueueId_t *id, + object_id_t *objectId) override; + ReturnValue_t prepareCommand(CommandMessage* message, + uint8_t subservice, const uint8_t *tcData, size_t tcDataLen, + uint32_t *state, object_id_t objectId) override; + ReturnValue_t handleReply(const CommandMessage* reply, + Command_t previousCommand, uint32_t *state, + CommandMessage* optionalNextCommand, object_id_t objectId, + bool *isStep) override; + + virtual MessageQueueId_t getHkQueue() const; +private: + enum class Subservice { + ENABLE_PERIODIC_HK_REPORT_GENERATION = 5, //!< [EXPORT] : [TC] + DISABLE_PERIODIC_HK_REPORT_GENERATION = 6, //!< [EXPORT] : [TC] + + ENABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION = 7, //!< [EXPORT] : [TC] + DISABLE_PERIODIC_DIAGNOSTICS_REPORT_GENERATION = 8, //!< [EXPORT] : [TC] + + //! [EXPORT] : [TC] Report HK structure by supplying SID + REPORT_HK_REPORT_STRUCTURES = 9, + //! [EXPORT] : [TC] Report Diagnostics structure by supplying SID + REPORT_DIAGNOSTICS_REPORT_STRUCTURES = 11, + + //! [EXPORT] : [TM] Report corresponding to Subservice 9 TC + HK_DEFINITIONS_REPORT = 10, + //! [EXPORT] : [TM] Report corresponding to Subservice 11 TC + DIAGNOSTICS_DEFINITION_REPORT = 12, + + //! [EXPORT] : [TM] Core packet. Contains Housekeeping data + HK_REPORT = 25, + //! [EXPORT] : [TM] Core packet. Contains diagnostics data + DIAGNOSTICS_REPORT = 26, + + /* PUS-C */ + GENERATE_ONE_PARAMETER_REPORT = 27, //!< [EXPORT] : [TC] + GENERATE_ONE_DIAGNOSTICS_REPORT = 28, //!< [EXPORT] : [TC] + + MODIFY_PARAMETER_REPORT_COLLECTION_INTERVAL = 31, //!< [EXPORT] : [TC] + MODIFY_DIAGNOSTICS_REPORT_COLLECTION_INTERVAL = 32, //!< [EXPORT] : [TC] + }; + + ReturnValue_t checkAndAcquireTargetID(object_id_t* objectIdToSet, + const uint8_t* tcData, size_t tcDataLen); + ReturnValue_t checkInterfaceAndAcquireMessageQueue( + MessageQueueId_t* messageQueueToSet, object_id_t* objectId); + + ReturnValue_t generateHkReply(const CommandMessage* hkMessage, + uint8_t subserviceId); + ReturnValue_t prepareReportingTogglingCommand(CommandMessage* command, + object_id_t objectId, bool enableReporting, bool isDiagnostics, + const uint8_t* tcData, size_t tcDataLen); + ReturnValue_t prepareStructureReportingCommand(CommandMessage* command, + object_id_t objectId, bool isDiagnostics, const uint8_t* tcData, + size_t tcDataLen); + ReturnValue_t prepareOneShotReportCommand(CommandMessage* command, + object_id_t objectId, bool isDiagnostics, const uint8_t* tcData, + size_t tcDataLen); + ReturnValue_t prepareCollectionIntervalModificationCommand( + CommandMessage* command, object_id_t objectId, bool isDiagnostics, + const uint8_t* tcData, size_t tcDataLen); + + void handleUnrequestedReply(CommandMessage* reply) override; + sid_t buildSid(object_id_t objectId, const uint8_t** tcData, + size_t* tcDataLen); +}; + +#endif /* FSFW_PUS_SERVICE3HOUSEKEEPINGSERVICE_H_ */ diff --git a/pus/servicepackets/Service3Packets.h b/pus/servicepackets/Service3Packets.h new file mode 100644 index 00000000..05732e11 --- /dev/null +++ b/pus/servicepackets/Service3Packets.h @@ -0,0 +1,21 @@ +#ifndef FSFW_PUS_SERVICEPACKETS_SERVICE3PACKETS_H_ +#define FSFW_PUS_SERVICEPACKETS_SERVICE3PACKETS_H_ + +#include +#include + +/** + * @brief Subservices 25 and 26: TM packets + * @ingroup spacepackets + */ +class HkPacket { //!< [EXPORT] : [SUBSERVICE] 25, 26 +public: + sid_t sid; //!< [EXPORT] : [COMMENT] Structure ID (SID) of housekeeping data. + const uint8_t* hkData; //!< [EXPORT] : [MAXSIZE] Deduced size + size_t hkSize; //!< [EXPORT] : [IGNORE] + + HkPacket(sid_t sid, const uint8_t* data, size_t size): + sid(sid), hkData(data), hkSize(size) {} +}; + +#endif /* FSFW_PUS_SERVICEPACKETS_SERVICE3PACKETS_H_ */ From a411df18db4a74f855bfdff1cfa6ffa06ab2cbf0 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Tue, 15 Dec 2020 22:52:29 +0100 Subject: [PATCH 10/26] deleted tpp files, replaced by source files --- storagemanager/LocalPool.tpp | 305 --------------------------------- storagemanager/PoolManager.tpp | 56 ------ 2 files changed, 361 deletions(-) delete mode 100644 storagemanager/LocalPool.tpp delete mode 100644 storagemanager/PoolManager.tpp diff --git a/storagemanager/LocalPool.tpp b/storagemanager/LocalPool.tpp deleted file mode 100644 index 5e61efe4..00000000 --- a/storagemanager/LocalPool.tpp +++ /dev/null @@ -1,305 +0,0 @@ -#ifndef FSFW_STORAGEMANAGER_LOCALPOOL_TPP_ -#define FSFW_STORAGEMANAGER_LOCALPOOL_TPP_ - -#ifndef FSFW_STORAGEMANAGER_LOCALPOOL_H_ -#error Include LocalPool.h before LocalPool.tpp! -#endif - -template -inline LocalPool::LocalPool(object_id_t setObjectId, - const uint16_t element_sizes[NUMBER_OF_POOLS], - const uint16_t n_elements[NUMBER_OF_POOLS], bool registered, - bool spillsToHigherPools) : - SystemObject(setObjectId, registered), internalErrorReporter(nullptr), - spillsToHigherPools(spillsToHigherPools) -{ - for (uint16_t n = 0; n < NUMBER_OF_POOLS; n++) { - this->element_sizes[n] = element_sizes[n]; - this->n_elements[n] = n_elements[n]; - store[n] = new uint8_t[n_elements[n] * element_sizes[n]]; - size_list[n] = new uint32_t[n_elements[n]]; - memset(store[n], 0x00, (n_elements[n] * element_sizes[n])); - //TODO checkme - memset(size_list[n], STORAGE_FREE, (n_elements[n] * sizeof(**size_list))); - } -} - - -template -inline ReturnValue_t LocalPool::findEmpty(uint16_t pool_index, - uint16_t* element) { - ReturnValue_t status = DATA_STORAGE_FULL; - for (uint16_t foundElement = 0; foundElement < n_elements[pool_index]; - foundElement++) { - if (size_list[pool_index][foundElement] == STORAGE_FREE) { - *element = foundElement; - status = RETURN_OK; - break; - } - } - return status; -} - -template -inline void LocalPool::write(store_address_t packet_id, - const uint8_t* data, size_t size) { - uint8_t* ptr; - uint32_t packet_position = getRawPosition(packet_id); - - //check size? -> Not necessary, because size is checked before calling this function. - ptr = &store[packet_id.pool_index][packet_position]; - memcpy(ptr, data, size); - size_list[packet_id.pool_index][packet_id.packet_index] = size; -} - -//Returns page size of 0 in case store_index is illegal -template -inline uint32_t LocalPool::getPageSize(uint16_t pool_index) { - if (pool_index < NUMBER_OF_POOLS) { - return element_sizes[pool_index]; - } else { - return 0; - } -} - -template -inline ReturnValue_t LocalPool::getPoolIndex( - size_t packet_size, uint16_t* poolIndex, uint16_t startAtIndex) { - for (uint16_t n = startAtIndex; n < NUMBER_OF_POOLS; n++) { - //debug << "LocalPool " << getObjectId() << "::getPoolIndex: Pool: " << - // n << ", Element Size: " << element_sizes[n] << std::endl; - if (element_sizes[n] >= packet_size) { - *poolIndex = n; - return RETURN_OK; - } - } - return DATA_TOO_LARGE; -} - -template -inline uint32_t LocalPool::getRawPosition( - store_address_t packet_id) { - return packet_id.packet_index * element_sizes[packet_id.pool_index]; -} - -template -inline ReturnValue_t LocalPool::reserveSpace( - const uint32_t size, store_address_t* address, bool ignoreFault) { - ReturnValue_t status = getPoolIndex(size, &address->pool_index); - if (status != RETURN_OK) { - sif::error << "LocalPool( " << std::hex << getObjectId() << std::dec - << " )::reserveSpace: Packet too large." << std::endl; - return status; - } - status = findEmpty(address->pool_index, &address->packet_index); - while (status != RETURN_OK && spillsToHigherPools) { - status = getPoolIndex(size, &address->pool_index, address->pool_index + 1); - if (status != RETURN_OK) { - //We don't find any fitting pool anymore. - break; - } - status = findEmpty(address->pool_index, &address->packet_index); - } - if (status == RETURN_OK) { - // if (getObjectId() == objects::IPC_STORE && address->pool_index >= 3) { - // debug << "Reserve: Pool: " << std::dec << address->pool_index << - // " Index: " << address->packet_index << std::endl; - // } - - size_list[address->pool_index][address->packet_index] = size; - } else { - if (!ignoreFault and internalErrorReporter != nullptr) { - internalErrorReporter->storeFull(); - } - // error << "LocalPool( " << std::hex << getObjectId() << std::dec - // << " )::reserveSpace: Packet store is full." << std::endl; - } - return status; -} - -template -inline LocalPool::~LocalPool(void) { - for (uint16_t n = 0; n < NUMBER_OF_POOLS; n++) { - delete[] store[n]; - delete[] size_list[n]; - } -} - -template -inline ReturnValue_t LocalPool::addData( - store_address_t* storageId, const uint8_t* data, size_t size, - bool ignoreFault) { - ReturnValue_t status = reserveSpace(size, storageId, ignoreFault); - if (status == RETURN_OK) { - write(*storageId, data, size); - } - return status; -} - -template -inline ReturnValue_t LocalPool::getFreeElement( - store_address_t* storageId, const size_t size, - uint8_t** p_data, bool ignoreFault) { - ReturnValue_t status = reserveSpace(size, storageId, ignoreFault); - if (status == RETURN_OK) { - *p_data = &store[storageId->pool_index][getRawPosition(*storageId)]; - } else { - *p_data = NULL; - } - return status; -} - -template -inline ConstAccessorPair LocalPool::getData( - store_address_t storeId) { - uint8_t* tempData = nullptr; - ConstStorageAccessor constAccessor(storeId, this); - ReturnValue_t status = modifyData(storeId, &tempData, &constAccessor.size_); - constAccessor.constDataPointer = tempData; - return ConstAccessorPair(status, std::move(constAccessor)); -} - -template -inline ReturnValue_t LocalPool::getData(store_address_t storeId, - ConstStorageAccessor& storeAccessor) { - uint8_t* tempData = nullptr; - ReturnValue_t status = modifyData(storeId, &tempData, &storeAccessor.size_); - storeAccessor.assignStore(this); - storeAccessor.constDataPointer = tempData; - return status; -} - -template -inline ReturnValue_t LocalPool::getData( - store_address_t packet_id, const uint8_t** packet_ptr, size_t* size) { - uint8_t* tempData = nullptr; - ReturnValue_t status = modifyData(packet_id, &tempData, size); - *packet_ptr = tempData; - return status; -} - -template -inline AccessorPair LocalPool::modifyData( - store_address_t storeId) { - StorageAccessor accessor(storeId, this); - ReturnValue_t status = modifyData(storeId, &accessor.dataPointer, - &accessor.size_); - accessor.assignConstPointer(); - return AccessorPair(status, std::move(accessor)); -} - -template -inline ReturnValue_t LocalPool::modifyData( - store_address_t storeId, StorageAccessor& storeAccessor) { - storeAccessor.assignStore(this); - ReturnValue_t status = modifyData(storeId, &storeAccessor.dataPointer, - &storeAccessor.size_); - storeAccessor.assignConstPointer(); - return status; -} - -template -inline ReturnValue_t LocalPool::modifyData( - store_address_t packet_id, uint8_t** packet_ptr, size_t* size) { - ReturnValue_t status = RETURN_FAILED; - if (packet_id.pool_index >= NUMBER_OF_POOLS) { - return ILLEGAL_STORAGE_ID; - } - if ((packet_id.packet_index >= n_elements[packet_id.pool_index])) { - return ILLEGAL_STORAGE_ID; - } - if (size_list[packet_id.pool_index][packet_id.packet_index] - != STORAGE_FREE) { - uint32_t packet_position = getRawPosition(packet_id); - *packet_ptr = &store[packet_id.pool_index][packet_position]; - *size = size_list[packet_id.pool_index][packet_id.packet_index]; - status = RETURN_OK; - } else { - status = DATA_DOES_NOT_EXIST; - } - return status; -} - -template -inline ReturnValue_t LocalPool::deleteData( - store_address_t packet_id) { - //if (getObjectId() == objects::IPC_STORE && packet_id.pool_index >= 3) { - // debug << "Delete: Pool: " << std::dec << packet_id.pool_index << " Index: " - // << packet_id.packet_index << std::endl; - //} - ReturnValue_t status = RETURN_OK; - uint32_t page_size = getPageSize(packet_id.pool_index); - if ((page_size != 0) - && (packet_id.packet_index < n_elements[packet_id.pool_index])) { - uint16_t packet_position = getRawPosition(packet_id); - uint8_t* ptr = &store[packet_id.pool_index][packet_position]; - memset(ptr, 0, page_size); - //Set free list - size_list[packet_id.pool_index][packet_id.packet_index] = STORAGE_FREE; - } else { - //pool_index or packet_index is too large - sif::error << "LocalPool:deleteData failed." << std::endl; - status = ILLEGAL_STORAGE_ID; - } - return status; -} - -template -inline void LocalPool::clearStore() { - for (uint16_t n = 0; n < NUMBER_OF_POOLS; n++) { - //TODO checkme - memset(size_list[n], STORAGE_FREE, (n_elements[n] * sizeof(**size_list))); - } -} - -template -inline ReturnValue_t LocalPool::deleteData(uint8_t* ptr, - size_t size, store_address_t* storeId) { - store_address_t localId; - ReturnValue_t result = ILLEGAL_ADDRESS; - for (uint16_t n = 0; n < NUMBER_OF_POOLS; n++) { - //Not sure if new allocates all stores in order. so better be careful. - if ((store[n] <= ptr) && (&store[n][n_elements[n]*element_sizes[n]]) > ptr) { - localId.pool_index = n; - uint32_t deltaAddress = ptr - store[n]; - // Getting any data from the right "block" is ok. - // This is necessary, as IF's sometimes don't point to the first - // element of an object. - localId.packet_index = deltaAddress / element_sizes[n]; - result = deleteData(localId); - //if (deltaAddress % element_sizes[n] != 0) { - // error << "Pool::deleteData: address not aligned!" << std::endl; - //} - break; - } - } - if (storeId != NULL) { - *storeId = localId; - } - return result; -} - -template -inline ReturnValue_t LocalPool::initialize() { - ReturnValue_t result = SystemObject::initialize(); - if (result != RETURN_OK) { - return result; - } - internalErrorReporter = objectManager->get( - objects::INTERNAL_ERROR_REPORTER); - if (internalErrorReporter == nullptr){ - return ObjectManagerIF::INTERNAL_ERR_REPORTER_UNINIT; - } - - //Check if any pool size is large than the maximum allowed. - for (uint8_t count = 0; count < NUMBER_OF_POOLS; count++) { - if (element_sizes[count] >= STORAGE_FREE) { - sif::error << "LocalPool::initialize: Pool is too large! " - "Max. allowed size is: " << (STORAGE_FREE - 1) << std::endl; - return StorageManagerIF::POOL_TOO_LARGE; - } - } - return RETURN_OK; -} - -#endif /* FSFW_STORAGEMANAGER_LOCALPOOL_TPP_ */ diff --git a/storagemanager/PoolManager.tpp b/storagemanager/PoolManager.tpp deleted file mode 100644 index 2be44ece..00000000 --- a/storagemanager/PoolManager.tpp +++ /dev/null @@ -1,56 +0,0 @@ -#ifndef FRAMEWORK_STORAGEMANAGER_POOLMANAGER_TPP_ -#define FRAMEWORK_STORAGEMANAGER_POOLMANAGER_TPP_ - -#ifndef FSFW_STORAGEMANAGER_POOLMANAGER_H_ -#error Include PoolManager.h before PoolManager.tpp! -#endif - -template -inline PoolManager::PoolManager(object_id_t setObjectId, - const uint16_t element_sizes[NUMBER_OF_POOLS], - const uint16_t n_elements[NUMBER_OF_POOLS]) : - LocalPool(setObjectId, element_sizes, n_elements, true) { - mutex = MutexFactory::instance()->createMutex(); -} - -template -inline PoolManager::~PoolManager(void) { - MutexFactory::instance()->deleteMutex(mutex); -} - -template -inline ReturnValue_t PoolManager::reserveSpace( - const uint32_t size, store_address_t* address, bool ignoreFault) { - MutexHelper mutexHelper(mutex,MutexIF::WAITING, mutexTimeoutMs); - ReturnValue_t status = LocalPool::reserveSpace(size, - address,ignoreFault); - return status; -} - -template -inline ReturnValue_t PoolManager::deleteData( - store_address_t packet_id) { - // debug << "PoolManager( " << translateObject(getObjectId()) << - // " )::deleteData from store " << packet_id.pool_index << - // ". id is "<< packet_id.packet_index << std::endl; - MutexHelper mutexHelper(mutex,MutexIF::WAITING, mutexTimeoutMs); - ReturnValue_t status = LocalPool::deleteData(packet_id); - return status; -} - -template -inline ReturnValue_t PoolManager::deleteData(uint8_t* buffer, - size_t size, store_address_t* storeId) { - MutexHelper mutexHelper(mutex,MutexIF::WAITING, mutexTimeoutMs); - ReturnValue_t status = LocalPool::deleteData(buffer, - size, storeId); - return status; -} - -template -inline void PoolManager::setMutexTimeout( - uint32_t mutexTimeoutMs) { - this->mutexTimeout = mutexTimeoutMs; -} - -#endif /* FRAMEWORK_STORAGEMANAGER_POOLMANAGER_TPP_ */ From c8ddfe598b7ccb1c4f7a4c67dbbd6aa27231137e Mon Sep 17 00:00:00 2001 From: Spacefish Date: Tue, 15 Dec 2020 23:00:30 +0100 Subject: [PATCH 11/26] timemanager update --- timemanager/CCSDSTime.cpp | 38 ++--- timemanager/CCSDSTime.h | 39 ++--- timemanager/Clock.h | 265 ++++++++++++++++--------------- timemanager/Countdown.cpp | 10 +- timemanager/Countdown.h | 28 ++-- timemanager/ReceivesTimeInfoIF.h | 13 +- timemanager/TimeMessage.cpp | 7 - timemanager/TimeMessage.h | 15 +- timemanager/TimeStamperIF.h | 6 +- timemanager/clockDefinitions.h | 13 ++ 10 files changed, 217 insertions(+), 217 deletions(-) create mode 100644 timemanager/clockDefinitions.h diff --git a/timemanager/CCSDSTime.cpp b/timemanager/CCSDSTime.cpp index f137e030..aefcac2e 100644 --- a/timemanager/CCSDSTime.cpp +++ b/timemanager/CCSDSTime.cpp @@ -1,9 +1,9 @@ #include "CCSDSTime.h" - +#include #include #include #include -#include + CCSDSTime::CCSDSTime() { } @@ -53,8 +53,8 @@ ReturnValue_t CCSDSTime::convertToCcsds(Ccs_mseconds* to, return RETURN_OK; } -ReturnValue_t CCSDSTime::convertFromCcsds(Clock::TimeOfDay_t* to, const uint8_t* from, - uint32_t length) { +ReturnValue_t CCSDSTime::convertFromCcsds(Clock::TimeOfDay_t* to, + const uint8_t* from, size_t length) { ReturnValue_t result; if (length > 0xFF) { return LENGTH_MISMATCH; @@ -72,7 +72,7 @@ ReturnValue_t CCSDSTime::convertFromCcsds(Clock::TimeOfDay_t* to, const uint8_t* case CDS: return convertFromCDS(to, from, length); case CCS: { - uint32_t temp = 0; + size_t temp = 0; return convertFromCCS(to, from, &temp, length); } @@ -81,13 +81,13 @@ ReturnValue_t CCSDSTime::convertFromCcsds(Clock::TimeOfDay_t* to, const uint8_t* } } -ReturnValue_t CCSDSTime::convertFromCUC(Clock::TimeOfDay_t* to, const uint8_t* from, - uint8_t length) { +ReturnValue_t CCSDSTime::convertFromCUC(Clock::TimeOfDay_t* to, + const uint8_t* from, uint8_t length) { return UNSUPPORTED_TIME_FORMAT; } -ReturnValue_t CCSDSTime::convertFromCDS(Clock::TimeOfDay_t* to, const uint8_t* from, - uint8_t length) { +ReturnValue_t CCSDSTime::convertFromCDS(Clock::TimeOfDay_t* to, + const uint8_t* from, uint8_t length) { timeval time; ReturnValue_t result = convertFromCDS(&time, from, NULL, length); if (result != HasReturnvaluesIF::RETURN_OK) { @@ -96,8 +96,8 @@ ReturnValue_t CCSDSTime::convertFromCDS(Clock::TimeOfDay_t* to, const uint8_t* f return convertTimevalToTimeOfDay(to, &time); } -ReturnValue_t CCSDSTime::convertFromCCS(Clock::TimeOfDay_t* to, const uint8_t* from, - uint32_t* foundLength, uint32_t maxLength) { +ReturnValue_t CCSDSTime::convertFromCCS(Clock::TimeOfDay_t* to, + const uint8_t* from, size_t* foundLength, size_t maxLength) { uint8_t subsecondsLength = *from & 0b111; uint32_t totalLength = subsecondsLength + 8; if (maxLength < totalLength) { @@ -152,8 +152,8 @@ ReturnValue_t CCSDSTime::convertFromCCS(Clock::TimeOfDay_t* to, const uint8_t* f } -ReturnValue_t CCSDSTime::convertFromASCII(Clock::TimeOfDay_t* to, const uint8_t* from, - uint8_t length) { +ReturnValue_t CCSDSTime::convertFromASCII(Clock::TimeOfDay_t* to, + const uint8_t* from, uint8_t length) { if (length < 19) { return RETURN_FAILED; } @@ -395,7 +395,7 @@ ReturnValue_t CCSDSTime::convertToCcsds(OBT_FLP* to, const timeval* from) { } ReturnValue_t CCSDSTime::convertFromCcsds(timeval* to, const uint8_t* from, - uint32_t* foundLength, uint32_t maxLength) { + size_t* foundLength, size_t maxLength) { //We don't expect ascii here. SHOULDDO uint8_t codeIdentification = (*from >> 4); switch (codeIdentification) { @@ -413,7 +413,7 @@ ReturnValue_t CCSDSTime::convertFromCcsds(timeval* to, const uint8_t* from, } ReturnValue_t CCSDSTime::convertFromCUC(timeval* to, const uint8_t* from, - uint32_t* foundLength, uint32_t maxLength) { + size_t* foundLength, size_t maxLength) { if (maxLength < 1) { return INVALID_TIME_FORMAT; } @@ -491,7 +491,7 @@ ReturnValue_t CCSDSTime::convertTimevalToTimeOfDay(Clock::TimeOfDay_t* to, } ReturnValue_t CCSDSTime::convertFromCDS(timeval* to, const uint8_t* from, - uint32_t* foundLength, uint32_t maxLength) { + size_t* foundLength, size_t maxLength) { uint8_t pField = *from; from++; //Check epoch @@ -556,12 +556,12 @@ ReturnValue_t CCSDSTime::convertFromCDS(timeval* to, const uint8_t* from, } ReturnValue_t CCSDSTime::convertFromCUC(timeval* to, uint8_t pField, - const uint8_t* from, uint32_t* foundLength, uint32_t maxLength) { + const uint8_t* from, size_t* foundLength, size_t maxLength) { uint32_t secs = 0; uint32_t subSeconds = 0; uint8_t nCoarse = ((pField & 0b1100) >> 2) + 1; uint8_t nFine = (pField & 0b11); - uint32_t totalLength = nCoarse + nFine; + size_t totalLength = nCoarse + nFine; if (foundLength != NULL) { *foundLength = totalLength; } @@ -593,7 +593,7 @@ uint32_t CCSDSTime::subsecondsToMicroseconds(uint16_t subseconds) { } ReturnValue_t CCSDSTime::convertFromCCS(timeval* to, const uint8_t* from, - uint32_t* foundLength, uint32_t maxLength) { + size_t* foundLength, size_t maxLength) { Clock::TimeOfDay_t tempTime; ReturnValue_t result = convertFromCCS(&tempTime, from, foundLength, maxLength); diff --git a/timemanager/CCSDSTime.h b/timemanager/CCSDSTime.h index 89fcff92..e9e6957f 100644 --- a/timemanager/CCSDSTime.h +++ b/timemanager/CCSDSTime.h @@ -1,9 +1,10 @@ -#ifndef CCSDSTIME_H_ -#define CCSDSTIME_H_ +#ifndef FSFW_TIMEMANAGER_CCSDSTIME_H_ +#define FSFW_TIMEMANAGER_CCSDSTIME_H_ // COULDDO: have calls in Clock.h which return time quality and use timespec accordingly #include "Clock.h" +#include "clockDefinitions.h" #include "../returnvalues/HasReturnvaluesIF.h" #include @@ -154,8 +155,8 @@ public: * - @c LENGTH_MISMATCH if the length does not match the P Field * - @c INVALID_TIME_FORMAT if the format or a value is invalid */ - static ReturnValue_t convertFromCcsds(Clock::TimeOfDay_t *to, uint8_t const *from, - uint32_t length); + static ReturnValue_t convertFromCcsds(Clock::TimeOfDay_t *to, + uint8_t const *from, size_t length); /** * not implemented yet @@ -165,34 +166,34 @@ public: * @return */ static ReturnValue_t convertFromCcsds(timeval *to, uint8_t const *from, - uint32_t* foundLength, uint32_t maxLength); + size_t* foundLength, size_t maxLength); - static ReturnValue_t convertFromCUC(Clock::TimeOfDay_t *to, uint8_t const *from, - uint8_t length); + static ReturnValue_t convertFromCUC(Clock::TimeOfDay_t *to, + uint8_t const *from, uint8_t length); static ReturnValue_t convertFromCUC(timeval *to, uint8_t const *from, - uint32_t* foundLength, uint32_t maxLength); + size_t* foundLength, size_t maxLength); static ReturnValue_t convertFromCUC(timeval *to, uint8_t pField, - uint8_t const *from, uint32_t* foundLength, uint32_t maxLength); + uint8_t const *from, size_t* foundLength, size_t maxLength); static ReturnValue_t convertFromCCS(timeval *to, uint8_t const *from, - uint32_t* foundLength, uint32_t maxLength); + size_t* foundLength, size_t maxLength); static ReturnValue_t convertFromCCS(timeval *to, uint8_t pField, - uint8_t const *from, uint32_t* foundLength, uint32_t maxLength); + uint8_t const *from, size_t* foundLength, size_t maxLength); - static ReturnValue_t convertFromCDS(Clock::TimeOfDay_t *to, uint8_t const *from, - uint8_t length); + static ReturnValue_t convertFromCDS(Clock::TimeOfDay_t *to, + uint8_t const *from, uint8_t length); static ReturnValue_t convertFromCDS(timeval *to, uint8_t const *from, - uint32_t* foundLength, uint32_t maxLength); + size_t* foundLength, size_t maxLength); - static ReturnValue_t convertFromCCS(Clock::TimeOfDay_t *to, uint8_t const *from, - uint32_t* foundLength, uint32_t maxLength); + static ReturnValue_t convertFromCCS(Clock::TimeOfDay_t *to, + uint8_t const *from, size_t* foundLength, size_t maxLength); - static ReturnValue_t convertFromASCII(Clock::TimeOfDay_t *to, uint8_t const *from, - uint8_t length); + static ReturnValue_t convertFromASCII(Clock::TimeOfDay_t *to, + uint8_t const *from, uint8_t length); static uint32_t subsecondsToMicroseconds(uint16_t subseconds); private: @@ -230,4 +231,4 @@ private: timeval* from); }; -#endif /* CCSDSTIME_H_ */ +#endif /* FSFW_TIMEMANAGER_CCSDSTIME_H_ */ diff --git a/timemanager/Clock.h b/timemanager/Clock.h index d8b06fda..f4ed847a 100644 --- a/timemanager/Clock.h +++ b/timemanager/Clock.h @@ -1,153 +1,166 @@ #ifndef FSFW_TIMEMANAGER_CLOCK_H_ #define FSFW_TIMEMANAGER_CLOCK_H_ +#include "clockDefinitions.h" #include "../returnvalues/HasReturnvaluesIF.h" -#include "../ipc/MutexHelper.h" +#include "../ipc/MutexFactory.h" #include "../globalfunctions/timevalOperations.h" #include #include -//! Don't use these for time points, type is not large enough for UNIX epoch. -using dur_millis_t = uint32_t; - class Clock { public: - typedef struct { - uint32_t year; //!< Year, A.D. - uint32_t month; //!< Month, 1 .. 12. - uint32_t day; //!< Day, 1 .. 31. - uint32_t hour; //!< Hour, 0 .. 23. - uint32_t minute; //!< Minute, 0 .. 59. - uint32_t second; //!< Second, 0 .. 59. - uint32_t usecond; //!< Microseconds, 0 .. 999999 - } TimeOfDay_t; + typedef struct { + uint32_t year; //!< Year, A.D. + uint32_t month; //!< Month, 1 .. 12. + uint32_t day; //!< Day, 1 .. 31. + uint32_t hour; //!< Hour, 0 .. 23. + uint32_t minute; //!< Minute, 0 .. 59. + uint32_t second; //!< Second, 0 .. 59. + uint32_t usecond; //!< Microseconds, 0 .. 999999 + } TimeOfDay_t; - /** - * This method returns the number of clock ticks per second. - * In RTEMS, this is typically 1000. - * @return The number of ticks. - * - * @deprecated, we should not worry about ticks, but only time - */ - static uint32_t getTicksPerSecond(void); - /** - * This system call sets the system time. - * To set the time, it uses a TimeOfDay_t struct. - * @param time The struct with the time settings to set. - * @return -@c RETURN_OK on success. Otherwise, the OS failure code - * is returned. - */ - static ReturnValue_t setClock(const TimeOfDay_t* time); - /** - * This system call sets the system time. - * To set the time, it uses a timeval struct. - * @param time The struct with the time settings to set. - * @return -@c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t setClock(const timeval* time); - /** - * This system call returns the current system clock in timeval format. - * The timval format has the fields @c tv_sec with seconds and @c tv_usec with - * microseconds since an OS-defined epoch. - * @param time A pointer to a timeval struct where the current time is stored. - * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getClock_timeval(timeval* time); + /** + * This method returns the number of clock ticks per second. + * In RTEMS, this is typically 1000. + * @return The number of ticks. + * + * @deprecated, we should not worry about ticks, but only time + */ + static uint32_t getTicksPerSecond(void); + /** + * This system call sets the system time. + * To set the time, it uses a TimeOfDay_t struct. + * @param time The struct with the time settings to set. + * @return -@c RETURN_OK on success. Otherwise, the OS failure code + * is returned. + */ + static ReturnValue_t setClock(const TimeOfDay_t* time); + /** + * This system call sets the system time. + * To set the time, it uses a timeval struct. + * @param time The struct with the time settings to set. + * @return -@c RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t setClock(const timeval* time); + /** + * This system call returns the current system clock in timeval format. + * The timval format has the fields @c tv_sec with seconds and @c tv_usec with + * microseconds since an OS-defined epoch. + * @param time A pointer to a timeval struct where the current time is stored. + * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getClock_timeval(timeval* time); - /** - * Get the time since boot in a timeval struct - * - * @param[out] time A pointer to a timeval struct where the uptime is stored. - * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. - * - * @deprecated, I do not think this should be able to fail, use timeval getUptime() - */ - static ReturnValue_t getUptime(timeval* uptime); + /** + * Get the time since boot in a timeval struct + * + * @param[out] time A pointer to a timeval struct where the uptime is stored. + * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. + * + * @deprecated, I do not think this should be able to fail, use timeval getUptime() + */ + static ReturnValue_t getUptime(timeval* uptime); - static timeval getUptime(); + static timeval getUptime(); - /** - * Get the time since boot in milliseconds - * - * This value can overflow! Still, it can be used to calculate time intervalls - * between two calls up to 49 days by always using uint32_t in the calculation - * - * @param ms uptime in ms - * @return RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getUptime(uint32_t* uptimeMs); + /** + * Get the time since boot in milliseconds + * + * This value can overflow! Still, it can be used to calculate time intervalls + * between two calls up to 49 days by always using uint32_t in the calculation + * + * @param ms uptime in ms + * @return RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getUptime(uint32_t* uptimeMs); - /** - * Returns the time in microseconds since an OS-defined epoch. - * The time is returned in a 64 bit unsigned integer. - * @param time A pointer to a 64 bit unisigned integer where the data is stored. - * @return \c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getClock_usecs(uint64_t* time); - /** - * Returns the time in a TimeOfDay_t struct. - * @param time A pointer to a TimeOfDay_t struct. - * @return \c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getDateAndTime(TimeOfDay_t* time); + /** + * Returns the time in microseconds since an OS-defined epoch. + * The time is returned in a 64 bit unsigned integer. + * @param time A pointer to a 64 bit unisigned integer where the data is stored. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getClock_usecs(uint64_t* time); + /** + * Returns the time in a TimeOfDay_t struct. + * @param time A pointer to a TimeOfDay_t struct. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getDateAndTime(TimeOfDay_t* time); - /** - * Converts a time of day struct to POSIX seconds. - * @param time The time of day as input - * @param timeval The corresponding seconds since the epoch. - * @return \c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t convertTimeOfDayToTimeval(const TimeOfDay_t* from, - timeval* to); + /** + * Converts a time of day struct to POSIX seconds. + * @param time The time of day as input + * @param timeval The corresponding seconds since the epoch. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t convertTimeOfDayToTimeval(const TimeOfDay_t* from, + timeval* to); - /** - * Converts a time represented as seconds and subseconds since unix epoch to days since J2000 - * - * @param time seconds since unix epoch - * @param[out] JD2000 days since J2000 - * @return \c RETURN_OK - */ - static ReturnValue_t convertTimevalToJD2000(timeval time, double* JD2000); + /** + * Converts a time represented as seconds and subseconds since unix + * epoch to days since J2000 + * + * @param time seconds since unix epoch + * @param[out] JD2000 days since J2000 + * @return @c RETURN_OK + */ + static ReturnValue_t convertTimevalToJD2000(timeval time, double* JD2000); - /** - * Calculates and adds the offset between UTC and TT - * - * Depends on the leap seconds to be set correctly. - * - * @param utc timeval, corresponding to UTC time - * @param[out] tt timeval, corresponding to Terrestial Time - * @return \c RETURN_OK on success, \c RETURN_FAILED if leapSeconds are not set - */ - static ReturnValue_t convertUTCToTT(timeval utc, timeval* tt); + /** + * Calculates and adds the offset between UTC and TT + * + * Depends on the leap seconds to be set correctly. + * + * @param utc timeval, corresponding to UTC time + * @param[out] tt timeval, corresponding to Terrestial Time + * @return + * - @c RETURN_OK on success + * - @c RETURN_FAILED if leapSeconds are not set + */ + static ReturnValue_t convertUTCToTT(timeval utc, timeval* tt); - /** - * Set the Leap Seconds since 1972 - * - * @param leapSeconds_ - * @return \c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t setLeapSeconds(const uint16_t leapSeconds_); + /** + * Set the Leap Seconds since 1972 + * + * @param leapSeconds_ + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t setLeapSeconds(const uint16_t leapSeconds_); - /** - * Get the Leap Seconds since 1972 - * - * Must be set before! - * - * @param[out] leapSeconds_ - * @return \c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getLeapSeconds(uint16_t *leapSeconds_); + /** + * Get the Leap Seconds since 1972 + * + * Must be set before! + * + * @param[out] leapSeconds_ + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getLeapSeconds(uint16_t *leapSeconds_); - /** - * Function to check and create the Mutex for the clock - * @return \c RETURN_OK on success. Otherwise \c RETURN_FAILED if not able to create one - */ - static ReturnValue_t checkOrCreateClockMutex(); + /** + * Function to check and create the Mutex for the clock + * @return + * - @c RETURN_OK on success. + * - Otherwise @c RETURN_FAILED if not able to create one + */ + static ReturnValue_t checkOrCreateClockMutex(); private: - static MutexIF* timeMutex; - static uint16_t leapSeconds; + static MutexIF* timeMutex; + static uint16_t leapSeconds; }; diff --git a/timemanager/Countdown.cpp b/timemanager/Countdown.cpp index d5695730..20b56189 100644 --- a/timemanager/Countdown.cpp +++ b/timemanager/Countdown.cpp @@ -1,14 +1,6 @@ -/** - * @file Countdown.cpp - * @brief This file defines the Countdown class. - * @date 21.03.2013 - * @author baetz - */ - - #include "Countdown.h" -Countdown::Countdown(uint32_t initialTimeout) : startTime(0), timeout(initialTimeout) { +Countdown::Countdown(uint32_t initialTimeout): timeout(initialTimeout) { } Countdown::~Countdown() { diff --git a/timemanager/Countdown.h b/timemanager/Countdown.h index b86d9fe0..f6a41e73 100644 --- a/timemanager/Countdown.h +++ b/timemanager/Countdown.h @@ -1,18 +1,13 @@ -/** - * @file Countdown.h - * @brief This file defines the Countdown class. - * @date 21.03.2013 - * @author baetz - */ - -#ifndef COUNTDOWN_H_ -#define COUNTDOWN_H_ +#ifndef FSFW_TIMEMANAGER_COUNTDOWN_H_ +#define FSFW_TIMEMANAGER_COUNTDOWN_H_ #include "Clock.h" +/** + * @brief This file defines the Countdown class. + * @author baetz + */ class Countdown { -private: - uint32_t startTime; public: uint32_t timeout; Countdown(uint32_t initialTimeout = 0); @@ -23,9 +18,14 @@ public: bool isBusy() const; - ReturnValue_t resetTimer(); //!< Use last set timeout value and restart timer. + //!< Use last set timeout value and restart timer. + ReturnValue_t resetTimer(); - void timeOut(); //!< Make hasTimedOut() return true + //!< Make hasTimedOut() return true + void timeOut(); + +private: + uint32_t startTime = 0; }; -#endif /* COUNTDOWN_H_ */ +#endif /* FSFW_TIMEMANAGER_COUNTDOWN_H_ */ diff --git a/timemanager/ReceivesTimeInfoIF.h b/timemanager/ReceivesTimeInfoIF.h index 14a750c5..c1247a42 100644 --- a/timemanager/ReceivesTimeInfoIF.h +++ b/timemanager/ReceivesTimeInfoIF.h @@ -1,12 +1,7 @@ -/** - * @file ReceivesTimeInfoIF.h - * @brief This file defines the ReceivesTimeInfoIF class. - * @date 26.02.2013 - * @author baetz - */ +#ifndef FSFW_TIMEMANAGER_RECEIVESTIMEINFOIF_H_ +#define FSFW_TIMEMANAGER_RECEIVESTIMEINFOIF_H_ -#ifndef RECEIVESTIMEINFOIF_H_ -#define RECEIVESTIMEINFOIF_H_ +#include "../ipc/MessageQueueSenderIF.h" /** * This is a Interface for classes that receive timing information @@ -28,4 +23,4 @@ public: }; -#endif /* RECEIVESTIMEINFOIF_H_ */ +#endif /* FSFW_TIMEMANAGER_RECEIVESTIMEINFOIF_H_ */ diff --git a/timemanager/TimeMessage.cpp b/timemanager/TimeMessage.cpp index 5a9a416b..a1042efe 100644 --- a/timemanager/TimeMessage.cpp +++ b/timemanager/TimeMessage.cpp @@ -1,10 +1,3 @@ -/** - * @file TimeMessage.cpp - * @brief This file defines the TimeMessage class. - * @date 26.02.2013 - * @author baetz - */ - #include "TimeMessage.h" TimeMessage::TimeMessage() { diff --git a/timemanager/TimeMessage.h b/timemanager/TimeMessage.h index 116002e6..f5ac3e14 100644 --- a/timemanager/TimeMessage.h +++ b/timemanager/TimeMessage.h @@ -1,15 +1,8 @@ -/** - * @file TimeMessage.h - * @brief This file defines the TimeMessage class. - * @date 26.02.2013 - * @author baetz - */ +#ifndef FSFW_TIMEMANAGER_TIMEMESSAGE_H_ +#define FSFW_TIMEMANAGER_TIMEMESSAGE_H_ -#ifndef TIMEMESSAGE_H_ -#define TIMEMESSAGE_H_ - -#include "../ipc/MessageQueueMessage.h" #include "Clock.h" +#include "../ipc/MessageQueueMessage.h" #include class TimeMessage : public MessageQueueMessage { @@ -53,4 +46,4 @@ public: uint32_t getCounterValue(); }; -#endif /* TIMEMESSAGE_H_ */ +#endif /* FSFW_TIMEMANAGER_TIMEMESSAGE_H_ */ diff --git a/timemanager/TimeStamperIF.h b/timemanager/TimeStamperIF.h index 96011088..57b7f014 100644 --- a/timemanager/TimeStamperIF.h +++ b/timemanager/TimeStamperIF.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_TIMEMANAGER_TIMESTAMPERIF_H_ -#define FRAMEWORK_TIMEMANAGER_TIMESTAMPERIF_H_ +#ifndef FSFW_TIMEMANAGER_TIMESTAMPERIF_H_ +#define FSFW_TIMEMANAGER_TIMESTAMPERIF_H_ #include "../returnvalues/HasReturnvaluesIF.h" @@ -25,4 +25,4 @@ public: -#endif /* FRAMEWORK_TIMEMANAGER_TIMESTAMPERIF_H_ */ +#endif /* FSFW_TIMEMANAGER_TIMESTAMPERIF_H_ */ diff --git a/timemanager/clockDefinitions.h b/timemanager/clockDefinitions.h new file mode 100644 index 00000000..bba6e3ca --- /dev/null +++ b/timemanager/clockDefinitions.h @@ -0,0 +1,13 @@ +#ifndef FSFW_TIMEMANAGER_CLOCKDEFINITIONS_H_ +#define FSFW_TIMEMANAGER_CLOCKDEFINITIONS_H_ + +#include + +// I'd also like to include the TimeOfDay_t struct here, but that would +// break code which uses Clock::TimeOfDay_t. Solution would be to use +// a Clock namespace instead of class with static functions. + +//! Don't use these for time points, type is not large enough for UNIX epoch. +using dur_millis_t = uint32_t; + +#endif /* FSFW_TIMEMANAGER_CLOCKDEFINITIONS_H_ */ From 5317391f8a1077eebc179e3ce3df8cdb9e753315 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 21 Dec 2020 17:19:43 +0100 Subject: [PATCH 12/26] reverted change --- serviceinterface/ServiceInterfaceBuffer.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/serviceinterface/ServiceInterfaceBuffer.h b/serviceinterface/ServiceInterfaceBuffer.h index e69538d1..c5d5b258 100644 --- a/serviceinterface/ServiceInterfaceBuffer.h +++ b/serviceinterface/ServiceInterfaceBuffer.h @@ -30,7 +30,7 @@ protected: //! This is called when buffer becomes full. If //! buffer is not used, then this is called every //! time when characters are put to stream. - int overflow(int c = std::ostream::traits_type::eof()) override; + int overflow(int c = Traits::eof()) override; //! This function is called when stream is flushed, //! for example when std::endl is put to stream. From b28bf35fc340cf9718af100c7531f15ea6bf1a8f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 12:44:55 +0100 Subject: [PATCH 13/26] devicehandler updates --- devicehandlers/DeviceHandlerBase.cpp | 10 +++- devicehandlers/DeviceHandlerBase.h | 69 ++++++++++++++-------------- devicehandlers/DeviceHandlerIF.h | 2 +- 3 files changed, 45 insertions(+), 36 deletions(-) diff --git a/devicehandlers/DeviceHandlerBase.cpp b/devicehandlers/DeviceHandlerBase.cpp index f095834e..cb040714 100644 --- a/devicehandlers/DeviceHandlerBase.cpp +++ b/devicehandlers/DeviceHandlerBase.cpp @@ -928,7 +928,7 @@ void DeviceHandlerBase::doTransition(Mode_t modeFrom, Submode_t subModeFrom) { uint32_t DeviceHandlerBase::getTransitionDelayMs(Mode_t modeFrom, Mode_t modeTo) { - return 0; + return 5000; } ReturnValue_t DeviceHandlerBase::getStateOfSwitches(void) { @@ -1459,3 +1459,11 @@ DeviceCommandId_t DeviceHandlerBase::getPendingCommand() const { } return DeviceHandlerIF::NO_COMMAND; } + +void DeviceHandlerBase::setNormalDatapoolEntriesInvalid() { + for(const auto& reply: deviceReplyMap) { + if(reply.second.dataSet != nullptr) { + reply.second.dataSet->setValidity(false, true); + } + } +} diff --git a/devicehandlers/DeviceHandlerBase.h b/devicehandlers/DeviceHandlerBase.h index 9a5287e0..ee4447ed 100644 --- a/devicehandlers/DeviceHandlerBase.h +++ b/devicehandlers/DeviceHandlerBase.h @@ -254,9 +254,10 @@ protected: * * @param[out] id the device command id that has been built * @return - * - @c RETURN_OK to send command after setting #rawPacket and #rawPacketLen. - * - @c NOTHING_TO_SEND when no command is to be sent. - * - Anything else triggers an even with the returnvalue as a parameter. + * - @c RETURN_OK to send command after setting #rawPacket and + * #rawPacketLen. + * - @c NOTHING_TO_SEND when no command is to be sent. + * - Anything else triggers an even with the returnvalue as a parameter. */ virtual ReturnValue_t buildNormalDeviceCommand(DeviceCommandId_t * id) = 0; @@ -273,7 +274,8 @@ protected: * and filling them in doStartUp(), doShutDown() and doTransition() so no * modes have to be checked here. * - * #rawPacket and #rawPacketLen must be set by this method to the packet to be sent. + * #rawPacket and #rawPacketLen must be set by this method to the + * packet to be sent. * * @param[out] id the device command id built * @return @@ -284,19 +286,23 @@ protected: virtual ReturnValue_t buildTransitionDeviceCommand(DeviceCommandId_t * id) = 0; /** - * @brief Build a device command packet from data supplied by a direct command. + * @brief Build a device command packet from data supplied by a + * direct command. * * @details - * #rawPacket and #rawPacketLen should be set by this method to the packet to be sent. - * The existence of the command in the command map and the command size check - * against 0 are done by the base class. + * #rawPacket and #rawPacketLen should be set by this method to the packet + * to be sent. The existence of the command in the command map and the + * command size check against 0 are done by the base class. * - * @param deviceCommand the command to build, already checked against deviceCommandMap + * @param deviceCommand the command to build, already checked against + * deviceCommandMap * @param commandData pointer to the data from the direct command * @param commandDataLen length of commandData * @return - * - @c RETURN_OK to send command after #rawPacket and #rawPacketLen have been set. - * - Anything else triggers an event with the returnvalue as a parameter + * - @c RETURN_OK to send command after #rawPacket and #rawPacketLen + * have been set. + * - Anything else triggers an event with the + * returnvalue as a parameter */ virtual ReturnValue_t buildCommandFromCommand(DeviceCommandId_t deviceCommand, const uint8_t * commandData, size_t commandDataLen) = 0; @@ -681,7 +687,7 @@ protected: //! The dataset used to access housekeeping data related to the //! respective device reply. Will point to a dataset held by //! the child handler (if one is specified) - LocalPoolDataSetBase* dataSet; + LocalPoolDataSetBase* dataSet = nullptr; //! The command that expects this reply. DeviceCommandMap::iterator command; }; @@ -743,6 +749,17 @@ protected: //!< Object which may be the root cause of an identified fault. static object_id_t defaultFdirParentId; + /** + * @brief Set all datapool variables that are update periodically in + * normal mode invalid + * @details + * The default implementation will set all datasets which have been added + * in #fillCommandAndReplyMap to invalid. It will also set all pool + * variables inside the dataset to invalid. The user can override this + * method optionally. + */ + virtual void setNormalDatapoolEntriesInvalid(); + /** * Helper function to get pending command. This is useful for devices * like SPI sensors to identify the last sent command. @@ -785,7 +802,6 @@ protected: * * The submode is left unchanged. * - * * @param newMode */ void setMode(Mode_t newMode); @@ -838,8 +854,6 @@ protected: virtual void doTransition(Mode_t modeFrom, Submode_t subModeFrom); /** - * Is the combination of mode and submode valid? - * * @param mode * @param submode * @return @@ -850,13 +864,10 @@ protected: Submode_t submode); /** - * Get the Rmap action for the current step. - * + * Get the communication action for the current step. * The step number can be read from #pstStep. - * - * @return The Rmap action to execute in this step + * @return The communication action to execute in this step */ - virtual CommunicationAction getComAction(); /** @@ -898,8 +909,8 @@ protected: * It gets space in the #IPCStore, copies data there, then sends a raw reply * containing the store address. * - * This method is virtual, as the STR has a different channel to send - * raw replies and overwrites it accordingly. + * This method is virtual, as devices can have different channels to send + * raw replies * * @param data data to send * @param len length of @c data @@ -918,7 +929,7 @@ protected: void replyRawReplyIfnotWiretapped(const uint8_t *data, size_t len); /** - * notify child about mode change + * @brief Notify child about mode change. */ virtual void modeChanged(void); @@ -950,8 +961,7 @@ protected: DeviceCommandId_t alternateReplyID = 0); /** - * get the state of the PCDU switches in the datapool - * + * Get the state of the PCDU switches in the local datapool * @return * - @c PowerSwitchIF::SWITCH_ON if all switches specified * by #switches are on @@ -961,15 +971,6 @@ protected: */ ReturnValue_t getStateOfSwitches(void); - /** - * @brief Set all datapool variables that are update periodically in - * normal mode invalid - * @details TODO: Use local pools - * Child classes should provide an implementation which sets all those - * variables invalid which are set periodically during any normal mode. - */ - virtual void setNormalDatapoolEntriesInvalid() = 0; - /** * build a list of sids and pass it to the #hkSwitcher */ diff --git a/devicehandlers/DeviceHandlerIF.h b/devicehandlers/DeviceHandlerIF.h index dba6b228..e5648751 100644 --- a/devicehandlers/DeviceHandlerIF.h +++ b/devicehandlers/DeviceHandlerIF.h @@ -131,7 +131,7 @@ public: // Standard codes used in interpretDeviceReply static const ReturnValue_t DEVICE_DID_NOT_EXECUTE = MAKE_RETURN_CODE(0xC0); //the device reported, that it did not execute the command static const ReturnValue_t DEVICE_REPORTED_ERROR = MAKE_RETURN_CODE(0xC1); - static const ReturnValue_t UNKNOW_DEVICE_REPLY = MAKE_RETURN_CODE(0xC2); //the deviceCommandId reported by scanforReply is unknown + static const ReturnValue_t UNKNOWN_DEVICE_REPLY = MAKE_RETURN_CODE(0xC2); //the deviceCommandId reported by scanforReply is unknown static const ReturnValue_t DEVICE_REPLY_INVALID = MAKE_RETURN_CODE(0xC3); //syntax etc is correct but still not ok, eg parameters where none are expected // Standard codes used in buildCommandFromCommand From ca2d242adb50a4795de8f9d33459707aec93490c Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 12:45:51 +0100 Subject: [PATCH 14/26] defaultcfg update --- defaultcfg/fsfwconfig/FSFWConfig.h | 16 ++++++++-------- defaultcfg/fsfwconfig/OBSWConfig.h | 4 ++++ 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/defaultcfg/fsfwconfig/FSFWConfig.h b/defaultcfg/fsfwconfig/FSFWConfig.h index 1386bf66..dda8497d 100644 --- a/defaultcfg/fsfwconfig/FSFWConfig.h +++ b/defaultcfg/fsfwconfig/FSFWConfig.h @@ -15,12 +15,6 @@ //! Can be used to enable additional debugging printouts for developing the FSFW #define FSFW_PRINT_VERBOSITY_LEVEL 0 -//! Defines the FIFO depth of each commanding service base which -//! also determines how many commands a CSB service can handle in one cycle -//! simulataneously. This will increase the required RAM for -//! each CSB service ! -#define FSFW_CSB_FIFO_DEPTH 6 - //! If FSFW_OBJ_EVENT_TRANSLATION is set to one, //! additional output which requires the translation files translateObjects //! and translateEvents (and their compiled source files) @@ -30,8 +24,8 @@ #define FSFW_DEBUG_OUTPUT 1 //! Specify whether info events are printed too. #define FSFW_DEBUG_INFO 1 -#include -#include +#include "objects/translateObjects.h" +#include "events/translateEvents.h" #else #define FSFW_DEBUG_OUTPUT 0 #endif @@ -52,6 +46,12 @@ static constexpr uint8_t FSFW_MISSION_TIMESTAMP_SIZE = 8; static constexpr size_t FSFW_EVENTMGMR_MATCHTREE_NODES = 240; static constexpr size_t FSFW_EVENTMGMT_EVENTIDMATCHERS = 120; static constexpr size_t FSFW_EVENTMGMR_RANGEMATCHERS = 120; + +//! Defines the FIFO depth of each commanding service base which +//! also determines how many commands a CSB service can handle in one cycle +//! simulataneously. This will increase the required RAM for +//! each CSB service ! +static constexpr uint8_t FSFW_CSB_FIFO_DEPTH = 6; } #endif /* CONFIG_FSFWCONFIG_H_ */ diff --git a/defaultcfg/fsfwconfig/OBSWConfig.h b/defaultcfg/fsfwconfig/OBSWConfig.h index a9f57638..8ad2cb67 100644 --- a/defaultcfg/fsfwconfig/OBSWConfig.h +++ b/defaultcfg/fsfwconfig/OBSWConfig.h @@ -3,6 +3,10 @@ #include "OBSWVersion.h" +#include "objects/systemObjectList.h" +#include "events/subsystemIdRanges.h" +#include "returnvalues/classIds.h" + #ifdef __cplusplus namespace config { #endif From 9de2b054ef6155293237cc928ca97bf2a5b0c718 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 12:53:03 +0100 Subject: [PATCH 15/26] updated changelog --- CHANGELOG | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index 7b07db08..4e51bc64 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -53,6 +53,12 @@ ID for now. - There is an additional `PERFORM_OPERATION` step for the device handler base. It is important that DHB users adapt their polling sequence tables to perform this step. This steps allows for aclear distinction between operation and communication steps +- setNormalDatapoolEntriesInvalid is not an abstract method and a default implementation was provided +- getTransitionDelayMs now return 5000 ms instead of 0 in default implementation + +### DeviceHandlerIF + +- Typo for UNKNOWN_DEVICE_REPLY ### Events From 6f756a721c9262cce17003d2dfe4163738e583d4 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 13:05:59 +0100 Subject: [PATCH 16/26] clearing HK messagei ncluded now --- ipc/CommandMessageCleaner.cpp | 8 ++++++-- ipc/MessageQueueMessageIF.h | 2 +- ipc/MutexFactory.h | 6 +++--- ipc/MutexHelper.h | 4 ++-- 4 files changed, 12 insertions(+), 8 deletions(-) diff --git a/ipc/CommandMessageCleaner.cpp b/ipc/CommandMessageCleaner.cpp index 6a99b4d2..6a364069 100644 --- a/ipc/CommandMessageCleaner.cpp +++ b/ipc/CommandMessageCleaner.cpp @@ -1,4 +1,4 @@ -#include "../ipc/CommandMessageCleaner.h" +#include "CommandMessageCleaner.h" #include "../devicehandlers/DeviceHandlerMessage.h" #include "../health/HealthMessage.h" @@ -7,11 +7,12 @@ #include "../monitoring/MonitoringMessage.h" #include "../subsystem/modes/ModeSequenceMessage.h" #include "../tmstorage/TmStoreMessage.h" +#include "../housekeeping/HousekeepingMessage.h" #include "../parameters/ParameterMessage.h" void CommandMessageCleaner::clearCommandMessage(CommandMessage* message) { switch(message->getMessageType()){ - case messagetypes::MODE_COMMAND: + case messagetypes::MODE_COMMAND: ModeMessage::clear(message); break; case messagetypes::HEALTH_COMMAND: @@ -38,6 +39,9 @@ void CommandMessageCleaner::clearCommandMessage(CommandMessage* message) { case messagetypes::PARAMETER: ParameterMessage::clear(message); break; + case messagetypes::HOUSEKEEPING: + HousekeepingMessage::clear(message); + break; default: messagetypes::clearMissionMessage(message); break; diff --git a/ipc/MessageQueueMessageIF.h b/ipc/MessageQueueMessageIF.h index b5a30c08..33e01e7d 100644 --- a/ipc/MessageQueueMessageIF.h +++ b/ipc/MessageQueueMessageIF.h @@ -1,7 +1,7 @@ #ifndef FRAMEWORK_IPC_MESSAGEQUEUEMESSAGEIF_H_ #define FRAMEWORK_IPC_MESSAGEQUEUEMESSAGEIF_H_ -#include +#include "messageQueueDefinitions.h" #include #include diff --git a/ipc/MutexFactory.h b/ipc/MutexFactory.h index f8133d81..db505ff9 100644 --- a/ipc/MutexFactory.h +++ b/ipc/MutexFactory.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_IPC_MUTEXFACTORY_H_ -#define FRAMEWORK_IPC_MUTEXFACTORY_H_ +#ifndef FSFW_IPC_MUTEXFACTORY_H_ +#define FSFW_IPC_MUTEXFACTORY_H_ #include "MutexIF.h" /** @@ -31,4 +31,4 @@ private: -#endif /* FRAMEWORK_IPC_MUTEXFACTORY_H_ */ +#endif /* FSFW_IPC_MUTEXFACTORY_H_ */ diff --git a/ipc/MutexHelper.h b/ipc/MutexHelper.h index 3dc36921..97001ade 100644 --- a/ipc/MutexHelper.h +++ b/ipc/MutexHelper.h @@ -16,8 +16,8 @@ public: << timeoutMs << " milliseconds!" << std::endl; } else if(status != HasReturnvaluesIF::RETURN_OK){ - sif::error << "MutexHelper: Lock of Mutex failed with code " << - status << std::endl; + sif::error << "MutexHelper: Lock of Mutex failed with code " + << status << std::endl; } } From 820731de7bfa40d88a592a927031793bbc73f873 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 13:23:19 +0100 Subject: [PATCH 17/26] updated docs, added new doc folder --- README.md | 100 ++++++++++++---------------------- doc/README-config.md | 21 +++++++ doc/README-core.md | 50 +++++++++++++++++ doc/README-devicehandlers.txt | 0 4 files changed, 106 insertions(+), 65 deletions(-) create mode 100644 doc/README-config.md create mode 100644 doc/README-core.md create mode 100644 doc/README-devicehandlers.txt diff --git a/README.md b/README.md index 4aabe36a..8552e0c8 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,5 @@ ![FSFW Logo](logo/FSFW_Logo_V3_bw.png) + # Flight Software Framework (FSFW) The Flight Software Framework is a C++ Object Oriented Framework for unmanned, @@ -14,83 +15,54 @@ The framework is designed for systems, which communicate with external devices, Therefore, a mode and health system provides control over the states of the software and the controlled devices. In addition, a simple mechanism of event based fault detection, isolation and recovery is implemented as well. -The recommended hardware is a microprocessor with more than 2 MB of RAM and 1 MB of non-volatile Memory. +The recommended hardware is a microprocessor with more than 1 MB of RAM and 1 MB of non-volatile Memory. For reference, current Applications use a Cobham Gaisler UT699 (LEON3FT), a ISISPACE IOBC or a Zynq-7020 SoC. +The `fsfw` was also tested on the STM32H743ZI-Nucleo board. +## How to Use + +The [FSFW example](https://egit.irs.uni-stuttgart.de/fsfw/fsfw_example) provides a good starting point and a demo +to see the FSFW capabilities and build it with the Make or the CMake build system. +Generally, the FSFW is included in a project by compiling the FSFW sources and providing +a configuration folder and adding it to the include path. +A template configuration folder was provided and can be copied into the project root to have +a starting point. The [configuration section](doc/README-config.md#top) provides more specific information about +the possible options. ## Structure -The general structure is driven by the usage of interfaces provided by objects. The FSFW uses C++11 as baseline. The intention behind this is that this C++ Standard should be widely available, even with older compilers. +The general structure is driven by the usage of interfaces provided by objects. +The FSFW uses C++11 as baseline. The intention behind this is that this C++ Standard should be widely available, even with older compilers. The FSFW uses dynamic allocation during the initialization but provides static containers during runtime. This simplifies the instantiation of objects and allows the usage of some standard containers. Dynamic Allocation after initialization is discouraged and different solutions are provided in the FSFW to achieve that. -The fsfw uses Run-time type information. -Exceptions are not allowed. +The fsfw uses run-time type information but exceptions are not allowed. ### Failure Handling -Functions should return a defined ReturnValue_t to signal to the caller that something is gone wrong. +Functions should return a defined ReturnValue_t to signal to the caller that something has gone wrong. Returnvalues must be unique. For this the function HasReturnvaluesIF::makeReturnCode or the Macro MAKE_RETURN can be used. The CLASS_ID is a unique id for that type of object. See returnvalues/FwClassIds. ### OSAL -The FSFW provides operation system abstraction layers for Linux, FreeRTOS and RTEMS. A independent OSAL called "host" is currently not finished. This aims to be running on windows as well. -The OSAL provides periodic tasks, message queues, clocks and Semaphores as well as Mutexes. + +The FSFW provides operation system abstraction layers for Linux, FreeRTOS and RTEMS. +A independent Host OSAL is in development which will provide abstraction for common type of +host OSes (tested for Linux and Windows, not for MacOS yet). +The OSAL provides periodic tasks, message queues, clocks and semaphores as well as mutexes. ### Core Components -Clock: - * This is a class of static functions that can be used at anytime - * Leap Seconds must be set if any time conversions from UTC to other times is used - -ObjectManager (must be created): - -* The component which handles all references. All SystemObjects register at this component. -* Any SystemObject needs to have a unique ObjectId. Those can be managed like objects::framework_objects. -* A reference to an object can be get by calling the following function. T must be the specific Interface you want to call. -A nullptr check of the returning Pointer must be done. This function is based on Run-time type information. - -``` c++ - template T* ObjectManagerIF::get( object_id_t id ) - -``` -* A typical way to create all objects on startup is a handing a static produce function to the ObjectManager on creation. -By calling objectManager->initialize() the produce function will be called and all SystemObjects will be initialized afterwards. - -Event Manager: - -* Component which allows routing of events -* Other objects can subscribe to specific events, ranges of events or all events of an object. -* Subscriptions can be done during runtime but should be done during initialization -* Amounts of allowed subscriptions must be configured by setting this parameters: - -``` c++ -namespace fsfwconfig { -//! Configure the allocated pool sizes for the event manager. -static constexpr size_t FSFW_EVENTMGMR_MATCHTREE_NODES = 240; -static constexpr size_t FSFW_EVENTMGMT_EVENTIDMATCHERS = 120; -static constexpr size_t FSFW_EVENTMGMR_RANGEMATCHERS = 120; -} -``` - - -Health Table: - -* A component which holds every health state -* Provides a thread safe way to access all health states without the need of message exchanges - -Stores - -* The message based communication can only exchange a few bytes of information inside the message itself. Therefore, additional information can be exchanged with Stores. With this, only the store address must be exchanged in the message. -* Internally, the FSFW uses an IPC Store to exchange data between processes. For incoming TCs a TC Store is used. For outgoing TM a TM store is used. -* All of them should use the Thread Safe Class storagemanager/PoolManager - -Tasks - -There are two different types of tasks: - * The PeriodicTask just executes objects that are of type ExecutableObjectIF in the order of the insertion to the Tasks. - * FixedTimeslotTask executes a list of calls in the order of the given list. This is intended for DeviceHandlers, where polling should be in a defined order. An example can be found in defaultcfg/fsfwconfig/pollingSequence +The FSFW has following core components. More detailed informations can be found in the +[core component section](doc/README-core.md#top): +1. Tasks: Abstraction for different (periodic) task types like periodic tasks or tasks with fixed timeslots +2. ObjectManager: This module stores all `SystemObjects` by mapping a provided unique object ID to the object handles. +3. Static Stores: Different stores are provided to store data of variable size (like telecommands or small telemetry) in a pool structure without + using dynamic memory allocation. These pools are allocated up front. +3. Clock: This module provided common time related functions +4. EventManager: This module allows routing of events generated by `SystemObjects` +5. HealthTable: A component which stores the health states of objects ### Static Ids in the framework @@ -121,13 +93,15 @@ If the communication is based on CCSDS Frames and Space Packets, several classes If Space Packets are used, a timestamper must be created. An example can be found in the timemanager folder, this uses CCSDSTime::CDS_short. -#### DeviceHandling +#### Device Handlers -DeviceHandlers are a core component of the FSFW. +DeviceHandlers are another important component of the FSFW. The idea is, to have a software counterpart of every physical device to provide a simple mode, health and commanding interface. -By separating the underlying Communication Interface with DeviceCommunicationIF, a DH can be tested on different hardware. +By separating the underlying Communication Interface with DeviceCommunicationIF, a device handler (DH) can be tested on different hardware. The DH has mechanisms to monitor the communication with the physical device which allow for FDIR reaction. +Device Handlers can be created by overriding `DeviceHandlerBase`. A standard FDIR component for the DH will be created automatically but can be overwritten by the user. +More information on DeviceHandlers can be found in the related [documentation section](doc/README-devicehandlers.md#top). #### Modes, Health @@ -149,10 +123,6 @@ The health state represents if the component is able to perform its tasks. This can be used to signal the system to avoid using this component instead of a redundant one. The on-board FDIR uses the health state for isolation and recovery. -## Example config - -A example config can be found in defaultcfg/fsfwconfig. - ## Unit Tests Unit Tests are provided in the unittest folder. Those use the catch2 framework but do not include catch2 itself. diff --git a/doc/README-config.md b/doc/README-config.md new file mode 100644 index 00000000..036a7d14 --- /dev/null +++ b/doc/README-config.md @@ -0,0 +1,21 @@ + +## Configuring the FSFW + +The FSFW can be configured via the `fsfwconfig` folder. A template folder has +been provided to have a starting point for this. The folder should be added +to the include path. + + +### Configuring the Event Manager + +The number of allowed subscriptions can be modified with the following +parameters: + +``` c++ +namespace fsfwconfig { +//! Configure the allocated pool sizes for the event manager. +static constexpr size_t FSFW_EVENTMGMR_MATCHTREE_NODES = 240; +static constexpr size_t FSFW_EVENTMGMT_EVENTIDMATCHERS = 120; +static constexpr size_t FSFW_EVENTMGMR_RANGEMATCHERS = 120; +} +``` \ No newline at end of file diff --git a/doc/README-core.md b/doc/README-core.md new file mode 100644 index 00000000..c47ae0f2 --- /dev/null +++ b/doc/README-core.md @@ -0,0 +1,50 @@ +## FSFW Core Modules + +These core modules provide the most important functionalities of the +Flight Software Framework + +### Clock + + * This is a class of static functions that can be used at anytime + * Leap Seconds must be set if any time conversions from UTC to other times is used + +### ObjectManager + +* Must be created during program startup +* The component which handles all references. All SystemObjects register at this component. +* Any SystemObject needs to have a unique ObjectId. Those can be managed like objects::framework_objects. +* A reference to an object can be get by calling the following function. T must be the specific Interface you want to call. +A nullptr check of the returning Pointer must be done. This function is based on Run-time type information. + +``` c++ + template T* ObjectManagerIF::get( object_id_t id ) + +``` +* A typical way to create all objects on startup is a handing a static produce function to the ObjectManager on creation. +By calling objectManager->initialize() the produce function will be called and all SystemObjects will be initialized afterwards. + +### Event Manager + +* Component which allows routing of events +* Other objects can subscribe to specific events, ranges of events or all events of an object. +* Subscriptions can be done during runtime but should be done during initialization +* Amounts of allowed subscriptions can be configured in `FSFWConfig.h` + +### Health Table + +* A component which holds every health state +* Provides a thread safe way to access all health states without the need of message exchanges + +### Stores + +* The message based communication can only exchange a few bytes of information inside the message itself. Therefore, additional information can + be exchanged with Stores. With this, only the store address must be exchanged in the message. +* Internally, the FSFW uses an IPC Store to exchange data between processes. For incoming TCs a TC Store is used. For outgoing TM a TM store is used. +* All of them should use the Thread Safe Class storagemanager/PoolManager + +### Tasks + +There are two different types of tasks: + * The PeriodicTask just executes objects that are of type ExecutableObjectIF in the order of the insertion to the Tasks. + * FixedTimeslotTask executes a list of calls in the order of the given list. This is intended for DeviceHandlers, where polling should be in a defined order. An example can be found in defaultcfg/fsfwconfig/pollingSequence + diff --git a/doc/README-devicehandlers.txt b/doc/README-devicehandlers.txt new file mode 100644 index 00000000..e69de29b From 6b1a8afe2b50a59f35946086ee6e846c28742ae1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 13:25:50 +0100 Subject: [PATCH 18/26] unittest update 2 --- .../objects => core}/CatchFactory.cpp | 0 .../{testcfg/objects => core}/CatchFactory.h | 6 +-- unittest/core/CatchSetup.cpp | 7 +-- unittest/testcfg/FSFWConfig.h | 49 ++++++++++++------- unittest/testcfg/Makefile-FSFW-Tests | 13 ++--- unittest/testcfg/testcfg.mk | 8 --- 6 files changed, 42 insertions(+), 41 deletions(-) rename unittest/{testcfg/objects => core}/CatchFactory.cpp (100%) rename unittest/{testcfg/objects => core}/CatchFactory.h (71%) diff --git a/unittest/testcfg/objects/CatchFactory.cpp b/unittest/core/CatchFactory.cpp similarity index 100% rename from unittest/testcfg/objects/CatchFactory.cpp rename to unittest/core/CatchFactory.cpp diff --git a/unittest/testcfg/objects/CatchFactory.h b/unittest/core/CatchFactory.h similarity index 71% rename from unittest/testcfg/objects/CatchFactory.h rename to unittest/core/CatchFactory.h index 84f9207e..f06e7ae5 100644 --- a/unittest/testcfg/objects/CatchFactory.h +++ b/unittest/core/CatchFactory.h @@ -1,5 +1,5 @@ -#ifndef FACTORY_H_ -#define FACTORY_H_ +#ifndef FSFW_CATCHFACTORY_H_ +#define FSFW_CATCHFACTORY_H_ #include @@ -13,4 +13,4 @@ namespace Factory { } -#endif /* FACTORY_H_ */ +#endif /* FSFW_CATCHFACTORY_H_ */ diff --git a/unittest/core/CatchSetup.cpp b/unittest/core/CatchSetup.cpp index cb5bd33e..c93cf032 100644 --- a/unittest/core/CatchSetup.cpp +++ b/unittest/core/CatchSetup.cpp @@ -1,6 +1,5 @@ +#include #include "CatchDefinitions.h" -#include "CatchFactory.h" - #include #ifdef GCOV @@ -10,15 +9,11 @@ #include "../../objectmanager/ObjectManager.h" #include "../../objectmanager/ObjectManagerIF.h" #include "../../storagemanager/StorageManagerIF.h" -#include "../../datapool/DataPool.h" #include "../../serviceinterface/ServiceInterfaceStream.h" /* Global instantiations normally done in main.cpp */ /* Initialize Data Pool */ -//namespace glob { -DataPool dataPool(datapool::dataPoolInit); -//} namespace sif { diff --git a/unittest/testcfg/FSFWConfig.h b/unittest/testcfg/FSFWConfig.h index 59934560..94f6e59d 100644 --- a/unittest/testcfg/FSFWConfig.h +++ b/unittest/testcfg/FSFWConfig.h @@ -1,44 +1,57 @@ #ifndef CONFIG_FSFWCONFIG_H_ #define CONFIG_FSFWCONFIG_H_ -#include +#include +#include //! Used to determine whether C++ ostreams are used //! Those can lead to code bloat. #define FSFW_CPP_OSTREAM_ENABLED 1 -//! Reduced printout to further decrese code size +//! Reduced printout to further decrease code size //! Be careful, this also turns off most diagnostic prinouts! -#define FSFW_REDUCED_PRINTOUT 0 +#define FSFW_ENHANCED_PRINTOUT 0 -//! Can be used to enable debugging printouts for developing the FSFW -#define FSFW_DEBUGGING 0 - -//! Defines the FIFO depth of each commanding service base which -//! also determines how many commands a CSB service can handle in one cycle -//! simulataneously. This will increase the required RAM for -//! each CSB service ! -#define FSFW_CSB_FIFO_DEPTH 6 +//! Can be used to enable additional debugging printouts for developing the FSFW +#define FSFW_PRINT_VERBOSITY_LEVEL 0 //! If FSFW_OBJ_EVENT_TRANSLATION is set to one, //! additional output which requires the translation files translateObjects //! and translateEvents (and their compiled source files) #define FSFW_OBJ_EVENT_TRANSLATION 0 -//! If -DDEBUG is supplied in the build defines, there will be -//! additional output which requires the translation files translateObjects -//! and translateEvents (and their compiles source files) #if FSFW_OBJ_EVENT_TRANSLATION == 1 +#define FSFW_DEBUG_OUTPUT 1 //! Specify whether info events are printed too. -#define FSFW_DEBUG_INFO 1 -#include -#include +#define FSFW_DEBUG_INFO 1 +#include "objects/translateObjects.h" +#include "events/translateEvents.h" #else +#define FSFW_DEBUG_OUTPUT 0 #endif //! When using the newlib nano library, C99 support for stdio facilities //! will not be provided. This define should be set to 1 if this is the case. -#define FSFW_NO_C99_IO 1 +#define FSFW_NO_C99_IO 1 +//! Specify whether a special mode store is used for Subsystem components. +#define FSFW_USE_MODESTORE 0 + +namespace fsfwconfig { +//! Default timestamp size. The default timestamp will be an eight byte CDC +//! short timestamp. +static constexpr uint8_t FSFW_MISSION_TIMESTAMP_SIZE = 8; + +//! Configure the allocated pool sizes for the event manager. +static constexpr size_t FSFW_EVENTMGMR_MATCHTREE_NODES = 240; +static constexpr size_t FSFW_EVENTMGMT_EVENTIDMATCHERS = 120; +static constexpr size_t FSFW_EVENTMGMR_RANGEMATCHERS = 120; + +//! Defines the FIFO depth of each commanding service base which +//! also determines how many commands a CSB service can handle in one cycle +//! simulataneously. This will increase the required RAM for +//! each CSB service ! +static constexpr uint8_t FSFW_CSB_FIFO_DEPTH = 3; +} #endif /* CONFIG_FSFWCONFIG_H_ */ diff --git a/unittest/testcfg/Makefile-FSFW-Tests b/unittest/testcfg/Makefile-FSFW-Tests index 2017d2bd..550fd1de 100644 --- a/unittest/testcfg/Makefile-FSFW-Tests +++ b/unittest/testcfg/Makefile-FSFW-Tests @@ -15,7 +15,7 @@ SHELL = /bin/sh # (can be overriden by adding CHIP=chip and BOARD=board to the command-line) # Unit Test can only be run on host machine for now (Linux) FRAMEWORK_PATH = fsfw -FILE_ROOT = $(FRAMEWORK_PATH)/unittest +TEST_FILE_ROOT = $(FRAMEWORK_PATH)/unittest BOARD = unittest LINUX = 1 OS_FSFW = linux @@ -58,9 +58,10 @@ endif UNIT_TEST = 1 # General folder paths -CONFIG_PATH = $(FILE_ROOT)/config -UNIT_TEST_PATH = $(FILE_ROOT)/tests -CORE_PATH = $(FILE_ROOT)/core +CONFIG_PATH = testcfg +# Core copy has to be copied as well. +CORE_PATH = core +UNIT_TEST_PATH = $(TEST_FILE_ROOT)/tests # Output file basename BASENAME = fsfw @@ -154,8 +155,8 @@ include $(S)/$(notdir $S).mk endef $(foreach S,$(SUBDIRS),$(eval $(INCLUDE_FILE))) -INCLUDES += $(FILE_ROOT) -INCLUDES += $(FILE_ROOT)/catch2/ +INCLUDES += $(TEST_FILE_ROOT) +INCLUDES += $(TEST_FILE_ROOT)/catch2/ #------------------------------------------------------------------------------- # Source Files diff --git a/unittest/testcfg/testcfg.mk b/unittest/testcfg/testcfg.mk index 31d3b60a..fca2f732 100644 --- a/unittest/testcfg/testcfg.mk +++ b/unittest/testcfg/testcfg.mk @@ -6,11 +6,3 @@ CXXSRC += $(wildcard $(CURRENTPATH)/events/*.cpp) CXXSRC += $(wildcard $(CURRENTPATH)/*.cpp) INCLUDES += $(CURRENTPATH) -INCLUDES += $(CURRENTPATH)/objects -INCLUDES += $(CURRENTPATH)/ipc -INCLUDES += $(CURRENTPATH)/pollingsequence -INCLUDES += $(CURRENTPATH)/returnvalues -INCLUDES += $(CURRENTPATH)/tmtc -INCLUDES += $(CURRENTPATH)/events -INCLUDES += $(CURRENTPATH)/devices -INCLUDES += $(CURRENTPATH)/cdatapool From 4c41e3604424f508556d96b4a32081cca0b5f8bb Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 13:29:06 +0100 Subject: [PATCH 19/26] nullptr check added --- datapool/PoolDataSetBase.cpp | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/datapool/PoolDataSetBase.cpp b/datapool/PoolDataSetBase.cpp index 1acd3fd3..cb2348f7 100644 --- a/datapool/PoolDataSetBase.cpp +++ b/datapool/PoolDataSetBase.cpp @@ -59,6 +59,11 @@ uint16_t PoolDataSetBase::getFillCount() const { ReturnValue_t PoolDataSetBase::readVariable(uint16_t count) { ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; + if(registeredVariables[count] == nullptr) { + // configuration error. + return HasReturnvaluesIF::RETURN_FAILED; + } + // These checks are often performed by the respective // variable implementation too, but I guess a double check does not hurt. if (registeredVariables[count]->getReadWriteMode() != From 9937842ded66d2ffca374bff275719cbba0fe4c1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 14:11:36 +0100 Subject: [PATCH 20/26] get transiition delay abstract --- devicehandlers/DeviceHandlerBase.cpp | 5 ----- devicehandlers/DeviceHandlerBase.h | 2 +- 2 files changed, 1 insertion(+), 6 deletions(-) diff --git a/devicehandlers/DeviceHandlerBase.cpp b/devicehandlers/DeviceHandlerBase.cpp index cb040714..d2d4ecb8 100644 --- a/devicehandlers/DeviceHandlerBase.cpp +++ b/devicehandlers/DeviceHandlerBase.cpp @@ -926,11 +926,6 @@ void DeviceHandlerBase::doTransition(Mode_t modeFrom, Submode_t subModeFrom) { setMode(getBaseMode(mode)); } -uint32_t DeviceHandlerBase::getTransitionDelayMs(Mode_t modeFrom, - Mode_t modeTo) { - return 5000; -} - ReturnValue_t DeviceHandlerBase::getStateOfSwitches(void) { if(powerSwitcher == nullptr) { return NO_SWITCH; diff --git a/devicehandlers/DeviceHandlerBase.h b/devicehandlers/DeviceHandlerBase.h index ee4447ed..45450f62 100644 --- a/devicehandlers/DeviceHandlerBase.h +++ b/devicehandlers/DeviceHandlerBase.h @@ -490,7 +490,7 @@ protected: * @param modeTo * @return time in ms */ - virtual uint32_t getTransitionDelayMs(Mode_t modeFrom, Mode_t modeTo); + virtual uint32_t getTransitionDelayMs(Mode_t modeFrom, Mode_t modeTo) = 0; /** * Return the switches connected to the device. From 3b391d33801ef998d8748364711c0dbb17231664 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 14:15:21 +0100 Subject: [PATCH 21/26] deleted service types header --- tmtcservices/ServiceTypes.h | 26 -------------------------- 1 file changed, 26 deletions(-) delete mode 100644 tmtcservices/ServiceTypes.h diff --git a/tmtcservices/ServiceTypes.h b/tmtcservices/ServiceTypes.h deleted file mode 100644 index 552601f9..00000000 --- a/tmtcservices/ServiceTypes.h +++ /dev/null @@ -1,26 +0,0 @@ -#ifndef SERVICETYPES_H_ -#define SERVICETYPES_H_ - -// SHOULDDO: This is a duplication of existing configuration structures. Delete it? -namespace SERVICE { -enum ServiceTypes { - TELECOMMAND_VERIFICATION = 1, - DEVICE_COMMAND_DISTRIBUTION = 2, - HOUSEKEEPING_AND_DIAGNOSTIC_DATA_REPORTING = 3, - PARAMETER_STATISTICS_REPORTING = 4, - EVENT_REPORTING = 5, - MEMORY_MANAGEMENT = 6, - FUNCTION_MANAGEMENT = 8, - TIME_MANAGEMENT = 9, - ON_BOARD_OPERATIONS_SCHEDULING = 11, - ON_BOARD_MONITORING = 12, - LARGE_DATA_TRANSFER = 13, - PACKET_FORWARDING_CONTROL = 14, - ON_BOARD_STORAGE_AND_RETRIEVAL = 15, - TEST = 17, - ON_BOARD_OPERATIONS_PROCEDURE = 18, - EVENT_ACTION = 19 -}; -} - -#endif /* SERVICETYPES_H_ */ From d607332f8d20477d47624e4562417f279b9ccd85 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 14:19:13 +0100 Subject: [PATCH 22/26] removed comment --- tmtcservices/AcceptsTelecommandsIF.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tmtcservices/AcceptsTelecommandsIF.h b/tmtcservices/AcceptsTelecommandsIF.h index bff0e955..7c871049 100644 --- a/tmtcservices/AcceptsTelecommandsIF.h +++ b/tmtcservices/AcceptsTelecommandsIF.h @@ -12,7 +12,7 @@ class AcceptsTelecommandsIF { public: static const uint8_t INTERFACE_ID = CLASS_ID::ACCEPTS_TELECOMMANDS_IF; - static const ReturnValue_t ACTIVITY_STARTED = MAKE_RETURN_CODE(1); // is this used anywhere or can it be removed? + static const ReturnValue_t ACTIVITY_STARTED = MAKE_RETURN_CODE(1); static const ReturnValue_t INVALID_SUBSERVICE = MAKE_RETURN_CODE(2); static const ReturnValue_t ILLEGAL_APPLICATION_DATA = MAKE_RETURN_CODE(3); static const ReturnValue_t SEND_TM_FAILED = MAKE_RETURN_CODE(4); From 9ac07368da3fab3a60fa0caffe0f10f8c35e2fd9 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 14:26:42 +0100 Subject: [PATCH 23/26] changelog update --- CHANGELOG | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG b/CHANGELOG index 4e51bc64..8b13b68d 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -54,7 +54,7 @@ ID for now. - There is an additional `PERFORM_OPERATION` step for the device handler base. It is important that DHB users adapt their polling sequence tables to perform this step. This steps allows for aclear distinction between operation and communication steps - setNormalDatapoolEntriesInvalid is not an abstract method and a default implementation was provided -- getTransitionDelayMs now return 5000 ms instead of 0 in default implementation +- getTransitionDelayMs is now an abstract method ### DeviceHandlerIF From ab9965cb8153fcfa6948a7c2d631715d0e37ad46 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 22 Dec 2020 15:29:42 +0100 Subject: [PATCH 24/26] clock corrected --- timemanager/Clock.h | 274 ++++++++++++++++++++++---------------------- 1 file changed, 137 insertions(+), 137 deletions(-) diff --git a/timemanager/Clock.h b/timemanager/Clock.h index f4ed847a..61e40d19 100644 --- a/timemanager/Clock.h +++ b/timemanager/Clock.h @@ -11,156 +11,156 @@ class Clock { public: - typedef struct { - uint32_t year; //!< Year, A.D. - uint32_t month; //!< Month, 1 .. 12. - uint32_t day; //!< Day, 1 .. 31. - uint32_t hour; //!< Hour, 0 .. 23. - uint32_t minute; //!< Minute, 0 .. 59. - uint32_t second; //!< Second, 0 .. 59. - uint32_t usecond; //!< Microseconds, 0 .. 999999 - } TimeOfDay_t; + typedef struct { + uint32_t year; //!< Year, A.D. + uint32_t month; //!< Month, 1 .. 12. + uint32_t day; //!< Day, 1 .. 31. + uint32_t hour; //!< Hour, 0 .. 23. + uint32_t minute; //!< Minute, 0 .. 59. + uint32_t second; //!< Second, 0 .. 59. + uint32_t usecond; //!< Microseconds, 0 .. 999999 + } TimeOfDay_t; - /** - * This method returns the number of clock ticks per second. - * In RTEMS, this is typically 1000. - * @return The number of ticks. - * - * @deprecated, we should not worry about ticks, but only time - */ - static uint32_t getTicksPerSecond(void); - /** - * This system call sets the system time. - * To set the time, it uses a TimeOfDay_t struct. - * @param time The struct with the time settings to set. - * @return -@c RETURN_OK on success. Otherwise, the OS failure code - * is returned. - */ - static ReturnValue_t setClock(const TimeOfDay_t* time); - /** - * This system call sets the system time. - * To set the time, it uses a timeval struct. - * @param time The struct with the time settings to set. - * @return -@c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t setClock(const timeval* time); - /** - * This system call returns the current system clock in timeval format. - * The timval format has the fields @c tv_sec with seconds and @c tv_usec with - * microseconds since an OS-defined epoch. - * @param time A pointer to a timeval struct where the current time is stored. - * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getClock_timeval(timeval* time); + /** + * This method returns the number of clock ticks per second. + * In RTEMS, this is typically 1000. + * @return The number of ticks. + * + * @deprecated, we should not worry about ticks, but only time + */ + static uint32_t getTicksPerSecond(void); + /** + * This system call sets the system time. + * To set the time, it uses a TimeOfDay_t struct. + * @param time The struct with the time settings to set. + * @return -@c RETURN_OK on success. Otherwise, the OS failure code + * is returned. + */ + static ReturnValue_t setClock(const TimeOfDay_t* time); + /** + * This system call sets the system time. + * To set the time, it uses a timeval struct. + * @param time The struct with the time settings to set. + * @return -@c RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t setClock(const timeval* time); + /** + * This system call returns the current system clock in timeval format. + * The timval format has the fields @c tv_sec with seconds and @c tv_usec with + * microseconds since an OS-defined epoch. + * @param time A pointer to a timeval struct where the current time is stored. + * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getClock_timeval(timeval* time); - /** - * Get the time since boot in a timeval struct - * - * @param[out] time A pointer to a timeval struct where the uptime is stored. - * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. - * - * @deprecated, I do not think this should be able to fail, use timeval getUptime() - */ - static ReturnValue_t getUptime(timeval* uptime); + /** + * Get the time since boot in a timeval struct + * + * @param[out] time A pointer to a timeval struct where the uptime is stored. + * @return @c RETURN_OK on success. Otherwise, the OS failure code is returned. + * + * @deprecated, I do not think this should be able to fail, use timeval getUptime() + */ + static ReturnValue_t getUptime(timeval* uptime); - static timeval getUptime(); + static timeval getUptime(); - /** - * Get the time since boot in milliseconds - * - * This value can overflow! Still, it can be used to calculate time intervalls - * between two calls up to 49 days by always using uint32_t in the calculation - * - * @param ms uptime in ms - * @return RETURN_OK on success. Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getUptime(uint32_t* uptimeMs); + /** + * Get the time since boot in milliseconds + * + * This value can overflow! Still, it can be used to calculate time intervalls + * between two calls up to 49 days by always using uint32_t in the calculation + * + * @param ms uptime in ms + * @return RETURN_OK on success. Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getUptime(uint32_t* uptimeMs); - /** - * Returns the time in microseconds since an OS-defined epoch. - * The time is returned in a 64 bit unsigned integer. - * @param time A pointer to a 64 bit unisigned integer where the data is stored. - * @return - * - @c RETURN_OK on success. - * - Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getClock_usecs(uint64_t* time); - /** - * Returns the time in a TimeOfDay_t struct. - * @param time A pointer to a TimeOfDay_t struct. - * @return - * - @c RETURN_OK on success. - * - Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getDateAndTime(TimeOfDay_t* time); + /** + * Returns the time in microseconds since an OS-defined epoch. + * The time is returned in a 64 bit unsigned integer. + * @param time A pointer to a 64 bit unisigned integer where the data is stored. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getClock_usecs(uint64_t* time); + /** + * Returns the time in a TimeOfDay_t struct. + * @param time A pointer to a TimeOfDay_t struct. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getDateAndTime(TimeOfDay_t* time); - /** - * Converts a time of day struct to POSIX seconds. - * @param time The time of day as input - * @param timeval The corresponding seconds since the epoch. - * @return - * - @c RETURN_OK on success. - * - Otherwise, the OS failure code is returned. - */ - static ReturnValue_t convertTimeOfDayToTimeval(const TimeOfDay_t* from, - timeval* to); + /** + * Converts a time of day struct to POSIX seconds. + * @param time The time of day as input + * @param timeval The corresponding seconds since the epoch. + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t convertTimeOfDayToTimeval(const TimeOfDay_t* from, + timeval* to); - /** - * Converts a time represented as seconds and subseconds since unix - * epoch to days since J2000 - * - * @param time seconds since unix epoch - * @param[out] JD2000 days since J2000 - * @return @c RETURN_OK - */ - static ReturnValue_t convertTimevalToJD2000(timeval time, double* JD2000); + /** + * Converts a time represented as seconds and subseconds since unix + * epoch to days since J2000 + * + * @param time seconds since unix epoch + * @param[out] JD2000 days since J2000 + * @return @c RETURN_OK + */ + static ReturnValue_t convertTimevalToJD2000(timeval time, double* JD2000); - /** - * Calculates and adds the offset between UTC and TT - * - * Depends on the leap seconds to be set correctly. - * - * @param utc timeval, corresponding to UTC time - * @param[out] tt timeval, corresponding to Terrestial Time - * @return - * - @c RETURN_OK on success - * - @c RETURN_FAILED if leapSeconds are not set - */ - static ReturnValue_t convertUTCToTT(timeval utc, timeval* tt); + /** + * Calculates and adds the offset between UTC and TT + * + * Depends on the leap seconds to be set correctly. + * + * @param utc timeval, corresponding to UTC time + * @param[out] tt timeval, corresponding to Terrestial Time + * @return + * - @c RETURN_OK on success + * - @c RETURN_FAILED if leapSeconds are not set + */ + static ReturnValue_t convertUTCToTT(timeval utc, timeval* tt); - /** - * Set the Leap Seconds since 1972 - * - * @param leapSeconds_ - * @return - * - @c RETURN_OK on success. - * - Otherwise, the OS failure code is returned. - */ - static ReturnValue_t setLeapSeconds(const uint16_t leapSeconds_); + /** + * Set the Leap Seconds since 1972 + * + * @param leapSeconds_ + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t setLeapSeconds(const uint16_t leapSeconds_); - /** - * Get the Leap Seconds since 1972 - * - * Must be set before! - * - * @param[out] leapSeconds_ - * @return - * - @c RETURN_OK on success. - * - Otherwise, the OS failure code is returned. - */ - static ReturnValue_t getLeapSeconds(uint16_t *leapSeconds_); + /** + * Get the Leap Seconds since 1972 + * + * Must be set before! + * + * @param[out] leapSeconds_ + * @return + * - @c RETURN_OK on success. + * - Otherwise, the OS failure code is returned. + */ + static ReturnValue_t getLeapSeconds(uint16_t *leapSeconds_); - /** - * Function to check and create the Mutex for the clock - * @return - * - @c RETURN_OK on success. - * - Otherwise @c RETURN_FAILED if not able to create one - */ - static ReturnValue_t checkOrCreateClockMutex(); + /** + * Function to check and create the Mutex for the clock + * @return + * - @c RETURN_OK on success. + * - Otherwise @c RETURN_FAILED if not able to create one + */ + static ReturnValue_t checkOrCreateClockMutex(); private: - static MutexIF* timeMutex; - static uint16_t leapSeconds; + static MutexIF* timeMutex; + static uint16_t leapSeconds; }; From 822cc0306c90603bbd66365293670e1163dc36cd Mon Sep 17 00:00:00 2001 From: Steffen Gaisser Date: Tue, 22 Dec 2020 15:35:23 +0100 Subject: [PATCH 25/26] Fixed file ending of devicehanlder remake --- doc/README-devicehandlers.md | 1 + doc/README-devicehandlers.txt | 0 2 files changed, 1 insertion(+) create mode 100644 doc/README-devicehandlers.md delete mode 100644 doc/README-devicehandlers.txt diff --git a/doc/README-devicehandlers.md b/doc/README-devicehandlers.md new file mode 100644 index 00000000..6e737cc5 --- /dev/null +++ b/doc/README-devicehandlers.md @@ -0,0 +1 @@ +## FSFW DeviceHandlers \ No newline at end of file diff --git a/doc/README-devicehandlers.txt b/doc/README-devicehandlers.txt deleted file mode 100644 index e69de29b..00000000 From 958db291e823746348434b72b7409baef2e031d4 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 22 Dec 2020 15:49:31 +0100 Subject: [PATCH 26/26] now it compiles --- timemanager/CCSDSTime.h | 1 + tmstorage/TmStorePackets.h | 15 +++++++++------ tmtcpacket/pus/TmPacketBase.cpp | 2 +- 3 files changed, 11 insertions(+), 7 deletions(-) diff --git a/timemanager/CCSDSTime.h b/timemanager/CCSDSTime.h index e9e6957f..d74adc61 100644 --- a/timemanager/CCSDSTime.h +++ b/timemanager/CCSDSTime.h @@ -7,6 +7,7 @@ #include "clockDefinitions.h" #include "../returnvalues/HasReturnvaluesIF.h" #include +#include bool operator<(const timeval& lhs, const timeval& rhs); bool operator<=(const timeval& lhs, const timeval& rhs); diff --git a/tmstorage/TmStorePackets.h b/tmstorage/TmStorePackets.h index e88e741a..b46ae6f6 100644 --- a/tmstorage/TmStorePackets.h +++ b/tmstorage/TmStorePackets.h @@ -139,8 +139,9 @@ public: static bool isOlderThan(const TmPacketInformation* packet, const timeval* cmpTime){ if(packet->isValid()){ timeval packetTime = {0,0}; - uint32_t foundlen = 0; - CCSDSTime::convertFromCcsds(&packetTime,&packet->rawTimestamp[0],&foundlen,sizeof(rawTimestamp)); + size_t foundlen = 0; + CCSDSTime::convertFromCcsds(&packetTime, + &packet->rawTimestamp[0],&foundlen,sizeof(rawTimestamp)); if(packetTime <= *cmpTime){ return true; } @@ -151,8 +152,9 @@ public: static bool isNewerThan(const TmPacketInformation* packet, const timeval* cmpTime){ if(packet->isValid()){ timeval packetTime = {0,0}; - uint32_t foundlen = 0; - CCSDSTime::convertFromCcsds(&packetTime,&packet->rawTimestamp[0],&foundlen,sizeof(rawTimestamp)); + size_t foundlen = 0; + CCSDSTime::convertFromCcsds(&packetTime,&packet->rawTimestamp[0], + &foundlen,sizeof(rawTimestamp)); if(packetTime >= *cmpTime){ return true; } @@ -204,8 +206,9 @@ public: timeval getTime() const { timeval packetTime = {0,0}; - uint32_t foundlen = 0; - CCSDSTime::convertFromCcsds(&packetTime,&this->rawTimestamp[0],&foundlen,sizeof(rawTimestamp)); + size_t foundlen = 0; + CCSDSTime::convertFromCcsds(&packetTime, &this->rawTimestamp[0], + &foundlen,sizeof(rawTimestamp)); return packetTime; } diff --git a/tmtcpacket/pus/TmPacketBase.cpp b/tmtcpacket/pus/TmPacketBase.cpp index f3bc3f00..2c8bfd63 100644 --- a/tmtcpacket/pus/TmPacketBase.cpp +++ b/tmtcpacket/pus/TmPacketBase.cpp @@ -74,7 +74,7 @@ bool TmPacketBase::checkAndSetStamper() { } ReturnValue_t TmPacketBase::getPacketTime(timeval* timestamp) const { - uint32_t tempSize = 0; + size_t tempSize = 0; return CCSDSTime::convertFromCcsds(timestamp, tmData->data_field.time, &tempSize, sizeof(tmData->data_field.time)); }