mirror of
https://github.com/holub/mame
synced 2025-04-20 23:42:22 +03:00
netlist: improve parsing performance
* preparational work for easier device addition.
This commit is contained in:
parent
4985e1e9b9
commit
167da15753
@ -333,6 +333,25 @@ namespace netlist
|
||||
pstring m_setup_func_name;
|
||||
};
|
||||
|
||||
class source_token_t : public source_netlist_t
|
||||
{
|
||||
public:
|
||||
source_token_t(const pstring &name, const parser_t::token_store &store)
|
||||
: m_store(store)
|
||||
, m_name(name)
|
||||
{
|
||||
}
|
||||
|
||||
bool parse(nlparse_t &setup, const pstring &name) override;
|
||||
|
||||
protected:
|
||||
stream_ptr stream(const pstring &name) override;
|
||||
|
||||
private:
|
||||
parser_t::token_store m_store;
|
||||
pstring m_name;
|
||||
};
|
||||
|
||||
} // namespace netlist
|
||||
|
||||
|
||||
|
@ -29,11 +29,6 @@
|
||||
#endif
|
||||
|
||||
NETLIST_EXTERNAL(base_lib)
|
||||
NETLIST_EXTERNAL(cd4xxx_lib)
|
||||
NETLIST_EXTERNAL(opamp_lib)
|
||||
NETLIST_EXTERNAL(otheric_lib)
|
||||
NETLIST_EXTERNAL(ttl74xx_lib)
|
||||
NETLIST_EXTERNAL(roms_lib)
|
||||
|
||||
#if NL_AUTO_DEVICES
|
||||
#include "nld_devinc.h"
|
||||
|
@ -2,6 +2,16 @@
|
||||
// copyright-holders:Couriersud
|
||||
#include "netlist/devices/net_lib.h"
|
||||
|
||||
/* ----------------------------------------------------------------------------
|
||||
* External declarations
|
||||
* ---------------------------------------------------------------------------*/
|
||||
|
||||
NETLIST_EXTERNAL(cd4xxx_lib)
|
||||
NETLIST_EXTERNAL(opamp_lib)
|
||||
NETLIST_EXTERNAL(otheric_lib)
|
||||
NETLIST_EXTERNAL(ttl74xx_lib)
|
||||
NETLIST_EXTERNAL(roms_lib)
|
||||
|
||||
/* ----------------------------------------------------------------------------
|
||||
* Diode Models
|
||||
* ---------------------------------------------------------------------------*/
|
||||
@ -107,11 +117,11 @@ NETLIST_START(base_lib)
|
||||
LOCAL_SOURCE(mosfet_models)
|
||||
LOCAL_SOURCE(family_models)
|
||||
|
||||
LOCAL_SOURCE(ttl74xx_lib)
|
||||
LOCAL_SOURCE(cd4xxx_lib)
|
||||
LOCAL_SOURCE(opamp_lib)
|
||||
LOCAL_SOURCE(otheric_lib)
|
||||
LOCAL_SOURCE(roms_lib)
|
||||
EXTERNAL_SOURCE(ttl74xx_lib)
|
||||
EXTERNAL_SOURCE(cd4xxx_lib)
|
||||
EXTERNAL_SOURCE(opamp_lib)
|
||||
EXTERNAL_SOURCE(otheric_lib)
|
||||
EXTERNAL_SOURCE(roms_lib)
|
||||
|
||||
INCLUDE(diode_models)
|
||||
INCLUDE(bjt_models)
|
||||
|
@ -144,17 +144,18 @@ namespace netlist
|
||||
NETLIST_NAME(base_lib)(m_setup->parser());
|
||||
#else
|
||||
// FIXME: This is very slow - need optimized parsing scanning
|
||||
#if 0
|
||||
m_setup->parser().register_source<source_pattern_t>("src/lib/netlist/macro/nlm_{}.cpp");
|
||||
#if 1
|
||||
m_setup->parser().register_source<source_pattern_t>("src/lib/netlist/macro/nlm_{1}.cpp");
|
||||
m_setup->parser().include("base_lib");
|
||||
#else
|
||||
pstring dir = "src/lib/netlist/macro/";
|
||||
//m_setup->parser().register_source<source_pattern_t>("src/lib/netlist/macro/nlm_{}.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_base.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_opamp.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_roms.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_cd4xxx.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_other.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_ttl74xx.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_base_lib.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_opamp_lib.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_roms_lib.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_cd4xxx_lib.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_otheric_lib.cpp");
|
||||
m_setup->parser().register_source<source_file_t>(dir + "nlm_ttl74xx_lib.cpp");
|
||||
m_setup->parser().include("base_lib");
|
||||
#endif
|
||||
#endif
|
||||
|
@ -43,6 +43,7 @@ namespace netlist
|
||||
PERRMSGV(MF_UNEXPECTED_NETLIST_END, 0, "Unexpected NETLIST_END")
|
||||
PERRMSGV(MF_UNEXPECTED_END_OF_FILE, 0, "Unexpected end of file, missing NETLIST_END")
|
||||
PERRMSGV(MF_UNEXPECTED_NETLIST_START, 0, "Unexpected NETLIST_START")
|
||||
PERRMSGV(MF_UNEXPECTED_NETLIST_EXTERNAL, 0, "Unexpected NETLIST_EXTERNAL within a netlist")
|
||||
PERRMSGV(MF_EXPECTED_NETLIST_START_1, 1, "Expected NETLIST_START but got {1}")
|
||||
PERRMSGV(MF_EXPECTED_IDENTIFIER_GOT_1, 1, "Expected an identifier, but got {1}")
|
||||
PERRMSGV(MF_EXPECTED_COMMA_OR_RP_1, 1, "Expected comma or right parenthesis but found <{1}>")
|
||||
|
@ -47,6 +47,8 @@ parser_t::parser_t(nlparse_t &setup)
|
||||
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_TT_HEAD = m_tokenizer.register_token("TT_HEAD");
|
||||
@ -75,7 +77,7 @@ void parser_t::parse_tokens(plib::psource_t::stream_ptr &&strm, token_store &tok
|
||||
m_tokenizer.append_to_store(&u8reader, tokstor);
|
||||
}
|
||||
|
||||
bool parser_t::parse(token_store &tokstor, const pstring &nlname)
|
||||
bool parser_t::parse(const token_store &tokstor, const pstring &nlname)
|
||||
{
|
||||
set_token_source(&tokstor);
|
||||
|
||||
@ -134,6 +136,14 @@ bool parser_t::parse(token_store &tokstor, const pstring &nlname)
|
||||
m_cur_local->push_back(token_t(m_tok_paren_right));
|
||||
in_nl = true;
|
||||
}
|
||||
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))
|
||||
@ -179,13 +189,17 @@ void parser_t::parse_netlist(const pstring &nlname)
|
||||
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_TRUTHTABLE_START))
|
||||
net_truthtable_start(nlname);
|
||||
else if (token.is(m_tok_LOCAL_LIB_ENTRY))
|
||||
{
|
||||
require_token(m_tok_paren_left);
|
||||
pstring name(get_identifier());
|
||||
register_local_as_source(name);
|
||||
// FIXME: Need to pass in parameter definition FIXME: get line number right
|
||||
m_setup.register_lib_entry(get_identifier(), "", plib::source_location("parser: " + nlname, 1));
|
||||
m_setup.register_lib_entry(name, "", plib::source_location("parser: " + nlname, 1));
|
||||
require_token(m_tok_paren_right);
|
||||
}
|
||||
else if (token.is(m_tok_NET_REGISTER_DEV))
|
||||
@ -315,6 +329,28 @@ void parser_t::net_include()
|
||||
}
|
||||
|
||||
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);
|
||||
|
||||
register_local_as_source(name);
|
||||
}
|
||||
|
||||
void parser_t::register_local_as_source(const pstring &name)
|
||||
{
|
||||
auto p = m_local.find(name);
|
||||
if (p != m_local.end())
|
||||
{
|
||||
printf("found %s\n", name.c_str());
|
||||
m_setup.register_source<source_token_t>(name, p->second);
|
||||
}
|
||||
else
|
||||
printf("argh %s\n", name.c_str());
|
||||
}
|
||||
|
||||
void parser_t::net_external_source()
|
||||
{
|
||||
// This directive is only for hardcoded netlists. Ignore it here.
|
||||
require_token(m_tok_paren_left);
|
||||
|
@ -26,7 +26,7 @@ namespace netlist
|
||||
parser_t(nlparse_t &setup);
|
||||
|
||||
bool parse(plib::psource_t::stream_ptr &&strm, const pstring &nlname);
|
||||
bool parse(token_store &tokstor, const pstring &nlname);
|
||||
bool parse(const token_store &tokstor, const pstring &nlname);
|
||||
void parse_tokens(plib::psource_t::stream_ptr &&strm, token_store &tokstor);
|
||||
|
||||
protected:
|
||||
@ -44,12 +44,16 @@ namespace netlist
|
||||
void net_submodel();
|
||||
void net_include();
|
||||
void net_local_source();
|
||||
void net_external_source();
|
||||
void net_register_dev();
|
||||
void net_truthtable_start(const pstring &nlname);
|
||||
|
||||
void verror(const pstring &msg) override;
|
||||
private:
|
||||
void register_local_as_source(const pstring &name);
|
||||
|
||||
pstring stringify_expression(token_t &tok);
|
||||
|
||||
token_id_t m_tok_paren_left;
|
||||
token_id_t m_tok_paren_right;
|
||||
token_id_t m_tok_comma;
|
||||
@ -65,8 +69,10 @@ namespace netlist
|
||||
token_id_t m_tok_NET_REGISTER_DEV;
|
||||
token_id_t m_tok_NETLIST_START;
|
||||
token_id_t m_tok_NETLIST_END;
|
||||
token_id_t m_tok_NETLIST_EXTERNAL;
|
||||
token_id_t m_tok_SUBMODEL;
|
||||
token_id_t m_tok_INCLUDE;
|
||||
token_id_t m_tok_EXTERNAL_SOURCE;
|
||||
token_id_t m_tok_LOCAL_SOURCE;
|
||||
token_id_t m_tok_LOCAL_LIB_ENTRY;
|
||||
token_id_t m_tok_TRUTHTABLE_START;
|
||||
|
@ -352,8 +352,15 @@ namespace netlist
|
||||
return false;
|
||||
}
|
||||
|
||||
bool nlparse_t::parse_tokens(const parser_t::token_store &tokens, const pstring &name)
|
||||
{
|
||||
parser_t parser(*this);
|
||||
return parser.parse(tokens, name);
|
||||
}
|
||||
|
||||
bool nlparse_t::parse_stream(plib::psource_t::stream_ptr &&istrm, const pstring &name)
|
||||
{
|
||||
#if 0
|
||||
auto key = istrm.filename();
|
||||
|
||||
if (m_source_cache.find(key) != m_source_cache.end())
|
||||
@ -374,6 +381,18 @@ namespace netlist
|
||||
parser.parse_tokens(plib::psource_t::stream_ptr(std::move(abc), key), st);
|
||||
return parser.parse(st, name);
|
||||
}
|
||||
#else
|
||||
plib::ppreprocessor y(m_includes, &m_defines);
|
||||
y.process(std::move(istrm), istrm.filename());
|
||||
|
||||
auto abc = std::make_unique<std::stringstream>();
|
||||
plib::copystream(*abc, y);
|
||||
|
||||
parser_t::token_store st;
|
||||
parser_t parser(*this);
|
||||
parser.parse_tokens(plib::psource_t::stream_ptr(std::move(abc), istrm.filename()), st);
|
||||
return parser.parse(st, name);
|
||||
#endif
|
||||
}
|
||||
|
||||
void nlparse_t::add_define(const pstring &defstr)
|
||||
@ -1712,8 +1731,10 @@ source_file_t::stream_ptr source_pattern_t::stream(const pstring &name)
|
||||
{
|
||||
pstring filename = plib::pfmt(m_pattern)(name);
|
||||
auto f = std::make_unique<plib::ifstream>(plib::filesystem::u8path(filename));
|
||||
printf("checking <%s> %s\n", name.c_str(), filename.c_str());
|
||||
if (f->is_open())
|
||||
{
|
||||
printf("found\n");
|
||||
return stream_ptr(std::move(f), filename);
|
||||
}
|
||||
else
|
||||
@ -1738,5 +1759,23 @@ source_proc_t::stream_ptr source_proc_t::stream(const pstring &name)
|
||||
return stream_ptr();
|
||||
}
|
||||
|
||||
bool source_token_t::parse(nlparse_t &setup, const pstring &name)
|
||||
{
|
||||
if (name == m_name)
|
||||
{
|
||||
auto ret = setup.parse_tokens(m_store, name);
|
||||
printf("parsed tokens: %s %d\n", name.c_str(), (int) ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
source_proc_t::stream_ptr source_token_t::stream(const pstring &name)
|
||||
{
|
||||
plib::unused_var(name);
|
||||
return stream_ptr();
|
||||
}
|
||||
|
||||
} // namespace netlist
|
||||
|
||||
|
@ -83,6 +83,9 @@ void NETLIST_NAME(name)(netlist::nlparse_t &setup) \
|
||||
#define LOCAL_SOURCE(name) \
|
||||
setup.register_source_proc(# name, &NETLIST_NAME(name));
|
||||
|
||||
#define EXTERNAL_SOURCE(name) \
|
||||
setup.register_source_proc(# name, &NETLIST_NAME(name));
|
||||
|
||||
// FIXME: Need to pass in parameter definition
|
||||
#define LOCAL_LIB_ENTRY_1(name) \
|
||||
LOCAL_SOURCE(name) \
|
||||
@ -230,6 +233,7 @@ namespace netlist
|
||||
|
||||
// FIXME: used by source_t - need a different approach at some time
|
||||
bool parse_stream(plib::psource_t::stream_ptr &&istrm, const pstring &name);
|
||||
bool parse_tokens(const parser_t::token_store &tokens, const pstring &name);
|
||||
|
||||
template <typename S, typename... Args>
|
||||
void add_include(Args&&... args)
|
||||
|
Loading…
Reference in New Issue
Block a user