diff options
author | 2016-05-15 14:43:15 +0200 | |
---|---|---|
committer | 2016-05-16 12:50:50 +0200 | |
commit | 332534cdf5ed94a51c67e089f00e52228085122f (patch) | |
tree | 9374cf087e08c532a5e4b56994ece7209fc5f321 | |
parent | f35ba3f5fdbc8394864863bca70d5b31fa582cfe (diff) |
Continuing work to move object initialization from start to constructor.
Removed family_t. All of this can be determined at runtime from object
as well. As part of this, the "template" to write devices has changed.
Converted a number of devices to use the new template. [Couriersud]
46 files changed, 894 insertions, 815 deletions
diff --git a/src/devices/machine/netlist.cpp b/src/devices/machine/netlist.cpp index b5ee493caba..d51c113d81c 100644 --- a/src/devices/machine/netlist.cpp +++ b/src/devices/machine/netlist.cpp @@ -476,7 +476,7 @@ void netlist_mame_cpu_device_t::device_start() for (int i=0; i < netlist().m_nets.size(); i++) { netlist::net_t *n = netlist().m_nets[i].get(); - if (n->isFamily(netlist::object_t::LOGIC)) + if (n->is_logic()) { state_add(i*2, n->name().cstr(), downcast<netlist::logic_net_t *>(n)->Q_state_ptr()); } diff --git a/src/lib/netlist/analog/nld_bjt.cpp b/src/lib/netlist/analog/nld_bjt.cpp index 75b76278bce..24ea4a63e5b 100644 --- a/src/lib/netlist/analog/nld_bjt.cpp +++ b/src/lib/netlist/analog/nld_bjt.cpp @@ -44,15 +44,6 @@ private: // nld_Q // ---------------------------------------------------------------------------------------- -NETLIB_NAME(Q)::NETLIB_NAME(Q)(const family_t afamily, netlist_t &anetlist, const pstring &name) -: device_t(afamily, anetlist, name) -, m_qtype(BJT_NPN) { } - -NETLIB_NAME(Q)::~NETLIB_NAME(Q)() -{ -} - - NETLIB_START(Q) { register_param("MODEL", m_model, ""); diff --git a/src/lib/netlist/analog/nld_bjt.h b/src/lib/netlist/analog/nld_bjt.h index 5448964a335..a84f01376ac 100644 --- a/src/lib/netlist/analog/nld_bjt.h +++ b/src/lib/netlist/analog/nld_bjt.h @@ -32,7 +32,7 @@ NETLIB_NAMESPACE_DEVICES_START() // Have a common start for transistors -class NETLIB_NAME(Q) : public device_t +NETLIB_OBJECT(Q) { public: enum q_type { @@ -40,8 +40,11 @@ public: BJT_PNP }; - NETLIB_NAME(Q)(const family_t afamily, netlist_t &anetlist, const pstring &name); - virtual ~NETLIB_NAME(Q)(); + NETLIB_CONSTRUCTOR(Q) + , m_qtype(BJT_NPN) + { } + + NETLIB_DYNAMIC() inline q_type qtype() const { return m_qtype; } inline bool is_qtype(q_type atype) const { return m_qtype == atype; } @@ -56,14 +59,11 @@ private: q_type m_qtype; }; -class NETLIB_NAME(QBJT) : public NETLIB_NAME(Q) +NETLIB_OBJECT_DERIVED(QBJT, Q) { public: - - NETLIB_NAME(QBJT)(const family_t afamily, netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(Q)(afamily, anetlist, name) { } - - virtual ~NETLIB_NAME(QBJT)() { } + NETLIB_CONSTRUCTOR_DERIVED(QBJT, Q) + { } protected: @@ -91,19 +91,17 @@ private: * E */ -class NETLIB_NAME(QBJT_switch) : public NETLIB_NAME(QBJT) +NETLIB_OBJECT_DERIVED(QBJT_switch, QBJT) { public: - ATTR_COLD NETLIB_NAME(QBJT_switch)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(QBJT)(BJT_SWITCH, anetlist, name), - m_RB(object_t::ANALOG, anetlist, "m_RB"), - m_RC(object_t::ANALOG, anetlist, "m_RC"), - m_BC_dummy(object_t::ANALOG, anetlist, "m_BC"), - m_gB(NETLIST_GMIN_DEFAULT), - m_gC(NETLIST_GMIN_DEFAULT), - m_V(0.0), - m_state_on(0) { } - + NETLIB_CONSTRUCTOR_DERIVED(QBJT_switch, QBJT) + , m_RB(owner, "m_RB") + , m_RC(owner, "m_RC") + , m_BC_dummy(owner, "m_BC") + , m_gB(NETLIST_GMIN_DEFAULT) + , m_gC(NETLIST_GMIN_DEFAULT) + , m_V(0.0) + , m_state_on(0) { } ATTR_HOT void virtual update() override; @@ -134,16 +132,15 @@ private: // ----------------------------------------------------------------------------- -class NETLIB_NAME(QBJT_EB) : public NETLIB_NAME(QBJT) +NETLIB_OBJECT_DERIVED(QBJT_EB, QBJT) { public: - ATTR_COLD NETLIB_NAME(QBJT_EB)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(QBJT)(BJT_EB, anetlist, name), - m_D_CB(object_t::ANALOG, anetlist, "m_D_CB"), - m_D_EB(object_t::ANALOG, anetlist, "m_D_EB"), - m_D_EC(object_t::ANALOG, anetlist, "m_D_EC"), - m_alpha_f(0), - m_alpha_r(0) + NETLIB_CONSTRUCTOR_DERIVED(QBJT_EB, QBJT) + , m_D_CB(owner, "m_D_CB") + , m_D_EB(owner, "m_D_EB") + , m_D_EC(owner, "m_D_EC") + , m_alpha_f(0) + , m_alpha_r(0) { } protected: diff --git a/src/lib/netlist/analog/nld_fourterm.cpp b/src/lib/netlist/analog/nld_fourterm.cpp index 5d1895f147c..431566de770 100644 --- a/src/lib/netlist/analog/nld_fourterm.cpp +++ b/src/lib/netlist/analog/nld_fourterm.cpp @@ -15,12 +15,6 @@ NETLIB_NAMESPACE_DEVICES_START() // nld_VCCS // ---------------------------------------------------------------------------------------- -NETLIB_START(VCCS) -{ - start_internal(NL_FCONST(1.0) / netlist().gmin()); - m_gfac = NL_FCONST(1.0); -} - void NETLIB_NAME(VCCS)::start_internal(const nl_double def_RI) { register_param("G", m_G, 1.0); @@ -62,11 +56,6 @@ NETLIB_RESET(VCCS) m_ON1.set(m_mult, NL_FCONST(0.0)); } -NETLIB_UPDATE_PARAM(VCCS) -{ - NETLIB_NAME(VCCS)::reset(); -} - NETLIB_UPDATE(VCCS) { /* only called if connected to a rail net ==> notify the solver to recalculate */ diff --git a/src/lib/netlist/analog/nld_fourterm.h b/src/lib/netlist/analog/nld_fourterm.h index 4f40eea3dc8..58a40c25498 100644 --- a/src/lib/netlist/analog/nld_fourterm.h +++ b/src/lib/netlist/analog/nld_fourterm.h @@ -51,22 +51,26 @@ NETLIB_NAMESPACE_DEVICES_START() * */ -class NETLIB_NAME(VCCS) : public device_t +NETLIB_OBJECT(VCCS) { public: - ATTR_COLD NETLIB_NAME(VCCS)(netlist_t &anetlist, const pstring &name) - : device_t(VCCS, anetlist, name), m_gfac(1.0) { } - ATTR_COLD NETLIB_NAME(VCCS)(const family_t afamily, netlist_t &anetlist, const pstring &name) - : device_t(afamily, anetlist, name), m_gfac(1.0) { } + NETLIB_CONSTRUCTOR(VCCS) + , m_gfac(1.0) + { + start_internal(NL_FCONST(1.0) / netlist().gmin()); + m_gfac = NL_FCONST(1.0); + } param_double_t m_G; param_double_t m_RI; protected: - virtual void start() override; - virtual void reset() override; - virtual void update_param() override; - ATTR_HOT virtual void update() override; + NETLIB_RESETI(); + NETLIB_UPDATEI(); + NETLIB_UPDATE_PARAMI() + { + NETLIB_NAME(VCCS)::reset(); + } ATTR_COLD void start_internal(const nl_double def_RI); @@ -84,13 +88,14 @@ protected: /* Limited Current source*/ -class NETLIB_NAME(LVCCS) : public NETLIB_NAME(VCCS) +NETLIB_OBJECT_DERIVED(LVCCS, VCCS) { public: - ATTR_COLD NETLIB_NAME(LVCCS)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(VCCS)(LVCCS, anetlist, name), m_vi(0.0) { } - ATTR_COLD NETLIB_NAME(LVCCS)(const family_t afamily, netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(VCCS)(afamily, anetlist, name), m_vi(0.0) { } + NETLIB_CONSTRUCTOR_DERIVED(LVCCS, VCCS) + , m_vi(0.0) + { } + + NETLIB_DYNAMIC() param_double_t m_cur_limit; /* current limit */ @@ -127,11 +132,12 @@ protected: * */ -class NETLIB_NAME(CCCS) : public NETLIB_NAME(VCCS) +NETLIB_OBJECT_DERIVED(CCCS, VCCS) { public: - ATTR_COLD NETLIB_NAME(CCCS)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(VCCS)(CCCS, anetlist, name), m_gfac(1.0) { } + NETLIB_CONSTRUCTOR_DERIVED(CCCS, VCCS) + , m_gfac(1.0) + { } protected: virtual void start() override; @@ -171,11 +177,10 @@ protected: */ -class NETLIB_NAME(VCVS) : public NETLIB_NAME(VCCS) +NETLIB_OBJECT_DERIVED(VCVS, VCCS) { public: - ATTR_COLD NETLIB_NAME(VCVS)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(VCCS)(VCVS, anetlist, name) { } + NETLIB_CONSTRUCTOR_DERIVED(VCVS, VCCS) { } param_double_t m_RO; diff --git a/src/lib/netlist/analog/nld_opamps.cpp b/src/lib/netlist/analog/nld_opamps.cpp index 606d0ef5515..0ffd5d56a9c 100644 --- a/src/lib/netlist/analog/nld_opamps.cpp +++ b/src/lib/netlist/analog/nld_opamps.cpp @@ -48,64 +48,6 @@ NETLIB_NAMESPACE_DEVICES_START() * 4: opamp with input stage, first pole + output limit */ -NETLIB_START(OPAMP) -{ - register_param("MODEL", m_model, ""); - - m_type = m_model.model_value("TYPE"); - - enregister("VCC", m_VCC); - enregister("GND", m_GND); - - enregister("VL", m_VL); - enregister("VH", m_VH); - enregister("VREF", m_VREF); - - register_sub("G1", m_G1); - register_sub("RP1", m_RP); - - if (m_type == 1) - { - register_subalias("PLUS", "G1.IP"); - register_subalias("MINUS", "G1.IN"); - register_subalias("OUT", "G1.OP"); - - connect_late("G1.ON", "VREF"); - connect_late("RP1.2", "VREF"); - connect_late("RP1.1", "G1.OP"); - - } - else if (m_type == 3) - { - register_sub("CP1", m_CP); - register_sub("EBUF", m_EBUF); - register_sub("DN", m_DN); - register_sub("DP", m_DP); - - register_subalias("PLUS", "G1.IP"); - register_subalias("MINUS", "G1.IN"); - register_subalias("OUT", "EBUF.OP"); - - connect_late("EBUF.ON", "VREF"); - - connect_late("G1.ON", "VREF"); - connect_late("RP1.2", "VREF"); - connect_late("CP1.2", "VREF"); - connect_late("EBUF.IN", "VREF"); - - connect_late("RP1.1", "G1.OP"); - connect_late("CP1.1", "RP1.1"); - - connect_late("DP.K", "VH"); - connect_late("VL", "DN.A"); - connect_late("DP.A", "DN.K"); - connect_late("DN.K", "RP1.1"); - connect_late("EBUF.IP", "RP1.1"); - } - else - netlist().log().fatal("Unknown opamp type: {1}", m_type); -} - /* .model abc OPAMP(VLH=2.0 VLL=0.2 FPF=5 UGF=10k SLEW=0.6u RI=1000k RO=50 DAB=0.002) * * Differential Amp Bias ~ op amp's total quiescent current. @@ -123,15 +65,15 @@ NETLIB_UPDATE(OPAMP) NETLIB_RESET(OPAMP) { - m_G1->do_reset(); - m_G1->m_RI.setTo(m_model.model_value("RI")); + m_G1.do_reset(); + m_G1.m_RI.setTo(m_model.model_value("RI")); if (m_type == 1) { double RO = m_model.model_value("RO"); double G = m_model.model_value("UGF") / m_model.model_value("FPF") / RO; - m_RP->set_R(RO); - m_G1->m_G.setTo(G); + m_RP.set_R(RO); + m_G1.m_G.setTo(G); } else if (m_type == 3) { @@ -139,7 +81,7 @@ NETLIB_RESET(OPAMP) m_DP->do_reset(); m_DN->do_reset(); m_CP->do_reset(); - m_RP->do_reset(); + m_RP.do_reset(); m_EBUF->m_G.setTo(1.0); m_EBUF->m_RO.setTo(m_model.model_value("RO")); @@ -151,16 +93,10 @@ NETLIB_RESET(OPAMP) double G = m_model.model_value("UGF") / m_model.model_value("FPF") / RP; m_CP->m_C.setTo(CP); - m_RP->set_R(RP); - m_G1->m_G.setTo(G); + m_RP.set_R(RP); + m_G1.m_G.setTo(G); } - - -} - -NETLIB_UPDATE_PARAM(OPAMP) -{ } /* diff --git a/src/lib/netlist/analog/nld_opamps.h b/src/lib/netlist/analog/nld_opamps.h index 65ad97b2b42..4aafb25e748 100644 --- a/src/lib/netlist/analog/nld_opamps.h +++ b/src/lib/netlist/analog/nld_opamps.h @@ -34,13 +34,80 @@ NETLIST_EXTERNAL(opamp_lm3900) NETLIB_NAMESPACE_DEVICES_START() -NETLIB_DEVICE_WITH_PARAMS(OPAMP, +NETLIB_OBJECT(OPAMP) +{ + NETLIB_CONSTRUCTOR(OPAMP) + , m_RP(*this, "RP1") + , m_G1(*this, "G1") + { + register_param("MODEL", m_model, ""); + + m_type = m_model.model_value("TYPE"); + + enregister("VCC", m_VCC); + enregister("GND", m_GND); + + enregister("VL", m_VL); + enregister("VH", m_VH); + enregister("VREF", m_VREF); + + if (m_type == 1) + { + register_subalias("PLUS", "G1.IP"); + register_subalias("MINUS", "G1.IN"); + register_subalias("OUT", "G1.OP"); + + connect_late("G1.ON", "VREF"); + connect_late("RP1.2", "VREF"); + connect_late("RP1.1", "G1.OP"); + + } + else if (m_type == 3) + { + register_sub("CP1", m_CP); + register_sub("EBUF", m_EBUF); + register_sub("DN", m_DN); + register_sub("DP", m_DP); + + register_subalias("PLUS", "G1.IP"); + register_subalias("MINUS", "G1.IN"); + register_subalias("OUT", "EBUF.OP"); + + connect_late("EBUF.ON", "VREF"); + + connect_late("G1.ON", "VREF"); + connect_late("RP1.2", "VREF"); + connect_late("CP1.2", "VREF"); + connect_late("EBUF.IN", "VREF"); + + connect_late("RP1.1", "G1.OP"); + connect_late("CP1.1", "RP1.1"); + + connect_late("DP.K", "VH"); + connect_late("VL", "DN.A"); + connect_late("DP.A", "DN.K"); + connect_late("DN.K", "RP1.1"); + connect_late("EBUF.IP", "RP1.1"); + } + else + netlist().log().fatal("Unknown opamp type: {1}", m_type); + + } + + NETLIB_UPDATEI(); + NETLIB_RESETI(); + NETLIB_UPDATE_PARAMI() + { + } + +private: + NETLIB_SUB(R) m_RP; - NETLIB_SUB(C) m_CP; NETLIB_SUB(VCCS) m_G1; - NETLIB_SUB(VCVS) m_EBUF; - NETLIB_SUB(D) m_DP; - NETLIB_SUB(D) m_DN; + NETLIB_SUBXX(C) m_CP; + NETLIB_SUBXX(VCVS) m_EBUF; + NETLIB_SUBXX(D) m_DP; + NETLIB_SUBXX(D) m_DN; analog_input_t m_VCC; analog_input_t m_GND; @@ -52,7 +119,7 @@ NETLIB_DEVICE_WITH_PARAMS(OPAMP, /* state */ unsigned m_type; -); +}; NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/analog/nld_switches.cpp b/src/lib/netlist/analog/nld_switches.cpp index 57a895f1d18..fe21fe4576b 100644 --- a/src/lib/netlist/analog/nld_switches.cpp +++ b/src/lib/netlist/analog/nld_switches.cpp @@ -17,35 +17,25 @@ NETLIB_NAMESPACE_DEVICES_START() // SWITCH // ---------------------------------------------------------------------------------------- -NETLIB_START(switch1) -{ - register_sub("R", m_R); - - register_param("POS", m_POS, 0); - - register_subalias("1", m_R->m_P); - register_subalias("2", m_R->m_N); -} - NETLIB_RESET(switch1) { - m_R->do_reset(); + m_R.do_reset(); - m_R->set_R(R_OFF); + m_R.set_R(R_OFF); } NETLIB_UPDATE(switch1) { if (m_POS.Value() == 0) { - m_R->set_R(R_OFF); + m_R.set_R(R_OFF); } else { - m_R->set_R(R_ON); + m_R.set_R(R_ON); } - m_R->update_dev(); + m_R.update_dev(); } NETLIB_UPDATE_PARAM(switch1) @@ -58,45 +48,30 @@ NETLIB_UPDATE_PARAM(switch1) // ---------------------------------------------------------------------------------------- -NETLIB_START(switch2) -{ - register_sub("R1", m_R[0]); - register_sub("R2", m_R[1]); - - register_param("POS", m_POS, 0); - - connect_late(m_R[0]->m_N, m_R[1]->m_N); - - register_subalias("1", m_R[0]->m_P); - register_subalias("2", m_R[1]->m_P); - - register_subalias("Q", m_R[0]->m_N); -} - NETLIB_RESET(switch2) { - m_R[0]->do_reset(); - m_R[1]->do_reset(); + m_R1.do_reset(); + m_R2.do_reset(); - m_R[0]->set_R(R_ON); - m_R[1]->set_R(R_OFF); + m_R1.set_R(R_ON); + m_R2.set_R(R_OFF); } NETLIB_UPDATE(switch2) { if (m_POS.Value() == 0) { - m_R[0]->set_R(R_ON); - m_R[1]->set_R(R_OFF); + m_R1.set_R(R_ON); + m_R2.set_R(R_OFF); } else { - m_R[0]->set_R(R_OFF); - m_R[1]->set_R(R_ON); + m_R1.set_R(R_OFF); + m_R2.set_R(R_ON); } - m_R[0]->update_dev(); - m_R[1]->update_dev(); + m_R1.update_dev(); + m_R2.update_dev(); } NETLIB_UPDATE_PARAM(switch2) diff --git a/src/lib/netlist/analog/nld_switches.h b/src/lib/netlist/analog/nld_switches.h index 590761b01e6..63afb47bdd1 100644 --- a/src/lib/netlist/analog/nld_switches.h +++ b/src/lib/netlist/analog/nld_switches.h @@ -29,17 +29,48 @@ NETLIB_NAMESPACE_DEVICES_START() -NETLIB_DEVICE_WITH_PARAMS(switch1, - NETLIB_SUB(R_base) m_R; +NETLIB_OBJECT(switch1) +{ + NETLIB_CONSTRUCTOR(switch1) + , m_R(*this, "R") + { + register_param("POS", m_POS, 0); + register_subalias("1", m_R.m_P); + register_subalias("2", m_R.m_N); + } + + NETLIB_RESETI(); + NETLIB_UPDATEI(); + NETLIB_UPDATE_PARAMI(); + NETLIB_SUB(R_base) m_R; param_int_t m_POS; -); +}; + +NETLIB_OBJECT(switch2) +{ + NETLIB_CONSTRUCTOR(switch2) + , m_R1(*this, "R1") + , m_R2(*this, "R2") + { + register_param("POS", m_POS, 0); + + connect_late(m_R1.m_N, m_R2.m_N); + + register_subalias("1", m_R1.m_P); + register_subalias("2", m_R2.m_P); + + register_subalias("Q", m_R1.m_N); + } -NETLIB_DEVICE_WITH_PARAMS(switch2, - NETLIB_SUB(R_base) m_R[2]; + NETLIB_RESETI(); + NETLIB_UPDATEI(); + NETLIB_UPDATE_PARAMI(); + NETLIB_SUB(R_base) m_R1; + NETLIB_SUB(R_base) m_R2; param_int_t m_POS; -); +}; NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/analog/nld_twoterm.cpp b/src/lib/netlist/analog/nld_twoterm.cpp index ae351560354..a19aecf7d61 100644 --- a/src/lib/netlist/analog/nld_twoterm.cpp +++ b/src/lib/netlist/analog/nld_twoterm.cpp @@ -48,20 +48,6 @@ ATTR_COLD void generic_diode::save(pstring name, object_t &parent) // nld_twoterm // ---------------------------------------------------------------------------------------- -ATTR_COLD NETLIB_NAME(twoterm)::NETLIB_NAME(twoterm)(const family_t afamily, netlist_t &anetlist, const pstring &name) - : device_t(afamily, anetlist, name) -{ - m_P.m_otherterm = &m_N; - m_N.m_otherterm = &m_P; -} - -ATTR_COLD NETLIB_NAME(twoterm)::NETLIB_NAME(twoterm)(netlist_t &anetlist, const pstring &name) - : device_t(TWOTERM, anetlist, name) -{ - m_P.m_otherterm = &m_N; - m_N.m_otherterm = &m_P; -} - NETLIB_START(twoterm) { } @@ -82,83 +68,19 @@ NETLIB_UPDATE(twoterm) } // ---------------------------------------------------------------------------------------- -// nld_R -// ---------------------------------------------------------------------------------------- - -NETLIB_START(R_base) -{ - NETLIB_NAME(twoterm)::start(); - enregister("1", m_P); - enregister("2", m_N); -} - -NETLIB_RESET(R_base) -{ - NETLIB_NAME(twoterm)::reset(); - set_R(1.0 / netlist().gmin()); -} - -NETLIB_UPDATE(R_base) -{ - NETLIB_NAME(twoterm)::update(); -} - -NETLIB_START(R) -{ - NETLIB_NAME(R_base)::start(); - register_param("R", m_R, 1.0 / netlist().gmin()); -} - -NETLIB_RESET(R) -{ - NETLIB_NAME(R_base)::reset(); -} - -NETLIB_UPDATE(R) -{ - NETLIB_NAME(twoterm)::update(); -} - -NETLIB_UPDATE_PARAM(R) -{ - update_dev(); - if (m_R.Value() > 1e-9) - set_R(m_R.Value()); - else - set_R(1e-9); -} - -// ---------------------------------------------------------------------------------------- // nld_POT // ---------------------------------------------------------------------------------------- -NETLIB_START(POT) -{ - register_sub("R1", m_R1); - register_sub("R2", m_R2); - - register_subalias("1", m_R1->m_P); - register_subalias("2", m_R1->m_N); - register_subalias("3", m_R2->m_N); - - connect_late(m_R2->m_P, m_R1->m_N); - - register_param("R", m_R, 1.0 / netlist().gmin()); - register_param("DIAL", m_Dial, 0.5); - register_param("DIALLOG", m_DialIsLog, 0); - -} - NETLIB_RESET(POT) { - m_R1->do_reset(); - m_R2->do_reset(); + m_R1.do_reset(); + m_R2.do_reset(); } NETLIB_UPDATE(POT) { - m_R1->update_dev(); - m_R2->update_dev(); + m_R1.update_dev(); + m_R2.update_dev(); } NETLIB_UPDATE_PARAM(POT) @@ -167,11 +89,11 @@ NETLIB_UPDATE_PARAM(POT) if (m_DialIsLog.Value()) v = (nl_math::exp(v) - 1.0) / (nl_math::exp(1.0) - 1.0); - m_R1->update_dev(); - m_R2->update_dev(); + m_R1.update_dev(); + m_R2.update_dev(); - m_R1->set_R(std::max(m_R.Value() * v, netlist().gmin())); - m_R2->set_R(std::max(m_R.Value() * (NL_FCONST(1.0) - v), netlist().gmin())); + m_R1.set_R(std::max(m_R.Value() * v, netlist().gmin())); + m_R2.set_R(std::max(m_R.Value() * (NL_FCONST(1.0) - v), netlist().gmin())); } @@ -179,28 +101,14 @@ NETLIB_UPDATE_PARAM(POT) // nld_POT2 // ---------------------------------------------------------------------------------------- -NETLIB_START(POT2) -{ - register_sub("R1", m_R1); - - register_subalias("1", m_R1->m_P); - register_subalias("2", m_R1->m_N); - - register_param("R", m_R, 1.0 / netlist().gmin()); - register_param("DIAL", m_Dial, 0.5); - register_param("REVERSE", m_Reverse, 0); - register_param("DIALLOG", m_DialIsLog, 0); - -} - NETLIB_RESET(POT2) { - m_R1->do_reset(); + m_R1.do_reset(); } NETLIB_UPDATE(POT2) { - m_R1->update_dev(); + m_R1.update_dev(); } NETLIB_UPDATE_PARAM(POT2) @@ -212,9 +120,9 @@ NETLIB_UPDATE_PARAM(POT2) if (m_Reverse.Value()) v = 1.0 - v; - m_R1->update_dev(); + m_R1.update_dev(); - m_R1->set_R(std::max(m_R.Value() * v, netlist().gmin())); + m_R1.set_R(std::max(m_R.Value() * v, netlist().gmin())); } // ---------------------------------------------------------------------------------------- @@ -250,14 +158,6 @@ NETLIB_UPDATE(C) NETLIB_NAME(twoterm)::update(); } -ATTR_HOT void NETLIB_NAME(C)::step_time(const nl_double st) -{ - /* Gpar should support convergence */ - const nl_double G = m_C.Value() / st + m_GParallel; - const nl_double I = -G * deltaV(); - set(G, 0.0, I); -} - // ---------------------------------------------------------------------------------------- // nld_D // ---------------------------------------------------------------------------------------- diff --git a/src/lib/netlist/analog/nld_twoterm.h b/src/lib/netlist/analog/nld_twoterm.h index bd61617af61..7b7474dca6e 100644 --- a/src/lib/netlist/analog/nld_twoterm.h +++ b/src/lib/netlist/analog/nld_twoterm.h @@ -100,16 +100,19 @@ NETLIB_NAMESPACE_DEVICES_START() // nld_twoterm // ----------------------------------------------------------------------------- -class NETLIB_NAME(twoterm) : public device_t +NETLIB_OBJECT(twoterm) { public: - ATTR_COLD NETLIB_NAME(twoterm)(const family_t afamily, netlist_t &anetlist, const pstring &name); - ATTR_COLD NETLIB_NAME(twoterm)(netlist_t &anetlist, const pstring &name); + NETLIB_CONSTRUCTOR(twoterm) + { + m_P.m_otherterm = &m_N; + m_N.m_otherterm = &m_P; + } terminal_t m_P; terminal_t m_N; - virtual NETLIB_UPDATE_TERMINALSI() + NETLIB_UPDATE_TERMINALSI() { } @@ -133,72 +136,152 @@ public: } protected: - virtual void start() override; - virtual void reset() override; + ATTR_HOT virtual void start() override; + ATTR_HOT virtual void reset() override; ATTR_HOT void update() override; private: }; + // ----------------------------------------------------------------------------- // nld_R // ----------------------------------------------------------------------------- -class NETLIB_NAME(R_base) : public NETLIB_NAME(twoterm) +NETLIB_OBJECT_DERIVED(R_base, twoterm) { -public: - ATTR_COLD NETLIB_NAME(R_base)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(twoterm)(RESISTOR, anetlist, name) { } + NETLIB_CONSTRUCTOR_DERIVED(R_base, twoterm) + { + enregister("1", m_P); + enregister("2", m_N); + } +public: inline void set_R(const nl_double R) { set(NL_FCONST(1.0) / R, 0.0, 0.0); } protected: - virtual void start() override; - virtual void reset() override; - ATTR_HOT void update() override; + NETLIB_RESETI() + { + NETLIB_NAME(twoterm)::reset(); + set_R(1.0 / netlist().gmin()); + } + + NETLIB_UPDATEI() + { + NETLIB_NAME(twoterm)::update(); + } + + }; -NETLIB_DEVICE_WITH_PARAMS_DERIVED(R, R_base, +NETLIB_OBJECT_DERIVED(R, R_base) +{ + NETLIB_CONSTRUCTOR_DERIVED(R, R_base) + { + register_param("R", m_R, 1.0 / netlist().gmin()); + } + param_double_t m_R; -); + +protected: + + NETLIB_RESETI() { NETLIB_NAME(R_base)::reset(); } + NETLIB_UPDATEI() { NETLIB_NAME(twoterm)::update(); } + NETLIB_UPDATE_PARAMI() + { + update_dev(); + if (m_R.Value() > 1e-9) + set_R(m_R.Value()); + else + set_R(1e-9); + } + +}; // ----------------------------------------------------------------------------- // nld_POT // ----------------------------------------------------------------------------- -NETLIB_DEVICE_WITH_PARAMS(POT, +NETLIB_OBJECT(POT) +{ + NETLIB_CONSTRUCTOR(POT) + , m_R1(*this, "R1") + , m_R2(*this, "R2") + { + register_subalias("1", m_R1.m_P); + register_subalias("2", m_R1.m_N); + register_subalias("3", m_R2.m_N); + + connect_late(m_R2.m_P, m_R1.m_N); + + register_param("R", m_R, 1.0 / netlist().gmin()); + register_param("DIAL", m_Dial, 0.5); + register_param("DIALLOG", m_DialIsLog, 0); + } + + NETLIB_UPDATEI(); + NETLIB_RESETI(); + NETLIB_UPDATE_PARAMI(); + +private: NETLIB_SUB(R_base) m_R1; NETLIB_SUB(R_base) m_R2; param_double_t m_R; param_double_t m_Dial; param_logic_t m_DialIsLog; -); +}; -NETLIB_DEVICE_WITH_PARAMS(POT2, +NETLIB_OBJECT(POT2) +{ + NETLIB_CONSTRUCTOR(POT2) + , m_R1(*this, "R1") + { + register_subalias("1", m_R1.m_P); + register_subalias("2", m_R1.m_N); + + register_param("R", m_R, 1.0 / netlist().gmin()); + register_param("DIAL", m_Dial, 0.5); + register_param("REVERSE", m_Reverse, 0); + register_param("DIALLOG", m_DialIsLog, 0); + } + + NETLIB_UPDATEI(); + NETLIB_RESETI(); + NETLIB_UPDATE_PARAMI(); + +private: NETLIB_SUB(R_base) m_R1; param_double_t m_R; param_double_t m_Dial; param_logic_t m_DialIsLog; param_logic_t m_Reverse; -); +}; // ----------------------------------------------------------------------------- // nld_C // ----------------------------------------------------------------------------- -class NETLIB_NAME(C) : public NETLIB_NAME(twoterm) +NETLIB_OBJECT_DERIVED(C, twoterm) { public: - ATTR_COLD NETLIB_NAME(C)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(twoterm)(CAPACITOR, anetlist, name), m_GParallel(0.0) { } + NETLIB_CONSTRUCTOR_DERIVED(C, twoterm) + , m_GParallel(0.0) + { } + + NETLIB_TIMESTEP() + { + /* Gpar should support convergence */ + const nl_double G = m_C.Value() / step + m_GParallel; + const nl_double I = -G * deltaV(); + set(G, 0.0, I); + } - ATTR_HOT void step_time(const nl_double st) override; param_double_t m_C; @@ -290,11 +373,13 @@ private: // nld_D // ----------------------------------------------------------------------------- -class NETLIB_NAME(D) : public NETLIB_NAME(twoterm) +NETLIB_OBJECT_DERIVED(D, twoterm) { public: - ATTR_COLD NETLIB_NAME(D)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(twoterm)(DIODE, anetlist, name) { } + NETLIB_CONSTRUCTOR_DERIVED(D, twoterm) + { } + + NETLIB_DYNAMIC() NETLIB_UPDATE_TERMINALSI(); @@ -308,17 +393,17 @@ protected: generic_diode m_D; }; + // ----------------------------------------------------------------------------- // nld_VS - Voltage source // // netlist voltage source must have inner resistance // ----------------------------------------------------------------------------- -class NETLIB_NAME(VS) : public NETLIB_NAME(twoterm) +NETLIB_OBJECT_DERIVED(VS, twoterm) { public: - ATTR_COLD NETLIB_NAME(VS)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(twoterm)(VS, anetlist, name) { } + NETLIB_CONSTRUCTOR_DERIVED(VS, twoterm) { } protected: virtual void start() override; @@ -333,11 +418,10 @@ protected: // nld_CS - Current source // ----------------------------------------------------------------------------- -class NETLIB_NAME(CS) : public NETLIB_NAME(twoterm) +NETLIB_OBJECT_DERIVED(CS, twoterm) { public: - ATTR_COLD NETLIB_NAME(CS)(netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(twoterm)(CS, anetlist, name) { } + NETLIB_CONSTRUCTOR_DERIVED(CS, twoterm) { } protected: virtual void start() override; diff --git a/src/lib/netlist/devices/nld_4020.h b/src/lib/netlist/devices/nld_4020.h index 00ce7158685..633fc3edfcc 100644 --- a/src/lib/netlist/devices/nld_4020.h +++ b/src/lib/netlist/devices/nld_4020.h @@ -55,8 +55,8 @@ NETLIB_SUBDEVICE(CD4020_sub, ); NETLIB_DEVICE(CD4020, - NETLIB_SUB(CD4020_sub) sub; - NETLIB_SUB(vdd_vss) m_supply; + NETLIB_SUBXX(CD4020_sub) sub; + NETLIB_SUBXX(vdd_vss) m_supply; logic_input_t m_RESET; ); diff --git a/src/lib/netlist/devices/nld_4066.h b/src/lib/netlist/devices/nld_4066.h index e392a80f11a..967bea3a964 100644 --- a/src/lib/netlist/devices/nld_4066.h +++ b/src/lib/netlist/devices/nld_4066.h @@ -36,9 +36,9 @@ NETLIB_DEVICE(CD4066_GATE, public: analog_input_t m_control; - NETLIB_SUB(R) m_R; + NETLIB_SUBXX(R) m_R; - NETLIB_SUB(vdd_vss) m_supply; + NETLIB_SUBXX(vdd_vss) m_supply; param_double_t m_base_r; ); diff --git a/src/lib/netlist/devices/nld_74107.h b/src/lib/netlist/devices/nld_74107.h index bddb3e88f0a..972f66b26b8 100644 --- a/src/lib/netlist/devices/nld_74107.h +++ b/src/lib/netlist/devices/nld_74107.h @@ -92,7 +92,7 @@ NETLIB_SUBDEVICE(74107Asub, NETLIB_DEVICE(74107A, public: - NETLIB_SUB(74107Asub) sub; + NETLIB_SUBXX(74107Asub) sub; logic_input_t m_J; logic_input_t m_K; @@ -100,18 +100,17 @@ public: ); -class NETLIB_NAME(74107) : public NETLIB_NAME(74107A) +NETLIB_OBJECT_DERIVED(74107, 74107A) { public: - NETLIB_NAME(74107) (netlist_t &anetlist, const pstring &name) - : NETLIB_NAME(74107A) (anetlist, name) {} + NETLIB_CONSTRUCTOR_DERIVED(74107, 74107A) { } }; NETLIB_DEVICE(74107_dip, - NETLIB_SUB(74107) m_1; - NETLIB_SUB(74107) m_2; + NETLIB_SUBXX(74107) m_1; + NETLIB_SUBXX(74107) m_2; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_74123.cpp b/src/lib/netlist/devices/nld_74123.cpp index 566d8c0ad29..5a61fb71eac 100644 --- a/src/lib/netlist/devices/nld_74123.cpp +++ b/src/lib/netlist/devices/nld_74123.cpp @@ -31,10 +31,10 @@ NETLIB_START(74123) enregister("_CV", m_CV); // internal - register_subalias("GND", m_RN->m_R->m_N); - register_subalias("VCC", m_RP->m_R->m_P); - register_subalias("C", m_RN->m_R->m_N); - register_subalias("RC", m_RN->m_R->m_P); + register_subalias("GND", m_RN->m_R.m_N); + register_subalias("VCC", m_RP->m_R.m_P); + register_subalias("C", m_RN->m_R.m_N); + register_subalias("RC", m_RN->m_R.m_P); if (m_dev_type == 4538) register_param("K", m_K, 0.4); @@ -46,8 +46,8 @@ NETLIB_START(74123) connect_late(m_RP_Q, m_RP->m_I); connect_late(m_RN_Q, m_RN->m_I); - connect_late(m_RN->m_R->m_P, m_RP->m_R->m_N); - connect_late(m_CV, m_RN->m_R->m_P); + connect_late(m_RN->m_R.m_P, m_RP->m_R.m_N); + connect_late(m_CV, m_RN->m_R.m_P); save(NLNAME(m_last_trig)); save(NLNAME(m_state)); @@ -107,7 +107,7 @@ NETLIB_UPDATE(74123) if (m_state == 1) { - const nl_double vLow = m_KP * TERMANALOG(m_RP->m_R->m_P); + const nl_double vLow = m_KP * TERMANALOG(m_RP->m_R.m_P); if (INPANALOG(m_CV) < vLow) { OUTLOGIC(m_RN_Q, 0, NLTIME_FROM_NS(10)); // R_OFF @@ -116,7 +116,7 @@ NETLIB_UPDATE(74123) } if (m_state == 2) { - const nl_double vHigh = TERMANALOG(m_RP->m_R->m_P) * (1.0 - m_KP); + const nl_double vHigh = TERMANALOG(m_RP->m_R.m_P) * (1.0 - m_KP); if (INPANALOG(m_CV) > vHigh) { OUTLOGIC(m_RP_Q, 0, NLTIME_FROM_NS(10)); // R_OFF @@ -152,20 +152,20 @@ NETLIB_START(74123_dip) register_subalias("3", m_1->m_CLRQ); register_subalias("4", m_1->m_QQ); register_subalias("5", m_2->m_Q); - register_subalias("6", m_2->m_RN->m_R->m_N); - register_subalias("7", m_2->m_RN->m_R->m_P); - register_subalias("8", m_1->m_RN->m_R->m_N); - connect_late(m_1->m_RN->m_R->m_N, m_2->m_RN->m_R->m_N); + register_subalias("6", m_2->m_RN->m_R.m_N); + register_subalias("7", m_2->m_RN->m_R.m_P); + register_subalias("8", m_1->m_RN->m_R.m_N); + connect_late(m_1->m_RN->m_R.m_N, m_2->m_RN->m_R.m_N); register_subalias("9", m_2->m_A); register_subalias("10", m_2->m_B); register_subalias("11", m_2->m_CLRQ); register_subalias("12", m_2->m_QQ); register_subalias("13", m_1->m_Q); - register_subalias("14", m_1->m_RN->m_R->m_N); - register_subalias("15", m_1->m_RN->m_R->m_P); - register_subalias("16", m_1->m_RP->m_R->m_P); - connect_late(m_1->m_RP->m_R->m_P, m_2->m_RP->m_R->m_P); + register_subalias("14", m_1->m_RN->m_R.m_N); + register_subalias("15", m_1->m_RN->m_R.m_P); + register_subalias("16", m_1->m_RP->m_R.m_P); + connect_late(m_1->m_RP->m_R.m_P, m_2->m_RP->m_R.m_P); } NETLIB_UPDATE(74123_dip) @@ -190,25 +190,25 @@ NETLIB_START(9602_dip) m_1->m_dev_type = 9602; m_2->m_dev_type = 9602; - register_subalias("1", m_1->m_RN->m_R->m_N); // C1 - register_subalias("2", m_1->m_RN->m_R->m_P); // RC1 + register_subalias("1", m_1->m_RN->m_R.m_N); // C1 + register_subalias("2", m_1->m_RN->m_R.m_P); // RC1 register_subalias("3", m_1->m_CLRQ); register_subalias("4", m_1->m_B); register_subalias("5", m_1->m_A); register_subalias("6", m_1->m_Q); register_subalias("7", m_1->m_QQ); - register_subalias("8", m_1->m_RN->m_R->m_N); - connect_late(m_1->m_RN->m_R->m_N, m_2->m_RN->m_R->m_N); + register_subalias("8", m_1->m_RN->m_R.m_N); + connect_late(m_1->m_RN->m_R.m_N, m_2->m_RN->m_R.m_N); register_subalias("9", m_2->m_QQ); register_subalias("10", m_2->m_Q); register_subalias("11", m_2->m_A); register_subalias("12", m_2->m_B); register_subalias("13", m_2->m_CLRQ); - register_subalias("14", m_2->m_RN->m_R->m_P); // RC2 - register_subalias("15", m_2->m_RN->m_R->m_N); // C2 - register_subalias("16", m_1->m_RP->m_R->m_P); - connect_late(m_1->m_RP->m_R->m_P, m_2->m_RP->m_R->m_P); + register_subalias("14", m_2->m_RN->m_R.m_P); // RC2 + register_subalias("15", m_2->m_RN->m_R.m_N); // C2 + register_subalias("16", m_1->m_RP->m_R.m_P); + connect_late(m_1->m_RP->m_R.m_P, m_2->m_RP->m_R.m_P); } NETLIB_UPDATE(9602_dip) @@ -234,25 +234,25 @@ NETLIB_START(4538_dip) m_1->m_dev_type = 4538; m_2->m_dev_type = 4538; - register_subalias("1", m_1->m_RN->m_R->m_N); // C1 - register_subalias("2", m_1->m_RN->m_R->m_P); // RC1 + register_subalias("1", m_1->m_RN->m_R.m_N); // C1 + register_subalias("2", m_1->m_RN->m_R.m_P); // RC1 register_subalias("3", m_1->m_CLRQ); register_subalias("4", m_1->m_A); register_subalias("5", m_1->m_B); register_subalias("6", m_1->m_Q); register_subalias("7", m_1->m_QQ); - register_subalias("8", m_1->m_RN->m_R->m_N); - connect_late(m_1->m_RN->m_R->m_N, m_2->m_RN->m_R->m_N); + register_subalias("8", m_1->m_RN->m_R.m_N); + connect_late(m_1->m_RN->m_R.m_N, m_2->m_RN->m_R.m_N); register_subalias("9", m_2->m_QQ); register_subalias("10", m_2->m_Q); register_subalias("11", m_2->m_B); register_subalias("12", m_2->m_A); register_subalias("13", m_2->m_CLRQ); - register_subalias("14", m_2->m_RN->m_R->m_P); // RC2 - register_subalias("15", m_2->m_RN->m_R->m_N); // C2 - register_subalias("16", m_1->m_RP->m_R->m_P); - connect_late(m_1->m_RP->m_R->m_P, m_2->m_RP->m_R->m_P); + register_subalias("14", m_2->m_RN->m_R.m_P); // RC2 + register_subalias("15", m_2->m_RN->m_R.m_N); // C2 + register_subalias("16", m_1->m_RP->m_R.m_P); + connect_late(m_1->m_RP->m_R.m_P, m_2->m_RP->m_R.m_P); } NETLIB_UPDATE(4538_dip) diff --git a/src/lib/netlist/devices/nld_74123.h b/src/lib/netlist/devices/nld_74123.h index fcf20af4793..ad7f30cc6b0 100644 --- a/src/lib/netlist/devices/nld_74123.h +++ b/src/lib/netlist/devices/nld_74123.h @@ -60,8 +60,8 @@ NETLIB_NAMESPACE_DEVICES_START() NETLIB_DEVICE(74123, public: - NETLIB_SUB(res_sw) m_RP; - NETLIB_SUB(res_sw) m_RN; + NETLIB_SUBXX(res_sw) m_RP; + NETLIB_SUBXX(res_sw) m_RN; logic_output_t m_RP_Q; logic_output_t m_RN_Q; @@ -89,8 +89,8 @@ public: NETLIB_DEVICE(74123_dip, - NETLIB_SUB(74123) m_1; - NETLIB_SUB(74123) m_2; + NETLIB_SUBXX(74123) m_1; + NETLIB_SUBXX(74123) m_2; ); @@ -103,8 +103,8 @@ NETLIB_DEVICE(74123_dip, NETLIB_DEVICE(9602_dip, - NETLIB_SUB(74123) m_1; - NETLIB_SUB(74123) m_2; + NETLIB_SUBXX(74123) m_1; + NETLIB_SUBXX(74123) m_2; ); @@ -116,8 +116,8 @@ NETLIB_DEVICE(9602_dip, NET_REGISTER_DEV(CD4538_DIP, _name) NETLIB_DEVICE(4538_dip, - NETLIB_SUB(74123) m_1; - NETLIB_SUB(74123) m_2; + NETLIB_SUBXX(74123) m_1; + NETLIB_SUBXX(74123) m_2; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_74153.h b/src/lib/netlist/devices/nld_74153.h index 08d0c7a7bf9..e26a7118890 100644 --- a/src/lib/netlist/devices/nld_74153.h +++ b/src/lib/netlist/devices/nld_74153.h @@ -73,15 +73,15 @@ NETLIB_SUBDEVICE(74153sub, NETLIB_DEVICE(74153, public: - NETLIB_SUB(74153sub) m_sub; + NETLIB_SUBXX(74153sub) m_sub; logic_input_t m_A; logic_input_t m_B; ); NETLIB_DEVICE(74153_dip, - NETLIB_SUB(74153sub) m_1; - NETLIB_SUB(74153sub) m_2; + NETLIB_SUBXX(74153sub) m_1; + NETLIB_SUBXX(74153sub) m_2; logic_input_t m_A; logic_input_t m_B; ); diff --git a/src/lib/netlist/devices/nld_74175.h b/src/lib/netlist/devices/nld_74175.h index 6faa3e71971..2d642122164 100644 --- a/src/lib/netlist/devices/nld_74175.h +++ b/src/lib/netlist/devices/nld_74175.h @@ -57,7 +57,7 @@ NETLIB_SUBDEVICE(74175_sub, NETLIB_DEVICE(74175, - NETLIB_SUB(74175_sub) m_sub; + NETLIB_SUBXX(74175_sub) m_sub; logic_input_t m_D[4]; logic_input_t m_CLRQ; ); diff --git a/src/lib/netlist/devices/nld_74192.h b/src/lib/netlist/devices/nld_74192.h index 26126d96e06..2d36a0b4b93 100644 --- a/src/lib/netlist/devices/nld_74192.h +++ b/src/lib/netlist/devices/nld_74192.h @@ -43,7 +43,7 @@ NETLIB_NAMESPACE_DEVICES_START() NETLIB_DEVICE(74192, ATTR_HOT void update_outputs(); - NETLIB_SUB(9316_subABCD) m_ABCD; + NETLIB_SUBXX(9316_subABCD) m_ABCD; logic_input_t m_CLEAR; logic_input_t m_LOADQ; logic_input_t m_CU; diff --git a/src/lib/netlist/devices/nld_74279.h b/src/lib/netlist/devices/nld_74279.h index c134eaaa6a3..b156ef66033 100644 --- a/src/lib/netlist/devices/nld_74279.h +++ b/src/lib/netlist/devices/nld_74279.h @@ -55,10 +55,10 @@ NETLIB_TRUTHTABLE(74279B, 4, 1, 0); NETLIB_DEVICE(74279_dip, - NETLIB_SUB(74279B) m_1; - NETLIB_SUB(74279A) m_2; - NETLIB_SUB(74279B) m_3; - NETLIB_SUB(74279A) m_4; + NETLIB_SUBXX(74279B) m_1; + NETLIB_SUBXX(74279A) m_2; + NETLIB_SUBXX(74279B) m_3; + NETLIB_SUBXX(74279A) m_4; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_7448.h b/src/lib/netlist/devices/nld_7448.h index b5de0091fb5..f0f4097fe73 100644 --- a/src/lib/netlist/devices/nld_7448.h +++ b/src/lib/netlist/devices/nld_7448.h @@ -72,7 +72,7 @@ NETLIB_SUBDEVICE(7448_sub, NETLIB_DEVICE(7448, public: - NETLIB_SUB(7448_sub) sub; + NETLIB_SUBXX(7448_sub) sub; logic_input_t m_LTQ; logic_input_t m_BIQ; diff --git a/src/lib/netlist/devices/nld_7450.h b/src/lib/netlist/devices/nld_7450.h index 9a2a19c57ee..635f1564cf2 100644 --- a/src/lib/netlist/devices/nld_7450.h +++ b/src/lib/netlist/devices/nld_7450.h @@ -49,8 +49,8 @@ public: NETLIB_DEVICE(7450_dip, - NETLIB_SUB(7450) m_1; - NETLIB_SUB(7450) m_2; + NETLIB_SUBXX(7450) m_1; + NETLIB_SUBXX(7450) m_2; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_7474.cpp b/src/lib/netlist/devices/nld_7474.cpp index a86c07a1ab6..8ada0a0a029 100644 --- a/src/lib/netlist/devices/nld_7474.cpp +++ b/src/lib/netlist/devices/nld_7474.cpp @@ -31,56 +31,32 @@ NETLIB_UPDATE(7474) if (INPLOGIC(m_PREQ) && INPLOGIC(m_CLRQ)) { m_D.activate(); - sub->m_nextD = INPLOGIC(m_D); - sub->m_CLK.activate_lh(); + sub.m_nextD = INPLOGIC(m_D); + sub.m_CLK.activate_lh(); } else if (!INPLOGIC(m_PREQ)) { - sub->newstate(1, 0); - sub->m_CLK.inactivate(); + sub.newstate(1, 0); + sub.m_CLK.inactivate(); m_D.inactivate(); } else if (!INPLOGIC(m_CLRQ)) { - sub->newstate(0, 1); - sub->m_CLK.inactivate(); + sub.newstate(0, 1); + sub.m_CLK.inactivate(); m_D.inactivate(); } else { - sub->newstate(1, 1); - sub->m_CLK.inactivate(); + sub.newstate(1, 1); + sub.m_CLK.inactivate(); m_D.inactivate(); } } -NETLIB_START(7474) -{ - register_sub("sub", sub); - - register_subalias("CLK", sub->m_CLK); - enregister("D", m_D); - enregister("CLRQ", m_CLRQ); - enregister("PREQ", m_PREQ); - - register_subalias("Q", sub->m_Q); - register_subalias("QQ", sub->m_QQ); - -} - NETLIB_RESET(7474) { - sub->do_reset(); -} - -NETLIB_START(7474sub) -{ - enregister("CLK", m_CLK); - - enregister("Q", m_Q); - enregister("QQ", m_QQ); - - save(NLNAME(m_nextD)); + sub.do_reset(); } NETLIB_RESET(7474sub) @@ -90,38 +66,16 @@ NETLIB_RESET(7474sub) m_nextD = 0; } -NETLIB_START(7474_dip) -{ - register_sub("1", m_1); - register_sub("2", m_2); - - register_subalias("1", m_1->m_CLRQ); - register_subalias("2", m_1->m_D); - register_subalias("3", m_1->sub->m_CLK); - register_subalias("4", m_1->m_PREQ); - register_subalias("5", m_1->sub->m_Q); - register_subalias("6", m_1->sub->m_QQ); - // register_subalias("7", ); ==> GND - - register_subalias("8", m_2->sub->m_QQ); - register_subalias("9", m_2->sub->m_Q); - register_subalias("10", m_2->m_PREQ); - register_subalias("11", m_2->sub->m_CLK); - register_subalias("12", m_2->m_D); - register_subalias("13", m_2->m_CLRQ); - // register_subalias("14", ); ==> VCC -} - NETLIB_RESET(7474_dip) { - m_1->do_reset(); - m_2->do_reset(); + m_1.do_reset(); + m_2.do_reset(); } NETLIB_UPDATE(7474_dip) { - m_1->update_dev(); - m_2->update_dev(); + m_1.update_dev(); + m_2.update_dev(); } NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_7474.h b/src/lib/netlist/devices/nld_7474.h index bdde44708a6..9286f638ebf 100644 --- a/src/lib/netlist/devices/nld_7474.h +++ b/src/lib/netlist/devices/nld_7474.h @@ -32,7 +32,7 @@ * * Q0 The output logic level of Q before the indicated input conditions were established * - * R: 0 --> 1 + * R: 0 -. 1 * * Naming conventions follow National Semiconductor datasheet * @@ -56,30 +56,88 @@ NETLIB_NAMESPACE_DEVICES_START() -NETLIB_SUBDEVICE(7474sub, - logic_input_t m_CLK; +NETLIB_OBJECT(7474sub) +{ + NETLIB_CONSTRUCTOR(7474sub) + , m_nextD(0) + { + enregister("CLK", m_CLK); - INT8 m_nextD; + enregister("Q", m_Q); + enregister("QQ", m_QQ); + + save(NLNAME(m_nextD)); + } + + NETLIB_RESETI(); + NETLIB_UPDATEI(); + + logic_input_t m_CLK; logic_output_t m_Q; logic_output_t m_QQ; + INT8 m_nextD; ATTR_HOT inline void newstate(const UINT8 stateQ, const UINT8 stateQQ); -); -NETLIB_DEVICE(7474, +private: + +}; + +NETLIB_OBJECT(7474) +{ + NETLIB_CONSTRUCTOR(7474) + , sub(*this, "sub") + { + register_subalias("CLK", sub.m_CLK); + enregister("D", m_D); + enregister("CLRQ", m_CLRQ); + enregister("PREQ", m_PREQ); + + register_subalias("Q", sub.m_Q); + register_subalias("QQ", sub.m_QQ); + } + + NETLIB_RESETI(); + NETLIB_UPDATEI(); + public: NETLIB_SUB(7474sub) sub; logic_input_t m_D; logic_input_t m_CLRQ; logic_input_t m_PREQ; -); +}; + +NETLIB_OBJECT(7474_dip) +{ + NETLIB_CONSTRUCTOR(7474_dip) + , m_1(*this, "1") + , m_2(*this, "2") + { + + register_subalias("1", m_1.m_CLRQ); + register_subalias("2", m_1.m_D); + register_subalias("3", m_1.sub.m_CLK); + register_subalias("4", m_1.m_PREQ); + register_subalias("5", m_1.sub.m_Q); + register_subalias("6", m_1.sub.m_QQ); + // register_subalias("7", ); ==> GND -NETLIB_DEVICE(7474_dip, + register_subalias("8", m_2.sub.m_QQ); + register_subalias("9", m_2.sub.m_Q); + register_subalias("10", m_2.m_PREQ); + register_subalias("11", m_2.sub.m_CLK); + register_subalias("12", m_2.m_D); + register_subalias("13", m_2.m_CLRQ); + // register_subalias("14", ); ==> VCC + } + NETLIB_UPDATEI(); + NETLIB_RESETI(); +private: NETLIB_SUB(7474) m_1; NETLIB_SUB(7474) m_2; -); +}; NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_7493.cpp b/src/lib/netlist/devices/nld_7493.cpp index 2df92aa7ed0..be47e2e2a05 100644 --- a/src/lib/netlist/devices/nld_7493.cpp +++ b/src/lib/netlist/devices/nld_7493.cpp @@ -10,43 +10,14 @@ NETLIB_NAMESPACE_DEVICES_START() -NETLIB_START(7493) -{ - register_sub("A", A); - register_sub("B", B); - register_sub("C", C); - register_sub("D", D); - - register_subalias("CLKA", A->m_I); - register_subalias("CLKB", B->m_I); - enregister("R1", m_R1); - enregister("R2", m_R2); - - register_subalias("QA", A->m_Q); - register_subalias("QB", B->m_Q); - register_subalias("QC", C->m_Q); - register_subalias("QD", D->m_Q); - - connect_late(C->m_I, B->m_Q); - connect_late(D->m_I, C->m_Q); -} - NETLIB_RESET(7493) { - A->do_reset(); - B->do_reset(); - C->do_reset(); - D->do_reset(); + A.do_reset(); + B.do_reset(); + C.do_reset(); + D.do_reset(); } -NETLIB_START(7493ff) -{ - enregister("CLK", m_I); - enregister("Q", m_Q); - - save(NLNAME(m_reset)); - save(NLNAME(m_state)); -} NETLIB_RESET(7493ff) { @@ -71,20 +42,20 @@ NETLIB_UPDATE(7493) if (r) { - A->m_I.inactivate(); - B->m_I.inactivate(); - OUTLOGIC(A->m_Q, 0, NLTIME_FROM_NS(40)); - OUTLOGIC(B->m_Q, 0, NLTIME_FROM_NS(40)); - OUTLOGIC(C->m_Q, 0, NLTIME_FROM_NS(40)); - OUTLOGIC(D->m_Q, 0, NLTIME_FROM_NS(40)); - A->m_reset = B->m_reset = C->m_reset = D->m_reset = 0; - A->m_state = B->m_state = C->m_state = D->m_state = 0; + A.m_I.inactivate(); + B.m_I.inactivate(); + OUTLOGIC(A.m_Q, 0, NLTIME_FROM_NS(40)); + OUTLOGIC(B.m_Q, 0, NLTIME_FROM_NS(40)); + OUTLOGIC(C.m_Q, 0, NLTIME_FROM_NS(40)); + OUTLOGIC(D.m_Q, 0, NLTIME_FROM_NS(40)); + A.m_reset = B.m_reset = C.m_reset = D.m_reset = 0; + A.m_state = B.m_state = C.m_state = D.m_state = 0; } else { - A->m_I.activate_hl(); - B->m_I.activate_hl(); - A->m_reset = B->m_reset = C->m_reset = D->m_reset = 1; + A.m_I.activate_hl(); + B.m_I.activate_hl(); + A.m_reset = B.m_reset = C.m_reset = D.m_reset = 1; } } @@ -92,7 +63,7 @@ NETLIB_START(7493_dip) { NETLIB_NAME(7493)::start(); - register_subalias("1", B->m_I); + register_subalias("1", B.m_I); register_subalias("2", m_R1); register_subalias("3", m_R2); @@ -101,13 +72,13 @@ NETLIB_START(7493_dip) // register_subalias("6", ); --> NC // register_subalias("7", ); --> NC - register_subalias("8", C->m_Q); - register_subalias("9", B->m_Q); - // register_subalias("10", ); --> GND - register_subalias("11", D->m_Q); - register_subalias("12", A->m_Q); - // register_subalias("13", ); --> NC - register_subalias("14", A->m_I); + register_subalias("8", C.m_Q); + register_subalias("9", B.m_Q); + // register_subalias("10", ); -. GND + register_subalias("11", D.m_Q); + register_subalias("12", A.m_Q); + // register_subalias("13", ); -. NC + register_subalias("14", A.m_I); } diff --git a/src/lib/netlist/devices/nld_7493.h b/src/lib/netlist/devices/nld_7493.h index e58fdc03c16..f72f1e9eb8d 100644 --- a/src/lib/netlist/devices/nld_7493.h +++ b/src/lib/netlist/devices/nld_7493.h @@ -71,15 +71,52 @@ NETLIB_NAMESPACE_DEVICES_START() -NETLIB_SUBDEVICE(7493ff, +NETLIB_OBJECT(7493ff) +{ + NETLIB_CONSTRUCTOR(7493ff) + { + enregister("CLK", m_I); + enregister("Q", m_Q); + + save(NLNAME(m_reset)); + save(NLNAME(m_state)); + } + + NETLIB_RESETI(); + NETLIB_UPDATEI(); + logic_input_t m_I; logic_output_t m_Q; UINT8 m_reset; UINT8 m_state; -); +}; + +NETLIB_OBJECT(7493) +{ + NETLIB_CONSTRUCTOR(7493) + , A(*this, "A") + , B(*this, "B") + , C(*this, "C") + , D(*this, "D") + { + register_subalias("CLKA", A.m_I); + register_subalias("CLKB", B.m_I); + enregister("R1", m_R1); + enregister("R2", m_R2); + + register_subalias("QA", A.m_Q); + register_subalias("QB", B.m_Q); + register_subalias("QC", C.m_Q); + register_subalias("QD", D.m_Q); + + connect_late(C.m_I, B.m_Q); + connect_late(D.m_I, C.m_Q); + } + + NETLIB_RESETI(); + NETLIB_UPDATEI(); -NETLIB_DEVICE(7493, logic_input_t m_R1; logic_input_t m_R2; @@ -87,7 +124,7 @@ NETLIB_DEVICE(7493, NETLIB_SUB(7493ff) B; NETLIB_SUB(7493ff) C; NETLIB_SUB(7493ff) D; -); +}; NETLIB_DEVICE_DERIVED_PURE(7493_dip, 7493); diff --git a/src/lib/netlist/devices/nld_74ls629.h b/src/lib/netlist/devices/nld_74ls629.h index e8f94c9ca75..5365f244312 100644 --- a/src/lib/netlist/devices/nld_74ls629.h +++ b/src/lib/netlist/devices/nld_74ls629.h @@ -48,9 +48,9 @@ NETLIB_SUBDEVICE(SN74LS629clk, NETLIB_DEVICE_WITH_PARAMS(SN74LS629, public: - NETLIB_SUB(SN74LS629clk) m_clock; - NETLIB_SUB(R_base) m_R_FC; - NETLIB_SUB(R_base) m_R_RNG; + NETLIB_SUBXX(SN74LS629clk) m_clock; + NETLIB_SUBXX(R_base) m_R_FC; + NETLIB_SUBXX(R_base) m_R_RNG; logic_input_t m_ENQ; analog_input_t m_RNG; @@ -65,8 +65,8 @@ public: NETDEV_PARAMI(_name, 2.CAP, _cap2) NETLIB_DEVICE(SN74LS629_dip, - NETLIB_SUB(SN74LS629) m_1; - NETLIB_SUB(SN74LS629) m_2; + NETLIB_SUBXX(SN74LS629) m_1; + NETLIB_SUBXX(SN74LS629) m_2; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_9310.h b/src/lib/netlist/devices/nld_9310.h index af6834160d3..f6b210f0481 100644 --- a/src/lib/netlist/devices/nld_9310.h +++ b/src/lib/netlist/devices/nld_9310.h @@ -96,8 +96,8 @@ NETLIB_SUBDEVICE(9310_sub, ); NETLIB_DEVICE(9310, - NETLIB_SUB(9310_sub) sub; - NETLIB_SUB(9310_subABCD) subABCD; + NETLIB_SUBXX(9310_sub) sub; + NETLIB_SUBXX(9310_subABCD) subABCD; logic_input_t m_ENP; logic_input_t m_ENT; logic_input_t m_CLRQ; diff --git a/src/lib/netlist/devices/nld_9312.h b/src/lib/netlist/devices/nld_9312.h index 8ecb29862e9..c7ff8f4ec48 100644 --- a/src/lib/netlist/devices/nld_9312.h +++ b/src/lib/netlist/devices/nld_9312.h @@ -72,7 +72,7 @@ public: #endif NETLIB_DEVICE(9312_dip, - NETLIB_SUB(9312) m_sub; + NETLIB_SUBXX(9312) m_sub; ); NETLIB_NAMESPACE_DEVICES_END() diff --git a/src/lib/netlist/devices/nld_9316.h b/src/lib/netlist/devices/nld_9316.h index c006f0e98a8..556c5c79c88 100644 --- a/src/lib/netlist/devices/nld_9316.h +++ b/src/lib/netlist/devices/nld_9316.h @@ -101,8 +101,8 @@ NETLIB_SUBDEVICE(9316_sub, ); NETLIB_DEVICE(9316, - NETLIB_SUB(9316_sub) sub; - NETLIB_SUB(9316_subABCD) subABCD; + NETLIB_SUBXX(9316_sub) sub; + NETLIB_SUBXX(9316_subABCD) subABCD; logic_input_t m_ENP; logic_input_t m_ENT; logic_input_t m_CLRQ; diff --git a/src/lib/netlist/devices/nld_cmos.h b/src/lib/netlist/devices/nld_cmos.h index 85edd622870..b9b17ef9520 100644 --- a/src/lib/netlist/devices/nld_cmos.h +++ b/src/lib/netlist/devices/nld_cmos.h @@ -13,12 +13,10 @@ NETLIB_NAMESPACE_DEVICES_START() -class nld_vdd_vss : public device_t +class NETLIB_NAME(vdd_vss) : public device_t { public: - nld_vdd_vss (netlist_t &anetlist, const pstring &name) - : device_t(anetlist, name) - { } + NETLIB_CONSTRUCTOR(vdd_vss) { } analog_input_t m_vdd; analog_input_t m_vss; diff --git a/src/lib/netlist/devices/nld_ne555.cpp b/src/lib/netlist/devices/nld_ne555.cpp index 95de650f02c..aefe66056b6 100644 --- a/src/lib/netlist/devices/nld_ne555.cpp +++ b/src/lib/netlist/devices/nld_ne555.cpp @@ -17,7 +17,7 @@ NETLIB_NAMESPACE_DEVICES_START() inline nl_double NETLIB_NAME(NE555)::clamp(const nl_double v, const nl_double a, const nl_double b) { nl_double ret = v; - nl_double vcc = TERMANALOG(m_R1->m_P); + nl_double vcc = TERMANALOG(m_R1.m_P); if (ret > vcc - a) ret = vcc - a; @@ -26,41 +26,17 @@ inline nl_double NETLIB_NAME(NE555)::clamp(const nl_double v, const nl_double a, return ret; } -NETLIB_START(NE555) -{ - register_sub("R1", m_R1); - register_sub("R2", m_R2); - register_sub("R3", m_R3); - register_sub("RDIS", m_RDIS); - - register_subalias("GND", m_R3->m_N); // Pin 1 - enregister("TRIG", m_TRIG); // Pin 2 - enregister("OUT", m_OUT); // Pin 3 - enregister("RESET", m_RESET); // Pin 4 - register_subalias("CONT", m_R1->m_N); // Pin 5 - enregister("THRESH", m_THRES); // Pin 6 - register_subalias("DISCH", m_RDIS->m_P); // Pin 7 - register_subalias("VCC", m_R1->m_P); // Pin 8 - - connect_late(m_R1->m_N, m_R2->m_P); - connect_late(m_R2->m_N, m_R3->m_P); - connect_late(m_RDIS->m_N, m_R3->m_N); - - save(NLNAME(m_last_out)); - save(NLNAME(m_ff)); -} - NETLIB_RESET(NE555) { - m_R1->do_reset(); - m_R2->do_reset(); - m_R3->do_reset(); - m_RDIS->do_reset(); + m_R1.do_reset(); + m_R2.do_reset(); + m_R3.do_reset(); + m_RDIS.do_reset(); - m_R1->set_R(5000); - m_R2->set_R(5000); - m_R3->set_R(5000); - m_RDIS->set_R(R_OFF); + m_R1.set_R(5000); + m_R2.set_R(5000); + m_R3.set_R(5000); + m_RDIS.set_R(R_OFF); m_last_out = true; } @@ -69,9 +45,9 @@ NETLIB_UPDATE(NE555) { // FIXME: assumes GND is connected to 0V. - nl_double vt = clamp(TERMANALOG(m_R2->m_P), 0.7, 1.4); + nl_double vt = clamp(TERMANALOG(m_R2.m_P), 0.7, 1.4); bool bthresh = (INPANALOG(m_THRES) > vt); - bool btrig = (INPANALOG(m_TRIG) > clamp(TERMANALOG(m_R2->m_N), 0.7, 1.4)); + bool btrig = (INPANALOG(m_TRIG) > clamp(TERMANALOG(m_R2.m_N), 0.7, 1.4)); if (!btrig) { @@ -86,16 +62,16 @@ NETLIB_UPDATE(NE555) if (m_last_out && !out) { - m_RDIS->update_dev(); - OUTANALOG(m_OUT, TERMANALOG(m_R3->m_N)); - m_RDIS->set_R(R_ON); + m_RDIS.update_dev(); + OUTANALOG(m_OUT, TERMANALOG(m_R3.m_N)); + m_RDIS.set_R(R_ON); } else if (!m_last_out && out) { - m_RDIS->update_dev(); + m_RDIS.update_dev(); // FIXME: Should be delayed by 100ns - OUTANALOG(m_OUT, TERMANALOG(m_R1->m_P)); - m_RDIS->set_R(R_OFF); + OUTANALOG(m_OUT, TERMANALOG(m_R1.m_P)); + m_RDIS.set_R(R_OFF); } m_last_out = out; } @@ -105,14 +81,14 @@ NETLIB_START(NE555_dip) { NETLIB_NAME(NE555)::start(); - register_subalias("1", m_R3->m_N); // Pin 1 + register_subalias("1", m_R3.m_N); // Pin 1 register_subalias("2", m_TRIG); // Pin 2 register_subalias("3", m_OUT); // Pin 3 register_subalias("4", m_RESET); // Pin 4 - register_subalias("5", m_R1->m_N); // Pin 5 + register_subalias("5", m_R1.m_N); // Pin 5 register_subalias("6", m_THRES); // Pin 6 - register_subalias("7", m_RDIS->m_P); // Pin 7 - register_subalias("8", m_R1->m_P); // Pin 8 + register_subalias("7", m_RDIS.m_P); // Pin 7 + register_subalias("8", m_R1.m_P); // Pin 8 } diff --git a/src/lib/netlist/devices/nld_ne555.h b/src/lib/netlist/devices/nld_ne555.h index 0029fd6c6ee..451db5ac2f1 100644 --- a/src/lib/netlist/devices/nld_ne555.h +++ b/src/lib/netlist/devices/nld_ne555.h @@ -27,7 +27,38 @@ NETLIB_NAMESPACE_DEVICES_START() -NETLIB_DEVICE(NE555, +NETLIB_OBJECT(NE555) +{ + NETLIB_CONSTRUCTOR(NE555) + , m_R1(*this, "R1") + , m_R2(*this, "R2") + , m_R3(*this, "R3") + , m_RDIS(*this, "RDIS") + , m_last_out(false) + , m_ff(false) + { + + register_subalias("GND", m_R3.m_N); // Pin 1 + enregister("TRIG", m_TRIG); // Pin 2 + enregister("OUT", m_OUT); // Pin 3 + enregister("RESET", m_RESET); // Pin 4 + register_subalias("CONT", m_R1.m_N); // Pin 5 + enregister("THRESH", m_THRES); // Pin 6 + register_subalias("DISCH", m_RDIS.m_P); // Pin 7 + register_subalias("VCC", m_R1.m_P); // Pin 8 + + connect_late(m_R1.m_N, m_R2.m_P); + connect_late(m_R2.m_N, m_R3.m_P); + connect_late(m_RDIS.m_N, m_R3.m_N); + + save(NLNAME(m_last_out)); + save(NLNAME(m_ff)); + } + + NETLIB_UPDATEI(); + NETLIB_RESETI(); + +protected: NETLIB_SUB(R) m_R1; NETLIB_SUB(R) m_R2; NETLIB_SUB(R) m_R3; @@ -38,12 +69,13 @@ NETLIB_DEVICE(NE555, analog_input_t m_TRIG; analog_output_t m_OUT; +private: bool m_last_out; bool m_ff; inline nl_double clamp(const nl_double v, const nl_double a, const nl_double b); -); +}; #define NE555_DIP(_name) \ NET_REGISTER_DEV(NE555_DIP, _name) diff --git a/src/lib/netlist/devices/nld_system.cpp b/src/lib/netlist/devices/nld_system.cpp index a67d3f835a1..6746e9af5cd 100644 --- a/src/lib/netlist/devices/nld_system.cpp +++ b/src/lib/netlist/devices/nld_system.cpp @@ -213,7 +213,7 @@ void nld_d_to_a_proxy::reset() m_Q.initial(0.0); m_last_state = -1; m_RV.do_reset(); - m_is_timestep = m_RV.m_P.net().solver()->is_timestep(); + m_is_timestep = m_RV.m_P.net().solver()->has_timestep_devices(); m_RV.set(NL_FCONST(1.0) / logic_family().m_R_low, logic_family().m_low_V, 0.0); } @@ -241,24 +241,6 @@ ATTR_HOT void nld_d_to_a_proxy::update() // nld_res_sw // ----------------------------------------------------------------------------- -NETLIB_START(res_sw) -{ - register_sub("R", m_R); - enregister("I", m_I); - register_param("RON", m_RON, 1.0); - register_param("ROFF", m_ROFF, 1.0E20); - - register_subalias("1", m_R->m_P); - register_subalias("2", m_R->m_N); - - save(NLNAME(m_last_state)); -} - -NETLIB_RESET(res_sw) -{ - m_last_state = 0; - m_R->set_R(m_ROFF.Value()); -} NETLIB_UPDATE(res_sw) { @@ -271,14 +253,14 @@ NETLIB_UPDATE(res_sw) // We only need to update the net first if this is a time stepping net if (0) // m_R->m_P.net().as_analog().solver()->is_timestep()) { - m_R->update_dev(); - m_R->set_R(R); - m_R->m_P.schedule_after(NLTIME_FROM_NS(1)); + m_R.update_dev(); + m_R.set_R(R); + m_R.m_P.schedule_after(NLTIME_FROM_NS(1)); } else { - m_R->set_R(R); - m_R->m_P.schedule_after(NLTIME_FROM_NS(1)); + m_R.set_R(R); + m_R.m_P.schedule_after(NLTIME_FROM_NS(1)); //m_R->update_dev(); } } diff --git a/src/lib/netlist/devices/nld_system.h b/src/lib/netlist/devices/nld_system.h index 6e1e532ad0a..cb7025dd1b4 100644 --- a/src/lib/netlist/devices/nld_system.h +++ b/src/lib/netlist/devices/nld_system.h @@ -153,13 +153,10 @@ NETLIB_DEVICE_WITH_PARAMS(analog_input, // nld_gnd // ----------------------------------------------------------------------------- -class NETLIB_NAME(gnd) : public device_t +NETLIB_OBJECT(gnd) { public: - NETLIB_NAME(gnd)(netlist_t &anetlist, const pstring &name) - : device_t(GND, anetlist, name) { } - - virtual ~NETLIB_NAME(gnd)() {} + NETLIB_CONSTRUCTOR(gnd) {} protected: @@ -186,13 +183,10 @@ private: // nld_dummy_input // ----------------------------------------------------------------------------- -class NETLIB_NAME(dummy_input) : public device_t +NETLIB_OBJECT_DERIVED(dummy_input, base_dummy) { public: - NETLIB_NAME(dummy_input)(netlist_t &anetlist, const pstring &name) - : device_t(DUMMY, anetlist, name) { } - - virtual ~NETLIB_NAME(dummy_input)() {} + NETLIB_CONSTRUCTOR_DERIVED(dummy_input, base_dummy) { } protected: @@ -218,16 +212,13 @@ private: // nld_frontier // ----------------------------------------------------------------------------- -class NETLIB_NAME(frontier) : public device_t +NETLIB_OBJECT_DERIVED(frontier, base_dummy) { public: - NETLIB_NAME(frontier)(netlist_t &anetlist, const pstring &name) - : device_t(DUMMY, anetlist, name), - m_RIN(netlist(), "m_RIN"), - m_ROUT(netlist(), "m_ROUT") - { } - - virtual ~NETLIB_NAME(frontier)() {} + NETLIB_CONSTRUCTOR_DERIVED(frontier, base_dummy) + , m_RIN(netlist(), "m_RIN") + , m_ROUT(netlist(), "m_ROUT") + { } protected: @@ -274,13 +265,11 @@ private: * FIXME: Currently a proof of concept to get congo bongo working * ----------------------------------------------------------------------------- */ -class NETLIB_NAME(function) : public device_t +NETLIB_OBJECT(function) { public: - NETLIB_NAME(function)(netlist_t &anetlist, const pstring &name) - : device_t(anetlist, name) { } - - virtual ~NETLIB_NAME(function)() {} + NETLIB_CONSTRUCTOR(function) + { } protected: @@ -319,25 +308,36 @@ private: // nld_res_sw // ----------------------------------------------------------------------------- -class NETLIB_NAME(res_sw) : public device_t +NETLIB_OBJECT(res_sw) { public: - NETLIB_NAME(res_sw)(netlist_t &anetlist, const pstring &name) - : device_t(anetlist, name) { } + NETLIB_CONSTRUCTOR(res_sw) + , m_R(*this, "R") + { + enregister("I", m_I); + register_param("RON", m_RON, 1.0); + register_param("ROFF", m_ROFF, 1.0E20); - virtual ~NETLIB_NAME(res_sw)() {} + register_subalias("1", m_R.m_P); + register_subalias("2", m_R.m_N); + + save(NLNAME(m_last_state)); + } + NETLIB_SUB(R) m_R; param_double_t m_RON; param_double_t m_ROFF; logic_input_t m_I; - NETLIB_SUB(R) m_R; protected: - void start() override; - void reset() override; - ATTR_HOT void update() override; - ATTR_HOT void update_param() override; + NETLIB_RESETI() + { + m_last_state = 0; + m_R.set_R(m_ROFF.Value()); + } + NETLIB_UPDATE_PARAMI(); + NETLIB_UPDATEI(); private: UINT8 m_last_state; @@ -347,7 +347,7 @@ private: // nld_base_proxy // ----------------------------------------------------------------------------- -class nld_base_proxy : public device_t +NETLIB_OBJECT(base_proxy) { public: nld_base_proxy(netlist_t &anetlist, const pstring &name, logic_t *inout_proxied, core_terminal_t *proxy_inout) @@ -380,7 +380,7 @@ private: // nld_a_to_d_proxy // ----------------------------------------------------------------------------- -class nld_a_to_d_proxy : public nld_base_proxy +NETLIB_OBJECT_DERIVED(a_to_d_proxy, base_proxy) { public: nld_a_to_d_proxy(netlist_t &anetlist, const pstring &name, logic_input_t *in_proxied) @@ -422,7 +422,7 @@ private: // nld_base_d_to_a_proxy // ----------------------------------------------------------------------------- -class nld_base_d_to_a_proxy : public nld_base_proxy +NETLIB_OBJECT_DERIVED(base_d_to_a_proxy, base_proxy) { public: virtual ~nld_base_d_to_a_proxy() {} @@ -445,12 +445,12 @@ protected: private: }; -class nld_d_to_a_proxy : public nld_base_d_to_a_proxy +NETLIB_OBJECT_DERIVED(d_to_a_proxy, base_d_to_a_proxy) { public: nld_d_to_a_proxy(netlist_t &anetlist, const pstring &name, logic_output_t *out_proxied) : nld_base_d_to_a_proxy(anetlist, name, out_proxied, m_RV.m_P) - , m_RV(TWOTERM, anetlist,"RV") + , m_RV(anetlist, "RV") , m_last_state(-1) , m_is_timestep(false) { diff --git a/src/lib/netlist/devices/nld_truthtable.h b/src/lib/netlist/devices/nld_truthtable.h index f4592936e6b..e73affc457d 100644 --- a/src/lib/netlist/devices/nld_truthtable.h +++ b/src/lib/netlist/devices/nld_truthtable.h @@ -17,8 +17,9 @@ class NETLIB_NAME(_name) : public nld_truthtable_t<_nIN, _nOUT, _state> \ { \ public: \ - NETLIB_NAME(_name)(netlist_t &anetlist, const pstring &name) \ - : nld_truthtable_t<_nIN, _nOUT, _state>(anetlist, name, &m_ttbl, m_desc) { }\ + template <class C> \ + NETLIB_NAME(_name)(C &owner, const pstring &name) \ + : nld_truthtable_t<_nIN, _nOUT, _state>(owner, name, nullptr, &m_ttbl, m_desc) { } \ private: \ static truthtable_t m_ttbl; \ static const char *m_desc[]; \ @@ -91,8 +92,10 @@ private: }; template<unsigned m_NI, unsigned m_NO, int has_state> -class nld_truthtable_t : public device_t +NETLIB_OBJECT(truthtable_t) { +private: + family_setter_t m_fam; public: static const int m_num_bits = m_NI + has_state * (m_NI + m_NO); @@ -101,9 +104,8 @@ public: struct truthtable_t { truthtable_t() - : m_initialized(false), - m_desc(m_NO, m_NI, has_state, - &m_initialized, m_outs, m_timing, m_timing_nt) {} + : m_initialized(false) + , m_desc(m_NO, m_NI, has_state, &m_initialized, m_outs, m_timing, m_timing_nt) {} bool m_initialized; UINT32 m_outs[m_size]; UINT8 m_timing[m_size * m_NO]; @@ -111,8 +113,15 @@ public: truthtable_desc_t m_desc; }; - nld_truthtable_t(netlist_t &anetlist, const pstring &name, truthtable_t *ttbl, const char *desc[]) - : device_t(anetlist, name), m_last_state(0), m_ign(0), m_active(1), m_ttp(ttbl) + template <class C> + nld_truthtable_t(C &owner, const pstring &name, logic_family_desc_t *fam, + truthtable_t *ttbl, const char *desc[]) + : device_t(owner, name) + , m_fam(*this, fam) + , m_last_state(0) + , m_ign(0) + , m_active(1) + , m_ttp(ttbl) { while (*desc != nullptr && **desc != 0 ) { @@ -122,8 +131,15 @@ public: } - nld_truthtable_t(netlist_t &anetlist, const pstring &name, truthtable_t *ttbl, const pstring_vector_t &desc) - : device_t(anetlist, name), m_last_state(0), m_ign(0), m_active(1), m_ttp(ttbl) + template <class C> + nld_truthtable_t(C &owner, const pstring &name, logic_family_desc_t *fam, + truthtable_t *ttbl, const pstring_vector_t &desc) + : device_t(owner, name) + , m_fam(*this, fam) + , m_last_state(0) + , m_ign(0) + , m_active(1) + , m_ttp(ttbl) { m_desc = desc; } @@ -326,8 +342,7 @@ public: device_t *Create(netlist_t &anetlist, const pstring &name) override { typedef nld_truthtable_t<m_NI, m_NO, has_state> tt_type; - device_t *r = palloc(tt_type(anetlist, name, &m_ttbl, m_desc)); - r->set_logic_family(m_family); + device_t *r = palloc(tt_type(anetlist, name, m_family, &m_ttbl, m_desc)); //r->init(setup, name); return r; } diff --git a/src/lib/netlist/nl_base.cpp b/src/lib/netlist/nl_base.cpp index 5fc5a4b1bab..4d5d3a93e11 100644 --- a/src/lib/netlist/nl_base.cpp +++ b/src/lib/netlist/nl_base.cpp @@ -74,7 +74,7 @@ logic_family_desc_t *family_CD4XXX = palloc(logic_family_cd4xxx_t); queue_t::queue_t(netlist_t &nl) : timed_queue<net_t *, netlist_time>(512) - , object_t(nl, "QUEUE", QUEUE, GENERIC) + , object_t(nl, "QUEUE", QUEUE) , pstate_callback_t() , m_qsize(0) , m_times(512) @@ -124,22 +124,19 @@ void queue_t::on_post_load() // object_t // ---------------------------------------------------------------------------------------- -ATTR_COLD object_t::object_t(const type_t atype, const family_t afamily) +ATTR_COLD object_t::object_t(const type_t atype) : m_objtype(atype) -, m_family(afamily) , m_netlist(nullptr) {} -ATTR_COLD object_t::object_t(netlist_t &nl, const type_t atype, const family_t afamily) +ATTR_COLD object_t::object_t(netlist_t &nl, const type_t atype) : m_objtype(atype) -, m_family(afamily) , m_netlist(&nl) {} -ATTR_COLD object_t::object_t(netlist_t &nl, const pstring &aname, const type_t atype, const family_t afamily) +ATTR_COLD object_t::object_t(netlist_t &nl, const pstring &aname, const type_t atype) : m_name(aname) , m_objtype(atype) -, m_family(afamily) , m_netlist(&nl) { } @@ -172,9 +169,8 @@ ATTR_COLD const pstring &object_t::name() const // device_object_t // ---------------------------------------------------------------------------------------- -ATTR_COLD device_object_t::device_object_t(const type_t atype, - const family_t afamily) -: object_t(atype, afamily) +ATTR_COLD device_object_t::device_object_t(const type_t atype) +: object_t(atype) , m_device(nullptr) { } @@ -214,7 +210,6 @@ netlist_t::~netlist_t() m_nets.clear(); m_devices.clear(); - //m_devices.clear_and_free(); pfree(m_lib); pstring::resetmem(); @@ -233,17 +228,27 @@ ATTR_COLD void netlist_t::start() m_lib = palloc(pdynlib(libpath)); - /* find the main clock and solver ... */ + /* make sure the solver and parameters are started first! */ + + for (auto & e : setup().m_device_factory) + { + if ( setup().factory().is_class<devices::NETLIB_NAME(mainclock)>(e.second) + || setup().factory().is_class<devices::NETLIB_NAME(solver)>(e.second) + || setup().factory().is_class<devices::NETLIB_NAME(gnd)>(e.second) + || setup().factory().is_class<devices::NETLIB_NAME(netlistparams)>(e.second)) + { + auto dev = std::shared_ptr<device_t>(e.second->Create(*this, e.first)); + setup().register_dev_s(dev); + } + } log().debug("Searching for mainclock and solver ...\n"); - m_mainclock = get_single_device<devices:: NETLIB_NAME(mainclock)>("mainclock"); + m_mainclock = get_single_device<devices::NETLIB_NAME(mainclock)>("mainclock"); m_solver = get_single_device<devices::NETLIB_NAME(solver)>("solver"); m_gnd = get_single_device<devices::NETLIB_NAME(gnd)>("gnd"); m_params = get_single_device<devices::NETLIB_NAME(netlistparams)>("parameter"); - /* make sure the solver and parameters are started first! */ - if (m_solver != nullptr) m_solver->start_dev(); @@ -254,6 +259,20 @@ ATTR_COLD void netlist_t::start() m_use_deactivate = (m_params->m_use_deactivate.Value() ? true : false); + /* create devices */ + + for (auto & e : setup().m_device_factory) + { + if ( !setup().factory().is_class<devices::NETLIB_NAME(mainclock)>(e.second) + && !setup().factory().is_class<devices::NETLIB_NAME(solver)>(e.second) + && !setup().factory().is_class<devices::NETLIB_NAME(gnd)>(e.second) + && !setup().factory().is_class<devices::NETLIB_NAME(netlistparams)>(e.second)) + { + auto dev = std::shared_ptr<device_t>(e.second->Create(*this, e.first)); + setup().register_dev_s(dev); + } + } + log().debug("Initializing devices ...\n"); for (auto &dev : m_devices) if (dev.get() != m_solver && dev.get() != m_params) @@ -398,8 +417,8 @@ void netlist_t::print_stats() const // net_core_device_t // ---------------------------------------------------------------------------------------- -ATTR_COLD core_device_t::core_device_t(const family_t afamily, netlist_t &anetlist, const pstring &name) -: object_t(DEVICE, afamily), logic_family_t() +ATTR_COLD core_device_t::core_device_t(netlist_t &owner, const pstring &name) +: object_t(DEVICE), logic_family_t() #if (NL_KEEP_STATISTICS) , stat_total_time(0) , stat_update_count(0) @@ -408,7 +427,21 @@ ATTR_COLD core_device_t::core_device_t(const family_t afamily, netlist_t &anetli { if (logic_family() == nullptr) set_logic_family(family_TTL); - init_object(anetlist, name); + init_object(owner, name); +} + +ATTR_COLD core_device_t::core_device_t(core_device_t &owner, const pstring &name) +: object_t(DEVICE), logic_family_t() +#if (NL_KEEP_STATISTICS) + , stat_total_time(0) + , stat_update_count(0) + , stat_call_count(0) +#endif +{ + set_logic_family(owner.logic_family()); + if (logic_family() == nullptr) + set_logic_family(family_TTL); + init_object(owner.netlist(), owner.name() +"." + name); } ATTR_COLD core_device_t::~core_device_t() @@ -457,18 +490,6 @@ ATTR_HOT netlist_sig_t core_device_t::INPLOGIC_PASSIVE(logic_input_t &inp) // device_t // ---------------------------------------------------------------------------------------- -device_t::device_t(netlist_t &anetlist, const pstring &name) - : core_device_t(GENERIC, anetlist, name), - m_terminals() -{ -} - -device_t::device_t(const family_t afamily, netlist_t &anetlist, const pstring &name) - : core_device_t(afamily, anetlist, name), - m_terminals() -{ -} - device_t::~device_t() { //log().debug("~net_device_t\n"); @@ -482,7 +503,7 @@ ATTR_COLD setup_t &device_t::setup() ATTR_COLD void device_t::register_sub_p(device_t &dev) { // subdevices always first inherit the logic family of the parent - dev.set_logic_family(this->logic_family()); + //dev.set_logic_family(this->logic_family()); dev.start_dev(); } @@ -552,13 +573,26 @@ template ATTR_COLD void device_t::register_param(const pstring &sname, param_str template ATTR_COLD void device_t::register_param(const pstring &sname, param_str_t ¶m, const pstring &initialVal); template ATTR_COLD void device_t::register_param(const pstring &sname, param_model_t ¶m, const char * const initialVal); +// ----------------------------------------------------------------------------- +// family_setter_t +// ----------------------------------------------------------------------------- + +family_setter_t::family_setter_t(core_device_t &dev, const char *desc) +{ + dev.set_logic_family(dev.netlist().setup().family_from_model(desc)); +} + +family_setter_t::family_setter_t(core_device_t &dev, logic_family_desc_t *desc) +{ + dev.set_logic_family(desc); +} // ---------------------------------------------------------------------------------------- // net_t // ---------------------------------------------------------------------------------------- -ATTR_COLD net_t::net_t(const family_t afamily) - : object_t(NET, afamily) +ATTR_COLD net_t::net_t() + : object_t(NET) , m_new_Q(0) , m_cur_Q (0) , m_railterminal(nullptr) @@ -749,7 +783,7 @@ ATTR_COLD void net_t::merge_net(net_t *othernet) // ---------------------------------------------------------------------------------------- ATTR_COLD logic_net_t::logic_net_t() - : net_t(LOGIC) + : net_t() { } @@ -769,13 +803,13 @@ ATTR_COLD void logic_net_t::save_register() // ---------------------------------------------------------------------------------------- ATTR_COLD analog_net_t::analog_net_t() - : net_t(ANALOG) + : net_t() , m_solver(nullptr) { } ATTR_COLD analog_net_t::analog_net_t(netlist_t &nl, const pstring &aname) - : net_t(ANALOG) + : net_t() , m_solver(nullptr) { init_object(nl, aname); @@ -826,8 +860,8 @@ ATTR_COLD void analog_net_t::process_net(pvector_t<list_t> &groups) // core_terminal_t // ---------------------------------------------------------------------------------------- -ATTR_COLD core_terminal_t::core_terminal_t(const type_t atype, const family_t afamily) -: device_object_t(atype, afamily) +ATTR_COLD core_terminal_t::core_terminal_t(const type_t atype) +: device_object_t(atype) , plinkedlist_element_t() , m_net(nullptr) , m_state(STATE_NONEX) @@ -962,7 +996,7 @@ ATTR_COLD void analog_output_t::initial(const nl_double val) // ---------------------------------------------------------------------------------------- ATTR_COLD param_t::param_t(const param_type_t atype) - : device_object_t(PARAM, ANALOG) + : device_object_t(PARAM) , m_param_type(atype) { } diff --git a/src/lib/netlist/nl_base.h b/src/lib/netlist/nl_base.h index bf9e9e09fb5..208fd966848 100644 --- a/src/lib/netlist/nl_base.h +++ b/src/lib/netlist/nl_base.h @@ -176,6 +176,43 @@ */ using netlist_sig_t = std::uint32_t; + //============================================================ + // MACROS / New Syntax + //============================================================ + +#define NETLIB_OBJECT_DERIVED(_name, _pclass) \ +class NETLIB_NAME(_name) : public NETLIB_NAME(_pclass) + +#define NETLIB_OBJECT(_name) \ +class NETLIB_NAME(_name) : public device_t + +#define NETLIB_CONSTRUCTOR_DERIVED(_name, _pclass) \ + private: family_setter_t m_famsetter; \ + public: template <class _C> ATTR_COLD NETLIB_NAME(_name)(_C &owner, const pstring name) \ + : NETLIB_NAME(_pclass)(owner, name) + +#define NETLIB_CONSTRUCTOR(_name) \ + private: family_setter_t m_famsetter; \ + public: template <class _C> ATTR_COLD NETLIB_NAME(_name)(_C &owner, const pstring name) \ + : device_t(owner, name) + +#define NETLIB_DYNAMIC() \ + ATTR_HOT virtual bool is_dynamic1() const override { return true; } + +#define NETLIB_TIMESTEP() \ + ATTR_HOT virtual bool is_timestep() const override { return true; } \ + ATTR_HOT void step_time(const nl_double step) override + +#define NETLIB_FAMILY(_family) m_famsetter(*this, _family) + +#define NETLIB_UPDATE_TERMINALSI() ATTR_HOT virtual void update_terminals(void) override +#define NETLIB_UPDATEI() ATTR_HOT virtual void update(void) override +#define NETLIB_UPDATE_PARAMI() ATTR_HOT virtual void update_param(void) override +#define NETLIB_RESETI() ATTR_COLD virtual void reset(void) override + +#define NETLIB_SUB(_chip) nld_ ## _chip + + //============================================================ // MACROS / netlist devices //============================================================ @@ -184,7 +221,7 @@ using netlist_sig_t = std::uint32_t; #define NETLIB_NAMESPACE_DEVICES_END() }} #define NETLIB_NAME(_chip) nld_ ## _chip -#define NETLIB_SUB(_chip) std::unique_ptr< nld_ ## _chip > +#define NETLIB_SUBXX(_chip) std::unique_ptr< nld_ ## _chip > #define NETLIB_NAME_STR_S(_s) # _s #define NETLIB_NAME_STR(_chip) NETLIB_NAME_STR_S(nld_ ## _chip) @@ -200,15 +237,14 @@ using netlist_sig_t = std::uint32_t; #define NETLIB_FUNC_VOID(_chip, _name, _params) ATTR_HOT void NETLIB_NAME(_chip) :: _name _params #define NETLIB_UPDATE_TERMINALS(_chip) ATTR_HOT void NETLIB_NAME(_chip) :: update_terminals(void) -#define NETLIB_UPDATE_TERMINALSI() ATTR_HOT void update_terminals(void) override -#define NETLIB_UPDATEI() ATTR_HOT void update(void) #define NETLIB_DEVICE_BASE(_name, _pclass, _extra, _priv) \ class _name : public _pclass \ { \ public: \ - _name(netlist_t &anetlist, const pstring &name) \ - : _pclass(anetlist, name) { } \ + template <class C> \ + _name(C &owner, const pstring &name) \ + : _pclass(owner, name) { } \ protected: \ _extra \ ATTR_HOT void update() override; \ @@ -230,8 +266,7 @@ using netlist_sig_t = std::uint32_t; class NETLIB_NAME(_name) : public device_t \ { \ public: \ - NETLIB_NAME(_name) (netlist_t &anetlist, const pstring &name) \ - : device_t(anetlist, name) \ + NETLIB_CONSTRUCTOR(_name) \ { } \ /*protected:*/ \ ATTR_HOT void update() override; \ @@ -375,32 +410,10 @@ namespace netlist DEVICE = 5, QUEUE = 6 }; - enum family_t { - // Terminal families - LOGIC, - ANALOG, - // Device families - GENERIC, // <== devices usually fall into this category - TWOTERM, // Generic twoterm ... - RESISTOR, // Resistor - CAPACITOR, // Capacitor - DIODE, // Diode - DUMMY, // DUMMY device without function - FRONTIER, // Net frontier - BJT_EB, // BJT(Ebers-Moll) - BJT_SWITCH, // BJT(Switch) - VCVS, // Voltage controlled voltage source - VCCS, // Voltage controlled current source - LVCCS, // Voltage controlled current source (Current limited) - CCCS, // Current controlled current source - VS, // Voltage Source - CS, // Current Source - GND // GND device - }; - ATTR_COLD object_t(const type_t atype, const family_t afamily); - ATTR_COLD object_t(netlist_t &nl, const type_t atype, const family_t afamily); - ATTR_COLD object_t(netlist_t &nl, const pstring &aname, const type_t atype, const family_t afamily); + ATTR_COLD object_t(const type_t atype); + ATTR_COLD object_t(netlist_t &nl, const type_t atype); + ATTR_COLD object_t(netlist_t &nl, const pstring &aname, const type_t atype); virtual ~object_t(); @@ -413,10 +426,8 @@ namespace netlist ATTR_COLD inline pstate_manager_t *state_manager(); ATTR_HOT type_t type() const { return m_objtype; } - ATTR_HOT family_t family() const { return m_family; } ATTR_HOT bool isType(const type_t atype) const { return (m_objtype == atype); } - ATTR_HOT bool isFamily(const family_t afamily) const { return (m_family == afamily); } ATTR_HOT netlist_t & netlist() { return *m_netlist; } ATTR_HOT const netlist_t & netlist() const { return *m_netlist; } @@ -435,7 +446,6 @@ namespace netlist private: pstring m_name; const type_t m_objtype; - const family_t m_family; netlist_t * m_netlist; }; @@ -447,7 +457,7 @@ namespace netlist { P_PREVENT_COPYING(device_object_t) public: - ATTR_COLD device_object_t(const type_t atype, const family_t afamily); + ATTR_COLD device_object_t(const type_t atype); ATTR_COLD void init_object(core_device_t &dev, const pstring &aname); @@ -480,10 +490,13 @@ namespace netlist }; - ATTR_COLD core_terminal_t(const type_t atype, const family_t afamily); + ATTR_COLD core_terminal_t(const type_t atype); ATTR_COLD void set_net(net_t *anet); ATTR_COLD void clear_net(); + ATTR_COLD bool is_logic() const; + ATTR_COLD bool is_analog() const; + ATTR_HOT bool has_net() const { return (m_net != nullptr); } ATTR_HOT const net_t & net() const { return *m_net;} @@ -519,7 +532,7 @@ namespace netlist ATTR_COLD analog_t(const type_t atype) - : core_terminal_t(atype, ANALOG) + : core_terminal_t(atype) { } @@ -611,7 +624,7 @@ namespace netlist ATTR_COLD logic_t(const type_t atype) - : core_terminal_t(atype, LOGIC), logic_family_t(), + : core_terminal_t(atype), logic_family_t(), m_proxy(nullptr) { } @@ -695,7 +708,7 @@ namespace netlist using ptr_t = net_t *; using list_t = pvector_t<std::shared_ptr<net_t>>; - ATTR_COLD net_t(const family_t afamily); + ATTR_COLD net_t(); virtual ~net_t(); ATTR_COLD void init_object(netlist_t &nl, const pstring &aname, core_terminal_t *mr = nullptr); @@ -703,6 +716,9 @@ namespace netlist ATTR_COLD void register_con(core_terminal_t &terminal); ATTR_COLD void merge_net(net_t *othernet); + ATTR_COLD bool is_logic() const; + ATTR_COLD bool is_analog() const; + ATTR_HOT logic_net_t & as_logic(); ATTR_HOT const logic_net_t & as_logic() const; @@ -1021,7 +1037,8 @@ namespace netlist using list_t = pvector_t<core_device_t *>; - ATTR_COLD core_device_t(const family_t afamily, netlist_t &anetlist, const pstring &name); + ATTR_COLD core_device_t(netlist_t &owner, const pstring &name); + ATTR_COLD core_device_t(core_device_t &owner, const pstring &name); virtual ~core_device_t(); @@ -1070,9 +1087,6 @@ namespace netlist ATTR_HOT virtual void dec_active() { } - ATTR_HOT virtual void step_time(ATTR_UNUSED const nl_double st) { } - ATTR_HOT virtual void update_terminals() { } - #if (NL_KEEP_STATISTICS) /* stats */ osd_ticks_t stat_total_time; @@ -1086,6 +1100,12 @@ namespace netlist virtual void start() { } virtual void stop() { } + public: + ATTR_HOT virtual void step_time(ATTR_UNUSED const nl_double st) { } + ATTR_HOT virtual void update_terminals() { } + ATTR_HOT virtual bool is_dynamic1() const { return false; } + ATTR_HOT virtual bool is_timestep() const { return false; } + private: #if (NL_PMF_TYPE == NL_PMF_TYPE_GNUC_PMF) @@ -1108,8 +1128,9 @@ namespace netlist P_PREVENT_COPYING(device_t) public: - ATTR_COLD device_t(netlist_t &anetlist, const pstring &name); - ATTR_COLD device_t(const family_t afamily, netlist_t &anetlist, const pstring &name); + template <class C> + ATTR_COLD device_t(C &owner, const pstring &name) + : core_device_t(owner, name) { } virtual ~device_t(); @@ -1118,7 +1139,7 @@ namespace netlist template<class C> void register_sub(const pstring &name, std::unique_ptr<C> &dev) { - dev.reset(new C(this->netlist(), this->name() + "." + name)); + dev.reset(new C(*this, name)); register_sub_p(*dev); } @@ -1158,6 +1179,26 @@ namespace netlist ATTR_COLD void register_sub_p(device_t &dev); }; + // ----------------------------------------------------------------------------- + // family_setter_t + // ----------------------------------------------------------------------------- + + struct family_setter_t + { + family_setter_t() { } + family_setter_t(core_device_t &dev, const char *desc); + family_setter_t(core_device_t &dev, logic_family_desc_t *desc); + }; + + // ----------------------------------------------------------------------------- + // nld_base_dummy : basis for dummy devices + // ----------------------------------------------------------------------------- + + NETLIB_OBJECT(base_dummy) + { + public: + NETLIB_CONSTRUCTOR(base_dummy) { } + }; // ----------------------------------------------------------------------------- // queue_t @@ -1190,7 +1231,7 @@ namespace netlist // ----------------------------------------------------------------------------- - class netlist_t : public pstate_manager_t, public plog_dispatch_intf + class netlist_t : public pstate_manager_t, public plog_dispatch_intf //, public device_owner_t { P_PREVENT_COPYING(netlist_t) public: @@ -1239,18 +1280,6 @@ namespace netlist } template<class _device_class> - ATTR_COLD _device_class *get_first_device() - { - for (auto &d : m_devices) - { - _device_class *dev = dynamic_cast<_device_class *>(d.get()); - if (dev != nullptr) - return dev; - } - return nullptr; - } - - template<class _device_class> ATTR_COLD _device_class *get_single_device(const char *classname) { _device_class *ret = nullptr; @@ -1268,8 +1297,6 @@ namespace netlist return ret; } - pvector_t<std::shared_ptr<device_t>> m_devices; - net_t::list_t m_nets; #if (NL_KEEP_STATISTICS) pvector_t<core_device_t *> m_started_devices; #endif @@ -1283,6 +1310,9 @@ namespace netlist void print_stats() const; + pvector_t<std::shared_ptr<device_t>> m_devices; + net_t::list_t m_nets; + protected: #if (NL_KEEP_STATISTICS) @@ -1331,27 +1361,47 @@ protected: } } + ATTR_COLD inline bool core_terminal_t::is_logic() const + { + return dynamic_cast<const logic_t *>(this) != nullptr; + } + + ATTR_COLD inline bool core_terminal_t::is_analog() const + { + return dynamic_cast<const analog_t *>(this) != nullptr; + } + + ATTR_COLD inline bool net_t::is_logic() const + { + return dynamic_cast<const logic_net_t *>(this) != nullptr; + } + + ATTR_COLD inline bool net_t::is_analog() const + { + return dynamic_cast<const analog_net_t *>(this) != nullptr; + } + ATTR_HOT inline logic_net_t & net_t::as_logic() { - nl_assert(family() == LOGIC); + nl_assert(is_logic()); return static_cast<logic_net_t &>(*this); } ATTR_HOT inline const logic_net_t & net_t::as_logic() const { - nl_assert(family() == LOGIC); + nl_assert(is_logic()); return static_cast<const logic_net_t &>(*this); } ATTR_HOT inline analog_net_t & net_t::as_analog() { - nl_assert(family() == ANALOG); + nl_assert(is_analog()); return static_cast<analog_net_t &>(*this); } ATTR_HOT inline const analog_net_t & net_t::as_analog() const { - nl_assert(family() == ANALOG); + nl_assert(is_analog()); return static_cast<const analog_net_t &>(*this); } diff --git a/src/lib/netlist/nl_config.h b/src/lib/netlist/nl_config.h index 835949a80e7..430ae8d6db8 100644 --- a/src/lib/netlist/nl_config.h +++ b/src/lib/netlist/nl_config.h @@ -46,8 +46,13 @@ * Disappointing is the GNUC_PMF performance. */ + +/* FIXME: Currently, we are not registering subdevices and thus these will not + * be started and the internal method will not be initialized. + */ + // This will be autodetected -// #define NL_PMF_TYPE 3 +#define NL_PMF_TYPE 0 #define NL_PMF_TYPE_VIRTUAL 0 #define NL_PMF_TYPE_GNUC_PMF 1 diff --git a/src/lib/netlist/nl_factory.h b/src/lib/netlist/nl_factory.h index 4a08b969923..386a33f39f0 100644 --- a/src/lib/netlist/nl_factory.h +++ b/src/lib/netlist/nl_factory.h @@ -9,6 +9,8 @@ #ifndef NLFACTORY_H_ #define NLFACTORY_H_ +#include <type_traits> + #include "nl_config.h" #include "plib/palloc.h" #include "plib/plists.h" @@ -59,6 +61,7 @@ namespace netlist device_t *r = palloc(_device_class(anetlist, name)); return r; } + }; class factory_list_t : public phashmap_t<pstring, base_factory_t *> @@ -86,6 +89,12 @@ namespace netlist std::shared_ptr<device_t> new_device_by_name(const pstring &devname, netlist_t &anetlist, const pstring &name); base_factory_t * factory_by_name(const pstring &devname); + template <class _class> + bool is_class(base_factory_t *f) + { + return dynamic_cast<factory_t<_class> *>(f) != nullptr; + } + private: void error(const pstring &s); diff --git a/src/lib/netlist/nl_setup.cpp b/src/lib/netlist/nl_setup.cpp index 35807c000bb..6b554a701ee 100644 --- a/src/lib/netlist/nl_setup.cpp +++ b/src/lib/netlist/nl_setup.cpp @@ -18,6 +18,7 @@ #include "devices/net_lib.h" #include "devices/nld_system.h" #include "analog/nld_twoterm.h" +#include "solver/nld_solver.h" static NETLIST_START(base) TTL_INPUT(ttlhigh, 1) @@ -215,22 +216,22 @@ void setup_t::register_object(device_t &dev, const pstring &name, object_t &obj) case terminal_t::OUTPUT: { core_terminal_t &term = dynamic_cast<core_terminal_t &>(obj); - if (obj.isType(terminal_t::OUTPUT)) + if (term.isType(terminal_t::OUTPUT)) { - if (obj.isFamily(terminal_t::LOGIC)) + if (term.is_logic()) { logic_output_t &port = dynamic_cast<logic_output_t &>(term); port.set_logic_family(dev.logic_family()); dynamic_cast<logic_output_t &>(term).init_object(dev, dev.name() + "." + name); } - else if (obj.isFamily(terminal_t::ANALOG)) + else if (term.is_analog()) dynamic_cast<analog_output_t &>(term).init_object(dev, dev.name() + "." + name); else log().fatal("Error adding {1} {2} to terminal list, neither LOGIC nor ANALOG\n", objtype_as_astr(term), term.name()); } - else if (obj.isType(terminal_t::INPUT)) + else if (term.isType(terminal_t::INPUT)) { - if (obj.isFamily(terminal_t::LOGIC)) + if (term.is_logic()) { logic_input_t &port = dynamic_cast<logic_input_t &>(term); port.set_logic_family(dev.logic_family()); @@ -487,7 +488,7 @@ param_t *setup_t::find_param(const pstring ¶m_in, bool required) // FIXME avoid dynamic cast here devices::nld_base_proxy *setup_t::get_d_a_proxy(core_terminal_t &out) { - nl_assert(out.isFamily(terminal_t::LOGIC)); + nl_assert(out.is_logic()); logic_output_t &out_cast = dynamic_cast<logic_output_t &>(out); devices::nld_base_proxy *proxy = out_cast.get_proxy(); @@ -522,7 +523,7 @@ devices::nld_base_proxy *setup_t::get_d_a_proxy(core_terminal_t &out) void setup_t::connect_input_output(core_terminal_t &in, core_terminal_t &out) { - if (out.isFamily(terminal_t::ANALOG) && in.isFamily(terminal_t::LOGIC)) + if (out.is_analog() && in.is_logic()) { logic_input_t &incast = dynamic_cast<logic_input_t &>(in); pstring x = pfmt("proxy_ad_{1}_{2}")(in.name())( m_proxy_cnt); @@ -537,7 +538,7 @@ void setup_t::connect_input_output(core_terminal_t &in, core_terminal_t &out) out.net().register_con(proxy->m_I); } - else if (out.isFamily(terminal_t::LOGIC) && in.isFamily(terminal_t::ANALOG)) + else if (out.is_logic() && in.is_analog()) { devices::nld_base_proxy *proxy = get_d_a_proxy(out); @@ -556,11 +557,11 @@ void setup_t::connect_input_output(core_terminal_t &in, core_terminal_t &out) void setup_t::connect_terminal_input(terminal_t &term, core_terminal_t &inp) { - if (inp.isFamily(terminal_t::ANALOG)) + if (inp.is_analog()) { connect_terminals(inp, term); } - else if (inp.isFamily(terminal_t::LOGIC)) + else if (inp.is_logic()) { logic_input_t &incast = dynamic_cast<logic_input_t &>(inp); log().debug("connect_terminal_input: connecting proxy\n"); @@ -588,7 +589,7 @@ void setup_t::connect_terminal_input(terminal_t &term, core_terminal_t &inp) void setup_t::connect_terminal_output(terminal_t &in, core_terminal_t &out) { - if (out.isFamily(terminal_t::ANALOG)) + if (out.is_analog()) { log().debug("connect_terminal_output: {1} {2}\n", in.name(), out.name()); /* no proxy needed, just merge existing terminal net */ @@ -597,7 +598,7 @@ void setup_t::connect_terminal_output(terminal_t &in, core_terminal_t &out) else out.net().register_con(in); } - else if (out.isFamily(terminal_t::LOGIC)) + else if (out.is_logic()) { log().debug("connect_terminal_output: connecting proxy\n"); devices::nld_base_proxy *proxy = get_d_a_proxy(out); @@ -640,7 +641,7 @@ void setup_t::connect_terminals(core_terminal_t &t1, core_terminal_t &t2) static core_terminal_t &resolve_proxy(core_terminal_t &term) { - if (term.isFamily(core_terminal_t::LOGIC)) + if (term.is_logic()) { logic_t &out = dynamic_cast<logic_t &>(term); if (out.has_proxy()) @@ -853,13 +854,6 @@ void setup_t::start_devices() } } - /* create devices */ - - for (auto & e : m_device_factory) - { - auto dev = std::shared_ptr<device_t>(e.second->Create(netlist(), e.first)); - register_dev_s(dev); - } netlist().start(); } diff --git a/src/lib/netlist/nl_setup.h b/src/lib/netlist/nl_setup.h index 1ebcf49964d..8ac47159411 100644 --- a/src/lib/netlist/nl_setup.h +++ b/src/lib/netlist/nl_setup.h @@ -180,6 +180,8 @@ namespace netlist plog_base<NL_DEBUG> &log() { return netlist().log(); } const plog_base<NL_DEBUG> &log() const { return netlist().log(); } + pvector_t<std::pair<pstring, base_factory_t *>> m_device_factory; + protected: private: @@ -207,7 +209,6 @@ namespace netlist phashmap_t<pstring, core_terminal_t *> m_terminals; pvector_t<link_t> m_links; - pvector_t<std::pair<pstring, base_factory_t *>> m_device_factory; factory_list_t m_factory; diff --git a/src/lib/netlist/solver/nld_matrix_solver.h b/src/lib/netlist/solver/nld_matrix_solver.h index ce8de00b55a..eea3634885d 100644 --- a/src/lib/netlist/solver/nld_matrix_solver.h +++ b/src/lib/netlist/solver/nld_matrix_solver.h @@ -94,8 +94,8 @@ public: netlist_time solve(); - inline bool is_dynamic() const { return m_dynamic_devices.size() > 0; } - inline bool is_timestep() const { return m_step_devices.size() > 0; } + inline bool has_dynamic_devices() const { return m_dynamic_devices.size() > 0; } + inline bool has_timestep_devices() const { return m_step_devices.size() > 0; } void update_forced(); void update_after(const netlist_time after) diff --git a/src/lib/netlist/solver/nld_ms_direct1.h b/src/lib/netlist/solver/nld_ms_direct1.h index a8e5baf8395..fa994cc0413 100644 --- a/src/lib/netlist/solver/nld_ms_direct1.h +++ b/src/lib/netlist/solver/nld_ms_direct1.h @@ -36,7 +36,7 @@ inline int matrix_solver_direct1_t::vsolve_non_dynamic(ATTR_UNUSED const bool ne nl_double new_val[1] = { RHS(0) / A(0,0) }; - if (is_dynamic()) + if (has_dynamic_devices()) { nl_double err = this->delta(new_val); store(new_val); diff --git a/src/lib/netlist/solver/nld_ms_direct2.h b/src/lib/netlist/solver/nld_ms_direct2.h index 646291e6e55..0a9c5cdd0b4 100644 --- a/src/lib/netlist/solver/nld_ms_direct2.h +++ b/src/lib/netlist/solver/nld_ms_direct2.h @@ -42,7 +42,7 @@ inline int matrix_solver_direct2_t::vsolve_non_dynamic(ATTR_UNUSED const bool ne new_val[1] = (a * RHS(1) - c * RHS(0)) / (a * d - b * c); new_val[0] = (RHS(0) - b * new_val[1]) / a; - if (is_dynamic()) + if (has_dynamic_devices()) { nl_double err = this->delta(new_val); store(new_val); diff --git a/src/lib/netlist/solver/nld_solver.cpp b/src/lib/netlist/solver/nld_solver.cpp index 1238fba39f8..2e66068fcf9 100644 --- a/src/lib/netlist/solver/nld_solver.cpp +++ b/src/lib/netlist/solver/nld_solver.cpp @@ -146,28 +146,17 @@ ATTR_COLD void matrix_solver_t::setup_base(analog_net_t::list_t &nets) switch (p->type()) { case terminal_t::TERMINAL: - switch (p->device().family()) - { - case device_t::CAPACITOR: - if (!m_step_devices.contains(&p->device())) - m_step_devices.push_back(&p->device()); - break; - case device_t::BJT_EB: - case device_t::DIODE: - case device_t::LVCCS: - case device_t::BJT_SWITCH: - log().debug("found BJT/Diode/LVCCS\n"); - if (!m_dynamic_devices.contains(&p->device())) - m_dynamic_devices.push_back(&p->device()); - break; - default: - break; - } + if (p->device().is_timestep()) + if (!m_step_devices.contains(&p->device())) + m_step_devices.push_back(&p->device()); + if (p->device().is_dynamic1()) + if (!m_dynamic_devices.contains(&p->device())) + m_dynamic_devices.push_back(&p->device()); { terminal_t *pterm = dynamic_cast<terminal_t *>(p); add_term(k, pterm); } - log().debug("Added terminal\n"); + log().debug("Added terminal {1}\n", p->name()); break; case terminal_t::INPUT: { @@ -427,7 +416,7 @@ ATTR_COLD void matrix_solver_t::update() { const netlist_time new_timestep = solve(); - if (m_params.m_dynamic && is_timestep() && new_timestep > netlist_time::zero) + if (m_params.m_dynamic && has_timestep_devices() && new_timestep > netlist_time::zero) m_Q_sync.net().reschedule_in_queue(new_timestep); } @@ -435,7 +424,7 @@ ATTR_COLD void matrix_solver_t::update_forced() { ATTR_UNUSED const netlist_time new_timestep = solve(); - if (m_params.m_dynamic && is_timestep()) + if (m_params.m_dynamic && has_timestep_devices()) m_Q_sync.net().reschedule_in_queue(netlist_time::from_double(m_params.m_min_timestep)); } @@ -449,7 +438,7 @@ void matrix_solver_t::step(const netlist_time &delta) netlist_time matrix_solver_t::solve_base() { m_stat_vsolver_calls++; - if (is_dynamic()) + if (has_dynamic_devices()) { int this_resched; int newton_loops = 0; @@ -578,8 +567,8 @@ void matrix_solver_t::log_stats() log().verbose("=============================================="); log().verbose("Solver {1}", this->name()); log().verbose(" ==> {1} nets", this->m_nets.size()); //, (*(*groups[i].first())->m_core_terms.first())->name()); - log().verbose(" has {1} elements", this->is_dynamic() ? "dynamic" : "no dynamic"); - log().verbose(" has {1} elements", this->is_timestep() ? "timestep" : "no timestep"); + 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", (double) this->m_stat_newton_raphson / (double) this->m_stat_vsolver_calls); log().verbose(" {1:10} invocations ({2:6} Hz) {3:10} gs fails ({4:6.2} %) {5:6.3} average", this->m_stat_calculations, @@ -677,7 +666,7 @@ NETLIB_UPDATE(solver) { #pragma omp for for (int i = 0; i < t_cnt; i++) - if (m_mat_solvers[i]->is_timestep()) + if (m_mat_solvers[i]->has_timestep_devices()) { // Ignore return value ATTR_UNUSED const netlist_time ts = m_mat_solvers[i]->solve(); @@ -686,14 +675,14 @@ NETLIB_UPDATE(solver) } else for (int i = 0; i < t_cnt; i++) - if (m_mat_solvers[i]->is_timestep()) + if (m_mat_solvers[i]->has_timestep_devices()) { // Ignore return value ATTR_UNUSED const netlist_time ts = m_mat_solvers[i]->solve(); } #else for (auto & solver : m_mat_solvers) - if (solver->is_timestep()) + if (solver->has_timestep_devices()) // Ignore return value ATTR_UNUSED const netlist_time ts = solver->solve(); #endif @@ -910,8 +899,8 @@ ATTR_COLD void NETLIB_NAME(solver)::post_start() netlist().log().verbose("Solver {1}", ms->name()); netlist().log().verbose(" ==> {2} nets", grp.size()); - netlist().log().verbose(" has {1} elements", ms->is_dynamic() ? "dynamic" : "no dynamic"); - netlist().log().verbose(" has {1} elements", ms->is_timestep() ? "timestep" : "no timestep"); + netlist().log().verbose(" has {1} elements", ms->has_dynamic_devices() ? "dynamic" : "no dynamic"); + netlist().log().verbose(" has {1} elements", ms->has_timestep_devices() ? "timestep" : "no timestep"); for (net_t *n : grp) { netlist().log().verbose("Net {1}", n->name()); |