mirror of
https://github.com/holub/mame
synced 2025-10-05 08:41:31 +03:00
Removed netlist_input_t and net_output_t. Instead introduced
netlist_logic_t and netlist_analog_t. Afterwards refactored proxies. This enabled more flexible connection parsing. In addition, connections between two inputs are now parked and retried after all connections were made. The netlist code now correctly parses TTL_7400_DIP(XU1) RES(R1, RES_K(1)) CAP(C1, CAP_U(1)) NET_C(XU1.1, XU1.2, R1.2, C1.2) NET_C(XU1.3, XU1.4, XU1.5, R1.1) NET_C(XU1.6, C1.1) NET_C(ttllow, XU1.9, XU1.10, XU1.12, XU1.13) This failed before. (nw)
This commit is contained in:
parent
029e9a4d33
commit
f9495b9856
@ -29,9 +29,9 @@ public:
|
||||
, m_gs_fail(0)
|
||||
, m_gs_total(0)
|
||||
{
|
||||
const char *p = osd_getenv("NETLIST_STATS");
|
||||
if (p != NULL)
|
||||
m_log_stats = (bool) atoi(p);
|
||||
pstring p = nl_util::environment("NETLIST_STATS");
|
||||
if (p != "")
|
||||
m_log_stats = (bool) p.as_long();
|
||||
else
|
||||
m_log_stats = false;
|
||||
}
|
||||
|
@ -173,7 +173,6 @@ ATTR_HOT void netlist_matrix_solver_t::update_inputs()
|
||||
|
||||
}
|
||||
|
||||
|
||||
ATTR_HOT void netlist_matrix_solver_t::update_dynamic()
|
||||
{
|
||||
/* update all non-linear devices */
|
||||
@ -465,9 +464,9 @@ ATTR_COLD void NETLIB_NAME(solver)::post_start()
|
||||
}
|
||||
|
||||
// Override log statistics
|
||||
const char *p = osd_getenv("NL_STATS");
|
||||
if (p != NULL)
|
||||
m_params.m_log_stats = (bool) atoi(p);
|
||||
pstring p = nl_util::environment("NL_STATS");
|
||||
if (p != "")
|
||||
m_params.m_log_stats = (bool) p.as_long();
|
||||
else
|
||||
m_params.m_log_stats = (bool) m_log_stats.Value();
|
||||
|
||||
|
@ -58,7 +58,7 @@ NETLIB_START(4020_sub)
|
||||
|
||||
NETLIB_RESET(4020_sub)
|
||||
{
|
||||
m_IP.set_state(netlist_input_t::STATE_INP_HL);
|
||||
m_IP.set_state(netlist_logic_t::STATE_INP_HL);
|
||||
m_cnt = 0;
|
||||
}
|
||||
|
||||
|
@ -20,7 +20,7 @@ NETLIB_START(74107Asub)
|
||||
|
||||
NETLIB_RESET(74107Asub)
|
||||
{
|
||||
m_clk.set_state(netlist_input_t::STATE_INP_HL);
|
||||
m_clk.set_state(netlist_logic_t::STATE_INP_HL);
|
||||
m_Q.initial(0);
|
||||
m_QQ.initial(1);
|
||||
|
||||
|
@ -29,7 +29,7 @@ NETLIB_START(74175_sub)
|
||||
|
||||
NETLIB_RESET(74175_sub)
|
||||
{
|
||||
m_CLK.set_state(netlist_input_t::STATE_INP_LH);
|
||||
m_CLK.set_state(netlist_logic_t::STATE_INP_LH);
|
||||
m_clrq = 0;
|
||||
m_data = 0xFF;
|
||||
}
|
||||
|
@ -83,7 +83,7 @@ NETLIB_START(7474sub)
|
||||
|
||||
NETLIB_RESET(7474sub)
|
||||
{
|
||||
m_CLK.set_state(netlist_input_t::STATE_INP_LH);
|
||||
m_CLK.set_state(netlist_logic_t::STATE_INP_LH);
|
||||
|
||||
m_nextD = 0;
|
||||
/* FIXME: required by pong doubles - need a mechanism to set this from netlist */
|
||||
|
@ -48,7 +48,7 @@ NETLIB_START(7493ff)
|
||||
NETLIB_RESET(7493ff)
|
||||
{
|
||||
m_reset = 1;
|
||||
m_I.set_state(netlist_input_t::STATE_INP_HL);
|
||||
m_I.set_state(netlist_logic_t::STATE_INP_HL);
|
||||
}
|
||||
|
||||
NETLIB_UPDATE(7493ff)
|
||||
|
@ -81,7 +81,7 @@ NETLIB_START(9310_sub)
|
||||
|
||||
NETLIB_RESET(9310_sub)
|
||||
{
|
||||
m_CLK.set_state(netlist_input_t::STATE_INP_LH);
|
||||
m_CLK.set_state(netlist_logic_t::STATE_INP_LH);
|
||||
m_cnt = 0;
|
||||
m_loadq = 1;
|
||||
m_ent = 1;
|
||||
|
@ -81,7 +81,7 @@ NETLIB_START(9316_sub)
|
||||
|
||||
NETLIB_RESET(9316_sub)
|
||||
{
|
||||
m_CLK.set_state(netlist_input_t::STATE_INP_LH);
|
||||
m_CLK.set_state(netlist_logic_t::STATE_INP_LH);
|
||||
m_cnt = 0;
|
||||
m_loadq = 1;
|
||||
m_ent = 1;
|
||||
|
@ -198,19 +198,14 @@ ATTR_COLD void nld_d_to_a_proxy::reset()
|
||||
m_is_timestep = m_RV.m_P.net().as_analog().solver()->is_timestep();
|
||||
}
|
||||
|
||||
ATTR_COLD netlist_core_terminal_t &nld_d_to_a_proxy::out()
|
||||
{
|
||||
return m_RV.m_P;
|
||||
}
|
||||
|
||||
ATTR_HOT ATTR_ALIGN void nld_d_to_a_proxy::update()
|
||||
{
|
||||
const int state = INPLOGIC(m_I);
|
||||
if (state != m_last_state)
|
||||
{
|
||||
m_last_state = state;
|
||||
const nl_double R = state ? m_logic_family->m_R_high : m_logic_family->m_R_low;
|
||||
const nl_double V = state ? m_logic_family->m_high_V : m_logic_family->m_low_V;
|
||||
const nl_double R = state ? logic_family().m_R_high : logic_family().m_R_low;
|
||||
const nl_double V = state ? logic_family().m_high_V : logic_family().m_low_V;
|
||||
|
||||
// We only need to update the net first if this is a time stepping net
|
||||
if (m_is_timestep)
|
||||
|
@ -256,19 +256,49 @@ private:
|
||||
UINT8 m_last_state;
|
||||
};
|
||||
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// netdev_a_to_d
|
||||
// nld_base_proxy
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class nld_a_to_d_proxy : public netlist_device_t
|
||||
class nld_base_proxy : public netlist_device_t
|
||||
{
|
||||
public:
|
||||
ATTR_COLD nld_base_proxy(netlist_logic_t &inout_proxied, netlist_core_terminal_t &proxy_inout)
|
||||
: netlist_device_t()
|
||||
{
|
||||
m_logic_family = inout_proxied.logic_family();
|
||||
m_term_proxied = &inout_proxied;
|
||||
m_proxy_term = &proxy_inout;
|
||||
}
|
||||
|
||||
ATTR_COLD virtual ~nld_base_proxy() {}
|
||||
|
||||
ATTR_COLD netlist_logic_t &term_proxied() const { return *m_term_proxied; }
|
||||
ATTR_COLD netlist_core_terminal_t &proxy_term() const { return *m_proxy_term; }
|
||||
|
||||
protected:
|
||||
|
||||
ATTR_COLD virtual const netlist_logic_family_desc_t &logic_family() const
|
||||
{
|
||||
return *m_logic_family;
|
||||
}
|
||||
|
||||
private:
|
||||
const netlist_logic_family_desc_t *m_logic_family;
|
||||
netlist_logic_t *m_term_proxied;
|
||||
netlist_core_terminal_t *m_proxy_term;
|
||||
};
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// nld_a_to_d_proxy
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class nld_a_to_d_proxy : public nld_base_proxy
|
||||
{
|
||||
public:
|
||||
ATTR_COLD nld_a_to_d_proxy(netlist_logic_input_t &in_proxied)
|
||||
: netlist_device_t()
|
||||
: nld_base_proxy(in_proxied, m_I)
|
||||
{
|
||||
nl_assert(in_proxied.family() == LOGIC);
|
||||
m_logic_family = in_proxied.logic_family();
|
||||
}
|
||||
|
||||
ATTR_COLD virtual ~nld_a_to_d_proxy() {}
|
||||
@ -289,34 +319,32 @@ protected:
|
||||
|
||||
ATTR_HOT ATTR_ALIGN void update()
|
||||
{
|
||||
if (m_I.Q_Analog() > m_logic_family->m_high_thresh_V)
|
||||
if (m_I.Q_Analog() > logic_family().m_high_thresh_V)
|
||||
OUTLOGIC(m_Q, 1, NLTIME_FROM_NS(1));
|
||||
else if (m_I.Q_Analog() < m_logic_family->m_low_thresh_V)
|
||||
else if (m_I.Q_Analog() < logic_family().m_low_thresh_V)
|
||||
OUTLOGIC(m_Q, 0, NLTIME_FROM_NS(1));
|
||||
//else
|
||||
// OUTLOGIC(m_Q, m_Q.net().last_Q(), NLTIME_FROM_NS(1));
|
||||
else
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
}
|
||||
private:
|
||||
const netlist_logic_family_desc_t *m_logic_family;
|
||||
};
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// nld_base_d_to_a_proxy
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class nld_base_d_to_a_proxy : public netlist_device_t
|
||||
class nld_base_d_to_a_proxy : public nld_base_proxy
|
||||
{
|
||||
public:
|
||||
ATTR_COLD nld_base_d_to_a_proxy(netlist_logic_output_t &out_proxied)
|
||||
: netlist_device_t()
|
||||
ATTR_COLD nld_base_d_to_a_proxy(netlist_logic_output_t &out_proxied, netlist_core_terminal_t &proxy_out)
|
||||
: nld_base_proxy(out_proxied, proxy_out)
|
||||
{
|
||||
nl_assert(out_proxied.family() == LOGIC);
|
||||
m_logic_family = out_proxied.logic_family();
|
||||
}
|
||||
|
||||
ATTR_COLD virtual ~nld_base_d_to_a_proxy() {}
|
||||
|
||||
ATTR_COLD virtual netlist_core_terminal_t &out() = 0;
|
||||
ATTR_COLD virtual netlist_logic_input_t &in() { return m_I; }
|
||||
|
||||
protected:
|
||||
@ -325,60 +353,16 @@ protected:
|
||||
register_input("I", m_I);
|
||||
}
|
||||
|
||||
ATTR_COLD virtual const netlist_logic_family_desc_t *logic_family()
|
||||
{
|
||||
return m_logic_family;
|
||||
}
|
||||
|
||||
const netlist_logic_family_desc_t *m_logic_family;
|
||||
|
||||
netlist_logic_input_t m_I;
|
||||
|
||||
private:
|
||||
};
|
||||
|
||||
#if 0
|
||||
class nld_d_to_a_proxy : public nld_base_d_to_a_proxy
|
||||
{
|
||||
public:
|
||||
ATTR_COLD nld_d_to_a_proxy(netlist_output_t &out_proxied)
|
||||
: nld_base_d_to_a_proxy(out_proxied)
|
||||
{
|
||||
}
|
||||
|
||||
ATTR_COLD virtual ~nld_d_to_a_proxy() {}
|
||||
|
||||
protected:
|
||||
ATTR_COLD void start()
|
||||
{
|
||||
nld_base_d_to_a_proxy::start();
|
||||
register_output("Q", m_Q);
|
||||
}
|
||||
|
||||
ATTR_COLD void reset()
|
||||
{
|
||||
//m_Q.initial(0);
|
||||
}
|
||||
|
||||
ATTR_COLD virtual netlist_core_terminal_t &out()
|
||||
{
|
||||
return m_Q;
|
||||
}
|
||||
|
||||
ATTR_HOT ATTR_ALIGN void update()
|
||||
{
|
||||
OUTANALOG(m_Q, INPLOGIC(m_I) ? m_logic_family->m_high_V : m_logic_family->m_low_V, NLTIME_FROM_NS(1));
|
||||
}
|
||||
|
||||
private:
|
||||
netlist_analog_output_t m_Q;
|
||||
};
|
||||
#else
|
||||
class nld_d_to_a_proxy : public nld_base_d_to_a_proxy
|
||||
{
|
||||
public:
|
||||
ATTR_COLD nld_d_to_a_proxy(netlist_logic_output_t &out_proxied)
|
||||
: nld_base_d_to_a_proxy(out_proxied)
|
||||
: nld_base_d_to_a_proxy(out_proxied, m_RV.m_P)
|
||||
, m_RV(TWOTERM)
|
||||
, m_last_state(-1)
|
||||
, m_is_timestep(false)
|
||||
@ -392,8 +376,6 @@ protected:
|
||||
|
||||
ATTR_COLD virtual void reset();
|
||||
|
||||
ATTR_COLD virtual netlist_core_terminal_t &out();
|
||||
|
||||
ATTR_HOT ATTR_ALIGN void update();
|
||||
|
||||
private:
|
||||
@ -402,6 +384,5 @@ private:
|
||||
int m_last_state;
|
||||
bool m_is_timestep;
|
||||
};
|
||||
#endif
|
||||
|
||||
#endif /* NLD_SYSTEM_H_ */
|
||||
|
@ -11,8 +11,6 @@
|
||||
#include "pstring.h"
|
||||
#include "nl_util.h"
|
||||
|
||||
#include <stdlib.h> // FIXME: only included for atof
|
||||
|
||||
const netlist_time netlist_time::zero = netlist_time::from_raw(0);
|
||||
|
||||
class netlist_logic_family_ttl_t : public netlist_logic_family_desc_t
|
||||
@ -161,7 +159,6 @@ ATTR_COLD void netlist_owned_object_t::init_object(netlist_core_device_t &dev,
|
||||
netlist_base_t::netlist_base_t()
|
||||
: netlist_object_t(NETLIST, GENERIC),
|
||||
m_stop(netlist_time::zero),
|
||||
// FIXME:: Use a parameter to set this on a schematics per schematics basis
|
||||
m_time(netlist_time::zero),
|
||||
m_queue(*this),
|
||||
m_use_deactivate(0),
|
||||
@ -429,7 +426,7 @@ ATTR_COLD void netlist_core_device_t::stop_dev()
|
||||
|
||||
ATTR_HOT ATTR_ALIGN netlist_sig_t netlist_core_device_t::INPLOGIC_PASSIVE(netlist_logic_input_t &inp)
|
||||
{
|
||||
if (inp.state() != netlist_input_t::STATE_INP_PASSIVE)
|
||||
if (inp.state() != netlist_logic_t::STATE_INP_PASSIVE)
|
||||
return inp.Q();
|
||||
else
|
||||
{
|
||||
@ -476,7 +473,7 @@ ATTR_COLD void netlist_device_t::init(netlist_base_t &anetlist, const pstring &n
|
||||
ATTR_COLD void netlist_device_t::register_sub(const pstring &name, netlist_device_t &dev)
|
||||
{
|
||||
dev.init(netlist(), this->name() + "." + name);
|
||||
// FIXME: subdevices always first inherit the logic family of the parent
|
||||
// subdevices always first inherit the logic family of the parent
|
||||
dev.set_logic_family(this->logic_family());
|
||||
dev.start_dev();
|
||||
}
|
||||
@ -505,7 +502,7 @@ ATTR_COLD void netlist_device_t::register_output(const pstring &name, netlist_lo
|
||||
setup().register_object(*this, name, port);
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_device_t::register_output(const pstring &name, netlist_output_t &port)
|
||||
ATTR_COLD void netlist_device_t::register_output(const pstring &name, netlist_analog_output_t &port)
|
||||
{
|
||||
//port.set_logic_family(this->logic_family());
|
||||
setup().register_object(*this, name, port);
|
||||
@ -518,7 +515,7 @@ ATTR_COLD void netlist_device_t::register_input(const pstring &name, netlist_log
|
||||
m_terminals.add(inp.name());
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_device_t::register_input(const pstring &name, netlist_input_t &inp)
|
||||
ATTR_COLD void netlist_device_t::register_input(const pstring &name, netlist_analog_input_t &inp)
|
||||
{
|
||||
//inp.set_logic_family(this->logic_family());
|
||||
setup().register_object(*this, name, inp);
|
||||
@ -527,7 +524,9 @@ ATTR_COLD void netlist_device_t::register_input(const pstring &name, netlist_inp
|
||||
|
||||
ATTR_COLD void netlist_device_t::connect(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2)
|
||||
{
|
||||
setup().connect(t1, t2);
|
||||
/* FIXME: These should really first be collected like NET_C connects */
|
||||
if (!setup().connect(t1, t2))
|
||||
netlist().error("Error connecting %s to %s\n", t1.name().cstr(), t2.name().cstr());
|
||||
}
|
||||
|
||||
|
||||
@ -614,7 +613,7 @@ ATTR_HOT void netlist_net_t::dec_active(netlist_core_terminal_t &term)
|
||||
railterminal().netdev().dec_active();
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_net_t::register_railterminal(netlist_output_t &mr)
|
||||
ATTR_COLD void netlist_net_t::register_railterminal(netlist_core_terminal_t &mr)
|
||||
{
|
||||
nl_assert(m_railterminal == NULL);
|
||||
m_railterminal = &mr;
|
||||
@ -626,7 +625,7 @@ ATTR_COLD void netlist_net_t::rebuild_list()
|
||||
|
||||
m_list_active.clear();
|
||||
for (int i=0; i < m_core_terms.count(); i++)
|
||||
if (m_core_terms[i]->state() != netlist_input_t::STATE_INP_PASSIVE)
|
||||
if (m_core_terms[i]->state() != netlist_logic_t::STATE_INP_PASSIVE)
|
||||
m_list_active.add(*m_core_terms[i]);
|
||||
}
|
||||
|
||||
@ -663,31 +662,11 @@ ATTR_HOT /*ATTR_ALIGN*/ inline void netlist_net_t::update_devs()
|
||||
|
||||
netlist_core_terminal_t *p = m_list_active.first();
|
||||
|
||||
#if 0
|
||||
switch (m_active)
|
||||
{
|
||||
case 2:
|
||||
p->update_dev(mask);
|
||||
p = m_list_active.next(p);
|
||||
case 1:
|
||||
p->update_dev(mask);
|
||||
break;
|
||||
default:
|
||||
while (p != NULL)
|
||||
{
|
||||
p->update_dev(mask);
|
||||
p = m_list_active.next(p);
|
||||
}
|
||||
break;
|
||||
}
|
||||
#else
|
||||
while (p != NULL)
|
||||
{
|
||||
p->update_dev(mask);
|
||||
p = m_list_active.next(p);
|
||||
}
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_net_t::reset()
|
||||
@ -710,7 +689,7 @@ ATTR_COLD void netlist_net_t::reset()
|
||||
m_core_terms[i]->do_reset();
|
||||
|
||||
for (int i=0; i < m_core_terms.count(); i++)
|
||||
if (m_core_terms[i]->state() != netlist_input_t::STATE_INP_PASSIVE)
|
||||
if (m_core_terms[i]->state() != netlist_logic_t::STATE_INP_PASSIVE)
|
||||
m_active++;
|
||||
}
|
||||
|
||||
@ -720,7 +699,7 @@ ATTR_COLD void netlist_net_t::register_con(netlist_core_terminal_t &terminal)
|
||||
|
||||
m_core_terms.add(&terminal);
|
||||
|
||||
if (terminal.state() != netlist_input_t::STATE_INP_PASSIVE)
|
||||
if (terminal.state() != netlist_logic_t::STATE_INP_PASSIVE)
|
||||
m_active++;
|
||||
}
|
||||
|
||||
@ -909,51 +888,50 @@ ATTR_COLD void netlist_terminal_t::save_register()
|
||||
// net_output_t
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
netlist_output_t::netlist_output_t(const type_t atype, const family_t afamily)
|
||||
: netlist_core_terminal_t(atype, afamily)
|
||||
{
|
||||
set_state(STATE_OUT);
|
||||
}
|
||||
|
||||
ATTR_COLD netlist_output_t::~netlist_output_t()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
ATTR_COLD void netlist_output_t::init_object(netlist_core_device_t &dev, const pstring &aname)
|
||||
{
|
||||
netlist_core_terminal_t::init_object(dev, aname);
|
||||
net().init_object(dev.netlist(), aname + ".net");
|
||||
net().register_railterminal(*this);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
// netlist_logic_output_t
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
ATTR_COLD netlist_logic_output_t::netlist_logic_output_t()
|
||||
: netlist_output_t(OUTPUT, LOGIC), netlist_logic_family_t(), m_proxy(NULL)
|
||||
: netlist_logic_t(OUTPUT)
|
||||
{
|
||||
set_state(STATE_OUT);
|
||||
this->set_net(m_my_net);
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_logic_output_t::init_object(netlist_core_device_t &dev, const pstring &aname)
|
||||
{
|
||||
netlist_core_terminal_t::init_object(dev, aname);
|
||||
net().init_object(dev.netlist(), aname + ".net");
|
||||
net().register_railterminal(*this);
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_logic_output_t::initial(const netlist_sig_t val)
|
||||
{
|
||||
net().as_logic().initial(val);
|
||||
}
|
||||
|
||||
|
||||
// ----------------------------------------------------------------------------------------
|
||||
// netlist_analog_output_t
|
||||
// ----------------------------------------------------------------------------------------
|
||||
|
||||
ATTR_COLD netlist_analog_output_t::netlist_analog_output_t()
|
||||
: netlist_output_t(OUTPUT, ANALOG), m_proxied_net(NULL)
|
||||
: netlist_analog_t(OUTPUT), m_proxied_net(NULL)
|
||||
{
|
||||
this->set_net(m_my_net);
|
||||
set_state(STATE_OUT);
|
||||
|
||||
net().as_analog().m_cur_Analog = 0.98;
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_analog_output_t::init_object(netlist_core_device_t &dev, const pstring &aname)
|
||||
{
|
||||
netlist_core_terminal_t::init_object(dev, aname);
|
||||
net().init_object(dev.netlist(), aname + ".net");
|
||||
net().register_railterminal(*this);
|
||||
}
|
||||
|
||||
ATTR_COLD void netlist_analog_output_t::initial(const nl_double val)
|
||||
{
|
||||
// FIXME: Really necessary?
|
||||
@ -1039,7 +1017,7 @@ ATTR_COLD nl_double netlist_param_model_t::model_value(const pstring &entity, co
|
||||
}
|
||||
if (factor != NL_FCONST(1.0))
|
||||
tmp = tmp.left(tmp.len() - 1);
|
||||
return (nl_double) atof(tmp.cstr()) * factor;
|
||||
return tmp.as_double() * factor;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -263,7 +263,6 @@ ATTR_COLD virtual const netlist_logic_family_desc_t *default_logic_family()
|
||||
class netlist_net_t;
|
||||
class netlist_analog_net_t;
|
||||
class netlist_logic_net_t;
|
||||
class netlist_output_t;
|
||||
class netlist_logic_output_t;
|
||||
class netlist_param_t;
|
||||
class netlist_setup_t;
|
||||
@ -273,7 +272,7 @@ class NETLIB_NAME(gnd);
|
||||
class NETLIB_NAME(solver);
|
||||
class NETLIB_NAME(mainclock);
|
||||
class NETLIB_NAME(netlistparams);
|
||||
class NETLIB_NAME(base_d_to_a_proxy);
|
||||
class NETLIB_NAME(base_proxy);
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// netlist_output_family_t
|
||||
@ -530,27 +529,39 @@ private:
|
||||
// netlist_input_t
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class netlist_input_t : public netlist_core_terminal_t
|
||||
class netlist_logic_t : public netlist_core_terminal_t, public netlist_logic_family_t
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
ATTR_COLD netlist_input_t(const type_t atype, const family_t afamily)
|
||||
: netlist_core_terminal_t(atype, afamily)
|
||||
ATTR_COLD netlist_logic_t(const type_t atype)
|
||||
: netlist_core_terminal_t(atype, LOGIC), netlist_logic_family_t(),
|
||||
m_proxy(NULL)
|
||||
{
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
|
||||
ATTR_HOT inline void inactivate();
|
||||
ATTR_HOT inline void activate();
|
||||
ATTR_COLD bool has_proxy() const { return (m_proxy != NULL); }
|
||||
ATTR_COLD nld_base_proxy *get_proxy() const { return m_proxy; }
|
||||
ATTR_COLD void set_proxy(nld_base_proxy *proxy) { m_proxy = proxy; }
|
||||
|
||||
protected:
|
||||
ATTR_COLD virtual void reset()
|
||||
|
||||
private:
|
||||
nld_base_proxy *m_proxy;
|
||||
};
|
||||
|
||||
class netlist_analog_t : public netlist_core_terminal_t
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
ATTR_COLD netlist_analog_t(const type_t atype)
|
||||
: netlist_core_terminal_t(atype, ANALOG)
|
||||
{
|
||||
//netlist_core_terminal_t::reset();
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
private:
|
||||
};
|
||||
|
||||
@ -558,33 +569,53 @@ private:
|
||||
// netlist_logic_input_t
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class netlist_logic_input_t : public netlist_input_t, public netlist_logic_family_t
|
||||
class netlist_logic_input_t : public netlist_logic_t
|
||||
{
|
||||
public:
|
||||
ATTR_COLD netlist_logic_input_t()
|
||||
: netlist_input_t(INPUT, LOGIC), netlist_logic_family_t()
|
||||
: netlist_logic_t(INPUT)
|
||||
{
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
|
||||
ATTR_HOT inline netlist_sig_t Q() const;
|
||||
ATTR_HOT inline netlist_sig_t last_Q() const;
|
||||
|
||||
ATTR_HOT inline void inactivate();
|
||||
ATTR_HOT inline void activate();
|
||||
ATTR_HOT inline void activate_hl();
|
||||
ATTR_HOT inline void activate_lh();
|
||||
|
||||
protected:
|
||||
ATTR_COLD virtual void reset()
|
||||
{
|
||||
//netlist_core_terminal_t::reset();
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// netlist_analog_input_t
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class netlist_analog_input_t : public netlist_input_t
|
||||
class netlist_analog_input_t : public netlist_analog_t
|
||||
{
|
||||
public:
|
||||
ATTR_COLD netlist_analog_input_t()
|
||||
: netlist_input_t(INPUT, ANALOG) { }
|
||||
: netlist_analog_t(INPUT)
|
||||
{
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
|
||||
ATTR_HOT inline nl_double Q_Analog() const;
|
||||
|
||||
protected:
|
||||
ATTR_COLD virtual void reset()
|
||||
{
|
||||
//netlist_core_terminal_t::reset();
|
||||
set_state(STATE_INP_ACTIVE);
|
||||
}
|
||||
};
|
||||
|
||||
//#define INPVAL(_x) (_x).Q()
|
||||
@ -607,7 +638,7 @@ public:
|
||||
|
||||
ATTR_COLD void register_con(netlist_core_terminal_t &terminal);
|
||||
ATTR_COLD void merge_net(netlist_net_t *othernet);
|
||||
ATTR_COLD void register_railterminal(netlist_output_t &mr);
|
||||
ATTR_COLD void register_railterminal(netlist_core_terminal_t &mr);
|
||||
|
||||
ATTR_HOT inline netlist_logic_net_t & RESTRICT as_logic();
|
||||
ATTR_HOT inline const netlist_logic_net_t & RESTRICT as_logic() const;
|
||||
@ -621,7 +652,7 @@ public:
|
||||
ATTR_HOT inline void set_time(const netlist_time &ntime) { m_time = ntime; }
|
||||
|
||||
ATTR_HOT inline bool isRailNet() const { return !(m_railterminal == NULL); }
|
||||
ATTR_HOT inline const netlist_core_terminal_t & RESTRICT railterminal() const { return *m_railterminal; }
|
||||
ATTR_HOT inline netlist_core_terminal_t & railterminal() const { return *m_railterminal; }
|
||||
|
||||
ATTR_HOT inline void push_to_queue(const netlist_time &delay);
|
||||
ATTR_HOT inline void reschedule_in_queue(const netlist_time &delay);
|
||||
@ -783,13 +814,12 @@ public:
|
||||
// net_output_t
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
class netlist_output_t : public netlist_core_terminal_t
|
||||
class netlist_logic_output_t : public netlist_logic_t
|
||||
{
|
||||
NETLIST_PREVENT_COPYING(netlist_output_t)
|
||||
NETLIST_PREVENT_COPYING(netlist_logic_output_t)
|
||||
public:
|
||||
|
||||
ATTR_COLD netlist_output_t(const type_t atype, const family_t afamily);
|
||||
ATTR_COLD virtual ~netlist_output_t();
|
||||
ATTR_COLD netlist_logic_output_t();
|
||||
|
||||
ATTR_COLD void init_object(netlist_core_device_t &dev, const pstring &aname);
|
||||
ATTR_COLD virtual void reset()
|
||||
@ -797,17 +827,6 @@ public:
|
||||
set_state(STATE_OUT);
|
||||
}
|
||||
|
||||
private:
|
||||
};
|
||||
|
||||
|
||||
class netlist_logic_output_t : public netlist_output_t, public netlist_logic_family_t
|
||||
{
|
||||
NETLIST_PREVENT_COPYING(netlist_logic_output_t)
|
||||
public:
|
||||
|
||||
ATTR_COLD netlist_logic_output_t();
|
||||
|
||||
ATTR_COLD void initial(const netlist_sig_t val);
|
||||
|
||||
ATTR_HOT inline void set_Q(const netlist_sig_t newQ, const netlist_time &delay)
|
||||
@ -815,22 +834,23 @@ public:
|
||||
net().as_logic().set_Q(newQ, delay);
|
||||
}
|
||||
|
||||
ATTR_COLD bool has_proxy() const { return (m_proxy != NULL); }
|
||||
ATTR_COLD nld_base_d_to_a_proxy *get_proxy() const { return m_proxy; }
|
||||
ATTR_COLD void set_proxy(nld_base_d_to_a_proxy *proxy) { m_proxy = proxy; }
|
||||
|
||||
private:
|
||||
netlist_logic_net_t m_my_net;
|
||||
nld_base_d_to_a_proxy *m_proxy;
|
||||
};
|
||||
|
||||
class netlist_analog_output_t : public netlist_output_t
|
||||
class netlist_analog_output_t : public netlist_analog_t
|
||||
{
|
||||
NETLIST_PREVENT_COPYING(netlist_analog_output_t)
|
||||
public:
|
||||
|
||||
ATTR_COLD netlist_analog_output_t();
|
||||
|
||||
ATTR_COLD void init_object(netlist_core_device_t &dev, const pstring &aname);
|
||||
ATTR_COLD virtual void reset()
|
||||
{
|
||||
set_state(STATE_OUT);
|
||||
}
|
||||
|
||||
ATTR_COLD void initial(const nl_double val);
|
||||
|
||||
ATTR_HOT inline void set_Q(const nl_double newQ);
|
||||
@ -993,7 +1013,7 @@ public:
|
||||
|
||||
ATTR_HOT inline netlist_sig_t INPLOGIC(const netlist_logic_input_t &inp) const
|
||||
{
|
||||
nl_assert(inp.state() != netlist_input_t::STATE_INP_PASSIVE);
|
||||
nl_assert(inp.state() != netlist_logic_t::STATE_INP_PASSIVE);
|
||||
return inp.Q();
|
||||
}
|
||||
|
||||
@ -1062,9 +1082,9 @@ public:
|
||||
ATTR_COLD void register_sub(const pstring &name, netlist_device_t &dev);
|
||||
ATTR_COLD void register_subalias(const pstring &name, netlist_core_terminal_t &term);
|
||||
ATTR_COLD void register_terminal(const pstring &name, netlist_terminal_t &port);
|
||||
ATTR_COLD void register_output(const pstring &name, netlist_output_t &out);
|
||||
ATTR_COLD void register_output(const pstring &name, netlist_analog_output_t &out);
|
||||
ATTR_COLD void register_output(const pstring &name, netlist_logic_output_t &out);
|
||||
ATTR_COLD void register_input(const pstring &name, netlist_input_t &in);
|
||||
ATTR_COLD void register_input(const pstring &name, netlist_analog_input_t &in);
|
||||
ATTR_COLD void register_input(const pstring &name, netlist_logic_input_t &in);
|
||||
|
||||
ATTR_COLD void connect(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2);
|
||||
@ -1167,7 +1187,6 @@ public:
|
||||
template<class _C>
|
||||
_C *get_first_device()
|
||||
{
|
||||
//FIXME:
|
||||
for (netlist_device_t * const *entry = m_devices.first(); entry != NULL; entry = m_devices.next(entry))
|
||||
{
|
||||
_C *dev = dynamic_cast<_C *>(*entry);
|
||||
@ -1296,7 +1315,7 @@ ATTR_HOT inline const netlist_analog_net_t & RESTRICT netlist_net_t::as_analog()
|
||||
}
|
||||
|
||||
|
||||
ATTR_HOT inline void netlist_input_t::inactivate()
|
||||
ATTR_HOT inline void netlist_logic_input_t::inactivate()
|
||||
{
|
||||
if (EXPECTED(!is_state(STATE_INP_PASSIVE)))
|
||||
{
|
||||
@ -1305,7 +1324,7 @@ ATTR_HOT inline void netlist_input_t::inactivate()
|
||||
}
|
||||
}
|
||||
|
||||
ATTR_HOT inline void netlist_input_t::activate()
|
||||
ATTR_HOT inline void netlist_logic_input_t::activate()
|
||||
{
|
||||
if (is_state(STATE_INP_PASSIVE))
|
||||
{
|
||||
|
@ -12,11 +12,6 @@
|
||||
#include "nl_config.h"
|
||||
#include "plists.h"
|
||||
#include "nl_base.h"
|
||||
#if 0
|
||||
#include "nl_time.h"
|
||||
#include "nl_util.h"
|
||||
#include "pstate.h"
|
||||
#endif
|
||||
#include "pstring.h"
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
@ -15,9 +15,6 @@
|
||||
#include "analog/nld_solver.h"
|
||||
#include "analog/nld_twoterm.h"
|
||||
|
||||
//FIXME: we need a nl_getenv
|
||||
#include <stdlib.h>
|
||||
|
||||
static NETLIST_START(base)
|
||||
TTL_INPUT(ttlhigh, 1)
|
||||
TTL_INPUT(ttllow, 0)
|
||||
@ -193,7 +190,14 @@ void netlist_setup_t::register_object(netlist_device_t &dev, const pstring &name
|
||||
{
|
||||
netlist_core_terminal_t &term = dynamic_cast<netlist_core_terminal_t &>(obj);
|
||||
if (obj.isType(netlist_terminal_t::OUTPUT))
|
||||
dynamic_cast<netlist_output_t &>(term).init_object(dev, dev.name() + "." + name);
|
||||
{
|
||||
if (obj.isFamily(netlist_terminal_t::LOGIC))
|
||||
dynamic_cast<netlist_logic_output_t &>(term).init_object(dev, dev.name() + "." + name);
|
||||
else if (obj.isFamily(netlist_terminal_t::ANALOG))
|
||||
dynamic_cast<netlist_analog_output_t &>(term).init_object(dev, dev.name() + "." + name);
|
||||
else
|
||||
netlist().error("Error adding %s %s to terminal list, neither LOGIC nor ANALOG\n", objtype_as_astr(term).cstr(), term.name().cstr());
|
||||
}
|
||||
else
|
||||
term.init_object(dev, dev.name() + "." + name);
|
||||
|
||||
@ -389,23 +393,24 @@ netlist_param_t *netlist_setup_t::find_param(const pstring ¶m_in, bool requi
|
||||
return ret;
|
||||
}
|
||||
|
||||
nld_base_d_to_a_proxy *netlist_setup_t::get_d_a_proxy(netlist_output_t &out)
|
||||
// FIXME avoid dynamic cast here
|
||||
nld_base_proxy *netlist_setup_t::get_d_a_proxy(netlist_core_terminal_t &out)
|
||||
{
|
||||
nl_assert(out.isFamily(netlist_terminal_t::LOGIC));
|
||||
|
||||
//printf("proxy for %s\n", out.name().cstr());;
|
||||
netlist_logic_output_t &out_cast = dynamic_cast<netlist_logic_output_t &>(out);
|
||||
nld_base_d_to_a_proxy *proxy = out_cast.get_proxy();
|
||||
nld_base_proxy *proxy = out_cast.get_proxy();
|
||||
|
||||
if (proxy == NULL)
|
||||
{
|
||||
// create a new one ...
|
||||
proxy = out_cast.logic_family()->create_d_a_proxy(out_cast);
|
||||
nld_base_d_to_a_proxy *new_proxy = out_cast.logic_family()->create_d_a_proxy(out_cast);
|
||||
pstring x = pstring::sprintf("proxy_da_%s_%d", out.name().cstr(), m_proxy_cnt);
|
||||
m_proxy_cnt++;
|
||||
|
||||
register_dev(proxy, x);
|
||||
proxy->start_dev();
|
||||
register_dev(new_proxy, x);
|
||||
new_proxy->start_dev();
|
||||
|
||||
#if 1
|
||||
/* connect all existing terminals to new net */
|
||||
@ -414,23 +419,25 @@ nld_base_d_to_a_proxy *netlist_setup_t::get_d_a_proxy(netlist_output_t &out)
|
||||
{
|
||||
netlist_core_terminal_t *p = out.net().m_core_terms[i];
|
||||
p->clear_net(); // de-link from all nets ...
|
||||
connect(proxy->out(), *p);
|
||||
if (!connect(new_proxy->proxy_term(), *p))
|
||||
netlist().error("Error connecting %s to %s\n", new_proxy->proxy_term().name().cstr(), (*p).name().cstr());
|
||||
}
|
||||
out.net().m_core_terms.clear(); // clear the list
|
||||
#endif
|
||||
out.net().register_con(proxy->in());
|
||||
out_cast.set_proxy(proxy);
|
||||
|
||||
out.net().register_con(new_proxy->in());
|
||||
out_cast.set_proxy(new_proxy);
|
||||
proxy = new_proxy;
|
||||
}
|
||||
return proxy;
|
||||
}
|
||||
|
||||
void netlist_setup_t::connect_input_output(netlist_input_t &in, netlist_output_t &out)
|
||||
void netlist_setup_t::connect_input_output(netlist_core_terminal_t &in, netlist_core_terminal_t &out)
|
||||
{
|
||||
if (out.isFamily(netlist_terminal_t::ANALOG) && in.isFamily(netlist_terminal_t::LOGIC))
|
||||
{
|
||||
netlist_logic_input_t &incast = dynamic_cast<netlist_logic_input_t &>(in);
|
||||
nld_a_to_d_proxy *proxy = nl_alloc(nld_a_to_d_proxy, incast);
|
||||
incast.set_proxy(proxy);
|
||||
pstring x = pstring::sprintf("proxy_ad_%s_%d", in.name().cstr(), m_proxy_cnt);
|
||||
m_proxy_cnt++;
|
||||
|
||||
@ -443,9 +450,9 @@ void netlist_setup_t::connect_input_output(netlist_input_t &in, netlist_output_t
|
||||
}
|
||||
else if (out.isFamily(netlist_terminal_t::LOGIC) && in.isFamily(netlist_terminal_t::ANALOG))
|
||||
{
|
||||
nld_base_d_to_a_proxy *proxy = get_d_a_proxy(out);
|
||||
nld_base_proxy *proxy = get_d_a_proxy(out);
|
||||
|
||||
connect_terminals(proxy->out(), in);
|
||||
connect_terminals(proxy->proxy_term(), in);
|
||||
//proxy->out().net().register_con(in);
|
||||
}
|
||||
else
|
||||
@ -457,7 +464,8 @@ void netlist_setup_t::connect_input_output(netlist_input_t &in, netlist_output_t
|
||||
}
|
||||
}
|
||||
|
||||
void netlist_setup_t::connect_terminal_input(netlist_terminal_t &term, netlist_input_t &inp)
|
||||
|
||||
void netlist_setup_t::connect_terminal_input(netlist_terminal_t &term, netlist_core_terminal_t &inp)
|
||||
{
|
||||
if (inp.isFamily(netlist_terminal_t::ANALOG))
|
||||
{
|
||||
@ -468,6 +476,7 @@ void netlist_setup_t::connect_terminal_input(netlist_terminal_t &term, netlist_i
|
||||
netlist_logic_input_t &incast = dynamic_cast<netlist_logic_input_t &>(inp);
|
||||
NL_VERBOSE_OUT(("connect_terminal_input: connecting proxy\n"));
|
||||
nld_a_to_d_proxy *proxy = nl_alloc(nld_a_to_d_proxy, incast);
|
||||
incast.set_proxy(proxy);
|
||||
pstring x = pstring::sprintf("proxy_ad_%s_%d", inp.name().cstr(), m_proxy_cnt);
|
||||
m_proxy_cnt++;
|
||||
|
||||
@ -488,7 +497,7 @@ void netlist_setup_t::connect_terminal_input(netlist_terminal_t &term, netlist_i
|
||||
}
|
||||
}
|
||||
|
||||
void netlist_setup_t::connect_terminal_output(netlist_terminal_t &in, netlist_output_t &out)
|
||||
void netlist_setup_t::connect_terminal_output(netlist_terminal_t &in, netlist_core_terminal_t &out)
|
||||
{
|
||||
if (out.isFamily(netlist_terminal_t::ANALOG))
|
||||
{
|
||||
@ -502,9 +511,9 @@ void netlist_setup_t::connect_terminal_output(netlist_terminal_t &in, netlist_ou
|
||||
else if (out.isFamily(netlist_terminal_t::LOGIC))
|
||||
{
|
||||
NL_VERBOSE_OUT(("connect_terminal_output: connecting proxy\n"));
|
||||
nld_base_d_to_a_proxy *proxy = get_d_a_proxy(out);
|
||||
nld_base_proxy *proxy = get_d_a_proxy(out);
|
||||
|
||||
connect_terminals(proxy->out(), in);
|
||||
connect_terminals(proxy->proxy_term(), in);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -547,55 +556,92 @@ void netlist_setup_t::connect_terminals(netlist_core_terminal_t &t1, netlist_cor
|
||||
|
||||
static netlist_core_terminal_t &resolve_proxy(netlist_core_terminal_t &term)
|
||||
{
|
||||
if (term.isType(netlist_core_terminal_t::OUTPUT) && term.isFamily(netlist_core_terminal_t::LOGIC))
|
||||
if (term.isFamily(netlist_core_terminal_t::LOGIC))
|
||||
{
|
||||
netlist_logic_output_t &out = dynamic_cast<netlist_logic_output_t &>(term);
|
||||
netlist_logic_t &out = dynamic_cast<netlist_logic_t &>(term);
|
||||
if (out.has_proxy())
|
||||
return out.get_proxy()->out();
|
||||
return out.get_proxy()->proxy_term();
|
||||
}
|
||||
return term;
|
||||
}
|
||||
|
||||
void netlist_setup_t::connect(netlist_core_terminal_t &t1_in, netlist_core_terminal_t &t2_in)
|
||||
bool netlist_setup_t::connect_input_input(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2)
|
||||
{
|
||||
bool ret = false;
|
||||
if (t1.has_net())
|
||||
{
|
||||
for (int i=0; i<t1.net().m_core_terms.count(); i++)
|
||||
{
|
||||
if (t1.net().m_core_terms[i]->isType(netlist_core_terminal_t::TERMINAL)
|
||||
|| t1.net().m_core_terms[i]->isType(netlist_core_terminal_t::OUTPUT))
|
||||
ret = connect(t2, *t1.net().m_core_terms[i]);
|
||||
if (ret)
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!ret && t2.has_net())
|
||||
{
|
||||
for (int i=0; i<t2.net().m_core_terms.count(); i++)
|
||||
{
|
||||
if (t2.net().m_core_terms[i]->isType(netlist_core_terminal_t::TERMINAL)
|
||||
|| t2.net().m_core_terms[i]->isType(netlist_core_terminal_t::OUTPUT))
|
||||
ret = connect(t1, *t2.net().m_core_terms[i]);
|
||||
if (ret)
|
||||
break;
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool netlist_setup_t::connect(netlist_core_terminal_t &t1_in, netlist_core_terminal_t &t2_in)
|
||||
{
|
||||
NL_VERBOSE_OUT(("Connecting %s to %s\n", t1_in.name().cstr(), t2_in.name().cstr()));
|
||||
netlist_core_terminal_t &t1 = resolve_proxy(t1_in);
|
||||
netlist_core_terminal_t &t2 = resolve_proxy(t2_in);
|
||||
bool ret = true;
|
||||
|
||||
if (t1.isType(netlist_core_terminal_t::OUTPUT) && t2.isType(netlist_core_terminal_t::INPUT))
|
||||
{
|
||||
if (t2.has_net() && t2.net().isRailNet())
|
||||
netlist().error("Input %s already connected\n", t2.name().cstr());
|
||||
connect_input_output(dynamic_cast<netlist_input_t &>(t2), dynamic_cast<netlist_output_t &>(t1));
|
||||
connect_input_output(t2, t1);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::INPUT) && t2.isType(netlist_core_terminal_t::OUTPUT))
|
||||
{
|
||||
if (t1.has_net() && t1.net().isRailNet())
|
||||
netlist().error("Input %s already connected\n", t1.name().cstr());
|
||||
connect_input_output(dynamic_cast<netlist_input_t &>(t1), dynamic_cast<netlist_output_t &>(t2));
|
||||
connect_input_output(t1, t2);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::OUTPUT) && t2.isType(netlist_core_terminal_t::TERMINAL))
|
||||
{
|
||||
connect_terminal_output(dynamic_cast<netlist_terminal_t &>(t2), dynamic_cast<netlist_output_t &>(t1));
|
||||
connect_terminal_output(dynamic_cast<netlist_terminal_t &>(t2), t1);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::TERMINAL) && t2.isType(netlist_core_terminal_t::OUTPUT))
|
||||
{
|
||||
connect_terminal_output(dynamic_cast<netlist_terminal_t &>(t1), dynamic_cast<netlist_output_t &>(t2));
|
||||
connect_terminal_output(dynamic_cast<netlist_terminal_t &>(t1), t2);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::INPUT) && t2.isType(netlist_core_terminal_t::TERMINAL))
|
||||
{
|
||||
connect_terminal_input(dynamic_cast<netlist_terminal_t &>(t2), dynamic_cast<netlist_input_t &>(t1));
|
||||
connect_terminal_input(dynamic_cast<netlist_terminal_t &>(t2), t1);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::TERMINAL) && t2.isType(netlist_core_terminal_t::INPUT))
|
||||
{
|
||||
connect_terminal_input(dynamic_cast<netlist_terminal_t &>(t1), dynamic_cast<netlist_input_t &>(t2));
|
||||
connect_terminal_input(dynamic_cast<netlist_terminal_t &>(t1), t2);
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::TERMINAL) && t2.isType(netlist_core_terminal_t::TERMINAL))
|
||||
{
|
||||
connect_terminals(dynamic_cast<netlist_terminal_t &>(t1), dynamic_cast<netlist_terminal_t &>(t2));
|
||||
}
|
||||
else if (t1.isType(netlist_core_terminal_t::INPUT) && t2.isType(netlist_core_terminal_t::INPUT))
|
||||
{
|
||||
ret = connect_input_input(t1, t2);
|
||||
}
|
||||
else
|
||||
netlist().error("Connecting %s to %s not supported!\n", t1.name().cstr(), t2.name().cstr());
|
||||
ret = false;
|
||||
//netlist().error("Connecting %s to %s not supported!\n", t1.name().cstr(), t2.name().cstr());
|
||||
return ret;
|
||||
}
|
||||
|
||||
void netlist_setup_t::resolve_inputs()
|
||||
@ -604,23 +650,40 @@ void netlist_setup_t::resolve_inputs()
|
||||
|
||||
netlist().log("Resolving inputs ...");
|
||||
|
||||
for (const link_t *entry = m_links.first(); entry != NULL; entry = m_links.next(entry))
|
||||
/* Netlist can directly connect input to input.
|
||||
* We therefore first park connecting inputs and retry
|
||||
* after all other terminals were connected.
|
||||
*/
|
||||
int tries = 100;
|
||||
while (m_links.count() > 0 && tries > 0) // FIXME: convert into constant
|
||||
{
|
||||
const pstring t1s = entry->e1;
|
||||
const pstring t2s = entry->e2;
|
||||
netlist_core_terminal_t *t1 = find_terminal(t1s);
|
||||
netlist_core_terminal_t *t2 = find_terminal(t2s);
|
||||
int li = 0;
|
||||
while (li < m_links.count())
|
||||
{
|
||||
const pstring t1s = m_links[li].e1;
|
||||
const pstring t2s = m_links[li].e2;
|
||||
netlist_core_terminal_t *t1 = find_terminal(t1s);
|
||||
netlist_core_terminal_t *t2 = find_terminal(t2s);
|
||||
|
||||
connect(*t1, *t2);
|
||||
if (connect(*t1, *t2))
|
||||
{
|
||||
printf("%s and %s connected\n", t1s.cstr(), t2s.cstr());
|
||||
m_links.remove_at(li);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("%s and %s failed\n", t1s.cstr(), t2s.cstr());
|
||||
li++;
|
||||
}
|
||||
}
|
||||
tries--;
|
||||
}
|
||||
|
||||
//netlist().log("printing outputs ...");
|
||||
/* print all outputs */
|
||||
for (int i = 0; i < m_terminals.count(); i++)
|
||||
if (tries == 0)
|
||||
{
|
||||
ATTR_UNUSED netlist_output_t *out = dynamic_cast<netlist_output_t *>(m_terminals[i]);
|
||||
//if (out != NULL)
|
||||
//VERBOSE_OUT(("%s %d\n", out->netdev()->name(), *out->Q_ptr()));
|
||||
for (int i = 0; i < m_links.count(); i++ )
|
||||
netlist().warning("Error connecting %s to %s\n", m_links[i].e1.cstr(), m_links[i].e2.cstr());
|
||||
|
||||
netlist().error("Error connecting -- bailing out\n");
|
||||
}
|
||||
|
||||
netlist().log("deleting empty nets ...");
|
||||
@ -637,12 +700,7 @@ void netlist_setup_t::resolve_inputs()
|
||||
}
|
||||
else
|
||||
{
|
||||
#if 0
|
||||
for (netlist_core_terminal_t *p = (*pn)->m_list.first(); p != NULL; p = (*pn)->m_list.next(p))
|
||||
(*pn)->m_registered.add(p);
|
||||
#else
|
||||
(*pn)->rebuild_list();
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
@ -698,11 +756,12 @@ void netlist_setup_t::resolve_inputs()
|
||||
|
||||
void netlist_setup_t::start_devices()
|
||||
{
|
||||
//FIXME: we need a nl_getenv
|
||||
if (getenv("NL_LOGS"))
|
||||
pstring env = nl_util::environment("NL_LOGS");
|
||||
|
||||
if (env != "")
|
||||
{
|
||||
NL_VERBOSE_OUT(("Creating dynamic logs ...\n"));
|
||||
nl_util::pstring_list ll = nl_util::split(getenv("NL_LOGS"), ":");
|
||||
nl_util::pstring_list ll = nl_util::split(env, ":");
|
||||
for (int i=0; i < ll.count(); i++)
|
||||
{
|
||||
NL_VERBOSE_OUT(("%d: <%s>\n",i, ll[i].cstr()));
|
||||
|
@ -129,7 +129,7 @@ public:
|
||||
void register_param(const pstring ¶m, const double value);
|
||||
|
||||
void register_object(netlist_device_t &dev, const pstring &name, netlist_object_t &obj);
|
||||
void connect(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2);
|
||||
bool connect(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2);
|
||||
|
||||
netlist_core_terminal_t *find_terminal(const pstring &outname_in, bool required = true);
|
||||
netlist_core_terminal_t *find_terminal(const pstring &outname_in, netlist_object_t::type_t atype, bool required = true);
|
||||
@ -175,15 +175,16 @@ private:
|
||||
|
||||
|
||||
void connect_terminals(netlist_core_terminal_t &in, netlist_core_terminal_t &out);
|
||||
void connect_input_output(netlist_input_t &in, netlist_output_t &out);
|
||||
void connect_terminal_output(netlist_terminal_t &in, netlist_output_t &out);
|
||||
void connect_terminal_input(netlist_terminal_t &term, netlist_input_t &inp);
|
||||
void connect_input_output(netlist_core_terminal_t &in, netlist_core_terminal_t &out);
|
||||
void connect_terminal_output(netlist_terminal_t &in, netlist_core_terminal_t &out);
|
||||
void connect_terminal_input(netlist_terminal_t &term, netlist_core_terminal_t &inp);
|
||||
bool connect_input_input(netlist_core_terminal_t &t1, netlist_core_terminal_t &t2);
|
||||
|
||||
// helpers
|
||||
pstring objtype_as_astr(netlist_object_t &in) const;
|
||||
|
||||
const pstring resolve_alias(const pstring &name) const;
|
||||
nld_base_d_to_a_proxy *get_d_a_proxy(netlist_output_t &out);
|
||||
nld_base_proxy *get_d_a_proxy(netlist_core_terminal_t &out);
|
||||
};
|
||||
|
||||
#endif /* NLSETUP_H_ */
|
||||
|
@ -45,6 +45,13 @@ public:
|
||||
}
|
||||
return temp;
|
||||
}
|
||||
static const pstring environment(const pstring &var, const pstring &default_val = "")
|
||||
{
|
||||
if (getenv(var.cstr()) == NULL)
|
||||
return default_val;
|
||||
else
|
||||
return pstring(getenv(var.cstr()));
|
||||
}
|
||||
};
|
||||
|
||||
class nl_math
|
||||
|
@ -85,8 +85,7 @@ struct options_entry oplist[] =
|
||||
{ "logs;l", "", OPTION_STRING, "colon separated list of terminals to log" },
|
||||
{ "file;f", "-", OPTION_STRING, "file to process (default is stdin)" },
|
||||
{ "cmd;c", "run", OPTION_STRING, "run|convert|listdevices" },
|
||||
{ "listdevices;ld", "", OPTION_BOOLEAN, "list all devices available for use" },
|
||||
{ "verbose;v", "0", OPTION_BOOLEAN, "list all devices available for use" },
|
||||
{ "verbose;v", "0", OPTION_BOOLEAN, "be verbose - this produces lots of output" },
|
||||
{ "help;h", "0", OPTION_BOOLEAN, "display help" },
|
||||
{ NULL, NULL, 0, NULL }
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user