Merge remote-tracking branch 'origin/develop' into feature_str_assy
All checks were successful
EIVE/eive-obsw/pipeline/pr-develop This commit looks good

This commit is contained in:
Robin Müller 2023-03-08 11:13:02 +01:00
commit d30bab7bc0
No known key found for this signature in database
GPG Key ID: 71B58F8A3CDFA9AC
19 changed files with 242 additions and 158 deletions

View File

@ -22,6 +22,20 @@ will consitute of a breaking change warranting a new major release:
## Changed ## Changed
- Persistent TM stores will now create new files on each reboot.
- Fast ACS subsystem commanding: Command SUS board consecutively with other devices now
- Star Tracker: Use ground confguration for EM and flight config for FM by default.
## Fixed
- Star Tracker: OFF to NORMAL transition now posssible. Requires FSFW bump which sets
transition source modes properly for those transitions.
FSFW PR: https://egit.irs.uni-stuttgart.de/eive/fsfw/pulls/131
- Star Tracker JSON initialization is now done during object initization instead of redoing it
when building a command. This avoids missed deadlines issues in the ACS PST.
- Allow arbitrary submodes for dual lane boards to avoid FDIR reactions of subsystem components.
Bump FSFW to allow this.
- PUS 15 was not scheduled
- Transmitter timeout set to 2 minutes instead of 15 minutes. This will prevent to discharge the battery - Transmitter timeout set to 2 minutes instead of 15 minutes. This will prevent to discharge the battery
in case the syrlinks starts transmitting due to detection of unintentional bitlock. This happened e.g. on ground in case the syrlinks starts transmitting due to detection of unintentional bitlock. This happened e.g. on ground
when the uplink to the flying latop was established. when the uplink to the flying latop was established.

View File

@ -71,11 +71,13 @@ if(EIVE_Q7S_EM)
1 1
CACHE STRING "Q7S EM configuration") CACHE STRING "Q7S EM configuration")
set(INIT_VAL 0) set(INIT_VAL 0)
set(OBSW_STAR_TRACKER_GROUND_CONFIG 1)
else() else()
set(OBSW_Q7S_EM set(OBSW_Q7S_EM
0 0
CACHE STRING "Q7S EM configuration") CACHE STRING "Q7S EM configuration")
set(INIT_VAL 1) set(INIT_VAL 1)
set(OBSW_STAR_TRACKER_GROUND_CONFIG 0)
endif() endif()
set(OBSW_ADD_MGT set(OBSW_ADD_MGT
${INIT_VAL} ${INIT_VAL}

View File

@ -67,7 +67,7 @@
#define OBSW_PRINT_MISSED_DEADLINES 1 #define OBSW_PRINT_MISSED_DEADLINES 1
#define OBSW_MPSOC_JTAG_BOOT 0 #define OBSW_MPSOC_JTAG_BOOT 0
#define OBSW_STAR_TRACKER_GROUND_CONFIG 1 #define OBSW_STAR_TRACKER_GROUND_CONFIG @OBSW_STAR_TRACKER_GROUND_CONFIG@
#define OBSW_SYRLINKS_SIMULATED @OBSW_SYRLINKS_SIMULATED@ #define OBSW_SYRLINKS_SIMULATED @OBSW_SYRLINKS_SIMULATED@
#define OBSW_ADD_TEST_CODE 0 #define OBSW_ADD_TEST_CODE 0
#define OBSW_ADD_TEST_TASK 0 #define OBSW_ADD_TEST_TASK 0

View File

@ -911,9 +911,23 @@ void ObjectFactory::createStrComponents(PowerSwitchIF* pwrSwitcher) {
startracker::MAX_FRAME_SIZE * 2 + 2, UartModes::NON_CANONICAL); startracker::MAX_FRAME_SIZE * 2 + 2, UartModes::NON_CANONICAL);
starTrackerCookie->setNoFixedSizeReply(); starTrackerCookie->setNoFixedSizeReply();
StrHelper* strHelper = new StrHelper(objects::STR_HELPER); StrHelper* strHelper = new StrHelper(objects::STR_HELPER);
const char* paramJsonFile = nullptr;
#ifdef EGSE
paramJsonFile = "/home/pi/arcsec/json/flight-config.json";
#else
#if OBSW_STAR_TRACKER_GROUND_CONFIG == 1
paramJsonFile = "/mnt/sd0/startracker/ground-config.json";
#else
paramJsonFile = "/mnt/sd0/startracker/flight-config.json";
#endif
#endif
if (paramJsonFile == nullptr) {
sif::error << "No valid Star Tracker parameter JSON file" << std::endl;
}
auto starTracker = auto starTracker =
new StarTrackerHandler(objects::STAR_TRACKER, objects::UART_COM_IF, starTrackerCookie, new StarTrackerHandler(objects::STAR_TRACKER, objects::UART_COM_IF, starTrackerCookie,
strHelper, pcdu::PDU1_CH2_STAR_TRACKER_5V); paramJsonFile, strHelper, pcdu::PDU1_CH2_STAR_TRACKER_5V);
starTracker->setPowerSwitcher(pwrSwitcher); starTracker->setPowerSwitcher(pwrSwitcher);
starTracker->connectModeTreeParent(*strAssy); starTracker->connectModeTreeParent(*strAssy);
} }

View File

@ -523,6 +523,10 @@ void scheduling::createPusTasks(TaskFactory& factory, TaskDeadlineMissedFunction
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
scheduling::printAddObjectError("PUS_8", objects::PUS_SERVICE_8_FUNCTION_MGMT); scheduling::printAddObjectError("PUS_8", objects::PUS_SERVICE_8_FUNCTION_MGMT);
} }
result = pusMedPrio->addComponent(objects::PUS_SERVICE_15_TM_STORAGE);
if (result != returnvalue::OK) {
scheduling::printAddObjectError("PUS_15", objects::PUS_SERVICE_15_TM_STORAGE);
}
result = pusMedPrio->addComponent(objects::PUS_SERVICE_11_TC_SCHEDULER); result = pusMedPrio->addComponent(objects::PUS_SERVICE_11_TC_SCHEDULER);
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
scheduling::printAddObjectError("PUS_11", objects::PUS_SERVICE_11_TC_SCHEDULER); scheduling::printAddObjectError("PUS_11", objects::PUS_SERVICE_11_TC_SCHEDULER);

