32 #ifndef EIGEN_PARDISOSUPPORT_H
33 #define EIGEN_PARDISOSUPPORT_H
35 #include "./InternalHeaderCheck.h"
39 template<
typename MatrixType_>
class PardisoLU;
40 template<
typename MatrixType_,
int Options=Upper>
class PardisoLLT;
41 template<
typename MatrixType_,
int Options=Upper>
class PardisoLDLT;
45 template<
typename IndexType>
46 struct pardiso_run_selector
48 static IndexType run( _MKL_DSS_HANDLE_t pt, IndexType maxfct, IndexType mnum, IndexType type, IndexType phase, IndexType n,
void *a,
49 IndexType *ia, IndexType *ja, IndexType *perm, IndexType nrhs, IndexType *iparm, IndexType msglvl,
void *b,
void *x)
52 ::pardiso(pt, &maxfct, &mnum, &type, &phase, &n, a, ia, ja, perm, &nrhs, iparm, &msglvl, b, x, &error);
57 struct pardiso_run_selector<long long int>
59 typedef long long int IndexType;
60 static IndexType run( _MKL_DSS_HANDLE_t pt, IndexType maxfct, IndexType mnum, IndexType type, IndexType phase, IndexType n,
void *a,
61 IndexType *ia, IndexType *ja, IndexType *perm, IndexType nrhs, IndexType *iparm, IndexType msglvl,
void *b,
void *x)
64 ::pardiso_64(pt, &maxfct, &mnum, &type, &phase, &n, a, ia, ja, perm, &nrhs, iparm, &msglvl, b, x, &error);
69 template<
class Pardiso>
struct pardiso_traits;
71 template<
typename MatrixType_>
72 struct pardiso_traits< PardisoLU<MatrixType_> >
74 typedef MatrixType_ MatrixType;
75 typedef typename MatrixType_::Scalar Scalar;
76 typedef typename MatrixType_::RealScalar RealScalar;
77 typedef typename MatrixType_::StorageIndex StorageIndex;
80 template<
typename MatrixType_,
int Options>
81 struct pardiso_traits< PardisoLLT<MatrixType_, Options> >
83 typedef MatrixType_ MatrixType;
84 typedef typename MatrixType_::Scalar Scalar;
85 typedef typename MatrixType_::RealScalar RealScalar;
86 typedef typename MatrixType_::StorageIndex StorageIndex;
89 template<
typename MatrixType_,
int Options>
90 struct pardiso_traits< PardisoLDLT<MatrixType_, Options> >
92 typedef MatrixType_ MatrixType;
93 typedef typename MatrixType_::Scalar Scalar;
94 typedef typename MatrixType_::RealScalar RealScalar;
95 typedef typename MatrixType_::StorageIndex StorageIndex;
100 template<
class Derived>
101 class PardisoImpl :
public SparseSolverBase<Derived>
104 typedef SparseSolverBase<Derived> Base;
106 using Base::m_isInitialized;
108 typedef internal::pardiso_traits<Derived> Traits;
110 using Base::_solve_impl;
112 typedef typename Traits::MatrixType MatrixType;
113 typedef typename Traits::Scalar Scalar;
114 typedef typename Traits::RealScalar RealScalar;
115 typedef typename Traits::StorageIndex StorageIndex;
116 typedef SparseMatrix<Scalar,RowMajor,StorageIndex> SparseMatrixType;
117 typedef Matrix<Scalar,Dynamic,1> VectorType;
118 typedef Matrix<StorageIndex, 1, MatrixType::ColsAtCompileTime> IntRowVectorType;
119 typedef Matrix<StorageIndex, MatrixType::RowsAtCompileTime, 1> IntColVectorType;
120 typedef Array<StorageIndex,64,1,DontAlign> ParameterType;
122 ScalarIsComplex = NumTraits<Scalar>::IsComplex,
128 : m_analysisIsOk(false), m_factorizationIsOk(false)
130 eigen_assert((
sizeof(StorageIndex) >=
sizeof(_INTEGER_t) &&
sizeof(StorageIndex) <= 8) &&
"Non-supported index type");
133 m_isInitialized =
false;
141 inline Index cols()
const {
return m_size; }
142 inline Index rows()
const {
return m_size; }
151 eigen_assert(m_isInitialized &&
"Decomposition is not initialized.");
158 ParameterType& pardisoParameterArray()
169 Derived& analyzePattern(
const MatrixType& matrix);
177 Derived& factorize(
const MatrixType& matrix);
179 Derived& compute(
const MatrixType& matrix);
181 template<
typename Rhs,
typename Dest>
182 void _solve_impl(
const MatrixBase<Rhs> &b, MatrixBase<Dest> &dest)
const;
185 void pardisoRelease()
189 internal::pardiso_run_selector<StorageIndex>::run(m_pt, 1, 1, m_type, -1, internal::convert_index<StorageIndex>(m_size),0, 0, 0, m_perm.data(), 0,
190 m_iparm.data(), m_msglvl, NULL, NULL);
191 m_isInitialized =
false;
195 void pardisoInit(
int type)
198 bool symmetric = std::abs(m_type) < 10;
209 m_iparm[10] = symmetric ? 0 : 1;
211 m_iparm[12] = symmetric ? 0 : 1;
223 m_iparm[27] = (
sizeof(RealScalar) == 4) ? 1 : 0;
228 memset(m_pt, 0,
sizeof(m_pt));
234 void manageErrorCode(
Index error)
const
250 mutable SparseMatrixType m_matrix;
252 bool m_analysisIsOk, m_factorizationIsOk;
253 StorageIndex m_type, m_msglvl;
254 mutable void *m_pt[64];
255 mutable ParameterType m_iparm;
256 mutable IntColVectorType m_perm;
261 template<
class Derived>
262 Derived& PardisoImpl<Derived>::compute(
const MatrixType& a)
265 eigen_assert(a.rows() == a.cols());
268 m_perm.setZero(m_size);
269 derived().getMatrix(a);
272 error = internal::pardiso_run_selector<StorageIndex>::run(m_pt, 1, 1, m_type, 12, internal::convert_index<StorageIndex>(m_size),
273 m_matrix.valuePtr(), m_matrix.outerIndexPtr(), m_matrix.innerIndexPtr(),
274 m_perm.data(), 0, m_iparm.data(), m_msglvl, NULL, NULL);
275 manageErrorCode(error);
276 m_analysisIsOk =
true;
277 m_factorizationIsOk =
true;
278 m_isInitialized =
true;
282 template<
class Derived>
283 Derived& PardisoImpl<Derived>::analyzePattern(
const MatrixType& a)
286 eigen_assert(m_size == a.cols());
289 m_perm.setZero(m_size);
290 derived().getMatrix(a);
293 error = internal::pardiso_run_selector<StorageIndex>::run(m_pt, 1, 1, m_type, 11, internal::convert_index<StorageIndex>(m_size),
294 m_matrix.valuePtr(), m_matrix.outerIndexPtr(), m_matrix.innerIndexPtr(),
295 m_perm.data(), 0, m_iparm.data(), m_msglvl, NULL, NULL);
297 manageErrorCode(error);
298 m_analysisIsOk =
true;
299 m_factorizationIsOk =
false;
300 m_isInitialized =
true;
304 template<
class Derived>
305 Derived& PardisoImpl<Derived>::factorize(
const MatrixType& a)
307 eigen_assert(m_analysisIsOk &&
"You must first call analyzePattern()");
308 eigen_assert(m_size == a.rows() && m_size == a.cols());
310 derived().getMatrix(a);
313 error = internal::pardiso_run_selector<StorageIndex>::run(m_pt, 1, 1, m_type, 22, internal::convert_index<StorageIndex>(m_size),
314 m_matrix.valuePtr(), m_matrix.outerIndexPtr(), m_matrix.innerIndexPtr(),
315 m_perm.data(), 0, m_iparm.data(), m_msglvl, NULL, NULL);
317 manageErrorCode(error);
318 m_factorizationIsOk =
true;
322 template<
class Derived>
323 template<
typename BDerived,
typename XDerived>
324 void PardisoImpl<Derived>::_solve_impl(
const MatrixBase<BDerived> &b, MatrixBase<XDerived>& x)
const
334 eigen_assert(m_size==b.rows());
337 eigen_assert(((nrhs == 1) || b.outerStride() == b.rows()));
349 Scalar* rhs_ptr =
const_cast<Scalar*
>(b.derived().data());
350 Matrix<Scalar,Dynamic,Dynamic,ColMajor> tmp;
353 if(rhs_ptr == x.derived().data())
356 rhs_ptr = tmp.data();
360 error = internal::pardiso_run_selector<StorageIndex>::run(m_pt, 1, 1, m_type, 33, internal::convert_index<StorageIndex>(m_size),
361 m_matrix.valuePtr(), m_matrix.outerIndexPtr(), m_matrix.innerIndexPtr(),
362 m_perm.data(), internal::convert_index<StorageIndex>(nrhs), m_iparm.data(), m_msglvl,
363 rhs_ptr, x.derived().data());
365 manageErrorCode(error);
386 template<
typename MatrixType>
387 class PardisoLU :
public PardisoImpl< PardisoLU<MatrixType> >
390 typedef PardisoImpl<PardisoLU>
Base;
391 using Base::pardisoInit;
392 using Base::m_matrix;
393 friend class PardisoImpl<
PardisoLU<MatrixType> >;
397 typedef typename Base::Scalar Scalar;
398 typedef typename Base::RealScalar RealScalar;
406 pardisoInit(Base::ScalarIsComplex ? 13 : 11);
409 explicit PardisoLU(
const MatrixType& matrix)
412 pardisoInit(Base::ScalarIsComplex ? 13 : 11);
416 void getMatrix(
const MatrixType& matrix)
419 m_matrix.makeCompressed();
442 template<
typename MatrixType,
int UpLo_>
443 class PardisoLLT :
public PardisoImpl< PardisoLLT<MatrixType,UpLo_> >
446 typedef PardisoImpl< PardisoLLT<MatrixType,UpLo_> >
Base;
447 using Base::pardisoInit;
448 using Base::m_matrix;
449 friend class PardisoImpl<
PardisoLLT<MatrixType,UpLo_> >;
453 typedef typename Base::Scalar Scalar;
454 typedef typename Base::RealScalar RealScalar;
455 typedef typename Base::StorageIndex StorageIndex;
456 enum { UpLo = UpLo_ };
462 pardisoInit(Base::ScalarIsComplex ? 4 : 2);
468 pardisoInit(Base::ScalarIsComplex ? 4 : 2);
474 void getMatrix(
const MatrixType& matrix)
478 m_matrix.
resize(matrix.rows(), matrix.cols());
479 m_matrix.template selfadjointView<Upper>() = matrix.template selfadjointView<UpLo>().twistedBy(p_null);
480 m_matrix.makeCompressed();
505 template<
typename MatrixType,
int Options>
506 class PardisoLDLT :
public PardisoImpl< PardisoLDLT<MatrixType,Options> >
509 typedef PardisoImpl< PardisoLDLT<MatrixType,Options> >
Base;
510 using Base::pardisoInit;
511 using Base::m_matrix;
512 friend class PardisoImpl<
PardisoLDLT<MatrixType,Options> >;
516 typedef typename Base::Scalar Scalar;
517 typedef typename Base::RealScalar RealScalar;
518 typedef typename Base::StorageIndex StorageIndex;
525 pardisoInit(Base::ScalarIsComplex ? (
bool(Options&
Symmetric) ? 6 : -4 ) : -2);
531 pardisoInit(Base::ScalarIsComplex ? (
bool(Options&
Symmetric) ? 6 : -4 ) : -2);
535 void getMatrix(
const MatrixType& matrix)
539 m_matrix.
resize(matrix.rows(), matrix.cols());
540 m_matrix.template selfadjointView<Upper>() = matrix.template selfadjointView<UpLo>().twistedBy(p_null);
541 m_matrix.makeCompressed();
@ Flags
Definition: DenseBase.h:159
A sparse direct Cholesky (LDLT) factorization and solver based on the PARDISO library.
Definition: PardisoSupport.h:507
A sparse direct Cholesky (LLT) factorization and solver based on the PARDISO library.
Definition: PardisoSupport.h:444
A sparse direct LU factorization and solver based on the PARDISO library.
Definition: PardisoSupport.h:388
void resize(Index newSize)
Definition: PermutationMatrix.h:127
A base class for sparse solvers.
Definition: SparseSolverBase.h:70
ComputationInfo
Definition: Constants.h:442
@ Symmetric
Definition: Constants.h:229
@ Lower
Definition: Constants.h:211
@ Upper
Definition: Constants.h:213
@ NumericalIssue
Definition: Constants.h:446
@ InvalidInput
Definition: Constants.h:451
@ Success
Definition: Constants.h:444
const unsigned int RowMajorBit
Definition: Constants.h:68
Namespace containing all symbols from the Eigen library.
Definition: Core:139
EIGEN_DEFAULT_DENSE_INDEX_TYPE Index
The Index type as used for the API.
Definition: Meta.h:59
const int Dynamic
Definition: Constants.h:24