Rework Lock Handling #419

Merged
meggert merged 8 commits from rework_lock_handling into develop 2023-03-03 09:13:34 +01:00
18 changed files with 92 additions and 65 deletions

View File

@ -21,6 +21,7 @@ will consitute of a breaking change warranting a new major release:
- Moved polling of all SPI parts to the same PST. - Moved polling of all SPI parts to the same PST.
- Allow quicker transition for the EIVE system component by allowing consecutive TCS and ACS - Allow quicker transition for the EIVE system component by allowing consecutive TCS and ACS
component commanding again. component commanding again.
- Changed a lot of lock guards to use timeouts
## Fixed ## Fixed

View File

@ -20,14 +20,14 @@
SdCardManager* SdCardManager::INSTANCE = nullptr; SdCardManager* SdCardManager::INSTANCE = nullptr;
SdCardManager::SdCardManager() : SystemObject(objects::SDC_MANAGER), cmdExecutor(256) { SdCardManager::SdCardManager() : SystemObject(objects::SDC_MANAGER), cmdExecutor(256) {
mutex = MutexFactory::instance()->createMutex(); sdLock = MutexFactory::instance()->createMutex();
ReturnValue_t result = mutex->lockMutex(); ReturnValue_t result = sdLock->lockMutex();
if (result != returnvalue::OK) { if (result != 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); result = scratch::readNumber(scratch::PREFERED_SDC_KEY, prefSdRaw);
if (mutex->unlockMutex() != returnvalue::OK) { if (sdLock->unlockMutex() != returnvalue::OK) {
sif::error << "SdCardManager::SdCardManager: Mutex unlock failed" << std::endl; sif::error << "SdCardManager::SdCardManager: Mutex unlock failed" << std::endl;
} }
@ -195,7 +195,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(mutex); MutexGuard mg(sdLock, LOCK_TYPE, 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 +378,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(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_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 +387,7 @@ std::optional<sd::SdCard> SdCardManager::getPreferredSdCard() const {
} }
ReturnValue_t SdCardManager::setPreferredSdCard(sd::SdCard sdCard) { ReturnValue_t SdCardManager::setPreferredSdCard(sd::SdCard sdCard) {
MutexGuard mg(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (sdCard == sd::SdCard::BOTH) { if (sdCard == sd::SdCard::BOTH) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
@ -399,7 +399,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(mutex); MutexGuard mg(sdLock, LOCK_TYPE, 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 +411,7 @@ ReturnValue_t SdCardManager::updateSdCardStateFile() {
} }
const char* SdCardManager::getCurrentMountPrefix() const { const char* SdCardManager::getCurrentMountPrefix() const {
MutexGuard mg(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (currentPrefix.has_value()) { if (currentPrefix.has_value()) {
return currentPrefix.value().c_str(); return currentPrefix.value().c_str();
} }
@ -464,7 +464,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(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (markedUnusable) { if (markedUnusable) {
return false; return false;
} }
@ -560,7 +560,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(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_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 +570,7 @@ void SdCardManager::setActiveSdCard(sd::SdCard sdCard) {
} }
std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const { std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const {
MutexGuard mg(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (markedUnusable) { if (markedUnusable) {
return std::nullopt; return std::nullopt;
} }
@ -578,6 +578,6 @@ std::optional<sd::SdCard> SdCardManager::getActiveSdCard() const {
} }
void SdCardManager::markUnusable() { void SdCardManager::markUnusable() {
MutexGuard mg(mutex); MutexGuard mg(sdLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
markedUnusable = true; markedUnusable = true;
} }

View File

@ -223,7 +223,10 @@ class SdCardManager : public SystemObject, public SdCardMountedIF {
bool sdCardActive = true; bool sdCardActive = true;
bool printCmdOutput = true; bool printCmdOutput = true;
bool markedUnusable = false; bool markedUnusable = false;
MutexIF* mutex = nullptr; MutexIF* sdLock = nullptr;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 40;
static constexpr char LOCK_CTX[] = "SdCardManager";
SdCardManager(); SdCardManager();

2
fsfw

@ -1 +1 @@
Subproject commit 511d07c0c78de7b1850e341dfcf8be7589f3c523 Subproject commit 245886c55500b9e70ba71eab68c46d44af9f6836

View File

@ -105,7 +105,7 @@ ReturnValue_t AcsBoardPolling::sendMessage(CookieIF* cookie, const uint8_t* send
return returnvalue::FAILED; return returnvalue::FAILED;
} }
auto* req = reinterpret_cast<const acs::Adis1650XRequest*>(sendData); auto* req = reinterpret_cast<const acs::Adis1650XRequest*>(sendData);
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (req->mode != adis.mode) { if (req->mode != adis.mode) {
if (req->mode == acs::SimpleSensorMode::NORMAL) { if (req->mode == acs::SimpleSensorMode::NORMAL) {
adis.type = req->type; adis.type = req->type;
@ -135,7 +135,7 @@ ReturnValue_t AcsBoardPolling::sendMessage(CookieIF* cookie, const uint8_t* send
return returnvalue::FAILED; return returnvalue::FAILED;
} }
auto* req = reinterpret_cast<const acs::GyroL3gRequest*>(sendData); auto* req = reinterpret_cast<const acs::GyroL3gRequest*>(sendData);
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (req->mode != gyro.mode) { if (req->mode != gyro.mode) {
if (req->mode == acs::SimpleSensorMode::NORMAL) { if (req->mode == acs::SimpleSensorMode::NORMAL) {
std::memcpy(gyro.sensorCfg, req->ctrlRegs, 5); std::memcpy(gyro.sensorCfg, req->ctrlRegs, 5);
@ -154,7 +154,7 @@ ReturnValue_t AcsBoardPolling::sendMessage(CookieIF* cookie, const uint8_t* send
return returnvalue::FAILED; return returnvalue::FAILED;
} }
auto* req = reinterpret_cast<const acs::MgmLis3Request*>(sendData); auto* req = reinterpret_cast<const acs::MgmLis3Request*>(sendData);
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (req->mode != mgm.mode) { if (req->mode != mgm.mode) {
if (req->mode == acs::SimpleSensorMode::NORMAL) { if (req->mode == acs::SimpleSensorMode::NORMAL) {
mgm.performStartup = true; mgm.performStartup = true;
@ -173,7 +173,7 @@ ReturnValue_t AcsBoardPolling::sendMessage(CookieIF* cookie, const uint8_t* send
return returnvalue::FAILED; return returnvalue::FAILED;
} }
auto* req = reinterpret_cast<const acs::MgmRm3100Request*>(sendData); auto* req = reinterpret_cast<const acs::MgmRm3100Request*>(sendData);
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (req->mode != mgm.mode) { if (req->mode != mgm.mode) {
if (req->mode == acs::SimpleSensorMode::NORMAL) { if (req->mode == acs::SimpleSensorMode::NORMAL) {
mgm.performStartup = true; mgm.performStartup = true;
@ -218,7 +218,7 @@ ReturnValue_t AcsBoardPolling::sendMessage(CookieIF* cookie, const uint8_t* send
break; break;
} }
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (state == InternalState::IDLE) { if (state == InternalState::IDLE) {
state = InternalState::BUSY; state = InternalState::BUSY;
semaphore->release(); semaphore->release();
@ -238,7 +238,7 @@ ReturnValue_t AcsBoardPolling::readReceivedMessage(CookieIF* cookie, uint8_t** b
if (spiCookie == nullptr) { if (spiCookie == nullptr) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
auto handleAdisReply = [&](GyroAdis& gyro) { auto handleAdisReply = [&](GyroAdis& gyro) {
std::memcpy(&gyro.readerReply, &gyro.ownReply, sizeof(acs::Adis1650XReply)); std::memcpy(&gyro.readerReply, &gyro.ownReply, sizeof(acs::Adis1650XReply));
*buffer = reinterpret_cast<uint8_t*>(&gyro.readerReply); *buffer = reinterpret_cast<uint8_t*>(&gyro.readerReply);
@ -297,7 +297,7 @@ void AcsBoardPolling::gyroL3gHandler(GyroL3g& l3g) {
acs::SimpleSensorMode mode; acs::SimpleSensorMode mode;
bool gyroPerformStartup; bool gyroPerformStartup;
{ {
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mode = l3g.mode; mode = l3g.mode;
gyroPerformStartup = l3g.performStartup; gyroPerformStartup = l3g.performStartup;
} }
@ -320,7 +320,7 @@ void AcsBoardPolling::gyroL3gHandler(GyroL3g& l3g) {
if (result != returnvalue::OK) { if (result != returnvalue::OK) {
l3g.replyResult = returnvalue::OK; l3g.replyResult = returnvalue::OK;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
// Cross check configuration as verification that communication is working // Cross check configuration as verification that communication is working
for (uint8_t idx = 0; idx < 5; idx++) { for (uint8_t idx = 0; idx < 5; idx++) {
if (rawReply[idx + 1] != l3g.sensorCfg[idx]) { if (rawReply[idx + 1] != l3g.sensorCfg[idx]) {
@ -345,7 +345,7 @@ void AcsBoardPolling::gyroL3gHandler(GyroL3g& l3g) {
l3g.replyResult = returnvalue::FAILED; l3g.replyResult = returnvalue::FAILED;
return; return;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
// The regular read function always returns the full sensor config as well. Use that // The regular read function always returns the full sensor config as well. Use that
// to verify communications. // to verify communications.
for (uint8_t idx = 0; idx < 5; idx++) { for (uint8_t idx = 0; idx < 5; idx++) {
@ -444,7 +444,7 @@ void AcsBoardPolling::gyroAdisHandler(GyroAdis& gyro) {
bool cdHasTimedOut = false; bool cdHasTimedOut = false;
bool mustPerformStartup = false; bool mustPerformStartup = false;
{ {
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mode = gyro.mode; mode = gyro.mode;
cdHasTimedOut = gyro.countdown.hasTimedOut(); cdHasTimedOut = gyro.countdown.hasTimedOut();
mustPerformStartup = gyro.performStartup; mustPerformStartup = gyro.performStartup;
@ -478,7 +478,7 @@ void AcsBoardPolling::gyroAdisHandler(GyroAdis& gyro) {
gyro.replyResult = returnvalue::FAILED; gyro.replyResult = returnvalue::FAILED;
return; return;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
gyro.ownReply.cfgWasSet = true; gyro.ownReply.cfgWasSet = true;
gyro.ownReply.cfg.diagStat = (rawReply[2] << 8) | rawReply[3]; gyro.ownReply.cfg.diagStat = (rawReply[2] << 8) | rawReply[3];
gyro.ownReply.cfg.filterSetting = (rawReply[4] << 8) | rawReply[5]; gyro.ownReply.cfg.filterSetting = (rawReply[4] << 8) | rawReply[5];
@ -525,7 +525,7 @@ void AcsBoardPolling::gyroAdisHandler(GyroAdis& gyro) {
return; return;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
gyro.ownReply.dataWasSet = true; gyro.ownReply.dataWasSet = true;
gyro.ownReply.cfg.diagStat = rawReply[2] << 8 | rawReply[3]; gyro.ownReply.cfg.diagStat = rawReply[2] << 8 | rawReply[3];
gyro.ownReply.data.angVelocities[0] = (rawReply[4] << 8) | rawReply[5]; gyro.ownReply.data.angVelocities[0] = (rawReply[4] << 8) | rawReply[5];
@ -545,7 +545,7 @@ void AcsBoardPolling::mgmLis3Handler(MgmLis3& mgm) {
acs::SimpleSensorMode mode; acs::SimpleSensorMode mode;
bool mustPerformStartup = false; bool mustPerformStartup = false;
{ {
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mode = mgm.mode; mode = mgm.mode;
mustPerformStartup = mgm.performStartup; mustPerformStartup = mgm.performStartup;
} }
@ -605,7 +605,7 @@ void AcsBoardPolling::mgmLis3Handler(MgmLis3& mgm) {
return; return;
} }
{ {
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mgm.ownReply.dataWasSet = true; mgm.ownReply.dataWasSet = true;
mgm.ownReply.sensitivity = mgmLis3::getSensitivityFactor(mgmLis3::getSensitivity(mgm.cfg[1])); mgm.ownReply.sensitivity = mgmLis3::getSensitivityFactor(mgmLis3::getSensitivity(mgm.cfg[1]));
mgm.ownReply.mgmValuesRaw[0] = mgm.ownReply.mgmValuesRaw[0] =
@ -627,7 +627,7 @@ void AcsBoardPolling::mgmLis3Handler(MgmLis3& mgm) {
mgm.replyResult = result; mgm.replyResult = result;
return; return;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mgm.ownReply.temperatureWasSet = true; mgm.ownReply.temperatureWasSet = true;
mgm.ownReply.temperatureRaw = (rawReply[2] << 8) | rawReply[1]; mgm.ownReply.temperatureRaw = (rawReply[2] << 8) | rawReply[1];
} }
@ -638,7 +638,7 @@ void AcsBoardPolling::mgmRm3100Handler(MgmRm3100& mgm) {
acs::SimpleSensorMode mode; acs::SimpleSensorMode mode;
bool mustPerformStartup = false; bool mustPerformStartup = false;
{ {
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
mode = mgm.mode; mode = mgm.mode;
mustPerformStartup = mgm.performStartup; mustPerformStartup = mgm.performStartup;
} }
@ -712,7 +712,7 @@ void AcsBoardPolling::mgmRm3100Handler(MgmRm3100& mgm) {
mgm.replyResult = result; mgm.replyResult = result;
return; return;
} }
MutexGuard mg(ipcLock); MutexGuard mg(ipcLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
for (uint8_t idx = 0; idx < 3; idx++) { for (uint8_t idx = 0; idx < 3; idx++) {
// Hardcoded, but note that the gain depends on the cycle count // Hardcoded, but note that the gain depends on the cycle count
// value which is configurable! // value which is configurable!

View File

@ -22,6 +22,9 @@ class AcsBoardPolling : public SystemObject,
private: private:
enum class InternalState { IDLE, BUSY } state = InternalState::IDLE; enum class InternalState { IDLE, BUSY } state = InternalState::IDLE;
MutexIF* ipcLock; MutexIF* ipcLock;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "AcsBoardPolling";
SemaphoreIF* semaphore; SemaphoreIF* semaphore;
std::array<uint8_t, 32> cmdBuf; std::array<uint8_t, 32> cmdBuf;

View File

@ -19,7 +19,7 @@ static constexpr uint8_t BASE_CFG =
Max31865RtdPolling::Max31865RtdPolling(object_id_t objectId, SpiComIF* lowLevelComIF, Max31865RtdPolling::Max31865RtdPolling(object_id_t objectId, SpiComIF* lowLevelComIF,
GpioIF* gpioIF) GpioIF* gpioIF)
: SystemObject(objectId), rtds(EiveMax31855::NUM_RTDS), comIF(lowLevelComIF), gpioIF(gpioIF) { : SystemObject(objectId), rtds(EiveMax31855::NUM_RTDS), comIF(lowLevelComIF), gpioIF(gpioIF) {
readerMutex = MutexFactory::instance()->createMutex(); readerLock = MutexFactory::instance()->createMutex();
} }
ReturnValue_t Max31865RtdPolling::performOperation(uint8_t operationCode) { ReturnValue_t Max31865RtdPolling::performOperation(uint8_t operationCode) {
@ -63,7 +63,7 @@ bool Max31865RtdPolling::periodicInitHandling() {
if (rtd == nullptr) { if (rtd == nullptr) {
continue; continue;
} }
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
sif::warning << "Max31865RtdReader::periodicInitHandling: Mutex lock failed" << std::endl; sif::warning << "Max31865RtdReader::periodicInitHandling: Mutex lock failed" << std::endl;
return false; return false;
@ -119,7 +119,7 @@ ReturnValue_t Max31865RtdPolling::periodicReadReqHandling() {
if (rtd == nullptr) { if (rtd == nullptr) {
continue; continue;
} }
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
sif::warning << "Max31865RtdReader::periodicReadReqHandling: Mutex lock failed" << std::endl; sif::warning << "Max31865RtdReader::periodicReadReqHandling: Mutex lock failed" << std::endl;
return returnvalue::FAILED; return returnvalue::FAILED;
@ -144,7 +144,7 @@ ReturnValue_t Max31865RtdPolling::periodicReadHandling() {
if (rtd == nullptr) { if (rtd == nullptr) {
continue; continue;
} }
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
sif::warning << "Max31865RtdReader::periodicReadHandling: Mutex lock failed" << std::endl; sif::warning << "Max31865RtdReader::periodicReadHandling: Mutex lock failed" << std::endl;
return returnvalue::FAILED; return returnvalue::FAILED;
@ -200,7 +200,7 @@ ReturnValue_t Max31865RtdPolling::initializeInterface(CookieIF* cookie) {
throw std::invalid_argument("Invalid RTD index"); throw std::invalid_argument("Invalid RTD index");
} }
rtds[rtdCookie->idx] = rtdCookie; rtds[rtdCookie->idx] = rtdCookie;
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (dbLen == 0) { if (dbLen == 0) {
dbLen = rtdCookie->db.getSerializedSize(); dbLen = rtdCookie->db.getSerializedSize();
} }
@ -216,7 +216,7 @@ ReturnValue_t Max31865RtdPolling::sendMessage(CookieIF* cookie, const uint8_t* s
if (sendLen < 1) { if (sendLen < 1) {
return returnvalue::OK; return returnvalue::OK;
} }
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
sif::warning << "Max31865RtdReader::sendMessage: Mutex lock failed" << std::endl; sif::warning << "Max31865RtdReader::sendMessage: Mutex lock failed" << std::endl;
return returnvalue::FAILED; return returnvalue::FAILED;
@ -312,7 +312,7 @@ ReturnValue_t Max31865RtdPolling::requestReceiveMessage(CookieIF* cookie, size_t
ReturnValue_t Max31865RtdPolling::readReceivedMessage(CookieIF* cookie, uint8_t** buffer, ReturnValue_t Max31865RtdPolling::readReceivedMessage(CookieIF* cookie, uint8_t** buffer,
size_t* size) { size_t* size) {
MutexGuard mg(readerMutex); MutexGuard mg(readerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
// TODO: Emit warning // TODO: Emit warning
return returnvalue::FAILED; return returnvalue::FAILED;

View File

@ -48,7 +48,10 @@ class Max31865RtdPolling : public SystemObject,
std::vector<Max31865ReaderCookie*> rtds; std::vector<Max31865ReaderCookie*> rtds;
std::array<uint8_t, 4> cmdBuf = {}; std::array<uint8_t, 4> cmdBuf = {};
size_t dbLen = 0; size_t dbLen = 0;
MutexIF* readerMutex; MutexIF* readerLock;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "Max31865RtdPolling";
SpiComIF* comIF; SpiComIF* comIF;
GpioIF* gpioIF; GpioIF* gpioIF;

View File

@ -9,12 +9,12 @@ MutexIF* DATARATE_LOCK = nullptr;
MutexIF* lazyLock(); MutexIF* lazyLock();
com::Datarate com::getCurrentDatarate() { com::Datarate com::getCurrentDatarate() {
MutexGuard mg(lazyLock()); MutexGuard mg(lazyLock(), MutexIF::TimeoutType::WAITING, 20, "com");
return DATARATE_CFG_RAW; return DATARATE_CFG_RAW;
} }
void com::setCurrentDatarate(com::Datarate newRate) { void com::setCurrentDatarate(com::Datarate newRate) {
MutexGuard mg(lazyLock()); MutexGuard mg(lazyLock(), MutexIF::TimeoutType::WAITING, 20, "com");
DATARATE_CFG_RAW = newRate; DATARATE_CFG_RAW = newRate;
} }

View File

@ -9,6 +9,9 @@ namespace torquer {
// Additional buffer time to accont for time until I2C command arrives and ramp up / ramp down // Additional buffer time to accont for time until I2C command arrives and ramp up / ramp down
// time of the MGT // time of the MGT
static constexpr dur_millis_t TORQUE_BUFFER_TIME_MS = 20; static constexpr dur_millis_t TORQUE_BUFFER_TIME_MS = 20;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "torquer";
MutexIF* lazyLock(); MutexIF* lazyLock();
extern bool TORQUEING; extern bool TORQUEING;

View File

@ -432,7 +432,8 @@ ReturnValue_t AcsController::commandActuators(int16_t xDipole, int16_t yDipole,
uint16_t rampTime) { uint16_t rampTime) {
{ {
PoolReadGuard pg(&dipoleSet); PoolReadGuard pg(&dipoleSet);
MutexGuard mg(torquer::lazyLock()); MutexGuard mg(torquer::lazyLock(), torquer::LOCK_TYPE, torquer::LOCK_TIMEOUT,
torquer::LOCK_CTX);
torquer::NEW_ACTUATION_FLAG = true; torquer::NEW_ACTUATION_FLAG = true;
dipoleSet.setDipoles(xDipole, yDipole, zDipole, dipoleTorqueDuration); dipoleSet.setDipoles(xDipole, yDipole, zDipole, dipoleTorqueDuration);
} }

View File

@ -30,8 +30,8 @@ HeaterHandler::HeaterHandler(object_id_t setObjectId_, GpioIF* gpioInterface_, H
if (mainLineSwitcher == nullptr) { if (mainLineSwitcher == nullptr) {
throw std::invalid_argument("HeaterHandler::HeaterHandler: Invalid PowerSwitchIF"); throw std::invalid_argument("HeaterHandler::HeaterHandler: Invalid PowerSwitchIF");
} }
heaterHealthAndStateMutex = MutexFactory::instance()->createMutex(); handlerLock = MutexFactory::instance()->createMutex();
if (heaterHealthAndStateMutex == nullptr) { if (handlerLock == nullptr) {
throw std::runtime_error("HeaterHandler::HeaterHandler: Creating Mutex failed"); throw std::runtime_error("HeaterHandler::HeaterHandler: Creating Mutex failed");
} }
auto mqArgs = MqArgs(setObjectId_, static_cast<void*>(this)); auto mqArgs = MqArgs(setObjectId_, static_cast<void*>(this));
@ -144,7 +144,7 @@ ReturnValue_t HeaterHandler::executeAction(ActionId_t actionId, MessageQueueId_t
if (action == SwitchAction::SET_SWITCH_ON) { if (action == SwitchAction::SET_SWITCH_ON) {
HasHealthIF::HealthState health; HasHealthIF::HealthState health;
{ {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
health = heater.healthDevice->getHealth(); health = heater.healthDevice->getHealth();
} }
if (health == HasHealthIF::FAULTY or health == HasHealthIF::PERMANENT_FAULTY or if (health == HasHealthIF::FAULTY or health == HasHealthIF::PERMANENT_FAULTY or
@ -270,7 +270,7 @@ void HeaterHandler::handleSwitchOnCommand(heater::Switchers heaterIdx) {
} else { } else {
triggerEvent(HEATER_WENT_ON, heaterIdx, 0); triggerEvent(HEATER_WENT_ON, heaterIdx, 0);
{ {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
heater.switchState = ON; heater.switchState = ON;
} }
} }
@ -320,7 +320,7 @@ void HeaterHandler::handleSwitchOffCommand(heater::Switchers heaterIdx) {
triggerEvent(GPIO_PULL_LOW_FAILED, result); triggerEvent(GPIO_PULL_LOW_FAILED, result);
} else { } else {
{ {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
heater.switchState = OFF; heater.switchState = OFF;
} }
triggerEvent(HEATER_WENT_OFF, heaterIdx, 0); triggerEvent(HEATER_WENT_OFF, heaterIdx, 0);
@ -346,7 +346,7 @@ void HeaterHandler::handleSwitchOffCommand(heater::Switchers heaterIdx) {
} }
HeaterHandler::SwitchState HeaterHandler::checkSwitchState(heater::Switchers switchNr) const { HeaterHandler::SwitchState HeaterHandler::checkSwitchState(heater::Switchers switchNr) const {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
return heaterVec.at(switchNr).switchState; return heaterVec.at(switchNr).switchState;
} }
@ -396,7 +396,7 @@ object_id_t HeaterHandler::getObjectId() const { return SystemObject::getObjectI
ReturnValue_t HeaterHandler::getAllSwitchStates(std::array<SwitchState, 8>& statesBuf) { ReturnValue_t HeaterHandler::getAllSwitchStates(std::array<SwitchState, 8>& statesBuf) {
{ {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (mg.getLockResult() != returnvalue::OK) { if (mg.getLockResult() != returnvalue::OK) {
return returnvalue::FAILED; return returnvalue::FAILED;
} }
@ -409,7 +409,7 @@ ReturnValue_t HeaterHandler::getAllSwitchStates(std::array<SwitchState, 8>& stat
bool HeaterHandler::allSwitchesOff() { bool HeaterHandler::allSwitchesOff() {
bool allSwitchesOrd = false; bool allSwitchesOrd = false;
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
/* Or all switches. As soon one switch is on, allSwitchesOrd will be true */ /* Or all switches. As soon one switch is on, allSwitchesOrd will be true */
for (power::Switch_t switchNr = 0; switchNr < heater::NUMBER_OF_SWITCHES; switchNr++) { for (power::Switch_t switchNr = 0; switchNr < heater::NUMBER_OF_SWITCHES; switchNr++) {
allSwitchesOrd = allSwitchesOrd || heaterVec.at(switchNr).switchState; allSwitchesOrd = allSwitchesOrd || heaterVec.at(switchNr).switchState;
@ -442,7 +442,7 @@ uint32_t HeaterHandler::getSwitchDelayMs(void) const { return 2000; }
HasHealthIF::HealthState HeaterHandler::getHealth(heater::Switchers heater) { HasHealthIF::HealthState HeaterHandler::getHealth(heater::Switchers heater) {
auto* healthDev = heaterVec.at(heater).healthDevice; auto* healthDev = heaterVec.at(heater).healthDevice;
if (healthDev != nullptr) { if (healthDev != nullptr) {
MutexGuard mg(heaterHealthAndStateMutex); MutexGuard mg(handlerLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
return healthDev->getHealth(); return healthDev->getHealth();
} }
return HasHealthIF::HealthState::FAULTY; return HasHealthIF::HealthState::FAULTY;

View File

@ -136,7 +136,10 @@ class HeaterHandler : public ExecutableObjectIF,
HeaterMap heaterVec = {}; HeaterMap heaterVec = {};
MutexIF* heaterHealthAndStateMutex = nullptr; MutexIF* handlerLock = nullptr;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "HeaterHandler";
HeaterHelper helper; HeaterHelper helper;
ModeHelper modeHelper; ModeHelper modeHelper;

View File

@ -214,7 +214,8 @@ ReturnValue_t ImtqHandler::buildCommandFromCommand(DeviceCommandId_t deviceComma
<< ", y = " << dipoleSet.yDipole.value << ", z = " << dipoleSet.zDipole.value << ", y = " << dipoleSet.yDipole.value << ", z = " << dipoleSet.zDipole.value
<< ", duration = " << dipoleSet.currentTorqueDurationMs.value << std::endl; << ", duration = " << dipoleSet.currentTorqueDurationMs.value << std::endl;
} }
MutexGuard mg(torquer::lazyLock()); MutexGuard mg(torquer::lazyLock(), torquer::LOCK_TYPE, torquer::LOCK_TIMEOUT,
torquer::LOCK_CTX);
torquer::TORQUEING = true; torquer::TORQUEING = true;
torquer::TORQUE_COUNTDOWN.setTimeout(dipoleSet.currentTorqueDurationMs.value); torquer::TORQUE_COUNTDOWN.setTimeout(dipoleSet.currentTorqueDurationMs.value);
rawPacket = commandBuffer; rawPacket = commandBuffer;

View File

@ -18,7 +18,7 @@ PCDUHandler::PCDUHandler(object_id_t setObjectId, size_t cmdQueueSize)
auto mqArgs = MqArgs(setObjectId, static_cast<void*>(this)); auto mqArgs = MqArgs(setObjectId, static_cast<void*>(this));
commandQueue = QueueFactory::instance()->createMessageQueue( commandQueue = QueueFactory::instance()->createMessageQueue(
cmdQueueSize, MessageQueueMessage::MAX_MESSAGE_SIZE, &mqArgs); cmdQueueSize, MessageQueueMessage::MAX_MESSAGE_SIZE, &mqArgs);
pwrMutex = MutexFactory::instance()->createMutex(); pwrLock = MutexFactory::instance()->createMutex();
} }
PCDUHandler::~PCDUHandler() {} PCDUHandler::~PCDUHandler() {}
@ -41,7 +41,7 @@ ReturnValue_t PCDUHandler::performOperation(uint8_t counter) {
if (pg.getReadResult() == returnvalue::OK) { if (pg.getReadResult() == returnvalue::OK) {
if (switcherSet.p60Dock5VStack.value != switchState) { if (switcherSet.p60Dock5VStack.value != switchState) {
triggerEvent(power::SWITCH_HAS_CHANGED, switchState, pcdu::Switches::P60_DOCK_5V_STACK); triggerEvent(power::SWITCH_HAS_CHANGED, switchState, pcdu::Switches::P60_DOCK_5V_STACK);
MutexGuard mg(pwrMutex); MutexGuard mg(pwrLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
switchStates[pcdu::P60_DOCK_5V_STACK] = switchState; switchStates[pcdu::P60_DOCK_5V_STACK] = switchState;
} }
switcherSet.p60Dock5VStack.setValid(true); switcherSet.p60Dock5VStack.setValid(true);
@ -179,7 +179,7 @@ void PCDUHandler::updatePdu2SwitchStates() {
switcherSet.pdu2Switches[idx] = pdu2CoreHk.outputEnables[idx]; switcherSet.pdu2Switches[idx] = pdu2CoreHk.outputEnables[idx];
} }
switcherSet.pdu2Switches.setValid(true); switcherSet.pdu2Switches.setValid(true);
MutexGuard mg(pwrMutex); MutexGuard mg(pwrLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
checkAndUpdatePduSwitch(pdu, Switches::PDU2_CH0_Q7S, pdu2CoreHk.outputEnables[Channels::Q7S]); checkAndUpdatePduSwitch(pdu, Switches::PDU2_CH0_Q7S, pdu2CoreHk.outputEnables[Channels::Q7S]);
checkAndUpdatePduSwitch(pdu, Switches::PDU2_CH1_PL_PCDU_BATT_0_14V8, checkAndUpdatePduSwitch(pdu, Switches::PDU2_CH1_PL_PCDU_BATT_0_14V8,
@ -216,7 +216,7 @@ void PCDUHandler::updatePdu1SwitchStates() {
switcherSet.pdu1Switches[idx] = pdu1CoreHk.outputEnables[idx]; switcherSet.pdu1Switches[idx] = pdu1CoreHk.outputEnables[idx];
} }
switcherSet.pdu1Switches.setValid(true); switcherSet.pdu1Switches.setValid(true);
MutexGuard mg(pwrMutex); MutexGuard mg(pwrLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
checkAndUpdatePduSwitch(pdu, Switches::PDU1_CH0_TCS_BOARD_3V3, checkAndUpdatePduSwitch(pdu, Switches::PDU1_CH0_TCS_BOARD_3V3,
pdu1CoreHk.outputEnables[Channels::TCS_BOARD_3V3]); pdu1CoreHk.outputEnables[Channels::TCS_BOARD_3V3]);
checkAndUpdatePduSwitch(pdu, Switches::PDU1_CH1_SYRLINKS_12V, checkAndUpdatePduSwitch(pdu, Switches::PDU1_CH1_SYRLINKS_12V,
@ -402,9 +402,11 @@ ReturnValue_t PCDUHandler::getSwitchState(uint8_t switchNr) const {
sif::debug << "PCDUHandler::getSwitchState: Invalid switch number" << std::endl; sif::debug << "PCDUHandler::getSwitchState: Invalid switch number" << std::endl;
return returnvalue::FAILED; return returnvalue::FAILED;
} }
pwrMutex->lockMutex(); uint8_t currentState = 0;
uint8_t currentState = switchStates[switchNr]; {
pwrMutex->unlockMutex(); MutexGuard mg(pwrLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
currentState = switchStates[switchNr];
}
if (currentState == 1) { if (currentState == 1) {
return PowerSwitchIF::SWITCH_ON; return PowerSwitchIF::SWITCH_ON;
} else { } else {

View File

@ -51,7 +51,10 @@ class PCDUHandler : public PowerSwitchIF,
private: private:
uint32_t pstIntervalMs = 0; uint32_t pstIntervalMs = 0;
MutexIF* pwrMutex = nullptr; MutexIF* pwrLock = nullptr;
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
static constexpr char LOCK_CTX[] = "PcduHandler";
/** Housekeeping manager. Handles updates of local pool variables. */ /** Housekeeping manager. Handles updates of local pool variables. */
LocalDataPoolManager poolManager; LocalDataPoolManager poolManager;

View File

@ -5,7 +5,7 @@ Stack5VHandler::Stack5VHandler(PowerSwitchIF& switcher) : switcher(switcher) {
} }
ReturnValue_t Stack5VHandler::deviceToOn(StackCommander commander, bool updateStates) { ReturnValue_t Stack5VHandler::deviceToOn(StackCommander commander, bool updateStates) {
MutexGuard mg(stackLock); MutexGuard mg(stackLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (updateStates) { if (updateStates) {
updateInternalStates(); updateInternalStates();
} }
@ -27,7 +27,7 @@ ReturnValue_t Stack5VHandler::deviceToOn(StackCommander commander, bool updateSt
} }
ReturnValue_t Stack5VHandler::deviceToOff(StackCommander commander, bool updateStates) { ReturnValue_t Stack5VHandler::deviceToOff(StackCommander commander, bool updateStates) {
MutexGuard mg(stackLock); MutexGuard mg(stackLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
if (updateStates) { if (updateStates) {
updateInternalStates(); updateInternalStates();
} }
@ -55,12 +55,12 @@ ReturnValue_t Stack5VHandler::deviceToOff(StackCommander commander, bool updateS
} }
bool Stack5VHandler::isSwitchOn() { bool Stack5VHandler::isSwitchOn() {
MutexGuard mg(stackLock); MutexGuard mg(stackLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
return updateInternalStates(); return updateInternalStates();
} }
void Stack5VHandler::update() { void Stack5VHandler::update() {
MutexGuard mg(stackLock); MutexGuard mg(stackLock, LOCK_TYPE, LOCK_TIMEOUT, LOCK_CTX);
updateInternalStates(); updateInternalStates();
} }

View File

@ -21,7 +21,11 @@ class Stack5VHandler {
void update(); void update();
private: private:
static constexpr MutexIF::TimeoutType LOCK_TYPE = MutexIF::TimeoutType::WAITING;
static constexpr uint32_t LOCK_TIMEOUT = 20;
MutexIF* stackLock; MutexIF* stackLock;
static constexpr char LOCK_CTX[] = "Stack5VHandler";
PowerSwitchIF& switcher; PowerSwitchIF& switcher;
bool switchIsOn = false; bool switchIsOn = false;
bool targetState = false; bool targetState = false;