View File

@ -21,15 +21,15 @@ SdCardManager* SdCardManager::INSTANCE = nullptr;
SdCardManager::SdCardManager() : SystemObject(objects::SDC_MANAGER), cmdExecutor(256) { SdCardManager::SdCardManager() : SystemObject(objects::SDC_MANAGER), cmdExecutor(256) {
sdLock = MutexFactory::instance()->createMutex(); sdLock = MutexFactory::instance()->createMutex();
ReturnValue_t result = sdLock->lockMutex(); prefLock = MutexFactory::instance()->createMutex();
if (result != returnvalue::OK) { defaultLock = MutexFactory::instance()->createMutex();
MutexGuard mg(prefLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) {
sif::error << "SdCardManager::SdCardManager: Mutex lock failed" << std::endl; sif::error << "SdCardManager::SdCardManager: Mutex lock failed" << std::endl;
} }
uint8_t prefSdRaw = 0; uint8_t prefSdRaw = 0;
result = scratch::readNumber(scratch::PREFERED_SDC_KEY, prefSdRaw); ReturnValue_t result = scratch::readNumber(scratch::PREFERED_SDC_KEY, prefSdRaw);
if (sdLock->unlockMutex() != returnvalue::OK) {
sif::error << "SdCardManager::SdCardManager: Mutex unlock failed" << std::endl;
}
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
if (result == scratch::KEY_NOT_FOUND) { if (result == scratch::KEY_NOT_FOUND) {
@ -37,14 +37,16 @@ SdCardManager::SdCardManager() : SystemObject(objects::SDC_MANAGER), cmdExecutor
"Preferred SD card not set. Setting to 0" "Preferred SD card not set. Setting to 0"
<< std::endl; << std::endl;
setPreferredSdCard(sd::SdCard::SLOT_0); setPreferredSdCard(sd::SdCard::SLOT_0);
sdInfo.pref = sd::SdCard::SLOT_0; scratch::writeNumber(scratch::PREFERED_SDC_KEY, static_cast<uint8_t>(sd::SdCard::SLOT_0));
prefSdRaw = sd::SdCard::SLOT_0;
} else { } else {
// Should not happen. // Should not happen.
// TODO: Maybe trigger event? // TODO: Maybe trigger event?
sif::error << "SdCardManager::SdCardManager: Reading preferred SD card from scratch" sif::error << "SdCardManager::SdCardManager: Reading preferred SD card from scratch"
"buffer failed" "buffer failed"
<< std::endl; << std::endl;
sdInfo.pref = sd::SdCard::SLOT_0; prefSdRaw = sd::SdCard::SLOT_0;
} }
} }
sdInfo.pref = static_cast<sd::SdCard>(prefSdRaw); sdInfo.pref = static_cast<sd::SdCard>(prefSdRaw);
@ -195,7 +197,7 @@ ReturnValue_t SdCardManager::setSdCardState(sd::SdCard sdCard, bool on) {
ReturnValue_t SdCardManager::getSdCardsStatus(SdStatePair& active) { ReturnValue_t SdCardManager::getSdCardsStatus(SdStatePair& active) {
using namespace std; using namespace std;
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(sdLock, LOCK_TYPE, SD_LOCK_TIMEOUT, LOCK_CTX);
if (not filesystem::exists(SD_STATE_FILE)) { if (not filesystem::exists(SD_STATE_FILE)) {
return STATUS_FILE_NEXISTS; return STATUS_FILE_NEXISTS;
} }
@ -378,7 +380,7 @@ void SdCardManager::processSdStatusLine(std::pair<sd::SdState, sd::SdState>& act
} }
std::optional<sd::SdCard> SdCardManager::getPreferredSdCard() const { std::optional<sd::SdCard> SdCardManager::getPreferredSdCard() const {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(prefLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
auto res = mg.getLockResult(); auto res = mg.getLockResult();
if (res != returnvalue::OK) { if (res != returnvalue::OK) {
sif::error << "SdCardManager::getPreferredSdCard: Lock error" << std::endl; sif::error << "SdCardManager::getPreferredSdCard: Lock error" << std::endl;
@ -387,7 +389,7 @@ std::optional<sd::SdCard> SdCardManager::getPreferredSdCard() const {
} }
ReturnValue_t SdCardManager::setPreferredSdCard(sd::SdCard sdCard) { ReturnValue_t SdCardManager::setPreferredSdCard(sd::SdCard sdCard) {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(prefLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
if (sdCard == sd::SdCard::BOTH) { if (sdCard == sd::SdCard::BOTH) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
@ -399,7 +401,7 @@ ReturnValue_t SdCardManager::updateSdCardStateFile() {
if (cmdExecutor.getCurrentState() == CommandExecutor::States::PENDING) { if (cmdExecutor.getCurrentState() == CommandExecutor::States::PENDING) {
return CommandExecutor::COMMAND_PENDING; return CommandExecutor::COMMAND_PENDING;
} }
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(sdLock, LOCK_TYPE, SD_LOCK_TIMEOUT, LOCK_CTX);
// Use q7hw utility and pipe the command output into the state file // Use q7hw utility and pipe the command output into the state file
std::string updateCmd = "q7hw sd info all > " + std::string(SD_STATE_FILE); std::string updateCmd = "q7hw sd info all > " + std::string(SD_STATE_FILE);
cmdExecutor.load(updateCmd, blocking, printCmdOutput); cmdExecutor.load(updateCmd, blocking, printCmdOutput);
@ -411,7 +413,7 @@ ReturnValue_t SdCardManager::updateSdCardStateFile() {
} }
const char* SdCardManager::getCurrentMountPrefix() const { const char* SdCardManager::getCurrentMountPrefix() const {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(defaultLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
if (currentPrefix.has_value()) { if (currentPrefix.has_value()) {
return currentPrefix.value().c_str(); return currentPrefix.value().c_str();
} }
@ -464,7 +466,7 @@ void SdCardManager::setPrintCommandOutput(bool print) { this->printCmdOutput = p
bool SdCardManager::isSdCardUsable(std::optional<sd::SdCard> sdCard) { bool SdCardManager::isSdCardUsable(std::optional<sd::SdCard> sdCard) {
{ {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(defaultLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
if (markedUnusable) { if (markedUnusable) {
return false; return false;
} }
@ -560,7 +562,7 @@ ReturnValue_t SdCardManager::performFsck(sd::SdCard sdcard, bool printOutput, in
} }
void SdCardManager::setActiveSdCard(sd::SdCard sdCard) { void SdCardManager::setActiveSdCard(sd::SdCard sdCard) {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(defaultLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
sdInfo.active = sdCard; sdInfo.active = sdCard;
if (sdInfo.active == sd::SdCard::SLOT_0) { if (sdInfo.active == sd::SdCard::SLOT_0) {
currentPrefix = config::SD_0_MOUNT_POINT; currentPrefix = config::SD_0_MOUNT_POINT;
@ -570,7 +572,7 @@ void SdCardManager::setActiveSdCard(sd::SdCard sdCard) {
} }
std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const { std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(defaultLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
if (markedUnusable) { if (markedUnusable) {
return std::nullopt; return std::nullopt;
} }
@ -578,6 +580,6 @@ std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const {
} }
void SdCardManager::markUnusable() { void SdCardManager::markUnusable() {
MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX); MutexGuard mg(defaultLock, LOCK_TYPE, OTHER_TIMEOUT, LOCK_CTX);
markedUnusable = true; markedUnusable = true;
} }

View File

@ -224,8 +224,11 @@ class SdCardManager : public SystemObject, public SdCardMountedIF {
bool printCmdOutput = true; bool printCmdOutput = true;
bool markedUnusable = false; bool markedUnusable = false;
MutexIF* sdLock = nullptr; MutexIF* sdLock = nullptr;
MutexIF* prefLock = nullptr;
MutexIF* defaultLock = nullptr;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING; static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 150; static constexpr uint32_t SD_LOCK_TIMEOUT = 250;
static constexpr uint32_t OTHER_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "SdCardManager"; static constexpr char LOCK_CTX[] = "SdCardManager";
SdCardManager(); SdCardManager();

2
fsfw

@ -1 +1 @@
Subproject commit e9d9f446053699a91d89250910cc0d59d05fbe6b Subproject commit 1b7493f945302b3785ceba6e7a34a727e3898a13

View File

@ -5,14 +5,14 @@
ArcsecJsonParamBase::ArcsecJsonParamBase(std::string setName) : setName(setName) {} ArcsecJsonParamBase::ArcsecJsonParamBase(std::string setName) : setName(setName) {}
ReturnValue_t ArcsecJsonParamBase::create(std::string fullname, uint8_t* buffer) { ReturnValue_t ArcsecJsonParamBase::create(std::string fullname, uint8_t* buffer) {
ReturnValue_t result = returnvalue::OK; // ReturnValue_t result = returnvalue::OK;
result = init(fullname); // result = init(fullname);
if (result != returnvalue::OK) { // if (result != returnvalue::OK) {
sif::warning << "ArcsecJsonParamBase::create: Failed to init parameter command for set " // sif::warning << "ArcsecJsonParamBase::create: Failed to init parameter command for set "
<< setName << std::endl; // << setName << std::endl;
return result; // return result;
} // }
result = createCommand(buffer); ReturnValue_t result = createCommand(buffer);
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
sif::warning << "ArcsecJsonParamBase::create: Failed to create parameter command for set " sif::warning << "ArcsecJsonParamBase::create: Failed to create parameter command for set "
<< setName << std::endl; << setName << std::endl;
@ -74,12 +74,17 @@ ReturnValue_t ArcsecJsonParamBase::init(const std::string filename) {
<< std::endl; << std::endl;
return JSON_FILE_NOT_EXISTS; return JSON_FILE_NOT_EXISTS;
} }
try {
createJsonObject(filename); createJsonObject(filename);
result = initSet(); result = initSet();
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
return result; return result;
} }
return returnvalue::OK; return returnvalue::OK;
} catch (json::exception& e) {
// TODO: Re-create json file from backup here.
return returnvalue::FAILED;
}
} }
void ArcsecJsonParamBase::createJsonObject(const std::string fullname) { void ArcsecJsonParamBase::createJsonObject(const std::string fullname) {

View File

@ -41,6 +41,17 @@ class ArcsecJsonParamBase {
*/ */
ArcsecJsonParamBase(std::string setName); ArcsecJsonParamBase(std::string setName);
/**
* @brief Initializes the properties json object and the set json object
*
* @param fullname Name including absolute path to json file
* @param setName The name of the set to work on
*
* @param return JSON_FILE_NOT_EXISTS if specified file does not exist, otherwise
* returnvalue::OK
*/
ReturnValue_t init(const std::string filename);
/** /**
* @brief Fills a buffer with a parameter set * @brief Fills a buffer with a parameter set
* *
@ -124,17 +135,6 @@ class ArcsecJsonParamBase {
*/ */
virtual ReturnValue_t createCommand(uint8_t* buffer) = 0; virtual ReturnValue_t createCommand(uint8_t* buffer) = 0;
/**
* @brief Initializes the properties json object and the set json object
*
* @param fullname Name including absolute path to json file
* @param setName The name of the set to work on
*
* @param return JSON_FILE_NOT_EXISTS if specified file does not exist, otherwise
* returnvalue::OK
*/
ReturnValue_t init(const std::string filename);
void createJsonObject(const std::string fullname); void createJsonObject(const std::string fullname);
/** /**

View File

@ -1,8 +1,11 @@
#include "StarTrackerHandler.h" #include "StarTrackerHandler.h"
#include <fsfw/ipc/QueueFactory.h> #include <fsfw/ipc/QueueFactory.h>
#include <fsfw/timemanager/Stopwatch.h>
#include <atomic>
#include <fstream> #include <fstream>
#include <thread>
#include "OBSWConfig.h" #include "OBSWConfig.h"
#include "StarTrackerJsonCommands.h" #include "StarTrackerJsonCommands.h"
@ -14,8 +17,11 @@ extern "C" {
#include "common/misc.h" #include "common/misc.h"
} }
std::atomic_bool JCFG_DONE(false);
StarTrackerHandler::StarTrackerHandler(object_id_t objectId, object_id_t comIF, CookieIF* comCookie, StarTrackerHandler::StarTrackerHandler(object_id_t objectId, object_id_t comIF, CookieIF* comCookie,
StrHelper* strHelper, power::Switch_t powerSwitch) const char* jsonFileStr, StrHelper* strHelper,
power::Switch_t powerSwitch)
: DeviceHandlerBase(objectId, comIF, comCookie), : DeviceHandlerBase(objectId, comIF, comCookie),
temperatureSet(this), temperatureSet(this),
versionSet(this), versionSet(this),
@ -40,6 +46,7 @@ StarTrackerHandler::StarTrackerHandler(object_id_t objectId, object_id_t comIF,
logSubscriptionSet(this), logSubscriptionSet(this),
debugCameraSet(this), debugCameraSet(this),
strHelper(strHelper), strHelper(strHelper),
paramJsonFile(jsonFileStr),
powerSwitch(powerSwitch) { powerSwitch(powerSwitch) {
if (comCookie == nullptr) { if (comCookie == nullptr) {
sif::error << "StarTrackerHandler: Invalid com cookie" << std::endl; sif::error << "StarTrackerHandler: Invalid com cookie" << std::endl;
@ -59,6 +66,11 @@ ReturnValue_t StarTrackerHandler::initialize() {
return result; return result;
} }
// Spin up a thread to do the JSON initialization, takes 200-250 ms which would
// delay whole satellite boot process.
jcfgCountdown.resetTimer();
jsonCfgTask = std::thread{setUpJsonCfgs, std::ref(jcfgs), paramJsonFile.c_str()};
EventManagerIF* manager = ObjectManager::instance()->get<EventManagerIF>(objects::EVENT_MANAGER); EventManagerIF* manager = ObjectManager::instance()->get<EventManagerIF>(objects::EVENT_MANAGER);
if (manager == nullptr) { if (manager == nullptr) {
#if FSFW_CPP_OSTREAM_ENABLED == 1 #if FSFW_CPP_OSTREAM_ENABLED == 1
@ -240,8 +252,19 @@ void StarTrackerHandler::doStartUp() {
// the device handler's submode to the star tracker's mode // the device handler's submode to the star tracker's mode
return; return;
case StartupState::DONE: case StartupState::DONE:
if (jcfgCountdown.isBusy()) {
startupState = StartupState::WAIT_JCFG;
return;
}
startupState = StartupState::IDLE; startupState = StartupState::IDLE;
break; break;
case StartupState::WAIT_JCFG: {
if (jcfgCountdown.hasTimedOut()) {
startupState = StartupState::IDLE;
break;
}
return;
}
default: default:
return; return;
} }
@ -419,8 +442,7 @@ ReturnValue_t StarTrackerHandler::buildCommandFromCommand(DeviceCommandId_t devi
return returnvalue::OK; return returnvalue::OK;
} }
case (startracker::SUBSCRIPTION): { case (startracker::SUBSCRIPTION): {
Subscription subscription; result = prepareParamCommand(commandData, commandDataLen, jcfgs.subscription);
result = prepareParamCommand(commandData, commandDataLen, subscription);
return returnvalue::OK; return returnvalue::OK;
} }
case (startracker::REQ_SOLUTION): { case (startracker::REQ_SOLUTION): {
@ -436,68 +458,55 @@ ReturnValue_t StarTrackerHandler::buildCommandFromCommand(DeviceCommandId_t devi
return returnvalue::OK; return returnvalue::OK;
} }
case (startracker::LIMITS): { case (startracker::LIMITS): {
Limits limits; result = prepareParamCommand(commandData, commandDataLen, jcfgs.limits);
result = prepareParamCommand(commandData, commandDataLen, limits);
return result; return result;
} }
case (startracker::MOUNTING): { case (startracker::MOUNTING): {
Mounting mounting; result = prepareParamCommand(commandData, commandDataLen, jcfgs.mounting);
result = prepareParamCommand(commandData, commandDataLen, mounting);
return result; return result;
} }
case (startracker::IMAGE_PROCESSOR): { case (startracker::IMAGE_PROCESSOR): {
ImageProcessor imageProcessor; result = prepareParamCommand(commandData, commandDataLen, jcfgs.imageProcessor);
result = prepareParamCommand(commandData, commandDataLen, imageProcessor);
return result; return result;
} }
case (startracker::CAMERA): { case (startracker::CAMERA): {
Camera camera; result = prepareParamCommand(commandData, commandDataLen, jcfgs.camera);
result = prepareParamCommand(commandData, commandDataLen, camera);
return result; return result;
} }
case (startracker::CENTROIDING): { case (startracker::CENTROIDING): {
Centroiding centroiding; result = prepareParamCommand(commandData, commandDataLen, jcfgs.centroiding);
result = prepareParamCommand(commandData, commandDataLen, centroiding);
return result; return result;
} }
case (startracker::LISA): { case (startracker::LISA): {
Lisa lisa; result = prepareParamCommand(commandData, commandDataLen, jcfgs.lisa);
result = prepareParamCommand(commandData, commandDataLen, lisa);
return result; return result;
} }
case (startracker::MATCHING): { case (startracker::MATCHING): {
Matching matching; result = prepareParamCommand(commandData, commandDataLen, jcfgs.matching);
result = prepareParamCommand(commandData, commandDataLen, matching);
return result; return result;
} }
case (startracker::VALIDATION): { case (startracker::VALIDATION): {
Validation validation; result = prepareParamCommand(commandData, commandDataLen, jcfgs.validation);
result = prepareParamCommand(commandData, commandDataLen, validation);
return result; return result;
} }
case (startracker::ALGO): { case (startracker::ALGO): {
Algo algo; result = prepareParamCommand(commandData, commandDataLen, jcfgs.algo);
result = prepareParamCommand(commandData, commandDataLen, algo);
return result; return result;
} }
case (startracker::TRACKING): { case (startracker::TRACKING): {
Tracking tracking; result = prepareParamCommand(commandData, commandDataLen, jcfgs.tracking);
result = prepareParamCommand(commandData, commandDataLen, tracking);
return result; return result;
} }
case (startracker::LOGLEVEL): { case (startracker::LOGLEVEL): {
LogLevel logLevel; result = prepareParamCommand(commandData, commandDataLen, jcfgs.logLevel);
result = prepareParamCommand(commandData, commandDataLen, logLevel);
return result; return result;
} }
case (startracker::LOGSUBSCRIPTION): { case (startracker::LOGSUBSCRIPTION): {
LogSubscription logSubscription; result = prepareParamCommand(commandData, commandDataLen, jcfgs.logSubscription);
result = prepareParamCommand(commandData, commandDataLen, logSubscription);
return result; return result;
} }
case (startracker::DEBUG_CAMERA): { case (startracker::DEBUG_CAMERA): {
DebugCamera debugCamera; result = prepareParamCommand(commandData, commandDataLen, jcfgs.debugCamera);
result = prepareParamCommand(commandData, commandDataLen, debugCamera);
return result; return result;
} }
case (startracker::CHECKSUM): { case (startracker::CHECKSUM): {
@ -746,6 +755,24 @@ void StarTrackerHandler::bootFirmware(Mode_t toMode) {
} }
} }
void StarTrackerHandler::setUpJsonCfgs(JsonConfigs& cfgs, const char* paramJsonFile) {
cfgs.tracking.init(paramJsonFile);
cfgs.logLevel.init(paramJsonFile);
cfgs.logSubscription.init(paramJsonFile);
cfgs.debugCamera.init(paramJsonFile);
cfgs.algo.init(paramJsonFile);
cfgs.validation.init(paramJsonFile);
cfgs.matching.init(paramJsonFile);
cfgs.lisa.init(paramJsonFile);
cfgs.centroiding.init(paramJsonFile);
cfgs.camera.init(paramJsonFile);
cfgs.imageProcessor.init(paramJsonFile);
cfgs.mounting.init(paramJsonFile);
cfgs.limits.init(paramJsonFile);
cfgs.subscription.init(paramJsonFile);
JCFG_DONE = true;
}
void StarTrackerHandler::bootBootloader() { void StarTrackerHandler::bootBootloader() {
if (internalState == InternalState::IDLE) { if (internalState == InternalState::IDLE) {
internalState = InternalState::BOOT_BOOTLOADER; internalState = InternalState::BOOT_BOOTLOADER;
@ -1650,6 +1677,7 @@ void StarTrackerHandler::prepareHistogramRequest() {
ReturnValue_t StarTrackerHandler::prepareParamCommand(const uint8_t* commandData, ReturnValue_t StarTrackerHandler::prepareParamCommand(const uint8_t* commandData,
size_t commandDataLen, size_t commandDataLen,
ArcsecJsonParamBase& paramSet) { ArcsecJsonParamBase& paramSet) {
Stopwatch watch;
ReturnValue_t result = returnvalue::OK; ReturnValue_t result = returnvalue::OK;
if (commandDataLen > MAX_PATH_SIZE) { if (commandDataLen > MAX_PATH_SIZE) {
return FILE_PATH_TOO_LONG; return FILE_PATH_TOO_LONG;

View File

@ -2,6 +2,9 @@
#define MISSION_DEVICES_STARTRACKERHANDLER_H_ #define MISSION_DEVICES_STARTRACKERHANDLER_H_
#include <fsfw/datapool/PoolReadGuard.h> #include <fsfw/datapool/PoolReadGuard.h>
#include <linux/devices/startracker/StarTrackerJsonCommands.h>
#include <thread>
#include "ArcsecDatalinkLayer.h" #include "ArcsecDatalinkLayer.h"
#include "ArcsecJsonParamBase.h" #include "ArcsecJsonParamBase.h"
@ -35,7 +38,7 @@ class StarTrackerHandler : public DeviceHandlerBase {
* to high to enable the device. * to high to enable the device.
*/ */
StarTrackerHandler(object_id_t objectId, object_id_t comIF, CookieIF* comCookie, StarTrackerHandler(object_id_t objectId, object_id_t comIF, CookieIF* comCookie,
StrHelper* strHelper, power::Switch_t powerSwitch); const char* jsonFileStr, StrHelper* strHelper, power::Switch_t powerSwitch);
virtual ~StarTrackerHandler(); virtual ~StarTrackerHandler();
ReturnValue_t initialize() override; ReturnValue_t initialize() override;
@ -216,15 +219,29 @@ class StarTrackerHandler : public DeviceHandlerBase {
// Loading firmware requires some time and the command will not trigger a reply when executed // Loading firmware requires some time and the command will not trigger a reply when executed
Countdown bootCountdown; Countdown bootCountdown;
#ifdef EGSE struct JsonConfigs {
std::string paramJsonFile = "/home/pi/arcsec/json/flight-config.json"; Tracking tracking;
#else LogLevel logLevel;
#if OBSW_STAR_TRACKER_GROUND_CONFIG == 1 LogSubscription logSubscription;
std::string paramJsonFile = "/mnt/sd0/startracker/ground-config.json"; DebugCamera debugCamera;
#else Algo algo;
std::string paramJsonFile = "/mnt/sd0/startracker/flight-config.json"; Validation validation;
#endif Matching matching;
#endif Lisa lisa;
Centroiding centroiding;
Camera camera;
ImageProcessor imageProcessor;
Mounting mounting;
Limits limits;
Subscription subscription;
};
JsonConfigs jcfgs;
Countdown jcfgCountdown = Countdown(250);
bool commandExecuted = false;
std::thread jsonCfgTask;
static void setUpJsonCfgs(JsonConfigs& cfgs, const char* paramJsonFile);
std::string paramJsonFile;
enum class NormalState { TEMPERATURE_REQUEST, SOLUTION_REQUEST }; enum class NormalState { TEMPERATURE_REQUEST, SOLUTION_REQUEST };
@ -262,7 +279,14 @@ class StarTrackerHandler : public DeviceHandlerBase {
InternalState internalState = InternalState::IDLE; InternalState internalState = InternalState::IDLE;
enum class StartupState { IDLE, CHECK_PROGRAM, WAIT_CHECK_PROGRAM, BOOT_BOOTLOADER, DONE }; enum class StartupState {
IDLE,
CHECK_PROGRAM,
WAIT_CHECK_PROGRAM,
BOOT_BOOTLOADER,
WAIT_JCFG,
DONE
};
StartupState startupState = StartupState::IDLE; StartupState startupState = StartupState::IDLE;

View File

@ -96,7 +96,6 @@ inline void DualLaneAssemblyBase::initModeTableEntry(
entry.setObject(id); entry.setObject(id);
entry.setMode(MODE_OFF); entry.setMode(MODE_OFF);
entry.setSubmode(SUBMODE_NONE); entry.setSubmode(SUBMODE_NONE);
entry.setInheritSubmode(false);
modeTable.insert(entry); modeTable.insert(entry);
} }

View File

@ -8,7 +8,6 @@ RwAssembly::RwAssembly(object_id_t objectId, PowerSwitchIF* pwrSwitcher, power::
entry.setObject(helper.rwIds[idx]); entry.setObject(helper.rwIds[idx]);
entry.setMode(MODE_OFF); entry.setMode(MODE_OFF);
entry.setSubmode(SUBMODE_NONE); entry.setSubmode(SUBMODE_NONE);
entry.setInheritSubmode(false);
modeTable.insert(entry); modeTable.insert(entry);
} }
} }

View File

@ -12,7 +12,6 @@ TcsBoardAssembly::TcsBoardAssembly(object_id_t objectId, PowerSwitchIF* pwrSwitc
entry.setObject(helper.rtdInfos[idx].first); entry.setObject(helper.rtdInfos[idx].first);
entry.setMode(MODE_OFF); entry.setMode(MODE_OFF);
entry.setSubmode(SUBMODE_NONE); entry.setSubmode(SUBMODE_NONE);
entry.setInheritSubmode(false);
modeTable.insert(entry); modeTable.insert(entry);
} }
} }

View File

@ -6,8 +6,11 @@
#include <fsfw/subsystem/Subsystem.h> #include <fsfw/subsystem/Subsystem.h>
#include <fsfw/subsystem/modes/ModeDefinitions.h> #include <fsfw/subsystem/modes/ModeDefinitions.h>
#include <optional>
#include "eive/objects.h" #include "eive/objects.h"
#include "mission/acsDefs.h" #include "mission/acsDefs.h"
#include "mission/system/objects/definitions.h"
#include "util.h" #include "util.h"
AcsSubsystem satsystem::acs::ACS_SUBSYSTEM(objects::ACS_SUBSYSTEM, 12, 24); AcsSubsystem satsystem::acs::ACS_SUBSYSTEM(objects::ACS_SUBSYSTEM, 12, 24);
@ -100,16 +103,20 @@ Subsystem& satsystem::acs::init() {
ModeListEntry entry; ModeListEntry entry;
const char* ctxc = "satsystem::acs::init: generic target"; const char* ctxc = "satsystem::acs::init: generic target";
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, ArrayList<ModeListEntry>& table) { auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, ArrayList<ModeListEntry>& table,
bool allowAllSubmodes = false) {
entry.setObject(obj); entry.setObject(obj);
entry.setMode(mode); entry.setMode(mode);
entry.setSubmode(submode); entry.setSubmode(submode);
if (allowAllSubmodes) {
entry.allowAllSubmodes();
}
check(table.insert(entry), "satsystem::acs::init: generic target"); check(table.insert(entry), "satsystem::acs::init: generic target");
}; };
// Build TARGET PT transition 0 // Build TARGET PT transition 0
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TRANS_0.second); iht(objects::SUS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_PTG_TRANS_0.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TRANS_0.second); iht(objects::ACS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_PTG_TRANS_0.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TRANS_0.second);
check(ACS_SUBSYSTEM.addTable( check(ACS_SUBSYSTEM.addTable(
@ -117,7 +124,7 @@ Subsystem& satsystem::acs::init() {
ctxc); ctxc);
// Build SUS board transition // Build SUS board transition
iht(objects::SUS_BOARD_ASS, NML, 0, SUS_BOARD_NML_TRANS.second); iht(objects::SUS_BOARD_ASS, NML, duallane::A_SIDE, SUS_BOARD_NML_TRANS.second, true);
check(ACS_SUBSYSTEM.addTable(TableEntry(SUS_BOARD_NML_TRANS.first, &SUS_BOARD_NML_TRANS.second)), check(ACS_SUBSYSTEM.addTable(TableEntry(SUS_BOARD_NML_TRANS.first, &SUS_BOARD_NML_TRANS.second)),
ctxc); ctxc);
@ -182,10 +189,13 @@ void buildSafeSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -199,13 +209,14 @@ void buildSafeSequence(Subsystem& ss, ModeListEntry& eh) {
// Build SAFE target // Build SAFE target
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::SAFE, ACS_TABLE_SAFE_TGT.second); iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::SAFE, ACS_TABLE_SAFE_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_SAFE_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_SAFE_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_SAFE_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_SAFE_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_SAFE_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_SAFE_TGT.second, true);
check(ss.addTable(&ACS_TABLE_SAFE_TGT.second, ACS_TABLE_SAFE_TGT.first, false, true), ctxc); check(ss.addTable(&ACS_TABLE_SAFE_TGT.second, ACS_TABLE_SAFE_TGT.first, false, true), ctxc);
// Build SAFE transition 0 // Build SAFE transition 0
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_SAFE_TRANS_0.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_SAFE_TRANS_0.second);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_SAFE_TRANS_0.second); iht(objects::ACS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_SAFE_TRANS_0.second, true);
iht(objects::SUS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_SAFE_TRANS_0.second, true);
iht(objects::STR_ASSY, OFF, 0, ACS_TABLE_SAFE_TRANS_0.second); iht(objects::STR_ASSY, OFF, 0, ACS_TABLE_SAFE_TRANS_0.second);
iht(objects::RW_ASSY, OFF, 0, ACS_TABLE_SAFE_TRANS_0.second); iht(objects::RW_ASSY, OFF, 0, ACS_TABLE_SAFE_TRANS_0.second);
check(ss.addTable(&ACS_TABLE_SAFE_TRANS_0.second, ACS_TABLE_SAFE_TRANS_0.first, false, true), check(ss.addTable(&ACS_TABLE_SAFE_TRANS_0.second, ACS_TABLE_SAFE_TRANS_0.first, false, true),
@ -220,7 +231,6 @@ void buildSafeSequence(Subsystem& ss, ModeListEntry& eh) {
// Build SAFE sequence // Build SAFE sequence
ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TGT.first, 0, true); ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TGT.first, 0, true);
ihs(ACS_SEQUENCE_SAFE.second, SUS_BOARD_NML_TRANS.first, 0, false);
ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TRANS_0.first, 0, false); ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TRANS_0.first, 0, false);
ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TRANS_1.first, 0, false); ihs(ACS_SEQUENCE_SAFE.second, ACS_TABLE_SAFE_TRANS_1.first, 0, false);
check(ss.addSequence(&ACS_SEQUENCE_SAFE.second, ACS_SEQUENCE_SAFE.first, ACS_SEQUENCE_SAFE.first, check(ss.addSequence(&ACS_SEQUENCE_SAFE.second, ACS_SEQUENCE_SAFE.first, ACS_SEQUENCE_SAFE.first,
@ -233,10 +243,13 @@ void buildDetumbleSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -250,17 +263,15 @@ void buildDetumbleSequence(Subsystem& ss, ModeListEntry& eh) {
// Build DETUMBLE target // Build DETUMBLE target
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::DETUMBLE, ACS_TABLE_DETUMBLE_TGT.second); iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::DETUMBLE, ACS_TABLE_DETUMBLE_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_DETUMBLE_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_DETUMBLE_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TGT.second, true);
check(ss.addTable(&ACS_TABLE_DETUMBLE_TGT.second, ACS_TABLE_DETUMBLE_TGT.first, false, true), check(ss.addTable(&ACS_TABLE_DETUMBLE_TGT.second, ACS_TABLE_DETUMBLE_TGT.first, false, true),
ctxc); ctxc);
// SUS board transition table is defined above
// Build DETUMBLE transition 0 // Build DETUMBLE transition 0
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_DETUMBLE_TRANS_0.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_DETUMBLE_TRANS_0.second);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TRANS_0.second); iht(objects::ACS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_DETUMBLE_TRANS_0.second, true);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_DETUMBLE_TRANS_0.second); iht(objects::SUS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_DETUMBLE_TRANS_0.second, true);
iht(objects::STR_ASSY, OFF, 0, ACS_TABLE_DETUMBLE_TRANS_0.second); iht(objects::STR_ASSY, OFF, 0, ACS_TABLE_DETUMBLE_TRANS_0.second);
iht(objects::RW_ASSY, OFF, 0, ACS_TABLE_DETUMBLE_TRANS_0.second); iht(objects::RW_ASSY, OFF, 0, ACS_TABLE_DETUMBLE_TRANS_0.second);
check(ss.addTable(&ACS_TABLE_DETUMBLE_TRANS_0.second, ACS_TABLE_DETUMBLE_TRANS_0.first, false, check(ss.addTable(&ACS_TABLE_DETUMBLE_TRANS_0.second, ACS_TABLE_DETUMBLE_TRANS_0.first, false,
@ -275,7 +286,6 @@ void buildDetumbleSequence(Subsystem& ss, ModeListEntry& eh) {
// Build DETUMBLE sequence // Build DETUMBLE sequence
ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TGT.first, 0, true); ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TGT.first, 0, true);
ihs(ACS_SEQUENCE_DETUMBLE.second, SUS_BOARD_NML_TRANS.first, 0, false);
ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TRANS_0.first, 0, false); ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TRANS_0.first, 0, false);
ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TRANS_1.first, 0, false); ihs(ACS_SEQUENCE_DETUMBLE.second, ACS_TABLE_DETUMBLE_TRANS_1.first, 0, false);
check(ss.addSequence(&ACS_SEQUENCE_DETUMBLE.second, ACS_SEQUENCE_DETUMBLE.first, check(ss.addSequence(&ACS_SEQUENCE_DETUMBLE.second, ACS_SEQUENCE_DETUMBLE.first,
@ -288,10 +298,13 @@ void buildIdleSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -306,16 +319,14 @@ void buildIdleSequence(Subsystem& ss, ModeListEntry& eh) {
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_IDLE, ACS_TABLE_IDLE_TGT.second); iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_IDLE, ACS_TABLE_IDLE_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_IDLE_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_IDLE_TGT.second);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_IDLE_TGT.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_IDLE_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TGT.second, true);
ss.addTable(&ACS_TABLE_IDLE_TGT.second, ACS_TABLE_IDLE_TGT.first, false, true); ss.addTable(&ACS_TABLE_IDLE_TGT.second, ACS_TABLE_IDLE_TGT.first, false, true);
// SUS board transition table is built above
// Build IDLE transition 0 // Build IDLE transition 0
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TRANS_0.second); iht(objects::ACS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_IDLE_TRANS_0.second, true);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_IDLE_TRANS_0.second); iht(objects::SUS_BOARD_ASS, NML, duallane::A_SIDE, ACS_TABLE_IDLE_TRANS_0.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_IDLE_TRANS_0.second);
ss.addTable(&ACS_TABLE_IDLE_TRANS_0.second, ACS_TABLE_IDLE_TRANS_0.first, false, true); ss.addTable(&ACS_TABLE_IDLE_TRANS_0.second, ACS_TABLE_IDLE_TRANS_0.first, false, true);
@ -326,7 +337,6 @@ void buildIdleSequence(Subsystem& ss, ModeListEntry& eh) {
// Build IDLE sequence // Build IDLE sequence
ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TGT.first, 0, true); ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TGT.first, 0, true);
ihs(ACS_SEQUENCE_IDLE.second, SUS_BOARD_NML_TRANS.first, 0, true);
ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TRANS_0.first, 0, true); ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TRANS_0.first, 0, true);
ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TRANS_1.first, 0, true); ihs(ACS_SEQUENCE_IDLE.second, ACS_TABLE_IDLE_TRANS_1.first, 0, true);
ss.addSequence(&ACS_SEQUENCE_IDLE.second, ACS_SEQUENCE_IDLE.first, ACS_SEQUENCE_SAFE.first, false, ss.addSequence(&ACS_SEQUENCE_IDLE.second, ACS_SEQUENCE_IDLE.first, ACS_SEQUENCE_SAFE.first, false,
@ -338,10 +348,13 @@ void buildTargetPtSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -356,14 +369,13 @@ void buildTargetPtSequence(Subsystem& ss, ModeListEntry& eh) {
// Build TARGET PT table // Build TARGET PT table
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET, ACS_TABLE_PTG_TARGET_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_TGT.second);
check(ss.addTable(&ACS_TABLE_PTG_TARGET_TGT.second, ACS_TABLE_PTG_TARGET_TGT.first, false, true), check(ss.addTable(&ACS_TABLE_PTG_TARGET_TGT.second, ACS_TABLE_PTG_TARGET_TGT.first, false, true),
ctxc); ctxc);
// SUS board transition table is built above
// Transition 0 already built // Transition 0 already built
// Build TARGET PT transition 1 // Build TARGET PT transition 1
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET, ACS_TABLE_PTG_TARGET_TRANS_1.second); iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET, ACS_TABLE_PTG_TARGET_TRANS_1.second);
@ -373,7 +385,6 @@ void buildTargetPtSequence(Subsystem& ss, ModeListEntry& eh) {
// Build IDLE sequence // Build IDLE sequence
ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TARGET_TGT.first, 0, true); ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TARGET_TGT.first, 0, true);
ihs(ACS_SEQUENCE_PTG_TARGET.second, SUS_BOARD_NML_TRANS.first, 0, true);
ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TRANS_0.first, 0, true); ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TRANS_0.first, 0, true);
ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TARGET_TRANS_1.first, 0, true); ihs(ACS_SEQUENCE_PTG_TARGET.second, ACS_TABLE_PTG_TARGET_TRANS_1.first, 0, true);
check(ss.addSequence(&ACS_SEQUENCE_PTG_TARGET.second, ACS_SEQUENCE_PTG_TARGET.first, check(ss.addSequence(&ACS_SEQUENCE_PTG_TARGET.second, ACS_SEQUENCE_PTG_TARGET.first,
@ -386,10 +397,13 @@ void buildTargetPtNadirSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -405,8 +419,8 @@ void buildTargetPtNadirSequence(Subsystem& ss, ModeListEntry& eh) {
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET, iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET,
ACS_TABLE_PTG_TARGET_NADIR_TGT.second); ACS_TABLE_PTG_TARGET_NADIR_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_NADIR_TGT.second);
check(ss.addTable(TableEntry(ACS_TABLE_PTG_TARGET_NADIR_TGT.first, check(ss.addTable(TableEntry(ACS_TABLE_PTG_TARGET_NADIR_TGT.first,
@ -437,10 +451,13 @@ void buildTargetPtGsSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -456,8 +473,8 @@ void buildTargetPtGsSequence(Subsystem& ss, ModeListEntry& eh) {
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET_GS, iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_TARGET_GS,
ACS_TABLE_PTG_TARGET_GS_TGT.second); ACS_TABLE_PTG_TARGET_GS_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_GS_TGT.second);
check(ss.addTable( check(ss.addTable(
@ -487,10 +504,13 @@ void buildTargetPtInertialSequence(Subsystem& ss, ModeListEntry& eh) {
auto ctxc = context.c_str(); auto ctxc = context.c_str();
// Insert Helper Table // Insert Helper Table
auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode, auto iht = [&](object_id_t obj, Mode_t mode, Submode_t submode,
ArrayList<ModeListEntry>& sequence) { ArrayList<ModeListEntry>& sequence, bool allowAllSubmodes = false) {
eh.setObject(obj); eh.setObject(obj);
eh.setMode(mode); eh.setMode(mode);
eh.setSubmode(submode); eh.setSubmode(submode);
if (allowAllSubmodes) {
eh.allowAllSubmodes();
}
check(sequence.insert(eh), ctxc); check(sequence.insert(eh), ctxc);
}; };
// Insert Helper Sequence // Insert Helper Sequence
@ -506,8 +526,8 @@ void buildTargetPtInertialSequence(Subsystem& ss, ModeListEntry& eh) {
iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_INERTIAL, iht(objects::ACS_CONTROLLER, NML, acs::AcsMode::PTG_INERTIAL,
ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second);
iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); iht(objects::IMTQ_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second);
iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); iht(objects::SUS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second, true);
iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); iht(objects::ACS_BOARD_ASS, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second, true);
iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); iht(objects::RW_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second);
iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second); iht(objects::STR_ASSY, NML, 0, ACS_TABLE_PTG_TARGET_INERTIAL_TGT.second);
check(ss.addTable(TableEntry(ACS_TABLE_PTG_TARGET_INERTIAL_TGT.first, check(ss.addTable(TableEntry(ACS_TABLE_PTG_TARGET_INERTIAL_TGT.first,

View File

@ -28,35 +28,6 @@ PersistentTmStore::PersistentTmStore(object_id_t objectId, const char* baseDir,
} }
ReturnValue_t PersistentTmStore::assignAndOrCreateMostRecentFile() { ReturnValue_t PersistentTmStore::assignAndOrCreateMostRecentFile() {
using namespace std::filesystem;
for (auto const& file : directory_iterator(basePath)) {
if (file.is_directory()) {
continue;
}
auto pathStr = file.path().string();
if (pathStr.find(baseName) == std::string::npos) {
continue;
}
unsigned int underscorePos = pathStr.find_last_of('_');
std::string stampStr = pathStr.substr(underscorePos + 1);
struct tm time {};
if (nullptr == strptime(stampStr.c_str(), FILE_DATE_FORMAT, &time)) {
sif::error << "PersistentTmStore::assignOrCreateMostRecentFile: Error reading timestamp"
<< std::endl;
// Delete the file and re-create it.
activeFile = std::nullopt;
std::filesystem::remove(file.path());
break;
}
time_t fileEpoch = timegm(&time);
// There is still a file within the active time window, so re-use that file for new TMs to
// store.
if (fileEpoch + static_cast<time_t>(rolloverDiffSeconds) > currentTv.tv_sec) {
activeFileTv.tv_sec = fileEpoch;
activeFile = file.path();
break;
}
}
if (not activeFile.has_value()) { if (not activeFile.has_value()) {
return createMostRecentFile(std::nullopt); return createMostRecentFile(std::nullopt);
} }

@ -1 +1 @@
Subproject commit 93e93965e2c6405170b62c523dea1990db02d2ad Subproject commit 42907c36c58e7133d3d3cbefbf96c1a8e35b60b7

2
tmtc

@ -1 +1 @@
Subproject commit 9462a6e2459e11ac03c2bb9694772959ac228cd0 Subproject commit e74e751142e46c801852a110bef11510cc7c7bfa