Browse Source

Refactored and sorted bitvector

Former-commit-id: 28ca00af50
tempestpy_adaptions
Mavo 9 years ago
parent
commit
0d3687cf5e
  1. 43
      src/builder/ExplicitDFTModelBuilder.cpp
  2. 8
      src/builder/ExplicitDFTModelBuilder.h
  3. 98
      src/storage/dft/DFT.cpp
  4. 115
      src/storage/dft/DFT.h
  5. 23
      src/storage/dft/DFTElements.h
  6. 72
      src/storage/dft/DFTState.cpp
  7. 16
      src/storage/dft/DFTState.h

43
src/builder/ExplicitDFTModelBuilder.cpp

@ -14,10 +14,51 @@ namespace storm {
// Intentionally left empty. // Intentionally left empty.
} }
template <typename ValueType>
ExplicitDFTModelBuilder<ValueType>::ExplicitDFTModelBuilder(storm::storage::DFT<ValueType> const& dft) : mDft(dft), mStates(((mDft.stateVectorSize() / 64) + 1) * 64, std::pow(2, mDft.nrBasicElements())) {
// stateSize is bound for size of bitvector
// 2^nrBE is upper bound for state space
// Find symmetries
// TODO activate
// Currently using hack to test
std::vector<std::vector<size_t>> symmetries;
std::vector<size_t> vecB;
std::vector<size_t> vecC;
std::vector<size_t> vecD;
if (false) {
for (size_t i = 0; i < mDft.nrElements(); ++i) {
std::string name = mDft.getElement(i)->name();
size_t id = mDft.getElement(i)->id();
if (boost::starts_with(name, "B")) {
vecB.push_back(id);
} else if (boost::starts_with(name, "C")) {
vecC.push_back(id);
} else if (boost::starts_with(name, "D")) {
vecD.push_back(id);
}
}
symmetries.push_back(vecB);
symmetries.push_back(vecC);
symmetries.push_back(vecD);
std::cout << "Found the following symmetries:" << std::endl;
for (auto const& symmetry : symmetries) {
for (auto const& elem : symmetry) {
std::cout << elem << " -> ";
}
std::cout << std::endl;
}
} else {
vecB.push_back(mDft.getTopLevelIndex());
}
mStateGenerationInfo = std::make_shared<storm::storage::DFTStateGenerationInfo>(mDft.buildStateGenerationInfo(vecB, symmetries));
}
template <typename ValueType> template <typename ValueType>
std::shared_ptr<storm::models::sparse::Model<ValueType>> ExplicitDFTModelBuilder<ValueType>::buildModel() { std::shared_ptr<storm::models::sparse::Model<ValueType>> ExplicitDFTModelBuilder<ValueType>::buildModel() {
// Initialize // Initialize
DFTStatePointer state = std::make_shared<storm::storage::DFTState<ValueType>>(mDft, newIndex++);
DFTStatePointer state = std::make_shared<storm::storage::DFTState<ValueType>>(mDft, *mStateGenerationInfo, newIndex++);
mStates.findOrAdd(state->status(), state); mStates.findOrAdd(state->status(), state);
std::queue<DFTStatePointer> stateQueue; std::queue<DFTStatePointer> stateQueue;

8
src/builder/ExplicitDFTModelBuilder.h

@ -44,15 +44,13 @@ namespace storm {
boost::optional<std::vector<boost::container::flat_set<uint_fast64_t>>> choiceLabeling; boost::optional<std::vector<boost::container::flat_set<uint_fast64_t>>> choiceLabeling;
}; };
storm::storage::DFT<ValueType> const &mDft;
storm::storage::DFT<ValueType> const& mDft;
std::shared_ptr<storm::storage::DFTStateGenerationInfo> mStateGenerationInfo;
storm::storage::BitVectorHashMap<DFTStatePointer> mStates; storm::storage::BitVectorHashMap<DFTStatePointer> mStates;
size_t newIndex = 0; size_t newIndex = 0;
public: public:
ExplicitDFTModelBuilder(storm::storage::DFT<ValueType> const &dft) : mDft(dft), mStates(((mDft.stateVectorSize() / 64) + 1) * 64, std::pow(2, mDft.nrBasicElements())) {
// stateSize is bound for size of bitvector
// 2^nrBE is upper bound for state space
}
ExplicitDFTModelBuilder(storm::storage::DFT<ValueType> const& dft);
std::shared_ptr<storm::models::sparse::Model<ValueType>> buildModel(); std::shared_ptr<storm::models::sparse::Model<ValueType>> buildModel();

98
src/storage/dft/DFT.cpp

@ -10,15 +10,18 @@ namespace storm {
namespace storage { namespace storage {
template<typename ValueType> template<typename ValueType>
DFT<ValueType>::DFT(DFTElementVector const& elements, DFTElementPointer const& tle) : mElements(elements), mTopLevelIndex(tle->id()), mNrOfBEs(0), mNrOfSpares(0)
{
DFT<ValueType>::DFT(DFTElementVector const& elements, DFTElementPointer const& tle) : mElements(elements), mNrOfBEs(0), mNrOfSpares(0), mTopLevelIndex(tle->id()) {
assert(elementIndicesCorrect()); assert(elementIndicesCorrect());
mUsageInfoBits = storm::utility::math::uint64_log2(mElements.size()-1)+1;
size_t stateIndex = 0;
size_t stateVectorIndex = 0;
std::set<size_t> tmpRepresentatives;
size_t usageInfoBits = storm::utility::math::uint64_log2(mElements.size()-1)+1;
size_t nrRepresentatives = 0;
for (auto& elem : mElements) { for (auto& elem : mElements) {
mIdToFailureIndex.push_back(stateIndex);
stateIndex += 2;
stateVectorIndex += 2;
if (isRepresentative(elem->id())) {
++nrRepresentatives;
}
if(elem->isBasicElement()) { if(elem->isBasicElement()) {
++mNrOfBEs; ++mNrOfBEs;
} }
@ -26,9 +29,7 @@ namespace storm {
++mNrOfSpares; ++mNrOfSpares;
bool firstChild = true; bool firstChild = true;
for(auto const& spareReprs : std::static_pointer_cast<DFTSpare<ValueType>>(elem)->children()) { for(auto const& spareReprs : std::static_pointer_cast<DFTSpare<ValueType>>(elem)->children()) {
if(mActivationIndex.count(spareReprs->id()) == 0) {
mActivationIndex[spareReprs->id()] = stateIndex++;
}
tmpRepresentatives.insert(spareReprs->id());
std::set<size_t> module = {spareReprs->id()}; std::set<size_t> module = {spareReprs->id()};
spareReprs->extendSpareModule(module); spareReprs->extendSpareModule(module);
std::vector<size_t> sparesAndBes; std::vector<size_t> sparesAndBes;
@ -44,14 +45,13 @@ namespace storm {
mSpareModules.insert(std::make_pair(spareReprs->id(), sparesAndBes)); mSpareModules.insert(std::make_pair(spareReprs->id(), sparesAndBes));
firstChild = false; firstChild = false;
} }
std::static_pointer_cast<DFTSpare<ValueType>>(elem)->setUseIndex(stateIndex);
mUsageIndex.insert(std::make_pair(elem->id(), stateIndex));
stateIndex += mUsageInfoBits;
stateVectorIndex += usageInfoBits;
} else if (elem->isDependency()) { } else if (elem->isDependency()) {
mDependencies.push_back(elem->id()); mDependencies.push_back(elem->id());
} }
} }
stateVectorIndex += tmpRepresentatives.size();
// For the top module, we assume, contrary to [Jun15], that we have all spare gates and basic elements which are not in another module. // For the top module, we assume, contrary to [Jun15], that we have all spare gates and basic elements which are not in another module.
std::set<size_t> topModuleSet; std::set<size_t> topModuleSet;
@ -69,10 +69,82 @@ namespace storm {
} }
mTopModule = std::vector<size_t>(topModuleSet.begin(), topModuleSet.end()); mTopModule = std::vector<size_t>(topModuleSet.begin(), topModuleSet.end());
mStateVectorSize = stateIndex;
std::cout << tmpRepresentatives.size() << ", " << nrRepresentatives << std::endl;
std::cout << stateVectorIndex << ", " << (nrElements() * 2 + mNrOfSpares * usageInfoBits + tmpRepresentatives.size()) << std::endl;
assert(tmpRepresentatives.size() == nrRepresentatives);
assert(stateVectorIndex == nrElements() * 2 + mNrOfSpares * usageInfoBits + tmpRepresentatives.size());
mStateVectorSize = stateVectorIndex;
}
template<typename ValueType>
DFTStateGenerationInfo DFT<ValueType>::buildStateGenerationInfo(std::vector<size_t> const& subTreeRoots, std::vector<std::vector<size_t>> const& symmetries) const {
// Use symmetry
// Collect all elements in the first subtree
// TODO make recursive to use for nested subtrees
DFTStateGenerationInfo generationInfo(nrElements());
// Perform DFS and insert all elements of subtree sequentially
size_t stateIndex = 0;
std::queue<size_t> visitQueue;
std::set<size_t> visited;
visitQueue.push(subTreeRoots[0]);
bool consideredDependencies = false;
while (true) {
while (!visitQueue.empty()) {
size_t id = visitQueue.front();
visitQueue.pop();
if (visited.count(id) == 1) {
// Already visited
continue;
}
visited.insert(id);
DFTElementPointer element = mElements[id];
// Insert children
if (element->isGate()) {
for (auto const& child : std::static_pointer_cast<DFTGate<ValueType>>(element)->children()) {
visitQueue.push(child->id());
}
}
// Reserve bits for element
generationInfo.addStateIndex(id, stateIndex);
stateIndex += 2;
if (isRepresentative(id)) {
generationInfo.addSpareActivationIndex(id, stateIndex);
++stateIndex;
}
if (element->isSpareGate()) {
generationInfo.addSpareUsageIndex(id, stateIndex);
stateIndex += generationInfo.usageInfoBits();
}
}
if (consideredDependencies) {
break;
} }
// Consider dependencies
for (size_t idDependency : getDependencies()) {
std::shared_ptr<DFTDependency<ValueType> const> dependency = getDependency(idDependency);
visitQueue.push(dependency->id());
visitQueue.push(dependency->triggerEvent()->id());
visitQueue.push(dependency->dependentEvent()->id());
}
consideredDependencies = true;
} }
assert(stateIndex = mStateVectorSize);
STORM_LOG_TRACE(generationInfo);
return generationInfo;
}
template<typename ValueType> template<typename ValueType>
std::string DFT<ValueType>::getElementsString() const { std::string DFT<ValueType>::getElementsString() const {

115
src/storage/dft/DFT.h

@ -34,6 +34,69 @@ namespace storm {
template<typename T> class DFTColouring; template<typename T> class DFTColouring;
class DFTStateGenerationInfo {
private:
const size_t mUsageInfoBits;
std::map<size_t, size_t> mSpareUsageIndex; // id spare -> index first bit in state
std::map<size_t, size_t> mSpareActivationIndex; // id spare representative -> index in state
std::vector<size_t> mIdToStateIndex; // id -> index first bit in state
public:
DFTStateGenerationInfo(size_t nrElements) : mUsageInfoBits(storm::utility::math::uint64_log2(nrElements-1)+1), mIdToStateIndex(nrElements) {
}
size_t usageInfoBits() const {
return mUsageInfoBits;
}
void addStateIndex(size_t id, size_t index) {
assert(id < mIdToStateIndex.size());
mIdToStateIndex[id] = index;
}
void addSpareActivationIndex(size_t id, size_t index) {
mSpareActivationIndex[id] = index;
}
void addSpareUsageIndex(size_t id, size_t index) {
mSpareUsageIndex[id] = index;
}
size_t getStateIndex(size_t id) const {
assert(id < mIdToStateIndex.size());
return mIdToStateIndex[id];
}
size_t getSpareUsageIndex(size_t id) const {
assert(mSpareUsageIndex.count(id) > 0);
return mSpareUsageIndex.at(id);
}
size_t getSpareActivationIndex(size_t id) const {
assert(mSpareActivationIndex.count(id) > 0);
return mSpareActivationIndex.at(id);
}
friend std::ostream& operator<<(std::ostream& os, DFTStateGenerationInfo const& info) {
os << "Id to state index:" << std::endl;
for (size_t id = 0; id < info.mIdToStateIndex.size(); ++id) {
os << id << " -> " << info.getStateIndex(id) << std::endl;
}
os << "Spare usage index with usage InfoBits of size " << info.mUsageInfoBits << ":" << std::endl;
for (auto pair : info.mSpareUsageIndex) {
os << pair.first << " -> " << pair.second << std::endl;
}
os << "Spare activation index:" << std::endl;
for (auto pair : info.mSpareActivationIndex) {
os << pair.first << " -> " << pair.second << std::endl;
}
return os;
}
};
/** /**
* Represents a Dynamic Fault Tree * Represents a Dynamic Fault Tree
*/ */
@ -52,19 +115,18 @@ namespace storm {
size_t mNrOfBEs; size_t mNrOfBEs;
size_t mNrOfSpares; size_t mNrOfSpares;
size_t mTopLevelIndex; size_t mTopLevelIndex;
size_t mUsageInfoBits;
size_t mStateVectorSize; size_t mStateVectorSize;
std::map<size_t, size_t> mActivationIndex;
std::map<size_t, std::vector<size_t>> mSpareModules; std::map<size_t, std::vector<size_t>> mSpareModules;
std::vector<size_t> mDependencies; std::vector<size_t> mDependencies;
std::vector<size_t> mTopModule; std::vector<size_t> mTopModule;
std::vector<size_t> mIdToFailureIndex;
std::map<size_t, size_t> mUsageIndex;
std::map<size_t, size_t> mRepresentants;
std::map<size_t, size_t> mRepresentants; // id element -> id representative
std::vector<std::vector<size_t>> mSymmetries;
public: public:
DFT(DFTElementVector const& elements, DFTElementPointer const& tle); DFT(DFTElementVector const& elements, DFTElementPointer const& tle);
DFTStateGenerationInfo buildStateGenerationInfo(std::vector<size_t> const& subTreeRoots, std::vector<std::vector<size_t>> const& symmetries) const;
size_t stateVectorSize() const { size_t stateVectorSize() const {
return mStateVectorSize; return mStateVectorSize;
} }
@ -77,34 +139,8 @@ namespace storm {
return mNrOfBEs; return mNrOfBEs;
} }
size_t usageInfoBits() const {
return mUsageInfoBits;
}
size_t usageIndex(size_t id) const {
assert(mUsageIndex.find(id) != mUsageIndex.end());
return mUsageIndex.find(id)->second;
}
size_t failureIndex(size_t id) const {
return mIdToFailureIndex[id];
}
void initializeUses(DFTState<ValueType>& state) const {
for(auto const& elem : mElements) {
if(elem->isSpareGate()) {
std::static_pointer_cast<DFTSpare<ValueType>>(elem)->initializeUses(state);
}
}
}
void initializeActivation(DFTState<ValueType>& state) const {
state.activate(mTopLevelIndex);
for(auto const& elem : mTopModule) {
if(mElements[elem]->isSpareGate()) {
propagateActivation(state, state.uses(elem));
}
}
size_t getTopLevelIndex() const {
return mTopLevelIndex;
} }
std::vector<size_t> getSpareIndices() const { std::vector<size_t> getSpareIndices() const {
@ -130,15 +166,6 @@ namespace storm {
return mDependencies; return mDependencies;
} }
void propagateActivation(DFTState<ValueType>& state, size_t representativeId) const {
state.activate(representativeId);
for(size_t id : module(representativeId)) {
if(mElements[id]->isSpareGate()) {
propagateActivation(state, state.uses(id));
}
}
}
std::vector<size_t> nonColdBEs() const { std::vector<size_t> nonColdBEs() const {
std::vector<size_t> result; std::vector<size_t> result;
for(DFTElementPointer elem : mElements) { for(DFTElementPointer elem : mElements) {
@ -170,10 +197,6 @@ namespace storm {
return getElement(index)->isDependency(); return getElement(index)->isDependency();
} }
// std::shared_ptr<DFTGate<ValueType> const> getGate(size_t index) const {
// return
// }
std::shared_ptr<DFTBE<ValueType> const> getBasicElement(size_t index) const { std::shared_ptr<DFTBE<ValueType> const> getBasicElement(size_t index) const {
assert(isBasicElement(index)); assert(isBasicElement(index));
return std::static_pointer_cast<DFTBE<ValueType> const>(mElements[index]); return std::static_pointer_cast<DFTBE<ValueType> const>(mElements[index]);

23
src/storage/dft/DFTElements.h

@ -898,10 +898,6 @@ namespace storm {
template<typename ValueType> template<typename ValueType>
class DFTSpare : public DFTGate<ValueType> { class DFTSpare : public DFTGate<ValueType> {
private:
size_t mUseIndex;
size_t mActiveIndex;
public: public:
DFTSpare(size_t id, std::string const& name, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children = {}) : DFTSpare(size_t id, std::string const& name, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children = {}) :
DFTGate<ValueType>(id, name, children) DFTGate<ValueType>(id, name, children)
@ -919,24 +915,11 @@ namespace storm {
return true; return true;
} }
void setUseIndex(size_t useIndex) {
mUseIndex = useIndex;
}
void setActiveIndex(size_t activeIndex) {
mActiveIndex = activeIndex;
}
void initializeUses(storm::storage::DFTState<ValueType>& state) {
assert(this->mChildren.size() > 0);
state.setUsesAtPosition(mUseIndex, this->mChildren[0]->id());
}
void checkFails(storm::storage::DFTState<ValueType>& state, DFTStateSpaceGenerationQueues<ValueType>& queues) const override { void checkFails(storm::storage::DFTState<ValueType>& state, DFTStateSpaceGenerationQueues<ValueType>& queues) const override {
if(state.isOperational(this->mId)) { if(state.isOperational(this->mId)) {
size_t uses = state.extractUses(mUseIndex);
size_t uses = state.uses(this->mId);
if(!state.isOperational(uses)) { if(!state.isOperational(uses)) {
bool claimingSuccessful = state.claimNew(this->mId, mUseIndex, uses, this->mChildren);
bool claimingSuccessful = state.claimNew(this->mId, uses, this->mChildren);
if(!claimingSuccessful) { if(!claimingSuccessful) {
this->fail(state, queues); this->fail(state, queues);
} }
@ -946,7 +929,7 @@ namespace storm {
void checkFailsafe(storm::storage::DFTState<ValueType>& state, DFTStateSpaceGenerationQueues<ValueType>& queues) const override { void checkFailsafe(storm::storage::DFTState<ValueType>& state, DFTStateSpaceGenerationQueues<ValueType>& queues) const override {
if(state.isOperational(this->mId)) { if(state.isOperational(this->mId)) {
if(state.isFailsafe(state.extractUses((mUseIndex)))) {
if(state.isFailsafe(state.uses(this->mId))) {
this->failsafe(state, queues); this->failsafe(state, queues);
this->childrenDontCare(state, queues); this->childrenDontCare(state, queues);
} }

72
src/storage/dft/DFTState.cpp

@ -6,10 +6,25 @@ namespace storm {
namespace storage { namespace storage {
template<typename ValueType> template<typename ValueType>
DFTState<ValueType>::DFTState(DFT<ValueType> const& dft, size_t id) : mStatus(dft.stateVectorSize()), mId(id), mDft(dft) {
DFTState<ValueType>::DFTState(DFT<ValueType> const& dft, DFTStateGenerationInfo const& stateGenerationInfo, size_t id) : mStatus(dft.stateVectorSize()), mId(id), mDft(dft), mStateGenerationInfo(stateGenerationInfo) {
mInactiveSpares = dft.getSpareIndices(); mInactiveSpares = dft.getSpareIndices();
dft.initializeUses(*this);
dft.initializeActivation(*this);
// Initialize uses
for(size_t id : mDft.getSpareIndices()) {
std::shared_ptr<DFTGate<ValueType> const> elem = mDft.getGate(id);
assert(elem->isSpareGate());
assert(elem->nrChildren() > 0);
this->setUses(id, elem->children()[0]->id());
}
// Initialize activation
this->activate(mDft.getTopLevelIndex());
for(auto const& id : mDft.module(mDft.getTopLevelIndex())) {
if(mDft.getElement(id)->isSpareGate()) {
propagateActivation(uses(id));
}
}
std::vector<size_t> alwaysActiveBEs = dft.nonColdBEs(); std::vector<size_t> alwaysActiveBEs = dft.nonColdBEs();
mIsCurrentlyFailableBE.insert(mIsCurrentlyFailableBE.end(), alwaysActiveBEs.begin(), alwaysActiveBEs.end()); mIsCurrentlyFailableBE.insert(mIsCurrentlyFailableBE.end(), alwaysActiveBEs.begin(), alwaysActiveBEs.end());
} }
@ -26,7 +41,7 @@ namespace storm {
template<typename ValueType> template<typename ValueType>
int DFTState<ValueType>::getElementStateInt(size_t id) const { int DFTState<ValueType>::getElementStateInt(size_t id) const {
return mStatus.getAsInt(mDft.failureIndex(id), 2);
return mStatus.getAsInt(mStateGenerationInfo.getStateIndex(id), 2);
} }
template<typename ValueType> template<typename ValueType>
@ -46,12 +61,12 @@ namespace storm {
template<typename ValueType> template<typename ValueType>
bool DFTState<ValueType>::hasFailed(size_t id) const { bool DFTState<ValueType>::hasFailed(size_t id) const {
return mStatus[mDft.failureIndex(id)];
return mStatus[mStateGenerationInfo.getStateIndex(id)];
} }
template<typename ValueType> template<typename ValueType>
bool DFTState<ValueType>::isFailsafe(size_t id) const { bool DFTState<ValueType>::isFailsafe(size_t id) const {
return mStatus[mDft.failureIndex(id)+1];
return mStatus[mStateGenerationInfo.getStateIndex(id)+1];
} }
template<typename ValueType> template<typename ValueType>
@ -66,38 +81,38 @@ namespace storm {
template<typename ValueType> template<typename ValueType>
bool DFTState<ValueType>::dependencySuccessful(size_t id) const { bool DFTState<ValueType>::dependencySuccessful(size_t id) const {
return mStatus[mDft.failureIndex(id)];
return mStatus[mStateGenerationInfo.getStateIndex(id)];
} }
template<typename ValueType> template<typename ValueType>
bool DFTState<ValueType>::dependencyUnsuccessful(size_t id) const { bool DFTState<ValueType>::dependencyUnsuccessful(size_t id) const {
return mStatus[mDft.failureIndex(id)+1];
return mStatus[mStateGenerationInfo.getStateIndex(id)+1];
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setFailed(size_t id) { void DFTState<ValueType>::setFailed(size_t id) {
mStatus.set(mDft.failureIndex(id));
mStatus.set(mStateGenerationInfo.getStateIndex(id));
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setFailsafe(size_t id) { void DFTState<ValueType>::setFailsafe(size_t id) {
mStatus.set(mDft.failureIndex(id)+1);
mStatus.set(mStateGenerationInfo.getStateIndex(id)+1);
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setDontCare(size_t id) { void DFTState<ValueType>::setDontCare(size_t id) {
mStatus.setFromInt(mDft.failureIndex(id), 2, static_cast<uint_fast64_t>(DFTElementState::DontCare) );
mStatus.setFromInt(mStateGenerationInfo.getStateIndex(id), 2, static_cast<uint_fast64_t>(DFTElementState::DontCare) );
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setDependencySuccessful(size_t id) { void DFTState<ValueType>::setDependencySuccessful(size_t id) {
// No distinction between successful dependency and no dependency at all // No distinction between successful dependency and no dependency at all
// -> we do not set bit
//mStatus.set(mDft.failureIndex(id));
// => we do not set bit
//mStatus.set(mStateGenerationInfo.mIdToStateIndex(id));
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setDependencyUnsuccessful(size_t id) { void DFTState<ValueType>::setDependencyUnsuccessful(size_t id) {
mStatus.set(mDft.failureIndex(id)+1);
mStatus.set(mStateGenerationInfo.getStateIndex(id)+1);
} }
template<typename ValueType> template<typename ValueType>
@ -157,8 +172,7 @@ namespace storm {
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::activate(size_t repr) { void DFTState<ValueType>::activate(size_t repr) {
std::vector<size_t> const& module = mDft.module(repr);
for(size_t elem : module) {
for(size_t elem : mDft.module(repr)) {
if(mDft.getElement(elem)->isColdBasicElement() && isOperational(elem)) { if(mDft.getElement(elem)->isColdBasicElement() && isOperational(elem)) {
mIsCurrentlyFailableBE.push_back(elem); mIsCurrentlyFailableBE.push_back(elem);
} }
@ -175,15 +189,25 @@ namespace storm {
return (std::find(mInactiveSpares.begin(), mInactiveSpares.end(), id) == mInactiveSpares.end()); return (std::find(mInactiveSpares.begin(), mInactiveSpares.end(), id) == mInactiveSpares.end());
} }
template<typename ValueType>
void DFTState<ValueType>::propagateActivation(size_t representativeId) {
activate(representativeId);
for(size_t id : mDft.module(representativeId)) {
if(mDft.getElement(id)->isSpareGate()) {
propagateActivation(uses(id));
}
}
}
template<typename ValueType> template<typename ValueType>
uint_fast64_t DFTState<ValueType>::uses(size_t id) const { uint_fast64_t DFTState<ValueType>::uses(size_t id) const {
return extractUses(mDft.usageIndex(id));
return extractUses(mStateGenerationInfo.getSpareUsageIndex(id));
} }
template<typename ValueType> template<typename ValueType>
uint_fast64_t DFTState<ValueType>::extractUses(size_t from) const { uint_fast64_t DFTState<ValueType>::extractUses(size_t from) const {
assert(mDft.usageInfoBits() < 64);
return mStatus.getAsInt(from, mDft.usageInfoBits());
assert(mStateGenerationInfo.usageInfoBits() < 64);
return mStatus.getAsInt(from, mStateGenerationInfo.usageInfoBits());
} }
template<typename ValueType> template<typename ValueType>
@ -192,13 +216,13 @@ namespace storm {
} }
template<typename ValueType> template<typename ValueType>
void DFTState<ValueType>::setUsesAtPosition(size_t usageIndex, size_t child) {
mStatus.setFromInt(usageIndex, mDft.usageInfoBits(), child);
void DFTState<ValueType>::setUses(size_t spareId, size_t child) {
mStatus.setFromInt(mStateGenerationInfo.getSpareUsageIndex(spareId), mStateGenerationInfo.usageInfoBits(), child);
mUsedRepresentants.push_back(child); mUsedRepresentants.push_back(child);
} }
template<typename ValueType> template<typename ValueType>
bool DFTState<ValueType>::claimNew(size_t spareId, size_t usageIndex, size_t currentlyUses, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children) {
bool DFTState<ValueType>::claimNew(size_t spareId, size_t currentlyUses, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children) {
auto it = children.begin(); auto it = children.begin();
while ((*it)->id() != currentlyUses) { while ((*it)->id() != currentlyUses) {
assert(it != children.end()); assert(it != children.end());
@ -208,9 +232,9 @@ namespace storm {
while(it != children.end()) { while(it != children.end()) {
size_t childId = (*it)->id(); size_t childId = (*it)->id();
if(!hasFailed(childId) && !isUsed(childId)) { if(!hasFailed(childId) && !isUsed(childId)) {
setUsesAtPosition(usageIndex, childId);
setUses(spareId, childId);
if(isActiveSpare(spareId)) { if(isActiveSpare(spareId)) {
mDft.propagateActivation(*this, childId);
propagateActivation(childId);
} }
return true; return true;
} }

16
src/storage/dft/DFTState.h

@ -17,6 +17,7 @@ namespace storm {
class DFTBE; class DFTBE;
template<typename ValueType> template<typename ValueType>
class DFTElement; class DFTElement;
class DFTStateGenerationInfo;
template<typename ValueType> template<typename ValueType>
class DFTState { class DFTState {
@ -31,9 +32,10 @@ namespace storm {
std::vector<size_t> mUsedRepresentants; std::vector<size_t> mUsedRepresentants;
bool mValid = true; bool mValid = true;
const DFT<ValueType>& mDft; const DFT<ValueType>& mDft;
const DFTStateGenerationInfo& mStateGenerationInfo;
public: public:
DFTState(DFT<ValueType> const& dft, size_t id);
DFTState(DFT<ValueType> const& dft, DFTStateGenerationInfo const& stateGenerationInfo, size_t id);
DFTElementState getElementState(size_t id) const; DFTElementState getElementState(size_t id) const;
@ -75,6 +77,8 @@ namespace storm {
bool isActiveSpare(size_t id) const; bool isActiveSpare(size_t id) const;
void propagateActivation(size_t representativeId);
void markAsInvalid() { void markAsInvalid() {
mValid = false; mValid = false;
} }
@ -109,13 +113,13 @@ namespace storm {
bool isUsed(size_t child) const; bool isUsed(size_t child) const;
/** /**
* Sets to to the usageIndex which child is now used.
* @param usageIndex
* @param child
* Sets for the spare which child is now used.
* @param spareId Id of the spare
* @param child Id of the child which is now used
*/ */
void setUsesAtPosition(size_t usageIndex, size_t child);
void setUses(size_t spareId, size_t child);
bool claimNew(size_t spareId, size_t usageIndex, size_t currentlyUses, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children);
bool claimNew(size_t spareId, size_t currentlyUses, std::vector<std::shared_ptr<DFTElement<ValueType>>> const& children);
bool hasOutgoingEdges() const { bool hasOutgoingEdges() const {
return !mIsCurrentlyFailableBE.empty(); return !mIsCurrentlyFailableBE.empty();

Loading…
Cancel
Save