Compare commits

...

34 Commits

Author SHA1 Message Date
45cf31c2b1 new fsfw
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
EIVE/-/pipeline/head Build queued...
2022-09-14 11:30:15 +02:00
f6f6393c4a reverting mib only changes to cmake
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-09-07 12:02:18 +02:00
7754d65753 reverting changes to CMakeList.txt to move back topwards upstream 2022-09-07 11:09:17 +02:00
Uli
c14b131e6f fixed fsfw
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-09-07 10:57:39 +02:00
de856a514b workarounds for MIB build
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-09-06 22:17:54 +02:00
acd365e421 Mode introspection and fixes
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-26 16:12:22 +02:00
06b6c0838a compiling both with and without introspection 2022-08-25 16:28:01 +02:00
3c762e7437 switching mission object ids to FSFW_CLASSLESS_ENUM 2022-08-25 15:13:15 +02:00
4a147a442c removing debug code 2022-08-25 14:44:18 +02:00
fe8036361d I knew this was stupid: Revert "changing mission dependend object IDs to FSFW_ENUM"
This reverts commit 2800484f6b.
2022-08-25 14:43:27 +02:00
2800484f6b changing mission dependend object IDs to FSFW_ENUM
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-24 22:29:42 +02:00
aaeb101442 mostly done with gomspacehandlers, some todos left
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-24 18:13:03 +02:00
da2acd1fa8 continuing on gomspace handlers 2022-08-24 17:19:14 +02:00
1f47c970af working on gomespace handlers
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-23 23:34:20 +02:00
dfb800f58a more dirty hacks to check amd64 build. To be cleaned up
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-19 14:31:48 +02:00
a93fe8ef8e fixing bug in handlers 2022-08-19 14:31:22 +02:00
35effb9e68 stubs to be able to compile on modern amd64 2022-08-19 14:28:44 +02:00
c0e896b371 working on compiling bsp_q7s on amd64
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-18 19:04:49 +02:00
73971ad486 fixes 2022-08-18 16:33:53 +02:00
45e5ea362d Merge branch 'develop' into mohr/introspection
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-18 13:15:58 +02:00
7bcc4b18b7 compiles 2022-08-18 10:42:18 +02:00
a3b5993fdc compiles, does not link yet
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-17 19:19:49 +02:00
eb886dc53c Ploc Memory Dumper 2022-08-17 19:19:20 +02:00
a91393b4b4 Small fixes 2022-08-17 17:55:21 +02:00
ef40db7fe4 CCSDS Handler 2022-08-17 17:54:59 +02:00
60a20acc5b Core controlle rincomplete, but compiles
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-17 11:21:35 +02:00
13cc31dca9 working on core controller
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-08-16 18:31:58 +02:00
ad88bfa5b4 core controller bigWIP
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
2022-07-28 17:16:24 +02:00
d92b1b170d Boilerplate Code to make ploc and star tracker compile 2022-07-27 23:09:05 +02:00
24297a6a97 WIP adapting PlocMpSoCHandler
Some checks failed
EIVE/eive-obsw/pipeline/head There was a failure building this commit
major PITA, but does compile now, will be back with more patience
2022-07-27 22:03:41 +02:00
c8f4f0b03e GPSHyperionController adapted 2022-07-27 22:02:37 +02:00
eeaef13916 PdecHandler adapted 2022-07-26 21:23:41 +02:00
a2910a401e adapted SolarArrayDeploymentHandler 2022-07-26 17:18:35 +02:00
cd1200d23d introspection fsfw, HeaterHandler adapted 2022-07-26 17:18:04 +02:00
66 changed files with 2116 additions and 1576 deletions

View File

@ -15,6 +15,7 @@ set(OBSW_VERSION_REVISION_IF_GIT_FAILS 0)
# set(CMAKE_VERBOSE TRUE)
option(
EIVE_HARDCODED_TOOLCHAIN_FILE
"\
@ -160,7 +161,7 @@ if(NOT GIT_VER_HANDLING_OK)
endif()
# Set names and variables
set(OBSW_NAME ${CMAKE_PROJECT_NAME})
set(OBSW_NAME ${PROJECT_NAME})
set(WATCHDOG_NAME eive-watchdog)
set(SIMPLE_OBSW_NAME eive-simple)
set(UNITTEST_NAME eive-unittest)
@ -182,7 +183,7 @@ set(FSFW_PATH fsfw)
set(TEST_PATH test)
set(UNITTEST_PATH unittest)
set(LINUX_PATH linux)
set(COMMON_PATH common)
set(COMMON_PATH ${CMAKE_CURRENT_SOURCE_DIR}/common)
set(DUMMY_PATH dummies)
set(WATCHDOG_PATH watchdog)
set(COMMON_CONFIG_PATH ${COMMON_PATH}/config)
@ -205,6 +206,7 @@ pre_source_hw_os_config()
if(TGT_BSP)
set(LIBGPS_VERSION_MAJOR 3)
# I assume a newer version than 3.17 will be installed on other Linux board
# than the Q7S
set(LIBGPS_VERSION_MINOR 20)
@ -214,7 +216,8 @@ if(TGT_BSP)
OR TGT_BSP MATCHES "arm/egse"
OR TGT_BSP MATCHES "arm/te0720-1cfa")
find_library(${LIB_GPS} gps)
set(FSFW_CONFIG_PATH "linux/fsfwconfig")
set(FSFW_CONFIG_PATH ${CMAKE_CURRENT_SOURCE_DIR}/linux/fsfwconfig)
if(NOT BUILD_Q7S_SIMPLE_MODE)
set(EIVE_ADD_LINUX_FILES TRUE)
set(ADD_CSP_LIB TRUE)
@ -271,8 +274,9 @@ endif()
configure_file(${WATCHDOG_PATH}/watchdogConf.h.in watchdogConf.h)
# Set common config path for FSFW
set(FSFW_ADDITIONAL_INC_PATHS "${COMMON_PATH}/config"
${CMAKE_CURRENT_BINARY_DIR})
set(FSFW_ADDITIONAL_INC_PATHS "${COMMON_PATH}"
${COMMON_CONFIG_PATH}
${CMAKE_CURRENT_BINARY_DIR})
# ##############################################################################
# Executable and Sources
@ -320,7 +324,7 @@ add_library(${LIB_DUMMIES})
# Add main executable
add_executable(${OBSW_NAME})
set(OBSW_BIN_NAME ${CMAKE_PROJECT_NAME})
set(OBSW_BIN_NAME ${PROJECT_NAME})
set_target_properties(${OBSW_NAME} PROPERTIES OUTPUT_NAME ${OBSW_BIN_NAME})
@ -356,7 +360,10 @@ if(EIVE_ADD_LINUX_FILES)
add_subdirectory(${LIB_ARCSEC_PATH})
add_subdirectory(${LINUX_PATH})
endif()
add_subdirectory(${BSP_PATH})
if(ADD_CSP_LIB)
add_subdirectory(${LIB_CSP_PATH})
endif()

View File

@ -9,7 +9,7 @@ add_subdirectory(simple)
target_sources(${OBSW_NAME} PUBLIC main.cpp obsw.cpp)
add_subdirectory(boardtest)
#add_subdirectory(boardtest)
add_subdirectory(boardconfig)
add_subdirectory(comIF)

View File

@ -1,4 +1,4 @@
target_sources(${OBSW_NAME} PRIVATE FileSystemTest.cpp Q7STestTask.cpp)
target_sources(${OBSW_NAME} PUBLIC FileSystemTest.cpp Q7STestTask.cpp)
if(EIVE_BUILD_Q7S_SIMPLE_MODE)
target_sources(${SIMPLE_OBSW_NAME} PRIVATE FileSystemTest.cpp)

View File

