Skip to content
Snippets Groups Projects
Commit 6fa95cd7 authored by Tomasz Kozak's avatar Tomasz Kozak
Browse files

Start of implementation for issue #80

parent 8ab22387
No related branches found
No related tags found
No related merge requests found
...@@ -19,8 +19,8 @@ namespace ChimeraTK { ...@@ -19,8 +19,8 @@ namespace ChimeraTK {
class ExceptionHandlingDecorator : public ChimeraTK::NDRegisterAccessorDecorator<UserType> { class ExceptionHandlingDecorator : public ChimeraTK::NDRegisterAccessorDecorator<UserType> {
public: public:
ExceptionHandlingDecorator( ExceptionHandlingDecorator(
boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>> accessor, DeviceModule& devMod) boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>> accessor, DeviceModule& devMod, EntityOwner* owner)
: ChimeraTK::NDRegisterAccessorDecorator<UserType>(accessor), dm(devMod) {} : ChimeraTK::NDRegisterAccessorDecorator<UserType>(accessor), deviceModule(devMod), _owner(owner) {}
bool doWriteTransfer(ChimeraTK::VersionNumber versionNumber = {}) override; bool doWriteTransfer(ChimeraTK::VersionNumber versionNumber = {}) override;
...@@ -48,9 +48,11 @@ namespace ChimeraTK { ...@@ -48,9 +48,11 @@ namespace ChimeraTK {
void interrupt() override; void interrupt() override;
protected: protected:
DeviceModule& dm; DeviceModule& deviceModule;
DataValidity validity{DataValidity::ok}; DataValidity validity{DataValidity::ok};
bool genericTransfer(std::function<bool(void)> callable, bool invalidateOnFailure = true); bool genericTransfer(std::function<bool(void)> callable, bool invalidateOnFailure = true);
void setOwnerValidity(DataValidity newValidity);
EntityOwner* _owner;
}; };
DECLARE_TEMPLATE_FOR_CHIMERATK_USER_TYPES(ExceptionHandlingDecorator); DECLARE_TEMPLATE_FOR_CHIMERATK_USER_TYPES(ExceptionHandlingDecorator);
......
...@@ -358,7 +358,7 @@ boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>> Application::createDe ...@@ -358,7 +358,7 @@ boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>> Application::createDe
assert(devmod != nullptr); assert(devmod != nullptr);
// decorate the accessor with a ExceptionHandlingDecorator and return it // decorate the accessor with a ExceptionHandlingDecorator and return it
return boost::make_shared<ExceptionHandlingDecorator<UserType>>(accessor, *devmod); return boost::make_shared<ExceptionHandlingDecorator<UserType>>(accessor, *devmod, nullptr);
} }
/*********************************************************************************************************************/ /*********************************************************************************************************************/
...@@ -802,7 +802,7 @@ void Application::typedMakeConnection(VariableNetwork& network) { ...@@ -802,7 +802,7 @@ void Application::typedMakeConnection(VariableNetwork& network) {
// In case we have one or more trigger receivers among our consumers, we // In case we have one or more trigger receivers among our consumers, we
// produce one consuming application variable for each device. Later this will create a TriggerFanOut for // produce one consuming application variable for each device. Later this will create a TriggerFanOut for
// each trigger consimer, i.e. one per device so one blocking device does not affect the others. // each trigger consumer, i.e. one per device so one blocking device does not affect the others.
/** Map of deviceAliases to their corresponding TriggerFanOuts. */ /** Map of deviceAliases to their corresponding TriggerFanOuts. */
std::map<std::string, boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>>> triggerFanOuts; std::map<std::string, boost::shared_ptr<ChimeraTK::NDRegisterAccessor<UserType>>> triggerFanOuts;
......
...@@ -7,33 +7,49 @@ constexpr useconds_t DeviceOpenTimeout = 500; ...@@ -7,33 +7,49 @@ constexpr useconds_t DeviceOpenTimeout = 500;
namespace ChimeraTK { namespace ChimeraTK {
template<typename UserType>
void ExceptionHandlingDecorator<UserType>::setOwnerValidity(DataValidity newValidity) {
if (newValidity != validity) {
validity = newValidity;
if (!_owner) return; // hack to deal with null ptr until it filled correctly
if (newValidity == DataValidity::faulty) {
_owner->incrementDataFaultCounter();
} else {
_owner->decrementDataFaultCounter();
}
}
}
template<typename UserType> template<typename UserType>
bool ExceptionHandlingDecorator<UserType>::genericTransfer( bool ExceptionHandlingDecorator<UserType>::genericTransfer(
std::function<bool(void)> callable, bool invalidateOnFailure) { std::function<bool(void)> callable, bool updateOwnerValidityFlag) {
std::function<void()> invalidateData{};
if(invalidateOnFailure) { std::function<void(DataValidity)> setOwnerValidityFunction{};
invalidateData = [=]() { setDataValidity(DataValidity::faulty); }; if(updateOwnerValidityFlag) {
} setOwnerValidityFunction = std::bind(&ExceptionHandlingDecorator<UserType>::setOwnerValidity, this, std::placeholders::_1);
}
else { else {
invalidateData = []() {}; // do nothing if user does setOwnerValidityFunction = [](DataValidity) {}; // do nothing if user does
// not want to invalidate data. // not want to invalidate data.
} }
while(true) { while(true) {
try { try {
if(!dm.device.isOpened()) { if(!deviceModule.device.isOpened()) {
invalidateData(); setOwnerValidityFunction(DataValidity::faulty);
Application::getInstance().testableModeUnlock("waitForDeviceOpen"); Application::getInstance().testableModeUnlock("waitForDeviceOpen");
boost::this_thread::sleep(boost::posix_time::millisec(DeviceOpenTimeout)); boost::this_thread::sleep(boost::posix_time::millisec(DeviceOpenTimeout));
Application::getInstance().testableModeLock("waitForDeviceOpen"); Application::getInstance().testableModeLock("waitForDeviceOpen");
continue; continue;
} }
auto retval = callable(); auto retval = callable();
setDataValidity(DataValidity::ok); auto delegatedValidity = ChimeraTK::NDRegisterAccessorDecorator<UserType>::dataValidity();
setOwnerValidityFunction(delegatedValidity);
return retval; return retval;
} }
catch(ChimeraTK::runtime_error& e) { catch(ChimeraTK::runtime_error& e) {
invalidateData(); setOwnerValidityFunction(DataValidity::faulty);
dm.reportException(e.what()); deviceModule.reportException(e.what());
} }
} }
} }
...@@ -127,7 +143,7 @@ namespace ChimeraTK { ...@@ -127,7 +143,7 @@ namespace ChimeraTK {
template<typename UserType> template<typename UserType>
void ExceptionHandlingDecorator<UserType>::interrupt() { void ExceptionHandlingDecorator<UserType>::interrupt() {
// notify the condition variable waiting in reportException of the genericTransfer // notify the condition variable waiting in reportException of the genericTransfer
dm.notify(); deviceModule.notify();
ChimeraTK::NDRegisterAccessorDecorator<UserType>::interrupt(); ChimeraTK::NDRegisterAccessorDecorator<UserType>::interrupt();
} }
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment