From b6a23727f2dcbe498276b3c86306d24a8e1462f8 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Mon, 12 Oct 2020 15:40:27 +0200 Subject: [PATCH 001/103] added extended controller base --- controller/ExtendedControllerBase.cpp | 114 ++++++++++++++++++++++++++ controller/ExtendedControllerBase.h | 72 ++++++++++++++++ 2 files changed, 186 insertions(+) create mode 100644 controller/ExtendedControllerBase.cpp create mode 100644 controller/ExtendedControllerBase.h diff --git a/controller/ExtendedControllerBase.cpp b/controller/ExtendedControllerBase.cpp new file mode 100644 index 00000000..f69d2ea1 --- /dev/null +++ b/controller/ExtendedControllerBase.cpp @@ -0,0 +1,114 @@ +#include "ExtendedControllerBase.h" + + +ExtendedControllerBase::ExtendedControllerBase(object_id_t objectId, + object_id_t parentId, size_t commandQueueDepth): + ControllerBase(objectId, parentId, commandQueueDepth), + localPoolManager(this, commandQueue), + actionHelper(this, commandQueue) { +} + +ReturnValue_t ExtendedControllerBase::executeAction(ActionId_t actionId, + MessageQueueId_t commandedBy, const uint8_t *data, size_t size) { + // needs to be overriden and implemented by child class. + return HasReturnvaluesIF::RETURN_OK; +} + + + +ReturnValue_t ExtendedControllerBase::initializeLocalDataPool( + LocalDataPool &localDataPoolMap, LocalDataPoolManager &poolManager) { + // needs to be overriden and implemented by child class. + return HasReturnvaluesIF::RETURN_OK; +} + +object_id_t ExtendedControllerBase::getObjectId() const { + return SystemObject::getObjectId(); +} + +LocalDataPoolManager* ExtendedControllerBase::getHkManagerHandle() { + return &localPoolManager; +} + +uint32_t ExtendedControllerBase::getPeriodicOperationFrequency() const { + return this->executingTask->getPeriodMs(); +} + +ReturnValue_t ExtendedControllerBase::handleCommandMessage( + CommandMessage *message) { + ReturnValue_t result = actionHelper.handleActionMessage(message); + if(result == HasReturnvaluesIF::RETURN_OK) { + return result; + } + return localPoolManager.handleHousekeepingMessage(message); +} + +void ExtendedControllerBase::handleQueue() { + CommandMessage command; + ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; + for (result = commandQueue->receiveMessage(&command); + result == RETURN_OK; + result = commandQueue->receiveMessage(&command)) { + result = actionHelper.handleActionMessage(&command); + if (result == RETURN_OK) { + continue; + } + + result = modeHelper.handleModeCommand(&command); + if (result == RETURN_OK) { + continue; + } + + result = healthHelper.handleHealthCommand(&command); + if (result == RETURN_OK) { + continue; + } + + result = localPoolManager.handleHousekeepingMessage(&command); + if (result == RETURN_OK) { + continue; + } + + result = handleCommandMessage(&command); + if (result == RETURN_OK) { + continue; + } + command.setToUnknownCommand(); + commandQueue->reply(&command); + } +} + +ReturnValue_t ExtendedControllerBase::initialize() { + ReturnValue_t result = ControllerBase::initialize(); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + result = actionHelper.initialize(commandQueue); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + + return localPoolManager.initialize(commandQueue); +} + +ReturnValue_t ExtendedControllerBase::initializeAfterTaskCreation() { + return localPoolManager.initializeAfterTaskCreation(); +} + +ReturnValue_t ExtendedControllerBase::performOperation(uint8_t opCode) { + handleQueue(); + hkSwitcher.performOperation(); + localPoolManager.performHkOperation(); + performControlOperation(); + return RETURN_OK; +} + +MessageQueueId_t ExtendedControllerBase::getCommandQueue() const { + return commandQueue->getId(); +} + +LocalPoolDataSetBase* ExtendedControllerBase::getDataSetHandle(sid_t sid) { + sif::warning << "ExtendedControllerBase::getDataSetHandle: No child " + << " implementation provided, returning nullptr!" << std::endl; + return nullptr; +} diff --git a/controller/ExtendedControllerBase.h b/controller/ExtendedControllerBase.h new file mode 100644 index 00000000..02c5728e --- /dev/null +++ b/controller/ExtendedControllerBase.h @@ -0,0 +1,72 @@ +#ifndef FSFW_CONTROLLER_EXTENDEDCONTROLLERBASE_H_ +#define FSFW_CONTROLLER_EXTENDEDCONTROLLERBASE_H_ + +#include "ControllerBase.h" + +#include "../action/HasActionsIF.h" +#include "../datapoollocal/HasLocalDataPoolIF.h" +#include "../action/ActionHelper.h" +#include "../datapoollocal/LocalDataPoolManager.h" + +/** + * @brief Extendes the basic ControllerBase with the common components + * HasActionsIF for commandability and HasLocalDataPoolIF to keep + * a pool of local data pool variables. + * @details + * Default implementations required for the interfaces will be empty and have + * to be implemented by child class. + */ +class ExtendedControllerBase: public ControllerBase, + public HasActionsIF, + public HasLocalDataPoolIF { +public: + ExtendedControllerBase(object_id_t objectId, object_id_t parentId, + size_t commandQueueDepth = 3); + + /** SystemObjectIF overrides */ + virtual ReturnValue_t initialize() override; + + virtual MessageQueueId_t getCommandQueue() const override; + + /** ExecutableObjectIF overrides */ + virtual ReturnValue_t performOperation(uint8_t opCode) override; + virtual ReturnValue_t initializeAfterTaskCreation() override; + +protected: + LocalDataPoolManager localPoolManager; + ActionHelper actionHelper; + + /** + * Implemented by child class. Handle all command messages which are + * not health, mode, action or housekeeping messages. + * @param message + * @return + */ + virtual ReturnValue_t handleCommandMessage(CommandMessage *message) = 0; + + /** + * Periodic helper from ControllerBase, implemented by child class. + */ + virtual void performControlOperation() = 0; + + /** Handle the four messages mentioned above */ + void handleQueue() override; + + /** HasActionsIF overrides */ + virtual ReturnValue_t executeAction(ActionId_t actionId, + MessageQueueId_t commandedBy, const uint8_t* data, + size_t size) override; + + /** HasLocalDatapoolIF overrides */ + virtual object_id_t getObjectId() const override; + virtual ReturnValue_t initializeLocalDataPool( + LocalDataPool& localDataPoolMap, + LocalDataPoolManager& poolManager) override; + virtual LocalDataPoolManager* getHkManagerHandle() override; + virtual uint32_t getPeriodicOperationFrequency() const override; + virtual LocalPoolDataSetBase* getDataSetHandle(sid_t sid) override; +}; + + + +#endif /* FSFW_CONTROLLER_EXTENDEDCONTROLLERBASE_H_ */ From 73215baf118066c2eb5278416f302216a243cd9d Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Thu, 15 Oct 2020 13:43:23 +0200 Subject: [PATCH 002/103] init commit --- storagemanager/ConstStorageAccessor.h | 2 - storagemanager/LocalPool.cpp | 346 ++++++++++++++++++++++++++ storagemanager/LocalPool.h | 233 ++++++++++------- storagemanager/PoolManager.cpp | 59 +++++ storagemanager/PoolManager.h | 41 ++- storagemanager/StorageAccessor.h | 2 - storagemanager/StorageManagerIF.h | 23 +- storagemanager/storeAddress.h | 13 +- 8 files changed, 612 insertions(+), 107 deletions(-) create mode 100644 storagemanager/LocalPool.cpp create mode 100644 storagemanager/PoolManager.cpp diff --git a/storagemanager/ConstStorageAccessor.h b/storagemanager/ConstStorageAccessor.h index 96d2dca2..570c20ce 100644 --- a/storagemanager/ConstStorageAccessor.h +++ b/storagemanager/ConstStorageAccessor.h @@ -20,9 +20,7 @@ class StorageManagerIF; */ class ConstStorageAccessor { //! StorageManager classes have exclusive access to private variables. - template friend class PoolManager; - template friend class LocalPool; public: /** diff --git a/storagemanager/LocalPool.cpp b/storagemanager/LocalPool.cpp new file mode 100644 index 00000000..8e5f4d48 --- /dev/null +++ b/storagemanager/LocalPool.cpp @@ -0,0 +1,346 @@ +#include "LocalPool.h" +#include + +LocalPool::LocalPool(object_id_t setObjectId, const LocalPoolConfig& poolConfig, + bool registered, bool spillsToHigherPools): + SystemObject(setObjectId, registered), + NUMBER_OF_POOLS(poolConfig.size()), + spillsToHigherPools(spillsToHigherPools) { + if(NUMBER_OF_POOLS == 0) { + sif::error << "LocalPool::LocalPool: Passed pool configuration is " + << " invalid!" << std::endl; + } + max_pools_t index = 0; + for (const auto& currentPoolConfig: poolConfig) { + this->numberOfElements[index] = currentPoolConfig.first; + this->elementSizes[index] = currentPoolConfig.second; + store[index] = std::vector( + numberOfElements[index] * elementSizes[index]); + sizeLists[index] = std::vector(numberOfElements[index]); + for(auto& size: sizeLists[index]) { + size = STORAGE_FREE; + } + index++; + } +} + +LocalPool::~LocalPool(void) {} + + +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; +} + +ReturnValue_t LocalPool::getData(store_address_t packetId, + const uint8_t **packetPtr, size_t *size) { + uint8_t* tempData = nullptr; + ReturnValue_t status = modifyData(packetId, &tempData, size); + *packetPtr = tempData; + return status; +} + +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; +} + +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)); +} + +ReturnValue_t LocalPool::getFreeElement(store_address_t *storageId, + const size_t size, uint8_t **pData, bool ignoreFault) { + ReturnValue_t status = reserveSpace(size, storageId, ignoreFault); + if (status == RETURN_OK) { + *pData = &store[storageId->poolIndex][getRawPosition(*storageId)]; + } + else { + *pData = nullptr; + } + return status; +} + + +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)); +} + +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; +} + +ReturnValue_t LocalPool::modifyData(store_address_t storeId, + uint8_t **packetPtr, size_t *size) { + ReturnValue_t status = RETURN_FAILED; + if (storeId.poolIndex >= NUMBER_OF_POOLS) { + return ILLEGAL_STORAGE_ID; + } + if ((storeId.packetIndex >= numberOfElements[storeId.poolIndex])) { + return ILLEGAL_STORAGE_ID; + } + + if (sizeLists[storeId.poolIndex][storeId.packetIndex] + != STORAGE_FREE) { + size_type packetPosition = getRawPosition(storeId); + *packetPtr = &store[storeId.poolIndex][packetPosition]; + *size = sizeLists[storeId.poolIndex][storeId.packetIndex]; + status = RETURN_OK; + } + else { + status = DATA_DOES_NOT_EXIST; + } + return status; +} + +ReturnValue_t LocalPool::deleteData(store_address_t storeId) { +#if FSFW_DEBUGGING == 1 + sif::debug << "Delete: Pool: " << std::dec << storeId.poolIndex + << " Index: " << storeId.packetIndex << std::endl; + +#endif + ReturnValue_t status = RETURN_OK; + size_type pageSize = getPageSize(storeId.poolIndex); + if ((pageSize != 0) and + (storeId.packetIndex < numberOfElements[storeId.poolIndex])) { + uint16_t packetPosition = getRawPosition(storeId); + uint8_t* ptr = &store[storeId.poolIndex][packetPosition]; + std::memset(ptr, 0, pageSize); + //Set free list + sizeLists[storeId.poolIndex][storeId.packetIndex] = STORAGE_FREE; + } + else { + //pool_index or packet_index is too large + sif::error << "LocalPool::deleteData: Illegal store ID, no deletion!" + << std::endl; + status = ILLEGAL_STORAGE_ID; + } + return status; +} + +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].data() <= ptr) and + (&store[n][numberOfElements[n]*elementSizes[n]] > ptr)) { + localId.poolIndex = n; + uint32_t deltaAddress = ptr - store[n].data(); + // 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.packetIndex = deltaAddress / elementSizes[n]; + result = deleteData(localId); +#if FSFW_DEBUGGING == 1 + if (deltaAddress % elementSizes[n] != 0) { + sif::error << "LocalPool::deleteData: Address not aligned!" + << std::endl; + } +#endif + break; + } + } + if (storeId != nullptr) { + *storeId = localId; + } + return result; +} + + +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 (elementSizes[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 HasReturnvaluesIF::RETURN_OK; +} + +void LocalPool::clearStore() { + for(auto& sizeList: sizeLists) { + for(auto& size: sizeList) { + size = STORAGE_FREE; + } +// std::memset(sizeList[index], 0xff, +// numberOfElements[index] * sizeof(size_type)); + } + +} + +ReturnValue_t LocalPool::reserveSpace(const size_t size, + store_address_t *storeId, bool ignoreFault) { + ReturnValue_t status = getPoolIndex(size, &storeId->poolIndex); + if (status != RETURN_OK) { + sif::error << "LocalPool( " << std::hex << getObjectId() << std::dec + << " )::reserveSpace: Packet too large." << std::endl; + return status; + } + status = findEmpty(storeId->poolIndex, &storeId->packetIndex); + while (status != RETURN_OK && spillsToHigherPools) { + status = getPoolIndex(size, &storeId->poolIndex, storeId->poolIndex + 1); + if (status != RETURN_OK) { + //We don't find any fitting pool anymore. + break; + } + status = findEmpty(storeId->poolIndex, &storeId->packetIndex); + } + if (status == RETURN_OK) { +#if FSFW_DEBUGGING == 1 + sif::debug << "Reserve: Pool: " << std::dec + << storeId->poolIndex << " Index: " << storeId->packetIndex + << std::endl; +#endif + sizeLists[storeId->poolIndex][storeId->packetIndex] = size; + } + else { + if ((not ignoreFault) and (internalErrorReporter != nullptr)) { + internalErrorReporter->storeFull(); + } + } + return status; +} + +void LocalPool::write(store_address_t storeId, const uint8_t *data, + size_t size) { + uint8_t* ptr = nullptr; + size_type packetPosition = getRawPosition(storeId); + + // Size was checked before calling this function. + ptr = &store[storeId.poolIndex][packetPosition]; + std::memcpy(ptr, data, size); + sizeLists[storeId.poolIndex][storeId.packetIndex] = size; +} + +LocalPool::size_type LocalPool::getPageSize(max_pools_t poolIndex) { + if (poolIndex < NUMBER_OF_POOLS) { + return elementSizes[poolIndex]; + } + else { + return 0; + } +} + +void LocalPool::setToSpillToHigherPools(bool enable) { + this->spillsToHigherPools = enable; +} + +ReturnValue_t LocalPool::getPoolIndex(size_t packetSize, uint16_t *poolIndex, + uint16_t startAtIndex) { + for (uint16_t n = startAtIndex; n < NUMBER_OF_POOLS; n++) { +#if FSFW_DEBUGGING == 1 + sif::debug << "LocalPool " << getObjectId() << "::getPoolIndex: Pool: " + << n << ", Element Size: " << elementSizes[n] << std::endl; +#endif + if (elementSizes[n] >= packetSize) { + *poolIndex = n; + return RETURN_OK; + } + } + return DATA_TOO_LARGE; +} + +LocalPool::size_type LocalPool::getRawPosition(store_address_t storeId) { + return storeId.packetIndex * elementSizes[storeId.poolIndex]; +} + +ReturnValue_t LocalPool::findEmpty(n_pool_elem_t poolIndex, uint16_t *element) { + ReturnValue_t status = DATA_STORAGE_FULL; + for (uint16_t foundElement = 0; foundElement < numberOfElements[poolIndex]; + foundElement++) { + if (sizeLists[poolIndex][foundElement] == STORAGE_FREE) { + *element = foundElement; + status = RETURN_OK; + break; + } + } + return status; +} + +size_t LocalPool::getTotalSize(size_t* additionalSize) { + size_t totalSize = 0; + size_t sizesSize = 0; + for(uint8_t idx = 0; idx < NUMBER_OF_POOLS; idx ++) { + totalSize += elementSizes[idx] * numberOfElements[idx]; + sizesSize += numberOfElements[idx] * sizeof(size_type); + } + if(additionalSize != nullptr) { + *additionalSize = sizesSize; + } + return totalSize; +} + +void LocalPool::getFillCount(uint8_t *buffer, uint8_t *bytesWritten) { + if(bytesWritten == nullptr or buffer == nullptr) { + return; + } + + uint16_t reservedHits = 0; + uint8_t idx = 0; + uint16_t sum = 0; + for(; idx < NUMBER_OF_POOLS; idx ++) { + for(const auto& size: sizeLists[idx]) { + if(size != STORAGE_FREE) { + reservedHits++; + } + } + buffer[idx] = static_cast(reservedHits) / + numberOfElements[idx] * 100; + *bytesWritten += 1; + sum += buffer[idx]; + reservedHits = 0; + } + buffer[idx] = sum / NUMBER_OF_POOLS; + *bytesWritten += 1; +} + + +void LocalPool::clearPage(max_pools_t pageIndex) { + if(pageIndex >= NUMBER_OF_POOLS) { + return; + } + + // Mark the storage as free + for(auto& size: sizeLists[pageIndex]) { + size = STORAGE_FREE; + } + + // Set all the page content to 0. + std::memset(store[pageIndex].data(), 0, elementSizes[pageIndex]); +} diff --git a/storagemanager/LocalPool.h b/storagemanager/LocalPool.h index 3a94c03d..db771152 100644 --- a/storagemanager/LocalPool.h +++ b/storagemanager/LocalPool.h @@ -7,57 +7,93 @@ #include "../serviceinterface/ServiceInterfaceStream.h" #include "../internalError/InternalErrorReporterIF.h" #include "../storagemanager/StorageAccessor.h" -#include + +#include +#include +#include +#include /** - * @brief The LocalPool class provides an intermediate data storage with - * a fixed pool size policy. - * @details The class implements the StorageManagerIF interface. While the - * total number of pools is fixed, the element sizes in one pool and - * the number of pool elements per pool are set on construction. - * The full amount of memory is allocated on construction. - * The overhead is 4 byte per pool element to store the size - * information of each stored element. - * To maintain an "empty" information, the pool size is limited to - * 0xFFFF-1 bytes. - * It is possible to store empty packets in the pool. - * The local pool is NOT thread-safe. - * @author Bastian Baetz + * @brief The LocalPool class provides an intermediate data storage with + * a fixed pool size policy. + * @details + * The class implements the StorageManagerIF interface. While the total number + * of pools is fixed, the element sizes in one pool and the number of pool + * elements per pool are set on construction. The full amount of memory is + * allocated on construction. + * The overhead is 4 byte per pool element to store the size information of + * each stored element. To maintain an "empty" information, the pool size is + * limited to 0xFFFF-1 bytes. + * It is possible to store empty packets in the pool. + * The local pool is NOT thread-safe. */ -template class LocalPool: public SystemObject, public StorageManagerIF { public: - /** - * @brief This definition generally sets the number of different sized pools. - * @details This must be less than the maximum number of pools (currently 0xff). - */ - // static const uint32_t NUMBER_OF_POOLS; - /** - * @brief This is the default constructor for a pool manager instance. - * @details By passing two arrays of size NUMBER_OF_POOLS, the constructor - * allocates memory (with @c new) for store and size_list. These - * regions are all set to zero on start up. - * @param setObjectId The object identifier to be set. This allows for - * multiple instances of LocalPool in the system. - * @param element_sizes An array of size NUMBER_OF_POOLS in which the size - * of a single element in each pool is determined. - * The sizes must be provided in ascending order. - * - * @param n_elements An array of size NUMBER_OF_POOLS in which the - * number of elements for each pool is determined. - * The position of these values correspond to those in - * element_sizes. - * @param registered Register the pool in object manager or not. - * Default is false (local pool). - * @param spillsToHigherPools A variable to determine whether - * higher n pools are used if the store is full. - */ - LocalPool(object_id_t setObjectId, - const uint16_t element_sizes[NUMBER_OF_POOLS], - const uint16_t n_elements[NUMBER_OF_POOLS], - bool registered = false, - bool spillsToHigherPools = false); + using pool_elem_size_t = size_type; + using n_pool_elem_t = uint16_t; + using LocalPoolCfgPair = std::pair; + + // The configuration needs to be provided with the pool sizes ascending + // but the number of pool elements as the first value is more intuitive. + // Therefore, a custom comparator was provided. + struct LocalPoolConfigCmp + { + bool operator ()(const LocalPoolCfgPair &a, + const LocalPoolCfgPair &b) const + { + if(a.second < b.second) { + return true; + } + else if(a.second > b.second) { + return false; + } + else { + if(a.first < b.first) { + return true; + } + else { + return false; + } + } + } + }; + using LocalPoolConfig = std::multiset; + + /** + * @brief This definition generally sets the number of + * different sized pools. It is derived from the number of pairs + * inside the LocalPoolConfig set on object creation. + * @details + * This must be less than the maximum number of pools (currently 0xff). + */ + const max_pools_t NUMBER_OF_POOLS; + + /** + * @brief This is the default constructor for a pool manager instance. + * @details + * The pool is configured by passing a set of pairs into the constructor. + * The first value of that pair determines the number of one elements on + * the respective page of the pool while the second value determines how + * many elements with that size are created on that page. + * All regions are to zero on start up. + * @param setObjectId The object identifier to be set. This allows for + * multiple instances of LocalPool in the system. + * @param poolConfig + * This is a set of pairs to configure the number of pages in the pool, + * the size of an element on a page, the number of elements on a page + * and the total size of the pool at once while also implicitely + * sorting the pairs in the right order. + * @param registered + * Determines whether the pool is registered in the object manager or not. + * @param spillsToHigherPools A variable to determine whether + * higher n pools are used if the store is full. + */ + LocalPool(object_id_t setObjectId, const LocalPoolConfig& poolConfig, + bool registered = false, bool spillsToHigherPools = false); + + void setToSpillToHigherPools(bool enable); + /** * @brief In the LocalPool's destructor all allocated memory is freed. */ @@ -66,25 +102,49 @@ public: /** * Documentation: See StorageManagerIF.h */ - ReturnValue_t addData(store_address_t* storageId, const uint8_t * data, + ReturnValue_t addData(store_address_t* storeId, const uint8_t * data, size_t size, bool ignoreFault = false) override; - ReturnValue_t getFreeElement(store_address_t* storageId,const size_t size, - uint8_t** p_data, bool ignoreFault = false) override; + ReturnValue_t getFreeElement(store_address_t* storeId,const size_t size, + uint8_t** pData, bool ignoreFault = false) override; - ConstAccessorPair getData(store_address_t packet_id) override; - ReturnValue_t getData(store_address_t packet_id, ConstStorageAccessor&) override; - ReturnValue_t getData(store_address_t packet_id, const uint8_t** packet_ptr, + ConstAccessorPair getData(store_address_t storeId) override; + ReturnValue_t getData(store_address_t storeId, + ConstStorageAccessor& constAccessor) override; + ReturnValue_t getData(store_address_t storeId, + const uint8_t** packet_ptr, size_t * size) override; + + AccessorPair modifyData(store_address_t storeId) override; + ReturnValue_t modifyData(store_address_t storeId, + StorageAccessor& storeAccessor) override; + ReturnValue_t modifyData(store_address_t storeId, uint8_t** packet_ptr, size_t * size) override; - AccessorPair modifyData(store_address_t packet_id) override; - ReturnValue_t modifyData(store_address_t packet_id, StorageAccessor&) override; - ReturnValue_t modifyData(store_address_t packet_id, uint8_t** packet_ptr, - size_t * size) override; - - virtual ReturnValue_t deleteData(store_address_t) override; + virtual ReturnValue_t deleteData(store_address_t storeId) override; virtual ReturnValue_t deleteData(uint8_t* ptr, size_t size, - store_address_t* storeId = NULL) override; + store_address_t* storeId = nullptr) override; + + /** + * Get the total size of allocated memory for pool data. + * There is an additional overhead of the sizes of elements which will + * be assigned to additionalSize + * @return + */ + size_t getTotalSize(size_t* additionalSize) override; + + /** + * Get the fill count of the pool. Each character inside the provided + * buffer will be assigned to a rounded percentage fill count for each + * page. The last written byte (at the index bytesWritten - 1) + * will contain the total fill count of the pool as a mean of the + * percentages of single pages. + * @param buffer + * @param maxSize + */ + void getFillCount(uint8_t* buffer, uint8_t* bytesWritten) override; + void clearStore() override; + void clearPage(max_pools_t pageIndex) override; + ReturnValue_t initialize() override; protected: /** @@ -94,43 +154,48 @@ protected: * @return - #RETURN_OK on success, * - the return codes of #getPoolIndex or #findEmpty otherwise. */ - virtual ReturnValue_t reserveSpace(const uint32_t size, + virtual ReturnValue_t reserveSpace(const size_t size, store_address_t* address, bool ignoreFault); - InternalErrorReporterIF *internalErrorReporter; private: - /** - * Indicates that this element is free. - * This value limits the maximum size of a pool. Change to larger data type - * if increase is required. - */ - static const uint32_t STORAGE_FREE = 0xFFFFFFFF; + /** + * Indicates that this element is free. + * This value limits the maximum size of a pool. + * Change to larger data type if increase is required. + */ + static const size_type STORAGE_FREE = std::numeric_limits::max(); /** * @brief In this array, the element sizes of each pool is stored. * @details The sizes are maintained for internal pool management. The sizes * must be set in ascending order on construction. */ - uint32_t element_sizes[NUMBER_OF_POOLS]; + std::vector elementSizes = + std::vector(NUMBER_OF_POOLS); /** * @brief n_elements stores the number of elements per pool. * @details These numbers are maintained for internal pool management. */ - uint16_t n_elements[NUMBER_OF_POOLS]; + std::vector numberOfElements = + std::vector(NUMBER_OF_POOLS); /** * @brief store represents the actual memory pool. * @details It is an array of pointers to memory, which was allocated with * a @c new call on construction. */ - uint8_t* store[NUMBER_OF_POOLS]; + std::vector> store = + std::vector>(NUMBER_OF_POOLS); + /** * @brief The size_list attribute stores the size values of every pool element. * @details As the number of elements is determined on construction, the size list * is also dynamically allocated there. */ - uint32_t* size_list[NUMBER_OF_POOLS]; + std::vector> sizeLists = + std::vector>(NUMBER_OF_POOLS); + //! A variable to determine whether higher n pools are used if //! the store is full. - bool spillsToHigherPools; + bool spillsToHigherPools = false; /** * @brief This method safely stores the given data in the given packet_id. * @details It also sets the size in size_list. The method does not perform @@ -139,30 +204,24 @@ private: * @param data The data to be stored. * @param size The size of the data to be stored. */ - void write(store_address_t packet_id, const uint8_t* data, size_t size); + void write(store_address_t packetId, const uint8_t* data, size_t size); /** * @brief A helper method to read the element size of a certain pool. * @param pool_index The pool in which to look. * @return Returns the size of an element or 0. */ - uint32_t getPageSize(uint16_t pool_index); - /** - * @brief This helper method looks up a fitting pool for a given size. - * @details The pools are looked up in ascending order, so the first that - * fits is used. - * @param packet_size The size of the data to be stored. - * @return Returns the pool that fits or StorageManagerIF::INVALID_ADDRESS. - */ + size_type getPageSize(max_pools_t poolIndex); + /** * @brief This helper method looks up a fitting pool for a given size. * @details The pools are looked up in ascending order, so the first that * fits is used. * @param packet_size The size of the data to be stored. * @param[out] poolIndex The fitting pool index found. - * @return - #RETURN_OK on success, - * - #DATA_TOO_LARGE otherwise. + * @return - @c RETURN_OK on success, + * - @c DATA_TOO_LARGE otherwise. */ - ReturnValue_t getPoolIndex(size_t packet_size, uint16_t* poolIndex, + ReturnValue_t getPoolIndex(size_t packetSize, uint16_t* poolIndex, uint16_t startAtIndex = 0); /** * @brief This helper method calculates the true array position in store @@ -172,7 +231,7 @@ private: * @param packet_id The packet id to look up. * @return Returns the position of the data in store. */ - uint32_t getRawPosition(store_address_t packet_id); + size_type getRawPosition(store_address_t storeId); /** * @brief This is a helper method to find an empty element in a given pool. * @details The method searches size_list for the first empty element, so @@ -182,9 +241,9 @@ private: * @return - #RETURN_OK on success, * - #DATA_STORAGE_FULL if the store is full */ - ReturnValue_t findEmpty(uint16_t pool_index, uint16_t* element); + ReturnValue_t findEmpty(n_pool_elem_t poolIndex, uint16_t* element); + + InternalErrorReporterIF *internalErrorReporter = nullptr; }; -#include "LocalPool.tpp" - #endif /* FSFW_STORAGEMANAGER_LOCALPOOL_H_ */ diff --git a/storagemanager/PoolManager.cpp b/storagemanager/PoolManager.cpp new file mode 100644 index 00000000..9c801a3d --- /dev/null +++ b/storagemanager/PoolManager.cpp @@ -0,0 +1,59 @@ +#include "PoolManager.h" + +PoolManager::PoolManager(object_id_t setObjectId, + const LocalPoolConfig& localPoolConfig): + LocalPool(setObjectId, localPoolConfig, true) { + mutex = MutexFactory::instance()->createMutex(); +} + + +PoolManager::~PoolManager(void) { + MutexFactory::instance()->deleteMutex(mutex); +} + + +ReturnValue_t PoolManager::reserveSpace(const size_t size, + store_address_t* address, bool ignoreFault) { + MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING, + mutexTimeoutMs); + ReturnValue_t status = LocalPool::reserveSpace(size, + address,ignoreFault); + return status; +} + + +ReturnValue_t PoolManager::deleteData( + store_address_t storeId) { +#if FSFW_DEBUGGING == 1 + sif::debug << "PoolManager( " << translateObject(getObjectId()) << + " )::deleteData from store " << storeId.poolIndex << + ". id is "<< storeId.packetIndex << std::endl; +#endif + MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING, + mutexTimeoutMs); + return LocalPool::deleteData(storeId); +} + + +ReturnValue_t PoolManager::deleteData(uint8_t* buffer, + size_t size, store_address_t* storeId) { + MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING, 20); + ReturnValue_t status = LocalPool::deleteData(buffer, + size, storeId); + return status; +} + + +void PoolManager::setMutexTimeout( + uint32_t mutexTimeoutMs) { + this->mutexTimeoutMs = mutexTimeoutMs; +} + +ReturnValue_t PoolManager::lockMutex(MutexIF::TimeoutType timeoutType, + uint32_t timeoutMs) { + return mutex->lockMutex(timeoutType, timeoutMs); +} + +ReturnValue_t PoolManager::unlockMutex() { + return mutex->unlockMutex(); +} diff --git a/storagemanager/PoolManager.h b/storagemanager/PoolManager.h index 8cc6c065..5786a225 100644 --- a/storagemanager/PoolManager.h +++ b/storagemanager/PoolManager.h @@ -9,16 +9,20 @@ /** * @brief The PoolManager class provides an intermediate data storage with * a fixed pool size policy for inter-process communication. - * @details Uses local pool calls but is thread safe by protecting the call - * with a lock. + * @details + * Uses local pool calls but is thread safe by protecting most calls + * with a lock. The developer can lock the pool with the provided API + * if the lock needs to persists beyond the function call. + * + * Other than that, the class provides the same interface as the LocalPool + * class. The class is always registered as a system object as it is assumed + * it will always be used concurrently (if this is not the case, it is + * recommended to use the LocalPool class instead). * @author Bastian Baetz */ -template -class PoolManager : public LocalPool { +class PoolManager: public LocalPool { public: - PoolManager(object_id_t setObjectId, - const uint16_t element_sizes[NUMBER_OF_POOLS], - const uint16_t n_elements[NUMBER_OF_POOLS]); + PoolManager(object_id_t setObjectId, const LocalPoolConfig& poolConfig); /** * @brief In the PoolManager's destructor all allocated memory @@ -26,6 +30,12 @@ public: */ virtual ~PoolManager(); + /** + * Set the default mutex timeout for internal calls. + * @param mutexTimeoutMs + */ + void setMutexTimeout(uint32_t mutexTimeoutMs); + /** * @brief LocalPool overrides for thread-safety. Decorator function * which wraps LocalPool calls with a mutex protection. @@ -34,12 +44,23 @@ public: ReturnValue_t deleteData(uint8_t* buffer, size_t size, store_address_t* storeId = nullptr) override; - void setMutexTimeout(uint32_t mutexTimeoutMs); + /** + * The developer is allowed to lock the mutex in case the lock needs + * to persist beyond the function calls which are not protected by the + * class. + * @param timeoutType + * @param timeoutMs + * @return + */ + ReturnValue_t lockMutex(MutexIF::TimeoutType timeoutType, + uint32_t timeoutMs); + ReturnValue_t unlockMutex(); + protected: //! Default mutex timeout value to prevent permanent blocking. uint32_t mutexTimeoutMs = 20; - ReturnValue_t reserveSpace(const uint32_t size, store_address_t* address, + ReturnValue_t reserveSpace(const size_t size, store_address_t* address, bool ignoreFault) override; /** @@ -51,6 +72,4 @@ protected: MutexIF* mutex; }; -#include "PoolManager.tpp" - #endif /* FSFW_STORAGEMANAGER_POOLMANAGER_H_ */ diff --git a/storagemanager/StorageAccessor.h b/storagemanager/StorageAccessor.h index 5cf15d50..d5b383eb 100644 --- a/storagemanager/StorageAccessor.h +++ b/storagemanager/StorageAccessor.h @@ -10,9 +10,7 @@ class StorageManagerIF; */ class StorageAccessor: public ConstStorageAccessor { //! StorageManager classes have exclusive access to private variables. - template friend class PoolManager; - template friend class LocalPool; public: StorageAccessor(store_address_t storeId); diff --git a/storagemanager/StorageManagerIF.h b/storagemanager/StorageManagerIF.h index 834e7563..769616d7 100644 --- a/storagemanager/StorageManagerIF.h +++ b/storagemanager/StorageManagerIF.h @@ -28,6 +28,9 @@ using ConstAccessorPair = std::pair; */ class StorageManagerIF : public HasReturnvaluesIF { public: + using size_type = size_t; + using max_pools_t = uint8_t; + static const uint8_t INTERFACE_ID = CLASS_ID::STORAGE_MANAGER_IF; //!< The unique ID for return codes for this interface. static const ReturnValue_t DATA_TOO_LARGE = MAKE_RETURN_CODE(1); //!< This return code indicates that the data to be stored is too large for the store. static const ReturnValue_t DATA_STORAGE_FULL = MAKE_RETURN_CODE(2); //!< This return code indicates that a data storage is full. @@ -40,7 +43,9 @@ public: static const Event GET_DATA_FAILED = MAKE_EVENT(0, SEVERITY::LOW); static const Event STORE_DATA_FAILED = MAKE_EVENT(1, SEVERITY::LOW); - static const uint32_t INVALID_ADDRESS = 0xFFFFFFFF; //!< Indicates an invalid (i.e unused) storage address. + //!< Indicates an invalid (i.e unused) storage address. + static const uint32_t INVALID_ADDRESS = 0xFFFFFFFF; + /** * @brief This is the empty virtual destructor as required for C++ interfaces. */ @@ -164,6 +169,22 @@ public: * Use with care! */ virtual void clearStore() = 0; + + /** + * Clears a page in the store. Use with care! + * @param pageIndex + */ + virtual void clearPage(uint8_t pageIndex) = 0; + + /** + * Get the fill count of the pool. The exact form will be implementation + * dependant. + * @param buffer + * @param bytesWritten + */ + virtual void getFillCount(uint8_t* buffer, uint8_t* bytesWritten) = 0; + + virtual size_t getTotalSize(size_t* additionalSize) = 0; }; #endif /* FSFW_STORAGEMANAGER_STORAGEMANAGERIF_H_ */ diff --git a/storagemanager/storeAddress.h b/storagemanager/storeAddress.h index 044c0790..ea72f6f8 100644 --- a/storagemanager/storeAddress.h +++ b/storagemanager/storeAddress.h @@ -3,16 +3,21 @@ #include +namespace storeId { +static constexpr uint32_t INVALID_STORE_ADDRESS = 0xffffffff; +} + /** * This union defines the type that identifies where a data packet is * stored in the store. It comprises of a raw part to read it as raw value and * a structured part to use it in pool-like stores. */ union store_address_t { + /** * Default Constructor, initializing to INVALID_ADDRESS */ - store_address_t():raw(0xFFFFFFFF){} + store_address_t(): raw(storeId::INVALID_STORE_ADDRESS){} /** * Constructor to create an address object using the raw address * @@ -28,7 +33,7 @@ union store_address_t { * @param packetIndex */ store_address_t(uint16_t poolIndex, uint16_t packetIndex): - pool_index(poolIndex),packet_index(packetIndex){} + poolIndex(poolIndex), packetIndex(packetIndex){} /** * A structure with two elements to access the store address pool-like. */ @@ -36,11 +41,11 @@ union store_address_t { /** * The index in which pool the packet lies. */ - uint16_t pool_index; + uint16_t poolIndex; /** * The position in the chosen pool. */ - uint16_t packet_index; + uint16_t packetIndex; }; /** * Alternative access to the raw value. From 67e33918e0fb07fe3dd6afbfda9eb5bbfcd044fe Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Thu, 15 Oct 2020 13:44:09 +0200 Subject: [PATCH 003/103] event manager uses refactored pool now --- events/EventManager.cpp | 18 +++++++++--------- events/EventManager.h | 10 +++++++--- 2 files changed, 16 insertions(+), 12 deletions(-) diff --git a/events/EventManager.cpp b/events/EventManager.cpp index e71951e3..57bda13f 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -1,23 +1,23 @@ #include "EventManager.h" -#include "EventMessage.h" #include "../serviceinterface/ServiceInterfaceStream.h" #include "../ipc/QueueFactory.h" #include "../ipc/MutexFactory.h" -const uint16_t EventManager::POOL_SIZES[N_POOLS] = { - sizeof(EventMatchTree::Node), sizeof(EventIdRangeMatcher), - sizeof(ReporterRangeMatcher) }; // If one checks registerListener calls, there are around 40 (to max 50) // objects registering for certain events. // Each listener requires 1 or 2 EventIdMatcher and 1 or 2 ReportRangeMatcher. // So a good guess is 75 to a max of 100 pools required for each, which fits well. -// SHOULDDO: Shouldn't this be in the config folder and passed via ctor? -const uint16_t EventManager::N_ELEMENTS[N_POOLS] = { 240, 120, 120 }; +// This should be configurable.. +const LocalPool::LocalPoolConfig EventManager::poolConfig = { + {240, sizeof(EventMatchTree::Node)}, + {120, sizeof(EventIdRangeMatcher)}, + {120, sizeof(ReporterRangeMatcher)} +}; EventManager::EventManager(object_id_t setObjectId) : SystemObject(setObjectId), - factoryBackend(0, POOL_SIZES, N_ELEMENTS, false, true) { + factoryBackend(0, poolConfig, false, true) { mutex = MutexFactory::instance()->createMutex(); eventReportQueue = QueueFactory::instance()->createMessageQueue( MAX_EVENTS_PER_CYCLE, EventMessage::EVENT_MESSAGE_SIZE); @@ -109,13 +109,13 @@ ReturnValue_t EventManager::unsubscribeFromEventRange(MessageQueueId_t listener, return result; } -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 void EventManager::printEvent(EventMessage* message) { const char *string = 0; switch (message->getSeverity()) { case SEVERITY::INFO: -#ifdef DEBUG_INFO_EVENT +#if DEBUG_INFO_EVENT == 1 string = translateObject(message->getReporter()); sif::info << "EVENT: "; if (string != 0) { diff --git a/events/EventManager.h b/events/EventManager.h index 2602aeb2..fe35d9d3 100644 --- a/events/EventManager.h +++ b/events/EventManager.h @@ -8,9 +8,11 @@ #include "../tasks/ExecutableObjectIF.h" #include "../ipc/MessageQueueIF.h" #include "../ipc/MutexIF.h" +#include + #include -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 // forward declaration, should be implemented by mission extern const char* translateObject(object_id_t object); extern const char* translateEvents(Event event); @@ -49,13 +51,15 @@ protected: MutexIF* mutex = nullptr; static const uint8_t N_POOLS = 3; - LocalPool factoryBackend; + LocalPool factoryBackend; + static const LocalPool::LocalPoolConfig poolConfig; + static const uint16_t POOL_SIZES[N_POOLS]; static const uint16_t N_ELEMENTS[N_POOLS]; void notifyListeners(EventMessage *message); -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 void printEvent(EventMessage *message); #endif From 7d358483dd1f684609d52f144e64aa02e1e82425 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Thu, 15 Oct 2020 13:44:59 +0200 Subject: [PATCH 004/103] added back config includes --- storagemanager/LocalPool.cpp | 1 + storagemanager/PoolManager.cpp | 1 + 2 files changed, 2 insertions(+) diff --git a/storagemanager/LocalPool.cpp b/storagemanager/LocalPool.cpp index 8e5f4d48..48934a0c 100644 --- a/storagemanager/LocalPool.cpp +++ b/storagemanager/LocalPool.cpp @@ -1,4 +1,5 @@ #include "LocalPool.h" +#include #include LocalPool::LocalPool(object_id_t setObjectId, const LocalPoolConfig& poolConfig, diff --git a/storagemanager/PoolManager.cpp b/storagemanager/PoolManager.cpp index 9c801a3d..85376b28 100644 --- a/storagemanager/PoolManager.cpp +++ b/storagemanager/PoolManager.cpp @@ -1,4 +1,5 @@ #include "PoolManager.h" +#include PoolManager::PoolManager(object_id_t setObjectId, const LocalPoolConfig& localPoolConfig): From bd2f8b3e8ce09c6328519a9047d7144ff7932d37 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Thu, 15 Oct 2020 13:45:47 +0200 Subject: [PATCH 005/103] packet matcher uses refactored pool now --- tmtcpacket/packetmatcher/PacketMatchTree.cpp | 28 ++++++++++++-------- tmtcpacket/packetmatcher/PacketMatchTree.h | 3 ++- 2 files changed, 19 insertions(+), 12 deletions(-) diff --git a/tmtcpacket/packetmatcher/PacketMatchTree.cpp b/tmtcpacket/packetmatcher/PacketMatchTree.cpp index a4579657..ac72b3e7 100644 --- a/tmtcpacket/packetmatcher/PacketMatchTree.cpp +++ b/tmtcpacket/packetmatcher/PacketMatchTree.cpp @@ -3,19 +3,30 @@ #include "ServiceMatcher.h" #include "SubserviceMatcher.h" +// This should be configurable.. +const LocalPool::LocalPoolConfig PacketMatchTree::poolConfig = { + {10, sizeof(ServiceMatcher)}, + {20, sizeof(SubServiceMatcher)}, + {2, sizeof(ApidMatcher)}, + {40, sizeof(PacketMatchTree::Node)} +}; + PacketMatchTree::PacketMatchTree(Node* root) : - MatchTree(root, 2), factoryBackend(0, POOL_SIZES, - N_ELEMENTS, false, true), factory(&factoryBackend) { + MatchTree(root, 2), + factoryBackend(0, poolConfig, false, true), + factory(&factoryBackend) { } PacketMatchTree::PacketMatchTree(iterator root) : - MatchTree(root.element, 2), factoryBackend(0, - POOL_SIZES, N_ELEMENTS, false, true), factory(&factoryBackend) { + MatchTree(root.element, 2), + factoryBackend(0, poolConfig, false, true), + factory(&factoryBackend) { } PacketMatchTree::PacketMatchTree() : - MatchTree((Node*) NULL, 2), factoryBackend(0, - POOL_SIZES, N_ELEMENTS, false, true), factory(&factoryBackend) { + MatchTree((Node*) NULL, 2), + factoryBackend(0, poolConfig, false, true), + factory(&factoryBackend) { } PacketMatchTree::~PacketMatchTree() { @@ -172,11 +183,6 @@ ReturnValue_t PacketMatchTree::initialize() { return factoryBackend.initialize(); } -const uint16_t PacketMatchTree::POOL_SIZES[N_POOLS] = { sizeof(ServiceMatcher), - sizeof(SubServiceMatcher), sizeof(ApidMatcher), - sizeof(PacketMatchTree::Node) }; -//Maximum number of types and subtypes to filter should be more than sufficient. -const uint16_t PacketMatchTree::N_ELEMENTS[N_POOLS] = { 10, 20, 2, 40 }; ReturnValue_t PacketMatchTree::changeMatch(bool addToMatch, uint16_t apid, uint8_t type, uint8_t subtype) { diff --git a/tmtcpacket/packetmatcher/PacketMatchTree.h b/tmtcpacket/packetmatcher/PacketMatchTree.h index 86fb087e..54fc856c 100644 --- a/tmtcpacket/packetmatcher/PacketMatchTree.h +++ b/tmtcpacket/packetmatcher/PacketMatchTree.h @@ -23,8 +23,9 @@ protected: ReturnValue_t cleanUpElement(iterator position); private: static const uint8_t N_POOLS = 4; - LocalPool factoryBackend; + LocalPool factoryBackend; PlacementFactory factory; + static const LocalPool::LocalPoolConfig poolConfig; static const uint16_t POOL_SIZES[N_POOLS]; static const uint16_t N_ELEMENTS[N_POOLS]; template From 6ea933492368e31217851717f9d880c033cfce17 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Thu, 29 Oct 2020 17:57:27 +0100 Subject: [PATCH 006/103] parameter updates --- parameters/HasParametersIF.h | 42 ++++++++++------- parameters/ParameterHelper.cpp | 80 +++++++++++++++++---------------- parameters/ParameterMessage.cpp | 20 ++++++++- parameters/ParameterMessage.h | 35 ++++++++++++++- parameters/ParameterWrapper.cpp | 55 ++++++++++++++++++++--- parameters/ParameterWrapper.h | 23 +++++++--- 6 files changed, 186 insertions(+), 69 deletions(-) diff --git a/parameters/HasParametersIF.h b/parameters/HasParametersIF.h index 005403fa..c4fd81b3 100644 --- a/parameters/HasParametersIF.h +++ b/parameters/HasParametersIF.h @@ -1,12 +1,16 @@ #ifndef FSFW_PARAMETERS_HASPARAMETERSIF_H_ #define FSFW_PARAMETERS_HASPARAMETERSIF_H_ -#include "../parameters/ParameterWrapper.h" #include "../returnvalues/HasReturnvaluesIF.h" -#include +#include "ParameterWrapper.h" +#include -/** Each parameter is identified with a unique parameter ID */ -typedef uint32_t ParameterId_t; +/** + * Each parameter is identified with a unique parameter ID + * The first byte of the parameter ID will denote the domain ID. + * The second and third byte will be the unique identifier number. + */ +using ParameterId_t = uint32_t; /** * @brief This interface is used by components which have modifiable @@ -19,13 +23,13 @@ typedef uint32_t ParameterId_t; * The second and third byte represent the matrix ID, which can represent * a 8-bit row and column number and the last byte... * - * Yeah, it it matrix ID oder parameter ID now and is index a 16 bit number + * Yeah, is it matrix ID or parameter ID now and is index a 16 bit number * of a 8 bit number now? */ class HasParametersIF { public: static const uint8_t INTERFACE_ID = CLASS_ID::HAS_PARAMETERS_IF; - static const ReturnValue_t INVALID_MATRIX_ID = MAKE_RETURN_CODE(0x01); + static const ReturnValue_t INVALID_IDENTIFIER_ID = MAKE_RETURN_CODE(0x01); static const ReturnValue_t INVALID_DOMAIN_ID = MAKE_RETURN_CODE(0x02); static const ReturnValue_t INVALID_VALUE = MAKE_RETURN_CODE(0x03); static const ReturnValue_t READ_ONLY = MAKE_RETURN_CODE(0x05); @@ -34,17 +38,24 @@ public: return id >> 24; } - static uint16_t getMatrixId(ParameterId_t id) { - return id >> 8; + static uint8_t getUniqueIdentifierId(ParameterId_t id) { + return id >> 16; } - static uint8_t getIndex(ParameterId_t id) { + /** + * Get the index of a parameter. Please note that the index is always a + * linear index. For a vector, this is straightforward. + * For a matrix, the linear indexing run from left to right, top to bottom. + * @param id + * @return + */ + static uint16_t getIndex(ParameterId_t id) { return id; } - static uint32_t getFullParameterId(uint8_t domainId, uint16_t parameterId, - uint8_t index) { - return (domainId << 24) + (parameterId << 8) + index; + static uint32_t getFullParameterId(uint8_t domainId, + uint8_t uniqueIdentifier, uint16_t linearIndex) { + return (domainId << 24) + (uniqueIdentifier << 16) + linearIndex; } virtual ~HasParametersIF() {} @@ -56,11 +67,12 @@ public: * @param parameterId * @param parameterWrapper * @param newValues - * @param startAtIndex + * @param startAtIndex Linear index, runs left to right, top to bottom for + * matrix indexes. * @return */ - virtual ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, - ParameterWrapper *parameterWrapper, + virtual ReturnValue_t getParameter(uint8_t domainId, + uint16_t uniqueIdentifier, ParameterWrapper *parameterWrapper, const ParameterWrapper *newValues, uint16_t startAtIndex) = 0; }; diff --git a/parameters/ParameterHelper.cpp b/parameters/ParameterHelper.cpp index 659b00de..d2193b28 100644 --- a/parameters/ParameterHelper.cpp +++ b/parameters/ParameterHelper.cpp @@ -9,15 +9,20 @@ ParameterHelper::~ParameterHelper() { } ReturnValue_t ParameterHelper::handleParameterMessage(CommandMessage *message) { + if(storage == nullptr) { + // ParameterHelper was not initialized + return HasReturnvaluesIF::RETURN_FAILED; + } + ReturnValue_t result = HasReturnvaluesIF::RETURN_FAILED; switch (message->getCommand()) { case ParameterMessage::CMD_PARAMETER_DUMP: { ParameterWrapper description; uint8_t domain = HasParametersIF::getDomain( ParameterMessage::getParameterId(message)); - uint16_t parameterId = HasParametersIF::getMatrixId( + uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( ParameterMessage::getParameterId(message)); - result = owner->getParameter(domain, parameterId, + result = owner->getParameter(domain, uniqueIdentifier, &description, &description, 0); if (result == HasReturnvaluesIF::RETURN_OK) { result = sendParameter(message->getSender(), @@ -26,49 +31,48 @@ ReturnValue_t ParameterHelper::handleParameterMessage(CommandMessage *message) { } break; case ParameterMessage::CMD_PARAMETER_LOAD: { - uint8_t domain = HasParametersIF::getDomain( - ParameterMessage::getParameterId(message)); - uint16_t parameterId = HasParametersIF::getMatrixId( - ParameterMessage::getParameterId(message)); - uint8_t index = HasParametersIF::getIndex( - ParameterMessage::getParameterId(message)); + ParameterId_t parameterId = 0; + uint8_t ptc = 0; + uint8_t pfc = 0; + uint8_t rows = 0; + uint8_t columns = 0; + store_address_t storeId = ParameterMessage::getParameterLoadCommand( + message, ¶meterId, &ptc, &pfc, &rows, &columns); + Type type(Type::getActualType(ptc, pfc)); - const uint8_t *storedStream = nullptr; - size_t storedStreamSize = 0; - result = storage->getData( - ParameterMessage::getStoreId(message), &storedStream, - &storedStreamSize); + uint8_t domain = HasParametersIF::getDomain(parameterId); + uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( + parameterId); + uint16_t linearIndex = HasParametersIF::getIndex(parameterId); + + ConstStorageAccessor accessor(storeId); + result = storage->getData(storeId, accessor); if (result != HasReturnvaluesIF::RETURN_OK) { sif::error << "ParameterHelper::handleParameterMessage: Getting" - " store data failed for load command." << std::endl; + << " store data failed for load command." << std::endl; break; } ParameterWrapper streamWrapper; - result = streamWrapper.set(storedStream, storedStreamSize); - if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(ParameterMessage::getStoreId(message)); - break; + result = streamWrapper.set(type, rows, columns, accessor.data(), + accessor.size()); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; } ParameterWrapper ownerWrapper; - result = owner->getParameter(domain, parameterId, &ownerWrapper, - &streamWrapper, index); + result = owner->getParameter(domain, uniqueIdentifier, &ownerWrapper, + &streamWrapper, linearIndex); + + result = ownerWrapper.copyFrom(&streamWrapper, linearIndex); if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(ParameterMessage::getStoreId(message)); - break; + return result; } - result = ownerWrapper.copyFrom(&streamWrapper, index); - - storage->deleteData(ParameterMessage::getStoreId(message)); - - if (result == HasReturnvaluesIF::RETURN_OK) { - result = sendParameter(message->getSender(), - ParameterMessage::getParameterId(message), &ownerWrapper); - } - } + result = sendParameter(message->getSender(), + ParameterMessage::getParameterId(message), &ownerWrapper); break; + } default: return HasReturnvaluesIF::RETURN_FAILED; } @@ -113,15 +117,13 @@ ReturnValue_t ParameterHelper::sendParameter(MessageQueueId_t to, uint32_t id, } ReturnValue_t ParameterHelper::initialize() { - ownerQueueId = owner->getCommandQueue(); + ownerQueueId = owner->getCommandQueue(); - - storage = objectManager->get(objects::IPC_STORE); - if (storage == NULL) { - return HasReturnvaluesIF::RETURN_FAILED; - } else { - return HasReturnvaluesIF::RETURN_OK; - } + storage = objectManager->get(objects::IPC_STORE); + if (storage == nullptr) { + return ObjectManagerIF::CHILD_INIT_FAILED; + } + return HasReturnvaluesIF::RETURN_OK; } void ParameterHelper::rejectCommand(MessageQueueId_t to, ReturnValue_t reason, diff --git a/parameters/ParameterMessage.cpp b/parameters/ParameterMessage.cpp index e9f3191f..af1f9ce8 100644 --- a/parameters/ParameterMessage.cpp +++ b/parameters/ParameterMessage.cpp @@ -25,10 +25,26 @@ void ParameterMessage::setParameterDumpReply(CommandMessage* message, } void ParameterMessage::setParameterLoadCommand(CommandMessage* message, - ParameterId_t id, store_address_t storageID) { + ParameterId_t id, store_address_t storeId, uint8_t ptc, uint8_t pfc, + uint8_t rows = 1, uint8_t columns = 1) { message->setCommand(CMD_PARAMETER_LOAD); message->setParameter(id); - message->setParameter2(storageID.raw); + message->setParameter2(storeId.raw); + uint32_t packedParameterSettings = (ptc << 24) | (pfc << 16) | + (rows << 8) | columns; + message->setParameter3(packedParameterSettings); +} + +store_address_t ParameterMessage::getParameterLoadCommand( + const CommandMessage *message, ParameterId_t* parameterId, uint8_t *ptc, + uint8_t *pfc, uint8_t *rows, uint8_t *columns) { + *parameterId = message->getParameter2(); + uint32_t packedParamSettings = message->getParameter3(); + *ptc = packedParamSettings >> 24 & 0xff; + *pfc = packedParamSettings >> 16 & 0xff; + *rows = packedParamSettings >> 8 & 0xff; + *columns = packedParamSettings & 0xff; + return message->getParameter2(); } void ParameterMessage::clear(CommandMessage* message) { diff --git a/parameters/ParameterMessage.h b/parameters/ParameterMessage.h index 31d7fe0b..fd4481ee 100644 --- a/parameters/ParameterMessage.h +++ b/parameters/ParameterMessage.h @@ -5,6 +5,20 @@ #include "../ipc/CommandMessage.h" #include "../storagemanager/StorageManagerIF.h" +/** + * @brief ParameterMessage interface + * @details + * General structure of a parameter message: + * 1. 4-byte Object ID + * 2. 4-byte Parameter ID, first byte is Domain ID, second byte is unique + * identifier, third and fourth byte is linear index to start from + * 3. 4-byte Parameter Settings. First byte and second byte are the PTC and PFC + * ECSS type identifiers (see ECSS-E-ST-70-41C15 p.428 or Type class in + * globalfunctions). Third byte is the number of rows and fourth byte + * is the number of columns. For single variable parameters, this will + * be [1, 1]. + * + */ class ParameterMessage { private: ParameterMessage(); @@ -20,8 +34,27 @@ public: ParameterId_t id); static void setParameterDumpReply(CommandMessage* message, ParameterId_t id, store_address_t storageID); + + /** + * Command to set a load parameter message. The CCSDS / ECSS type in + * form of a PTC and a PFC is expected. See ECSS-E-ST-70-41C15 p.428 + * for all types or the Type class in globalfunctions. + * @param message + * @param id + * @param storeId + * @param ptc Type information according to CCSDS/ECSS standards + * @param pfc Type information according to CCSDS/ECSS standards + * @param rows Set number of rows in parameter set, minimum one. + * @param columns Set number of columns in parameter set, minimum one + */ static void setParameterLoadCommand(CommandMessage* message, - ParameterId_t id, store_address_t storageID); + ParameterId_t id, store_address_t storeId, uint8_t ptc, + uint8_t pfc, uint8_t rows, uint8_t columns); + + static store_address_t getParameterLoadCommand( + const CommandMessage* message, ParameterId_t* parameterId, + uint8_t* ptc, uint8_t* pfc, uint8_t* rows, uint8_t* columns) ; + static void clear(CommandMessage* message); }; diff --git a/parameters/ParameterWrapper.cpp b/parameters/ParameterWrapper.cpp index 6adc6857..23955516 100644 --- a/parameters/ParameterWrapper.cpp +++ b/parameters/ParameterWrapper.cpp @@ -115,7 +115,7 @@ ReturnValue_t ParameterWrapper::deSerializeData(uint8_t startingRow, uint8_t fromColumns) { //treat from as a continuous Stream as we copy all of it - const uint8_t *fromAsStream = (const uint8_t*) from; + const uint8_t *fromAsStream = reinterpret_cast(from); size_t streamSize = fromRows * fromColumns * sizeof(T); ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; @@ -123,8 +123,8 @@ ReturnValue_t ParameterWrapper::deSerializeData(uint8_t startingRow, for (uint8_t fromRow = 0; fromRow < fromRows; fromRow++) { //get the start element of this row in data - T *dataWithDataType = ((T*) data) - + (((startingRow + fromRow) * columns) + startingColumn); + uint16_t offset = (((startingRow + fromRow) * columns) + startingColumn); + T *dataWithDataType = static_cast(data) + offset; for (uint8_t fromColumn = 0; fromColumn < fromColumns; fromColumn++) { result = SerializeAdapter::deSerialize( @@ -159,6 +159,23 @@ ReturnValue_t ParameterWrapper::deSerialize(const uint8_t **buffer, return copyFrom(&streamDescription, startWritingAtIndex); } +ReturnValue_t ParameterWrapper::set(Type type, uint8_t rows, uint8_t columns, + const void *data, size_t dataSize) { + this->type = type; + this->rows = rows; + this->columns = columns; + + size_t expectedSize = type.getSize() * rows * columns; + if (expectedSize < dataSize) { + return SerializeIF::STREAM_TOO_SHORT; + } + + this->data = nullptr; + this->readonlyData = data; + pointsToStream = true; + return HasReturnvaluesIF::RETURN_OK; +} + ReturnValue_t ParameterWrapper::set(const uint8_t *stream, size_t streamSize, const uint8_t **remainingStream, size_t *remainingSize) { ReturnValue_t result = SerializeAdapter::deSerialize(&type, &stream, @@ -202,11 +219,13 @@ ReturnValue_t ParameterWrapper::set(const uint8_t *stream, size_t streamSize, ReturnValue_t ParameterWrapper::copyFrom(const ParameterWrapper *from, uint16_t startWritingAtIndex) { - if (data == NULL) { + // TODO: Optional diagnostic output (which can be disabled in FSFWConfig) + // to determined faulty implementations and configuration errors quickly. + if (data == nullptr) { return READONLY; } - if (from->readonlyData == NULL) { + if (from->readonlyData == nullptr) { return SOURCE_NOT_SET; } @@ -214,9 +233,16 @@ ReturnValue_t ParameterWrapper::copyFrom(const ParameterWrapper *from, return DATATYPE_MISSMATCH; } + // The smallest allowed value for rows and columns is one. + if(rows == 0 or columns == 0) { + return COLUMN_OR_ROWS_ZERO; + } + //check if from fits into this - uint8_t startingRow = startWritingAtIndex / columns; - uint8_t startingColumn = startWritingAtIndex % columns; + uint8_t startingRow = 0; + uint8_t startingColumn = 0; + ParameterWrapper::convertLinearIndexToRowAndColumn(startWritingAtIndex, + &startingRow, &startingColumn); if ((from->rows > (rows - startingRow)) || (from->columns > (columns - startingColumn))) { @@ -279,3 +305,18 @@ ReturnValue_t ParameterWrapper::copyFrom(const ParameterWrapper *from, return result; } + +void ParameterWrapper::convertLinearIndexToRowAndColumn(uint16_t index, + uint8_t *row, uint8_t *column) { + if(row == nullptr or column == nullptr) { + return; + } + // Integer division. + *row = index / columns; + *column = index % columns; +} + +uint16_t ParameterWrapper::convertRowAndColumnToLinearIndex(uint8_t row, + uint8_t column) { + return row * columns + column; +} diff --git a/parameters/ParameterWrapper.h b/parameters/ParameterWrapper.h index f07205d4..168a535f 100644 --- a/parameters/ParameterWrapper.h +++ b/parameters/ParameterWrapper.h @@ -22,6 +22,7 @@ public: static const ReturnValue_t SOURCE_NOT_SET = MAKE_RETURN_CODE(0x05); static const ReturnValue_t OUT_OF_BOUNDS = MAKE_RETURN_CODE(0x06); static const ReturnValue_t NOT_SET = MAKE_RETURN_CODE(0x07); + static const ReturnValue_t COLUMN_OR_ROWS_ZERO = MAKE_RETURN_CODE(0x08); ParameterWrapper(); ParameterWrapper(Type type, uint8_t rows, uint8_t columns, void *data); @@ -68,7 +69,7 @@ public: template void set(const T *readonlyData, uint8_t rows, uint8_t columns) { - this->data = NULL; + this->data = nullptr; this->readonlyData = readonlyData; this->type = PodTypeConversion::type; this->rows = rows; @@ -97,14 +98,19 @@ public: } template void setMatrix(T& member) { - this->set(member[0], sizeof(member)/sizeof(member[0]), sizeof(member[0])/sizeof(member[0][0])); + this->set(member[0], sizeof(member)/sizeof(member[0]), + sizeof(member[0])/sizeof(member[0][0])); } template void setMatrix(const T& member) { - this->set(member[0], sizeof(member)/sizeof(member[0]), sizeof(member[0])/sizeof(member[0][0])); + this->set(member[0], sizeof(member)/sizeof(member[0]), + sizeof(member[0])/sizeof(member[0][0])); } + ReturnValue_t set(Type type, uint8_t rows, uint8_t columns, + const void *data, size_t dataSize); + ReturnValue_t set(const uint8_t *stream, size_t streamSize, const uint8_t **remainingStream = nullptr, size_t *remainingSize = nullptr); @@ -113,6 +119,13 @@ public: uint16_t startWritingAtIndex); private: + + void convertLinearIndexToRowAndColumn(uint16_t index, + uint8_t *row, uint8_t *column); + + uint16_t convertRowAndColumnToLinearIndex(uint8_t row, + uint8_t column); + bool pointsToStream = false; Type type; @@ -148,9 +161,9 @@ inline ReturnValue_t ParameterWrapper::getElement(T *value, uint8_t row, if (pointsToStream) { const uint8_t *streamWithType = static_cast(readonlyData); streamWithType += (row * columns + column) * type.getSize(); - int32_t size = type.getSize(); + size_t size = type.getSize(); return SerializeAdapter::deSerialize(value, &streamWithType, - &size, true); + &size, SerializeIF::Endianness::BIG); } else { const T *dataWithType = static_cast(readonlyData); From 7ffce219d5f86df29fe3348cdeb703419ba32acd Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 7 Nov 2020 14:32:28 +0100 Subject: [PATCH 007/103] hosted build fix --- events/EventManager.cpp | 4 ++-- events/EventManager.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/events/EventManager.cpp b/events/EventManager.cpp index f60a8a66..d171b591 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -42,7 +42,7 @@ ReturnValue_t EventManager::performOperation(uint8_t opCode) { EventMessage message; result = eventReportQueue->receiveMessage(&message); if (result == HasReturnvaluesIF::RETURN_OK) { -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 printEvent(&message); #endif notifyListeners(&message); @@ -113,7 +113,7 @@ ReturnValue_t EventManager::unsubscribeFromEventRange(MessageQueueId_t listener, return result; } -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 void EventManager::printEvent(EventMessage* message) { const char *string = 0; diff --git a/events/EventManager.h b/events/EventManager.h index 2602aeb2..5e1a8153 100644 --- a/events/EventManager.h +++ b/events/EventManager.h @@ -55,7 +55,7 @@ protected: void notifyListeners(EventMessage *message); -#ifdef DEBUG +#if FSFW_DEBUG_OUTPUT == 1 void printEvent(EventMessage *message); #endif From 0304f61bdeb3035137bea029b145bacd34b5dd75 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 10 Nov 2020 11:00:13 +0100 Subject: [PATCH 008/103] has parametersIF doc improved --- parameters/HasParametersIF.h | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/parameters/HasParametersIF.h b/parameters/HasParametersIF.h index c4fd81b3..19c12d81 100644 --- a/parameters/HasParametersIF.h +++ b/parameters/HasParametersIF.h @@ -1,8 +1,8 @@ #ifndef FSFW_PARAMETERS_HASPARAMETERSIF_H_ #define FSFW_PARAMETERS_HASPARAMETERSIF_H_ -#include "../returnvalues/HasReturnvaluesIF.h" #include "ParameterWrapper.h" +#include "../returnvalues/HasReturnvaluesIF.h" #include /** @@ -20,11 +20,10 @@ using ParameterId_t = uint32_t; * ID is the domain ID which can be used to identify unqiue spacecraft domains * (e.g. control and sensor domain in the AOCS controller). * - * The second and third byte represent the matrix ID, which can represent - * a 8-bit row and column number and the last byte... + * The second byte is a unique identfier ID. * - * Yeah, is it matrix ID or parameter ID now and is index a 16 bit number - * of a 8 bit number now? + * The third and fourth byte can be used as a linear index for matrix or array + * parameter entries. */ class HasParametersIF { public: @@ -61,6 +60,10 @@ public: virtual ~HasParametersIF() {} /** + * This is the generic function overriden by child classes to set + * parameters. To set a parameter, the parameter wrapper is used with + * a variety of set functions. The provided values can be checked with + * newValues. * Always set parameter before checking newValues! * * @param domainId From 7c75c6e8cc22a4b8540f8866a5425f101bcfea6e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 10 Nov 2020 11:14:07 +0100 Subject: [PATCH 009/103] parameter helper update --- parameters/ParameterHelper.cpp | 166 ++++++++++++++++----------------- 1 file changed, 83 insertions(+), 83 deletions(-) diff --git a/parameters/ParameterHelper.cpp b/parameters/ParameterHelper.cpp index d2193b28..22465ca3 100644 --- a/parameters/ParameterHelper.cpp +++ b/parameters/ParameterHelper.cpp @@ -3,7 +3,7 @@ #include "../objectmanager/ObjectManagerIF.h" ParameterHelper::ParameterHelper(ReceivesParameterMessagesIF* owner) : - owner(owner) {} +owner(owner) {} ParameterHelper::~ParameterHelper() { } @@ -14,106 +14,106 @@ ReturnValue_t ParameterHelper::handleParameterMessage(CommandMessage *message) { return HasReturnvaluesIF::RETURN_FAILED; } - ReturnValue_t result = HasReturnvaluesIF::RETURN_FAILED; - switch (message->getCommand()) { - case ParameterMessage::CMD_PARAMETER_DUMP: { - ParameterWrapper description; - uint8_t domain = HasParametersIF::getDomain( - ParameterMessage::getParameterId(message)); - uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( - ParameterMessage::getParameterId(message)); - result = owner->getParameter(domain, uniqueIdentifier, - &description, &description, 0); - if (result == HasReturnvaluesIF::RETURN_OK) { - result = sendParameter(message->getSender(), - ParameterMessage::getParameterId(message), &description); - } - } - break; - case ParameterMessage::CMD_PARAMETER_LOAD: { - ParameterId_t parameterId = 0; - uint8_t ptc = 0; - uint8_t pfc = 0; - uint8_t rows = 0; - uint8_t columns = 0; - store_address_t storeId = ParameterMessage::getParameterLoadCommand( - message, ¶meterId, &ptc, &pfc, &rows, &columns); - Type type(Type::getActualType(ptc, pfc)); + ReturnValue_t result = HasReturnvaluesIF::RETURN_FAILED; + switch (message->getCommand()) { + case ParameterMessage::CMD_PARAMETER_DUMP: { + ParameterWrapper description; + uint8_t domain = HasParametersIF::getDomain( + ParameterMessage::getParameterId(message)); + uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( + ParameterMessage::getParameterId(message)); + result = owner->getParameter(domain, uniqueIdentifier, + &description, &description, 0); + if (result == HasReturnvaluesIF::RETURN_OK) { + result = sendParameter(message->getSender(), + ParameterMessage::getParameterId(message), &description); + } + } + break; + case ParameterMessage::CMD_PARAMETER_LOAD: { + ParameterId_t parameterId = 0; + uint8_t ptc = 0; + uint8_t pfc = 0; + uint8_t rows = 0; + uint8_t columns = 0; + store_address_t storeId = ParameterMessage::getParameterLoadCommand( + message, ¶meterId, &ptc, &pfc, &rows, &columns); + Type type(Type::getActualType(ptc, pfc)); - uint8_t domain = HasParametersIF::getDomain(parameterId); - uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( - parameterId); - uint16_t linearIndex = HasParametersIF::getIndex(parameterId); + uint8_t domain = HasParametersIF::getDomain(parameterId); + uint8_t uniqueIdentifier = HasParametersIF::getUniqueIdentifierId( + parameterId); + uint16_t linearIndex = HasParametersIF::getIndex(parameterId); - ConstStorageAccessor accessor(storeId); - result = storage->getData(storeId, accessor); - if (result != HasReturnvaluesIF::RETURN_OK) { - sif::error << "ParameterHelper::handleParameterMessage: Getting" - << " store data failed for load command." << std::endl; - break; - } + ConstStorageAccessor accessor(storeId); + result = storage->getData(storeId, accessor); + if (result != HasReturnvaluesIF::RETURN_OK) { + sif::error << "ParameterHelper::handleParameterMessage: Getting" + << " store data failed for load command." << std::endl; + break; + } - ParameterWrapper streamWrapper; - result = streamWrapper.set(type, rows, columns, accessor.data(), - accessor.size()); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } + ParameterWrapper streamWrapper; + result = streamWrapper.set(type, rows, columns, accessor.data(), + accessor.size()); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } - ParameterWrapper ownerWrapper; - result = owner->getParameter(domain, uniqueIdentifier, &ownerWrapper, - &streamWrapper, linearIndex); + ParameterWrapper ownerWrapper; + result = owner->getParameter(domain, uniqueIdentifier, &ownerWrapper, + &streamWrapper, linearIndex); - result = ownerWrapper.copyFrom(&streamWrapper, linearIndex); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } + result = ownerWrapper.copyFrom(&streamWrapper, linearIndex); + if (result != HasReturnvaluesIF::RETURN_OK) { + return result; + } result = sendParameter(message->getSender(), ParameterMessage::getParameterId(message), &ownerWrapper); - break; - } - default: - return HasReturnvaluesIF::RETURN_FAILED; - } + break; + } + default: + return HasReturnvaluesIF::RETURN_FAILED; + } - if (result != HasReturnvaluesIF::RETURN_OK) { - rejectCommand(message->getSender(), result, message->getCommand()); - } + if (result != HasReturnvaluesIF::RETURN_OK) { + rejectCommand(message->getSender(), result, message->getCommand()); + } - return HasReturnvaluesIF::RETURN_OK; + return HasReturnvaluesIF::RETURN_OK; } ReturnValue_t ParameterHelper::sendParameter(MessageQueueId_t to, uint32_t id, - const ParameterWrapper* description) { - size_t serializedSize = description->getSerializedSize(); + const ParameterWrapper* description) { + size_t serializedSize = description->getSerializedSize(); - uint8_t *storeElement; - store_address_t address; + uint8_t *storeElement; + store_address_t address; - ReturnValue_t result = storage->getFreeElement(&address, serializedSize, - &storeElement); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } + ReturnValue_t result = storage->getFreeElement(&address, serializedSize, + &storeElement); + if (result != HasReturnvaluesIF::RETURN_OK) { + return result; + } - size_t storeElementSize = 0; + size_t storeElementSize = 0; - result = description->serialize(&storeElement, &storeElementSize, - serializedSize, SerializeIF::Endianness::BIG); + result = description->serialize(&storeElement, &storeElementSize, + serializedSize, SerializeIF::Endianness::BIG); - if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(address); - return result; - } + if (result != HasReturnvaluesIF::RETURN_OK) { + storage->deleteData(address); + return result; + } - CommandMessage reply; + CommandMessage reply; - ParameterMessage::setParameterDumpReply(&reply, id, address); + ParameterMessage::setParameterDumpReply(&reply, id, address); - MessageQueueSenderIF::sendMessage(to, &reply, ownerQueueId); + MessageQueueSenderIF::sendMessage(to, &reply, ownerQueueId); - return HasReturnvaluesIF::RETURN_OK; + return HasReturnvaluesIF::RETURN_OK; } ReturnValue_t ParameterHelper::initialize() { @@ -127,8 +127,8 @@ ReturnValue_t ParameterHelper::initialize() { } void ParameterHelper::rejectCommand(MessageQueueId_t to, ReturnValue_t reason, - Command_t initialCommand) { - CommandMessage reply; - reply.setReplyRejected(reason, initialCommand); - MessageQueueSenderIF::sendMessage(to, &reply, ownerQueueId); + Command_t initialCommand) { + CommandMessage reply; + reply.setReplyRejected(reason, initialCommand); + MessageQueueSenderIF::sendMessage(to, &reply, ownerQueueId); } From 5865e56c54209ffe3076fda86cf94e02a706df25 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 10 Nov 2020 11:15:42 +0100 Subject: [PATCH 010/103] indentation fixed --- parameters/ParameterHelper.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/parameters/ParameterHelper.cpp b/parameters/ParameterHelper.cpp index 22465ca3..23d1a1f3 100644 --- a/parameters/ParameterHelper.cpp +++ b/parameters/ParameterHelper.cpp @@ -2,8 +2,8 @@ #include "ParameterMessage.h" #include "../objectmanager/ObjectManagerIF.h" -ParameterHelper::ParameterHelper(ReceivesParameterMessagesIF* owner) : -owner(owner) {} +ParameterHelper::ParameterHelper(ReceivesParameterMessagesIF* owner): + owner(owner) {} ParameterHelper::~ParameterHelper() { } From 9086ee2ffed94f5bd2343105ad6ccd81bc7de3ab Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 13:24:29 +0100 Subject: [PATCH 011/103] added new tests --- unittest/tests/storagemanager/TestPool.cpp | 591 ++++++++++----------- 1 file changed, 295 insertions(+), 296 deletions(-) diff --git a/unittest/tests/storagemanager/TestPool.cpp b/unittest/tests/storagemanager/TestPool.cpp index f278c40c..daeb6bb5 100644 --- a/unittest/tests/storagemanager/TestPool.cpp +++ b/unittest/tests/storagemanager/TestPool.cpp @@ -1,296 +1,295 @@ -//#include "CatchDefinitions.h" -// -//#include -//#include -//#include -// -//#include -//#include -// -//#include -// -// -//TEST_CASE( "Local Pool Simple Tests [1 Pool]" , "[TestPool]") { -//// uint16_t numberOfElements[1] = {1}; -//// uint16_t sizeofElements[1] = {10}; -// LocalPool::LocalPoolConfig config = {{1, 10}}; -// LocalPool simplePool(0, config); -// std::array testDataArray; -// std::array receptionArray; -// store_address_t testStoreId; -// ReturnValue_t result = retval::CATCH_FAILED; -// uint8_t *pointer = nullptr; -// const uint8_t * constPointer = nullptr; -// -// for(size_t i = 0; i < testDataArray.size(); i++) { -// testDataArray[i] = i; -// } -// size_t size = 10; -// -// SECTION ( "Basic tests") { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.getData(testStoreId, &constPointer, &size); -// REQUIRE(result == retval::CATCH_OK); -// memcpy(receptionArray.data(), constPointer, size); -// for(size_t i = 0; i < size; i++) { -// CHECK(receptionArray[i] == i ); -// } -// memset(receptionArray.data(), 0, size); -// result = simplePool.modifyData(testStoreId, &pointer, &size); -// memcpy(receptionArray.data(), pointer, size); -// REQUIRE(result == retval::CATCH_OK); -// for(size_t i = 0; i < size; i++) { -// CHECK(receptionArray[i] == i ); -// } -// result = simplePool.deleteData(testStoreId); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.addData(&testStoreId, testDataArray.data(), 15); -// CHECK (result == (int) StorageManagerIF::DATA_TOO_LARGE); -// } -// -// SECTION ( "Reservation Tests ") { -// pointer = nullptr; -// result = simplePool.getFreeElement(&testStoreId, size, &pointer); -// REQUIRE (result == retval::CATCH_OK); -// memcpy(pointer, testDataArray.data(), size); -// constPointer = nullptr; -// result = simplePool.getData(testStoreId, &constPointer, &size); -// -// REQUIRE (result == retval::CATCH_OK); -// memcpy(receptionArray.data(), constPointer, size); -// for(size_t i = 0; i < size; i++) { -// CHECK(receptionArray[i] == i ); -// } -// } -// -// SECTION ( "Add, delete, add, add when full") { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.getData(testStoreId, &constPointer, &size); -// REQUIRE( result == retval::CATCH_OK); -// memcpy(receptionArray.data(), constPointer, size); -// for(size_t i = 0; i < size; i++) { -// CHECK(receptionArray[i] == i ); -// } -// -// result = simplePool.deleteData(testStoreId); -// REQUIRE(result == retval::CATCH_OK); -// -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.getData(testStoreId, &constPointer, &size); -// REQUIRE( result == retval::CATCH_OK); -// memcpy(receptionArray.data(), constPointer, size); -// for(size_t i = 0; i < size; i++) { -// CHECK(receptionArray[i] == i ); -// } -// -// store_address_t newAddress; -// result = simplePool.addData(&newAddress, testDataArray.data(), size); -// REQUIRE(result == (int) StorageManagerIF::DATA_STORAGE_FULL); -// -// // Packet Index to high intentionally -// newAddress.packetIndex = 2; -// pointer = testDataArray.data(); -// result = simplePool.modifyData(newAddress, &pointer, &size); -// REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); -// -// result = simplePool.deleteData(newAddress); -// REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); -// -// newAddress.packetIndex = 0; -// newAddress.poolIndex = 2; -// result = simplePool.deleteData(newAddress); -// REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); -// } -// -// SECTION ( "Initialize and clear store, delete with pointer") { -// result = simplePool.initialize(); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// simplePool.clearStore(); -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// result = simplePool.modifyData(testStoreId, &pointer, &size); -// REQUIRE(result == retval::CATCH_OK); -// store_address_t newId; -// result = simplePool.deleteData(pointer, size, &testStoreId); -// REQUIRE(result == retval::CATCH_OK); -// REQUIRE(testStoreId.raw != (uint32_t) StorageManagerIF::INVALID_ADDRESS); -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// } -//} -// -//int runIdx = 0; -// -//TEST_CASE( "Local Pool Extended Tests [3 Pools]" , "[TestPool2]") { -// LocalPool::LocalPoolConfig* config; -// if(runIdx == 0) { -// config = new LocalPool::LocalPoolConfig{{10, 5}, {5, 10}, {2, 20}}; -// } -// else { -// // shufle the order, they should be sort implictely so that the -// // order is ascending for the page sizes. -// config = new LocalPool::LocalPoolConfig{{5, 10}, {2, 20}, {10, 5}}; -// size_t lastSize = 0; -// for(const auto& pair: *config) { -// CHECK(pair.second > lastSize); -// lastSize = pair.second; -// } -// } -// runIdx++; -// -// LocalPool simplePool(0, *config); -// std::array testDataArray; -// std::array receptionArray; -// store_address_t testStoreId; -// ReturnValue_t result = retval::CATCH_FAILED; -// for(size_t i = 0; i < testDataArray.size(); i++) { -// testDataArray[i] = i; -// } -// size_t size = 0; -// -// SECTION ("Basic tests") { -// size = 8; -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// // Should be on second page of the pool now for 8 bytes -// CHECK(testStoreId.poolIndex == 1); -// CHECK(testStoreId.packetIndex == 0); -// -// size = 15; -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// // Should be on third page of the pool now for 15 bytes -// CHECK(testStoreId.poolIndex == 2); -// CHECK(testStoreId.packetIndex == 0); -// -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// // Should be on third page of the pool now for 15 bytes -// CHECK(testStoreId.poolIndex == 2); -// CHECK(testStoreId.packetIndex == 1); -// -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// // Should be on third page of the pool now for 15 bytes -// REQUIRE(result == (int) LocalPool::DATA_STORAGE_FULL); -// -// size = 8; -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// // Should still work -// CHECK(testStoreId.poolIndex == 1); -// CHECK(testStoreId.packetIndex == 1); -// -// // fill the rest of the pool -// for(uint8_t idx = 2; idx < 5; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 1); -// CHECK(testStoreId.packetIndex == idx); -// } -// } -// -// SECTION ("Fill Count and Clearing") { -// //SECTION("Basic tests"); -// uint8_t bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// // fill count should be all zeros now. -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 0); -// CHECK(receptionArray[1] == 0); -// CHECK(receptionArray[2] == 0); -// CHECK(receptionArray[3] == 0); -// -// // now fill the store completely. -// size = 5; -// for(uint8_t idx = 0; idx < 10; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 0); -// CHECK(testStoreId.packetIndex == idx); -// } -// size = 10; -// for(uint8_t idx = 0; idx < 5; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 1); -// CHECK(testStoreId.packetIndex == idx); -// } -// size = 20; -// for(uint8_t idx = 0; idx < 2; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 2); -// CHECK(testStoreId.packetIndex == idx); -// } -// bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// // fill count should be all 100 now. -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 100); -// CHECK(receptionArray[1] == 100); -// CHECK(receptionArray[2] == 100); -// CHECK(receptionArray[3] == 100); -// -// // now clear the store -// simplePool.clearStore(); -// bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 0); -// CHECK(receptionArray[1] == 0); -// CHECK(receptionArray[2] == 0); -// CHECK(receptionArray[3] == 0); -// -// // now fill one page -// size = 5; -// for(uint8_t idx = 0; idx < 10; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 0); -// CHECK(testStoreId.packetIndex == idx); -// } -// bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// // First page full, median fill count is 33 % -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 100); -// CHECK(receptionArray[1] == 0); -// CHECK(receptionArray[2] == 0); -// CHECK(receptionArray[3] == 33); -// -// // now fill second page -// size = 10; -// for(uint8_t idx = 0; idx < 5; idx++) { -// result = simplePool.addData(&testStoreId, testDataArray.data(), size); -// REQUIRE(result == retval::CATCH_OK); -// CHECK(testStoreId.poolIndex == 1); -// CHECK(testStoreId.packetIndex == idx); -// } -// bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// // First and second page full, median fill count is 66 % -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 100); -// CHECK(receptionArray[1] == 100); -// CHECK(receptionArray[2] == 0); -// CHECK(receptionArray[3] == 66); -// -// // now clear first page -// simplePool.clearPage(0); -// bytesWritten = 0; -// simplePool.getFillCount(receptionArray.data(), &bytesWritten); -// // Second page full, median fill count is 33 % -// CHECK(bytesWritten == 4); -// CHECK(receptionArray[0] == 0); -// CHECK(receptionArray[1] == 100); -// CHECK(receptionArray[2] == 0); -// CHECK(receptionArray[3] == 33); -// } -// -// delete(config); -//} +#include "CatchDefinitions.h" + +#include +#include + +#include +#include + +#include + + +TEST_CASE( "Local Pool Simple Tests [1 Pool]" , "[TestPool]") { +// uint16_t numberOfElements[1] = {1}; +// uint16_t sizeofElements[1] = {10}; + LocalPool::LocalPoolConfig config = {{1, 10}}; + LocalPool simplePool(0, config); + std::array testDataArray; + std::array receptionArray; + store_address_t testStoreId; + ReturnValue_t result = retval::CATCH_FAILED; + uint8_t *pointer = nullptr; + const uint8_t * constPointer = nullptr; + + for(size_t i = 0; i < testDataArray.size(); i++) { + testDataArray[i] = i; + } + size_t size = 10; + + SECTION ( "Basic tests") { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.getData(testStoreId, &constPointer, &size); + REQUIRE(result == retval::CATCH_OK); + memcpy(receptionArray.data(), constPointer, size); + for(size_t i = 0; i < size; i++) { + CHECK(receptionArray[i] == i ); + } + memset(receptionArray.data(), 0, size); + result = simplePool.modifyData(testStoreId, &pointer, &size); + memcpy(receptionArray.data(), pointer, size); + REQUIRE(result == retval::CATCH_OK); + for(size_t i = 0; i < size; i++) { + CHECK(receptionArray[i] == i ); + } + result = simplePool.deleteData(testStoreId); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.addData(&testStoreId, testDataArray.data(), 15); + CHECK (result == (int) StorageManagerIF::DATA_TOO_LARGE); + } + + SECTION ( "Reservation Tests ") { + pointer = nullptr; + result = simplePool.getFreeElement(&testStoreId, size, &pointer); + REQUIRE (result == retval::CATCH_OK); + memcpy(pointer, testDataArray.data(), size); + constPointer = nullptr; + result = simplePool.getData(testStoreId, &constPointer, &size); + + REQUIRE (result == retval::CATCH_OK); + memcpy(receptionArray.data(), constPointer, size); + for(size_t i = 0; i < size; i++) { + CHECK(receptionArray[i] == i ); + } + } + + SECTION ( "Add, delete, add, add when full") { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.getData(testStoreId, &constPointer, &size); + REQUIRE( result == retval::CATCH_OK); + memcpy(receptionArray.data(), constPointer, size); + for(size_t i = 0; i < size; i++) { + CHECK(receptionArray[i] == i ); + } + + result = simplePool.deleteData(testStoreId); + REQUIRE(result == retval::CATCH_OK); + + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.getData(testStoreId, &constPointer, &size); + REQUIRE( result == retval::CATCH_OK); + memcpy(receptionArray.data(), constPointer, size); + for(size_t i = 0; i < size; i++) { + CHECK(receptionArray[i] == i ); + } + + store_address_t newAddress; + result = simplePool.addData(&newAddress, testDataArray.data(), size); + REQUIRE(result == (int) StorageManagerIF::DATA_STORAGE_FULL); + + // Packet Index to high intentionally + newAddress.packetIndex = 2; + pointer = testDataArray.data(); + result = simplePool.modifyData(newAddress, &pointer, &size); + REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); + + result = simplePool.deleteData(newAddress); + REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); + + newAddress.packetIndex = 0; + newAddress.poolIndex = 2; + result = simplePool.deleteData(newAddress); + REQUIRE(result == (int) StorageManagerIF::ILLEGAL_STORAGE_ID); + } + + SECTION ( "Initialize and clear store, delete with pointer") { + result = simplePool.initialize(); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + simplePool.clearStore(); + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + result = simplePool.modifyData(testStoreId, &pointer, &size); + REQUIRE(result == retval::CATCH_OK); + store_address_t newId; + result = simplePool.deleteData(pointer, size, &testStoreId); + REQUIRE(result == retval::CATCH_OK); + REQUIRE(testStoreId.raw != (uint32_t) StorageManagerIF::INVALID_ADDRESS); + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + } +} + +int runIdx = 0; + +TEST_CASE( "Local Pool Extended Tests [3 Pools]" , "[TestPool2]") { + LocalPool::LocalPoolConfig* config; + if(runIdx == 0) { + config = new LocalPool::LocalPoolConfig{{10, 5}, {5, 10}, {2, 20}}; + } + else { + // shufle the order, they should be sort implictely so that the + // order is ascending for the page sizes. + config = new LocalPool::LocalPoolConfig{{5, 10}, {2, 20}, {10, 5}}; + size_t lastSize = 0; + for(const auto& pair: *config) { + CHECK(pair.second > lastSize); + lastSize = pair.second; + } + } + runIdx++; + + LocalPool simplePool(0, *config); + std::array testDataArray; + std::array receptionArray; + store_address_t testStoreId; + ReturnValue_t result = retval::CATCH_FAILED; + for(size_t i = 0; i < testDataArray.size(); i++) { + testDataArray[i] = i; + } + size_t size = 0; + + SECTION ("Basic tests") { + size = 8; + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + // Should be on second page of the pool now for 8 bytes + CHECK(testStoreId.poolIndex == 1); + CHECK(testStoreId.packetIndex == 0); + + size = 15; + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + // Should be on third page of the pool now for 15 bytes + CHECK(testStoreId.poolIndex == 2); + CHECK(testStoreId.packetIndex == 0); + + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + // Should be on third page of the pool now for 15 bytes + CHECK(testStoreId.poolIndex == 2); + CHECK(testStoreId.packetIndex == 1); + + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + // Should be on third page of the pool now for 15 bytes + REQUIRE(result == (int) LocalPool::DATA_STORAGE_FULL); + + size = 8; + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + // Should still work + CHECK(testStoreId.poolIndex == 1); + CHECK(testStoreId.packetIndex == 1); + + // fill the rest of the pool + for(uint8_t idx = 2; idx < 5; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 1); + CHECK(testStoreId.packetIndex == idx); + } + } + + SECTION ("Fill Count and Clearing") { + //SECTION("Basic tests"); + uint8_t bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + // fill count should be all zeros now. + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 0); + CHECK(receptionArray[1] == 0); + CHECK(receptionArray[2] == 0); + CHECK(receptionArray[3] == 0); + + // now fill the store completely. + size = 5; + for(uint8_t idx = 0; idx < 10; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 0); + CHECK(testStoreId.packetIndex == idx); + } + size = 10; + for(uint8_t idx = 0; idx < 5; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 1); + CHECK(testStoreId.packetIndex == idx); + } + size = 20; + for(uint8_t idx = 0; idx < 2; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 2); + CHECK(testStoreId.packetIndex == idx); + } + bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + // fill count should be all 100 now. + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 100); + CHECK(receptionArray[1] == 100); + CHECK(receptionArray[2] == 100); + CHECK(receptionArray[3] == 100); + + // now clear the store + simplePool.clearStore(); + bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 0); + CHECK(receptionArray[1] == 0); + CHECK(receptionArray[2] == 0); + CHECK(receptionArray[3] == 0); + + // now fill one page + size = 5; + for(uint8_t idx = 0; idx < 10; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 0); + CHECK(testStoreId.packetIndex == idx); + } + bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + // First page full, median fill count is 33 % + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 100); + CHECK(receptionArray[1] == 0); + CHECK(receptionArray[2] == 0); + CHECK(receptionArray[3] == 33); + + // now fill second page + size = 10; + for(uint8_t idx = 0; idx < 5; idx++) { + result = simplePool.addData(&testStoreId, testDataArray.data(), size); + REQUIRE(result == retval::CATCH_OK); + CHECK(testStoreId.poolIndex == 1); + CHECK(testStoreId.packetIndex == idx); + } + bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + // First and second page full, median fill count is 66 % + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 100); + CHECK(receptionArray[1] == 100); + CHECK(receptionArray[2] == 0); + CHECK(receptionArray[3] == 66); + + // now clear first page + simplePool.clearPage(0); + bytesWritten = 0; + simplePool.getFillCount(receptionArray.data(), &bytesWritten); + // Second page full, median fill count is 33 % + CHECK(bytesWritten == 4); + CHECK(receptionArray[0] == 0); + CHECK(receptionArray[1] == 100); + CHECK(receptionArray[2] == 0); + CHECK(receptionArray[3] == 33); + } + + delete(config); +} From 378cbab64d0449c78aafc97922ea20118f842d57 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 13:25:00 +0100 Subject: [PATCH 012/103] removed config includes --- storagemanager/LocalPool.cpp | 1 - storagemanager/PoolManager.cpp | 1 - 2 files changed, 2 deletions(-) diff --git a/storagemanager/LocalPool.cpp b/storagemanager/LocalPool.cpp index 48934a0c..8e5f4d48 100644 --- a/storagemanager/LocalPool.cpp +++ b/storagemanager/LocalPool.cpp @@ -1,5 +1,4 @@ #include "LocalPool.h" -#include #include LocalPool::LocalPool(object_id_t setObjectId, const LocalPoolConfig& poolConfig, diff --git a/storagemanager/PoolManager.cpp b/storagemanager/PoolManager.cpp index 85376b28..9c801a3d 100644 --- a/storagemanager/PoolManager.cpp +++ b/storagemanager/PoolManager.cpp @@ -1,5 +1,4 @@ #include "PoolManager.h" -#include PoolManager::PoolManager(object_id_t setObjectId, const LocalPoolConfig& localPoolConfig): From 9ebf259a9e0ac9c10e501182bd18916bfef41a56 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 13:50:33 +0100 Subject: [PATCH 013/103] added back config --- storagemanager/LocalPool.cpp | 9 +++++---- storagemanager/PoolManager.cpp | 3 ++- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/storagemanager/LocalPool.cpp b/storagemanager/LocalPool.cpp index 8e5f4d48..74e362d4 100644 --- a/storagemanager/LocalPool.cpp +++ b/storagemanager/LocalPool.cpp @@ -1,4 +1,5 @@ #include "LocalPool.h" +#include #include LocalPool::LocalPool(object_id_t setObjectId, const LocalPoolConfig& poolConfig, @@ -116,7 +117,7 @@ ReturnValue_t LocalPool::modifyData(store_address_t storeId, } ReturnValue_t LocalPool::deleteData(store_address_t storeId) { -#if FSFW_DEBUGGING == 1 +#if FSFW_VERBOSE_PRINTOUT == 2 sif::debug << "Delete: Pool: " << std::dec << storeId.poolIndex << " Index: " << storeId.packetIndex << std::endl; @@ -155,7 +156,7 @@ ReturnValue_t LocalPool::deleteData(uint8_t *ptr, size_t size, // element of an object. localId.packetIndex = deltaAddress / elementSizes[n]; result = deleteData(localId); -#if FSFW_DEBUGGING == 1 +#if FSFW_VERBOSE_PRINTOUT == 2 if (deltaAddress % elementSizes[n] != 0) { sif::error << "LocalPool::deleteData: Address not aligned!" << std::endl; @@ -222,7 +223,7 @@ ReturnValue_t LocalPool::reserveSpace(const size_t size, status = findEmpty(storeId->poolIndex, &storeId->packetIndex); } if (status == RETURN_OK) { -#if FSFW_DEBUGGING == 1 +#if FSFW_VERBOSE_PRINTOUT == 2 sif::debug << "Reserve: Pool: " << std::dec << storeId->poolIndex << " Index: " << storeId->packetIndex << std::endl; @@ -264,7 +265,7 @@ void LocalPool::setToSpillToHigherPools(bool enable) { ReturnValue_t LocalPool::getPoolIndex(size_t packetSize, uint16_t *poolIndex, uint16_t startAtIndex) { for (uint16_t n = startAtIndex; n < NUMBER_OF_POOLS; n++) { -#if FSFW_DEBUGGING == 1 +#if FSFW_VERBOSE_PRINTOUT == 2 sif::debug << "LocalPool " << getObjectId() << "::getPoolIndex: Pool: " << n << ", Element Size: " << elementSizes[n] << std::endl; #endif diff --git a/storagemanager/PoolManager.cpp b/storagemanager/PoolManager.cpp index 9c801a3d..3b7b549b 100644 --- a/storagemanager/PoolManager.cpp +++ b/storagemanager/PoolManager.cpp @@ -1,4 +1,5 @@ #include "PoolManager.h" +#include PoolManager::PoolManager(object_id_t setObjectId, const LocalPoolConfig& localPoolConfig): @@ -24,7 +25,7 @@ ReturnValue_t PoolManager::reserveSpace(const size_t size, ReturnValue_t PoolManager::deleteData( store_address_t storeId) { -#if FSFW_DEBUGGING == 1 +#if FSFW_VERBOSE_PRINTOUT == 2 sif::debug << "PoolManager( " << translateObject(getObjectId()) << " )::deleteData from store " << storeId.poolIndex << ". id is "<< storeId.packetIndex << std::endl; From 2930b2dd5ac533188d3a8969ddf70f44a587f169 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 13:52:40 +0100 Subject: [PATCH 014/103] changelog update --- CHANGELOG | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index 96f5703c..7637700c 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -5,3 +5,7 @@ - vRequestContextSwitchFromISR is declared extern "C" so it can be defined in a C file without issues + +### Local Pool + +- Interface of LocalPools has change. LocalPool is not a template anymore. Instead the size and bucket number of the pools per page and the number of pages are passed to the ctor instead of two ctor arguments and a template parameter From 1f78496cd3512d2f8f1cd080a9ff9e161d2cc280 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 14:01:04 +0100 Subject: [PATCH 015/103] changelog update --- CHANGELOG | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index 96f5703c..ed73248d 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -5,3 +5,7 @@ - vRequestContextSwitchFromISR is declared extern "C" so it can be defined in a C file without issues + +### EnhancedControllerBase + +- New base class for a controller which also implements HasActionsIF and HasLocalDataPoolIF From 8c14cdfbd84654b6761f96769cdefdc98f542043 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 15:34:56 +0100 Subject: [PATCH 016/103] changelog update --- CHANGELOG | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG b/CHANGELOG index 35547c2c..16275d7a 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -14,4 +14,4 @@ a C file without issues ### Local Pool -- Interface of LocalPools has change. LocalPool is not a template anymore. Instead the size and bucket number of the pools per page and the number of pages are passed to the ctor instead of two ctor arguments and a template parameter +- Interface of LocalPools has changed. LocalPool is not a template anymore. Instead the size and bucket number of the pools per page and the number of pages are passed to the ctor instead of two ctor arguments and a template parameter From 09caeffbc7a82ee262723ec13933fe65fc10be0f Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 17:15:25 +0100 Subject: [PATCH 017/103] added new interface for file systems --- memory/HasFileSystemIF.h | 80 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 80 insertions(+) create mode 100644 memory/HasFileSystemIF.h diff --git a/memory/HasFileSystemIF.h b/memory/HasFileSystemIF.h new file mode 100644 index 00000000..dcec6346 --- /dev/null +++ b/memory/HasFileSystemIF.h @@ -0,0 +1,80 @@ +#ifndef FSFW_MEMORY_HASFILESYSTEMIF_H_ +#define FSFW_MEMORY_HASFILESYSTEMIF_H_ + +#include "../returnvalues/HasReturnvaluesIF.h" +#include "../returnvalues/FwClassIds.h" +#include "../ipc/messageQueueDefinitions.h" + +#include + +/** + * @brief Generic interface for objects which expose a file system to enable + * message based file handling. + * @author J. Meier, R. Mueller + */ +class HasFileSystemIF { +public: + static constexpr uint8_t INTERFACE_ID = CLASS_ID::FILE_SYSTEM; + + static constexpr ReturnValue_t FILE_DOES_NOT_EXIST = MAKE_RETURN_CODE(0x00); + static constexpr ReturnValue_t FILE_ALREADY_EXISTS = MAKE_RETURN_CODE(0x01); + static constexpr ReturnValue_t FILE_LOCKED = MAKE_RETURN_CODE(0x02); + + static constexpr ReturnValue_t DIRECTORY_DOES_NOT_EXIST = MAKE_RETURN_CODE(0x03); + static constexpr ReturnValue_t DIRECTORY_ALREADY_EXISTS = MAKE_RETURN_CODE(0x04); + static constexpr ReturnValue_t DIRECTORY_NOT_EMPTY = MAKE_RETURN_CODE(0x05); + + + static constexpr ReturnValue_t SEQUENCE_PACKET_MISSING_WRITE = MAKE_RETURN_CODE(0x06); //! P1: Sequence number missing + static constexpr ReturnValue_t SEQUENCE_PACKET_MISSING_READ = MAKE_RETURN_CODE(0x07); //! P1: Sequence number missing + + virtual ~HasFileSystemIF() {} + /** + * Function to get the MessageQueueId_t of the implementing object + * @return MessageQueueId_t of the object + */ + virtual MessageQueueId_t getCommandQueue() const = 0; + + /** + * Generic function to append to file. + * @param dirname Directory of the file + * @param filename The filename of the file + * @param data The data to write to the file + * @param size The size of the data to write + * @param packetNumber Current packet number. Can be used to verify that + * there are no missing packets. + * @param args Any other arguments which an implementation might require. + * @param bytesWritten Actual bytes written to file + * For large files the write procedure must be split in multiple calls + * to writeToFile + */ + virtual ReturnValue_t appendToFile(const char* repositoryPath, + const char* filename, const uint8_t* data, size_t size, + uint16_t packetNumber, void* args = nullptr) = 0; + + /** + * Generic function to create a new file. + * @param repositoryPath + * @param filename + * @param data + * @param size + * @param args Any other arguments which an implementation might require. + * @return + */ + virtual ReturnValue_t createFile(const char* repositoryPath, + const char* filename, const uint8_t* data = nullptr, + size_t size = 0, void* args = nullptr) = 0; + + /** + * Generic function to delete a file. + * @param repositoryPath + * @param filename + * @param args + * @return + */ + virtual ReturnValue_t deleteFile(const char* repositoryPath, + const char* filename, void* args = nullptr) = 0; +}; + + +#endif /* FSFW_MEMORY_HASFILESYSTEMIF_H_ */ From f1c5f192134656c7bf2683cb2497cef81cbc747b Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 1 Dec 2020 17:17:53 +0100 Subject: [PATCH 018/103] changelog update --- CHANGELOG | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index a6686478..2791c761 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -11,3 +11,7 @@ a C file without issues - It is now possible to change the message queue depth for the telecommand verification service (PUS1) - The same is possible for the event reporting service (PUS5) - PUS Health Service added, which allows to command and retrieve health via PUS packets + +### File System Interface + +- A new interfaces specifies the functions for a software object which exposes the file system of a given hardware to use message based file handling (e.g. PUS commanding) From 74ba8b76644c31405d67878421b2081306eab453 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:10:33 +0100 Subject: [PATCH 019/103] changel og updated --- CHANGELOG | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index a6686478..62a6b0a9 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -11,3 +11,19 @@ a C file without issues - It is now possible to change the message queue depth for the telecommand verification service (PUS1) - The same is possible for the event reporting service (PUS5) - PUS Health Service added, which allows to command and retrieve health via PUS packets + +### Parameter Service + +- The API of the parameter service has been changed to prevent incosistencies +and clarify usage when inspecting the code. +- The parameter ID now consists of: + 1. Domain ID (1 byte) + 2. Unique Identifier (1 byte) + 3. Linear Index (2 bytes) +The linear index can be used for arrays as well as matrices. +The parameter load command now explicitely expects the ECSS PTC and PFC +information as well as the rows and column number. Rows and column will +default to one, which is equivalent to one scalar parameter (the most +important use-case) + + From 3f9f062435061c32818c4c4ddb078cb328ea8f4d Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:11:52 +0100 Subject: [PATCH 020/103] changelog update --- CHANGELOG | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGELOG b/CHANGELOG index 62a6b0a9..8341e138 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -14,8 +14,8 @@ a C file without issues ### Parameter Service -- The API of the parameter service has been changed to prevent incosistencies -and clarify usage when inspecting the code. +- The API of the parameter service has been changed to prevent inconsistencies +between documentation and actual code and to clarify usage. - The parameter ID now consists of: 1. Domain ID (1 byte) 2. Unique Identifier (1 byte) From 795ff585f858f7ca4a155eaf7bf704964ad6f13d Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:14:30 +0100 Subject: [PATCH 021/103] controller base update --- controller/ControllerBase.cpp | 41 ++++++++++-------- controller/ControllerBase.h | 78 +++++++++++++++++++++-------------- 2 files changed, 71 insertions(+), 48 deletions(-) diff --git a/controller/ControllerBase.cpp b/controller/ControllerBase.cpp index 69551731..45e678eb 100644 --- a/controller/ControllerBase.cpp +++ b/controller/ControllerBase.cpp @@ -1,16 +1,16 @@ -#include "../subsystem/SubsystemBase.h" #include "ControllerBase.h" + #include "../subsystem/SubsystemBase.h" #include "../ipc/QueueFactory.h" #include "../action/HasActionsIF.h" -ControllerBase::ControllerBase(uint32_t setObjectId, uint32_t parentId, +ControllerBase::ControllerBase(object_id_t setObjectId, object_id_t parentId, size_t commandQueueDepth) : - SystemObject(setObjectId), parentId(parentId), mode(MODE_OFF), submode( - SUBMODE_NONE), commandQueue(NULL), modeHelper( - this), healthHelper(this, setObjectId),hkSwitcher(this),executingTask(NULL) { - commandQueue = QueueFactory::instance()->createMessageQueue(commandQueueDepth); - + SystemObject(setObjectId), parentId(parentId), mode(MODE_OFF), + submode(SUBMODE_NONE), modeHelper(this), + healthHelper(this, setObjectId), hkSwitcher(this) { + commandQueue = QueueFactory::instance()->createMessageQueue( + commandQueueDepth); } ControllerBase::~ControllerBase() { @@ -24,9 +24,9 @@ ReturnValue_t ControllerBase::initialize() { } MessageQueueId_t parentQueue = 0; - if (parentId != 0) { + if (parentId != objects::NO_OBJECT) { SubsystemBase *parent = objectManager->get(parentId); - if (parent == NULL) { + if (parent == nullptr) { return RETURN_FAILED; } parentQueue = parent->getCommandQueue(); @@ -56,26 +56,27 @@ MessageQueueId_t ControllerBase::getCommandQueue() const { } void ControllerBase::handleQueue() { - CommandMessage message; - ReturnValue_t result; - for (result = commandQueue->receiveMessage(&message); result == RETURN_OK; - result = commandQueue->receiveMessage(&message)) { + CommandMessage command; + ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; + for (result = commandQueue->receiveMessage(&command); + result == RETURN_OK; + result = commandQueue->receiveMessage(&command)) { - result = modeHelper.handleModeCommand(&message); + result = modeHelper.handleModeCommand(&command); if (result == RETURN_OK) { continue; } - result = healthHelper.handleHealthCommand(&message); + result = healthHelper.handleHealthCommand(&command); if (result == RETURN_OK) { continue; } - result = handleCommandMessage(&message); + result = handleCommandMessage(&command); if (result == RETURN_OK) { continue; } - message.setToUnknownCommand(); - commandQueue->reply(&message); + command.setToUnknownCommand(); + commandQueue->reply(&command); } } @@ -135,3 +136,7 @@ void ControllerBase::setTaskIF(PeriodicTaskIF* task_){ void ControllerBase::changeHK(Mode_t mode, Submode_t submode, bool enable) { } + +ReturnValue_t ControllerBase::initializeAfterTaskCreation() { + return HasReturnvaluesIF::RETURN_OK; +} diff --git a/controller/ControllerBase.h b/controller/ControllerBase.h index f5182ceb..25d3ab1f 100644 --- a/controller/ControllerBase.h +++ b/controller/ControllerBase.h @@ -1,5 +1,5 @@ -#ifndef CONTROLLERBASE_H_ -#define CONTROLLERBASE_H_ +#ifndef FSFW_CONTROLLER_CONTROLLERBASE_H_ +#define FSFW_CONTROLLER_CONTROLLERBASE_H_ #include "../health/HasHealthIF.h" #include "../health/HealthHelper.h" @@ -7,73 +7,91 @@ #include "../modes/ModeHelper.h" #include "../objectmanager/SystemObject.h" #include "../tasks/ExecutableObjectIF.h" +#include "../tasks/PeriodicTaskIF.h" #include "../datapool/HkSwitchHelper.h" - +/** + * @brief Generic base class for controller classes + * @details + * Implements common interfaces for controllers, which generally have + * a mode and a health state. This avoids boilerplate code. + */ class ControllerBase: public HasModesIF, public HasHealthIF, public ExecutableObjectIF, public SystemObject, public HasReturnvaluesIF { public: - static const Mode_t MODE_NORMAL = 2; - ControllerBase(uint32_t setObjectId, uint32_t parentId, + ControllerBase(object_id_t setObjectId, object_id_t parentId, size_t commandQueueDepth = 3); virtual ~ControllerBase(); - ReturnValue_t initialize(); + /** SystemObject override */ + virtual ReturnValue_t initialize() override; - virtual MessageQueueId_t getCommandQueue() const; + virtual MessageQueueId_t getCommandQueue() const override; - virtual ReturnValue_t performOperation(uint8_t opCode); - - virtual ReturnValue_t setHealth(HealthState health); - - virtual HasHealthIF::HealthState getHealth(); - - /** - * Implementation of ExecutableObjectIF function - * - * Used to setup the reference of the task, that executes this component - * @param task_ Pointer to the taskIF of this task - */ - virtual void setTaskIF(PeriodicTaskIF* task_); + /** HasHealthIF overrides */ + virtual ReturnValue_t setHealth(HealthState health) override; + virtual HasHealthIF::HealthState getHealth() override; + /** ExecutableObjectIF overrides */ + virtual ReturnValue_t performOperation(uint8_t opCode) override; + virtual void setTaskIF(PeriodicTaskIF* task) override; + virtual ReturnValue_t initializeAfterTaskCreation() override; protected: - const uint32_t parentId; + + /** + * Implemented by child class. Handle command messages which are not + * mode or health messages. + * @param message + * @return + */ + virtual ReturnValue_t handleCommandMessage(CommandMessage *message) = 0; + + /** + * Periodic helper, implemented by child class. + */ + virtual void performControlOperation() = 0; + + virtual ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode, + uint32_t *msToReachTheMode) = 0; + + const object_id_t parentId; Mode_t mode; Submode_t submode; - MessageQueueIF* commandQueue; + MessageQueueIF* commandQueue = nullptr; ModeHelper modeHelper; HealthHelper healthHelper; + // Is this still needed? HkSwitchHelper hkSwitcher; /** - * Pointer to the task which executes this component, is invalid before setTaskIF was called. + * Pointer to the task which executes this component, + * is invalid before setTaskIF was called. */ - PeriodicTaskIF* executingTask; + PeriodicTaskIF* executingTask = nullptr; - void handleQueue(); + /** Handle mode and health messages */ + virtual void handleQueue(); - virtual ReturnValue_t handleCommandMessage(CommandMessage *message) = 0; - virtual void performControlOperation() = 0; - virtual ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode, - uint32_t *msToReachTheMode) = 0; + /** Mode helpers */ virtual void modeChanged(Mode_t mode, Submode_t submode); virtual void startTransition(Mode_t mode, Submode_t submode); virtual void getMode(Mode_t *mode, Submode_t *submode); virtual void setToExternalControl(); virtual void announceMode(bool recursive); + /** HK helpers */ virtual void changeHK(Mode_t mode, Submode_t submode, bool enable); }; -#endif /* CONTROLLERBASE_H_ */ +#endif /* FSFW_CONTROLLER_CONTROLLERBASE_H_ */ From 5e092778edcce53ba6bdc89c8b5e0b9a7b9482b8 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:17:28 +0100 Subject: [PATCH 022/103] some minor changes --- datalinklayer/MapPacketExtraction.cpp | 17 +++++------------ datalinklayer/MapPacketExtraction.h | 8 +------- 2 files changed, 6 insertions(+), 19 deletions(-) diff --git a/datalinklayer/MapPacketExtraction.cpp b/datalinklayer/MapPacketExtraction.cpp index d64348e1..45f7d3f8 100644 --- a/datalinklayer/MapPacketExtraction.cpp +++ b/datalinklayer/MapPacketExtraction.cpp @@ -1,10 +1,3 @@ -/** - * @file MapPacketExtraction.cpp - * @brief This file defines the MapPacketExtraction class. - * @date 26.03.2013 - * @author baetz - */ - #include "MapPacketExtraction.h" #include "../ipc/QueueFactory.h" #include "../serviceinterface/ServiceInterfaceStream.h" @@ -12,14 +5,14 @@ #include "../tmtcpacket/SpacePacketBase.h" #include "../tmtcservices/AcceptsTelecommandsIF.h" #include "../tmtcservices/TmTcMessage.h" -#include +#include MapPacketExtraction::MapPacketExtraction(uint8_t setMapId, object_id_t setPacketDestination) : - lastSegmentationFlag(NO_SEGMENTATION), mapId(setMapId), packetLength(0), bufferPosition( - packetBuffer), packetDestination(setPacketDestination), packetStore( - NULL), tcQueueId(MessageQueueIF::NO_QUEUE) { - memset(packetBuffer, 0, sizeof(packetBuffer)); + lastSegmentationFlag(NO_SEGMENTATION), mapId(setMapId), packetLength(0), + bufferPosition(packetBuffer), packetDestination(setPacketDestination), + packetStore(NULL), tcQueueId(MessageQueueIF::NO_QUEUE) { + std::memset(packetBuffer, 0, sizeof(packetBuffer)); } ReturnValue_t MapPacketExtraction::extractPackets(TcTransferFrame* frame) { diff --git a/datalinklayer/MapPacketExtraction.h b/datalinklayer/MapPacketExtraction.h index 507f13db..eff9b7c3 100644 --- a/datalinklayer/MapPacketExtraction.h +++ b/datalinklayer/MapPacketExtraction.h @@ -1,10 +1,3 @@ -/** - * @file MapPacketExtraction.h - * @brief This file defines the MapPacketExtraction class. - * @date 26.03.2013 - * @author baetz - */ - #ifndef MAPPACKETEXTRACTION_H_ #define MAPPACKETEXTRACTION_H_ @@ -20,6 +13,7 @@ class StorageManagerIF; * The class implements the full MAP Packet Extraction functionality as described in the CCSDS * TC Space Data Link Protocol. It internally stores incomplete segmented packets until they are * fully received. All found packets are forwarded to a single distribution entity. + * @author B. Baetz */ class MapPacketExtraction: public MapPacketExtractionIF { private: From f7f062570e63a249eea95d51312b0dbb0dd104d3 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:21:44 +0100 Subject: [PATCH 023/103] new internal error reporter using local pools --- internalError/InternalErrorDataset.h | 34 +++++++ internalError/InternalErrorReporter.cpp | 127 ++++++++++++++++++------ internalError/InternalErrorReporter.h | 66 +++++++++--- 3 files changed, 182 insertions(+), 45 deletions(-) create mode 100644 internalError/InternalErrorDataset.h diff --git a/internalError/InternalErrorDataset.h b/internalError/InternalErrorDataset.h new file mode 100644 index 00000000..fa91116d --- /dev/null +++ b/internalError/InternalErrorDataset.h @@ -0,0 +1,34 @@ +#ifndef FSFW_INTERNALERROR_INTERNALERRORDATASET_H_ +#define FSFW_INTERNALERROR_INTERNALERRORDATASET_H_ + +#include +#include + +enum errorPoolIds { + TM_HITS, + QUEUE_HITS, + STORE_HITS +}; + + +class InternalErrorDataset: public StaticLocalDataSet<3 * sizeof(uint32_t)> { +public: + static constexpr uint8_t ERROR_SET_ID = 0; + + InternalErrorDataset(HasLocalDataPoolIF* owner): + StaticLocalDataSet(owner, ERROR_SET_ID) {} + + InternalErrorDataset(object_id_t objectId): + StaticLocalDataSet(sid_t(objectId , ERROR_SET_ID)) {} + + lp_var_t tmHits = lp_var_t(hkManager->getOwner(), + TM_HITS, this); + lp_var_t queueHits = lp_var_t(hkManager->getOwner(), + QUEUE_HITS, this); + lp_var_t storeHits = lp_var_t(hkManager->getOwner(), + STORE_HITS, this); +}; + + + +#endif /* FSFW_INTERNALERROR_INTERNALERRORDATASET_H_ */ diff --git a/internalError/InternalErrorReporter.cpp b/internalError/InternalErrorReporter.cpp index 861e1595..8d5c792b 100644 --- a/internalError/InternalErrorReporter.cpp +++ b/internalError/InternalErrorReporter.cpp @@ -1,17 +1,17 @@ #include "InternalErrorReporter.h" -#include "../datapool/DataSet.h" -#include "../datapool/PoolVariable.h" +#include "../ipc/QueueFactory.h" #include "../ipc/MutexFactory.h" - #include "../serviceinterface/ServiceInterfaceStream.h" InternalErrorReporter::InternalErrorReporter(object_id_t setObjectId, - uint32_t queuePoolId, uint32_t tmPoolId, uint32_t storePoolId) : - SystemObject(setObjectId), mutex(NULL), queuePoolId(queuePoolId), tmPoolId( - tmPoolId), storePoolId( - storePoolId), queueHits(0), tmHits(0), storeHits( - 0) { + uint32_t messageQueueDepth) : + SystemObject(setObjectId), + commandQueue(QueueFactory::instance()-> + createMessageQueue(messageQueueDepth)), + poolManager(this, commandQueue), + internalErrorSid(setObjectId, InternalErrorDataset::ERROR_SET_ID), + internalErrorDataset(this) { mutex = MutexFactory::instance()->createMutex(); } @@ -19,28 +19,42 @@ InternalErrorReporter::~InternalErrorReporter() { MutexFactory::instance()->deleteMutex(mutex); } +void InternalErrorReporter::setDiagnosticPrintout(bool enable) { + this->diagnosticPrintout = enable; +} + ReturnValue_t InternalErrorReporter::performOperation(uint8_t opCode) { - - DataSet mySet; - PoolVariable queueHitsInPool(queuePoolId, &mySet, - PoolVariableIF::VAR_READ_WRITE); - PoolVariable tmHitsInPool(tmPoolId, &mySet, - PoolVariableIF::VAR_READ_WRITE); - - PoolVariable storeHitsInPool(storePoolId, &mySet, - PoolVariableIF::VAR_READ_WRITE); - mySet.read(); + internalErrorDataset.read(INTERNAL_ERROR_MUTEX_TIMEOUT); uint32_t newQueueHits = getAndResetQueueHits(); uint32_t newTmHits = getAndResetTmHits(); uint32_t newStoreHits = getAndResetStoreHits(); - queueHitsInPool.value += newQueueHits; - tmHitsInPool.value += newTmHits; - storeHitsInPool.value += newStoreHits; +#ifdef DEBUG + if(diagnosticPrintout) { + if((newQueueHits > 0) or (newTmHits > 0) or (newStoreHits > 0)) { + sif::debug << "InternalErrorReporter::performOperation: Errors " + << "occured!" << std::endl; + sif::debug << "Queue errors: " << newQueueHits << std::endl; + sif::debug << "TM errors: " << newTmHits << std::endl; + sif::debug << "Store errors: " << newStoreHits << std::endl; + } + } +#endif - mySet.commit(PoolVariableIF::VALID); + internalErrorDataset.queueHits.value += newQueueHits; + internalErrorDataset.storeHits.value += newStoreHits; + internalErrorDataset.tmHits.value += newTmHits; + internalErrorDataset.commit(INTERNAL_ERROR_MUTEX_TIMEOUT); + + poolManager.performHkOperation(); + + CommandMessage message; + ReturnValue_t result = commandQueue->receiveMessage(&message); + if(result != MessageQueueIF::EMPTY) { + poolManager.handleHousekeepingMessage(&message); + } return HasReturnvaluesIF::RETURN_OK; } @@ -54,7 +68,7 @@ void InternalErrorReporter::lostTm() { uint32_t InternalErrorReporter::getAndResetQueueHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = queueHits; queueHits = 0; mutex->unlockMutex(); @@ -63,21 +77,21 @@ uint32_t InternalErrorReporter::getAndResetQueueHits() { uint32_t InternalErrorReporter::getQueueHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = queueHits; mutex->unlockMutex(); return value; } void InternalErrorReporter::incrementQueueHits() { - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); queueHits++; mutex->unlockMutex(); } uint32_t InternalErrorReporter::getAndResetTmHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = tmHits; tmHits = 0; mutex->unlockMutex(); @@ -86,14 +100,14 @@ uint32_t InternalErrorReporter::getAndResetTmHits() { uint32_t InternalErrorReporter::getTmHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = tmHits; mutex->unlockMutex(); return value; } void InternalErrorReporter::incrementTmHits() { - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); tmHits++; mutex->unlockMutex(); } @@ -104,7 +118,7 @@ void InternalErrorReporter::storeFull() { uint32_t InternalErrorReporter::getAndResetStoreHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = storeHits; storeHits = 0; mutex->unlockMutex(); @@ -113,14 +127,65 @@ uint32_t InternalErrorReporter::getAndResetStoreHits() { uint32_t InternalErrorReporter::getStoreHits() { uint32_t value; - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); value = storeHits; mutex->unlockMutex(); return value; } void InternalErrorReporter::incrementStoreHits() { - mutex->lockMutex(MutexIF::BLOCKING); + mutex->lockMutex(MutexIF::WAITING, INTERNAL_ERROR_MUTEX_TIMEOUT); storeHits++; mutex->unlockMutex(); } + +object_id_t InternalErrorReporter::getObjectId() const { + return SystemObject::getObjectId(); +} + +MessageQueueId_t InternalErrorReporter::getCommandQueue() const { + return this->commandQueue->getId(); +} + +ReturnValue_t InternalErrorReporter::initializeLocalDataPool( + LocalDataPool &localDataPoolMap, LocalDataPoolManager &poolManager) { + localDataPoolMap.emplace(errorPoolIds::TM_HITS, + new PoolEntry()); + localDataPoolMap.emplace(errorPoolIds::QUEUE_HITS, + new PoolEntry()); + localDataPoolMap.emplace(errorPoolIds::STORE_HITS, + new PoolEntry()); + poolManager.subscribeForPeriodicPacket(internalErrorSid, false, + getPeriodicOperationFrequency(), true); + internalErrorDataset.setValidity(true, true); + return HasReturnvaluesIF::RETURN_OK; +} + +LocalDataPoolManager* InternalErrorReporter::getHkManagerHandle() { + return &poolManager; +} + +dur_millis_t InternalErrorReporter::getPeriodicOperationFrequency() const { + return this->executingTask->getPeriodMs(); +} + +LocalPoolDataSetBase* InternalErrorReporter::getDataSetHandle(sid_t sid) { + return &internalErrorDataset; +} + +void InternalErrorReporter::setTaskIF(PeriodicTaskIF *task) { + this->executingTask = task; +} + +ReturnValue_t InternalErrorReporter::initialize() { + ReturnValue_t result = poolManager.initialize(commandQueue); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + return SystemObject::initialize(); +} + +ReturnValue_t InternalErrorReporter::initializeAfterTaskCreation() { + return poolManager.initializeAfterTaskCreation(); +} + diff --git a/internalError/InternalErrorReporter.h b/internalError/InternalErrorReporter.h index 9aa24a0f..8d33c06e 100644 --- a/internalError/InternalErrorReporter.h +++ b/internalError/InternalErrorReporter.h @@ -1,37 +1,75 @@ -#ifndef INTERNALERRORREPORTER_H_ -#define INTERNALERRORREPORTER_H_ +#ifndef FSFW_INTERNALERROR_INTERNALERRORREPORTER_H_ +#define FSFW_INTERNALERROR_INTERNALERRORREPORTER_H_ #include "InternalErrorReporterIF.h" +#include "../tasks/PeriodicTaskIF.h" +#include "../internalError/InternalErrorDataset.h" +#include "../datapoollocal/LocalDataPoolManager.h" #include "../tasks/ExecutableObjectIF.h" #include "../objectmanager/SystemObject.h" #include "../ipc/MutexIF.h" +/** + * @brief This class is used to track internal errors like lost telemetry, + * failed message sending or a full store. + * @details + * All functions were kept virtual so this class can be extended easily + * to store custom internal errors (e.g. communication interface errors). + */ class InternalErrorReporter: public SystemObject, public ExecutableObjectIF, - public InternalErrorReporterIF { + public InternalErrorReporterIF, + public HasLocalDataPoolIF { public: - InternalErrorReporter(object_id_t setObjectId, uint32_t queuePoolId, - uint32_t tmPoolId, uint32_t storePoolId); + static constexpr uint8_t INTERNAL_ERROR_MUTEX_TIMEOUT = 20; + + InternalErrorReporter(object_id_t setObjectId, + uint32_t messageQueueDepth = 5); + + /** + * Enable diagnostic printout. Please note that this feature will + * only work if DEBUG has been supplied to the build defines. + * @param enable + */ + void setDiagnosticPrintout(bool enable); + virtual ~InternalErrorReporter(); - virtual ReturnValue_t performOperation(uint8_t opCode); + virtual object_id_t getObjectId() const override; + virtual MessageQueueId_t getCommandQueue() const override; + virtual ReturnValue_t initializeLocalDataPool( + LocalDataPool& localDataPoolMap, + LocalDataPoolManager& poolManager) override; + virtual LocalDataPoolManager* getHkManagerHandle() override; + virtual dur_millis_t getPeriodicOperationFrequency() const override; + virtual LocalPoolDataSetBase* getDataSetHandle(sid_t sid) override; + + virtual ReturnValue_t initialize() override; + virtual ReturnValue_t initializeAfterTaskCreation() override; + virtual ReturnValue_t performOperation(uint8_t opCode) override; virtual void queueMessageNotSent(); virtual void lostTm(); virtual void storeFull(); + + virtual void setTaskIF(PeriodicTaskIF* task) override; protected: - MutexIF* mutex; + MessageQueueIF* commandQueue; + LocalDataPoolManager poolManager; - uint32_t queuePoolId; - uint32_t tmPoolId; - uint32_t storePoolId; + PeriodicTaskIF* executingTask = nullptr; + MutexIF* mutex = nullptr; + sid_t internalErrorSid; + InternalErrorDataset internalErrorDataset; - uint32_t queueHits; - uint32_t tmHits; - uint32_t storeHits; + bool diagnosticPrintout = true; + + uint32_t queueHits = 0; + uint32_t tmHits = 0; + uint32_t storeHits = 0; uint32_t getAndResetQueueHits(); uint32_t getQueueHits(); @@ -47,4 +85,4 @@ protected: }; -#endif /* INTERNALERRORREPORTER_H_ */ +#endif /* FSFW_INTERNALERROR_INTERNALERRORREPORTER_H_ */ From c6db9944fd57d934fed5a54f0816feeea346ebf1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 13:26:50 +0100 Subject: [PATCH 024/103] changelog update --- CHANGELOG | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/CHANGELOG b/CHANGELOG index a6686478..b8f589f8 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -11,3 +11,10 @@ a C file without issues - It is now possible to change the message queue depth for the telecommand verification service (PUS1) - The same is possible for the event reporting service (PUS5) - PUS Health Service added, which allows to command and retrieve health via PUS packets + +### Internal Error Reporter + +- The new internal error reporter uses the local data pools. The pool IDs for +the exisiting three error values and the new error set will be hardcoded for +now, the the constructor for the internal error reporter just takes an object +ID for now. From ec3c83bcc1e9cbf587b4602fa3d65d9f797c781e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 18:24:51 +0100 Subject: [PATCH 025/103] monitoring update --- monitoring/AbsLimitMonitor.h | 28 +++++++----- monitoring/HasMonitorsIF.h | 12 ++--- monitoring/LimitMonitor.h | 27 ++++++----- monitoring/MonitorBase.h | 64 +++++++++++++++++---------- monitoring/MonitorReporter.h | 37 +++++++++------- monitoring/MonitoringIF.h | 8 ++-- monitoring/MonitoringMessageContent.h | 37 ++++++++++------ monitoring/TriplexMonitor.h | 2 +- 8 files changed, 127 insertions(+), 88 deletions(-) diff --git a/monitoring/AbsLimitMonitor.h b/monitoring/AbsLimitMonitor.h index 2e60f6f8..5feb369c 100644 --- a/monitoring/AbsLimitMonitor.h +++ b/monitoring/AbsLimitMonitor.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_MONITORING_ABSLIMITMONITOR_H_ -#define FRAMEWORK_MONITORING_ABSLIMITMONITOR_H_ +#ifndef FSFW_MONITORING_ABSLIMITMONITOR_H_ +#define FSFW_MONITORING_ABSLIMITMONITOR_H_ #include "MonitorBase.h" #include @@ -7,9 +7,14 @@ template class AbsLimitMonitor: public MonitorBase { public: - AbsLimitMonitor(object_id_t reporterId, uint8_t monitorId, uint32_t parameterId, - uint16_t confirmationLimit, T limit, Event violationEvent = MonitoringIF::VALUE_OUT_OF_RANGE, bool aboveIsViolation = true) : - MonitorBase(reporterId, monitorId, parameterId, confirmationLimit), limit(limit), violationEvent(violationEvent), aboveIsViolation(aboveIsViolation) { + AbsLimitMonitor(object_id_t reporterId, uint8_t monitorId, + gp_id_t globalPoolId, uint16_t confirmationLimit, T limit, + Event violationEvent = MonitoringIF::VALUE_OUT_OF_RANGE, + bool aboveIsViolation = true) : + MonitorBase(reporterId, monitorId, globalPoolId, + confirmationLimit), + limit(limit), violationEvent(violationEvent), + aboveIsViolation(aboveIsViolation) { } virtual ~AbsLimitMonitor() { } @@ -32,8 +37,9 @@ public: const ParameterWrapper *newValues, uint16_t startAtIndex) { ReturnValue_t result = this->MonitorBase::getParameter(domainId, parameterId, parameterWrapper, newValues, startAtIndex); - //We'll reuse the DOMAIN_ID of MonitorReporter, as we know the parameterIds used there. - if (result != this->INVALID_MATRIX_ID) { + // We'll reuse the DOMAIN_ID of MonitorReporter, + // as we know the parameterIds used there. + if (result != this->INVALID_IDENTIFIER_ID) { return result; } switch (parameterId) { @@ -41,7 +47,7 @@ public: parameterWrapper->set(this->limit); break; default: - return this->INVALID_MATRIX_ID; + return this->INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } @@ -59,7 +65,9 @@ protected: void sendTransitionEvent(T currentValue, ReturnValue_t state) { switch (state) { case MonitoringIF::OUT_OF_RANGE: - EventManagerIF::triggerEvent(this->reportingId, violationEvent, this->parameterId); + EventManagerIF::triggerEvent(this->reportingId, + violationEvent, this->globalPoolId.objectId, + this->globalPoolId.localPoolId); break; default: break; @@ -70,4 +78,4 @@ protected: const bool aboveIsViolation; }; -#endif /* FRAMEWORK_MONITORING_ABSLIMITMONITOR_H_ */ +#endif /* FSFW_MONITORING_ABSLIMITMONITOR_H_ */ diff --git a/monitoring/HasMonitorsIF.h b/monitoring/HasMonitorsIF.h index 85d92b6b..04f63437 100644 --- a/monitoring/HasMonitorsIF.h +++ b/monitoring/HasMonitorsIF.h @@ -1,11 +1,5 @@ -/** - * @file HasMonitorsIF.h - * @brief This file defines the HasMonitorsIF class. - * @date 28.07.2014 - * @author baetz - */ -#ifndef HASMONITORSIF_H_ -#define HASMONITORSIF_H_ +#ifndef FSFW_MONITORING_HASMONITORSIF_H_ +#define FSFW_MONITORING_HASMONITORSIF_H_ #include "../events/EventReportingProxyIF.h" #include "../objectmanager/ObjectManagerIF.h" @@ -27,4 +21,4 @@ public: } }; -#endif /* HASMONITORSIF_H_ */ +#endif /* FSFW_MONITORING_HASMONITORSIF_H_ */ diff --git a/monitoring/LimitMonitor.h b/monitoring/LimitMonitor.h index 66e6725e..c4448ced 100644 --- a/monitoring/LimitMonitor.h +++ b/monitoring/LimitMonitor.h @@ -12,13 +12,15 @@ template class LimitMonitor: public MonitorBase { public: - LimitMonitor(object_id_t reporterId, uint8_t monitorId, uint32_t parameterId, - uint16_t confirmationLimit, T lowerLimit, T upperLimit, - Event belowLowEvent = MonitoringIF::VALUE_BELOW_LOW_LIMIT, + LimitMonitor(object_id_t reporterId, uint8_t monitorId, + gp_id_t globalPoolId, uint16_t confirmationLimit, T lowerLimit, + T upperLimit, Event belowLowEvent = + MonitoringIF::VALUE_BELOW_LOW_LIMIT, Event aboveHighEvent = MonitoringIF::VALUE_ABOVE_HIGH_LIMIT) : - MonitorBase(reporterId, monitorId, parameterId, confirmationLimit), lowerLimit( - lowerLimit), upperLimit(upperLimit), belowLowEvent( - belowLowEvent), aboveHighEvent(aboveHighEvent) { + MonitorBase(reporterId, monitorId, globalPoolId, + confirmationLimit), + lowerLimit(lowerLimit), upperLimit(upperLimit), + belowLowEvent(belowLowEvent), aboveHighEvent(aboveHighEvent) { } virtual ~LimitMonitor() { } @@ -41,7 +43,7 @@ public: ReturnValue_t result = this->MonitorBase::getParameter(domainId, parameterId, parameterWrapper, newValues, startAtIndex); //We'll reuse the DOMAIN_ID of MonitorReporter, as we know the parameterIds used there. - if (result != this->INVALID_MATRIX_ID) { + if (result != this->INVALID_IDENTIFIER_ID) { return result; } switch (parameterId) { @@ -52,12 +54,13 @@ public: parameterWrapper->set(this->upperLimit); break; default: - return this->INVALID_MATRIX_ID; + return this->INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } bool isOutOfLimits() { - if (this->oldState == MonitoringIF::ABOVE_HIGH_LIMIT || this->oldState == MonitoringIF::BELOW_LOW_LIMIT) { + if (this->oldState == MonitoringIF::ABOVE_HIGH_LIMIT or + this->oldState == MonitoringIF::BELOW_LOW_LIMIT) { return true; } else { return false; @@ -76,10 +79,12 @@ protected: void sendTransitionEvent(T currentValue, ReturnValue_t state) { switch (state) { case MonitoringIF::BELOW_LOW_LIMIT: - EventManagerIF::triggerEvent(this->reportingId, belowLowEvent, this->parameterId); + EventManagerIF::triggerEvent(this->reportingId, belowLowEvent, + this->globalPoolId.objectId, this->globalPoolId.localPoolId); break; case MonitoringIF::ABOVE_HIGH_LIMIT: - EventManagerIF::triggerEvent(this->reportingId, aboveHighEvent, this->parameterId); + EventManagerIF::triggerEvent(this->reportingId, aboveHighEvent, + this->globalPoolId.objectId, this->globalPoolId.localPoolId); break; default: break; diff --git a/monitoring/MonitorBase.h b/monitoring/MonitorBase.h index b2d0e6cb..530a3840 100644 --- a/monitoring/MonitorBase.h +++ b/monitoring/MonitorBase.h @@ -1,39 +1,50 @@ -#ifndef MONITORBASE_H_ -#define MONITORBASE_H_ +#ifndef FSFW_MONITORING_MONITORBASE_H_ +#define FSFW_MONITORING_MONITORBASE_H_ -#include "../datapool/DataSet.h" -#include "../datapool/PIDReader.h" #include "LimitViolationReporter.h" #include "MonitoringIF.h" #include "MonitoringMessageContent.h" #include "MonitorReporter.h" +#include "../datapoollocal/LocalPoolVariable.h" + + /** - * Base class for monitoring of parameters. - * Can be used anywhere, specializations need to implement checkSample and should override sendTransitionEvent. - * Manages state handling, enabling and disabling of events/reports and forwarding of transition - * reports via MonitorReporter. In addition, it provides default implementations for fetching the parameter sample from - * the data pool and a simple confirmation counter. + * @brief Base class for monitoring of parameters. + * @details + * Can be used anywhere, specializations need to implement checkSample and + * should override sendTransitionEvent. + * Manages state handling, enabling and disabling of events/reports and + * forwarding of transition reports via MonitorReporter. + * + * In addition, it provides default implementations for fetching the + * parameter sample from the data pool and a simple confirmation counter. */ template class MonitorBase: public MonitorReporter { public: + MonitorBase(object_id_t reporterId, uint8_t monitorId, - uint32_t parameterId, uint16_t confirmationLimit) : - MonitorReporter(reporterId, monitorId, parameterId, confirmationLimit) { + gp_id_t globalPoolId, uint16_t confirmationLimit): + MonitorReporter(reporterId, monitorId, globalPoolId, + confirmationLimit), + poolVariable(globalPoolId) { } + virtual ~MonitorBase() { } + virtual ReturnValue_t check() { - //1. Fetch sample of type T, return validity. + // 1. Fetch sample of type T, return validity. T sample = 0; ReturnValue_t validity = fetchSample(&sample); - //2. If returning from fetch != OK, parameter is invalid. Report (if oldState is != invalidity). + // 2. If returning from fetch != OK, parameter is invalid. + // Report (if oldState is != invalidity). if (validity != HasReturnvaluesIF::RETURN_OK) { this->monitorStateIs(validity, sample, 0); - //3. Otherwise, check sample. } else { + //3. Otherwise, check sample. this->oldState = doCheck(sample); } return this->oldState; @@ -43,20 +54,25 @@ public: ReturnValue_t currentState = checkSample(sample, &crossedLimit); return this->monitorStateIs(currentState,sample, crossedLimit); } - //Abstract or default. + + // Abstract or default. virtual ReturnValue_t checkSample(T sample, T* crossedLimit) = 0; protected: + virtual ReturnValue_t fetchSample(T* sample) { - DataSet mySet; - PIDReader parameter(this->parameterId, &mySet); - mySet.read(); - if (!parameter.isValid()) { - return MonitoringIF::INVALID; - } - *sample = parameter.value; - return HasReturnvaluesIF::RETURN_OK; + ReturnValue_t result = poolVariable.read(); + if(result != HasReturnvaluesIF::RETURN_OK) { + return result; + } + if (not poolVariable.isValid()) { + return MonitoringIF::INVALID; + } + *sample = poolVariable.value; + return HasReturnvaluesIF::RETURN_OK; } + + LocalPoolVar poolVariable; }; -#endif /* MONITORBASE_H_ */ +#endif /* FSFW_MONITORING_MONITORBASE_H_ */ diff --git a/monitoring/MonitorReporter.h b/monitoring/MonitorReporter.h index ca2b534b..9028e7e4 100644 --- a/monitoring/MonitorReporter.h +++ b/monitoring/MonitorReporter.h @@ -1,10 +1,12 @@ -#ifndef FRAMEWORK_MONITORING_MONITORREPORTER_H_ -#define FRAMEWORK_MONITORING_MONITORREPORTER_H_ +#ifndef FSFW_MONITORING_MONITORREPORTER_H_ +#define FSFW_MONITORING_MONITORREPORTER_H_ -#include "../events/EventManagerIF.h" #include "LimitViolationReporter.h" #include "MonitoringIF.h" #include "MonitoringMessageContent.h" + +#include "../datapoollocal/locPoolDefinitions.h" +#include "../events/EventManagerIF.h" #include "../parameters/HasParametersIF.h" template @@ -14,11 +16,14 @@ public: static const uint8_t ENABLED = 1; static const uint8_t DISABLED = 0; - MonitorReporter(object_id_t reportingId, uint8_t monitorId, uint32_t parameterId, uint16_t confirmationLimit) : - monitorId(monitorId), parameterId(parameterId), reportingId( - reportingId), oldState(MonitoringIF::UNCHECKED), reportingEnabled( - ENABLED), eventEnabled(ENABLED), currentCounter(0), confirmationLimit( - confirmationLimit) { + // TODO: Adapt to use SID instead of parameter ID. + + MonitorReporter(object_id_t reportingId, uint8_t monitorId, + gp_id_t globalPoolId, uint16_t confirmationLimit) : + monitorId(monitorId), globalPoolId(globalPoolId), + reportingId(reportingId), oldState(MonitoringIF::UNCHECKED), + reportingEnabled(ENABLED), eventEnabled(ENABLED), currentCounter(0), + confirmationLimit(confirmationLimit) { } virtual ~MonitorReporter() { @@ -63,7 +68,7 @@ public: parameterWrapper->set(this->eventEnabled); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } @@ -91,7 +96,7 @@ public: protected: const uint8_t monitorId; - const uint32_t parameterId; + const gp_id_t globalPoolId; object_id_t reportingId; ReturnValue_t oldState; @@ -148,7 +153,8 @@ protected: case HasReturnvaluesIF::RETURN_OK: break; default: - EventManagerIF::triggerEvent(reportingId, MonitoringIF::MONITOR_CHANGED_STATE, state); + EventManagerIF::triggerEvent(reportingId, + MonitoringIF::MONITOR_CHANGED_STATE, state); break; } } @@ -159,14 +165,15 @@ protected: * @param crossedLimit The limit crossed (if applicable). * @param state Current state the monitor is in. */ - virtual void sendTransitionReport(T parameterValue, T crossedLimit, ReturnValue_t state) { - MonitoringReportContent report(parameterId, + virtual void sendTransitionReport(T parameterValue, T crossedLimit, + ReturnValue_t state) { + MonitoringReportContent report(globalPoolId, parameterValue, crossedLimit, oldState, state); LimitViolationReporter::sendLimitViolationReport(&report); } ReturnValue_t setToState(ReturnValue_t state) { if (oldState != state && reportingEnabled) { - MonitoringReportContent report(parameterId, 0, 0, oldState, + MonitoringReportContent report(globalPoolId, 0, 0, oldState, state); LimitViolationReporter::sendLimitViolationReport(&report); oldState = state; @@ -175,4 +182,4 @@ protected: } }; -#endif /* FRAMEWORK_MONITORING_MONITORREPORTER_H_ */ +#endif /* FSFW_MONITORING_MONITORREPORTER_H_ */ diff --git a/monitoring/MonitoringIF.h b/monitoring/MonitoringIF.h index 44218c36..aa266f33 100644 --- a/monitoring/MonitoringIF.h +++ b/monitoring/MonitoringIF.h @@ -1,8 +1,8 @@ -#ifndef MONITORINGIF_H_ -#define MONITORINGIF_H_ +#ifndef FSFW_MONITORING_MONITORINGIF_H_ +#define FSFW_MONITORING_MONITORINGIF_H_ -#include "../memory/HasMemoryIF.h" #include "MonitoringMessage.h" +#include "../memory/HasMemoryIF.h" #include "../serialize/SerializeIF.h" class MonitoringIF : public SerializeIF { @@ -64,4 +64,4 @@ public: -#endif /* MONITORINGIF_H_ */ +#endif /* FSFW_MONITORING_MONITORINGIF_H_ */ diff --git a/monitoring/MonitoringMessageContent.h b/monitoring/MonitoringMessageContent.h index c82506f3..44d32656 100644 --- a/monitoring/MonitoringMessageContent.h +++ b/monitoring/MonitoringMessageContent.h @@ -3,6 +3,7 @@ #include "HasMonitorsIF.h" #include "MonitoringIF.h" +#include "../datapoollocal/locPoolDefinitions.h" #include "../objectmanager/ObjectManagerIF.h" #include "../serialize/SerialBufferAdapter.h" #include "../serialize/SerialFixedArrayListAdapter.h" @@ -16,12 +17,17 @@ void setStaticFrameworkObjectIds(); } //PID(uint32_t), TYPE, LIMIT_ID, value,limitValue, previous, later, timestamp +/** + * @brief Does magic. + * @tparam T + */ template class MonitoringReportContent: public SerialLinkedListAdapter { friend void (Factory::setStaticFrameworkObjectIds)(); public: SerializeElement monitorId; - SerializeElement parameterId; + SerializeElement parameterObjectId; + SerializeElement localPoolId; SerializeElement parameterValue; SerializeElement limitValue; SerializeElement oldState; @@ -30,20 +36,23 @@ public: SerializeElement> timestampSerializer; TimeStamperIF* timeStamper; MonitoringReportContent() : - SerialLinkedListAdapter( - LinkedElement::Iterator(¶meterId)), monitorId(0), parameterId( - 0), parameterValue(0), limitValue(0), oldState(0), newState( - 0), rawTimestamp( { 0 }), timestampSerializer(rawTimestamp, + SerialLinkedListAdapter(¶meterObjectId), + monitorId(0), parameterObjectId(0), + localPoolId(0), parameterValue(0), + limitValue(0), oldState(0), newState(0), + rawTimestamp( { 0 }), timestampSerializer(rawTimestamp, sizeof(rawTimestamp)), timeStamper(NULL) { setAllNext(); } - MonitoringReportContent(uint32_t setPID, T value, T limitValue, + MonitoringReportContent(gp_id_t globalPoolId, T value, T limitValue, ReturnValue_t oldState, ReturnValue_t newState) : - SerialLinkedListAdapter( - LinkedElement::Iterator(¶meterId)), monitorId(0), parameterId( - setPID), parameterValue(value), limitValue(limitValue), oldState( - oldState), newState(newState), timestampSerializer(rawTimestamp, - sizeof(rawTimestamp)), timeStamper(NULL) { + SerialLinkedListAdapter(¶meterObjectId), + monitorId(0), parameterObjectId(globalPoolId.objectId), + localPoolId(globalPoolId.localPoolId), + parameterValue(value), limitValue(limitValue), + oldState(oldState), newState(newState), + timestampSerializer(rawTimestamp, sizeof(rawTimestamp)), + timeStamper(NULL) { setAllNext(); if (checkAndSetStamper()) { timeStamper->addTimeStamp(rawTimestamp, sizeof(rawTimestamp)); @@ -53,16 +62,16 @@ private: static object_id_t timeStamperId; void setAllNext() { - parameterId.setNext(¶meterValue); + parameterObjectId.setNext(¶meterValue); parameterValue.setNext(&limitValue); limitValue.setNext(&oldState); oldState.setNext(&newState); newState.setNext(×tampSerializer); } bool checkAndSetStamper() { - if (timeStamper == NULL) { + if (timeStamper == nullptr) { timeStamper = objectManager->get( timeStamperId ); - if ( timeStamper == NULL ) { + if ( timeStamper == nullptr ) { sif::error << "MonitoringReportContent::checkAndSetStamper: " "Stamper not found!" << std::endl; return false; diff --git a/monitoring/TriplexMonitor.h b/monitoring/TriplexMonitor.h index 9b60aeb6..c4b3c537 100644 --- a/monitoring/TriplexMonitor.h +++ b/monitoring/TriplexMonitor.h @@ -82,7 +82,7 @@ public: parameterWrapper->set(limit); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } From 9ba8ef1ae212f9058671399933cf29335cd436f5 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 18:29:28 +0100 Subject: [PATCH 026/103] power update --- power/Fuse.cpp | 33 +++++++++++++++------------- power/Fuse.h | 47 ++++++++++++++++++++++------------------ power/PowerComponent.cpp | 27 ++++++++++------------- power/PowerComponent.h | 24 +++++++++++--------- power/PowerComponentIF.h | 19 ++++++++-------- power/PowerSensor.cpp | 30 ++++++++++++++----------- power/PowerSensor.h | 38 ++++++++++++++++++-------------- power/PowerSwitchIF.h | 22 +++++++++---------- power/PowerSwitcher.cpp | 28 +++++++++++++++--------- power/PowerSwitcher.h | 17 ++++++++++----- 10 files changed, 156 insertions(+), 129 deletions(-) diff --git a/power/Fuse.cpp b/power/Fuse.cpp index 9986ab6b..1c30d83f 100644 --- a/power/Fuse.cpp +++ b/power/Fuse.cpp @@ -1,22 +1,25 @@ +#include "Fuse.h" + #include "../monitoring/LimitViolationReporter.h" #include "../monitoring/MonitoringMessageContent.h" #include "../objectmanager/ObjectManagerIF.h" -#include "Fuse.h" #include "../serialize/SerialFixedArrayListAdapter.h" #include "../ipc/QueueFactory.h" object_id_t Fuse::powerSwitchId = 0; -Fuse::Fuse(object_id_t fuseObjectId, uint8_t fuseId, VariableIds ids, +Fuse::Fuse(object_id_t fuseObjectId, uint8_t fuseId, + sid_t variableSet, VariableIds ids, float maxCurrent, uint16_t confirmationCount) : - SystemObject(fuseObjectId), oldFuseState(0), fuseId(fuseId), powerIF( - NULL), currentLimit(fuseObjectId, 1, ids.pidCurrent, confirmationCount, - maxCurrent, FUSE_CURRENT_HIGH), powerMonitor(fuseObjectId, 2, - DataPool::poolIdAndPositionToPid(ids.poolIdPower, 0), - confirmationCount), set(), voltage(ids.pidVoltage, &set), current( - ids.pidCurrent, &set), state(ids.pidState, &set), power( - ids.poolIdPower, &set, PoolVariableIF::VAR_READ_WRITE), commandQueue( - NULL), parameterHelper(this), healthHelper(this, fuseObjectId) { + SystemObject(fuseObjectId), oldFuseState(0), fuseId(fuseId), + currentLimit(fuseObjectId, 1, ids.pidCurrent, confirmationCount, + maxCurrent, FUSE_CURRENT_HIGH), + powerMonitor(fuseObjectId, 2, ids.poolIdPower, + confirmationCount), + set(variableSet), voltage(ids.pidVoltage, &set), + current(ids.pidCurrent, &set), state(ids.pidState, &set), + power(ids.poolIdPower, &set, PoolVariableIF::VAR_READ_WRITE), + parameterHelper(this), healthHelper(this, fuseObjectId) { commandQueue = QueueFactory::instance()->createMessageQueue(); } @@ -75,7 +78,7 @@ ReturnValue_t Fuse::check() { float lowLimit = 0.0; float highLimit = RESIDUAL_POWER; calculatePowerLimits(&lowLimit, &highLimit); - result = powerMonitor.checkPower(power, lowLimit, highLimit); + result = powerMonitor.checkPower(power.value, lowLimit, highLimit); if (result == MonitoringIF::BELOW_LOW_LIMIT) { reportEvents(POWER_BELOW_LOW_LIMIT); } else if (result == MonitoringIF::ABOVE_HIGH_LIMIT) { @@ -109,7 +112,7 @@ size_t Fuse::getSerializedSize() const { } ReturnValue_t Fuse::deSerialize(const uint8_t** buffer, size_t* size, -Endianness streamEndianness) { + Endianness streamEndianness) { ReturnValue_t result = RETURN_FAILED; for (DeviceList::iterator iter = devices.begin(); iter != devices.end(); iter++) { @@ -132,7 +135,7 @@ void Fuse::calculateFusePower() { return; } //Calculate fuse power. - power = current * voltage; + power.value = current.value * voltage.value; power.setValid(PoolVariableIF::VALID); } @@ -190,12 +193,12 @@ void Fuse::checkFuseState() { reportEvents(FUSE_WENT_OFF); } } - oldFuseState = state; + oldFuseState = state.value; } float Fuse::getPower() { if (power.isValid()) { - return power; + return power.value; } else { return 0.0; } diff --git a/power/Fuse.h b/power/Fuse.h index 279642be..e9e9290b 100644 --- a/power/Fuse.h +++ b/power/Fuse.h @@ -1,16 +1,16 @@ -#ifndef FUSE_H_ -#define FUSE_H_ +#ifndef FSFW_POWER_FUSE_H_ +#define FSFW_POWER_FUSE_H_ -#include "../datapool/DataSet.h" -#include "../datapool/PIDReader.h" -#include "../devicehandlers/HealthDevice.h" -#include "../monitoring/AbsLimitMonitor.h" #include "PowerComponentIF.h" #include "PowerSwitchIF.h" + +#include "../devicehandlers/HealthDevice.h" +#include "../monitoring/AbsLimitMonitor.h" #include "../returnvalues/HasReturnvaluesIF.h" #include "../parameters/ParameterHelper.h" #include +#include "../datapoollocal/StaticLocalDataSet.h" namespace Factory { void setStaticFrameworkObjectIds(); } @@ -25,10 +25,10 @@ private: static constexpr float RESIDUAL_POWER = 0.005 * 28.5; //!< This is the upper limit of residual power lost by fuses and switches. Worst case is Fuse and one of two switches on. See PCDU ICD 1.9 p29 bottom public: struct VariableIds { - uint32_t pidVoltage; - uint32_t pidCurrent; - uint32_t pidState; - uint32_t poolIdPower; + gp_id_t pidVoltage; + gp_id_t pidCurrent; + gp_id_t pidState; + gp_id_t poolIdPower; }; static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::PCDU_1; @@ -38,8 +38,8 @@ public: static const Event POWER_BELOW_LOW_LIMIT = MAKE_EVENT(5, SEVERITY::LOW); //!< PSS detected a fuse that violates its limits. typedef std::list DeviceList; - Fuse(object_id_t fuseObjectId, uint8_t fuseId, VariableIds ids, - float maxCurrent, uint16_t confirmationCount = 2); + Fuse(object_id_t fuseObjectId, uint8_t fuseId, sid_t variableSet, + VariableIds ids, float maxCurrent, uint16_t confirmationCount = 2); virtual ~Fuse(); void addDevice(PowerComponentIF *set); float getPower(); @@ -69,12 +69,12 @@ public: private: uint8_t oldFuseState; uint8_t fuseId; - PowerSwitchIF *powerIF; //could be static in our case. + PowerSwitchIF *powerIF = nullptr; //could be static in our case. AbsLimitMonitor currentLimit; class PowerMonitor: public MonitorReporter { public: template - PowerMonitor(Args ... args) : + PowerMonitor(Args ... args): MonitorReporter(std::forward(args)...) { } ReturnValue_t checkPower(float sample, float lowerLimit, @@ -84,12 +84,17 @@ private: }; PowerMonitor powerMonitor; - DataSet set; - PIDReader voltage; - PIDReader current; - PIDReader state; - db_float_t power; - MessageQueueIF *commandQueue; + StaticLocalDataSet<3> set; + //LocalPoolDataSetBase* set = nullptr; + //PIDReader voltage; + //PIDReader current; + //PIDReader state; + lp_var_t voltage; + lp_var_t current; + lp_var_t state; + + lp_var_t power; + MessageQueueIF* commandQueue = nullptr; ParameterHelper parameterHelper; HealthHelper healthHelper; static object_id_t powerSwitchId; @@ -102,4 +107,4 @@ private: bool areSwitchesOfComponentOn(DeviceList::iterator iter); }; -#endif /* FUSE_H_ */ +#endif /* FSFW_POWER_FUSE_H_ */ diff --git a/power/PowerComponent.cpp b/power/PowerComponent.cpp index 6012ad4c..c31b9a85 100644 --- a/power/PowerComponent.cpp +++ b/power/PowerComponent.cpp @@ -1,20 +1,15 @@ -/** - * @file PowerComponent.cpp - * @brief This file defines the PowerComponent class. - * @date 28.08.2014 - * @author baetz - */ - #include "PowerComponent.h" +#include "../serialize/SerializeAdapter.h" -PowerComponent::PowerComponent() : - deviceObjectId(0), switchId1(0xFF), switchId2(0xFF), doIHaveTwoSwitches( - false), min(0.0), max(0.0), moduleId(0) { +PowerComponent::PowerComponent(): switchId1(0xFF), switchId2(0xFF), + doIHaveTwoSwitches(false) { } -PowerComponent::PowerComponent(object_id_t setId, uint8_t moduleId, float min, float max, - uint8_t switchId1, bool twoSwitches, uint8_t switchId2) : - deviceObjectId(setId), switchId1(switchId1), switchId2(switchId2), doIHaveTwoSwitches( - twoSwitches), min(min), max(max), moduleId(moduleId) { + +PowerComponent::PowerComponent(object_id_t setId, uint8_t moduleId, float min, + float max, uint8_t switchId1, bool twoSwitches, uint8_t switchId2) : + deviceObjectId(setId), switchId1(switchId1), switchId2(switchId2), + doIHaveTwoSwitches(twoSwitches), min(min), max(max), + moduleId(moduleId) { } ReturnValue_t PowerComponent::serialize(uint8_t** buffer, size_t* size, @@ -57,7 +52,7 @@ float PowerComponent::getMax() { } ReturnValue_t PowerComponent::deSerialize(const uint8_t** buffer, size_t* size, -Endianness streamEndianness) { + Endianness streamEndianness) { ReturnValue_t result = SerializeAdapter::deSerialize(&min, buffer, size, streamEndianness); if (result != HasReturnvaluesIF::RETURN_OK) { @@ -80,7 +75,7 @@ ReturnValue_t PowerComponent::getParameter(uint8_t domainId, parameterWrapper->set<>(max); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } diff --git a/power/PowerComponent.h b/power/PowerComponent.h index 6d1c9c06..c1add3b9 100644 --- a/power/PowerComponent.h +++ b/power/PowerComponent.h @@ -1,13 +1,17 @@ -#ifndef POWERCOMPONENT_H_ -#define POWERCOMPONENT_H_ +#ifndef FSFW_POWER_POWERCOMPONENT_H_ +#define FSFW_POWER_POWERCOMPONENT_H_ -#include "../objectmanager/SystemObjectIF.h" #include "PowerComponentIF.h" +#include "../objectmanager/frameworkObjects.h" +#include "../objectmanager/SystemObjectIF.h" + + class PowerComponent: public PowerComponentIF { public: - PowerComponent(object_id_t setId, uint8_t moduleId, float min, float max, uint8_t switchId1, - bool twoSwitches = false, uint8_t switchId2 = 0xFF); + PowerComponent(object_id_t setId, uint8_t moduleId, float min, float max, + uint8_t switchId1, bool twoSwitches = false, + uint8_t switchId2 = 0xFF); virtual object_id_t getDeviceObjectId(); @@ -31,18 +35,18 @@ public: ParameterWrapper *parameterWrapper, const ParameterWrapper *newValues, uint16_t startAtIndex); private: - const object_id_t deviceObjectId; + const object_id_t deviceObjectId = objects::NO_OBJECT; const uint8_t switchId1; const uint8_t switchId2; const bool doIHaveTwoSwitches; - float min; - float max; + float min = 0.0; + float max = 0.0; - uint8_t moduleId; + uint8_t moduleId = 0; PowerComponent(); }; -#endif /* POWERCOMPONENT_H_ */ +#endif /* FSFW_POWER_POWERCOMPONENT_H_ */ diff --git a/power/PowerComponentIF.h b/power/PowerComponentIF.h index c2e3a6a5..f35b4d1d 100644 --- a/power/PowerComponentIF.h +++ b/power/PowerComponentIF.h @@ -1,24 +1,23 @@ -#ifndef POWERCOMPONENTIF_H_ -#define POWERCOMPONENTIF_H_ +#ifndef FSFW_POWER_POWERCOMPONENTIF_H_ +#define FSFW_POWER_POWERCOMPONENTIF_H_ #include "../serialize/SerializeIF.h" #include "../parameters/HasParametersIF.h" +#include "../objectmanager/SystemObjectIF.h" class PowerComponentIF : public SerializeIF, public HasParametersIF { public: - virtual ~PowerComponentIF() { + virtual ~PowerComponentIF() {} - } + virtual object_id_t getDeviceObjectId() = 0; - virtual object_id_t getDeviceObjectId()=0; - - virtual uint8_t getSwitchId1()=0; - virtual uint8_t getSwitchId2()=0; - virtual bool hasTwoSwitches()=0; + virtual uint8_t getSwitchId1() = 0; + virtual uint8_t getSwitchId2() = 0; + virtual bool hasTwoSwitches() = 0; virtual float getMin() = 0; virtual float getMax() = 0; }; -#endif /* POWERCOMPONENTIF_H_ */ +#endif /* FSFW_POWER_POWERCOMPONENTIF_H_ */ diff --git a/power/PowerSensor.cpp b/power/PowerSensor.cpp index 50cb6acd..1ef041e3 100644 --- a/power/PowerSensor.cpp +++ b/power/PowerSensor.cpp @@ -1,14 +1,18 @@ #include "PowerSensor.h" + #include "../ipc/QueueFactory.h" -PowerSensor::PowerSensor(object_id_t setId, VariableIds ids, +PowerSensor::PowerSensor(object_id_t objectId, sid_t setId, VariableIds ids, DefaultLimits limits, SensorEvents events, uint16_t confirmationCount) : - SystemObject(setId), commandQueue(NULL), parameterHelper(this), healthHelper(this, setId), set(), current( - ids.pidCurrent, &set), voltage(ids.pidVoltage, &set), power( - ids.poolIdPower, &set, PoolVariableIF::VAR_WRITE), currentLimit( - setId, MODULE_ID_CURRENT, ids.pidCurrent, confirmationCount, + SystemObject(objectId), parameterHelper(this), + healthHelper(this, objectId), + powerSensorSet(setId), current(ids.pidCurrent, &powerSensorSet), + voltage(ids.pidVoltage, &powerSensorSet), + power(ids.poolIdPower, &powerSensorSet, PoolVariableIF::VAR_WRITE), + currentLimit(objectId, MODULE_ID_CURRENT, ids.pidCurrent, confirmationCount, limits.currentMin, limits.currentMax, events.currentLow, - events.currentHigh), voltageLimit(setId, MODULE_ID_VOLTAGE, + events.currentHigh), + voltageLimit(objectId, MODULE_ID_VOLTAGE, ids.pidVoltage, confirmationCount, limits.voltageMin, limits.voltageMax, events.voltageLow, events.voltageHigh) { commandQueue = QueueFactory::instance()->createMessageQueue(); @@ -19,13 +23,13 @@ PowerSensor::~PowerSensor() { } ReturnValue_t PowerSensor::calculatePower() { - set.read(); + powerSensorSet.read(); ReturnValue_t result1 = HasReturnvaluesIF::RETURN_FAILED; ReturnValue_t result2 = HasReturnvaluesIF::RETURN_FAILED; if (healthHelper.healthTable->isHealthy(getObjectId()) && voltage.isValid() && current.isValid()) { - result1 = voltageLimit.doCheck(voltage); - result2 = currentLimit.doCheck(current); + result1 = voltageLimit.doCheck(voltage.value); + result2 = currentLimit.doCheck(current.value); } else { voltageLimit.setToInvalid(); currentLimit.setToInvalid(); @@ -37,9 +41,9 @@ ReturnValue_t PowerSensor::calculatePower() { power.setValid(PoolVariableIF::INVALID); } else { power.setValid(PoolVariableIF::VALID); - power = current * voltage; + power.value = current.value * voltage.value; } - set.commit(); + powerSensorSet.commit(); return result1; } @@ -92,8 +96,8 @@ void PowerSensor::checkCommandQueue() { } void PowerSensor::setDataPoolEntriesInvalid() { - set.read(); - set.commit(PoolVariableIF::INVALID); + powerSensorSet.read(); + powerSensorSet.commit(PoolVariableIF::INVALID); } float PowerSensor::getPower() { diff --git a/power/PowerSensor.h b/power/PowerSensor.h index 0f973e45..a0ccb1ca 100644 --- a/power/PowerSensor.h +++ b/power/PowerSensor.h @@ -1,9 +1,7 @@ -#ifndef POWERSENSOR_H_ -#define POWERSENSOR_H_ +#ifndef FSFW_POWER_POWERSENSOR_H_ +#define FSFW_POWER_POWERSENSOR_H_ -#include "../datapool/DataSet.h" -#include "../datapool/PIDReader.h" -#include "../datapool/PoolVariable.h" +#include "../datapoollocal/StaticLocalDataSet.h" #include "../devicehandlers/HealthDevice.h" #include "../monitoring/LimitMonitor.h" #include "../parameters/ParameterHelper.h" @@ -12,15 +10,18 @@ class PowerController; +/** + * @brief Does magic. + */ class PowerSensor: public SystemObject, public ReceivesParameterMessagesIF, public HasHealthIF { friend class PowerController; public: struct VariableIds { - uint32_t pidCurrent; - uint32_t pidVoltage; - uint32_t poolIdPower; + gp_id_t pidCurrent; + gp_id_t pidVoltage; + gp_id_t poolIdPower; }; struct DefaultLimits { float currentMin; @@ -34,8 +35,9 @@ public: Event voltageLow; Event voltageHigh; }; - PowerSensor(object_id_t setId, VariableIds setIds, DefaultLimits limits, - SensorEvents events, uint16_t confirmationCount = 0); + PowerSensor(object_id_t objectId, sid_t sid, VariableIds setIds, + DefaultLimits limits, SensorEvents events, + uint16_t confirmationCount = 0); virtual ~PowerSensor(); ReturnValue_t calculatePower(); ReturnValue_t performOperation(uint8_t opCode); @@ -50,15 +52,19 @@ public: ParameterWrapper *parameterWrapper, const ParameterWrapper *newValues, uint16_t startAtIndex); private: - MessageQueueIF* commandQueue; + MessageQueueIF* commandQueue = nullptr; ParameterHelper parameterHelper; HealthHelper healthHelper; - DataSet set; + //GlobDataSet set; + StaticLocalDataSet<3> powerSensorSet; //Variables in - PIDReader current; - PIDReader voltage; + lp_var_t current; + lp_var_t voltage; + //PIDReader current; + //PIDReader voltage; //Variables out - db_float_t power; + lp_var_t power; + //gp_float_t power; static const uint8_t MODULE_ID_CURRENT = 1; static const uint8_t MODULE_ID_VOLTAGE = 2; @@ -68,4 +74,4 @@ protected: LimitMonitor voltageLimit; }; -#endif /* POWERSENSOR_H_ */ +#endif /* FSFW_POWER_POWERSENSOR_H_ */ diff --git a/power/PowerSwitchIF.h b/power/PowerSwitchIF.h index 40220fb6..1422baeb 100644 --- a/power/PowerSwitchIF.h +++ b/power/PowerSwitchIF.h @@ -1,18 +1,16 @@ -/** - * @file PowerSwitchIF.h - * @brief This file defines the PowerSwitchIF class. - * @date 20.03.2013 - * @author baetz - */ - -#ifndef POWERSWITCHIF_H_ -#define POWERSWITCHIF_H_ +#ifndef FSFW_POWER_POWERSWITCHIF_H_ +#define FSFW_POWER_POWERSWITCHIF_H_ #include "../events/Event.h" #include "../returnvalues/HasReturnvaluesIF.h" /** - * This interface defines a connection to a device that is capable of turning on and off - * switches of devices identified by a switch ID. + * + * @brief This interface defines a connection to a device that is capable of + * turning on and off switches of devices identified by a switch ID. + * @details + * The virtual functions of this interface do not allow to make any assignments + * because they can be called asynchronosuly (const ending). + * @ingroup interfaces */ class PowerSwitchIF : public HasReturnvaluesIF { public: @@ -72,4 +70,4 @@ public: }; -#endif /* POWERSWITCHIF_H_ */ +#endif /* FSFW_POWER_POWERSWITCHIF_H_ */ diff --git a/power/PowerSwitcher.cpp b/power/PowerSwitcher.cpp index 6296a04c..ed37998e 100644 --- a/power/PowerSwitcher.cpp +++ b/power/PowerSwitcher.cpp @@ -1,15 +1,17 @@ -#include "../objectmanager/ObjectManagerIF.h" #include "PowerSwitcher.h" + +#include "../objectmanager/ObjectManagerIF.h" #include "../serviceinterface/ServiceInterfaceStream.h" PowerSwitcher::PowerSwitcher(uint8_t setSwitch1, uint8_t setSwitch2, - PowerSwitcher::State_t setStartState) : - state(setStartState), firstSwitch(setSwitch1), secondSwitch(setSwitch2), power(NULL) { + PowerSwitcher::State_t setStartState): + state(setStartState), firstSwitch(setSwitch1), + secondSwitch(setSwitch2) { } ReturnValue_t PowerSwitcher::initialize(object_id_t powerSwitchId) { power = objectManager->get(powerSwitchId); - if (power == NULL) { + if (power == nullptr) { return HasReturnvaluesIF::RETURN_FAILED; } return HasReturnvaluesIF::RETURN_OK; @@ -17,19 +19,25 @@ ReturnValue_t PowerSwitcher::initialize(object_id_t powerSwitchId) { ReturnValue_t PowerSwitcher::getStateOfSwitches() { SwitchReturn_t result = howManySwitches(); + switch (result) { case ONE_SWITCH: return power->getSwitchState(firstSwitch); - case TWO_SWITCHES: - if ((power->getSwitchState(firstSwitch) == PowerSwitchIF::SWITCH_ON) - && (power->getSwitchState(secondSwitch) == PowerSwitchIF::SWITCH_ON)) { + case TWO_SWITCHES: { + ReturnValue_t firstSwitchState = power->getSwitchState(firstSwitch); + ReturnValue_t secondSwitchState = power->getSwitchState(firstSwitch); + if ((firstSwitchState == PowerSwitchIF::SWITCH_ON) + && (secondSwitchState == PowerSwitchIF::SWITCH_ON)) { return PowerSwitchIF::SWITCH_ON; - } else if ((power->getSwitchState(firstSwitch) == PowerSwitchIF::SWITCH_OFF) - && (power->getSwitchState(secondSwitch) == PowerSwitchIF::SWITCH_OFF)) { + } + else if ((firstSwitchState == PowerSwitchIF::SWITCH_OFF) + && (secondSwitchState == PowerSwitchIF::SWITCH_OFF)) { return PowerSwitchIF::SWITCH_OFF; - } else { + } + else { return HasReturnvaluesIF::RETURN_FAILED; } + } default: return HasReturnvaluesIF::RETURN_FAILED; } diff --git a/power/PowerSwitcher.h b/power/PowerSwitcher.h index 0f1c02de..f4e2138d 100644 --- a/power/PowerSwitcher.h +++ b/power/PowerSwitcher.h @@ -1,10 +1,13 @@ -#ifndef POWERSWITCHER_H_ -#define POWERSWITCHER_H_ +#ifndef FSFW_POWER_POWERSWITCHER_H_ +#define FSFW_POWER_POWERSWITCHER_H_ + #include "PowerSwitchIF.h" + +#include "../objectmanager/SystemObjectIF.h" #include "../returnvalues/HasReturnvaluesIF.h" #include "../timemanager/Countdown.h" -class PowerSwitcher : public HasReturnvaluesIF { +class PowerSwitcher: public HasReturnvaluesIF { public: enum State_t { WAIT_OFF, @@ -16,7 +19,8 @@ public: static const uint8_t INTERFACE_ID = CLASS_ID::POWER_SWITCHER; static const ReturnValue_t IN_POWER_TRANSITION = MAKE_RETURN_CODE(1); static const ReturnValue_t SWITCH_STATE_MISMATCH = MAKE_RETURN_CODE(2); - PowerSwitcher( uint8_t setSwitch1, uint8_t setSwitch2 = NO_SWITCH, State_t setStartState = SWITCH_IS_OFF ); + PowerSwitcher( uint8_t setSwitch1, uint8_t setSwitch2 = NO_SWITCH, + State_t setStartState = SWITCH_IS_OFF ); ReturnValue_t initialize(object_id_t powerSwitchId); void turnOn(); void turnOff(); @@ -29,7 +33,8 @@ public: private: uint8_t firstSwitch; uint8_t secondSwitch; - PowerSwitchIF* power; + PowerSwitchIF* power = nullptr; + static const uint8_t NO_SWITCH = 0xFF; enum SwitchReturn_t { ONE_SWITCH = 1, @@ -42,4 +47,4 @@ private: -#endif /* POWERSWITCHER_H_ */ +#endif /* FSFW_POWER_POWERSWITCHER_H_ */ From 64cf0d0a7028313a5f5ad9429d9738964902762e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 3 Dec 2020 18:32:32 +0100 Subject: [PATCH 027/103] thermal update --- thermal/AbstractTemperatureSensor.cpp | 12 +- thermal/AbstractTemperatureSensor.h | 10 + thermal/AcceptsThermalMessagesIF.h | 22 ++ thermal/Heater.cpp | 10 +- thermal/RedundantHeater.h | 13 +- thermal/TemperatureSensor.h | 138 +++++++++---- thermal/ThermalComponent.cpp | 59 +++--- thermal/ThermalComponent.h | 49 ++++- thermal/ThermalComponentCore.cpp | 285 ++++++++++++++++++++++++++ thermal/ThermalComponentCore.h | 117 +++++++++++ thermal/ThermalComponentIF.h | 12 +- thermal/ThermalModule.cpp | 84 ++++---- thermal/ThermalModule.h | 49 +++-- thermal/ThermalMonitorReporter.cpp | 75 +++++++ thermal/ThermalMonitorReporter.h | 28 +++ thermal/tcsDefinitions.h | 2 +- 16 files changed, 796 insertions(+), 169 deletions(-) create mode 100644 thermal/AcceptsThermalMessagesIF.h create mode 100644 thermal/ThermalComponentCore.cpp create mode 100644 thermal/ThermalComponentCore.h create mode 100644 thermal/ThermalMonitorReporter.cpp create mode 100644 thermal/ThermalMonitorReporter.h diff --git a/thermal/AbstractTemperatureSensor.cpp b/thermal/AbstractTemperatureSensor.cpp index 45ebe4a2..40b305af 100644 --- a/thermal/AbstractTemperatureSensor.cpp +++ b/thermal/AbstractTemperatureSensor.cpp @@ -44,19 +44,19 @@ ReturnValue_t AbstractTemperatureSensor::performHealthOp() { } void AbstractTemperatureSensor::handleCommandQueue() { - CommandMessage message; - ReturnValue_t result = commandQueue->receiveMessage(&message); + CommandMessage command; + ReturnValue_t result = commandQueue->receiveMessage(&command); if (result == HasReturnvaluesIF::RETURN_OK) { - result = healthHelper.handleHealthCommand(&message); + result = healthHelper.handleHealthCommand(&command); if (result == HasReturnvaluesIF::RETURN_OK) { return; } - result = parameterHelper.handleParameterMessage(&message); + result = parameterHelper.handleParameterMessage(&command); if (result == HasReturnvaluesIF::RETURN_OK) { return; } - message.setToUnknownCommand(); - commandQueue->reply(&message); + command.setToUnknownCommand(); + commandQueue->reply(&command); } } diff --git a/thermal/AbstractTemperatureSensor.h b/thermal/AbstractTemperatureSensor.h index 726ab9f4..cc064ce4 100644 --- a/thermal/AbstractTemperatureSensor.h +++ b/thermal/AbstractTemperatureSensor.h @@ -10,6 +10,16 @@ #include "ThermalModuleIF.h" #include "tcsDefinitions.h" +/** + * @defgroup thermal Thermal Components + * @brief Contains all components related to thermal tasks (sensors, heaters) + */ + +/** + * @brief Base class for Temperature Sensor, implements all important interfaces. + * Please use the TemperatureSensor class to implement the actual sensors. + * @ingroup thermal + */ class AbstractTemperatureSensor: public HasHealthIF, public SystemObject, public ExecutableObjectIF, diff --git a/thermal/AcceptsThermalMessagesIF.h b/thermal/AcceptsThermalMessagesIF.h new file mode 100644 index 00000000..5fbd6bb3 --- /dev/null +++ b/thermal/AcceptsThermalMessagesIF.h @@ -0,0 +1,22 @@ +/** + * \file AcceptsThermalMessagesIF.h + * + * \date 16.02.2020 + */ + +#ifndef FRAMEWORK_THERMAL_ACCEPTSTHERMALMESSAGESIF_H_ +#define FRAMEWORK_THERMAL_ACCEPTSTHERMALMESSAGESIF_H_ +#include "../ipc/MessageQueueSenderIF.h" + +class AcceptsThermalMessagesIF { +public: + + /** + * @brief This is the empty virtual destructor as required for C++ interfaces. + */ + virtual ~AcceptsThermalMessagesIF() { } + + virtual MessageQueueId_t getReceptionQueue() const = 0; +}; + +#endif /* FRAMEWORK_THERMAL_ACCEPTSTHERMALMESSAGESIF_H_ */ diff --git a/thermal/Heater.cpp b/thermal/Heater.cpp index 1301e2e0..ce965d5e 100644 --- a/thermal/Heater.cpp +++ b/thermal/Heater.cpp @@ -279,14 +279,14 @@ ReturnValue_t Heater::initialize() { } void Heater::handleQueue() { - CommandMessage message; - ReturnValue_t result = commandQueue->receiveMessage(&message); + CommandMessage command; + ReturnValue_t result = commandQueue->receiveMessage(&command); if (result == HasReturnvaluesIF::RETURN_OK) { - result = healthHelper.handleHealthCommand(&message); + result = healthHelper.handleHealthCommand(&command); if (result == HasReturnvaluesIF::RETURN_OK) { return; } - parameterHelper.handleParameterMessage(&message); + parameterHelper.handleParameterMessage(&command); } } @@ -301,7 +301,7 @@ ReturnValue_t Heater::getParameter(uint8_t domainId, uint16_t parameterId, parameterWrapper->set(heaterOnCountdown.timeout); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } diff --git a/thermal/RedundantHeater.h b/thermal/RedundantHeater.h index ab745a69..76537542 100644 --- a/thermal/RedundantHeater.h +++ b/thermal/RedundantHeater.h @@ -1,7 +1,7 @@ #ifndef REDUNDANTHEATER_H_ #define REDUNDANTHEATER_H_ -#include "Heater.h" +#include "../thermal/Heater.h" class RedundantHeater { public: @@ -10,15 +10,14 @@ public: Parameters(uint32_t objectIdHeater0, uint32_t objectIdHeater1, uint8_t switch0Heater0, uint8_t switch1Heater0, uint8_t switch0Heater1, uint8_t switch1Heater1) : - objectIdHeater0(objectIdHeater0), objectIdHeater1( - objectIdHeater1), switch0Heater0(switch0Heater0), switch1Heater0( - switch1Heater0), switch0Heater1(switch0Heater1), switch1Heater1( - switch1Heater1) { + objectIdHeater0(objectIdHeater0), objectIdHeater1(objectIdHeater1), + switch0Heater0(switch0Heater0),switch1Heater0(switch1Heater0), + switch0Heater1(switch0Heater1), switch1Heater1(switch1Heater1) { } Parameters() : - objectIdHeater0(0), objectIdHeater1(0), switch0Heater0(0), switch1Heater0( - 0), switch0Heater1(0), switch1Heater1(0) { + objectIdHeater0(0), objectIdHeater1(0), switch0Heater0(0), + switch1Heater0(0), switch0Heater1(0), switch1Heater1(0) { } uint32_t objectIdHeater0; diff --git a/thermal/TemperatureSensor.h b/thermal/TemperatureSensor.h index 356ca722..f41b3761 100644 --- a/thermal/TemperatureSensor.h +++ b/thermal/TemperatureSensor.h @@ -1,40 +1,101 @@ #ifndef TEMPERATURESENSOR_H_ #define TEMPERATURESENSOR_H_ -#include "../datapool/DataSet.h" -#include "AbstractTemperatureSensor.h" +#include "../thermal/AbstractTemperatureSensor.h" +#include "../datapoolglob/GlobalDataSet.h" +#include "../datapoolglob/GlobalPoolVariable.h" #include "../monitoring/LimitMonitor.h" -template +/** + * @brief This building block handles non-linear value conversion and + * range checks for analog temperature sensors. + * @details This class can be used to perform all necessary tasks for temperature sensors. + * A sensor can be instantiated by calling the constructor. + * The temperature is calculated from an input value with + * the calculateOutputTemperature() function. Range checking and + * limit monitoring is performed automatically. + * The inputType specifies the type of the raw input while the + * limitType specifies the type of the upper and lower limit to check against. + * @ingroup thermal + */ + +template class TemperatureSensor: public AbstractTemperatureSensor { public: + /** + * This structure contains parameters required for range checking + * and the conversion from the input value to the output temperature. + * a, b and c can be any parameters required to calculate the output + * temperature from the input value, depending on the formula used. + * + * The parameters a,b and c are used in the calculateOutputTemperature() call. + * + * The lower and upper limits can be specified in any type, for example float for C values + * or any other type for raw values. + */ struct Parameters { float a; float b; float c; - T lowerLimit; - T upperLimit; - float gradient; + limitType lowerLimit; + limitType upperLimit; + float maxGradient; }; + + /** + * Forward declaration for explicit instantiation of used parameters. + */ struct UsedParameters { UsedParameters(Parameters parameters) : - a(parameters.a), b(parameters.b), c(parameters.c), gradient( - parameters.gradient) { - } + a(parameters.a), b(parameters.b), c(parameters.c), + gradient(parameters.maxGradient) {} float a; float b; float c; float gradient; }; - static const uint16_t ADDRESS_A = 0; - static const uint16_t ADDRESS_B = 1; - static const uint16_t ADDRESS_C = 2; - static const uint16_t ADDRESS_GRADIENT = 3; + /** + * Instantiate Temperature Sensor Object. + * @param setObjectid objectId of the sensor object + * @param inputValue Input value which is converted to a temperature + * @param poolVariable Pool Variable to store the temperature value + * @param vectorIndex Vector Index for the sensor monitor + * @param parameters Calculation parameters, temperature limits, gradient limit + * @param datapoolId Datapool ID of the output temperature + * @param outputSet Output dataset for the output temperature to fetch it with read() + * @param thermalModule respective thermal module, if it has one + */ + TemperatureSensor(object_id_t setObjectid, + inputType *inputValue, PoolVariableIF *poolVariable, + uint8_t vectorIndex, uint32_t datapoolId, Parameters parameters = {0, 0, 0, 0, 0, 0}, + GlobDataSet *outputSet = NULL, ThermalModuleIF *thermalModule = NULL) : + AbstractTemperatureSensor(setObjectid, thermalModule), parameters(parameters), + inputValue(inputValue), poolVariable(poolVariable), + outputTemperature(datapoolId, outputSet, PoolVariableIF::VAR_WRITE), + sensorMonitor(setObjectid, DOMAIN_ID_SENSOR, + GlobalDataPool::poolIdAndPositionToPid(poolVariable->getDataPoolId(), vectorIndex), + DEFAULT_CONFIRMATION_COUNT, parameters.lowerLimit, parameters.upperLimit, + TEMP_SENSOR_LOW, TEMP_SENSOR_HIGH), + oldTemperature(20), uptimeOfOldTemperature( { INVALID_TEMPERATURE, 0 }) { + } + + +protected: + /** + * This formula is used to calculate the temperature from an input value + * with an arbitrary type. + * A default implementation is provided but can be replaced depending + * on the required calculation. + * @param inputTemperature + * @return + */ + virtual float calculateOutputTemperature(inputType inputValue) { + return parameters.a * inputValue * inputValue + + parameters.b * inputValue + parameters.c; + } - static const uint16_t DEFAULT_CONFIRMATION_COUNT = 1; //!< Changed due to issue with later temperature checking even tough the sensor monitor was confirming already (Was 10 before with comment = Correlates to a 10s confirmation time. Chosen rather large, should not be so bad for components and helps survive glitches.) - static const uint8_t DOMAIN_ID_SENSOR = 1; private: void setInvalid() { outputTemperature = INVALID_TEMPERATURE; @@ -47,22 +108,17 @@ protected: UsedParameters parameters; - T *inputTemperature; + inputType * inputValue; PoolVariableIF *poolVariable; - PoolVariable outputTemperature; + gp_float_t outputTemperature; - LimitMonitor sensorMonitor; + LimitMonitor sensorMonitor; float oldTemperature; timeval uptimeOfOldTemperature; - virtual float calculateOutputTemperature(T inputTemperature) { - return parameters.a * inputTemperature * inputTemperature - + parameters.b * inputTemperature + parameters.c; - } - void doChildOperation() { if (!poolVariable->isValid() || !healthHelper.healthTable->isHealthy(getObjectId())) { @@ -70,7 +126,7 @@ protected: return; } - outputTemperature = calculateOutputTemperature(*inputTemperature); + outputTemperature = calculateOutputTemperature(*inputValue); outputTemperature.setValid(PoolVariableIF::VALID); timeval uptime; @@ -78,7 +134,7 @@ protected: if (uptimeOfOldTemperature.tv_sec != INVALID_UPTIME) { //In theory, we could use an AbsValueMonitor to monitor the gradient. - //But this would require storing the gradient in DP and quite some overhead. + //But this would require storing the maxGradient in DP and quite some overhead. //The concept of delta limits is a bit strange anyway. float deltaTime; float deltaTemp; @@ -96,8 +152,8 @@ protected: } } - //Check is done against raw limits. SHOULDDO: Why? Using °C would be more easy to handle. - sensorMonitor.doCheck(*inputTemperature); + //Check is done against raw limits. SHOULDDO: Why? Using �C would be more easy to handle. + sensorMonitor.doCheck(outputTemperature.value); if (sensorMonitor.isOutOfLimits()) { uptimeOfOldTemperature.tv_sec = INVALID_UPTIME; @@ -110,23 +166,6 @@ protected: } public: - TemperatureSensor(object_id_t setObjectid, - T *inputTemperature, PoolVariableIF *poolVariable, - uint8_t vectorIndex, Parameters parameters, uint32_t datapoolId, - DataSet *outputSet, ThermalModuleIF *thermalModule) : - AbstractTemperatureSensor(setObjectid, thermalModule), parameters( - parameters), inputTemperature(inputTemperature), poolVariable( - poolVariable), outputTemperature(datapoolId, outputSet, - PoolVariableIF::VAR_WRITE), sensorMonitor(setObjectid, - DOMAIN_ID_SENSOR, - DataPool::poolIdAndPositionToPid( - poolVariable->getDataPoolId(), vectorIndex), - DEFAULT_CONFIRMATION_COUNT, parameters.lowerLimit, - parameters.upperLimit, TEMP_SENSOR_LOW, TEMP_SENSOR_HIGH), oldTemperature( - 20), uptimeOfOldTemperature( { INVALID_TEMPERATURE, 0 }) { - - } - float getTemperature() { return outputTemperature; } @@ -135,6 +174,15 @@ public: return outputTemperature.isValid(); } + static const uint16_t ADDRESS_A = 0; + static const uint16_t ADDRESS_B = 1; + static const uint16_t ADDRESS_C = 2; + static const uint16_t ADDRESS_GRADIENT = 3; + + static const uint16_t DEFAULT_CONFIRMATION_COUNT = 1; //!< Changed due to issue with later temperature checking even tough the sensor monitor was confirming already (Was 10 before with comment = Correlates to a 10s confirmation time. Chosen rather large, should not be so bad for components and helps survive glitches.) + + static const uint8_t DOMAIN_ID_SENSOR = 1; + virtual ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, ParameterWrapper *parameterWrapper, const ParameterWrapper *newValues, uint16_t startAtIndex) { @@ -160,7 +208,7 @@ public: parameterWrapper->set(parameters.gradient); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } diff --git a/thermal/ThermalComponent.cpp b/thermal/ThermalComponent.cpp index 5dcd0bc6..084201dd 100644 --- a/thermal/ThermalComponent.cpp +++ b/thermal/ThermalComponent.cpp @@ -1,48 +1,46 @@ #include "ThermalComponent.h" ThermalComponent::ThermalComponent(object_id_t reportingObjectId, - uint8_t domainId, uint32_t temperaturePoolId, - uint32_t targetStatePoolId, uint32_t currentStatePoolId, - uint32_t requestPoolId, DataSet* dataSet, + uint8_t domainId, gp_id_t temperaturePoolId, + gp_id_t targetStatePoolId, gp_id_t currentStatePoolId, + gp_id_t requestPoolId, LocalPoolDataSetBase* dataSet, AbstractTemperatureSensor* sensor, AbstractTemperatureSensor* firstRedundantSensor, AbstractTemperatureSensor* secondRedundantSensor, ThermalModuleIF* thermalModule, Parameters parameters, Priority priority) : - CoreComponent(reportingObjectId, domainId, temperaturePoolId, + ThermalComponentCore(reportingObjectId, domainId, temperaturePoolId, targetStatePoolId, currentStatePoolId, requestPoolId, dataSet, - sensor, firstRedundantSensor, secondRedundantSensor, - thermalModule, { parameters.lowerOpLimit, parameters.upperOpLimit, - parameters.heaterOn, parameters.hysteresis, - parameters.heaterSwitchoff }, priority, - ThermalComponentIF::STATE_REQUEST_NON_OPERATIONAL), nopParameters( - { parameters.lowerNopLimit, parameters.upperNopLimit }) { + parameters.heaterOn, parameters.hysteresis, + parameters.heaterSwitchoff }, + ThermalComponentIF::STATE_REQUEST_NON_OPERATIONAL), + nopParameters({ parameters.lowerNopLimit, parameters.upperNopLimit }) { } ThermalComponent::~ThermalComponent() { } ReturnValue_t ThermalComponent::setTargetState(int8_t newState) { - DataSet mySet; - PoolVariable writableTargetState(targetState.getDataPoolId(), - &mySet, PoolVariableIF::VAR_READ_WRITE); - mySet.read(); - if ((writableTargetState == STATE_REQUEST_OPERATIONAL) - && (newState != STATE_REQUEST_IGNORE)) { + targetState.setReadWriteMode(pool_rwm_t::VAR_READ_WRITE); + targetState.read(); + if ((targetState == STATE_REQUEST_OPERATIONAL) + and (newState != STATE_REQUEST_IGNORE)) { return HasReturnvaluesIF::RETURN_FAILED; } switch (newState) { case STATE_REQUEST_NON_OPERATIONAL: - writableTargetState = newState; - mySet.commit(PoolVariableIF::VALID); + targetState = newState; + targetState.setValid(true); + targetState.commit(PoolVariableIF::VALID); return HasReturnvaluesIF::RETURN_OK; default: - return CoreComponent::setTargetState(newState); + return ThermalComponentCore::setTargetState(newState); } + return HasReturnvaluesIF::RETURN_OK; } -ReturnValue_t ThermalComponent::setLimits(const uint8_t* data, uint32_t size) { +ReturnValue_t ThermalComponent::setLimits(const uint8_t* data, size_t size) { if (size != 4 * sizeof(parameters.lowerOpLimit)) { return MonitoringIF::INVALID_SIZE; } @@ -59,11 +57,11 @@ ReturnValue_t ThermalComponent::setLimits(const uint8_t* data, uint32_t size) { } ThermalComponentIF::State ThermalComponent::getState(float temperature, - CoreComponent::Parameters parameters, int8_t targetState) { + ThermalComponentCore::Parameters parameters, int8_t targetState) { if (temperature < nopParameters.lowerNopLimit) { return OUT_OF_RANGE_LOW; } else { - State state = CoreComponent::getState(temperature, parameters, + State state = ThermalComponentCore::getState(temperature, parameters, targetState); if (state != NON_OPERATIONAL_HIGH && state != NON_OPERATIONAL_HIGH_IGNORED) { @@ -80,18 +78,19 @@ ThermalComponentIF::State ThermalComponent::getState(float temperature, } void ThermalComponent::checkLimits(ThermalComponentIF::State state) { - if (targetState == STATE_REQUEST_OPERATIONAL || targetState == STATE_REQUEST_IGNORE) { - CoreComponent::checkLimits(state); + if ((targetState == STATE_REQUEST_OPERATIONAL) or + (targetState == STATE_REQUEST_IGNORE)) { + ThermalComponentCore::checkLimits(state); return; } - //If component is not operational, it checks the NOP limits. + // If component is not operational, it checks the NOP limits. temperatureMonitor.translateState(state, temperature.value, nopParameters.lowerNopLimit, nopParameters.upperNopLimit, false); } ThermalComponentIF::HeaterRequest ThermalComponent::getHeaterRequest( int8_t targetState, float temperature, - CoreComponent::Parameters parameters) { + ThermalComponentCore::Parameters parameters) { if (targetState == STATE_REQUEST_IGNORE) { isHeating = false; return HEATER_DONT_CARE; @@ -144,16 +143,16 @@ ThermalComponentIF::State ThermalComponent::getIgnoredState(int8_t state) { case OUT_OF_RANGE_HIGH_IGNORED: return OUT_OF_RANGE_HIGH_IGNORED; default: - return CoreComponent::getIgnoredState(state); + return ThermalComponentCore::getIgnoredState(state); } } ReturnValue_t ThermalComponent::getParameter(uint8_t domainId, uint16_t parameterId, ParameterWrapper* parameterWrapper, const ParameterWrapper* newValues, uint16_t startAtIndex) { - ReturnValue_t result = CoreComponent::getParameter(domainId, parameterId, + ReturnValue_t result = ThermalComponentCore::getParameter(domainId, parameterId, parameterWrapper, newValues, startAtIndex); - if (result != INVALID_MATRIX_ID) { + if (result != INVALID_IDENTIFIER_ID) { return result; } switch (parameterId) { @@ -164,7 +163,7 @@ ReturnValue_t ThermalComponent::getParameter(uint8_t domainId, parameterWrapper->set(nopParameters.upperNopLimit); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } diff --git a/thermal/ThermalComponent.h b/thermal/ThermalComponent.h index 93243868..0785a914 100644 --- a/thermal/ThermalComponent.h +++ b/thermal/ThermalComponent.h @@ -1,9 +1,14 @@ -#ifndef THERMALCOMPONENT_H_ -#define THERMALCOMPONENT_H_ +#ifndef FSFW_THERMAL_THERMALCOMPONENT_H_ +#define FSFW_THERMAL_THERMALCOMPONENT_H_ -#include "CoreComponent.h" +#include "ThermalComponentCore.h" -class ThermalComponent: public CoreComponent { +/** + * @brief + * @details + * Some more documentation. + */ +class ThermalComponent: public ThermalComponentCore { public: struct Parameters { float lowerNopLimit; @@ -14,13 +19,35 @@ public: float hysteresis; float heaterSwitchoff; }; + + /** + * Non-Operational Temperatures + */ struct NopParameters { float lowerNopLimit; float upperNopLimit; }; - ThermalComponent(object_id_t reportingObjectId, uint8_t domainId, uint32_t temperaturePoolId, - uint32_t targetStatePoolId, uint32_t currentStatePoolId, uint32_t requestPoolId, - DataSet *dataSet, AbstractTemperatureSensor *sensor, + + /** + * How to use. + * @param reportingObjectId + * @param domainId + * @param temperaturePoolId + * @param targetStatePoolId + * @param currentStatePoolId + * @param requestPoolId + * @param dataSet + * @param sensor + * @param firstRedundantSensor + * @param secondRedundantSensor + * @param thermalModule + * @param parameters + * @param priority + */ + ThermalComponent(object_id_t reportingObjectId, uint8_t domainId, + gp_id_t temperaturePoolId, gp_id_t targetStatePoolId, + gp_id_t currentStatePoolId, gp_id_t requestPoolId, + LocalPoolDataSetBase *dataSet, AbstractTemperatureSensor *sensor, AbstractTemperatureSensor *firstRedundantSensor, AbstractTemperatureSensor *secondRedundantSensor, ThermalModuleIF *thermalModule, Parameters parameters, @@ -29,7 +56,7 @@ public: ReturnValue_t setTargetState(int8_t newState); - virtual ReturnValue_t setLimits( const uint8_t* data, uint32_t size); + virtual ReturnValue_t setLimits( const uint8_t* data, size_t size); virtual ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, ParameterWrapper *parameterWrapper, @@ -39,15 +66,15 @@ protected: NopParameters nopParameters; - State getState(float temperature, CoreComponent::Parameters parameters, + State getState(float temperature, ThermalComponentCore::Parameters parameters, int8_t targetState); virtual void checkLimits(State state); virtual HeaterRequest getHeaterRequest(int8_t targetState, float temperature, - CoreComponent::Parameters parameters); + ThermalComponentCore::Parameters parameters); State getIgnoredState(int8_t state); }; -#endif /* THERMALCOMPONENT_H_ */ +#endif /* FSFW_THERMAL_THERMALCOMPONENT_H_ */ diff --git a/thermal/ThermalComponentCore.cpp b/thermal/ThermalComponentCore.cpp new file mode 100644 index 00000000..7b594d0c --- /dev/null +++ b/thermal/ThermalComponentCore.cpp @@ -0,0 +1,285 @@ +#include "ThermalComponentCore.h" + +ThermalComponentCore::ThermalComponentCore(object_id_t reportingObjectId, + uint8_t domainId, gp_id_t temperaturePoolId, + gp_id_t targetStatePoolId, gp_id_t currentStatePoolId, + gp_id_t requestPoolId, LocalPoolDataSetBase* dataSet, + Parameters parameters, StateRequest initialTargetState) : + temperature(temperaturePoolId, dataSet, PoolVariableIF::VAR_WRITE), + targetState(targetStatePoolId, dataSet, PoolVariableIF::VAR_READ), + currentState(currentStatePoolId, dataSet, PoolVariableIF::VAR_WRITE), + heaterRequest(requestPoolId, dataSet, PoolVariableIF::VAR_WRITE), + parameters(parameters), domainId(domainId), + temperatureMonitor(reportingObjectId, domainId + 1,temperaturePoolId, + COMPONENT_TEMP_CONFIRMATION) { + //Set thermal state once, then leave to operator. + targetState.setReadWriteMode(PoolVariableIF::VAR_WRITE); + ReturnValue_t result = targetState.read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + targetState = initialTargetState; + targetState.setValid(true); + targetState.commit(); + } + targetState.setReadWriteMode(PoolVariableIF::VAR_READ); +} + +void ThermalComponentCore::addSensor(AbstractTemperatureSensor* sensor) { + this->sensor = sensor; +} + +void ThermalComponentCore::addFirstRedundantSensor( + AbstractTemperatureSensor *firstRedundantSensor) { + this->firstRedundantSensor = firstRedundantSensor; +} + +void ThermalComponentCore::addSecondRedundantSensor( + AbstractTemperatureSensor *secondRedundantSensor) { + this->secondRedundantSensor = secondRedundantSensor; +} + +void ThermalComponentCore::addThermalModule(ThermalModule *thermalModule, + Priority priority) { + this->thermalModule = thermalModule; + if(thermalModule != nullptr) { + thermalModule->registerComponent(this, priority); + } +} + +void ThermalComponentCore::setPriority(Priority priority) { + if(priority == SAFE) { + this->isSafeComponent = true; + } +} + +ThermalComponentCore::~ThermalComponentCore() { +} + +ThermalComponentIF::HeaterRequest ThermalComponentCore::performOperation( + uint8_t opCode) { + HeaterRequest request = HEATER_DONT_CARE; + //SHOULDDO: Better pass db_float_t* to getTemperature and set it invalid if invalid. + temperature = getTemperature(); + updateMinMaxTemp(); + if (temperature != INVALID_TEMPERATURE) { + temperature.setValid(PoolVariableIF::VALID); + State state = getState(temperature.value, getParameters(), + targetState.value); + currentState = state; + checkLimits(state); + request = getHeaterRequest(targetState.value, temperature.value, + getParameters()); + } else { + temperatureMonitor.setToInvalid(); + temperature.setValid(PoolVariableIF::INVALID); + currentState = UNKNOWN; + request = HEATER_DONT_CARE; + } + currentState.setValid(PoolVariableIF::VALID); + heaterRequest = request; + heaterRequest.setValid(PoolVariableIF::VALID); + return request; +} + +void ThermalComponentCore::markStateIgnored() { + currentState = getIgnoredState(currentState.value); +} + +object_id_t ThermalComponentCore::getObjectId() { + return temperatureMonitor.getReporterId(); + return 0; +} + +float ThermalComponentCore::getLowerOpLimit() { + return parameters.lowerOpLimit; +} + + + +ReturnValue_t ThermalComponentCore::setTargetState(int8_t newState) { + targetState.setReadWriteMode(pool_rwm_t::VAR_READ_WRITE); + targetState.read(); + if((targetState == STATE_REQUEST_OPERATIONAL) and + (newState != STATE_REQUEST_IGNORE)) { + return HasReturnvaluesIF::RETURN_FAILED; + } + + switch (newState) { + case STATE_REQUEST_HEATING: + case STATE_REQUEST_IGNORE: + case STATE_REQUEST_OPERATIONAL: + targetState = newState; + break; + case STATE_REQUEST_NON_OPERATIONAL: + default: + return INVALID_TARGET_STATE; + } + targetState.setValid(true); + targetState.commit(); + return HasReturnvaluesIF::RETURN_OK; +} + +void ThermalComponentCore::setOutputInvalid() { + temperature = INVALID_TEMPERATURE; + temperature.setValid(PoolVariableIF::INVALID); + currentState.setValid(PoolVariableIF::INVALID); + heaterRequest = HEATER_DONT_CARE; + heaterRequest.setValid(PoolVariableIF::INVALID); + temperatureMonitor.setToUnchecked(); +} + +float ThermalComponentCore::getTemperature() { + if ((sensor != nullptr) && (sensor->isValid())) { + return sensor->getTemperature(); + } + + if ((firstRedundantSensor != nullptr) && + (firstRedundantSensor->isValid())) { + return firstRedundantSensor->getTemperature(); + } + + if ((secondRedundantSensor != nullptr) && + (secondRedundantSensor->isValid())) { + return secondRedundantSensor->getTemperature(); + } + + if (thermalModule != nullptr) { + float temperature = thermalModule->getTemperature(); + if (temperature != ThermalModuleIF::INVALID_TEMPERATURE) { + return temperature; + } else { + return INVALID_TEMPERATURE; + } + } else { + return INVALID_TEMPERATURE; + } +} + +ThermalComponentIF::State ThermalComponentCore::getState(float temperature, + Parameters parameters, int8_t targetState) { + ThermalComponentIF::State state; + + if (temperature < parameters.lowerOpLimit) { + state = NON_OPERATIONAL_LOW; + } else if (temperature < parameters.upperOpLimit) { + state = OPERATIONAL; + } else { + state = NON_OPERATIONAL_HIGH; + } + if (targetState == STATE_REQUEST_IGNORE) { + state = getIgnoredState(state); + } + + return state; +} + +void ThermalComponentCore::checkLimits(ThermalComponentIF::State state) { + //Checks operational limits only. + temperatureMonitor.translateState(state, temperature.value, + getParameters().lowerOpLimit, getParameters().upperOpLimit); + +} + +ThermalComponentIF::HeaterRequest ThermalComponentCore::getHeaterRequest( + int8_t targetState, float temperature, Parameters parameters) { + if (targetState == STATE_REQUEST_IGNORE) { + isHeating = false; + return HEATER_DONT_CARE; + } + + if (temperature > parameters.upperOpLimit - parameters.heaterSwitchoff) { + isHeating = false; + return HEATER_REQUEST_EMERGENCY_OFF; + } + + float opHeaterLimit = parameters.lowerOpLimit + parameters.heaterOn; + + if (isHeating) { + opHeaterLimit += parameters.hysteresis; + } + + if (temperature < opHeaterLimit) { + isHeating = true; + return HEATER_REQUEST_EMERGENCY_ON; + } + isHeating = false; + return HEATER_DONT_CARE; +} + +ThermalComponentIF::State ThermalComponentCore::getIgnoredState(int8_t state) { + switch (state) { + case NON_OPERATIONAL_LOW: + return NON_OPERATIONAL_LOW_IGNORED; + case OPERATIONAL: + return OPERATIONAL_IGNORED; + case NON_OPERATIONAL_HIGH: + return NON_OPERATIONAL_HIGH_IGNORED; + case NON_OPERATIONAL_LOW_IGNORED: + return NON_OPERATIONAL_LOW_IGNORED; + case OPERATIONAL_IGNORED: + return OPERATIONAL_IGNORED; + case NON_OPERATIONAL_HIGH_IGNORED: + return NON_OPERATIONAL_HIGH_IGNORED; + default: + case UNKNOWN: + return UNKNOWN; + } +} + +void ThermalComponentCore::updateMinMaxTemp() { + if (temperature == INVALID_TEMPERATURE) { + return; + } + if (temperature < minTemp) { + minTemp = static_cast(temperature); + } + if (temperature > maxTemp) { + maxTemp = static_cast(temperature); + } +} + +uint8_t ThermalComponentCore::getDomainId() const { + return domainId; +} + +ThermalComponentCore::Parameters ThermalComponentCore::getParameters() { + return parameters; +} + +ReturnValue_t ThermalComponentCore::getParameter(uint8_t domainId, + uint16_t parameterId, ParameterWrapper* parameterWrapper, + const ParameterWrapper* newValues, uint16_t startAtIndex) { + ReturnValue_t result = temperatureMonitor.getParameter(domainId, + parameterId, parameterWrapper, newValues, startAtIndex); + if (result != INVALID_DOMAIN_ID) { + return result; + } + if (domainId != this->domainId) { + return INVALID_DOMAIN_ID; + } + switch (parameterId) { + case 0: + parameterWrapper->set(parameters.heaterOn); + break; + case 1: + parameterWrapper->set(parameters.hysteresis); + break; + case 2: + parameterWrapper->set(parameters.heaterSwitchoff); + break; + case 3: + parameterWrapper->set(minTemp); + break; + case 4: + parameterWrapper->set(maxTemp); + break; + case 10: + parameterWrapper->set(parameters.lowerOpLimit); + break; + case 11: + parameterWrapper->set(parameters.upperOpLimit); + break; + default: + return INVALID_IDENTIFIER_ID; + } + return HasReturnvaluesIF::RETURN_OK; +} diff --git a/thermal/ThermalComponentCore.h b/thermal/ThermalComponentCore.h new file mode 100644 index 00000000..da9424e6 --- /dev/null +++ b/thermal/ThermalComponentCore.h @@ -0,0 +1,117 @@ +#ifndef FSFW_THERMAL_THERMALCOMPONENTCORE_H_ +#define FSFW_THERMAL_THERMALCOMPONENTCORE_H_ + +#include "ThermalMonitorReporter.h" +#include "ThermalComponentIF.h" +#include "AbstractTemperatureSensor.h" +#include "ThermalModule.h" + +#include "../datapoollocal/LocalPoolVariable.h" + +/** + * @brief + * @details + */ +class ThermalComponentCore: public ThermalComponentIF { +public: + struct Parameters { + float lowerOpLimit; + float upperOpLimit; + float heaterOn; + float hysteresis; + float heaterSwitchoff; + }; + + static const uint16_t COMPONENT_TEMP_CONFIRMATION = 5; + + /** + * Some documentation + * @param reportingObjectId + * @param domainId + * @param temperaturePoolId + * @param targetStatePoolId + * @param currentStatePoolId + * @param requestPoolId + * @param dataSet + * @param parameters + * @param initialTargetState + */ + ThermalComponentCore(object_id_t reportingObjectId, uint8_t domainId, + gp_id_t temperaturePoolId, gp_id_t targetStatePoolId, + gp_id_t currentStatePoolId, gp_id_t requestPoolId, + LocalPoolDataSetBase* dataSet, Parameters parameters, + StateRequest initialTargetState = + ThermalComponentIF::STATE_REQUEST_OPERATIONAL); + + void addSensor(AbstractTemperatureSensor* firstRedundantSensor); + void addFirstRedundantSensor( + AbstractTemperatureSensor* firstRedundantSensor); + void addSecondRedundantSensor( + AbstractTemperatureSensor* secondRedundantSensor); + void addThermalModule(ThermalModule* thermalModule, Priority priority); + + void setPriority(Priority priority); + + virtual ~ThermalComponentCore(); + + virtual HeaterRequest performOperation(uint8_t opCode); + + void markStateIgnored(); + + object_id_t getObjectId(); + + uint8_t getDomainId() const; + + virtual float getLowerOpLimit(); + + ReturnValue_t setTargetState(int8_t newState); + + virtual void setOutputInvalid(); + + virtual ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, + ParameterWrapper *parameterWrapper, + const ParameterWrapper *newValues, uint16_t startAtIndex); + +protected: + + AbstractTemperatureSensor *sensor = nullptr; + AbstractTemperatureSensor *firstRedundantSensor = nullptr; + AbstractTemperatureSensor *secondRedundantSensor = nullptr; + ThermalModuleIF *thermalModule = nullptr; + + lp_var_t temperature; + lp_var_t targetState; + lp_var_t currentState; + lp_var_t heaterRequest; + + bool isHeating = false; + + bool isSafeComponent = false; + + float minTemp = 999; + + float maxTemp = AbstractTemperatureSensor::ZERO_KELVIN_C; + + Parameters parameters; + + const uint8_t domainId; + + ThermalMonitorReporter temperatureMonitor; + + virtual float getTemperature(); + virtual State getState(float temperature, Parameters parameters, + int8_t targetState); + + virtual void checkLimits(State state); + + virtual HeaterRequest getHeaterRequest(int8_t targetState, + float temperature, Parameters parameters); + + virtual State getIgnoredState(int8_t state); + + void updateMinMaxTemp(); + + virtual Parameters getParameters(); +}; + +#endif /* FSFW_THERMAL_THERMALCOMPONENT_CORE_H_ */ diff --git a/thermal/ThermalComponentIF.h b/thermal/ThermalComponentIF.h index 522d4e44..16739e36 100644 --- a/thermal/ThermalComponentIF.h +++ b/thermal/ThermalComponentIF.h @@ -49,18 +49,18 @@ public: SAFE = 0, //!< SAFE IDLE, //!< IDLE PAYLOAD, //!< PAYLOAD - NUMBER_OF_PRIORITIES //!< MAX_PRIORITY + NUMBER_OF_PRIORITIES //!< MAX_PRIORITY }; /** * The elements are ordered by priority, lowest have highest priority */ enum HeaterRequest { - HEATER_REQUEST_EMERGENCY_OFF = 0, //!< REQUEST_EMERGENCY_OFF - HEATER_REQUEST_EMERGENCY_ON, //!< REQUEST_EMERGENCY_ON - HEATER_REQUEST_OFF, //!< REQUEST_OFF - HEATER_REQUEST_ON, //!< REQUEST_ON - HEATER_DONT_CARE //!< DONT_CARE + HEATER_REQUEST_EMERGENCY_OFF = 0, //!< REQUEST_EMERGENCY_OFF + HEATER_REQUEST_EMERGENCY_ON, //!< REQUEST_EMERGENCY_ON + HEATER_REQUEST_OFF, //!< REQUEST_OFF + HEATER_REQUEST_ON, //!< REQUEST_ON + HEATER_DONT_CARE //!< DONT_CARE }; virtual ~ThermalComponentIF() { diff --git a/thermal/ThermalModule.cpp b/thermal/ThermalModule.cpp index c573008e..2bc1741f 100644 --- a/thermal/ThermalModule.cpp +++ b/thermal/ThermalModule.cpp @@ -1,28 +1,31 @@ -#include "../monitoring/LimitViolationReporter.h" -#include "../monitoring/MonitoringMessageContent.h" #include "ThermalModule.h" - #include "AbstractTemperatureSensor.h" -ThermalModule::ThermalModule(uint32_t moduleTemperaturePoolId, - uint32_t currentStatePoolId, uint32_t targetStatePoolId, - DataSet *dataSet, Parameters parameters, +#include "../monitoring/LimitViolationReporter.h" +#include "../monitoring/MonitoringMessageContent.h" + + +ThermalModule::ThermalModule(gp_id_t moduleTemperaturePoolId, + gp_id_t currentStatePoolId, gp_id_t targetStatePoolId, + LocalPoolDataSetBase *dataSet, Parameters parameters, RedundantHeater::Parameters heaterParameters) : - oldStrategy(ACTIVE_SINGLE), survivalTargetTemp(0), targetTemp(0), heating( - false), parameters(parameters), moduleTemperature( - moduleTemperaturePoolId, dataSet, PoolVariableIF::VAR_WRITE), currentState( - currentStatePoolId, dataSet, PoolVariableIF::VAR_WRITE), targetState( - targetStatePoolId, dataSet, PoolVariableIF::VAR_READ) { + oldStrategy(ACTIVE_SINGLE), parameters(parameters), + moduleTemperature(moduleTemperaturePoolId, dataSet, + PoolVariableIF::VAR_WRITE), + currentState(currentStatePoolId, dataSet, PoolVariableIF::VAR_WRITE), + targetState(targetStatePoolId, dataSet, PoolVariableIF::VAR_READ) { heater = new RedundantHeater(heaterParameters); } -ThermalModule::ThermalModule(uint32_t moduleTemperaturePoolId, DataSet* dataSet) : - oldStrategy(ACTIVE_SINGLE), survivalTargetTemp(0), targetTemp(0), heating( - false), parameters( { 0, 0 }), moduleTemperature( - moduleTemperaturePoolId, dataSet, PoolVariableIF::VAR_WRITE), heater( - NULL), currentState(PoolVariableIF::INVALID, dataSet, - PoolVariableIF::VAR_WRITE), targetState(PoolVariableIF::INVALID, - dataSet, PoolVariableIF::VAR_READ) { +ThermalModule::ThermalModule(gp_id_t moduleTemperaturePoolId, + LocalPoolDataSetBase* dataSet) : + oldStrategy(ACTIVE_SINGLE), parameters( { 0, 0 }), + moduleTemperature(moduleTemperaturePoolId, dataSet, + PoolVariableIF::VAR_WRITE), + currentState(gp_id_t(), dataSet, + PoolVariableIF::VAR_WRITE), + targetState(gp_id_t(), dataSet, + PoolVariableIF::VAR_READ) { } ThermalModule::~ThermalModule() { @@ -30,7 +33,7 @@ ThermalModule::~ThermalModule() { } void ThermalModule::performOperation(uint8_t opCode) { - if (heater != NULL) { + if (heater != nullptr) { heater->performOperation(0); } } @@ -42,7 +45,7 @@ void ThermalModule::performMode(Strategy strategy) { ThermalComponentIF::HeaterRequest componentHeaterRequest = letComponentsPerformAndDeciceIfWeNeedToHeat(safeOnly); - if (heater == NULL) { + if (heater == nullptr) { informComponentsAboutHeaterState(false, NONE); return; } @@ -53,8 +56,8 @@ void ThermalModule::performMode(Strategy strategy) { //Components overwrite the module request. heating = ((componentHeaterRequest == ThermalComponentIF::HEATER_REQUEST_ON) - || (componentHeaterRequest - == ThermalComponentIF::HEATER_REQUEST_EMERGENCY_ON)); + or (componentHeaterRequest + == ThermalComponentIF::HEATER_REQUEST_EMERGENCY_ON)); } bool dual = (strategy == ACTIVE_DUAL); @@ -76,7 +79,7 @@ void ThermalModule::performMode(Strategy strategy) { } float ThermalModule::getTemperature() { - return moduleTemperature; + return moduleTemperature.value; } void ThermalModule::registerSensor(AbstractTemperatureSensor * sensor) { @@ -85,7 +88,8 @@ void ThermalModule::registerSensor(AbstractTemperatureSensor * sensor) { void ThermalModule::registerComponent(ThermalComponentIF* component, ThermalComponentIF::Priority priority) { - components.push_back(ComponentData( { component, priority, ThermalComponentIF::HEATER_DONT_CARE })); + components.push_back(ComponentData( { component, priority, + ThermalComponentIF::HEATER_DONT_CARE })); } void ThermalModule::calculateTemperature() { @@ -94,12 +98,13 @@ void ThermalModule::calculateTemperature() { std::list::iterator iter = sensors.begin(); for (; iter != sensors.end(); iter++) { if ((*iter)->isValid()) { - moduleTemperature = moduleTemperature + (*iter)->getTemperature(); + moduleTemperature = moduleTemperature.value + + (*iter)->getTemperature(); numberOfValidSensors++; } } if (numberOfValidSensors != 0) { - moduleTemperature = moduleTemperature / numberOfValidSensors; + moduleTemperature = moduleTemperature.value / numberOfValidSensors; moduleTemperature.setValid(PoolVariableIF::VALID); } else { moduleTemperature = INVALID_TEMPERATURE; @@ -117,9 +122,10 @@ ThermalComponentIF* ThermalModule::findComponent(object_id_t objectId) { return NULL; } -ThermalComponentIF::HeaterRequest ThermalModule::letComponentsPerformAndDeciceIfWeNeedToHeat( - bool safeOnly) { - ThermalComponentIF::HeaterRequest heaterRequests[ThermalComponentIF::NUMBER_OF_PRIORITIES]; +ThermalComponentIF::HeaterRequest +ThermalModule::letComponentsPerformAndDeciceIfWeNeedToHeat(bool safeOnly) { + ThermalComponentIF::HeaterRequest + heaterRequests[ThermalComponentIF::NUMBER_OF_PRIORITIES]; survivalTargetTemp = -999; targetTemp = -999; @@ -224,7 +230,7 @@ bool ThermalModule::calculateModuleHeaterRequestAndSetModuleStatus( limit = survivalTargetTemp; } - if (moduleTemperature >= limit) { + if (moduleTemperature.value >= limit) { currentState = OPERATIONAL; } else { currentState = NON_OPERATIONAL; @@ -250,15 +256,15 @@ bool ThermalModule::calculateModuleHeaterRequestAndSetModuleStatus( } void ThermalModule::setHeating(bool on) { - DataSet mySet; - PoolVariable writableTargetState(targetState.getDataPoolId(), - &mySet, PoolVariableIF::VAR_WRITE); - if (on) { - writableTargetState = STATE_REQUEST_HEATING; - } else { - writableTargetState = STATE_REQUEST_PASSIVE; - } - mySet.commit(PoolVariableIF::VALID); +// GlobDataSet mySet; +// gp_int8_t writableTargetState(targetState.getDataPoolId(), +// &mySet, PoolVariableIF::VAR_WRITE); +// if (on) { +// writableTargetState = STATE_REQUEST_HEATING; +// } else { +// writableTargetState = STATE_REQUEST_PASSIVE; +// } +// mySet.commit(PoolVariableIF::VALID); } void ThermalModule::updateTargetTemperatures(ThermalComponentIF* component, diff --git a/thermal/ThermalModule.h b/thermal/ThermalModule.h index 19ab9a54..d1e4fccb 100644 --- a/thermal/ThermalModule.h +++ b/thermal/ThermalModule.h @@ -1,16 +1,25 @@ -#ifndef THERMALMODULE_H_ -#define THERMALMODULE_H_ +#ifndef FSFW_THERMAL_THERMALMODULE_H_ +#define FSFW_THERMAL_THERMALMODULE_H_ -#include "../datapool/DataSet.h" -#include "../datapool/PoolVariable.h" -#include "../devicehandlers/HealthDevice.h" -#include "../events/EventReportingProxyIF.h" #include "ThermalModuleIF.h" -#include #include "tcsDefinitions.h" #include "RedundantHeater.h" + +//#include "../datapoolglob/GlobalDataSet.h" +//#include "../datapoolglob/GlobalPoolVariable.h" +#include "../datapoollocal/LocalPoolDataSetBase.h" +#include "../datapoollocal/LocalPoolVariable.h" +#include "../devicehandlers/HealthDevice.h" +#include "../events/EventReportingProxyIF.h" + +#include + + class PowerSwitchIF; +/** + * @brief Allows creation of different thermal control domains within a system. + */ class ThermalModule: public ThermalModuleIF { friend class ThermalController; public: @@ -19,11 +28,12 @@ public: float hysteresis; }; - ThermalModule(uint32_t moduleTemperaturePoolId, uint32_t currentStatePoolId, - uint32_t targetStatePoolId, DataSet *dataSet, Parameters parameters, - RedundantHeater::Parameters heaterParameters); + ThermalModule(gp_id_t moduleTemperaturePoolId, gp_id_t currentStatePoolId, + gp_id_t targetStatePoolId, LocalPoolDataSetBase *dataSet, + Parameters parameters, RedundantHeater::Parameters heaterParameters); - ThermalModule(uint32_t moduleTemperaturePoolId, DataSet *dataSet); + ThermalModule(gp_id_t moduleTemperaturePoolId, + LocalPoolDataSetBase *dataSet); virtual ~ThermalModule(); @@ -59,20 +69,21 @@ protected: Strategy oldStrategy; - float survivalTargetTemp; + float survivalTargetTemp = 0.0; - float targetTemp; + float targetTemp = 0.0; - bool heating; + bool heating = false; Parameters parameters; - db_float_t moduleTemperature; + lp_var_t moduleTemperature; + //gp_float_t moduleTemperature; - RedundantHeater *heater; + RedundantHeater *heater = nullptr; - db_int8_t currentState; - db_int8_t targetState; + lp_var_t currentState; + lp_var_t targetState; std::list sensors; std::list components; @@ -89,4 +100,4 @@ protected: void updateTargetTemperatures(ThermalComponentIF *component, bool isSafe); }; -#endif /* THERMALMODULE_H_ */ +#endif /* FSFW_THERMAL_THERMALMODULE_H_ */ diff --git a/thermal/ThermalMonitorReporter.cpp b/thermal/ThermalMonitorReporter.cpp new file mode 100644 index 00000000..cefc6110 --- /dev/null +++ b/thermal/ThermalMonitorReporter.cpp @@ -0,0 +1,75 @@ +#include "ThermalMonitorReporter.h" +#include "ThermalComponentIF.h" + +#include "../monitoring/MonitoringIF.h" + +ThermalMonitorReporter::~ThermalMonitorReporter() { +} + +void ThermalMonitorReporter::sendTransitionEvent(float currentValue, + ReturnValue_t state) { + switch (state) { + case MonitoringIF::BELOW_LOW_LIMIT: + EventManagerIF::triggerEvent(reportingId, + ThermalComponentIF::COMPONENT_TEMP_OOL_LOW, state); + break; + case MonitoringIF::ABOVE_HIGH_LIMIT: + EventManagerIF::triggerEvent(reportingId, + ThermalComponentIF::COMPONENT_TEMP_OOL_HIGH, state); + break; + case ThermalComponentIF::BELOW_OPERATIONAL_LIMIT: + EventManagerIF::triggerEvent(reportingId, + ThermalComponentIF::COMPONENT_TEMP_LOW, state); + break; + case ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT: + EventManagerIF::triggerEvent(reportingId, + ThermalComponentIF::COMPONENT_TEMP_HIGH, state); + break; + default: + break; + } +} + +bool ThermalMonitorReporter::isAboveHighLimit() { + if (oldState == ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT) { + return true; + } else { + return false; + } +} + +ReturnValue_t ThermalMonitorReporter::translateState( + ThermalComponentIF::State state, float sample, float lowerLimit, + float upperLimit, bool componentIsOperational) { + if (ThermalComponentIF::isIgnoredState(state)) { + setToUnchecked(); + return MonitoringIF::UNCHECKED; + } + switch (state) { + case ThermalComponentIF::OUT_OF_RANGE_LOW: + return monitorStateIs(MonitoringIF::BELOW_LOW_LIMIT, sample, + lowerLimit); + case ThermalComponentIF::NON_OPERATIONAL_LOW: + if (componentIsOperational) { + return monitorStateIs(ThermalComponentIF::BELOW_OPERATIONAL_LIMIT, + sample, lowerLimit); + } else { + return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); + } + case ThermalComponentIF::OPERATIONAL: + return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); + case ThermalComponentIF::NON_OPERATIONAL_HIGH: + if (componentIsOperational) { + return monitorStateIs(ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT, + sample, upperLimit); + } else { + return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); + } + case ThermalComponentIF::OUT_OF_RANGE_HIGH: + return monitorStateIs(MonitoringIF::ABOVE_HIGH_LIMIT, sample, + upperLimit); + default: + //Never reached, all states covered. + return HasReturnvaluesIF::RETURN_FAILED; + } +} diff --git a/thermal/ThermalMonitorReporter.h b/thermal/ThermalMonitorReporter.h new file mode 100644 index 00000000..4fb68a99 --- /dev/null +++ b/thermal/ThermalMonitorReporter.h @@ -0,0 +1,28 @@ +#ifndef FSFW_THERMAL_THERMALMONITORREPORTER_H_ +#define FSFW_THERMAL_THERMALMONITORREPORTER_H_ + +#include "ThermalComponentIF.h" +#include "../monitoring/MonitorReporter.h" + + +/** + * @brief Monitor Reporter implementation for thermal components. + */ +class ThermalMonitorReporter: public MonitorReporter { +public: + template + ThermalMonitorReporter(Args ... args) : + MonitorReporter(std::forward(args)...) { + } + ~ThermalMonitorReporter(); + ReturnValue_t translateState(ThermalComponentIF::State state, float sample, + float lowerLimit, float upperLimit, + bool componentIsOperational = true); + + bool isAboveHighLimit(); +protected: + virtual void sendTransitionEvent(float currentValue, ReturnValue_t state); + +}; + +#endif /* FSFW_THERMAL_THERMALMONITORREPORTERREPORTER_H_ */ diff --git a/thermal/tcsDefinitions.h b/thermal/tcsDefinitions.h index ad258ced..37e5b849 100644 --- a/thermal/tcsDefinitions.h +++ b/thermal/tcsDefinitions.h @@ -2,7 +2,7 @@ #define TCSDEFINITIONS_H_ -static const uint32_t INVALID_TEMPERATURE = 999; +static const float INVALID_TEMPERATURE = 999; #endif /* TCSDEFINITIONS_H_ */ From 5e234f1e23e82c98a18f7f82c8ff37d66ed98f5e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 7 Dec 2020 01:40:10 +0100 Subject: [PATCH 028/103] cmake init, printChar tests --- CMakeLists.txt | 58 +++++++++++++++++++++ action/CMakeLists.txt | 7 +++ container/CMakeLists.txt | 5 ++ controller/CMakeLists.txt | 4 ++ coordinates/CMakeLists.txt | 5 ++ datalinklayer/CMakeLists.txt | 12 +++++ datapool/CMakeLists.txt | 11 ++++ defaultcfg/fsfwconfig/CMakeLists.txt | 15 ++++++ devicehandlers/CMakeLists.txt | 11 ++++ events/CMakeLists.txt | 8 +++ events/eventmatching/CMakeLists.txt | 7 +++ fdir/CMakeLists.txt | 6 +++ globalfunctions/CMakeLists.txt | 12 +++++ globalfunctions/math/CMakeLists.txt | 4 ++ health/CMakeLists.txt | 6 +++ internalError/CMakeLists.txt | 4 ++ ipc/CMakeLists.txt | 6 +++ memory/CMakeLists.txt | 5 ++ modes/CMakeLists.txt | 5 ++ monitoring/CMakeLists.txt | 5 ++ objectmanager/CMakeLists.txt | 5 ++ osal/CMakeLists.txt | 28 ++++++++++ osal/host/CMakeLists.txt | 13 +++++ osal/windows/CMakeLists.txt | 11 ++++ parameters/CMakeLists.txt | 6 +++ power/CMakeLists.txt | 7 +++ pus/CMakeLists.txt | 11 ++++ rmap/CMakeLists.txt | 7 +++ serialize/CMakeLists.txt | 4 ++ serviceinterface/CMakeLists.txt | 5 ++ serviceinterface/ServiceInterfaceBuffer.cpp | 2 +- storagemanager/CMakeLists.txt | 5 ++ subsystem/CMakeLists.txt | 7 +++ subsystem/modes/CMakeLists.txt | 5 ++ tasks/CMakeLists.txt | 5 ++ tcdistribution/CMakeLists.txt | 7 +++ thermal/CMakeLists.txt | 10 ++++ timemanager/CMakeLists.txt | 8 +++ tmstorage/CMakeLists.txt | 4 ++ tmtcpacket/CMakeLists.txt | 8 +++ tmtcpacket/packetmatcher/CMakeLists.txt | 4 ++ tmtcpacket/pus/CMakeLists.txt | 8 +++ tmtcservices/CMakeLists.txt | 9 ++++ 43 files changed, 374 insertions(+), 1 deletion(-) create mode 100644 CMakeLists.txt create mode 100644 action/CMakeLists.txt create mode 100644 container/CMakeLists.txt create mode 100644 controller/CMakeLists.txt create mode 100644 coordinates/CMakeLists.txt create mode 100644 datalinklayer/CMakeLists.txt create mode 100644 datapool/CMakeLists.txt create mode 100644 defaultcfg/fsfwconfig/CMakeLists.txt create mode 100644 devicehandlers/CMakeLists.txt create mode 100644 events/CMakeLists.txt create mode 100644 events/eventmatching/CMakeLists.txt create mode 100644 fdir/CMakeLists.txt create mode 100644 globalfunctions/CMakeLists.txt create mode 100644 globalfunctions/math/CMakeLists.txt create mode 100644 health/CMakeLists.txt create mode 100644 internalError/CMakeLists.txt create mode 100644 ipc/CMakeLists.txt create mode 100644 memory/CMakeLists.txt create mode 100644 modes/CMakeLists.txt create mode 100644 monitoring/CMakeLists.txt create mode 100644 objectmanager/CMakeLists.txt create mode 100644 osal/CMakeLists.txt create mode 100644 osal/host/CMakeLists.txt create mode 100644 osal/windows/CMakeLists.txt create mode 100644 parameters/CMakeLists.txt create mode 100644 power/CMakeLists.txt create mode 100644 pus/CMakeLists.txt create mode 100644 rmap/CMakeLists.txt create mode 100644 serialize/CMakeLists.txt create mode 100644 serviceinterface/CMakeLists.txt create mode 100644 storagemanager/CMakeLists.txt create mode 100644 subsystem/CMakeLists.txt create mode 100644 subsystem/modes/CMakeLists.txt create mode 100644 tasks/CMakeLists.txt create mode 100644 tcdistribution/CMakeLists.txt create mode 100644 thermal/CMakeLists.txt create mode 100644 timemanager/CMakeLists.txt create mode 100644 tmstorage/CMakeLists.txt create mode 100644 tmtcpacket/CMakeLists.txt create mode 100644 tmtcpacket/packetmatcher/CMakeLists.txt create mode 100644 tmtcpacket/pus/CMakeLists.txt create mode 100644 tmtcservices/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 00000000..eff272df --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,58 @@ +cmake_minimum_required(VERSION 3.13) + +set(LIB_FSFW_NAME fsfw) +add_library(${LIB_FSFW_NAME}) + +option(FSFW_USE_RMAP "Compile with RMAP" ON) + +add_subdirectory(action) +add_subdirectory(container) +add_subdirectory(controller) +add_subdirectory(coordinates) +add_subdirectory(datalinklayer) +add_subdirectory(datapool) +add_subdirectory(devicehandlers) +add_subdirectory(events) +add_subdirectory(fdir) +add_subdirectory(globalfunctions) +add_subdirectory(health) +add_subdirectory(internalError) +add_subdirectory(ipc) +add_subdirectory(memory) +add_subdirectory(modes) +add_subdirectory(monitoring) +add_subdirectory(objectmanager) +add_subdirectory(osal) +add_subdirectory(parameters) +add_subdirectory(power) +add_subdirectory(pus) + +if(FSFW_USE_RMAP) +add_subdirectory(rmap) +endif() + +add_subdirectory(serialize) +add_subdirectory(serviceinterface) +add_subdirectory(storagemanager) +add_subdirectory(subsystem) +add_subdirectory(tasks) +add_subdirectory(tcdistribution) +add_subdirectory(thermal) +add_subdirectory(timemanager) +add_subdirectory(tmstorage) +add_subdirectory(tmtcpacket) +add_subdirectory(tmtcservices) + +# The project CMakeLists file has to set the FSFW_CONFIG_PATH and add it. +# If this is not given, we include the default configuration and emit a warning. +if(NOT FSFW_CONFIG_PATH) +message(WARNING "Flight Software Framework configuration path not set!") +message(WARNING "Setting default configuration!") +add_subdirectory(defaultcfg/fsfwconfig) +endif() + +# Required include paths to compile the FSFW +target_include_directories(${LIB_FSFW_NAME} + INTERFACE + ${FSFW_CONFIG_PATH} +) diff --git a/action/CMakeLists.txt b/action/CMakeLists.txt new file mode 100644 index 00000000..a62d4044 --- /dev/null +++ b/action/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ActionHelper.cpp + ActionMessage.cpp + CommandActionHelper.cpp + SimpleActionHelper.cpp +) \ No newline at end of file diff --git a/container/CMakeLists.txt b/container/CMakeLists.txt new file mode 100644 index 00000000..904cde55 --- /dev/null +++ b/container/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + SharedRingBuffer.cpp + SimpleRingBuffer.cpp +) \ No newline at end of file diff --git a/controller/CMakeLists.txt b/controller/CMakeLists.txt new file mode 100644 index 00000000..6f660738 --- /dev/null +++ b/controller/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ControllerBase.cpp +) \ No newline at end of file diff --git a/coordinates/CMakeLists.txt b/coordinates/CMakeLists.txt new file mode 100644 index 00000000..a1fa1e52 --- /dev/null +++ b/coordinates/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CoordinateTransformations.cpp + Sgp4Propagator.cpp +) \ No newline at end of file diff --git a/datalinklayer/CMakeLists.txt b/datalinklayer/CMakeLists.txt new file mode 100644 index 00000000..148e7c5d --- /dev/null +++ b/datalinklayer/CMakeLists.txt @@ -0,0 +1,12 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Clcw.cpp + DataLinkLayer.cpp + Farm1StateLockout.cpp + Farm1StateOpen.cpp + Farm1StateWait.cpp + MapPacketExtraction.cpp + TcTransferFrame.cpp + TcTransferFrameLocal.cpp + VirtualChannelReception.cpp +) \ No newline at end of file diff --git a/datapool/CMakeLists.txt b/datapool/CMakeLists.txt new file mode 100644 index 00000000..e741f6a1 --- /dev/null +++ b/datapool/CMakeLists.txt @@ -0,0 +1,11 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ControllerSet.cpp + DataPool.cpp + DataPoolAdmin.cpp + DataPoolParameterWrapper.cpp + DataSet.cpp + HkSwitchHelper.cpp + PoolEntry.cpp + PoolRawAccess.cpp +) \ No newline at end of file diff --git a/defaultcfg/fsfwconfig/CMakeLists.txt b/defaultcfg/fsfwconfig/CMakeLists.txt new file mode 100644 index 00000000..b8b41c93 --- /dev/null +++ b/defaultcfg/fsfwconfig/CMakeLists.txt @@ -0,0 +1,15 @@ +target_sources(${TARGET_NAME} + PRIVATE +) + +# Add include paths for the executable +target_include_directories(${TARGET_NAME} + PUBLIC + ${CMAKE_CURRENT_SOURCE_DIR} +) + +# Add include paths for the FSFW library +target_include_directories(${LIB_FSFW_NAME} + PUBLIC + ${CMAKE_CURRENT_SOURCE_DIR} +) \ No newline at end of file diff --git a/devicehandlers/CMakeLists.txt b/devicehandlers/CMakeLists.txt new file mode 100644 index 00000000..50c1008f --- /dev/null +++ b/devicehandlers/CMakeLists.txt @@ -0,0 +1,11 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + AssemblyBase.cpp + ChildHandlerBase.cpp + ChildHandlerFDIR.cpp + DeviceHandlerBase.cpp + DeviceHandlerFailureIsolation.cpp + DeviceHandlerMessage.cpp + DeviceTmReportingWrapper.cpp + HealthDevice.cpp +) \ No newline at end of file diff --git a/events/CMakeLists.txt b/events/CMakeLists.txt new file mode 100644 index 00000000..9e63deb8 --- /dev/null +++ b/events/CMakeLists.txt @@ -0,0 +1,8 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Event.cpp + EventManager.cpp + EventMessage.cpp +) + +add_subdirectory(eventmatching) \ No newline at end of file diff --git a/events/eventmatching/CMakeLists.txt b/events/eventmatching/CMakeLists.txt new file mode 100644 index 00000000..81ff9ed8 --- /dev/null +++ b/events/eventmatching/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + EventIdRangeMatcher.cpp + EventMatchTree.cpp + ReporterRangeMatcher.cpp + SeverityRangeMatcher.cpp +) \ No newline at end of file diff --git a/fdir/CMakeLists.txt b/fdir/CMakeLists.txt new file mode 100644 index 00000000..f5ffbba8 --- /dev/null +++ b/fdir/CMakeLists.txt @@ -0,0 +1,6 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + EventCorrelation.cpp + FailureIsolationBase.cpp + FaultCounter.cpp +) \ No newline at end of file diff --git a/globalfunctions/CMakeLists.txt b/globalfunctions/CMakeLists.txt new file mode 100644 index 00000000..2b3dcf8e --- /dev/null +++ b/globalfunctions/CMakeLists.txt @@ -0,0 +1,12 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + arrayprinter.cpp + AsciiConverter.cpp + CRC.cpp + DleEncoder.cpp + PeriodicOperationDivider.cpp + timevalOperations.cpp + Type.cpp +) + +add_subdirectory(math) \ No newline at end of file diff --git a/globalfunctions/math/CMakeLists.txt b/globalfunctions/math/CMakeLists.txt new file mode 100644 index 00000000..a9c4ded7 --- /dev/null +++ b/globalfunctions/math/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + QuaternionOperations.cpp +) diff --git a/health/CMakeLists.txt b/health/CMakeLists.txt new file mode 100644 index 00000000..d5f3ccd3 --- /dev/null +++ b/health/CMakeLists.txt @@ -0,0 +1,6 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + HealthHelper.cpp + HealthMessage.cpp + HealthTable.cpp +) \ No newline at end of file diff --git a/internalError/CMakeLists.txt b/internalError/CMakeLists.txt new file mode 100644 index 00000000..2b383914 --- /dev/null +++ b/internalError/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + InternalErrorReporter.cpp +) \ No newline at end of file diff --git a/ipc/CMakeLists.txt b/ipc/CMakeLists.txt new file mode 100644 index 00000000..6a3afe33 --- /dev/null +++ b/ipc/CMakeLists.txt @@ -0,0 +1,6 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CommandMessage.cpp + CommandMessageCleaner.cpp + MessageQueueMessage.cpp +) \ No newline at end of file diff --git a/memory/CMakeLists.txt b/memory/CMakeLists.txt new file mode 100644 index 00000000..9edb9031 --- /dev/null +++ b/memory/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + MemoryHelper.cpp + MemoryMessage.cpp +) \ No newline at end of file diff --git a/modes/CMakeLists.txt b/modes/CMakeLists.txt new file mode 100644 index 00000000..8e5c719b --- /dev/null +++ b/modes/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ModeHelper.cpp + ModeMessage.cpp +) \ No newline at end of file diff --git a/monitoring/CMakeLists.txt b/monitoring/CMakeLists.txt new file mode 100644 index 00000000..d26e807c --- /dev/null +++ b/monitoring/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + LimitViolationReporter.cpp + MonitoringMessage.cpp +) \ No newline at end of file diff --git a/objectmanager/CMakeLists.txt b/objectmanager/CMakeLists.txt new file mode 100644 index 00000000..72aaec89 --- /dev/null +++ b/objectmanager/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ObjectManager.cpp + SystemObject.cpp +) \ No newline at end of file diff --git a/osal/CMakeLists.txt b/osal/CMakeLists.txt new file mode 100644 index 00000000..d7aa1303 --- /dev/null +++ b/osal/CMakeLists.txt @@ -0,0 +1,28 @@ +# Check the OS_FSFW variable +if(${OS_FSFW} STREQUAL "freertos") + add_subdirectory(FreeRTOS) +elseif(${OS_FSFW} STREQUAL "rtems") + add_subdirectory(rtems) +elseif(${OS_FSFW} STREQUAL "linux") + add_subdirectory(linux) +elseif(${OS_FSFW} STREQUAL "host") + add_subdirectory(host) + if (WIN32) + add_subdirectory(windows) + endif () + +else() + + message(WARNING "The OS_FSFW variable was not set. Assuming host OS..") + # Not set. Assumuing this is a host build, try to determine host OS + if (WIN32) + add_subdirectory(host) + add_subdirectory(windows) + elseif (UNIX) + add_subdirectory(linux) + else () + # MacOS or other OSes have not been tested yet / are not supported. + message(FATAL_ERROR "The host OS could not be determined! Aborting.") + endif() + +endif() \ No newline at end of file diff --git a/osal/host/CMakeLists.txt b/osal/host/CMakeLists.txt new file mode 100644 index 00000000..3efd91d2 --- /dev/null +++ b/osal/host/CMakeLists.txt @@ -0,0 +1,13 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Clock.cpp + FixedTimeslotTask.cpp + MessageQueue.cpp + Mutex.cpp + MutexFactory.cpp + PeriodicTask.cpp + QueueFactory.cpp + QueueMapManager.cpp + SemaphoreFactory.cpp + TaskFactory.cpp +) \ No newline at end of file diff --git a/osal/windows/CMakeLists.txt b/osal/windows/CMakeLists.txt new file mode 100644 index 00000000..b6e76d6a --- /dev/null +++ b/osal/windows/CMakeLists.txt @@ -0,0 +1,11 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + TcWinUdpPollingTask.cpp + TmTcWinUdpBridge.cpp +) + +target_link_libraries(${LIB_FSFW_NAME} + PRIVATE + wsock32 + ws2_32 +) \ No newline at end of file diff --git a/parameters/CMakeLists.txt b/parameters/CMakeLists.txt new file mode 100644 index 00000000..fb5e4590 --- /dev/null +++ b/parameters/CMakeLists.txt @@ -0,0 +1,6 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ParameterHelper.cpp + ParameterMessage.cpp + ParameterWrapper.cpp +) \ No newline at end of file diff --git a/power/CMakeLists.txt b/power/CMakeLists.txt new file mode 100644 index 00000000..1c625db1 --- /dev/null +++ b/power/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Fuse.cpp + PowerComponent.cpp + PowerSensor.cpp + PowerSwitcher.cpp +) \ No newline at end of file diff --git a/pus/CMakeLists.txt b/pus/CMakeLists.txt new file mode 100644 index 00000000..758c2629 --- /dev/null +++ b/pus/CMakeLists.txt @@ -0,0 +1,11 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CService200ModeCommanding.cpp + CService201HealthCommanding.cpp + Service17Test.cpp + Service1TelecommandVerification.cpp + Service2DeviceAccess.cpp + Service5EventReporting.cpp + Service8FunctionManagement.cpp + Service9TimeManagement.cpp +) \ No newline at end of file diff --git a/rmap/CMakeLists.txt b/rmap/CMakeLists.txt new file mode 100644 index 00000000..78c99e42 --- /dev/null +++ b/rmap/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + RMAP.cpp + RMAPCookie.cpp + RmapDeviceCommunicationIF.cpp +) + diff --git a/serialize/CMakeLists.txt b/serialize/CMakeLists.txt new file mode 100644 index 00000000..fc2387e8 --- /dev/null +++ b/serialize/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + SerialBufferAdapter.cpp +) \ No newline at end of file diff --git a/serviceinterface/CMakeLists.txt b/serviceinterface/CMakeLists.txt new file mode 100644 index 00000000..d84adbeb --- /dev/null +++ b/serviceinterface/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ServiceInterfaceStream.cpp + ServiceInterfaceBuffer.cpp +) \ No newline at end of file diff --git a/serviceinterface/ServiceInterfaceBuffer.cpp b/serviceinterface/ServiceInterfaceBuffer.cpp index 68fc4dec..bc360334 100644 --- a/serviceinterface/ServiceInterfaceBuffer.cpp +++ b/serviceinterface/ServiceInterfaceBuffer.cpp @@ -4,7 +4,7 @@ #include // to be implemented by bsp -extern "C" void printChar(const char*, bool errStream); +/*extern "C" */void printChar(const char*, bool errStream); #ifndef UT699 diff --git a/storagemanager/CMakeLists.txt b/storagemanager/CMakeLists.txt new file mode 100644 index 00000000..57c92195 --- /dev/null +++ b/storagemanager/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ConstStorageAccessor.cpp + StorageAccessor.cpp +) \ No newline at end of file diff --git a/subsystem/CMakeLists.txt b/subsystem/CMakeLists.txt new file mode 100644 index 00000000..5c98ee70 --- /dev/null +++ b/subsystem/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Subsystem.cpp + SubsystemBase.cpp +) + +add_subdirectory(modes) \ No newline at end of file diff --git a/subsystem/modes/CMakeLists.txt b/subsystem/modes/CMakeLists.txt new file mode 100644 index 00000000..6ac6a293 --- /dev/null +++ b/subsystem/modes/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + ModeSequenceMessage.cpp + ModeStore.cpp +) diff --git a/tasks/CMakeLists.txt b/tasks/CMakeLists.txt new file mode 100644 index 00000000..1964bb4e --- /dev/null +++ b/tasks/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + FixedSequenceSlot.cpp + FixedSlotSequence.cpp +) \ No newline at end of file diff --git a/tcdistribution/CMakeLists.txt b/tcdistribution/CMakeLists.txt new file mode 100644 index 00000000..17dc186c --- /dev/null +++ b/tcdistribution/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CCSDSDistributor.cpp + PUSDistributor.cpp + TcDistributor.cpp + TcPacketCheck.cpp +) diff --git a/thermal/CMakeLists.txt b/thermal/CMakeLists.txt new file mode 100644 index 00000000..67664fbe --- /dev/null +++ b/thermal/CMakeLists.txt @@ -0,0 +1,10 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + AbstractTemperatureSensor.cpp + CoreComponent.cpp + Heater.cpp + RedundantHeater.cpp + ThermalComponent.cpp + ThermalModule.cpp + ThermalMonitor.cpp +) diff --git a/timemanager/CMakeLists.txt b/timemanager/CMakeLists.txt new file mode 100644 index 00000000..3367775f --- /dev/null +++ b/timemanager/CMakeLists.txt @@ -0,0 +1,8 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CCSDSTime.cpp + Countdown.cpp + Stopwatch.cpp + TimeMessage.cpp + TimeStamper.cpp +) diff --git a/tmstorage/CMakeLists.txt b/tmstorage/CMakeLists.txt new file mode 100644 index 00000000..7990d85a --- /dev/null +++ b/tmstorage/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + TmStoreMessage.cpp +) diff --git a/tmtcpacket/CMakeLists.txt b/tmtcpacket/CMakeLists.txt new file mode 100644 index 00000000..fe3d2a4d --- /dev/null +++ b/tmtcpacket/CMakeLists.txt @@ -0,0 +1,8 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + SpacePacket.cpp + SpacePacketBase.cpp +) + +add_subdirectory(packetmatcher) +add_subdirectory(pus) \ No newline at end of file diff --git a/tmtcpacket/packetmatcher/CMakeLists.txt b/tmtcpacket/packetmatcher/CMakeLists.txt new file mode 100644 index 00000000..e9a8d03b --- /dev/null +++ b/tmtcpacket/packetmatcher/CMakeLists.txt @@ -0,0 +1,4 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + PacketMatchTree.cpp +) diff --git a/tmtcpacket/pus/CMakeLists.txt b/tmtcpacket/pus/CMakeLists.txt new file mode 100644 index 00000000..fcfc82d2 --- /dev/null +++ b/tmtcpacket/pus/CMakeLists.txt @@ -0,0 +1,8 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + TcPacketBase.cpp + TcPacketStored.cpp + TmPacketBase.cpp + TmPacketMinimal.cpp + TmPacketStored.cpp +) diff --git a/tmtcservices/CMakeLists.txt b/tmtcservices/CMakeLists.txt new file mode 100644 index 00000000..c30af214 --- /dev/null +++ b/tmtcservices/CMakeLists.txt @@ -0,0 +1,9 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + CommandingServiceBase.cpp + PusServiceBase.cpp + PusVerificationReport.cpp + TmTcBridge.cpp + TmTcMessage.cpp + VerificationReporter.cpp +) \ No newline at end of file From 33d4b574001e89828c044eff295ca0a20295e549 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 7 Dec 2020 02:03:42 +0100 Subject: [PATCH 029/103] additional build option --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index eff272df..9973c0ec 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -4,6 +4,7 @@ set(LIB_FSFW_NAME fsfw) add_library(${LIB_FSFW_NAME}) option(FSFW_USE_RMAP "Compile with RMAP" ON) +option(FSFW_USE_DATALINKLAYER "Compile with Data Link Layer" ON) add_subdirectory(action) add_subdirectory(container) From c4ba243885cf912eb940e0442bb2728802eac46b Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Mon, 7 Dec 2020 12:17:02 +0100 Subject: [PATCH 030/103] small bugfixes --- osal/host/CMakeLists.txt | 10 +++++++++- serviceinterface/ServiceInterfaceBuffer.cpp | 2 +- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/osal/host/CMakeLists.txt b/osal/host/CMakeLists.txt index 3efd91d2..d54cfac8 100644 --- a/osal/host/CMakeLists.txt +++ b/osal/host/CMakeLists.txt @@ -10,4 +10,12 @@ target_sources(${LIB_FSFW_NAME} QueueMapManager.cpp SemaphoreFactory.cpp TaskFactory.cpp -) \ No newline at end of file +) + +if(UNIX) + target_link_libraries(${LIB_FSFW_NAME} + PRIVATE + pthread + rt + ) +endif() \ No newline at end of file diff --git a/serviceinterface/ServiceInterfaceBuffer.cpp b/serviceinterface/ServiceInterfaceBuffer.cpp index bc360334..68fc4dec 100644 --- a/serviceinterface/ServiceInterfaceBuffer.cpp +++ b/serviceinterface/ServiceInterfaceBuffer.cpp @@ -4,7 +4,7 @@ #include // to be implemented by bsp -/*extern "C" */void printChar(const char*, bool errStream); +extern "C" void printChar(const char*, bool errStream); #ifndef UT699 From 489a2097b850313154866cf4d7bbfbc09320a5b5 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Mon, 7 Dec 2020 12:25:30 +0100 Subject: [PATCH 031/103] fix for host osal linux --- osal/CMakeLists.txt | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/osal/CMakeLists.txt b/osal/CMakeLists.txt index d7aa1303..02ff2405 100644 --- a/osal/CMakeLists.txt +++ b/osal/CMakeLists.txt @@ -9,6 +9,12 @@ elseif(${OS_FSFW} STREQUAL "host") add_subdirectory(host) if (WIN32) add_subdirectory(windows) + elseif(UNIX) + target_sources(${LIB_FSFW_NAME} + PUBLIC + linux/TcUnixUdpPollingTask.cpp + linux/TmTcUnixUdpBridge.cpp + ) endif () else() From d93a8692e08abbe7926955ffdaa95ad569c372f9 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Mon, 7 Dec 2020 12:59:09 +0100 Subject: [PATCH 032/103] cmakelists update --- CMakeLists.txt | 26 ++++++++++++++++++++++++++ osal/host/CMakeLists.txt | 2 +- osal/linux/CMakeLists.txt | 25 +++++++++++++++++++++++++ 3 files changed, 52 insertions(+), 1 deletion(-) create mode 100644 osal/linux/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt index 9973c0ec..669283c7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -3,6 +3,32 @@ cmake_minimum_required(VERSION 3.13) set(LIB_FSFW_NAME fsfw) add_library(${LIB_FSFW_NAME}) +# Set options for FSFW OSAL selection. +if(UNIX) +set(OS_FSFW "linux" CACHE STRING "OS abstraction layer used in the FSFW") +elseif(WIN32) +set(OS_FSFW "host" CACHE STRING "OS abstraction layer used in the FSFW") +endif() + +set_property(CACHE OS_FSFW PROPERTY STRINGS host linux rtems freertos) + +if(${OS_FSFW} STREQUAL host) +set(OS_FSFW_NAME "Host") +elseif(${OS_FSFW} STREQUAL linux) +set(OS_FSFW_NAME "Linux") +elseif(${OS_FSFW} STREQUAL freertos) +set(OS_FSFW_NAME "FreeRTOS") +elseif(${OS_FSFW} STREQUAL rtems) +set(OS_FSFW_NAME "RTEMS") +else() +message(WARNING "Invalid operating system for FSFW specified! Setting to host..") +set(OS_FSFW_NAME "Host") +set(OS_FSFW "host") +endif() + +message(STATUS "Compiling FSFW for the ${OS_FSFW_NAME} operating system") + +# Options to exclude parts of the FSFW from compilation. option(FSFW_USE_RMAP "Compile with RMAP" ON) option(FSFW_USE_DATALINKLAYER "Compile with Data Link Layer" ON) diff --git a/osal/host/CMakeLists.txt b/osal/host/CMakeLists.txt index d54cfac8..d73e6f27 100644 --- a/osal/host/CMakeLists.txt +++ b/osal/host/CMakeLists.txt @@ -13,9 +13,9 @@ target_sources(${LIB_FSFW_NAME} ) if(UNIX) + add_definitions(-pthread) target_link_libraries(${LIB_FSFW_NAME} PRIVATE - pthread rt ) endif() \ No newline at end of file diff --git a/osal/linux/CMakeLists.txt b/osal/linux/CMakeLists.txt new file mode 100644 index 00000000..c0096e42 --- /dev/null +++ b/osal/linux/CMakeLists.txt @@ -0,0 +1,25 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Clock.cpp + BinarySemaphore.cpp + CountingSemaphore.cpp + FixedTimeslotTask.cpp + InternalErrorCodes.cpp + MessageQueue.cpp + Mutex.cpp + MutexFactory.cpp + PeriodicPosixTask.cpp + PosixThread.cpp + QueueFactory.cpp + SemaphoreFactory.cpp + TaskFactory.cpp + TcUnixUdpPollingTask.cpp + TmTcUnixUdpBridge.cpp + Timer.cpp +) + +target_link_libraries(${LIB_FSFW_NAME} + PRIVATE + rt + pthread +) From 4a4634928620b68fc0aa253cf9ccd1e977a81318 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 15:14:39 +0100 Subject: [PATCH 033/103] minor imrpovements --- datalinklayer/MapPacketExtraction.cpp | 4 ++-- datalinklayer/MapPacketExtraction.h | 11 ++++++----- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/datalinklayer/MapPacketExtraction.cpp b/datalinklayer/MapPacketExtraction.cpp index 45f7d3f8..845ed7c1 100644 --- a/datalinklayer/MapPacketExtraction.cpp +++ b/datalinklayer/MapPacketExtraction.cpp @@ -9,9 +9,9 @@ MapPacketExtraction::MapPacketExtraction(uint8_t setMapId, object_id_t setPacketDestination) : - lastSegmentationFlag(NO_SEGMENTATION), mapId(setMapId), packetLength(0), + lastSegmentationFlag(NO_SEGMENTATION), mapId(setMapId), bufferPosition(packetBuffer), packetDestination(setPacketDestination), - packetStore(NULL), tcQueueId(MessageQueueIF::NO_QUEUE) { + tcQueueId(MessageQueueIF::NO_QUEUE) { std::memset(packetBuffer, 0, sizeof(packetBuffer)); } diff --git a/datalinklayer/MapPacketExtraction.h b/datalinklayer/MapPacketExtraction.h index eff9b7c3..ddb867fb 100644 --- a/datalinklayer/MapPacketExtraction.h +++ b/datalinklayer/MapPacketExtraction.h @@ -1,5 +1,5 @@ -#ifndef MAPPACKETEXTRACTION_H_ -#define MAPPACKETEXTRACTION_H_ +#ifndef FSFW_DATALINKLAYER_MAPPACKETEXTRACTION_H_ +#define FSFW_DATALINKLAYER_MAPPACKETEXTRACTION_H_ #include "MapPacketExtractionIF.h" #include "../objectmanager/ObjectManagerIF.h" @@ -20,11 +20,12 @@ private: static const uint32_t MAX_PACKET_SIZE = 4096; uint8_t lastSegmentationFlag; //!< The segmentation flag of the last received frame. uint8_t mapId; //!< MAP ID of this MAP Channel. - uint32_t packetLength; //!< Complete length of the current Space Packet. + uint32_t packetLength = 0; //!< Complete length of the current Space Packet. uint8_t* bufferPosition; //!< Position to write to in the internal Packet buffer. uint8_t packetBuffer[MAX_PACKET_SIZE]; //!< The internal Space Packet Buffer. object_id_t packetDestination; - StorageManagerIF* packetStore; //!< Pointer to the store where full TC packets are stored. + //!< Pointer to the store where full TC packets are stored. + StorageManagerIF* packetStore = nullptr; MessageQueueId_t tcQueueId; //!< QueueId to send found packets to the distributor. /** * Debug method to print the packet Buffer's content. @@ -69,4 +70,4 @@ public: uint8_t getMapId() const; }; -#endif /* MAPPACKETEXTRACTION_H_ */ +#endif /* FSFW_DATALINKLAYER_MAPPACKETEXTRACTION_H_ */ From ac5446b2b145eee8a3a5183913989b66d20fcc63 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 15:43:58 +0100 Subject: [PATCH 034/103] removed hk switcher helper member --- controller/ControllerBase.cpp | 7 +------ controller/ControllerBase.h | 3 --- 2 files changed, 1 insertion(+), 9 deletions(-) diff --git a/controller/ControllerBase.cpp b/controller/ControllerBase.cpp index 45e678eb..2a402468 100644 --- a/controller/ControllerBase.cpp +++ b/controller/ControllerBase.cpp @@ -8,7 +8,7 @@ ControllerBase::ControllerBase(object_id_t setObjectId, object_id_t parentId, size_t commandQueueDepth) : SystemObject(setObjectId), parentId(parentId), mode(MODE_OFF), submode(SUBMODE_NONE), modeHelper(this), - healthHelper(this, setObjectId), hkSwitcher(this) { + healthHelper(this, setObjectId) { commandQueue = QueueFactory::instance()->createMessageQueue( commandQueueDepth); } @@ -44,10 +44,6 @@ ReturnValue_t ControllerBase::initialize() { return result; } - result = hkSwitcher.initialize(); - if (result != RETURN_OK) { - return result; - } return RETURN_OK; } @@ -107,7 +103,6 @@ void ControllerBase::announceMode(bool recursive) { ReturnValue_t ControllerBase::performOperation(uint8_t opCode) { handleQueue(); - hkSwitcher.performOperation(); performControlOperation(); return RETURN_OK; } diff --git a/controller/ControllerBase.h b/controller/ControllerBase.h index 25d3ab1f..6e83fe80 100644 --- a/controller/ControllerBase.h +++ b/controller/ControllerBase.h @@ -72,9 +72,6 @@ protected: HealthHelper healthHelper; - // Is this still needed? - HkSwitchHelper hkSwitcher; - /** * Pointer to the task which executes this component, * is invalid before setTaskIF was called. From a612e19e94a3edcbd3a5997410e8c4b87800cfb3 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 15:49:46 +0100 Subject: [PATCH 035/103] ndentation --- internalError/InternalErrorReporter.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/internalError/InternalErrorReporter.cpp b/internalError/InternalErrorReporter.cpp index 12f36f33..818b00cf 100644 --- a/internalError/InternalErrorReporter.cpp +++ b/internalError/InternalErrorReporter.cpp @@ -6,8 +6,7 @@ #include "../serviceinterface/ServiceInterfaceStream.h" InternalErrorReporter::InternalErrorReporter(object_id_t setObjectId, - uint32_t messageQueueDepth) : - SystemObject(setObjectId), + uint32_t messageQueueDepth): SystemObject(setObjectId), commandQueue(QueueFactory::instance()-> createMessageQueue(messageQueueDepth)), poolManager(this, commandQueue), From 7f40566031f40d8ebe214bf29a7958731d936cd0 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 15:50:21 +0100 Subject: [PATCH 036/103] include removed --- internalError/InternalErrorReporter.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/internalError/InternalErrorReporter.cpp b/internalError/InternalErrorReporter.cpp index 818b00cf..bfb67289 100644 --- a/internalError/InternalErrorReporter.cpp +++ b/internalError/InternalErrorReporter.cpp @@ -1,4 +1,3 @@ -#include "../datapoolglob/GlobalDataSet.h" #include "InternalErrorReporter.h" #include "../ipc/QueueFactory.h" From 5e2e18ac078b3ea78ab1328adda5116d532b222c Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 15:59:30 +0100 Subject: [PATCH 037/103] device handler uses local pools now --- devicehandlers/DeviceHandlerBase.cpp | 148 +++++++++++++---------- devicehandlers/DeviceHandlerBase.h | 169 ++++++++++++++++----------- 2 files changed, 193 insertions(+), 124 deletions(-) diff --git a/devicehandlers/DeviceHandlerBase.cpp b/devicehandlers/DeviceHandlerBase.cpp index b5d43d77..733106e5 100644 --- a/devicehandlers/DeviceHandlerBase.cpp +++ b/devicehandlers/DeviceHandlerBase.cpp @@ -3,8 +3,6 @@ #include "DeviceTmReportingWrapper.h" #include "../serviceinterface/ServiceInterfaceStream.h" -#include "../datapoolglob/GlobalDataSet.h" -#include "../datapoolglob/GlobalPoolVariable.h" #include "../objectmanager/ObjectManager.h" #include "../storagemanager/StorageManagerIF.h" #include "../thermal/ThermalComponentIF.h" @@ -13,9 +11,11 @@ #include "../ipc/MessageQueueMessage.h" #include "../ipc/QueueFactory.h" #include "../subsystem/SubsystemBase.h" +#include "../datapoollocal/LocalPoolVariable.h" #include + object_id_t DeviceHandlerBase::powerSwitcherId = objects::NO_OBJECT; object_id_t DeviceHandlerBase::rawDataReceiverId = objects::NO_OBJECT; object_id_t DeviceHandlerBase::defaultFdirParentId = objects::NO_OBJECT; @@ -56,9 +56,10 @@ void DeviceHandlerBase::setHkDestination(object_id_t hkDestination) { } void DeviceHandlerBase::setThermalStateRequestPoolIds( - uint32_t thermalStatePoolId, uint32_t thermalRequestPoolId) { - this->deviceThermalRequestPoolId = thermalStatePoolId; - this->deviceThermalRequestPoolId = thermalRequestPoolId; + lp_id_t thermalStatePoolId, lp_id_t heaterRequestPoolId, + uint32_t thermalSetId) { + thermalSet = new DeviceHandlerThermalSet(this, thermalSetId, + thermalStatePoolId, heaterRequestPoolId); } @@ -86,7 +87,6 @@ ReturnValue_t DeviceHandlerBase::performOperation(uint8_t counter) { decrementDeviceReplyMap(); fdirInstance->checkForFailures(); hkSwitcher.performOperation(); - hkManager.performHkOperation(); performOperationHook(); return RETURN_OK; } @@ -111,6 +111,9 @@ ReturnValue_t DeviceHandlerBase::performOperation(uint8_t counter) { break; case CommunicationAction::GET_READ: doGetRead(); + // This will be performed after datasets have been updated by the + // custom device implementation. + hkManager.performHkOperation(); break; default: break; @@ -208,16 +211,18 @@ ReturnValue_t DeviceHandlerBase::initialize() { fillCommandAndReplyMap(); - //Set temperature target state to NON_OP. - GlobDataSet mySet; - gp_uint8_t thermalRequest(deviceThermalRequestPoolId, &mySet, - PoolVariableIF::VAR_WRITE); - mySet.read(); - thermalRequest = ThermalComponentIF::STATE_REQUEST_NON_OPERATIONAL; - mySet.commit(PoolVariableIF::VALID); + if(thermalSet != nullptr) { + //Set temperature target state to NON_OP. + result = thermalSet->read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + thermalSet->heaterRequest.value = + ThermalComponentIF::STATE_REQUEST_NON_OPERATIONAL; + thermalSet->commit(PoolVariableIF::VALID); + } + + } return RETURN_OK; - } void DeviceHandlerBase::decrementDeviceReplyMap() { @@ -505,15 +510,17 @@ void DeviceHandlerBase::setMode(Mode_t newMode, uint8_t newSubmode) { } Clock::getUptime(&timeoutStart); - if (mode == MODE_OFF) { - GlobDataSet mySet; - gp_uint8_t thermalRequest(deviceThermalRequestPoolId, &mySet, - PoolVariableIF::VAR_READ_WRITE); - mySet.read(); - if (thermalRequest != ThermalComponentIF::STATE_REQUEST_IGNORE) { - thermalRequest = ThermalComponentIF::STATE_REQUEST_NON_OPERATIONAL; + if (mode == MODE_OFF and thermalSet != nullptr) { + ReturnValue_t result = thermalSet->read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + if (thermalSet->heaterRequest.value != + ThermalComponentIF::STATE_REQUEST_IGNORE) { + thermalSet->heaterRequest.value = ThermalComponentIF:: + STATE_REQUEST_NON_OPERATIONAL; + } + thermalSet->heaterRequest.commit(PoolVariableIF::VALID); } - mySet.commit(PoolVariableIF::VALID); + } changeHK(mode, submode, true); } @@ -976,17 +983,15 @@ ReturnValue_t DeviceHandlerBase::checkModeCommand(Mode_t commandedMode, } if ((commandedMode == MODE_ON) && (mode == MODE_OFF) - && (deviceThermalStatePoolId != PoolVariableIF::NO_PARAMETER)) { - GlobDataSet mySet; - gp_uint8_t thermalState(deviceThermalStatePoolId, &mySet, - PoolVariableIF::VAR_READ); - gp_uint8_t thermalRequest(deviceThermalRequestPoolId, &mySet, - PoolVariableIF::VAR_READ); - mySet.read(); - if (thermalRequest != ThermalComponentIF::STATE_REQUEST_IGNORE) { - if (!ThermalComponentIF::isOperational(thermalState)) { + and (thermalSet != nullptr)) { + ReturnValue_t result = thermalSet->read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + if((thermalSet->heaterRequest.value != + ThermalComponentIF::STATE_REQUEST_IGNORE) and (not + ThermalComponentIF::isOperational( + thermalSet->thermalState.value))) { triggerEvent(ThermalComponentIF::TEMP_NOT_IN_OP_RANGE, - thermalState); + thermalSet->thermalState.value); return NON_OP_TEMPERATURE; } } @@ -999,32 +1004,15 @@ void DeviceHandlerBase::startTransition(Mode_t commandedMode, Submode_t commandedSubmode) { switch (commandedMode) { case MODE_ON: - if (mode == MODE_OFF) { - transitionSourceMode = _MODE_POWER_DOWN; - transitionSourceSubMode = SUBMODE_NONE; - setMode(_MODE_POWER_ON, commandedSubmode); - //already set the delay for the child transition so we don't need to call it twice - childTransitionDelay = getTransitionDelayMs(_MODE_START_UP, - MODE_ON); - triggerEvent(CHANGING_MODE, commandedMode, commandedSubmode); - GlobDataSet mySet; - gp_int8_t thermalRequest(deviceThermalRequestPoolId, - &mySet, PoolVariableIF::VAR_READ_WRITE); - mySet.read(); - if (thermalRequest != ThermalComponentIF::STATE_REQUEST_IGNORE) { - thermalRequest = ThermalComponentIF::STATE_REQUEST_OPERATIONAL; - mySet.commit(PoolVariableIF::VALID); - } - } else { - setTransition(MODE_ON, commandedSubmode); - } + handleTransitionToOnMode(commandedMode, commandedSubmode); break; case MODE_OFF: if (mode == MODE_OFF) { triggerEvent(CHANGING_MODE, commandedMode, commandedSubmode); setMode(_MODE_POWER_DOWN, commandedSubmode); } else { - //already set the delay for the child transition so we don't need to call it twice + // already set the delay for the child transition + // so we don't need to call it twice childTransitionDelay = getTransitionDelayMs(mode, _MODE_POWER_DOWN); transitionSourceMode = _MODE_POWER_DOWN; transitionSourceSubMode = commandedSubmode; @@ -1050,6 +1038,33 @@ void DeviceHandlerBase::startTransition(Mode_t commandedMode, } } +void DeviceHandlerBase::handleTransitionToOnMode(Mode_t commandedMode, + Submode_t commandedSubmode) { + if (mode == MODE_OFF) { + transitionSourceMode = _MODE_POWER_DOWN; + transitionSourceSubMode = SUBMODE_NONE; + setMode(_MODE_POWER_ON, commandedSubmode); + // already set the delay for the child transition so we don't + // need to call it twice + childTransitionDelay = getTransitionDelayMs(_MODE_START_UP, + MODE_ON); + triggerEvent(CHANGING_MODE, commandedMode, commandedSubmode); + if(thermalSet != nullptr) { + ReturnValue_t result = thermalSet->read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + if(thermalSet->heaterRequest != + ThermalComponentIF::STATE_REQUEST_IGNORE) { + thermalSet->heaterRequest = + ThermalComponentIF::STATE_REQUEST_OPERATIONAL; + thermalSet->commit(); + } + } + } + } else { + setTransition(MODE_ON, commandedSubmode); + } +} + void DeviceHandlerBase::getMode(Mode_t* mode, Submode_t* submode) { *mode = this->mode; *submode = this->submode; @@ -1222,10 +1237,12 @@ void DeviceHandlerBase::handleDeviceTM(SerializeIF* data, } } //Try to cast to GlobDataSet and commit data. - if (!neverInDataPool) { - GlobDataSet* dataSet = dynamic_cast(data); - if (dataSet != NULL) { - dataSet->commit(PoolVariableIF::VALID); + if (not neverInDataPool) { + LocalPoolDataSetBase* dataSet = + dynamic_cast(data); + if (dataSet != nullptr) { + dataSet->setValidity(true, true); + dataSet->commit(); } } } @@ -1262,7 +1279,8 @@ void DeviceHandlerBase::buildInternalCommand(void) { if (result == BUSY) { //so we can track misconfigurations sif::debug << std::hex << getObjectId() - << ": DHB::buildInternalCommand: Busy" << std::dec << std::endl; + << ": DHB::buildInternalCommand: Busy" << std::dec + << std::endl; result = NOTHING_TO_SEND; //no need to report this } } @@ -1371,8 +1389,8 @@ bool DeviceHandlerBase::commandIsExecuting(DeviceCommandId_t commandId) { void DeviceHandlerBase::changeHK(Mode_t mode, Submode_t submode, bool enable) { } -void DeviceHandlerBase::setTaskIF(PeriodicTaskIF* task_){ - executingTask = task_; +void DeviceHandlerBase::setTaskIF(PeriodicTaskIF* task){ + executingTask = task; } // Default implementations empty. @@ -1385,6 +1403,12 @@ void DeviceHandlerBase::performOperationHook() { ReturnValue_t DeviceHandlerBase::initializeLocalDataPool( LocalDataPool &localDataPoolMap, LocalDataPoolManager& poolManager) { + if(thermalSet != nullptr) { + localDataPoolMap.emplace(thermalSet->thermalStatePoolId, + new PoolEntry); + localDataPoolMap.emplace(thermalSet->heaterRequestPoolId, + new PoolEntry); + } return RETURN_OK; } @@ -1429,3 +1453,9 @@ dur_millis_t DeviceHandlerBase::getPeriodicOperationFrequency() const { return pstIntervalMs; } +DeviceCommandId_t DeviceHandlerBase::getPendingCommand() const { + if(cookieInfo.pendingCommand != deviceCommandMap.end()) { + return cookieInfo.pendingCommand->first; + } + return DeviceHandlerIF::NO_COMMAND; +} diff --git a/devicehandlers/DeviceHandlerBase.h b/devicehandlers/DeviceHandlerBase.h index 627a6423..2bfa62a6 100644 --- a/devicehandlers/DeviceHandlerBase.h +++ b/devicehandlers/DeviceHandlerBase.h @@ -4,6 +4,7 @@ #include "DeviceHandlerIF.h" #include "DeviceCommunicationIF.h" #include "DeviceHandlerFailureIsolation.h" +#include "DeviceHandlerThermalSet.h" #include "../objectmanager/SystemObject.h" #include "../tasks/ExecutableObjectIF.h" @@ -103,8 +104,21 @@ public: size_t cmdQueueSize = 20); void setHkDestination(object_id_t hkDestination); - void setThermalStateRequestPoolIds(uint32_t thermalStatePoolId, - uint32_t thermalRequestPoolId); + + /** + * If the device handler is controlled by the FSFW thermal building blocks, + * this function should be called to initialize all required components. + * The device handler will then take care of creating local pool entries + * for the device thermal state and device heating request. + * Custom local pool IDs can be assigned as well. + * @param thermalStatePoolId + * @param thermalRequestPoolId + */ + void setThermalStateRequestPoolIds(lp_id_t thermalStatePoolId = + DeviceHandlerIF::DEFAULT_THERMAL_STATE_POOL_ID, + lp_id_t thermalRequestPoolId = + DeviceHandlerIF::DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID, + uint32_t thermalSetId = DeviceHandlerIF::DEFAULT_THERMAL_SET_ID); /** * @brief Helper function to ease device handler development. * This will instruct the transition to MODE_ON immediately @@ -694,19 +708,7 @@ protected: //! and to send replies. MessageQueueIF* commandQueue = nullptr; - /** - * this is the datapool variable with the thermal state of the device - * - * can be set to PoolVariableIF::NO_PARAMETER to deactivate thermal checking - */ - uint32_t deviceThermalStatePoolId = PoolVariableIF::NO_PARAMETER; - - /** - * this is the datapool variable with the thermal request of the device - * - * can be set to PoolVariableIF::NO_PARAMETER to deactivate thermal checking - */ - uint32_t deviceThermalRequestPoolId = PoolVariableIF::NO_PARAMETER; + DeviceHandlerThermalSet* thermalSet = nullptr; /** * Optional Error code. Can be set in doStartUp(), doShutDown() and @@ -732,15 +734,27 @@ protected: //! before setTaskIF was called. PeriodicTaskIF* executingTask = nullptr; - static object_id_t powerSwitcherId; //!< Object which switches power on and off. + //!< Object which switches power on and off. + static object_id_t powerSwitcherId; - static object_id_t rawDataReceiverId; //!< Object which receives RAW data by default. + //!< Object which receives RAW data by default. + static object_id_t rawDataReceiverId; + + //!< Object which may be the root cause of an identified fault. + static object_id_t defaultFdirParentId; + + /** + * Helper function to get pending command. This is useful for devices + * like SPI sensors to identify the last sent command. + * @return + */ + DeviceCommandId_t getPendingCommand() const; - static object_id_t defaultFdirParentId; //!< Object which may be the root cause of an identified fault. /** * Helper function to report a missed reply * - * Can be overwritten by children to act on missed replies or to fake reporting Id. + * Can be overwritten by children to act on missed replies or to fake + * reporting Id. * * @param id of the missed reply */ @@ -847,15 +861,18 @@ protected: /** * Build the device command to send for raw mode. * - * This is only called in @c MODE_RAW. It is for the rare case that in raw mode packets - * are to be sent by the handler itself. It is NOT needed for the raw commanding service. - * Its only current use is in the STR handler which gets its raw packets from a different - * source. - * Also it can be used for transitional commands, to get the device ready for @c MODE_RAW + * This is only called in @c MODE_RAW. It is for the rare case that in + * raw mode packets are to be sent by the handler itself. It is NOT needed + * for the raw commanding service. Its only current use is in the STR + * handler which gets its raw packets from a different source. + * Also it can be used for transitional commands, to get the device ready + * for @c MODE_RAW * - * As it is almost never used, there is a default implementation returning @c NOTHING_TO_SEND. + * As it is almost never used, there is a default implementation + * returning @c NOTHING_TO_SEND. * - * #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 @@ -868,7 +885,9 @@ protected: * Returns the delay cycle count of a reply. * A count != 0 indicates that the command is already executed. * @param deviceCommand The command to look for - * @return The current delay count. If the command does not exist (should never happen) it returns 0. + * @return + * The current delay count. If the command does not exist (should never + * happen) it returns 0. */ uint8_t getReplyDelayCycles(DeviceCommandId_t deviceCommand); @@ -878,20 +897,22 @@ 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 the STR has a different channel to send + * raw replies and overwrites it accordingly. * * @param data data to send * @param len length of @c data * @param sendTo the messageQueueId of the one to send to - * @param isCommand marks the raw data as a command, the message then will be of type raw_command + * @param isCommand marks the raw data as a command, the message then + * will be of type raw_command */ virtual void replyRawData(const uint8_t *data, size_t len, MessageQueueId_t sendTo, bool isCommand = false); /** - * Calls replyRawData() with #defaultRawReceiver, but checks if wiretapping is active and if so, - * does not send the Data as the wiretapping will have sent it already + * Calls replyRawData() with #defaultRawReceiver, but checks if wiretapping + * is active and if so, does not send the data as the wiretapping will have + * sent it already */ void replyRawReplyIfnotWiretapped(const uint8_t *data, size_t len); @@ -903,17 +924,19 @@ protected: /** * Enable the reply checking for a command * - * Is only called, if the command was sent (ie the getWriteReply was successful). - * Must ensure that all replies are activated and correctly linked to the command that initiated it. - * The default implementation looks for a reply with the same id as the command id in the replyMap or - * uses the alternativeReplyId if flagged so. - * When found, copies maxDelayCycles to delayCycles in the reply information and sets the command to - * expect one reply. + * Is only called, if the command was sent (i.e. the getWriteReply was + * successful). Must ensure that all replies are activated and correctly + * linked to the command that initiated it. + * The default implementation looks for a reply with the same id as the + * command id in the replyMap or uses the alternativeReplyId if flagged so. + * When found, copies maxDelayCycles to delayCycles in the reply information + * and sets the command to expect one reply. * * Can be overwritten by the child, if a command activates multiple replies * or replyId differs from commandId. * Notes for child implementations: - * - If the command was not found in the reply map, NO_REPLY_EXPECTED MUST be returned. + * - If the command was not found in the reply map, + * NO_REPLY_EXPECTED MUST be returned. * - A failure code may be returned if something went fundamentally wrong. * * @param deviceCommand @@ -929,17 +952,20 @@ protected: * get the state of the PCDU switches in the datapool * * @return - * - @c PowerSwitchIF::SWITCH_ON if all switches specified by #switches are on - * - @c PowerSwitchIF::SWITCH_OFF one of the switches specified by #switches are off - * - @c PowerSwitchIF::RETURN_FAILED if an error occured + * - @c PowerSwitchIF::SWITCH_ON if all switches specified + * by #switches are on + * - @c PowerSwitchIF::SWITCH_OFF one of the switches specified by + * #switches are off + * - @c PowerSwitchIF::RETURN_FAILED if an error occured */ ReturnValue_t getStateOfSwitches(void); /** - * set all datapool variables that are update periodically in normal mode invalid - * - * Child classes should provide an implementation which sets all those variables invalid - * which are set periodically during any normal mode. + * @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; @@ -949,11 +975,12 @@ protected: virtual void changeHK(Mode_t mode, Submode_t submode, bool enable); /** - * Children can overwrite this function to suppress checking of the command Queue + * Children can overwrite this function to suppress checking of the + * command Queue * - * This can be used when the child does not want to receive a command in a certain - * situation. Care must be taken that checking is not permanentely disabled as this - * would render the handler unusable. + * This can be used when the child does not want to receive a command in + * a certain situation. Care must be taken that checking is not + * permanentely disabled as this would render the handler unusable. * * @return whether checking the queue should NOT be done */ @@ -992,17 +1019,20 @@ protected: virtual void forwardEvent(Event event, uint32_t parameter1 = 0, uint32_t parameter2 = 0) const; /** - * Checks state of switches in conjunction with mode and triggers an event if they don't fit. + * Checks state of switches in conjunction with mode and triggers an event + * if they don't fit. */ virtual void checkSwitchState(); /** - * Reserved for the rare case where a device needs to perform additional operation cyclically in OFF mode. + * Reserved for the rare case where a device needs to perform additional + * operation cyclically in OFF mode. */ virtual void doOffActivity(); /** - * Reserved for the rare case where a device needs to perform additional operation cyclically in ON mode. + * Reserved for the rare case where a device needs to perform additional + * operation cyclically in ON mode. */ virtual void doOnActivity(); @@ -1043,9 +1073,10 @@ private: /** * Information about a cookie. * - * This is stored in a map for each cookie, to not only track the state, but also information - * about the sent command. Tracking this information is needed as - * the state of a commandId (waiting for reply) is done when a RMAP write reply is received. + * This is stored in a map for each cookie, to not only track the state, + * but also information about the sent command. Tracking this information + * is needed as the state of a commandId (waiting for reply) is done when a + * write reply is received. */ struct CookieInfo { CookieState_t state; @@ -1102,10 +1133,14 @@ private: /** * Handle the device handler mode. * - * - checks whether commands are valid for the current mode, rejects them accordingly - * - checks whether commanded mode transitions are required and calls handleCommandedModeTransition() - * - does the necessary action for the current mode or calls doChildStateMachine in modes @c MODE_TO_ON and @c MODE_TO_OFF - * - actions that happen in transitions (eg setting a timeout) are handled in setMode() + * - checks whether commands are valid for the current mode, rejects + * them accordingly + * - checks whether commanded mode transitions are required and calls + * handleCommandedModeTransition() + * - does the necessary action for the current mode or calls + * doChildStateMachine in modes @c MODE_TO_ON and @c MODE_TO_OFF + * - actions that happen in transitions (e.g. setting a timeout) are + * handled in setMode() */ void doStateMachine(void); @@ -1115,16 +1150,17 @@ private: /** * Decrement the counter for the timout of replies. * - * This is called at the beginning of each cycle. It checks whether a reply has timed out (that means a reply was expected - * but not received). + * This is called at the beginning of each cycle. It checks whether a + * reply has timed out (that means a reply was expected but not received). */ void decrementDeviceReplyMap(void); /** * Convenience function to handle a reply. * - * Called after scanForReply() has found a packet. Checks if the found id is in the #deviceCommandMap, if so, - * calls interpretDeviceReply(DeviceCommandId_t id, const uint8_t *packet) for further action. + * Called after scanForReply() has found a packet. Checks if the found ID + * is in the #deviceCommandMap, if so, calls + * #interpretDeviceReply for further action. * * It also resets the timeout counter for the command id. * @@ -1184,7 +1220,7 @@ private: * @param[out] len * @return * - @c RETURN_OK @c data is valid - * - @c RETURN_FAILED IPCStore is NULL + * - @c RETURN_FAILED IPCStore is nullptr * - the return value from the IPCStore if it was not @c RETURN_OK */ ReturnValue_t getStorageData(store_address_t storageAddress, uint8_t **data, @@ -1208,6 +1244,9 @@ private: void parseReply(const uint8_t* receivedData, size_t receivedDataLen); + + void handleTransitionToOnMode(Mode_t commandedMode, + Submode_t commandedSubmode); }; #endif /* FSFW_DEVICEHANDLERS_DEVICEHANDLERBASE_H_ */ From 46596f9397d7cea1a82a16f093117e64e133c919 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 8 Dec 2020 16:01:48 +0100 Subject: [PATCH 038/103] tab changed --- devicehandlers/DeviceHandlerBase.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/devicehandlers/DeviceHandlerBase.cpp b/devicehandlers/DeviceHandlerBase.cpp index 733106e5..f095834e 100644 --- a/devicehandlers/DeviceHandlerBase.cpp +++ b/devicehandlers/DeviceHandlerBase.cpp @@ -113,7 +113,7 @@ ReturnValue_t DeviceHandlerBase::performOperation(uint8_t counter) { doGetRead(); // This will be performed after datasets have been updated by the // custom device implementation. - hkManager.performHkOperation(); + hkManager.performHkOperation(); break; default: break; From ff62ab8427f84442cb14759e81fb03972caa7bfc Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 16:32:52 +0100 Subject: [PATCH 039/103] removed core component --- thermal/CoreComponent.cpp | 257 -------------------------------------- thermal/CoreComponent.h | 96 -------------- 2 files changed, 353 deletions(-) delete mode 100644 thermal/CoreComponent.cpp delete mode 100644 thermal/CoreComponent.h diff --git a/thermal/CoreComponent.cpp b/thermal/CoreComponent.cpp deleted file mode 100644 index 657e79cb..00000000 --- a/thermal/CoreComponent.cpp +++ /dev/null @@ -1,257 +0,0 @@ -#include "CoreComponent.h" - -CoreComponent::CoreComponent(object_id_t reportingObjectId, uint8_t domainId, - uint32_t temperaturePoolId, uint32_t targetStatePoolId, - uint32_t currentStatePoolId, uint32_t requestPoolId, GlobDataSet* dataSet, - AbstractTemperatureSensor* sensor, - AbstractTemperatureSensor* firstRedundantSensor, - AbstractTemperatureSensor* secondRedundantSensor, - ThermalModuleIF* thermalModule, Parameters parameters, - Priority priority, StateRequest initialTargetState) : - sensor(sensor), firstRedundantSensor(firstRedundantSensor), secondRedundantSensor( - secondRedundantSensor), thermalModule(thermalModule), temperature( - temperaturePoolId, dataSet, PoolVariableIF::VAR_WRITE), targetState( - targetStatePoolId, dataSet, PoolVariableIF::VAR_READ), currentState( - currentStatePoolId, dataSet, PoolVariableIF::VAR_WRITE), heaterRequest( - requestPoolId, dataSet, PoolVariableIF::VAR_WRITE), isHeating( - false), isSafeComponent(priority == SAFE), minTemp(999), maxTemp( - AbstractTemperatureSensor::ZERO_KELVIN_C), parameters( - parameters), temperatureMonitor(reportingObjectId, - domainId + 1, - GlobalDataPool::poolIdAndPositionToPid(temperaturePoolId, 0), - COMPONENT_TEMP_CONFIRMATION), domainId(domainId) { - if (thermalModule != NULL) { - thermalModule->registerComponent(this, priority); - } - //Set thermal state once, then leave to operator. - GlobDataSet mySet; - gp_uint8_t writableTargetState(targetStatePoolId, &mySet, - PoolVariableIF::VAR_WRITE); - writableTargetState = initialTargetState; - mySet.commit(PoolVariableIF::VALID); -} - -CoreComponent::~CoreComponent() { -} - -ThermalComponentIF::HeaterRequest CoreComponent::performOperation(uint8_t opCode) { - HeaterRequest request = HEATER_DONT_CARE; - //SHOULDDO: Better pass db_float_t* to getTemperature and set it invalid if invalid. - temperature = getTemperature(); - updateMinMaxTemp(); - if ((temperature != INVALID_TEMPERATURE)) { - temperature.setValid(PoolVariableIF::VALID); - State state = getState(temperature, getParameters(), targetState); - currentState = state; - checkLimits(state); - request = getHeaterRequest(targetState, temperature, getParameters()); - } else { - temperatureMonitor.setToInvalid(); - temperature.setValid(PoolVariableIF::INVALID); - currentState = UNKNOWN; - request = HEATER_DONT_CARE; - } - currentState.setValid(PoolVariableIF::VALID); - heaterRequest = request; - heaterRequest.setValid(PoolVariableIF::VALID); - return request; -} - -void CoreComponent::markStateIgnored() { - currentState = getIgnoredState(currentState); -} - -object_id_t CoreComponent::getObjectId() { - return temperatureMonitor.getReporterId(); -} - -float CoreComponent::getLowerOpLimit() { - return parameters.lowerOpLimit; -} - -ReturnValue_t CoreComponent::setTargetState(int8_t newState) { - GlobDataSet mySet; - gp_uint8_t writableTargetState(targetState.getDataPoolId(), - &mySet, PoolVariableIF::VAR_READ_WRITE); - mySet.read(); - if ((writableTargetState == STATE_REQUEST_OPERATIONAL) - && (newState != STATE_REQUEST_IGNORE)) { - return HasReturnvaluesIF::RETURN_FAILED; - } - switch (newState) { - case STATE_REQUEST_HEATING: - case STATE_REQUEST_IGNORE: - case STATE_REQUEST_OPERATIONAL: - writableTargetState = newState; - break; - case STATE_REQUEST_NON_OPERATIONAL: - default: - return INVALID_TARGET_STATE; - } - mySet.commit(PoolVariableIF::VALID); - return HasReturnvaluesIF::RETURN_OK; -} - -void CoreComponent::setOutputInvalid() { - temperature = INVALID_TEMPERATURE; - temperature.setValid(PoolVariableIF::INVALID); - currentState.setValid(PoolVariableIF::INVALID); - heaterRequest = HEATER_DONT_CARE; - heaterRequest.setValid(PoolVariableIF::INVALID); - temperatureMonitor.setToUnchecked(); -} - -float CoreComponent::getTemperature() { - if ((sensor != NULL) && (sensor->isValid())) { - return sensor->getTemperature(); - } - - if ((firstRedundantSensor != NULL) && (firstRedundantSensor->isValid())) { - return firstRedundantSensor->getTemperature(); - } - - if ((secondRedundantSensor != NULL) && (secondRedundantSensor->isValid())) { - return secondRedundantSensor->getTemperature(); - } - - if (thermalModule != NULL) { - float temperature = thermalModule->getTemperature(); - if (temperature != ThermalModuleIF::INVALID_TEMPERATURE) { - return temperature; - } else { - return INVALID_TEMPERATURE; - } - } else { - return INVALID_TEMPERATURE; - } -} - -ThermalComponentIF::State CoreComponent::getState(float temperature, - Parameters parameters, int8_t targetState) { - ThermalComponentIF::State state; - - if (temperature < parameters.lowerOpLimit) { - state = NON_OPERATIONAL_LOW; - } else if (temperature < parameters.upperOpLimit) { - state = OPERATIONAL; - } else { - state = NON_OPERATIONAL_HIGH; - } - if (targetState == STATE_REQUEST_IGNORE) { - state = getIgnoredState(state); - } - - return state; -} - -void CoreComponent::checkLimits(ThermalComponentIF::State state) { - //Checks operational limits only. - temperatureMonitor.translateState(state, temperature.value, - getParameters().lowerOpLimit, getParameters().upperOpLimit); - -} - -ThermalComponentIF::HeaterRequest CoreComponent::getHeaterRequest( - int8_t targetState, float temperature, Parameters parameters) { - if (targetState == STATE_REQUEST_IGNORE) { - isHeating = false; - return HEATER_DONT_CARE; - } - - if (temperature > parameters.upperOpLimit - parameters.heaterSwitchoff) { - isHeating = false; - return HEATER_REQUEST_EMERGENCY_OFF; - } - - float opHeaterLimit = parameters.lowerOpLimit + parameters.heaterOn; - - if (isHeating) { - opHeaterLimit += parameters.hysteresis; - } - - if (temperature < opHeaterLimit) { - isHeating = true; - return HEATER_REQUEST_EMERGENCY_ON; - } - isHeating = false; - return HEATER_DONT_CARE; -} - -ThermalComponentIF::State CoreComponent::getIgnoredState(int8_t state) { - switch (state) { - case NON_OPERATIONAL_LOW: - return NON_OPERATIONAL_LOW_IGNORED; - case OPERATIONAL: - return OPERATIONAL_IGNORED; - case NON_OPERATIONAL_HIGH: - return NON_OPERATIONAL_HIGH_IGNORED; - case NON_OPERATIONAL_LOW_IGNORED: - return NON_OPERATIONAL_LOW_IGNORED; - case OPERATIONAL_IGNORED: - return OPERATIONAL_IGNORED; - case NON_OPERATIONAL_HIGH_IGNORED: - return NON_OPERATIONAL_HIGH_IGNORED; - default: - case UNKNOWN: - return UNKNOWN; - } -} - -void CoreComponent::updateMinMaxTemp() { - if (temperature == INVALID_TEMPERATURE) { - return; - } - if (temperature < minTemp) { - minTemp = temperature; - } - if (temperature > maxTemp) { - maxTemp = temperature; - } -} - -uint8_t CoreComponent::getDomainId() const { - return domainId; -} - -CoreComponent::Parameters CoreComponent::getParameters() { - return parameters; -} - -ReturnValue_t CoreComponent::getParameter(uint8_t domainId, - uint16_t parameterId, ParameterWrapper* parameterWrapper, - const ParameterWrapper* newValues, uint16_t startAtIndex) { - ReturnValue_t result = temperatureMonitor.getParameter(domainId, - parameterId, parameterWrapper, newValues, startAtIndex); - if (result != INVALID_DOMAIN_ID) { - return result; - } - if (domainId != this->domainId) { - return INVALID_DOMAIN_ID; - } - switch (parameterId) { - case 0: - parameterWrapper->set(parameters.heaterOn); - break; - case 1: - parameterWrapper->set(parameters.hysteresis); - break; - case 2: - parameterWrapper->set(parameters.heaterSwitchoff); - break; - case 3: - parameterWrapper->set(minTemp); - break; - case 4: - parameterWrapper->set(maxTemp); - break; - case 10: - parameterWrapper->set(parameters.lowerOpLimit); - break; - case 11: - parameterWrapper->set(parameters.upperOpLimit); - break; - default: - return INVALID_MATRIX_ID; - } - return HasReturnvaluesIF::RETURN_OK; -} diff --git a/thermal/CoreComponent.h b/thermal/CoreComponent.h deleted file mode 100644 index 8093711d..00000000 --- a/thermal/CoreComponent.h +++ /dev/null @@ -1,96 +0,0 @@ -#ifndef MISSION_CONTROLLERS_TCS_CORECOMPONENT_H_ -#define MISSION_CONTROLLERS_TCS_CORECOMPONENT_H_ - -#include "../datapoolglob/GlobalDataSet.h" -#include "../datapoolglob/GlobalPoolVariable.h" -#include "../thermal/ThermalComponentIF.h" -#include "../thermal/AbstractTemperatureSensor.h" -#include "../thermal/ThermalModule.h" -#include "../thermal/ThermalMonitor.h" - -// TODO: Documentaiton, how to use this? only use Thermal Component, which inherits core component? -class CoreComponent: public ThermalComponentIF { -public: - struct Parameters { - float lowerOpLimit; - float upperOpLimit; - float heaterOn; - float hysteresis; - float heaterSwitchoff; - }; - - static const uint16_t COMPONENT_TEMP_CONFIRMATION = 5; - - CoreComponent(object_id_t reportingObjectId, uint8_t domainId, uint32_t temperaturePoolId, - uint32_t targetStatePoolId, uint32_t currentStatePoolId, - uint32_t requestPoolId, GlobDataSet *dataSet, - AbstractTemperatureSensor *sensor, - AbstractTemperatureSensor *firstRedundantSensor, - AbstractTemperatureSensor *secondRedundantSensor, - ThermalModuleIF *thermalModule, Parameters parameters, - Priority priority, StateRequest initialTargetState = - ThermalComponentIF::STATE_REQUEST_OPERATIONAL); - - virtual ~CoreComponent(); - - virtual HeaterRequest performOperation(uint8_t opCode); - - void markStateIgnored(); - - object_id_t getObjectId(); - - uint8_t getDomainId() const; - - virtual float getLowerOpLimit(); - - ReturnValue_t setTargetState(int8_t newState); - - virtual void setOutputInvalid(); - - virtual ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, - ParameterWrapper *parameterWrapper, - const ParameterWrapper *newValues, uint16_t startAtIndex); - -protected: - - AbstractTemperatureSensor *sensor; - AbstractTemperatureSensor *firstRedundantSensor; - AbstractTemperatureSensor *secondRedundantSensor; - ThermalModuleIF *thermalModule; - - gp_float_t temperature; - gp_int8_t targetState; - gp_int8_t currentState; - gp_uint8_t heaterRequest; - - bool isHeating; - - bool isSafeComponent; - - float minTemp; - - float maxTemp; - - Parameters parameters; - - ThermalMonitor temperatureMonitor; - - const uint8_t domainId; - - virtual float getTemperature(); - virtual State getState(float temperature, Parameters parameters, - int8_t targetState); - - virtual void checkLimits(State state); - - virtual HeaterRequest getHeaterRequest(int8_t targetState, - float temperature, Parameters parameters); - - virtual State getIgnoredState(int8_t state); - - void updateMinMaxTemp(); - - virtual Parameters getParameters(); -}; - -#endif /* MISSION_CONTROLLERS_TCS_CORECOMPONENT_H_ */ From 0a5099e293acc10407dcfe8078fddca303b901a3 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 16:34:25 +0100 Subject: [PATCH 040/103] deleted file which was renamed --- thermal/ThermalMonitor.cpp | 68 -------------------------------------- thermal/ThermalMonitor.h | 23 ------------- 2 files changed, 91 deletions(-) delete mode 100644 thermal/ThermalMonitor.cpp delete mode 100644 thermal/ThermalMonitor.h diff --git a/thermal/ThermalMonitor.cpp b/thermal/ThermalMonitor.cpp deleted file mode 100644 index 11abfbe5..00000000 --- a/thermal/ThermalMonitor.cpp +++ /dev/null @@ -1,68 +0,0 @@ -#include "ThermalMonitor.h" -#include "ThermalComponentIF.h" -#include "../monitoring/MonitoringIF.h" -ThermalMonitor::~ThermalMonitor() { -} - -void ThermalMonitor::sendTransitionEvent(float currentValue, - ReturnValue_t state) { - switch (state) { - case MonitoringIF::BELOW_LOW_LIMIT: - EventManagerIF::triggerEvent(reportingId, - ThermalComponentIF::COMPONENT_TEMP_OOL_LOW, state); - break; - case MonitoringIF::ABOVE_HIGH_LIMIT: - EventManagerIF::triggerEvent(reportingId, - ThermalComponentIF::COMPONENT_TEMP_OOL_HIGH, state); - break; - case ThermalComponentIF::BELOW_OPERATIONAL_LIMIT: - EventManagerIF::triggerEvent(reportingId, - ThermalComponentIF::COMPONENT_TEMP_LOW, state); - break; - case ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT: - EventManagerIF::triggerEvent(reportingId, - ThermalComponentIF::COMPONENT_TEMP_HIGH, state); - break; - default: - break; - } -} - -bool ThermalMonitor::isAboveHighLimit() { - if (oldState == ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT) { - return true; - } else { - return false; - } -} - -ReturnValue_t ThermalMonitor::translateState(ThermalComponentIF::State state, float sample, float lowerLimit, - float upperLimit, bool componentIsOperational) { - if (ThermalComponentIF::isIgnoredState(state)) { - setToUnchecked(); - return MonitoringIF::UNCHECKED; - } - switch (state) { - case ThermalComponentIF::OUT_OF_RANGE_LOW: - return monitorStateIs(MonitoringIF::BELOW_LOW_LIMIT, sample, lowerLimit); - case ThermalComponentIF::NON_OPERATIONAL_LOW: - if (componentIsOperational) { - return monitorStateIs(ThermalComponentIF::BELOW_OPERATIONAL_LIMIT, sample, lowerLimit); - } else { - return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); - } - case ThermalComponentIF::OPERATIONAL: - return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); - case ThermalComponentIF::NON_OPERATIONAL_HIGH: - if (componentIsOperational) { - return monitorStateIs(ThermalComponentIF::ABOVE_OPERATIONAL_LIMIT, sample, upperLimit); - } else { - return monitorStateIs(HasReturnvaluesIF::RETURN_OK, sample, 0.0); - } - case ThermalComponentIF::OUT_OF_RANGE_HIGH: - return monitorStateIs(MonitoringIF::ABOVE_HIGH_LIMIT, sample, upperLimit); - default: - //Never reached, all states covered. - return HasReturnvaluesIF::RETURN_FAILED; - } -} diff --git a/thermal/ThermalMonitor.h b/thermal/ThermalMonitor.h deleted file mode 100644 index 5c6806c1..00000000 --- a/thermal/ThermalMonitor.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef FRAMEWORK_THERMAL_THERMALMONITOR_H_ -#define FRAMEWORK_THERMAL_THERMALMONITOR_H_ - -#include "../monitoring/MonitorReporter.h" -#include "ThermalComponentIF.h" - -class ThermalMonitor: public MonitorReporter { -public: - template - ThermalMonitor(Args ... args) : - MonitorReporter(std::forward(args)...) { - } - ~ThermalMonitor(); - ReturnValue_t translateState(ThermalComponentIF::State state, float sample, - float lowerLimit, float upperLimit, bool componentIsOperational = true); - - bool isAboveHighLimit(); -protected: - virtual void sendTransitionEvent(float currentValue, ReturnValue_t state); - -}; - -#endif /* FRAMEWORK_THERMAL_THERMALMONITOR_H_ */ From f81c9d7ecc54442eeabfae066f4fafc7feae7698 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 16:36:09 +0100 Subject: [PATCH 041/103] resolved merge conflicts --- thermal/ThermalModule.cpp | 28 ---------------------------- 1 file changed, 28 deletions(-) diff --git a/thermal/ThermalModule.cpp b/thermal/ThermalModule.cpp index cc541c8c..2bc1741f 100644 --- a/thermal/ThermalModule.cpp +++ b/thermal/ThermalModule.cpp @@ -5,15 +5,9 @@ #include "../monitoring/MonitoringMessageContent.h" -<<<<<<< HEAD ThermalModule::ThermalModule(gp_id_t moduleTemperaturePoolId, gp_id_t currentStatePoolId, gp_id_t targetStatePoolId, LocalPoolDataSetBase *dataSet, Parameters parameters, -======= -ThermalModule::ThermalModule(uint32_t moduleTemperaturePoolId, - uint32_t currentStatePoolId, uint32_t targetStatePoolId, - GlobDataSet *dataSet, Parameters parameters, ->>>>>>> upstream/development RedundantHeater::Parameters heaterParameters) : oldStrategy(ACTIVE_SINGLE), parameters(parameters), moduleTemperature(moduleTemperaturePoolId, dataSet, @@ -23,7 +17,6 @@ ThermalModule::ThermalModule(uint32_t moduleTemperaturePoolId, heater = new RedundantHeater(heaterParameters); } -<<<<<<< HEAD ThermalModule::ThermalModule(gp_id_t moduleTemperaturePoolId, LocalPoolDataSetBase* dataSet) : oldStrategy(ACTIVE_SINGLE), parameters( { 0, 0 }), @@ -33,15 +26,6 @@ ThermalModule::ThermalModule(gp_id_t moduleTemperaturePoolId, PoolVariableIF::VAR_WRITE), targetState(gp_id_t(), dataSet, PoolVariableIF::VAR_READ) { -======= -ThermalModule::ThermalModule(uint32_t moduleTemperaturePoolId, GlobDataSet* dataSet) : - oldStrategy(ACTIVE_SINGLE), survivalTargetTemp(0), targetTemp(0), heating( - false), parameters( { 0, 0 }), moduleTemperature( - moduleTemperaturePoolId, dataSet, PoolVariableIF::VAR_WRITE), heater( - NULL), currentState(PoolVariableIF::INVALID, dataSet, - PoolVariableIF::VAR_WRITE), targetState(PoolVariableIF::INVALID, - dataSet, PoolVariableIF::VAR_READ) { ->>>>>>> upstream/development } ThermalModule::~ThermalModule() { @@ -272,7 +256,6 @@ bool ThermalModule::calculateModuleHeaterRequestAndSetModuleStatus( } void ThermalModule::setHeating(bool on) { -<<<<<<< HEAD // GlobDataSet mySet; // gp_int8_t writableTargetState(targetState.getDataPoolId(), // &mySet, PoolVariableIF::VAR_WRITE); @@ -282,17 +265,6 @@ void ThermalModule::setHeating(bool on) { // writableTargetState = STATE_REQUEST_PASSIVE; // } // mySet.commit(PoolVariableIF::VALID); -======= - GlobDataSet mySet; - gp_int8_t writableTargetState(targetState.getDataPoolId(), - &mySet, PoolVariableIF::VAR_WRITE); - if (on) { - writableTargetState = STATE_REQUEST_HEATING; - } else { - writableTargetState = STATE_REQUEST_PASSIVE; - } - mySet.commit(PoolVariableIF::VALID); ->>>>>>> upstream/development } void ThermalModule::updateTargetTemperatures(ThermalComponentIF* component, From be9913f262e879f8c264f54550d61e983fddc1e5 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 16:40:22 +0100 Subject: [PATCH 042/103] themral module update --- thermal/ThermalModule.cpp | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/thermal/ThermalModule.cpp b/thermal/ThermalModule.cpp index 2bc1741f..457a6743 100644 --- a/thermal/ThermalModule.cpp +++ b/thermal/ThermalModule.cpp @@ -256,15 +256,16 @@ bool ThermalModule::calculateModuleHeaterRequestAndSetModuleStatus( } void ThermalModule::setHeating(bool on) { -// GlobDataSet mySet; -// gp_int8_t writableTargetState(targetState.getDataPoolId(), -// &mySet, PoolVariableIF::VAR_WRITE); -// if (on) { -// writableTargetState = STATE_REQUEST_HEATING; -// } else { -// writableTargetState = STATE_REQUEST_PASSIVE; -// } -// mySet.commit(PoolVariableIF::VALID); + ReturnValue_t result = targetState.read(); + if(result == HasReturnvaluesIF::RETURN_OK) { + if(on) { + targetState.value = STATE_REQUEST_HEATING; + } + else { + targetState.value = STATE_REQUEST_PASSIVE; + } + } + targetState.setValid(true); } void ThermalModule::updateTargetTemperatures(ThermalComponentIF* component, From 50ad2c03809502d9494e37bff99a54bf39fc024c Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 16:57:43 +0100 Subject: [PATCH 043/103] resolved merge conflicts --- power/Fuse.h | 24 +----------------------- 1 file changed, 1 insertion(+), 23 deletions(-) diff --git a/power/Fuse.h b/power/Fuse.h index 8a1b29f0..b892611b 100644 --- a/power/Fuse.h +++ b/power/Fuse.h @@ -1,21 +1,11 @@ #ifndef FSFW_POWER_FUSE_H_ #define FSFW_POWER_FUSE_H_ -<<<<<<< HEAD #include "PowerComponentIF.h" #include "PowerSwitchIF.h" #include "../devicehandlers/HealthDevice.h" #include "../monitoring/AbsLimitMonitor.h" -======= -#include "../datapoolglob/GlobalDataSet.h" -#include "../datapoolglob/GlobalPoolVariable.h" -#include "../datapoolglob/PIDReader.h" -#include "../devicehandlers/HealthDevice.h" -#include "../monitoring/AbsLimitMonitor.h" -#include "../power/PowerComponentIF.h" -#include "../power/PowerSwitchIF.h" ->>>>>>> upstream/development #include "../returnvalues/HasReturnvaluesIF.h" #include "../parameters/ParameterHelper.h" #include @@ -94,26 +84,14 @@ private: }; PowerMonitor powerMonitor; -<<<<<<< HEAD StaticLocalDataSet<3> set; - //LocalPoolDataSetBase* set = nullptr; - //PIDReader voltage; - //PIDReader current; - //PIDReader state; + lp_var_t voltage; lp_var_t current; lp_var_t state; lp_var_t power; MessageQueueIF* commandQueue = nullptr; -======= - GlobDataSet set; - PIDReader voltage; - PIDReader current; - PIDReader state; - gp_float_t power; - MessageQueueIF* commandQueue; ->>>>>>> upstream/development ParameterHelper parameterHelper; HealthHelper healthHelper; static object_id_t powerSwitchId; From a2823835dd8f6708fd004aef2d95d74547c7cdf7 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 17:05:41 +0100 Subject: [PATCH 044/103] explicit cast added --- parameters/ParameterWrapper.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/parameters/ParameterWrapper.cpp b/parameters/ParameterWrapper.cpp index 23955516..d9f1ef68 100644 --- a/parameters/ParameterWrapper.cpp +++ b/parameters/ParameterWrapper.cpp @@ -123,7 +123,8 @@ ReturnValue_t ParameterWrapper::deSerializeData(uint8_t startingRow, for (uint8_t fromRow = 0; fromRow < fromRows; fromRow++) { //get the start element of this row in data - uint16_t offset = (((startingRow + fromRow) * columns) + startingColumn); + uint16_t offset = (((startingRow + fromRow) * + static_cast(columns)) + startingColumn); T *dataWithDataType = static_cast(data) + offset; for (uint8_t fromColumn = 0; fromColumn < fromColumns; fromColumn++) { @@ -296,8 +297,8 @@ ReturnValue_t ParameterWrapper::copyFrom(const ParameterWrapper *from, //need a type to do arithmetic uint8_t* typedData = static_cast(data); for (uint8_t fromRow = 0; fromRow < from->rows; fromRow++) { - size_t offset = (((startingRow + fromRow) * columns) + - startingColumn) * typeSize; + size_t offset = (((startingRow + fromRow) * static_cast( + columns)) + startingColumn) * typeSize; std::memcpy(typedData + offset, from->readonlyData, typeSize * from->columns); } From 7986584d17d65da8ed06fc217b216472e0cc12da Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 17:18:46 +0100 Subject: [PATCH 045/103] updated comment --- devicehandlers/DeviceHandlerBase.h | 1 + 1 file changed, 1 insertion(+) diff --git a/devicehandlers/DeviceHandlerBase.h b/devicehandlers/DeviceHandlerBase.h index 2bfa62a6..9a5287e0 100644 --- a/devicehandlers/DeviceHandlerBase.h +++ b/devicehandlers/DeviceHandlerBase.h @@ -746,6 +746,7 @@ protected: /** * Helper function to get pending command. This is useful for devices * like SPI sensors to identify the last sent command. + * This only returns the command sent in the last SEND_WRITE cycle. * @return */ DeviceCommandId_t getPendingCommand() const; From bb7ebf4b275331db5181826e8be33088170f9a8d Mon Sep 17 00:00:00 2001 From: Spacefish Date: Thu, 10 Dec 2020 17:29:23 +0100 Subject: [PATCH 046/103] removed glob pool --- datapoolglob/ControllerSet.cpp | 14 - datapoolglob/ControllerSet.h | 15 -- datapoolglob/DataPoolAdmin.cpp | 301 ---------------------- datapoolglob/DataPoolAdmin.h | 60 ----- datapoolglob/DataPoolParameterWrapper.cpp | 179 ------------- datapoolglob/DataPoolParameterWrapper.h | 38 --- datapoolglob/GlobalDataPool.cpp | 133 ---------- datapoolglob/GlobalDataPool.h | 149 ----------- datapoolglob/GlobalDataSet.cpp | 48 ---- datapoolglob/GlobalDataSet.h | 98 ------- datapoolglob/GlobalPoolVariable.h | 213 --------------- datapoolglob/GlobalPoolVariable.tpp | 117 --------- datapoolglob/GlobalPoolVector.h | 185 ------------- datapoolglob/GlobalPoolVector.tpp | 117 --------- datapoolglob/PIDReader.h | 164 ------------ datapoolglob/PIDReaderList.h | 27 -- datapoolglob/PoolRawAccess.cpp | 239 ----------------- datapoolglob/PoolRawAccess.h | 220 ---------------- 18 files changed, 2317 deletions(-) delete mode 100644 datapoolglob/ControllerSet.cpp delete mode 100644 datapoolglob/ControllerSet.h delete mode 100644 datapoolglob/DataPoolAdmin.cpp delete mode 100644 datapoolglob/DataPoolAdmin.h delete mode 100644 datapoolglob/DataPoolParameterWrapper.cpp delete mode 100644 datapoolglob/DataPoolParameterWrapper.h delete mode 100644 datapoolglob/GlobalDataPool.cpp delete mode 100644 datapoolglob/GlobalDataPool.h delete mode 100644 datapoolglob/GlobalDataSet.cpp delete mode 100644 datapoolglob/GlobalDataSet.h delete mode 100644 datapoolglob/GlobalPoolVariable.h delete mode 100644 datapoolglob/GlobalPoolVariable.tpp delete mode 100644 datapoolglob/GlobalPoolVector.h delete mode 100644 datapoolglob/GlobalPoolVector.tpp delete mode 100644 datapoolglob/PIDReader.h delete mode 100644 datapoolglob/PIDReaderList.h delete mode 100644 datapoolglob/PoolRawAccess.cpp delete mode 100644 datapoolglob/PoolRawAccess.h diff --git a/datapoolglob/ControllerSet.cpp b/datapoolglob/ControllerSet.cpp deleted file mode 100644 index 54fc6e8c..00000000 --- a/datapoolglob/ControllerSet.cpp +++ /dev/null @@ -1,14 +0,0 @@ -#include - -ControllerSet::ControllerSet() { - -} - -ControllerSet::~ControllerSet() { -} - -void ControllerSet::setInvalid() { - read(); - setToDefault(); - commit(PoolVariableIF::INVALID); -} diff --git a/datapoolglob/ControllerSet.h b/datapoolglob/ControllerSet.h deleted file mode 100644 index 5da11397..00000000 --- a/datapoolglob/ControllerSet.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef FSFW_DATAPOOLGLOB_CONTROLLERSET_H_ -#define FSFW_DATAPOOLGLOB_CONTROLLERSET_H_ - -#include "../datapoolglob/GlobalDataSet.h" - -class ControllerSet :public GlobDataSet { -public: - ControllerSet(); - virtual ~ControllerSet(); - - virtual void setToDefault() = 0; - void setInvalid(); -}; - -#endif /* FSFW_DATAPOOLGLOB_CONTROLLERSET_H_ */ diff --git a/datapoolglob/DataPoolAdmin.cpp b/datapoolglob/DataPoolAdmin.cpp deleted file mode 100644 index 6ede0841..00000000 --- a/datapoolglob/DataPoolAdmin.cpp +++ /dev/null @@ -1,301 +0,0 @@ -#include "DataPoolAdmin.h" -#include "GlobalDataSet.h" -#include "GlobalDataPool.h" -#include "PoolRawAccess.h" - -#include "../ipc/CommandMessage.h" -#include "../ipc/QueueFactory.h" -#include "../parameters/ParameterMessage.h" - -DataPoolAdmin::DataPoolAdmin(object_id_t objectId) : - SystemObject(objectId), storage(NULL), commandQueue(NULL), memoryHelper( - this, NULL), actionHelper(this, NULL) { - commandQueue = QueueFactory::instance()->createMessageQueue(); -} - -DataPoolAdmin::~DataPoolAdmin() { - QueueFactory::instance()->deleteMessageQueue(commandQueue); -} - -ReturnValue_t DataPoolAdmin::performOperation(uint8_t opCode) { - handleCommand(); - return RETURN_OK; -} - -MessageQueueId_t DataPoolAdmin::getCommandQueue() const { - return commandQueue->getId(); -} - -ReturnValue_t DataPoolAdmin::executeAction(ActionId_t actionId, - MessageQueueId_t commandedBy, const uint8_t* data, size_t size) { - if (actionId != SET_VALIDITY) { - return INVALID_ACTION_ID; - } - - if (size != 5) { - return INVALID_PARAMETERS; - } - - uint32_t address = (data[0] << 24) | (data[1] << 16) | (data[2] << 8) - | data[3]; - - uint8_t valid = data[4]; - - uint32_t poolId = glob::dataPool.PIDToDataPoolId(address); - - GlobDataSet mySet; - PoolRawAccess variable(poolId, 0, &mySet, PoolVariableIF::VAR_READ_WRITE); - ReturnValue_t status = mySet.read(); - if (status != RETURN_OK) { - return INVALID_ADDRESS; - } - if (valid != 0) { - variable.setValid(PoolVariableIF::VALID); - } else { - variable.setValid(PoolVariableIF::INVALID); - } - - mySet.commit(); - - return EXECUTION_FINISHED; -} - -ReturnValue_t DataPoolAdmin::getParameter(uint8_t domainId, - uint16_t parameterId, ParameterWrapper* parameterWrapper, - const ParameterWrapper* newValues, uint16_t startAtIndex) { - return HasReturnvaluesIF::RETURN_FAILED; -} - -void DataPoolAdmin::handleCommand() { - CommandMessage command; - ReturnValue_t result = commandQueue->receiveMessage(&command); - if (result != RETURN_OK) { - return; - } - - result = actionHelper.handleActionMessage(&command); - - if (result == HasReturnvaluesIF::RETURN_OK) { - return; - } - - result = handleParameterCommand(&command); - if (result == HasReturnvaluesIF::RETURN_OK) { - return; - } - - result = memoryHelper.handleMemoryCommand(&command); - if (result != RETURN_OK) { - command.setToUnknownCommand(); - commandQueue->reply(&command); - } -} - -ReturnValue_t DataPoolAdmin::handleMemoryLoad(uint32_t address, - const uint8_t* data, size_t size, uint8_t** dataPointer) { - uint32_t poolId = glob::dataPool.PIDToDataPoolId(address); - uint8_t arrayIndex = glob::dataPool.PIDToArrayIndex(address); - GlobDataSet testSet; - PoolRawAccess varToGetSize(poolId, arrayIndex, &testSet, - PoolVariableIF::VAR_READ); - ReturnValue_t status = testSet.read(); - if (status != RETURN_OK) { - return INVALID_ADDRESS; - } - uint8_t typeSize = varToGetSize.getSizeOfType(); - - if (size % typeSize != 0) { - return INVALID_SIZE; - } - - if (size > varToGetSize.getSizeTillEnd()) { - return INVALID_SIZE; - } - const uint8_t* readPosition = data; - - for (; size > 0; size -= typeSize) { - GlobDataSet rawSet; - PoolRawAccess variable(poolId, arrayIndex, &rawSet, - PoolVariableIF::VAR_READ_WRITE); - status = rawSet.read(); - if (status == RETURN_OK) { - status = variable.setEntryFromBigEndian(readPosition, typeSize); - if (status == RETURN_OK) { - status = rawSet.commit(); - } - } - arrayIndex += 1; - readPosition += typeSize; - } - return ACTIVITY_COMPLETED; -} - -ReturnValue_t DataPoolAdmin::handleMemoryDump(uint32_t address, size_t size, - uint8_t** dataPointer, uint8_t* copyHere) { - uint32_t poolId = glob::dataPool.PIDToDataPoolId(address); - uint8_t arrayIndex = glob::dataPool.PIDToArrayIndex(address); - GlobDataSet testSet; - PoolRawAccess varToGetSize(poolId, arrayIndex, &testSet, - PoolVariableIF::VAR_READ); - ReturnValue_t status = testSet.read(); - if (status != RETURN_OK) { - return INVALID_ADDRESS; - } - uint8_t typeSize = varToGetSize.getSizeOfType(); - if (size > varToGetSize.getSizeTillEnd()) { - return INVALID_SIZE; - } - uint8_t* ptrToCopy = copyHere; - for (; size > 0; size -= typeSize) { - GlobDataSet rawSet; - PoolRawAccess variable(poolId, arrayIndex, &rawSet, - PoolVariableIF::VAR_READ); - status = rawSet.read(); - if (status == RETURN_OK) { - size_t temp = 0; - status = variable.getEntryEndianSafe(ptrToCopy, &temp, size); - if (status != RETURN_OK) { - return RETURN_FAILED; - } - } else { - //Error reading parameter. - } - arrayIndex += 1; - ptrToCopy += typeSize; - } - return ACTIVITY_COMPLETED; -} - -ReturnValue_t DataPoolAdmin::initialize() { - ReturnValue_t result = SystemObject::initialize(); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - result = memoryHelper.initialize(commandQueue); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - storage = objectManager->get(objects::IPC_STORE); - if (storage == NULL) { - return HasReturnvaluesIF::RETURN_FAILED; - } - - result = actionHelper.initialize(commandQueue); - - return result; -} - -//mostly identical to ParameterHelper::handleParameterMessage() -ReturnValue_t DataPoolAdmin::handleParameterCommand(CommandMessage* command) { - ReturnValue_t result = HasReturnvaluesIF::RETURN_FAILED; - switch (command->getCommand()) { - case ParameterMessage::CMD_PARAMETER_DUMP: { - uint8_t domain = HasParametersIF::getDomain( - ParameterMessage::getParameterId(command)); - uint16_t parameterId = HasParametersIF::getMatrixId( - ParameterMessage::getParameterId(command)); - - DataPoolParameterWrapper wrapper; - result = wrapper.set(domain, parameterId); - - if (result == HasReturnvaluesIF::RETURN_OK) { - result = sendParameter(command->getSender(), - ParameterMessage::getParameterId(command), &wrapper); - } - } - break; - case ParameterMessage::CMD_PARAMETER_LOAD: { - - uint8_t domain = HasParametersIF::getDomain( - ParameterMessage::getParameterId(command)); - uint16_t parameterId = HasParametersIF::getMatrixId( - ParameterMessage::getParameterId(command)); - uint8_t index = HasParametersIF::getIndex( - ParameterMessage::getParameterId(command)); - - const uint8_t *storedStream; - size_t storedStreamSize; - result = storage->getData(ParameterMessage::getStoreId(command), - &storedStream, &storedStreamSize); - if (result != HasReturnvaluesIF::RETURN_OK) { - break; - } - - ParameterWrapper streamWrapper; - result = streamWrapper.set(storedStream, storedStreamSize); - if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(ParameterMessage::getStoreId(command)); - break; - } - - DataPoolParameterWrapper poolWrapper; - result = poolWrapper.set(domain, parameterId); - if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(ParameterMessage::getStoreId(command)); - break; - } - - result = poolWrapper.copyFrom(&streamWrapper, index); - - storage->deleteData(ParameterMessage::getStoreId(command)); - - if (result == HasReturnvaluesIF::RETURN_OK) { - result = sendParameter(command->getSender(), - ParameterMessage::getParameterId(command), &poolWrapper); - } - } - break; - default: - return HasReturnvaluesIF::RETURN_FAILED; - } - - if (result != HasReturnvaluesIF::RETURN_OK) { - rejectCommand(command->getSender(), result, command->getCommand()); - } - - return HasReturnvaluesIF::RETURN_OK; - -} - -//identical to ParameterHelper::sendParameter() -ReturnValue_t DataPoolAdmin::sendParameter(MessageQueueId_t to, uint32_t id, - const DataPoolParameterWrapper* wrapper) { - size_t serializedSize = wrapper->getSerializedSize(); - - uint8_t *storeElement; - store_address_t address; - - ReturnValue_t result = storage->getFreeElement(&address, serializedSize, - &storeElement); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - size_t storeElementSize = 0; - - result = wrapper->serialize(&storeElement, &storeElementSize, - serializedSize, SerializeIF::Endianness::BIG); - - if (result != HasReturnvaluesIF::RETURN_OK) { - storage->deleteData(address); - return result; - } - - CommandMessage reply; - - ParameterMessage::setParameterDumpReply(&reply, id, address); - - commandQueue->sendMessage(to, &reply); - - return HasReturnvaluesIF::RETURN_OK; -} - -//identical to ParameterHelper::rejectCommand() -void DataPoolAdmin::rejectCommand(MessageQueueId_t to, ReturnValue_t reason, - Command_t initialCommand) { - CommandMessage reply; - reply.setReplyRejected(reason, initialCommand); - commandQueue->sendMessage(to, &reply); -} diff --git a/datapoolglob/DataPoolAdmin.h b/datapoolglob/DataPoolAdmin.h deleted file mode 100644 index d8871b65..00000000 --- a/datapoolglob/DataPoolAdmin.h +++ /dev/null @@ -1,60 +0,0 @@ -#ifndef FSFW_DATAPOOLGLOB_DATAPOOLADMIN_H_ -#define FSFW_DATAPOOLGLOB_DATAPOOLADMIN_H_ - -#include "DataPoolParameterWrapper.h" - -#include "../objectmanager/SystemObject.h" -#include "../returnvalues/HasReturnvaluesIF.h" -#include "../tasks/ExecutableObjectIF.h" -#include "../action/HasActionsIF.h" -#include "../ipc/MessageQueueIF.h" -#include "../parameters/ReceivesParameterMessagesIF.h" -#include "../action/SimpleActionHelper.h" -#include "../memory/MemoryHelper.h" - - -class DataPoolAdmin: public HasActionsIF, - public ExecutableObjectIF, - public AcceptsMemoryMessagesIF, - public HasReturnvaluesIF, - public ReceivesParameterMessagesIF, - public SystemObject { -public: - static const ActionId_t SET_VALIDITY = 1; - - DataPoolAdmin(object_id_t objectId); - - ~DataPoolAdmin(); - - ReturnValue_t performOperation(uint8_t opCode); - - MessageQueueId_t getCommandQueue() const; - - ReturnValue_t handleMemoryLoad(uint32_t address, const uint8_t* data, - size_t size, uint8_t** dataPointer); - ReturnValue_t handleMemoryDump(uint32_t address, size_t size, - uint8_t** dataPointer, uint8_t* copyHere); - - ReturnValue_t executeAction(ActionId_t actionId, - MessageQueueId_t commandedBy, const uint8_t* data, size_t size); - - //not implemented as ParameterHelper is no used - ReturnValue_t getParameter(uint8_t domainId, uint16_t parameterId, - ParameterWrapper *parameterWrapper, - const ParameterWrapper *newValues, uint16_t startAtIndex); - - ReturnValue_t initialize(); -private: - StorageManagerIF *storage; - MessageQueueIF* commandQueue; - MemoryHelper memoryHelper; - SimpleActionHelper actionHelper; - void handleCommand(); - ReturnValue_t handleParameterCommand(CommandMessage *command); - ReturnValue_t sendParameter(MessageQueueId_t to, uint32_t id, - const DataPoolParameterWrapper* wrapper); - void rejectCommand(MessageQueueId_t to, ReturnValue_t reason, - Command_t initialCommand); -}; - -#endif /* FSFW_DATAPOOLGLOB_DATAPOOLADMIN_H_ */ diff --git a/datapoolglob/DataPoolParameterWrapper.cpp b/datapoolglob/DataPoolParameterWrapper.cpp deleted file mode 100644 index 3a57d90d..00000000 --- a/datapoolglob/DataPoolParameterWrapper.cpp +++ /dev/null @@ -1,179 +0,0 @@ -#include "../datapoolglob/GlobalDataSet.h" -#include "../datapoolglob/DataPoolParameterWrapper.h" -#include "../datapoolglob/PoolRawAccess.h" -#include "../parameters/HasParametersIF.h" - - -DataPoolParameterWrapper::DataPoolParameterWrapper() : - type(Type::UNKNOWN_TYPE), rows(0), columns(0), poolId( - PoolVariableIF::NO_PARAMETER) { - -} - -DataPoolParameterWrapper::~DataPoolParameterWrapper() { - -} - -ReturnValue_t DataPoolParameterWrapper::set(uint8_t domainId, - uint16_t parameterId) { - poolId = (domainId << 16) + parameterId; - - GlobDataSet mySet; - PoolRawAccess raw(poolId, 0, &mySet, PoolVariableIF::VAR_READ); - ReturnValue_t status = mySet.read(); - if (status != HasReturnvaluesIF::RETURN_OK) { - //should only fail for invalid pool id - return HasParametersIF::INVALID_MATRIX_ID; - } - - type = raw.getType(); - rows = raw.getArraySize(); - columns = 1; - - return HasReturnvaluesIF::RETURN_OK; -} - -ReturnValue_t DataPoolParameterWrapper::serialize(uint8_t** buffer, - size_t* size, size_t maxSize, Endianness streamEndianness) const { - ReturnValue_t result; - - result = SerializeAdapter::serialize(&type, buffer, size, maxSize, - streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - result = SerializeAdapter::serialize(&columns, buffer, size, - maxSize, streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = SerializeAdapter::serialize(&rows, buffer, size, maxSize, - streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - for (uint8_t index = 0; index < rows; index++){ - GlobDataSet mySet; - PoolRawAccess raw(poolId, index, &mySet,PoolVariableIF::VAR_READ); - mySet.read(); - result = raw.serialize(buffer,size,maxSize,streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK){ - return result; - } - } - return HasReturnvaluesIF::RETURN_OK; -} - -//same as ParameterWrapper -size_t DataPoolParameterWrapper::getSerializedSize() const { - size_t serializedSize = 0; - serializedSize += type.getSerializedSize(); - serializedSize += sizeof(rows); - serializedSize += sizeof(columns); - serializedSize += rows * columns * type.getSize(); - - return serializedSize; -} - -ReturnValue_t DataPoolParameterWrapper::deSerialize(const uint8_t** buffer, - size_t* size, Endianness streamEndianness) { - return HasReturnvaluesIF::RETURN_FAILED; -} - -template -ReturnValue_t DataPoolParameterWrapper::deSerializeData(uint8_t startingRow, - uint8_t startingColumn, const void* from, uint8_t fromRows) { - //treat from as a continuous Stream as we copy all of it - const uint8_t *fromAsStream = (const uint8_t *) from; - - ReturnValue_t result = HasReturnvaluesIF::RETURN_OK; - - for (uint8_t fromRow = 0; fromRow < fromRows; fromRow++) { - - GlobDataSet mySet; - PoolRawAccess raw(poolId, startingRow + fromRow, &mySet, - PoolVariableIF::VAR_READ_WRITE); - mySet.read(); - - result = raw.setEntryFromBigEndian(fromAsStream, sizeof(T)); - - fromAsStream += sizeof(T); - - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - - mySet.commit(); - } - - return HasReturnvaluesIF::RETURN_OK; -} - -ReturnValue_t DataPoolParameterWrapper::copyFrom(const ParameterWrapper* from, - uint16_t startWritingAtIndex) { - if (poolId == PoolVariableIF::NO_PARAMETER) { - return ParameterWrapper::NOT_SET; - } - - if (type != from->type) { - return ParameterWrapper::DATATYPE_MISSMATCH; - } - - //check if from fits into this - uint8_t startingRow = startWritingAtIndex / columns; - uint8_t startingColumn = startWritingAtIndex % columns; - - if ((from->rows > (rows - startingRow)) - || (from->columns > (columns - startingColumn))) { - return ParameterWrapper::TOO_BIG; - } - - ReturnValue_t result; - //copy data - if (from->pointsToStream) { - switch (type) { - case Type::UINT8_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::INT8_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::UINT16_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::INT16_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::UINT32_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::INT32_T: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::FLOAT: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - case Type::DOUBLE: - result = deSerializeData(startingRow, startingColumn, - from->readonlyData, from->rows); - break; - default: - result = ParameterWrapper::UNKNOW_DATATYPE; - break; - } - } else { - //not supported - return HasReturnvaluesIF::RETURN_FAILED; - } - - return result; -} diff --git a/datapoolglob/DataPoolParameterWrapper.h b/datapoolglob/DataPoolParameterWrapper.h deleted file mode 100644 index b1e505a7..00000000 --- a/datapoolglob/DataPoolParameterWrapper.h +++ /dev/null @@ -1,38 +0,0 @@ -#ifndef DATAPOOLPARAMETERWRAPPER_H_ -#define DATAPOOLPARAMETERWRAPPER_H_ - -#include "../globalfunctions/Type.h" -#include "../parameters/ParameterWrapper.h" - -class DataPoolParameterWrapper: public SerializeIF { -public: - DataPoolParameterWrapper(); - virtual ~DataPoolParameterWrapper(); - - ReturnValue_t set(uint8_t domainId, uint16_t parameterId); - - virtual ReturnValue_t serialize(uint8_t** buffer, size_t* size, - size_t maxSize, Endianness streamEndianness) const override; - - virtual size_t getSerializedSize() const override; - - virtual ReturnValue_t deSerialize(const uint8_t** buffer, size_t* size, - Endianness streamEndianness) override; - - ReturnValue_t copyFrom(const ParameterWrapper *from, - uint16_t startWritingAtIndex); - -private: - Type type; - uint8_t rows; - uint8_t columns; - - uint32_t poolId; - - template - ReturnValue_t deSerializeData(uint8_t startingRow, uint8_t startingColumn, - const void *from, uint8_t fromRows); - -}; - -#endif /* DATAPOOLPARAMETERWRAPPER_H_ */ diff --git a/datapoolglob/GlobalDataPool.cpp b/datapoolglob/GlobalDataPool.cpp deleted file mode 100644 index afb27b77..00000000 --- a/datapoolglob/GlobalDataPool.cpp +++ /dev/null @@ -1,133 +0,0 @@ -#include "../datapoolglob/GlobalDataPool.h" -#include "../serviceinterface/ServiceInterfaceStream.h" -#include "../ipc/MutexFactory.h" - -GlobalDataPool::GlobalDataPool( - void(*initFunction)(GlobPoolMap* pool_map)) { - mutex = MutexFactory::instance()->createMutex(); - if (initFunction != NULL ) { - initFunction( &this->globDataPool ); - } -} - -GlobalDataPool::~GlobalDataPool() { - MutexFactory::instance()->deleteMutex(mutex); - for(GlobPoolMapIter it = this->globDataPool.begin(); - it != this->globDataPool.end(); ++it ) - { - delete it->second; - } -} - -// The function checks PID, type and array length before returning a copy of -// the PoolEntry. In failure case, it returns a temp-Entry with size 0 and NULL-ptr. -template PoolEntry* GlobalDataPool::getData( uint32_t data_pool_id, - uint8_t sizeOrPosition ) { - GlobPoolMapIter it = this->globDataPool.find( data_pool_id ); - if ( it != this->globDataPool.end() ) { - PoolEntry* entry = dynamic_cast< PoolEntry* >( it->second ); - if (entry != nullptr ) { - if ( sizeOrPosition <= entry->length ) { - return entry; - } - } - } - return nullptr; -} - -PoolEntryIF* GlobalDataPool::getRawData( uint32_t data_pool_id ) { - GlobPoolMapIter it = this->globDataPool.find( data_pool_id ); - if ( it != this->globDataPool.end() ) { - return it->second; - } else { - return nullptr; - } -} - -ReturnValue_t GlobalDataPool::unlockDataPool() { - ReturnValue_t status = mutex->unlockMutex(); - if(status != RETURN_OK) { - sif::error << "DataPool::DataPool: unlock of mutex failed with" - " error code: " << status << std::endl; - } - return status; -} - -ReturnValue_t GlobalDataPool::lockDataPool(uint32_t timeoutMs) { - ReturnValue_t status = mutex->lockMutex(MutexIF::TimeoutType::WAITING, - timeoutMs); - if(status != RETURN_OK) { - sif::error << "DataPool::DataPool: lock of mutex failed " - "with error code: " << status << std::endl; - } - return status; -} - -void GlobalDataPool::print() { - sif::debug << "DataPool contains: " << std::endl; - std::map::iterator dataPoolIt; - dataPoolIt = this->globDataPool.begin(); - while( dataPoolIt != this->globDataPool.end() ) { - sif::debug << std::hex << dataPoolIt->first << std::dec << " |"; - dataPoolIt->second->print(); - dataPoolIt++; - } -} - -uint32_t GlobalDataPool::PIDToDataPoolId(uint32_t parameter_id) { - return (parameter_id >> 8) & 0x00FFFFFF; -} - -uint8_t GlobalDataPool::PIDToArrayIndex(uint32_t parameter_id) { - return (parameter_id & 0x000000FF); -} - -uint32_t GlobalDataPool::poolIdAndPositionToPid(uint32_t poolId, uint8_t index) { - return (poolId << 8) + index; -} - - -//SHOULDDO: Do we need a mutex lock here... I don't think so, -//as we only check static const values of elements in a list that do not change. -//there is no guarantee in the standard, but it seems to me that the implementation is safe -UM -ReturnValue_t GlobalDataPool::getType(uint32_t parameter_id, Type* type) { - GlobPoolMapIter it = this->globDataPool.find( PIDToDataPoolId(parameter_id)); - if ( it != this->globDataPool.end() ) { - *type = it->second->getType(); - return RETURN_OK; - } else { - *type = Type::UNKNOWN_TYPE; - return RETURN_FAILED; - } -} - -bool GlobalDataPool::exists(uint32_t parameterId) { - uint32_t poolId = PIDToDataPoolId(parameterId); - uint32_t index = PIDToArrayIndex(parameterId); - GlobPoolMapIter it = this->globDataPool.find( poolId ); - if (it != globDataPool.end()) { - if (it->second->getSize() >= index) { - return true; - } - } - return false; -} - -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size ); -template PoolEntry* GlobalDataPool::getData( - uint32_t data_pool_id, uint8_t size); diff --git a/datapoolglob/GlobalDataPool.h b/datapoolglob/GlobalDataPool.h deleted file mode 100644 index ce5b132c..00000000 --- a/datapoolglob/GlobalDataPool.h +++ /dev/null @@ -1,149 +0,0 @@ -#ifndef GLOBALDATAPOOL_H_ -#define GLOBALDATAPOOL_H_ - -#include "../datapool/PoolEntry.h" -#include "../globalfunctions/Type.h" -#include "../ipc/MutexIF.h" -#include - -/** - * @defgroup data_pool Global data pool - * This is the group, where all classes associated with global - * data pool handling belong to. - * This includes classes to access Data Pool variables. - */ - -/** - * Typedefs for the global pool representations - */ -using GlobPoolMap = std::map; -using GlobPoolMapIter = GlobPoolMap::iterator; - -/** - * @brief This class represents the OBSW global data-pool. - * - * @details - * All variables are registered and space is allocated in an initialization - * function, which is passed do the constructor. Space for the variables is - * allocated on the heap (with a new call). - * - * The data is found by a data pool id, which uniquely represents a variable. - * Data pool variables should be used with a blackboard logic in mind, - * which means read data is valid (if flagged so), - * but not necessarily up-to-date. - * - * Variables are either single values or arrays. - * @author Bastian Baetz - * @ingroup data_pool - */ -class GlobalDataPool : public HasReturnvaluesIF { -private: - /** - * @brief This is the actual data pool itself. - * @details It is represented by a map with the data pool id as index - * and a pointer to a single PoolEntry as value. - */ - GlobPoolMap globDataPool; - - /** - * @brief The mutex is created in the constructor and makes - * access mutual exclusive. - * @details Locking and unlocking the pool is only done by the DataSet class. - */ - MutexIF* mutex; -public: - /** - * @brief In the classes constructor, - * the passed initialization function is called. - * @details - * To enable filling the pool, a pointer to the map is passed, - * allowing direct access to the pool's content. - * On runtime, adding or removing variables is forbidden. - */ - GlobalDataPool( void ( *initFunction )( GlobPoolMap* pool_map ) ); - - /** - * @brief The destructor iterates through the data_pool map and - * calls all entries destructors to clean up the heap. - */ - ~GlobalDataPool(); - - /** - * @brief This is the default call to access the pool. - * @details - * A pointer to the PoolEntry object is returned. - * The call checks data pool id, type and array size. - * Returns NULL in case of failure. - * @param data_pool_id The data pool id to search. - * @param sizeOrPosition The array size (not byte size!) of the pool entry, - * or the position the user wants to read. - * If smaller than the entry size, everything's ok. - */ - template PoolEntry* getData( uint32_t data_pool_id, - uint8_t sizeOrPosition ); - - /** - * @brief An alternative call to get a data pool entry in case the type is not implicitly known - * (i.e. in Housekeeping Telemetry). - * @details It returns a basic interface and does NOT perform - * a size check. The caller has to assure he does not copy too much data. - * Returns NULL in case the entry is not found. - * @param data_pool_id The data pool id to search. - */ - PoolEntryIF* getRawData( uint32_t data_pool_id ); - /** - * @brief This is a small helper function to facilitate locking the global data pool. - * @details It fetches the pool's mutex id and tries to acquire the mutex. - */ - ReturnValue_t lockDataPool(uint32_t timeoutMs = MutexIF::BLOCKING); - /** - * @brief This is a small helper function to facilitate unlocking the global data pool. - * @details It fetches the pool's mutex id and tries to free the mutex. - */ - ReturnValue_t unlockDataPool(); - /** - * @brief The print call is a simple debug method. - * @details It prints the current content of the data pool. - * It iterates through the data_pool map and calls each entry's print() method. - */ - void print(); - /** - * Extracts the data pool id from a SCOS 2000 PID. - * @param parameter_id The passed Parameter ID. - * @return The data pool id as used within the OBSW. - */ - static uint32_t PIDToDataPoolId( uint32_t parameter_id ); - /** - * Extracts an array index out of a SCOS 2000 PID. - * @param parameter_id The passed Parameter ID. - * @return The index of the corresponding data pool entry. - */ - static uint8_t PIDToArrayIndex( uint32_t parameter_id ); - /** - * Retransforms a data pool id and an array index to a SCOS 2000 PID. - */ - static uint32_t poolIdAndPositionToPid( uint32_t poolId, uint8_t index ); - - /** - * Method to return the type of a pool variable. - * @param parameter_id A parameterID (not pool id) of a DP member. - * @param type Returns the type or TYPE::UNKNOWN_TYPE - * @return RETURN_OK if parameter exists, RETURN_FAILED else. - */ - ReturnValue_t getType( uint32_t parameter_id, Type* type ); - - /** - * Method to check if a PID exists. Does not lock, as there's no - * possibility to alter the list that is checked during run-time. - * @param parameterId The PID (not pool id!) of a parameter. - * @return true if exists, false else. - */ - bool exists(uint32_t parameterId); -}; - -//We assume someone globally instantiates a DataPool. -namespace glob { -extern GlobalDataPool dataPool; -} - -#endif /* DATAPOOL_H_ */ diff --git a/datapoolglob/GlobalDataSet.cpp b/datapoolglob/GlobalDataSet.cpp deleted file mode 100644 index 1e99f805..00000000 --- a/datapoolglob/GlobalDataSet.cpp +++ /dev/null @@ -1,48 +0,0 @@ -#include "../datapoolglob/GlobalDataPool.h" -#include "../datapoolglob/GlobalDataSet.h" -#include "../serviceinterface/ServiceInterfaceStream.h" - -GlobDataSet::GlobDataSet(): PoolDataSetBase( - reinterpret_cast(®isteredVariables), - DATA_SET_MAX_SIZE) {} - -// Don't do anything with your variables, they are dead already! -// (Destructor is already called) -GlobDataSet::~GlobDataSet() {} - -ReturnValue_t GlobDataSet::commit(bool valid, uint32_t lockTimeout) { - setEntriesValid(valid); - setSetValid(valid); - return commit(lockTimeout); -} - -ReturnValue_t GlobDataSet::commit(uint32_t lockTimeout) { - return PoolDataSetBase::commit(lockTimeout); -} - -bool GlobDataSet::isValid() const { - return this->valid; -} - -ReturnValue_t GlobDataSet::unlockDataPool() { - return glob::dataPool.unlockDataPool(); -} - -ReturnValue_t GlobDataSet::lockDataPool(uint32_t timeoutMs) { - return glob::dataPool.lockDataPool(timeoutMs); -} - -void GlobDataSet::setEntriesValid(bool valid) { - for (uint16_t count = 0; count < fillCount; count++) { - if (registeredVariables[count]->getReadWriteMode() - != PoolVariableIF::VAR_READ) { - registeredVariables[count]->setValid(valid); - } - } -} - -void GlobDataSet::setSetValid(bool valid) { - this->valid = valid; -} - - diff --git a/datapoolglob/GlobalDataSet.h b/datapoolglob/GlobalDataSet.h deleted file mode 100644 index 2f0edbd5..00000000 --- a/datapoolglob/GlobalDataSet.h +++ /dev/null @@ -1,98 +0,0 @@ -#ifndef FRAMEWORK_DATAPOOLGLOB_DATASET_H_ -#define FRAMEWORK_DATAPOOLGLOB_DATASET_H_ - -#include "../datapool/PoolDataSetBase.h" - -/** - * @brief The DataSet class manages a set of locally checked out variables - * for the global data pool. - * @details - * This class uses the read-commit() semantic provided by the DataSetBase class. - * It extends the base class by using the global data pool, - * having a valid state and implementing lock und unlock calls for the global - * datapool. - * - * For more information on how this class works, see the DataSetBase - * documentation. - * @author Bastian Baetz - * @ingroup data_pool - */ -class GlobDataSet: public PoolDataSetBase { -public: - - /** - * @brief Creates an empty GlobDataSet. Use registerVariable or - * supply a pointer to this dataset to PoolVariable - * initializations to register pool variables. - */ - GlobDataSet(); - - /** - * @brief The destructor automatically manages writing the valid - * information of variables. - * @details - * In case the data set was read out, but not committed(indicated by state), - * the destructor parses all variables that are still registered to the set. - * For each, the valid flag in the data pool is set to "invalid". - */ - ~GlobDataSet(); - - /** - * Variant of method above which sets validity of all elements of the set. - * @param valid Validity information from PoolVariableIF. - * @return - @c RETURN_OK if all variables were read successfully. - * - @c COMMITING_WITHOUT_READING if set was not read yet and - * contains non write-only variables - */ - ReturnValue_t commit(bool valid, uint32_t lockTimeout = MutexIF::BLOCKING); - ReturnValue_t commit(uint32_t lockTimeout = MutexIF::BLOCKING) override; - - /** - * Set all entries - * @param valid - */ - void setSetValid(bool valid); - - bool isValid() const override; - - /** - * Set the valid information of all variables contained in the set which - * are not read-only - * - * @param valid Validity information from PoolVariableIF. - */ - void setEntriesValid(bool valid); - - //!< This definition sets the maximum number of variables to - //! register in one DataSet. - static const uint8_t DATA_SET_MAX_SIZE = 63; - -private: - /** - * If the valid state of a dataset is always relevant to the whole - * data set we can use this flag. - */ - bool valid = false; - - /** - * @brief This is a small helper function to facilitate locking - * the global data pool. - * @details - * It makes use of the lockDataPool method offered by the DataPool class. - */ - ReturnValue_t lockDataPool(uint32_t timeoutMs) override; - /** - * @brief This is a small helper function to facilitate - * unlocking the global data pool - * @details - * It makes use of the freeDataPoolLock method offered by the DataPool class. - */ - ReturnValue_t unlockDataPool() override; - - void handleAlreadyReadDatasetCommit(); - ReturnValue_t handleUnreadDatasetCommit(); - - PoolVariableIF* registeredVariables[DATA_SET_MAX_SIZE]; -}; - -#endif /* FRAMEWORK_DATAPOOLGLOB_DATASET_H_ */ diff --git a/datapoolglob/GlobalPoolVariable.h b/datapoolglob/GlobalPoolVariable.h deleted file mode 100644 index a995bfaf..00000000 --- a/datapoolglob/GlobalPoolVariable.h +++ /dev/null @@ -1,213 +0,0 @@ -#ifndef GLOBALPOOLVARIABLE_H_ -#define GLOBALPOOLVARIABLE_H_ - -#include "../datapool/DataSetIF.h" -#include "../datapoolglob/GlobalDataPool.h" -#include "../datapool/PoolVariableIF.h" -#include "../datapool/PoolEntry.h" -#include "../serialize/SerializeAdapter.h" -#include "../serviceinterface/ServiceInterfaceStream.h" - -template class PoolVarList; - - -/** - * @brief This is the access class for non-array data pool entries. - * - * @details - * To ensure safe usage of the data pool, operation is not done directly - * on the data pool entries, but on local copies. This class provides simple - * type-safe access to single data pool entries (i.e. entries with length = 1). - * The class can be instantiated as read-write and read only. - * It provides a commit-and-roll-back semantic, which means that the - * variable's value in the data pool is not changed until the - * commit call is executed. - * @tparam T The template parameter sets the type of the variable. - * Currently, all plain data types are supported, but in principle - * any type is possible. - * @ingroup data_pool - */ -template -class GlobPoolVar: public PoolVariableIF { - template friend class PoolVarList; - static_assert(not std::is_same::value, - "Do not use boolean for the PoolEntry type, use uint8_t instead!" - "There is no boolean type in CCSDS."); -public: - /** - * @brief In the constructor, the variable can register itself in a - * DataSet (if nullptr is not passed). - * @details - * It DOES NOT fetch the current value from the data pool, but - * sets the value attribute to default (0). - * The value is fetched within the read() operation. - * @param set_id This is the id in the global data pool - * this instance of the access class corresponds to. - * @param dataSet The data set in which the variable shall register - * itself. If NULL, the variable is not registered. - * @param setWritable If this flag is set to true, changes in the value - * attribute can be written back to the data pool, otherwise not. - */ - GlobPoolVar(uint32_t set_id, DataSetIF* dataSet, - ReadWriteMode_t setReadWriteMode); - - /** - * @brief This is the local copy of the data pool entry. - * @details The user can work on this attribute - * just like he would on a simple local variable. - */ - T value = 0; - - /** - * @brief Copy ctor to copy classes containing Pool Variables. - * (Robin): This only copies member variables, which is done - * by the default copy ctor. maybe we can ommit this ctor? - */ - GlobPoolVar(const GlobPoolVar& rhs); - - /** - * @brief The classes destructor is empty. - * @details If commit() was not called, the local value is - * discarded and not written back to the data pool. - */ - ~GlobPoolVar() {} - - /** - * @brief This is a call to read the value from the global data pool. - * @details - * When executed, this operation tries to fetch the pool entry with matching - * data pool id from the global data pool and copies the value and the valid - * information to its local attributes. In case of a failure (wrong type or - * pool id not found), the variable is set to zero and invalid. - * The read call is protected with a lock. - * It is recommended to use DataSets to read and commit multiple variables - * at once to avoid the overhead of unnecessary lock und unlock operations. - */ - ReturnValue_t read(uint32_t lockTimeout) override; - /** - * @brief The commit call writes back the variable's value to the data pool. - * @details - * It checks type and size, as well as if the variable is writable. If so, - * the value is copied and the valid flag is automatically set to "valid". - * The operation does NOT provide any mutual exclusive protection by itself. - * The commit call is protected with a lock. - * It is recommended to use DataSets to read and commit multiple variables - * at once to avoid the overhead of unnecessary lock und unlock operations. - */ - ReturnValue_t commit(uint32_t lockTimeout) override; - -protected: - /** - * @brief Like #read, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t readWithoutLock() override; - /** - * @brief Like #commit, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t commitWithoutLock() override; - /** - * @brief To access the correct data pool entry on read and commit calls, - * the data pool is stored. - */ - uint32_t dataPoolId; - - /** - * @brief The valid information as it was stored in the data pool is - * copied to this attribute. - */ - uint8_t valid; - - /** - * @brief The information whether the class is read-write or read-only - * is stored here. - */ - pool_rwm_t readWriteMode; - - /** - * Empty ctor for List initialization - */ - GlobPoolVar(); -public: - /** - * \brief This operation returns the data pool id of the variable. - */ - uint32_t getDataPoolId() const override; - - /** - * This method returns if the variable is write-only, read-write or read-only. - */ - ReadWriteMode_t getReadWriteMode() const override; - /** - * This operation sets the data pool id of the variable. - * The method is necessary to set id's of data pool member variables with bad initialization. - */ - void setDataPoolId(uint32_t poolId); - - /** - * \brief With this call, the valid information of the variable is returned. - */ - bool isValid() const override; - - uint8_t getValid(); - - void setValid(bool valid) override; - - operator T() { - return value; - } - - operator T() const { - return value; - } - - GlobPoolVar &operator=(T newValue) { - value = newValue; - return *this; - } - - GlobPoolVar &operator=(GlobPoolVar newPoolVariable) { - value = newPoolVariable.value; - return *this; - } - - virtual ReturnValue_t serialize(uint8_t** buffer, size_t* size, - const size_t max_size, - SerializeIF::Endianness streamEndianness) const override { - return SerializeAdapter::serialize(&value, buffer, size, max_size, - streamEndianness); - } - - virtual size_t getSerializedSize() const { - return SerializeAdapter::getSerializedSize(&value); - } - - virtual ReturnValue_t deSerialize(const uint8_t** buffer, size_t* size, - SerializeIF::Endianness streamEndianness) { - return SerializeAdapter::deSerialize(&value, buffer, size, - streamEndianness); - } -}; - -#include "../datapoolglob/GlobalPoolVariable.tpp" - -typedef GlobPoolVar gp_bool_t; -typedef GlobPoolVar gp_uint8_t; -typedef GlobPoolVar gp_uint16_t; -typedef GlobPoolVar gp_uint32_t; -typedef GlobPoolVar gp_int8_t; -typedef GlobPoolVar gp_int16_t; -typedef GlobPoolVar gp_int32_t; -typedef GlobPoolVar gp_float_t; -typedef GlobPoolVar gp_double_t; - -#endif /* POOLVARIABLE_H_ */ diff --git a/datapoolglob/GlobalPoolVariable.tpp b/datapoolglob/GlobalPoolVariable.tpp deleted file mode 100644 index d61d605d..00000000 --- a/datapoolglob/GlobalPoolVariable.tpp +++ /dev/null @@ -1,117 +0,0 @@ -#ifndef GLOBALPOOLVARIABLE_TPP_ -#define GLOBALPOOLVARIABLE_TPP_ - -template -inline GlobPoolVar::GlobPoolVar(uint32_t set_id, - DataSetIF* dataSet, ReadWriteMode_t setReadWriteMode): - dataPoolId(set_id), valid(PoolVariableIF::INVALID), - readWriteMode(setReadWriteMode) -{ - if (dataSet != nullptr) { - dataSet->registerVariable(this); - } -} - -template -inline ReturnValue_t GlobPoolVar::read(uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = readWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -template -inline ReturnValue_t GlobPoolVar::commit(uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = commitWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -template -inline ReturnValue_t GlobPoolVar::readWithoutLock() { - PoolEntry* read_out = glob::dataPool.getData(dataPoolId, 1); - if (read_out != NULL) { - valid = read_out->valid; - value = *(read_out->address); - return HasReturnvaluesIF::RETURN_OK; - } else { - value = 0; - valid = false; - sif::error << "PoolVariable: read of DP Variable 0x" << std::hex - << dataPoolId << std::dec << " failed." << std::endl; - return HasReturnvaluesIF::RETURN_FAILED; - } -} - -template -inline ReturnValue_t GlobPoolVar::commitWithoutLock() { - PoolEntry* write_back = glob::dataPool.getData(dataPoolId, 1); - if ((write_back != NULL) && (readWriteMode != VAR_READ)) { - write_back->valid = valid; - *(write_back->address) = value; - return HasReturnvaluesIF::RETURN_OK; - } else { - return HasReturnvaluesIF::RETURN_FAILED; - } -} - -template -inline GlobPoolVar::GlobPoolVar(): - dataPoolId(PoolVariableIF::NO_PARAMETER), - valid(PoolVariableIF::INVALID), - readWriteMode(VAR_READ), value(0) {} - -template -inline GlobPoolVar::GlobPoolVar(const GlobPoolVar& rhs) : - dataPoolId(rhs.dataPoolId), valid(rhs.valid), readWriteMode( - rhs.readWriteMode), value(rhs.value) {} - -template -inline pool_rwm_t GlobPoolVar::getReadWriteMode() const { - return readWriteMode; -} - -template -inline uint32_t GlobPoolVar::getDataPoolId() const { - return dataPoolId; -} - -template -inline void GlobPoolVar::setDataPoolId(uint32_t poolId) { - dataPoolId = poolId; -} - -template -inline bool GlobPoolVar::isValid() const { - if (valid) - return true; - else - return false; -} - -template -inline uint8_t GlobPoolVar::getValid() { - return valid; -} - -template -inline void GlobPoolVar::setValid(bool valid) { - this->valid = valid; -} - -#endif diff --git a/datapoolglob/GlobalPoolVector.h b/datapoolglob/GlobalPoolVector.h deleted file mode 100644 index 0f5daacd..00000000 --- a/datapoolglob/GlobalPoolVector.h +++ /dev/null @@ -1,185 +0,0 @@ -#ifndef FSFW_DATAPOOLGLOB_GLOBALPOOLVECTOR_H_ -#define FSFW_DATAPOOLGLOB_GLOBALPOOLVECTOR_H_ - -#include "../datapool/DataSetIF.h" -#include "../datapool/PoolEntry.h" -#include "../datapool/PoolVariableIF.h" -#include "../serialize/SerializeAdapter.h" -#include "../serviceinterface/ServiceInterfaceStream.h" - -/** - * @brief This is the access class for array-type data pool entries. - * - * @details - * To ensure safe usage of the data pool, operation is not done directly on the - * data pool entries, but on local copies. This class provides simple type- - * and length-safe access to vector-style data pool entries (i.e. entries with - * length > 1). The class can be instantiated as read-write and read only. - * - * It provides a commit-and-roll-back semantic, which means that no array - * entry in the data pool is changed until the commit call is executed. - * There are two template parameters: - * @tparam T - * This template parameter specifies the data type of an array entry. Currently, - * all plain data types are supported, but in principle any type is possible. - * @tparam vector_size - * This template parameter specifies the vector size of this entry. Using a - * template parameter for this is not perfect, but avoids - * dynamic memory allocation. - * @ingroup data_pool - */ -template -class GlobPoolVector: public PoolVariableIF { -public: - /** - * @brief In the constructor, the variable can register itself in a - * DataSet (if no nullptr is passed). - * @details - * It DOES NOT fetch the current value from the data pool, but sets the - * value attribute to default (0). The value is fetched within the - * read() operation. - * @param set_id - * This is the id in the global data pool this instance of the access - * class corresponds to. - * @param dataSet - * The data set in which the variable shall register itself. If nullptr, - * the variable is not registered. - * @param setWritable - * If this flag is set to true, changes in the value attribute can be - * written back to the data pool, otherwise not. - */ - GlobPoolVector(uint32_t set_id, DataSetIF* set, - ReadWriteMode_t setReadWriteMode); - - /** - * @brief This is the local copy of the data pool entry. - * @details The user can work on this attribute - * just like he would on a local array of this type. - */ - T value[vectorSize]; - /** - * @brief The classes destructor is empty. - * @details If commit() was not called, the local value is - * discarded and not written back to the data pool. - */ - ~GlobPoolVector() {}; - /** - * @brief The operation returns the number of array entries - * in this variable. - */ - uint8_t getSize() { - return vectorSize; - } - /** - * @brief This operation returns the data pool id of the variable. - */ - uint32_t getDataPoolId() const { - return dataPoolId; - } - /** - * @brief This operation sets the data pool id of the variable. - * @details - * The method is necessary to set id's of data pool member variables - * with bad initialization. - */ - void setDataPoolId(uint32_t poolId) { - dataPoolId = poolId; - } - /** - * This method returns if the variable is write-only, read-write or read-only. - */ - ReadWriteMode_t getReadWriteMode() const { - return readWriteMode; - } - - - /** - * @brief With this call, the valid information of the variable is returned. - */ - bool isValid() const { - if (valid != INVALID) - return true; - else - return false; - } - void setValid(bool valid) {this->valid = valid;} - uint8_t getValid() {return valid;} - - T &operator [](int i) {return value[i];} - const T &operator [](int i) const {return value[i];} - - virtual ReturnValue_t serialize(uint8_t** buffer, size_t* size, - size_t max_size, Endianness streamEndianness) const override; - virtual size_t getSerializedSize() const override; - virtual ReturnValue_t deSerialize(const uint8_t** buffer, size_t* size, - Endianness streamEndianness) override; - - /** - * @brief This is a call to read the array's values - * from the global data pool. - * @details - * When executed, this operation tries to fetch the pool entry with matching - * data pool id from the global data pool and copies all array values - * and the valid information to its local attributes. - * In case of a failure (wrong type, size or pool id not found), the - * variable is set to zero and invalid. - * The read call is protected by a lock of the global data pool. - * It is recommended to use DataSets to read and commit multiple variables - * at once to avoid the overhead of unnecessary lock und unlock operations. - */ - ReturnValue_t read(uint32_t lockTimeout = MutexIF::BLOCKING) override; - /** - * @brief The commit call copies the array values back to the data pool. - * @details - * It checks type and size, as well as if the variable is writable. If so, - * the value is copied and the valid flag is automatically set to "valid". - * The commit call is protected by a lock of the global data pool. - * It is recommended to use DataSets to read and commit multiple variables - * at once to avoid the overhead of unnecessary lock und unlock operations. - */ - ReturnValue_t commit(uint32_t lockTimeout = MutexIF::BLOCKING) override; - -protected: - /** - * @brief Like #read, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t readWithoutLock() override; - /** - * @brief Like #commit, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t commitWithoutLock() override; - -private: - /** - * @brief To access the correct data pool entry on read and commit calls, - * the data pool id is stored. - */ - uint32_t dataPoolId; - /** - * @brief The valid information as it was stored in the data pool - * is copied to this attribute. - */ - uint8_t valid; - /** - * @brief The information whether the class is read-write or - * read-only is stored here. - */ - ReadWriteMode_t readWriteMode; -}; - -#include "../datapoolglob/GlobalPoolVector.tpp" - -template -using gp_vec_t = GlobPoolVector; - -#endif /* FSFW_DATAPOOLGLOB_GLOBALPOOLVECTOR_H_ */ diff --git a/datapoolglob/GlobalPoolVector.tpp b/datapoolglob/GlobalPoolVector.tpp deleted file mode 100644 index 013a682a..00000000 --- a/datapoolglob/GlobalPoolVector.tpp +++ /dev/null @@ -1,117 +0,0 @@ -#ifndef FSFW_DATAPOOLGLOB_GLOBALPOOLVECTOR_TPP_ -#define FSFW_DATAPOOLGLOB_GLOBALPOOLVECTOR_TPP_ - - -template -inline GlobPoolVector::GlobPoolVector(uint32_t set_id, - DataSetIF* set, ReadWriteMode_t setReadWriteMode) : - dataPoolId(set_id), valid(false), readWriteMode(setReadWriteMode) { - memset(this->value, 0, vectorSize * sizeof(T)); - if (set != nullptr) { - set->registerVariable(this); - } -} - - -template -inline ReturnValue_t GlobPoolVector::read(uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = readWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -template -inline ReturnValue_t GlobPoolVector::commit( - uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = commitWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -template -inline ReturnValue_t GlobPoolVector::readWithoutLock() { - PoolEntry* read_out = glob::dataPool.getData(this->dataPoolId, - vectorSize); - if (read_out != nullptr) { - this->valid = read_out->valid; - memcpy(this->value, read_out->address, read_out->getByteSize()); - - return HasReturnvaluesIF::RETURN_OK; - - } else { - memset(this->value, 0, vectorSize * sizeof(T)); - sif::error << "PoolVector: Read of DP Variable 0x" << std::hex - << std::setw(8) << std::setfill('0') << dataPoolId << - std::dec << " failed." << std::endl; - this->valid = INVALID; - return HasReturnvaluesIF::RETURN_FAILED; - } -} - -template -inline ReturnValue_t GlobPoolVector::commitWithoutLock() { - PoolEntry* writeBack = glob::dataPool.getData(this->dataPoolId, - vectorSize); - if ((writeBack != nullptr) && (this->readWriteMode != VAR_READ)) { - writeBack->valid = valid; - memcpy(writeBack->address, this->value, writeBack->getByteSize()); - return HasReturnvaluesIF::RETURN_OK; - } else { - return HasReturnvaluesIF::RETURN_FAILED; - } -} - -template -inline ReturnValue_t GlobPoolVector::serialize(uint8_t** buffer, - size_t* size, size_t max_size, - SerializeIF::Endianness streamEndianness) const { - uint16_t i; - ReturnValue_t result; - for (i = 0; i < vectorSize; i++) { - result = SerializeAdapter::serialize(&(value[i]), buffer, size, - max_size, streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - } - return result; -} - -template -inline size_t GlobPoolVector::getSerializedSize() const { - return vectorSize * SerializeAdapter::getSerializedSize(value); -} - -template -inline ReturnValue_t GlobPoolVector::deSerialize( - const uint8_t** buffer, size_t* size, - SerializeIF::Endianness streamEndianness) { - uint16_t i; - ReturnValue_t result; - for (i = 0; i < vectorSize; i++) { - result = SerializeAdapter::deSerialize(&(value[i]), buffer, size, - streamEndianness); - if (result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - } - return result; -} - -#endif diff --git a/datapoolglob/PIDReader.h b/datapoolglob/PIDReader.h deleted file mode 100644 index 9431e1d4..00000000 --- a/datapoolglob/PIDReader.h +++ /dev/null @@ -1,164 +0,0 @@ -#ifndef PIDREADER_H_ -#define PIDREADER_H_ -#include "../datapool/DataSetIF.h" -#include "../datapoolglob/GlobalDataPool.h" -#include "../datapool/PoolEntry.h" -#include "../datapool/PoolVariableIF.h" -#include "../serialize/SerializeAdapter.h" -#include "../serviceinterface/ServiceInterfaceStream.h" - -template class PIDReaderList; - -template -class PIDReader: public PoolVariableIF { - template friend class PIDReaderList; -protected: - uint32_t parameterId; - uint8_t valid; - ReturnValue_t readWithoutLock() { - uint8_t arrayIndex = GlobalDataPool::PIDToArrayIndex(parameterId); - PoolEntry *read_out = glob::dataPool.getData( - GlobalDataPool::PIDToDataPoolId(parameterId), arrayIndex); - if (read_out != NULL) { - valid = read_out->valid; - value = read_out->address[arrayIndex]; - return HasReturnvaluesIF::RETURN_OK; - } else { - value = 0; - valid = false; - sif::error << "PIDReader: read of PID 0x" << std::hex << parameterId - << std::dec << " failed." << std::endl; - return HasReturnvaluesIF::RETURN_FAILED; - } - } - /** - * Never commit, is read-only. - * Reason is the possibility to access a single DP vector element, but if we commit, - * we set validity of the whole vector. - */ - ReturnValue_t commit(uint32_t lockTimeout) override { - return HasReturnvaluesIF::RETURN_FAILED; - } - ReturnValue_t commitWithoutLock() override { - return HasReturnvaluesIF::RETURN_FAILED; - } - - /** - * Empty ctor for List initialization - */ - PIDReader() : - parameterId(PoolVariableIF::NO_PARAMETER), valid( - PoolVariableIF::INVALID), value(0) { - - } -public: - /** - * \brief This is the local copy of the data pool entry. - */ - T value; - /** - * \brief In the constructor, the variable can register itself in a DataSet (if not NULL is - * passed). - * \details It DOES NOT fetch the current value from the data pool, but sets the value - * attribute to default (0). The value is fetched within the read() operation. - * \param set_id This is the id in the global data pool this instance of the access class - * corresponds to. - * \param dataSet The data set in which the variable shall register itself. If NULL, - * the variable is not registered. - * \param setWritable If this flag is set to true, changes in the value attribute can be - * written back to the data pool, otherwise not. - */ - PIDReader(uint32_t setParameterId, DataSetIF *dataSet) : - parameterId(setParameterId), valid(PoolVariableIF::INVALID), value( - 0) { - if (dataSet != NULL) { - dataSet->registerVariable(this); - } - } - - ReturnValue_t read(uint32_t lockTimeout) override { - ReturnValue_t result = glob::dataPool.lockDataPool(); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = readWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "PIDReader::read: Could not unlock data pool!" - << std::endl; - } - return result; - } - /** - * Copy ctor to copy classes containing Pool Variables. - */ - PIDReader(const PIDReader &rhs) : - parameterId(rhs.parameterId), valid(rhs.valid), value(rhs.value) { - } - - /** - * \brief The classes destructor is empty. - */ - ~PIDReader() { - - } - /** - * \brief This operation returns the data pool id of the variable. - */ - uint32_t getDataPoolId() const { - return GlobalDataPool::PIDToDataPoolId(parameterId); - } - uint32_t getParameterId() const { - return parameterId; - } - /** - * This method returns if the variable is write-only, read-write or read-only. - */ - ReadWriteMode_t getReadWriteMode() const { - return VAR_READ; - } - /** - * \brief With this call, the valid information of the variable is returned. - */ - bool isValid() const { - if (valid) - return true; - else - return false; - } - - uint8_t getValid() { - return valid; - } - - void setValid(bool valid) { - this->valid = valid; - } - - operator T() { - return value; - } - - PIDReader& operator=(T newValue) { - value = newValue; - return *this; - } - - virtual ReturnValue_t serialize(uint8_t **buffer, size_t *size, - size_t maxSize, Endianness streamEndianness) const override { - return SerializeAdapter::serialize(&value, buffer, size, maxSize, - streamEndianness); - } - - virtual size_t getSerializedSize() const override { - return SerializeAdapter::getSerializedSize(&value); - } - - virtual ReturnValue_t deSerialize(const uint8_t **buffer, size_t *size, - Endianness streamEndianness) override { - return SerializeAdapter::deSerialize(&value, buffer, size, - streamEndianness); - } -}; - -#endif /* PIDREADER_H_ */ diff --git a/datapoolglob/PIDReaderList.h b/datapoolglob/PIDReaderList.h deleted file mode 100644 index ae99f3aa..00000000 --- a/datapoolglob/PIDReaderList.h +++ /dev/null @@ -1,27 +0,0 @@ -#ifndef FRAMEWORK_DATAPOOLGLOB_PIDREADERLIST_H_ -#define FRAMEWORK_DATAPOOLGLOB_PIDREADERLIST_H_ - -#include "../datapool/PoolVariableIF.h" -#include "../datapoolglob/PIDReader.h" -template -class PIDReaderList { -private: - PIDReader variables[n_var]; -public: - PIDReaderList( const uint32_t setPid[n_var], DataSetIF* dataSet) { - //I really should have a look at the new init list c++ syntax. - if (dataSet == NULL) { - return; - } - for (uint8_t count = 0; count < n_var; count++) { - variables[count].parameterId = setPid[count]; - dataSet->registerVariable(&variables[count]); - } - } - - PIDReader &operator [](int i) { return variables[i]; } -}; - - - -#endif /* FRAMEWORK_DATAPOOLGLOB_PIDREADERLIST_H_ */ diff --git a/datapoolglob/PoolRawAccess.cpp b/datapoolglob/PoolRawAccess.cpp deleted file mode 100644 index 53706c6d..00000000 --- a/datapoolglob/PoolRawAccess.cpp +++ /dev/null @@ -1,239 +0,0 @@ -#include "../datapoolglob/GlobalDataPool.h" -#include "../datapoolglob/PoolRawAccess.h" -#include "../serviceinterface/ServiceInterfaceStream.h" -#include "../serialize/EndianConverter.h" - -#include - -PoolRawAccess::PoolRawAccess(uint32_t set_id, uint8_t setArrayEntry, - DataSetIF* dataSet, ReadWriteMode_t setReadWriteMode) : - dataPoolId(set_id), arrayEntry(setArrayEntry), valid(false), - type(Type::UNKNOWN_TYPE), typeSize(0), arraySize(0), sizeTillEnd(0), - readWriteMode(setReadWriteMode) { - memset(value, 0, sizeof(value)); - if (dataSet != nullptr) { - dataSet->registerVariable(this); - } -} - -PoolRawAccess::~PoolRawAccess() {} - -ReturnValue_t PoolRawAccess::read(uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = readWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -ReturnValue_t PoolRawAccess::readWithoutLock() { - ReturnValue_t result = RETURN_FAILED; - PoolEntryIF* readOut = glob::dataPool.getRawData(dataPoolId); - if (readOut != nullptr) { - result = handleReadOut(readOut); - if(result == RETURN_OK) { - return result; - } - } else { - result = READ_ENTRY_NON_EXISTENT; - } - handleReadError(result); - return result; -} - -ReturnValue_t PoolRawAccess::handleReadOut(PoolEntryIF* readOut) { - ReturnValue_t result = RETURN_FAILED; - valid = readOut->getValid(); - if (readOut->getSize() > arrayEntry) { - arraySize = readOut->getSize(); - typeSize = readOut->getByteSize() / readOut->getSize(); - type = readOut->getType(); - if (typeSize <= sizeof(value)) { - uint16_t arrayPosition = arrayEntry * typeSize; - sizeTillEnd = readOut->getByteSize() - arrayPosition; - uint8_t* ptr = &((uint8_t*) readOut->getRawData())[arrayPosition]; - memcpy(value, ptr, typeSize); - return RETURN_OK; - } else { - result = READ_TYPE_TOO_LARGE; - } - } else { - //debug << "PoolRawAccess: Size: " << (int)read_out->getSize() << std::endl; - result = READ_INDEX_TOO_LARGE; - } - return result; -} - -void PoolRawAccess::handleReadError(ReturnValue_t result) { - sif::error << "PoolRawAccess: read of DP Variable 0x" << std::hex << dataPoolId - << std::dec << " failed, "; - if(result == READ_TYPE_TOO_LARGE) { - sif::error << "type too large." << std::endl; - } - else if(result == READ_INDEX_TOO_LARGE) { - sif::error << "index too large." << std::endl; - } - else if(result == READ_ENTRY_NON_EXISTENT) { - sif::error << "entry does not exist." << std::endl; - } - - valid = INVALID; - typeSize = 0; - sizeTillEnd = 0; - memset(value, 0, sizeof(value)); -} - -ReturnValue_t PoolRawAccess::commit(uint32_t lockTimeout) { - ReturnValue_t result = glob::dataPool.lockDataPool(lockTimeout); - if(result != HasReturnvaluesIF::RETURN_OK) { - return result; - } - result = commitWithoutLock(); - ReturnValue_t unlockResult = glob::dataPool.unlockDataPool(); - if(unlockResult != HasReturnvaluesIF::RETURN_OK) { - sif::error << "GlobPoolVar::read: Could not unlock global data pool" - << std::endl; - } - return result; -} - -ReturnValue_t PoolRawAccess::commitWithoutLock() { - PoolEntryIF* write_back = glob::dataPool.getRawData(dataPoolId); - if ((write_back != NULL) && (readWriteMode != VAR_READ)) { - write_back->setValid(valid); - uint8_t array_position = arrayEntry * typeSize; - uint8_t* ptr = &((uint8_t*) write_back->getRawData())[array_position]; - memcpy(ptr, value, typeSize); - return HasReturnvaluesIF::RETURN_OK; - } else { - return HasReturnvaluesIF::RETURN_FAILED; - } -} - -uint8_t* PoolRawAccess::getEntry() { - return value; -} - -ReturnValue_t PoolRawAccess::getEntryEndianSafe(uint8_t* buffer, - size_t* writtenBytes, size_t max_size) { - uint8_t* data_ptr = getEntry(); - // debug << "PoolRawAccess::getEntry: Array position: " << - // index * size_of_type << " Size of T: " << (int)size_of_type << - // " ByteSize: " << byte_size << " Position: " << *size << std::endl; - if (typeSize == 0) - return DATA_POOL_ACCESS_FAILED; - if (typeSize > max_size) - return INCORRECT_SIZE; - EndianConverter::convertBigEndian(buffer, data_ptr, typeSize); - *writtenBytes = typeSize; - return HasReturnvaluesIF::RETURN_OK; -} - - -ReturnValue_t PoolRawAccess::serialize(uint8_t** buffer, size_t* size, - size_t maxSize, Endianness streamEndianness) const { - if (typeSize + *size <= maxSize) { - switch(streamEndianness) { - case(Endianness::BIG): - EndianConverter::convertBigEndian(*buffer, value, typeSize); - break; - case(Endianness::LITTLE): - EndianConverter::convertLittleEndian(*buffer, value, typeSize); - break; - case(Endianness::MACHINE): - default: - memcpy(*buffer, value, typeSize); - break; - } - *size += typeSize; - (*buffer) += typeSize; - return HasReturnvaluesIF::RETURN_OK; - } else { - return SerializeIF::BUFFER_TOO_SHORT; - } -} - - -Type PoolRawAccess::getType() { - return type; -} - -size_t PoolRawAccess::getSizeOfType() { - return typeSize; -} - -size_t PoolRawAccess::getArraySize(){ - return arraySize; -} - -uint32_t PoolRawAccess::getDataPoolId() const { - return dataPoolId; -} - -PoolVariableIF::ReadWriteMode_t PoolRawAccess::getReadWriteMode() const { - return readWriteMode; -} - -ReturnValue_t PoolRawAccess::setEntryFromBigEndian(const uint8_t *buffer, - size_t setSize) { - if (typeSize == setSize) { - EndianConverter::convertBigEndian(value, buffer, typeSize); - return HasReturnvaluesIF::RETURN_OK; - } else { - sif::error << "PoolRawAccess::setEntryFromBigEndian: Illegal sizes: " - "Internal" << (uint32_t) typeSize << ", Requested: " << setSize - << std::endl; - return INCORRECT_SIZE; - } -} - -bool PoolRawAccess::isValid() const { - if (valid != INVALID) - return true; - else - return false; -} - -void PoolRawAccess::setValid(bool valid) { - this->valid = valid; -} - -size_t PoolRawAccess::getSizeTillEnd() const { - return sizeTillEnd; -} - - -size_t PoolRawAccess::getSerializedSize() const { - return typeSize; -} - -ReturnValue_t PoolRawAccess::deSerialize(const uint8_t **buffer, size_t *size, - Endianness streamEndianness) { - - if (*size >= typeSize) { - switch(streamEndianness) { - case(Endianness::BIG): - EndianConverter::convertBigEndian(value, *buffer, typeSize); - break; - case(Endianness::LITTLE): - EndianConverter::convertLittleEndian(value, *buffer, typeSize); - break; - case(Endianness::MACHINE): - default: - memcpy(value, *buffer, typeSize); - break; - } - *size -= typeSize; - *buffer += typeSize; - return HasReturnvaluesIF::RETURN_OK; - } - else { - return SerializeIF::STREAM_TOO_SHORT; - } -} diff --git a/datapoolglob/PoolRawAccess.h b/datapoolglob/PoolRawAccess.h deleted file mode 100644 index 15643a41..00000000 --- a/datapoolglob/PoolRawAccess.h +++ /dev/null @@ -1,220 +0,0 @@ -#ifndef POOLRAWACCESS_H_ -#define POOLRAWACCESS_H_ - -#include "../datapool/DataSetIF.h" -#include "../datapool/PoolEntryIF.h" -#include "../datapool/PoolVariableIF.h" -#include "../globalfunctions/Type.h" - -/** - * @brief This class allows accessing Data Pool variables as raw bytes. - * @details - * This is necessary to have an access method for HK data, as the PID's alone - * do not provide type information. Please note that the the raw pool access - * read() and commit() calls are not thread-safe. - * - * Please supply a data set and use the data set read(), commit() calls for - * thread-safe data pool access. - * @ingroup data_pool - */ -class PoolRawAccess: public PoolVariableIF, HasReturnvaluesIF { -public: - /** - * This constructor is used to access a data pool entry with a - * given ID if the target type is not known. A DataSet object is supplied - * and the data pool entry with the given ID is registered to that data set. - * Please note that a pool raw access buffer only has a buffer - * with a size of double. As such, for vector entries which have - * @param data_pool_id Target data pool entry ID - * @param arrayEntry - * @param data_set Dataset to register data pool entry to - * @param setReadWriteMode - * @param registerVectors If set to true, the constructor checks if - * there are multiple vector entries to registers - * and registers all of them recursively into the data_set - * - */ - PoolRawAccess(uint32_t data_pool_id, uint8_t arrayEntry, - DataSetIF* data_set, ReadWriteMode_t setReadWriteMode = - PoolVariableIF::VAR_READ); - - /** - * @brief This operation returns a pointer to the entry fetched. - * @details Return pointer to the buffer containing the raw data - * Size and number of data can be retrieved by other means. - */ - uint8_t* getEntry(); - /** - * @brief This operation returns the fetched entry from the data pool and - * flips the bytes, if necessary. - * @details It makes use of the getEntry call of this function, but additionally flips the - * bytes to big endian, which is the default for external communication (as House- - * keeping telemetry). To achieve this, the data is copied directly to the passed - * buffer, if it fits in the given max_size. - * @param buffer A pointer to a buffer to write to - * @param writtenBytes The number of bytes written is returned with this value. - * @param max_size The maximum size that the function may write to buffer. - * @return - @c RETURN_OK if entry could be acquired - * - @c RETURN_FAILED else. - */ - ReturnValue_t getEntryEndianSafe(uint8_t *buffer, size_t *size, - size_t maxSize); - - /** - * @brief Serialize raw pool entry into provided buffer directly - * @param buffer Provided buffer. Raw pool data will be copied here - * @param size [out] Increment provided size value by serialized size - * @param max_size Maximum allowed serialization size - * @param bigEndian Specify endianess - * @return - @c RETURN_OK if serialization was successfull - * - @c SerializeIF::BUFFER_TOO_SHORT if range check failed - */ - ReturnValue_t serialize(uint8_t **buffer, size_t *size, - size_t maxSize, Endianness streamEndianness) const override; - - size_t getSerializedSize() const override; - - ReturnValue_t deSerialize(const uint8_t **buffer, size_t *size, - Endianness streamEndianness) override; - - /** - * With this method, the content can be set from a big endian buffer safely. - * @param buffer Pointer to the data to set - * @param size Size of the data to write. Must fit this->size. - * @return - @c RETURN_OK on success - * - @c RETURN_FAILED on failure - */ - ReturnValue_t setEntryFromBigEndian(const uint8_t* buffer, - size_t setSize); - /** - * @brief This operation returns the type of the entry currently stored. - */ - Type getType(); - /** - * @brief This operation returns the size of the entry currently stored. - */ - size_t getSizeOfType(); - /** - * - * @return the size of the datapool array - */ - size_t getArraySize(); - /** - * @brief This operation returns the data pool id of the variable. - */ - uint32_t getDataPoolId() const; - - static const uint8_t INTERFACE_ID = CLASS_ID::POOL_RAW_ACCESS_CLASS; - static const ReturnValue_t INCORRECT_SIZE = MAKE_RETURN_CODE(0x01); - static const ReturnValue_t DATA_POOL_ACCESS_FAILED = MAKE_RETURN_CODE(0x02); - static const ReturnValue_t READ_TYPE_TOO_LARGE = MAKE_RETURN_CODE(0x03); - static const ReturnValue_t READ_INDEX_TOO_LARGE = MAKE_RETURN_CODE(0x04); - static const ReturnValue_t READ_ENTRY_NON_EXISTENT = MAKE_RETURN_CODE(0x05); - static const uint8_t RAW_MAX_SIZE = sizeof(double); - uint8_t value[RAW_MAX_SIZE]; - - - /** - * @brief The classes destructor is empty. If commit() was not called, the local value is - * discarded and not written back to the data pool. - */ - ~PoolRawAccess(); - - /** - * This method returns if the variable is read-write or read-only. - */ - ReadWriteMode_t getReadWriteMode() const; - /** - * @brief With this call, the valid information of the variable is returned. - */ - bool isValid() const; - - void setValid(bool valid); - /** - * Getter for the remaining size. - */ - size_t getSizeTillEnd() const; - - /** - * @brief This is a call to read the value from the global data pool. - * @details - * When executed, this operation tries to fetch the pool entry with matching - * data pool id from the global data pool and copies the value and the valid - * information to its local attributes. In case of a failure (wrong type or - * pool id not found), the variable is set to zero and invalid. - * The call is protected by a lock of the global data pool. - * @return -@c RETURN_OK Read successfull - * -@c READ_TYPE_TOO_LARGE - * -@c READ_INDEX_TOO_LARGE - * -@c READ_ENTRY_NON_EXISTENT - */ - ReturnValue_t read(uint32_t lockTimeout = MutexIF::BLOCKING) override; - /** - * @brief The commit call writes back the variable's value to the data pool. - * @details - * It checks type and size, as well as if the variable is writable. If so, - * the value is copied and the valid flag is automatically set to "valid". - * The call is protected by a lock of the global data pool. - * - */ - ReturnValue_t commit(uint32_t lockTimeout = MutexIF::BLOCKING) override; - -protected: - /** - * @brief Like #read, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t readWithoutLock() override; - /** - * @brief Like #commit, but without a lock protection of the global pool. - * @details - * The operation does NOT provide any mutual exclusive protection by itself. - * This can be used if the lock is handled externally to avoid the overhead - * of consecutive lock und unlock operations. - * Declared protected to discourage free public usage. - */ - ReturnValue_t commitWithoutLock() override; - - ReturnValue_t handleReadOut(PoolEntryIF* read_out); - void handleReadError(ReturnValue_t result); -private: - /** - * @brief To access the correct data pool entry on read and commit calls, the data pool id - * is stored. - */ - uint32_t dataPoolId; - /** - * @brief The array entry that is fetched from the data pool. - */ - uint8_t arrayEntry; - /** - * @brief The valid information as it was stored in the data pool is copied to this attribute. - */ - uint8_t valid; - /** - * @brief This value contains the type of the data pool entry. - */ - Type type; - /** - * @brief This value contains the size of the data pool entry type in bytes. - */ - size_t typeSize; - /** - * The size of the DP array (single values return 1) - */ - size_t arraySize; - /** - * The size (in bytes) from the selected entry till the end of this DataPool variable. - */ - size_t sizeTillEnd; - /** - * @brief The information whether the class is read-write or read-only is stored here. - */ - ReadWriteMode_t readWriteMode; -}; - -#endif /* POOLRAWACCESS_H_ */ From f9d54032041237396b03c4c94e9b3f591769d824 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 11 Dec 2020 23:50:00 +0100 Subject: [PATCH 047/103] added device handler thermalset --- devicehandlers/DeviceHandlerThermalSet.h | 44 ++++++++++++++++++++++++ 1 file changed, 44 insertions(+) create mode 100644 devicehandlers/DeviceHandlerThermalSet.h diff --git a/devicehandlers/DeviceHandlerThermalSet.h b/devicehandlers/DeviceHandlerThermalSet.h new file mode 100644 index 00000000..239012e2 --- /dev/null +++ b/devicehandlers/DeviceHandlerThermalSet.h @@ -0,0 +1,44 @@ +#ifndef FSFW_DEVICEHANDLERS_DEVICEHANDLERTHERMALSET_H_ +#define FSFW_DEVICEHANDLERS_DEVICEHANDLERTHERMALSET_H_ + +#include "DeviceHandlerIF.h" +#include "../datapoollocal/StaticLocalDataSet.h" +#include "../datapoollocal/LocalPoolVariable.h" + + +class DeviceHandlerThermalSet: public StaticLocalDataSet<2> { +public: + + DeviceHandlerThermalSet(HasLocalDataPoolIF* hkOwner, uint32_t setId = + DeviceHandlerIF::DEFAULT_THERMAL_SET_ID, + lp_id_t thermalStateId = + DeviceHandlerIF::DEFAULT_THERMAL_STATE_POOL_ID, + lp_id_t heaterRequestId = + DeviceHandlerIF::DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID): + DeviceHandlerThermalSet(hkOwner->getObjectId(), setId, + thermalStateId, heaterRequestId) {} + + DeviceHandlerThermalSet(object_id_t deviceHandler, uint32_t setId = + DeviceHandlerIF::DEFAULT_THERMAL_SET_ID, + lp_id_t thermalStateId = + DeviceHandlerIF::DEFAULT_THERMAL_STATE_POOL_ID, + lp_id_t thermalStateRequestId = + DeviceHandlerIF::DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID): + StaticLocalDataSet(sid_t(deviceHandler, setId)), + thermalStatePoolId(thermalStateId), + heaterRequestPoolId(thermalStateRequestId) {} + + const lp_id_t thermalStatePoolId; + const lp_id_t heaterRequestPoolId; + + lp_var_t thermalState = + lp_var_t( + thermalStatePoolId, sid.objectId, this); + lp_var_t heaterRequest = + lp_var_t( + heaterRequestPoolId, sid.objectId, this); +}; + + + +#endif /* FSFW_DEVICEHANDLERS_DEVICEHANDLERTHERMALSET_H_ */ From 101babd863788df611316d68a342e1548d4584e7 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Fri, 11 Dec 2020 23:53:29 +0100 Subject: [PATCH 048/103] indentation consistent now --- devicehandlers/DeviceHandlerIF.h | 282 ++++++++++++++++--------------- 1 file changed, 146 insertions(+), 136 deletions(-) diff --git a/devicehandlers/DeviceHandlerIF.h b/devicehandlers/DeviceHandlerIF.h index 491a2c08..f5a1b4bb 100644 --- a/devicehandlers/DeviceHandlerIF.h +++ b/devicehandlers/DeviceHandlerIF.h @@ -4,6 +4,7 @@ #include "DeviceHandlerMessage.h" #include "../action/HasActionsIF.h" +#include "../datapoollocal/locPoolDefinitions.h" #include "../events/Event.h" #include "../modes/HasModesIF.h" #include "../ipc/MessageQueueSenderIF.h" @@ -21,145 +22,154 @@ using DeviceCommandId_t = uint32_t; */ class DeviceHandlerIF { public: + static constexpr DeviceCommandId_t NO_COMMAND = -1; + + static constexpr uint8_t TRANSITION_MODE_CHILD_ACTION_MASK = 0x20; + static constexpr uint8_t TRANSITION_MODE_BASE_ACTION_MASK = 0x10; + + using dh_heater_request_t = uint8_t; + using dh_thermal_state_t = int8_t; + + /** + * @brief This is the mode the device handler is in. + * + * @details The mode of the device handler must not be confused with the mode the device is in. + * The mode of the device itself is transparent to the user but related to the mode of the handler. + * MODE_ON and MODE_OFF are included in hasModesIF.h + */ + + // MODE_ON = 0, //!< The device is powered and ready to perform operations. In this mode, no commands are sent by the device handler itself, but direct commands van be commanded and will be interpreted + // MODE_OFF = 1, //!< The device is powered off. The only command accepted in this mode is a mode change to on. + //! The device is powered on and the device handler periodically sends + //! commands. The commands to be sent are selected by the handler + //! according to the submode. + static const Mode_t MODE_NORMAL = 2; + //! The device is powered on and ready to perform operations. In this mode, + //! raw commands can be sent. The device handler will send all replies + //! received from the command back to the commanding object. + static const Mode_t MODE_RAW = 3; + //! The device is shut down but the switch could not be turned off, so the + //! device still is powered. In this mode, only a mode change to @c MODE_OFF + //! can be commanded, which tries to switch off the device again. + static const Mode_t MODE_ERROR_ON = 4; + //! This is a transitional state which can not be commanded. The device + //! handler performs all commands to get the device in a state ready to + //! perform commands. When this is completed, the mode changes to @c MODE_ON. + static const Mode_t _MODE_START_UP = TRANSITION_MODE_CHILD_ACTION_MASK | 5; + //! This is a transitional state which can not be commanded. + //! The device handler performs all actions and commands to get the device + //! shut down. When the device is off, the mode changes to @c MODE_OFF. + //! It is possible to set the mode to _MODE_SHUT_DOWN to use the to off + //! transition if available. + static const Mode_t _MODE_SHUT_DOWN = TRANSITION_MODE_CHILD_ACTION_MASK | 6; + //! It is possible to set the mode to _MODE_TO_ON to use the to on + //! transition if available. + static const Mode_t _MODE_TO_ON = TRANSITION_MODE_CHILD_ACTION_MASK | HasModesIF::MODE_ON; + //! It is possible to set the mode to _MODE_TO_RAW to use the to raw + //! transition if available. + static const Mode_t _MODE_TO_RAW = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_RAW; + //! It is possible to set the mode to _MODE_TO_NORMAL to use the to normal + //! transition if available. + static const Mode_t _MODE_TO_NORMAL = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_NORMAL; + //! This is a transitional state which can not be commanded. + //! The device is shut down and ready to be switched off. + //! After the command to set the switch off has been sent, + //! the mode changes to @c MODE_WAIT_OFF + static const Mode_t _MODE_POWER_DOWN = TRANSITION_MODE_BASE_ACTION_MASK | 1; + //! This is a transitional state which can not be commanded. The device + //! will be switched on in this state. After the command to set the switch + //! on has been sent, the mode changes to @c MODE_WAIT_ON. + static const Mode_t _MODE_POWER_ON = TRANSITION_MODE_BASE_ACTION_MASK | 2; + //! This is a transitional state which can not be commanded. The switch has + //! been commanded off and the handler waits for it to be off. + //! When the switch is off, the mode changes to @c MODE_OFF. + static const Mode_t _MODE_WAIT_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 3; + //! This is a transitional state which can not be commanded. The switch + //! has been commanded on and the handler waits for it to be on. + //! When the switch is on, the mode changes to @c MODE_TO_ON. + static const Mode_t _MODE_WAIT_ON = TRANSITION_MODE_BASE_ACTION_MASK | 4; + //! This is a transitional state which can not be commanded. The switch has + //! been commanded off and is off now. This state is only to do an RMAP + //! cycle once more where the doSendRead() function will set the mode to + //! MODE_OFF. The reason to do this is to get rid of stuck packets in the IO Board. + static const Mode_t _MODE_SWITCH_IS_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 5; + + static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CDH; + static const Event DEVICE_BUILDING_COMMAND_FAILED = MAKE_EVENT(0, severity::LOW); + static const Event DEVICE_SENDING_COMMAND_FAILED = MAKE_EVENT(1, severity::LOW); + static const Event DEVICE_REQUESTING_REPLY_FAILED = MAKE_EVENT(2, severity::LOW); + static const Event DEVICE_READING_REPLY_FAILED = MAKE_EVENT(3, severity::LOW); + static const Event DEVICE_INTERPRETING_REPLY_FAILED = MAKE_EVENT(4, severity::LOW); + static const Event DEVICE_MISSED_REPLY = MAKE_EVENT(5, severity::LOW); + static const Event DEVICE_UNKNOWN_REPLY = MAKE_EVENT(6, severity::LOW); + static const Event DEVICE_UNREQUESTED_REPLY = MAKE_EVENT(7, severity::LOW); + static const Event INVALID_DEVICE_COMMAND = MAKE_EVENT(8, severity::LOW); //!< Indicates a SW bug in child class. + static const Event MONITORING_LIMIT_EXCEEDED = MAKE_EVENT(9, severity::LOW); + static const Event MONITORING_AMBIGUOUS = MAKE_EVENT(10, severity::HIGH); + + static const uint8_t INTERFACE_ID = CLASS_ID::DEVICE_HANDLER_IF; + + // Standard codes used when building commands. + static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If no command data was given when expected. + static const ReturnValue_t COMMAND_NOT_SUPPORTED = MAKE_RETURN_CODE(0xA1); //!< Command ID not in commandMap. Checked in DHB + static const ReturnValue_t COMMAND_ALREADY_SENT = MAKE_RETURN_CODE(0xA2); //!< Command was already executed. Checked in DHB + static const ReturnValue_t COMMAND_WAS_NOT_SENT = MAKE_RETURN_CODE(0xA3); + static const ReturnValue_t CANT_SWITCH_ADDRESS = MAKE_RETURN_CODE(0xA4); + static const ReturnValue_t WRONG_MODE_FOR_COMMAND = MAKE_RETURN_CODE(0xA5); + static const ReturnValue_t TIMEOUT = MAKE_RETURN_CODE(0xA6); + static const ReturnValue_t BUSY = MAKE_RETURN_CODE(0xA7); + static const ReturnValue_t NO_REPLY_EXPECTED = MAKE_RETURN_CODE(0xA8); //!< Used to indicate that this is a command-only command. + static const ReturnValue_t NON_OP_TEMPERATURE = MAKE_RETURN_CODE(0xA9); + static const ReturnValue_t COMMAND_NOT_IMPLEMENTED = MAKE_RETURN_CODE(0xAA); + + // Standard codes used in scanForReply + static const ReturnValue_t CHECKSUM_ERROR = MAKE_RETURN_CODE(0xB0); + static const ReturnValue_t LENGTH_MISSMATCH = MAKE_RETURN_CODE(0xB1); + static const ReturnValue_t INVALID_DATA = MAKE_RETURN_CODE(0xB2); + static const ReturnValue_t PROTOCOL_ERROR = MAKE_RETURN_CODE(0xB3); + + // 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 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 + static const ReturnValue_t INVALID_COMMAND_PARAMETER = MAKE_RETURN_CODE(0xD0); + static const ReturnValue_t INVALID_NUMBER_OR_LENGTH_OF_PARAMETERS = MAKE_RETURN_CODE(0xD1); + + /** + * Communication action that will be executed. + * + * This is used by the child class to tell the base class what to do. + */ + enum CommunicationAction: uint8_t { + PERFORM_OPERATION, + SEND_WRITE,//!< Send write + GET_WRITE, //!< Get write + SEND_READ, //!< Send read + GET_READ, //!< Get read + NOTHING //!< Do nothing. + }; + + static constexpr uint32_t DEFAULT_THERMAL_SET_ID = sid_t::INVALID_SET_ID - 1; + + static constexpr lp_id_t DEFAULT_THERMAL_STATE_POOL_ID = + localpool::INVALID_LPID - 2; + static constexpr lp_id_t DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID = + localpool::INVALID_LPID - 1; - static const uint8_t TRANSITION_MODE_CHILD_ACTION_MASK = 0x20; - static const uint8_t TRANSITION_MODE_BASE_ACTION_MASK = 0x10; + /** + * Default Destructor + */ + virtual ~DeviceHandlerIF() {} - static constexpr Command_t NO_COMMAND = -1; - - /** - * @brief This is the mode the device handler is in. - * - * @details The mode of the device handler must not be confused with the mode the device is in. - * The mode of the device itself is transparent to the user but related to the mode of the handler. - * MODE_ON and MODE_OFF are included in hasModesIF.h - */ - - // MODE_ON = 0, //!< The device is powered and ready to perform operations. In this mode, no commands are sent by the device handler itself, but direct commands van be commanded and will be interpreted - // MODE_OFF = 1, //!< The device is powered off. The only command accepted in this mode is a mode change to on. - //! The device is powered on and the device handler periodically sends - //! commands. The commands to be sent are selected by the handler - //! according to the submode. - static const Mode_t MODE_NORMAL = 2; - //! The device is powered on and ready to perform operations. In this mode, - //! raw commands can be sent. The device handler will send all replies - //! received from the command back to the commanding object. - static const Mode_t MODE_RAW = 3; - //! The device is shut down but the switch could not be turned off, so the - //! device still is powered. In this mode, only a mode change to @c MODE_OFF - //! can be commanded, which tries to switch off the device again. - static const Mode_t MODE_ERROR_ON = 4; - //! This is a transitional state which can not be commanded. The device - //! handler performs all commands to get the device in a state ready to - //! perform commands. When this is completed, the mode changes to @c MODE_ON. - static const Mode_t _MODE_START_UP = TRANSITION_MODE_CHILD_ACTION_MASK | 5; - //! This is a transitional state which can not be commanded. - //! The device handler performs all actions and commands to get the device - //! shut down. When the device is off, the mode changes to @c MODE_OFF. - //! It is possible to set the mode to _MODE_SHUT_DOWN to use the to off - //! transition if available. - static const Mode_t _MODE_SHUT_DOWN = TRANSITION_MODE_CHILD_ACTION_MASK | 6; - //! It is possible to set the mode to _MODE_TO_ON to use the to on - //! transition if available. - static const Mode_t _MODE_TO_ON = TRANSITION_MODE_CHILD_ACTION_MASK | HasModesIF::MODE_ON; - //! It is possible to set the mode to _MODE_TO_RAW to use the to raw - //! transition if available. - static const Mode_t _MODE_TO_RAW = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_RAW; - //! It is possible to set the mode to _MODE_TO_NORMAL to use the to normal - //! transition if available. - static const Mode_t _MODE_TO_NORMAL = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_NORMAL; - //! This is a transitional state which can not be commanded. - //! The device is shut down and ready to be switched off. - //! After the command to set the switch off has been sent, - //! the mode changes to @c MODE_WAIT_OFF - static const Mode_t _MODE_POWER_DOWN = TRANSITION_MODE_BASE_ACTION_MASK | 1; - //! This is a transitional state which can not be commanded. The device - //! will be switched on in this state. After the command to set the switch - //! on has been sent, the mode changes to @c MODE_WAIT_ON. - static const Mode_t _MODE_POWER_ON = TRANSITION_MODE_BASE_ACTION_MASK | 2; - //! This is a transitional state which can not be commanded. The switch has - //! been commanded off and the handler waits for it to be off. - //! When the switch is off, the mode changes to @c MODE_OFF. - static const Mode_t _MODE_WAIT_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 3; - //! This is a transitional state which can not be commanded. The switch - //! has been commanded on and the handler waits for it to be on. - //! When the switch is on, the mode changes to @c MODE_TO_ON. - static const Mode_t _MODE_WAIT_ON = TRANSITION_MODE_BASE_ACTION_MASK | 4; - //! This is a transitional state which can not be commanded. The switch has - //! been commanded off and is off now. This state is only to do an RMAP - //! cycle once more where the doSendRead() function will set the mode to - //! MODE_OFF. The reason to do this is to get rid of stuck packets in the IO Board. - static const Mode_t _MODE_SWITCH_IS_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 5; - - static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CDH; - static const Event DEVICE_BUILDING_COMMAND_FAILED = MAKE_EVENT(0, severity::LOW); - static const Event DEVICE_SENDING_COMMAND_FAILED = MAKE_EVENT(1, severity::LOW); - static const Event DEVICE_REQUESTING_REPLY_FAILED = MAKE_EVENT(2, severity::LOW); - static const Event DEVICE_READING_REPLY_FAILED = MAKE_EVENT(3, severity::LOW); - static const Event DEVICE_INTERPRETING_REPLY_FAILED = MAKE_EVENT(4, severity::LOW); - static const Event DEVICE_MISSED_REPLY = MAKE_EVENT(5, severity::LOW); - static const Event DEVICE_UNKNOWN_REPLY = MAKE_EVENT(6, severity::LOW); - static const Event DEVICE_UNREQUESTED_REPLY = MAKE_EVENT(7, severity::LOW); - static const Event INVALID_DEVICE_COMMAND = MAKE_EVENT(8, severity::LOW); //!< Indicates a SW bug in child class. - static const Event MONITORING_LIMIT_EXCEEDED = MAKE_EVENT(9, severity::LOW); - static const Event MONITORING_AMBIGUOUS = MAKE_EVENT(10, severity::HIGH); - - static const uint8_t INTERFACE_ID = CLASS_ID::DEVICE_HANDLER_IF; - - // Standard codes used when building commands. - static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If no command data was given when expected. - static const ReturnValue_t COMMAND_NOT_SUPPORTED = MAKE_RETURN_CODE(0xA1); //!< Command ID not in commandMap. Checked in DHB - static const ReturnValue_t COMMAND_ALREADY_SENT = MAKE_RETURN_CODE(0xA2); //!< Command was already executed. Checked in DHB - static const ReturnValue_t COMMAND_WAS_NOT_SENT = MAKE_RETURN_CODE(0xA3); - static const ReturnValue_t CANT_SWITCH_ADDRESS = MAKE_RETURN_CODE(0xA4); - static const ReturnValue_t WRONG_MODE_FOR_COMMAND = MAKE_RETURN_CODE(0xA5); - static const ReturnValue_t TIMEOUT = MAKE_RETURN_CODE(0xA6); - static const ReturnValue_t BUSY = MAKE_RETURN_CODE(0xA7); - static const ReturnValue_t NO_REPLY_EXPECTED = MAKE_RETURN_CODE(0xA8); //!< Used to indicate that this is a command-only command. - static const ReturnValue_t NON_OP_TEMPERATURE = MAKE_RETURN_CODE(0xA9); - static const ReturnValue_t COMMAND_NOT_IMPLEMENTED = MAKE_RETURN_CODE(0xAA); - - // Standard codes used in scanForReply - static const ReturnValue_t CHECKSUM_ERROR = MAKE_RETURN_CODE(0xB0); - static const ReturnValue_t LENGTH_MISSMATCH = MAKE_RETURN_CODE(0xB1); - static const ReturnValue_t INVALID_DATA = MAKE_RETURN_CODE(0xB2); - static const ReturnValue_t PROTOCOL_ERROR = MAKE_RETURN_CODE(0xB3); - - // 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 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 - static const ReturnValue_t INVALID_COMMAND_PARAMETER = MAKE_RETURN_CODE(0xD0); - static const ReturnValue_t INVALID_NUMBER_OR_LENGTH_OF_PARAMETERS = MAKE_RETURN_CODE(0xD1); - - /** - * Communication action that will be executed. - * - * This is used by the child class to tell the base class what to do. - */ - enum CommunicationAction: uint8_t { - PERFORM_OPERATION, - SEND_WRITE,//!< Send write - GET_WRITE, //!< Get write - SEND_READ, //!< Send read - GET_READ, //!< Get read - NOTHING //!< Do nothing. - }; - - /** - * Default Destructor - */ - virtual ~DeviceHandlerIF() {} - - /** - * This MessageQueue is used to command the device handler. - * @return the id of the MessageQueue - */ - virtual MessageQueueId_t getCommandQueue() const = 0; + /** + * This MessageQueue is used to command the device handler. + * @return the id of the MessageQueue + */ + virtual MessageQueueId_t getCommandQueue() const = 0; }; From d0d6247753120c8354ecbde51266b7fb63d3c47e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 12 Dec 2020 00:01:36 +0100 Subject: [PATCH 049/103] and now it compiles --- controller/ExtendedControllerBase.cpp | 1 - fdir/FaultCounter.cpp | 2 +- fsfw.mk | 1 - thermal/ThermalComponentCore.cpp | 13 +++++++------ thermal/ThermalModule.cpp | 6 +++--- thermal/ThermalModuleIF.h | 3 +-- thermal/tcsDefinitions.h | 6 +++--- 7 files changed, 15 insertions(+), 17 deletions(-) diff --git a/controller/ExtendedControllerBase.cpp b/controller/ExtendedControllerBase.cpp index f69d2ea1..fa4f6786 100644 --- a/controller/ExtendedControllerBase.cpp +++ b/controller/ExtendedControllerBase.cpp @@ -97,7 +97,6 @@ ReturnValue_t ExtendedControllerBase::initializeAfterTaskCreation() { ReturnValue_t ExtendedControllerBase::performOperation(uint8_t opCode) { handleQueue(); - hkSwitcher.performOperation(); localPoolManager.performHkOperation(); performControlOperation(); return RETURN_OK; diff --git a/fdir/FaultCounter.cpp b/fdir/FaultCounter.cpp index 443adb52..6519a3a8 100644 --- a/fdir/FaultCounter.cpp +++ b/fdir/FaultCounter.cpp @@ -76,7 +76,7 @@ ReturnValue_t FaultCounter::getParameter(uint8_t domainId, uint16_t parameterId, parameterWrapper->set(timer.timeout); break; default: - return INVALID_MATRIX_ID; + return INVALID_IDENTIFIER_ID; } return HasReturnvaluesIF::RETURN_OK; } diff --git a/fsfw.mk b/fsfw.mk index c5847554..3df63060 100644 --- a/fsfw.mk +++ b/fsfw.mk @@ -9,7 +9,6 @@ CXXSRC += $(wildcard $(FRAMEWORK_PATH)/controller/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/coordinates/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/datalinklayer/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/datapool/*.cpp) -CXXSRC += $(wildcard $(FRAMEWORK_PATH)/datapoolglob/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/datapoollocal/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/housekeeping/*.cpp) CXXSRC += $(wildcard $(FRAMEWORK_PATH)/devicehandlers/*.cpp) diff --git a/thermal/ThermalComponentCore.cpp b/thermal/ThermalComponentCore.cpp index 7b594d0c..ba875053 100644 --- a/thermal/ThermalComponentCore.cpp +++ b/thermal/ThermalComponentCore.cpp @@ -1,4 +1,5 @@ #include "ThermalComponentCore.h" +#include "tcsDefinitions.h" ThermalComponentCore::ThermalComponentCore(object_id_t reportingObjectId, uint8_t domainId, gp_id_t temperaturePoolId, @@ -60,7 +61,7 @@ ThermalComponentIF::HeaterRequest ThermalComponentCore::performOperation( //SHOULDDO: Better pass db_float_t* to getTemperature and set it invalid if invalid. temperature = getTemperature(); updateMinMaxTemp(); - if (temperature != INVALID_TEMPERATURE) { + if (temperature != thermal::INVALID_TEMPERATURE) { temperature.setValid(PoolVariableIF::VALID); State state = getState(temperature.value, getParameters(), targetState.value); @@ -119,7 +120,7 @@ ReturnValue_t ThermalComponentCore::setTargetState(int8_t newState) { } void ThermalComponentCore::setOutputInvalid() { - temperature = INVALID_TEMPERATURE; + temperature = thermal::INVALID_TEMPERATURE; temperature.setValid(PoolVariableIF::INVALID); currentState.setValid(PoolVariableIF::INVALID); heaterRequest = HEATER_DONT_CARE; @@ -144,13 +145,13 @@ float ThermalComponentCore::getTemperature() { if (thermalModule != nullptr) { float temperature = thermalModule->getTemperature(); - if (temperature != ThermalModuleIF::INVALID_TEMPERATURE) { + if (temperature != thermal::INVALID_TEMPERATURE) { return temperature; } else { - return INVALID_TEMPERATURE; + return thermal::INVALID_TEMPERATURE; } } else { - return INVALID_TEMPERATURE; + return thermal::INVALID_TEMPERATURE; } } @@ -226,7 +227,7 @@ ThermalComponentIF::State ThermalComponentCore::getIgnoredState(int8_t state) { } void ThermalComponentCore::updateMinMaxTemp() { - if (temperature == INVALID_TEMPERATURE) { + if (temperature == thermal::INVALID_TEMPERATURE) { return; } if (temperature < minTemp) { diff --git a/thermal/ThermalModule.cpp b/thermal/ThermalModule.cpp index 457a6743..de347542 100644 --- a/thermal/ThermalModule.cpp +++ b/thermal/ThermalModule.cpp @@ -107,7 +107,7 @@ void ThermalModule::calculateTemperature() { moduleTemperature = moduleTemperature.value / numberOfValidSensors; moduleTemperature.setValid(PoolVariableIF::VALID); } else { - moduleTemperature = INVALID_TEMPERATURE; + moduleTemperature.value = thermal::INVALID_TEMPERATURE; moduleTemperature.setValid(PoolVariableIF::INVALID); } } @@ -219,7 +219,7 @@ void ThermalModule::initialize(PowerSwitchIF* powerSwitch) { bool ThermalModule::calculateModuleHeaterRequestAndSetModuleStatus( Strategy strategy) { currentState.setValid(PoolVariableIF::VALID); - if (moduleTemperature == INVALID_TEMPERATURE) { + if (moduleTemperature == thermal::INVALID_TEMPERATURE) { currentState = UNKNOWN; return false; } @@ -282,7 +282,7 @@ void ThermalModule::updateTargetTemperatures(ThermalComponentIF* component, } void ThermalModule::setOutputInvalid() { - moduleTemperature = INVALID_TEMPERATURE; + moduleTemperature = thermal::INVALID_TEMPERATURE; moduleTemperature.setValid(PoolVariableIF::INVALID); currentState.setValid(PoolVariableIF::INVALID); std::list::iterator iter = components.begin(); diff --git a/thermal/ThermalModuleIF.h b/thermal/ThermalModuleIF.h index 2d11a6f2..89cf93d6 100644 --- a/thermal/ThermalModuleIF.h +++ b/thermal/ThermalModuleIF.h @@ -2,6 +2,7 @@ #define THERMALMODULEIF_H_ #include "ThermalComponentIF.h" + class AbstractTemperatureSensor; class ThermalModuleIF{ @@ -18,8 +19,6 @@ public: NON_OPERATIONAL = 0, OPERATIONAL = 1, UNKNOWN = 2 }; - static constexpr float INVALID_TEMPERATURE = 999; - virtual ~ThermalModuleIF() { } diff --git a/thermal/tcsDefinitions.h b/thermal/tcsDefinitions.h index 37e5b849..3225be5c 100644 --- a/thermal/tcsDefinitions.h +++ b/thermal/tcsDefinitions.h @@ -1,8 +1,8 @@ #ifndef TCSDEFINITIONS_H_ #define TCSDEFINITIONS_H_ - -static const float INVALID_TEMPERATURE = 999; - +namespace thermal { +static constexpr float INVALID_TEMPERATURE = 999; +} #endif /* TCSDEFINITIONS_H_ */ From 5927d944de61672a16afc366d0ebec10f46e19c2 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Sat, 12 Dec 2020 18:32:24 +0100 Subject: [PATCH 050/103] cmake fixes --- CMakeLists.txt | 2 ++ datapool/CMakeLists.txt | 7 +------ datapoollocal/CMakeLists.txt | 8 ++++++++ events/CMakeLists.txt | 1 - housekeeping/CMakeLists.txt | 5 +++++ storagemanager/CMakeLists.txt | 2 ++ thermal/CMakeLists.txt | 4 ++-- 7 files changed, 20 insertions(+), 9 deletions(-) create mode 100644 datapoollocal/CMakeLists.txt create mode 100644 housekeeping/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt index 669283c7..09760f8e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -38,6 +38,8 @@ add_subdirectory(controller) add_subdirectory(coordinates) add_subdirectory(datalinklayer) add_subdirectory(datapool) +add_subdirectory(datapoollocal) +add_subdirectory(housekeeping) add_subdirectory(devicehandlers) add_subdirectory(events) add_subdirectory(fdir) diff --git a/datapool/CMakeLists.txt b/datapool/CMakeLists.txt index e741f6a1..0d53e1ba 100644 --- a/datapool/CMakeLists.txt +++ b/datapool/CMakeLists.txt @@ -1,11 +1,6 @@ target_sources(${LIB_FSFW_NAME} PRIVATE - ControllerSet.cpp - DataPool.cpp - DataPoolAdmin.cpp - DataPoolParameterWrapper.cpp - DataSet.cpp HkSwitchHelper.cpp + PoolDataSetBase.cpp PoolEntry.cpp - PoolRawAccess.cpp ) \ No newline at end of file diff --git a/datapoollocal/CMakeLists.txt b/datapoollocal/CMakeLists.txt new file mode 100644 index 00000000..c6b187cd --- /dev/null +++ b/datapoollocal/CMakeLists.txt @@ -0,0 +1,8 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + LocalDataPoolManager.cpp + LocalDataSet.cpp + LocalPoolDataSetBase.cpp + LocalPoolObjectBase.cpp + SharedLocalDataSet.cpp +) \ No newline at end of file diff --git a/events/CMakeLists.txt b/events/CMakeLists.txt index 9e63deb8..4e935167 100644 --- a/events/CMakeLists.txt +++ b/events/CMakeLists.txt @@ -1,6 +1,5 @@ target_sources(${LIB_FSFW_NAME} PRIVATE - Event.cpp EventManager.cpp EventMessage.cpp ) diff --git a/housekeeping/CMakeLists.txt b/housekeeping/CMakeLists.txt new file mode 100644 index 00000000..fecad2e3 --- /dev/null +++ b/housekeeping/CMakeLists.txt @@ -0,0 +1,5 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + HousekeepingMessage.cpp + PeriodicHousekeepingHelper.cpp +) \ No newline at end of file diff --git a/storagemanager/CMakeLists.txt b/storagemanager/CMakeLists.txt index 57c92195..b8138cae 100644 --- a/storagemanager/CMakeLists.txt +++ b/storagemanager/CMakeLists.txt @@ -2,4 +2,6 @@ target_sources(${LIB_FSFW_NAME} PRIVATE ConstStorageAccessor.cpp StorageAccessor.cpp + LocalPool.cpp + PoolManager.cpp ) \ No newline at end of file diff --git a/thermal/CMakeLists.txt b/thermal/CMakeLists.txt index 67664fbe..ad532721 100644 --- a/thermal/CMakeLists.txt +++ b/thermal/CMakeLists.txt @@ -1,10 +1,10 @@ target_sources(${LIB_FSFW_NAME} PRIVATE AbstractTemperatureSensor.cpp - CoreComponent.cpp Heater.cpp RedundantHeater.cpp + ThermalComponentCore.cpp ThermalComponent.cpp ThermalModule.cpp - ThermalMonitor.cpp + ThermalMonitorReporter.cpp ) From bc6936ddddd59030b659f662127b642740474201 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Sat, 12 Dec 2020 18:35:58 +0100 Subject: [PATCH 051/103] indentation corrected (again) --- devicehandlers/DeviceHandlerIF.h | 264 +++++++++++++++---------------- 1 file changed, 132 insertions(+), 132 deletions(-) diff --git a/devicehandlers/DeviceHandlerIF.h b/devicehandlers/DeviceHandlerIF.h index f5a1b4bb..dba6b228 100644 --- a/devicehandlers/DeviceHandlerIF.h +++ b/devicehandlers/DeviceHandlerIF.h @@ -22,154 +22,154 @@ using DeviceCommandId_t = uint32_t; */ class DeviceHandlerIF { public: - static constexpr DeviceCommandId_t NO_COMMAND = -1; + static constexpr DeviceCommandId_t NO_COMMAND = -1; - static constexpr uint8_t TRANSITION_MODE_CHILD_ACTION_MASK = 0x20; - static constexpr uint8_t TRANSITION_MODE_BASE_ACTION_MASK = 0x10; + static constexpr uint8_t TRANSITION_MODE_CHILD_ACTION_MASK = 0x20; + static constexpr uint8_t TRANSITION_MODE_BASE_ACTION_MASK = 0x10; - using dh_heater_request_t = uint8_t; - using dh_thermal_state_t = int8_t; + using dh_heater_request_t = uint8_t; + using dh_thermal_state_t = int8_t; - /** - * @brief This is the mode the device handler is in. - * - * @details The mode of the device handler must not be confused with the mode the device is in. - * The mode of the device itself is transparent to the user but related to the mode of the handler. - * MODE_ON and MODE_OFF are included in hasModesIF.h - */ + /** + * @brief This is the mode the device handler is in. + * + * @details The mode of the device handler must not be confused with the mode the device is in. + * The mode of the device itself is transparent to the user but related to the mode of the handler. + * MODE_ON and MODE_OFF are included in hasModesIF.h + */ - // MODE_ON = 0, //!< The device is powered and ready to perform operations. In this mode, no commands are sent by the device handler itself, but direct commands van be commanded and will be interpreted - // MODE_OFF = 1, //!< The device is powered off. The only command accepted in this mode is a mode change to on. - //! The device is powered on and the device handler periodically sends - //! commands. The commands to be sent are selected by the handler - //! according to the submode. - static const Mode_t MODE_NORMAL = 2; - //! The device is powered on and ready to perform operations. In this mode, - //! raw commands can be sent. The device handler will send all replies - //! received from the command back to the commanding object. - static const Mode_t MODE_RAW = 3; - //! The device is shut down but the switch could not be turned off, so the - //! device still is powered. In this mode, only a mode change to @c MODE_OFF - //! can be commanded, which tries to switch off the device again. - static const Mode_t MODE_ERROR_ON = 4; - //! This is a transitional state which can not be commanded. The device - //! handler performs all commands to get the device in a state ready to - //! perform commands. When this is completed, the mode changes to @c MODE_ON. - static const Mode_t _MODE_START_UP = TRANSITION_MODE_CHILD_ACTION_MASK | 5; - //! This is a transitional state which can not be commanded. - //! The device handler performs all actions and commands to get the device - //! shut down. When the device is off, the mode changes to @c MODE_OFF. - //! It is possible to set the mode to _MODE_SHUT_DOWN to use the to off - //! transition if available. - static const Mode_t _MODE_SHUT_DOWN = TRANSITION_MODE_CHILD_ACTION_MASK | 6; - //! It is possible to set the mode to _MODE_TO_ON to use the to on - //! transition if available. - static const Mode_t _MODE_TO_ON = TRANSITION_MODE_CHILD_ACTION_MASK | HasModesIF::MODE_ON; - //! It is possible to set the mode to _MODE_TO_RAW to use the to raw - //! transition if available. - static const Mode_t _MODE_TO_RAW = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_RAW; - //! It is possible to set the mode to _MODE_TO_NORMAL to use the to normal - //! transition if available. - static const Mode_t _MODE_TO_NORMAL = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_NORMAL; - //! This is a transitional state which can not be commanded. - //! The device is shut down and ready to be switched off. - //! After the command to set the switch off has been sent, - //! the mode changes to @c MODE_WAIT_OFF - static const Mode_t _MODE_POWER_DOWN = TRANSITION_MODE_BASE_ACTION_MASK | 1; - //! This is a transitional state which can not be commanded. The device - //! will be switched on in this state. After the command to set the switch - //! on has been sent, the mode changes to @c MODE_WAIT_ON. - static const Mode_t _MODE_POWER_ON = TRANSITION_MODE_BASE_ACTION_MASK | 2; - //! This is a transitional state which can not be commanded. The switch has - //! been commanded off and the handler waits for it to be off. - //! When the switch is off, the mode changes to @c MODE_OFF. - static const Mode_t _MODE_WAIT_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 3; - //! This is a transitional state which can not be commanded. The switch - //! has been commanded on and the handler waits for it to be on. - //! When the switch is on, the mode changes to @c MODE_TO_ON. - static const Mode_t _MODE_WAIT_ON = TRANSITION_MODE_BASE_ACTION_MASK | 4; - //! This is a transitional state which can not be commanded. The switch has - //! been commanded off and is off now. This state is only to do an RMAP - //! cycle once more where the doSendRead() function will set the mode to - //! MODE_OFF. The reason to do this is to get rid of stuck packets in the IO Board. - static const Mode_t _MODE_SWITCH_IS_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 5; + // MODE_ON = 0, //!< The device is powered and ready to perform operations. In this mode, no commands are sent by the device handler itself, but direct commands van be commanded and will be interpreted + // MODE_OFF = 1, //!< The device is powered off. The only command accepted in this mode is a mode change to on. + //! The device is powered on and the device handler periodically sends + //! commands. The commands to be sent are selected by the handler + //! according to the submode. + static const Mode_t MODE_NORMAL = 2; + //! The device is powered on and ready to perform operations. In this mode, + //! raw commands can be sent. The device handler will send all replies + //! received from the command back to the commanding object. + static const Mode_t MODE_RAW = 3; + //! The device is shut down but the switch could not be turned off, so the + //! device still is powered. In this mode, only a mode change to @c MODE_OFF + //! can be commanded, which tries to switch off the device again. + static const Mode_t MODE_ERROR_ON = 4; + //! This is a transitional state which can not be commanded. The device + //! handler performs all commands to get the device in a state ready to + //! perform commands. When this is completed, the mode changes to @c MODE_ON. + static const Mode_t _MODE_START_UP = TRANSITION_MODE_CHILD_ACTION_MASK | 5; + //! This is a transitional state which can not be commanded. + //! The device handler performs all actions and commands to get the device + //! shut down. When the device is off, the mode changes to @c MODE_OFF. + //! It is possible to set the mode to _MODE_SHUT_DOWN to use the to off + //! transition if available. + static const Mode_t _MODE_SHUT_DOWN = TRANSITION_MODE_CHILD_ACTION_MASK | 6; + //! It is possible to set the mode to _MODE_TO_ON to use the to on + //! transition if available. + static const Mode_t _MODE_TO_ON = TRANSITION_MODE_CHILD_ACTION_MASK | HasModesIF::MODE_ON; + //! It is possible to set the mode to _MODE_TO_RAW to use the to raw + //! transition if available. + static const Mode_t _MODE_TO_RAW = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_RAW; + //! It is possible to set the mode to _MODE_TO_NORMAL to use the to normal + //! transition if available. + static const Mode_t _MODE_TO_NORMAL = TRANSITION_MODE_CHILD_ACTION_MASK | MODE_NORMAL; + //! This is a transitional state which can not be commanded. + //! The device is shut down and ready to be switched off. + //! After the command to set the switch off has been sent, + //! the mode changes to @c MODE_WAIT_OFF + static const Mode_t _MODE_POWER_DOWN = TRANSITION_MODE_BASE_ACTION_MASK | 1; + //! This is a transitional state which can not be commanded. The device + //! will be switched on in this state. After the command to set the switch + //! on has been sent, the mode changes to @c MODE_WAIT_ON. + static const Mode_t _MODE_POWER_ON = TRANSITION_MODE_BASE_ACTION_MASK | 2; + //! This is a transitional state which can not be commanded. The switch has + //! been commanded off and the handler waits for it to be off. + //! When the switch is off, the mode changes to @c MODE_OFF. + static const Mode_t _MODE_WAIT_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 3; + //! This is a transitional state which can not be commanded. The switch + //! has been commanded on and the handler waits for it to be on. + //! When the switch is on, the mode changes to @c MODE_TO_ON. + static const Mode_t _MODE_WAIT_ON = TRANSITION_MODE_BASE_ACTION_MASK | 4; + //! This is a transitional state which can not be commanded. The switch has + //! been commanded off and is off now. This state is only to do an RMAP + //! cycle once more where the doSendRead() function will set the mode to + //! MODE_OFF. The reason to do this is to get rid of stuck packets in the IO Board. + static const Mode_t _MODE_SWITCH_IS_OFF = TRANSITION_MODE_BASE_ACTION_MASK | 5; - static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CDH; - static const Event DEVICE_BUILDING_COMMAND_FAILED = MAKE_EVENT(0, severity::LOW); - static const Event DEVICE_SENDING_COMMAND_FAILED = MAKE_EVENT(1, severity::LOW); - static const Event DEVICE_REQUESTING_REPLY_FAILED = MAKE_EVENT(2, severity::LOW); - static const Event DEVICE_READING_REPLY_FAILED = MAKE_EVENT(3, severity::LOW); - static const Event DEVICE_INTERPRETING_REPLY_FAILED = MAKE_EVENT(4, severity::LOW); - static const Event DEVICE_MISSED_REPLY = MAKE_EVENT(5, severity::LOW); - static const Event DEVICE_UNKNOWN_REPLY = MAKE_EVENT(6, severity::LOW); - static const Event DEVICE_UNREQUESTED_REPLY = MAKE_EVENT(7, severity::LOW); - static const Event INVALID_DEVICE_COMMAND = MAKE_EVENT(8, severity::LOW); //!< Indicates a SW bug in child class. - static const Event MONITORING_LIMIT_EXCEEDED = MAKE_EVENT(9, severity::LOW); - static const Event MONITORING_AMBIGUOUS = MAKE_EVENT(10, severity::HIGH); + static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CDH; + static const Event DEVICE_BUILDING_COMMAND_FAILED = MAKE_EVENT(0, severity::LOW); + static const Event DEVICE_SENDING_COMMAND_FAILED = MAKE_EVENT(1, severity::LOW); + static const Event DEVICE_REQUESTING_REPLY_FAILED = MAKE_EVENT(2, severity::LOW); + static const Event DEVICE_READING_REPLY_FAILED = MAKE_EVENT(3, severity::LOW); + static const Event DEVICE_INTERPRETING_REPLY_FAILED = MAKE_EVENT(4, severity::LOW); + static const Event DEVICE_MISSED_REPLY = MAKE_EVENT(5, severity::LOW); + static const Event DEVICE_UNKNOWN_REPLY = MAKE_EVENT(6, severity::LOW); + static const Event DEVICE_UNREQUESTED_REPLY = MAKE_EVENT(7, severity::LOW); + static const Event INVALID_DEVICE_COMMAND = MAKE_EVENT(8, severity::LOW); //!< Indicates a SW bug in child class. + static const Event MONITORING_LIMIT_EXCEEDED = MAKE_EVENT(9, severity::LOW); + static const Event MONITORING_AMBIGUOUS = MAKE_EVENT(10, severity::HIGH); - static const uint8_t INTERFACE_ID = CLASS_ID::DEVICE_HANDLER_IF; + static const uint8_t INTERFACE_ID = CLASS_ID::DEVICE_HANDLER_IF; - // Standard codes used when building commands. - static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If no command data was given when expected. - static const ReturnValue_t COMMAND_NOT_SUPPORTED = MAKE_RETURN_CODE(0xA1); //!< Command ID not in commandMap. Checked in DHB - static const ReturnValue_t COMMAND_ALREADY_SENT = MAKE_RETURN_CODE(0xA2); //!< Command was already executed. Checked in DHB - static const ReturnValue_t COMMAND_WAS_NOT_SENT = MAKE_RETURN_CODE(0xA3); - static const ReturnValue_t CANT_SWITCH_ADDRESS = MAKE_RETURN_CODE(0xA4); - static const ReturnValue_t WRONG_MODE_FOR_COMMAND = MAKE_RETURN_CODE(0xA5); - static const ReturnValue_t TIMEOUT = MAKE_RETURN_CODE(0xA6); - static const ReturnValue_t BUSY = MAKE_RETURN_CODE(0xA7); - static const ReturnValue_t NO_REPLY_EXPECTED = MAKE_RETURN_CODE(0xA8); //!< Used to indicate that this is a command-only command. - static const ReturnValue_t NON_OP_TEMPERATURE = MAKE_RETURN_CODE(0xA9); - static const ReturnValue_t COMMAND_NOT_IMPLEMENTED = MAKE_RETURN_CODE(0xAA); + // Standard codes used when building commands. + static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If no command data was given when expected. + static const ReturnValue_t COMMAND_NOT_SUPPORTED = MAKE_RETURN_CODE(0xA1); //!< Command ID not in commandMap. Checked in DHB + static const ReturnValue_t COMMAND_ALREADY_SENT = MAKE_RETURN_CODE(0xA2); //!< Command was already executed. Checked in DHB + static const ReturnValue_t COMMAND_WAS_NOT_SENT = MAKE_RETURN_CODE(0xA3); + static const ReturnValue_t CANT_SWITCH_ADDRESS = MAKE_RETURN_CODE(0xA4); + static const ReturnValue_t WRONG_MODE_FOR_COMMAND = MAKE_RETURN_CODE(0xA5); + static const ReturnValue_t TIMEOUT = MAKE_RETURN_CODE(0xA6); + static const ReturnValue_t BUSY = MAKE_RETURN_CODE(0xA7); + static const ReturnValue_t NO_REPLY_EXPECTED = MAKE_RETURN_CODE(0xA8); //!< Used to indicate that this is a command-only command. + static const ReturnValue_t NON_OP_TEMPERATURE = MAKE_RETURN_CODE(0xA9); + static const ReturnValue_t COMMAND_NOT_IMPLEMENTED = MAKE_RETURN_CODE(0xAA); - // Standard codes used in scanForReply - static const ReturnValue_t CHECKSUM_ERROR = MAKE_RETURN_CODE(0xB0); - static const ReturnValue_t LENGTH_MISSMATCH = MAKE_RETURN_CODE(0xB1); - static const ReturnValue_t INVALID_DATA = MAKE_RETURN_CODE(0xB2); - static const ReturnValue_t PROTOCOL_ERROR = MAKE_RETURN_CODE(0xB3); + // Standard codes used in scanForReply + static const ReturnValue_t CHECKSUM_ERROR = MAKE_RETURN_CODE(0xB0); + static const ReturnValue_t LENGTH_MISSMATCH = MAKE_RETURN_CODE(0xB1); + static const ReturnValue_t INVALID_DATA = MAKE_RETURN_CODE(0xB2); + static const ReturnValue_t PROTOCOL_ERROR = MAKE_RETURN_CODE(0xB3); - // 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 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 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 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 - static const ReturnValue_t INVALID_COMMAND_PARAMETER = MAKE_RETURN_CODE(0xD0); - static const ReturnValue_t INVALID_NUMBER_OR_LENGTH_OF_PARAMETERS = MAKE_RETURN_CODE(0xD1); + // Standard codes used in buildCommandFromCommand + static const ReturnValue_t INVALID_COMMAND_PARAMETER = MAKE_RETURN_CODE(0xD0); + static const ReturnValue_t INVALID_NUMBER_OR_LENGTH_OF_PARAMETERS = MAKE_RETURN_CODE(0xD1); - /** - * Communication action that will be executed. - * - * This is used by the child class to tell the base class what to do. - */ - enum CommunicationAction: uint8_t { - PERFORM_OPERATION, - SEND_WRITE,//!< Send write - GET_WRITE, //!< Get write - SEND_READ, //!< Send read - GET_READ, //!< Get read - NOTHING //!< Do nothing. - }; + /** + * Communication action that will be executed. + * + * This is used by the child class to tell the base class what to do. + */ + enum CommunicationAction: uint8_t { + PERFORM_OPERATION, + SEND_WRITE,//!< Send write + GET_WRITE, //!< Get write + SEND_READ, //!< Send read + GET_READ, //!< Get read + NOTHING //!< Do nothing. + }; - static constexpr uint32_t DEFAULT_THERMAL_SET_ID = sid_t::INVALID_SET_ID - 1; + static constexpr uint32_t DEFAULT_THERMAL_SET_ID = sid_t::INVALID_SET_ID - 1; - static constexpr lp_id_t DEFAULT_THERMAL_STATE_POOL_ID = - localpool::INVALID_LPID - 2; - static constexpr lp_id_t DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID = - localpool::INVALID_LPID - 1; + static constexpr lp_id_t DEFAULT_THERMAL_STATE_POOL_ID = + localpool::INVALID_LPID - 2; + static constexpr lp_id_t DEFAULT_THERMAL_HEATING_REQUEST_POOL_ID = + localpool::INVALID_LPID - 1; - /** - * Default Destructor - */ - virtual ~DeviceHandlerIF() {} + /** + * Default Destructor + */ + virtual ~DeviceHandlerIF() {} - /** - * This MessageQueue is used to command the device handler. - * @return the id of the MessageQueue - */ - virtual MessageQueueId_t getCommandQueue() const = 0; + /** + * This MessageQueue is used to command the device handler. + * @return the id of the MessageQueue + */ + virtual MessageQueueId_t getCommandQueue() const = 0; }; From 715386e366d40eb4dacfed62cd529ab72e53cb79 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sun, 13 Dec 2020 22:12:57 +0100 Subject: [PATCH 052/103] clened up a bit --- rmap/RMAP.cpp | 14 ++-- rmap/RMAP.h | 12 ++-- rmap/RMAPChannelIF.h | 11 +-- rmap/RMAPCookie.cpp | 9 +-- rmap/RMAPCookie.h | 16 +++-- rmap/RmapDeviceCommunicationIF.cpp | 10 +-- rmap/RmapDeviceCommunicationIF.h | 105 ++++++++++++++++------------- rmap/rmapStructs.h | 8 +-- 8 files changed, 100 insertions(+), 85 deletions(-) diff --git a/rmap/RMAP.cpp b/rmap/RMAP.cpp index 4ab8b17b..7ea6e532 100644 --- a/rmap/RMAP.cpp +++ b/rmap/RMAP.cpp @@ -1,8 +1,10 @@ -#include "../devicehandlers/DeviceCommunicationIF.h" -#include "rmapStructs.h" #include "RMAP.h" +#include "rmapStructs.h" #include "RMAPChannelIF.h" -#include + +#include "../devicehandlers/DeviceCommunicationIF.h" + +#include ReturnValue_t RMAP::reset(RMAPCookie* cookie) { return cookie->getChannel()->reset(); @@ -12,8 +14,8 @@ RMAP::RMAP(){ } -ReturnValue_t RMAP::sendWriteCommand(RMAPCookie *cookie, uint8_t* buffer, - uint32_t length) { +ReturnValue_t RMAP::sendWriteCommand(RMAPCookie *cookie, const uint8_t* buffer, + size_t length) { uint8_t instruction; if ((buffer == NULL) && (length != 0)) { @@ -61,7 +63,7 @@ ReturnValue_t RMAP::sendReadCommand(RMAPCookie *cookie, uint32_t expLength) { } ReturnValue_t RMAP::getReadReply(RMAPCookie *cookie, uint8_t **buffer, - uint32_t *size) { + size_t *size) { if (cookie->getChannel() == NULL) { return COMMAND_NO_CHANNEL; } diff --git a/rmap/RMAP.h b/rmap/RMAP.h index d14320cb..83e29fed 100644 --- a/rmap/RMAP.h +++ b/rmap/RMAP.h @@ -1,8 +1,8 @@ -#ifndef RMAPpp_H_ -#define RMAPpp_H_ +#ifndef FSFW_RMAP_RMAP_H_ +#define FSFW_RMAP_RMAP_H_ #include "../returnvalues/HasReturnvaluesIF.h" -#include "RMAPCookie.h" +#include "../rmap/RMAPCookie.h" //SHOULDTODO: clean up includes for RMAP, should be enough to include RMAP.h but right now it's quite chaotic... @@ -153,8 +153,8 @@ public: * - @c COMMAND_NULLPOINTER datalen was != 0 but data was == NULL in write command * - return codes of RMAPChannelIF::sendCommand() */ - static ReturnValue_t sendWriteCommand(RMAPCookie *cookie, uint8_t* buffer, - uint32_t length); + static ReturnValue_t sendWriteCommand(RMAPCookie *cookie, const uint8_t* buffer, + size_t length); /** * get the reply to a write command @@ -204,7 +204,7 @@ public: * - return codes of RMAPChannelIF::getReply() */ static ReturnValue_t getReadReply(RMAPCookie *cookie, uint8_t **buffer, - uint32_t *size); + size_t *size); /** * @see sendReadCommand() diff --git a/rmap/RMAPChannelIF.h b/rmap/RMAPChannelIF.h index dac4a722..0aa809c5 100644 --- a/rmap/RMAPChannelIF.h +++ b/rmap/RMAPChannelIF.h @@ -1,8 +1,9 @@ -#ifndef RMAPCHANNELIF_H_ -#define RMAPCHANNELIF_H_ +#ifndef FSFW_RMAP_RMAPCHANNELIF_H_ +#define FSFW_RMAP_RMAPCHANNELIF_H_ #include "RMAPCookie.h" #include "../returnvalues/HasReturnvaluesIF.h" +#include class RMAPChannelIF { public: @@ -73,7 +74,7 @@ public: * - @c NOT_SUPPORTED if you dont feel like implementing something... */ virtual ReturnValue_t sendCommand(RMAPCookie *cookie, uint8_t instruction, - uint8_t *data, uint32_t datalen)=0; + const uint8_t *data, size_t datalen)=0; /** * get the reply to an rmap command @@ -92,7 +93,7 @@ public: * - all RMAP standard replies */ virtual ReturnValue_t getReply(RMAPCookie *cookie, uint8_t **databuffer, - uint32_t *len)=0; + size_t *len)=0; /** * @@ -112,4 +113,4 @@ public: }; -#endif /* RMAPCHANNELIF_H_ */ +#endif /* FSFW_RMAP_RMAPCHANNELIF_H_ */ diff --git a/rmap/RMAPCookie.cpp b/rmap/RMAPCookie.cpp index 597f066c..f8fe2d3e 100644 --- a/rmap/RMAPCookie.cpp +++ b/rmap/RMAPCookie.cpp @@ -1,6 +1,6 @@ #include "RMAPChannelIF.h" #include "RMAPCookie.h" -#include +#include RMAPCookie::RMAPCookie() { @@ -31,7 +31,8 @@ RMAPCookie::RMAPCookie() { RMAPCookie::RMAPCookie(uint32_t set_address, uint8_t set_extended_address, - RMAPChannelIF *set_channel, uint8_t set_command_mask, uint32_t maxReplyLen) { + RMAPChannelIF *set_channel, uint8_t set_command_mask, + size_t maxReplyLen) { this->header.dest_address = 0; this->header.protocol = 0x01; this->header.instruction = 0; @@ -93,11 +94,11 @@ RMAPCookie::~RMAPCookie() { } -uint32_t RMAPCookie::getMaxReplyLen() const { +size_t RMAPCookie::getMaxReplyLen() const { return maxReplyLen; } -void RMAPCookie::setMaxReplyLen(uint32_t maxReplyLen) { +void RMAPCookie::setMaxReplyLen(size_t maxReplyLen) { this->maxReplyLen = maxReplyLen; } diff --git a/rmap/RMAPCookie.h b/rmap/RMAPCookie.h index 4c6081bd..38542646 100644 --- a/rmap/RMAPCookie.h +++ b/rmap/RMAPCookie.h @@ -1,8 +1,9 @@ -#ifndef RMAPCOOKIE_H_ -#define RMAPCOOKIE_H_ +#ifndef FSFW_RMAP_RMAPCOOKIE_H_ +#define FSFW_RMAP_RMAPCOOKIE_H_ -#include "../devicehandlers/CookieIF.h" #include "rmapStructs.h" +#include "../devicehandlers/CookieIF.h" +#include class RMAPChannelIF; @@ -12,7 +13,8 @@ public: RMAPCookie(); RMAPCookie(uint32_t set_address, uint8_t set_extended_address, - RMAPChannelIF *set_channel, uint8_t set_command_mask, uint32_t maxReplyLen = 0); + RMAPChannelIF *set_channel, uint8_t set_command_mask, + size_t maxReplyLen = 0); virtual ~RMAPCookie(); @@ -28,8 +30,8 @@ public: void setCommandMask(uint8_t commandMask); uint8_t getCommandMask(); - uint32_t getMaxReplyLen() const; - void setMaxReplyLen(uint32_t maxReplyLen); + size_t getMaxReplyLen() const; + void setMaxReplyLen(size_t maxReplyLen); uint16_t getTransactionIdentifier() const; void setTransactionIdentifier(uint16_t id_); @@ -55,4 +57,4 @@ protected: uint8_t dataCRC; }; -#endif /* RMAPCOOKIE_H_ */ +#endif /* FSFW_RMAP_RMAPCOOKIE_H_ */ diff --git a/rmap/RmapDeviceCommunicationIF.cpp b/rmap/RmapDeviceCommunicationIF.cpp index db4a75b5..d81baabd 100644 --- a/rmap/RmapDeviceCommunicationIF.cpp +++ b/rmap/RmapDeviceCommunicationIF.cpp @@ -5,9 +5,9 @@ RmapDeviceCommunicationIF::~RmapDeviceCommunicationIF() { } -ReturnValue_t RmapDeviceCommunicationIF::sendMessage(CookieIF* cookie, - uint8_t* data, uint32_t len) { - return RMAP::sendWriteCommand((RMAPCookie *) cookie, data, len); +ReturnValue_t RmapDeviceCommunicationIF::sendMessage(CookieIF *cookie, + const uint8_t * sendData, size_t sendLen) { + return RMAP::sendWriteCommand((RMAPCookie *) cookie, sendData, sendLen); } ReturnValue_t RmapDeviceCommunicationIF::getSendSuccess(CookieIF* cookie) { @@ -15,13 +15,13 @@ ReturnValue_t RmapDeviceCommunicationIF::getSendSuccess(CookieIF* cookie) { } ReturnValue_t RmapDeviceCommunicationIF::requestReceiveMessage( - CookieIF* cookie) { + CookieIF *cookie, size_t requestLen) { return RMAP::sendReadCommand((RMAPCookie *) cookie, ((RMAPCookie *) cookie)->getMaxReplyLen()); } ReturnValue_t RmapDeviceCommunicationIF::readReceivedMessage(CookieIF* cookie, - uint8_t** buffer, uint32_t* size) { + uint8_t** buffer, size_t * size) { return RMAP::getReadReply((RMAPCookie *) cookie, buffer, size); } diff --git a/rmap/RmapDeviceCommunicationIF.h b/rmap/RmapDeviceCommunicationIF.h index dacc720b..1333966a 100644 --- a/rmap/RmapDeviceCommunicationIF.h +++ b/rmap/RmapDeviceCommunicationIF.h @@ -1,10 +1,11 @@ -#ifndef MISSION_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ -#define MISSION_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ +#ifndef FSFW_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ +#define FSFW_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ #include "../devicehandlers/DeviceCommunicationIF.h" /** - * @brief This class is a implementation of a DeviceCommunicationIF for RMAP calls. It expects RMAPCookies or a derived class of RMAPCookies + * @brief This class is a implementation of a DeviceCommunicationIF for RMAP calls. + * It expects RMAPCookies or a derived class of RMAPCookies * * @details The open, close and reOpen calls are mission specific * The open call might return any child of RMAPCookies @@ -16,65 +17,73 @@ class RmapDeviceCommunicationIF: public DeviceCommunicationIF { public: virtual ~RmapDeviceCommunicationIF(); - /** - * This method is mission specific as the open call will return a mission specific cookie - * - * @param cookie A cookie, can be mission specific subclass of RMAP Cookie - * @param address The address of the RMAP Cookie - * @param maxReplyLen Maximum length of expected reply - * @return - */ - virtual ReturnValue_t open(CookieIF **cookie, uint32_t address, - uint32_t maxReplyLen) = 0; - - /** - * Use an existing cookie to open a connection to a new DeviceCommunication. - * The previous connection must not be closed. - * If the returnvalue is not RETURN_OK, the cookie is unchanged and - * can be used with the previous connection. - * + * @brief Device specific initialization, using the cookie. + * @details + * The cookie is already prepared in the factory. If the communication + * interface needs to be set up in some way and requires cookie information, + * this can be performed in this function, which is called on device handler + * initialization. * @param cookie - * @param address - * @param maxReplyLen - * @return + * @return -@c RETURN_OK if initialization was successfull + * - Everything else triggers failure event with returnvalue as parameter 1 */ - virtual ReturnValue_t reOpen(CookieIF *cookie, uint32_t address, - uint32_t maxReplyLen) = 0; - + virtual ReturnValue_t initializeInterface(CookieIF * cookie) = 0; /** - * Closing call of connection and memory free of cookie. Mission dependent call + * Called by DHB in the SEND_WRITE doSendWrite(). + * This function is used to send data to the physical device + * by implementing and calling related drivers or wrapper functions. * @param cookie + * @param data + * @param len + * @return -@c RETURN_OK for successfull send + * - Everything else triggers failure event with returnvalue as parameter 1 */ - virtual void close(CookieIF *cookie) = 0; + virtual ReturnValue_t sendMessage(CookieIF *cookie, const uint8_t * sendData, + size_t sendLen); - //SHOULDDO can data be const? /** - * - * - * @param cookie Expects an RMAPCookie or derived from RMAPCookie Class - * @param data Data to be send - * @param len Length of the data to be send - * @return - Return codes of RMAP::sendWriteCommand() + * Called by DHB in the GET_WRITE doGetWrite(). + * Get send confirmation that the data in sendMessage() was sent successfully. + * @param cookie + * @return -@c RETURN_OK if data was sent successfull + * - Everything else triggers falure event with returnvalue as parameter 1 */ - virtual ReturnValue_t sendMessage(CookieIF *cookie, uint8_t *data, - uint32_t len); - virtual ReturnValue_t getSendSuccess(CookieIF *cookie); - virtual ReturnValue_t requestReceiveMessage(CookieIF *cookie); + /** + * Called by DHB in the SEND_WRITE doSendRead(). + * It is assumed that it is always possible to request a reply + * from a device. + * + * @param cookie + * @return -@c RETURN_OK to confirm the request for data has been sent. + * -@c NO_READ_REQUEST if no request shall be made. readReceivedMessage() + * will not be called in the respective communication cycle. + * - Everything else triggers failure event with returnvalue as parameter 1 + */ + virtual ReturnValue_t requestReceiveMessage(CookieIF *cookie, size_t requestLen); + /** + * Called by DHB in the GET_WRITE doGetRead(). + * This function is used to receive data from the physical device + * by implementing and calling related drivers or wrapper functions. + * @param cookie + * @param data + * @param len + * @return @c RETURN_OK for successfull receive + * - Everything else triggers failure event with returnvalue as parameter 1 + */ virtual ReturnValue_t readReceivedMessage(CookieIF *cookie, uint8_t **buffer, - uint32_t *size); + size_t *size); - virtual ReturnValue_t setAddress(CookieIF *cookie, uint32_t address); - - virtual uint32_t getAddress(CookieIF *cookie); - - virtual ReturnValue_t setParameter(CookieIF *cookie, uint32_t parameter); - - virtual uint32_t getParameter(CookieIF *cookie); + ReturnValue_t setAddress(CookieIF* cookie, + uint32_t address); + uint32_t getAddress(CookieIF* cookie); + ReturnValue_t setParameter(CookieIF* cookie, + uint32_t parameter); + uint32_t getParameter(CookieIF* cookie); }; -#endif /* MISSION_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ */ +#endif /* FSFW_RMAP_RMAPDEVICECOMMUNICATIONINTERFACE_H_ */ diff --git a/rmap/rmapStructs.h b/rmap/rmapStructs.h index bf0fb260..11d8bb85 100644 --- a/rmap/rmapStructs.h +++ b/rmap/rmapStructs.h @@ -1,7 +1,7 @@ -#ifndef RMAPSTRUCTS_H_ -#define RMAPSTRUCTS_H_ +#ifndef FSFW_RMAP_RMAPSTRUCTS_H_ +#define FSFW_RMAP_RMAPSTRUCTS_H_ -#include +#include //SHOULDDO: having the defines within a namespace would be nice. Problem are the defines referencing the previous define, eg RMAP_COMMAND_WRITE @@ -95,4 +95,4 @@ struct rmap_write_reply_header { } -#endif /* RMAPSTRUCTS_H_ */ +#endif /* FSFW_RMAP_RMAPSTRUCTS_H_ */ From 720e3baa9080eb0d2a3b3bbcf398788ed4639a4f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 10:48:39 +0100 Subject: [PATCH 053/103] fixed includes --- unittest/internal/osal/IntTestMq.cpp | 4 ++-- unittest/internal/osal/IntTestMutex.cpp | 2 +- unittest/internal/osal/IntTestSemaphore.cpp | 6 +++--- unittest/internal/serialize/IntTestSerialization.cpp | 7 ++++--- unittest/internal/serialize/IntTestSerialization.h | 2 +- 5 files changed, 11 insertions(+), 10 deletions(-) diff --git a/unittest/internal/osal/IntTestMq.cpp b/unittest/internal/osal/IntTestMq.cpp index 8d95f51e..9917285f 100644 --- a/unittest/internal/osal/IntTestMq.cpp +++ b/unittest/internal/osal/IntTestMq.cpp @@ -1,8 +1,8 @@ #include "IntTestMq.h" #include "../UnittDefinitions.h" -#include "../../ipc/MessageQueueIF.h" -#include "../../ipc/QueueFactory.h" +#include "../../../ipc/MessageQueueIF.h" +#include "../../../ipc/QueueFactory.h" #include diff --git a/unittest/internal/osal/IntTestMutex.cpp b/unittest/internal/osal/IntTestMutex.cpp index 01581347..d2f8b962 100644 --- a/unittest/internal/osal/IntTestMutex.cpp +++ b/unittest/internal/osal/IntTestMutex.cpp @@ -1,6 +1,6 @@ #include "IntTestMutex.h" -#include "../../ipc/MutexFactory.h" +#include "../../../ipc/MutexFactory.h" #include "../UnittDefinitions.h" #if defined(hosted) diff --git a/unittest/internal/osal/IntTestSemaphore.cpp b/unittest/internal/osal/IntTestSemaphore.cpp index f260b6a5..6d2719d5 100644 --- a/unittest/internal/osal/IntTestSemaphore.cpp +++ b/unittest/internal/osal/IntTestSemaphore.cpp @@ -1,9 +1,9 @@ #include "IntTestSemaphore.h" #include "../UnittDefinitions.h" -#include "../../tasks/SemaphoreFactory.h" -#include "../../serviceinterface/ServiceInterfaceStream.h" -#include "../../timemanager/Stopwatch.h" +#include "../../../tasks/SemaphoreFactory.h" +#include "../../../serviceinterface/ServiceInterfaceStream.h" +#include "../../../timemanager/Stopwatch.h" void testsemaph::testBinSemaph() { diff --git a/unittest/internal/serialize/IntTestSerialization.cpp b/unittest/internal/serialize/IntTestSerialization.cpp index 1e33ff33..793661c5 100644 --- a/unittest/internal/serialize/IntTestSerialization.cpp +++ b/unittest/internal/serialize/IntTestSerialization.cpp @@ -1,8 +1,9 @@ #include "IntTestSerialization.h" #include "../UnittDefinitions.h" -#include "../../serialize/SerializeElement.h" -#include "../../serialize/SerialBufferAdapter.h" -#include "../../serialize/SerializeIF.h" + +#include "../../../serialize/SerializeElement.h" +#include "../../../serialize/SerialBufferAdapter.h" +#include "../../../serialize/SerializeIF.h" #include diff --git a/unittest/internal/serialize/IntTestSerialization.h b/unittest/internal/serialize/IntTestSerialization.h index e8dbd35a..8706e057 100644 --- a/unittest/internal/serialize/IntTestSerialization.h +++ b/unittest/internal/serialize/IntTestSerialization.h @@ -1,7 +1,7 @@ #ifndef FSFW_UNITTEST_INTERNAL_INTTESTSERIALIZATION_H_ #define FSFW_UNITTEST_INTERNAL_INTTESTSERIALIZATION_H_ -#include "../../returnvalues/HasReturnvaluesIF.h" +#include "../../../returnvalues/HasReturnvaluesIF.h" #include namespace testserialize { From dc72fa938d593083b8fb60ff38ea7f9b6d754711 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:10:22 +0100 Subject: [PATCH 054/103] type update --- globalfunctions/Type.cpp | 1 - globalfunctions/Type.h | 13 ++++++++++--- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/globalfunctions/Type.cpp b/globalfunctions/Type.cpp index ae595b81..fa6d2f28 100644 --- a/globalfunctions/Type.cpp +++ b/globalfunctions/Type.cpp @@ -1,4 +1,3 @@ -#include "../serialize/SerializeAdapter.h" #include "Type.h" #include "../serialize/SerializeAdapter.h" diff --git a/globalfunctions/Type.h b/globalfunctions/Type.h index be499ffc..d28f56ac 100644 --- a/globalfunctions/Type.h +++ b/globalfunctions/Type.h @@ -1,9 +1,12 @@ -#ifndef TYPE_H_ -#define TYPE_H_ +#ifndef FSFW_GLOBALFUNCTIONS_TYPE_H_ +#define FSFW_GLOBALFUNCTIONS_TYPE_H_ #include "../returnvalues/HasReturnvaluesIF.h" #include "../serialize/SerializeIF.h" +/** + * @brief Type definition for CCSDS or ECSS. + */ class Type: public SerializeIF { public: enum ActualType_t { @@ -56,6 +59,10 @@ struct PodTypeConversion { static const Type::ActualType_t type = Type::UNKNOWN_TYPE; }; template<> +struct PodTypeConversion { + static const Type::ActualType_t type = Type::UINT8_T; +}; +template<> struct PodTypeConversion { static const Type::ActualType_t type = Type::UINT8_T; }; @@ -88,4 +95,4 @@ struct PodTypeConversion { static const Type::ActualType_t type = Type::DOUBLE; }; -#endif /* TYPE_H_ */ +#endif /* FSFW_GLOBALFUNCTIONS_TYPE_H_ */ From 94fa917202970b0e7ecf516497be87ce8f1727c3 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:17:22 +0100 Subject: [PATCH 055/103] some tweaks --- osal/FreeRTOS/BinSemaphUsingTask.cpp | 8 +++++-- osal/FreeRTOS/BinSemaphUsingTask.h | 27 ++++++++++++++++++----- osal/FreeRTOS/BinarySemaphore.cpp | 4 ++-- osal/FreeRTOS/BinarySemaphore.h | 6 ++--- osal/FreeRTOS/Clock.cpp | 10 ++++++++- osal/FreeRTOS/CountingSemaphUsingTask.cpp | 5 +++-- osal/FreeRTOS/CountingSemaphUsingTask.h | 13 ++++++----- osal/FreeRTOS/CountingSemaphore.cpp | 5 +++-- osal/FreeRTOS/CountingSemaphore.h | 3 ++- osal/FreeRTOS/MessageQueue.cpp | 7 +++++- osal/FreeRTOS/MessageQueue.h | 3 ++- osal/FreeRTOS/MutexFactory.cpp | 10 +++++---- osal/FreeRTOS/QueueFactory.cpp | 4 ++-- osal/FreeRTOS/TaskFactory.cpp | 20 ++++++++--------- osal/FreeRTOS/TaskManagement.cpp | 2 +- osal/FreeRTOS/TaskManagement.h | 3 +-- osal/FreeRTOS/Timekeeper.cpp | 2 +- timemanager/Clock.h | 6 ++--- 18 files changed, 88 insertions(+), 50 deletions(-) diff --git a/osal/FreeRTOS/BinSemaphUsingTask.cpp b/osal/FreeRTOS/BinSemaphUsingTask.cpp index dd1e48ca..9c29948e 100644 --- a/osal/FreeRTOS/BinSemaphUsingTask.cpp +++ b/osal/FreeRTOS/BinSemaphUsingTask.cpp @@ -1,5 +1,5 @@ -#include "../../osal/FreeRTOS/BinSemaphUsingTask.h" -#include "../../osal/FreeRTOS/TaskManagement.h" +#include "BinSemaphUsingTask.h" +#include "TaskManagement.h" #include "../../serviceinterface/ServiceInterfaceStream.h" BinarySemaphoreUsingTask::BinarySemaphoreUsingTask() { @@ -16,6 +16,10 @@ BinarySemaphoreUsingTask::~BinarySemaphoreUsingTask() { xTaskNotifyAndQuery(handle, 0, eSetValueWithOverwrite, nullptr); } +void BinarySemaphoreUsingTask::refreshTaskHandle() { + handle = TaskManagement::getCurrentTaskHandle(); +} + ReturnValue_t BinarySemaphoreUsingTask::acquire(TimeoutType timeoutType, uint32_t timeoutMs) { TickType_t timeout = 0; diff --git a/osal/FreeRTOS/BinSemaphUsingTask.h b/osal/FreeRTOS/BinSemaphUsingTask.h index f3c0b0ea..65a091a3 100644 --- a/osal/FreeRTOS/BinSemaphUsingTask.h +++ b/osal/FreeRTOS/BinSemaphUsingTask.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ -#define FRAMEWORK_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ +#ifndef FSFW_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ +#define FSFW_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ #include "../../returnvalues/HasReturnvaluesIF.h" #include "../../tasks/SemaphoreIF.h" @@ -7,13 +7,20 @@ #include #include +// todo: does not work for older FreeRTOS version, so we should +// actually check whether tskKERNEL_VERSION_MAJOR is larger than.. 7 or 8 ? + /** * @brief Binary Semaphore implementation using the task notification value. * The notification value should therefore not be used - * for other purposes. + * for other purposes! * @details * Additional information: https://www.freertos.org/RTOS-task-notifications.html * and general semaphore documentation. + * This semaphore is bound to the task it is created in! + * Take care of building this class with the correct executing task, + * (for example in the initializeAfterTaskCreation() function) or + * by calling refreshTaskHandle() with the correct executing task. */ class BinarySemaphoreUsingTask: public SemaphoreIF, public HasReturnvaluesIF { @@ -25,6 +32,16 @@ public: //! @brief Default dtor virtual~ BinarySemaphoreUsingTask(); + /** + * This function can be used to get the correct task handle from the + * currently executing task. + * + * This is required because the task notification value will be used + * as a binary semaphore, and the semaphore might be created by another + * task. + */ + void refreshTaskHandle(); + ReturnValue_t acquire(TimeoutType timeoutType = TimeoutType::BLOCKING, uint32_t timeoutMs = portMAX_DELAY) override; ReturnValue_t release() override; @@ -67,10 +84,10 @@ public: * - @c RETURN_FAILED on failure */ static ReturnValue_t releaseFromISR(TaskHandle_t taskToNotify, - BaseType_t * higherPriorityTaskWoken); + BaseType_t* higherPriorityTaskWoken); protected: TaskHandle_t handle; }; -#endif /* FRAMEWORK_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ */ +#endif /* FSFW_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ */ diff --git a/osal/FreeRTOS/BinarySemaphore.cpp b/osal/FreeRTOS/BinarySemaphore.cpp index 8cc3c495..6fee5c35 100644 --- a/osal/FreeRTOS/BinarySemaphore.cpp +++ b/osal/FreeRTOS/BinarySemaphore.cpp @@ -1,5 +1,5 @@ -#include "../../osal/FreeRTOS/BinarySemaphore.h" -#include "../../osal/FreeRTOS/TaskManagement.h" +#include "BinarySemaphore.h" +#include "TaskManagement.h" #include "../../serviceinterface/ServiceInterfaceStream.h" BinarySemaphore::BinarySemaphore() { diff --git a/osal/FreeRTOS/BinarySemaphore.h b/osal/FreeRTOS/BinarySemaphore.h index c6cedc53..8969d503 100644 --- a/osal/FreeRTOS/BinarySemaphore.h +++ b/osal/FreeRTOS/BinarySemaphore.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_OSAL_FREERTOS_BINARYSEMPAHORE_H_ -#define FRAMEWORK_OSAL_FREERTOS_BINARYSEMPAHORE_H_ +#ifndef FSFW_OSAL_FREERTOS_BINARYSEMPAHORE_H_ +#define FSFW_OSAL_FREERTOS_BINARYSEMPAHORE_H_ #include "../../returnvalues/HasReturnvaluesIF.h" #include "../../tasks/SemaphoreIF.h" @@ -104,4 +104,4 @@ protected: SemaphoreHandle_t handle; }; -#endif /* FRAMEWORK_OSAL_FREERTOS_BINARYSEMPAHORE_H_ */ +#endif /* FSFW_OSAL_FREERTOS_BINARYSEMPAHORE_H_ */ diff --git a/osal/FreeRTOS/Clock.cpp b/osal/FreeRTOS/Clock.cpp index acfa98d7..d3f4e68e 100644 --- a/osal/FreeRTOS/Clock.cpp +++ b/osal/FreeRTOS/Clock.cpp @@ -1,6 +1,7 @@ +#include "Timekeeper.h" + #include "../../timemanager/Clock.h" #include "../../globalfunctions/timevalOperations.h" -#include "Timekeeper.h" #include #include @@ -67,6 +68,13 @@ ReturnValue_t Clock::getUptime(uint32_t* uptimeMs) { return HasReturnvaluesIF::RETURN_OK; } + +//uint32_t Clock::getUptimeSeconds() { +// timeval uptime = getUptime(); +// return uptime.tv_sec; +//} + + ReturnValue_t Clock::getClock_usecs(uint64_t* time) { timeval time_timeval; ReturnValue_t result = getClock_timeval(&time_timeval); diff --git a/osal/FreeRTOS/CountingSemaphUsingTask.cpp b/osal/FreeRTOS/CountingSemaphUsingTask.cpp index a47341bc..17cdf7ce 100644 --- a/osal/FreeRTOS/CountingSemaphUsingTask.cpp +++ b/osal/FreeRTOS/CountingSemaphUsingTask.cpp @@ -1,5 +1,6 @@ -#include "../../osal/FreeRTOS/CountingSemaphUsingTask.h" -#include "../../osal/FreeRTOS/TaskManagement.h" +#include "CountingSemaphUsingTask.h" +#include "TaskManagement.h" + #include "../../serviceinterface/ServiceInterfaceStream.h" CountingSemaphoreUsingTask::CountingSemaphoreUsingTask(const uint8_t maxCount, diff --git a/osal/FreeRTOS/CountingSemaphUsingTask.h b/osal/FreeRTOS/CountingSemaphUsingTask.h index 8977258c..f258197b 100644 --- a/osal/FreeRTOS/CountingSemaphUsingTask.h +++ b/osal/FreeRTOS/CountingSemaphUsingTask.h @@ -1,13 +1,11 @@ -#ifndef FRAMEWORK_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ -#define FRAMEWORK_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ +#ifndef FSFW_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ +#define FSFW_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ -#include "../../osal/FreeRTOS/CountingSemaphUsingTask.h" +#include "CountingSemaphUsingTask.h" #include "../../tasks/SemaphoreIF.h" -extern "C" { #include #include -} /** * @brief Couting Semaphore implementation which uses the notification value @@ -16,6 +14,9 @@ extern "C" { * @details * Additional information: https://www.freertos.org/RTOS-task-notifications.html * and general semaphore documentation. + * This semaphore is bound to the task it is created in! + * Take care of calling this function with the correct executing task, + * (for example in the initializeAfterTaskCreation() function). */ class CountingSemaphoreUsingTask: public SemaphoreIF { public: @@ -99,4 +100,4 @@ private: const uint8_t maxCount; }; -#endif /* FRAMEWORK_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ */ +#endif /* FSFW_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ */ diff --git a/osal/FreeRTOS/CountingSemaphore.cpp b/osal/FreeRTOS/CountingSemaphore.cpp index d1310a6a..a202e480 100644 --- a/osal/FreeRTOS/CountingSemaphore.cpp +++ b/osal/FreeRTOS/CountingSemaphore.cpp @@ -1,6 +1,7 @@ -#include "../../osal/FreeRTOS/CountingSemaphore.h" +#include "CountingSemaphore.h" +#include "TaskManagement.h" + #include "../../serviceinterface/ServiceInterfaceStream.h" -#include "../../osal/FreeRTOS/TaskManagement.h" #include diff --git a/osal/FreeRTOS/CountingSemaphore.h b/osal/FreeRTOS/CountingSemaphore.h index ae2f62ae..6af1d6d2 100644 --- a/osal/FreeRTOS/CountingSemaphore.h +++ b/osal/FreeRTOS/CountingSemaphore.h @@ -1,6 +1,7 @@ #ifndef FRAMEWORK_OSAL_FREERTOS_COUNTINGSEMAPHORE_H_ #define FRAMEWORK_OSAL_FREERTOS_COUNTINGSEMAPHORE_H_ -#include "../../osal/FreeRTOS/BinarySemaphore.h" + +#include "BinarySemaphore.h" /** * @brief Counting semaphores, which can be acquire more than once. diff --git a/osal/FreeRTOS/MessageQueue.cpp b/osal/FreeRTOS/MessageQueue.cpp index 2dfe5ab6..fdadf8b7 100644 --- a/osal/FreeRTOS/MessageQueue.cpp +++ b/osal/FreeRTOS/MessageQueue.cpp @@ -11,7 +11,12 @@ MessageQueue::MessageQueue(size_t messageDepth, size_t maxMessageSize): maxMessageSize(maxMessageSize) { handle = xQueueCreate(messageDepth, maxMessageSize); if (handle == nullptr) { - sif::error << "MessageQueue::MessageQueue Creation failed" << std::endl; + sif::error << "MessageQueue::MessageQueue:" + << " Creation failed." << std::endl; + sif::error << "Specified Message Depth: " << messageDepth + << std::endl; + sif::error << "Specified Maximum Message Size: " + << maxMessageSize << std::endl; } } diff --git a/osal/FreeRTOS/MessageQueue.h b/osal/FreeRTOS/MessageQueue.h index b99bf7c8..8fa86283 100644 --- a/osal/FreeRTOS/MessageQueue.h +++ b/osal/FreeRTOS/MessageQueue.h @@ -1,10 +1,11 @@ #ifndef FSFW_OSAL_FREERTOS_MESSAGEQUEUE_H_ #define FSFW_OSAL_FREERTOS_MESSAGEQUEUE_H_ +#include "TaskManagement.h" + #include "../../internalError/InternalErrorReporterIF.h" #include "../../ipc/MessageQueueIF.h" #include "../../ipc/MessageQueueMessageIF.h" -#include "../../osal/FreeRTOS/TaskManagement.h" #include #include diff --git a/osal/FreeRTOS/MutexFactory.cpp b/osal/FreeRTOS/MutexFactory.cpp index 75b63d07..d9569e35 100644 --- a/osal/FreeRTOS/MutexFactory.cpp +++ b/osal/FreeRTOS/MutexFactory.cpp @@ -1,10 +1,12 @@ +#include "Mutex.h" + #include "../../ipc/MutexFactory.h" -#include "../FreeRTOS/Mutex.h" -//TODO: Different variant than the lazy loading in QueueFactory. What's better and why? -> one is on heap the other on bss/data +//TODO: Different variant than the lazy loading in QueueFactory. +//What's better and why? -> one is on heap the other on bss/data //MutexFactory* MutexFactory::factoryInstance = new MutexFactory(); -MutexFactory* MutexFactory::factoryInstance = NULL; +MutexFactory* MutexFactory::factoryInstance = nullptr; MutexFactory::MutexFactory() { } @@ -13,7 +15,7 @@ MutexFactory::~MutexFactory() { } MutexFactory* MutexFactory::instance() { - if (factoryInstance == NULL){ + if (factoryInstance == nullptr){ factoryInstance = new MutexFactory(); } return MutexFactory::factoryInstance; diff --git a/osal/FreeRTOS/QueueFactory.cpp b/osal/FreeRTOS/QueueFactory.cpp index ed29e10c..5b3c73dc 100644 --- a/osal/FreeRTOS/QueueFactory.cpp +++ b/osal/FreeRTOS/QueueFactory.cpp @@ -1,8 +1,8 @@ -#include "MessageQueue.h" - #include "../../ipc/MessageQueueSenderIF.h" #include "../../ipc/QueueFactory.h" +#include "../../osal/FreeRTOS/MessageQueue.h" + QueueFactory* QueueFactory::factoryInstance = nullptr; diff --git a/osal/FreeRTOS/TaskFactory.cpp b/osal/FreeRTOS/TaskFactory.cpp index 80df38b2..3ac5cb49 100644 --- a/osal/FreeRTOS/TaskFactory.cpp +++ b/osal/FreeRTOS/TaskFactory.cpp @@ -13,32 +13,30 @@ TaskFactory::~TaskFactory() { TaskFactory* TaskFactory::instance() { return TaskFactory::factoryInstance; } -/*** - * Keep in Mind that you need to call before this vTaskStartScheduler()! - * High taskPriority_ number means high priority. - */ + PeriodicTaskIF* TaskFactory::createPeriodicTask(TaskName name_, TaskPriority taskPriority_, TaskStackSize stackSize_, TaskPeriod period_, TaskDeadlineMissedFunction deadLineMissedFunction_) { - return (PeriodicTaskIF*) (new PeriodicTask(name_, taskPriority_, stackSize_, - period_, deadLineMissedFunction_)); + return dynamic_cast(new PeriodicTask(name_, taskPriority_, + stackSize_, period_, deadLineMissedFunction_)); } -/*** + +/** * Keep in Mind that you need to call before this vTaskStartScheduler()! */ FixedTimeslotTaskIF* TaskFactory::createFixedTimeslotTask(TaskName name_, TaskPriority taskPriority_, TaskStackSize stackSize_, TaskPeriod period_, TaskDeadlineMissedFunction deadLineMissedFunction_) { - return (FixedTimeslotTaskIF*) (new FixedTimeslotTask(name_, taskPriority_, - stackSize_, period_, deadLineMissedFunction_)); + return dynamic_cast(new FixedTimeslotTask(name_, + taskPriority_,stackSize_, period_, deadLineMissedFunction_)); } ReturnValue_t TaskFactory::deleteTask(PeriodicTaskIF* task) { - if (task == NULL) { + if (task == nullptr) { //delete self - vTaskDelete(NULL); + vTaskDelete(nullptr); return HasReturnvaluesIF::RETURN_OK; } else { //TODO not implemented diff --git a/osal/FreeRTOS/TaskManagement.cpp b/osal/FreeRTOS/TaskManagement.cpp index b77f12a9..18572045 100644 --- a/osal/FreeRTOS/TaskManagement.cpp +++ b/osal/FreeRTOS/TaskManagement.cpp @@ -1,4 +1,4 @@ -#include "../../osal/FreeRTOS/TaskManagement.h" +#include "TaskManagement.h" void TaskManagement::vRequestContextSwitchFromTask() { vTaskDelay(0); diff --git a/osal/FreeRTOS/TaskManagement.h b/osal/FreeRTOS/TaskManagement.h index eb735185..c6c46f21 100644 --- a/osal/FreeRTOS/TaskManagement.h +++ b/osal/FreeRTOS/TaskManagement.h @@ -3,10 +3,9 @@ #include "../../returnvalues/HasReturnvaluesIF.h" -extern "C" { #include #include -} + #include /** diff --git a/osal/FreeRTOS/Timekeeper.cpp b/osal/FreeRTOS/Timekeeper.cpp index 1031f0c4..d986d832 100644 --- a/osal/FreeRTOS/Timekeeper.cpp +++ b/osal/FreeRTOS/Timekeeper.cpp @@ -1,6 +1,6 @@ #include "Timekeeper.h" -#include "FreeRTOSConfig.h" +#include Timekeeper * Timekeeper::myinstance = nullptr; diff --git a/timemanager/Clock.h b/timemanager/Clock.h index bc112388..d8b06fda 100644 --- a/timemanager/Clock.h +++ b/timemanager/Clock.h @@ -1,5 +1,5 @@ -#ifndef FRAMEWORK_TIMEMANAGER_CLOCK_H_ -#define FRAMEWORK_TIMEMANAGER_CLOCK_H_ +#ifndef FSFW_TIMEMANAGER_CLOCK_H_ +#define FSFW_TIMEMANAGER_CLOCK_H_ #include "../returnvalues/HasReturnvaluesIF.h" #include "../ipc/MutexHelper.h" @@ -151,4 +151,4 @@ private: }; -#endif /* FRAMEWORK_TIMEMANAGER_CLOCK_H_ */ +#endif /* FSFW_TIMEMANAGER_CLOCK_H_ */ From 313d898aef8dd1f2591892aebbec7daab2be3fad Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:22:44 +0100 Subject: [PATCH 056/103] small update --- ipc/QueueFactory.h | 1 + osal/FreeRTOS/QueueFactory.cpp | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/ipc/QueueFactory.h b/ipc/QueueFactory.h index 9853d256..6fc0643e 100644 --- a/ipc/QueueFactory.h +++ b/ipc/QueueFactory.h @@ -3,6 +3,7 @@ #include "MessageQueueIF.h" #include "MessageQueueMessage.h" + #include /** diff --git a/osal/FreeRTOS/QueueFactory.cpp b/osal/FreeRTOS/QueueFactory.cpp index 5b3c73dc..ed29e10c 100644 --- a/osal/FreeRTOS/QueueFactory.cpp +++ b/osal/FreeRTOS/QueueFactory.cpp @@ -1,8 +1,8 @@ +#include "MessageQueue.h" + #include "../../ipc/MessageQueueSenderIF.h" #include "../../ipc/QueueFactory.h" -#include "../../osal/FreeRTOS/MessageQueue.h" - QueueFactory* QueueFactory::factoryInstance = nullptr; From 7eeba71619c982fd8f7ca5449cdf3441b42a4ef1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:34:54 +0100 Subject: [PATCH 057/103] subsystem update --- subsystem/Subsystem.cpp | 4 +++- subsystem/SubsystemBase.cpp | 10 +++++----- subsystem/modes/ModeDefinitions.h | 21 +++++++++------------ subsystem/modes/ModeSequenceMessage.cpp | 25 ++++++------------------- subsystem/modes/ModeSequenceMessage.h | 10 ++++++---- subsystem/modes/ModeStore.cpp | 4 +++- subsystem/modes/ModeStore.h | 6 ++++-- subsystem/modes/ModeStoreIF.h | 6 ++++-- 8 files changed, 40 insertions(+), 46 deletions(-) diff --git a/subsystem/Subsystem.cpp b/subsystem/Subsystem.cpp index 56d47da2..50fc4d05 100644 --- a/subsystem/Subsystem.cpp +++ b/subsystem/Subsystem.cpp @@ -1,10 +1,12 @@ +#include "Subsystem.h" + #include "../health/HealthMessage.h" #include "../objectmanager/ObjectManagerIF.h" #include "../serialize/SerialArrayListAdapter.h" #include "../serialize/SerialFixedArrayListAdapter.h" #include "../serialize/SerializeElement.h" #include "../serialize/SerialLinkedListAdapter.h" -#include "Subsystem.h" + #include Subsystem::Subsystem(object_id_t setObjectId, object_id_t parent, diff --git a/subsystem/SubsystemBase.cpp b/subsystem/SubsystemBase.cpp index 56ae1062..787d6be1 100644 --- a/subsystem/SubsystemBase.cpp +++ b/subsystem/SubsystemBase.cpp @@ -1,13 +1,13 @@ -#include "../serviceinterface/ServiceInterfaceStream.h" -#include "../serviceinterface/ServiceInterfaceStream.h" #include "SubsystemBase.h" + +#include "../serviceinterface/ServiceInterfaceStream.h" #include "../ipc/QueueFactory.h" SubsystemBase::SubsystemBase(object_id_t setObjectId, object_id_t parent, Mode_t initialMode, uint16_t commandQueueDepth) : - SystemObject(setObjectId), mode(initialMode), submode(SUBMODE_NONE), childrenChangedMode( - false), commandsOutstanding(0), commandQueue(NULL), healthHelper(this, - setObjectId), modeHelper(this), parentId(parent) { + SystemObject(setObjectId), mode(initialMode), submode(SUBMODE_NONE), + childrenChangedMode(false), commandsOutstanding(0), commandQueue(NULL), + healthHelper(this, setObjectId), modeHelper(this), parentId(parent) { commandQueue = QueueFactory::instance()->createMessageQueue(commandQueueDepth, CommandMessage::MAX_MESSAGE_SIZE); } diff --git a/subsystem/modes/ModeDefinitions.h b/subsystem/modes/ModeDefinitions.h index a865ab0c..13a780ee 100644 --- a/subsystem/modes/ModeDefinitions.h +++ b/subsystem/modes/ModeDefinitions.h @@ -1,22 +1,19 @@ -#ifndef MODEDEFINITIONS_H_ -#define MODEDEFINITIONS_H_ +#ifndef FSFW_SUBSYSTEM_MODES_MODEDEFINITIONS_H_ +#define FSFW_SUBSYSTEM_MODES_MODEDEFINITIONS_H_ #include "../../modes/HasModesIF.h" #include "../../objectmanager/SystemObjectIF.h" #include "../../serialize/SerializeIF.h" #include "../../serialize/SerialLinkedListAdapter.h" + class ModeListEntry: public SerializeIF, public LinkedElement { public: - ModeListEntry() : - LinkedElement(this), value1(0), value2(0), value3(0), value4( - 0) { + ModeListEntry(): LinkedElement(this) {} - } - - uint32_t value1; - uint32_t value2; - uint8_t value3; - uint8_t value4; + uint32_t value1 = 0; + uint32_t value2 = 0; + uint8_t value3 = 0; + uint8_t value4 = 0; virtual ReturnValue_t serialize(uint8_t** buffer, size_t* size, size_t maxSize, Endianness streamEndianness) const { @@ -149,4 +146,4 @@ public: } }; -#endif //MODEDEFINITIONS_H_ +#endif /* FSFW_SUBSYSTEM_MODES_MODEDEFINITIONS_H_ */ diff --git a/subsystem/modes/ModeSequenceMessage.cpp b/subsystem/modes/ModeSequenceMessage.cpp index 33019f58..7733098e 100644 --- a/subsystem/modes/ModeSequenceMessage.cpp +++ b/subsystem/modes/ModeSequenceMessage.cpp @@ -1,8 +1,7 @@ -#include "../../objectmanager/ObjectManagerIF.h" -#include "../../objectmanager/ObjectManagerIF.h" +#include "ModeSequenceMessage.h" + #include "../../objectmanager/ObjectManagerIF.h" #include "../../storagemanager/StorageManagerIF.h" -#include "ModeSequenceMessage.h" void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, Command_t command, Mode_t sequence, store_address_t storeAddress) { @@ -11,25 +10,12 @@ void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, message->setParameter2(sequence); } -//void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, -// Command_t command, ModeTableId_t table, store_address_t storeAddress) { -// message->setCommand(command); -// message->setParameter(storeAddress.raw); -// message->setParameter2(table); -//} - void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, Command_t command, Mode_t sequence) { message->setCommand(command); message->setParameter2(sequence); } -//void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, -// Command_t command, ModeTableId_t table) { -// message->setCommand(command); -// message->setParameter2(table); -//} - void ModeSequenceMessage::setModeSequenceMessage(CommandMessage* message, Command_t command, store_address_t storeAddress) { message->setCommand(command); @@ -63,9 +49,10 @@ void ModeSequenceMessage::clear(CommandMessage *message) { case SEQUENCE_LIST: case TABLE_LIST: case TABLE: - case SEQUENCE:{ - StorageManagerIF *ipcStore = objectManager->get(objects::IPC_STORE); - if (ipcStore != NULL){ + case SEQUENCE: { + StorageManagerIF *ipcStore = objectManager->get( + objects::IPC_STORE); + if (ipcStore != nullptr){ ipcStore->deleteData(ModeSequenceMessage::getStoreAddress(message)); } } diff --git a/subsystem/modes/ModeSequenceMessage.h b/subsystem/modes/ModeSequenceMessage.h index bbf747f1..7852c984 100644 --- a/subsystem/modes/ModeSequenceMessage.h +++ b/subsystem/modes/ModeSequenceMessage.h @@ -1,9 +1,11 @@ -#ifndef MODESEQUENCEMESSAGE_H_ -#define MODESEQUENCEMESSAGE_H_ +#ifndef FSFW_SUBSYSTEM_MODES_MODESEQUENCEMESSAGE_H_ +#define FSFW_SUBSYSTEM_MODES_MODESEQUENCEMESSAGE_H_ + +#include "ModeDefinitions.h" #include "../../ipc/CommandMessage.h" #include "../../storagemanager/StorageManagerIF.h" -#include "ModeDefinitions.h" + class ModeSequenceMessage { public: @@ -45,4 +47,4 @@ private: ModeSequenceMessage(); }; -#endif /* MODESEQUENCEMESSAGE_H_ */ +#endif /* FSFW_SUBSYSTEM_MODES_MODESEQUENCEMESSAGE_H_ */ diff --git a/subsystem/modes/ModeStore.cpp b/subsystem/modes/ModeStore.cpp index 217e177c..e216a167 100644 --- a/subsystem/modes/ModeStore.cpp +++ b/subsystem/modes/ModeStore.cpp @@ -1,6 +1,8 @@ #include "ModeStore.h" -#ifdef USE_MODESTORE +// todo: I think some parts are deprecated. If this is used, the define +// USE_MODESTORE could be part of the new FSFWConfig.h file. +#if FSFW_USE_MODESTORE == 1 ModeStore::ModeStore(object_id_t objectId, uint32_t slots) : SystemObject(objectId), store(slots), emptySlot(store.front()) { diff --git a/subsystem/modes/ModeStore.h b/subsystem/modes/ModeStore.h index 0bf856a3..c05086c7 100644 --- a/subsystem/modes/ModeStore.h +++ b/subsystem/modes/ModeStore.h @@ -1,12 +1,14 @@ #ifndef MODESTORE_H_ #define MODESTORE_H_ -#ifdef USE_MODESTORE +#include + +#if FSFW_USE_MODESTORE == 1 #include "../../container/ArrayList.h" #include "../../container/SinglyLinkedList.h" #include "../../objectmanager/SystemObject.h" -#include "ModeStoreIF.h" +#include "../../subsystem/modes/ModeStoreIF.h" class ModeStore: public ModeStoreIF, public SystemObject { public: diff --git a/subsystem/modes/ModeStoreIF.h b/subsystem/modes/ModeStoreIF.h index e5cac3b2..9e76deef 100644 --- a/subsystem/modes/ModeStoreIF.h +++ b/subsystem/modes/ModeStoreIF.h @@ -1,12 +1,14 @@ #ifndef MODESTOREIF_H_ #define MODESTOREIF_H_ -#ifdef USE_MODESTORE +#include + +#if FSFW_USE_MODESTORE == 1 #include "../../container/ArrayList.h" #include "../../container/SinglyLinkedList.h" #include "../../returnvalues/HasReturnvaluesIF.h" -#include "ModeDefinitions.h" +#include "../../subsystem/modes/ModeDefinitions.h" class ModeStoreIF { public: From 252bfa5c3935681ebd4717027eb67ce9dc5fcb0f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:35:45 +0100 Subject: [PATCH 058/103] subsystem convergence --- subsystem/Subsystem.cpp | 39 ++++++++++------------ subsystem/Subsystem.h | 59 ++++++++++++++++++---------------- subsystem/SubsystemBase.cpp | 64 ++++++++++++++++++------------------- subsystem/SubsystemBase.h | 27 +++++++++------- 4 files changed, 96 insertions(+), 93 deletions(-) diff --git a/subsystem/Subsystem.cpp b/subsystem/Subsystem.cpp index 50fc4d05..9712d7d4 100644 --- a/subsystem/Subsystem.cpp +++ b/subsystem/Subsystem.cpp @@ -1,5 +1,4 @@ #include "Subsystem.h" - #include "../health/HealthMessage.h" #include "../objectmanager/ObjectManagerIF.h" #include "../serialize/SerialArrayListAdapter.h" @@ -11,21 +10,12 @@ Subsystem::Subsystem(object_id_t setObjectId, object_id_t parent, uint32_t maxNumberOfSequences, uint32_t maxNumberOfTables) : - SubsystemBase(setObjectId, parent, 0), isInTransition(false), childrenChangedHealth( - false), uptimeStartTable(0), currentTargetTable(), targetMode( - 0), targetSubmode(SUBMODE_NONE), initialMode(0), currentSequenceIterator(), modeTables( - maxNumberOfTables), modeSequences(maxNumberOfSequences), IPCStore( - NULL) -#ifdef USE_MODESTORE -,modeStore(NULL) -#endif -{ + SubsystemBase(setObjectId, parent, 0), isInTransition(false), + childrenChangedHealth(false), currentTargetTable(), + targetSubmode(SUBMODE_NONE), currentSequenceIterator(), + modeTables(maxNumberOfTables), modeSequences(maxNumberOfSequences) {} -} - -Subsystem::~Subsystem() { - //Auto-generated destructor stub -} +Subsystem::~Subsystem() {} ReturnValue_t Subsystem::checkSequence(HybridIterator iter, Mode_t fallbackSequence) { @@ -351,7 +341,8 @@ ReturnValue_t Subsystem::addSequence(ArrayList *sequence, ReturnValue_t result; - //Before initialize() is called, tables must not be checked as the children are not added yet. + //Before initialize() is called, tables must not be checked as the + //children are not added yet. //Sequences added before are checked by initialize() if (!preInit) { result = checkSequence( @@ -397,8 +388,8 @@ ReturnValue_t Subsystem::addTable(ArrayList *table, Mode_t id, ReturnValue_t result; - //Before initialize() is called, tables must not be checked as the children are not added yet. - //Tables added before are checked by initialize() + //Before initialize() is called, tables must not be checked as the children + //are not added yet. Tables added before are checked by initialize() if (!preInit) { result = checkTable( HybridIterator(table->front(), table->back())); @@ -589,12 +580,14 @@ void Subsystem::transitionFailed(ReturnValue_t failureCode, triggerEvent(MODE_TRANSITION_FAILED, failureCode, parameter); if (mode == targetMode) { //already tried going back to the current mode - //go into fallback mode, also set current mode to fallback mode, so we come here at the next fail + //go into fallback mode, also set current mode to fallback mode, + //so we come here at the next fail modeHelper.setForced(true); ReturnValue_t result; if ((result = checkSequence(getFallbackSequence(mode))) != RETURN_OK) { triggerEvent(FALLBACK_FAILED, result, getFallbackSequence(mode)); - isInTransition = false; //keep still and allow arbitrary mode commands to recover + //keep still and allow arbitrary mode commands to recover + isInTransition = false; return; } mode = getFallbackSequence(mode); @@ -658,8 +651,10 @@ void Subsystem::cantKeepMode() { modeHelper.setForced(true); - //already set the mode, so that we do not try to go back in our old mode when the transition fails + //already set the mode, so that we do not try to go back in our old mode + //when the transition fails mode = getFallbackSequence(mode); - //SHOULDDO: We should store submodes for fallback sequence as well, otherwise we should get rid of submodes completely. + //SHOULDDO: We should store submodes for fallback sequence as well, + //otherwise we should get rid of submodes completely. startTransition(mode, SUBMODE_NONE); } diff --git a/subsystem/Subsystem.h b/subsystem/Subsystem.h index a40b8028..09d7850a 100644 --- a/subsystem/Subsystem.h +++ b/subsystem/Subsystem.h @@ -1,14 +1,19 @@ -#ifndef SUBSYSTEM_H_ -#define SUBSYSTEM_H_ +#ifndef FSFW_SUBSYSTEM_SUBSYSTEM_H_ +#define FSFW_SUBSYSTEM_SUBSYSTEM_H_ + +#include "SubsystemBase.h" +#include "modes/ModeDefinitions.h" #include "../container/FixedArrayList.h" #include "../container/FixedMap.h" #include "../container/HybridIterator.h" #include "../container/SinglyLinkedList.h" #include "../serialize/SerialArrayListAdapter.h" -#include "modes/ModeDefinitions.h" -#include "SubsystemBase.h" +/** + * @brief TODO: documentation missing + * @details + */ class Subsystem: public SubsystemBase, public HasModeSequenceIF { public: static const uint8_t INTERFACE_ID = CLASS_ID::SUBSYSTEM; @@ -30,8 +35,13 @@ public: static const ReturnValue_t TARGET_TABLE_NOT_REACHED = MAKE_RETURN_CODE(0xA1); static const ReturnValue_t TABLE_CHECK_FAILED = MAKE_RETURN_CODE(0xA2); - - + /** + * TODO: Doc for constructor + * @param setObjectId + * @param parent + * @param maxNumberOfSequences + * @param maxNumberOfTables + */ Subsystem(object_id_t setObjectId, object_id_t parent, uint32_t maxNumberOfSequences, uint32_t maxNumberOfTables); virtual ~Subsystem(); @@ -44,31 +54,27 @@ public: void setInitialMode(Mode_t mode); - virtual ReturnValue_t initialize(); + virtual ReturnValue_t initialize() override; - virtual ReturnValue_t checkObjectConnections(); + virtual ReturnValue_t checkObjectConnections() override; - virtual MessageQueueId_t getSequenceCommandQueue() const; + virtual MessageQueueId_t getSequenceCommandQueue() const override; /** - * - * - * IMPORTANT: Do not call on non existing sequence! Use existsSequence() first - * + * @brief Checks whether a sequence, identified by a mode. * @param sequence * @return */ ReturnValue_t checkSequence(Mode_t sequence); /** - * - * - * IMPORTANT: Do not call on non existing sequence! Use existsSequence() first - * + * @brief Checks whether a sequence, identified by a mode list iterator + * and a fallback sequence. * @param iter * @return */ - ReturnValue_t checkSequence(HybridIterator iter, Mode_t fallbackSequence); + ReturnValue_t checkSequence(HybridIterator iter, + Mode_t fallbackSequence); protected: struct EntryPointer { @@ -92,15 +98,15 @@ protected: bool childrenChangedHealth; - uint32_t uptimeStartTable; + uint32_t uptimeStartTable = 0; HybridIterator currentTargetTable; - Mode_t targetMode; + Mode_t targetMode = 0; Submode_t targetSubmode; - Mode_t initialMode; + Mode_t initialMode = 0; HybridIterator currentSequenceIterator; @@ -108,10 +114,10 @@ protected: FixedMap modeSequences; - StorageManagerIF *IPCStore; + StorageManagerIF *IPCStore = nullptr; #ifdef USE_MODESTORE - ModeStoreIF *modeStore; + ModeStoreIF *modeStore = nullptr; #endif bool existsModeSequence(Mode_t id); @@ -124,8 +130,6 @@ protected: HybridIterator getCurrentTable(); -// void startSequence(Mode_t sequence); - /** * DO NOT USE ON NON EXISTING SEQUENCE * @@ -153,7 +157,8 @@ protected: virtual void startTransition(Mode_t mode, Submode_t submode); - void sendSerializablesAsCommandMessage(Command_t command, SerializeIF **elements, uint8_t count); + void sendSerializablesAsCommandMessage(Command_t command, + SerializeIF **elements, uint8_t count); void transitionFailed(ReturnValue_t failureCode, uint32_t parameter); @@ -161,4 +166,4 @@ protected: }; -#endif /* SUBSYSTEM_H_ */ +#endif /* FSFW_SUBSYSTEM_SUBSYSTEM_H_ */ diff --git a/subsystem/SubsystemBase.cpp b/subsystem/SubsystemBase.cpp index 787d6be1..f60c8847 100644 --- a/subsystem/SubsystemBase.cpp +++ b/subsystem/SubsystemBase.cpp @@ -1,15 +1,15 @@ -#include "SubsystemBase.h" - #include "../serviceinterface/ServiceInterfaceStream.h" +#include "../serviceinterface/ServiceInterfaceStream.h" +#include "../subsystem/SubsystemBase.h" #include "../ipc/QueueFactory.h" SubsystemBase::SubsystemBase(object_id_t setObjectId, object_id_t parent, Mode_t initialMode, uint16_t commandQueueDepth) : SystemObject(setObjectId), mode(initialMode), submode(SUBMODE_NONE), - childrenChangedMode(false), commandsOutstanding(0), commandQueue(NULL), + childrenChangedMode(false), + commandQueue(QueueFactory::instance()->createMessageQueue( + commandQueueDepth, CommandMessage::MAX_MESSAGE_SIZE)), healthHelper(this, setObjectId), modeHelper(this), parentId(parent) { - commandQueue = QueueFactory::instance()->createMessageQueue(commandQueueDepth, - CommandMessage::MAX_MESSAGE_SIZE); } SubsystemBase::~SubsystemBase() { @@ -21,10 +21,11 @@ ReturnValue_t SubsystemBase::registerChild(object_id_t objectId) { ChildInfo info; HasModesIF *child = objectManager->get(objectId); - //This is a rather ugly hack to have the changedHealth info for all children available. (needed for FOGs). + // This is a rather ugly hack to have the changedHealth info for all + // children available. HasHealthIF* healthChild = objectManager->get(objectId); - if (child == NULL) { - if (healthChild == NULL) { + if (child == nullptr) { + if (healthChild == nullptr) { return CHILD_DOESNT_HAVE_MODES; } else { info.commandQueue = healthChild->getCommandQueue(); @@ -38,14 +39,11 @@ ReturnValue_t SubsystemBase::registerChild(object_id_t objectId) { info.submode = SUBMODE_NONE; info.healthChanged = false; - std::pair::iterator, bool> returnValue = - childrenMap.insert( - std::pair(objectId, info)); - if (!(returnValue.second)) { + auto resultPair = childrenMap.emplace(objectId, info); + if (not resultPair.second) { return COULD_NOT_INSERT_CHILD; - } else { - return RETURN_OK; } + return RETURN_OK; } ReturnValue_t SubsystemBase::checkStateAgainstTable( @@ -76,15 +74,15 @@ ReturnValue_t SubsystemBase::checkStateAgainstTable( return RETURN_OK; } -void SubsystemBase::executeTable(HybridIterator tableIter, Submode_t targetSubmode) { - - CommandMessage message; +void SubsystemBase::executeTable(HybridIterator tableIter, + Submode_t targetSubmode) { + CommandMessage command; std::map::iterator iter; commandsOutstanding = 0; - for (; tableIter.value != NULL; ++tableIter) { + for (; tableIter.value != nullptr; ++tableIter) { object_id_t object = tableIter.value->getObject(); if ((iter = childrenMap.find(object)) == childrenMap.end()) { //illegal table entry, should only happen due to misconfigured mode table @@ -100,17 +98,17 @@ void SubsystemBase::executeTable(HybridIterator tableIter, Submod if (healthHelper.healthTable->hasHealth(object)) { if (healthHelper.healthTable->isFaulty(object)) { - ModeMessage::setModeMessage(&message, + ModeMessage::setModeMessage(&command, ModeMessage::CMD_MODE_COMMAND, HasModesIF::MODE_OFF, SUBMODE_NONE); } else { if (modeHelper.isForced()) { - ModeMessage::setModeMessage(&message, + ModeMessage::setModeMessage(&command, ModeMessage::CMD_MODE_COMMAND_FORCED, tableIter.value->getMode(), submodeToCommand); } else { if (healthHelper.healthTable->isCommandable(object)) { - ModeMessage::setModeMessage(&message, + ModeMessage::setModeMessage(&command, ModeMessage::CMD_MODE_COMMAND, tableIter.value->getMode(), submodeToCommand); } else { @@ -119,17 +117,17 @@ void SubsystemBase::executeTable(HybridIterator tableIter, Submod } } } else { - ModeMessage::setModeMessage(&message, ModeMessage::CMD_MODE_COMMAND, + ModeMessage::setModeMessage(&command, ModeMessage::CMD_MODE_COMMAND, tableIter.value->getMode(), submodeToCommand); } - if ((iter->second.mode == ModeMessage::getMode(&message)) - && (iter->second.submode == ModeMessage::getSubmode(&message)) + if ((iter->second.mode == ModeMessage::getMode(&command)) + && (iter->second.submode == ModeMessage::getSubmode(&command)) && !modeHelper.isForced()) { continue; //don't send redundant mode commands (produces event spam), but still command if mode is forced to reach lower levels } ReturnValue_t result = commandQueue->sendMessage( - iter->second.commandQueue, &message); + iter->second.commandQueue, &command); if (result == RETURN_OK) { ++commandsOutstanding; } @@ -306,31 +304,31 @@ void SubsystemBase::announceMode(bool recursive) { void SubsystemBase::checkCommandQueue() { ReturnValue_t result; - CommandMessage message; + CommandMessage command; - for (result = commandQueue->receiveMessage(&message); result == RETURN_OK; - result = commandQueue->receiveMessage(&message)) { + for (result = commandQueue->receiveMessage(&command); result == RETURN_OK; + result = commandQueue->receiveMessage(&command)) { - result = healthHelper.handleHealthCommand(&message); + result = healthHelper.handleHealthCommand(&command); if (result == RETURN_OK) { continue; } - result = modeHelper.handleModeCommand(&message); + result = modeHelper.handleModeCommand(&command); if (result == RETURN_OK) { continue; } - result = handleModeReply(&message); + result = handleModeReply(&command); if (result == RETURN_OK) { continue; } - result = handleCommandMessage(&message); + result = handleCommandMessage(&command); if (result != RETURN_OK) { CommandMessage reply; reply.setReplyRejected(CommandMessage::UNKNOWN_COMMAND, - message.getCommand()); + command.getCommand()); replyToCommand(&reply); } } diff --git a/subsystem/SubsystemBase.h b/subsystem/SubsystemBase.h index 61a7eaef..b8e4f902 100644 --- a/subsystem/SubsystemBase.h +++ b/subsystem/SubsystemBase.h @@ -1,5 +1,7 @@ -#ifndef SUBSYSTEMBASE_H_ -#define SUBSYSTEMBASE_H_ +#ifndef FSFW_SUBSYSTEM_SUBSYSTEMBASE_H_ +#define FSFW_SUBSYSTEM_SUBSYSTEMBASE_H_ + +#include "modes/HasModeSequenceIF.h" #include "../container/HybridIterator.h" #include "../health/HasHealthIF.h" @@ -7,11 +9,14 @@ #include "../modes/HasModesIF.h" #include "../objectmanager/SystemObject.h" #include "../returnvalues/HasReturnvaluesIF.h" -#include "modes/HasModeSequenceIF.h" #include "../tasks/ExecutableObjectIF.h" #include "../ipc/MessageQueueIF.h" #include +/** + * @defgroup subsystems Subsystem Objects + * Contains all Subsystem and Assemblies + */ class SubsystemBase: public SystemObject, public HasModesIF, public HasHealthIF, @@ -30,17 +35,17 @@ public: Mode_t initialMode = 0, uint16_t commandQueueDepth = 8); virtual ~SubsystemBase(); - virtual MessageQueueId_t getCommandQueue() const; + virtual MessageQueueId_t getCommandQueue() const override; ReturnValue_t registerChild(object_id_t objectId); - virtual ReturnValue_t initialize(); + virtual ReturnValue_t initialize() override; - virtual ReturnValue_t performOperation(uint8_t opCode); + virtual ReturnValue_t performOperation(uint8_t opCode) override; - virtual ReturnValue_t setHealth(HealthState health); + virtual ReturnValue_t setHealth(HealthState health) override; - virtual HasHealthIF::HealthState getHealth(); + virtual HasHealthIF::HealthState getHealth() override; protected: struct ChildInfo { @@ -58,9 +63,9 @@ protected: /** * Always check this against <=0, so you are robust against too many replies */ - int32_t commandsOutstanding; + int32_t commandsOutstanding = 0; - MessageQueueIF* commandQueue; + MessageQueueIF* commandQueue = nullptr; HealthHelper healthHelper; @@ -122,4 +127,4 @@ protected: virtual void modeChanged(); }; -#endif /* SUBSYSTEMBASE_H_ */ +#endif /* FSFW_SUBSYSTEM_SUBSYSTEMBASE_H_ */ From e97787cceb7380d78b64d157333672c2a56edde3 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:39:19 +0100 Subject: [PATCH 059/103] some more tweaks --- subsystem/Subsystem.cpp | 12 ++++++------ subsystem/Subsystem.h | 4 +++- 2 files changed, 9 insertions(+), 7 deletions(-) diff --git a/subsystem/Subsystem.cpp b/subsystem/Subsystem.cpp index 9712d7d4..4de6906c 100644 --- a/subsystem/Subsystem.cpp +++ b/subsystem/Subsystem.cpp @@ -367,7 +367,7 @@ ReturnValue_t Subsystem::addSequence(ArrayList *sequence, } if (inStore) { -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 result = modeStore->storeArray(sequence, &(modeSequences.find(id)->entries.firstLinkedElement)); if (result != RETURN_OK) { @@ -410,7 +410,7 @@ ReturnValue_t Subsystem::addTable(ArrayList *table, Mode_t id, } if (inStore) { -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 result = modeStore->storeArray(table, &(modeTables.find(id)->firstLinkedElement)); if (result != RETURN_OK) { @@ -440,7 +440,7 @@ ReturnValue_t Subsystem::deleteSequence(Mode_t id) { return ACCESS_DENIED; } -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 modeStore->deleteList(sequenceInfo->entries.firstLinkedElement); #endif modeSequences.erase(id); @@ -463,7 +463,7 @@ ReturnValue_t Subsystem::deleteTable(Mode_t id) { return ACCESS_DENIED; } -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 modeStore->deleteList(pointer->firstLinkedElement); #endif modeSequences.erase(id); @@ -482,10 +482,10 @@ ReturnValue_t Subsystem::initialize() { return RETURN_FAILED; } -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 modeStore = objectManager->get(objects::MODE_STORE); - if (modeStore == NULL) { + if (modeStore == nullptr) { return RETURN_FAILED; } #endif diff --git a/subsystem/Subsystem.h b/subsystem/Subsystem.h index 09d7850a..c3a72d54 100644 --- a/subsystem/Subsystem.h +++ b/subsystem/Subsystem.h @@ -10,6 +10,8 @@ #include "../container/SinglyLinkedList.h" #include "../serialize/SerialArrayListAdapter.h" +#include + /** * @brief TODO: documentation missing * @details @@ -116,7 +118,7 @@ protected: StorageManagerIF *IPCStore = nullptr; -#ifdef USE_MODESTORE +#if FSFW_USE_MODESTORE == 1 ModeStoreIF *modeStore = nullptr; #endif From 5eafd4f353a2dd48fe5f4546a2a17d2bd16ad3f7 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:42:02 +0100 Subject: [PATCH 060/103] tiny format stuff --- subsystem/modes/ModeStoreIF.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/subsystem/modes/ModeStoreIF.h b/subsystem/modes/ModeStoreIF.h index 9e76deef..9682501d 100644 --- a/subsystem/modes/ModeStoreIF.h +++ b/subsystem/modes/ModeStoreIF.h @@ -5,10 +5,11 @@ #if FSFW_USE_MODESTORE == 1 +#include "ModeDefinitions.h" + #include "../../container/ArrayList.h" #include "../../container/SinglyLinkedList.h" #include "../../returnvalues/HasReturnvaluesIF.h" -#include "../../subsystem/modes/ModeDefinitions.h" class ModeStoreIF { public: From 9d5ac16398d1da81116b9ba0df0a3100bf85390d Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:43:08 +0100 Subject: [PATCH 061/103] some more improvements --- subsystem/modes/ModeStore.h | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/subsystem/modes/ModeStore.h b/subsystem/modes/ModeStore.h index c05086c7..a5cb4059 100644 --- a/subsystem/modes/ModeStore.h +++ b/subsystem/modes/ModeStore.h @@ -1,14 +1,15 @@ -#ifndef MODESTORE_H_ -#define MODESTORE_H_ +#ifndef FSFW_SUBSYSTEM_MODES_MODESTORE_H_ +#define FSFW_SUBSYSTEM_MODES_MODESTORE_H_ #include #if FSFW_USE_MODESTORE == 1 +#include "ModeStoreIF.h" + #include "../../container/ArrayList.h" #include "../../container/SinglyLinkedList.h" #include "../../objectmanager/SystemObject.h" -#include "../../subsystem/modes/ModeStoreIF.h" class ModeStore: public ModeStoreIF, public SystemObject { public: @@ -43,5 +44,5 @@ private: #endif -#endif /* MODESTORE_H_ */ +#endif /* FSFW_SUBSYSTEM_MODES_MODESTORE_H_ */ From d62e092be6c57ccfad63d61cc5dea3e785ddad98 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 11:49:30 +0100 Subject: [PATCH 062/103] task convergence --- tasks/FixedTimeslotTaskIF.h | 21 ++++++++++++++++++--- tasks/TaskFactory.h | 14 ++++++++------ 2 files changed, 26 insertions(+), 9 deletions(-) diff --git a/tasks/FixedTimeslotTaskIF.h b/tasks/FixedTimeslotTaskIF.h index 421978f0..a138db4e 100644 --- a/tasks/FixedTimeslotTaskIF.h +++ b/tasks/FixedTimeslotTaskIF.h @@ -1,16 +1,31 @@ #ifndef FRAMEWORK_TASKS_FIXEDTIMESLOTTASKIF_H_ #define FRAMEWORK_TASKS_FIXEDTIMESLOTTASKIF_H_ -#include "../objectmanager/ObjectManagerIF.h" #include "PeriodicTaskIF.h" +#include "../objectmanager/ObjectManagerIF.h" /** - * Following the same principle as the base class IF. This is the interface for a Fixed timeslot task + * @brief Following the same principle as the base class IF. + * This is the interface for a Fixed timeslot task */ class FixedTimeslotTaskIF : public PeriodicTaskIF { public: virtual ~FixedTimeslotTaskIF() {} - virtual ReturnValue_t addSlot(object_id_t componentId, uint32_t slotTimeMs, int8_t executionStep) = 0; + + /** + * Add an object with a slot time and the execution step to the task. + * The execution step shall be passed to the object. + * @param componentId + * @param slotTimeMs + * @param executionStep + * @return + */ + virtual ReturnValue_t addSlot(object_id_t componentId, uint32_t slotTimeMs, + int8_t executionStep) = 0; + /** + * Check whether the sequence is valid and perform all other required + * initialization steps which are needed after task creation + */ virtual ReturnValue_t checkSequence() const = 0; }; diff --git a/tasks/TaskFactory.h b/tasks/TaskFactory.h index cbf2272c..85cdda90 100644 --- a/tasks/TaskFactory.h +++ b/tasks/TaskFactory.h @@ -1,10 +1,11 @@ -#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. */ @@ -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 @@ -69,4 +71,4 @@ private: }; -#endif /* FRAMEWORK_TASKS_TASKFACTORY_H_ */ +#endif /* FSFW_TASKS_TASKFACTORY_H_ */ From 57853ba566eb786b66eaaaf64954bbf2e1d694cb Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 20:22:59 +0100 Subject: [PATCH 063/103] event update --- events/EventManager.cpp | 9 ++++----- events/EventManagerIF.h | 22 ++++++++++++++-------- 2 files changed, 18 insertions(+), 13 deletions(-) diff --git a/events/EventManager.cpp b/events/EventManager.cpp index 3fbe3ee8..182fb72b 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -1,7 +1,5 @@ #include "EventManager.h" -#include "EventMessage.h" #include - #include "../serviceinterface/ServiceInterfaceStream.h" #include "../ipc/QueueFactory.h" #include "../ipc/MutexFactory.h" @@ -11,6 +9,7 @@ // objects registering for certain events. // Each listener requires 1 or 2 EventIdMatcher and 1 or 2 ReportRangeMatcher. // So a good guess is 75 to a max of 100 pools required for each, which fits well. +// This should be configurable.. const LocalPool::LocalPoolConfig EventManager::poolConfig = { {fsfwconfig::FSFW_EVENTMGMR_MATCHTREE_NODES, sizeof(EventMatchTree::Node)}, @@ -43,7 +42,7 @@ ReturnValue_t EventManager::performOperation(uint8_t opCode) { EventMessage message; result = eventReportQueue->receiveMessage(&message); if (result == HasReturnvaluesIF::RETURN_OK) { -#ifdef DEBUG +#if FSFW_OBJ_EVENT_TRANSLATION == 1 printEvent(&message); #endif notifyListeners(&message); @@ -119,8 +118,8 @@ ReturnValue_t EventManager::unsubscribeFromEventRange(MessageQueueId_t listener, void EventManager::printEvent(EventMessage* message) { const char *string = 0; switch (message->getSeverity()) { - case severity::INFO: -#ifdef DEBUG_INFO_EVENT + case SEVERITY::INFO: +#if DEBUG_INFO_EVENT == 1 string = translateObject(message->getReporter()); sif::info << "EVENT: "; if (string != 0) { diff --git a/events/EventManagerIF.h b/events/EventManagerIF.h index f9ac420b..253e6910 100644 --- a/events/EventManagerIF.h +++ b/events/EventManagerIF.h @@ -1,10 +1,11 @@ #ifndef EVENTMANAGERIF_H_ #define EVENTMANAGERIF_H_ -#include "eventmatching/eventmatching.h" #include "EventMessage.h" +#include "eventmatching/eventmatching.h" #include "../objectmanager/ObjectManagerIF.h" #include "../ipc/MessageQueueSenderIF.h" +#include "../ipc/MessageQueueIF.h" class EventManagerIF { public: @@ -16,7 +17,8 @@ public: virtual MessageQueueId_t getEventReportQueue() = 0; - virtual ReturnValue_t registerListener(MessageQueueId_t listener, bool forwardAllButSelected = false) = 0; + virtual ReturnValue_t registerListener(MessageQueueId_t listener, + bool forwardAllButSelected = false) = 0; virtual ReturnValue_t subscribeToEvent(MessageQueueId_t listener, EventId_t event) = 0; virtual ReturnValue_t subscribeToAllEventsFrom(MessageQueueId_t listener, @@ -31,18 +33,22 @@ public: bool reporterInverted = false) = 0; static void triggerEvent(object_id_t reportingObject, Event event, - uint32_t parameter1 = 0, uint32_t parameter2 = 0, MessageQueueId_t sentFrom = 0) { + uint32_t parameter1 = 0, uint32_t parameter2 = 0, + MessageQueueId_t sentFrom = 0) { EventMessage message(event, reportingObject, parameter1, parameter2); triggerEvent(&message, sentFrom); } - static void triggerEvent(EventMessage* message, MessageQueueId_t sentFrom = 0) { - static MessageQueueId_t eventmanagerQueue = 0; - if (eventmanagerQueue == 0) { + + static void triggerEvent(EventMessage* message, + MessageQueueId_t sentFrom = 0) { + static MessageQueueId_t eventmanagerQueue = MessageQueueIF::NO_QUEUE; + if (eventmanagerQueue == MessageQueueIF::NO_QUEUE) { EventManagerIF *eventmanager = objectManager->get( objects::EVENT_MANAGER); - if (eventmanager != NULL) { - eventmanagerQueue = eventmanager->getEventReportQueue(); + if (eventmanager == nullptr) { + return; } + eventmanagerQueue = eventmanager->getEventReportQueue(); } MessageQueueSenderIF::sendMessage(eventmanagerQueue, message, sentFrom); } From 0f6d878d86d3f01b9ee32b5d842e50b77873aba8 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 20:48:41 +0100 Subject: [PATCH 064/103] update --- events/EventManager.cpp | 3 ++- events/EventManager.h | 12 +++++++----- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/events/EventManager.cpp b/events/EventManager.cpp index 182fb72b..33276141 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -1,4 +1,6 @@ #include "EventManager.h" +#include "EventMessage.h" + #include #include "../serviceinterface/ServiceInterfaceStream.h" #include "../ipc/QueueFactory.h" @@ -9,7 +11,6 @@ // objects registering for certain events. // Each listener requires 1 or 2 EventIdMatcher and 1 or 2 ReportRangeMatcher. // So a good guess is 75 to a max of 100 pools required for each, which fits well. -// This should be configurable.. const LocalPool::LocalPoolConfig EventManager::poolConfig = { {fsfwconfig::FSFW_EVENTMGMR_MATCHTREE_NODES, sizeof(EventMatchTree::Node)}, diff --git a/events/EventManager.h b/events/EventManager.h index fe35d9d3..6678fc07 100644 --- a/events/EventManager.h +++ b/events/EventManager.h @@ -1,14 +1,16 @@ -#ifndef EVENTMANAGER_H_ -#define EVENTMANAGER_H_ +#ifndef FSFW_EVENT_EVENTMANAGER_H_ +#define FSFW_EVENT_EVENTMANAGER_H_ -#include "eventmatching/EventMatchTree.h" #include "EventManagerIF.h" +#include "eventmatching/EventMatchTree.h" + +#include + #include "../objectmanager/SystemObject.h" #include "../storagemanager/LocalPool.h" #include "../tasks/ExecutableObjectIF.h" #include "../ipc/MessageQueueIF.h" #include "../ipc/MutexIF.h" -#include #include @@ -68,4 +70,4 @@ protected: void unlockMutex(); }; -#endif /* EVENTMANAGER_H_ */ +#endif /* FSFW_EVENT_EVENTMANAGER_H_ */ From d96d3d6c46c1c8e060f6705c17f0f7489f415385 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 20:58:20 +0100 Subject: [PATCH 065/103] one define now --- defaultcfg/fsfwconfig/FSFWConfig.h | 2 -- events/EventManager.cpp | 2 +- events/EventManager.h | 4 ++-- unittest/testcfg/FSFWConfig.h | 4 +--- 4 files changed, 4 insertions(+), 8 deletions(-) diff --git a/defaultcfg/fsfwconfig/FSFWConfig.h b/defaultcfg/fsfwconfig/FSFWConfig.h index 1386bf66..7e19235c 100644 --- a/defaultcfg/fsfwconfig/FSFWConfig.h +++ b/defaultcfg/fsfwconfig/FSFWConfig.h @@ -27,13 +27,11 @@ #define FSFW_OBJ_EVENT_TRANSLATION 0 #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 #else -#define FSFW_DEBUG_OUTPUT 0 #endif //! When using the newlib nano library, C99 support for stdio facilities diff --git a/events/EventManager.cpp b/events/EventManager.cpp index 33276141..ba31cc58 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -114,7 +114,7 @@ ReturnValue_t EventManager::unsubscribeFromEventRange(MessageQueueId_t listener, return result; } -#if FSFW_DEBUG_OUTPUT == 1 +#if FSFW_OBJ_EVENT_TRANSLATION == 1 void EventManager::printEvent(EventMessage* message) { const char *string = 0; diff --git a/events/EventManager.h b/events/EventManager.h index 6678fc07..c6bd07be 100644 --- a/events/EventManager.h +++ b/events/EventManager.h @@ -14,7 +14,7 @@ #include -#if FSFW_DEBUG_OUTPUT == 1 +#if FSFW_OBJ_EVENT_TRANSLATION == 1 // forward declaration, should be implemented by mission extern const char* translateObject(object_id_t object); extern const char* translateEvents(Event event); @@ -61,7 +61,7 @@ protected: void notifyListeners(EventMessage *message); -#if FSFW_DEBUG_OUTPUT == 1 +#if FSFW_OBJ_EVENT_TRANSLATION == 1 void printEvent(EventMessage *message); #endif 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 From a3ebad46e7335f0b4287f388359f02793062d44b Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:00:15 +0100 Subject: [PATCH 066/103] small fix --- events/EventManager.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/events/EventManager.cpp b/events/EventManager.cpp index ba31cc58..6cc97eb6 100644 --- a/events/EventManager.cpp +++ b/events/EventManager.cpp @@ -119,7 +119,7 @@ ReturnValue_t EventManager::unsubscribeFromEventRange(MessageQueueId_t listener, void EventManager::printEvent(EventMessage* message) { const char *string = 0; switch (message->getSeverity()) { - case SEVERITY::INFO: + case severity::INFO: #if DEBUG_INFO_EVENT == 1 string = translateObject(message->getReporter()); sif::info << "EVENT: "; From 55a663beb20ff5b9435b3dc358e6b869d8353ef8 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:14:38 +0100 Subject: [PATCH 067/103] 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 336b43572f1bb928be5475c2eabebdfa6d53a587 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 21:46:33 +0100 Subject: [PATCH 068/103] 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 069/103] 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 070/103] 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 3cc053a58105c51828147e0ea92efaeb11418b59 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 14 Dec 2020 23:56:44 +0100 Subject: [PATCH 071/103] changes from mueller/master taken over --- osal/FreeRTOS/BinSemaphUsingTask.cpp | 6 +++ osal/FreeRTOS/BinSemaphUsingTask.h | 7 ++- osal/FreeRTOS/CountingSemaphUsingTask.cpp | 5 ++ osal/FreeRTOS/CountingSemaphUsingTask.h | 6 +++ osal/FreeRTOS/FixedTimeslotTask.cpp | 42 ++++++----------- osal/FreeRTOS/FixedTimeslotTask.h | 2 - osal/FreeRTOS/FreeRTOSTaskIF.h | 38 +++++++++++++-- osal/FreeRTOS/PeriodicTask.cpp | 39 +++++----------- osal/FreeRTOS/PeriodicTask.h | 3 +- osal/FreeRTOS/TaskManagement.cpp | 1 + osal/FreeRTOS/TaskManagement.h | 57 +++++++++++------------ 11 files changed, 111 insertions(+), 95 deletions(-) diff --git a/osal/FreeRTOS/BinSemaphUsingTask.cpp b/osal/FreeRTOS/BinSemaphUsingTask.cpp index 9c29948e..a420ec48 100644 --- a/osal/FreeRTOS/BinSemaphUsingTask.cpp +++ b/osal/FreeRTOS/BinSemaphUsingTask.cpp @@ -2,6 +2,9 @@ #include "TaskManagement.h" #include "../../serviceinterface/ServiceInterfaceStream.h" +#if (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 + BinarySemaphoreUsingTask::BinarySemaphoreUsingTask() { handle = TaskManagement::getCurrentTaskHandle(); if(handle == nullptr) { @@ -97,3 +100,6 @@ uint8_t BinarySemaphoreUsingTask::getSemaphoreCounterFromISR( higherPriorityTaskWoken); return notificationValue; } + +#endif /* (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 */ diff --git a/osal/FreeRTOS/BinSemaphUsingTask.h b/osal/FreeRTOS/BinSemaphUsingTask.h index 65a091a3..ec434853 100644 --- a/osal/FreeRTOS/BinSemaphUsingTask.h +++ b/osal/FreeRTOS/BinSemaphUsingTask.h @@ -7,8 +7,8 @@ #include #include -// todo: does not work for older FreeRTOS version, so we should -// actually check whether tskKERNEL_VERSION_MAJOR is larger than.. 7 or 8 ? +#if (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 /** * @brief Binary Semaphore implementation using the task notification value. @@ -90,4 +90,7 @@ protected: TaskHandle_t handle; }; +#endif /* (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 */ + #endif /* FSFW_OSAL_FREERTOS_BINSEMAPHUSINGTASK_H_ */ diff --git a/osal/FreeRTOS/CountingSemaphUsingTask.cpp b/osal/FreeRTOS/CountingSemaphUsingTask.cpp index 17cdf7ce..9d309acc 100644 --- a/osal/FreeRTOS/CountingSemaphUsingTask.cpp +++ b/osal/FreeRTOS/CountingSemaphUsingTask.cpp @@ -3,6 +3,9 @@ #include "../../serviceinterface/ServiceInterfaceStream.h" +#if (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 + CountingSemaphoreUsingTask::CountingSemaphoreUsingTask(const uint8_t maxCount, uint8_t initCount): maxCount(maxCount) { if(initCount > maxCount) { @@ -113,3 +116,5 @@ uint8_t CountingSemaphoreUsingTask::getSemaphoreCounterFromISR( uint8_t CountingSemaphoreUsingTask::getMaxCount() const { return maxCount; } + +#endif diff --git a/osal/FreeRTOS/CountingSemaphUsingTask.h b/osal/FreeRTOS/CountingSemaphUsingTask.h index f258197b..45915b6b 100644 --- a/osal/FreeRTOS/CountingSemaphUsingTask.h +++ b/osal/FreeRTOS/CountingSemaphUsingTask.h @@ -7,6 +7,9 @@ #include #include +#if (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 + /** * @brief Couting Semaphore implementation which uses the notification value * of the task. The notification value should therefore not be used @@ -100,4 +103,7 @@ private: const uint8_t maxCount; }; +#endif /* (tskKERNEL_VERSION_MAJOR == 8 && tskKERNEL_VERSION_MINOR > 2) || \ + tskKERNEL_VERSION_MAJOR > 8 */ + #endif /* FSFW_OSAL_FREERTOS_COUNTINGSEMAPHUSINGTASK_H_ */ diff --git a/osal/FreeRTOS/FixedTimeslotTask.cpp b/osal/FreeRTOS/FixedTimeslotTask.cpp index 062686e2..fc5b89fe 100644 --- a/osal/FreeRTOS/FixedTimeslotTask.cpp +++ b/osal/FreeRTOS/FixedTimeslotTask.cpp @@ -114,38 +114,24 @@ void FixedTimeslotTask::taskFunctionality() { intervalMs = this->pst.getIntervalToPreviousSlotMs(); interval = pdMS_TO_TICKS(intervalMs); - checkMissedDeadline(xLastWakeTime, interval); - - // Wait for the interval. This exits immediately if a deadline was - // missed while also updating the last wake time. - vTaskDelayUntil(&xLastWakeTime, interval); +#if (tskKERNEL_VERSION_MAJOR == 10 && tskKERNEL_VERSION_MINOR >= 4) || \ + tskKERNEL_VERSION_MAJOR > 10 + BaseType_t wasDelayed = xTaskDelayUntil(&xLastWakeTime, interval); + if(wasDelayed == pdFALSE) { + handleMissedDeadline(); + } +#else + if(checkMissedDeadline(xLastWakeTime, interval)) { + handleMissedDeadline(); + } + // Wait for the interval. This exits immediately if a deadline was + // missed while also updating the last wake time. + vTaskDelayUntil(&xLastWakeTime, interval); +#endif } } } -void FixedTimeslotTask::checkMissedDeadline(const TickType_t xLastWakeTime, - const TickType_t interval) { - /* Check whether deadline was missed while also taking overflows - * into account. Drawing this on paper with a timeline helps to understand - * it. */ - TickType_t currentTickCount = xTaskGetTickCount(); - TickType_t timeToWake = xLastWakeTime + interval; - // Time to wake has not overflown. - if(timeToWake > xLastWakeTime) { - /* If the current time has overflown exclusively or the current - * tick count is simply larger than the time to wake, a deadline was - * missed */ - if((currentTickCount < xLastWakeTime) or (currentTickCount > timeToWake)) { - handleMissedDeadline(); - } - } - /* Time to wake has overflown. A deadline was missed if the current time - * is larger than the time to wake */ - else if((timeToWake < xLastWakeTime) and (currentTickCount > timeToWake)) { - handleMissedDeadline(); - } -} - void FixedTimeslotTask::handleMissedDeadline() { if(deadlineMissedFunc != nullptr) { this->deadlineMissedFunc(); diff --git a/osal/FreeRTOS/FixedTimeslotTask.h b/osal/FreeRTOS/FixedTimeslotTask.h index 7d2cdb70..f2245ba4 100644 --- a/osal/FreeRTOS/FixedTimeslotTask.h +++ b/osal/FreeRTOS/FixedTimeslotTask.h @@ -93,8 +93,6 @@ protected: */ void taskFunctionality(void); - void checkMissedDeadline(const TickType_t xLastWakeTime, - const TickType_t interval); void handleMissedDeadline(); }; diff --git a/osal/FreeRTOS/FreeRTOSTaskIF.h b/osal/FreeRTOS/FreeRTOSTaskIF.h index 06fda282..2a2d9494 100644 --- a/osal/FreeRTOS/FreeRTOSTaskIF.h +++ b/osal/FreeRTOS/FreeRTOSTaskIF.h @@ -1,13 +1,41 @@ -#ifndef FRAMEWORK_OSAL_FREERTOS_FREERTOSTASKIF_H_ -#define FRAMEWORK_OSAL_FREERTOS_FREERTOSTASKIF_H_ +#ifndef FSFW_OSAL_FREERTOS_FREERTOSTASKIF_H_ +#define FSFW_OSAL_FREERTOS_FREERTOSTASKIF_H_ #include #include class FreeRTOSTaskIF { public: - virtual~ FreeRTOSTaskIF() {} - virtual TaskHandle_t getTaskHandle() = 0; + virtual~ FreeRTOSTaskIF() {} + virtual TaskHandle_t getTaskHandle() = 0; + +protected: + + bool checkMissedDeadline(const TickType_t xLastWakeTime, + const TickType_t interval) { + /* Check whether deadline was missed while also taking overflows + * into account. Drawing this on paper with a timeline helps to understand + * it. */ + TickType_t currentTickCount = xTaskGetTickCount(); + TickType_t timeToWake = xLastWakeTime + interval; + // Time to wake has not overflown. + if(timeToWake > xLastWakeTime) { + /* If the current time has overflown exclusively or the current + * tick count is simply larger than the time to wake, a deadline was + * missed */ + if((currentTickCount < xLastWakeTime) or + (currentTickCount > timeToWake)) { + return true; + } + } + /* Time to wake has overflown. A deadline was missed if the current time + * is larger than the time to wake */ + else if((timeToWake < xLastWakeTime) and + (currentTickCount > timeToWake)) { + return true; + } + return false; + } }; -#endif /* FRAMEWORK_OSAL_FREERTOS_FREERTOSTASKIF_H_ */ +#endif /* FSFW_OSAL_FREERTOS_FREERTOSTASKIF_H_ */ diff --git a/osal/FreeRTOS/PeriodicTask.cpp b/osal/FreeRTOS/PeriodicTask.cpp index 5c0a840d..2ee7bec0 100644 --- a/osal/FreeRTOS/PeriodicTask.cpp +++ b/osal/FreeRTOS/PeriodicTask.cpp @@ -80,10 +80,18 @@ void PeriodicTask::taskFunctionality() { object->performOperation(); } - checkMissedDeadline(xLastWakeTime, xPeriod); - - vTaskDelayUntil(&xLastWakeTime, xPeriod); - +#if (tskKERNEL_VERSION_MAJOR == 10 && tskKERNEL_VERSION_MINOR >= 4) || \ + tskKERNEL_VERSION_MAJOR > 10 + BaseType_t wasDelayed = xTaskDelayUntil(&xLastWakeTime, xPeriod); + if(wasDelayed == pdFALSE) { + handleMissedDeadline(); + } +#else + if(checkMissedDeadline(xLastWakeTime, xPeriod)) { + handleMissedDeadline(); + } + vTaskDelayUntil(&xLastWakeTime, xPeriod); +#endif } } @@ -105,29 +113,6 @@ uint32_t PeriodicTask::getPeriodMs() const { return period * 1000; } -void PeriodicTask::checkMissedDeadline(const TickType_t xLastWakeTime, - const TickType_t interval) { - /* Check whether deadline was missed while also taking overflows - * into account. Drawing this on paper with a timeline helps to understand - * it. */ - TickType_t currentTickCount = xTaskGetTickCount(); - TickType_t timeToWake = xLastWakeTime + interval; - // Time to wake has not overflown. - if(timeToWake > xLastWakeTime) { - /* If the current time has overflown exclusively or the current - * tick count is simply larger than the time to wake, a deadline was - * missed */ - if((currentTickCount < xLastWakeTime) or (currentTickCount > timeToWake)) { - handleMissedDeadline(); - } - } - /* Time to wake has overflown. A deadline was missed if the current time - * is larger than the time to wake */ - else if((timeToWake < xLastWakeTime) and (currentTickCount > timeToWake)) { - handleMissedDeadline(); - } -} - TaskHandle_t PeriodicTask::getTaskHandle() { return handle; } diff --git a/osal/FreeRTOS/PeriodicTask.h b/osal/FreeRTOS/PeriodicTask.h index 87b8b6d2..36ef568f 100644 --- a/osal/FreeRTOS/PeriodicTask.h +++ b/osal/FreeRTOS/PeriodicTask.h @@ -71,6 +71,7 @@ public: TaskHandle_t getTaskHandle() override; protected: + bool started; TaskHandle_t handle; @@ -118,8 +119,6 @@ protected: */ void taskFunctionality(void); - void checkMissedDeadline(const TickType_t xLastWakeTime, - const TickType_t interval); void handleMissedDeadline(); }; diff --git a/osal/FreeRTOS/TaskManagement.cpp b/osal/FreeRTOS/TaskManagement.cpp index 18572045..c0d0067e 100644 --- a/osal/FreeRTOS/TaskManagement.cpp +++ b/osal/FreeRTOS/TaskManagement.cpp @@ -22,3 +22,4 @@ size_t TaskManagement::getTaskStackHighWatermark( TaskHandle_t task) { return uxTaskGetStackHighWaterMark(task) * sizeof(StackType_t); } + diff --git a/osal/FreeRTOS/TaskManagement.h b/osal/FreeRTOS/TaskManagement.h index c6c46f21..b9aece48 100644 --- a/osal/FreeRTOS/TaskManagement.h +++ b/osal/FreeRTOS/TaskManagement.h @@ -26,38 +26,37 @@ enum class CallContext { }; -class TaskManagement { -public: - /** - * @brief In this function, a function dependant on the portmacro.h header - * function calls to request a context switch can be specified. - * This can be used if sending to the queue from an ISR caused a task - * to unblock and a context switch is required. - */ - static void requestContextSwitch(CallContext callContext); +namespace TaskManagement { +/** + * @brief In this function, a function dependant on the portmacro.h header + * function calls to request a context switch can be specified. + * This can be used if sending to the queue from an ISR caused a task + * to unblock and a context switch is required. + */ +void requestContextSwitch(CallContext callContext); - /** - * If task preemption in FreeRTOS is disabled, a context switch - * can be requested manually by calling this function. - */ - static void vRequestContextSwitchFromTask(void); +/** + * If task preemption in FreeRTOS is disabled, a context switch + * can be requested manually by calling this function. + */ +void vRequestContextSwitchFromTask(void); - /** - * @return The current task handle - */ - static TaskHandle_t getCurrentTaskHandle(); +/** + * @return The current task handle + */ +TaskHandle_t getCurrentTaskHandle(); + +/** + * Get returns the minimum amount of remaining stack space in words + * that was a available to the task since the task started executing. + * Please note that the actual value in bytes depends + * on the stack depth type. + * E.g. on a 32 bit machine, a value of 200 means 800 bytes. + * @return Smallest value of stack remaining since the task was started in + * words. + */ +size_t getTaskStackHighWatermark(TaskHandle_t task = nullptr); - /** - * Get returns the minimum amount of remaining stack space in words - * that was a available to the task since the task started executing. - * Please note that the actual value in bytes depends - * on the stack depth type. - * E.g. on a 32 bit machine, a value of 200 means 800 bytes. - * @return Smallest value of stack remaining since the task was started in - * words. - */ - static size_t getTaskStackHighWatermark( - TaskHandle_t task = nullptr); }; #endif /* FRAMEWORK_OSAL_FREERTOS_TASKMANAGEMENT_H_ */ From f733a85a9c51a8612084f947485c33161d75346f Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 14:41:33 +0100 Subject: [PATCH 072/103] type update --- globalfunctions/Type.h | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/globalfunctions/Type.h b/globalfunctions/Type.h index d28f56ac..fa894e3e 100644 --- a/globalfunctions/Type.h +++ b/globalfunctions/Type.h @@ -3,6 +3,7 @@ #include "../returnvalues/HasReturnvaluesIF.h" #include "../serialize/SerializeIF.h" +#include /** * @brief Type definition for CCSDS or ECSS. @@ -56,13 +57,14 @@ private: template struct PodTypeConversion { + static_assert(not std::is_same::value, + "Do not use boolean for the PoolEntry type, use uint8_t " + "instead! The ECSS standard defines a boolean as a one bit " + "field. Therefore it is preferred to store a boolean as an " + "uint8_t"); static const Type::ActualType_t type = Type::UNKNOWN_TYPE; }; template<> -struct PodTypeConversion { - static const Type::ActualType_t type = Type::UINT8_T; -}; -template<> struct PodTypeConversion { static const Type::ActualType_t type = Type::UINT8_T; }; From a57af5852d9ce76cd3340e147e82bceffce92303 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:04:07 +0100 Subject: [PATCH 073/103] made check sequence --- subsystem/Subsystem.h | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/subsystem/Subsystem.h b/subsystem/Subsystem.h index c3a72d54..a3f7de45 100644 --- a/subsystem/Subsystem.h +++ b/subsystem/Subsystem.h @@ -62,21 +62,6 @@ public: virtual MessageQueueId_t getSequenceCommandQueue() const override; - /** - * @brief Checks whether a sequence, identified by a mode. - * @param sequence - * @return - */ - ReturnValue_t checkSequence(Mode_t sequence); - - /** - * @brief Checks whether a sequence, identified by a mode list iterator - * and a fallback sequence. - * @param iter - * @return - */ - ReturnValue_t checkSequence(HybridIterator iter, - Mode_t fallbackSequence); protected: struct EntryPointer { @@ -166,6 +151,21 @@ protected: void cantKeepMode(); + /** + * @brief Checks whether a sequence, identified by a mode. + * @param sequence + * @return + */ + ReturnValue_t checkSequence(Mode_t sequence); + + /** + * @brief Checks whether a sequence, identified by a mode list iterator + * and a fallback sequence. + * @param iter + * @return + */ + ReturnValue_t checkSequence(HybridIterator iter, + Mode_t fallbackSequence); }; #endif /* FSFW_SUBSYSTEM_SUBSYSTEM_H_ */ From 4c152e9fd83f94916b36410a53d0c530b94c7d55 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:07:41 +0100 Subject: [PATCH 074/103] subsystem doc upodate --- subsystem/Subsystem.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/subsystem/Subsystem.h b/subsystem/Subsystem.h index a3f7de45..69563643 100644 --- a/subsystem/Subsystem.h +++ b/subsystem/Subsystem.h @@ -160,7 +160,8 @@ protected: /** * @brief Checks whether a sequence, identified by a mode list iterator - * and a fallback sequence. + * and a fallback sequence. Iterator needs to point to a valid + * sequence. * @param iter * @return */ From 103d8b8c6a1669c6dabf2d10b7b20505088fe58c Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Tue, 15 Dec 2020 15:12:31 +0100 Subject: [PATCH 075/103] fixed timeslot task IF --- tasks/FixedTimeslotTaskIF.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tasks/FixedTimeslotTaskIF.h b/tasks/FixedTimeslotTaskIF.h index a138db4e..2fc7e092 100644 --- a/tasks/FixedTimeslotTaskIF.h +++ b/tasks/FixedTimeslotTaskIF.h @@ -14,7 +14,8 @@ public: /** * Add an object with a slot time and the execution step to the task. - * The execution step shall be passed to the object. + * The execution step will be passed to the object (e.g. as an operation + * code in #performOperation) * @param componentId * @param slotTimeMs * @param executionStep From e39c4fe2a862706f5be1a00fb14b21daa9f097da Mon Sep 17 00:00:00 2001 From: Spacefish Date: Tue, 15 Dec 2020 22:42:50 +0100 Subject: [PATCH 076/103] 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 077/103] 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 f128a1dc3d33c7bd22919b13240230373843f13c Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 15 Dec 2020 23:44:43 +0100 Subject: [PATCH 078/103] made datalinklayer optional --- CMakeLists.txt | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 09760f8e..c8092629 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -36,7 +36,11 @@ add_subdirectory(action) add_subdirectory(container) add_subdirectory(controller) add_subdirectory(coordinates) + +if(FSFW_USE_DATALINKLAYER) add_subdirectory(datalinklayer) +endif() + add_subdirectory(datapool) add_subdirectory(datapoollocal) add_subdirectory(housekeeping) From ac40b1c966bb025ce433dc55554100de29f77d5a Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 17 Dec 2020 11:46:50 +0100 Subject: [PATCH 079/103] cmake list formatting --- CMakeLists.txt | 49 ++++++++++++++++++++++++++++++------------------- 1 file changed, 30 insertions(+), 19 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index c8092629..fbbe386b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -3,27 +3,38 @@ cmake_minimum_required(VERSION 3.13) set(LIB_FSFW_NAME fsfw) add_library(${LIB_FSFW_NAME}) -# Set options for FSFW OSAL selection. -if(UNIX) -set(OS_FSFW "linux" CACHE STRING "OS abstraction layer used in the FSFW") -elseif(WIN32) -set(OS_FSFW "host" CACHE STRING "OS abstraction layer used in the FSFW") -endif() - set_property(CACHE OS_FSFW PROPERTY STRINGS host linux rtems freertos) +if(NOT OS_FSFW) + message(STATUS "No OS for FSFW via OS_FSFW set. Assuming host OS") + # Assume host OS and autodetermine from OS_FSFW + if(UNIX) + set(OS_FSFW "linux" + CACHE STRING + "OS abstraction layer used in the FSFW" + ) + elseif(WIN32) + set(OS_FSFW "host" + CACHE STRING "OS abstraction layer used in the FSFW" + ) + endif() + +endif + if(${OS_FSFW} STREQUAL host) -set(OS_FSFW_NAME "Host") + set(OS_FSFW_NAME "Host") elseif(${OS_FSFW} STREQUAL linux) -set(OS_FSFW_NAME "Linux") + set(OS_FSFW_NAME "Linux") elseif(${OS_FSFW} STREQUAL freertos) -set(OS_FSFW_NAME "FreeRTOS") + set(OS_FSFW_NAME "FreeRTOS") elseif(${OS_FSFW} STREQUAL rtems) -set(OS_FSFW_NAME "RTEMS") + set(OS_FSFW_NAME "RTEMS") else() -message(WARNING "Invalid operating system for FSFW specified! Setting to host..") -set(OS_FSFW_NAME "Host") -set(OS_FSFW "host") + message(WARNING + "Invalid operating system for FSFW specified! Setting to host.." + ) + set(OS_FSFW_NAME "Host") + set(OS_FSFW "host") endif() message(STATUS "Compiling FSFW for the ${OS_FSFW_NAME} operating system") @@ -38,7 +49,7 @@ add_subdirectory(controller) add_subdirectory(coordinates) if(FSFW_USE_DATALINKLAYER) -add_subdirectory(datalinklayer) + add_subdirectory(datalinklayer) endif() add_subdirectory(datapool) @@ -61,7 +72,7 @@ add_subdirectory(power) add_subdirectory(pus) if(FSFW_USE_RMAP) -add_subdirectory(rmap) + add_subdirectory(rmap) endif() add_subdirectory(serialize) @@ -79,9 +90,9 @@ add_subdirectory(tmtcservices) # The project CMakeLists file has to set the FSFW_CONFIG_PATH and add it. # If this is not given, we include the default configuration and emit a warning. if(NOT FSFW_CONFIG_PATH) -message(WARNING "Flight Software Framework configuration path not set!") -message(WARNING "Setting default configuration!") -add_subdirectory(defaultcfg/fsfwconfig) + message(WARNING "Flight Software Framework configuration path not set!") + message(WARNING "Setting default configuration!") + add_subdirectory(defaultcfg/fsfwconfig) endif() # Required include paths to compile the FSFW From 62b5c19063c6b55f08aae54bc93e879619bd1a06 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 17 Dec 2020 20:18:16 +0100 Subject: [PATCH 080/103] small fix --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index fbbe386b..5cb4b28e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -19,7 +19,7 @@ if(NOT OS_FSFW) ) endif() -endif +endif() if(${OS_FSFW} STREQUAL host) set(OS_FSFW_NAME "Host") From c0099481a16897273b10a0c8b59c8f2504392b3d Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 00:21:08 +0100 Subject: [PATCH 081/103] added freertos cmakelists --- osal/FreeRTOS/CMakeLists.txt | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 osal/FreeRTOS/CMakeLists.txt diff --git a/osal/FreeRTOS/CMakeLists.txt b/osal/FreeRTOS/CMakeLists.txt new file mode 100644 index 00000000..a7b1338f --- /dev/null +++ b/osal/FreeRTOS/CMakeLists.txt @@ -0,0 +1,18 @@ +target_sources(${LIB_FSFW_NAME} + PRIVATE + Clock.cpp + FixedTimeslotTask.cpp + BinarySemaphore.cpp + BinSemaphUsingTask.cpp + CountingSemaphore.cpp + CountingSemaphUsingTask.cpp + MessageQueue.cpp + Mutex.cpp + MutexFactory.cpp + PeriodicTask.cpp + QueueFactory.cpp + QueueMapManager.cpp + SemaphoreFactory.cpp + TaskFactory.cpp + Timekeeper.cpp +) \ No newline at end of file From e030d7ed97609c377af8540b7754b08bbb7c87ef Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 02:29:22 +0100 Subject: [PATCH 082/103] correct interface and private includes --- CMakeLists.txt | 24 +++++++++++++++++++++--- osal/FreeRTOS/CMakeLists.txt | 15 +++++++++++++-- 2 files changed, 34 insertions(+), 5 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 5cb4b28e..a3ca3e0d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -95,8 +95,26 @@ if(NOT FSFW_CONFIG_PATH) add_subdirectory(defaultcfg/fsfwconfig) endif() +# FSFW might be part of a possibly complicated folder structure, so we +# extract the absolute path of the fsfwconfig folder. +if(IS_ABSOLUTE ${FSFW_CONFIG_PATH}) + set(${FSFW_CONFIG_PATH_ABSOLUTE} ${FSFW_CONFIG_PATH}) +else() + get_filename_component(${FSFW_CONFIG_PATH_ABSOLUTE} + ${FSFW_CONFIG_PATH} ABSOLUTE + ) +endif() + # Required include paths to compile the FSFW -target_include_directories(${LIB_FSFW_NAME} - INTERFACE - ${FSFW_CONFIG_PATH} +target_include_directories(${LIB_FSFW_NAME} INTERFACE + ${CMAKE_SOURCE_DIR} + ${FSFW_CONFIG_PATH_ABSOLUTE} +) + +# Includes path required to compile FSFW itself as well +# We assume that the fsfwconfig folder uses include relative to the project +# root here! +target_include_directories(${LIB_FSFW_NAME} PRIVATE + ${CMAKE_SOURCE_DIR} + ${FSFW_CONFIG_PATH_ABSOLUTE} ) diff --git a/osal/FreeRTOS/CMakeLists.txt b/osal/FreeRTOS/CMakeLists.txt index a7b1338f..c310c5cf 100644 --- a/osal/FreeRTOS/CMakeLists.txt +++ b/osal/FreeRTOS/CMakeLists.txt @@ -11,8 +11,19 @@ target_sources(${LIB_FSFW_NAME} MutexFactory.cpp PeriodicTask.cpp QueueFactory.cpp - QueueMapManager.cpp SemaphoreFactory.cpp TaskFactory.cpp Timekeeper.cpp -) \ No newline at end of file +) + +# FreeRTOS is required to link the FSFW now. It is recommended to compile +# FreeRTOS as a static library and set LIB_OS_NAME to the target name of the +# library. +if(NOT LIB_OS_NAME) + message(FATAL_ERROR + "FreeRTOS needs to be linked as a target and " + "LIB_OS_NAME needs to be set to the target" + ) +endif() + +target_link_libraries(${LIB_FSWFW_NAME} ${LIB_OS_NAME}) \ No newline at end of file From be20978998bc2d6852cd7ecdc6d3061354e13104 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 12:10:29 +0100 Subject: [PATCH 083/103] better path determination --- CMakeLists.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index a3ca3e0d..21f4c90e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -98,10 +98,10 @@ endif() # FSFW might be part of a possibly complicated folder structure, so we # extract the absolute path of the fsfwconfig folder. if(IS_ABSOLUTE ${FSFW_CONFIG_PATH}) - set(${FSFW_CONFIG_PATH_ABSOLUTE} ${FSFW_CONFIG_PATH}) + set(FSFW_CONFIG_PATH_ABSOLUTE ${FSFW_CONFIG_PATH}) else() - get_filename_component(${FSFW_CONFIG_PATH_ABSOLUTE} - ${FSFW_CONFIG_PATH} ABSOLUTE + get_filename_component(FSFW_CONFIG_PATH_ABSOLUTE + ${FSFW_CONFIG_PATH} REALPATH BASE_DIR ${CMAKE_SOURCE_DIR} ) endif() From b8e703ca833295d5dbfaadf20bb45b358295b6ff Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 13:04:16 +0100 Subject: [PATCH 084/103] linked against OS --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 21f4c90e..5660443f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -27,6 +27,7 @@ elseif(${OS_FSFW} STREQUAL linux) set(OS_FSFW_NAME "Linux") elseif(${OS_FSFW} STREQUAL freertos) set(OS_FSFW_NAME "FreeRTOS") + target_link_libraries(${LIB_FSFW_NAME} ${LIB_OS_NAME}) elseif(${OS_FSFW} STREQUAL rtems) set(OS_FSFW_NAME "RTEMS") else() From 8ede00fdf18c8a0fb7afd808a2d76d69bd5c23a9 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 18:38:02 +0100 Subject: [PATCH 085/103] small bugfixes --- CMakeLists.txt | 4 ++++ osal/FreeRTOS/CMakeLists.txt | 1 + 2 files changed, 5 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 5660443f..0497a42f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -119,3 +119,7 @@ target_include_directories(${LIB_FSFW_NAME} PRIVATE ${CMAKE_SOURCE_DIR} ${FSFW_CONFIG_PATH_ABSOLUTE} ) + +target_compile_options(${LIB_FSFW_NAME} PRIVATE + ${ABI_FLAGS} +) diff --git a/osal/FreeRTOS/CMakeLists.txt b/osal/FreeRTOS/CMakeLists.txt index c310c5cf..95462010 100644 --- a/osal/FreeRTOS/CMakeLists.txt +++ b/osal/FreeRTOS/CMakeLists.txt @@ -14,6 +14,7 @@ target_sources(${LIB_FSFW_NAME} SemaphoreFactory.cpp TaskFactory.cpp Timekeeper.cpp + TaskManagement.cpp ) # FreeRTOS is required to link the FSFW now. It is recommended to compile From d186b70d2edf5265f99e6d933ce90ccf5faf641f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 18:41:28 +0100 Subject: [PATCH 086/103] comment added --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 0497a42f..b2c55d95 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -120,6 +120,7 @@ target_include_directories(${LIB_FSFW_NAME} PRIVATE ${FSFW_CONFIG_PATH_ABSOLUTE} ) +# Machine specific options can be set with the ABI_FLAGS variable. target_compile_options(${LIB_FSFW_NAME} PRIVATE ${ABI_FLAGS} ) From c64a9654ea54ab843406b9966fffd9f26c76e17a Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sat, 19 Dec 2020 22:51:10 +0100 Subject: [PATCH 087/103] xcompile update --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index b2c55d95..2fc33e58 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -38,7 +38,7 @@ else() set(OS_FSFW "host") endif() -message(STATUS "Compiling FSFW for the ${OS_FSFW_NAME} operating system") +message(STATUS "Compiling FSFW for the ${OS_FSFW_NAME} operating system.") # Options to exclude parts of the FSFW from compilation. option(FSFW_USE_RMAP "Compile with RMAP" ON) From ebe7f02fc4c65ac4f28825d54671fe402e61cd9f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sun, 20 Dec 2020 01:56:21 +0100 Subject: [PATCH 088/103] better error handling --- osal/windows/TcWinUdpPollingTask.cpp | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/osal/windows/TcWinUdpPollingTask.cpp b/osal/windows/TcWinUdpPollingTask.cpp index 7b54bb2c..06deafd1 100644 --- a/osal/windows/TcWinUdpPollingTask.cpp +++ b/osal/windows/TcWinUdpPollingTask.cpp @@ -119,7 +119,7 @@ void TcWinUdpPollingTask::setTimeout(double timeoutSeconds) { int result = setsockopt(serverUdpSocket, SOL_SOCKET, SO_RCVTIMEO, reinterpret_cast(&timeoutMs), sizeof(DWORD)); if(result == -1) { - sif::error << "TcSocketPollingTask::TcSocketPollingTask: Setting " + sif::error << "TcWinUdpPollingTask::TcSocketPollingTask: Setting " "receive timeout failed with " << strerror(errno) << std::endl; } } @@ -128,17 +128,22 @@ void TcWinUdpPollingTask::handleReadError() { int error = WSAGetLastError(); switch(error) { case(WSANOTINITIALISED): { - sif::info << "TmTcWinUdpBridge::handleReadError: WSANOTINITIALISED: " + sif::info << "TcWinUdpPollingTask::handleReadError: WSANOTINITIALISED: " << "WSAStartup(...) call " << "necessary" << std::endl; break; } case(WSAEFAULT): { - sif::info << "TmTcWinUdpBridge::handleReadError: WSADEFAULT: " + sif::info << "TcWinUdpPollingTask::handleReadError: WSADEFAULT: " << "Bad address " << std::endl; break; } + case(WSAEINVAL): { + sif::info << "TcWinUdpPollingTask::handleReadError: WSAEINVAL: " + << "Invalid input parameters. " << std::endl; + break; + } default: { - sif::info << "TmTcWinUdpBridge::handleReadError: Error code: " + sif::info << "TcWinUdpPollingTask::handleReadError: Error code: " << error << std::endl; break; } From a0d5b2331183d40edacc4a81a6022573d00a18a0 Mon Sep 17 00:00:00 2001 From: "Robin.Mueller" Date: Sun, 20 Dec 2020 02:09:08 +0100 Subject: [PATCH 089/103] small improvement --- osal/host/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/osal/host/CMakeLists.txt b/osal/host/CMakeLists.txt index d73e6f27..aa32990b 100644 --- a/osal/host/CMakeLists.txt +++ b/osal/host/CMakeLists.txt @@ -13,9 +13,9 @@ target_sources(${LIB_FSFW_NAME} ) if(UNIX) - add_definitions(-pthread) target_link_libraries(${LIB_FSFW_NAME} PRIVATE rt + pthread ) endif() \ No newline at end of file From 3540adf022c792c5ba3470482a2cc4e83aad96fa Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sun, 20 Dec 2020 13:21:12 +0100 Subject: [PATCH 090/103] added warning flags --- CMakeLists.txt | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 2fc33e58..084bd4ae 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -106,6 +106,15 @@ else() ) endif() +set(WARNING_FLAGS + -Wall + -Wextra + -Wshadow=local + -Wimplicit-fallthrough=1 + -Wno-unused-parameter + -Wno-psabi +) + # Required include paths to compile the FSFW target_include_directories(${LIB_FSFW_NAME} INTERFACE ${CMAKE_SOURCE_DIR} @@ -122,5 +131,6 @@ target_include_directories(${LIB_FSFW_NAME} PRIVATE # Machine specific options can be set with the ABI_FLAGS variable. target_compile_options(${LIB_FSFW_NAME} PRIVATE + ${WARNING_FLAGS} ${ABI_FLAGS} ) From d8e5000d47c705e4527f9cd8fe5c5960bdcea64f Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sun, 20 Dec 2020 15:32:03 +0100 Subject: [PATCH 091/103] msvc tests --- CMakeLists.txt | 23 +++++++++++++++-------- coordinates/Sgp4Propagator.h | 2 ++ globalfunctions/timevalOperations.h | 6 ++++++ osal/Endiness.h | 14 ++++++++++++++ serviceinterface/ServiceInterfaceBuffer.h | 2 +- timemanager/Clock.h | 2 ++ 6 files changed, 40 insertions(+), 9 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 084bd4ae..02849ca4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -106,14 +106,20 @@ else() ) endif() -set(WARNING_FLAGS - -Wall - -Wextra - -Wshadow=local - -Wimplicit-fallthrough=1 - -Wno-unused-parameter - -Wno-psabi -) +if(CMAKE_COMPILER_IS_GNUCXX) + set(WARNING_FLAGS + -Wall + -Wextra + -Wshadow=local + -Wimplicit-fallthrough=1 + -Wno-unused-parameter + -Wno-psabi + ) +endif() + +if(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC") + set(COMPILER_FLAGS "/permissive-") +endif() # Required include paths to compile the FSFW target_include_directories(${LIB_FSFW_NAME} INTERFACE @@ -132,5 +138,6 @@ target_include_directories(${LIB_FSFW_NAME} PRIVATE # Machine specific options can be set with the ABI_FLAGS variable. target_compile_options(${LIB_FSFW_NAME} PRIVATE ${WARNING_FLAGS} + ${COMPILER_FLAGS} ${ABI_FLAGS} ) diff --git a/coordinates/Sgp4Propagator.h b/coordinates/Sgp4Propagator.h index 3949547e..f813c6f4 100644 --- a/coordinates/Sgp4Propagator.h +++ b/coordinates/Sgp4Propagator.h @@ -1,7 +1,9 @@ #ifndef SGP4PROPAGATOR_H_ #define SGP4PROPAGATOR_H_ +#ifndef WIN32 #include +#endif #include "../contrib/sgp4/sgp4unit.h" #include "../returnvalues/HasReturnvaluesIF.h" diff --git a/globalfunctions/timevalOperations.h b/globalfunctions/timevalOperations.h index 3977d5d9..18eef866 100644 --- a/globalfunctions/timevalOperations.h +++ b/globalfunctions/timevalOperations.h @@ -2,7 +2,13 @@ #define TIMEVALOPERATIONS_H_ #include + +#ifdef WIN32 +// Why MSVC? Why? :))) +#include +#else #include +#endif timeval& operator+=(timeval& lhs, const timeval& rhs); diff --git a/osal/Endiness.h b/osal/Endiness.h index 65cc0a10..9d3fdef0 100644 --- a/osal/Endiness.h +++ b/osal/Endiness.h @@ -22,9 +22,23 @@ #else #error "Can't decide which end is which!" #endif +#else + +#ifdef WIN32 +#include +#if REG_DWORD == REG_DWORD_LITTLE_ENDIAN +#define BYTE_ORDER_SYSTEM LITTLE_ENDIAN +#else +#define BYTE_ORDER_SYSTEM BIG_ENDIAN +#endif + + #else #error __BYTE_ORDER__ not defined #endif + +#endif + #endif diff --git a/serviceinterface/ServiceInterfaceBuffer.h b/serviceinterface/ServiceInterfaceBuffer.h index c5d5b258..e69538d1 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 = Traits::eof()) override; + int overflow(int c = std::ostream::traits_type::eof()) override; //! This function is called when stream is flushed, //! for example when std::endl is put to stream. diff --git a/timemanager/Clock.h b/timemanager/Clock.h index d8b06fda..7e27e40d 100644 --- a/timemanager/Clock.h +++ b/timemanager/Clock.h @@ -6,7 +6,9 @@ #include "../globalfunctions/timevalOperations.h" #include +#ifndef WIN32 #include +#endif //! Don't use these for time points, type is not large enough for UNIX epoch. using dur_millis_t = uint32_t; From de183e6c6589386cbbfefe6ba56e0dc45a2f6faa Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Sun, 20 Dec 2020 17:01:22 +0100 Subject: [PATCH 092/103] removed comment --- globalfunctions/timevalOperations.h | 1 - 1 file changed, 1 deletion(-) diff --git a/globalfunctions/timevalOperations.h b/globalfunctions/timevalOperations.h index 18eef866..46f763b9 100644 --- a/globalfunctions/timevalOperations.h +++ b/globalfunctions/timevalOperations.h @@ -4,7 +4,6 @@ #include #ifdef WIN32 -// Why MSVC? Why? :))) #include #else #include From 5c45b823ad8807d4cd83e109eed7da87feceb56e Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 21 Dec 2020 13:52:41 +0100 Subject: [PATCH 093/103] include fix --- globalfunctions/timevalOperations.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/globalfunctions/timevalOperations.h b/globalfunctions/timevalOperations.h index 46f763b9..db68f330 100644 --- a/globalfunctions/timevalOperations.h +++ b/globalfunctions/timevalOperations.h @@ -4,7 +4,7 @@ #include #ifdef WIN32 -#include +#include #else #include #endif From 1d080ba6cb3d6a73fa5647c32033ec718fe3bb72 Mon Sep 17 00:00:00 2001 From: Spacefish Date: Mon, 21 Dec 2020 14:07:06 +0100 Subject: [PATCH 094/103] clock update --- timemanager/Clock.h | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/timemanager/Clock.h b/timemanager/Clock.h index 7e27e40d..fcc602a2 100644 --- a/timemanager/Clock.h +++ b/timemanager/Clock.h @@ -6,7 +6,10 @@ #include "../globalfunctions/timevalOperations.h" #include -#ifndef WIN32 + +#ifdef WIN32 +#include +#else #include #endif From 5317391f8a1077eebc179e3ce3df8cdb9e753315 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Mon, 21 Dec 2020 17:19:43 +0100 Subject: [PATCH 095/103] 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 096/103] 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 097/103] 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 098/103] 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 099/103] 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 6b1a8afe2b50a59f35946086ee6e846c28742ae1 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 13:25:50 +0100 Subject: [PATCH 100/103] 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 101/103] 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 102/103] 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 9ac07368da3fab3a60fa0caffe0f10f8c35e2fd9 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Tue, 22 Dec 2020 14:26:42 +0100 Subject: [PATCH 103/103] 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