@ -4,11 +4,7 @@
#include "fsfw/action/HasActionsIF.h"
#include "fsfw/tasks/TaskFactory.h"
ReturnValue_t gps::triggerGpioResetPin(const uint8_t* actionData, size_t len, void* args) {
// At least one byte which denotes which GPS to reset is required
if (len < 1 or actionData == nullptr) {
return HasActionsIF::INVALID_PARAMETERS;
}
ReturnValue_t gps::triggerGpioResetPin(uint8_t gpsId, void* args) {
ResetArgs* resetArgs = reinterpret_cast<ResetArgs*>(args);
if (args == nullptr) {
return HasReturnvaluesIF::RETURN_FAILED;
@ -16,10 +12,8 @@ ReturnValue_t gps::triggerGpioResetPin(const uint8_t* actionData, size_t len, vo
if (resetArgs->gpioComIF == nullptr) {
return HasReturnvaluesIF::RETURN_FAILED;
}
gpioId_t gpioId;
if (actionData[0] == 0) {
gpioId = gpioIds::GNSS_0_NRESET;
} else {
gpioId_t gpioId = gpioIds::GNSS_0_NRESET;
if (gpsId == 1) {
gpioId = gpioIds::GNSS_1_NRESET;
}
resetArgs->gpioComIF->pullLow(gpioId);

View File

@ -11,7 +11,7 @@ struct ResetArgs {
namespace gps {
ReturnValue_t triggerGpioResetPin(const uint8_t* actionData, size_t len, void* args);
ReturnValue_t triggerGpioResetPin(uint8_t gpsId, void* args);
}

View File

@ -0,0 +1,87 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
class CoreController;
namespace core {
FSFW_ENUM(ActionId, ActionId_t,
((LIST_DIRECTORY_INTO_FILE, 0, "List Directory into file"))(
(SWITCH_REBOOT_FILE_HANDLING, 5,
"Switch Reboot File Handling"))((RESET_REBOOT_COUNTERS, 6, "Reset Boot Counters"))(
(SWITCH_IMG_LOCK, 7, "Switch Image Lock"))((SET_MAX_REBOOT_CNT, 8,
"Set maximum reboot Count"))(
(XSC_REBOOT_OBC, 32, "Reboot using the xsc_boot_copy command"))(
(MOUNT_OTHER_COPY, 33, "Mount Other Copy"))((REBOOT_OBC, 34,
"Reboot using the reboot command")))
FSFW_ENUM(Boolenum, uint8_t, ((NO, 0, "NO"))((YES, 1, "Yes")))
class ListDirectoryIntoFileAction
: public TemplateAction<CoreController, ListDirectoryIntoFileAction, ActionId> {
public:
ListDirectoryIntoFileAction(CoreController *owner)
: TemplateAction(owner, ActionId::LIST_DIRECTORY_INTO_FILE){};
};
class SwitchRebootFileHandlingAction
: public TemplateAction<CoreController, SwitchRebootFileHandlingAction, ActionId> {
public:
SwitchRebootFileHandlingAction(CoreController *owner)
: TemplateAction(owner, ActionId::SWITCH_REBOOT_FILE_HANDLING){};
Parameter<Boolenum> enableRebootFile =
Parameter<Boolenum>::createParameter(this, "Enable Reboot File");
};
class ResetRebootCountersAction
: public TemplateAction<CoreController, ResetRebootCountersAction, ActionId> {
public:
FSFW_ENUM(Selection, uint8_t, ((ZERO, "0"))((ONE, "1"))((ALL, "All")))
ResetRebootCountersAction(CoreController *owner)
: TemplateAction(owner, ActionId::RESET_REBOOT_COUNTERS){};
Parameter<Selection> chip = Parameter<Selection>::createParameter(this, "Chip");
Parameter<Selection> copy = Parameter<Selection>::createParameter(this, "Copy");
};
class SwitchImageLockAction
: public TemplateAction<CoreController, SwitchImageLockAction, ActionId> {
public:
FSFW_ENUM(Selection, uint8_t, ((ZERO, "0"))((ONE, "1")))
SwitchImageLockAction(CoreController *owner) : TemplateAction(owner, ActionId::SWITCH_IMG_LOCK){};
Parameter<Boolenum> lock = Parameter<Boolenum>::createParameter(this, "Lock Image");
Parameter<Selection> chip = Parameter<Selection>::createParameter(this, "Chip");
Parameter<Selection> copy = Parameter<Selection>::createParameter(this, "Copy");
};
class SetMaxRebootCntAction
: public TemplateAction<CoreController, SetMaxRebootCntAction, ActionId> {
public:
SetMaxRebootCntAction(CoreController *owner)
: TemplateAction(owner, ActionId::SET_MAX_REBOOT_CNT){};
Parameter<uint8_t> maxCount = Parameter<uint8_t>::createParameter(this, "Count");
};
class XscRebootObcAction : public TemplateAction<CoreController, XscRebootObcAction, ActionId> {
public:
FSFW_ENUM(Selection, uint8_t, ((ZERO, "0"))((ONE, "1"))((SAME, "Same")))
XscRebootObcAction(CoreController *owner) : TemplateAction(owner, ActionId::XSC_REBOOT_OBC){};
Parameter<Selection> chip = Parameter<Selection>::createParameter(this, "Chip");
Parameter<Selection> copy = Parameter<Selection>::createParameter(this, "Copy");
};
class RebootObcAction : public TemplateAction<CoreController, RebootObcAction, ActionId> {
public:
RebootObcAction(CoreController *owner) : TemplateAction(owner, ActionId::REBOOT_OBC){};
};
} // namespace core

View File

@ -163,75 +163,73 @@ ReturnValue_t CoreController::initializeAfterTaskCreation() {
return result;
}
ReturnValue_t CoreController::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t *data, size_t size) {
switch (actionId) {
case (LIST_DIRECTORY_INTO_FILE): {
return actionListDirectoryIntoFile(actionId, commandedBy, data, size);
}
case (SWITCH_REBOOT_FILE_HANDLING): {
if (size < 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
std::string path = sdcMan->getCurrentMountPrefix() + REBOOT_FILE;
// Disable the reboot file mechanism
parseRebootFile(path, rebootFile);
if (data[0] == 0) {
rebootFile.enabled = false;
rewriteRebootFile(rebootFile);
} else if (data[0] == 1) {
rebootFile.enabled = true;
rewriteRebootFile(rebootFile);
} else {
return HasActionsIF::INVALID_PARAMETERS;
}
return HasActionsIF::EXECUTION_FINISHED;
}
case (RESET_REBOOT_COUNTERS): {
if (size == 0) {
resetRebootCount(xsc::ALL_CHIP, xsc::ALL_COPY);
} else if (size == 2) {
if (data[0] > 1 or data[1] > 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
resetRebootCount(static_cast<xsc::Chip>(data[0]), static_cast<xsc::Copy>(data[1]));
}
return HasActionsIF::EXECUTION_FINISHED;
}
case (SWITCH_IMG_LOCK): {
if (size != 3) {
return HasActionsIF::INVALID_PARAMETERS;
}
if (data[1] > 1 or data[2] > 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
setRebootMechanismLock(data[0], static_cast<xsc::Chip>(data[1]),
static_cast<xsc::Copy>(data[2]));
return HasActionsIF::EXECUTION_FINISHED;
}
case (SET_MAX_REBOOT_CNT): {
if (size < 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
std::string path = sdcMan->getCurrentMountPrefix() + REBOOT_FILE;
// Disable the reboot file mechanism
parseRebootFile(path, rebootFile);
rebootFile.maxCount = data[0];
rewriteRebootFile(rebootFile);
return HasActionsIF::EXECUTION_FINISHED;
}
case (XSC_REBOOT_OBC): {
// Warning: This function will never return, because it reboots the system
return actionXscReboot(data, size);
}
case (REBOOT_OBC): {
// Warning: This function will never return, because it reboots the system
return actionReboot(data, size);
}
default: {
return HasActionsIF::INVALID_ACTION_ID;
}
ReturnValue_t CoreController::executeAction(Action *action) { return action->handle(); }
ReturnValue_t CoreController::handleAction(core::SwitchRebootFileHandlingAction *action) {
std::string path = sdcMan->getCurrentMountPrefix() + REBOOT_FILE;
// Disable the reboot file mechanism
parseRebootFile(path, rebootFile);
if (action->enableRebootFile.value == core::Boolenum::NO) {
rebootFile.enabled = false;
rewriteRebootFile(rebootFile);
} else {
rebootFile.enabled = true;
rewriteRebootFile(rebootFile);
}
return HasActionsIF::EXECUTION_FINISHED;
}
ReturnValue_t CoreController::handleAction(core::ResetRebootCountersAction *action) {
xsc::Chip chip = xsc::NO_CHIP;
switch (action->chip.value) {
case core::ResetRebootCountersAction::Selection::ALL:
chip = xsc::ALL_CHIP;
break;
case core::ResetRebootCountersAction::Selection::ZERO:
chip = xsc::CHIP_0;
break;
case core::ResetRebootCountersAction::Selection::ONE:
chip = xsc::CHIP_1;
break;
}
xsc::Copy copy = xsc::NO_COPY;
switch (action->copy.value) {
case core::ResetRebootCountersAction::Selection::ALL:
copy = xsc::ALL_COPY;
break;
case core::ResetRebootCountersAction::Selection::ZERO:
copy = xsc::COPY_0;
break;
case core::ResetRebootCountersAction::Selection::ONE:
copy = xsc::COPY_1;
break;
}
resetRebootCount(chip, copy);
return HasActionsIF::EXECUTION_FINISHED;
}
ReturnValue_t CoreController::handleAction(core::SwitchImageLockAction *action) {
bool lock = action->lock.value == core::Boolenum::YES;
xsc::Chip chip = xsc::CHIP_0;
if (action->chip.value == core::SwitchImageLockAction::Selection::ONE) {
chip = xsc::CHIP_1;
}
xsc::Copy copy = xsc::COPY_0;
if (action->copy.value == core::SwitchImageLockAction::Selection::ONE) {
copy = xsc::COPY_0;
}
setRebootMechanismLock(lock, chip, copy);
return HasActionsIF::EXECUTION_FINISHED;
}
ReturnValue_t CoreController::handleAction(core::SetMaxRebootCntAction *action) {
std::string path = sdcMan->getCurrentMountPrefix() + REBOOT_FILE;
// Disable the reboot file mechanism
parseRebootFile(path, rebootFile);
rebootFile.maxCount = action->maxCount;
rewriteRebootFile(rebootFile);
return HasActionsIF::EXECUTION_FINISHED;
}
ReturnValue_t CoreController::checkModeCommand(Mode_t mode, Submode_t submode,
@ -748,30 +746,29 @@ ReturnValue_t CoreController::initVersionFile() {
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t CoreController::actionListDirectoryIntoFile(ActionId_t actionId,
MessageQueueId_t commandedBy,
const uint8_t *data, size_t size) {
ReturnValue_t CoreController::handleAction(core::ListDirectoryIntoFileAction *action) {
// TODO: Packet definition for clean deserialization
// 2 bytes for a and R flag, at least 5 bytes for minimum valid path /tmp with
// null termination, at least 7 bytes for minimum target file name /tmp/a with
// null termination.
if (size < 14) {
return HasActionsIF::INVALID_PARAMETERS;
}
// TODO make work again
// if (size < 14) {
// return HasActionsIF::INVALID_PARAMETERS;
// }
// We could also make -l optional, but I can't think of a reason why to not use -l..
// This flag specifies to run ls with -a
bool aFlag = data[0];
data += 1;
// This flag specifies to run ls with -R
bool RFlag = data[1];
data += 1;
bool aFlag = 0; // data[0];
// data += 1;
// This flag specifies to run ls with -R
bool RFlag = 0; // data[1];
// data += 1;
size_t remainingSize = size - 2;
size_t remainingSize = 0; // size - 2;
// One larger for null termination, which prevents undefined behaviour if the sent
// strings are not 0 terminated properly
std::vector<uint8_t> repoAndTargetFileBuffer(remainingSize + 1, 0);
std::memcpy(repoAndTargetFileBuffer.data(), data, remainingSize);
// std::memcpy(repoAndTargetFileBuffer.data(), data, remainingSize);
const char *currentCharPtr = reinterpret_cast<const char *>(repoAndTargetFileBuffer.data());
// Full target file name
std::string repoName(currentCharPtr);
@ -798,7 +795,7 @@ ReturnValue_t CoreController::actionListDirectoryIntoFile(ActionId_t actionId,
int result = std::system(oss.str().c_str());
if (result != 0) {
utility::handleSystemError(result, "CoreController::actionListDirectoryIntoFile");
actionHelper.finish(false, commandedBy, actionId);
actionHelper.finish(false, action->commandedBy, action->getId());
}
return HasReturnvaluesIF::RETURN_OK;
}
@ -857,11 +854,16 @@ void CoreController::initPrint() {
#endif
}
ReturnValue_t CoreController::actionXscReboot(const uint8_t *data, size_t size) {
if (size < 1) {
ReturnValue_t CoreController::handleAction(core::XscRebootObcAction *action) {
if (action->chip.value == core::XscRebootObcAction::Selection::SAME and
not(action->copy.value == core::XscRebootObcAction::Selection::SAME)) {
return HasActionsIF::INVALID_PARAMETERS;
}
bool rebootSameBootCopy = data[0];
bool rebootSameBootCopy = false;
if (action->chip.value == core::XscRebootObcAction::Selection::SAME and
action->copy.value == core::XscRebootObcAction::Selection::SAME) {
rebootSameBootCopy = true;
}
bool protOpPerformed = false;
SdCardManager::instance()->setBlocking(true);
if (rebootSameBootCopy) {
@ -876,19 +878,23 @@ ReturnValue_t CoreController::actionXscReboot(const uint8_t *data, size_t size)
}
return HasActionsIF::EXECUTION_FINISHED;
}
if (size < 3 or (data[1] > 1 or data[2] > 1)) {
return HasActionsIF::INVALID_PARAMETERS;
}
#if OBSW_VERBOSE_LEVEL >= 1
sif::info << "CoreController::actionPerformReboot: Rebooting on " << static_cast<int>(data[1])
<< " " << static_cast<int>(data[2]) << std::endl;
sif::info << "CoreController::actionPerformReboot: Rebooting on "
<< static_cast<uint8_t>(action->chip.value) << " "
<< static_cast<uint8_t>(action->copy.value) << std::endl;
#endif
// Check that the target chip and copy is writeprotected first
generateChipStateFile();
// If any boot copies are unprotected, protect them here
auto tgtChip = static_cast<xsc::Chip>(data[1]);
auto tgtCopy = static_cast<xsc::Copy>(data[2]);
auto tgtChip = xsc::CHIP_0;
if (action->chip.value == core::XscRebootObcAction::Selection::ONE) {
tgtChip = xsc::CHIP_1;
}
auto tgtCopy = xsc::COPY_0;
if (action->copy.value == core::XscRebootObcAction::Selection::ONE) {
tgtCopy = xsc::COPY_1;
}
// This function can not really fail
gracefulShutdownTasks(tgtChip, tgtCopy, protOpPerformed);
@ -932,7 +938,7 @@ ReturnValue_t CoreController::actionXscReboot(const uint8_t *data, size_t size)
return HasReturnvaluesIF::RETURN_FAILED;
}
ReturnValue_t CoreController::actionReboot(const uint8_t *data, size_t size) {
ReturnValue_t CoreController::handleAction(core::RebootObcAction *action) {
bool protOpPerformed = false;
gracefulShutdownTasks(xsc::Chip::CHIP_0, xsc::Copy::COPY_0, protOpPerformed);
std::system("reboot");
@ -1692,24 +1698,20 @@ void CoreController::resetRebootCount(xsc::Chip tgtChip, xsc::Copy tgtCopy) {
std::string path = currMntPrefix + REBOOT_FILE;
// Disable the reboot file mechanism
parseRebootFile(path, rebootFile);
if (tgtChip == xsc::ALL_CHIP and tgtCopy == xsc::ALL_COPY) {
rebootFile.img00Cnt = 0;
rebootFile.img01Cnt = 0;
rebootFile.img10Cnt = 0;
rebootFile.img11Cnt = 0;
} else {
if (tgtChip == xsc::CHIP_0) {
if (tgtCopy == xsc::COPY_0) {
rebootFile.img00Cnt = 0;
} else {
rebootFile.img01Cnt = 0;
}
} else {
if (tgtCopy == xsc::COPY_0) {
rebootFile.img10Cnt = 0;
} else {
rebootFile.img11Cnt = 0;
}
if (tgtChip == xsc::ALL_CHIP or tgtChip == xsc::CHIP_0) {
if (tgtCopy == xsc::ALL_COPY or tgtCopy == xsc::COPY_0) {
rebootFile.img00Cnt = 0;
}
if (tgtCopy == xsc::ALL_COPY or tgtCopy == xsc::COPY_1) {
rebootFile.img01Cnt = 0;
}
}
if (tgtChip == xsc::ALL_CHIP or tgtChip == xsc::CHIP_1) {
if (tgtCopy == xsc::ALL_COPY or tgtCopy == xsc::COPY_0) {
rebootFile.img10Cnt = 0;
}
if (tgtCopy == xsc::ALL_COPY or tgtCopy == xsc::COPY_1) {
rebootFile.img11Cnt = 0;
}
}
rewriteRebootFile(rebootFile);
@ -1849,3 +1851,7 @@ bool CoreController::isNumber(const std::string &s) {
return !s.empty() && std::find_if(s.begin(), s.end(),
[](unsigned char c) { return !std::isdigit(c); }) == s.end();
}
ModeDefinitionHelper CoreController::getModeDefinitionHelper() {
return ModeDefinitionHelper::create<ControllerModes, DefaultSubmode>();
}

View File

@ -6,6 +6,7 @@
#include <cstddef>
#include "CoreActions.h"
#include "CoreDefinitions.h"
#include "bsp_q7s/memory/SdCardManager.h"
#include "events/subsystemIdRanges.h"
@ -61,18 +62,6 @@ class CoreController : public ExtendedControllerBase {
"/" + std::string(CONF_FOLDER) + "/" + std::string(REBOOT_FILE_NAME);
const std::string TIME_FILE = "/" + std::string(CONF_FOLDER) + "/" + std::string(TIME_FILE_NAME);
static constexpr ActionId_t LIST_DIRECTORY_INTO_FILE = 0;
static constexpr ActionId_t SWITCH_REBOOT_FILE_HANDLING = 5;
static constexpr ActionId_t RESET_REBOOT_COUNTERS = 6;
static constexpr ActionId_t SWITCH_IMG_LOCK = 7;
static constexpr ActionId_t SET_MAX_REBOOT_CNT = 8;
//! Reboot using the xsc_boot_copy command
static constexpr ActionId_t XSC_REBOOT_OBC = 32;
static constexpr ActionId_t MOUNT_OTHER_COPY = 33;
//! Reboot using the reboot command
static constexpr ActionId_t REBOOT_OBC = 34;
static constexpr uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CORE;
static constexpr Event ALLOC_FAILURE = event::makeEvent(SUBSYSTEM_ID, 0, severity::MEDIUM);
@ -94,8 +83,17 @@ class CoreController : public ExtendedControllerBase {
ReturnValue_t initializeAfterTaskCreation() override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(core::ListDirectoryIntoFileAction* action);
ReturnValue_t handleAction(core::SwitchRebootFileHandlingAction* action);
ReturnValue_t handleAction(core::ResetRebootCountersAction* action);
ReturnValue_t handleAction(core::SwitchImageLockAction* action);
ReturnValue_t handleAction(core::SetMaxRebootCntAction* action);
ReturnValue_t handleAction(core::XscRebootObcAction* action);
ReturnValue_t handleAction(core::RebootObcAction* action);
ModeDefinitionHelper getModeDefinitionHelper() override;
ReturnValue_t handleCommandMessage(CommandMessage* message) override;
void performControlOperation() override;
@ -197,6 +195,16 @@ class CoreController : public ExtendedControllerBase {
core::HkSet hkSet;
core::ListDirectoryIntoFileAction listDirectoryIntoFileAction =
core::ListDirectoryIntoFileAction(this);
core::SwitchRebootFileHandlingAction switchRebootFileHandlingAction =
core::SwitchRebootFileHandlingAction(this);
core::ResetRebootCountersAction resetRebootCountersAction = core::ResetRebootCountersAction(this);
core::SwitchImageLockAction switchImageLockAction = core::SwitchImageLockAction(this);
core::SetMaxRebootCntAction setMaxRebootCntAction = core::SetMaxRebootCntAction(this);
core::XscRebootObcAction xscRebootObcAction = core::XscRebootObcAction(this);
core::RebootObcAction rebootObcAction = core::RebootObcAction(this);
ReturnValue_t initializeLocalDataPool(localpool::DataPool& localDataPoolMap,
LocalDataPoolManager& poolManager) override;
Countdown sdCardCheckCd = Countdown(120000);
@ -224,8 +232,6 @@ class CoreController : public ExtendedControllerBase {
void checkExternalSdCommandStatus();
void performRebootFileHandling(bool recreateFile);
ReturnValue_t actionListDirectoryIntoFile(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size);
ReturnValue_t actionXscReboot(const uint8_t* data, size_t size);
ReturnValue_t actionReboot(const uint8_t* data, size_t size);

View File

@ -92,7 +92,7 @@ ReturnValue_t readToFile(std::string name, std::ifstream& file, std::string& fil
} // End of anonymous namespace
template <typename T, class = typename std::enable_if<std::is_integral<T>::value>::type>
template <typename T, class>
inline ReturnValue_t writeNumber(std::string key, T num) noexcept {
std::ostringstream oss;
oss << "xsc_scratch write " << key << " " << std::to_string(num);
@ -104,7 +104,7 @@ inline ReturnValue_t writeNumber(std::string key, T num) noexcept {
return HasReturnvaluesIF::RETURN_OK;
}
template <typename T, class = typename std::enable_if<std::is_integral<T>::value>::type>
template <typename T, class>
inline ReturnValue_t readNumber(std::string key, T& num) noexcept {
using namespace std;
ifstream file;

View File

@ -3,83 +3,85 @@
#include <cstdint>
#include <fsfw/introspection/ClasslessEnum.h>
namespace objects {
enum commonObjects : uint32_t {
FSFW_CLASSLESS_ENUM(commonObjects, uint32_t,
/* First Byte 0x50-0x52 reserved for PUS Services **/
CCSDS_PACKET_DISTRIBUTOR = 0x50000100,
PUS_PACKET_DISTRIBUTOR = 0x50000200,
TMTC_BRIDGE = 0x50000300,
TMTC_POLLING_TASK = 0x50000400,
FILE_SYSTEM_HANDLER = 0x50000500,
SDC_MANAGER = 0x50000550,
PTME = 0x50000600,
PDEC_HANDLER = 0x50000700,
CCSDS_HANDLER = 0x50000800,
((CCSDS_PACKET_DISTRIBUTOR, 0x50000100, "CCSDS_PACKET_DISTRIBUTOR"))
((PUS_PACKET_DISTRIBUTOR, 0x50000200, "PUS_PACKET_DISTRIBUTOR"))
((TMTC_BRIDGE, 0x50000300, "TMTC_BRIDGE"))
((TMTC_POLLING_TASK, 0x50000400, "TMTC_POLLING_TASK"))
((FILE_SYSTEM_HANDLER, 0x50000500, "FILE_SYSTEM_HANDLER"))
((SDC_MANAGER, 0x50000550, "SDC_MANAGER"))
((PTME, 0x50000600, "PTME"))
((PDEC_HANDLER, 0x50000700, "PDEC_HANDLER"))
((CCSDS_HANDLER, 0x50000800, "CCSDS_HANDLER"))
/* 0x43 ('C') for Controllers */
THERMAL_CONTROLLER = 0x43400001,
ACS_CONTROLLER = 0x43000002,
CORE_CONTROLLER = 0x43000003,
((THERMAL_CONTROLLER, 0x43400001, "THERMAL_CONTROLLER"))
((ACS_CONTROLLER, 0x43000002, "ACS_CONTROLLER"))
((CORE_CONTROLLER, 0x43000003, "CORE_CONTROLLER"))
/* 0x44 ('D') for device handlers */
MGM_0_LIS3_HANDLER = 0x44120006,
MGM_1_RM3100_HANDLER = 0x44120107,
MGM_2_LIS3_HANDLER = 0x44120208,
MGM_3_RM3100_HANDLER = 0x44120309,
GYRO_0_ADIS_HANDLER = 0x44120010,
GYRO_1_L3G_HANDLER = 0x44120111,
GYRO_2_ADIS_HANDLER = 0x44120212,
GYRO_3_L3G_HANDLER = 0x44120313,
RW1 = 0x44120047,
RW2 = 0x44120148,
RW3 = 0x44120249,
RW4 = 0x44120350,
STAR_TRACKER = 0x44130001,
GPS_CONTROLLER = 0x44130045,
((MGM_0_LIS3_HANDLER, 0x44120006, "MGM_0_LIS3_HANDLER"))
((MGM_1_RM3100_HANDLER, 0x44120107, "MGM_1_RM3100_HANDLER"))
((MGM_2_LIS3_HANDLER, 0x44120208, "MGM_2_LIS3_HANDLER"))
((MGM_3_RM3100_HANDLER, 0x44120309, "MGM_3_RM3100_HANDLER"))
((GYRO_0_ADIS_HANDLER, 0x44120010, "GYRO_0_ADIS_HANDLER"))
((GYRO_1_L3G_HANDLER, 0x44120111, "GYRO_1_L3G_HANDLER"))
((GYRO_2_ADIS_HANDLER, 0x44120212, "GYRO_2_ADIS_HANDLER"))
((GYRO_3_L3G_HANDLER, 0x44120313, "GYRO_3_L3G_HANDLER"))
((RW1, 0x44120047, "RW1"))
((RW2, 0x44120148, "RW2"))
((RW3, 0x44120249, "RW3"))
((RW4, 0x44120350, "RW4"))
((STAR_TRACKER, 0x44130001, "STAR_TRACKER"))
((GPS_CONTROLLER, 0x44130045, "GPS_CONTROLLER"))
IMTQ_HANDLER = 0x44140014,
TMP1075_HANDLER_1 = 0x44420004,
TMP1075_HANDLER_2 = 0x44420005,
PCDU_HANDLER = 0x442000A1,
P60DOCK_HANDLER = 0x44250000,
PDU1_HANDLER = 0x44250001,
PDU2_HANDLER = 0x44250002,
ACU_HANDLER = 0x44250003,
BPX_BATT_HANDLER = 0x44260000,
PLPCDU_HANDLER = 0x44300000,
RAD_SENSOR = 0x443200A5,
PLOC_UPDATER = 0x44330000,
PLOC_MEMORY_DUMPER = 0x44330001,
STR_HELPER = 0x44330002,
PLOC_MPSOC_HELPER = 0x44330003,
AXI_PTME_CONFIG = 0x44330004,
PTME_CONFIG = 0x44330005,
PLOC_MPSOC_HANDLER = 0x44330015,
PLOC_SUPERVISOR_HANDLER = 0x44330016,
PLOC_SUPERVISOR_HELPER = 0x44330017,
SOLAR_ARRAY_DEPL_HANDLER = 0x444100A2,
HEATER_HANDLER = 0x444100A4,
((IMTQ_HANDLER, 0x44140014, "IMTQ_HANDLER"))
((TMP1075_HANDLER_1, 0x44420004, "TMP1075_HANDLER_1"))
((TMP1075_HANDLER_2, 0x44420005, "TMP1075_HANDLER_2"))
((PCDU_HANDLER, 0x442000A1, "PCDU_HANDLER"))
((P60DOCK_HANDLER, 0x44250000, "P60DOCK_HANDLER"))
((PDU1_HANDLER, 0x44250001, "PDU1_HANDLER"))
((PDU2_HANDLER, 0x44250002, "PDU2_HANDLER"))
((ACU_HANDLER, 0x44250003, "ACU_HANDLER"))
((BPX_BATT_HANDLER, 0x44260000, "BPX_BATT_HANDLER"))
((PLPCDU_HANDLER, 0x44300000, "PLPCDU_HANDLER"))
((RAD_SENSOR, 0x443200A5, "RAD_SENSOR"))
((PLOC_UPDATER, 0x44330000, "PLOC_UPDATER"))
((PLOC_MEMORY_DUMPER, 0x44330001, "PLOC_MEMORY_DUMPER"))
((STR_HELPER, 0x44330002, "STR_HELPER"))
((PLOC_MPSOC_HELPER, 0x44330003, "PLOC_MPSOC_HELPER"))
((AXI_PTME_CONFIG, 0x44330004, "AXI_PTME_CONFIG"))
((PTME_CONFIG, 0x44330005, "PTME_CONFIG"))
((PLOC_MPSOC_HANDLER, 0x44330015, "PLOC_MPSOC_HANDLER"))
((PLOC_SUPERVISOR_HANDLER, 0x44330016, "PLOC_SUPERVISOR_HANDLER"))
((PLOC_SUPERVISOR_HELPER, 0x44330017, "PLOC_SUPERVISOR_HELPER"))
((SOLAR_ARRAY_DEPL_HANDLER, 0x444100A2, "SOLAR_ARRAY_DEPL_HANDLER"))
((HEATER_HANDLER, 0x444100A4, "HEATER_HANDLER"))
/**
* Not yet specified which pt1000 will measure which device/location in the satellite.
* Therefore object ids are named according to the IC naming of the RTDs in the schematic.
*/
RTD_0_IC3_PLOC_HEATSPREADER = 0x44420016,
RTD_1_IC4_PLOC_MISSIONBOARD = 0x44420017,
RTD_2_IC5_4K_CAMERA = 0x44420018,
RTD_3_IC6_DAC_HEATSPREADER = 0x44420019,
RTD_4_IC7_STARTRACKER = 0x44420020,
RTD_5_IC8_RW1_MX_MY = 0x44420021,
RTD_6_IC9_DRO = 0x44420022,
RTD_7_IC10_SCEX = 0x44420023,
RTD_8_IC11_X8 = 0x44420024,
RTD_9_IC12_HPA = 0x44420025,
RTD_10_IC13_PL_TX = 0x44420026,
RTD_11_IC14_MPA = 0x44420027,
RTD_12_IC15_ACU = 0x44420028,
RTD_13_IC16_PLPCDU_HEATSPREADER = 0x44420029,
RTD_14_IC17_TCS_BOARD = 0x44420030,
RTD_15_IC18_IMTQ = 0x44420031,
((RTD_0_IC3_PLOC_HEATSPREADER, 0x44420016, "RTD_0_IC3_PLOC_HEATSPREADER"))
((RTD_1_IC4_PLOC_MISSIONBOARD, 0x44420017, "RTD_1_IC4_PLOC_MISSIONBOARD"))
((RTD_2_IC5_4K_CAMERA, 0x44420018, "RTD_2_IC5_4K_CAMERA"))
((RTD_3_IC6_DAC_HEATSPREADER, 0x44420019, "RTD_3_IC6_DAC_HEATSPREADER"))
((RTD_4_IC7_STARTRACKER, 0x44420020, "RTD_4_IC7_STARTRACKER"))
((RTD_5_IC8_RW1_MX_MY, 0x44420021, "RTD_5_IC8_RW1_MX_MY"))
((RTD_6_IC9_DRO, 0x44420022, "RTD_6_IC9_DRO"))
((RTD_7_IC10_SCEX, 0x44420023, "RTD_7_IC10_SCEX"))
((RTD_8_IC11_X8, 0x44420024, "RTD_8_IC11_X8"))
((RTD_9_IC12_HPA, 0x44420025, "RTD_9_IC12_HPA"))
((RTD_10_IC13_PL_TX, 0x44420026, "RTD_10_IC13_PL_TX"))
((RTD_11_IC14_MPA, 0x44420027, "RTD_11_IC14_MPA"))
((RTD_12_IC15_ACU, 0x44420028, "RTD_12_IC15_ACU"))
((RTD_13_IC16_PLPCDU_HEATSPREADER, 0x44420029, "RTD_13_IC16_PLPCDU_HEATSPREADER"))
((RTD_14_IC17_TCS_BOARD, 0x44420030, "RTD_14_IC17_TCS_BOARD"))
((RTD_15_IC18_IMTQ, 0x44420031, "RTD_15_IC18_IMTQ"))
// Name convention for SUS devices
// SUS_<IDX>_<N/R>_LOC_X<F/M/B>Y<F/M/B>Z<F/M/B>_PT_<DIR><F/B>
@ -87,42 +89,42 @@ enum commonObjects : uint32_t {
// PT: Pointing
// N/R: Nominal/Redundant
// F/M/B: Forward/Middle/Backwards
SUS_0_N_LOC_XFYFZM_PT_XF = 0x44120032,
SUS_6_R_LOC_XFYBZM_PT_XF = 0x44120038,
((SUS_0_N_LOC_XFYFZM_PT_XF, 0x44120032, "SUS_0_N_LOC_XFYFZM_PT_XF"))
((SUS_6_R_LOC_XFYBZM_PT_XF, 0x44120038, "SUS_6_R_LOC_XFYBZM_PT_XF"))
SUS_1_N_LOC_XBYFZM_PT_XB = 0x44120033,
SUS_7_R_LOC_XBYBZM_PT_XB = 0x44120039,
((SUS_1_N_LOC_XBYFZM_PT_XB, 0x44120033, "SUS_1_N_LOC_XBYFZM_PT_XB"))
((SUS_7_R_LOC_XBYBZM_PT_XB, 0x44120039, "SUS_7_R_LOC_XBYBZM_PT_XB"))
SUS_2_N_LOC_XFYBZB_PT_YB = 0x44120034,
SUS_8_R_LOC_XBYBZB_PT_YB = 0x44120040,
((SUS_2_N_LOC_XFYBZB_PT_YB, 0x44120034, "SUS_2_N_LOC_XFYBZB_PT_YB"))
((SUS_8_R_LOC_XBYBZB_PT_YB, 0x44120040, "SUS_8_R_LOC_XBYBZB_PT_YB"))
SUS_3_N_LOC_XFYBZF_PT_YF = 0x44120035,
SUS_9_R_LOC_XBYBZB_PT_YF = 0x44120041,
((SUS_3_N_LOC_XFYBZF_PT_YF, 0x44120035, "SUS_3_N_LOC_XFYBZF_PT_YF"))
((SUS_9_R_LOC_XBYBZB_PT_YF, 0x44120041, "SUS_9_R_LOC_XBYBZB_PT_YF"))
SUS_4_N_LOC_XMYFZF_PT_ZF = 0x44120036,
SUS_10_N_LOC_XMYBZF_PT_ZF = 0x44120042,
((SUS_4_N_LOC_XMYFZF_PT_ZF, 0x44120036, "SUS_4_N_LOC_XMYFZF_PT_ZF"))
((SUS_10_N_LOC_XMYBZF_PT_ZF, 0x44120042, "SUS_10_N_LOC_XMYBZF_PT_ZF"))
SUS_5_N_LOC_XFYMZB_PT_ZB = 0x44120037,
SUS_11_R_LOC_XBYMZB_PT_ZB = 0x44120043,
((SUS_5_N_LOC_XFYMZB_PT_ZB, 0x44120037, "SUS_5_N_LOC_XFYMZB_PT_ZB"))
((SUS_11_R_LOC_XBYMZB_PT_ZB, 0x44120043, "SUS_11_R_LOC_XBYMZB_PT_ZB"))
SYRLINKS_HK_HANDLER = 0x445300A3,
((SYRLINKS_HK_HANDLER, 0x445300A3, "SYRLINKS_HK_HANDLER"))
// 0x60 for other stuff
HEATER_0_PLOC_PROC_BRD = 0x60000000,
HEATER_1_PCDU_BRD = 0x60000001,
HEATER_2_ACS_BRD = 0x60000002,
HEATER_3_OBC_BRD = 0x60000003,
HEATER_4_CAMERA = 0x60000004,
HEATER_5_STR = 0x60000005,
HEATER_6_DRO = 0x60000006,
HEATER_7_HPA = 0x60000007,
((HEATER_0_PLOC_PROC_BRD, 0x60000000, "HEATER_0_PLOC_PROC_BRD"))
((HEATER_1_PCDU_BRD, 0x60000001, "HEATER_1_PCDU_BRD"))
((HEATER_2_ACS_BRD, 0x60000002, "HEATER_2_ACS_BRD"))
((HEATER_3_OBC_BRD, 0x60000003, "HEATER_3_OBC_BRD"))
((HEATER_4_CAMERA, 0x60000004, "HEATER_4_CAMERA"))
((HEATER_5_STR, 0x60000005, "HEATER_5_STR"))
((HEATER_6_DRO, 0x60000006, "HEATER_6_DRO"))
((HEATER_7_HPA, 0x60000007, "HEATER_7_HPA"))
// 0x73 ('s') for assemblies and system/subsystem components
ACS_BOARD_ASS = 0x73000001,
SUS_BOARD_ASS = 0x73000002,
TCS_BOARD_ASS = 0x73000003,
RW_ASS = 0x73000004
};
((ACS_BOARD_ASS, 0x73000001, "ACS_BOARD_ASS"))
((SUS_BOARD_ASS, 0x73000002, "SUS_BOARD_ASS"))
((TCS_BOARD_ASS, 0x73000003, "TCS_BOARD_ASS"))
((RW_ASS, 0x73000004, "RW_ASS"))
)
}
#endif /* COMMON_CONFIG_COMMONOBJECTS_H_ */

2
fsfw

@ -1 +1 @@
Subproject commit d975958120bd151dabdc450a104e9cc8069ff509
Subproject commit 383bafe3446a832edc466d850c637ea879fa1934

View File

@ -1,7 +1,7 @@
add_subdirectory(csp)
add_subdirectory(utility)
add_subdirectory(callbacks)
add_subdirectory(boardtest)
#add_subdirectory(boardtest)
add_subdirectory(devices)
add_subdirectory(fsfwconfig)
add_subdirectory(obc)

View File

@ -53,22 +53,24 @@ ReturnValue_t GPSHyperionLinuxController::checkModeCommand(Mode_t mode, Submode_
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GPSHyperionLinuxController::executeAction(ActionId_t actionId,
MessageQueueId_t commandedBy,
const uint8_t *data, size_t size) {
switch (actionId) {
case (GpsHyperion::TRIGGER_RESET_PIN_GNSS): {
if (resetCallback != nullptr) {
PoolReadGuard pg(&gpsSet);
// Set HK entries invalid
gpsSet.setValidity(false, true);
resetCallback(data, size, resetCallbackArgs);
return HasActionsIF::EXECUTION_FINISHED;
}
return DeviceHandlerIF::COMMAND_NOT_IMPLEMENTED;
}
ModeDefinitionHelper GPSHyperionLinuxController::getModeDefinitionHelper() {
//TODO verify which modes are supported
return ModeDefinitionHelper::create<ControllerModes, DefaultSubmode>();
}
ReturnValue_t GPSHyperionLinuxController::executeAction(Action *action) {
return action->handle();
}
ReturnValue_t GPSHyperionLinuxController::handleAction(GPSHyperionLinuxAction * action) {
if (resetCallback != nullptr) {
PoolReadGuard pg(&gpsSet);
// Set HK entries invalid
gpsSet.setValidity(false, true);
resetCallback(static_cast<uint8_t>(action->gpsId.value), resetCallbackArgs);
return HasActionsIF::EXECUTION_FINISHED;
}
return HasReturnvaluesIF::RETURN_OK;
return DeviceHandlerIF::COMMAND_NOT_IMPLEMENTED;
}
ReturnValue_t GPSHyperionLinuxController::initializeLocalDataPool(

View File

@ -2,10 +2,11 @@
#define MISSION_DEVICES_GPSHYPERIONHANDLER_H_
#include "commonSubsystemIds.h"
#include "devicedefinitions/GPSHyperionLinuxDefinitions.h"
#include "fsfw/FSFW.h"
#include "fsfw/controller/ExtendedControllerBase.h"
#include "fsfw/devicehandlers/DeviceHandlerBase.h"
#include "mission/devices/devicedefinitions/GPSDefinitions.h"
#ifdef FSFW_OSAL_LINUX
#include <gps.h>
@ -30,7 +31,7 @@ class GPSHyperionLinuxController : public ExtendedControllerBase {
bool debugHyperionGps = false);
virtual ~GPSHyperionLinuxController();
using gpioResetFunction_t = ReturnValue_t (*)(const uint8_t* actionData, size_t len, void* args);
using gpioResetFunction_t = ReturnValue_t (*)(uint8_t gpsId, void* args);
void setResetPinTriggerFunction(gpioResetFunction_t resetCallback, void* args);
ReturnValue_t handleCommandMessage(CommandMessage* message) override;
@ -38,8 +39,9 @@ class GPSHyperionLinuxController : public ExtendedControllerBase {
LocalPoolDataSetBase* getDataSetHandle(sid_t sid) override;
ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode,
uint32_t* msToReachTheMode) override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ModeDefinitionHelper getModeDefinitionHelper() override;
ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(GPSHyperionLinuxAction * action);
ReturnValue_t initialize() override;
protected:
@ -65,6 +67,7 @@ class GPSHyperionLinuxController : public ExtendedControllerBase {
int32_t noModeSetCntr = 0;
uint32_t timeIsConstantCounter = 0;
Countdown timeUpdateCd = Countdown(60);
GPSHyperionLinuxAction action = GPSHyperionLinuxAction(this);
void readGpsDataFromGpsd();
};

View File

@ -0,0 +1,23 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include "mission/devices/devicedefinitions/GPSDefinitions.h"
class GPSHyperionLinuxController;
FSFW_ENUM(GPSHyperionLinuxCommands, DeviceCommandId_t,
((TRIGGER_RESET_PIN_GNSS, GpsHyperion::TRIGGER_RESET_PIN_GNSS, "Trigger Reset Pin")))
class GPSHyperionLinuxAction
: public TemplateAction<GPSHyperionLinuxController, GPSHyperionLinuxAction,
GPSHyperionLinuxCommands> {
public:
FSFW_ENUM(GpsIDs, uint8_t, ((GPS_0, 0, "GPS 0"))((GPS_1, 1, "GPS 1")))
GPSHyperionLinuxAction(GPSHyperionLinuxController *owner)
: TemplateAction(owner, GPSHyperionLinuxCommands::TRIGGER_RESET_PIN_GNSS){};
Parameter<GpsIDs> gpsId = Parameter<GpsIDs>::createParameter(this, "GPS ID");
};

View File

@ -0,0 +1,646 @@
#ifndef MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCCOMMONDEFINITIONS_H_
#define MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCCOMMONDEFINITIONS_H_
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include "MPSoCReturnValuesIF.h"
#include "OBSWConfig.h"
#include "eive/definitions.h"
#include "fsfw/globalfunctions/CRC.h"
#include "fsfw/serialize/SerializeAdapter.h"
#include "fsfw/tmtcpacket/SpacePacket.h"
namespace mpsoc {
static const uint16_t SIZE_ACK_REPORT = 14;
static const uint16_t SIZE_EXE_REPORT = 14;
static const uint16_t SIZE_TM_MEM_READ_REPORT = 18;
static const uint16_t SIZE_TM_CAM_CMD_RPT = 18;
/**
* SpacePacket apids of PLOC telecommands and telemetry.
*/
namespace apid {
static const uint16_t TC_REPLAY_START = 0x110;
static const uint16_t TC_REPLAY_STOP = 0x111;
static const uint16_t TC_REPLAY_WRITE_SEQUENCE = 0x112;
static const uint16_t TC_DOWNLINK_PWR_ON = 0x113;
static const uint16_t TC_MEM_WRITE = 0x114;
static const uint16_t TC_MEM_READ = 0x115;
static const uint16_t TC_FLASHWRITE = 0x117;
static const uint16_t TC_FLASHFOPEN = 0x119;
static const uint16_t TC_FLASHFCLOSE = 0x11A;
static const uint16_t TC_FLASHDELETE = 0x11C;
static const uint16_t TC_MODE_REPLAY = 0x11F;
static const uint16_t TC_MODE_IDLE = 0x11E;
static const uint16_t TC_DOWNLINK_PWR_OFF = 0x124;
static const uint16_t TC_CAM_CMD_SEND = 0x12C;
static const uint16_t TM_MEMORY_READ_REPORT = 0x404;
static const uint16_t ACK_SUCCESS = 0x400;
static const uint16_t ACK_FAILURE = 0x401;
static const uint16_t EXE_SUCCESS = 0x402;
static const uint16_t EXE_FAILURE = 0x403;
static const uint16_t TM_CAM_CMD_RPT = 0x407;
} // namespace apid
/** Offset from first byte in space packet to first byte of data field */
static const uint8_t DATA_FIELD_OFFSET = 6;
static const size_t MEM_READ_RPT_LEN_OFFSET = 10;
static const char NULL_TERMINATOR = '\0';
static const uint8_t MIN_SPACE_PACKET_LENGTH = 7;
static const uint8_t SPACE_PACKET_HEADER_SIZE = 6;
/**
* The size of payload data which will be forwarded to the requesting object. e.g. PUS Service
* 8.
*/
static const uint8_t SIZE_MEM_READ_RPT_FIX = 6;
static const size_t MAX_FILENAME_SIZE = 256;
/**
* PLOC space packet length for fixed size packets. This is the size of the whole packet data
* field. For the length field in the space packet this size will be substracted by one.
*/
static const uint16_t LENGTH_TC_MEM_WRITE = 12;
static const uint16_t LENGTH_TC_MEM_READ = 8;
static const size_t MAX_REPLY_SIZE = SpacePacket::PACKET_MAX_SIZE * 3;
static const size_t MAX_COMMAND_SIZE = SpacePacket::PACKET_MAX_SIZE;
static const size_t MAX_DATA_SIZE = 1016;
/**
* The replay write sequence command has a maximum delay for the execution report which amounts to
* 30 seconds. (80 cycles * 0.5 seconds = 40 seconds).
*/
static const uint16_t TC_WRITE_SEQ_EXECUTION_DELAY = 80;
// Requires approx. 2 seconds for execution. 8 => 4 seconds
static const uint16_t TC_DOWNLINK_PWR_ON_EXECUTION_DELAY = 8;
namespace status_code {
static const uint16_t UNKNOWN_APID = 0x5DD;
static const uint16_t INCORRECT_LENGTH = 0x5DE;
static const uint16_t INCORRECT_CRC = 0x5DF;
static const uint16_t INCORRECT_PKT_SEQ_CNT = 0x5E0;
static const uint16_t TC_NOT_ALLOWED_IN_MODE = 0x5E1;
static const uint16_t TC_EXEUTION_DISABLED = 0x5E2;
static const uint16_t FLASH_MOUNT_FAILED = 0x5E3;
static const uint16_t FLASH_FILE_ALREADY_CLOSED = 0x5E4;
static const uint16_t FLASH_FILE_OPEN_FAILED = 0x5E5;
static const uint16_t FLASH_FILE_ALREDY_OPEN = 0x5E6;
static const uint16_t FLASH_FILE_NOT_OPEN = 0x5E7;
static const uint16_t FLASH_UNMOUNT_FAILED = 0x5E8;
static const uint16_t HEAP_ALLOCATION_FAILED = 0x5E9;
static const uint16_t INVALID_PARAMETER = 0x5EA;
static const uint16_t NOT_INITIALIZED = 0x5EB;
static const uint16_t REBOOT_IMMINENT = 0x5EC;
static const uint16_t CORRUPT_DATA = 0x5ED;
static const uint16_t FLASH_CORRECTABLE_MISMATCH = 0x5EE;
static const uint16_t FLASH_UNCORRECTABLE_MISMATCH = 0x5EF;
static const uint16_t RESERVED_0 = 0x5F0;
static const uint16_t RESERVED_1 = 0x5F1;
static const uint16_t RESERVED_2 = 0x5F2;
static const uint16_t RESERVED_3 = 0x5F3;
static const uint16_t RESERVED_4 = 0x5F4;
} // namespace status_code
/**
* @brief Abstract base class for TC space packet of MPSoC.
*/
class TcBase : public SpacePacket, public MPSoCReturnValuesIF {
public:
// Initial length field of space packet. Will always be updated when packet is created.
static const uint16_t INIT_LENGTH = 1;
/**
* @brief Constructor
*
* @param sequenceCount Sequence count of space packet which will be incremented with each
* sent and received packets.
*/
TcBase(uint16_t apid, uint16_t sequenceCount)
: SpacePacket(INIT_LENGTH, true, apid, sequenceCount) {}
/**
* @brief Function to initialize the space packet
*
* @param commandData Pointer to command specific data
* @param commandDataLen Length of command data
*
* @return RETURN_OK if packet creation was successful, otherwise error return value
*/
virtual ReturnValue_t createPacket(void *action) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = initPacket(action);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
protected:
/**
* @brief Must be overwritten by the child class to define the command specific parameters
*
* @param commandData Pointer to received command data
* @param commandDataLen Length of received command data
*/
virtual ReturnValue_t initPacket(void *action) {
return HasReturnvaluesIF::RETURN_OK;
}
/**
* @brief Calculates and adds the CRC
*/
ReturnValue_t addCrc() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t serializedSize = 0;
uint32_t full_size = getFullSize();
uint16_t crc = CRC::crc16ccitt(getWholeData(), full_size - CRC_SIZE);
result = SerializeAdapter::serialize<uint16_t>(
&crc, this->localData.byteStream + full_size - CRC_SIZE, &serializedSize, sizeof(crc),
SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
sif::debug << "TcBase::addCrc: Failed to serialize crc field" << std::endl;
}
return result;
}
};
/**
* @brief Class for handling tm replies of the PLOC MPSoC.
*/
class TmPacket : public SpacePacket, public MPSoCReturnValuesIF {
public:
/**
* @brief Constructor creates idle packet and sets length field to maximum allowed size.
*/
TmPacket() : SpacePacket(PACKET_MAX_SIZE) {}
ReturnValue_t checkCrc() {
uint8_t *crcPtr = this->getPacketData() + this->getPacketDataLength() - 1;
uint16_t receivedCrc = *(crcPtr) << 8 | *(crcPtr + 1);
uint16_t recalculatedCrc =
CRC::crc16ccitt(this->localData.byteStream, this->getFullSize() - CRC_SIZE);
if (recalculatedCrc != receivedCrc) {
return CRC_FAILURE;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the memory read command for the PLOC.
*/
class TcMemRead : public TcBase {
public:
/**
* @brief Constructor
*/
TcMemRead(uint16_t sequenceCount) : TcBase(apid::TC_MEM_READ, sequenceCount) {
this->setPacketDataLength(PACKET_LENGTH);
}
uint16_t getMemLen() const { return memLen; }
protected:
ReturnValue_t initPacket(const uint8_t *commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, MEM_ADDRESS_SIZE);
std::memcpy(this->localData.fields.buffer + MEM_ADDRESS_SIZE, commandData + MEM_ADDRESS_SIZE,
MEM_LEN_SIZE);
size_t size = sizeof(memLen);
const uint8_t *memLenPtr = commandData + MEM_ADDRESS_SIZE;
result =
SerializeAdapter::deSerialize(&memLen, &memLenPtr, &size, SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
private:
static const size_t COMMAND_LENGTH = 6;
static const size_t MEM_ADDRESS_SIZE = 4;
static const size_t MEM_LEN_SIZE = 2;
static const uint16_t PACKET_LENGTH = 7;
uint16_t memLen = 0;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_LENGTH) {
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to help creation of flash fopen command.
*/
class FlashFopen : public TcBase {
public:
FlashFopen(uint16_t sequenceCount) : TcBase(apid::TC_FLASHFOPEN, sequenceCount) {}
static const char APPEND = 'a';
static const char WRITE = 'w';
static const char READ = 'r';
ReturnValue_t createPacket(std::string filename, char accessMode_) {
accessMode = accessMode_;
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
std::memcpy(this->getPacketData() + nameSize + sizeof(NULL_TERMINATOR), &accessMode,
sizeof(accessMode));
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + sizeof(accessMode) + CRC_SIZE -
1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
private:
char accessMode = APPEND;
};
/**
* @brief Class to help creation of flash fclose command.
*/
class FlashFclose : public TcBase {
public:
FlashFclose(uint16_t sequenceCount) : TcBase(apid::TC_FLASHFCLOSE, sequenceCount) {}
ReturnValue_t createPacket(std::string filename) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
};
/**
* @brief Class to build flash write space packet.
*/
class TcFlashWrite : public TcBase {
public:
TcFlashWrite(uint16_t sequenceCount) : TcBase(apid::TC_FLASHWRITE, sequenceCount) {}
ReturnValue_t createPacket(const uint8_t *writeData, uint32_t writeLen_) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
writeLen = writeLen_;
if (writeLen > MAX_DATA_SIZE) {
sif::debug << "FlashWrite::createPacket: Command data too big" << std::endl;
return HasReturnvaluesIF::RETURN_FAILED;
}
size_t serializedSize = 0;
result =
SerializeAdapter::serialize<uint32_t>(&writeLen, this->getPacketData(), &serializedSize,
sizeof(writeLen), SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->getPacketData() + sizeof(writeLen), writeData, writeLen);
this->setPacketDataLength(static_cast<uint16_t>(writeLen + CRC_SIZE - 1));
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return HasReturnvaluesIF::RETURN_OK;
}
private:
uint32_t writeLen = 0;
};
/**
* @brief Class to help creation of flash delete command.
*/
class TcFlashDelete : public TcBase {
public:
TcFlashDelete(uint16_t sequenceCount) : TcBase(apid::TC_FLASHDELETE, sequenceCount) {}
ReturnValue_t createPacket(std::string filename) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
};
/**
* @brief Class to build replay stop space packet.
*/
class TcReplayStop : public TcBase {
public:
TcReplayStop(uint16_t sequenceCount) : TcBase(apid::TC_REPLAY_STOP, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the replay start command.
*/
class TcReplayStart : public TcBase {
public:
/**
* @brief Constructor
*/
TcReplayStart(uint16_t sequenceCount) : TcBase(apid::TC_REPLAY_START, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t *commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = checkData(*commandData);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
this->setPacketDataLength(commandDataLen + CRC_SIZE - 1);
return result;
}
private:
static const size_t COMMAND_DATA_LENGTH = 1;
static const uint8_t REPEATING = 0;
static const uint8_t ONCE = 1;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_DATA_LENGTH) {
sif::warning << "TcReplayStart: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t checkData(uint8_t replay) {
if (replay != REPEATING && replay != ONCE) {
sif::warning << "TcReplayStart::checkData: Invalid replay value" << std::endl;
return INVALID_PARAMETER;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build downlink power on command.
*/
class TcDownlinkPwrOn : public TcBase {
public:
/**
* @brief Constructor
*/
TcDownlinkPwrOn(uint16_t sequenceCount) : TcBase(apid::TC_DOWNLINK_PWR_ON, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t *commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = modeCheck(*commandData);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = laneRateCheck(*(commandData + 1));
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
std::memcpy(this->localData.fields.buffer + commandDataLen, &MAX_AMPLITUDE,
sizeof(MAX_AMPLITUDE));
this->setPacketDataLength(commandDataLen + sizeof(MAX_AMPLITUDE) + CRC_SIZE - 1);
return result;
}
private:
static const uint8_t INTERFACE_ID = CLASS_ID::DWLPWRON_CMD;
//! [EXPORT] : [COMMENT] Received command has invalid JESD mode (valid modes are 0 - 5)
static const ReturnValue_t INVALID_MODE = MAKE_RETURN_CODE(0xE0);
//! [EXPORT] : [COMMENT] Received command has invalid lane rate (valid lane rate are 0 - 9)
static const ReturnValue_t INVALID_LANE_RATE = MAKE_RETURN_CODE(0xE1);
static const size_t COMMAND_DATA_LENGTH = 2;
static const uint8_t MAX_MODE = 5;
static const uint8_t MAX_LANE_RATE = 9;
static const uint16_t MAX_AMPLITUDE = 0;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_DATA_LENGTH) {
sif::warning << "TcDownlinkPwrOn: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t modeCheck(uint8_t mode) {
if (mode > MAX_MODE) {
sif::warning << "TcDwonlinkPwrOn::modeCheck: Invalid JESD mode" << std::endl;
return INVALID_MODE;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t laneRateCheck(uint8_t laneRate) {
if (laneRate > MAX_LANE_RATE) {
sif::warning << "TcReplayStart::laneRateCheck: Invalid lane rate" << std::endl;
return INVALID_LANE_RATE;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to build replay stop space packet.
*/
class TcDownlinkPwrOff : public TcBase {
public:
TcDownlinkPwrOff(uint16_t sequenceCount) : TcBase(apid::TC_DOWNLINK_PWR_OFF, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the replay start command.
*/
class TcReplayWriteSeq : public TcBase {
public:
/**
* @brief Constructor
*/
TcReplayWriteSeq(uint16_t sequenceCount)
: TcBase(apid::TC_REPLAY_WRITE_SEQUENCE, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t *commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
*(this->localData.fields.buffer + commandDataLen) = NULL_TERMINATOR;
this->setPacketDataLength(commandDataLen + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
return result;
}
private:
static const size_t USE_DECODING_LENGTH = 1;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen > USE_DECODING_LENGTH + MAX_FILENAME_SIZE) {
sif::warning << "TcReplayWriteSeq: Command has invalid length " << commandDataLen
<< std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Helps to extract the fields of the flash write command from the PUS packet.
*/
class FlashWritePusCmd : public MPSoCReturnValuesIF {
public:
FlashWritePusCmd(){};
ReturnValue_t extractFields(const uint8_t *commandData, size_t commandDataLen) {
if (commandDataLen > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE + MAX_FILENAME_SIZE)) {
return INVALID_LENGTH;
}
obcFile = std::string(reinterpret_cast<const char *>(commandData));
if (obcFile.size() > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE)) {
return FILENAME_TOO_LONG;
}
mpsocFile = std::string(
reinterpret_cast<const char *>(commandData + obcFile.size() + SIZE_NULL_TERMINATOR));
if (mpsocFile.size() > MAX_FILENAME_SIZE) {
return MPSOC_FILENAME_TOO_LONG;
}
return HasReturnvaluesIF::RETURN_OK;
}
std::string getObcFile() { return obcFile; }
std::string getMPSoCFile() { return mpsocFile; }
private:
static const size_t SIZE_NULL_TERMINATOR = 1;
std::string obcFile = "";
std::string mpsocFile = "";
};
/**
* @brief Class to build replay stop space packet.
*/
class TcModeReplay : public TcBase {
public:
TcModeReplay(uint16_t sequenceCount) : TcBase(apid::TC_MODE_REPLAY, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to build mode idle command
*/
class TcModeIdle : public TcBase {
public:
TcModeIdle(uint16_t sequenceCount) : TcBase(apid::TC_MODE_IDLE, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
class TcCamcmdSend : public TcBase {
public:
TcCamcmdSend(uint16_t sequenceCount) : TcBase(apid::TC_CAM_CMD_SEND, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t *commandData, size_t commandDataLen) {
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
uint16_t dataLen = static_cast<uint16_t>(commandDataLen + sizeof(CARRIAGE_RETURN));
size_t size = sizeof(dataLen);
SerializeAdapter::serialize(&dataLen, this->getPacketData(), &size, sizeof(dataLen),
SerializeIF::Endianness::BIG);
std::memcpy(this->getPacketData() + sizeof(dataLen), commandData, commandDataLen);
*(this->getPacketData() + sizeof(dataLen) + commandDataLen) = CARRIAGE_RETURN;
uint16_t trueLength = sizeof(dataLen) + commandDataLen + sizeof(CARRIAGE_RETURN) + CRC_SIZE;
this->setPacketDataLength(trueLength - 1);
return HasReturnvaluesIF::RETURN_OK;
}
private:
static const uint8_t MAX_DATA_LENGTH = 10;
static const uint8_t CARRIAGE_RETURN = 0xD;
};
} // namespace mpsoc
#endif /* MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCCOMMONDEFINITIONS_H_ */

View File

@ -1,271 +1,146 @@
#ifndef MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_
#define MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include "MPSoCReturnValuesIF.h"
#include "OBSWConfig.h"
#include "PlocMPSoCCommonDefinitions.h"
#include "eive/definitions.h"
#include "fsfw/globalfunctions/CRC.h"
#include "fsfw/serialize/SerializeAdapter.h"
#include "fsfw/tmtcpacket/SpacePacket.h"
class PlocMPSoCHandler;
FSFW_ENUM(PlocMpSoCCommands, DeviceCommandId_t,
((NONE, 0, "No Command"))((TC_MEM_WRITE, 1, "Write to Memory"))(
(TC_MEM_READ, 2, "Read from Memory"))((ACK_REPORT, 3, ""))((EXE_REPORT, 5, ""))(
(TM_MEMORY_READ_REPORT, 6, ""))((TC_FLASHWRITE, 9, "Write Flash"))(
(TC_FLASHDELETE, 10, "Delete Flash"))((TC_REPLAY_START, 11, "Start Replay"))(
(TC_REPLAY_STOP, 12, "Stop Replay"))((TC_REPLAY_WRITE_SEQUENCE, 13,
"Write Sequence"))((TC_DOWNLINK_PWR_ON, 14,
"Set Downlink Power On"))(
(TC_DOWNLINK_PWR_OFF, 15, "Set Downlink Power Off"))((TC_MODE_REPLAY, 16,
"Set Replay Mode"))(
(TC_CAM_CMD_SEND, 17, "Set Replay Mode"))((TC_MODE_IDLE, 18, "Set Idle Mode"))(
(TM_CAM_CMD_RPT, 19, ""))((SET_UART_TX_TRISTATE, 20, "Set UART TX to Tristate"))(
(RELEASE_UART_TX, 21, "Release UART TX"))((OBSW_RESET_SEQ_COUNT, 50,
"Reset OBSW Reset Sequence Count")))
class PlocMpSoCMemWriteAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCMemWriteAction, PlocMpSoCCommands> {
public:
PlocMpSoCMemWriteAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_MEM_WRITE){};
Parameter<uint32_t> address = Parameter<uint32_t>::createParameter(this, "Memory Address");
Parameter<uint32_t> memoryData = Parameter<uint32_t>::createParameter(this, "Data to be written");
};
class PlocMpSoCMemReadAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCMemReadAction, PlocMpSoCCommands> {
public:
PlocMpSoCMemReadAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_MEM_READ){};
};
class PlocMpSoCFlashDeleteAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCFlashDeleteAction, PlocMpSoCCommands> {
public:
PlocMpSoCFlashDeleteAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_FLASHDELETE){};
};
class PlocMpSoCReplayStartAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCReplayStartAction, PlocMpSoCCommands> {
public:
PlocMpSoCReplayStartAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_REPLAY_START){};
};
class PlocMpSoCReplayStopAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCReplayStopAction, PlocMpSoCCommands> {
public:
PlocMpSoCReplayStopAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_REPLAY_STOP){};
};
class PlocMpSoCReplayWriteSequenceAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCReplayWriteSequenceAction,
PlocMpSoCCommands> {
public:
PlocMpSoCReplayWriteSequenceAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_REPLAY_WRITE_SEQUENCE){};
};
class PlocMpSoCDownlinkPwrOnAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCDownlinkPwrOnAction, PlocMpSoCCommands> {
public:
PlocMpSoCDownlinkPwrOnAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_DOWNLINK_PWR_ON){};
};
class PlocMpSoCDownlinkPwrOffAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCDownlinkPwrOffAction, PlocMpSoCCommands> {
public:
PlocMpSoCDownlinkPwrOffAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_DOWNLINK_PWR_OFF){};
};
class PlocMpSoCModeReplayAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCModeReplayAction, PlocMpSoCCommands> {
public:
PlocMpSoCModeReplayAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_MODE_REPLAY){};
};
class PlocMpSoCCamCmdSendAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCCamCmdSendAction, PlocMpSoCCommands> {
public:
PlocMpSoCCamCmdSendAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_CAM_CMD_SEND){};
};
class PlocMpSoCModeIdleAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCModeIdleAction, PlocMpSoCCommands> {
public:
PlocMpSoCModeIdleAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_MODE_IDLE){};
};
class PlocMpSoCFlashWriteAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCFlashWriteAction, PlocMpSoCCommands> {
public:
PlocMpSoCFlashWriteAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::TC_FLASHWRITE){};
};
class PlocMpSoCUartTxTristateAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCUartTxTristateAction, PlocMpSoCCommands> {
public:
PlocMpSoCUartTxTristateAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::SET_UART_TX_TRISTATE){};
};
class PlocMpSoCReleaseUartTxAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCReleaseUartTxAction, PlocMpSoCCommands> {
public:
PlocMpSoCReleaseUartTxAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::RELEASE_UART_TX){};
};
class PlocMpSoCObswResetSeqCountAction
: public TemplateAction<PlocMPSoCHandler, PlocMpSoCObswResetSeqCountAction, PlocMpSoCCommands> {
public:
PlocMpSoCObswResetSeqCountAction(PlocMPSoCHandler *owner)
: TemplateAction(owner, PlocMpSoCCommands::OBSW_RESET_SEQ_COUNT){};
};
namespace mpsoc {
static const DeviceCommandId_t NONE = 0;
static const DeviceCommandId_t TC_MEM_WRITE = 1;
static const DeviceCommandId_t TC_MEM_READ = 2;
static const DeviceCommandId_t ACK_REPORT = 3;
static const DeviceCommandId_t EXE_REPORT = 5;
static const DeviceCommandId_t TM_MEMORY_READ_REPORT = 6;
static const DeviceCommandId_t TC_FLASHFOPEN = 7;
static const DeviceCommandId_t TC_FLASHFCLOSE = 8;
static const DeviceCommandId_t TC_FLASHWRITE = 9;
static const DeviceCommandId_t TC_FLASHDELETE = 10;
static const DeviceCommandId_t TC_REPLAY_START = 11;
static const DeviceCommandId_t TC_REPLAY_STOP = 12;
static const DeviceCommandId_t TC_REPLAY_WRITE_SEQUENCE = 13;
static const DeviceCommandId_t TC_DOWNLINK_PWR_ON = 14;
static const DeviceCommandId_t TC_DOWNLINK_PWR_OFF = 15;
static const DeviceCommandId_t TC_MODE_REPLAY = 16;
static const DeviceCommandId_t TC_CAM_CMD_SEND = 17;
static const DeviceCommandId_t TC_MODE_IDLE = 18;
static const DeviceCommandId_t TM_CAM_CMD_RPT = 19;
static const DeviceCommandId_t SET_UART_TX_TRISTATE = 20;
static const DeviceCommandId_t RELEASE_UART_TX = 21;
// Will reset the sequence count of the OBSW
static const DeviceCommandId_t OBSW_RESET_SEQ_COUNT = 50;
static const uint16_t SIZE_ACK_REPORT = 14;
static const uint16_t SIZE_EXE_REPORT = 14;
static const uint16_t SIZE_TM_MEM_READ_REPORT = 18;
static const uint16_t SIZE_TM_CAM_CMD_RPT = 18;
/**
* SpacePacket apids of PLOC telecommands and telemetry.
*/
namespace apid {
static const uint16_t TC_REPLAY_START = 0x110;
static const uint16_t TC_REPLAY_STOP = 0x111;
static const uint16_t TC_REPLAY_WRITE_SEQUENCE = 0x112;
static const uint16_t TC_DOWNLINK_PWR_ON = 0x113;
static const uint16_t TC_MEM_WRITE = 0x114;
static const uint16_t TC_MEM_READ = 0x115;
static const uint16_t TC_FLASHWRITE = 0x117;
static const uint16_t TC_FLASHFOPEN = 0x119;
static const uint16_t TC_FLASHFCLOSE = 0x11A;
static const uint16_t TC_FLASHDELETE = 0x11C;
static const uint16_t TC_MODE_REPLAY = 0x11F;
static const uint16_t TC_MODE_IDLE = 0x11E;
static const uint16_t TC_DOWNLINK_PWR_OFF = 0x124;
static const uint16_t TC_CAM_CMD_SEND = 0x12C;
static const uint16_t TM_MEMORY_READ_REPORT = 0x404;
static const uint16_t ACK_SUCCESS = 0x400;
static const uint16_t ACK_FAILURE = 0x401;
static const uint16_t EXE_SUCCESS = 0x402;
static const uint16_t EXE_FAILURE = 0x403;
static const uint16_t TM_CAM_CMD_RPT = 0x407;
} // namespace apid
/** Offset from first byte in space packet to first byte of data field */
static const uint8_t DATA_FIELD_OFFSET = 6;
static const size_t MEM_READ_RPT_LEN_OFFSET = 10;
static const char NULL_TERMINATOR = '\0';
static const uint8_t MIN_SPACE_PACKET_LENGTH = 7;
static const uint8_t SPACE_PACKET_HEADER_SIZE = 6;
/**
* The size of payload data which will be forwarded to the requesting object. e.g. PUS Service
* 8.
*/
static const uint8_t SIZE_MEM_READ_RPT_FIX = 6;
static const size_t MAX_FILENAME_SIZE = 256;
/**
* PLOC space packet length for fixed size packets. This is the size of the whole packet data
* field. For the length field in the space packet this size will be substracted by one.
*/
static const uint16_t LENGTH_TC_MEM_WRITE = 12;
static const uint16_t LENGTH_TC_MEM_READ = 8;
static const size_t MAX_REPLY_SIZE = SpacePacket::PACKET_MAX_SIZE * 3;
static const size_t MAX_COMMAND_SIZE = SpacePacket::PACKET_MAX_SIZE;
static const size_t MAX_DATA_SIZE = 1016;
/**
* The replay write sequence command has a maximum delay for the execution report which amounts to
* 30 seconds. (80 cycles * 0.5 seconds = 40 seconds).
*/
static const uint16_t TC_WRITE_SEQ_EXECUTION_DELAY = 80;
// Requires approx. 2 seconds for execution. 8 => 4 seconds
static const uint16_t TC_DOWNLINK_PWR_ON_EXECUTION_DELAY = 8;
namespace status_code {
static const uint16_t UNKNOWN_APID = 0x5DD;
static const uint16_t INCORRECT_LENGTH = 0x5DE;
static const uint16_t INCORRECT_CRC = 0x5DF;
static const uint16_t INCORRECT_PKT_SEQ_CNT = 0x5E0;
static const uint16_t TC_NOT_ALLOWED_IN_MODE = 0x5E1;
static const uint16_t TC_EXEUTION_DISABLED = 0x5E2;
static const uint16_t FLASH_MOUNT_FAILED = 0x5E3;
static const uint16_t FLASH_FILE_ALREADY_CLOSED = 0x5E4;
static const uint16_t FLASH_FILE_OPEN_FAILED = 0x5E5;
static const uint16_t FLASH_FILE_ALREDY_OPEN = 0x5E6;
static const uint16_t FLASH_FILE_NOT_OPEN = 0x5E7;
static const uint16_t FLASH_UNMOUNT_FAILED = 0x5E8;
static const uint16_t HEAP_ALLOCATION_FAILED = 0x5E9;
static const uint16_t INVALID_PARAMETER = 0x5EA;
static const uint16_t NOT_INITIALIZED = 0x5EB;
static const uint16_t REBOOT_IMMINENT = 0x5EC;
static const uint16_t CORRUPT_DATA = 0x5ED;
static const uint16_t FLASH_CORRECTABLE_MISMATCH = 0x5EE;
static const uint16_t FLASH_UNCORRECTABLE_MISMATCH = 0x5EF;
static const uint16_t RESERVED_0 = 0x5F0;
static const uint16_t RESERVED_1 = 0x5F1;
static const uint16_t RESERVED_2 = 0x5F2;
static const uint16_t RESERVED_3 = 0x5F3;
static const uint16_t RESERVED_4 = 0x5F4;
} // namespace status_code
/**
* @brief Abstract base class for TC space packet of MPSoC.
*/
class TcBase : public SpacePacket, public MPSoCReturnValuesIF {
public:
// Initial length field of space packet. Will always be updated when packet is created.
static const uint16_t INIT_LENGTH = 1;
/**
* @brief Constructor
*
* @param sequenceCount Sequence count of space packet which will be incremented with each
* sent and received packets.
*/
TcBase(uint16_t apid, uint16_t sequenceCount)
: SpacePacket(INIT_LENGTH, true, apid, sequenceCount) {}
/**
* @brief Function to initialize the space packet
*
* @param commandData Pointer to command specific data
* @param commandDataLen Length of command data
*
* @return RETURN_OK if packet creation was successful, otherwise error return value
*/
virtual ReturnValue_t createPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = initPacket(commandData, commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
protected:
/**
* @brief Must be overwritten by the child class to define the command specific parameters
*
* @param commandData Pointer to received command data
* @param commandDataLen Length of received command data
*/
virtual ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
return HasReturnvaluesIF::RETURN_OK;
}
/**
* @brief Calculates and adds the CRC
*/
ReturnValue_t addCrc() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t serializedSize = 0;
uint32_t full_size = getFullSize();
uint16_t crc = CRC::crc16ccitt(getWholeData(), full_size - CRC_SIZE);
result = SerializeAdapter::serialize<uint16_t>(
&crc, this->localData.byteStream + full_size - CRC_SIZE, &serializedSize, sizeof(crc),
SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
sif::debug << "TcBase::addCrc: Failed to serialize crc field" << std::endl;
}
return result;
}
};
/**
* @brief Class for handling tm replies of the PLOC MPSoC.
*/
class TmPacket : public SpacePacket, public MPSoCReturnValuesIF {
public:
/**
* @brief Constructor creates idle packet and sets length field to maximum allowed size.
*/
TmPacket() : SpacePacket(PACKET_MAX_SIZE) {}
ReturnValue_t checkCrc() {
uint8_t* crcPtr = this->getPacketData() + this->getPacketDataLength() - 1;
uint16_t receivedCrc = *(crcPtr) << 8 | *(crcPtr + 1);
uint16_t recalculatedCrc =
CRC::crc16ccitt(this->localData.byteStream, this->getFullSize() - CRC_SIZE);
if (recalculatedCrc != receivedCrc) {
return CRC_FAILURE;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the memory read command for the PLOC.
*/
class TcMemRead : public TcBase {
public:
/**
* @brief Constructor
*/
TcMemRead(uint16_t sequenceCount) : TcBase(apid::TC_MEM_READ, sequenceCount) {
this->setPacketDataLength(PACKET_LENGTH);
}
uint16_t getMemLen() const { return memLen; }
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, MEM_ADDRESS_SIZE);
std::memcpy(this->localData.fields.buffer + MEM_ADDRESS_SIZE, commandData + MEM_ADDRESS_SIZE,
MEM_LEN_SIZE);
size_t size = sizeof(memLen);
const uint8_t* memLenPtr = commandData + MEM_ADDRESS_SIZE;
result =
SerializeAdapter::deSerialize(&memLen, &memLenPtr, &size, SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
private:
static const size_t COMMAND_LENGTH = 6;
static const size_t MEM_ADDRESS_SIZE = 4;
static const size_t MEM_LEN_SIZE = 2;
static const uint16_t PACKET_LENGTH = 7;
uint16_t memLen = 0;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_LENGTH) {
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to generate the space packet to write data to a memory address within
* the PLOC.
@ -278,23 +153,31 @@ class TcMemWrite : public TcBase {
TcMemWrite(uint16_t sequenceCount) : TcBase(apid::TC_MEM_WRITE, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t initPacket(void *actionIn) {
auto action = (PlocMpSoCMemWriteAction *)(actionIn); //TODO
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
// faking until framework code is ready
// uint16_t length = action->memoryData.length;
uint16_t dataLength = 1;
result = lengthCheck(dataLength);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
uint16_t memLen =
*(commandData + MEM_ADDRESS_SIZE) << 8 | *(commandData + MEM_ADDRESS_SIZE + 1);
this->setPacketDataLength(memLen * 4 + FIX_LENGTH - 1);
uint8_t *pointer = this->localData.fields.buffer;
size_t size = 0;
size_t maxSize = PACKET_MAX_SIZE;
SerializeAdapter::serialize(&action->address.value, &pointer, &size, maxSize,
SerializeIF::Endianness::BIG);
SerializeAdapter::serialize(&dataLength, &pointer, &size, maxSize,
SerializeIF::Endianness::BIG);
std::memcpy(pointer, &action->memoryData.value, dataLength);
this->setPacketDataLength(dataLength * sizeof(action->memoryData.value) + FIX_LENGTH - 1);
return result;
}
private:
// Min length consists of 4 byte address, 2 byte mem length field, 4 byte data (1 word)
static const size_t MIN_COMMAND_DATA_LENGTH = 10;
static const size_t MEM_ADDRESS_SIZE = 4;
// Min length consists of 4 byte data (1 word)
static const size_t MIN_COMMAND_DATA_LENGTH = 1;
static const size_t FIX_LENGTH = 8;
ReturnValue_t lengthCheck(size_t commandDataLen) {
@ -305,400 +188,5 @@ class TcMemWrite : public TcBase {
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to help creation of flash fopen command.
*/
class FlashFopen : public TcBase {
public:
FlashFopen(uint16_t sequenceCount) : TcBase(apid::TC_FLASHFOPEN, sequenceCount) {}
static const char APPEND = 'a';
static const char WRITE = 'w';
static const char READ = 'r';
ReturnValue_t createPacket(std::string filename, char accessMode_) {
accessMode = accessMode_;
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
std::memcpy(this->getPacketData() + nameSize + sizeof(NULL_TERMINATOR), &accessMode,
sizeof(accessMode));
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + sizeof(accessMode) + CRC_SIZE -
1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
private:
char accessMode = APPEND;
};
/**
* @brief Class to help creation of flash fclose command.
*/
class FlashFclose : public TcBase {
public:
FlashFclose(uint16_t sequenceCount) : TcBase(apid::TC_FLASHFCLOSE, sequenceCount) {}
ReturnValue_t createPacket(std::string filename) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
};
/**
* @brief Class to build flash write space packet.
*/
class TcFlashWrite : public TcBase {
public:
TcFlashWrite(uint16_t sequenceCount) : TcBase(apid::TC_FLASHWRITE, sequenceCount) {}
ReturnValue_t createPacket(const uint8_t* writeData, uint32_t writeLen_) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
writeLen = writeLen_;
if (writeLen > MAX_DATA_SIZE) {
sif::debug << "FlashWrite::createPacket: Command data too big" << std::endl;
return HasReturnvaluesIF::RETURN_FAILED;
}
size_t serializedSize = 0;
result =
SerializeAdapter::serialize<uint32_t>(&writeLen, this->getPacketData(), &serializedSize,
sizeof(writeLen), SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->getPacketData() + sizeof(writeLen), writeData, writeLen);
this->setPacketDataLength(static_cast<uint16_t>(writeLen + CRC_SIZE - 1));
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return HasReturnvaluesIF::RETURN_OK;
}
private:
uint32_t writeLen = 0;
};
/**
* @brief Class to help creation of flash delete command.
*/
class TcFlashDelete : public TcBase {
public:
TcFlashDelete(uint16_t sequenceCount) : TcBase(apid::TC_FLASHDELETE, sequenceCount) {}
ReturnValue_t createPacket(std::string filename) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
size_t nameSize = filename.size();
std::memcpy(this->getPacketData(), filename.c_str(), nameSize);
*(this->getPacketData() + nameSize) = NULL_TERMINATOR;
this->setPacketDataLength(nameSize + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
return result;
}
};
/**
* @brief Class to build replay stop space packet.
*/
class TcReplayStop : public TcBase {
public:
TcReplayStop(uint16_t sequenceCount) : TcBase(apid::TC_REPLAY_STOP, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the replay start command.
*/
class TcReplayStart : public TcBase {
public:
/**
* @brief Constructor
*/
TcReplayStart(uint16_t sequenceCount) : TcBase(apid::TC_REPLAY_START, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = checkData(*commandData);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
this->setPacketDataLength(commandDataLen + CRC_SIZE - 1);
return result;
}
private:
static const size_t COMMAND_DATA_LENGTH = 1;
static const uint8_t REPEATING = 0;
static const uint8_t ONCE = 1;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_DATA_LENGTH) {
sif::warning << "TcReplayStart: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t checkData(uint8_t replay) {
if (replay != REPEATING && replay != ONCE) {
sif::warning << "TcReplayStart::checkData: Invalid replay value" << std::endl;
return INVALID_PARAMETER;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build downlink power on command.
*/
class TcDownlinkPwrOn : public TcBase {
public:
/**
* @brief Constructor
*/
TcDownlinkPwrOn(uint16_t sequenceCount) : TcBase(apid::TC_DOWNLINK_PWR_ON, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = modeCheck(*commandData);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
result = laneRateCheck(*(commandData + 1));
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
std::memcpy(this->localData.fields.buffer + commandDataLen, &MAX_AMPLITUDE,
sizeof(MAX_AMPLITUDE));
this->setPacketDataLength(commandDataLen + sizeof(MAX_AMPLITUDE) + CRC_SIZE - 1);
return result;
}
private:
static const uint8_t INTERFACE_ID = CLASS_ID::DWLPWRON_CMD;
//! [EXPORT] : [COMMENT] Received command has invalid JESD mode (valid modes are 0 - 5)
static const ReturnValue_t INVALID_MODE = MAKE_RETURN_CODE(0xE0);
//! [EXPORT] : [COMMENT] Received command has invalid lane rate (valid lane rate are 0 - 9)
static const ReturnValue_t INVALID_LANE_RATE = MAKE_RETURN_CODE(0xE1);
static const size_t COMMAND_DATA_LENGTH = 2;
static const uint8_t MAX_MODE = 5;
static const uint8_t MAX_LANE_RATE = 9;
static const uint16_t MAX_AMPLITUDE = 0;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen != COMMAND_DATA_LENGTH) {
sif::warning << "TcDownlinkPwrOn: Command has invalid length " << commandDataLen << std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t modeCheck(uint8_t mode) {
if (mode > MAX_MODE) {
sif::warning << "TcDwonlinkPwrOn::modeCheck: Invalid JESD mode" << std::endl;
return INVALID_MODE;
}
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t laneRateCheck(uint8_t laneRate) {
if (laneRate > MAX_LANE_RATE) {
sif::warning << "TcReplayStart::laneRateCheck: Invalid lane rate" << std::endl;
return INVALID_LANE_RATE;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to build replay stop space packet.
*/
class TcDownlinkPwrOff : public TcBase {
public:
TcDownlinkPwrOff(uint16_t sequenceCount) : TcBase(apid::TC_DOWNLINK_PWR_OFF, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief This class helps to build the replay start command.
*/
class TcReplayWriteSeq : public TcBase {
public:
/**
* @brief Constructor
*/
TcReplayWriteSeq(uint16_t sequenceCount)
: TcBase(apid::TC_REPLAY_WRITE_SEQUENCE, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = lengthCheck(commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
std::memcpy(this->localData.fields.buffer, commandData, commandDataLen);
*(this->localData.fields.buffer + commandDataLen) = NULL_TERMINATOR;
this->setPacketDataLength(commandDataLen + sizeof(NULL_TERMINATOR) + CRC_SIZE - 1);
return result;
}
private:
static const size_t USE_DECODING_LENGTH = 1;
ReturnValue_t lengthCheck(size_t commandDataLen) {
if (commandDataLen > USE_DECODING_LENGTH + MAX_FILENAME_SIZE) {
sif::warning << "TcReplayWriteSeq: Command has invalid length " << commandDataLen
<< std::endl;
return INVALID_LENGTH;
}
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Helps to extract the fields of the flash write command from the PUS packet.
*/
class FlashWritePusCmd : public MPSoCReturnValuesIF {
public:
FlashWritePusCmd(){};
ReturnValue_t extractFields(const uint8_t* commandData, size_t commandDataLen) {
if (commandDataLen > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE + MAX_FILENAME_SIZE)) {
return INVALID_LENGTH;
}
obcFile = std::string(reinterpret_cast<const char*>(commandData));
if (obcFile.size() > (config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE)) {
return FILENAME_TOO_LONG;
}
mpsocFile = std::string(
reinterpret_cast<const char*>(commandData + obcFile.size() + SIZE_NULL_TERMINATOR));
if (mpsocFile.size() > MAX_FILENAME_SIZE) {
return MPSOC_FILENAME_TOO_LONG;
}
return HasReturnvaluesIF::RETURN_OK;
}
std::string getObcFile() { return obcFile; }
std::string getMPSoCFile() { return mpsocFile; }
private:
static const size_t SIZE_NULL_TERMINATOR = 1;
std::string obcFile = "";
std::string mpsocFile = "";
};
/**
* @brief Class to build replay stop space packet.
*/
class TcModeReplay : public TcBase {
public:
TcModeReplay(uint16_t sequenceCount) : TcBase(apid::TC_MODE_REPLAY, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
/**
* @brief Class to build mode idle command
*/
class TcModeIdle : public TcBase {
public:
TcModeIdle(uint16_t sequenceCount) : TcBase(apid::TC_MODE_IDLE, sequenceCount) {}
ReturnValue_t createPacket() {
ReturnValue_t result = HasReturnvaluesIF::RETURN_OK;
result = addCrc();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
this->setPacketDataLength(static_cast<uint16_t>(CRC_SIZE - 1));
return HasReturnvaluesIF::RETURN_OK;
}
};
class TcCamcmdSend : public TcBase {
public:
TcCamcmdSend(uint16_t sequenceCount) : TcBase(apid::TC_CAM_CMD_SEND, sequenceCount) {}
protected:
ReturnValue_t initPacket(const uint8_t* commandData, size_t commandDataLen) {
if (commandDataLen > MAX_DATA_LENGTH) {
return INVALID_LENGTH;
}
uint16_t dataLen = static_cast<uint16_t>(commandDataLen + sizeof(CARRIAGE_RETURN));
size_t size = sizeof(dataLen);
SerializeAdapter::serialize(&dataLen, this->getPacketData(), &size, sizeof(dataLen),
SerializeIF::Endianness::BIG);
std::memcpy(this->getPacketData() + sizeof(dataLen), commandData, commandDataLen);
*(this->getPacketData() + sizeof(dataLen) + commandDataLen) = CARRIAGE_RETURN;
uint16_t trueLength = sizeof(dataLen) + commandDataLen + sizeof(CARRIAGE_RETURN) + CRC_SIZE;
this->setPacketDataLength(trueLength - 1);
return HasReturnvaluesIF::RETURN_OK;
}
private:
static const uint8_t MAX_DATA_LENGTH = 10;
static const uint8_t CARRIAGE_RETURN = 0xD;
};
} // namespace mpsoc
#endif /* MISSION_DEVICES_DEVICEDEFINITIONS_PLOCMPSOCDEFINITIONS_H_ */

View File

@ -0,0 +1,20 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
class PlocMemoryDumper;
FSFW_ENUM(PlocMemoryDumperCommands, DeviceCommandId_t,
((DUMP_MRAM, 1 ,"Dump Memory")))
class DumpMemoryAction : public TemplateAction<PlocMemoryDumper, DumpMemoryAction, PlocMemoryDumperCommands> {
public:
DumpMemoryAction(PlocMemoryDumper * owner): TemplateAction(owner, PlocMemoryDumperCommands::DUMP_MRAM) {}
//Memory is 512KiB
MinMaxParameter<uint32_t> startAddress = MinMaxParameter<uint32_t>::createMinMaxParameter(this, "Start Address", 0 , 0x80000);
MinMaxParameter<uint32_t> endAddress = MinMaxParameter<uint32_t>::createMinMaxParameter(this, "End Address", 0 , 0x80000);
};

View File

@ -5,6 +5,8 @@
#include "fsfw/globalfunctions/CRC.h"
#include "linux/devices/devicedefinitions/PlocSupervisorDefinitions.h"
// TODO this is work in progress in adapting to new actions
PlocMPSoCHandler::PlocMPSoCHandler(object_id_t objectId, object_id_t uartComIFid,
CookieIF* comCookie, PlocMPSoCHelper* plocMPSoCHelper,
Gpio uartIsolatorSwitch, object_id_t supervisorHandler)
@ -96,16 +98,14 @@ void PlocMPSoCHandler::performOperationHook() {
}
}
ReturnValue_t PlocMPSoCHandler::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t result = RETURN_OK;
switch (actionId) {
case mpsoc::SET_UART_TX_TRISTATE: {
ReturnValue_t PlocMPSoCHandler::executeAction(Action* action) {
switch (PlocMpSoCCommands(action->getId())) {
case PlocMpSoCCommands::SET_UART_TX_TRISTATE: {
uartIsolatorSwitch.pullLow();
return EXECUTION_FINISHED;
break;
}
case mpsoc::RELEASE_UART_TX: {
case PlocMpSoCCommands::RELEASE_UART_TX: {
uartIsolatorSwitch.pullHigh();
return EXECUTION_FINISHED;
break;
@ -118,32 +118,28 @@ ReturnValue_t PlocMPSoCHandler::executeAction(ActionId_t actionId, MessageQueueI
return MPSoCReturnValuesIF::MPSOC_HELPER_EXECUTING;
}
switch (actionId) {
case mpsoc::TC_FLASHWRITE: {
if (size > config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE) {
return MPSoCReturnValuesIF::FILENAME_TOO_LONG;
}
mpsoc::FlashWritePusCmd flashWritePusCmd;
result = flashWritePusCmd.extractFields(data, size);
if (result != RETURN_OK) {
return result;
}
result = plocMPSoCHelper->startFlashWrite(flashWritePusCmd.getObcFile(),
flashWritePusCmd.getMPSoCFile());
if (result != RETURN_OK) {
return result;
}
plocMPSoCHelperExecuting = true;
return EXECUTION_FINISHED;
switch (PlocMpSoCCommands(action->getId())) {
case PlocMpSoCCommands::TC_FLASHWRITE: {
// refer handling to the handleAction() below
return action->handle();
}
case (mpsoc::OBSW_RESET_SEQ_COUNT): {
case (PlocMpSoCCommands::OBSW_RESET_SEQ_COUNT): {
sequenceCount = 0;
return EXECUTION_FINISHED;
}
default:
break;
}
return DeviceHandlerBase::executeAction(actionId, commandedBy, data, size);
ReturnValue_t result = DeviceHandlerBase::executeAction(action);
if (result == RETURN_OK) {
/**
* Flushing the receive buffer to make sure there are no data left from a faulty reply.
*/
uartComIf->flushUartRxBuffer(comCookie);
}
return result;
}
void PlocMPSoCHandler::doStartUp() {
@ -203,90 +199,29 @@ ReturnValue_t PlocMPSoCHandler::buildTransitionDeviceCommand(DeviceCommandId_t*
return NOTHING_TO_SEND;
}
ReturnValue_t PlocMPSoCHandler::buildCommandFromCommand(DeviceCommandId_t deviceCommand,
const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t result = RETURN_OK;
switch (deviceCommand) {
case (mpsoc::TC_MEM_WRITE): {
result = prepareTcMemWrite(commandData, commandDataLen);
break;
}
case (mpsoc::TC_MEM_READ): {
result = prepareTcMemRead(commandData, commandDataLen);
break;
}
case (mpsoc::TC_FLASHDELETE): {
result = prepareTcFlashDelete(commandData, commandDataLen);
break;
}
case (mpsoc::TC_REPLAY_START): {
result = prepareTcReplayStart(commandData, commandDataLen);
break;
}
case (mpsoc::TC_REPLAY_STOP): {
result = prepareTcReplayStop();
break;
}
case (mpsoc::TC_DOWNLINK_PWR_ON): {
result = prepareTcDownlinkPwrOn(commandData, commandDataLen);
break;
}
case (mpsoc::TC_DOWNLINK_PWR_OFF): {
result = prepareTcDownlinkPwrOff();
break;
}
case (mpsoc::TC_REPLAY_WRITE_SEQUENCE): {
result = prepareTcReplayWriteSequence(commandData, commandDataLen);
break;
}
case (mpsoc::TC_MODE_REPLAY): {
result = prepareTcModeReplay();
break;
}
case (mpsoc::TC_MODE_IDLE): {
result = prepareTcModeIdle();
break;
}
case (mpsoc::TC_CAM_CMD_SEND): {
result = prepareTcCamCmdSend(commandData, commandDataLen);
break;
}
default:
sif::debug << "PlocMPSoCHandler::buildCommandFromCommand: Command not implemented"
<< std::endl;
result = DeviceHandlerIF::COMMAND_NOT_IMPLEMENTED;
break;
}
if (result == RETURN_OK) {
/**
* Flushing the receive buffer to make sure there are no data left from a faulty reply.
*/
uartComIf->flushUartRxBuffer(comCookie);
}
return result;
}
void PlocMPSoCHandler::fillCommandAndReplyMap() {
this->insertInCommandMap(mpsoc::TC_MEM_WRITE);
this->insertInCommandMap(mpsoc::TC_MEM_READ);
this->insertInCommandMap(mpsoc::TC_FLASHDELETE);
this->insertInCommandMap(mpsoc::TC_REPLAY_START);
this->insertInCommandMap(mpsoc::TC_REPLAY_STOP);
this->insertInCommandMap(mpsoc::TC_DOWNLINK_PWR_ON);
this->insertInCommandMap(mpsoc::TC_DOWNLINK_PWR_OFF);
this->insertInCommandMap(mpsoc::TC_REPLAY_WRITE_SEQUENCE);
this->insertInCommandMap(mpsoc::TC_MODE_REPLAY);
this->insertInCommandMap(mpsoc::TC_MODE_IDLE);
this->insertInCommandMap(mpsoc::TC_CAM_CMD_SEND);
this->insertInCommandMap(mpsoc::RELEASE_UART_TX);
this->insertInCommandMap(mpsoc::SET_UART_TX_TRISTATE);
this->insertInReplyMap(mpsoc::ACK_REPORT, 3, nullptr, mpsoc::SIZE_ACK_REPORT);
this->insertInReplyMap(mpsoc::EXE_REPORT, 3, nullptr, mpsoc::SIZE_EXE_REPORT);
this->insertInReplyMap(mpsoc::TM_MEMORY_READ_REPORT, 2, nullptr, mpsoc::SIZE_TM_MEM_READ_REPORT);
this->insertInReplyMap(mpsoc::TM_CAM_CMD_RPT, 2, nullptr, SpacePacket::PACKET_MAX_SIZE);
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_MEM_WRITE));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_MEM_READ));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_FLASHDELETE));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_REPLAY_START));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_REPLAY_STOP));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_DOWNLINK_PWR_ON));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_DOWNLINK_PWR_OFF));
this->insertInCommandMap(
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_REPLAY_WRITE_SEQUENCE));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_MODE_REPLAY));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_MODE_IDLE));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TC_CAM_CMD_SEND));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::RELEASE_UART_TX));
this->insertInCommandMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::SET_UART_TX_TRISTATE));
this->insertInReplyMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT), 3, nullptr,
mpsoc::SIZE_ACK_REPORT);
this->insertInReplyMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT), 3, nullptr,
mpsoc::SIZE_EXE_REPORT);
this->insertInReplyMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT),
2, nullptr, mpsoc::SIZE_TM_MEM_READ_REPORT);
this->insertInReplyMap(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT), 2,
nullptr, SpacePacket::PACKET_MAX_SIZE);
}
ReturnValue_t PlocMPSoCHandler::scanForReply(const uint8_t* start, size_t remainingSize,
@ -300,28 +235,28 @@ ReturnValue_t PlocMPSoCHandler::scanForReply(const uint8_t* start, size_t remain
switch (apid) {
case (mpsoc::apid::ACK_SUCCESS):
*foundLen = mpsoc::SIZE_ACK_REPORT;
*foundId = mpsoc::ACK_REPORT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT);
break;
case (mpsoc::apid::ACK_FAILURE):
*foundLen = mpsoc::SIZE_ACK_REPORT;
*foundId = mpsoc::ACK_REPORT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT);
break;
case (mpsoc::apid::TM_MEMORY_READ_REPORT):
*foundLen = tmMemReadReport.rememberRequestedSize;
*foundId = mpsoc::TM_MEMORY_READ_REPORT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT);
break;
case (mpsoc::apid::TM_CAM_CMD_RPT):
*foundLen = spacePacket.getFullSize();
tmCamCmdRpt.rememberSpacePacketSize = *foundLen;
*foundId = mpsoc::TM_CAM_CMD_RPT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT);
break;
case (mpsoc::apid::EXE_SUCCESS):
*foundLen = mpsoc::SIZE_EXE_REPORT;
*foundId = mpsoc::EXE_REPORT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT);
break;
case (mpsoc::apid::EXE_FAILURE):
*foundLen = mpsoc::SIZE_EXE_REPORT;
*foundId = mpsoc::EXE_REPORT;
*foundId = static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT);
break;
default: {
sif::debug << "PlocMPSoCHandler::scanForReply: Reply has invalid apid" << std::endl;
@ -342,20 +277,22 @@ ReturnValue_t PlocMPSoCHandler::scanForReply(const uint8_t* start, size_t remain
ReturnValue_t PlocMPSoCHandler::interpretDeviceReply(DeviceCommandId_t id, const uint8_t* packet) {
ReturnValue_t result = RETURN_OK;
switch (id) {
case mpsoc::ACK_REPORT: {
PlocMpSoCCommands enumId = PlocMpSoCCommands(id);
switch (enumId) {
case PlocMpSoCCommands::ACK_REPORT: {
result = handleAckReport(packet);
break;
}
case (mpsoc::TM_MEMORY_READ_REPORT): {
case (PlocMpSoCCommands::TM_MEMORY_READ_REPORT): {
result = handleMemoryReadReport(packet);
break;
}
case (mpsoc::TM_CAM_CMD_RPT): {
case (PlocMpSoCCommands::TM_CAM_CMD_RPT): {
result = handleCamCmdRpt(packet);
break;
}
case (mpsoc::EXE_REPORT): {
case (PlocMpSoCCommands::EXE_REPORT): {
result = handleExecutionReport(packet);
break;
}
@ -390,12 +327,17 @@ void PlocMPSoCHandler::handleEvent(EventMessage* eventMessage) {
}
}
ReturnValue_t PlocMPSoCHandler::prepareTcMemWrite(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::buildCommandFromCommand(DeviceCommandId_t deviceCommand,
const uint8_t* commandData,
size_t commandDataLen) {
return NOTHING_TO_SEND;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCMemWriteAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcMemWrite tcMemWrite(sequenceCount);
result = tcMemWrite.createPacket(commandData, commandDataLen);
result = tcMemWrite.createPacket(action);
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -403,13 +345,11 @@ ReturnValue_t PlocMPSoCHandler::prepareTcMemWrite(const uint8_t* commandData,
copyToCommandBuffer(&tcMemWrite);
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcMemRead(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCMemReadAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcMemRead tcMemRead(sequenceCount);
result = tcMemRead.createPacket(commandData, commandDataLen);
// result = tcMemRead.createPacket(commandData, commandDataLen);
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -418,17 +358,15 @@ ReturnValue_t PlocMPSoCHandler::prepareTcMemRead(const uint8_t* commandData,
tmMemReadReport.rememberRequestedSize = tcMemRead.getMemLen() * 4 + TmMemReadReport::FIX_SIZE;
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcFlashDelete(const uint8_t* commandData,
size_t commandDataLen) {
if (commandDataLen > config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE) {
return MPSoCReturnValuesIF::NAME_TOO_LONG;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCFlashDeleteAction* action) {
// if (commandDataLen > config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE) {
// return MPSoCReturnValuesIF::NAME_TOO_LONG;
// }
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcFlashDelete tcFlashDelete(sequenceCount);
result = tcFlashDelete.createPacket(
std::string(reinterpret_cast<const char*>(commandData), commandDataLen));
// result = tcFlashDelete.createPacket(
// std::string(reinterpret_cast<const char*>(commandData), commandDataLen));
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -436,13 +374,11 @@ ReturnValue_t PlocMPSoCHandler::prepareTcFlashDelete(const uint8_t* commandData,
copyToCommandBuffer(&tcFlashDelete);
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcReplayStart(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCReplayStartAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcReplayStart tcReplayStart(sequenceCount);
result = tcReplayStart.createPacket(commandData, commandDataLen);
// result = tcReplayStart.createPacket(commandData, commandDataLen);
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -450,8 +386,7 @@ ReturnValue_t PlocMPSoCHandler::prepareTcReplayStart(const uint8_t* commandData,
copyToCommandBuffer(&tcReplayStart);
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcReplayStop() {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCReplayStopAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcReplayStop tcReplayStop(sequenceCount);
@ -464,12 +399,11 @@ ReturnValue_t PlocMPSoCHandler::prepareTcReplayStop() {
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcDownlinkPwrOn(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCDownlinkPwrOnAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcDownlinkPwrOn tcDownlinkPwrOn(sequenceCount);
result = tcDownlinkPwrOn.createPacket(commandData, commandDataLen);
// result = tcDownlinkPwrOn.createPacket(commandData, commandDataLen);
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -477,8 +411,7 @@ ReturnValue_t PlocMPSoCHandler::prepareTcDownlinkPwrOn(const uint8_t* commandDat
copyToCommandBuffer(&tcDownlinkPwrOn);
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcDownlinkPwrOff() {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCDownlinkPwrOffAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcDownlinkPwrOff tcDownlinkPwrOff(sequenceCount);
@ -491,12 +424,11 @@ ReturnValue_t PlocMPSoCHandler::prepareTcDownlinkPwrOff() {
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcReplayWriteSequence(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCReplayWriteSequenceAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcReplayWriteSeq tcReplayWriteSeq(sequenceCount);
result = tcReplayWriteSeq.createPacket(commandData, commandDataLen);
// result = tcReplayWriteSeq.createPacket(commandData, commandDataLen);
if (result != RETURN_OK) {
sequenceCount--;
return result;
@ -505,7 +437,7 @@ ReturnValue_t PlocMPSoCHandler::prepareTcReplayWriteSequence(const uint8_t* comm
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcModeReplay() {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCModeReplayAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcModeReplay tcModeReplay(sequenceCount);
@ -517,11 +449,11 @@ ReturnValue_t PlocMPSoCHandler::prepareTcModeReplay() {
memcpy(commandBuffer, tcModeReplay.getWholeData(), tcModeReplay.getFullSize());
rawPacket = commandBuffer;
rawPacketLen = tcModeReplay.getFullSize();
nextReplyId = mpsoc::ACK_REPORT;
nextReplyId = PlocMpSoCCommands::ACK_REPORT;
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcModeIdle() {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCModeIdleAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcModeIdle tcModeIdle(sequenceCount);
@ -533,22 +465,52 @@ ReturnValue_t PlocMPSoCHandler::prepareTcModeIdle() {
memcpy(commandBuffer, tcModeIdle.getWholeData(), tcModeIdle.getFullSize());
rawPacket = commandBuffer;
rawPacketLen = tcModeIdle.getFullSize();
nextReplyId = mpsoc::ACK_REPORT;
nextReplyId = PlocMpSoCCommands::ACK_REPORT;
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::prepareTcCamCmdSend(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCCamCmdSendAction* action) {
ReturnValue_t result = RETURN_OK;
sequenceCount++;
mpsoc::TcCamcmdSend tcCamCmdSend(sequenceCount);
result = tcCamCmdSend.createPacket(commandData, commandDataLen);
// result = tcCamCmdSend.createPacket(commandData, commandDataLen);
if (result != RETURN_OK) {
sequenceCount--;
return result;
}
copyToCommandBuffer(&tcCamCmdSend);
nextReplyId = mpsoc::TM_CAM_CMD_RPT;
nextReplyId = PlocMpSoCCommands::TM_CAM_CMD_RPT;
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCFlashWriteAction* action) {
ReturnValue_t result = RETURN_OK;
// if (size > config::MAX_PATH_SIZE + config::MAX_FILENAME_SIZE) {
// return MPSoCReturnValuesIF::FILENAME_TOO_LONG;
// }
mpsoc::FlashWritePusCmd flashWritePusCmd;
// result = flashWritePusCmd.extractFields(data, size);
if (result != RETURN_OK) {
return result;
}
result = plocMPSoCHelper->startFlashWrite(flashWritePusCmd.getObcFile(),
flashWritePusCmd.getMPSoCFile());
if (result != RETURN_OK) {
return result;
}
plocMPSoCHelperExecuting = true;
return EXECUTION_FINISHED;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCUartTxTristateAction* action) {
// not used
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCReleaseUartTxAction* action) {
// not used
return RETURN_OK;
}
ReturnValue_t PlocMPSoCHandler::handleAction(PlocMpSoCObswResetSeqCountAction* action) {
// not used
return RETURN_OK;
}
@ -559,7 +521,7 @@ void PlocMPSoCHandler::copyToCommandBuffer(mpsoc::TcBase* tc) {
memcpy(commandBuffer, tc->getWholeData(), tc->getFullSize());
rawPacket = commandBuffer;
rawPacketLen = tc->getFullSize();
nextReplyId = mpsoc::ACK_REPORT;
nextReplyId = PlocMpSoCCommands::ACK_REPORT;
}
ReturnValue_t PlocMPSoCHandler::verifyPacket(const uint8_t* start, size_t foundLen) {
@ -577,10 +539,10 @@ ReturnValue_t PlocMPSoCHandler::handleAckReport(const uint8_t* data) {
result = verifyPacket(data, mpsoc::SIZE_ACK_REPORT);
if (result == MPSoCReturnValuesIF::CRC_FAILURE) {
sif::warning << "PlocMPSoCHandler::handleAckReport: CRC failure" << std::endl;
nextReplyId = mpsoc::NONE;
nextReplyId = PlocMpSoCCommands::NONE;
replyRawReplyIfnotWiretapped(data, mpsoc::SIZE_ACK_REPORT);
triggerEvent(MPSOC_HANDLER_CRC_FAILURE);
sendFailureReport(mpsoc::ACK_REPORT, MPSoCReturnValuesIF::CRC_FAILURE);
sendFailureReport(PlocMpSoCCommands::ACK_REPORT, MPSoCReturnValuesIF::CRC_FAILURE);
disableAllReplies();
return IGNORE_REPLY_DATA;
}
@ -596,9 +558,9 @@ ReturnValue_t PlocMPSoCHandler::handleAckReport(const uint8_t* data) {
if (commandId != DeviceHandlerIF::NO_COMMAND_ID) {
triggerEvent(ACK_FAILURE, commandId, status);
}
sendFailureReport(mpsoc::ACK_REPORT, status);
sendFailureReport(PlocMpSoCCommands::ACK_REPORT, status);
disableAllReplies();
nextReplyId = mpsoc::NONE;
nextReplyId = PlocMpSoCCommands::NONE;
result = IGNORE_REPLY_DATA;
break;
}
@ -622,7 +584,7 @@ ReturnValue_t PlocMPSoCHandler::handleExecutionReport(const uint8_t* data) {
result = verifyPacket(data, mpsoc::SIZE_EXE_REPORT);
if (result == MPSoCReturnValuesIF::CRC_FAILURE) {
sif::warning << "PlocMPSoCHandler::handleExecutionReport: CRC failure" << std::endl;
nextReplyId = mpsoc::NONE;
nextReplyId = PlocMpSoCCommands::NONE;
return result;
}
@ -644,7 +606,7 @@ ReturnValue_t PlocMPSoCHandler::handleExecutionReport(const uint8_t* data) {
sif::debug << "PlocMPSoCHandler::handleExecutionReport: Unknown command id" << std::endl;
}
printStatus(data);
sendFailureReport(mpsoc::EXE_REPORT, MPSoCReturnValuesIF::RECEIVED_EXE_FAILURE);
sendFailureReport(PlocMpSoCCommands::EXE_REPORT, MPSoCReturnValuesIF::RECEIVED_EXE_FAILURE);
disableExeReportReply();
result = IGNORE_REPLY_DATA;
break;
@ -655,7 +617,7 @@ ReturnValue_t PlocMPSoCHandler::handleExecutionReport(const uint8_t* data) {
break;
}
}
nextReplyId = mpsoc::NONE;
nextReplyId = PlocMpSoCCommands::NONE;
return result;
}
@ -670,8 +632,8 @@ ReturnValue_t PlocMPSoCHandler::handleMemoryReadReport(const uint8_t* data) {
*(data + mpsoc::MEM_READ_RPT_LEN_OFFSET) << 8 | *(data + mpsoc::MEM_READ_RPT_LEN_OFFSET + 1);
/** Send data to commanding queue */
handleDeviceTM(data + mpsoc::DATA_FIELD_OFFSET, mpsoc::SIZE_MEM_READ_RPT_FIX + memLen * 4,
mpsoc::TM_MEMORY_READ_REPORT);
nextReplyId = mpsoc::EXE_REPORT;
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT));
nextReplyId = PlocMpSoCCommands::EXE_REPORT;
return result;
}
@ -694,7 +656,7 @@ ReturnValue_t PlocMPSoCHandler::handleCamCmdRpt(const uint8_t* data) {
<< static_cast<unsigned int>(ackValue) << std::endl;
#endif /* OBSW_DEBUG_PLOC_MPSOC == 1 */
handleDeviceTM(packet.getPacketData() + sizeof(uint16_t), packet.getPacketDataLength() - 1,
mpsoc::TM_CAM_CMD_RPT);
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT));
return result;
}
@ -705,41 +667,47 @@ ReturnValue_t PlocMPSoCHandler::enableReplyInReplyMap(DeviceCommandMap::iterator
uint8_t enabledReplies = 0;
switch (command->first) {
case mpsoc::TC_MEM_WRITE:
case mpsoc::TC_FLASHDELETE:
case mpsoc::TC_REPLAY_START:
case mpsoc::TC_REPLAY_STOP:
case mpsoc::TC_DOWNLINK_PWR_ON:
case mpsoc::TC_DOWNLINK_PWR_OFF:
case mpsoc::TC_REPLAY_WRITE_SEQUENCE:
case mpsoc::TC_MODE_REPLAY:
case mpsoc::TC_MODE_IDLE:
PlocMpSoCCommands enumCommand = PlocMpSoCCommands(command->first);
switch (enumCommand) {
case PlocMpSoCCommands::TC_MEM_WRITE:
case PlocMpSoCCommands::TC_FLASHDELETE:
case PlocMpSoCCommands::TC_REPLAY_START:
case PlocMpSoCCommands::TC_REPLAY_STOP:
case PlocMpSoCCommands::TC_DOWNLINK_PWR_ON:
case PlocMpSoCCommands::TC_DOWNLINK_PWR_OFF:
case PlocMpSoCCommands::TC_REPLAY_WRITE_SEQUENCE:
case PlocMpSoCCommands::TC_MODE_REPLAY:
case PlocMpSoCCommands::TC_MODE_IDLE:
enabledReplies = 2;
break;
case mpsoc::TC_MEM_READ: {
case PlocMpSoCCommands::TC_MEM_READ: {
enabledReplies = 3;
result = DeviceHandlerBase::enableReplyInReplyMap(command, enabledReplies, true,
mpsoc::TM_MEMORY_READ_REPORT);
result = DeviceHandlerBase::enableReplyInReplyMap(
command, enabledReplies, true,
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT));
if (result != RETURN_OK) {
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id "
<< mpsoc::TM_MEMORY_READ_REPORT << " not in replyMap" << std::endl;
<< static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT)
<< " not in replyMap" << std::endl;
return result;
}
break;
}
case mpsoc::TC_CAM_CMD_SEND: {
case PlocMpSoCCommands::TC_CAM_CMD_SEND: {
enabledReplies = 3;
result = DeviceHandlerBase::enableReplyInReplyMap(command, enabledReplies, true,
mpsoc::TM_CAM_CMD_RPT);
result = DeviceHandlerBase::enableReplyInReplyMap(
command, enabledReplies, true,
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT));
if (result != RETURN_OK) {
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id "
<< mpsoc::TM_CAM_CMD_RPT << " not in replyMap" << std::endl;
<< static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT)
<< " not in replyMap" << std::endl;
return result;
}
break;
}
case mpsoc::OBSW_RESET_SEQ_COUNT:
case PlocMpSoCCommands::OBSW_RESET_SEQ_COUNT:
break;
default:
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Unknown command id" << std::endl;
@ -750,32 +718,36 @@ ReturnValue_t PlocMPSoCHandler::enableReplyInReplyMap(DeviceCommandMap::iterator
* Every command causes at least one acknowledgment and one execution report. Therefore both
* replies will be enabled here.
*/
result =
DeviceHandlerBase::enableReplyInReplyMap(command, enabledReplies, true, mpsoc::ACK_REPORT);
result = DeviceHandlerBase::enableReplyInReplyMap(
command, enabledReplies, true, static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT));
if (result != RETURN_OK) {
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id " << mpsoc::ACK_REPORT
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id "
<< static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT)
<< " not in replyMap" << std::endl;
}
result =
DeviceHandlerBase::enableReplyInReplyMap(command, enabledReplies, true, mpsoc::EXE_REPORT);
result = DeviceHandlerBase::enableReplyInReplyMap(
command, enabledReplies, true, static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT));
if (result != RETURN_OK) {
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id " << mpsoc::EXE_REPORT
sif::debug << "PlocMPSoCHandler::enableReplyInReplyMap: Reply with id "
<< static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT)
<< " not in replyMap" << std::endl;
}
switch (command->first) {
case mpsoc::TC_REPLAY_WRITE_SEQUENCE: {
DeviceReplyIter iter = deviceReplyMap.find(mpsoc::EXE_REPORT);
switch (enumCommand) {
case PlocMpSoCCommands::TC_REPLAY_WRITE_SEQUENCE: {
DeviceReplyIter iter =
deviceReplyMap.find(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT));
// Overwrite delay cycles because replay write sequence command can required up to
// 30 seconds for execution
iter->second.delayCycles = mpsoc::TC_WRITE_SEQ_EXECUTION_DELAY;
break;
}
case mpsoc::TC_DOWNLINK_PWR_ON: {
DeviceReplyIter iter = deviceReplyMap.find(mpsoc::EXE_REPORT);
case PlocMpSoCCommands::TC_DOWNLINK_PWR_ON: {
DeviceReplyIter iter =
deviceReplyMap.find(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT));
//
iter->second.delayCycles = mpsoc::TC_DOWNLINK_PWR_ON;
iter->second.delayCycles = mpsoc::TC_DOWNLINK_PWR_ON_EXECUTION_DELAY;
break;
}
default:
@ -786,24 +758,24 @@ ReturnValue_t PlocMPSoCHandler::enableReplyInReplyMap(DeviceCommandMap::iterator
}
void PlocMPSoCHandler::setNextReplyId() {
switch (getPendingCommand()) {
case mpsoc::TC_MEM_READ:
nextReplyId = mpsoc::TM_MEMORY_READ_REPORT;
switch (PlocMpSoCCommands(getPendingCommand())) {
case PlocMpSoCCommands::TC_MEM_READ:
nextReplyId = PlocMpSoCCommands::TM_MEMORY_READ_REPORT;
break;
default:
/* If no telemetry is expected the next reply is always the execution report */
nextReplyId = mpsoc::EXE_REPORT;
nextReplyId = PlocMpSoCCommands::EXE_REPORT;
break;
}
}
size_t PlocMPSoCHandler::getNextReplyLength(DeviceCommandId_t commandId) {
size_t replyLen = 0;
if (nextReplyId == mpsoc::NONE) {
if (nextReplyId == PlocMpSoCCommands::NONE) {
return replyLen;
}
DeviceReplyIter iter = deviceReplyMap.find(nextReplyId);
DeviceReplyIter iter = deviceReplyMap.find(static_cast<DeviceCommandId_t>(nextReplyId));
if (iter != deviceReplyMap.end()) {
if (iter->second.delayCycles == 0) {
@ -811,11 +783,11 @@ size_t PlocMPSoCHandler::getNextReplyLength(DeviceCommandId_t commandId) {
return replyLen;
}
switch (nextReplyId) {
case mpsoc::TM_MEMORY_READ_REPORT: {
case PlocMpSoCCommands::TM_MEMORY_READ_REPORT: {
replyLen = tmMemReadReport.rememberRequestedSize;
break;
}
case mpsoc::TM_CAM_CMD_RPT:
case PlocMpSoCCommands::TM_CAM_CMD_RPT:
// Read acknowledgment, camera and execution report in one go because length of camera
// report is not fixed
replyLen = SpacePacket::PACKET_MAX_SIZE;
@ -827,7 +799,8 @@ size_t PlocMPSoCHandler::getNextReplyLength(DeviceCommandId_t commandId) {
}
} else {
sif::debug << "PlocMPSoCHandler::getNextReplyLength: No entry for reply with reply id "
<< std::hex << nextReplyId << " in deviceReplyMap" << std::endl;
<< std::hex << static_cast<DeviceCommandId_t>(nextReplyId) << " in deviceReplyMap"
<< std::endl;
}
return replyLen;
@ -924,31 +897,33 @@ void PlocMPSoCHandler::handleDeviceTM(const uint8_t* data, size_t dataSize,
}
void PlocMPSoCHandler::disableAllReplies() {
using namespace mpsoc;
DeviceReplyMap::iterator iter;
/* Disable ack reply */
iter = deviceReplyMap.find(ACK_REPORT);
iter = deviceReplyMap.find(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::ACK_REPORT));
DeviceReplyInfo* info = &(iter->second);
info->delayCycles = 0;
info->command = deviceCommandMap.end();
DeviceCommandId_t commandId = getPendingCommand();
PlocMpSoCCommands enumCommand = PlocMpSoCCommands(commandId);
/* If the command expects a telemetry packet the appropriate tm reply will be disabled here */
switch (commandId) {
case TC_MEM_WRITE:
switch (enumCommand) {
case PlocMpSoCCommands::TC_MEM_WRITE:
break;
case TC_MEM_READ: {
iter = deviceReplyMap.find(TM_MEMORY_READ_REPORT);
case PlocMpSoCCommands::TC_MEM_READ: {
iter = deviceReplyMap.find(
static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_MEMORY_READ_REPORT));
info = &(iter->second);
info->delayCycles = 0;
info->active = false;
info->command = deviceCommandMap.end();
break;
}
case TC_CAM_CMD_SEND: {
iter = deviceReplyMap.find(TM_CAM_CMD_RPT);
case PlocMpSoCCommands::TC_CAM_CMD_SEND: {
iter = deviceReplyMap.find(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::TM_CAM_CMD_RPT));
info = &(iter->second);
info->delayCycles = 0;
info->active = false;
@ -964,11 +939,11 @@ void PlocMPSoCHandler::disableAllReplies() {
/* We always need to disable the execution report reply here */
disableExeReportReply();
nextReplyId = mpsoc::NONE;
nextReplyId = PlocMpSoCCommands::NONE;
}
void PlocMPSoCHandler::sendFailureReport(DeviceCommandId_t replyId, ReturnValue_t status) {
DeviceReplyIter iter = deviceReplyMap.find(replyId);
void PlocMPSoCHandler::sendFailureReport(PlocMpSoCCommands replyId, ReturnValue_t status) {
DeviceReplyIter iter = deviceReplyMap.find(static_cast<DeviceCommandId_t>(replyId));
if (iter == deviceReplyMap.end()) {
sif::debug << "PlocMPSoCHandler::sendFailureReport: Reply not in reply map" << std::endl;
return;
@ -985,7 +960,8 @@ void PlocMPSoCHandler::sendFailureReport(DeviceCommandId_t replyId, ReturnValue_
}
void PlocMPSoCHandler::disableExeReportReply() {
DeviceReplyIter iter = deviceReplyMap.find(mpsoc::EXE_REPORT);
DeviceReplyIter iter =
deviceReplyMap.find(static_cast<DeviceCommandId_t>(PlocMpSoCCommands::EXE_REPORT));
DeviceReplyInfo* info = &(iter->second);
info->delayCycles = 0;
info->command = deviceCommandMap.end();

View File

@ -48,8 +48,7 @@ class PlocMPSoCHandler : public DeviceHandlerBase, public CommandsActionsIF {
object_id_t supervisorHandler);
virtual ~PlocMPSoCHandler();
virtual ReturnValue_t initialize() override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ReturnValue_t executeAction(Action* action) override;
void performOperationHook() override;
MessageQueueIF* getCommandQueuePtr() override;
void stepSuccessfulReceived(ActionId_t actionId, uint8_t step) override;
@ -58,6 +57,22 @@ class PlocMPSoCHandler : public DeviceHandlerBase, public CommandsActionsIF {
void completionSuccessfulReceived(ActionId_t actionId) override;
void completionFailedReceived(ActionId_t actionId, ReturnValue_t returnCode) override;
ReturnValue_t handleAction(PlocMpSoCMemWriteAction* action);
ReturnValue_t handleAction(PlocMpSoCMemReadAction* action);
ReturnValue_t handleAction(PlocMpSoCFlashDeleteAction* action);
ReturnValue_t handleAction(PlocMpSoCReplayStartAction* action);
ReturnValue_t handleAction(PlocMpSoCReplayStopAction* action);
ReturnValue_t handleAction(PlocMpSoCReplayWriteSequenceAction* action);
ReturnValue_t handleAction(PlocMpSoCDownlinkPwrOnAction* action);
ReturnValue_t handleAction(PlocMpSoCDownlinkPwrOffAction* action);
ReturnValue_t handleAction(PlocMpSoCModeReplayAction* action);
ReturnValue_t handleAction(PlocMpSoCCamCmdSendAction* action);
ReturnValue_t handleAction(PlocMpSoCModeIdleAction* action);
ReturnValue_t handleAction(PlocMpSoCFlashWriteAction* action);
ReturnValue_t handleAction(PlocMpSoCUartTxTristateAction* action);
ReturnValue_t handleAction(PlocMpSoCReleaseUartTxAction* action);
ReturnValue_t handleAction(PlocMpSoCObswResetSeqCountAction* action);
protected:
void doStartUp() override;
void doShutDown() override;
@ -121,7 +136,7 @@ class PlocMPSoCHandler : public DeviceHandlerBase, public CommandsActionsIF {
* because the PLOC sends as reply to each command at least one acknowledgment and execution
* report.
*/
DeviceCommandId_t nextReplyId = mpsoc::NONE;
PlocMpSoCCommands nextReplyId = PlocMpSoCCommands::NONE;
UartComIF* uartComIf = nullptr;
@ -172,6 +187,7 @@ class PlocMPSoCHandler : public DeviceHandlerBase, public CommandsActionsIF {
ReturnValue_t prepareTcReplayWriteSequence(const uint8_t* commandData, size_t commandDataLen);
ReturnValue_t prepareTcCamCmdSend(const uint8_t* commandData, size_t commandDataLen);
ReturnValue_t prepareTcModeIdle();
/**
* @brief Copies space packet into command buffer
*/
@ -248,7 +264,7 @@ class PlocMPSoCHandler : public DeviceHandlerBase, public CommandsActionsIF {
* @param replyId The id of the reply which signals a failure.
* @param status A status byte which gives information about the failure type.
*/
void sendFailureReport(DeviceCommandId_t replyId, ReturnValue_t status);
void sendFailureReport(PlocMpSoCCommands replyId, ReturnValue_t status);
/**
* @brief This function disables the execution report reply. Within this function also the

View File

@ -10,7 +10,7 @@
#include "fsfw/tasks/ExecutableObjectIF.h"
#include "fsfw/tmtcservices/SourceSequenceCounter.h"
#include "fsfw_hal/linux/uart/UartComIF.h"
#include "linux/devices/devicedefinitions/PlocMPSoCDefinitions.h"
#include "linux/devices/devicedefinitions/PlocMPSoCCommonDefinitions.h"
#ifdef XIPHOS_Q7S
#include "bsp_q7s/memory/SdCardManager.h"
#endif

View File

@ -40,40 +40,27 @@ ReturnValue_t PlocMemoryDumper::performOperation(uint8_t operationCode) {
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t PlocMemoryDumper::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t PlocMemoryDumper::executeAction(Action* action) { return action->handle(); }
ReturnValue_t PlocMemoryDumper::handleAction(DumpMemoryAction* action) {
if (state != State::IDLE) {
return IS_BUSY;
}
switch (actionId) {
case DUMP_MRAM: {
size_t deserializeSize = sizeof(mram.startAddress) + sizeof(mram.endAddress);
SerializeAdapter::deSerialize(&mram.startAddress, &data, &deserializeSize,
SerializeIF::Endianness::BIG);
SerializeAdapter::deSerialize(&mram.endAddress, &data, &deserializeSize,
SerializeIF::Endianness::BIG);
if (mram.endAddress > MAX_MRAM_ADDRESS) {
return MRAM_ADDRESS_TOO_HIGH;
}
if (mram.endAddress <= mram.startAddress) {
return MRAM_INVALID_ADDRESS_COMBINATION;
}
state = State::COMMAND_FIRST_MRAM_DUMP;
break;
}
default: {
sif::warning << "PlocMemoryDumper::executeAction: Received command with invalid action id"
<< std::endl;
return INVALID_ACTION_ID;
}
if (action->endAddress <= action->startAddress) {
return MRAM_INVALID_ADDRESS_COMBINATION;
}
mram.startAddress = action->startAddress;
mram.endAddress = action->endAddress;
state = State::COMMAND_FIRST_MRAM_DUMP;
return EXECUTION_FINISHED;
}
MessageQueueId_t PlocMemoryDumper::getCommandQueue() const { return commandQueue->getId(); }
ActionHelper* PlocMemoryDumper::getActionHelper() { return &actionHelper; }
MessageQueueIF* PlocMemoryDumper::getCommandQueuePtr() { return commandQueue; }
void PlocMemoryDumper::readCommandQueue() {

View File

@ -2,6 +2,7 @@
#define MISSION_DEVICES_PLOCMEMORYDUMPER_H_
#include <linux/devices/devicedefinitions/PlocMemDumpDefinitions.h>
#include <linux/devices/devicedefinitions/PlocMemDumpActions.h>
#include <linux/devices/devicedefinitions/PlocSupervisorDefinitions.h>
#include "OBSWConfig.h"
@ -37,8 +38,9 @@ class PlocMemoryDumper : public SystemObject,
virtual ~PlocMemoryDumper();
ReturnValue_t performOperation(uint8_t operationCode = 0) override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size);
ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(DumpMemoryAction* action);
ActionHelper *getActionHelper() override;
MessageQueueId_t getCommandQueue() const;
ReturnValue_t initialize() override;
MessageQueueIF* getCommandQueuePtr() override;
@ -53,9 +55,6 @@ class PlocMemoryDumper : public SystemObject,
static const uint8_t INTERFACE_ID = CLASS_ID::PLOC_MEMORY_DUMPER;
//! [EXPORT] : [COMMENT] The capacity of the MRAM amounts to 512 kB. Thus the maximum address must
//! not be higher than 0x7d000.
static const ReturnValue_t MRAM_ADDRESS_TOO_HIGH = MAKE_RETURN_CODE(0xA0);
//! [EXPORT] : [COMMENT] The specified end address is lower than the start address
static const ReturnValue_t MRAM_INVALID_ADDRESS_COMBINATION = MAKE_RETURN_CODE(0xA1);
@ -73,7 +72,6 @@ class PlocMemoryDumper : public SystemObject,
// Maximum size of mram dump which can be retrieved with one command
static const uint32_t MAX_MRAM_DUMP_SIZE = 100000;
static const uint32_t MAX_MRAM_ADDRESS = 0x7d000;
MessageQueueIF* commandQueue = nullptr;

View File

@ -80,12 +80,15 @@ void PlocSupervisorHandler::performOperationHook() {
}
}
ReturnValue_t PlocSupervisorHandler::executeAction(ActionId_t actionId,
MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t PlocSupervisorHandler::executeAction(Action* action) {
using namespace supv;
ReturnValue_t result = RETURN_OK;
//TODO
ActionId_t actionId = 0;
uint8_t *data = nullptr;
size_t size = 0;
switch (actionId) {
case TERMINATE_SUPV_HELPER: {
supvHelper->stopProcess();
@ -138,7 +141,7 @@ ReturnValue_t PlocSupervisorHandler::executeAction(ActionId_t actionId,
default:
break;
}
return DeviceHandlerBase::executeAction(actionId, commandedBy, data, size);
return DeviceHandlerBase::executeAction(action);
}
void PlocSupervisorHandler::doStartUp() {
@ -828,7 +831,7 @@ void PlocSupervisorHandler::handleEvent(EventMessage* eventMessage) {
event == PlocSupvHelper::SUPV_UPDATE_SUCCESSFUL ||
event == PlocSupvHelper::SUPV_CONTINUE_UPDATE_FAILED ||
event == PlocSupvHelper::SUPV_CONTINUE_UPDATE_SUCCESSFUL) {
result = this->executeAction(supv::SHUTDOWN_MPSOC, NO_COMMANDER, nullptr, 0);
//TODO result = this->executeAction(supv::SHUTDOWN_MPSOC, NO_COMMANDER, nullptr, 0);
if (result != RETURN_OK) {
triggerEvent(SUPV_MPSOC_SHUWDOWN_BUILD_FAILED);
sif::warning << "PlocSupervisorHandler::handleEvent: Failed to build MPSoC shutdown "

View File

@ -34,8 +34,7 @@ class PlocSupervisorHandler : public DeviceHandlerBase {
virtual ReturnValue_t initialize() override;
void performOperationHook() override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ReturnValue_t executeAction(Action* action) override;
protected:
void doStartUp() override;

View File

@ -91,10 +91,14 @@ ReturnValue_t StarTrackerHandler::initialize() {
return RETURN_OK;
}
ReturnValue_t StarTrackerHandler::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t StarTrackerHandler::executeAction(Action* action) {
ReturnValue_t result = RETURN_OK;
//TODO
ActionId_t actionId = 0;
uint8_t *data = nullptr;
size_t size = 0;
switch (actionId) {
case (startracker::STOP_IMAGE_LOADER): {
strHelper->stopProcess();
@ -209,7 +213,7 @@ ReturnValue_t StarTrackerHandler::executeAction(ActionId_t actionId, MessageQueu
default:
break;
}
return DeviceHandlerBase::executeAction(actionId, commandedBy, data, size);
return DeviceHandlerBase::executeAction(action);
}
void StarTrackerHandler::performOperationHook() {

View File

@ -44,8 +44,7 @@ class StarTrackerHandler : public DeviceHandlerBase {
* @brief Overwrite this function from DHB to handle commands executed by the str image
* loader task.
*/
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ReturnValue_t executeAction(Action* action) override;
void performOperationHook() override;

View File

@ -3,7 +3,7 @@
#include <cstdint>
#include "common/config/commonSubsystemIds.h"
#include <config/commonSubsystemIds.h>
#include "fsfw/events/fwSubsystemIdRanges.h"
/**

View File

@ -2,6 +2,7 @@
#define LINUX_FSFWCONFIG_OBJECTS_SYSTEMOBJECTLIST_H_
#include <fsfw/objectmanager/frameworkObjects.h>
#include <fsfw/introspection/ClasslessEnum.h>
#include <cstdint>
@ -33,36 +34,34 @@ Fourth byte is a unique counter.
*/
namespace objects {
enum sourceObjects : uint32_t {
FSFW_CLASSLESS_ENUM(systemObjects, uint32_t,
/* 0x53 reserved for FSFW */
FW_ADDRESS_START = PUS_SERVICE_1_VERIFICATION,
FW_ADDRESS_END = TIME_STAMPER,
PUS_SERVICE_6 = 0x51000500,
((PUS_SERVICE_6, 0x51000500, "PUS_SERVICE_6"))
CCSDS_IP_CORE_BRIDGE = 0x73500000,
TM_FUNNEL = 0x73000100,
((CCSDS_IP_CORE_BRIDGE, 0x73500000, "CCSDS_IP_CORE_BRIDGE"))
((TM_FUNNEL, 0x73000100, "TM_FUNNEL"))
/* 0x49 ('I') for Communication Interfaces **/
ARDUINO_COM_IF = 0x49000000,
CSP_COM_IF = 0x49050001,
I2C_COM_IF = 0x49040002,
UART_COM_IF = 0x49030003,
SPI_MAIN_COM_IF = 0x49020004,
GPIO_IF = 0x49010005,
SPI_RW_COM_IF = 0x49020005,
SPI_RTD_COM_IF = 0x49020006,
((ARDUINO_COM_IF, 0x49000000, "ARDUINO_COM_IF"))
((CSP_COM_IF, 0x49050001, "CSP_COM_IF"))
((I2C_COM_IF, 0x49040002, "I2C_COM_IF"))
((UART_COM_IF, 0x49030003, "UART_COM_IF"))
((SPI_MAIN_COM_IF, 0x49020004, "SPI_MAIN_COM_IF"))
((GPIO_IF, 0x49010005, "GPIO_IF"))
((SPI_RW_COM_IF, 0x49020005, "SPI_RW_COM_IF"))
((SPI_RTD_COM_IF, 0x49020006, "SPI_RTD_COM_IF"))
/* 0x54 ('T') for test handlers */
TEST_TASK = 0x54694269,
LIBGPIOD_TEST = 0x54123456,
SPI_TEST = 0x54000010,
UART_TEST = 0x54000020,
I2C_TEST = 0x54000030,
DUMMY_INTERFACE = 0x5400CAFE,
DUMMY_HANDLER = 0x5400AFFE,
P60DOCK_TEST_TASK = 0x00005060,
DUMMY_COM_IF = 0x54000040
};
((TEST_TASK, 0x54694269, "TEST_TASK"))
((LIBGPIOD_TEST, 0x54123456, "LIBGPIOD_TEST"))
((SPI_TEST, 0x54000010, "SPI_TEST"))
((UART_TEST, 0x54000020, "UART_TEST"))
((I2C_TEST, 0x54000030, "I2C_TEST"))
((DUMMY_INTERFACE, 0x5400CAFE, "DUMMY_INTERFACE"))
((DUMMY_HANDLER, 0x5400AFFE, "DUMMY_HANDLER"))
((P60DOCK_TEST_TASK, 0x00005060, "P60DOCK_TEST_TASK"))
((DUMMY_COM_IF, 0x54000040, "DUMMY_COM_IF"))
)
}
#endif /* LINUX_FSFWCONFIG_OBJECTS_SYSTEMOBJECTLIST_H_ */

View File

@ -1,7 +1,7 @@
#ifndef FSFWCONFIG_RETURNVALUES_CLASSIDS_H_
#define FSFWCONFIG_RETURNVALUES_CLASSIDS_H_
#include <common/config/commonClassIds.h>
#include <config/commonClassIds.h>
#include <fsfw/returnvalues/FwClassIds.h>
/**

View File

@ -0,0 +1,24 @@
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
class PdecHandler;
FSFW_ENUM(PdecCommands, DeviceCommandId_t,((PRINT_CLCW, "Print CLCW")) ((PRINT_PDEC_MON, "Print PDEC Mon Status")))
class PdecPrintClcwAction
: public TemplateAction<PdecHandler, PdecPrintClcwAction,
PdecCommands> {
public:
PdecPrintClcwAction(PdecHandler *owner)
: TemplateAction(owner, PdecCommands::PRINT_CLCW) {};
};
class PdecPrintMonAction
: public TemplateAction<PdecHandler, PdecPrintMonAction,
PdecCommands> {
public:
PdecPrintMonAction(PdecHandler *owner)
: TemplateAction(owner, PdecCommands::PRINT_PDEC_MON) {};
};

View File

@ -79,6 +79,8 @@ ReturnValue_t PdecHandler::initialize() {
MessageQueueId_t PdecHandler::getCommandQueue() const { return commandQueue->getId(); }
ActionHelper* PdecHandler::getActionHelper() { return &actionHelper; }
void PdecHandler::writePdecConfig() {
PdecConfig pdecConfig;
@ -514,16 +516,14 @@ std::string PdecHandler::getMonStatusString(uint32_t status) {
}
}
ReturnValue_t PdecHandler::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
switch (actionId) {
case PRINT_CLCW:
printClcw();
return EXECUTION_FINISHED;
case PRINT_PDEC_MON:
printPdecMon();
return EXECUTION_FINISHED;
default:
return COMMAND_NOT_IMPLEMENTED;
}
ReturnValue_t PdecHandler::executeAction(Action* action) { return action->handle(); }
ReturnValue_t PdecHandler::handleAction(PdecPrintClcwAction* action) {
printClcw();
return EXECUTION_FINISHED;
}
ReturnValue_t PdecHandler::handleAction(PdecPrintMonAction* action) {
printPdecMon();
return EXECUTION_FINISHED;
}

View File

@ -3,6 +3,7 @@
#include "OBSWConfig.h"
#include "PdecConfig.h"
#include "PdecDefinitions.h"
#include "fsfw/action/ActionHelper.h"
#include "fsfw/action/HasActionsIF.h"
#include "fsfw/objectmanager/SystemObject.h"
@ -57,8 +58,10 @@ class PdecHandler : public SystemObject,
MessageQueueId_t getCommandQueue() const;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ActionHelper* getActionHelper() override;
ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(PdecPrintClcwAction* action);
ReturnValue_t handleAction(PdecPrintMonAction* action);
static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::PDEC_HANDLER;
@ -89,9 +92,6 @@ class PdecHandler : public SystemObject,
static const ReturnValue_t AD_DISCARDED_WAIT = MAKE_RETURN_CODE(0xA4);
static const ReturnValue_t AD_DISCARDED_NS_VS = MAKE_RETURN_CODE(0xA5);
//! [EXPORT] : [COMMENT] Received action message with unknown action id
static const ReturnValue_t COMMAND_NOT_IMPLEMENTED = MAKE_RETURN_CODE(0xB0);
static const ReturnValue_t NO_REPORT = MAKE_RETURN_CODE(0xA6);
//! Error in version number and reserved A and B fields
static const ReturnValue_t ERROR_VERSION_NUMBER = MAKE_RETURN_CODE(0xA7);
@ -110,11 +110,6 @@ class PdecHandler : public SystemObject,
static const uint32_t QUEUE_SIZE = common::CCSDS_HANDLER_QUEUE_SIZE;
// Action IDs
static const ActionId_t PRINT_CLCW = 0;
// Print PDEC monitor register
static const ActionId_t PRINT_PDEC_MON = 1;
static const uint8_t STAT_POSITION = 31;
static const uint8_t FRAME_ANA_POSITION = 28;
static const uint8_t IREASON_POSITION = 25;
@ -371,6 +366,9 @@ class PdecHandler : public SystemObject,
ActionHelper actionHelper;
PdecPrintClcwAction pdecPrintClcwAction = PdecPrintClcwAction(this);
PdecPrintMonAction pdecPrintMonAction = PdecPrintMonAction(this);
StorageManagerIF* tcStore = nullptr;
MessageQueueIF* commandQueue = nullptr;

View File

@ -61,6 +61,10 @@ ReturnValue_t AcsController::checkModeCommand(Mode_t mode, Submode_t submode,
return HasReturnvaluesIF::RETURN_OK;
}
ModeDefinitionHelper AcsController::getModeDefinitionHelper() {
return ModeDefinitionHelper::create<ControllerModes, DefaultSubmode>();
}
void AcsController::copyMgmData() {
{
PoolReadGuard pg(&mgm0Lis3Set);

View File

@ -30,6 +30,8 @@ class AcsController : public ExtendedControllerBase {
ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode,
uint32_t* msToReachTheMode) override;
ModeDefinitionHelper getModeDefinitionHelper() override;
// MGMs
acsctrl::MgmData mgmData;

View File

@ -231,6 +231,10 @@ ReturnValue_t ThermalController::checkModeCommand(Mode_t mode, Submode_t submode
return RETURN_OK;
}
ModeDefinitionHelper ThermalController::getModeDefinitionHelper() {
return ModeDefinitionHelper::create<ControllerModes, DefaultSubmode>();
}
void ThermalController::copySensors() {
PoolReadGuard pg0(&max31865Set0);
if (pg0.getReadResult() == HasReturnvaluesIF::RETURN_OK) {

View File

@ -27,6 +27,8 @@ class ThermalController : public ExtendedControllerBase {
virtual ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode,
uint32_t* msToReachTheMode) override;
ModeDefinitionHelper getModeDefinitionHelper() override;
private:
static const uint32_t DELAY = 500;

View File

@ -13,7 +13,7 @@ ACUHandler::~ACUHandler() {}
ReturnValue_t ACUHandler::buildNormalDeviceCommand(DeviceCommandId_t *id) {
*id = GOMSPACE::REQUEST_HK_TABLE;
return buildCommandFromCommand(*id, NULL, 0);
return requestHkTableAction.handle();
}
void ACUHandler::fillCommandAndReplyMap() { GomspaceDeviceHandler::fillCommandAndReplyMap(); }

View File

@ -33,59 +33,11 @@ ReturnValue_t GomspaceDeviceHandler::buildTransitionDeviceCommand(DeviceCommandI
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::buildCommandFromCommand(DeviceCommandId_t deviceCommand,
const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t result = childCommandHook(deviceCommand, commandData, commandDataLen);
switch (deviceCommand) {
case (GOMSPACE::PING): {
result = generatePingCommand(commandData, commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
break;
}
case (GOMSPACE::REBOOT): {
generateRebootCommand();
break;
}
case (GOMSPACE::PARAM_SET): {
result = generateSetParamCommand(commandData, commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
break;
}
case (GOMSPACE::PARAM_GET): {
result = generateGetParamCommand(commandData, commandDataLen);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
break;
}
case (GOMSPACE::GNDWDT_RESET): {
result = generateResetWatchdogCmd();
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
break;
}
case (GOMSPACE::PRINT_SWITCH_V_I):
case (GOMSPACE::PRINT_LATCHUPS): {
result = printStatus(deviceCommand);
break;
}
case (GOMSPACE::REQUEST_HK_TABLE): {
result = generateRequestFullHkTableCmd(hkTableReplySize);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
break;
}
default:
return DeviceHandlerIF::COMMAND_NOT_IMPLEMENTED;
}
return HasReturnvaluesIF::RETURN_OK;
ReturnValue_t GomspaceDeviceHandler::handleAction(PrintSwitchVIAction* action) {
return printStatus(action->getId());
}
ReturnValue_t GomspaceDeviceHandler::handleAction(PrintLatchupsAction* action) {
return printStatus(action->getId());
}
void GomspaceDeviceHandler::fillCommandAndReplyMap() {
@ -172,7 +124,8 @@ ReturnValue_t GomspaceDeviceHandler::interpretDeviceReply(DeviceCommandId_t id,
if (*packet != PARAM_SET_OK) {
return HasReturnvaluesIF::RETURN_FAILED;
}
setParamCallback(setParamCacher, true);
// TODO fix
setParamCallback(setParamCacher.getParameter(), setParamCacher.getParameter(), setParamCacher.getParameterSize(), true);
break;
}
case (GOMSPACE::REQUEST_HK_TABLE): {
@ -187,29 +140,23 @@ ReturnValue_t GomspaceDeviceHandler::interpretDeviceReply(DeviceCommandId_t id,
void GomspaceDeviceHandler::setNormalDatapoolEntriesInvalid() {}
ReturnValue_t GomspaceDeviceHandler::generateSetParamCommand(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t result =
setParamCacher.deSerialize(&commandData, &commandDataLen, SerializeIF::Endianness::BIG);
ReturnValue_t GomspaceDeviceHandler::handleAction(ParamSetAction* action) {
// This breaks layering but I really don't want to accept this command..
if (setParamCacher.getAddress() == PDU2::CONFIG_ADDRESS_OUT_EN_Q7S and
if (action->address == PDU2::CONFIG_ADDRESS_OUT_EN_Q7S and
this->getObjectId() == objects::PDU2_HANDLER) {
triggerEvent(power::SWITCHING_Q7S_DENIED, 0, 0);
return HasReturnvaluesIF::RETURN_FAILED;
}
if (result != HasReturnvaluesIF::RETURN_OK) {
sif::error << "GomspaceDeviceHandler: Failed to deserialize set parameter "
"message"
<< std::endl;
return result;
}
result = setParamCallback(setParamCacher, false);
//cache for later use
setParamCacher.set(action->address, action->parameter,
static_cast<uint8_t>(action->parameterSize.value));
ReturnValue_t result = setParamCallback(action->address, action->parameter,
static_cast<uint8_t>(action->parameterSize.value), false);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
/* Get and check address */
uint16_t address = setParamCacher.getAddress();
if (address > maxConfigTableAddress) {
if (action->address > maxConfigTableAddress) {
sif::error << "GomspaceDeviceHandler: Invalid address for set parameter "
<< "action" << std::endl;
return INVALID_ADDRESS;
@ -219,13 +166,52 @@ ReturnValue_t GomspaceDeviceHandler::generateSetParamCommand(const uint8_t* comm
uint16_t total = 0;
/* CSP reply only contains the transaction state */
uint16_t querySize = 1;
const uint8_t* parameterPtr = setParamCacher.getParameter();
uint8_t parameterSize = setParamCacher.getParameterSize();
uint16_t payloadlength = sizeof(address) + parameterSize;
size_t parameterSize = 0;
uint8_t parameterBytes[4];
uint8_t* uselessPointer = parameterBytes;
switch (action->parameterSize.value) {
case ParamSetAction::ParameterByteSize::ONE_BYTE: {
if (action->parameter > 255) {
return INVALID_PARAMETERS;
}
uint8_t oneByte = action->parameter.value;
result = SerializeAdapter::serialize<uint8_t>(&oneByte, &uselessPointer, &parameterSize,
sizeof(parameterBytes),
SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
parameterSize = 1;
} break;
case ParamSetAction::ParameterByteSize::TWO_BYTES: {
if (action->parameter > 65535) {
return INVALID_PARAMETERS;
}
uint16_t twoBytes = action->parameter.value;
result = SerializeAdapter::serialize<uint16_t>(&twoBytes, &uselessPointer, &parameterSize,
sizeof(parameterBytes),
SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
parameterSize = 2;
} break;
case ParamSetAction::ParameterByteSize::FOUR_BYTES:
result = SerializeAdapter::serialize<uint32_t>(&(action->parameter.value), &uselessPointer,
&parameterSize, sizeof(parameterBytes),
SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
return result;
}
parameterSize = 4;
break;
}
uint16_t payloadlength = sizeof(action->address) + parameterSize;
/* Generate command for CspComIF */
CspSetParamCommand setParamCmd(querySize, payloadlength, checksum, seq, total, address,
parameterPtr, parameterSize);
CspSetParamCommand setParamCmd(querySize, payloadlength, checksum, seq, total, action->address,
parameterBytes, parameterSize);
size_t cspPacketLen = 0;
uint8_t* buffer = cspPacket;
result = setParamCmd.serialize(&buffer, &cspPacketLen, sizeof(cspPacket),
@ -249,34 +235,18 @@ ReturnValue_t GomspaceDeviceHandler::generateSetParamCommand(const uint8_t* comm
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::generateGetParamCommand(const uint8_t* commandData,
size_t commandDataLen) {
ReturnValue_t GomspaceDeviceHandler::handleAction(ParamGetAction* action) {
ReturnValue_t result;
/* Unpack the received action message */
GetParamMessageUnpacker getParamMessage;
result = getParamMessage.deSerialize(&commandData, &commandDataLen, SerializeIF::Endianness::BIG);
if (result != HasReturnvaluesIF::RETURN_OK) {
sif::error << "Failed to deserialize message to extract information "
"from get parameter message"
<< std::endl;
return result;
}
/* Get an check table id to read from */
uint8_t tableId = getParamMessage.getTableId();
if (tableId != CONFIG_TABLE_ID && tableId != HK_TABLE_ID) {
sif::error << "GomspaceDeviceHandler: Invalid table id in get parameter"
" message"
<< std::endl;
return INVALID_TABLE_ID;
}
auto tableId = action->tableId.value;
/* Get and check address */
uint16_t address = getParamMessage.getAddress();
if (address > maxHkTableAddress && tableId == HK_TABLE_ID) {
uint16_t address = action->address;
if (address > maxHkTableAddress && tableId == ParamGetAction::TableId::HK_TABLE_ID) {
sif::error << "GomspaceDeviceHandler: Invalid address to get parameter from "
<< "housekeeping table" << std::endl;
return INVALID_ADDRESS;
}
if (address > maxConfigTableAddress && tableId == CONFIG_TABLE_ID) {
if (address > maxConfigTableAddress && tableId == ParamGetAction::TableId::CONFIG_TABLE_ID) {
sif::error << "GomspaceDeviceHandler: Invalid address to get parameter from "
<< "configuration table" << std::endl;
return INVALID_ADDRESS;
@ -285,16 +255,11 @@ ReturnValue_t GomspaceDeviceHandler::generateGetParamCommand(const uint8_t* comm
uint16_t checksum = GOMSPACE::IGNORE_CHECKSUM;
uint16_t seq = 0;
uint16_t total = 0;
uint8_t parameterSize = getParamMessage.getParameterSize();
if (parameterSize > sizeof(uint32_t)) {
sif::error << "GomspaceDeviceHandler: GET_PARAM: Invalid parameter "
<< "size" << std::endl;
return INVALID_PARAM_SIZE;
}
uint8_t parameterSize = static_cast<uint8_t>(action->parameterSize.value);
uint16_t querySize = parameterSize + GOMSPACE::GS_HDR_LENGTH;
/* Generate the CSP command to send to the P60 Dock */
CspGetParamCommand getParamCmd(querySize, tableId, length, checksum, seq, total, address);
CspGetParamCommand getParamCmd(querySize, static_cast<uint8_t>(tableId), length, checksum, seq, total, address);
size_t cspPacketLen = 0;
uint8_t* buffer = cspPacket;
result = getParamCmd.serialize(&buffer, &cspPacketLen, sizeof(cspPacket),
@ -303,12 +268,14 @@ ReturnValue_t GomspaceDeviceHandler::generateGetParamCommand(const uint8_t* comm
sif::error << "GomspaceDeviceHandler: Failed to serialize command to "
<< "get parameter" << std::endl;
}
if (cspPacketLen > MAX_PACKET_LEN) {
// checked by serialize above
/* if (cspPacketLen > MAX_PACKET_LEN) {
sif::error << "GomspaceDeviceHandler: Received invalid get parameter "
"command"
<< std::endl;
return PACKET_TOO_LONG;
}
}*/
rawPacket = cspPacket;
rawPacketLen = cspPacketLen;
rememberRequestedSize = querySize;
@ -316,9 +283,8 @@ ReturnValue_t GomspaceDeviceHandler::generateGetParamCommand(const uint8_t* comm
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::generatePingCommand(const uint8_t* commandData,
size_t commandDataLen) {
CspPingCommand cspPingCommand(commandData, commandDataLen);
ReturnValue_t GomspaceDeviceHandler::handleAction(PingAction* action) {
CspPingCommand cspPingCommand(&action->pingData.value, 1); // TODO array
size_t cspPacketLen = 0;
uint8_t* buffer = cspPacket;
ReturnValue_t result = cspPingCommand.serialize(&buffer, &cspPacketLen, sizeof(cspPacket),
@ -327,24 +293,27 @@ ReturnValue_t GomspaceDeviceHandler::generatePingCommand(const uint8_t* commandD
sif::error << "GomspaceDeviceHandler: Failed to serialize ping command" << std::endl;
return result;
}
/* Checked by the serialize function
if (cspPacketLen > MAX_PACKET_LEN) {
sif::error << "GomspaceDeviceHandler: Received invalid ping message" << std::endl;
return PACKET_TOO_LONG;
}
}*/
rawPacket = cspPacket;
rawPacketLen = cspPacketLen;
rememberCommandId = GOMSPACE::PING;
return HasReturnvaluesIF::RETURN_OK;
}
void GomspaceDeviceHandler::generateRebootCommand() {
ReturnValue_t GomspaceDeviceHandler::handleAction(RebootAction* action) {
uint8_t cspPort = GOMSPACE::REBOOT_PORT;
uint16_t querySize = 0;
*cspPacket = GOMSPACE::REBOOT_PORT;
// TODO the following two lines look strange...
*(cspPacket + 1) = querySize;
size_t cspPacketLen = sizeof(cspPort) + sizeof(cspPacketLen);
rawPacket = cspPacket;
rawPacketLen = cspPacketLen;
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::childCommandHook(DeviceCommandId_t cmd,
@ -353,8 +322,8 @@ ReturnValue_t GomspaceDeviceHandler::childCommandHook(DeviceCommandId_t cmd,
return DeviceHandlerIF::COMMAND_NOT_IMPLEMENTED;
}
ReturnValue_t GomspaceDeviceHandler::setParamCallback(SetParamMessageUnpacker& unpacker,
bool afterExecution) {
ReturnValue_t GomspaceDeviceHandler::setParamCallback(uint16_t address, uint32_t value,
uint8_t valueBytes, bool afterExecution) {
return HasReturnvaluesIF::RETURN_OK;
}
@ -396,7 +365,7 @@ ReturnValue_t GomspaceDeviceHandler::initializePduPool(
return RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::generateResetWatchdogCmd() {
ReturnValue_t GomspaceDeviceHandler::handleAction(GndwdtResetAction* action) {
WatchdogResetCommand watchdogResetCommand;
size_t cspPacketLen = 0;
uint8_t* buffer = cspPacket;
@ -415,9 +384,9 @@ ReturnValue_t GomspaceDeviceHandler::generateResetWatchdogCmd() {
return HasReturnvaluesIF::RETURN_OK;
}
ReturnValue_t GomspaceDeviceHandler::generateRequestFullHkTableCmd(uint16_t hkTableReplySize) {
ReturnValue_t GomspaceDeviceHandler::handleAction(RequestHkTableAction* action) {
uint16_t querySize = hkTableReplySize;
uint8_t tableId = HK_TABLE_ID;
uint8_t tableId = static_cast<uint8_t>(ParamGetAction::TableId::HK_TABLE_ID);
RequestFullTableCommand requestFullTableCommand(querySize, tableId);
size_t cspPacketLen = 0;

View File

@ -4,6 +4,7 @@
#include <mission/devices/devicedefinitions/GomSpacePackets.h>
#include "fsfw/devicehandlers/DeviceHandlerBase.h"
#include "mission/devices/devicedefinitions/GomspaceActions.h"
#include "mission/devices/devicedefinitions/GomspaceDefinitions.h"
#include "returnvalues/classIds.h"
@ -48,12 +49,43 @@ class GomspaceDeviceHandler : public DeviceHandlerBase {
*/
void setModeNormal();
/**
* @brief Function to generate the ping command for the ComIF.
*/
ReturnValue_t handleAction(PingAction *action);
/**
* @brief Function to generate the command to reboot a gomspace device
* via the ComIF.
*/
ReturnValue_t handleAction(RebootAction *action);
/**
* @brief Function to generate the command to force a ground watchdog
* reset in a gomspace device.
*/
ReturnValue_t handleAction(GndwdtResetAction *action);
/**
* @brief Function to generate the command to get a parameter from a
* gomspace device. Command will be sent to the ComIF over the
* rawPacket buffer.
*/
ReturnValue_t handleAction(ParamGetAction *action);
/**
* @brief Function to generate the command to set a parameter. Command
* will be sent to the ComIF over the rawPacket buffer.
*/
ReturnValue_t handleAction(ParamSetAction *action);
ReturnValue_t handleAction(RequestHkTableAction *action);
ReturnValue_t handleAction(PrintSwitchVIAction *action);
ReturnValue_t handleAction(PrintLatchupsAction *action);
protected:
static const uint8_t MAX_PACKET_LEN = 36;
static const uint8_t PARAM_SET_OK = 1;
static const uint8_t PING_REPLY_SIZE = 2;
static const uint8_t CONFIG_TABLE_ID = 1;
static const uint8_t HK_TABLE_ID = 4;
uint8_t rememberRequestedSize = 0;
uint8_t rememberCommandId = GOMSPACE::NONE;
@ -67,28 +99,31 @@ class GomspaceDeviceHandler : public DeviceHandlerBase {
LocalPoolDataSetBase *hkTableDataset = nullptr;
PingAction pingAction = PingAction(this);
RebootAction rebootAction = RebootAction(this);
GndwdtResetAction gndwdtResetAction = GndwdtResetAction(this);
ParamGetAction paramGetAction = ParamGetAction(this);
ParamSetAction paramSetAction = ParamSetAction(this);
RequestHkTableAction requestHkTableAction = RequestHkTableAction(this);
PrintSwitchVIAction printSwitchVIAction = PrintSwitchVIAction(this);
PrintLatchupsAction printLatchupsAction = PrintLatchupsAction(this);
void doStartUp() override;
void doShutDown() override;
virtual ReturnValue_t buildNormalDeviceCommand(DeviceCommandId_t *id) override;
ReturnValue_t buildTransitionDeviceCommand(DeviceCommandId_t *id) override;
virtual void fillCommandAndReplyMap() override;
ReturnValue_t buildCommandFromCommand(DeviceCommandId_t deviceCommand, const uint8_t *commandData,
size_t commandDataLen) override;
ReturnValue_t scanForReply(const uint8_t *start, size_t remainingSize, DeviceCommandId_t *foundId,
size_t *foundLen) override;
ReturnValue_t interpretDeviceReply(DeviceCommandId_t id, const uint8_t *packet) override;
void setNormalDatapoolEntriesInvalid() override;
uint32_t getTransitionDelayMs(Mode_t modeFrom, Mode_t modeTo) override;
/**
* @brief The command to generate a request to receive the full housekeeping table is device
* specific. Thus the child has to build this command.
*/
virtual ReturnValue_t generateRequestFullHkTableCmd(uint16_t hkTableSize);
/**
* This command handles printing the HK table to the console. This is useful for debugging
* purposes
* @return
* TODO replace by overriding the handleAction()?
*/
virtual ReturnValue_t printStatus(DeviceCommandId_t cmd);
@ -117,46 +152,18 @@ class GomspaceDeviceHandler : public DeviceHandlerBase {
std::array<uint8_t, PDU::CHANNELS_LEN> initOutEnb);
private:
SetParamMessageUnpacker setParamCacher;
/**
* @brief Function to generate the command to set a parameter. Command
* will be sent to the ComIF over the rawPacket buffer.
*/
ReturnValue_t generateSetParamCommand(const uint8_t *commandData, size_t commandDataLen);
SetParamMessageCache setParamCacher;
/**
* Callback is called on a parameter set command. It is called before executing it and after
* Callback is called on a parameter set command. It is called before executing it and
* after successful execution
* @param unpacker Passed before
* @param beforeSet False for callback before execution, true if called after successful
* execution
* @return
*/
virtual ReturnValue_t setParamCallback(SetParamMessageUnpacker &unpacker, bool afterExecution);
/**
* @brief Function to generate the command to get a parameter from a
* gomspace device. Command will be sent to the ComIF over the
* rawPacket buffer.
*/
ReturnValue_t generateGetParamCommand(const uint8_t *commandData, size_t commandDataLen);
/**
* @brief Function to generate the ping command for the ComIF.
*/
ReturnValue_t generatePingCommand(const uint8_t *commandData, size_t commandDataLen);
/**
* @brief Function to generate the command to reboot a gomspace device
* via the ComIF.
*/
void generateRebootCommand();
/**
* @brief Function to generate the command to force a ground watchdog
* reset in a gomspace device.
*/
ReturnValue_t generateResetWatchdogCmd();
virtual ReturnValue_t setParamCallback(uint16_t address, uint32_t value, uint8_t valueBytes,
bool afterExecution);
};
#endif /* MISSION_DEVICES_GOMSPACEDEVICEHANDLER_H_ */

View File

@ -104,39 +104,21 @@ void HeaterHandler::readCommandQueue() {
} while (result == RETURN_OK);
}
ReturnValue_t HeaterHandler::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
if (data == nullptr or size < 3) {
return HasActionsIF::INVALID_PARAMETERS;
}
if (actionId != SWITCH_HEATER) {
return COMMAND_NOT_SUPPORTED;
}
auto switchNr = data[0];
if (switchNr > 7) {
return HasActionsIF::INVALID_PARAMETERS;
}
auto& heater = heaterVec.at(switchNr);
ReturnValue_t HeaterHandler::executeAction(Action* action) { return action->handle(); }
auto actionRaw = data[1];
if (actionRaw != 0 and actionRaw != 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
auto action = static_cast<SwitchAction>(data[1]);
ReturnValue_t HeaterHandler::handleAction(SetHeaterAction* heaterAction) {
auto& heater = heaterVec.at(heaterAction->switchNr);
auto action = heaterAction->switchAction.value;
// Always accepts OFF commands
if (action == SwitchAction::SET_SWITCH_ON) {
if (action == SetHeaterAction::SwitchAction::SET_SWITCH_ON) {
HasHealthIF::HealthState health = heater.healthDevice->getHealth();
if (health == HasHealthIF::FAULTY or health == HasHealthIF::PERMANENT_FAULTY or
health == HasHealthIF::NEEDS_RECOVERY) {
return HasHealthIF::OBJECT_NOT_HEALTHY;
}
CmdSourceParam cmdSource = CmdSourceParam::EXTERNAL;
uint8_t cmdSourceRaw = data[2];
if (cmdSourceRaw > 1) {
return HasActionsIF::INVALID_PARAMETERS;
}
cmdSource = static_cast<CmdSourceParam>(data[2]);
if (health == HasHealthIF::EXTERNAL_CONTROL and cmdSource == CmdSourceParam::INTERNAL) {
auto cmdSource = heaterAction->cmdSource.value;
if (health == HasHealthIF::EXTERNAL_CONTROL and
cmdSource == SetHeaterAction::CmdSourceParam::INTERNAL) {
return HasHealthIF::IS_EXTERNALLY_CONTROLLED;
}
}
@ -146,7 +128,7 @@ ReturnValue_t HeaterHandler::executeAction(ActionId_t actionId, MessageQueueId_t
}
heater.action = action;
heater.cmdActive = true;
heater.replyQueue = commandedBy;
heater.replyQueue = heaterAction->commandedBy;
return RETURN_OK;
}
@ -158,13 +140,13 @@ ReturnValue_t HeaterHandler::sendSwitchCommand(uint8_t switchNr, ReturnValue_t o
switch (onOff) {
case PowerSwitchIF::SWITCH_ON:
commandData[0] = switchNr;
commandData[1] = SET_SWITCH_ON;
commandData[2] = CmdSourceParam::INTERNAL;
commandData[1] = static_cast<uint8_t>(SetHeaterAction::SwitchAction::SET_SWITCH_ON);
commandData[2] = static_cast<uint8_t>(SetHeaterAction::CmdSourceParam::INTERNAL);
break;
case PowerSwitchIF::SWITCH_OFF:
commandData[0] = switchNr;
commandData[1] = SET_SWITCH_OFF;
commandData[2] = CmdSourceParam::INTERNAL;
commandData[1] = static_cast<uint8_t>(SetHeaterAction::SwitchAction::SET_SWITCH_OFF);
commandData[2] = static_cast<uint8_t>(SetHeaterAction::CmdSourceParam::INTERNAL);
break;
default:
sif::error << "HeaterHandler::sendSwitchCommand: Invalid switch request" << std::endl;
@ -174,7 +156,8 @@ ReturnValue_t HeaterHandler::sendSwitchCommand(uint8_t switchNr, ReturnValue_t o
result = ipcStore->addData(&storeAddress, commandData, sizeof(commandData));
if (result == RETURN_OK) {
CommandMessage message;
ActionMessage::setCommand(&message, SWITCH_HEATER, storeAddress);
ActionMessage::setCommand(&message, static_cast<ActionId_t>(HeaterCommands::SWITCH_HEATER),
storeAddress);
/* Send heater command to own command queue */
result = commandQueue->sendMessage(commandQueue->getId(), &message, 0);
if (result != RETURN_OK) {
@ -193,7 +176,7 @@ void HeaterHandler::handleSwitchHandling() {
// will shut down the heater
if (health == HasHealthIF::FAULTY or health == HasHealthIF::PERMANENT_FAULTY) {
heaterVec[idx].cmdActive = true;
heaterVec[idx].action = SET_SWITCH_OFF;
heaterVec[idx].action = SetHeaterAction::SwitchAction::SET_SWITCH_OFF;
triggerEvent(FAULTY_HEATER_WAS_ON, idx, 0);
handleSwitchOffCommand(static_cast<heater::Switchers>(idx));
continue;
@ -201,10 +184,10 @@ void HeaterHandler::handleSwitchHandling() {
}
if (heaterVec[idx].cmdActive) {
switch (heaterVec[idx].action) {
case SET_SWITCH_ON:
case SetHeaterAction::SwitchAction::SET_SWITCH_ON:
handleSwitchOnCommand(static_cast<heater::Switchers>(idx));
break;
case SET_SWITCH_OFF:
case SetHeaterAction::SwitchAction::SET_SWITCH_OFF:
handleSwitchOffCommand(static_cast<heater::Switchers>(idx));
break;
default:
@ -228,7 +211,8 @@ void HeaterHandler::handleSwitchOnCommand(heater::Switchers heaterIdx) {
heater.cmdActive = false;
heater.waitMainSwitchOn = false;
if (heater.replyQueue != commandQueue->getId()) {
actionHelper.finish(false, heater.replyQueue, heater.action, MAIN_SWITCH_SET_TIMEOUT);
actionHelper.finish(false, heater.replyQueue, static_cast<ActionId_t>(heater.action),
MAIN_SWITCH_SET_TIMEOUT);
}
return;
}
@ -254,9 +238,11 @@ void HeaterHandler::handleSwitchOnCommand(heater::Switchers heaterIdx) {
// HeaterHandler itself
if (heater.replyQueue != commandQueue->getId()) {
if (result == RETURN_OK) {
actionHelper.finish(true, heater.replyQueue, heater.action, result);
actionHelper.finish(true, heater.replyQueue, static_cast<ActionId_t>(heater.action),
result);
} else {
actionHelper.finish(false, heater.replyQueue, heater.action, result);
actionHelper.finish(false, heater.replyQueue, static_cast<ActionId_t>(heater.action),
result);
}
}
heater.cmdActive = false;
@ -272,7 +258,8 @@ void HeaterHandler::handleSwitchOnCommand(heater::Switchers heaterIdx) {
sif::debug << "HeaterHandler::handleSwitchHandling: Failed to get state of"
<< " main line switch" << std::endl;
if (heater.replyQueue != commandQueue->getId()) {
actionHelper.finish(false, heater.replyQueue, heater.action, mainSwitchState);
actionHelper.finish(false, heater.replyQueue, static_cast<ActionId_t>(heater.action),
mainSwitchState);
}
heater.cmdActive = false;
}
@ -308,9 +295,9 @@ void HeaterHandler::handleSwitchOffCommand(heater::Switchers heaterIdx) {
if (heater.replyQueue != NO_COMMANDER) {
// Report back switch command reply if necessary
if (result == HasReturnvaluesIF::RETURN_OK) {
actionHelper.finish(true, heater.replyQueue, heater.action, result);
actionHelper.finish(true, heater.replyQueue, static_cast<ActionId_t>(heater.action), result);
} else {
actionHelper.finish(false, heater.replyQueue, heater.action, result);
actionHelper.finish(false, heater.replyQueue, static_cast<ActionId_t>(heater.action), result);
}
}
heater.cmdActive = false;
@ -333,6 +320,8 @@ bool HeaterHandler::allSwitchesOff() {
MessageQueueId_t HeaterHandler::getCommandQueue() const { return commandQueue->getId(); }
ActionHelper* HeaterHandler::getActionHelper() { return &actionHelper; }
ReturnValue_t HeaterHandler::sendFuseOnCommand(uint8_t fuseNr) { return RETURN_OK; }
ReturnValue_t HeaterHandler::getSwitchState(uint8_t switchNr) const {

View File

@ -17,6 +17,7 @@
#include <array>
#include <vector>
#include "devicedefinitions/HeaterDefinitions.h"
#include "devices/heaterSwitcherList.h"
class PowerSwitchIF;
@ -47,11 +48,6 @@ class HeaterHandler : public ExecutableObjectIF,
static const ReturnValue_t MAIN_SWITCH_SET_TIMEOUT = MAKE_RETURN_CODE(0xA4);
static const ReturnValue_t COMMAND_ALREADY_WAITING = MAKE_RETURN_CODE(0xA5);
enum CmdSourceParam : uint8_t { INTERNAL = 0, EXTERNAL = 1 };
/** Device command IDs */
static const DeviceCommandId_t SWITCH_HEATER = 0x0;
HeaterHandler(object_id_t setObjectId, GpioIF* gpioInterface_, HeaterHelper helper,
PowerSwitchIF* mainLineSwitcherObjectId, power::Switch_t mainLineSwitch);
@ -70,8 +66,10 @@ class HeaterHandler : public ExecutableObjectIF,
uint32_t getSwitchDelayMs(void) const override;
MessageQueueId_t getCommandQueue() const override;
ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
ActionHelper* getActionHelper() override;
ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(SetHeaterAction* heaterAction);
ReturnValue_t initialize() override;
private:
@ -89,7 +87,6 @@ class HeaterHandler : public ExecutableObjectIF,
static const MessageQueueId_t NO_COMMANDER = 0;
enum SwitchState : bool { ON = true, OFF = false };
enum SwitchAction : uint8_t { SET_SWITCH_OFF, SET_SWITCH_ON, NONE };
/**
* @brief Struct holding information about a heater command to execute.
@ -106,7 +103,7 @@ class HeaterHandler : public ExecutableObjectIF,
: healthDevice(pair.first), gpioId(pair.second), switchState(initState) {}
HealthDevice* healthDevice = nullptr;
gpioId_t gpioId = gpio::NO_GPIO;
SwitchAction action = SwitchAction::NONE;
SetHeaterAction::SwitchAction action = SetHeaterAction::SwitchAction::NONE;
MessageQueueId_t replyQueue = MessageQueueIF::NO_QUEUE;
bool cmdActive = false;
SwitchState switchState = SwitchState::OFF;
@ -140,6 +137,8 @@ class HeaterHandler : public ExecutableObjectIF,
ActionHelper actionHelper;
SetHeaterAction setHeaterAction = SetHeaterAction(this);
StorageManagerIF* ipcStore = nullptr;
void readCommandQueue();

View File

@ -16,7 +16,7 @@ P60DockHandler::~P60DockHandler() {}
ReturnValue_t P60DockHandler::buildNormalDeviceCommand(DeviceCommandId_t *id) {
*id = GOMSPACE::REQUEST_HK_TABLE;
return buildCommandFromCommand(*id, NULL, 0);
return requestHkTableAction.handle();
}
void P60DockHandler::letChildHandleHkReply(DeviceCommandId_t id, const uint8_t *packet) {

View File

@ -16,7 +16,7 @@ PDU1Handler::~PDU1Handler() {}
ReturnValue_t PDU1Handler::buildNormalDeviceCommand(DeviceCommandId_t *id) {
*id = GOMSPACE::REQUEST_HK_TABLE;
return buildCommandFromCommand(*id, NULL, 0);
return requestHkTableAction.handle();
}
void PDU1Handler::letChildHandleHkReply(DeviceCommandId_t id, const uint8_t *packet) {
@ -29,49 +29,48 @@ void PDU1Handler::assignChannelHookFunction(GOMSPACE::ChannelSwitchHook hook, vo
this->hookArgs = args;
}
ReturnValue_t PDU1Handler::setParamCallback(SetParamMessageUnpacker &unpacker,
bool afterExecution) {
ReturnValue_t PDU1Handler::setParamCallback(uint16_t address, uint32_t value, uint8_t valueBytes, bool afterExecution) {
using namespace PDU1;
GOMSPACE::Pdu pdu = GOMSPACE::Pdu::PDU1;
if (not afterExecution) {
return HasReturnvaluesIF::RETURN_OK;
}
if (channelSwitchHook != nullptr and unpacker.getParameterSize() == 1) {
switch (unpacker.getAddress()) {
if (channelSwitchHook != nullptr and valueBytes == 1) {
switch (address) {
case (CONFIG_ADDRESS_OUT_EN_TCS_BOARD_3V3): {
channelSwitchHook(pdu, 0, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 0, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_SYRLINKS): {
channelSwitchHook(pdu, 1, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 1, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_STAR_TRACKER): {
channelSwitchHook(pdu, 2, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 2, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_MGT): {
channelSwitchHook(pdu, 3, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 3, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_SUS_NOMINAL): {
channelSwitchHook(pdu, 4, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 4, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_SOLAR_CELL_EXP): {
channelSwitchHook(pdu, 5, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 5, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_PLOC): {
channelSwitchHook(pdu, 6, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 6, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_ACS_BOARD_SIDE_A): {
channelSwitchHook(pdu, 7, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 7, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_CHANNEL8): {
channelSwitchHook(pdu, 8, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 8, value, hookArgs);
break;
}
}

View File

@ -38,7 +38,7 @@ class PDU1Handler : public GomspaceDeviceHandler {
virtual void letChildHandleHkReply(DeviceCommandId_t id, const uint8_t* packet) override;
ReturnValue_t printStatus(DeviceCommandId_t cmd) override;
LocalPoolDataSetBase* getDataSetHandle(sid_t sid) override;
ReturnValue_t setParamCallback(SetParamMessageUnpacker& unpacker, bool afterExectuion) override;
ReturnValue_t setParamCallback(uint16_t address, uint32_t value, uint8_t valueBytes, bool afterExecution) override;
private:
static constexpr uint8_t MAX_CHANNEL_STR_WIDTH = 24;

View File

@ -16,7 +16,7 @@ PDU2Handler::~PDU2Handler() {}
ReturnValue_t PDU2Handler::buildNormalDeviceCommand(DeviceCommandId_t *id) {
*id = GOMSPACE::REQUEST_HK_TABLE;
return buildCommandFromCommand(*id, NULL, 0);
return requestHkTableAction.handle();
}
void PDU2Handler::letChildHandleHkReply(DeviceCommandId_t id, const uint8_t *packet) {
@ -127,49 +127,48 @@ void PDU2Handler::printHkTableLatchups() {
printerHelper("Payload Camera", Channels::PAYLOAD_CAMERA);
}
ReturnValue_t PDU2Handler::setParamCallback(SetParamMessageUnpacker &unpacker,
bool afterExecution) {
ReturnValue_t PDU2Handler::setParamCallback(uint16_t address, uint32_t value, uint8_t valueBytes, bool afterExecution) {
using namespace PDU2;
GOMSPACE::Pdu pdu = GOMSPACE::Pdu::PDU2;
if (not afterExecution) {
return HasReturnvaluesIF::RETURN_OK;
}
if (channelSwitchHook != nullptr and unpacker.getParameterSize() == 1) {
switch (unpacker.getAddress()) {
if (channelSwitchHook != nullptr and valueBytes == 1) {
switch (address) {
case (CONFIG_ADDRESS_OUT_EN_Q7S): {
channelSwitchHook(pdu, 0, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 0, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_PAYLOAD_PCDU_CH1): {
channelSwitchHook(pdu, 1, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 1, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_RW): {
channelSwitchHook(pdu, 2, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 2, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_TCS_BOARD_HEATER_IN): {
channelSwitchHook(pdu, 3, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 3, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_SUS_REDUNDANT): {
channelSwitchHook(pdu, 4, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 4, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_DEPLOYMENT_MECHANISM): {
channelSwitchHook(pdu, 5, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 5, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_PAYLOAD_PCDU_CH6): {
channelSwitchHook(pdu, 6, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 6, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_ACS_BOARD_SIDE_B): {
channelSwitchHook(pdu, 7, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 7, value, hookArgs);
break;
}
case (CONFIG_ADDRESS_OUT_EN_PAYLOAD_CAMERA): {
channelSwitchHook(pdu, 8, unpacker.getParameter()[0], hookArgs);
channelSwitchHook(pdu, 8, value, hookArgs);
break;
}
}

View File

@ -36,7 +36,7 @@ class PDU2Handler : public GomspaceDeviceHandler {
virtual ReturnValue_t buildNormalDeviceCommand(DeviceCommandId_t* id) override;
virtual void letChildHandleHkReply(DeviceCommandId_t id, const uint8_t* packet) override;
ReturnValue_t printStatus(DeviceCommandId_t cmd) override;
ReturnValue_t setParamCallback(SetParamMessageUnpacker& unpacker, bool afterExecution) override;
ReturnValue_t setParamCallback(uint16_t address, uint32_t value, uint8_t valueBytes, bool afterExecution) override;
LocalPoolDataSetBase* getDataSetHandle(sid_t sid) override;
private:

View File

@ -111,8 +111,10 @@ void SolarArrayDeploymentHandler::performWaitOn8VActions() {
} else {
if (mainSwitchCountdown.hasTimedOut()) {
triggerEvent(MAIN_SWITCH_ON_TIMEOUT);
actionHelper.finish(false, rememberCommanderId, DEPLOY_SOLAR_ARRAYS,
MAIN_SWITCH_TIMEOUT_FAILURE);
actionHelper.finish(
false, rememberCommanderId,
static_cast<DeviceCommandId_t>(SolarArrayDeploymentCommands::DEPLOY_SOLAR_ARRAYS),
MAIN_SWITCH_TIMEOUT_FAILURE);
stateMachine = WAIT_ON_DELOYMENT_COMMAND;
}
}
@ -129,7 +131,10 @@ void SolarArrayDeploymentHandler::switchDeploymentTransistors() {
* the deployment sequence. */
stateMachine = WAIT_ON_DELOYMENT_COMMAND;
triggerEvent(DEPL_SA1_GPIO_SWTICH_ON_FAILED);
actionHelper.finish(false, rememberCommanderId, DEPLOY_SOLAR_ARRAYS, SWITCHING_DEPL_SA2_FAILED);
actionHelper.finish(
false, rememberCommanderId,
static_cast<DeviceCommandId_t>(SolarArrayDeploymentCommands::DEPLOY_SOLAR_ARRAYS),
SWITCHING_DEPL_SA1_FAILED);
mainLineSwitcher->sendSwitchCommand(mainLineSwitch, PowerSwitchIF::SWITCH_OFF);
}
result = gpioInterface->pullHigh(deplSA2);
@ -139,7 +144,10 @@ void SolarArrayDeploymentHandler::switchDeploymentTransistors() {
<< std::endl;
stateMachine = WAIT_ON_DELOYMENT_COMMAND;
triggerEvent(DEPL_SA2_GPIO_SWTICH_ON_FAILED);
actionHelper.finish(false, rememberCommanderId, DEPLOY_SOLAR_ARRAYS, SWITCHING_DEPL_SA2_FAILED);
actionHelper.finish(
false, rememberCommanderId,
static_cast<DeviceCommandId_t>(SolarArrayDeploymentCommands::DEPLOY_SOLAR_ARRAYS),
SWITCHING_DEPL_SA2_FAILED);
mainLineSwitcher->sendSwitchCommand(mainLineSwitch, PowerSwitchIF::SWITCH_OFF);
}
deploymentCountdown.setTimeout(burnTimeMs);
@ -149,7 +157,10 @@ void SolarArrayDeploymentHandler::switchDeploymentTransistors() {
void SolarArrayDeploymentHandler::handleDeploymentFinish() {
ReturnValue_t result = RETURN_OK;
if (deploymentCountdown.hasTimedOut()) {
actionHelper.finish(true, rememberCommanderId, DEPLOY_SOLAR_ARRAYS, RETURN_OK);
actionHelper.finish(
true, rememberCommanderId,
static_cast<DeviceCommandId_t>(SolarArrayDeploymentCommands::DEPLOY_SOLAR_ARRAYS),
RETURN_OK);
result = gpioInterface->pullLow(deplSA1);
if (result != RETURN_OK) {
sif::debug << "SolarArrayDeploymentHandler::handleStateMachine: Failed to pull solar"
@ -181,27 +192,24 @@ void SolarArrayDeploymentHandler::readCommandQueue() {
}
}
ReturnValue_t SolarArrayDeploymentHandler::executeAction(ActionId_t actionId,
MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t result;
ReturnValue_t SolarArrayDeploymentHandler::executeAction(Action* action) {
if (stateMachine != WAIT_ON_DELOYMENT_COMMAND) {
sif::error << "SolarArrayDeploymentHandler::executeAction: Received command while not in"
<< "waiting-on-command-state" << std::endl;
return DEPLOYMENT_ALREADY_EXECUTING;
}
if (actionId != DEPLOY_SOLAR_ARRAYS) {
sif::error << "SolarArrayDeploymentHandler::executeAction: Received invalid command"
<< std::endl;
result = COMMAND_NOT_SUPPORTED;
} else {
stateMachine = SWITCH_8V_ON;
rememberCommanderId = commandedBy;
result = RETURN_OK;
}
return result;
// delegates to SolarArrayDeploymentHandler::handleAction()
return action->handle();
}
ReturnValue_t SolarArrayDeploymentHandler::handleAction(SolarArrayDeploymentAction* action) {
stateMachine = SWITCH_8V_ON;
rememberCommanderId = action->commandedBy;
return RETURN_OK;
}
MessageQueueId_t SolarArrayDeploymentHandler::getCommandQueue() const {
return commandQueue->getId();
}
ActionHelper* SolarArrayDeploymentHandler::getActionHelper() { return &actionHelper; }

View File

@ -14,6 +14,8 @@
#include <unordered_map>
#include "devicedefinitions/SolarArrayDeploymentDefinitions.h"
/**
* @brief This class is used to control the solar array deployment.
*
@ -24,8 +26,6 @@ class SolarArrayDeploymentHandler : public ExecutableObjectIF,
public HasReturnvaluesIF,
public HasActionsIF {
public:
static const DeviceCommandId_t DEPLOY_SOLAR_ARRAYS = 0x5;
/**
* @brief constructor
*
@ -51,8 +51,9 @@ class SolarArrayDeploymentHandler : public ExecutableObjectIF,
virtual ReturnValue_t performOperation(uint8_t operationCode = 0) override;
virtual MessageQueueId_t getCommandQueue() const override;
virtual ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) override;
virtual ActionHelper* getActionHelper() override;
virtual ReturnValue_t executeAction(Action* action) override;
ReturnValue_t handleAction(SolarArrayDeploymentAction* action);
virtual ReturnValue_t initialize() override;
private:
@ -129,6 +130,8 @@ class SolarArrayDeploymentHandler : public ExecutableObjectIF,
ActionHelper actionHelper;
SolarArrayDeploymentAction deploymentAction = SolarArrayDeploymentAction(this);
void readCommandQueue();
/**

View File

@ -332,14 +332,37 @@ class Pdu2FullTableReply : public SerialLinkedListAdapter<SerializeIF> {
LinkedElement<SerializeIF> dataset;
};
class SetParamMessageCache {
public:
SetParamMessageCache() : address(0), parameter(0), parameterSize(1) {}
void set(uint16_t address, uint32_t parameter, uint8_t parameterSize) {
this->address = address;
this->parameter = parameter;
this->parameterSize = parameterSize;
}
uint16_t getAddress() { return address; }
uint32_t getParameter() { return parameter; }
uint8_t getParameterSize() { return parameterSize; }
private:
uint16_t address;
uint32_t parameter;
uint8_t parameterSize;
};
/**
* @brief This class helps to unpack information from an action message
* to set a parameter in gomspace devices. The action message can be
* for example received from the PUS Service 8.
*/
/*
class SetParamMessageUnpacker : public SerialLinkedListAdapter<SerializeIF> {
public:
/* Largest parameter is a uint32_t */
// Largest parameter is a uint32_t
static const uint32_t MAX_SIZE = 4;
SetParamMessageUnpacker() { setLinks(); }
@ -358,7 +381,7 @@ class SetParamMessageUnpacker : public SerialLinkedListAdapter<SerializeIF> {
SetParamMessageUnpacker(const SetParamMessageUnpacker &message);
SerializeElement<uint16_t> address;
SerializeElement<SerialFixedArrayListAdapter<uint8_t, MAX_SIZE, uint8_t>> parameter;
};
};*/
/**
* @brief This class generates a message which can be sent to the GomspaceDeviceHandler to
@ -405,6 +428,7 @@ class GomspaceSetParamMessage : public SerialLinkedListAdapter<SerializeIF> {
* to get a parameter from gomspace devices. The action message can be
* for example received from the PUS Service 8.
*/
/*
class GetParamMessageUnpacker : public SerialLinkedListAdapter<SerializeIF> {
public:
GetParamMessageUnpacker() { setLinks(); }
@ -424,8 +448,8 @@ class GetParamMessageUnpacker : public SerialLinkedListAdapter<SerializeIF> {
}
SerializeElement<uint8_t> tableId;
SerializeElement<uint16_t> address; // The memory address offset within the table
/* The size of the requested value (e.g. temperature is a uint16_t value) */
// The size of the requested value (e.g. temperature is a uint16_t value)
SerializeElement<uint8_t> parameterSize;
};
};*/
#endif /* MISSION_DEVICES_DEVICEDEFINITIONS_GOMSPACEPACKETS_H_ */

View File

@ -0,0 +1,81 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include "GomspaceDefinitions.h"
class GomspaceDeviceHandler;
class PingAction : public TemplateAction<GomspaceDeviceHandler, PingAction, GOMSPACE::GomspaceCommands> {
public:
PingAction(GomspaceDeviceHandler* owner) : TemplateAction(owner, GOMSPACE::PING) {}
// TODO array
Parameter<uint8_t> pingData = Parameter<uint8_t>::createParameter(this, "Ping Data");
};
class RebootAction : public TemplateAction<GomspaceDeviceHandler, RebootAction, GOMSPACE::GomspaceCommands> {
public:
RebootAction(GomspaceDeviceHandler* owner) : TemplateAction(owner, GOMSPACE::REBOOT) {}
};
class GndwdtResetAction
: public TemplateAction<GomspaceDeviceHandler, GndwdtResetAction, GOMSPACE::GomspaceCommands> {
public:
GndwdtResetAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::GNDWDT_RESET) {}
};
class ParamGetAction
: public TemplateAction<GomspaceDeviceHandler, ParamGetAction, GOMSPACE::GomspaceCommands> {
public:
FSFW_ENUM(ParameterByteSize, uint8_t,
((ONE_BYTE, 1, "One Byte"))((TWO_BYTES, 2, "Two Bytes"))((FOUR_BYTES, 4, "Four Bytes")))
FSFW_ENUM(TableId, uint8_t,
((CONFIG_TABLE_ID, 1, "Config Table"))((HK_TABLE_ID, 4, "Housekeeping Table")))
ParamGetAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::PARAM_GET) {}
Parameter<TableId> tableId =
Parameter<TableId>::createParameter(this, "Table");
Parameter<uint16_t> address = Parameter<uint16_t>::createParameter(this, "Address");
Parameter<ParameterByteSize> parameterSize =
Parameter<ParameterByteSize>::createParameter(this, "Parameter Size");
};
class ParamSetAction
: public TemplateAction<GomspaceDeviceHandler, ParamSetAction, GOMSPACE::GomspaceCommands> {
public:
FSFW_ENUM(ParameterByteSize, uint8_t,
((ONE_BYTE, 1, "One Byte"))((TWO_BYTES, 2, "Two Bytes"))((FOUR_BYTES, 4, "Four Bytes")))
ParamSetAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::PARAM_SET) {}
Parameter<uint16_t> address = Parameter<uint16_t>::createParameter(this, "Address");
Parameter<uint32_t> parameter = Parameter<uint32_t>::createParameter(this, "Parameter Value");
Parameter<ParameterByteSize> parameterSize =
Parameter<ParameterByteSize>::createParameter(this, "Parameter Size");
};
class RequestHkTableAction
: public TemplateAction<GomspaceDeviceHandler, RequestHkTableAction, GOMSPACE::GomspaceCommands> {
public:
RequestHkTableAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::REQUEST_HK_TABLE) {}
};
class PrintSwitchVIAction
: public TemplateAction<GomspaceDeviceHandler, PrintSwitchVIAction, GOMSPACE::GomspaceCommands> {
public:
PrintSwitchVIAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::PRINT_SWITCH_V_I) {}
};
class PrintLatchupsAction
: public TemplateAction<GomspaceDeviceHandler, PrintLatchupsAction, GOMSPACE::GomspaceCommands> {
public:
PrintLatchupsAction(GomspaceDeviceHandler* owner)
: TemplateAction(owner, GOMSPACE::PRINT_LATCHUPS) {}
};

View File

@ -4,6 +4,7 @@
#include <fsfw/datapoollocal/LocalPoolVariable.h>
#include <fsfw/datapoollocal/StaticLocalDataSet.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
#include <fsfw/introspection/ClasslessEnum.h>
#include <fsfw/power/definitions.h>
#include <cstdint>
@ -12,6 +13,18 @@
namespace GOMSPACE {
/**
* Device commands are derived from the rparam.h of the gomspace lib..
* IDs above 50 are reserved for device specific commands.
*/
FSFW_CLASSLESS_ENUM(
GomspaceCommands, DeviceCommandId_t,
((PING, 1, "Ping"))((NONE, 2, "None (used internally)"))((REBOOT, 4, "Reboot"))(
(GNDWDT_RESET, 9, "Reset Watchdog"))((PARAM_GET, 0, "Get Parameter"))(
(PARAM_SET, 255, "Set Parameter"))((REQUEST_HK_TABLE, 16, "Request Housekeeping Table"))(
(PRINT_SWITCH_V_I, 32, "Print switch states, voltages and currents to the console"))(
(PRINT_LATCHUPS, 33, "Print Latchups to the console")))
enum class Pdu { PDU1, PDU2 };
using ChannelSwitchHook = void (*)(Pdu pdu, uint8_t channel, bool on, void* args);
@ -26,23 +39,6 @@ static const uint8_t REBOOT_PORT = 4;
static const uint8_t PARAM_PORT = 7;
static const uint8_t P60_PORT_GNDWDT_RESET = 9;
/**
* Device commands are derived from the rparam.h of the gomspace lib..
* IDs above 50 are reserved for device specific commands.
*/
static const DeviceCommandId_t PING = 1; //!< [EXPORT] : [COMMAND]
static const DeviceCommandId_t NONE = 2; // Set when no command is pending
static const DeviceCommandId_t REBOOT = 4; //!< [EXPORT] : [COMMAND]
static const DeviceCommandId_t GNDWDT_RESET = 9; //!< [EXPORT] : [COMMAND]
static const DeviceCommandId_t PARAM_GET = 0; //!< [EXPORT] : [COMMAND]
static const DeviceCommandId_t PARAM_SET = 255; //!< [EXPORT] : [COMMAND]
static const DeviceCommandId_t REQUEST_HK_TABLE = 16; //!< [EXPORT] : [COMMAND]
//! [EXPORT] : [COMMAND] Print switch states, voltages and currents to the console
//! For the ACU device, only print voltages and currents of the 6 ACU channels
static const DeviceCommandId_t PRINT_SWITCH_V_I = 32;
static const DeviceCommandId_t PRINT_LATCHUPS = 33;
} // namespace GOMSPACE
namespace P60System {

View File

@ -0,0 +1,26 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
class HeaterHandler;
FSFW_ENUM(HeaterCommands, DeviceCommandId_t, ((SWITCH_HEATER, 0x0, "Switch Heater")))
class SetHeaterAction : public TemplateAction<HeaterHandler, SetHeaterAction, HeaterCommands> {
public:
FSFW_ENUM(SwitchAction, uint8_t,
((SET_SWITCH_OFF, "Set switch to Off"))((SET_SWITCH_ON, "Set switch to On")) ((NONE, "No Action")))
FSFW_ENUM(CmdSourceParam, uint8_t, ((INTERNAL, 0, "Internal"))((EXTERNAL, 1, "External")))
SetHeaterAction(HeaterHandler *owner) : TemplateAction(owner, HeaterCommands::SWITCH_HEATER) {}
MinMaxParameter<uint8_t> switchNr =
MinMaxParameter<uint8_t>::createMinMaxParameter(this, "Heater number", 0, 7);
Parameter<SwitchAction> switchAction =
Parameter<SwitchAction>::createParameter(this, "Switch Action");
Parameter<CmdSourceParam> cmdSource =
Parameter<CmdSourceParam>::createParameter(this, "Command Source");
};

View File

@ -0,0 +1,18 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/introspection/Enum.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
class SolarArrayDeploymentHandler;
FSFW_ENUM(SolarArrayDeploymentCommands, DeviceCommandId_t,((DEPLOY_SOLAR_ARRAYS, 0x05, "Deploy Solar Arrays")))
class SolarArrayDeploymentAction
: public TemplateAction<SolarArrayDeploymentHandler, SolarArrayDeploymentAction,
SolarArrayDeploymentCommands> {
public:
SolarArrayDeploymentAction(SolarArrayDeploymentHandler *owner)
: TemplateAction(owner, SolarArrayDeploymentCommands::DEPLOY_SOLAR_ARRAYS) {}
};

View File

@ -3,7 +3,7 @@
#include <cstring>
void max1227::prepareExternallyClockedSingleChannelRead(uint8_t *spiBuf, uint8_t channel,
size_t &sz) {
uint32_t &sz) {
spiBuf[0] = buildConvByte(ScanModes::N_ONCE, channel, false);
spiBuf[1] = 0x00;
spiBuf[2] = 0x00;

View File

@ -58,7 +58,7 @@ constexpr uint8_t buildSetupByte(ClkSel clkSel, RefSel refSel, DiffSel diffSel)
* @param n
* @param sz
*/
void prepareExternallyClockedSingleChannelRead(uint8_t* spiBuf, uint8_t channel, size_t& sz);
void prepareExternallyClockedSingleChannelRead(uint8_t* spiBuf, uint8_t channel, uint32_t& sz);
/**
* If there is a wakeup delay, there needs to be a 65 us delay between sending

View File

@ -1,6 +1,7 @@
#include "DualLaneAssemblyBase.h"
#include <fsfw/ipc/QueueFactory.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
#include "OBSWConfig.h"
@ -92,6 +93,10 @@ ReturnValue_t DualLaneAssemblyBase::pwrStateMachineWrapper() {
return RETURN_OK;
}
ModeDefinitionHelper DualLaneAssemblyBase::getModeDefinitionHelper() {
return ModeDefinitionHelper::create<DeviceHandlerIF::DeviceHandlerMode, duallane::Submodes>();
}
ReturnValue_t DualLaneAssemblyBase::isModeCombinationValid(Mode_t mode, Submode_t submode) {
using namespace duallane;
if (submode != A_SIDE and submode != B_SIDE and submode != DUAL_MODE) {

View File

@ -22,6 +22,8 @@ class DualLaneAssemblyBase : public AssemblyBase, public ConfirmsFailuresIF {
pcdu::Switches switch1, pcdu::Switches switch2, Event pwrSwitchTimeoutEvent,
Event sideSwitchNotAllowedEvent, Event transitionOtherSideFailedEvent);
ModeDefinitionHelper getModeDefinitionHelper() override;
protected:
// This helper object complete encapsulates power switching
DualLanePowerStateMachine pwrStateMachine;

View File

@ -189,3 +189,7 @@ void RwAssembly::handleModeTransitionFailed(ReturnValue_t result) {
}
}
}
ModeDefinitionHelper RwAssembly::getModeDefinitionHelper() {
return ModeDefinitionHelper::create<DeviceHandlerIF::DeviceHandlerMode, HasModesIF::DefaultSubmode>();
}

View File

@ -15,6 +15,10 @@ class RwAssembly : public AssemblyBase {
RwAssembly(object_id_t objectId, object_id_t parentId, PowerSwitchIF* pwrSwitcher,
power::Switch_t switcher, RwHelper helper);
~RwAssembly() {}
ModeDefinitionHelper getModeDefinitionHelper() override;
private:
static constexpr uint8_t NUMBER_RWS = 4;
RwHelper helper;

View File

@ -203,3 +203,7 @@ void TcsBoardAssembly::handleModeTransitionFailed(ReturnValue_t result) {
triggerEvent(MODE_TRANSITION_FAILED, result);
}
}
ModeDefinitionHelper TcsBoardAssembly::getModeDefinitionHelper(){
return ModeDefinitionHelper::create<DeviceHandlerIF::DeviceHandlerMode, HasModesIF::DefaultSubmode>();
}

View File

@ -22,6 +22,8 @@ class TcsBoardAssembly : public AssemblyBase, public ConfirmsFailuresIF {
ReturnValue_t initialize() override;
ModeDefinitionHelper getModeDefinitionHelper();
private:
static constexpr uint8_t NUMBER_RTDS = 16;
PowerSwitcher switcher;

View File

@ -2,6 +2,7 @@
#define MISSION_SYSTEM_DEFINITIONS_H_
#include <fsfw/modes/ModeMessage.h>
#include <fsfw/introspection/ClasslessEnum.h>
namespace power {
@ -12,7 +13,7 @@ enum class OpCodes { NONE, TO_OFF_DONE, TO_NOT_OFF_DONE, TIMEOUT_OCCURED };
namespace duallane {
enum Submodes : Submode_t { A_SIDE = 0, B_SIDE = 1, DUAL_MODE = 2 };
FSFW_CLASSLESS_ENUM(Submodes, Submode_t, ((A_SIDE, 0, "Side A")) ((B_SIDE, 1, "Side B")) ((DUAL_MODE, 2, "Dual mode")))
} // namespace duallane

View File

@ -0,0 +1,73 @@
#pragma once
#include <fsfw/action/MinMaxParameter.h>
#include <fsfw/action/TemplateAction.h>
#include <fsfw/devicehandlers/DeviceHandlerIF.h>
#include <fsfw/introspection/Enum.h>
class CCSDSHandler;
FSFW_ENUM(
CCSDSCommands, DeviceCommandId_t,
((SET_LOW_RATE, 0, "Set Low rate"))((SET_HIGH_RATE, 1, "Set High Rate"))(
(EN_TRANSMITTER, 2, "Enable Transmitter"))((DISABLE_TRANSMITTER, 3, "Disable Transmitter"))(
(ARBITRARY_RATE, 4, "Set Bit Rate"))((ENABLE_TX_CLK_MANIPULATOR, 5,
"Enable Tx Clock Manipulator"))(
(DISABLE_TX_CLK_MANIPULATOR, 6, "Enable Tx Clock Manipulator"))(
(UPDATE_ON_RISING_EDGE, 7, "update data on rising edge"))((UPDATE_ON_FALLING_EDGE, 8,
"update data on falling edge")))
class SetLowRateAction : public TemplateAction<CCSDSHandler, SetLowRateAction, CCSDSCommands> {
public:
SetLowRateAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::SET_LOW_RATE) {}
};
class SetHighRateAction : public TemplateAction<CCSDSHandler, SetHighRateAction, CCSDSCommands> {
public:
SetHighRateAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::SET_HIGH_RATE) {}
};
class EnTransmitterAction
: public TemplateAction<CCSDSHandler, EnTransmitterAction, CCSDSCommands> {
public:
EnTransmitterAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::EN_TRANSMITTER) {}
};
class DisableTransmitterAction
: public TemplateAction<CCSDSHandler, DisableTransmitterAction, CCSDSCommands> {
public:
DisableTransmitterAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::DISABLE_TRANSMITTER) {}
};
class ArbitraryRateAction
: public TemplateAction<CCSDSHandler, ArbitraryRateAction, CCSDSCommands> {
public:
ArbitraryRateAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::ARBITRARY_RATE) {}
Parameter<uint32_t> bitrate = Parameter<uint32_t>::createParameter(this, "Bitrate");
};
class EnableTxClkManipulatorAction
: public TemplateAction<CCSDSHandler, EnableTxClkManipulatorAction, CCSDSCommands> {
public:
EnableTxClkManipulatorAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::ENABLE_TX_CLK_MANIPULATOR) {}
};
class DisableTxClkManipulatorAction
: public TemplateAction<CCSDSHandler, DisableTxClkManipulatorAction, CCSDSCommands> {
public:
DisableTxClkManipulatorAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::DISABLE_TX_CLK_MANIPULATOR) {}
};
class UpdateOnRisingEdgeAction
: public TemplateAction<CCSDSHandler, UpdateOnRisingEdgeAction, CCSDSCommands> {
public:
UpdateOnRisingEdgeAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::UPDATE_ON_RISING_EDGE) {}
};
class UpdateOnFallingEdgeAction
: public TemplateAction<CCSDSHandler, UpdateOnFallingEdgeAction, CCSDSCommands> {
public:
UpdateOnFallingEdgeAction(CCSDSHandler* owner)
: TemplateAction(owner, CCSDSCommands::UPDATE_ON_FALLING_EDGE) {}
};

View File

@ -159,6 +159,8 @@ void CCSDSHandler::readCommandQueue(void) {
MessageQueueId_t CCSDSHandler::getCommandQueue() const { return commandQueue->getId(); }
ActionHelper* CCSDSHandler::getActionHelper() { return &actionHelper; }
void CCSDSHandler::addVirtualChannel(VcId_t vcId, VirtualChannel* virtualChannel) {
if (vcId > common::NUMBER_OF_VIRTUAL_CHANNELS) {
sif::warning << "CCSDSHandler::addVirtualChannel: Invalid virtual channel ID" << std::endl;
@ -210,57 +212,74 @@ MessageQueueId_t CCSDSHandler::getRequestQueue() {
return tcDistributorQueueId;
}
ReturnValue_t CCSDSHandler::executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size) {
ReturnValue_t result = RETURN_OK;
switch (actionId) {
case SET_LOW_RATE: {
result = ptmeConfig->setRate(RATE_100KBPS);
break;
}
case SET_HIGH_RATE: {
result = ptmeConfig->setRate(RATE_500KBPS);
break;
}
case ARBITRARY_RATE: {
uint32_t bitrate = 0;
SerializeAdapter::deSerialize(&bitrate, &data, &size, SerializeIF::Endianness::BIG);
result = ptmeConfig->setRate(bitrate);
break;
}
case EN_TRANSMITTER: {
enableTransmit();
return EXECUTION_FINISHED;
}
case DISABLE_TRANSMITTER: {
disableTransmit();
return EXECUTION_FINISHED;
}
case ENABLE_TX_CLK_MANIPULATOR: {
result = ptmeConfig->configTxManipulator(true);
break;
}
case DISABLE_TX_CLK_MANIPULATOR: {
result = ptmeConfig->configTxManipulator(false);
break;
}
case UPDATE_ON_RISING_EDGE: {
result = ptmeConfig->invertTxClock(false);
break;
}
case UPDATE_ON_FALLING_EDGE: {
result = ptmeConfig->invertTxClock(true);
break;
}
default:
return COMMAND_NOT_IMPLEMENTED;
ReturnValue_t CCSDSHandler::executeAction(Action* action) { return action->handle(); }
ReturnValue_t CCSDSHandler::handleAction(SetLowRateAction* action) {
ReturnValue_t result = ptmeConfig->setRate(RATE_100KBPS);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
if (result != RETURN_OK) {
return result;
return result;
}
ReturnValue_t CCSDSHandler::handleAction(SetHighRateAction* action) {
ReturnValue_t result = ptmeConfig->setRate(RATE_500KBPS);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
ReturnValue_t CCSDSHandler::handleAction(ArbitraryRateAction* action) {
ReturnValue_t result = ptmeConfig->setRate(action->bitrate);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
ReturnValue_t CCSDSHandler::handleAction(EnTransmitterAction* action) {
enableTransmit();
return EXECUTION_FINISHED;
}
ReturnValue_t CCSDSHandler::handleAction(DisableTransmitterAction* action) {
disableTransmit();
return EXECUTION_FINISHED;
}
ReturnValue_t CCSDSHandler::handleAction(EnableTxClkManipulatorAction* action) {
ReturnValue_t result = ptmeConfig->configTxManipulator(true);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
ReturnValue_t CCSDSHandler::handleAction(DisableTxClkManipulatorAction* action) {
ReturnValue_t result = ptmeConfig->configTxManipulator(false);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
ReturnValue_t CCSDSHandler::handleAction(UpdateOnRisingEdgeAction* action) {
ReturnValue_t result = ptmeConfig->invertTxClock(false);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
ReturnValue_t CCSDSHandler::handleAction(UpdateOnFallingEdgeAction* action) {
ReturnValue_t result = ptmeConfig->invertTxClock(true);
if (result == HasReturnvaluesIF::RETURN_OK) {
return EXECUTION_FINISHED;
}
return result;
}
void CCSDSHandler::checkEvents() {
EventMessage event;
for (ReturnValue_t result = eventQueue->receiveMessage(&event); result == RETURN_OK;

View File

@ -3,6 +3,7 @@
#include <unordered_map>
#include "CCSDSActions.h"
#include "OBSWConfig.h"
#include "VirtualChannel.h"
#include "fsfw/action/ActionHelper.h"
@ -76,8 +77,17 @@ class CCSDSHandler : public SystemObject,
uint16_t getIdentifier() override;
MessageQueueId_t getRequestQueue() override;
virtual ReturnValue_t executeAction(ActionId_t actionId, MessageQueueId_t commandedBy,
const uint8_t* data, size_t size);
virtual ActionHelper* getActionHelper() override;
virtual ReturnValue_t executeAction(Action* action);
ReturnValue_t handleAction(SetLowRateAction* action);
ReturnValue_t handleAction(SetHighRateAction* action);
ReturnValue_t handleAction(EnTransmitterAction* action);
ReturnValue_t handleAction(DisableTransmitterAction* action);
ReturnValue_t handleAction(ArbitraryRateAction* action);
ReturnValue_t handleAction(EnableTxClkManipulatorAction* action);
ReturnValue_t handleAction(DisableTxClkManipulatorAction* action);
ReturnValue_t handleAction(UpdateOnRisingEdgeAction* action);
ReturnValue_t handleAction(UpdateOnFallingEdgeAction* action);
private:
static const uint8_t INTERFACE_ID = CLASS_ID::CCSDS_HANDLER;
@ -85,18 +95,6 @@ class CCSDSHandler : public SystemObject,
static const uint32_t QUEUE_SIZE = common::CCSDS_HANDLER_QUEUE_SIZE;
static const ActionId_t SET_LOW_RATE = 0;
static const ActionId_t SET_HIGH_RATE = 1;
static const ActionId_t EN_TRANSMITTER = 2;
static const ActionId_t DISABLE_TRANSMITTER = 3;
static const ActionId_t ARBITRARY_RATE = 4;
static const ActionId_t ENABLE_TX_CLK_MANIPULATOR = 5;
static const ActionId_t DISABLE_TX_CLK_MANIPULATOR = 6;
// Will update data with respect to tx clock signal of cadu bitstream on rising edge
static const ActionId_t UPDATE_ON_RISING_EDGE = 7;
// Will update data with respect to tx clock signal of cadu bitstream on falling edge
static const ActionId_t UPDATE_ON_FALLING_EDGE = 8;
// Syrlinks supports two bitrates (200 kbps and 1000 kbps)
// Due to convolutional code added by the syrlinks the input frequency must be half the
// target frequency
@ -145,6 +143,17 @@ class CCSDSHandler : public SystemObject,
bool linkState = DOWN;
// instances of the actions
SetLowRateAction setLowRateAction = SetLowRateAction(this);
SetHighRateAction setHighRateAction = SetHighRateAction(this);
EnTransmitterAction enTransmitterAction = EnTransmitterAction(this);
DisableTransmitterAction disableTransmitterAction = DisableTransmitterAction(this);
ArbitraryRateAction arbitraryRateAction = ArbitraryRateAction(this);
EnableTxClkManipulatorAction enableTxClkManipulatorAction = EnableTxClkManipulatorAction(this);
DisableTxClkManipulatorAction disableTxClkManipulatorAction = DisableTxClkManipulatorAction(this);
UpdateOnRisingEdgeAction updateOnRisingEdgeAction = UpdateOnRisingEdgeAction(this);
UpdateOnFallingEdgeAction updateOnFallingEdgeAction = UpdateOnFallingEdgeAction(this);
void readCommandQueue(void);
void handleTelemetry();
void handleTelecommands();