From 6c075e602cf83b379b8fa2c981694134b679a538 Mon Sep 17 00:00:00 2001 From: couriersud Date: Thu, 31 Oct 2019 18:39:09 +0100 Subject: netlist: maintenance and simplifcation. (nw) - solver: align matrix population along the various solvers - solver: delete dead code - renamed nl_double to nl_fptype and use nl_fptype where previously double has been used. - renamed param_double_t to param_fp_t --- src/devices/machine/netlist.cpp | 28 ++--- src/lib/netlist/analog/nld_bjt.cpp | 78 ++++++------ src/lib/netlist/analog/nld_generic_models.h | 76 ++++++------ src/lib/netlist/analog/nld_mosfet.cpp | 174 +++++++++++++-------------- src/lib/netlist/analog/nld_opamps.cpp | 16 +-- src/lib/netlist/analog/nld_twoterm.h | 18 +-- src/lib/netlist/analog/nlid_fourterm.cpp | 38 +++--- src/lib/netlist/analog/nlid_fourterm.h | 16 +-- src/lib/netlist/analog/nlid_twoterm.cpp | 24 ++-- src/lib/netlist/analog/nlid_twoterm.h | 56 ++++----- src/lib/netlist/devices/nld_4066.cpp | 20 +-- src/lib/netlist/devices/nld_4316.cpp | 6 +- src/lib/netlist/devices/nld_74123.cpp | 10 +- src/lib/netlist/devices/nld_74ls629.cpp | 36 +++--- src/lib/netlist/devices/nld_log.cpp | 4 +- src/lib/netlist/devices/nld_mm5837.cpp | 10 +- src/lib/netlist/devices/nld_ne555.cpp | 8 +- src/lib/netlist/devices/nld_r2r_dac.cpp | 8 +- src/lib/netlist/devices/nld_schmitt.cpp | 8 +- src/lib/netlist/devices/nld_system.cpp | 2 +- src/lib/netlist/devices/nlid_cmos.h | 4 +- src/lib/netlist/devices/nlid_proxy.cpp | 10 +- src/lib/netlist/devices/nlid_proxy.h | 2 +- src/lib/netlist/devices/nlid_system.h | 26 ++-- src/lib/netlist/nl_base.cpp | 8 +- src/lib/netlist/nl_base.h | 90 +++++++------- src/lib/netlist/nl_config.h | 4 +- src/lib/netlist/nl_dice_compat.h | 18 +-- src/lib/netlist/nl_parser.cpp | 18 +-- src/lib/netlist/nl_parser.h | 2 +- src/lib/netlist/nl_setup.cpp | 16 +-- src/lib/netlist/nl_setup.h | 6 +- src/lib/netlist/nltypes.h | 4 +- src/lib/netlist/plib/ptokenizer.h | 1 + src/lib/netlist/prg/nltool.cpp | 10 +- src/lib/netlist/solver/nld_matrix_solver.cpp | 44 +++---- src/lib/netlist/solver/nld_matrix_solver.h | 156 +++++++++--------------- src/lib/netlist/solver/nld_ms_direct.h | 88 ++++++-------- src/lib/netlist/solver/nld_ms_direct1.h | 7 +- src/lib/netlist/solver/nld_ms_direct2.h | 16 +-- src/lib/netlist/solver/nld_ms_gcr.h | 8 +- src/lib/netlist/solver/nld_ms_gmres.h | 2 +- src/lib/netlist/solver/nld_ms_sm.h | 10 +- src/lib/netlist/solver/nld_ms_sor.h | 2 +- src/lib/netlist/solver/nld_ms_sor_mat.h | 17 ++- src/lib/netlist/solver/nld_ms_w.h | 11 +- src/lib/netlist/solver/nld_solver.cpp | 52 ++++---- src/lib/netlist/solver/nld_solver.h | 2 +- 48 files changed, 609 insertions(+), 661 deletions(-) diff --git a/src/devices/machine/netlist.cpp b/src/devices/machine/netlist.cpp index c6c0083e162..dae61de8e19 100644 --- a/src/devices/machine/netlist.cpp +++ b/src/devices/machine/netlist.cpp @@ -189,7 +189,7 @@ public: NETLIB_UPDATEI() { - nl_double cur = m_in(); + nl_fptype cur = m_in(); // FIXME: make this a parameter // avoid calls due to noise @@ -206,7 +206,7 @@ private: netlist::analog_input_t m_in; std::unique_ptr m_callback; // TODO: change to std::optional for C++17 netlist_mame_cpu_device *m_cpu_device; - netlist::state_var m_last; + netlist::state_var m_last; }; // ---------------------------------------------------------------------------------------- @@ -443,7 +443,7 @@ public: NETLIB_UPDATEI() { - nl_double val = m_in() * m_mult() + m_offset(); + nl_fptype val = m_in() * m_mult() + m_offset(); sound_update(exec().time()); /* ignore spikes */ if (std::abs(val) < 32767.0) @@ -463,8 +463,8 @@ public: } netlist::param_int_t m_channel; - netlist::param_double_t m_mult; - netlist::param_double_t m_offset; + netlist::param_fp_t m_mult; + netlist::param_fp_t m_offset; stream_sample_t *m_buffer; int m_bufsize; @@ -500,8 +500,8 @@ public: for (int i = 0; i < MAX_INPUT_CHANNELS; i++) { m_channels[i].m_param_name = netlist::pool().make_unique(*this, plib::pfmt("CHAN{1}")(i), ""); - m_channels[i].m_param_mult = netlist::pool().make_unique(*this, plib::pfmt("MULT{1}")(i), 1.0); - m_channels[i].m_param_offset = netlist::pool().make_unique(*this, plib::pfmt("OFFSET{1}")(i), 0.0); + m_channels[i].m_param_mult = netlist::pool().make_unique(*this, plib::pfmt("MULT{1}")(i), 1.0); + m_channels[i].m_param_offset = netlist::pool().make_unique(*this, plib::pfmt("OFFSET{1}")(i), 0.0); } } @@ -522,7 +522,7 @@ public: if (i != m_num_channels) state().log().fatal("sound input numbering has to be sequential!"); m_num_channels++; - m_channels[i].m_param = dynamic_cast(state().setup().find_param((*m_channels[i].m_param_name)(), true)); + m_channels[i].m_param = dynamic_cast(state().setup().find_param((*m_channels[i].m_param_name)(), true)); } } } @@ -533,7 +533,7 @@ public: { if (m_channels[i].m_buffer == nullptr) break; // stop, called outside of stream_update - const nl_double v = m_channels[i].m_buffer[m_pos]; + const nl_fptype v = m_channels[i].m_buffer[m_pos]; m_channels[i].m_param->setTo(v * (*m_channels[i].m_param_mult)() + (*m_channels[i].m_param_offset)()); } m_pos++; @@ -549,10 +549,10 @@ public: struct channel { netlist::unique_pool_ptr m_param_name; - netlist::param_double_t *m_param; + netlist::param_fp_t *m_param; stream_sample_t *m_buffer; - netlist::unique_pool_ptr m_param_mult; - netlist::unique_pool_ptr m_param_offset; + netlist::unique_pool_ptr m_param_mult; + netlist::unique_pool_ptr m_param_offset; }; channel m_channels[MAX_INPUT_CHANNELS]; netlist::netlist_time m_inc; @@ -688,7 +688,7 @@ void netlist_mame_analog_input_device::device_start() { LOGDEVCALLS("start\n"); netlist::param_t *p = this->nl_owner().setup().find_param(pstring(m_param_name)); - m_param = dynamic_cast(p); + m_param = dynamic_cast(p); if (m_param == nullptr) { fatalerror("device %s wrong parameter type for %s\n", basetag(), m_param_name); @@ -704,7 +704,7 @@ void netlist_mame_analog_input_device::validity_helper(validity_checker &valid, netlist::netlist_state_t &nlstate) const { netlist::param_t *p = nlstate.setup().find_param(pstring(m_param_name)); - auto *param = dynamic_cast(p); + auto *param = dynamic_cast(p); if (param == nullptr) { osd_printf_warning("device %s wrong parameter type for %s\n", basetag(), m_param_name); diff --git a/src/lib/netlist/analog/nld_bjt.cpp b/src/lib/netlist/analog/nld_bjt.cpp index 17d8405588a..0402f94e8b9 100644 --- a/src/lib/netlist/analog/nld_bjt.cpp +++ b/src/lib/netlist/analog/nld_bjt.cpp @@ -16,33 +16,33 @@ namespace netlist { namespace analog { - using constants = plib::constants; + using constants = plib::constants; class diode { public: diode() : m_Is(1e-15), m_VT(0.0258), m_VT_inv(1.0 / m_VT) {} - diode(const nl_double Is, const nl_double n) + diode(const nl_fptype Is, const nl_fptype n) { m_Is = Is; m_VT = 0.0258 * n; m_VT_inv = 1.0 / m_VT; } - void set(const nl_double Is, const nl_double n) + void set(const nl_fptype Is, const nl_fptype n) { m_Is = Is; m_VT = 0.0258 * n; m_VT_inv = 1.0 / m_VT; } - nl_double I(const nl_double V) const { return m_Is * std::exp(V * m_VT_inv) - m_Is; } - nl_double g(const nl_double V) const { return m_Is * m_VT_inv * std::exp(V * m_VT_inv); } - nl_double V(const nl_double I) const { return std::log1p(I / m_Is) * m_VT; } // log1p(x)=log(1.0 + x) - nl_double gI(const nl_double I) const { return m_VT_inv * (I + m_Is); } + nl_fptype I(const nl_fptype V) const { return m_Is * std::exp(V * m_VT_inv) - m_Is; } + nl_fptype g(const nl_fptype V) const { return m_Is * m_VT_inv * std::exp(V * m_VT_inv); } + nl_fptype V(const nl_fptype I) const { return std::log1p(I / m_Is) * m_VT; } // log1p(x)=log(1.0 + x) + nl_fptype gI(const nl_fptype I) const { return m_VT_inv * (I + m_Is); } private: - nl_double m_Is; - nl_double m_VT; - nl_double m_VT_inv; + nl_fptype m_Is; + nl_fptype m_VT; + nl_fptype m_VT_inv; }; // ----------------------------------------------------------------------------- @@ -203,9 +203,9 @@ namespace analog nld_twoterm m_RC; nld_twoterm m_BC; - nl_double m_gB; // base conductance / switch on - nl_double m_gC; // collector conductance / switch on - nl_double m_V; // internal voltage source + nl_fptype m_gB; // base conductance / switch on + nl_fptype m_gC; // collector conductance / switch on + nl_fptype m_V; // internal voltage source state_var m_state_on; private: @@ -267,8 +267,8 @@ namespace analog nld_twoterm m_D_EB; // gee, gec - gee, gce - gee, gee - gec | Ie nld_twoterm m_D_EC; // 0, -gec, -gcc, 0 | 0 - nl_double m_alpha_f; - nl_double m_alpha_r; + nl_fptype m_alpha_f; + nl_fptype m_alpha_r; NETLIB_SUBXX(analog, C) m_CJE; NETLIB_SUBXX(analog, C) m_CJC; @@ -316,14 +316,14 @@ namespace analog NETLIB_UPDATE_PARAM(QBJT_switch) { - nl_double IS = m_model.m_IS; - nl_double BF = m_model.m_BF; - nl_double NF = m_model.m_NF; - //nl_double VJE = m_model.dValue("VJE", 0.75); + nl_fptype IS = m_model.m_IS; + nl_fptype BF = m_model.m_BF; + nl_fptype NF = m_model.m_NF; + //nl_fptype VJE = m_model.dValue("VJE", 0.75); set_qtype((m_model.type() == "NPN") ? BJT_NPN : BJT_PNP); - nl_double alpha = BF / (1.0 + BF); + nl_fptype alpha = BF / (1.0 + BF); diode d(IS, NF); @@ -345,14 +345,14 @@ namespace analog NETLIB_UPDATE_TERMINALS(QBJT_switch) { - const nl_double m = (is_qtype( BJT_NPN) ? 1 : -1); + const nl_fptype m = (is_qtype( BJT_NPN) ? 1 : -1); const unsigned new_state = (m_RB.deltaV() * m > m_V ) ? 1 : 0; if (m_state_on ^ new_state) { - const nl_double gb = new_state ? m_gB : exec().gmin(); - const nl_double gc = new_state ? m_gC : exec().gmin(); - const nl_double v = new_state ? m_V * m : 0; + const nl_fptype gb = new_state ? m_gB : exec().gmin(); + const nl_fptype gc = new_state ? m_gC : exec().gmin(); + const nl_fptype v = new_state ? m_V * m : 0; m_RB.set_G_V_I(gb, v, 0.0); m_RC.set_G_V_I(gc, 0.0, 0.0); @@ -395,19 +395,19 @@ namespace analog NETLIB_UPDATE_TERMINALS(QBJT_EB) { - const nl_double polarity = (qtype() == BJT_NPN ? 1.0 : -1.0); + const nl_fptype polarity = (qtype() == BJT_NPN ? 1.0 : -1.0); m_gD_BE.update_diode(-m_D_EB.deltaV() * polarity); m_gD_BC.update_diode(-m_D_CB.deltaV() * polarity); - const nl_double gee = m_gD_BE.G(); - const nl_double gcc = m_gD_BC.G(); - const nl_double gec = m_alpha_r * gcc; - const nl_double gce = m_alpha_f * gee; - const nl_double sIe = -m_gD_BE.I() + m_alpha_r * m_gD_BC.I(); - const nl_double sIc = m_alpha_f * m_gD_BE.I() - m_gD_BC.I(); - const nl_double Ie = (sIe + gee * m_gD_BE.Vd() - gec * m_gD_BC.Vd()) * polarity; - const nl_double Ic = (sIc - gce * m_gD_BE.Vd() + gcc * m_gD_BC.Vd()) * polarity; + const nl_fptype gee = m_gD_BE.G(); + const nl_fptype gcc = m_gD_BC.G(); + const nl_fptype gec = m_alpha_r * gcc; + const nl_fptype gce = m_alpha_f * gee; + const nl_fptype sIe = -m_gD_BE.I() + m_alpha_r * m_gD_BC.I(); + const nl_fptype sIc = m_alpha_f * m_gD_BE.I() - m_gD_BC.I(); + const nl_fptype Ie = (sIe + gee * m_gD_BE.Vd() - gec * m_gD_BC.Vd()) * polarity; + const nl_fptype Ic = (sIc - gce * m_gD_BE.Vd() + gcc * m_gD_BC.Vd()) * polarity; // "Circuit Design", page 174 @@ -422,12 +422,12 @@ namespace analog NETLIB_UPDATE_PARAM(QBJT_EB) { - nl_double IS = m_model.m_IS; - nl_double BF = m_model.m_BF; - nl_double NF = m_model.m_NF; - nl_double BR = m_model.m_BR; - nl_double NR = m_model.m_NR; - //nl_double VJE = m_model.dValue("VJE", 0.75); + nl_fptype IS = m_model.m_IS; + nl_fptype BF = m_model.m_BF; + nl_fptype NF = m_model.m_NF; + nl_fptype BR = m_model.m_BR; + nl_fptype NR = m_model.m_NR; + //nl_fptype VJE = m_model.dValue("VJE", 0.75); set_qtype((m_model.type() == "NPN") ? BJT_NPN : BJT_PNP); diff --git a/src/lib/netlist/analog/nld_generic_models.h b/src/lib/netlist/analog/nld_generic_models.h index 1edc4abd320..af5c6ac4450 100644 --- a/src/lib/netlist/analog/nld_generic_models.h +++ b/src/lib/netlist/analog/nld_generic_models.h @@ -54,14 +54,14 @@ namespace analog // so that G depends on un+1 only and Ieq on un only. // In both cases, i = G * un+1 + Ieq - nl_double G(nl_double cap) const + nl_fptype G(nl_fptype cap) const { //return m_h * cap + m_gmin; return m_h * 0.5 * (cap + m_c) + m_gmin; //return m_h * cap + m_gmin; } - nl_double Ieq(nl_double cap, nl_double v) const + nl_fptype Ieq(nl_fptype cap, nl_fptype v) const { plib::unused_var(v); //return -m_h * 0.5 * ((cap + m_c) * m_v + (cap - m_c) * v) ; @@ -69,20 +69,20 @@ namespace analog //return -m_h * cap * m_v; } - void timestep(nl_double cap, nl_double v, nl_double step) + void timestep(nl_fptype cap, nl_fptype v, nl_fptype step) { m_h = 1.0 / step; m_c = cap; m_v = v; } - void setparams(nl_double gmin) { m_gmin = gmin; } + void setparams(nl_fptype gmin) { m_gmin = gmin; } private: - state_var m_h; - state_var m_c; - state_var m_v; - nl_double m_gmin; + state_var m_h; + state_var m_c; + state_var m_v; + nl_fptype m_gmin; }; // "Circuit simulation", page 274 @@ -98,24 +98,24 @@ namespace analog } capacitor_e type() const { return capacitor_e::CONSTANT_CAPACITY; } - nl_double G(nl_double cap) const { return cap * m_h + m_gmin; } - nl_double Ieq(nl_double cap, nl_double v) const + nl_fptype G(nl_fptype cap) const { return cap * m_h + m_gmin; } + nl_fptype Ieq(nl_fptype cap, nl_fptype v) const { plib::unused_var(v); return - G(cap) * m_v; } - void timestep(nl_double cap, nl_double v, nl_double step) + void timestep(nl_fptype cap, nl_fptype v, nl_fptype step) { plib::unused_var(cap); m_h = 1.0 / step; m_v = v; } - void setparams(nl_double gmin) { m_gmin = gmin; } + void setparams(nl_fptype gmin) { m_gmin = gmin; } private: - state_var m_h; - state_var m_v; - nl_double m_gmin; + state_var m_h; + state_var m_v; + nl_fptype m_gmin; }; // ----------------------------------------------------------------------------- @@ -149,17 +149,17 @@ namespace analog set_param(1e-15, 1, 1e-15, 300.0); } - void update_diode(const nl_double nVd) + void update_diode(const nl_fptype nVd) { - nl_double IseVDVt(0.0); + nl_fptype IseVDVt(0.0); if (TYPE == diode_e::BIPOLAR) { - //printf("%s: %g %g\n", m_name.c_str(), nVd, (double) m_Vd); + //printf("%s: %g %g\n", m_name.c_str(), nVd, (nl_fptype) m_Vd); if (nVd > m_Vcrit) { - const nl_double d = std::min(1e100, nVd - m_Vd); - const nl_double a = std::abs(d) * m_VtInv; + const nl_fptype d = std::min(1e100, nVd - m_Vd); + const nl_fptype a = std::abs(d) * m_VtInv; m_Vd = m_Vd + (d < 0 ? -1.0 : 1.0) * std::log1p(a) * m_Vt; } else @@ -196,7 +196,7 @@ namespace analog } } - void set_param(const nl_double Is, const nl_double n, nl_double gmin, nl_double temp) + void set_param(const nl_fptype Is, const nl_fptype n, nl_fptype gmin, nl_fptype temp) { m_Is = Is; m_logIs = std::log(Is); @@ -213,27 +213,27 @@ namespace analog } - nl_double I() const { return m_Id; } - nl_double G() const { return m_G; } - nl_double Ieq() const { return (m_Id - m_Vd * m_G); } - nl_double Vd() const { return m_Vd; } + nl_fptype I() const { return m_Id; } + nl_fptype G() const { return m_G; } + nl_fptype Ieq() const { return (m_Id - m_Vd * m_G); } + nl_fptype Vd() const { return m_Vd; } /* owning object must save those ... */ private: - state_var m_Vd; - state_var m_Id; - state_var m_G; - - nl_double m_Vt; - nl_double m_Vmin; - nl_double m_Is; - nl_double m_logIs; - nl_double m_n; - nl_double m_gmin; - - nl_double m_VtInv; - nl_double m_Vcrit; + state_var m_Vd; + state_var m_Id; + state_var m_G; + + nl_fptype m_Vt; + nl_fptype m_Vmin; + nl_fptype m_Is; + nl_fptype m_logIs; + nl_fptype m_n; + nl_fptype m_gmin; + + nl_fptype m_VtInv; + nl_fptype m_Vcrit; pstring m_name; }; diff --git a/src/lib/netlist/analog/nld_mosfet.cpp b/src/lib/netlist/analog/nld_mosfet.cpp index 6349029e65c..3bd4d4fa2c4 100644 --- a/src/lib/netlist/analog/nld_mosfet.cpp +++ b/src/lib/netlist/analog/nld_mosfet.cpp @@ -31,7 +31,7 @@ namespace netlist namespace analog { - using constants = plib::constants; + using constants = plib::constants; // ----------------------------------------------------------------------------- // nld_FET - Base classes @@ -223,7 +223,7 @@ namespace analog m_polarity = qtype() == FET_NMOS ? 1.0 : -1.0; m_capmod = m_model.m_CAPMOD; - // printf("capmod %d %g %g\n", m_capmod, (double)m_model.m_VTO, m_polarity); + // printf("capmod %d %g %g\n", m_capmod, (nl_fptype)m_model.m_VTO, m_polarity); nl_assert_always(m_capmod == 0 || m_capmod == 2, "Error: CAPMODEL invalid value for " + m_model.name()); /* @@ -243,7 +243,7 @@ namespace analog m_Leff = m_model.m_L - 2 * m_model.m_LD; nl_assert_always(m_Leff > 0.0, "Effective Lateral diffusion would be negative for model " + m_model.name()); - nl_double Cox = (m_model.m_TOX > 0.0) ? (constants::eps_SiO2() * constants::eps_0() / m_model.m_TOX) : 0.0; + nl_fptype Cox = (m_model.m_TOX > 0.0) ? (constants::eps_SiO2() * constants::eps_0() / m_model.m_TOX) : 0.0; // calculate DC transconductance coefficient if (m_model.m_KP > 0) @@ -254,7 +254,7 @@ namespace analog m_beta = 2e-5 * m_model.m_W / m_Leff; //FIXME::UT can disappear - const double Vt = constants::T0() * constants::k_b() / constants::Q_e(); + const nl_fptype Vt = constants::T0() * constants::k_b() / constants::Q_e(); // calculate surface potential if not given @@ -298,12 +298,12 @@ namespace analog { if (m_capmod != 0) { - //const nl_double Ugd = -m_DG.deltaV() * m_polarity; // Gate - Drain - //const nl_double Ugs = -m_SG.deltaV() * m_polarity; // Gate - Source - const nl_double Ugd = m_Vgd; // Gate - Drain - const nl_double Ugs = m_Vgs; // Gate - Source - const nl_double Ubs = 0.0; // Bulk - Source == 0 if connected - const nl_double Ugb = Ugs - Ubs; + //const nl_nl_fptype Ugd = -m_DG.deltaV() * m_polarity; // Gate - Drain + //const nl_nl_fptype Ugs = -m_SG.deltaV() * m_polarity; // Gate - Source + const nl_fptype Ugd = m_Vgd; // Gate - Drain + const nl_fptype Ugs = m_Vgs; // Gate - Source + const nl_fptype Ubs = 0.0; // Bulk - Source == 0 if connected + const nl_fptype Ugb = Ugs - Ubs; m_cap_gb.timestep(m_Cgb, Ugb, step); m_cap_gs.timestep(m_Cgs, Ugs, step); @@ -343,43 +343,43 @@ namespace analog generic_capacitor m_cap_gs; generic_capacitor m_cap_gd; - nl_double m_phi; - nl_double m_gamma; - nl_double m_vto; - nl_double m_beta; - nl_double m_lambda; + nl_fptype m_phi; + nl_fptype m_gamma; + nl_fptype m_vto; + nl_fptype m_beta; + nl_fptype m_lambda; /* used in capacitance calculation */ - nl_double m_Leff; - nl_double m_CoxWL; - nl_double m_polarity; + nl_fptype m_Leff; + nl_fptype m_CoxWL; + nl_fptype m_polarity; /* capacitance values */ - nl_double m_Cgb; - nl_double m_Cgs; - nl_double m_Cgd; + nl_fptype m_Cgb; + nl_fptype m_Cgs; + nl_fptype m_Cgd; int m_capmod; - state_var m_Vgs; - state_var m_Vgd; + state_var m_Vgs; + state_var m_Vgd; void set_cap(generic_capacitor cap, - nl_double capval, nl_double V, - nl_double &g11, nl_double &g12, nl_double &g21, nl_double &g22, - nl_double &I1, nl_double &I2) + nl_fptype capval, nl_fptype V, + nl_fptype &g11, nl_fptype &g12, nl_fptype &g21, nl_fptype &g22, + nl_fptype &I1, nl_fptype &I2) { - const nl_double I = cap.Ieq(capval, V) * m_polarity; - const nl_double G = cap.G(capval); + const nl_fptype I = cap.Ieq(capval, V) * m_polarity; + const nl_fptype G = cap.G(capval); g11 += G; g12 -= G; g21 -= G; g22 += G; I1 -= I; I2 += I; //printf("Cap: %g\n", capval); } - void calculate_caps(nl_double Vgs, nl_double Vgd, nl_double Vth, - nl_double &Cgs, nl_double &Cgd, nl_double &Cgb) + void calculate_caps(nl_fptype Vgs, nl_fptype Vgd, nl_fptype Vth, + nl_fptype &Cgs, nl_fptype &Cgd, nl_fptype &Cgb) { - nl_double Vctrl = Vgs - Vth * m_polarity; + nl_fptype Vctrl = Vgs - Vth * m_polarity; // Cut off - now further differentiated into 3 different formulas // Accumulation if (Vctrl <= -m_phi) @@ -403,8 +403,8 @@ namespace analog } else { - const nl_double Vdsat = Vctrl; - const nl_double Vds = Vgs - Vgd; + const nl_fptype Vdsat = Vctrl; + const nl_fptype Vds = Vgs - Vgd; // saturation if (Vdsat <= Vds) { @@ -415,8 +415,8 @@ namespace analog else { // linear - const nl_double Sqr1 = std::pow(Vdsat - Vds, 2); - const nl_double Sqr2 = std::pow(2.0 * Vdsat - Vds, 2); + const nl_fptype Sqr1 = std::pow(Vdsat - Vds, 2); + const nl_fptype Sqr2 = std::pow(2.0 * Vdsat - Vds, 2); Cgb = 0; Cgs = m_CoxWL * (1.0 - Sqr1 / Sqr2) * (2.0 / 3.0); Cgd = m_CoxWL * (1.0 - Vdsat * Vdsat / Sqr2) * (2.0 / 3.0); @@ -442,13 +442,13 @@ namespace analog NETLIB_UPDATE_TERMINALS(MOSFET) { - nl_double Vgd = -m_DG.deltaV() * m_polarity; // Gate - Drain - nl_double Vgs = -m_SG.deltaV() * m_polarity; // Gate - Source + nl_fptype Vgd = -m_DG.deltaV() * m_polarity; // Gate - Drain + nl_fptype Vgs = -m_SG.deltaV() * m_polarity; // Gate - Source // limit step sizes - const nl_double k = 3.5; // see "Circuit Simulation", page 185 - nl_double d = (Vgs - m_Vgs); + const nl_fptype k = 3.5; // see "Circuit Simulation", page 185 + nl_fptype d = (Vgs - m_Vgs); Vgs = m_Vgs + 1.0/k * (d < 0 ? -1.0 : 1.0) * std::log1p(k * std::abs(d)); d = (Vgd - m_Vgd); Vgd = m_Vgd + 1.0/k * (d < 0 ? -1.0 : 1.0) * std::log1p(k * std::abs(d)); @@ -456,10 +456,10 @@ namespace analog m_Vgs = Vgs; m_Vgd = Vgd; - const nl_double Vbs = 0.0; // Bulk - Source == 0 if connected - //const nl_double Vbd = m_SD.deltaV() * m_polarity; // Bulk - Drain = Source - Drain - const nl_double Vds = Vgs - Vgd; - const nl_double Vbd = -Vds; // Bulk - Drain = Source - Drain + const nl_fptype Vbs = 0.0; // Bulk - Source == 0 if connected + //const nl_nl_fptype Vbd = m_SD.deltaV() * m_polarity; // Bulk - Drain = Source - Drain + const nl_fptype Vds = Vgs - Vgd; + const nl_fptype Vbd = -Vds; // Bulk - Drain = Source - Drain #if (!BODY_CONNECTED_TO_SOURCE) m_D_BS.update_diode(Vbs); @@ -471,14 +471,14 @@ namespace analog const bool is_forward = Vds >= 0; // calculate Vth - const nl_double Vbulk = is_forward ? Vbs : Vbd; - const nl_double phi_m_Vbulk = (m_phi > Vbulk) ? std::sqrt(m_phi - Vbulk) : 0.0; - const nl_double Vth = m_vto * m_polarity + m_gamma * (phi_m_Vbulk - std::sqrt(m_phi)); + const nl_fptype Vbulk = is_forward ? Vbs : Vbd; + const nl_fptype phi_m_Vbulk = (m_phi > Vbulk) ? std::sqrt(m_phi - Vbulk) : 0.0; + const nl_fptype Vth = m_vto * m_polarity + m_gamma * (phi_m_Vbulk - std::sqrt(m_phi)); - const nl_double Vctrl = (is_forward ? Vgs : Vgd) - Vth; + const nl_fptype Vctrl = (is_forward ? Vgs : Vgd) - Vth; - nl_double Ids(0), gm(0), gds(0), gmb(0); - const nl_double absVds = std::abs(Vds); + nl_fptype Ids(0), gm(0), gds(0), gmb(0); + const nl_fptype absVds = std::abs(Vds); if (Vctrl <= 0.0) { @@ -490,7 +490,7 @@ namespace analog } else { - const nl_double beta = m_beta * (1.0 + m_lambda * absVds); + const nl_fptype beta = m_beta * (1.0 + m_lambda * absVds); if (Vctrl <= absVds) { // saturation region @@ -507,63 +507,63 @@ namespace analog } // backgate transconductance - const nl_double bgtc = (phi_m_Vbulk != 0.0) ? (m_gamma / phi_m_Vbulk / 2.0) : 0.0; + const nl_fptype bgtc = (phi_m_Vbulk != 0.0) ? (m_gamma / phi_m_Vbulk / 2.0) : 0.0; gmb = gm * bgtc; } // FIXME: these are needed to compute capacitance - // nl_double Udsat = pol * std::max (Utst, 0.0); + // nl_fptype Udsat = pol * std::max (Utst, 0.0); // Uon = pol * Vth; // compute bulk diode equivalent currents - const nl_double IeqBD = m_D_BD.Ieq(); - const nl_double gbd = m_D_BD.G(); + const nl_fptype IeqBD = m_D_BD.Ieq(); + const nl_fptype gbd = m_D_BD.G(); #if (!BODY_CONNECTED_TO_SOURCE) - const nl_double IeqBS = m_D_BS.Ieq(); - const nl_double gbs = m_D_BS.G(); + const nl_fptype IeqBS = m_D_BS.Ieq(); + const nl_fptype gbs = m_D_BS.G(); #else - const nl_double IeqBS = 0.0; - const nl_double gbs = 0.0; + const nl_fptype IeqBS = 0.0; + const nl_fptype gbs = 0.0; #endif // exchange controlling nodes if necessary - const nl_double gsource = is_forward ? (gm + gmb) : 0; - const nl_double gdrain = is_forward ? 0.0 : (gm + gmb); + const nl_fptype gsource = is_forward ? (gm + gmb) : 0; + const nl_fptype gdrain = is_forward ? 0.0 : (gm + gmb); - const nl_double IeqDS = (is_forward) ? + const nl_fptype IeqDS = (is_forward) ? Ids - gm * Vgs - gmb * Vbs - gds * Vds : -Ids - gm * Vgd - gmb * Vbd - gds * Vds; // IG = 0 - nl_double IG = 0.0; - nl_double ID = (+IeqBD - IeqDS) * m_polarity; - nl_double IS = (+IeqBS + IeqDS) * m_polarity; - nl_double IB = (-IeqBD - IeqBS) * m_polarity; - - nl_double gGG = 0.0; - nl_double gGD = 0.0; - nl_double gGS = 0.0; - nl_double gGB = 0.0; - - nl_double gDG = gm; - nl_double gDD = gds + gbd - gdrain; - const nl_double gDS = -gds - gsource; - const nl_double gDB = gmb - gbd; - - nl_double gSG = -gm; - const nl_double gSD = -gds + gdrain; - nl_double gSS = gbs + gds + gsource; - const nl_double gSB = -gbs - gmb; - - nl_double gBG = 0.0; - const nl_double gBD = -gbd; - const nl_double gBS = -gbs; - nl_double gBB = gbs + gbd; + nl_fptype IG = 0.0; + nl_fptype ID = (+IeqBD - IeqDS) * m_polarity; + nl_fptype IS = (+IeqBS + IeqDS) * m_polarity; + nl_fptype IB = (-IeqBD - IeqBS) * m_polarity; + + nl_fptype gGG = 0.0; + nl_fptype gGD = 0.0; + nl_fptype gGS = 0.0; + nl_fptype gGB = 0.0; + + nl_fptype gDG = gm; + nl_fptype gDD = gds + gbd - gdrain; + const nl_fptype gDS = -gds - gsource; + const nl_fptype gDB = gmb - gbd; + + nl_fptype gSG = -gm; + const nl_fptype gSD = -gds + gdrain; + nl_fptype gSS = gbs + gds + gsource; + const nl_fptype gSB = -gbs - gmb; + + nl_fptype gBG = 0.0; + const nl_fptype gBD = -gbd; + const nl_fptype gBS = -gbs; + nl_fptype gBB = gbs + gbd; if (m_capmod != 0) { - const nl_double Vgb = Vgs - Vbs; + const nl_fptype Vgb = Vgs - Vbs; if (is_forward) calculate_caps(Vgs, Vgd, Vth, m_Cgs, m_Cgd, m_Cgb); @@ -576,7 +576,7 @@ namespace analog } // Source connected to body, Diode S-B shorted! - const nl_double gSSBB = gSS + gBB + gBS + gSB; + const nl_fptype gSSBB = gSS + gBB + gBS + gSB; // S G m_SG.set_mat( gSSBB, gSG + gBG, +(IS + IB), // S diff --git a/src/lib/netlist/analog/nld_opamps.cpp b/src/lib/netlist/analog/nld_opamps.cpp index 24f239e9455..77ca356116c 100644 --- a/src/lib/netlist/analog/nld_opamps.cpp +++ b/src/lib/netlist/analog/nld_opamps.cpp @@ -197,9 +197,9 @@ namespace netlist NETLIB_UPDATE(opamp) { - const double cVt = 0.0258 * 1.0; // * m_n; - const double cId = m_model.m_DAB; // 3 mA - const double cVd = cVt * std::log(cId / 1e-15 + 1.0); + const nl_fptype cVt = 0.0258 * 1.0; // * m_n; + const nl_fptype cId = m_model.m_DAB; // 3 mA + const nl_fptype cVd = cVt * std::log(cId / 1e-15 + 1.0); m_VH.push(m_VCC() - m_model.m_VLH - cVd); m_VL.push(m_GND() + m_model.m_VLL + cVd); @@ -212,16 +212,16 @@ namespace netlist if (m_type == 1) { - double RO = m_model.m_RO; - double G = m_model.m_UGF / m_model.m_FPF / RO; + nl_fptype RO = m_model.m_RO; + nl_fptype G = m_model.m_UGF / m_model.m_FPF / RO; m_RP.set_R(RO); m_G1.m_G.setTo(G); } if (m_type == 3 || m_type == 2) { - double CP = m_model.m_DAB / m_model.m_SLEW; - double RP = 0.5 / constants::pi() / CP / m_model.m_FPF; - double G = m_model.m_UGF / m_model.m_FPF / RP; + nl_fptype CP = m_model.m_DAB / m_model.m_SLEW; + nl_fptype RP = 0.5 / constants::pi() / CP / m_model.m_FPF; + nl_fptype G = m_model.m_UGF / m_model.m_FPF / RP; //printf("OPAMP %s: %g %g %g\n", name().c_str(), CP, RP, G); if (m_model.m_SLEW / (4.0 * constants::pi() * 0.0258) < m_model.m_UGF) diff --git a/src/lib/netlist/analog/nld_twoterm.h b/src/lib/netlist/analog/nld_twoterm.h index b175f40af97..fbebe8be6cf 100644 --- a/src/lib/netlist/analog/nld_twoterm.h +++ b/src/lib/netlist/analog/nld_twoterm.h @@ -53,15 +53,15 @@ #warning "Do not include rescap.h in a netlist environment" #endif #ifndef RES_R -#define RES_R(res) (static_cast(res)) -#define RES_K(res) (static_cast(res) * 1e3) -#define RES_M(res) (static_cast(res) * 1e6) -#define CAP_U(cap) (static_cast(cap) * 1e-6) -#define CAP_N(cap) (static_cast(cap) * 1e-9) -#define CAP_P(cap) (static_cast(cap) * 1e-12) -#define IND_U(ind) (static_cast(ind) * 1e-6) -#define IND_N(ind) (static_cast(ind) * 1e-9) -#define IND_P(ind) (static_cast(ind) * 1e-12) +#define RES_R(res) (static_cast(res)) +#define RES_K(res) (static_cast(res) * 1e3) +#define RES_M(res) (static_cast(res) * 1e6) +#define CAP_U(cap) (static_cast(cap) * 1e-6) +#define CAP_N(cap) (static_cast(cap) * 1e-9) +#define CAP_P(cap) (static_cast(cap) * 1e-12) +#define IND_U(ind) (static_cast(ind) * 1e-6) +#define IND_N(ind) (static_cast(ind) * 1e-9) +#define IND_P(ind) (static_cast(ind) * 1e-12) #endif #endif /* NLD_TWOTERM_H_ */ diff --git a/src/lib/netlist/analog/nlid_fourterm.cpp b/src/lib/netlist/analog/nlid_fourterm.cpp index 7fa6a2f3809..49955c0c952 100644 --- a/src/lib/netlist/analog/nlid_fourterm.cpp +++ b/src/lib/netlist/analog/nlid_fourterm.cpp @@ -23,17 +23,17 @@ namespace netlist NETLIB_RESET(VCCS) { - const nl_double m_mult = m_G() * m_gfac; // 1.0 ==> 1V ==> 1A - const nl_double GI = plib::constants::one() / m_RI(); + const nl_fptype m_mult = m_G() * m_gfac; // 1.0 ==> 1V ==> 1A + const nl_fptype GI = plib::constants::one() / m_RI(); m_IP.set_conductivity(GI); m_IN.set_conductivity(GI); - m_OP.set_go_gt(-m_mult, plib::constants::zero()); - m_OP1.set_go_gt(m_mult, plib::constants::zero()); + m_OP.set_go_gt(-m_mult, plib::constants::zero()); + m_OP1.set_go_gt(m_mult, plib::constants::zero()); - m_ON.set_go_gt(m_mult, plib::constants::zero()); - m_ON1.set_go_gt(-m_mult, plib::constants::zero()); + m_ON.set_go_gt(m_mult, plib::constants::zero()); + m_ON1.set_go_gt(-m_mult, plib::constants::zero()); } NETLIB_UPDATE(VCCS) @@ -65,25 +65,25 @@ NETLIB_UPDATE_PARAM(LVCCS) NETLIB_UPDATE_TERMINALS(LVCCS) { - const nl_double m_mult = m_G() * m_gfac; // 1.0 ==> 1V ==> 1A - const nl_double vi = m_IP.net().Q_Analog() - m_IN.net().Q_Analog(); + const nl_fptype m_mult = m_G() * m_gfac; // 1.0 ==> 1V ==> 1A + const nl_fptype vi = m_IP.net().Q_Analog() - m_IN.net().Q_Analog(); if (std::abs(m_mult / m_cur_limit() * vi) > 0.5) m_vi = m_vi + 0.2*std::tanh((vi - m_vi)/0.2); else m_vi = vi; - const nl_double x = m_mult / m_cur_limit() * m_vi; - const nl_double X = std::tanh(x); + const nl_fptype x = m_mult / m_cur_limit() * m_vi; + const nl_fptype X = std::tanh(x); - const nl_double beta = m_mult * (1.0 - X*X); - const nl_double I = m_cur_limit() * X - beta * m_vi; + const nl_fptype beta = m_mult * (1.0 - X*X); + const nl_fptype I = m_cur_limit() * X - beta * m_vi; - m_OP.set_go_gt_I(-beta, plib::constants::zero(), I); - m_OP1.set_go_gt(beta, plib::constants::zero()); + m_OP.set_go_gt_I(-beta, plib::constants::zero(), I); + m_OP1.set_go_gt(beta, plib::constants::zero()); - m_ON.set_go_gt_I(beta, plib::constants::zero(), -I); - m_ON1.set_go_gt(-beta, plib::constants::zero()); + m_ON.set_go_gt_I(beta, plib::constants::zero(), -I); + m_ON1.set_go_gt(-beta, plib::constants::zero()); } // ---------------------------------------------------------------------------------------- @@ -106,11 +106,11 @@ NETLIB_UPDATE_PARAM(CCCS) NETLIB_RESET(VCVS) { - m_gfac = plib::constants::one() / m_RO(); + m_gfac = plib::constants::one() / m_RO(); NETLIB_NAME(VCCS)::reset(); - m_OP2.set_conductivity(plib::constants::one() / m_RO()); - m_ON2.set_conductivity(plib::constants::one() / m_RO()); + m_OP2.set_conductivity(plib::constants::one() / m_RO()); + m_ON2.set_conductivity(plib::constants::one() / m_RO()); } } //namespace analog diff --git a/src/lib/netlist/analog/nlid_fourterm.h b/src/lib/netlist/analog/nlid_fourterm.h index 5ca6a747116..7faaac926c1 100644 --- a/src/lib/netlist/analog/nlid_fourterm.h +++ b/src/lib/netlist/analog/nlid_fourterm.h @@ -51,13 +51,13 @@ namespace netlist { { connect(m_OP, m_OP1); connect(m_ON, m_ON1); - m_gfac = plib::constants::one(); + m_gfac = plib::constants::one(); } NETLIB_RESETI(); - param_double_t m_G; - param_double_t m_RI; + param_fp_t m_G; + param_fp_t m_RI; protected: NETLIB_UPDATEI(); @@ -76,7 +76,7 @@ namespace netlist { terminal_t m_OP1; terminal_t m_ON1; - nl_double m_gfac; + nl_fptype m_gfac; }; /* Limited Current source*/ @@ -99,8 +99,8 @@ namespace netlist { NETLIB_UPDATE_TERMINALSI(); private: - param_double_t m_cur_limit; /* current limit */ - nl_double m_vi; + param_fp_t m_cur_limit; /* current limit */ + nl_fptype m_vi; }; // ---------------------------------------------------------------------------------------- @@ -131,7 +131,7 @@ namespace netlist { public: NETLIB_CONSTRUCTOR_DERIVED(CCCS, VCCS) { - m_gfac = plib::constants::one() / m_RI(); + m_gfac = plib::constants::one() / m_RI(); } NETLIB_RESETI(); @@ -184,7 +184,7 @@ namespace netlist { NETLIB_RESETI(); - param_double_t m_RO; + param_fp_t m_RO; private: //NETLIB_UPDATEI(); diff --git a/src/lib/netlist/analog/nlid_twoterm.cpp b/src/lib/netlist/analog/nlid_twoterm.cpp index aaddb65387a..bc63e625c1a 100644 --- a/src/lib/netlist/analog/nlid_twoterm.cpp +++ b/src/lib/netlist/analog/nlid_twoterm.cpp @@ -62,12 +62,12 @@ NETLIB_RESET(R_base) NETLIB_RESET(POT) { - nl_double v = m_Dial(); + nl_fptype v = m_Dial(); if (m_DialIsLog()) v = (std::exp(v) - 1.0) / (std::exp(1.0) - 1.0); m_R1.set_R(std::max(m_R() * v, exec().gmin())); - m_R2.set_R(std::max(m_R() * (plib::constants::one() - v), exec().gmin())); + m_R2.set_R(std::max(m_R() * (plib::constants::one() - v), exec().gmin())); } NETLIB_UPDATE_PARAM(POT) @@ -75,13 +75,13 @@ NETLIB_UPDATE_PARAM(POT) m_R1.solve_now(); m_R2.solve_now(); - nl_double v = m_Dial(); + nl_fptype v = m_Dial(); if (m_DialIsLog()) v = (std::exp(v) - 1.0) / (std::exp(1.0) - 1.0); if (m_Reverse()) v = 1.0 - v; m_R1.set_R(std::max(m_R() * v, exec().gmin())); - m_R2.set_R(std::max(m_R() * (plib::constants::one() - v), exec().gmin())); + m_R2.set_R(std::max(m_R() * (plib::constants::one() - v), exec().gmin())); } @@ -91,7 +91,7 @@ NETLIB_UPDATE_PARAM(POT) NETLIB_RESET(POT2) { - nl_double v = m_Dial(); + nl_fptype v = m_Dial(); if (m_DialIsLog()) v = (std::exp(v) - 1.0) / (std::exp(1.0) - 1.0); @@ -105,7 +105,7 @@ NETLIB_UPDATE_PARAM(POT2) { m_R1.solve_now(); - nl_double v = m_Dial(); + nl_fptype v = m_Dial(); if (m_DialIsLog()) v = (std::exp(v) - 1.0) / (std::exp(1.0) - 1.0); @@ -148,8 +148,8 @@ NETLIB_TIMESTEP(L) NETLIB_RESET(D) { - nl_double Is = m_model.m_IS; - nl_double n = m_model.m_N; + nl_fptype Is = m_model.m_IS; + nl_fptype n = m_model.m_N; m_D.set_param(Is, n, exec().gmin(), constants::T0()); set_G_V_I(m_D.G(), 0.0, m_D.Ieq()); @@ -157,8 +157,8 @@ NETLIB_RESET(D) NETLIB_UPDATE_PARAM(D) { - nl_double Is = m_model.m_IS; - nl_double n = m_model.m_N; + nl_fptype Is = m_model.m_IS; + nl_fptype n = m_model.m_N; m_D.set_param(Is, n, exec().gmin(), constants::T0()); } @@ -166,8 +166,8 @@ NETLIB_UPDATE_PARAM(D) NETLIB_UPDATE_TERMINALS(D) { m_D.update_diode(deltaV()); - const nl_double G = m_D.G(); - const nl_double I = m_D.Ieq(); + const nl_fptype G = m_D.G(); + const nl_fptype I = m_D.Ieq(); set_mat( G, -G, -I, -G, G, I); //set(m_D.G(), 0.0, m_D.Ieq()); diff --git a/src/lib/netlist/analog/nlid_twoterm.h b/src/lib/netlist/analog/nlid_twoterm.h index f1931a2f81e..4f448615380 100644 --- a/src/lib/netlist/analog/nlid_twoterm.h +++ b/src/lib/netlist/analog/nlid_twoterm.h @@ -91,20 +91,20 @@ namespace analog void solve_later(netlist_time delay = netlist_time::quantum()); - void set_G_V_I(const nl_double G, const nl_double V, const nl_double I) + void set_G_V_I(const nl_fptype G, const nl_fptype V, const nl_fptype I) { /* GO, GT, I */ m_P.set_go_gt_I( -G, G, ( V) * G - I); m_N.set_go_gt_I( -G, G, ( -V) * G + I); } - nl_double deltaV() const + nl_fptype deltaV() const { return m_P.net().Q_Analog() - m_N.net().Q_Analog(); } - void set_mat(const nl_double a11, const nl_double a12, const nl_double rhs1, - const nl_double a21, const nl_double a22, const nl_double rhs2) + void set_mat(const nl_fptype a11, const nl_fptype a12, const nl_fptype rhs1, + const nl_fptype a21, const nl_fptype a22, const nl_fptype rhs2) { /* GO, GT, I */ m_P.set_go_gt_I(a12, a11, rhs1); @@ -125,9 +125,9 @@ namespace analog { } - void set_R(const nl_double R) + void set_R(const nl_fptype R) { - const nl_double G = plib::constants::one() / R; + const nl_fptype G = plib::constants::one() / R; set_mat( G, -G, 0.0, -G, G, 0.0); } @@ -163,7 +163,7 @@ namespace analog } private: - param_double_t m_R; + param_fp_t m_R; /* protect set_R ... it's a recipe to desaster when used to bypass the parameter */ using NETLIB_NAME(R_base)::set_R; }; @@ -198,8 +198,8 @@ namespace analog NETLIB_SUB(R_base) m_R1; NETLIB_SUB(R_base) m_R2; - param_double_t m_R; - param_double_t m_Dial; + param_fp_t m_R; + param_fp_t m_Dial; param_logic_t m_DialIsLog; param_logic_t m_Reverse; }; @@ -225,8 +225,8 @@ namespace analog private: NETLIB_SUB(R_base) m_R1; - param_double_t m_R; - param_double_t m_Dial; + param_fp_t m_R; + param_fp_t m_Dial; param_logic_t m_DialIsLog; param_logic_t m_Reverse; }; @@ -250,8 +250,8 @@ namespace analog m_cap.timestep(m_C(), deltaV(), step); if (m_cap.type() == capacitor_e::CONSTANT_CAPACITY) { - const nl_double I = m_cap.Ieq(m_C(), deltaV()); - const nl_double G = m_cap.G(m_C()); + const nl_fptype I = m_cap.Ieq(m_C(), deltaV()); + const nl_fptype G = m_cap.G(m_C()); set_mat( G, -G, -I, -G, G, I); } @@ -260,13 +260,13 @@ namespace analog NETLIB_IS_DYNAMIC(m_cap.type() == capacitor_e::VARIABLE_CAPACITY) NETLIB_UPDATE_TERMINALSI() { - const nl_double I = m_cap.Ieq(m_C(), deltaV()); - const nl_double G = m_cap.G(m_C()); + const nl_fptype I = m_cap.Ieq(m_C(), deltaV()); + const nl_fptype G = m_cap.G(m_C()); set_mat( G, -G, -I, -G, G, I); } - param_double_t m_C; + param_fp_t m_C; NETLIB_RESETI() { m_cap.setparams(exec().gmin()); @@ -307,11 +307,11 @@ namespace analog NETLIB_UPDATE_PARAMI(); private: - param_double_t m_L; + param_fp_t m_L; - nl_double m_gmin; - nl_double m_G; - nl_double m_I; + nl_fptype m_gmin; + nl_fptype m_G; + nl_fptype m_I; }; /*! Class representing the diode model paramers. @@ -426,12 +426,12 @@ namespace analog } private: - state_var m_t; - param_double_t m_R; - param_double_t m_V; + state_var m_t; + param_fp_t m_R; + param_fp_t m_V; param_str_t m_func; plib::pfunction m_compiled; - std::vector m_funcparam; + std::vector m_funcparam; }; // ----------------------------------------------------------------------------- @@ -459,7 +459,7 @@ namespace analog { m_t += step; m_funcparam[0] = m_t; - const double I = m_compiled.evaluate(m_funcparam); + const nl_fptype I = m_compiled.evaluate(m_funcparam); set_mat(0.0, 0.0, -I, 0.0, 0.0, I); } @@ -483,11 +483,11 @@ namespace analog private: - state_var m_t; - param_double_t m_I; + state_var m_t; + param_fp_t m_I; param_str_t m_func; plib::pfunction m_compiled; - std::vector m_funcparam; + std::vector m_funcparam; }; diff --git a/src/lib/netlist/devices/nld_4066.cpp b/src/lib/netlist/devices/nld_4066.cpp index 96200688400..798beffa975 100644 --- a/src/lib/netlist/devices/nld_4066.cpp +++ b/src/lib/netlist/devices/nld_4066.cpp @@ -34,35 +34,35 @@ namespace netlist analog::NETLIB_SUB(R_base) m_R; analog_input_t m_control; - param_double_t m_base_r; + param_fp_t m_base_r; }; NETLIB_RESET(CD4066_GATE) { // Start in off condition // FIXME: is ROFF correct? - m_R.set_R(plib::constants::one() / exec().gmin()); + m_R.set_R(plib::constants::one() / exec().gmin()); } NETLIB_UPDATE(CD4066_GATE) { - nl_double sup = (m_supply.VCC() - m_supply.GND()); - nl_double low = plib::constants::cast(0.45) * sup; - nl_double high = plib::constants::cast(0.55) * sup; - nl_double in = m_control() - m_supply.GND(); - nl_double rON = m_base_r() * plib::constants::cast(5.0) / sup; - nl_double R = -1.0; + nl_fptype sup = (m_supply.VCC() - m_supply.GND()); + nl_fptype low = plib::constants::cast(0.45) * sup; + nl_fptype high = plib::constants::cast(0.55) * sup; + nl_fptype in = m_control() - m_supply.GND(); + nl_fptype rON = m_base_r() * plib::constants::cast(5.0) / sup; + nl_fptype R = -1.0; if (in < low) { - R = plib::constants::one() / exec().gmin(); + R = plib::constants::one() / exec().gmin(); } else if (in > high) { R = rON; } - if (R > plib::constants::zero()) + if (R > plib::constants::zero()) { m_R.update(); m_R.set_R(R); diff --git a/src/lib/netlist/devices/nld_4316.cpp b/src/lib/netlist/devices/nld_4316.cpp index bf04882fa27..26a188502a8 100644 --- a/src/lib/netlist/devices/nld_4316.cpp +++ b/src/lib/netlist/devices/nld_4316.cpp @@ -33,12 +33,12 @@ namespace netlist { namespace devices { logic_input_t m_S; logic_input_t m_E; - param_double_t m_base_r; + param_fp_t m_base_r; }; NETLIB_RESET(CD4316_GATE) { - m_R.set_R(plib::constants::one() / exec().gmin()); + m_R.set_R(plib::constants::one() / exec().gmin()); } NETLIB_UPDATE(CD4316_GATE) @@ -47,7 +47,7 @@ namespace netlist { namespace devices { if (m_S() && !m_E()) m_R.set_R(m_base_r()); else - m_R.set_R(plib::constants::one() / exec().gmin()); + m_R.set_R(plib::constants::one() / exec().gmin()); m_R.solve_later(NLTIME_FROM_NS(1)); } diff --git a/src/lib/netlist/devices/nld_74123.cpp b/src/lib/netlist/devices/nld_74123.cpp index 2e1e34949da..213fa9cc396 100644 --- a/src/lib/netlist/devices/nld_74123.cpp +++ b/src/lib/netlist/devices/nld_74123.cpp @@ -74,10 +74,10 @@ namespace netlist state_var m_last_trig; state_var m_state; - state_var m_KP; + state_var m_KP; - param_double_t m_K; - param_double_t m_RI; + param_fp_t m_K; + param_fp_t m_RI; }; NETLIB_OBJECT(74123_dip) @@ -232,7 +232,7 @@ namespace netlist if (m_state == 1) { - const nl_double vLow = m_KP * m_RP.m_R.m_P(); + const nl_fptype vLow = m_KP * m_RP.m_R.m_P(); if (m_CV() < vLow) { m_RN_Q.push(0, NLTIME_FROM_NS(10)); // R_OFF @@ -241,7 +241,7 @@ namespace netlist } if (m_state == 2) { - const nl_double vHigh = m_RP.m_R.m_P() * (1.0 - m_KP); + const nl_fptype vHigh = m_RP.m_R.m_P() * (1.0 - m_KP); if (m_CV() > vHigh) { m_RP_Q.push(0, NLTIME_FROM_NS(10)); // R_OFF diff --git a/src/lib/netlist/devices/nld_74ls629.cpp b/src/lib/netlist/devices/nld_74ls629.cpp index fd8f424fa32..0f1c64fc74a 100644 --- a/src/lib/netlist/devices/nld_74ls629.cpp +++ b/src/lib/netlist/devices/nld_74ls629.cpp @@ -118,7 +118,7 @@ namespace netlist analog_input_t m_RNG; analog_input_t m_FC; - param_double_t m_CAP; + param_fp_t m_CAP; }; NETLIB_OBJECT(SN74LS629_dip) @@ -175,29 +175,29 @@ namespace netlist { { // recompute - nl_double v_freq = m_FC(); - nl_double v_rng = m_RNG(); + nl_fptype v_freq = m_FC(); + nl_fptype v_rng = m_RNG(); /* coefficients */ - const nl_double k1 = 1.9904769024796283E+03; - const nl_double k2 = 1.2070059213983407E+03; - const nl_double k3 = 1.3266985579561108E+03; - const nl_double k4 = -1.5500979825922698E+02; - const nl_double k5 = 2.8184536266938172E+00; - const nl_double k6 = -2.3503421582744556E+02; - const nl_double k7 = -3.3836786704527788E+02; - const nl_double k8 = -1.3569136703258670E+02; - const nl_double k9 = 2.9914575453819188E+00; - const nl_double k10 = 1.6855569086173170E+00; + const nl_fptype k1 = 1.9904769024796283E+03; + const nl_fptype k2 = 1.2070059213983407E+03; + const nl_fptype k3 = 1.3266985579561108E+03; + const nl_fptype k4 = -1.5500979825922698E+02; + const nl_fptype k5 = 2.8184536266938172E+00; + const nl_fptype k6 = -2.3503421582744556E+02; + const nl_fptype k7 = -3.3836786704527788E+02; + const nl_fptype k8 = -1.3569136703258670E+02; + const nl_fptype k9 = 2.9914575453819188E+00; + const nl_fptype k10 = 1.6855569086173170E+00; /* scale due to input resistance */ /* Polyfunctional3D_model created by zunzun.com using sum of squared absolute error */ - nl_double v_freq_2 = v_freq * v_freq; - nl_double v_freq_3 = v_freq_2 * v_freq; - nl_double v_freq_4 = v_freq_3 * v_freq; - nl_double freq = k1; + nl_fptype v_freq_2 = v_freq * v_freq; + nl_fptype v_freq_3 = v_freq_2 * v_freq; + nl_fptype v_freq_4 = v_freq_3 * v_freq; + nl_fptype freq = k1; freq += k2 * v_freq; freq += k3 * v_freq_2; freq += k4 * v_freq_3; @@ -208,7 +208,7 @@ namespace netlist freq += k9 * v_rng * v_freq_3; freq += k10 * v_rng * v_freq_4; - freq *= plib::constants::cast(0.1e-6) / m_CAP(); + freq *= plib::constants::cast(0.1e-6) / m_CAP(); // FIXME: we need a possibility to remove entries from queue ... // or an exact model ... diff --git a/src/lib/netlist/devices/nld_log.cpp b/src/lib/netlist/devices/nld_log.cpp index c8569f473c3..3b173060986 100644 --- a/src/lib/netlist/devices/nld_log.cpp +++ b/src/lib/netlist/devices/nld_log.cpp @@ -31,7 +31,7 @@ namespace netlist NETLIB_UPDATEI() { /* use pstring::sprintf, it is a LOT faster */ - m_writer.writeline(plib::pfmt("{1:.9} {2}").e(exec().time().as_double()).e(static_cast(m_I()))); + m_writer.writeline(plib::pfmt("{1:.9} {2}").e(exec().time().as_double()).e(static_cast(m_I()))); } NETLIB_RESETI() { } @@ -50,7 +50,7 @@ namespace netlist NETLIB_UPDATEI() { - m_writer.writeline(plib::pfmt("{1:.9} {2}").e(exec().time().as_double()).e(static_cast(m_I() - m_I2()))); + m_writer.writeline(plib::pfmt("{1:.9} {2}").e(exec().time().as_double()).e(static_cast(m_I() - m_I2()))); } NETLIB_RESETI() { } diff --git a/src/lib/netlist/devices/nld_mm5837.cpp b/src/lib/netlist/devices/nld_mm5837.cpp index a8add5aaeea..2c58354fd3f 100644 --- a/src/lib/netlist/devices/nld_mm5837.cpp +++ b/src/lib/netlist/devices/nld_mm5837.cpp @@ -51,7 +51,7 @@ namespace netlist analog_input_t m_VDD; analog_input_t m_VGG; analog_input_t m_VSS; - param_double_t m_FREQ; + param_fp_t m_FREQ; /* clock stage */ logic_input_t m_feedback; @@ -69,7 +69,7 @@ namespace netlist { //m_V0.initial(0.0); //m_RV.do_reset(); - m_RV.set_G_V_I(plib::constants::one() / R_LOW, 0.0, 0.0); + m_RV.set_G_V_I(plib::constants::one() / R_LOW, 0.0, 0.0); m_inc = netlist_time::from_double(1.0 / m_FREQ()); if (m_FREQ() < 24000 || m_FREQ() > 56000) log().warning(MW_FREQUENCY_OUTSIDE_OF_SPECS_1(m_FREQ())); @@ -102,13 +102,13 @@ namespace netlist if (state != last_state) { - const nl_double R = state ? R_HIGH : R_LOW; - const nl_double V = state ? m_VDD() : m_VSS(); + const nl_fptype R = state ? R_HIGH : R_LOW; + const nl_fptype V = state ? m_VDD() : m_VSS(); // We only need to update the net first if this is a time stepping net if (m_is_timestep) m_RV.update(); - m_RV.set_G_V_I(plib::constants::one() / R, V, plib::constants::zero()); + m_RV.set_G_V_I(plib::constants::one() / R, V, plib::constants::zero()); m_RV.solve_later(NLTIME_FROM_NS(1)); } diff --git a/src/lib/netlist/devices/nld_ne555.cpp b/src/lib/netlist/devices/nld_ne555.cpp index dc6e3e5696a..05a334c2fe4 100644 --- a/src/lib/netlist/devices/nld_ne555.cpp +++ b/src/lib/netlist/devices/nld_ne555.cpp @@ -103,10 +103,10 @@ namespace netlist state_var m_ff; state_var m_last_reset; - nl_double clamp(const nl_double v, const nl_double a, const nl_double b) + nl_fptype clamp(const nl_fptype v, const nl_fptype a, const nl_fptype b) { - nl_double ret = v; - nl_double vcc = m_R1.m_P(); + nl_fptype ret = v; + nl_fptype vcc = m_R1.m_P(); if (ret > vcc - a) ret = vcc - a; @@ -161,7 +161,7 @@ namespace netlist } else { - const nl_double vt = clamp(m_R2.m_P(), 0.7, 1.4); + const nl_fptype vt = clamp(m_R2.m_P(), 0.7, 1.4); const bool bthresh = (m_THRES() > vt); const bool btrig = (m_TRIG() > clamp(m_R2.m_N(), 0.7, 1.4)); diff --git a/src/lib/netlist/devices/nld_r2r_dac.cpp b/src/lib/netlist/devices/nld_r2r_dac.cpp index 284b6673f76..e2695766332 100644 --- a/src/lib/netlist/devices/nld_r2r_dac.cpp +++ b/src/lib/netlist/devices/nld_r2r_dac.cpp @@ -30,8 +30,8 @@ namespace netlist //NETLIB_UPDATEI(); protected: - param_double_t m_VIN; - param_double_t m_R; + param_fp_t m_VIN; + param_fp_t m_R; param_int_t m_num; param_int_t m_val; }; @@ -41,8 +41,8 @@ namespace netlist { solve_now(); - double V = m_VIN() / static_cast(1 << m_num()) - * static_cast(m_val()); + nl_fptype V = m_VIN() / static_cast(1 << m_num()) + * static_cast(m_val()); this->set_G_V_I(1.0 / m_R(), V, 0.0); } diff --git a/src/lib/netlist/devices/nld_schmitt.cpp b/src/lib/netlist/devices/nld_schmitt.cpp index f219d215520..95739cfd662 100644 --- a/src/lib/netlist/devices/nld_schmitt.cpp +++ b/src/lib/netlist/devices/nld_schmitt.cpp @@ -85,8 +85,8 @@ namespace netlist m_RVI.reset(); m_RVO.reset(); m_is_timestep = m_RVO.m_P.net().solver()->has_timestep_devices(); - m_RVI.set_G_V_I(plib::constants::one() / m_model.m_RI, m_model.m_VI, 0.0); - m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROL, m_model.m_VOL, 0.0); + m_RVI.set_G_V_I(plib::constants::one() / m_model.m_RI, m_model.m_VI, 0.0); + m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROL, m_model.m_VOL, 0.0); } NETLIB_UPDATEI() @@ -98,7 +98,7 @@ namespace netlist m_last_state = 0; if (m_is_timestep) m_RVO.update(); - m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROH, m_model.m_VOH, 0.0); + m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROH, m_model.m_VOH, 0.0); m_RVO.solve_later(); } } @@ -109,7 +109,7 @@ namespace netlist m_last_state = 1; if (m_is_timestep) m_RVO.update(); - m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROL, m_model.m_VOL, 0.0); + m_RVO.set_G_V_I(plib::constants::one() / m_model.m_ROL, m_model.m_VOL, 0.0); m_RVO.solve_later(); } } diff --git a/src/lib/netlist/devices/nld_system.cpp b/src/lib/netlist/devices/nld_system.cpp index d75dd7d0fe9..427c2f3dcae 100644 --- a/src/lib/netlist/devices/nld_system.cpp +++ b/src/lib/netlist/devices/nld_system.cpp @@ -76,7 +76,7 @@ namespace netlist if (state != m_last_state) { m_last_state = state; - const nl_double R = state ? m_RON() : m_ROFF(); + const nl_fptype R = state ? m_RON() : m_ROFF(); // FIXME: We only need to update the net first if this is a time stepping net m_R.update(); diff --git a/src/lib/netlist/devices/nlid_cmos.h b/src/lib/netlist/devices/nlid_cmos.h index 06388a73535..03e6e9dd01d 100644 --- a/src/lib/netlist/devices/nlid_cmos.h +++ b/src/lib/netlist/devices/nlid_cmos.h @@ -28,8 +28,8 @@ namespace devices NETLIB_RESETI() {} public: - nl_double vdd() { return m_vdd(); } - nl_double vss() { return m_vss(); } + nl_fptype vdd() { return m_vdd(); } + nl_fptype vss() { return m_vss(); } analog_input_t m_vdd; analog_input_t m_vss; diff --git a/src/lib/netlist/devices/nlid_proxy.cpp b/src/lib/netlist/devices/nlid_proxy.cpp index 444d1c32540..2b608185ff6 100644 --- a/src/lib/netlist/devices/nlid_proxy.cpp +++ b/src/lib/netlist/devices/nlid_proxy.cpp @@ -51,7 +51,7 @@ namespace netlist { nl_assert(m_logic_family != nullptr); // FIXME: Variable supply voltage! - double supply_V = logic_family()->fixed_V(); + nl_fptype supply_V = logic_family()->fixed_V(); if (supply_V == 0.0) supply_V = 5.0; if (m_I.Q_Analog() > logic_family()->high_thresh_V(0.0, supply_V)) @@ -147,7 +147,7 @@ namespace netlist void nld_d_to_a_proxy::reset() { // FIXME: Variable voltage - double supply_V = logic_family()->fixed_V(); + nl_fptype supply_V = logic_family()->fixed_V(); if (supply_V == 0.0) supply_V = 5.0; //m_Q.initial(0.0); @@ -159,7 +159,7 @@ namespace netlist if (m_VCCHack) m_VCCHack->initial(supply_V); m_is_timestep = m_RN.m_P.net().solver()->has_timestep_devices(); - m_RN.set_G_V_I(plib::constants::one() / logic_family()->R_low(), + m_RN.set_G_V_I(plib::constants::one() / logic_family()->R_low(), logic_family()->low_offset_V(), 0.0); m_RP.set_G_V_I(G_OFF, 0.0, 0.0); @@ -179,12 +179,12 @@ namespace netlist { m_RN.set_G_V_I(G_OFF, 0.0, 0.0); - m_RP.set_G_V_I(plib::constants::one() / logic_family()->R_high(), + m_RP.set_G_V_I(plib::constants::one() / logic_family()->R_high(), logic_family()->high_offset_V(), 0.0); } else { - m_RN.set_G_V_I(plib::constants::one() / logic_family()->R_low(), + m_RN.set_G_V_I(plib::constants::one() / logic_family()->R_low(), logic_family()->low_offset_V(), 0.0); m_RP.set_G_V_I(G_OFF, 0.0, 0.0); diff --git a/src/lib/netlist/devices/nlid_proxy.h b/src/lib/netlist/devices/nlid_proxy.h index 7a8377276a1..bdf871d9f9b 100644 --- a/src/lib/netlist/devices/nlid_proxy.h +++ b/src/lib/netlist/devices/nlid_proxy.h @@ -104,7 +104,7 @@ namespace netlist private: - static constexpr const nl_double G_OFF = 1e-9; + static constexpr const nl_fptype G_OFF = 1e-9; plib::unique_ptr m_GNDHack; // FIXME: Long term, we need to connect proxy gnd to device gnd plib::unique_ptr m_VCCHack; // FIXME: Long term, we need to connect proxy gnd to device gnd diff --git a/src/lib/netlist/devices/nlid_system.h b/src/lib/netlist/devices/nlid_system.h index 611a2eff6af..bdccf2ab6c0 100644 --- a/src/lib/netlist/devices/nlid_system.h +++ b/src/lib/netlist/devices/nlid_system.h @@ -79,7 +79,7 @@ namespace devices logic_output_t m_Q; netlist_time m_inc; private: - param_double_t m_freq; + param_fp_t m_freq; }; // ----------------------------------------------------------------------------- @@ -113,7 +113,7 @@ namespace devices logic_input_t m_feedback; logic_output_t m_Q; - param_double_t m_freq; + param_fp_t m_freq; netlist_time m_inc; }; @@ -150,7 +150,7 @@ namespace devices param_str_t m_func; plib::pfunction m_compiled; - std::vector m_funcparam; + std::vector m_funcparam; }; // ----------------------------------------------------------------------------- @@ -207,9 +207,9 @@ namespace devices private: - param_double_t m_freq; + param_fp_t m_freq; param_str_t m_pattern; - param_double_t m_offset; + param_fp_t m_offset; logic_input_t m_feedback; logic_output_t m_Q; @@ -260,7 +260,7 @@ namespace devices private: analog_output_t m_Q; - param_double_t m_IN; + param_fp_t m_IN; }; // ----------------------------------------------------------------------------- @@ -347,8 +347,8 @@ namespace devices analog_input_t m_I; analog_output_t m_Q; - param_double_t m_p_RIN; - param_double_t m_p_ROUT; + param_fp_t m_p_RIN; + param_fp_t m_p_ROUT; }; /* ----------------------------------------------------------------------------- @@ -388,7 +388,7 @@ namespace devices analog_output_t m_Q; std::vector> m_I; - std::vector m_vals; + std::vector m_vals; plib::pfunction m_compiled; }; @@ -416,8 +416,8 @@ namespace devices analog::NETLIB_SUB(R_base) m_R; logic_input_t m_I; - param_double_t m_RON; - param_double_t m_ROFF; + param_fp_t m_RON; + param_fp_t m_ROFF; private: @@ -452,8 +452,8 @@ namespace devices } /* FIXME: this will seg-fault if force_analog_input = false */ - nl_double VCC() const NL_NOEXCEPT { return m_VCC->Q_Analog(); } - nl_double GND() const NL_NOEXCEPT { return m_GND->Q_Analog(); } + nl_fptype VCC() const NL_NOEXCEPT { return m_VCC->Q_Analog(); } + nl_fptype GND() const NL_NOEXCEPT { return m_GND->Q_Analog(); } NETLIB_SUBXX(analog, R) m_RVG; // dummy resistor between VCC and GND diff --git a/src/lib/netlist/nl_base.cpp b/src/lib/netlist/nl_base.cpp index 209992d1562..f3cdef98e1d 100644 --- a/src/lib/netlist/nl_base.cpp +++ b/src/lib/netlist/nl_base.cpp @@ -482,7 +482,7 @@ namespace netlist if (stats->m_stat_inc_active() > 3 * stats->m_stat_total_time.count() && stats->m_stat_inc_active() > trigger) log().verbose("HINT({}, NO_DEACTIVATE) // {} {} {}", ep->name(), - static_cast(stats->m_stat_inc_active()) / static_cast(stats->m_stat_total_time.count()), + static_cast(stats->m_stat_inc_active()) / static_cast(stats->m_stat_total_time.count()), stats->m_stat_inc_active(), stats->m_stat_total_time.count()); } } @@ -847,7 +847,7 @@ namespace netlist state().setup().register_term(*this); } - void analog_output_t::initial(const nl_double val) + void analog_output_t::initial(const nl_fptype val) { net().set_Q_Analog(val); } @@ -878,7 +878,7 @@ namespace netlist { if (dynamic_cast(this) != nullptr) return STRING; - else if (dynamic_cast(this) != nullptr) + else if (dynamic_cast(this) != nullptr) return DOUBLE; else if (dynamic_cast(this) != nullptr) return INTEGER; @@ -938,7 +938,7 @@ namespace netlist return state().setup().models().value_str(str(), entity); } - nl_double param_model_t::value(const pstring &entity) + nl_fptype param_model_t::value(const pstring &entity) { return state().setup().models().value(str(), entity); } diff --git a/src/lib/netlist/nl_base.h b/src/lib/netlist/nl_base.h index 1ed7b645c0e..1063690894f 100644 --- a/src/lib/netlist/nl_base.h +++ b/src/lib/netlist/nl_base.h @@ -115,8 +115,8 @@ class NETLIB_NAME(name) : public device_t * NETLIB_TIMESTEPI() * { * // Gpar should support convergence - * const nl_double G = m_C.Value() / step + m_GParallel; - * const nl_double I = -G * deltaV(); + * const nl_fptype G = m_C.Value() / step + m_GParallel; + * const nl_fptype I = -G * deltaV(); * set(G, 0.0, I); * } * @@ -129,7 +129,7 @@ class NETLIB_NAME(name) : public device_t * Please see NETLIB_IS_TIMESTEP for an example. */ #define NETLIB_TIMESTEPI() \ - public: virtual void timestep(const nl_double step) NL_NOEXCEPT override + public: virtual void timestep(const nl_fptype step) NL_NOEXCEPT override #define NETLIB_FAMILY(family) , m_famsetter(*this, family) @@ -141,7 +141,7 @@ class NETLIB_NAME(name) : public device_t #define NETLIB_UPDATE_PARAMI() virtual void update_param() NL_NOEXCEPT override #define NETLIB_RESETI() virtual void reset() override -#define NETLIB_TIMESTEP(chip) void NETLIB_NAME(chip) :: timestep(nl_double step) NL_NOEXCEPT +#define NETLIB_TIMESTEP(chip) void NETLIB_NAME(chip) :: timestep(nl_fptype step) NL_NOEXCEPT #define NETLIB_SUB(chip) nld_ ## chip #define NETLIB_SUBXX(ns, chip) unique_pool_ptr< ns :: nld_ ## chip > @@ -250,21 +250,21 @@ namespace netlist virtual unique_pool_ptr create_a_d_proxy(netlist_state_t &anetlist, const pstring &name, logic_input_t *proxied) const = 0; - double fixed_V() const noexcept{ return m_fixed_V; } - double low_thresh_V(const double VN, const double VP) const noexcept{ return VN + (VP - VN) * m_low_thresh_PCNT; } - double high_thresh_V(const double VN, const double VP) const noexcept{ return VN + (VP - VN) * m_high_thresh_PCNT; } - double low_offset_V() const noexcept{ return m_low_VO; } - double high_offset_V() const noexcept{ return m_high_VO; } - double R_low() const noexcept{ return m_R_low; } - double R_high() const noexcept{ return m_R_high; } - - double m_fixed_V; //!< For variable voltage families, specify 0. For TTL this would be 5. */ - double m_low_thresh_PCNT; //!< low input threshhold offset. If the input voltage is below this value times supply voltage, a "0" input is signalled - double m_high_thresh_PCNT; //!< high input threshhold offset. If the input voltage is above the value times supply voltage, a "0" input is signalled - double m_low_VO; //!< low output voltage offset. This voltage is output if the ouput is "0" - double m_high_VO; //!< high output voltage offset. The supply voltage minus this offset is output if the ouput is "1" - double m_R_low; //!< low output resistance. Value of series resistor used for low output - double m_R_high; //!< high output resistance. Value of series resistor used for high output + nl_fptype fixed_V() const noexcept{ return m_fixed_V; } + nl_fptype low_thresh_V(const nl_fptype VN, const nl_fptype VP) const noexcept{ return VN + (VP - VN) * m_low_thresh_PCNT; } + nl_fptype high_thresh_V(const nl_fptype VN, const nl_fptype VP) const noexcept{ return VN + (VP - VN) * m_high_thresh_PCNT; } + nl_fptype low_offset_V() const noexcept{ return m_low_VO; } + nl_fptype high_offset_V() const noexcept{ return m_high_VO; } + nl_fptype R_low() const noexcept{ return m_R_low; } + nl_fptype R_high() const noexcept{ return m_R_high; } + + nl_fptype m_fixed_V; //!< For variable voltage families, specify 0. For TTL this would be 5. */ + nl_fptype m_low_thresh_PCNT; //!< low input threshhold offset. If the input voltage is below this value times supply voltage, a "0" input is signalled + nl_fptype m_high_thresh_PCNT; //!< high input threshhold offset. If the input voltage is above the value times supply voltage, a "0" input is signalled + nl_fptype m_low_VO; //!< low output voltage offset. This voltage is output if the ouput is "0" + nl_fptype m_high_VO; //!< high output voltage offset. The supply voltage minus this offset is output if the ouput is "1" + nl_fptype m_R_low; //!< low output resistance. Value of series resistor used for low output + nl_fptype m_R_high; //!< high output resistance. Value of series resistor used for high output }; /*! Base class for devices, terminals, outputs and inputs which support @@ -761,19 +761,19 @@ namespace netlist terminal_t(core_device_t &dev, const pstring &aname, terminal_t *otherterm); - nl_double operator ()() const NL_NOEXCEPT; + nl_fptype operator ()() const NL_NOEXCEPT; - void set_conductivity(const nl_double G) noexcept + void set_conductivity(const nl_fptype G) noexcept { set_go_gt_I(-G, G, 0.0); } - void set_go_gt(const nl_double GO, const nl_double GT) noexcept + void set_go_gt(const nl_fptype GO, const nl_fptype GT) noexcept { set_go_gt_I(GO, GT, 0.0); } - void set_go_gt_I(const nl_double GO, const nl_double GT, const nl_double I) noexcept + void set_go_gt_I(const nl_fptype GO, const nl_fptype GT, const nl_fptype I) noexcept { if (m_go1 != nullptr) { @@ -786,14 +786,14 @@ namespace netlist void solve_now(); void schedule_solve_after(const netlist_time after); - void set_ptrs(nl_double *gt, nl_double *go, nl_double *Idr) noexcept; + void set_ptrs(nl_fptype *gt, nl_fptype *go, nl_fptype *Idr) noexcept; terminal_t *connected_terminal() const noexcept { return m_connected_terminal; } private: - nl_double *m_Idr1; // drive current - nl_double *m_go1; // conductance for Voltage from other term - nl_double *m_gt1; // conductance for total conductance + nl_fptype *m_Idr1; // drive current + nl_fptype *m_go1; // conductance for Voltage from other term + nl_fptype *m_gt1; // conductance for total conductance terminal_t *m_connected_terminal; @@ -867,12 +867,12 @@ namespace netlist /*! returns voltage at terminal. * \returns voltage at terminal. */ - nl_double operator()() const NL_NOEXCEPT { return Q_Analog(); } + nl_fptype operator()() const NL_NOEXCEPT { return Q_Analog(); } /*! returns voltage at terminal. * \returns voltage at terminal. */ - nl_double Q_Analog() const NL_NOEXCEPT; + nl_fptype Q_Analog() const NL_NOEXCEPT; }; @@ -901,16 +901,16 @@ namespace netlist analog_net_t(netlist_state_t &nl, const pstring &aname, detail::core_terminal_t *mr = nullptr); - nl_double Q_Analog() const noexcept { return m_cur_Analog; } - void set_Q_Analog(const nl_double v) noexcept { m_cur_Analog = v; } - nl_double *Q_Analog_state_ptr() NL_NOEXCEPT { return m_cur_Analog.ptr(); } + nl_fptype Q_Analog() const noexcept { return m_cur_Analog; } + void set_Q_Analog(const nl_fptype v) noexcept { m_cur_Analog = v; } + nl_fptype *Q_Analog_state_ptr() NL_NOEXCEPT { return m_cur_Analog.ptr(); } //FIXME: needed by current solver code solver::matrix_solver_t *solver() const noexcept { return m_solver; } void set_solver(solver::matrix_solver_t *solver) noexcept { m_solver = solver; } private: - state_var m_cur_Analog; + state_var m_cur_Analog; solver::matrix_solver_t *m_solver; }; @@ -945,11 +945,11 @@ namespace netlist public: analog_output_t(core_device_t &dev, const pstring &aname); - void push(const nl_double val) NL_NOEXCEPT { set_Q(val); } - void initial(const nl_double val); + void push(const nl_fptype val) NL_NOEXCEPT { set_Q(val); } + void initial(const nl_fptype val); private: - void set_Q(const nl_double newQ) NL_NOEXCEPT; + void set_Q(const nl_fptype newQ) NL_NOEXCEPT; analog_net_t m_my_net; }; @@ -1028,7 +1028,7 @@ namespace netlist /* FIXME: these should go as well */ using param_logic_t = param_num_t; using param_int_t = param_num_t; - using param_double_t = param_num_t; + using param_fp_t = param_num_t; // ----------------------------------------------------------------------------- // pointer parameter @@ -1093,7 +1093,7 @@ namespace netlist const T m_value; }; - using value_t = value_base_t; + using value_t = value_base_t; template friend class value_base_t; @@ -1102,7 +1102,7 @@ namespace netlist : param_str_t(device, name, val) { } const pstring value_str(const pstring &entity) /*const*/; - nl_double value(const pstring &entity) /*const*/; + nl_fptype value(const pstring &entity) /*const*/; const pstring type() /*const*/; /* hide this */ void setTo(const pstring ¶m) = delete; @@ -1218,7 +1218,7 @@ namespace netlist log_type & log(); public: - virtual void timestep(const nl_double st) NL_NOEXCEPT { plib::unused_var(st); } + virtual void timestep(const nl_fptype st) NL_NOEXCEPT { plib::unused_var(st); } virtual void update_terminals() NL_NOEXCEPT { } virtual void update_param() NL_NOEXCEPT {} @@ -1595,7 +1595,7 @@ namespace netlist /* force late type resolution */ template - nl_double gmin(X *solv = nullptr) const NL_NOEXCEPT + nl_fptype gmin(X *solv = nullptr) const NL_NOEXCEPT { plib::unused_var(solv); return static_cast(m_solver)->gmin(); @@ -1823,9 +1823,9 @@ namespace netlist return static_cast(core_terminal_t::net()); } - inline nl_double terminal_t::operator ()() const NL_NOEXCEPT { return net().Q_Analog(); } + inline nl_fptype terminal_t::operator ()() const NL_NOEXCEPT { return net().Q_Analog(); } - inline void terminal_t::set_ptrs(nl_double *gt, nl_double *go, nl_double *Idr) noexcept + inline void terminal_t::set_ptrs(nl_fptype *gt, nl_fptype *go, nl_fptype *Idr) noexcept { if (!(gt && go && Idr) && (gt || go || Idr)) state().log().fatal("Inconsistent nullptrs for terminal {}", name()); @@ -1859,12 +1859,12 @@ namespace netlist #endif } - inline nl_double analog_input_t::Q_Analog() const NL_NOEXCEPT + inline nl_fptype analog_input_t::Q_Analog() const NL_NOEXCEPT { return net().Q_Analog(); } - inline void analog_output_t::set_Q(const nl_double newQ) NL_NOEXCEPT + inline void analog_output_t::set_Q(const nl_fptype newQ) NL_NOEXCEPT { if (newQ != m_my_net.Q_Analog()) { diff --git a/src/lib/netlist/nl_config.h b/src/lib/netlist/nl_config.h index 93fe10fbe08..0417172203b 100644 --- a/src/lib/netlist/nl_config.h +++ b/src/lib/netlist/nl_config.h @@ -96,7 +96,7 @@ static constexpr const auto NETLIST_INTERNAL_RES = 1000000000; static constexpr const auto NETLIST_CLOCK = NETLIST_INTERNAL_RES; -//#define nl_double float -using nl_double = double; +//#define nl_fptype float +using nl_fptype = double; #endif /* NLCONFIG_H_ */ diff --git a/src/lib/netlist/nl_dice_compat.h b/src/lib/netlist/nl_dice_compat.h index 48695e393ec..7683f9dd451 100644 --- a/src/lib/netlist/nl_dice_compat.h +++ b/src/lib/netlist/nl_dice_compat.h @@ -72,40 +72,40 @@ sed -e 's/#define \(.*\)"\(.*\)"[ \t]*,[ \t]*\(.*\)/NET_ALIAS(\1,\2.\3)/' src/ma struct Mono555Desc { public: - nl_double r, c; + nl_fptype r, c; - Mono555Desc(nl_double res, nl_double cap) : r(res), c(cap) { } + Mono555Desc(nl_fptype res, nl_fptype cap) : r(res), c(cap) { } }; struct Astable555Desc { public: - nl_double r1, r2, c; + nl_fptype r1, r2, c; - Astable555Desc(nl_double res1, nl_double res2, nl_double cap) : r1(res1), r2(res2), c(cap) { } + Astable555Desc(nl_fptype res1, nl_fptype res2, nl_fptype cap) : r1(res1), r2(res2), c(cap) { } }; struct Mono9602Desc { public: - nl_double r1, c1, r2, c2; + nl_fptype r1, c1, r2, c2; - Mono9602Desc(nl_double res1, nl_double cap1, nl_double res2, nl_double cap2) + Mono9602Desc(nl_fptype res1, nl_fptype cap1, nl_fptype res2, nl_fptype cap2) : r1(res1), c1(cap1), r2(res2), c2(cap2) { } }; struct SeriesRCDesc { public: - nl_double r, c; + nl_fptype r, c; - SeriesRCDesc(nl_double res, nl_double cap) : r(res), c(cap) { } + SeriesRCDesc(nl_fptype res, nl_fptype cap) : r(res), c(cap) { } }; struct CapacitorDesc : public SeriesRCDesc { public: - CapacitorDesc(nl_double cap) : SeriesRCDesc(0.0, cap) { } + CapacitorDesc(nl_fptype cap) : SeriesRCDesc(0.0, cap) { } }; #else diff --git a/src/lib/netlist/nl_parser.cpp b/src/lib/netlist/nl_parser.cpp index 8a3ea3fa027..27165d9d1f4 100644 --- a/src/lib/netlist/nl_parser.cpp +++ b/src/lib/netlist/nl_parser.cpp @@ -236,9 +236,9 @@ void parser_t::frontier() // don't do much pstring attachat = get_identifier(); require_token(m_tok_comma); - double r_IN = eval_param(get_token()); + nl_fptype r_IN = eval_param(get_token()); require_token(m_tok_comma); - double r_OUT = eval_param(get_token()); + nl_fptype r_OUT = eval_param(get_token()); require_token(m_tok_param_right); m_setup.register_frontier(attachat, r_IN, r_OUT); @@ -334,7 +334,7 @@ void parser_t::netdev_param() } else { - nl_double val = eval_param(tok); + nl_fptype val = eval_param(tok); m_setup.log().debug("Parser: Param: {1} {2}\n", param, val); m_setup.register_param(param, val); } @@ -394,7 +394,7 @@ void parser_t::device(const pstring &dev_type) } else { - nl_double val = eval_param(tok); + nl_fptype val = eval_param(tok); m_setup.register_param(paramfq, val); } } @@ -410,12 +410,12 @@ void parser_t::device(const pstring &dev_type) // ---------------------------------------------------------------------------------------- -nl_double parser_t::eval_param(const token_t &tok) +nl_fptype parser_t::eval_param(const token_t &tok) { static std::array macs = {"", "RES_R", "RES_K", "RES_M", "CAP_U", "CAP_N", "CAP_P"}; - static std::array facs = {1, 1, 1e3, 1e6, 1e-6, 1e-9, 1e-12}; + static std::array facs = {1, 1, 1e3, 1e6, 1e-6, 1e-9, 1e-12}; std::size_t f=0; - nl_double ret(0); + nl_fptype ret(0); for (std::size_t i=1; i(tok.str(), err); + ret = plib::pstonum_ne(tok.str(), err); if (err) - error(plib::pfmt("Parameter value <{1}> not double \n")(tok.str())); + error(plib::pfmt("Parameter value <{1}> not floating point \n")(tok.str())); } return ret * facs[f]; diff --git a/src/lib/netlist/nl_parser.h b/src/lib/netlist/nl_parser.h index 3140fad6138..ce95f6ec346 100644 --- a/src/lib/netlist/nl_parser.h +++ b/src/lib/netlist/nl_parser.h @@ -48,7 +48,7 @@ namespace netlist void verror(const pstring &msg) override; private: - nl_double eval_param(const token_t &tok); + nl_fptype eval_param(const token_t &tok); token_id_t m_tok_param_left; token_id_t m_tok_param_right; diff --git a/src/lib/netlist/nl_setup.cpp b/src/lib/netlist/nl_setup.cpp index 4ab250c16d4..b35445e78d5 100644 --- a/src/lib/netlist/nl_setup.cpp +++ b/src/lib/netlist/nl_setup.cpp @@ -119,7 +119,7 @@ namespace netlist m_namespace_stack.pop(); } - void nlparse_t::register_param(const pstring ¶m, const double value) + void nlparse_t::register_param(const pstring ¶m, const nl_fptype value) { if (std::abs(value - std::floor(value)) > 1e-30 || std::abs(value) > 1e9) register_param(param, plib::pfmt("{1:.9}").e(value)); @@ -150,7 +150,7 @@ namespace netlist m_factory.register_device(plib::make_unique(name, name, "", sourcefile)); } - void nlparse_t::register_frontier(const pstring &attach, const double r_IN, const double r_OUT) + void nlparse_t::register_frontier(const pstring &attach, const nl_fptype r_IN, const nl_fptype r_OUT) { pstring frontier_name = plib::pfmt("frontier_{1}")(m_frontier_cnt); m_frontier_cnt++; @@ -932,7 +932,7 @@ pstring models_t::value_str(const pstring &model, const pstring &entity) return ret; } -nl_double models_t::value(const pstring &model, const pstring &entity) +nl_fptype models_t::value(const pstring &model, const pstring &entity) { model_map_t &map = m_cache[model]; @@ -941,7 +941,7 @@ nl_double models_t::value(const pstring &model, const pstring &entity) pstring tmp = value_str(model, entity); - nl_double factor = plib::constants::one(); + nl_fptype factor = plib::constants::one(); auto p = std::next(tmp.begin(), static_cast(tmp.size() - 1)); switch (*p) { @@ -958,12 +958,12 @@ nl_double models_t::value(const pstring &model, const pstring &entity) if (*p < '0' || *p > '9') throw nl_exception(MF_UNKNOWN_NUMBER_FACTOR_IN_1(entity)); } - if (factor != plib::constants::one()) + if (factor != plib::constants::one()) tmp = plib::left(tmp, tmp.size() - 1); // FIXME: check for errors - //printf("%s %s %e %e\n", entity.c_str(), tmp.c_str(), plib::pstonum(tmp), factor); + //printf("%s %s %e %e\n", entity.c_str(), tmp.c_str(), plib::pstonum(tmp), factor); bool err(false); - auto val = plib::pstonum_ne(tmp, err); + auto val = plib::pstonum_ne(tmp, err); if (err) throw nl_exception(MF_MODEL_NUMBER_CONVERSION_ERROR(entity, tmp, "double", model)); return val * factor; @@ -1124,7 +1124,7 @@ void setup_t::prepare_to_run() { //FIXME: check for errors ... bool err(false); - auto v = plib::pstonum_ne(p->second, err); + auto v = plib::pstonum_ne(p->second, err); if (err || std::abs(v - std::floor(v)) > 1e-6 ) log().fatal(MF_HND_VAL_NOT_SUPPORTED(p->second)); d.second->set_hint_deactivate(v == 0.0); diff --git a/src/lib/netlist/nl_setup.h b/src/lib/netlist/nl_setup.h index a42b10047d4..180b437d293 100644 --- a/src/lib/netlist/nl_setup.h +++ b/src/lib/netlist/nl_setup.h @@ -212,7 +212,7 @@ namespace netlist pstring value_str(const pstring &model, const pstring &entity); - nl_double value(const pstring &model, const pstring &entity); + nl_fptype value(const pstring &model, const pstring &entity); pstring type(const pstring &model) { return value_str(model, "COREMODEL"); } @@ -244,9 +244,9 @@ namespace netlist void register_link(const pstring &sin, const pstring &sout); void register_link_arr(const pstring &terms); void register_param(const pstring ¶m, const pstring &value); - void register_param(const pstring ¶m, const double value); + void register_param(const pstring ¶m, const nl_fptype value); void register_lib_entry(const pstring &name, const pstring &sourcefile); - void register_frontier(const pstring &attach, const double r_IN, const double r_OUT); + void register_frontier(const pstring &attach, const nl_fptype r_IN, const nl_fptype r_OUT); /* register a source */ void register_source(plib::unique_ptr &&src) diff --git a/src/lib/netlist/nltypes.h b/src/lib/netlist/nltypes.h index 75470ca2ebf..fe51be8c17d 100644 --- a/src/lib/netlist/nltypes.h +++ b/src/lib/netlist/nltypes.h @@ -27,12 +27,12 @@ namespace netlist { - /*! @brief plib::constants struct specialized for nl_double + /*! @brief plib::constants struct specialized for nl_fptype * * This may be any of bool, uint8_t, uint16_t, uin32_t and uint64_t. * The choice has little to no impact on performance. */ - using constants = plib::constants; + using constants = plib::constants; /*! @brief netlist_sig_t is the type used for logic signals. * diff --git a/src/lib/netlist/plib/ptokenizer.h b/src/lib/netlist/plib/ptokenizer.h index 5a6b886a2a2..cb6b0dac7f9 100644 --- a/src/lib/netlist/plib/ptokenizer.h +++ b/src/lib/netlist/plib/ptokenizer.h @@ -100,6 +100,7 @@ namespace plib { pstring get_string(); pstring get_identifier(); pstring get_identifier_or_number(); + double get_number_double(); long get_number_long(); diff --git a/src/lib/netlist/prg/nltool.cpp b/src/lib/netlist/prg/nltool.cpp index c94d02a77b6..5f25ac20219 100644 --- a/src/lib/netlist/prg/nltool.cpp +++ b/src/lib/netlist/prg/nltool.cpp @@ -91,7 +91,7 @@ public: plib::option_group opt_grp3; plib::option_str opt_dir; plib::option_group opt_grp4; - plib::option_num opt_ttr; + plib::option_num opt_ttr; plib::option_bool opt_stats; plib::option_vec opt_logs; plib::option_str opt_inp; @@ -311,7 +311,7 @@ struct input_t : m_value(0.0) { std::array buf; // NOLINT(cppcoreguidelines-pro-type-member-init) - double t(0); + nl_fptype t(0); // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg) int e = std::sscanf(line.c_str(), "%lf,%[^,],%lf", &t, buf.data(), &m_value); if (e != 3) @@ -328,7 +328,7 @@ struct input_t case netlist::param_t::POINTER: throw netlist::nl_exception(plib::pfmt("param {1} is not numeric\n")(m_param->name())); case netlist::param_t::DOUBLE: - static_cast(m_param)->setTo(m_value); + static_cast(m_param)->setTo(m_value); break; case netlist::param_t::INTEGER: static_cast(m_param)->setTo(static_cast(m_value)); @@ -341,7 +341,7 @@ struct input_t netlist::netlist_time m_time; netlist::param_t *m_param; - double m_value; + nl_fptype m_value; }; static std::vector read_input(const netlist::setup_t &setup, const pstring &fname) @@ -456,7 +456,7 @@ void tool_app_t::run() nt.stop(); } - double emutime = t.as_seconds(); + nl_fptype emutime = t.as_seconds(); pout("{1:f} seconds emulation took {2:f} real time ==> {3:5.2f}%\n", (ttr - nlt).as_double(), emutime, (ttr - nlt).as_double() / emutime * 100.0); diff --git a/src/lib/netlist/solver/nld_matrix_solver.cpp b/src/lib/netlist/solver/nld_matrix_solver.cpp index c8dfa4ba384..97a496822d9 100644 --- a/src/lib/netlist/solver/nld_matrix_solver.cpp +++ b/src/lib/netlist/solver/nld_matrix_solver.cpp @@ -341,9 +341,9 @@ namespace solver * save states */ - m_last_V.resize(iN, plib::constants::zero()); - m_DD_n_m_1.resize(iN, plib::constants::zero()); - m_h_n_m_1.resize(iN, plib::constants::zero()); + m_last_V.resize(iN, plib::constants::zero()); + m_DD_n_m_1.resize(iN, plib::constants::zero()); + m_h_n_m_1.resize(iN, plib::constants::zero()); state().save(*this, m_last_V.as_base(), this->name(), "m_last_V"); state().save(*this, m_DD_n_m_1.as_base(), this->name(), "m_DD_n_m_1"); @@ -411,7 +411,7 @@ namespace solver void matrix_solver_t::step(const netlist_time &delta) { - const nl_double dd = delta.as_double(); + const nl_fptype dd = delta.as_double(); for (auto &d : m_step_devices) d->timestep(dd); } @@ -500,7 +500,7 @@ namespace solver return {colmax, colmin}; } - double matrix_solver_t::get_weight_around_diag(std::size_t row, std::size_t diag) + nl_fptype matrix_solver_t::get_weight_around_diag(std::size_t row, std::size_t diag) { { /* @@ -509,7 +509,7 @@ namespace solver std::vector touched(1024, false); // FIXME! - double weight = 0.0; + nl_fptype weight = 0.0; auto &term = m_terms[row]; for (std::size_t i = 0; i < term.count(); i++) { @@ -522,12 +522,12 @@ namespace solver if (colu==row) colu = static_cast(diag); else if (colu==diag) colu = static_cast(row); - weight = weight + std::abs(static_cast(colu) - static_cast(diag)); + weight = weight + std::abs(static_cast(colu) - static_cast(diag)); touched[colu] = true; } } } - return weight; // / static_cast(term.railstart()); + return weight; // / static_cast(term.railstart()); } } @@ -553,29 +553,29 @@ namespace solver } } - netlist_time matrix_solver_t::compute_next_timestep(const double cur_ts) + netlist_time matrix_solver_t::compute_next_timestep(const nl_fptype cur_ts) { - nl_double new_solver_timestep = m_params.m_max_timestep; + nl_fptype new_solver_timestep = m_params.m_max_timestep; if (m_params.m_dynamic_ts) { for (std::size_t k = 0; k < m_terms.size(); k++) { auto &t = m_terms[k]; - //const nl_double DD_n = (n->Q_Analog() - t->m_last_V); + //const nl_fptype DD_n = (n->Q_Analog() - t->m_last_V); // avoid floating point exceptions - const nl_double DD_n = std::max(-1e100, std::min(1e100,(t.getV() - m_last_V[k]))); - const nl_double hn = cur_ts; + const nl_fptype DD_n = std::max(-1e100, std::min(1e100,(t.getV() - m_last_V[k]))); + const nl_fptype hn = cur_ts; //printf("%g %g %g %g\n", DD_n, hn, t.m_DD_n_m_1, t.m_h_n_m_1); - nl_double DD2 = (DD_n / hn - m_DD_n_m_1[k] / m_h_n_m_1[k]) / (hn + m_h_n_m_1[k]); - nl_double new_net_timestep(0); + nl_fptype DD2 = (DD_n / hn - m_DD_n_m_1[k] / m_h_n_m_1[k]) / (hn + m_h_n_m_1[k]); + nl_fptype new_net_timestep(0); m_h_n_m_1[k] = hn; m_DD_n_m_1[k] = DD_n; - if (std::fabs(DD2) > plib::constants::cast(1e-60)) // avoid div-by-zero - new_net_timestep = std::sqrt(m_params.m_dynamic_lte / std::fabs(plib::constants::cast(0.5)*DD2)); + if (std::fabs(DD2) > plib::constants::cast(1e-60)) // avoid div-by-zero + new_net_timestep = std::sqrt(m_params.m_dynamic_lte / std::fabs(plib::constants::cast(0.5)*DD2)); else new_net_timestep = m_params.m_max_timestep; @@ -607,14 +607,14 @@ namespace solver log().verbose(" has {1} elements", this->has_dynamic_devices() ? "dynamic" : "no dynamic"); log().verbose(" has {1} elements", this->has_timestep_devices() ? "timestep" : "no timestep"); log().verbose(" {1:6.3} average newton raphson loops", - static_cast(this->m_stat_newton_raphson) / static_cast(this->m_stat_vsolver_calls)); + static_cast(this->m_stat_newton_raphson) / static_cast(this->m_stat_vsolver_calls)); log().verbose(" {1:10} invocations ({2:6.0} Hz) {3:10} gs fails ({4:6.2} %) {5:6.3} average", this->m_stat_calculations, - static_cast(this->m_stat_calculations) / this->exec().time().as_double(), + static_cast(this->m_stat_calculations) / this->exec().time().as_double(), this->m_iterative_fail, - 100.0 * static_cast(this->m_iterative_fail) - / static_cast(this->m_stat_calculations), - static_cast(this->m_iterative_total) / static_cast(this->m_stat_calculations)); + 100.0 * static_cast(this->m_iterative_fail) + / static_cast(this->m_stat_calculations), + static_cast(this->m_iterative_total) / static_cast(this->m_stat_calculations)); } } diff --git a/src/lib/netlist/solver/nld_matrix_solver.h b/src/lib/netlist/solver/nld_matrix_solver.h index 07fafd1ece1..4252e7ed751 100644 --- a/src/lib/netlist/solver/nld_matrix_solver.h +++ b/src/lib/netlist/solver/nld_matrix_solver.h @@ -61,7 +61,7 @@ namespace solver /* automatic time step */ , m_dynamic_ts(parent, "DYNAMIC_TS", false) , m_dynamic_lte(parent, "DYNAMIC_LTE", 1e-5) // diff/timestep - , m_dynamic_min_ts(parent, "DYNAMIC_MIN_TIMESTEP", 1e-6) // nl_double timestep resolution + , m_dynamic_min_ts(parent, "DYNAMIC_MIN_TIMESTEP", 1e-6) // nl_fptype timestep resolution /* matrix sorting */ , m_sort_type(parent, "SORT_TYPE", matrix_sort_type_e::PREFER_IDENTITY_TOP_LEFT) @@ -84,26 +84,26 @@ namespace solver } } - param_double_t m_freq; - param_double_t m_gs_sor; + param_fp_t m_freq; + param_fp_t m_gs_sor; param_enum_t m_method; - param_double_t m_accuracy; + param_fp_t m_accuracy; param_num_t m_gs_loops; - param_double_t m_gmin; + param_fp_t m_gmin; param_logic_t m_pivot; param_num_t m_nr_loops; - param_double_t m_nr_recalc_delay; + param_fp_t m_nr_recalc_delay; param_int_t m_parallel; param_logic_t m_dynamic_ts; - param_double_t m_dynamic_lte; - param_double_t m_dynamic_min_ts; + param_fp_t m_dynamic_lte; + param_fp_t m_dynamic_min_ts; param_enum_t m_sort_type; param_logic_t m_use_gabs; param_logic_t m_use_linear_prediction; - nl_double m_min_timestep; - nl_double m_max_timestep; + nl_fptype m_min_timestep; + nl_fptype m_max_timestep; }; @@ -122,9 +122,9 @@ namespace solver terminal_t **terms() noexcept { return m_terms.data(); } - nl_double getV() const noexcept { return m_net->Q_Analog(); } + nl_fptype getV() const noexcept { return m_net->Q_Analog(); } - void setV(nl_double v) noexcept { m_net->set_Q_Analog(v); } + void setV(nl_fptype v) noexcept { m_net->set_Q_Analog(v); } bool isNet(const analog_net_t * net) const noexcept { return net == m_net; } @@ -184,7 +184,7 @@ namespace solver public: int get_net_idx(const analog_net_t *net) const noexcept; std::pair get_left_right_of_diag(std::size_t row, std::size_t diag); - double get_weight_around_diag(std::size_t row, std::size_t diag); + nl_fptype get_weight_around_diag(std::size_t row, std::size_t diag); virtual void log_stats(); @@ -208,7 +208,7 @@ namespace solver virtual unsigned vsolve_non_dynamic(const bool newton_raphson) = 0; - netlist_time compute_next_timestep(const double cur_ts); + netlist_time compute_next_timestep(const nl_fptype cur_ts); /* virtual */ void add_term(std::size_t net_idx, terminal_t *term); template @@ -217,11 +217,6 @@ namespace solver template auto delta(const T & V) -> typename std::decay::type; - template - void build_LE_A(T &child); - template - void build_LE_RHS(T &child); - void set_pointers() { const std::size_t iN = this->m_terms.size(); @@ -252,13 +247,13 @@ namespace solver } } - template - void fill_matrix(std::size_t N, AP &tcr, FT &RHS) + template + void fill_matrix(std::size_t N, FT &RHS) { for (std::size_t k = 0; k < N; k++) { auto &net = m_terms[k]; - auto **tcr_r = &(tcr[k][0]); + auto **tcr_r = &(m_mat_ptr[k][0]); const std::size_t term_count = net.count(); const std::size_t railstart = net.railstart(); @@ -350,28 +345,60 @@ namespace solver } } + template + void clear_square_mat(std::size_t n, M &m) + { + for (std::size_t k=0; k < n; k++) + { + auto *p = &(m[k][0]); + for (std::size_t i=0; i < n; i++) + p[i] = 0.0; + } + } + + template + void build_mat_ptr(std::size_t iN, M &mat) + { + for (std::size_t k=0; km_terms[k].railstart();j++) + { + int other = this->m_terms[k].m_connected_net_idx[j]; + if (other >= 0) + { + m_mat_ptr[k][j] = &(mat[k][static_cast(other)]); + cnt++; + } + } + nl_assert_always(cnt == this->m_terms[k].railstart(), "Count and railstart mismatch"); + m_mat_ptr[k][this->m_terms[k].railstart()] = &(mat[k][k]); + } + } + template using aligned_alloc = plib::aligned_allocator; - plib::pmatrix2d> m_gonn; - plib::pmatrix2d> m_gtn; - plib::pmatrix2d> m_Idrn; - plib::pmatrix2d> m_mat_ptr; - plib::pmatrix2d> m_connected_net_Vn; + plib::pmatrix2d> m_gonn; + plib::pmatrix2d> m_gtn; + plib::pmatrix2d> m_Idrn; + plib::pmatrix2d> m_mat_ptr; + plib::pmatrix2d> m_connected_net_Vn; plib::aligned_vector m_terms; plib::aligned_vector m_rails_temp; /* state - variable time_stepping */ - plib::aligned_vector m_last_V; - plib::aligned_vector m_DD_n_m_1; - plib::aligned_vector m_h_n_m_1; + plib::aligned_vector m_last_V; + plib::aligned_vector m_DD_n_m_1; + plib::aligned_vector m_h_n_m_1; // FIXME: it should be like this, however dimensions are determined // in vsetup. - //state_container> m_last_V; - //state_container> m_DD_n_m_1; - //state_container> m_h_n_m_1; + //state_container> m_last_V; + //state_container> m_DD_n_m_1; + //state_container> m_h_n_m_1; std::vector> m_inps; @@ -426,69 +453,6 @@ namespace solver this->m_terms[i].setV(V[i]); } - template - void matrix_solver_t::build_LE_A(T &child) - { - using float_type = typename T::float_type; - static_assert(std::is_base_of::value, "T must derive from matrix_solver_t"); - - const std::size_t iN = child.size(); - for (std::size_t k = 0; k < iN; k++) - { - terms_for_net_t &terms = m_terms[k]; - float_type * Ak = &child.A(k, 0ul); - - for (std::size_t i=0; i < iN; i++) - Ak[i] = 0.0; - - const std::size_t terms_count = terms.count(); - const std::size_t railstart = terms.railstart(); - const float_type * const gt = m_gtn[k]; - - { - float_type akk = 0.0; - for (std::size_t i = 0; i < terms_count; i++) - akk += gt[i]; - - Ak[k] = akk; - } - - const float_type * const go = m_gonn[k]; - int * net_other = terms.m_connected_net_idx.data(); - - for (std::size_t i = 0; i < railstart; i++) - Ak[net_other[i]] += go[i]; - } - } - - template - void matrix_solver_t::build_LE_RHS(T &child) - { - static_assert(std::is_base_of::value, "T must derive from matrix_solver_t"); - using float_type = typename T::float_type; - - const std::size_t iN = child.size(); - for (std::size_t k = 0; k < iN; k++) - { - float_type rhsk_a = 0.0; - float_type rhsk_b = 0.0; - - const std::size_t terms_count = m_terms[k].count(); - const float_type * const go = m_gonn[k]; - const float_type * const Idr = m_Idrn[k]; - const float_type * const * other_cur_analog = m_connected_net_Vn[k]; - - for (std::size_t i = 0; i < terms_count; i++) - rhsk_a += Idr[i]; - - for (std::size_t i = m_terms[k].railstart(); i < terms_count; i++) - //rhsk = rhsk + go[i] * terms[i]->m_otherterm->net().as_analog().Q_Analog(); - rhsk_b += - go[i] * *other_cur_analog[i]; - - child.RHS(k) = rhsk_a + rhsk_b; - } - } - } // namespace solver } // namespace netlist diff --git a/src/lib/netlist/solver/nld_ms_direct.h b/src/lib/netlist/solver/nld_ms_direct.h index 582a7996947..f3c31dc3371 100644 --- a/src/lib/netlist/solver/nld_ms_direct.h +++ b/src/lib/netlist/solver/nld_ms_direct.h @@ -35,7 +35,15 @@ namespace solver void reset() override { matrix_solver_t::reset(); } + private: + + const std::size_t m_dim; + const std::size_t m_pitch; + protected: + static constexpr const std::size_t SIZEABS = plib::parray::SIZEABS(); + static constexpr const std::size_t m_pitch_ABS = (((SIZEABS + 0) + 7) / 8) * 8; + unsigned vsolve_non_dynamic(const bool newton_raphson) override; unsigned solve_non_dynamic(const bool newton_raphson); @@ -46,24 +54,12 @@ namespace solver template void LE_back_subst(T & x); - const FT &A(std::size_t r, std::size_t c) const noexcept { return m_A[r][c]; } - FT &A(std::size_t r, std::size_t c) noexcept { return m_A[r][c]; } - - const FT &RHS(std::size_t r) const noexcept { return m_A[r][size()]; } - FT &RHS(std::size_t r) noexcept { return m_A[r][size()]; } - PALIGNAS_VECTOROPT() plib::parray m_new_V; - - private: - static constexpr const std::size_t SIZEABS = plib::parray::SIZEABS(); - static constexpr const std::size_t m_pitch_ABS = (((SIZEABS + 1) + 7) / 8) * 8; - - const std::size_t m_dim; - const std::size_t m_pitch; - PALIGNAS_VECTOROPT() plib::parray2D m_A; + PALIGNAS_VECTOROPT() + plib::parray m_RHS; }; // ---------------------------------------------------------------------------------------- @@ -79,16 +75,16 @@ namespace solver for (std::size_t i = 0; i < kN; i++) { /* FIXME: Singular matrix? */ - const FT f = 1.0 / A(i,i); + const FT f = 1.0 / m_A[i][i]; const auto &nzrd = m_terms[i].m_nzrd; const auto &nzbd = m_terms[i].m_nzbd; for (auto &j : nzbd) { - const FT f1 = -f * A(j, i); + const FT f1 = -f * m_A[j][i]; for (auto &k : nzrd) - A(j, k) += A(i, k) * f1; - //RHS(j) += RHS(i) * f1; + m_A[j][k] += m_A[i][k] * f1; + m_RHS[j] += m_RHS[i] * f1; } } } @@ -101,7 +97,7 @@ namespace solver for (std::size_t j = i + 1; j < kN; j++) { //if (std::abs(m_A[j][i]) > std::abs(m_A[maxrow][i])) - if (A(j,i) * A(j,i) > A(maxrow,i) * A(maxrow,i)) + if (m_A[j][i] * m_A[j][i] > m_A[maxrow][i] * m_A[maxrow][i]) maxrow = j; } @@ -109,32 +105,28 @@ namespace solver { /* Swap the maxrow and ith row */ for (std::size_t k = 0; k < kN + 1; k++) { - std::swap(A(i,k), A(maxrow,k)); + std::swap(m_A[i][k], m_A[maxrow][k]); } //std::swap(RHS(i), RHS(maxrow)); } /* FIXME: Singular matrix? */ - const FT f = 1.0 / A(i,i); + const FT f = 1.0 / m_A[i][i]; /* Eliminate column i from row j */ for (std::size_t j = i + 1; j < kN; j++) { - const FT f1 = - A(j,i) * f; + const FT f1 = - m_A[j][i] * f; if (f1 != plib::constants::zero()) { - const FT * pi = &A(i,i+1); - FT * pj = &A(j,i+1); - #if 1 - plib::vec_add_mult_scalar_p(kN-i,pj, pi,f1); - #else - vec_add_mult_scalar_p1(kN-i-1,pj,pi,f1); + const FT * pi = &(m_A[i][i+1]); + FT * pj = &(m_A[j][i+1]); + plib::vec_add_mult_scalar_p(kN-i-1,pj,pi,f1); //for (unsigned k = i+1; k < kN; k++) // pj[k] = pj[k] + pi[k] * f1; //for (unsigned k = i+1; k < kN; k++) //A(j,k) += A(i,k) * f1; - RHS(j) += RHS(i) * f1; - #endif + m_RHS[j] += m_RHS[i] * f1; } } } @@ -155,8 +147,8 @@ namespace solver { FT tmp = 0; for (std::size_t k = j+1; k < kN; k++) - tmp += A(j,k) * x[k]; - x[j] = (RHS(j) - tmp) / A(j,j); + tmp += m_A[j][k] * x[k]; + x[j] = (m_RHS[j] - tmp) / m_A[j][j]; } } else @@ -165,10 +157,10 @@ namespace solver { FT tmp = 0; const auto &nzrd = m_terms[j].m_nzrd; - const auto e = nzrd.size() - 1; /* exclude RHS element */ + const auto e = nzrd.size(); // - 1; /* exclude RHS element */ for ( std::size_t k = 0; k < e; k++) - tmp += A(j, nzrd[k]) * x[nzrd[k]]; - x[j] = (RHS(j) - tmp) / A(j,j); + tmp += m_A[j][nzrd[k]] * x[nzrd[k]]; + x[j] = (m_RHS[j] - tmp) / m_A[j][j]; } } } @@ -187,8 +179,12 @@ namespace solver template unsigned matrix_solver_direct_t::vsolve_non_dynamic(const bool newton_raphson) { - this->build_LE_A(*this); - this->build_LE_RHS(*this); + const std::size_t iN = this->size(); + + /* populate matrix */ + + this->clear_square_mat(iN, m_A); + this->fill_matrix(iN, m_RHS); this->m_stat_calculations++; return this->solve_non_dynamic(newton_raphson); @@ -200,23 +196,13 @@ namespace solver const solver_parameters_t *params, const std::size_t size) : matrix_solver_t(anetlist, name, nets, params) - , m_new_V(size) , m_dim(size) - , m_pitch(m_pitch_ABS ? m_pitch_ABS : (((m_dim + 1) + 7) / 8) * 8) + , m_pitch(m_pitch_ABS ? m_pitch_ABS : (((m_dim + 0) + 7) / 8) * 8) + , m_new_V(size) , m_A(size, m_pitch) + , m_RHS(size) { - /* add RHS element */ - for (std::size_t k = 0; k < this->size(); k++) - { - terms_for_net_t & t = m_terms[k]; - - if (!plib::container::contains(t.m_nzrd, static_cast(this->size()))) - t.m_nzrd.push_back(static_cast(this->size())); - } - - // FIXME: This shouldn't be necessary ... - for (std::size_t k = 0; k < this->size(); k++) - state().save(*this, RHS(k), this->name(), plib::pfmt("RHS.{1}")(k)); + this->build_mat_ptr(size, m_A); } } // namespace solver diff --git a/src/lib/netlist/solver/nld_ms_direct1.h b/src/lib/netlist/solver/nld_ms_direct1.h index c6ebd77e198..1eb992104a8 100644 --- a/src/lib/netlist/solver/nld_ms_direct1.h +++ b/src/lib/netlist/solver/nld_ms_direct1.h @@ -34,11 +34,10 @@ namespace solver // ---------------------------------------------------------------------------------------- unsigned vsolve_non_dynamic(const bool newton_raphson) override { - this->build_LE_A(*this); - this->build_LE_RHS(*this); - //NL_VERBOSE_OUT(("{1} {2}\n", new_val, m_RHS[0] / m_A[0][0]); + this->clear_square_mat(1, this->m_A); + this->fill_matrix(1, this->m_RHS); - std::array new_V = { this->RHS(0) / this->A(0,0) }; + std::array new_V = { this->m_RHS[0] / this->m_A[0][0] }; const FT err = (newton_raphson ? this->delta(new_V) : 0.0); this->store(new_V); diff --git a/src/lib/netlist/solver/nld_ms_direct2.h b/src/lib/netlist/solver/nld_ms_direct2.h index 20d3bb659e5..4479ce8003e 100644 --- a/src/lib/netlist/solver/nld_ms_direct2.h +++ b/src/lib/netlist/solver/nld_ms_direct2.h @@ -34,16 +34,16 @@ namespace solver {} unsigned vsolve_non_dynamic(const bool newton_raphson) override { - this->build_LE_A(*this); - this->build_LE_RHS(*this); + this->clear_square_mat(2, this->m_A); + this->fill_matrix(2, this->m_RHS); - const float_type a = this->A(0,0); - const float_type b = this->A(0,1); - const float_type c = this->A(1,0); - const float_type d = this->A(1,1); + const float_type a = this->m_A[0][0]; + const float_type b = this->m_A[0][1]; + const float_type c = this->m_A[1][0]; + const float_type d = this->m_A[1][1]; - const float_type v1 = (a * this->RHS(1) - c * this->RHS(0)) / (a * d - b * c); - const float_type v0 = (this->RHS(0) - b * v1) / a; + const float_type v1 = (a * this->m_RHS[1] - c * this->m_RHS[0]) / (a * d - b * c); + const float_type v0 = (this->m_RHS[0] - b * v1) / a; std::array new_V = {v0, v1}; this->m_stat_calculations++; diff --git a/src/lib/netlist/solver/nld_ms_gcr.h b/src/lib/netlist/solver/nld_ms_gcr.h index 3aa39b7bb54..bfc92ba97f9 100644 --- a/src/lib/netlist/solver/nld_ms_gcr.h +++ b/src/lib/netlist/solver/nld_ms_gcr.h @@ -90,9 +90,9 @@ namespace solver this->log().verbose("maximum fill: {1}", gr.first); this->log().verbose("Post elimination occupancy ratio: {2} Ops: {1}", gr.second, - static_cast(mat.nz_num) / static_cast(iN * iN)); + static_cast(mat.nz_num) / static_cast(iN * iN)); this->log().verbose(" Pre elimination occupancy ratio: {2}", - static_cast(raw_elements) / static_cast(iN * iN)); + static_cast(raw_elements) / static_cast(iN * iN)); // FIXME: Move me @@ -131,7 +131,7 @@ namespace solver mat_type mat; - plib::dynproc m_proc; + plib::dynproc m_proc; }; @@ -238,7 +238,7 @@ namespace solver /* populate matrix */ - this->fill_matrix(iN, m_mat_ptr, RHS); + this->fill_matrix(iN, RHS); /* now solve it */ diff --git a/src/lib/netlist/solver/nld_ms_gmres.h b/src/lib/netlist/solver/nld_ms_gmres.h index b5e3f605cc0..a4926e2fc1d 100644 --- a/src/lib/netlist/solver/nld_ms_gmres.h +++ b/src/lib/netlist/solver/nld_ms_gmres.h @@ -106,7 +106,7 @@ namespace solver m_ops.m_mat.set_scalar(0.0); /* populate matrix and V for first estimate */ - this->fill_matrix(iN, this->m_mat_ptr, RHS); + this->fill_matrix(iN, RHS); for (std::size_t k = 0; k < iN; k++) { diff --git a/src/lib/netlist/solver/nld_ms_sm.h b/src/lib/netlist/solver/nld_ms_sm.h index 30ad2031628..83e309407f7 100644 --- a/src/lib/netlist/solver/nld_ms_sm.h +++ b/src/lib/netlist/solver/nld_ms_sm.h @@ -63,9 +63,7 @@ namespace solver , m_dim(size) , m_cnt(0) { - /* FIXME: Shouldn't be necessary */ - for (std::size_t k = 0; k < this->size(); k++) - state().save(*this, RHS(k), this->name(), plib::pfmt("RHS.{1}")(k)); + this->build_mat_ptr(this->size(), m_A); } void reset() override { matrix_solver_t::reset(); } @@ -289,8 +287,10 @@ namespace solver template unsigned matrix_solver_sm_t::vsolve_non_dynamic(const bool newton_raphson) { - this->build_LE_A(*this); - this->build_LE_RHS(*this); + + const std::size_t iN = this->size(); + this->clear_square_mat(iN, this->m_A); + this->fill_matrix(iN, this->m_RHS); this->m_stat_calculations++; return this->solve_non_dynamic(newton_raphson); diff --git a/src/lib/netlist/solver/nld_ms_sor.h b/src/lib/netlist/solver/nld_ms_sor.h index 98e2c8ddc6d..cfc0e1e8fd5 100644 --- a/src/lib/netlist/solver/nld_ms_sor.h +++ b/src/lib/netlist/solver/nld_ms_sor.h @@ -102,7 +102,7 @@ namespace solver for (std::size_t i = 0; i < term_count; i++) gabs_t = gabs_t + std::abs(go[i]); - gabs_t *= plib::constants::cast(0.5); // derived by try and error + gabs_t *= plib::constants::cast(0.5); // derived by try and error if (gabs_t <= gtot_t) { w[k] = ws / gtot_t; diff --git a/src/lib/netlist/solver/nld_ms_sor_mat.h b/src/lib/netlist/solver/nld_ms_sor_mat.h index 2b705858854..f73e88a4d02 100644 --- a/src/lib/netlist/solver/nld_ms_sor_mat.h +++ b/src/lib/netlist/solver/nld_ms_sor_mat.h @@ -117,14 +117,13 @@ namespace solver const std::size_t iN = this->size(); - this->build_LE_A(*this); - this->build_LE_RHS(*this); + this->clear_square_mat(iN, this->m_A); + this->fill_matrix(iN, this->m_RHS); bool resched = false; unsigned resched_cnt = 0; - #if 0 static int ws_cnt = 0; ws_cnt++; @@ -174,24 +173,24 @@ namespace solver const std::size_t e = this->m_terms[k].m_nz.size(); for (std::size_t i = 0; i < e; i++) - Idrive = Idrive + this->A(k,p[i]) * this->m_new_V[p[i]]; + Idrive = Idrive + this->m_A[k][p[i]] * this->m_new_V[p[i]]; - FT w = m_omega / this->A(k,k); + FT w = m_omega / this->m_A[k][k]; if (this->m_params.m_use_gabs) { FT gabs_t = 0.0; for (std::size_t i = 0; i < e; i++) if (p[i] != k) - gabs_t = gabs_t + std::abs(this->A(k,p[i])); + gabs_t = gabs_t + std::abs(this->m_A[k][p[i]]); gabs_t *= plib::constants::one(); // derived by try and error - if (gabs_t > this->A(k,k)) + if (gabs_t > this->m_A[k][k]) { - w = plib::constants::one() / (this->A(k,k) + gabs_t); + w = plib::constants::one() / (this->m_A[k][k] + gabs_t); } } - const float_type delta = w * (this->RHS(k) - Idrive) ; + const float_type delta = w * (this->m_RHS[k] - Idrive) ; cerr = std::max(cerr, std::abs(delta)); this->m_new_V[k] += delta; } diff --git a/src/lib/netlist/solver/nld_ms_w.h b/src/lib/netlist/solver/nld_ms_w.h index 0e627c86a72..2fd62250b3c 100644 --- a/src/lib/netlist/solver/nld_ms_w.h +++ b/src/lib/netlist/solver/nld_ms_w.h @@ -70,9 +70,7 @@ namespace solver , m_cnt(0) , m_dim(size) { - // FIXME: This shouldn't be necessary, recalculate on each entry ... - for (std::size_t k = 0; k < this->size(); k++) - state().save(*this, RHS(k), this->name(), plib::pfmt("RHS.{1}")(k)); + this->build_mat_ptr(this->size(), m_A); } void reset() override { matrix_solver_t::reset(); } @@ -267,7 +265,7 @@ namespace solver for (unsigned i = 0; i < rowcount; i++) { const unsigned r = rows[i]; - double tmp = 0.0; + nl_fptype tmp = 0.0; for (unsigned k = 0; k < iN; k++) tmp += VT(r,k) * new_V[k]; w[i] = tmp; @@ -359,8 +357,9 @@ namespace solver template unsigned matrix_solver_w_t::vsolve_non_dynamic(const bool newton_raphson) { - this->build_LE_A(*this); - this->build_LE_RHS(*this); + const std::size_t iN = this->size(); + this->clear_square_mat(iN, this->m_A); + this->fill_matrix(iN, this->m_RHS); this->m_stat_calculations++; return this->solve_non_dynamic(newton_raphson); diff --git a/src/lib/netlist/solver/nld_solver.cpp b/src/lib/netlist/solver/nld_solver.cpp index e19e216a09f..db2c831a79e 100644 --- a/src/lib/netlist/solver/nld_solver.cpp +++ b/src/lib/netlist/solver/nld_solver.cpp @@ -231,62 +231,62 @@ namespace devices switch (net_count) { case 1: - ms = plib::make_unique>(state(), sname, grp, &m_params); + ms = plib::make_unique>(state(), sname, grp, &m_params); break; case 2: - ms = plib::make_unique>(state(), sname, grp, &m_params); + ms = plib::make_unique>(state(), sname, grp, &m_params); break; #if 0 case 3: - ms = create_solver(3, sname, grp); + ms = create_solver(3, sname, grp); break; case 4: - ms = create_solver(4, sname, grp); + ms = create_solver(4, sname, grp); break; case 5: - ms = create_solver(5, sname, grp); + ms = create_solver(5, sname, grp); break; case 6: - ms = create_solver(6, sname, grp); + ms = create_solver(6, sname, grp); break; case 7: - ms = create_solver(7, sname, grp); + ms = create_solver(7, sname, grp); break; case 8: - ms = create_solver(8, sname, grp); + ms = create_solver(8, sname, grp); break; case 9: - ms = create_solver(9, sname, grp); + ms = create_solver(9, sname, grp); break; case 10: - ms = create_solver(10, sname, grp); + ms = create_solver(10, sname, grp); break; #if 0 case 11: - ms = create_solver(11, sname); + ms = create_solver(11, sname); break; case 12: - ms = create_solver(12, sname); + ms = create_solver(12, sname); break; case 15: - ms = create_solver(15, sname); + ms = create_solver(15, sname); break; case 31: - ms = create_solver(31, sname); + ms = create_solver(31, sname); break; case 35: - ms = create_solver(35, sname); + ms = create_solver(35, sname); break; case 43: - ms = create_solver(43, sname); + ms = create_solver(43, sname); break; case 49: - ms = create_solver(49, sname); + ms = create_solver(49, sname); break; #endif #if 1 case 87: - ms = create_solver(86, sname, grp); + ms = create_solver(86, sname, grp); break; #endif #endif @@ -294,35 +294,35 @@ namespace devices log().info(MI_NO_SPECIFIC_SOLVER(net_count)); if (net_count <= 8) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 16) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 32) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 64) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 128) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 256) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else if (net_count <= 512) { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } else { - ms = create_solver(net_count, sname, grp); + ms = create_solver(net_count, sname, grp); } break; } diff --git a/src/lib/netlist/solver/nld_solver.h b/src/lib/netlist/solver/nld_solver.h index d4d506d3683..dba6b69f358 100644 --- a/src/lib/netlist/solver/nld_solver.h +++ b/src/lib/netlist/solver/nld_solver.h @@ -39,7 +39,7 @@ namespace devices void post_start(); void stop(); - nl_double gmin() const { return m_params.m_gmin(); } + nl_fptype gmin() const { return m_params.m_gmin(); } void create_solver_code(std::map &mp); -- cgit v1.2.3