Merge branch 'mueller/master' into mueller/project/distribDatapool
This commit is contained in:
commit
4afb19be51
@ -3,40 +3,57 @@
|
||||
#include <framework/ipc/MutexHelper.h>
|
||||
|
||||
SharedRingBuffer::SharedRingBuffer(object_id_t objectId, const size_t size,
|
||||
bool overwriteOld, dur_millis_t mutexTimeout):
|
||||
SystemObject(objectId), SimpleRingBuffer(size, overwriteOld),
|
||||
mutexTimeout(mutexTimeout) {
|
||||
bool overwriteOld, size_t maxExcessBytes, dur_millis_t mutexTimeout):
|
||||
SystemObject(objectId), SimpleRingBuffer(size, overwriteOld,
|
||||
maxExcessBytes), mutexTimeout(mutexTimeout) {
|
||||
mutex = MutexFactory::instance()->createMutex();
|
||||
}
|
||||
|
||||
SharedRingBuffer::SharedRingBuffer(object_id_t objectId, uint8_t *buffer,
|
||||
const size_t size, bool overwriteOld, dur_millis_t mutexTimeout):
|
||||
SystemObject(objectId), SimpleRingBuffer(buffer, size, overwriteOld),
|
||||
mutexTimeout(mutexTimeout) {
|
||||
const size_t size, bool overwriteOld, size_t maxExcessBytes,
|
||||
dur_millis_t mutexTimeout):
|
||||
SystemObject(objectId), SimpleRingBuffer(buffer, size, overwriteOld,
|
||||
maxExcessBytes), mutexTimeout(mutexTimeout) {
|
||||
mutex = MutexFactory::instance()->createMutex();
|
||||
}
|
||||
|
||||
ReturnValue_t SharedRingBuffer::getFreeElementProtected(uint8_t** writePtr,
|
||||
size_t amount) {
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::getFreeElement(writePtr,amount);
|
||||
}
|
||||
|
||||
ReturnValue_t SharedRingBuffer::writeDataProtected(const uint8_t *data,
|
||||
size_t amount) {
|
||||
MutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::writeData(data,amount);
|
||||
}
|
||||
|
||||
ReturnValue_t SharedRingBuffer::readDataProtected(uint8_t *data, size_t amount,
|
||||
bool incrementReadPtr, bool readRemaining,
|
||||
size_t *trueAmount) {
|
||||
MutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::readData(data,amount, incrementReadPtr,
|
||||
readRemaining, trueAmount);
|
||||
}
|
||||
|
||||
ReturnValue_t SharedRingBuffer::deleteDataProtected(size_t amount,
|
||||
bool deleteRemaining, size_t *trueAmount) {
|
||||
MutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::deleteData(amount, deleteRemaining, trueAmount);
|
||||
}
|
||||
|
||||
size_t SharedRingBuffer::getExcessBytes() const {
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::getExcessBytes();
|
||||
}
|
||||
|
||||
void SharedRingBuffer::moveExcessBytesToStart() {
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return SimpleRingBuffer::moveExcessBytesToStart();
|
||||
}
|
||||
|
||||
size_t SharedRingBuffer::getAvailableReadDataProtected(uint8_t n) const {
|
||||
MutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper(mutex, MutexIF::TimeoutType::WAITING, mutexTimeout);
|
||||
return ((write + size) - read[n]) % size;
|
||||
}
|
||||
|
@ -17,7 +17,8 @@ public:
|
||||
* will be overwritten.
|
||||
*/
|
||||
SharedRingBuffer(object_id_t objectId, const size_t size,
|
||||
bool overwriteOld, dur_millis_t mutexTimeout = 10);
|
||||
bool overwriteOld, size_t maxExcessBytes,
|
||||
dur_millis_t mutexTimeout = 10);
|
||||
|
||||
/**
|
||||
* This constructor takes an external buffer with the specified size.
|
||||
@ -28,10 +29,22 @@ public:
|
||||
* will be overwritten.
|
||||
*/
|
||||
SharedRingBuffer(object_id_t objectId, uint8_t* buffer, const size_t size,
|
||||
bool overwriteOld, dur_millis_t mutexTimeout = 10);
|
||||
bool overwriteOld, size_t maxExcessBytes,
|
||||
dur_millis_t mutexTimeout = 10);
|
||||
|
||||
void setMutexTimeout(dur_millis_t newTimeout);
|
||||
|
||||
virtual size_t getExcessBytes() const override;
|
||||
/**
|
||||
* Helper functions which moves any excess bytes to the start
|
||||
* of the ring buffer.
|
||||
* @return
|
||||
*/
|
||||
virtual void moveExcessBytesToStart() override;
|
||||
|
||||
/** Performs mutex protected SimpleRingBuffer::getFreeElement call */
|
||||
ReturnValue_t getFreeElementProtected(uint8_t** writePtr, size_t amount);
|
||||
|
||||
/** Performs mutex protected SimpleRingBuffer::writeData call */
|
||||
ReturnValue_t writeDataProtected(const uint8_t* data, size_t amount);
|
||||
|
||||
|
@ -1,20 +1,55 @@
|
||||
#include <framework/container/SimpleRingBuffer.h>
|
||||
#include <cstring>
|
||||
|
||||
SimpleRingBuffer::SimpleRingBuffer(const size_t size, bool overwriteOld) :
|
||||
RingBufferBase<>(0, size, overwriteOld) {
|
||||
buffer = new uint8_t[size];
|
||||
SimpleRingBuffer::SimpleRingBuffer(const size_t size, bool overwriteOld,
|
||||
size_t maxExcessBytes) :
|
||||
RingBufferBase<>(0, size, overwriteOld),
|
||||
maxExcessBytes(maxExcessBytes) {
|
||||
if(maxExcessBytes > size) {
|
||||
this->maxExcessBytes = size;
|
||||
}
|
||||
else {
|
||||
this->maxExcessBytes = maxExcessBytes;
|
||||
}
|
||||
buffer = new uint8_t[size + maxExcessBytes];
|
||||
}
|
||||
|
||||
SimpleRingBuffer::SimpleRingBuffer(uint8_t *buffer, const size_t size,
|
||||
bool overwriteOld):
|
||||
RingBufferBase<>(0, size, overwriteOld), buffer(buffer) {}
|
||||
bool overwriteOld, size_t maxExcessBytes):
|
||||
RingBufferBase<>(0, size, overwriteOld), buffer(buffer) {
|
||||
if(maxExcessBytes > size) {
|
||||
this->maxExcessBytes = size;
|
||||
}
|
||||
else {
|
||||
this->maxExcessBytes = maxExcessBytes;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
SimpleRingBuffer::~SimpleRingBuffer() {
|
||||
delete[] buffer;
|
||||
}
|
||||
|
||||
|
||||
ReturnValue_t SimpleRingBuffer::getFreeElement(uint8_t **writePointer,
|
||||
size_t amount) {
|
||||
if (availableWriteSpace() >= amount or overwriteOld) {
|
||||
size_t amountTillWrap = writeTillWrap();
|
||||
if (amountTillWrap < amount) {
|
||||
if((amount - amountTillWrap + excessBytes) > maxExcessBytes) {
|
||||
return HasReturnvaluesIF::RETURN_FAILED;
|
||||
}
|
||||
excessBytes = amount - amountTillWrap;
|
||||
}
|
||||
*writePointer = &buffer[write];
|
||||
incrementWrite(amount);
|
||||
return HasReturnvaluesIF::RETURN_OK;
|
||||
}
|
||||
else {
|
||||
return HasReturnvaluesIF::RETURN_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
ReturnValue_t SimpleRingBuffer::writeData(const uint8_t* data,
|
||||
size_t amount) {
|
||||
if (availableWriteSpace() >= amount or overwriteOld) {
|
||||
@ -62,6 +97,17 @@ ReturnValue_t SimpleRingBuffer::readData(uint8_t* data, size_t amount,
|
||||
return HasReturnvaluesIF::RETURN_OK;
|
||||
}
|
||||
|
||||
size_t SimpleRingBuffer::getExcessBytes() const {
|
||||
return excessBytes;
|
||||
}
|
||||
|
||||
void SimpleRingBuffer::moveExcessBytesToStart() {
|
||||
if(excessBytes > 0) {
|
||||
std::memcpy(buffer, &buffer[size], excessBytes);
|
||||
excessBytes = 0;
|
||||
}
|
||||
}
|
||||
|
||||
ReturnValue_t SimpleRingBuffer::deleteData(size_t amount,
|
||||
bool deleteRemaining, size_t* trueAmount) {
|
||||
size_t availableData = availableReadData(READ_PTR);
|
||||
|
@ -16,12 +16,17 @@ class SimpleRingBuffer: public RingBufferBase<> {
|
||||
public:
|
||||
/**
|
||||
* This constructor allocates a new internal buffer with the supplied size.
|
||||
*
|
||||
* @param size
|
||||
* @param overwriteOld
|
||||
* If the ring buffer is overflowing at a write operartion, the oldest data
|
||||
* will be overwritten.
|
||||
* @param overwriteOld If the ring buffer is overflowing at a write
|
||||
* operation, the oldest data will be overwritten.
|
||||
* @param maxExcessBytes These additional bytes will be allocated in addtion
|
||||
* to the specified size to accomodate contiguous write operations
|
||||
* with getFreeElement.
|
||||
*
|
||||
*/
|
||||
SimpleRingBuffer(const size_t size, bool overwriteOld);
|
||||
SimpleRingBuffer(const size_t size, bool overwriteOld,
|
||||
size_t maxExcessBytes = 0);
|
||||
/**
|
||||
* This constructor takes an external buffer with the specified size.
|
||||
* @param buffer
|
||||
@ -29,8 +34,13 @@ public:
|
||||
* @param overwriteOld
|
||||
* If the ring buffer is overflowing at a write operartion, the oldest data
|
||||
* will be overwritten.
|
||||
* @param maxExcessBytes
|
||||
* If the buffer can accomodate additional bytes for contigous write
|
||||
* operations with getFreeElement, this is the maximum allowed additional
|
||||
* size
|
||||
*/
|
||||
SimpleRingBuffer(uint8_t* buffer, const size_t size, bool overwriteOld);
|
||||
SimpleRingBuffer(uint8_t* buffer, const size_t size, bool overwriteOld,
|
||||
size_t maxExcessBytes = 0);
|
||||
|
||||
virtual ~SimpleRingBuffer();
|
||||
|
||||
@ -43,6 +53,25 @@ public:
|
||||
*/
|
||||
ReturnValue_t writeData(const uint8_t* data, size_t amount);
|
||||
|
||||
/**
|
||||
* Returns a pointer to a free element. If the remaining buffer is
|
||||
* not large enough, the data will be written past the actual size
|
||||
* and the amount of excess bytes will be cached.
|
||||
* @param writePointer Pointer to a pointer which can be used to write
|
||||
* contiguous blocks into the ring buffer
|
||||
* @param amount
|
||||
* @return
|
||||
*/
|
||||
ReturnValue_t getFreeElement(uint8_t** writePointer, size_t amount);
|
||||
|
||||
virtual size_t getExcessBytes() const;
|
||||
/**
|
||||
* Helper functions which moves any excess bytes to the start
|
||||
* of the ring buffer.
|
||||
* @return
|
||||
*/
|
||||
virtual void moveExcessBytesToStart();
|
||||
|
||||
/**
|
||||
* Read from circular buffer at read pointer.
|
||||
* @param data
|
||||
@ -82,6 +111,8 @@ public:
|
||||
private:
|
||||
static const uint8_t READ_PTR = 0;
|
||||
uint8_t* buffer = nullptr;
|
||||
size_t maxExcessBytes;
|
||||
size_t excessBytes = 0;
|
||||
};
|
||||
|
||||
#endif /* FRAMEWORK_CONTAINER_SIMPLERINGBUFFER_H_ */
|
||||
|
@ -54,7 +54,8 @@ ReturnValue_t GlobalDataPool::unlockDataPool() {
|
||||
}
|
||||
|
||||
ReturnValue_t GlobalDataPool::lockDataPool(uint32_t timeoutMs) {
|
||||
ReturnValue_t status = mutex->lockMutex(timeoutMs);
|
||||
ReturnValue_t status = mutex->lockMutex(MutexIF::TimeoutType::WAITING,
|
||||
timeoutMs);
|
||||
if(status != RETURN_OK) {
|
||||
sif::error << "DataPool::DataPool: lock of mutex failed "
|
||||
"with error code: " << status << std::endl;
|
||||
|
@ -1,11 +1,105 @@
|
||||
#include <framework/datapoollocal/LocalDataPoolManager.h>
|
||||
#include <framework/datapoollocal/LocalDataSet.h>
|
||||
#include <framework/serialize/SerializeAdapter.h>
|
||||
|
||||
LocalDataSet::LocalDataSet(HasLocalDataPoolIF *hkOwner, const size_t maxSize):
|
||||
LocalDataSetBase(hkOwner, nullptr, maxSize), poolVarList(maxSize) {
|
||||
this->setContainer(poolVarList.data());
|
||||
#include <cmath>
|
||||
#include <cstring>
|
||||
|
||||
LocalDataSet::LocalDataSet(HasLocalDataPoolIF *hkOwner,
|
||||
const size_t maxNumberOfVariables):
|
||||
DataSetBase(poolVarList.data(), maxNumberOfVariables) {
|
||||
poolVarList.reserve(maxNumberOfVariables);
|
||||
poolVarList.resize(maxNumberOfVariables);
|
||||
if(hkOwner == nullptr) {
|
||||
sif::error << "LocalDataSet::LocalDataSet: Owner can't be nullptr!"
|
||||
<< std::endl;
|
||||
return;
|
||||
}
|
||||
hkManager = hkOwner->getHkManagerHandle();
|
||||
}
|
||||
|
||||
LocalDataSet::LocalDataSet(object_id_t owner, const size_t maxSize):
|
||||
LocalDataSetBase(owner, nullptr, maxSize), poolVarList(maxSize) {
|
||||
this->setContainer(poolVarList.data());
|
||||
LocalDataSet::LocalDataSet(object_id_t ownerId,
|
||||
const size_t maxNumberOfVariables):
|
||||
DataSetBase(poolVarList.data(), maxNumberOfVariables) {
|
||||
poolVarList.reserve(maxNumberOfVariables);
|
||||
poolVarList.resize(maxNumberOfVariables);
|
||||
HasLocalDataPoolIF* hkOwner = objectManager->get<HasLocalDataPoolIF>(
|
||||
ownerId);
|
||||
if(hkOwner == nullptr) {
|
||||
sif::error << "LocalDataSet::LocalDataSet: Owner can't be nullptr!"
|
||||
<< std::endl;
|
||||
return;
|
||||
}
|
||||
hkManager = hkOwner->getHkManagerHandle();
|
||||
}
|
||||
|
||||
LocalDataSet::~LocalDataSet() {
|
||||
}
|
||||
|
||||
ReturnValue_t LocalDataSet::lockDataPool(uint32_t timeoutMs) {
|
||||
MutexIF* mutex = hkManager->getMutexHandle();
|
||||
return mutex->lockMutex(MutexIF::TimeoutType::WAITING, timeoutMs);
|
||||
}
|
||||
|
||||
ReturnValue_t LocalDataSet::serializeWithValidityBuffer(uint8_t **buffer,
|
||||
size_t *size, size_t maxSize,
|
||||
SerializeIF::Endianness streamEndianness) const {
|
||||
ReturnValue_t result = HasReturnvaluesIF::RETURN_FAILED;
|
||||
uint8_t validityMaskSize = std::ceil(static_cast<float>(fillCount)/8.0);
|
||||
uint8_t validityMask[validityMaskSize];
|
||||
uint8_t validBufferIndex = 0;
|
||||
uint8_t validBufferIndexBit = 0;
|
||||
for (uint16_t count = 0; count < fillCount; count++) {
|
||||
if(registeredVariables[count]->isValid()) {
|
||||
// set validity buffer here.
|
||||
this->bitSetter(validityMask + validBufferIndex,
|
||||
validBufferIndexBit);
|
||||
if(validBufferIndexBit == 7) {
|
||||
validBufferIndex ++;
|
||||
validBufferIndexBit = 0;
|
||||
}
|
||||
else {
|
||||
validBufferIndexBit ++;
|
||||
}
|
||||
}
|
||||
result = registeredVariables[count]->serialize(buffer, size, maxSize,
|
||||
streamEndianness);
|
||||
if (result != HasReturnvaluesIF::RETURN_OK) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
// copy validity buffer to end
|
||||
std::memcpy(*buffer, validityMask, validityMaskSize);
|
||||
*size += validityMaskSize;
|
||||
return result;
|
||||
}
|
||||
|
||||
ReturnValue_t LocalDataSet::unlockDataPool() {
|
||||
MutexIF* mutex = hkManager->getMutexHandle();
|
||||
return mutex->unlockMutex();
|
||||
}
|
||||
|
||||
ReturnValue_t LocalDataSet::serializeLocalPoolIds(uint8_t** buffer,
|
||||
size_t* size, size_t maxSize,
|
||||
SerializeIF::Endianness streamEndianness) const {
|
||||
for (uint16_t count = 0; count < fillCount; count++) {
|
||||
lp_id_t currentPoolId = registeredVariables[count]->getDataPoolId();
|
||||
auto result = SerializeAdapter::serialize(¤tPoolId, buffer,
|
||||
size, maxSize, streamEndianness);
|
||||
if(result != HasReturnvaluesIF::RETURN_OK) {
|
||||
sif::warning << "LocalDataSet::serializeLocalPoolIds: Serialization"
|
||||
" error!" << std::endl;
|
||||
return result;
|
||||
}
|
||||
}
|
||||
return HasReturnvaluesIF::RETURN_OK;
|
||||
}
|
||||
|
||||
void LocalDataSet::bitSetter(uint8_t* byte, uint8_t position) const {
|
||||
if(position > 7) {
|
||||
sif::debug << "Pool Raw Access: Bit setting invalid position" << std::endl;
|
||||
return;
|
||||
}
|
||||
uint8_t shiftNumber = position + (7 - 2 * position);
|
||||
*byte |= 1 << shiftNumber;
|
||||
}
|
||||
|
@ -48,7 +48,8 @@ inline LocalPoolVar<T>::LocalPoolVar(lp_id_t poolId, object_id_t poolOwner,
|
||||
|
||||
template<typename T>
|
||||
inline ReturnValue_t LocalPoolVar<T>::read(dur_millis_t lockTimeout) {
|
||||
MutexHelper(hkManager->getMutexHandle(), lockTimeout);
|
||||
MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING,
|
||||
lockTimeout);
|
||||
return readWithoutLock();
|
||||
}
|
||||
|
||||
@ -76,7 +77,8 @@ inline ReturnValue_t LocalPoolVar<T>::readWithoutLock() {
|
||||
|
||||
template<typename T>
|
||||
inline ReturnValue_t LocalPoolVar<T>::commit(dur_millis_t lockTimeout) {
|
||||
MutexHelper(hkManager->getMutexHandle(), lockTimeout);
|
||||
MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING,
|
||||
lockTimeout);
|
||||
return commitWithoutLock();
|
||||
}
|
||||
|
||||
|
@ -44,7 +44,8 @@ inline LocalPoolVector<T, vectorSize>::LocalPoolVector(lp_id_t poolId,
|
||||
|
||||
template<typename T, uint16_t vectorSize>
|
||||
inline ReturnValue_t LocalPoolVector<T, vectorSize>::read(uint32_t lockTimeout) {
|
||||
MutexHelper(hkManager->getMutexHandle(), lockTimeout);
|
||||
MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING,
|
||||
lockTimeout);
|
||||
return readWithoutLock();
|
||||
}
|
||||
template<typename T, uint16_t vectorSize>
|
||||
@ -74,7 +75,8 @@ inline ReturnValue_t LocalPoolVector<T, vectorSize>::readWithoutLock() {
|
||||
template<typename T, uint16_t vectorSize>
|
||||
inline ReturnValue_t LocalPoolVector<T, vectorSize>::commit(
|
||||
uint32_t lockTimeout) {
|
||||
MutexHelper(hkManager->getMutexHandle(), lockTimeout);
|
||||
MutexHelper(hkManager->getMutexHandle(), MutexIF::TimeoutType::WAITING,
|
||||
lockTimeout);
|
||||
return commitWithoutLock();
|
||||
}
|
||||
|
||||
|
@ -165,9 +165,8 @@ ReturnValue_t AssemblyBase::checkChildrenState() {
|
||||
}
|
||||
|
||||
ReturnValue_t AssemblyBase::checkChildrenStateOff() {
|
||||
for (std::map<object_id_t, ChildInfo>::iterator iter = childrenMap.begin();
|
||||
iter != childrenMap.end(); iter++) {
|
||||
if (checkChildOff(iter->first) != RETURN_OK) {
|
||||
for (const auto& childIter: childrenMap) {
|
||||
if (checkChildOff(childIter.first) != RETURN_OK) {
|
||||
return NOT_ENOUGH_CHILDREN_IN_CORRECT_STATE;
|
||||
}
|
||||
}
|
||||
|
@ -1,10 +1,30 @@
|
||||
#ifndef ASSEMBLYBASE_H_
|
||||
#define ASSEMBLYBASE_H_
|
||||
#ifndef FRAMEWORK_DEVICEHANDLERS_ASSEMBLYBASE_H_
|
||||
#define FRAMEWORK_DEVICEHANDLERS_ASSEMBLYBASE_H_
|
||||
|
||||
#include <framework/container/FixedArrayList.h>
|
||||
#include <framework/devicehandlers/DeviceHandlerBase.h>
|
||||
#include <framework/subsystem/SubsystemBase.h>
|
||||
|
||||
/**
|
||||
* @brief Base class to implement reconfiguration and failure handling for
|
||||
* redundant devices by monitoring their modes health states.
|
||||
* @details
|
||||
* Documentation: Dissertation Baetz p.156, 157.
|
||||
*
|
||||
* This class reduces the complexity of controller components which would
|
||||
* otherwise be needed for the handling of redundant devices.
|
||||
*
|
||||
* The template class monitors mode and health state of its children
|
||||
* and checks availability of devices on every detected change.
|
||||
* AssemblyBase does not implement any redundancy logic by itself, but provides
|
||||
* adaptation points for implementations to do so. Since most monitoring
|
||||
* activities rely on mode and health state only and are therefore
|
||||
* generic, it is sufficient for subclasses to provide:
|
||||
*
|
||||
* 1. check logic when active-> checkChildrenStateOn
|
||||
* 2. transition logic to change the mode -> commandChildren
|
||||
*
|
||||
*/
|
||||
class AssemblyBase: public SubsystemBase {
|
||||
public:
|
||||
static const uint8_t INTERFACE_ID = CLASS_ID::ASSEMBLY_BASE;
|
||||
@ -16,10 +36,41 @@ public:
|
||||
static const ReturnValue_t NOT_ENOUGH_CHILDREN_IN_CORRECT_STATE =
|
||||
MAKE_RETURN_CODE(0xa1);
|
||||
|
||||
AssemblyBase(object_id_t objectId, object_id_t parentId, uint16_t commandQueueDepth = 8);
|
||||
AssemblyBase(object_id_t objectId, object_id_t parentId,
|
||||
uint16_t commandQueueDepth = 8);
|
||||
virtual ~AssemblyBase();
|
||||
|
||||
protected:
|
||||
|
||||
// SHOULDDO: Change that OVERWRITE_HEALTH may be returned
|
||||
// (or return internalState directly?)
|
||||
/**
|
||||
* Command children to reach [mode,submode] combination
|
||||
* Can be done by setting #commandsOutstanding correctly,
|
||||
* or using executeTable()
|
||||
* @param mode
|
||||
* @param submode
|
||||
* @return
|
||||
* - @c RETURN_OK if ok
|
||||
* - @c NEED_SECOND_STEP if children need to be commanded again
|
||||
*/
|
||||
virtual ReturnValue_t commandChildren(Mode_t mode, Submode_t submode) = 0;
|
||||
|
||||
/**
|
||||
* Check whether desired assembly mode was achieved by checking the modes
|
||||
* or/and health states of child device handlers.
|
||||
* The assembly template class will also call this function if a health
|
||||
* or mode change of a child device handler was detected.
|
||||
* @param wantedMode
|
||||
* @param wantedSubmode
|
||||
* @return
|
||||
*/
|
||||
virtual ReturnValue_t checkChildrenStateOn(Mode_t wantedMode,
|
||||
Submode_t wantedSubmode) = 0;
|
||||
|
||||
virtual ReturnValue_t isModeCombinationValid(Mode_t mode,
|
||||
Submode_t submode) = 0;
|
||||
|
||||
enum InternalState {
|
||||
STATE_NONE,
|
||||
STATE_OVERWRITE_HEALTH,
|
||||
@ -36,6 +87,7 @@ protected:
|
||||
RECOVERY_WAIT
|
||||
} recoveryState; //!< Indicates if one of the children requested a recovery.
|
||||
ChildrenMap::iterator recoveringDevice;
|
||||
|
||||
/**
|
||||
* the mode the current transition is trying to achieve.
|
||||
* Can be different from the modehelper.commandedMode!
|
||||
@ -61,8 +113,8 @@ protected:
|
||||
bool handleChildrenChanged();
|
||||
|
||||
/**
|
||||
* This method is called if the children changed its mode in a way that the current
|
||||
* mode can't be kept.
|
||||
* This method is called if the children changed its mode in a way that
|
||||
* the current mode can't be kept.
|
||||
* Default behavior is to go to MODE_OFF.
|
||||
* @param result The failure code which was returned by checkChildrenState.
|
||||
*/
|
||||
@ -75,9 +127,6 @@ protected:
|
||||
ReturnValue_t checkModeCommand(Mode_t mode, Submode_t submode,
|
||||
uint32_t *msToReachTheMode);
|
||||
|
||||
virtual ReturnValue_t isModeCombinationValid(Mode_t mode,
|
||||
Submode_t submode) = 0;
|
||||
|
||||
virtual void startTransition(Mode_t mode, Submode_t submode);
|
||||
|
||||
virtual void doStartTransition(Mode_t mode, Submode_t submode);
|
||||
@ -90,24 +139,6 @@ protected:
|
||||
|
||||
void sendHealthCommand(MessageQueueId_t sendTo, HealthState health);
|
||||
|
||||
//SHOULDDO: Change that OVERWRITE_HEALTH may be returned (or return internalState directly?)
|
||||
/**
|
||||
* command children to reach mode,submode
|
||||
*
|
||||
* set #commandsOutstanding correctly, or use executeTable()
|
||||
*
|
||||
* @param mode
|
||||
* @param submode
|
||||
* @return
|
||||
* - @c RETURN_OK if ok
|
||||
* - @c NEED_SECOND_STEP if children need to be commanded again
|
||||
*/
|
||||
virtual ReturnValue_t commandChildren(Mode_t mode, Submode_t submode) = 0;
|
||||
|
||||
//SHOULDDO: Remove wantedMode, wantedSubmode, as targetMode/submode is available?
|
||||
virtual ReturnValue_t checkChildrenStateOn(Mode_t wantedMode,
|
||||
Submode_t wantedSubmode) = 0;
|
||||
|
||||
virtual ReturnValue_t checkChildrenStateOff();
|
||||
|
||||
ReturnValue_t checkChildrenState();
|
||||
@ -129,4 +160,4 @@ protected:
|
||||
|
||||
};
|
||||
|
||||
#endif /* ASSEMBLYBASE_H_ */
|
||||
#endif /* FRAMEWORK_DEVICEHANDLERS_ASSEMBLYBASE_H_ */
|
||||
|
@ -39,7 +39,7 @@ ReturnValue_t ChildHandlerBase::initialize() {
|
||||
parent->registerChild(getObjectId());
|
||||
}
|
||||
|
||||
healthHelper.setParentQeueue(parentQueue);
|
||||
healthHelper.setParentQueue(parentQueue);
|
||||
|
||||
modeHelper.setParentQueue(parentQueue);
|
||||
|
||||
|
@ -128,6 +128,8 @@ ReturnValue_t DeviceHandlerBase::initialize() {
|
||||
|
||||
result = communicationInterface->initializeInterface(comCookie);
|
||||
if (result != RETURN_OK) {
|
||||
sif::error << "DeviceHandlerBase::initialize: Initializing "
|
||||
"communication interface failed!" << std::endl;
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -678,6 +680,10 @@ void DeviceHandlerBase::parseReply(const uint8_t* receivedData,
|
||||
switch (result) {
|
||||
case RETURN_OK:
|
||||
handleReply(receivedData, foundId, foundLen);
|
||||
if(foundLen == 0) {
|
||||
sif::warning << "DeviceHandlerBase::parseReply: foundLen is 0!"
|
||||
" Packet parsing will be stuck." << std::endl;
|
||||
}
|
||||
break;
|
||||
case APERIODIC_REPLY: {
|
||||
result = interpretDeviceReply(foundId, receivedData);
|
||||
@ -686,8 +692,12 @@ void DeviceHandlerBase::parseReply(const uint8_t* receivedData,
|
||||
triggerEvent(DEVICE_INTERPRETING_REPLY_FAILED, result,
|
||||
foundId);
|
||||
}
|
||||
if(foundLen == 0) {
|
||||
sif::warning << "DeviceHandlerBase::parseReply: foundLen is 0!"
|
||||
" Packet parsing will be stuck." << std::endl;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case IGNORE_REPLY_DATA:
|
||||
break;
|
||||
case IGNORE_FULL_PACKET:
|
||||
@ -1134,7 +1144,7 @@ ReturnValue_t DeviceHandlerBase::handleDeviceHandlerMessage(
|
||||
|
||||
void DeviceHandlerBase::setParentQueue(MessageQueueId_t parentQueueId) {
|
||||
modeHelper.setParentQueue(parentQueueId);
|
||||
healthHelper.setParentQeueue(parentQueueId);
|
||||
healthHelper.setParentQueue(parentQueueId);
|
||||
}
|
||||
|
||||
bool DeviceHandlerBase::isAwaitingReply() {
|
||||
|
@ -379,6 +379,8 @@ protected:
|
||||
* @param deviceCommand Identifier of the command to add.
|
||||
* @param maxDelayCycles The maximum number of delay cycles the command
|
||||
* waits until it times out.
|
||||
* @param replyLen Will be supplied to the requestReceiveMessage call of
|
||||
* the communication interface.
|
||||
* @param periodic Indicates if the command is periodic (i.e. it is sent
|
||||
* by the device repeatedly without request) or not. Default is aperiodic (0)
|
||||
* @return - @c RETURN_OK when the command was successfully inserted,
|
||||
|
@ -98,7 +98,7 @@ public:
|
||||
static const uint8_t INTERFACE_ID = CLASS_ID::DEVICE_HANDLER_IF;
|
||||
|
||||
// Standard codes used when building commands.
|
||||
static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If the command size is 0. Checked in DHB
|
||||
static const ReturnValue_t NO_COMMAND_DATA = MAKE_RETURN_CODE(0xA0); //!< If no command data was given when expected.
|
||||
static const ReturnValue_t COMMAND_NOT_SUPPORTED = MAKE_RETURN_CODE(0xA1); //!< Command ID not in commandMap. Checked in DHB
|
||||
static const ReturnValue_t COMMAND_ALREADY_SENT = MAKE_RETURN_CODE(0xA2); //!< Command was already executed. Checked in DHB
|
||||
static const ReturnValue_t COMMAND_WAS_NOT_SENT = MAKE_RETURN_CODE(0xA3);
|
||||
|
@ -38,7 +38,7 @@ MessageQueueId_t HealthDevice::getCommandQueue() const {
|
||||
}
|
||||
|
||||
void HealthDevice::setParentQueue(MessageQueueId_t parentQueue) {
|
||||
healthHelper.setParentQeueue(parentQueue);
|
||||
healthHelper.setParentQueue(parentQueue);
|
||||
}
|
||||
|
||||
bool HealthDevice::hasHealthChanged() {
|
||||
|
@ -18,6 +18,8 @@ enum {
|
||||
SYSTEM_MANAGER = 74,
|
||||
SYSTEM_MANAGER_1 = 75,
|
||||
SYSTEM_1 = 79,
|
||||
PUS_SERVICE_1 = 80,
|
||||
FW_SUBSYSTEM_ID_RANGE
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -7,8 +7,8 @@
|
||||
|
||||
FailureIsolationBase::FailureIsolationBase(object_id_t owner,
|
||||
object_id_t parent, uint8_t messageDepth, uint8_t parameterDomainBase) :
|
||||
eventQueue(NULL), ownerId(owner), owner(NULL),
|
||||
faultTreeParent(parent), parameterDomainBase(parameterDomainBase) {
|
||||
ownerId(owner), faultTreeParent(parent),
|
||||
parameterDomainBase(parameterDomainBase) {
|
||||
eventQueue = QueueFactory::instance()->createMessageQueue(messageDepth,
|
||||
EventMessage::EVENT_MESSAGE_SIZE);
|
||||
}
|
||||
@ -104,9 +104,9 @@ MessageQueueId_t FailureIsolationBase::getEventReceptionQueue() {
|
||||
ReturnValue_t FailureIsolationBase::sendConfirmationRequest(EventMessage* event,
|
||||
MessageQueueId_t destination) {
|
||||
event->setMessageId(EventMessage::CONFIRMATION_REQUEST);
|
||||
if (destination != 0) {
|
||||
if (destination != MessageQueueIF::NO_QUEUE) {
|
||||
return eventQueue->sendMessage(destination, event);
|
||||
} else if (faultTreeParent != 0) {
|
||||
} else if (faultTreeParent != objects::NO_OBJECT) {
|
||||
return eventQueue->sendToDefault(event);
|
||||
}
|
||||
return RETURN_FAILED;
|
||||
|
@ -33,9 +33,9 @@ public:
|
||||
virtual void triggerEvent(Event event, uint32_t parameter1 = 0,
|
||||
uint32_t parameter2 = 0);
|
||||
protected:
|
||||
MessageQueueIF* eventQueue;
|
||||
MessageQueueIF* eventQueue = nullptr;
|
||||
object_id_t ownerId;
|
||||
HasHealthIF* owner;
|
||||
HasHealthIF* owner = nullptr;
|
||||
object_id_t faultTreeParent;
|
||||
uint8_t parameterDomainBase;
|
||||
void setOwnerHealth(HasHealthIF::HealthState health);
|
||||
@ -45,7 +45,7 @@ protected:
|
||||
virtual ReturnValue_t confirmFault(EventMessage* event);
|
||||
virtual void decrementFaultCounters() = 0;
|
||||
ReturnValue_t sendConfirmationRequest(EventMessage* event,
|
||||
MessageQueueId_t destination = 0);
|
||||
MessageQueueId_t destination = MessageQueueIF::NO_QUEUE);
|
||||
void throwFdirEvent(Event event, uint32_t parameter1 = 0,
|
||||
uint32_t parameter2 = 0);
|
||||
private:
|
||||
|
@ -28,11 +28,11 @@ HasHealthIF::HealthState HealthHelper::getHealth() {
|
||||
}
|
||||
|
||||
ReturnValue_t HealthHelper::initialize(MessageQueueId_t parentQueue) {
|
||||
setParentQeueue(parentQueue);
|
||||
setParentQueue(parentQueue);
|
||||
return initialize();
|
||||
}
|
||||
|
||||
void HealthHelper::setParentQeueue(MessageQueueId_t parentQueue) {
|
||||
void HealthHelper::setParentQueue(MessageQueueId_t parentQueue) {
|
||||
this->parentQueue = parentQueue;
|
||||
}
|
||||
|
||||
|
@ -79,7 +79,7 @@ public:
|
||||
/**
|
||||
* @param parentQueue the Queue id of the parent object. Set to 0 if no parent present
|
||||
*/
|
||||
void setParentQeueue(MessageQueueId_t parentQueue);
|
||||
void setParentQueue(MessageQueueId_t parentQueue);
|
||||
|
||||
/**
|
||||
*
|
||||
|
@ -88,6 +88,7 @@ void CommandMessage::setToUnknownCommand() {
|
||||
|
||||
void CommandMessage::setReplyRejected(ReturnValue_t reason,
|
||||
Command_t initialCommand) {
|
||||
setCommand(REPLY_REJECTED);
|
||||
setParameter(reason);
|
||||
setParameter2(initialCommand);
|
||||
}
|
||||
|
@ -6,9 +6,11 @@
|
||||
|
||||
class MutexHelper {
|
||||
public:
|
||||
MutexHelper(MutexIF* mutex, uint32_t timeoutMs) :
|
||||
MutexHelper(MutexIF* mutex, MutexIF::TimeoutType timeoutType =
|
||||
MutexIF::TimeoutType::BLOCKING, uint32_t timeoutMs = 0) :
|
||||
internalMutex(mutex) {
|
||||
ReturnValue_t status = mutex->lockMutex(timeoutMs);
|
||||
ReturnValue_t status = mutex->lockMutex(timeoutType,
|
||||
timeoutMs);
|
||||
if(status == MutexIF::MUTEX_TIMEOUT) {
|
||||
sif::error << "MutexHelper: Lock of mutex failed with timeout of "
|
||||
<< timeoutMs << " milliseconds!" << std::endl;
|
||||
|
@ -5,7 +5,6 @@
|
||||
|
||||
/**
|
||||
* @brief Common interface for OS Mutex objects which provide MUTual EXclusion.
|
||||
*
|
||||
* @details https://en.wikipedia.org/wiki/Lock_(computer_science)
|
||||
* @ingroup osal
|
||||
* @ingroup interface
|
||||
@ -13,19 +12,24 @@
|
||||
class MutexIF {
|
||||
public:
|
||||
/**
|
||||
* @brief Timeout value used for polling lock attempt.
|
||||
* @details
|
||||
* If the lock is not successfull, MUTEX_TIMEOUT will be returned
|
||||
* immediately. Value needs to be defined in implementation.
|
||||
* Different types of timeout for the mutex lock.
|
||||
*/
|
||||
static const uint32_t POLLING;
|
||||
enum TimeoutType {
|
||||
POLLING, //!< If mutex is not available, return immediately
|
||||
WAITING, //!< Wait a specified time for the mutex to become available
|
||||
BLOCKING //!< Block indefinitely until the mutex becomes available.
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Timeout value used for permanent blocking lock attempt.
|
||||
* @details
|
||||
* The task will be blocked (indefinitely) until the mutex is unlocked.
|
||||
* Value needs to be defined in implementation.
|
||||
* Lock the mutex. The timeout value will only be used for
|
||||
* TimeoutType::WAITING
|
||||
* @param timeoutType
|
||||
* @param timeoutMs
|
||||
* @return
|
||||
*/
|
||||
static const uint32_t BLOCKING;
|
||||
virtual ReturnValue_t lockMutex(TimeoutType timeoutType =
|
||||
TimeoutType::BLOCKING, uint32_t timeoutMs = 0) = 0;
|
||||
virtual ReturnValue_t unlockMutex() = 0;
|
||||
|
||||
static const uint8_t INTERFACE_ID = CLASS_ID::MUTEX_IF;
|
||||
/**
|
||||
@ -78,8 +82,6 @@ public:
|
||||
static const ReturnValue_t MUTEX_DESTROYED_WHILE_WAITING = MAKE_RETURN_CODE(12);
|
||||
|
||||
virtual ~MutexIF() {}
|
||||
virtual ReturnValue_t lockMutex(uint32_t timeoutMs) = 0;
|
||||
virtual ReturnValue_t unlockMutex() = 0;
|
||||
};
|
||||
|
||||
|
||||
|
@ -5,11 +5,12 @@
|
||||
uint32_t FixedTimeslotTask::deadlineMissedCount = 0;
|
||||
const size_t PeriodicTaskIF::MINIMUM_STACK_SIZE = configMINIMAL_STACK_SIZE;
|
||||
|
||||
FixedTimeslotTask::FixedTimeslotTask(const char *name, TaskPriority setPriority,
|
||||
FixedTimeslotTask::FixedTimeslotTask(TaskName name, TaskPriority setPriority,
|
||||
TaskStackSize setStack, TaskPeriod overallPeriod,
|
||||
void (*setDeadlineMissedFunc)()) :
|
||||
started(false), handle(NULL), pst(overallPeriod * 1000) {
|
||||
xTaskCreate(taskEntryPoint, name, setStack, this, setPriority, &handle);
|
||||
configSTACK_DEPTH_TYPE stackSize = setStack / sizeof(configSTACK_DEPTH_TYPE);
|
||||
xTaskCreate(taskEntryPoint, name, stackSize, this, setPriority, &handle);
|
||||
// All additional attributes are applied to the object.
|
||||
this->deadlineMissedFunc = setDeadlineMissedFunc;
|
||||
}
|
||||
@ -125,19 +126,18 @@ void FixedTimeslotTask::checkMissedDeadline(const TickType_t xLastWakeTime,
|
||||
* it. */
|
||||
TickType_t currentTickCount = xTaskGetTickCount();
|
||||
TickType_t timeToWake = xLastWakeTime + interval;
|
||||
// Tick count has overflown
|
||||
if(currentTickCount < xLastWakeTime) {
|
||||
// Time to wake has overflown as well. If the tick count
|
||||
// is larger than the time to wake, a deadline was missed.
|
||||
if(timeToWake < xLastWakeTime and
|
||||
currentTickCount > timeToWake) {
|
||||
// Time to wake has not overflown.
|
||||
if(timeToWake > xLastWakeTime) {
|
||||
/* If the current time has overflown exclusively or the current
|
||||
* tick count is simply larger than the time to wake, a deadline was
|
||||
* missed */
|
||||
if((currentTickCount < xLastWakeTime) or (currentTickCount > timeToWake)) {
|
||||
handleMissedDeadline();
|
||||
}
|
||||
}
|
||||
// No tick count overflow. If the timeToWake has not overflown
|
||||
// and the current tick count is larger than the time to wake,
|
||||
// a deadline was missed.
|
||||
else if(timeToWake > xLastWakeTime and currentTickCount > timeToWake) {
|
||||
/* Time to wake has overflown. A deadline was missed if the current time
|
||||
* is larger than the time to wake */
|
||||
else if((timeToWake < xLastWakeTime) and (currentTickCount > timeToWake)) {
|
||||
handleMissedDeadline();
|
||||
}
|
||||
}
|
||||
|
@ -24,7 +24,7 @@ public:
|
||||
* @param setDeadlineMissedFunc Callback if a deadline was missed.
|
||||
* @return Pointer to the newly created task.
|
||||
*/
|
||||
FixedTimeslotTask(const char *name, TaskPriority setPriority,
|
||||
FixedTimeslotTask(TaskName name, TaskPriority setPriority,
|
||||
TaskStackSize setStack, TaskPeriod overallPeriod,
|
||||
void (*setDeadlineMissedFunc)());
|
||||
|
||||
|
@ -123,11 +123,20 @@ bool MessageQueue::isDefaultDestinationSet() const {
|
||||
ReturnValue_t MessageQueue::sendMessageFromMessageQueue(MessageQueueId_t sendTo,
|
||||
MessageQueueMessageIF* message, MessageQueueId_t sentFrom,
|
||||
bool ignoreFault, CallContext callContext) {
|
||||
BaseType_t result = pdFALSE;
|
||||
QueueHandle_t destination = nullptr;
|
||||
|
||||
if(sendTo == MessageQueueIF::NO_QUEUE) {
|
||||
return MessageQueueIF::DESTINVATION_INVALID;
|
||||
}
|
||||
else {
|
||||
destination = reinterpret_cast<QueueHandle_t>(sendTo);
|
||||
}
|
||||
message->setSender(sentFrom);
|
||||
BaseType_t result;
|
||||
|
||||
|
||||
if(callContext == CallContext::TASK) {
|
||||
result = xQueueSendToBack(reinterpret_cast<QueueHandle_t>(sendTo),
|
||||
result = xQueueSendToBack(destination,
|
||||
static_cast<const void*>(message->getBuffer()), 0);
|
||||
}
|
||||
else {
|
||||
|
@ -2,13 +2,10 @@
|
||||
|
||||
#include <framework/serviceinterface/ServiceInterfaceStream.h>
|
||||
|
||||
const uint32_t MutexIF::POLLING = 0;
|
||||
const uint32_t MutexIF::BLOCKING = portMAX_DELAY;
|
||||
|
||||
Mutex::Mutex() {
|
||||
handle = xSemaphoreCreateMutex();
|
||||
if(handle == nullptr) {
|
||||
sif::error << "Mutex: Creation failure" << std::endl;
|
||||
sif::error << "Mutex::Mutex(FreeRTOS): Creation failure" << std::endl;
|
||||
}
|
||||
}
|
||||
|
||||
@ -19,15 +16,17 @@ Mutex::~Mutex() {
|
||||
|
||||
}
|
||||
|
||||
ReturnValue_t Mutex::lockMutex(uint32_t timeoutMs) {
|
||||
ReturnValue_t Mutex::lockMutex(TimeoutType timeoutType,
|
||||
uint32_t timeoutMs) {
|
||||
if (handle == nullptr) {
|
||||
return MutexIF::MUTEX_NOT_FOUND;
|
||||
}
|
||||
TickType_t timeout = MutexIF::POLLING;
|
||||
if(timeoutMs == MutexIF::BLOCKING) {
|
||||
timeout = MutexIF::BLOCKING;
|
||||
// If the timeout type is BLOCKING, this will be the correct value.
|
||||
uint32_t timeout = portMAX_DELAY;
|
||||
if(timeoutType == TimeoutType::POLLING) {
|
||||
timeout = 0;
|
||||
}
|
||||
else if(timeoutMs > MutexIF::POLLING){
|
||||
else if(timeoutType == TimeoutType::WAITING){
|
||||
timeout = pdMS_TO_TICKS(timeoutMs);
|
||||
}
|
||||
|
||||
|
@ -18,8 +18,10 @@ class Mutex : public MutexIF {
|
||||
public:
|
||||
Mutex();
|
||||
~Mutex();
|
||||
ReturnValue_t lockMutex(uint32_t timeoutMs = MutexIF::BLOCKING) override;
|
||||
ReturnValue_t lockMutex(TimeoutType timeoutType,
|
||||
uint32_t timeoutMs) override;
|
||||
ReturnValue_t unlockMutex() override;
|
||||
|
||||
private:
|
||||
SemaphoreHandle_t handle;
|
||||
};
|
||||
|
@ -5,12 +5,13 @@
|
||||
|
||||
PeriodicTask::PeriodicTask(const char *name, TaskPriority setPriority,
|
||||
TaskStackSize setStack, TaskPeriod setPeriod,
|
||||
void (*setDeadlineMissedFunc)()) :
|
||||
TaskDeadlineMissedFunction deadlineMissedFunc) :
|
||||
started(false), handle(NULL), period(setPeriod), deadlineMissedFunc(
|
||||
setDeadlineMissedFunc)
|
||||
deadlineMissedFunc)
|
||||
{
|
||||
configSTACK_DEPTH_TYPE stackSize = setStack / sizeof(configSTACK_DEPTH_TYPE);
|
||||
BaseType_t status = xTaskCreate(taskEntryPoint, name,
|
||||
setStack, this, setPriority, &handle);
|
||||
stackSize, this, setPriority, &handle);
|
||||
if(status != pdPASS){
|
||||
sif::debug << "PeriodicTask Insufficient heap memory remaining. "
|
||||
"Status: " << status << std::endl;
|
||||
@ -81,7 +82,7 @@ void PeriodicTask::taskFunctionality() {
|
||||
}
|
||||
}
|
||||
|
||||
ReturnValue_t PeriodicTask::addComponent(object_id_t object, bool setTaskIF) {
|
||||
ReturnValue_t PeriodicTask::addComponent(object_id_t object) {
|
||||
ExecutableObjectIF* newObject = objectManager->get<ExecutableObjectIF>(
|
||||
object);
|
||||
if (newObject == nullptr) {
|
||||
@ -90,12 +91,9 @@ ReturnValue_t PeriodicTask::addComponent(object_id_t object, bool setTaskIF) {
|
||||
return HasReturnvaluesIF::RETURN_FAILED;
|
||||
}
|
||||
objectList.push_back(newObject);
|
||||
|
||||
if(setTaskIF) {
|
||||
newObject->setTaskIF(this);
|
||||
}
|
||||
ReturnValue_t result = newObject->initializeAfterTaskCreation();
|
||||
return result;
|
||||
|
||||
return newObject->initializeAfterTaskCreation();
|
||||
}
|
||||
|
||||
uint32_t PeriodicTask::getPeriodMs() const {
|
||||
@ -109,19 +107,18 @@ void PeriodicTask::checkMissedDeadline(const TickType_t xLastWakeTime,
|
||||
* it. */
|
||||
TickType_t currentTickCount = xTaskGetTickCount();
|
||||
TickType_t timeToWake = xLastWakeTime + interval;
|
||||
// Tick count has overflown
|
||||
if(currentTickCount < xLastWakeTime) {
|
||||
// Time to wake has overflown as well. If the tick count
|
||||
// is larger than the time to wake, a deadline was missed.
|
||||
if(timeToWake < xLastWakeTime and
|
||||
currentTickCount > timeToWake) {
|
||||
// Time to wake has not overflown.
|
||||
if(timeToWake > xLastWakeTime) {
|
||||
/* If the current time has overflown exclusively or the current
|
||||
* tick count is simply larger than the time to wake, a deadline was
|
||||
* missed */
|
||||
if((currentTickCount < xLastWakeTime) or (currentTickCount > timeToWake)) {
|
||||
handleMissedDeadline();
|
||||
}
|
||||
}
|
||||
// No tick count overflow. If the timeToWake has not overflown
|
||||
// and the current tick count is larger than the time to wake,
|
||||
// a deadline was missed.
|
||||
else if(timeToWake > xLastWakeTime and currentTickCount > timeToWake) {
|
||||
/* Time to wake has overflown. A deadline was missed if the current time
|
||||
* is larger than the time to wake */
|
||||
else if((timeToWake < xLastWakeTime) and (currentTickCount > timeToWake)) {
|
||||
handleMissedDeadline();
|
||||
}
|
||||
}
|
||||
|
@ -40,9 +40,9 @@ public:
|
||||
* The function pointer to the deadline missed function that shall
|
||||
* be assigned.
|
||||
*/
|
||||
PeriodicTask(const char *name, TaskPriority setPriority,
|
||||
PeriodicTask(TaskName name, TaskPriority setPriority,
|
||||
TaskStackSize setStack, TaskPeriod setPeriod,
|
||||
void (*setDeadlineMissedFunc)());
|
||||
TaskDeadlineMissedFunction deadlineMissedFunc);
|
||||
/**
|
||||
* @brief Currently, the executed object's lifetime is not coupled with
|
||||
* the task object's lifetime, so the destructor is empty.
|
||||
@ -65,8 +65,7 @@ public:
|
||||
* -@c RETURN_OK on success
|
||||
* -@c RETURN_FAILED if the object could not be added.
|
||||
*/
|
||||
ReturnValue_t addComponent(object_id_t object,
|
||||
bool setTaskIF = true) override;
|
||||
ReturnValue_t addComponent(object_id_t object) override;
|
||||
|
||||
uint32_t getPeriodMs() const override;
|
||||
|
||||
|
@ -18,8 +18,8 @@ PeriodicTaskIF* TaskFactory::createPeriodicTask(TaskName name_,
|
||||
TaskPriority taskPriority_, TaskStackSize stackSize_,
|
||||
TaskPeriod period_,
|
||||
TaskDeadlineMissedFunction deadLineMissedFunction_) {
|
||||
return (PeriodicTaskIF*) (new PeriodicTask(name_, taskPriority_, stackSize_,
|
||||
period_, deadLineMissedFunction_));
|
||||
return dynamic_cast<PeriodicTaskIF*>(new PeriodicTask(name_, taskPriority_,
|
||||
stackSize_, period_, deadLineMissedFunction_));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -29,8 +29,8 @@ FixedTimeslotTaskIF* TaskFactory::createFixedTimeslotTask(TaskName name_,
|
||||
TaskPriority taskPriority_, TaskStackSize stackSize_,
|
||||
TaskPeriod period_,
|
||||
TaskDeadlineMissedFunction deadLineMissedFunction_) {
|
||||
return (FixedTimeslotTaskIF*) (new FixedTimeslotTask(name_, taskPriority_,
|
||||
stackSize_, period_, deadLineMissedFunction_));
|
||||
return dynamic_cast<FixedTimeslotTaskIF*>(new FixedTimeslotTask(name_,
|
||||
taskPriority_,stackSize_, period_, deadLineMissedFunction_));
|
||||
}
|
||||
|
||||
ReturnValue_t TaskFactory::deleteTask(PeriodicTaskIF* task) {
|
||||
|
@ -2,8 +2,6 @@
|
||||
#include <framework/serviceinterface/ServiceInterfaceStream.h>
|
||||
#include <framework/timemanager/Clock.h>
|
||||
|
||||
const uint32_t MutexIF::BLOCKING = 0xffffffff;
|
||||
const uint32_t MutexIF::POLLING = 0;
|
||||
uint8_t Mutex::count = 0;
|
||||
|
||||
|
||||
@ -40,9 +38,13 @@ Mutex::~Mutex() {
|
||||
pthread_mutex_destroy(&mutex);
|
||||
}
|
||||
|
||||
ReturnValue_t Mutex::lockMutex(uint32_t timeoutMs) {
|
||||
ReturnValue_t Mutex::lockMutex(TimeoutType timeoutType, uint32_t timeoutMs) {
|
||||
int status = 0;
|
||||
if (timeoutMs != MutexIF::BLOCKING) {
|
||||
|
||||
if(timeoutType == TimeoutType::POLLING) {
|
||||
status = pthread_mutex_trylock(&mutex);
|
||||
}
|
||||
else if (timeoutType == TimeoutType::WAITING) {
|
||||
timespec timeOut;
|
||||
clock_gettime(CLOCK_REALTIME, &timeOut);
|
||||
uint64_t nseconds = timeOut.tv_sec * 1000000000 + timeOut.tv_nsec;
|
||||
@ -50,27 +52,35 @@ ReturnValue_t Mutex::lockMutex(uint32_t timeoutMs) {
|
||||
timeOut.tv_sec = nseconds / 1000000000;
|
||||
timeOut.tv_nsec = nseconds - timeOut.tv_sec * 1000000000;
|
||||
status = pthread_mutex_timedlock(&mutex, &timeOut);
|
||||
} else {
|
||||
}
|
||||
else if(timeoutType == TimeoutType::BLOCKING) {
|
||||
status = pthread_mutex_lock(&mutex);
|
||||
}
|
||||
|
||||
switch (status) {
|
||||
case EINVAL:
|
||||
//The mutex was created with the protocol attribute having the value PTHREAD_PRIO_PROTECT and the calling thread's priority is higher than the mutex's current priority ceiling.
|
||||
// The mutex was created with the protocol attribute having the value
|
||||
// PTHREAD_PRIO_PROTECT and the calling thread's priority is higher
|
||||
// than the mutex's current priority ceiling.
|
||||
return WRONG_ATTRIBUTE_SETTING;
|
||||
//The process or thread would have blocked, and the abs_timeout parameter specified a nanoseconds field value less than zero or greater than or equal to 1000 million.
|
||||
//The value specified by mutex does not refer to an initialized mutex object.
|
||||
// The process or thread would have blocked, and the abs_timeout
|
||||
// parameter specified a nanoseconds field value less than zero or
|
||||
// greater than or equal to 1000 million.
|
||||
// The value specified by mutex does not refer to an initialized mutex object.
|
||||
//return MUTEX_NOT_FOUND;
|
||||
case EBUSY:
|
||||
//The mutex could not be acquired because it was already locked.
|
||||
// The mutex could not be acquired because it was already locked.
|
||||
return MUTEX_ALREADY_LOCKED;
|
||||
case ETIMEDOUT:
|
||||
//The mutex could not be locked before the specified timeout expired.
|
||||
// The mutex could not be locked before the specified timeout expired.
|
||||
return MUTEX_TIMEOUT;
|
||||
case EAGAIN:
|
||||
//The mutex could not be acquired because the maximum number of recursive locks for mutex has been exceeded.
|
||||
// The mutex could not be acquired because the maximum number of
|
||||
// recursive locks for mutex has been exceeded.
|
||||
return MUTEX_MAX_LOCKS;
|
||||
case EDEADLK:
|
||||
//A deadlock condition was detected or the current thread already owns the mutex.
|
||||
// A deadlock condition was detected or the current thread
|
||||
// already owns the mutex.
|
||||
return CURR_THREAD_ALREADY_OWNS_MUTEX;
|
||||
case 0:
|
||||
//Success
|
||||
|
@ -12,7 +12,7 @@ class Mutex : public MutexIF {
|
||||
public:
|
||||
Mutex();
|
||||
virtual ~Mutex();
|
||||
virtual ReturnValue_t lockMutex(uint32_t timeoutMs);
|
||||
virtual ReturnValue_t lockMutex(TimeoutType timeoutType, uint32_t timeoutMs);
|
||||
virtual ReturnValue_t unlockMutex();
|
||||
private:
|
||||
pthread_mutex_t mutex;
|
||||
|
@ -22,8 +22,7 @@ void* PeriodicPosixTask::taskEntryPoint(void* arg) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ReturnValue_t PeriodicPosixTask::addComponent(object_id_t object,
|
||||
bool setTaskIF) {
|
||||
ReturnValue_t PeriodicPosixTask::addComponent(object_id_t object) {
|
||||
ExecutableObjectIF* newObject = objectManager->get<ExecutableObjectIF>(
|
||||
object);
|
||||
if (newObject == nullptr) {
|
||||
@ -32,13 +31,9 @@ ReturnValue_t PeriodicPosixTask::addComponent(object_id_t object,
|
||||
return HasReturnvaluesIF::RETURN_FAILED;
|
||||
}
|
||||
objectList.push_back(newObject);
|
||||
|
||||
if(setTaskIF) {
|
||||
newObject->setTaskIF(this);
|
||||
}
|
||||
|
||||
ReturnValue_t result = newObject->initializeAfterTaskCreation();
|
||||
return result;
|
||||
return newObject->initializeAfterTaskCreation();
|
||||
}
|
||||
|
||||
ReturnValue_t PeriodicPosixTask::sleepFor(uint32_t ms) {
|
||||
|
@ -39,8 +39,7 @@ public:
|
||||
* @param object Id of the object to add.
|
||||
* @return RETURN_OK on success, RETURN_FAILED if the object could not be added.
|
||||
*/
|
||||
ReturnValue_t addComponent(object_id_t object,
|
||||
bool setTaskIF = true) override;
|
||||
ReturnValue_t addComponent(object_id_t object) override;
|
||||
|
||||
uint32_t getPeriodMs() const override;
|
||||
|
||||
|
@ -85,7 +85,7 @@ ReturnValue_t TmTcUnixUdpBridge::sendTm(const uint8_t *data, size_t dataLen) {
|
||||
}
|
||||
|
||||
void TmTcUnixUdpBridge::checkAndSetClientAddress(sockaddr_in newAddress) {
|
||||
MutexHelper lock(mutex, 10);
|
||||
MutexHelper lock(mutex, MutexIF::TimeoutType::WAITING, 10);
|
||||
|
||||
// char ipAddress [15];
|
||||
// sif::debug << "IP Address Sender: "<< inet_ntop(AF_INET,
|
||||
|
@ -5,8 +5,23 @@
|
||||
#include <framework/returnvalues/HasReturnvaluesIF.h>
|
||||
#include <stdint.h>
|
||||
|
||||
/** Each parameter is identified with a unique parameter ID */
|
||||
typedef uint32_t ParameterId_t;
|
||||
|
||||
/**
|
||||
* @brief This interface is used by components which have modifiable
|
||||
* parameters, e.g. atittude controllers
|
||||
* @details
|
||||
* Each parameter has a unique parameter ID. The first byte of the parameter
|
||||
* ID is the domain ID which can be used to identify unqiue spacecraft domains
|
||||
* (e.g. control and sensor domain in the AOCS controller).
|
||||
*
|
||||
* The second and third byte represent the matrix ID, which can represent
|
||||
* a 8-bit row and column number and the last byte...
|
||||
*
|
||||
* Yeah, it it matrix ID oder parameter ID now and is index a 16 bit number
|
||||
* of a 8 bit number now?
|
||||
*/
|
||||
class HasParametersIF {
|
||||
public:
|
||||
static const uint8_t INTERFACE_ID = CLASS_ID::HAS_PARAMETERS_IF;
|
||||
@ -32,13 +47,11 @@ public:
|
||||
return (domainId << 24) + (parameterId << 8) + index;
|
||||
}
|
||||
|
||||
virtual ~HasParametersIF() {
|
||||
}
|
||||
virtual ~HasParametersIF() {}
|
||||
|
||||
/**
|
||||
* Always set parameter before checking newValues!
|
||||
*
|
||||
*
|
||||
* @param domainId
|
||||
* @param parameterId
|
||||
* @param parameterWrapper
|
||||
|
@ -26,7 +26,6 @@ ReturnValue_t ParameterHelper::handleParameterMessage(CommandMessage *message) {
|
||||
}
|
||||
break;
|
||||
case ParameterMessage::CMD_PARAMETER_LOAD: {
|
||||
|
||||
uint8_t domain = HasParametersIF::getDomain(
|
||||
ParameterMessage::getParameterId(message));
|
||||
uint16_t parameterId = HasParametersIF::getMatrixId(
|
||||
@ -34,12 +33,14 @@ ReturnValue_t ParameterHelper::handleParameterMessage(CommandMessage *message) {
|
||||
uint8_t index = HasParametersIF::getIndex(
|
||||
ParameterMessage::getParameterId(message));
|
||||
|
||||
const uint8_t *storedStream;
|
||||
size_t storedStreamSize;
|
||||
const uint8_t *storedStream = nullptr;
|
||||
size_t storedStreamSize = 0;
|
||||
result = storage->getData(
|
||||
ParameterMessage::getStoreId(message), &storedStream,
|
||||
&storedStreamSize);
|
||||
if (result != HasReturnvaluesIF::RETURN_OK) {
|
||||
sif::error << "ParameterHelper::handleParameterMessage: Getting"
|
||||
" store data failed for load command." << std::endl;
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -5,6 +5,12 @@
|
||||
#include <framework/parameters/ParameterMessage.h>
|
||||
#include <framework/parameters/ReceivesParameterMessagesIF.h>
|
||||
|
||||
/**
|
||||
* @brief Helper class to handle parameter messages
|
||||
* @details
|
||||
* This class simplfiies handling of parameter messages, which are sent
|
||||
* to a class which implements ReceivesParameterMessagesIF.
|
||||
*/
|
||||
class ParameterHelper {
|
||||
public:
|
||||
ParameterHelper(ReceivesParameterMessagesIF *owner);
|
||||
|
@ -1,20 +1,19 @@
|
||||
#include <framework/parameters/ParameterWrapper.h>
|
||||
|
||||
ParameterWrapper::ParameterWrapper() :
|
||||
pointsToStream(false), type(Type::UNKNOWN_TYPE), rows(0), columns(0), data(
|
||||
NULL), readonlyData(NULL) {
|
||||
pointsToStream(false), type(Type::UNKNOWN_TYPE) {
|
||||
}
|
||||
|
||||
ParameterWrapper::ParameterWrapper(Type type, uint8_t rows, uint8_t columns,
|
||||
void *data) :
|
||||
pointsToStream(false), type(type), rows(rows), columns(columns), data(
|
||||
data), readonlyData(data) {
|
||||
pointsToStream(false), type(type), rows(rows), columns(columns),
|
||||
data(data), readonlyData(data) {
|
||||
}
|
||||
|
||||
ParameterWrapper::ParameterWrapper(Type type, uint8_t rows, uint8_t columns,
|
||||
const void *data) :
|
||||
pointsToStream(false), type(type), rows(rows), columns(columns), data(
|
||||
NULL), readonlyData(data) {
|
||||
pointsToStream(false), type(type), rows(rows), columns(columns),
|
||||
data(nullptr), readonlyData(data) {
|
||||
}
|
||||
|
||||
ParameterWrapper::~ParameterWrapper() {
|
||||
@ -266,15 +265,14 @@ ReturnValue_t ParameterWrapper::copyFrom(const ParameterWrapper *from,
|
||||
result = UNKNOW_DATATYPE;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
//need a type to do arithmetic
|
||||
uint8_t *toDataWithType = (uint8_t*) data;
|
||||
uint8_t* typedData = static_cast<uint8_t*>(data);
|
||||
for (uint8_t fromRow = 0; fromRow < from->rows; fromRow++) {
|
||||
memcpy(
|
||||
toDataWithType
|
||||
+ (((startingRow + fromRow) * columns)
|
||||
+ startingColumn) * typeSize,
|
||||
from->readonlyData, typeSize * from->columns);
|
||||
uint8_t offset = (((startingRow + fromRow) * columns) + startingColumn) * typeSize;
|
||||
std::memcpy(typedData + offset, from->readonlyData,
|
||||
typeSize * from->columns);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
#ifndef PARAMETERWRAPPER_H_
|
||||
#define PARAMETERWRAPPER_H_
|
||||
#ifndef FRAMEWORK_PARAMETERS_PARAMETERWRAPPER_H_
|
||||
#define FRAMEWORK_PARAMETERS_PARAMETERWRAPPER_H_
|
||||
|
||||
#include <framework/returnvalues/HasReturnvaluesIF.h>
|
||||
#include <framework/serialize/SerializeAdapter.h>
|
||||
@ -7,6 +7,10 @@
|
||||
#include <stddef.h>
|
||||
#include <framework/globalfunctions/Type.h>
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* @details
|
||||
*/
|
||||
class ParameterWrapper: public SerializeIF {
|
||||
friend class DataPoolParameterWrapper;
|
||||
public:
|
||||
@ -36,32 +40,21 @@ public:
|
||||
virtual ReturnValue_t deSerialize(const uint8_t** buffer, size_t* size,
|
||||
Endianness streamEndianness, uint16_t startWritingAtIndex = 0);
|
||||
|
||||
/**
|
||||
* Get a specific parameter value by supplying the row and the column.
|
||||
* @tparam T Type of target data
|
||||
* @param value [out] Pointer to storage location
|
||||
* @param row
|
||||
* @param column
|
||||
* @return
|
||||
* -@c RETURN_OK if element was retrieved successfully
|
||||
* -@c NOT_SET data has not been set yet
|
||||
* -@c DATATYPE_MISSMATCH Invalid supplied type
|
||||
* -@c OUT_OF_BOUNDS Invalid row and/or column.
|
||||
*/
|
||||
template<typename T>
|
||||
ReturnValue_t getElement(T *value, uint8_t row = 0, uint8_t column = 0) const {
|
||||
if (readonlyData == NULL){
|
||||
return NOT_SET;
|
||||
}
|
||||
|
||||
if (PodTypeConversion<T>::type != type) {
|
||||
return DATATYPE_MISSMATCH;
|
||||
}
|
||||
|
||||
if ((row >= rows) || (column >= columns)) {
|
||||
return OUT_OF_BOUNDS;
|
||||
}
|
||||
|
||||
if (pointsToStream) {
|
||||
const uint8_t *streamWithtype = (const uint8_t *) readonlyData;
|
||||
streamWithtype += (row * columns + column) * type.getSize();
|
||||
int32_t size = type.getSize();
|
||||
return SerializeAdapter::deSerialize(value, &streamWithtype,
|
||||
&size, true);
|
||||
} else {
|
||||
const T *dataWithType = (const T *) readonlyData;
|
||||
*value = dataWithType[row * columns + column];
|
||||
return HasReturnvaluesIF::RETURN_OK;
|
||||
}
|
||||
}
|
||||
ReturnValue_t getElement(T *value, uint8_t row = 0,
|
||||
uint8_t column = 0) const;
|
||||
|
||||
template<typename T>
|
||||
void set(T *data, uint8_t rows, uint8_t columns) {
|
||||
@ -111,21 +104,22 @@ public:
|
||||
void setMatrix(const T& member) {
|
||||
this->set(member[0], sizeof(member)/sizeof(member[0]), sizeof(member[0])/sizeof(member[0][0]));
|
||||
}
|
||||
|
||||
ReturnValue_t set(const uint8_t *stream, size_t streamSize,
|
||||
const uint8_t **remainingStream = NULL, size_t *remainingSize =
|
||||
NULL);
|
||||
const uint8_t **remainingStream = nullptr,
|
||||
size_t *remainingSize = nullptr);
|
||||
|
||||
ReturnValue_t copyFrom(const ParameterWrapper *from,
|
||||
uint16_t startWritingAtIndex);
|
||||
|
||||
private:
|
||||
bool pointsToStream;
|
||||
bool pointsToStream = false;
|
||||
|
||||
Type type;
|
||||
uint8_t rows;
|
||||
uint8_t columns;
|
||||
void *data;
|
||||
const void *readonlyData;
|
||||
uint8_t rows = 0;
|
||||
uint8_t columns = 0;
|
||||
void *data = nullptr;
|
||||
const void *readonlyData = nullptr;
|
||||
|
||||
template<typename T>
|
||||
ReturnValue_t serializeData(uint8_t** buffer, size_t* size,
|
||||
@ -136,4 +130,33 @@ private:
|
||||
const void *from, uint8_t fromRows, uint8_t fromColumns);
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
inline ReturnValue_t ParameterWrapper::getElement(T *value, uint8_t row,
|
||||
uint8_t column) const {
|
||||
if (readonlyData == nullptr){
|
||||
return NOT_SET;
|
||||
}
|
||||
|
||||
if (PodTypeConversion<T>::type != type) {
|
||||
return DATATYPE_MISSMATCH;
|
||||
}
|
||||
|
||||
if ((row >= rows) or (column >= columns)) {
|
||||
return OUT_OF_BOUNDS;
|
||||
}
|
||||
|
||||
if (pointsToStream) {
|
||||
const uint8_t *streamWithType = static_cast<const uint8_t*>(readonlyData);
|
||||
streamWithType += (row * columns + column) * type.getSize();
|
||||
int32_t size = type.getSize();
|
||||
return SerializeAdapter::deSerialize(value, &streamWithType,
|
||||
&size, true);
|
||||
}
|
||||
else {
|
||||
const T *dataWithType = static_cast<const T*>(readonlyData);
|
||||
*value = dataWithType[row * columns + column];
|
||||
return HasReturnvaluesIF::RETURN_OK;
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* PARAMETERWRAPPER_H_ */
|
||||
|
@ -1,22 +1,22 @@
|
||||
/**
|
||||
* @defgroup spacepackets PUS Packet Definitions
|
||||
* This group contains all implemented TM or TM packages that are sent to
|
||||
* or sent by the OBC.They are exported later to display
|
||||
* packet structures in Mission Information Base (MIB).
|
||||
*/
|
||||
|
||||
#ifndef MISSION_PUS_SERVICEPACKETS_SERVICE1PACKETS_H_
|
||||
#define MISSION_PUS_SERVICEPACKETS_SERVICE1PACKETS_H_
|
||||
|
||||
#include <framework/serialize/SerializeAdapter.h>
|
||||
#include <framework/tmtcservices/VerificationCodes.h>
|
||||
|
||||
/**
|
||||
* @defgroup spacepackets PUS Packet Definitions
|
||||
* This group contains all implemented TM or TM packages that are sent to
|
||||
* or sent by the OBC.They are exported later to display
|
||||
* packet structures in Mission Information Base (MIB).
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief FailureReport class to serialize a failure report
|
||||
* @brief Subservice 1, 3, 5, 7
|
||||
* @ingroup spacepackets
|
||||
*/
|
||||
class FailureReport: public SerializeIF { //!< [EXPORT] : [SUBSERVICE] 1, 3, 5, 7
|
||||
class FailureReport: public SerializeIF { //!< [EXPORT] : [SUBSERVICE] 2, 4, 6, 8
|
||||
public:
|
||||
FailureReport(uint8_t failureSubtype_, uint16_t packetId_,
|
||||
uint16_t packetSequenceControl_, uint8_t stepNumber_,
|
||||
@ -111,7 +111,7 @@ private:
|
||||
* @brief Subservices 2, 4, 6, 8
|
||||
* @ingroup spacepackets
|
||||
*/
|
||||
class SuccessReport: public SerializeIF { //!< [EXPORT] : [SUBSERVICE] 2, 4, 6, 8
|
||||
class SuccessReport: public SerializeIF { //!< [EXPORT] : [SUBSERVICE] 1, 3, 5, 7
|
||||
public:
|
||||
SuccessReport(uint8_t subtype_, uint16_t packetId_,
|
||||
uint16_t packetSequenceControl_,uint8_t stepNumber_) :
|
||||
|
@ -78,9 +78,9 @@ int ServiceInterfaceBuffer::sync(void) {
|
||||
}
|
||||
|
||||
size_t preambleSize = 0;
|
||||
auto preamble = getPreamble(&preambleSize);
|
||||
std::string* preamble = getPreamble(&preambleSize);
|
||||
// Write logMessage and time
|
||||
this->putChars(preamble.data(), preamble.data() + preambleSize);
|
||||
this->putChars(preamble->data(), preamble->data() + preambleSize);
|
||||
// Handle output
|
||||
this->putChars(pbase(), pptr());
|
||||
// This tells that buffer is empty again
|
||||
@ -92,7 +92,7 @@ bool ServiceInterfaceBuffer::isBuffered() const {
|
||||
return buffered;
|
||||
}
|
||||
|
||||
std::string ServiceInterfaceBuffer::getPreamble(size_t * preambleSize) {
|
||||
std::string* ServiceInterfaceBuffer::getPreamble(size_t * preambleSize) {
|
||||
Clock::TimeOfDay_t loggerTime;
|
||||
Clock::getDateAndTime(&loggerTime);
|
||||
size_t currentSize = 0;
|
||||
@ -110,18 +110,18 @@ std::string ServiceInterfaceBuffer::getPreamble(size_t * preambleSize) {
|
||||
loggerTime.usecond /1000);
|
||||
if(charCount < 0) {
|
||||
printf("ServiceInterfaceBuffer: Failure parsing preamble\r\n");
|
||||
return "";
|
||||
return &preamble;
|
||||
}
|
||||
if(charCount > MAX_PREAMBLE_SIZE) {
|
||||
printf("ServiceInterfaceBuffer: Char count too large for maximum "
|
||||
"preamble size");
|
||||
return "";
|
||||
return &preamble;
|
||||
}
|
||||
currentSize += charCount;
|
||||
if(preambleSize != nullptr) {
|
||||
*preambleSize = currentSize;
|
||||
}
|
||||
return preamble;
|
||||
return &preamble;
|
||||
}
|
||||
|
||||
|
||||
|
@ -60,7 +60,7 @@ private:
|
||||
//! In this function, the characters are parsed.
|
||||
void putChars(char const* begin, char const* end);
|
||||
|
||||
std::string getPreamble(size_t * preambleSize = nullptr);
|
||||
std::string* getPreamble(size_t * preambleSize = nullptr);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -9,7 +9,7 @@ void ServiceInterfaceStream::setActive( bool myActive) {
|
||||
this->streambuf.isActive = myActive;
|
||||
}
|
||||
|
||||
std::string ServiceInterfaceStream::getPreamble() {
|
||||
std::string* ServiceInterfaceStream::getPreamble() {
|
||||
return streambuf.getPreamble();
|
||||
}
|
||||
|
||||
|
@ -33,7 +33,7 @@ public:
|
||||
* the unbuffered mode.
|
||||
* @return Preamle consisting of log message and timestamp.
|
||||
*/
|
||||
std::string getPreamble();
|
||||
std::string* getPreamble();
|
||||
|
||||
/**
|
||||
* This prints an error with a preamble. Useful if using the unbuffered
|
||||
|
@ -21,7 +21,8 @@ inline PoolManager<NUMBER_OF_POOLS>::~PoolManager(void) {
|
||||
template<uint8_t NUMBER_OF_POOLS>
|
||||
inline ReturnValue_t PoolManager<NUMBER_OF_POOLS>::reserveSpace(
|
||||
const uint32_t size, store_address_t* address, bool ignoreFault) {
|
||||
MutexHelper mutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING,
|
||||
mutexTimeout);
|
||||
ReturnValue_t status = LocalPool<NUMBER_OF_POOLS>::reserveSpace(size,
|
||||
address,ignoreFault);
|
||||
return status;
|
||||
@ -33,7 +34,8 @@ inline ReturnValue_t PoolManager<NUMBER_OF_POOLS>::deleteData(
|
||||
// debug << "PoolManager( " << translateObject(getObjectId()) <<
|
||||
// " )::deleteData from store " << packet_id.pool_index <<
|
||||
// ". id is "<< packet_id.packet_index << std::endl;
|
||||
MutexHelper mutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING,
|
||||
mutexTimeout);
|
||||
ReturnValue_t status = LocalPool<NUMBER_OF_POOLS>::deleteData(packet_id);
|
||||
return status;
|
||||
}
|
||||
@ -41,7 +43,8 @@ inline ReturnValue_t PoolManager<NUMBER_OF_POOLS>::deleteData(
|
||||
template<uint8_t NUMBER_OF_POOLS>
|
||||
inline ReturnValue_t PoolManager<NUMBER_OF_POOLS>::deleteData(uint8_t* buffer,
|
||||
size_t size, store_address_t* storeId) {
|
||||
MutexHelper mutexHelper(mutex, mutexTimeout);
|
||||
MutexHelper mutexHelper(mutex, MutexIF::TimeoutType::WAITING,
|
||||
mutexTimeout);
|
||||
ReturnValue_t status = LocalPool<NUMBER_OF_POOLS>::deleteData(buffer,
|
||||
size, storeId);
|
||||
return status;
|
||||
|
@ -5,9 +5,9 @@
|
||||
|
||||
SubsystemBase::SubsystemBase(object_id_t setObjectId, object_id_t parent,
|
||||
Mode_t initialMode, uint16_t commandQueueDepth) :
|
||||
SystemObject(setObjectId), mode(initialMode), submode(SUBMODE_NONE), childrenChangedMode(
|
||||
false), commandsOutstanding(0), commandQueue(NULL), healthHelper(this,
|
||||
setObjectId), modeHelper(this), parentId(parent) {
|
||||
SystemObject(setObjectId), mode(initialMode), submode(SUBMODE_NONE),
|
||||
childrenChangedMode(false), commandsOutstanding(0), commandQueue(NULL),
|
||||
healthHelper(this, setObjectId), modeHelper(this), parentId(parent) {
|
||||
commandQueue = QueueFactory::instance()->createMessageQueue(commandQueueDepth,
|
||||
MessageQueueMessage::MAX_MESSAGE_SIZE);
|
||||
}
|
||||
@ -23,8 +23,8 @@ ReturnValue_t SubsystemBase::registerChild(object_id_t objectId) {
|
||||
HasModesIF *child = objectManager->get<HasModesIF>(objectId);
|
||||
//This is a rather ugly hack to have the changedHealth info for all children available. (needed for FOGs).
|
||||
HasHealthIF* healthChild = objectManager->get<HasHealthIF>(objectId);
|
||||
if (child == NULL) {
|
||||
if (healthChild == NULL) {
|
||||
if (child == nullptr) {
|
||||
if (healthChild == nullptr) {
|
||||
return CHILD_DOESNT_HAVE_MODES;
|
||||
} else {
|
||||
info.commandQueue = healthChild->getCommandQueue();
|
||||
@ -76,14 +76,15 @@ ReturnValue_t SubsystemBase::checkStateAgainstTable(
|
||||
return RETURN_OK;
|
||||
}
|
||||
|
||||
void SubsystemBase::executeTable(HybridIterator<ModeListEntry> tableIter, Submode_t targetSubmode) {
|
||||
void SubsystemBase::executeTable(HybridIterator<ModeListEntry> tableIter,
|
||||
Submode_t targetSubmode) {
|
||||
CommandMessage command;
|
||||
|
||||
std::map<object_id_t, ChildInfo>::iterator iter;
|
||||
|
||||
commandsOutstanding = 0;
|
||||
|
||||
for (; tableIter.value != NULL; ++tableIter) {
|
||||
for (; tableIter.value != nullptr; ++tableIter) {
|
||||
object_id_t object = tableIter.value->getObject();
|
||||
if ((iter = childrenMap.find(object)) == childrenMap.end()) {
|
||||
//illegal table entry, should only happen due to misconfigured mode table
|
||||
|
@ -36,8 +36,7 @@ public:
|
||||
* to the component.
|
||||
* @return
|
||||
*/
|
||||
virtual ReturnValue_t addComponent(object_id_t object,
|
||||
bool setTaskIF = true) {
|
||||
virtual ReturnValue_t addComponent(object_id_t object) {
|
||||
return HasReturnvaluesIF::RETURN_FAILED;
|
||||
};
|
||||
|
||||
|
@ -1,7 +1,6 @@
|
||||
#ifndef FRAMEWORK_TASKS_TYPEDEF_H_
|
||||
#define FRAMEWORK_TASKS_TYPEDEF_H_
|
||||
|
||||
//TODO more generic?
|
||||
typedef const char* TaskName;
|
||||
typedef uint8_t TaskPriority;
|
||||
typedef size_t TaskStackSize;
|
||||
|
@ -126,11 +126,11 @@ void CommandingServiceBase::handleCommandMessage(CommandMessage* reply) {
|
||||
&nextCommand, iter->objectId, &isStep);
|
||||
|
||||
/* If the child implementation does not implement special handling for
|
||||
* rejected replies (RETURN_FAILED is returned), a failure verification
|
||||
* will be generated with the reason as the return code and the initial
|
||||
* command as failure parameter 1 */
|
||||
if(reply->getCommand() == CommandMessage::REPLY_REJECTED and
|
||||
result == RETURN_FAILED) {
|
||||
* rejected replies (RETURN_FAILED or INVALID_REPLY is returned), a
|
||||
* failure verification will be generated with the reason as the
|
||||
* return code and the initial command as failure parameter 1 */
|
||||
if((reply->getCommand() == CommandMessage::REPLY_REJECTED) and
|
||||
(result == RETURN_FAILED or result == INVALID_REPLY)) {
|
||||
result = reply->getReplyRejectedReason();
|
||||
failureParameter1 = iter->command;
|
||||
}
|
||||
@ -230,8 +230,8 @@ void CommandingServiceBase::handleRequestQueue() {
|
||||
address = message.getStorageId();
|
||||
packet.setStoreAddress(address);
|
||||
|
||||
if (packet.getSubService() == 0
|
||||
or isValidSubservice(packet.getSubService()) != RETURN_OK) {
|
||||
if ((packet.getSubService() == 0)
|
||||
or (isValidSubservice(packet.getSubService()) != RETURN_OK)) {
|
||||
rejectPacket(TC_VERIFY::START_FAILURE, &packet, INVALID_SUBSERVICE);
|
||||
continue;
|
||||
}
|
||||
|
@ -87,7 +87,7 @@ public:
|
||||
* @param opCode is unused here at the moment
|
||||
* @return RETURN_OK
|
||||
*/
|
||||
virtual ReturnValue_t performOperation(uint8_t opCode);
|
||||
virtual ReturnValue_t performOperation(uint8_t opCode) override;
|
||||
|
||||
virtual uint16_t getIdentifier();
|
||||
|
||||
@ -116,7 +116,7 @@ public:
|
||||
* Used to setup the reference of the task, that executes this component
|
||||
* @param task Pointer to the taskIF of this task
|
||||
*/
|
||||
virtual void setTaskIF(PeriodicTaskIF* task);
|
||||
virtual void setTaskIF(PeriodicTaskIF* task) override;
|
||||
|
||||
protected:
|
||||
/**
|
||||
@ -173,9 +173,7 @@ protected:
|
||||
* This function is implemented by child services to specify how replies
|
||||
* to a command from another software component are handled.
|
||||
* @param reply
|
||||
* This is the reply which can be accessed via the command message
|
||||
* interface. The internal message pointer can be passed to different
|
||||
* command message implementations (see CommandMessageIF)
|
||||
* This is the reply in form of a generic read-only command message.
|
||||
* @param previousCommand
|
||||
* Command_t of related command
|
||||
* @param state [out/in]
|
||||
@ -189,10 +187,11 @@ protected:
|
||||
* - @c RETURN_OK, @c EXECUTION_COMPLETE or @c NO_STEP_MESSAGE to
|
||||
* generate TC verification success
|
||||
* - @c INVALID_REPLY Calls handleUnrequestedReply
|
||||
* - Anything else triggers a TC verification failure. If RETURN_FAILED
|
||||
* is returned and the command ID is CommandMessage::REPLY_REJECTED,
|
||||
* a failure verification message with the reason as the error parameter
|
||||
* and the initial command as failure parameter 1.
|
||||
* - Anything else triggers a TC verification failure. If RETURN_FAILED or
|
||||
* INVALID_REPLY is returned and the command ID is
|
||||
* CommandMessage::REPLY_REJECTED, a failure verification message with
|
||||
* the reason as the error parameter and the initial command as
|
||||
* failure parameter 1 is generated.
|
||||
*/
|
||||
virtual ReturnValue_t handleReply(const CommandMessage* reply,
|
||||
Command_t previousCommand, uint32_t *state,
|
||||
|
Loading…
Reference in New Issue
Block a user