Newer
Older
Martin Christoph Hierholzer
committed
/*
* ApplicationModule.h
*
* Created on: Jun 10, 2016
* Author: Martin Hierholzer
*/
#ifndef CHIMERATK_APPLICATION_MODULE_H
#define CHIMERATK_APPLICATION_MODULE_H
Martin Christoph Hierholzer
committed
#include <list>
#include <boost/thread.hpp>
Martin Christoph Hierholzer
committed
#include "ModuleImpl.h"
Martin Killenberg
committed
#include "Application.h"
Martin Killenberg
committed
#include "CircularDependencyDetectionRecursionStopper.h"
Martin Christoph Hierholzer
committed
Martin Christoph Hierholzer
committed
namespace ChimeraTK {
Martin Christoph Hierholzer
committed
class Application;
class ModuleGroup;
class ApplicationModule : public ModuleImpl {
public:
Martin Christoph Hierholzer
committed
/** Constructor: Create ApplicationModule by the given name with the given description and register it with its
* owner. The hierarchy will be modified according to the hierarchyModifier (when VirtualModules are created e.g.
* in findTag()). The specified list of tags will be added to all elements directly or indirectly owned by this
* instance.
Martin Christoph Hierholzer
committed
* Note: ApplicationModules may only be owned by ModuleGroups or Applications. */
ApplicationModule(EntityOwner* owner, const std::string& name, const std::string& description,
Martin Christoph Hierholzer
committed
HierarchyModifier hierarchyModifier = HierarchyModifier::none,
const std::unordered_set<std::string>& tags = {});
/** Deprecated form of the constructor. Use the new signature instead. */
ApplicationModule(EntityOwner* owner, const std::string& name, const std::string& description,
bool eliminateHierarchy, const std::unordered_set<std::string>& tags = {});
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
/** Default constructor: Allows late initialisation of modules (e.g. when
* creating arrays of modules).
*
* This construtor also has to be here to mitigate a bug in gcc. It is needed
* to allow constructor inheritance of modules owning other modules. This
* constructor will not actually be called then. See this bug report:
* https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67054 */
ApplicationModule() {}
/** Move operation with the move constructor */
ApplicationModule(ApplicationModule&& other) { operator=(std::move(other)); }
/** Move assignment */
ApplicationModule& operator=(ApplicationModule&& other) {
assert(!moduleThread.joinable()); // if the thread is already running,
// moving is no longer allowed!
ModuleImpl::operator=(std::move(other));
return *this;
}
/** Destructor */
virtual ~ApplicationModule();
/** To be implemented by the user: function called in a separate thread
* executing the main loop of the module */
virtual void mainLoop() = 0;
void run() override;
void terminate() override;
ModuleType getModuleType() const override { return ModuleType::ApplicationModule; }
VersionNumber getCurrentVersionNumber() const override { return currentVersionNumber; }
Martin Killenberg
committed
DataValidity getDataValidity() const override;
Martin Christoph Hierholzer
committed
void incrementDataFaultCounter() override;
void decrementDataFaultCounter() override;
Martin Christoph Hierholzer
committed
Martin Christoph Hierholzer
committed
void setCurrentVersionNumber(VersionNumber versionNumber) override {
if(versionNumber > currentVersionNumber) currentVersionNumber = versionNumber;
}
Martin Killenberg
committed
std::list<EntityOwner*> getInputModulesRecursively(std::list<EntityOwner*> startList) override;
Martin Killenberg
committed
size_t getCircularNetworkHash() override;
/** Set the ID of the circular dependency network. This function can be called multiple times and throws if the
* value is not identical.
*/
void setCircularNetworkHash(size_t circularNetworkHash);
protected:
/** Wrapper around mainLoop(), to execute additional tasks in the thread
* before entering the main loop */
void mainLoopWrapper();
/** The thread executing mainLoop() */
boost::thread moduleThread;
/** Version number of last push-type read operation - will be passed on to any
* write operations */
Martin Christoph Hierholzer
committed
VersionNumber currentVersionNumber{nullptr};
Martin Christoph Hierholzer
committed
/**
* Number of inputs which report DataValidity::faulty.
* This is atomic to allow the InvalidityTracer module to access this information.
*/
std::atomic<size_t> dataFaultCounter{0};
Martin Killenberg
committed
/**
* Unique ID for the circular dependency network. 0 if the EntityOwner is not in a circular dependency network.
* Only write when in LifeCycleState::initialisation (so getDataValidity() is thread safe, required by
* InvalidityTracer).
*/
Martin Killenberg
committed
size_t _circularNetworkHash{0};
Martin Killenberg
committed
/** Helper needed to stop the recusion when detecting circular dependency networks.
* Only used in the setp phase.
*/
detail::CircularDependencyDetectionRecursionStopper _recursionStopper;
Martin Christoph Hierholzer
committed
} /* namespace ChimeraTK */
#endif /* CHIMERATK_APPLICATION_MODULE_H */