summaryrefslogtreecommitdiffstatshomepage
path: root/src/lib/netlist/nl_parser.cpp
diff options
context:
space:
mode:
author couriersud <couriersud@users.noreply.github.com>2022-06-10 16:11:21 +0200
committer GitHub <noreply@github.com>2022-06-10 16:11:21 +0200
commit1f3f5e0d574e256bc106ee4bc9ee701858585ca3 (patch)
treee471112c27fccd862215cf2c460d5471d546de86 /src/lib/netlist/nl_parser.cpp
parent63e595ae364a6f9e6b3692af673d1a0c48523f2d (diff)
netlist: fix bugs and more cpp instead of macros (#9897)
* netlist: fix bugs and more cpp instead of macros - C-style comments converted to c++ - Fix crash in state saving code when an abort queue processing event is pending. - Fix a bug where a net could be twice in the queue. - Convert more macros to c++ - fixed SUBTARGET=nl build - fixed potential bugs which would allow a terminal to belong to more than one net. This is not possible even for a short time. - moved some member function definitions out-of-class. - moved code out-of-class - added constexpr where appropriate - fixed mamenl build - Cleanup and indentation
Diffstat (limited to 'src/lib/netlist/nl_parser.cpp')
-rw-r--r--src/lib/netlist/nl_parser.cpp964
1 files changed, 481 insertions, 483 deletions
diff --git a/src/lib/netlist/nl_parser.cpp b/src/lib/netlist/nl_parser.cpp
index 507ecea0aa7..02c7d11f2b2 100644
--- a/src/lib/netlist/nl_parser.cpp
+++ b/src/lib/netlist/nl_parser.cpp
@@ -8,577 +8,575 @@
namespace netlist
{
-// ----------------------------------------------------------------------------------------
-// A netlist parser
-// ----------------------------------------------------------------------------------------
+ // ----------------------------------------------------------------------------------------
+ // A netlist parser
+ // ----------------------------------------------------------------------------------------
-void parser_t::verror(const pstring &msg)
-{
- m_setup.log().fatal("{1}", msg);
- throw nl_exception(plib::pfmt("{1}")(msg));
-}
+ void parser_t::verror(const pstring &msg)
+ {
+ m_setup.log().fatal("{1}", msg);
+ throw nl_exception(plib::pfmt("{1}")(msg));
+ }
-parser_t::parser_t(nlparse_t &setup)
- : m_setup(setup)
- , m_cur_local(nullptr)
-{
- m_tokenizer.identifier_chars("abcdefghijklmnopqrstuvwvxyzABCDEFGHIJKLMNOPQRSTUVWXYZ01234567890_.-$@")
- .number_chars(".0123456789", "0123456789eE-.") //FIXME: processing of numbers
- .whitespace(pstring("") + ' ' + static_cast<char>(9) + static_cast<char>(10) + static_cast<char>(13))
- .comment("/*", "*/", "//");
- m_tok_paren_left = m_tokenizer.register_token("(");
- m_tok_paren_right = m_tokenizer.register_token(")");
- m_tok_comma = m_tokenizer.register_token(",");
-
- m_tok_static = m_tokenizer.register_token("static");
- m_tok_ALIAS = m_tokenizer.register_token("ALIAS");
- m_tok_DIPPINS = m_tokenizer.register_token("DIPPINS");
- m_tok_NET_C = m_tokenizer.register_token("NET_C");
- m_tok_FRONTIER = m_tokenizer.register_token("OPTIMIZE_FRONTIER");
- m_tok_PARAM = m_tokenizer.register_token("PARAM");
- m_tok_DEFPARAM = m_tokenizer.register_token("DEFPARAM");
- m_tok_HINT = m_tokenizer.register_token("HINT");
- m_tok_NET_MODEL = m_tokenizer.register_token("NET_MODEL");
- m_tok_NET_REGISTER_DEV = m_tokenizer.register_token("NET_REGISTER_DEV");
- m_tok_INCLUDE = m_tokenizer.register_token("INCLUDE");
- m_tok_LOCAL_SOURCE = m_tokenizer.register_token("LOCAL_SOURCE");
- m_tok_LOCAL_LIB_ENTRY = m_tokenizer.register_token("LOCAL_LIB_ENTRY");
- m_tok_EXTERNAL_LIB_ENTRY = m_tokenizer.register_token("EXTERNAL_LIB_ENTRY");
- m_tok_SUBMODEL = m_tokenizer.register_token("SUBMODEL");
- m_tok_NETLIST_START = m_tokenizer.register_token("NETLIST_START");
- m_tok_NETLIST_END = m_tokenizer.register_token("NETLIST_END");
- m_tok_NETLIST_EXTERNAL = m_tokenizer.register_token("NETLIST_EXTERNAL");
- m_tok_EXTERNAL_SOURCE = m_tokenizer.register_token("EXTERNAL_SOURCE");
- m_tok_TRUTHTABLE_START = m_tokenizer.register_token("TRUTHTABLE_START");
- m_tok_TRUTHTABLE_END = m_tokenizer.register_token("TRUTHTABLE_END");
- m_tok_TRUTHTABLE_ENTRY = m_tokenizer.register_token("TRUTHTABLE_ENTRY");
- m_tok_TT_HEAD = m_tokenizer.register_token("TT_HEAD");
- m_tok_TT_LINE = m_tokenizer.register_token("TT_LINE");
- m_tok_TT_FAMILY = m_tokenizer.register_token("TT_FAMILY");
-
- m_tokenizer.register_token("RES_R");
- m_tokenizer.register_token("RES_K");
- m_tokenizer.register_token("RES_M");
- m_tokenizer.register_token("CAP_U");
- m_tokenizer.register_token("CAP_N");
- m_tokenizer.register_token("CAP_P");
-
-}
-
-bool parser_t::parse(plib::istream_uptr &&strm, const pstring &nlname)
-{
- token_store_t tokstor;
- parse_tokens(std::move(strm), tokstor);
- return parse(tokstor, nlname);
-}
+ parser_t::parser_t(nlparse_t &setup)
+ : m_setup(setup)
+ , m_cur_local(nullptr)
+ {
+ m_tokenizer.identifier_chars("abcdefghijklmnopqrstuvwvxyzABCDEFGHIJKLMNOPQRSTUVWXYZ01234567890_.-$@")
+ .number_chars(".0123456789", "0123456789eE-.") //FIXME: processing of numbers
+ .whitespace(pstring("") + ' ' + static_cast<char>(9) + static_cast<char>(10) + static_cast<char>(13))
+ .comment("/*", "*/", "//");
+ m_tok_paren_left = m_tokenizer.register_token("(");
+ m_tok_paren_right = m_tokenizer.register_token(")");
+ m_tok_comma = m_tokenizer.register_token(",");
+
+ m_tok_static = m_tokenizer.register_token("static");
+ m_tok_ALIAS = m_tokenizer.register_token("ALIAS");
+ m_tok_DIPPINS = m_tokenizer.register_token("DIPPINS");
+ m_tok_NET_C = m_tokenizer.register_token("NET_C");
+ m_tok_FRONTIER = m_tokenizer.register_token("OPTIMIZE_FRONTIER");
+ m_tok_PARAM = m_tokenizer.register_token("PARAM");
+ m_tok_DEFPARAM = m_tokenizer.register_token("DEFPARAM");
+ m_tok_HINT = m_tokenizer.register_token("HINT");
+ m_tok_NET_MODEL = m_tokenizer.register_token("NET_MODEL");
+ m_tok_NET_REGISTER_DEV = m_tokenizer.register_token("NET_REGISTER_DEV");
+ m_tok_INCLUDE = m_tokenizer.register_token("INCLUDE");
+ m_tok_LOCAL_SOURCE = m_tokenizer.register_token("LOCAL_SOURCE");
+ m_tok_LOCAL_LIB_ENTRY = m_tokenizer.register_token("LOCAL_LIB_ENTRY");
+ m_tok_EXTERNAL_LIB_ENTRY = m_tokenizer.register_token("EXTERNAL_LIB_ENTRY");
+ m_tok_SUBMODEL = m_tokenizer.register_token("SUBMODEL");
+ m_tok_NETLIST_START = m_tokenizer.register_token("NETLIST_START");
+ m_tok_NETLIST_END = m_tokenizer.register_token("NETLIST_END");
+ m_tok_NETLIST_EXTERNAL = m_tokenizer.register_token("NETLIST_EXTERNAL");
+ m_tok_EXTERNAL_SOURCE = m_tokenizer.register_token("EXTERNAL_SOURCE");
+ m_tok_TRUTHTABLE_START = m_tokenizer.register_token("TRUTHTABLE_START");
+ m_tok_TRUTHTABLE_END = m_tokenizer.register_token("TRUTHTABLE_END");
+ m_tok_TRUTHTABLE_ENTRY = m_tokenizer.register_token("TRUTHTABLE_ENTRY");
+ m_tok_TT_HEAD = m_tokenizer.register_token("TT_HEAD");
+ m_tok_TT_LINE = m_tokenizer.register_token("TT_LINE");
+ m_tok_TT_FAMILY = m_tokenizer.register_token("TT_FAMILY");
+
+ m_tokenizer.register_token("RES_R");
+ m_tokenizer.register_token("RES_K");
+ m_tokenizer.register_token("RES_M");
+ m_tokenizer.register_token("CAP_U");
+ m_tokenizer.register_token("CAP_N");
+ m_tokenizer.register_token("CAP_P");
-void parser_t::parse_tokens(plib::istream_uptr &&strm, token_store_t &tokstor)
-{
- plib::putf8_reader u8reader(strm.release_stream());
- m_tokenizer.append_to_store(&u8reader, tokstor);
-}
+ }
-bool parser_t::parse(const token_store_t &tokstor, const pstring &nlname)
-{
- set_token_source(&tokstor);
+ bool parser_t::parse(plib::istream_uptr &&strm, const pstring &nlname)
+ {
+ token_store_t tokstor;
+ parse_tokens(std::move(strm), tokstor);
+ return parse(tokstor, nlname);
+ }
- bool in_nl = false;
+ void parser_t::parse_tokens(plib::istream_uptr &&strm, token_store_t &tokstor)
+ {
+ plib::putf8_reader u8reader(strm.release_stream());
+ m_tokenizer.append_to_store(&u8reader, tokstor);
+ }
- while (true)
+ bool parser_t::parse(const token_store_t &tokstor, const pstring &nlname)
{
- // FIXME: line numbers in cached local netlists are wrong
- // need to process raw tokens here.
- token_t token = get_token_raw();
- if (token.is_type(token_type::ENDOFFILE))
- {
- return false;
- }
+ set_token_source(&tokstor);
+
+ bool in_nl = false;
- if (token.is(m_tok_NETLIST_END) || token.is(m_tok_TRUTHTABLE_END))
+ while (true)
{
- if (!in_nl)
- error (MF_PARSER_UNEXPECTED_1(token.str()));
- else
+ // FIXME: line numbers in cached local netlists are wrong
+ // need to process raw tokens here.
+ token_t token = get_token_raw();
+ if (token.is_type(token_type::ENDOFFILE))
{
- in_nl = false;
+ return false;
}
- require_token(m_tok_paren_left);
- require_token(m_tok_paren_right);
- m_cur_local->push_back(token);
- m_cur_local->push_back(token_t(m_tok_paren_left));
- m_cur_local->push_back(token_t(m_tok_paren_right));
+ if (token.is(m_tok_NETLIST_END) || token.is(m_tok_TRUTHTABLE_END))
+ {
+ if (!in_nl)
+ error (MF_PARSER_UNEXPECTED_1(token.str()));
+ else
+ {
+ in_nl = false;
+ }
+ require_token(m_tok_paren_left);
+ require_token(m_tok_paren_right);
+
+ m_cur_local->push_back(token);
+ m_cur_local->push_back(token_t(m_tok_paren_left));
+ m_cur_local->push_back(token_t(m_tok_paren_right));
- }
- else if (token.is(m_tok_NETLIST_START) || token.is(m_tok_TRUTHTABLE_START))
- {
- if (in_nl)
- error (MF_PARSER_UNEXPECTED_1(token.str()));
- require_token(m_tok_paren_left);
- token_t name = get_token();
- if (token.is(m_tok_NETLIST_START) && (name.str() == nlname || nlname.empty()))
+ }
+ else if (token.is(m_tok_NETLIST_START) || token.is(m_tok_TRUTHTABLE_START))
+ {
+ if (in_nl)
+ error (MF_PARSER_UNEXPECTED_1(token.str()));
+ require_token(m_tok_paren_left);
+ token_t name = get_token();
+ if (token.is(m_tok_NETLIST_START) && (name.str() == nlname || nlname.empty()))
+ {
+ require_token(m_tok_paren_right);
+ parse_netlist();
+ return true;
+ }
+ if (token.is(m_tok_TRUTHTABLE_START) && name.str() == nlname)
+ {
+ net_truth_table_start(nlname);
+ return true;
+ }
+
+ // create a new cached local store
+ m_local.emplace(name.str(), token_store_t());
+ m_cur_local = &m_local[name.str()];
+ auto sl = location();
+ auto li = plib::pfmt("# {1} \"{2}\"")(sl.line(), sl.file_name());
+
+ m_cur_local->push_back(token_t(token_type::LINEMARKER, li));
+ m_cur_local->push_back(token);
+ m_cur_local->push_back(token_t(m_tok_paren_left));
+ m_cur_local->push_back(name);
+ //m_cur_local->push_back(token_t(m_tok_paren_right));
+ in_nl = true;
+ }
+ // FIXME: do we really need this going forward ? there should be no need
+ // for NETLIST_EXTERNAL in netlist files
+ else if (token.is(m_tok_NETLIST_EXTERNAL))
{
+ if (in_nl)
+ error (MF_UNEXPECTED_NETLIST_EXTERNAL());
+ require_token(m_tok_paren_left);
+ token_t name = get_token();
require_token(m_tok_paren_right);
- parse_netlist();
- return true;
}
- if (token.is(m_tok_TRUTHTABLE_START) && name.str() == nlname)
+ else if (!in_nl)
{
- net_truth_table_start(nlname);
- return true;
+ if (!token.is(m_tok_static) && !token.is_type(token_type::SOURCELINE)
+ && !token.is_type(token_type::LINEMARKER))
+ error(MF_EXPECTED_NETLIST_START_1(token.str()));
+ }
+ else
+ {
+ m_cur_local->push_back(token);
}
-
- // create a new cached local store
- m_local.emplace(name.str(), token_store_t());
- m_cur_local = &m_local[name.str()];
- auto sl = location();
- auto li = plib::pfmt("# {1} \"{2}\"")(sl.line(), sl.file_name());
-
- m_cur_local->push_back(token_t(token_type::LINEMARKER, li));
- m_cur_local->push_back(token);
- m_cur_local->push_back(token_t(m_tok_paren_left));
- m_cur_local->push_back(name);
- //m_cur_local->push_back(token_t(m_tok_paren_right));
- in_nl = true;
- }
- // FIXME: do we really need this going forward ? there should be no need
- // for NETLIST_EXTERNAL in netlist files
- else if (token.is(m_tok_NETLIST_EXTERNAL))
- {
- if (in_nl)
- error (MF_UNEXPECTED_NETLIST_EXTERNAL());
- require_token(m_tok_paren_left);
- token_t name = get_token();
- require_token(m_tok_paren_right);
- }
- else if (!in_nl)
- {
- if (!token.is(m_tok_static) && !token.is_type(token_type::SOURCELINE)
- && !token.is_type(token_type::LINEMARKER))
- error(MF_EXPECTED_NETLIST_START_1(token.str()));
- }
- else
- {
- m_cur_local->push_back(token);
}
}
-}
-void parser_t::parse_netlist()
-{
- while (true)
+ void parser_t::parse_netlist()
{
- token_t token = get_token();
-
- if (token.is_type(token_type::ENDOFFILE))
- error (MF_UNEXPECTED_END_OF_FILE());
-
- m_setup.log().debug("Parser: Device: {1}\n", token.str());
-
- if (token.is(m_tok_ALIAS))
- net_alias();
- else if (token.is(m_tok_DIPPINS))
- dip_pins();
- else if (token.is(m_tok_NET_C))
- net_c();
- else if (token.is(m_tok_FRONTIER))
- frontier();
- else if (token.is(m_tok_PARAM))
- netdev_param();
- else if (token.is(m_tok_DEFPARAM))
- netdev_default_param();
- else if (token.is(m_tok_HINT))
- netdev_hint();
- else if (token.is(m_tok_NET_MODEL))
- net_model();
- else if (token.is(m_tok_SUBMODEL))
- net_sub_model();
- else if (token.is(m_tok_INCLUDE))
- net_include();
- else if (token.is(m_tok_LOCAL_SOURCE))
- net_local_source();
- else if (token.is(m_tok_EXTERNAL_SOURCE))
- net_external_source();
- else if (token.is(m_tok_LOCAL_LIB_ENTRY))
- net_lib_entry(true);
- else if (token.is(m_tok_EXTERNAL_LIB_ENTRY))
- net_lib_entry(false);
- else if (token.is(m_tok_TRUTHTABLE_ENTRY))
- {
- require_token(m_tok_paren_left);
- pstring name(get_identifier());
- register_local_as_source(name);
- m_setup.include(name);
- require_token(m_tok_paren_right);
- }
- else if (token.is(m_tok_NET_REGISTER_DEV))
- {
- net_register_dev();
- }
- else if (token.is(m_tok_NETLIST_END))
+ while (true)
{
- netdev_netlist_end();
- return;
+ token_t token = get_token();
+
+ if (token.is_type(token_type::ENDOFFILE))
+ error (MF_UNEXPECTED_END_OF_FILE());
+
+ m_setup.log().debug("Parser: Device: {1}\n", token.str());
+
+ if (token.is(m_tok_ALIAS))
+ net_alias();
+ else if (token.is(m_tok_DIPPINS))
+ dip_pins();
+ else if (token.is(m_tok_NET_C))
+ net_c();
+ else if (token.is(m_tok_FRONTIER))
+ frontier();
+ else if (token.is(m_tok_PARAM))
+ netdev_param();
+ else if (token.is(m_tok_DEFPARAM))
+ netdev_default_param();
+ else if (token.is(m_tok_HINT))
+ netdev_hint();
+ else if (token.is(m_tok_NET_MODEL))
+ net_model();
+ else if (token.is(m_tok_SUBMODEL))
+ net_sub_model();
+ else if (token.is(m_tok_INCLUDE))
+ net_include();
+ else if (token.is(m_tok_LOCAL_SOURCE))
+ net_local_source();
+ else if (token.is(m_tok_EXTERNAL_SOURCE))
+ net_external_source();
+ else if (token.is(m_tok_LOCAL_LIB_ENTRY))
+ net_lib_entry(true);
+ else if (token.is(m_tok_EXTERNAL_LIB_ENTRY))
+ net_lib_entry(false);
+ else if (token.is(m_tok_TRUTHTABLE_ENTRY))
+ {
+ require_token(m_tok_paren_left);
+ pstring name(get_identifier());
+ register_local_as_source(name);
+ m_setup.include(name);
+ require_token(m_tok_paren_right);
+ }
+ else if (token.is(m_tok_NET_REGISTER_DEV))
+ {
+ net_register_dev();
+ }
+ else if (token.is(m_tok_NETLIST_END))
+ {
+ netdev_netlist_end();
+ return;
+ }
+ else if (!token.is_type(token_type::IDENTIFIER))
+ error(MF_EXPECTED_IDENTIFIER_GOT_1(token.str()));
+ else
+ device(token.str());
}
- else if (!token.is_type(token_type::IDENTIFIER))
- error(MF_EXPECTED_IDENTIFIER_GOT_1(token.str()));
- else
- device(token.str());
}
-}
-void parser_t::net_lib_entry(bool is_local)
-{
- require_token(m_tok_paren_left);
- pstring name(get_identifier());
+ void parser_t::net_lib_entry(bool is_local)
+ {
+ require_token(m_tok_paren_left);
+ pstring name(get_identifier());
- if (is_local)
- register_local_as_source(name);
- else if (m_local.find(name) != m_local.end())
- error(MF_EXTERNAL_SOURCE_IS_LOCAL_1(name));
+ if (is_local)
+ register_local_as_source(name);
+ else if (m_local.find(name) != m_local.end())
+ error(MF_EXTERNAL_SOURCE_IS_LOCAL_1(name));
- // FIXME: Need to pass in parameter definition FIXME: get line number right
- m_setup.register_lib_entry(name, "", location());
- require_token(m_tok_paren_right);
-}
+ // FIXME: Need to pass in parameter definition FIXME: get line number right
+ m_setup.register_lib_entry(name, "", location());
+ require_token(m_tok_paren_right);
+ }
-void parser_t::net_truth_table_start(const pstring &nlname)
-{
- bool head_found(false);
-
- // parse remaining parameters
- require_token(m_tok_comma);
- long ni = get_number_long();
- require_token(m_tok_comma);
- long no = get_number_long();
- require_token(m_tok_comma);
- pstring def_param = get_string();
- require_token(m_tok_paren_right);
-
- netlist::tt_desc desc;
- desc.name = nlname;
- desc.ni = gsl::narrow<unsigned long>(ni);
- desc.no = gsl::narrow<unsigned long>(no);
- desc.family = "";
-
- while (true)
+ void parser_t::net_truth_table_start(const pstring &nlname)
{
- token_t token = get_token();
+ bool head_found(false);
+
+ // parse remaining parameters
+ require_token(m_tok_comma);
+ long ni = get_number_long();
+ require_token(m_tok_comma);
+ long no = get_number_long();
+ require_token(m_tok_comma);
+ pstring def_param = get_string();
+ require_token(m_tok_paren_right);
- if (token.is(m_tok_TT_HEAD))
- {
- require_token(m_tok_paren_left);
- desc.desc.push_back(get_string());
- require_token(m_tok_paren_right);
- head_found = true;
- }
- else if (token.is(m_tok_TT_LINE))
- {
- if (!head_found)
- error(MF_TT_LINE_WITHOUT_HEAD());
- require_token(m_tok_paren_left);
- desc.desc.push_back(get_string());
- require_token(m_tok_paren_right);
- }
- else if (token.is(m_tok_TT_FAMILY))
- {
- require_token(m_tok_paren_left);
- desc.family = get_string();
- require_token(m_tok_paren_right);
- }
- else
+ netlist::tt_desc desc;
+ desc.name = nlname;
+ desc.ni = gsl::narrow<unsigned long>(ni);
+ desc.no = gsl::narrow<unsigned long>(no);
+ desc.family = "";
+
+ while (true)
{
- require_token(token, m_tok_TRUTHTABLE_END);
- require_token(m_tok_paren_left);
- require_token(m_tok_paren_right);
- // FIXME: proper location
- m_setup.truth_table_create(desc, def_param, location());
- return;
+ token_t token = get_token();
+
+ if (token.is(m_tok_TT_HEAD))
+ {
+ require_token(m_tok_paren_left);
+ desc.desc.push_back(get_string());
+ require_token(m_tok_paren_right);
+ head_found = true;
+ }
+ else if (token.is(m_tok_TT_LINE))
+ {
+ if (!head_found)
+ error(MF_TT_LINE_WITHOUT_HEAD());
+ require_token(m_tok_paren_left);
+ desc.desc.push_back(get_string());
+ require_token(m_tok_paren_right);
+ }
+ else if (token.is(m_tok_TT_FAMILY))
+ {
+ require_token(m_tok_paren_left);
+ desc.family = get_string();
+ require_token(m_tok_paren_right);
+ }
+ else
+ {
+ require_token(token, m_tok_TRUTHTABLE_END);
+ require_token(m_tok_paren_left);
+ require_token(m_tok_paren_right);
+ // FIXME: proper location
+ m_setup.truth_table_create(desc, def_param, location());
+ return;
+ }
}
}
-}
-void parser_t::netdev_netlist_end()
-{
- // don't do much
- require_token(m_tok_paren_left);
- require_token(m_tok_paren_right);
-}
-
-void parser_t::net_model()
-{
- require_token(m_tok_paren_left);
- pstring model = get_string();
- m_setup.register_model(model);
- require_token(m_tok_paren_right);
-}
+ void parser_t::netdev_netlist_end()
+ {
+ // don't do much
+ require_token(m_tok_paren_left);
+ require_token(m_tok_paren_right);
+ }
-void parser_t::net_sub_model()
-{
- require_token(m_tok_paren_left);
- pstring model(get_identifier());
- require_token(m_tok_comma);
- pstring name = get_identifier();
- require_token(m_tok_paren_right);
-
- m_setup.namespace_push(name);
- m_setup.include(model);
- m_setup.namespace_pop();
-}
-
-void parser_t::frontier()
-{
- require_token(m_tok_paren_left);
- // don't do much
- pstring attachat = get_identifier();
- require_token(m_tok_comma);
- auto tok = get_token();
- auto r_IN = stringify_expression(tok);
- require_token(tok, m_tok_comma);
- tok = get_token();
- auto r_OUT = stringify_expression(tok);
- require_token(tok, m_tok_paren_right);
-
- m_setup.register_frontier(attachat, r_IN, r_OUT);
-}
-
-void parser_t::net_include()
-{
- require_token(m_tok_paren_left);
- pstring name(get_identifier());
- require_token(m_tok_paren_right);
+ void parser_t::net_model()
+ {
+ require_token(m_tok_paren_left);
+ pstring model = get_string();
+ m_setup.register_model(model);
+ require_token(m_tok_paren_right);
+ }
- m_setup.include(name);
-}
+ void parser_t::net_sub_model()
+ {
+ require_token(m_tok_paren_left);
+ pstring model(get_identifier());
+ require_token(m_tok_comma);
+ pstring name = get_identifier();
+ require_token(m_tok_paren_right);
-void parser_t::net_local_source()
-{
- // This directive is only for hardcoded netlists. Ignore it here.
- require_token(m_tok_paren_left);
- pstring name(get_identifier());
- require_token(m_tok_paren_right);
+ m_setup.namespace_push(name);
+ m_setup.include(model);
+ m_setup.namespace_pop();
+ }
- register_local_as_source(name);
-}
+ void parser_t::frontier()
+ {
+ require_token(m_tok_paren_left);
+ // don't do much
+ pstring attach_at = get_identifier();
+ require_token(m_tok_comma);
+ auto tok = get_token();
+ auto r_IN = stringify_expression(tok);
+ require_token(tok, m_tok_comma);
+ tok = get_token();
+ auto r_OUT = stringify_expression(tok);
+ require_token(tok, m_tok_paren_right);
-void parser_t::register_local_as_source(const pstring &name)
-{
- auto p = m_local.find(name);
- if (p != m_local.end())
- m_setup.register_source<source_token_t>(name, p->second);
- else
- error(MF_LOCAL_SOURCE_NOT_FOUND_1(name));
-}
-
-void parser_t::net_external_source()
-{
- // This directive is only for hardcoded netlists. Ignore it here.
- require_token(m_tok_paren_left);
- pstring name(get_identifier());
- require_token(m_tok_paren_right);
+ m_setup.register_frontier(attach_at, r_IN, r_OUT);
+ }
-}
+ void parser_t::net_include()
+ {
+ require_token(m_tok_paren_left);
+ pstring name(get_identifier());
+ require_token(m_tok_paren_right);
-void parser_t::net_alias()
-{
- require_token(m_tok_paren_left);
- pstring alias = get_identifier_or_number();
+ m_setup.include(name);
+ }
- require_token(m_tok_comma);
+ void parser_t::net_local_source()
+ {
+ // This directive is only for hardcoded netlists. Ignore it here.
+ require_token(m_tok_paren_left);
+ pstring name(get_identifier());
+ require_token(m_tok_paren_right);
- pstring out = get_identifier();
+ register_local_as_source(name);
+ }
- require_token(m_tok_paren_right);
+ void parser_t::register_local_as_source(const pstring &name)
+ {
+ auto p = m_local.find(name);
+ if (p != m_local.end())
+ m_setup.register_source<source_token_t>(name, p->second);
+ else
+ error(MF_LOCAL_SOURCE_NOT_FOUND_1(name));
+ }
- m_setup.log().debug("Parser: Alias: {1} {2}\n", alias, out);
- m_setup.register_alias(alias, out);
-}
+ void parser_t::net_external_source()
+ {
+ // This directive is only for hardcoded netlists. Ignore it here.
+ require_token(m_tok_paren_left);
+ pstring name(get_identifier());
+ require_token(m_tok_paren_right);
-void parser_t::net_c()
-{
- require_token(m_tok_paren_left);
- pstring first = get_identifier();
- require_token(m_tok_comma);
+ }
- while (true)
+ void parser_t::net_alias()
{
- pstring t1 = get_identifier();
- m_setup.register_link(first , t1);
- m_setup.log().debug("Parser: Connect: {1} {2}\n", first, t1);
- token_t n = get_token();
- if (n.is(m_tok_paren_right))
- break;
- if (!n.is(m_tok_comma))
- error(MF_EXPECTED_COMMA_OR_RP_1(n.str()));
- }
+ require_token(m_tok_paren_left);
+ pstring alias = get_identifier_or_number();
-}
+ require_token(m_tok_comma);
-void parser_t::dip_pins()
-{
- std::vector<pstring> pins;
+ pstring out = get_identifier();
- require_token(m_tok_paren_left);
- pins.push_back(get_identifier());
- require_token(m_tok_comma);
+ require_token(m_tok_paren_right);
- while (true)
+ m_setup.log().debug("Parser: Alias: {1} {2}\n", alias, out);
+ m_setup.register_alias(alias, out);
+ }
+
+ void parser_t::net_c()
{
- pstring t1 = get_identifier();
- pins.push_back(t1);
- token_t n = get_token();
- if (n.is(m_tok_paren_right))
- break;
- if (!n.is(m_tok_comma))
- error(MF_EXPECTED_COMMA_OR_RP_1(n.str()));
+ require_token(m_tok_paren_left);
+ pstring first = get_identifier();
+ require_token(m_tok_comma);
+
+ while (true)
+ {
+ pstring t1 = get_identifier();
+ m_setup.register_link(first , t1);
+ m_setup.log().debug("Parser: Connect: {1} {2}\n", first, t1);
+ token_t n = get_token();
+ if (n.is(m_tok_paren_right))
+ break;
+ if (!n.is(m_tok_comma))
+ error(MF_EXPECTED_COMMA_OR_RP_1(n.str()));
+ }
+
}
- if ((pins.size() % 2) == 1)
- error(MF_DIPPINS_EQUAL_NUMBER_1(pins[0]));
- std::size_t n = pins.size();
- for (std::size_t i = 0; i < n / 2; i++)
+
+ void parser_t::dip_pins()
{
- m_setup.register_alias(plib::pfmt("{1}")(i+1), pins[i*2]);
- m_setup.register_alias(plib::pfmt("{1}")(n-i), pins[i*2 + 1]);
+ std::vector<pstring> pins;
+
+ require_token(m_tok_paren_left);
+ pins.push_back(get_identifier());
+ require_token(m_tok_comma);
+
+ while (true)
+ {
+ pstring t1 = get_identifier();
+ pins.push_back(t1);
+ token_t n = get_token();
+ if (n.is(m_tok_paren_right))
+ break;
+ if (!n.is(m_tok_comma))
+ error(MF_EXPECTED_COMMA_OR_RP_1(n.str()));
+ }
+ if ((pins.size() % 2) == 1)
+ error(MF_DIPPINS_EQUAL_NUMBER_1(pins[0]));
+ std::size_t n = pins.size();
+ for (std::size_t i = 0; i < n / 2; i++)
+ {
+ m_setup.register_alias(plib::pfmt("{1}")(i+1), pins[i*2]);
+ m_setup.register_alias(plib::pfmt("{1}")(n-i), pins[i*2 + 1]);
+ }
}
-}
-void parser_t::netdev_param()
-{
- require_token(m_tok_paren_left);
- pstring param(get_identifier());
- require_token(m_tok_comma);
- token_t tok = get_token();
- if (tok.is_type(token_type::STRING))
+ void parser_t::netdev_param()
{
- m_setup.log().debug("Parser: Param: {1} {2}\n", param, tok.str());
- m_setup.register_param(param, tok.str());
- require_token(m_tok_paren_right);
+ require_token(m_tok_paren_left);
+ pstring param(get_identifier());
+ require_token(m_tok_comma);
+ token_t tok = get_token();
+ if (tok.is_type(token_type::STRING))
+ {
+ m_setup.log().debug("Parser: Param: {1} {2}\n", param, tok.str());
+ m_setup.register_param(param, tok.str());
+ require_token(m_tok_paren_right);
+ }
+ else
+ {
+ auto val = stringify_expression(tok);
+ m_setup.log().debug("Parser: Param: {1} {2}\n", param, val);
+ m_setup.register_param(param, val);
+ require_token(tok, m_tok_paren_right);
+ }
}
- else
+
+ void parser_t::netdev_default_param()
{
- auto val = stringify_expression(tok);
- m_setup.log().debug("Parser: Param: {1} {2}\n", param, val);
- m_setup.register_param(param, val);
- require_token(tok, m_tok_paren_right);
+ require_token(m_tok_paren_left);
+ pstring param(get_identifier());
+ require_token(m_tok_comma);
+ token_t tok = get_token();
+ if (tok.is_type(token_type::STRING))
+ {
+ m_setup.log().debug("Parser: DefParam: {1} {2}\n", param, tok.str());
+ m_setup.register_default_param(param, tok.str());
+ require_token(m_tok_paren_right);
+ }
+ else
+ {
+ auto val = stringify_expression(tok);
+ m_setup.log().debug("Parser: Param: {1} {2}\n", param, val);
+ m_setup.register_default_param(param, val);
+ require_token(tok, m_tok_paren_right);
+ }
}
-}
-void parser_t::netdev_default_param()
-{
- require_token(m_tok_paren_left);
- pstring param(get_identifier());
- require_token(m_tok_comma);
- token_t tok = get_token();
- if (tok.is_type(token_type::STRING))
+ void parser_t::netdev_hint()
{
- m_setup.log().debug("Parser: DefParam: {1} {2}\n", param, tok.str());
- m_setup.register_defparam(param, tok.str());
+ require_token(m_tok_paren_left);
+ pstring id(get_identifier());
+ require_token(m_tok_comma);
+ pstring hint(get_identifier());
+ m_setup.register_hint(id, ".HINT_" + hint);
require_token(m_tok_paren_right);
}
- else
+
+ void parser_t::net_register_dev()
{
- auto val = stringify_expression(tok);
- m_setup.log().debug("Parser: Param: {1} {2}\n", param, val);
- m_setup.register_defparam(param, val);
- require_token(tok, m_tok_paren_right);
+ require_token(m_tok_paren_left);
+ pstring type(get_identifier());
+ require_token(m_tok_comma);
+ pstring name(get_identifier());
+ require_token(m_tok_paren_right);
+
+ m_setup.register_dev(type, name);
}
-}
-void parser_t::netdev_hint()
-{
- require_token(m_tok_paren_left);
- pstring id(get_identifier());
- require_token(m_tok_comma);
- pstring hint(get_identifier());
- m_setup.register_hint(id, ".HINT_" + hint);
- require_token(m_tok_paren_right);
-}
-
-void parser_t::net_register_dev()
-{
- require_token(m_tok_paren_left);
- pstring type(get_identifier());
- require_token(m_tok_comma);
- pstring name(get_identifier());
- require_token(m_tok_paren_right);
+ void parser_t::device(const pstring &dev_type)
+ {
+ std::vector<pstring> params;
- m_setup.register_dev(type, name);
-}
+ require_token(m_tok_paren_left);
+ pstring devname(get_identifier());
-void parser_t::device(const pstring &dev_type)
-{
- std::vector<pstring> params;
+ m_setup.log().debug("Parser: IC: {1}\n", devname);
- require_token(m_tok_paren_left);
- pstring devname(get_identifier());
+ auto tok(get_token());
- m_setup.log().debug("Parser: IC: {1}\n", devname);
+ while (tok.is(m_tok_comma))
+ {
+ tok = get_token();
+ if (tok.is_type(token_type::STRING))
+ {
+ params.push_back(tok.str());
+ tok = get_token();
+ }
+ else
+ {
+ auto value = stringify_expression(tok);
+ params.push_back(value);
+ }
+ }
+
+ require_token(tok, m_tok_paren_right);
+ m_setup.register_dev(dev_type, devname, params);
+ }
- auto tok(get_token());
+ // ----------------------------------------------------------------------------------------
+ // private
+ // ----------------------------------------------------------------------------------------
- while (tok.is(m_tok_comma))
+ pstring parser_t::stringify_expression(token_t &tok)
{
- tok = get_token();
- if (/*tok.is_type(token_type::IDENTIFIER) ||*/ tok.is_type(token_type::STRING))
+ int pc(0);
+ pstring ret;
+ while (!tok.is(m_tok_comma))
{
- params.push_back(tok.str());
+ if (tok.is(m_tok_paren_left))
+ pc++;
+ else if (tok.is(m_tok_paren_right))
+ {
+ if (pc<=0)
+ break;
+ pc--;
+ }
+ ret += tok.str();
tok = get_token();
}
- else
- {
- auto value = stringify_expression(tok);
- params.push_back(value);
- }
+ return ret;
}
- require_token(tok, m_tok_paren_right);
- m_setup.register_dev(dev_type, devname, params);
-}
-
+ // ----------------------------------------------------------------------------------------
+ // source_token_t
+ // ----------------------------------------------------------------------------------------
-// ----------------------------------------------------------------------------------------
-// private
-// ----------------------------------------------------------------------------------------
-
-pstring parser_t::stringify_expression(token_t &tok)
-{
- int pc(0);
- pstring ret;
- while (!tok.is(m_tok_comma))
+ bool source_token_t::parse(nlparse_t &setup, const pstring &name)
{
- if (tok.is(m_tok_paren_left))
- pc++;
- else if (tok.is(m_tok_paren_right))
+ if (name == m_name)
{
- if (pc<=0)
- break;
- pc--;
+ auto ret = setup.parse_tokens(m_store, name);
+ return ret;
}
- ret += tok.str();
- tok = get_token();
- }
- return ret;
-}
-// ----------------------------------------------------------------------------------------
-// source_token_t
-// ----------------------------------------------------------------------------------------
+ return false;
+ }
-bool source_token_t::parse(nlparse_t &setup, const pstring &name)
-{
- if (name == m_name)
+ plib::istream_uptr source_token_t::stream([[maybe_unused]] const pstring &name)
{
- auto ret = setup.parse_tokens(m_store, name);
- return ret;
+ return plib::istream_uptr();
}
- return false;
-}
-
-plib::istream_uptr source_token_t::stream([[maybe_unused]] const pstring &name)
-{
- return plib::istream_uptr();
-}
-
-
} // namespace netlist