summaryrefslogtreecommitdiffstatshomepage
path: root/src/lib/netlist
diff options
context:
space:
mode:
author couriersud <couriersud@gmx.org>2017-01-28 16:02:39 +0100
committer couriersud <couriersud@gmx.org>2017-01-29 15:45:50 +0100
commit2720512e31c8659294d05b336af58d982cd99329 (patch)
tree280402940055c4daf7bb057cb4abe8bfe28c7dc7 /src/lib/netlist
parent1070ea6d0f89f54bbe3141a94d0a43ab569b65ae (diff)
Solver stuff:
Rewrote mat_cr_t to include data as well. Fixed some bitrot in other parts. Simplified solver creation. (nw)
Diffstat (limited to 'src/lib/netlist')
-rw-r--r--src/lib/netlist/plib/palloc.h2
-rw-r--r--src/lib/netlist/solver/mat_cr.h81
-rw-r--r--src/lib/netlist/solver/nld_ms_direct.h22
-rw-r--r--src/lib/netlist/solver/nld_ms_gcr.h39
-rw-r--r--src/lib/netlist/solver/nld_ms_gmres.h23
-rw-r--r--src/lib/netlist/solver/nld_ms_sm.h5
-rw-r--r--src/lib/netlist/solver/nld_solver.cpp141
-rw-r--r--src/lib/netlist/solver/nld_solver.h2
8 files changed, 174 insertions, 141 deletions
diff --git a/src/lib/netlist/plib/palloc.h b/src/lib/netlist/plib/palloc.h
index d71ebc7dbc5..2e4c2809048 100644
--- a/src/lib/netlist/plib/palloc.h
+++ b/src/lib/netlist/plib/palloc.h
@@ -28,7 +28,7 @@ template<typename T>
void pfree(T *ptr) { delete ptr; }
template<typename T>
-inline T* palloc_array(std::size_t num)
+inline T* palloc_array(const std::size_t num)
{
return new T[num]();
}
diff --git a/src/lib/netlist/solver/mat_cr.h b/src/lib/netlist/solver/mat_cr.h
index 81e8615c16d..9d0f2076459 100644
--- a/src/lib/netlist/solver/mat_cr.h
+++ b/src/lib/netlist/solver/mat_cr.h
@@ -12,20 +12,59 @@
#include <algorithm>
#include "plib/pconfig.h"
+#include "plib/palloc.h"
-//template<std::size_t storage_N, typename C = std::size_t>
-template<std::size_t storage_N, typename C = uint16_t>
+template<std::size_t N, typename C = uint16_t, typename T = double>
struct mat_cr_t
{
- typedef C type;
+ typedef C index_type;
+ typedef T value_type;
- C nz_num;
- C ia[storage_N + 1];
- C ja[storage_N * storage_N];
- C diag[storage_N]; /* n */
+ C RESTRICT diag[N]; // diagonal index pointer n
+ C RESTRICT ia[N+1]; // row index pointer n + 1
+ C RESTRICT ja[N*N]; // column index array nz_num, initially (n * n)
+ T RESTRICT A[N*N]; // Matrix elements nz_num, initially (n * n)
- template<typename T>
- void mult_vec(const T * RESTRICT A, const T * RESTRICT x, T * RESTRICT res)
+ std::size_t size;
+ std::size_t nz_num;
+
+ mat_cr_t(const std::size_t n)
+ : size(n)
+ , nz_num(0)
+ {
+#if 0
+#if 0
+ ia = plib::palloc_array<C>(n + 1);
+ ja = plib::palloc_array<C>(n * n);
+ diag = plib::palloc_array<C>(n);
+#else
+ diag = plib::palloc_array<C>(n + (n + 1) + n * n);
+ ia = diag + n;
+ ja = ia + (n+1);
+ A = plib::palloc_array<T>(n * n);
+#endif
+#endif
+ }
+
+ ~mat_cr_t()
+ {
+#if 0
+ plib::pfree_array(diag);
+#if 0
+ plib::pfree_array(ia);
+ plib::pfree_array(ja);
+#endif
+ plib::pfree_array(A);
+#endif
+ }
+
+ void set_scalar(const T scalar)
+ {
+ for (std::size_t i=0, e=nz_num; i<e; i++)
+ A[i] = scalar;
+ }
+
+ void mult_vec(const T * RESTRICT x, T * RESTRICT res)
{
/*
* res = A * x
@@ -45,8 +84,7 @@ struct mat_cr_t
}
}
- template<typename T>
- void incomplete_LU_factorization(const T * RESTRICT A, T * RESTRICT LU)
+ void incomplete_LU_factorization(T * RESTRICT LU)
{
/*
* incomplete LU Factorization according to http://de.wikipedia.org/wiki/ILU-Zerlegung
@@ -86,7 +124,6 @@ struct mat_cr_t
}
}
- template<typename T>
void solveLUx (const T * RESTRICT LU, T * RESTRICT r)
{
/*
@@ -99,7 +136,7 @@ struct mat_cr_t
*
* ==> LUx = r
*
- * ==> Ux = L?????r = w
+ * ==> Ux = L⁻¹ r = w
*
* ==> r = Lw
*
@@ -111,32 +148,28 @@ struct mat_cr_t
*
*/
- std::size_t i;
-
- for (i = 1; ia[i] < nz_num; i++ )
+ for (std::size_t i = 1; ia[i] < nz_num; ++i )
{
T tmp = 0.0;
const std::size_t j1 = ia[i];
const std::size_t j2 = diag[i];
- for (std::size_t j = j1; j < j2; j++ )
+ for (std::size_t j = j1; j < j2; ++j )
tmp += LU[j] * r[ja[j]];
r[i] -= tmp;
}
// i now is equal to n;
- for (; 0 < i; i-- )
+ for (std::size_t i = size; i-- > 0; )
{
- const std::size_t im1 = i - 1;
T tmp = 0.0;
- const std::size_t j1 = diag[im1] + 1;
- const std::size_t j2 = ia[im1+1];
- for (std::size_t j = j1; j < j2; j++ )
+ const std::size_t di = diag[i];
+ const std::size_t j2 = ia[i+1];
+ for (std::size_t j = di + 1; j < j2; j++ )
tmp += LU[j] * r[ja[j]];
- r[im1] = (r[im1] - tmp) / LU[diag[im1]];
+ r[i] = (r[i] - tmp) / LU[di];
}
}
-
};
#endif /* MAT_CR_H_ */
diff --git a/src/lib/netlist/solver/nld_ms_direct.h b/src/lib/netlist/solver/nld_ms_direct.h
index d37a1fcc88c..9f9867c00e8 100644
--- a/src/lib/netlist/solver/nld_ms_direct.h
+++ b/src/lib/netlist/solver/nld_ms_direct.h
@@ -19,7 +19,7 @@
* going forward in case we implement cuda solvers in the future.
*/
#define NL_USE_DYNAMIC_ALLOCATION (0)
-#define TEST_PARALLEL (0)
+#define TEST_PARALLEL (0 )
#if TEST_PARALLEL
#include <thread>
@@ -36,16 +36,17 @@ namespace netlist
#if TEST_PARALLEL
#define MAXTHR 10
-static const int num_thr = 1;
+static const int num_thr = 3;
struct thr_intf
{
+ virtual ~thr_intf() = default;
virtual void do_work(const int id, void *param) = 0;
};
struct ti_t
{
- volatile std::atomic<int> lo;
+ /*volatile */std::atomic<int> lo;
thr_intf *intf;
void *params;
// int block[29]; /* make it 256 bytes */
@@ -163,6 +164,7 @@ protected:
nl_double m_last_RHS[storage_N]; // right hand side - contains currents
private:
+ //static const std::size_t m_pitch = (((storage_N + 1) + 0) / 1) * 1;
static const std::size_t m_pitch = (((storage_N + 1) + 7) / 8) * 8;
//static const std::size_t m_pitch = (((storage_N + 1) + 15) / 16) * 16;
//static const std::size_t m_pitch = (((storage_N + 1) + 31) / 32) * 32;
@@ -185,7 +187,7 @@ template <std::size_t m_N, std::size_t storage_N>
matrix_solver_direct_t<m_N, storage_N>::~matrix_solver_direct_t()
{
#if (NL_USE_DYNAMIC_ALLOCATION)
- pfree_array(m_A);
+ plib::pfree_array(m_A);
#endif
#if TEST_PARALLEL
thr_dispose();
@@ -215,7 +217,7 @@ void matrix_solver_direct_t<m_N, storage_N>::vsetup(analog_net_t::list_t &nets)
#if TEST_PARALLEL
-template <unsigned m_N, unsigned storage_N>
+template <std::size_t m_N, std::size_t storage_N>
void matrix_solver_direct_t<m_N, storage_N>::do_work(const int id, void *param)
{
const int i = x_i[id];
@@ -323,14 +325,14 @@ void matrix_solver_direct_t<m_N, storage_N>::LE_solve()
const auto &nzrd = m_terms[i]->m_nzrd;
const auto &nzbd = m_terms[i]->m_nzbd;
- for (auto & j : nzbd)
+ for (std::size_t j : nzbd)
{
const nl_double f1 = -f * A(j,i);
- for (auto & k : nzrd)
+ for (std::size_t k : nzrd)
A(j,k) += A(i,k) * f1;
//RHS(j) += RHS(i) * f1;
-#endif
}
+#endif
}
}
}
@@ -416,7 +418,7 @@ matrix_solver_direct_t<m_N, storage_N>::matrix_solver_direct_t(netlist_t &anetli
, m_dim(size)
{
#if (NL_USE_DYNAMIC_ALLOCATION)
- m_A = palloc_array(nl_ext_double, N() * m_pitch);
+ m_A = plib::palloc_array<nl_ext_double>(N() * m_pitch);
#endif
for (unsigned k = 0; k < N(); k++)
{
@@ -434,7 +436,7 @@ matrix_solver_direct_t<m_N, storage_N>::matrix_solver_direct_t(netlist_t &anetli
, m_dim(size)
{
#if (NL_USE_DYNAMIC_ALLOCATION)
- m_A = palloc_array(nl_ext_double, N() * m_pitch);
+ m_A = plib::palloc_array<nl_ext_double>(N() * m_pitch);
#endif
for (unsigned k = 0; k < N(); k++)
{
diff --git a/src/lib/netlist/solver/nld_ms_gcr.h b/src/lib/netlist/solver/nld_ms_gcr.h
index b48e4987ac1..6823e2e9209 100644
--- a/src/lib/netlist/solver/nld_ms_gcr.h
+++ b/src/lib/netlist/solver/nld_ms_gcr.h
@@ -39,6 +39,7 @@ public:
const solver_parameters_t *params, const std::size_t size)
: matrix_solver_t(anetlist, name, matrix_solver_t::ASCENDING, params)
, m_dim(size)
+ , mat(size)
, m_proc(nullptr)
{
}
@@ -56,7 +57,8 @@ public:
private:
- typedef typename mat_cr_t<storage_N>::type mattype;
+ //typedef typename mat_cr_t<storage_N>::type mattype;
+ typedef typename mat_cr_t<storage_N>::index_type mattype;
void csc_private(plib::putf8_fmt_writer &strm);
@@ -67,7 +69,6 @@ private:
const std::size_t m_dim;
std::vector<unsigned> m_term_cr[storage_N];
mat_cr_t<storage_N> mat;
- nl_double m_A[storage_N * storage_N];
extsolver m_proc;
@@ -185,7 +186,8 @@ void matrix_solver_GCR_t<m_N, storage_N>::csc_private(plib::putf8_fmt_writer &st
pi++;
const std::size_t piie = mat.ia[i+1];
- for (auto & j : nzbd)
+ //for (auto & j : nzbd)
+ for (std::size_t j : nzbd)
{
// proceed to column i
std::size_t pj = mat.ia[j];
@@ -248,8 +250,7 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
nl_double RHS[storage_N];
nl_double new_V[storage_N];
- for (std::size_t i=0, e=mat.nz_num; i<e; i++)
- m_A[i] = 0.0;
+ mat.set_scalar(0.0);
for (std::size_t k = 0; k < iN; k++)
{
@@ -283,7 +284,7 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
RHS_t += Idr[i];
}
#else
- for (unsigned i = 0; i < term_count; i++)
+ for (std::size_t i = 0; i < term_count; i++)
{
gtot_t += gt[i];
RHS_t += Idr[i];
@@ -295,10 +296,10 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
RHS[k] = RHS_t;
// add diagonal element
- m_A[mat.diag[k]] = gtot_t;
+ mat.A[mat.diag[k]] = gtot_t;
for (std::size_t i = 0; i < railstart; i++)
- m_A[tcr[i]] -= go[i];
+ mat.A[tcr[i]] -= go[i];
}
#else
for (std::size_t i = 0; i < railstart; i++)
@@ -325,7 +326,7 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
if (m_proc != nullptr)
{
//static_solver(m_A, RHS);
- m_proc(m_A, RHS);
+ m_proc(mat.A, RHS);
}
else
{
@@ -336,10 +337,10 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
if (nzbd.size() > 0)
{
std::size_t pi = mat.diag[i];
- const nl_double f = 1.0 / m_A[pi++];
+ const nl_double f = 1.0 / mat.A[pi++];
const std::size_t piie = mat.ia[i+1];
- for (auto & j : nzbd)
+ for (std::size_t j : nzbd) // for (std::size_t j = i + 1; j < iN; j++)
{
// proceed to column i
//__builtin_prefetch(&m_A[mat.diag[j+1]], 1);
@@ -348,14 +349,14 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
while (mat.ja[pj] < i)
pj++;
- const nl_double f1 = - m_A[pj++] * f;
+ const nl_double f1 = - mat.A[pj++] * f;
// subtract row i from j */
for (std::size_t pii = pi; pii<piie; )
{
while (mat.ja[pj] < mat.ja[pii])
pj++;
- m_A[pj++] += m_A[pii++] * f1;
+ mat.A[pj++] += mat.A[pii++] * f1;
}
RHS[j] += f1 * RHS[i];
}
@@ -368,7 +369,7 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
*/
/* row n-1 */
- new_V[iN - 1] = RHS[iN - 1] / m_A[mat.diag[iN - 1]];
+ new_V[iN - 1] = RHS[iN - 1] / mat.A[mat.diag[iN - 1]];
for (std::size_t j = iN - 1; j-- > 0;)
{
@@ -381,23 +382,23 @@ unsigned matrix_solver_GCR_t<m_N, storage_N>::vsolve_non_dynamic(const bool newt
for (; pk < e - 1; pk+=2)
{
//tmp += m_A[pk] * new_V[mat.ja[pk]];
- tmp = _mm_add_pd(tmp, _mm_mul_pd(_mm_set_pd(m_A[pk], m_A[pk+1]),
+ tmp = _mm_add_pd(tmp, _mm_mul_pd(_mm_set_pd(mat.A[pk], mat.A[pk+1]),
_mm_set_pd(new_V[mat.ja[pk]], new_V[mat.ja[pk+1]])));
}
double tmpx = _mm_cvtsd_f64(tmp) + _mm_cvtsd_f64(_mm_unpackhi_pd(tmp,tmp));
for (; pk < e; pk++)
{
- tmpx += m_A[pk] * new_V[mat.ja[pk]];
+ tmpx += mat.A[pk] * new_V[mat.ja[pk]];
}
- new_V[j] = (RHS[j] - tmpx) / m_A[mat.diag[j]];
+ new_V[j] = (RHS[j] - tmpx) / mat.A[mat.diag[j]];
#else
double tmp = 0;
const std::size_t e = mat.ia[j+1];
for (std::size_t pk = mat.diag[j] + 1; pk < e; pk++)
{
- tmp += m_A[pk] * new_V[mat.ja[pk]];
+ tmp += mat.A[pk] * new_V[mat.ja[pk]];
}
- new_V[j] = (RHS[j] - tmp) / m_A[mat.diag[j]];
+ new_V[j] = (RHS[j] - tmp) / mat.A[mat.diag[j]];
#endif
}
this->m_stat_calculations++;
diff --git a/src/lib/netlist/solver/nld_ms_gmres.h b/src/lib/netlist/solver/nld_ms_gmres.h
index 85ea0786500..644ddb6533b 100644
--- a/src/lib/netlist/solver/nld_ms_gmres.h
+++ b/src/lib/netlist/solver/nld_ms_gmres.h
@@ -33,6 +33,7 @@ public:
, m_use_iLU_preconditioning(true)
, m_use_more_precise_stop_condition(false)
, m_accuracy_mult(1.0)
+ , mat(size)
{
}
@@ -45,7 +46,8 @@ public:
private:
- typedef typename mat_cr_t<storage_N>::type mattype;
+ //typedef typename mat_cr_t<storage_N>::type mattype;
+ typedef typename mat_cr_t<storage_N>::index_type mattype;
unsigned solve_ilu_gmres(nl_double (& RESTRICT x)[storage_N], const nl_double * RESTRICT rhs, const unsigned restart_max, const std::size_t mr, nl_double accuracy);
@@ -57,7 +59,6 @@ private:
mat_cr_t<storage_N> mat;
- nl_double m_A[storage_N * storage_N];
nl_double m_LU[storage_N * storage_N];
nl_double m_c[storage_N + 1]; /* mr + 1 */
@@ -129,8 +130,7 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::vsolve_non_dynamic(const bool ne
nl_double RHS[storage_N];
nl_double new_V[storage_N];
- for (unsigned i=0, e=mat.nz_num; i<e; i++)
- m_A[i] = 0.0;
+ mat.set_scalar(0.0);
for (std::size_t k = 0; k < iN; k++)
{
@@ -158,12 +158,12 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::vsolve_non_dynamic(const bool ne
RHS[k] = RHS_t;
// add diagonal element
- m_A[mat.diag[k]] = gtot_t;
+ mat.A[mat.diag[k]] = gtot_t;
for (std::size_t i = 0; i < railstart; i++)
{
- const unsigned pi = m_term_cr[k][i];
- m_A[pi] -= go[i];
+ const std::size_t pi = m_term_cr[k][i];
+ mat.A[pi] -= go[i];
}
}
mat.ia[iN] = mat.nz_num;
@@ -242,7 +242,7 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::solve_ilu_gmres (nl_double (& RE
const std::size_t n = this->N();
if (m_use_iLU_preconditioning)
- mat.incomplete_LU_factorization(m_A, m_LU);
+ mat.incomplete_LU_factorization(m_LU);
if (m_use_more_precise_stop_condition)
{
@@ -260,7 +260,8 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::solve_ilu_gmres (nl_double (& RE
nl_double t[storage_N];
nl_double Ax[storage_N];
vec_set(n, accuracy, t);
- mat.mult_vec(m_A, t, Ax);
+ mat.mult_vec(t, Ax);
+
mat.solveLUx(m_LU, Ax);
const nl_double rho_to_accuracy = std::sqrt(vecmult2(n, Ax)) / accuracy;
@@ -278,7 +279,7 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::solve_ilu_gmres (nl_double (& RE
nl_double Ax[storage_N];
nl_double residual[storage_N];
- mat.mult_vec(m_A, x, Ax);
+ mat.mult_vec(x, Ax);
vec_sub(n, rhs, Ax, residual);
@@ -304,7 +305,7 @@ unsigned matrix_solver_GMRES_t<m_N, storage_N>::solve_ilu_gmres (nl_double (& RE
{
const std::size_t k1 = k + 1;
- mat.mult_vec(m_A, m_v[k], m_v[k1]);
+ mat.mult_vec(m_v[k], m_v[k1]);
if (m_use_iLU_preconditioning)
mat.solveLUx(m_LU, m_v[k1]);
diff --git a/src/lib/netlist/solver/nld_ms_sm.h b/src/lib/netlist/solver/nld_ms_sm.h
index e1a768a45c5..b87f5bcc835 100644
--- a/src/lib/netlist/solver/nld_ms_sm.h
+++ b/src/lib/netlist/solver/nld_ms_sm.h
@@ -115,7 +115,7 @@ template <std::size_t m_N, std::size_t storage_N>
matrix_solver_sm_t<m_N, storage_N>::~matrix_solver_sm_t()
{
#if (NL_USE_DYNAMIC_ALLOCATION)
- pfree_array(m_A);
+ plib::pfree_array(m_A);
#endif
}
@@ -324,9 +324,6 @@ matrix_solver_sm_t<m_N, storage_N>::matrix_solver_sm_t(netlist_t &anetlist, cons
: matrix_solver_t(anetlist, name, NOSORT, params)
, m_dim(size)
{
-#if (NL_USE_DYNAMIC_ALLOCATION)
- m_A = palloc_array(nl_ext_double, N() * m_pitch);
-#endif
for (std::size_t k = 0; k < N(); k++)
{
m_last_RHS[k] = 0.0;
diff --git a/src/lib/netlist/solver/nld_solver.cpp b/src/lib/netlist/solver/nld_solver.cpp
index 76c776c75dd..85ddcb5fcaf 100644
--- a/src/lib/netlist/solver/nld_solver.cpp
+++ b/src/lib/netlist/solver/nld_solver.cpp
@@ -147,58 +147,50 @@ std::unique_ptr<matrix_solver_t> create_it(netlist_t &nl, pstring name, solver_p
}
template <std::size_t m_N, std::size_t storage_N>
-std::unique_ptr<matrix_solver_t> NETLIB_NAME(solver)::create_solver(std::size_t size, const bool use_specific)
+std::unique_ptr<matrix_solver_t> NETLIB_NAME(solver)::create_solver(std::size_t size, const pstring &solvername)
{
- pstring solvername = plib::pfmt("Solver_{1}")(m_mat_solvers.size());
- if (use_specific && m_N == 1)
- return plib::make_unique<matrix_solver_direct1_t>(netlist(), solvername, &m_params);
- else if (use_specific && m_N == 2)
- return plib::make_unique<matrix_solver_direct2_t>(netlist(), solvername, &m_params);
+ if (pstring("SOR_MAT").equals(m_method()))
+ {
+ return create_it<matrix_solver_SOR_mat_t<m_N, storage_N>>(netlist(), solvername, m_params, size);
+ //typedef matrix_solver_SOR_mat_t<m_N,storage_N> solver_sor_mat;
+ //return plib::make_unique<solver_sor_mat>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("MAT_CR").equals(m_method()))
+ {
+ typedef matrix_solver_GCR_t<m_N,storage_N> solver_mat;
+ return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("MAT").equals(m_method()))
+ {
+ typedef matrix_solver_direct_t<m_N,storage_N> solver_mat;
+ return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("SM").equals(m_method()))
+ {
+ /* Sherman-Morrison Formula */
+ typedef matrix_solver_sm_t<m_N,storage_N> solver_mat;
+ return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("W").equals(m_method()))
+ {
+ /* Woodbury Formula */
+ typedef matrix_solver_w_t<m_N,storage_N> solver_mat;
+ return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("SOR").equals(m_method()))
+ {
+ typedef matrix_solver_SOR_t<m_N,storage_N> solver_GS;
+ return plib::make_unique<solver_GS>(netlist(), solvername, &m_params, size);
+ }
+ else if (pstring("GMRES").equals(m_method()))
+ {
+ typedef matrix_solver_GMRES_t<m_N,storage_N> solver_GMRES;
+ return plib::make_unique<solver_GMRES>(netlist(), solvername, &m_params, size);
+ }
else
{
- if (pstring("SOR_MAT").equals(m_method()))
- {
- return create_it<matrix_solver_SOR_mat_t<m_N, storage_N>>(netlist(), solvername, m_params, size);
- //typedef matrix_solver_SOR_mat_t<m_N,storage_N> solver_sor_mat;
- //return plib::make_unique<solver_sor_mat>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("MAT_CR").equals(m_method()))
- {
- typedef matrix_solver_GCR_t<m_N,storage_N> solver_mat;
- return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("MAT").equals(m_method()))
- {
- typedef matrix_solver_direct_t<m_N,storage_N> solver_mat;
- return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("SM").equals(m_method()))
- {
- /* Sherman-Morrison Formula */
- typedef matrix_solver_sm_t<m_N,storage_N> solver_mat;
- return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("W").equals(m_method()))
- {
- /* Woodbury Formula */
- typedef matrix_solver_w_t<m_N,storage_N> solver_mat;
- return plib::make_unique<solver_mat>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("SOR").equals(m_method()))
- {
- typedef matrix_solver_SOR_t<m_N,storage_N> solver_GS;
- return plib::make_unique<solver_GS>(netlist(), solvername, &m_params, size);
- }
- else if (pstring("GMRES").equals(m_method()))
- {
- typedef matrix_solver_GMRES_t<m_N,storage_N> solver_GMRES;
- return plib::make_unique<solver_GMRES>(netlist(), solvername, &m_params, size);
- }
- else
- {
- log().fatal(MF_1_UNKNOWN_SOLVER_TYPE, m_method());
- return nullptr;
- }
+ log().fatal(MF_1_UNKNOWN_SOLVER_TYPE, m_method());
+ return nullptr;
}
}
@@ -303,61 +295,68 @@ void NETLIB_NAME(solver)::post_start()
{
std::unique_ptr<matrix_solver_t> ms;
std::size_t net_count = grp.size();
+ pstring sname = plib::pfmt("Solver_{1}")(m_mat_solvers.size());
switch (net_count)
{
#if 1
case 1:
- ms = create_solver<1,1>(1, false);
+ if (use_specific)
+ ms = plib::make_unique<matrix_solver_direct1_t>(netlist(), sname, &m_params);
+ else
+ ms = create_solver<1,1>(1, sname);
break;
case 2:
- ms = create_solver<2,2>(2, false);
+ if (use_specific)
+ ms = plib::make_unique<matrix_solver_direct2_t>(netlist(), sname, &m_params);
+ else
+ ms = create_solver<2,2>(2, sname);
break;
case 3:
- ms = create_solver<3,3>(3, use_specific);
+ ms = create_solver<3,3>(3, sname);
break;
case 4:
- ms = create_solver<4,4>(4, use_specific);
+ ms = create_solver<4,4>(4, sname);
break;
case 5:
- ms = create_solver<5,5>(5, use_specific);
+ ms = create_solver<5,5>(5, sname);
break;
case 6:
- ms = create_solver<6,6>(6, use_specific);
+ ms = create_solver<6,6>(6, sname);
break;
case 7:
- ms = create_solver<7,7>(7, use_specific);
+ ms = create_solver<7,7>(7, sname);
break;
case 8:
- ms = create_solver<8,8>(8, use_specific);
+ ms = create_solver<8,8>(8, sname);
break;
case 9:
- ms = create_solver<9,9>(9, use_specific);
+ ms = create_solver<9,9>(9, sname);
break;
case 10:
- ms = create_solver<10,10>(10, use_specific);
+ ms = create_solver<10,10>(10, sname);
break;
case 11:
- ms = create_solver<11,11>(11, use_specific);
+ ms = create_solver<11,11>(11, sname);
break;
case 12:
- ms = create_solver<12,12>(12, use_specific);
+ ms = create_solver<12,12>(12, sname);
break;
case 15:
- ms = create_solver<15,15>(15, use_specific);
+ ms = create_solver<15,15>(15, sname);
break;
case 31:
- ms = create_solver<31,31>(31, use_specific);
+ ms = create_solver<31,31>(31, sname);
break;
case 35:
- ms = create_solver<31,31>(31, use_specific);
+ ms = create_solver<31,31>(31, sname);
break;
case 49:
- ms = create_solver<49,49>(49, use_specific);
+ ms = create_solver<49,49>(49, sname);
break;
#if 0
case 87:
- ms = create_solver<87,87>(87, use_specific);
+ ms = create_solver<87,87>(87, sname);
break;
#endif
#endif
@@ -365,25 +364,25 @@ void NETLIB_NAME(solver)::post_start()
log().warning(MW_1_NO_SPECIFIC_SOLVER, net_count);
if (net_count <= 8)
{
- ms = create_solver<0, 8>(net_count, use_specific);
+ ms = create_solver<0, 8>(net_count, sname);
}
else if (net_count <= 16)
{
- ms = create_solver<0,16>(net_count, use_specific);
+ ms = create_solver<0,16>(net_count, sname);
}
else if (net_count <= 32)
{
- ms = create_solver<0,32>(net_count, use_specific);
+ ms = create_solver<0,32>(net_count, sname);
}
else
if (net_count <= 64)
{
- ms = create_solver<0,64>(net_count, use_specific);
+ ms = create_solver<0,64>(net_count, sname);
}
else
if (net_count <= 128)
{
- ms = create_solver<0,128>(net_count, use_specific);
+ ms = create_solver<0,128>(net_count, sname);
}
else
{
diff --git a/src/lib/netlist/solver/nld_solver.h b/src/lib/netlist/solver/nld_solver.h
index bd3cc377217..fb50712e8f1 100644
--- a/src/lib/netlist/solver/nld_solver.h
+++ b/src/lib/netlist/solver/nld_solver.h
@@ -113,7 +113,7 @@ private:
solver_parameters_t m_params;
template <std::size_t m_N, std::size_t storage_N>
- std::unique_ptr<matrix_solver_t> create_solver(std::size_t size, bool use_specific);
+ std::unique_ptr<matrix_solver_t> create_solver(std::size_t size, const pstring &solvername);
};
} //namespace devices