Browse Source
Merge branch 'master' of https://sselab.de/lab9/private/git/MRMC/
Merge branch 'master' of https://sselab.de/lab9/private/git/MRMC/
Conflicts: src/modelChecker/DtmcPrctlModelChecker.h NOTE: makeRowsAbsorbing of SquareSparseMatrix did not return a value. To suppress the warning I added "return false", so that the program compiles for me with "-Werror", too.tempestpy_adaptions
Lanchid
12 years ago
7 changed files with 350 additions and 52 deletions
-
1resources/3rdparty/log4cplus-1.1.0/src/liblog4cplus.0.dylib
-
BINresources/3rdparty/log4cplus-1.1.0/src/liblog4cplus.0.dylib
-
1resources/3rdparty/log4cplus-1.1.0/src/liblog4cplus.dylib
-
BINresources/3rdparty/log4cplus-1.1.0/src/liblog4cplus.dylib
-
162src/modelChecker/GmmxxDtmcPrctlModelChecker.h
-
6src/mrmc.cpp
-
73src/solver/GraphAnalyzer.h
-
127src/storage/SquareSparseMatrix.h
-
34src/utility/vector.h
@ -1 +0,0 @@ |
|||
liblog4cplus.1.1.0.dylib |
@ -1 +0,0 @@ |
|||
liblog4cplus.0.dylib |
@ -0,0 +1,162 @@ |
|||
/* |
|||
* GmmxxDtmcPrctlModelChecker.h |
|||
* |
|||
* Created on: 06.12.2012 |
|||
* Author: Christian Dehnert |
|||
*/ |
|||
|
|||
#ifndef GMMXXDTMCPRCTLMODELCHECKER_H_ |
|||
#define GMMXXDTMCPRCTLMODELCHECKER_H_ |
|||
|
|||
#include "src/utility/vector.h" |
|||
|
|||
#include "src/models/dtmc.h" |
|||
#include "src/solver/GraphAnalyzer.h" |
|||
|
|||
#include "gmm/gmm_matrix.h" |
|||
#include "gmm/gmm_iter_solvers.h" |
|||
|
|||
#include "log4cplus/logger.h" |
|||
#include "log4cplus/loggingmacros.h" |
|||
|
|||
log4cplus::Logger logger; |
|||
|
|||
namespace mrmc { |
|||
|
|||
namespace modelChecker { |
|||
|
|||
/* |
|||
* A model checking engine that makes use of the gmm++ backend. |
|||
*/ |
|||
template <class T> |
|||
class GmmxxDtmcPrctlModelChecker : public DtmcPrctlModelChecker<T> { |
|||
|
|||
public: |
|||
explicit GmmxxDtmcPrctlModelChecker(const mrmc::models::Dtmc<T>* dtmc) : DtmcPrctlModelChecker(dtmc) { } |
|||
|
|||
virtual ~GmmxxDtmcPrctlModelChecker() { } |
|||
|
|||
virtual std::vector<T>* checkBoundedUntil(mrmc::formula::BoundedUntil<T>& formula) { |
|||
// First, we need to compute the states that satisfy the sub-formulas of the until-formula. |
|||
mrmc::storage::BitVector* leftStates = this->check(formula.getLeft()); |
|||
mrmc::storage::BitVector* rightStates = this->check(formula.getRight()); |
|||
|
|||
// Copy the matrix before we make any changes. |
|||
mrmc::storage::SquareSparseMatrix<T>* tmpMatrix(dtmc.getTransitionProbabilityMatrix()); |
|||
|
|||
// Make all rows absorbing that violate both sub-formulas or satisfy the second sub-formula. |
|||
tmpMatrix.makeRowsAbsorbing((~leftStates & rightStates) | rightStates); |
|||
|
|||
// Transform the transition probability matrix to the gmm++ format to use its arithmetic. |
|||
gmm::csr_matrix<double>* gmmxxMatrix = tmpMatrix.toGMMXXSparseMatrix(); |
|||
|
|||
// Create the vector with which to multiply. |
|||
std::vector<T>* result = new st::vector<T>(dtmc.getNumberOfStates()); |
|||
mrmc::utility::setVectorValue(result, *rightStates, 1); |
|||
|
|||
// Now perform matrix-vector multiplication as long as we meet the bound of the formula. |
|||
for (uint_fast64_t i = 0; i < formula.getBound(); ++i) { |
|||
gmm::mult(*gmmxxMatrix, *result, *result); |
|||
} |
|||
|
|||
// Delete intermediate results. |
|||
delete leftStates; |
|||
delete rightStates; |
|||
|
|||
return result; |
|||
} |
|||
|
|||
virtual std::vector<T>* checkNext(const mrmc::formula::Next<T>& formula) { |
|||
// First, we need to compute the states that satisfy the sub-formula of the next-formula. |
|||
mrmc::storage::BitVector* nextStates = this->check(formula.getChild()); |
|||
|
|||
// Transform the transition probability matrix to the gmm++ format to use its arithmetic. |
|||
gmm::csr_matrix<double>* gmmxxMatrix = dtmc.getTransitionProbabilityMatrix()->toGMMXXSparseMatrix(); |
|||
|
|||
// Create the vector with which to multiply and initialize it correctly. |
|||
std::vector<T> x(dtmc.getNumberOfStates()); |
|||
mrmc::utility::setVectorValue(x, nextStates, 1); |
|||
|
|||
// Delete not needed next states bit vector. |
|||
delete nextStates; |
|||
|
|||
// Create resulting vector. |
|||
std::vector<T>* result = new std::vector<T>(dtmc.getNumberOfStates()); |
|||
|
|||
// Perform the actual computation. |
|||
gmm::mult(*gmmxxMatrix, x, *result); |
|||
|
|||
// Delete temporary matrix and return result. |
|||
delete gmmxxMatrix; |
|||
return result; |
|||
} |
|||
|
|||
virtual std::vector<T>* checkUntil(const mrmc::formula::Until<T>& formula) { |
|||
// First, we need to compute the states that satisfy the sub-formulas of the until-formula. |
|||
mrmc::storage::BitVector* leftStates = this->check(formula.getLeft()); |
|||
mrmc::storage::BitVector* rightStates = this->check(formula.getRight()); |
|||
|
|||
// Then, we need to identify the states which have to be taken out of the matrix, i.e. |
|||
// all states that have probability 0 and 1 of satisfying the until-formula. |
|||
mrmc::storage::BitVector notExistsPhiUntilPsiStates(dtmc.getNumberOfStates()); |
|||
mrmc::storage::BitVector alwaysPhiUntilPsiStates(dtmc.getNumberOfStates()); |
|||
mrmc::solver::GraphAnalyzer::getPhiUntilPsiStates<double>(dtmc, *leftStates, *rightStates, ¬ExistsPhiUntilPsiStates, &alwaysPhiUntilPsiStates); |
|||
notExistsPhiUntilPsiStates->complement(); |
|||
|
|||
delete leftStates; |
|||
delete rightStates; |
|||
|
|||
LOG4CPLUS_INFO(logger, "Found " << notExistsPhiUntilPsiStates.getNumberOfSetBits() << " 'no' states."); |
|||
LOG4CPLUS_INFO(logger, "Found " << alwaysPhiUntilPsiStates.getNumberOfSetBits() << " 'yes' states."); |
|||
mrmc::storage::BitVector maybeStates = ~(notExistsPhiUntilPsiStates | alwaysPhiUntilPsiStates); |
|||
LOG4CPLUS_INFO(logger, "Found " << maybeStates.getNumberOfSetBits() << " maybe states."); |
|||
|
|||
// Only try to solve system if there are states for which the probability is unknown. |
|||
if (maybeStates.getNumberOfSetBits() > 0) { |
|||
// Now we can eliminate the rows and columns from the original transition probability matrix. |
|||
mrmc::storage::SquareSparseMatrix<double>* submatrix = dtmc.getTransitionProbabilityMatrix()->getSubmatrix(maybeStates); |
|||
// Converting the matrix to the form needed for the equation system. That is, we go from |
|||
// x = A*x + b to (I-A)x = b. |
|||
submatrix->convertToEquationSystem(); |
|||
|
|||
// Transform the submatrix to the gmm++ format to use its solvers. |
|||
gmm::csr_matrix<double>* gmmxxMatrix = submatrix->toGMMXXSparseMatrix(); |
|||
|
|||
// Initialize the x vector with 0.5 for each element. This is the initial guess for |
|||
// the iterative solvers. It should be safe as for all 'maybe' states we know that the |
|||
// probability is strictly larger than 0. |
|||
std::vector<T>* x = new std::vector<T>(maybeStates.getNumberOfSetBits(), 0.5); |
|||
|
|||
// Prepare the right-hand side of the equation system. For entry i this corresponds to |
|||
// the accumulated probability of going from state i to some 'yes' state. |
|||
std::vector<double> b(maybeStates.getNumberOfSetBits()); |
|||
dtmc.getTransitionProbabilityMatrix()->getConstrainedRowCountVector(maybeStates, alwaysPhiUntilPsiStates, &x); |
|||
|
|||
// Set up the precondition of the iterative solver. |
|||
gmm::ilu_precond<gmm::csr_matrix<double>> P(*gmmxxMatrix); |
|||
// Prepare an iteration object that determines the accuracy, maximum number of iterations |
|||
// and the like. |
|||
gmm::iteration iter(0.000001); |
|||
|
|||
// Now do the actual solving. |
|||
LOG4CPLUS_INFO(logger, "Starting iterations..."); |
|||
gmm::bicgstab(*gmmxxMatrix, x, b, P, iter); |
|||
LOG4CPLUS_INFO(logger, "Done with iterations."); |
|||
|
|||
// Create resulting vector and set values accordingly. |
|||
std::vector<T>* result = new std::vector<T>(dtmc.getNumberOfStates()); |
|||
mrmc::utility::setVectorValues<std::vector<T>>(result, maybeStates, x); |
|||
|
|||
// Delete temporary matrix and return result. |
|||
delete x; |
|||
delete gmmxxMatrix; |
|||
} |
|||
|
|||
mrmc::utility::setVectorValue<std::vector<T>>(result, notExistsPhiUntilPsiStates, 0); |
|||
mrmc::utility::setVectorValue<std::vector<T>>(result, alwaysPhiUntilPsiStates, 1); |
|||
|
|||
return result; |
|||
} |
|||
}; |
|||
|
|||
#endif /* GMMXXDTMCPRCTLMODELCHECKER_H_ */ |
@ -0,0 +1,34 @@ |
|||
/* |
|||
* vector.h |
|||
* |
|||
* Created on: 06.12.2012 |
|||
* Author: Christian Dehnert |
|||
*/ |
|||
|
|||
#ifndef VECTOR_H_ |
|||
#define VECTOR_H_ |
|||
|
|||
namespace mrmc { |
|||
|
|||
namespace utility { |
|||
|
|||
template<T> |
|||
void setVectorValues(std::vector<T>* vector, const mrmc::storage::BitVector& positions, std::vector<T>* values) { |
|||
uint_fast64_t oldPosition = 0; |
|||
for (auto position : positions) { |
|||
vector[position] = values[oldPosition++]; |
|||
} |
|||
} |
|||
|
|||
template<T> |
|||
void setVectorValue(std::vector<T>* vector, const mrmc::storage::BitVector& positions, T value) { |
|||
for (auto position : positions) { |
|||
vector[position] = value; |
|||
} |
|||
} |
|||
|
|||
} //namespace utility |
|||
|
|||
} //namespace mrmc |
|||
|
|||
#endif /* VECTOR_H_ */ |
Write
Preview
Loading…
Cancel
Save
Reference in new issue