summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
author Vas Crabb <vas@vastheman.com>2021-06-23 16:08:59 +1000
committer Vas Crabb <vas@vastheman.com>2021-06-23 16:08:59 +1000
commitc9a62818e9135c5b757cfbaa940c83ca5371e275 (patch)
tree2308021b4c003b9f6abe29efbb00aabe67909e01
parent12959e6e97a229c91757dff52f5153ca49cc7ced (diff)
-Miscellaneous improvements for software lists:
* Show list name in software selection menu (machines have multiple lists). * Actually report software list parsing errors during validation. * Check that software list name attribute matches filename. * Limit software list names to 24 characters - they're getting too long, and they need to be practical in command lines. * c128.cpp: Fix dangling reference to renamed software list. -emu/ioport.cpp: Slightly better test for deselected slot cards.
-rw-r--r--hash/leapster_explorer_cart.xml (renamed from hash/leapfrog_leapster_explorer_cart.xml)2
-rw-r--r--hash/ttwist_brainquest_cart.xml (renamed from hash/leapfrog_turbotwistbrainquest_cart.xml)2
-rw-r--r--hash/turboextreme_cart.xml (renamed from hash/leapfrog_turboextreme_cart.xml)2
-rw-r--r--hash/vtech_innotv_cart.xml (renamed from hash/vtech_innotv_innotabmax_cart.xml)2
-rw-r--r--src/emu/diimage.cpp5
-rw-r--r--src/emu/ioport.cpp24
-rw-r--r--src/emu/romload.cpp5
-rw-r--r--src/emu/softlist.cpp152
-rw-r--r--src/emu/softlist.h112
-rw-r--r--src/emu/softlist_dev.cpp114
-rw-r--r--src/emu/softlist_dev.h4
-rw-r--r--src/frontend/mame/clifront.cpp4
-rw-r--r--src/frontend/mame/ui/info.cpp6
-rw-r--r--src/frontend/mame/ui/inifile.cpp4
-rw-r--r--src/frontend/mame/ui/selmenu.cpp6
-rw-r--r--src/frontend/mame/ui/selsoft.cpp25
-rw-r--r--src/frontend/mame/ui/utils.cpp7
-rw-r--r--src/frontend/mame/ui/utils.h7
-rw-r--r--src/mame/drivers/c128.cpp52
-rw-r--r--src/mame/drivers/c64.cpp4
-rw-r--r--src/mame/drivers/innotv_innotabmax.cpp2
-rw-r--r--src/mame/drivers/leapfrog_iquest.cpp10
-rw-r--r--src/mame/drivers/leapfrog_leapster_explorer.cpp2
23 files changed, 296 insertions, 257 deletions
diff --git a/hash/leapfrog_leapster_explorer_cart.xml b/hash/leapster_explorer_cart.xml
index 306e7274575..9eb90ac54f7 100644
--- a/hash/leapfrog_leapster_explorer_cart.xml
+++ b/hash/leapster_explorer_cart.xml
@@ -2,7 +2,7 @@
<!DOCTYPE softwarelist SYSTEM "softwarelist.dtd">
<!-- license:CC0 -->
-<softwarelist name="leapfrog_leapster_explorer_cart" description="LeapFrog Leapster Explorer Cartridges">
+<softwarelist name="leapster_explorer_cart" description="LeapFrog Leapster Explorer Cartridges">
<software name="tblt" supported="no">
<description>TinkerBell and the Lost Treasure (USA)</description>
diff --git a/hash/leapfrog_turbotwistbrainquest_cart.xml b/hash/ttwist_brainquest_cart.xml
index f6317235594..71025fd403b 100644
--- a/hash/leapfrog_turbotwistbrainquest_cart.xml
+++ b/hash/ttwist_brainquest_cart.xml
@@ -3,7 +3,7 @@
<!--
license:CC0
-->
-<softwarelist name="leapfrog_turbotwistbrainquest_cart" description="LeapFrog Turbo Twist Brain Quest cartridges">
+<softwarelist name="ttwist_brainquest_cart" description="LeapFrog Turbo Twist Brain Quest cartridges">
<!-- also compatible with Fact Blaster -->
<software name="grades5_6" supported="no">
diff --git a/hash/leapfrog_turboextreme_cart.xml b/hash/turboextreme_cart.xml
index 4d4cb502517..000ad5b7133 100644
--- a/hash/leapfrog_turboextreme_cart.xml
+++ b/hash/turboextreme_cart.xml
@@ -3,7 +3,7 @@
<!--
license:CC0
-->
-<softwarelist name="leapfrog_turboextreme_cart" description="LeapFrog Turbo Extreme cartridges">
+<softwarelist name="turboextreme_cart" description="LeapFrog Turbo Extreme cartridges">
<software name="grade2" supported="no">
<description>Grade 2 (500-10652)</description>
diff --git a/hash/vtech_innotv_innotabmax_cart.xml b/hash/vtech_innotv_cart.xml
index 3bbbe866d1a..aaadb16fc59 100644
--- a/hash/vtech_innotv_innotabmax_cart.xml
+++ b/hash/vtech_innotv_cart.xml
@@ -8,7 +8,7 @@ license:CC0
<!-- Grey coloured 'pack-in' cartridge contains no ROM, only 2 pins bridged -->
-<softwarelist name="vtech_innotv_innotabmax_cart" description="VTech InnoTV / InnoTAB MAX cartridges">
+<softwarelist name="vtech_innotv_cart" description="VTech InnoTV / InnoTAB MAX cartridges">
<software name="pawpatrl" supported="no">
<description>Paw Patrol - Pups Save a UFO! (80-274103 UK)</description>
diff --git a/src/emu/diimage.cpp b/src/emu/diimage.cpp
index 9f63ebd4b4b..55a9193f3f1 100644
--- a/src/emu/diimage.cpp
+++ b/src/emu/diimage.cpp
@@ -801,10 +801,9 @@ bool device_image_interface::load_software(software_list_device &swlist, std::st
if (!swinfo)
return false;
- const u32 supported = swinfo->supported();
- if (supported == SOFTWARE_SUPPORTED_PARTIAL)
+ if (swinfo->supported() == software_support::PARTIALLY_SUPPORTED)
osd_printf_error("WARNING: support for software %s (in list %s) is only partial\n", swname, swlist.list_name());
- if (supported == SOFTWARE_SUPPORTED_NO)
+ else if (swinfo->supported() == software_support::UNSUPPORTED)
osd_printf_error("WARNING: support for software %s (in list %s) is only preliminary\n", swname, swlist.list_name());
u32 crc = 0;
diff --git a/src/emu/ioport.cpp b/src/emu/ioport.cpp
index 3c88c319a8b..02713356bf7 100644
--- a/src/emu/ioport.cpp
+++ b/src/emu/ioport.cpp
@@ -2323,20 +2323,24 @@ void ioport_manager::load_game_config(util::xml::data_node const *portnode, int
if (pos && (std::string_view::npos != pos))
{
parent_tag = parent_tag.substr(0, pos);
- for (pos = parent_tag.rfind(':'); pos && (std::string_view::npos != pos); pos = parent_tag.rfind(':'))
+ if (!machine().root_device().subdevice(parent_tag))
{
- parent_tag = parent_tag.substr(0, pos);
- device_t const *const parent_device(machine().root_device().subdevice(parent_tag));
- if (parent_device)
+ for (pos = parent_tag.rfind(':'); pos && (std::string_view::npos != pos); pos = parent_tag.rfind(':'))
{
- device_slot_interface const *slot;
- if (parent_device->interface(slot))
+ std::string_view const child_tag(parent_tag.substr(pos + 1));
+ parent_tag = parent_tag.substr(0, pos);
+ device_t const *const parent_device(machine().root_device().subdevice(parent_tag));
+ if (parent_device)
{
- if (!m_deselected_card_config)
- m_deselected_card_config = util::xml::file::create().release();
- portnode->copy_into(*m_deselected_card_config);
+ device_slot_interface const *slot;
+ if (parent_device->interface(slot) && (slot->option_list().find(std::string(child_tag)) != slot->option_list().end()))
+ {
+ if (!m_deselected_card_config)
+ m_deselected_card_config = util::xml::file::create().release();
+ portnode->copy_into(*m_deselected_card_config);
+ }
+ break;
}
- break;
}
}
}
diff --git a/src/emu/romload.cpp b/src/emu/romload.cpp
index 6ecc8ad6547..36d7896e467 100644
--- a/src/emu/romload.cpp
+++ b/src/emu/romload.cpp
@@ -1222,13 +1222,12 @@ void rom_load_manager::load_software_part_region(device_t &device, software_list
{
// dispay a warning for unsupported software
// TODO: list supported clones like we do for machines?
- const u32 supported(swinfo->supported());
- if (supported == SOFTWARE_SUPPORTED_PARTIAL)
+ if (swinfo->supported() == software_support::PARTIALLY_SUPPORTED)
{
m_errorstring.append(string_format("WARNING: support for software %s (in list %s) is only partial\n", swname, swlist.list_name()));
m_softwarningstring.append(string_format("Support for software %s (in list %s) is only partial\n", swname, swlist.list_name()));
}
- if (supported == SOFTWARE_SUPPORTED_NO)
+ else if (swinfo->supported() == software_support::UNSUPPORTED)
{
m_errorstring.append(string_format("WARNING: support for software %s (in list %s) is only preliminary\n", swname, swlist.list_name()));
m_softwarningstring.append(string_format("Support for software %s (in list %s) is only preliminary\n", swname, swlist.list_name()));
diff --git a/src/emu/softlist.cpp b/src/emu/softlist.cpp
index 8166888f80a..d7dec822f3d 100644
--- a/src/emu/softlist.cpp
+++ b/src/emu/softlist.cpp
@@ -36,7 +36,6 @@ static std::regex s_potential_softlist_regex("\\w+(\\:\\w+)*");
//-------------------------------------------------
feature_list_item::feature_list_item(const std::string &name, const std::string &value) :
- m_next(nullptr),
m_name(name),
m_value(value)
{
@@ -48,7 +47,6 @@ feature_list_item::feature_list_item(const std::string &name, const std::string
//-------------------------------------------------
feature_list_item::feature_list_item(std::string &&name, std::string &&value) :
- m_next(nullptr),
m_name(std::move(name)),
m_value(std::move(value))
{
@@ -64,7 +62,6 @@ feature_list_item::feature_list_item(std::string &&name, std::string &&value) :
//-------------------------------------------------
software_part::software_part(software_info &info, std::string &&name, std::string &&interface) :
- m_next(nullptr),
m_info(info),
m_name(std::move(name)),
m_interface(std::move(interface))
@@ -77,7 +74,7 @@ software_part::software_part(software_info &info, std::string &&name, std::strin
// feature, if specified
//-------------------------------------------------
-const char *software_part::feature(const std::string &feature_name) const noexcept
+const char *software_part::feature(std::string_view feature_name) const noexcept
{
// scan the feature list for an entry matching feature_name and return the value
auto iter = std::find_if(
@@ -126,16 +123,16 @@ bool software_part::matches_interface(const char *interface_list) const noexcept
// software_info - constructor
//-------------------------------------------------
-software_info::software_info(std::string &&name, std::string &&parent, const std::string &supported) :
- m_supported(SOFTWARE_SUPPORTED_YES),
+software_info::software_info(std::string &&name, std::string &&parent, std::string_view supported) :
+ m_supported(software_support::SUPPORTED),
m_shortname(std::move(name)),
m_parentname(std::move(parent))
{
// handle the supported flag if provided
if (supported == "partial")
- m_supported = SOFTWARE_SUPPORTED_PARTIAL;
+ m_supported = software_support::PARTIALLY_SUPPORTED;
else if (supported == "no")
- m_supported = SOFTWARE_SUPPORTED_NO;
+ m_supported = software_support::UNSUPPORTED;
}
@@ -144,13 +141,13 @@ software_info::software_info(std::string &&name, std::string &&parent, const std
// optional interface match
//-------------------------------------------------
-const software_part *software_info::find_part(const std::string &part_name, const char *interface) const
+const software_part *software_info::find_part(std::string_view part_name, const char *interface) const
{
// look for the part by name and match against the interface if provided
auto iter = std::find_if(
m_partdata.begin(),
m_partdata.end(),
- [&](const software_part &part)
+ [&part_name, interface] (const software_part &part)
{
// try to match the part_name (or all parts if part_name is empty), and then try
// to match the interface (or all interfaces if interface is nullptr)
@@ -184,20 +181,97 @@ bool software_info::has_multiple_parts(const char *interface) const
}
+namespace detail {
+
//**************************************************************************
// SOFTWARE LIST PARSER
//**************************************************************************
+class softlist_parser
+{
+public:
+ // construction (== execution)
+ softlist_parser(
+ util::core_file &file,
+ std::string_view filename,
+ std::string &listname,
+ std::string &description,
+ std::list<software_info> &infolist,
+ std::ostream &errors);
+
+private:
+ enum parse_position
+ {
+ POS_ROOT,
+ POS_MAIN,
+ POS_SOFT,
+ POS_PART,
+ POS_DATA
+ };
+
+ // internal parsing helpers
+ const char *infoname() const { return m_current_info ? m_current_info->shortname().c_str() : "???"; }
+ int line() const { return XML_GetCurrentLineNumber(m_parser); }
+ int column() const { return XML_GetCurrentColumnNumber(m_parser); }
+ const char *parser_error() const { return XML_ErrorString(XML_GetErrorCode(m_parser)); }
+
+ // internal error helpers
+ template <typename Format, typename... Params> void parse_error(Format &&fmt, Params &&... args);
+ void unknown_tag(const char *tagname) { parse_error("Unknown tag: %s", tagname); }
+ void unknown_attribute(const char *attrname) { parse_error("Unknown attribute: %s", attrname); }
+
+ // internal helpers
+ template <typename T> std::vector<std::string> parse_attributes(const char **attributes, const T &attrlist);
+ bool parse_name_and_value(const char **attributes, std::string &name, std::string &value);
+ void add_rom_entry(std::string &&name, std::string &&hashdata, u32 offset, u32 length, u32 flags);
+
+ // expat callbacks
+ static void start_handler(void *data, const char *tagname, const char **attributes);
+ static void data_handler(void *data, const char *s, int len);
+ static void end_handler(void *data, const char *name);
+
+ // internal parsing
+ void parse_root_start(const char *tagname, const char **attributes);
+ void parse_main_start(const char *tagname, const char **attributes);
+ void parse_soft_start(const char *tagname, const char **attributes);
+ void parse_part_start(const char *tagname, const char **attributes);
+ void parse_data_start(const char *tagname, const char **attributes);
+ void parse_soft_end(const char *name);
+
+ // internal parsing state
+ util::core_file & m_file;
+ const std::string_view m_filename;
+ std::list<software_info> & m_infolist;
+ std::ostream & m_errors;
+ struct XML_ParserStruct * m_parser;
+ bool m_done;
+ std::string & m_listname;
+ std::string & m_description;
+ bool m_data_accum_expected;
+ std::string m_data_accum;
+ software_info * m_current_info;
+ software_part * m_current_part;
+ parse_position m_pos;
+};
+
+
//-------------------------------------------------
// softlist_parser - constructor
//-------------------------------------------------
-softlist_parser::softlist_parser(util::core_file &file, const std::string &filename, std::string &description, std::list<software_info> &infolist, std::ostringstream &errors) :
+softlist_parser::softlist_parser(
+ util::core_file &file,
+ std::string_view filename,
+ std::string &listname,
+ std::string &description,
+ std::list<software_info> &infolist,
+ std::ostream &errors) :
m_file(file),
m_filename(filename),
m_infolist(infolist),
m_errors(errors),
m_done(false),
+ m_listname(listname),
m_description(description),
m_data_accum_expected(false),
m_current_info(nullptr),
@@ -234,36 +308,6 @@ softlist_parser::softlist_parser(util::core_file &file, const std::string &filen
//-------------------------------------------------
-// line
-//-------------------------------------------------
-
-int softlist_parser::line() const
-{
- return XML_GetCurrentLineNumber(m_parser);
-}
-
-
-//-------------------------------------------------
-// column
-//-------------------------------------------------
-
-int softlist_parser::column() const
-{
- return XML_GetCurrentColumnNumber(m_parser);
-}
-
-
-//-------------------------------------------------
-// parser_error
-//-------------------------------------------------
-
-const char *softlist_parser::parser_error() const
-{
- return XML_ErrorString(XML_GetErrorCode(m_parser));
-}
-
-
-//-------------------------------------------------
// parse_error - append a parsing error with
// filename, line and column information
//-------------------------------------------------
@@ -459,18 +503,21 @@ void softlist_parser::data_handler(void *data, const char *s, int len)
{
softlist_parser *state = reinterpret_cast<softlist_parser *>(data);
- // if we have an std::string to accumulate data in, do it
if (state->m_data_accum_expected)
+ {
+ // if we have an std::string to accumulate data in, do it
state->m_data_accum.append(s, len);
-
- // otherwise, report an error if the data is non-blank
+ }
else
+ {
+ // otherwise, report an error if the data is non-blank
for (int i = 0; i < len; i++)
if (!isspace(s[i]))
{
state->parse_error("Unexpected content");
break;
}
+ }
}
@@ -486,6 +533,9 @@ void softlist_parser::parse_root_start(const char *tagname, const char **attribu
static char const *const attrnames[] = { "name", "description" };
const auto attrvalues = parse_attributes(attributes, attrnames);
+ if (!attrvalues[0].empty())
+ m_listname = attrvalues[0];
+
if (!attrvalues[1].empty())
m_description = attrvalues[1];
}
@@ -831,6 +881,20 @@ void softlist_parser::parse_soft_end(const char *tagname)
}
}
+} // namespace detail
+
+
+void parse_software_list(
+ util::core_file &file,
+ std::string_view filename,
+ std::string &listname,
+ std::string &description,
+ std::list<software_info> &infolist,
+ std::ostream &errors)
+{
+ detail::softlist_parser(file, filename, listname, description, infolist, errors);
+}
+
//-------------------------------------------------
// software_name_parse - helper that splits a
diff --git a/src/emu/softlist.h b/src/emu/softlist.h
index 5f8f7fd2fbd..67c1f9b9535 100644
--- a/src/emu/softlist.h
+++ b/src/emu/softlist.h
@@ -22,20 +22,28 @@
//**************************************************************************
+// FORWARD DECLARATIONS
+//**************************************************************************
+
+namespace detail { class softlist_parser; }
+
+
+//**************************************************************************
// CONSTANTS
//**************************************************************************
-#define SOFTWARE_SUPPORTED_YES 0
-#define SOFTWARE_SUPPORTED_PARTIAL 1
-#define SOFTWARE_SUPPORTED_NO 2
+enum class software_support
+{
+ SUPPORTED,
+ PARTIALLY_SUPPORTED,
+ UNSUPPORTED
+};
//**************************************************************************
// TYPE DEFINITIONS
//**************************************************************************
-// ======================> feature_list_item
-
// an item in a list of name/value pairs
class feature_list_item
{
@@ -49,24 +57,20 @@ public:
feature_list_item& operator=(feature_list_item &&) = delete;
// getters
- feature_list_item *next() const noexcept { return m_next; }
const std::string &name() const noexcept { return m_name; }
const std::string &value() const noexcept { return m_value; }
private:
// internal state
- feature_list_item * m_next;
std::string m_name;
std::string m_value;
};
-// ======================> software_part
-
// a single part of a software item
class software_part
{
- friend class softlist_parser;
+ friend class detail::softlist_parser;
public:
// construction/destruction
@@ -77,7 +81,6 @@ public:
software_part& operator=(software_part &&) = delete;
// getters
- software_part *next() const noexcept { return m_next; }
software_info &info() const noexcept { return m_info; }
const std::string &name() const noexcept { return m_name; }
const std::string &interface() const noexcept { return m_interface; }
@@ -86,11 +89,10 @@ public:
// helpers
bool matches_interface(const char *interface_list) const noexcept;
- const char *feature(const std::string &feature_name) const noexcept;
+ const char *feature(std::string_view feature_name) const noexcept;
private:
// internal state
- software_part * m_next;
software_info & m_info;
std::string m_name;
std::string m_interface;
@@ -99,16 +101,14 @@ private:
};
-// ======================> software_info
-
// a single software item
class software_info
{
- friend class softlist_parser;
+ friend class detail::softlist_parser;
public:
// construction/destruction
- software_info(std::string &&name, std::string &&parent, const std::string &supported);
+ software_info(std::string &&name, std::string &&parent, std::string_view supported);
software_info(software_info const &) = delete;
software_info(software_info &&) = delete;
software_info& operator=(software_info const &) = delete;
@@ -122,16 +122,16 @@ public:
const std::string &publisher() const { return m_publisher; }
const std::list<feature_list_item> &other_info() const { return m_other_info; }
const std::list<feature_list_item> &shared_info() const { return m_shared_info; }
- u32 supported() const { return m_supported; }
+ software_support supported() const { return m_supported; }
const std::list<software_part> &parts() const { return m_partdata; }
// additional operations
- const software_part *find_part(const std::string &part_name, const char *interface = nullptr) const;
+ const software_part *find_part(std::string_view part_name, const char *interface = nullptr) const;
bool has_multiple_parts(const char *interface) const;
private:
// internal state
- u32 m_supported;
+ software_support m_supported;
std::string m_shortname;
std::string m_longname;
std::string m_parentname;
@@ -144,71 +144,17 @@ private:
};
-// ======================> softlist_parser
-
-class softlist_parser
-{
-public:
- // construction (== execution)
- softlist_parser(util::core_file &file, const std::string &filename, std::string &description, std::list<software_info> &infolist, std::ostringstream &errors);
-
-private:
- enum parse_position
- {
- POS_ROOT,
- POS_MAIN,
- POS_SOFT,
- POS_PART,
- POS_DATA
- };
-
- // internal parsing helpers
- const char *infoname() const { return (m_current_info != nullptr) ? m_current_info->shortname().c_str() : "???"; }
- int line() const;
- int column() const;
- const char *parser_error() const;
-
- // internal error helpers
- template <typename Format, typename... Params> void parse_error(Format &&fmt, Params &&... args);
- void unknown_tag(const char *tagname) { parse_error("Unknown tag: %s", tagname); }
- void unknown_attribute(const char *attrname) { parse_error("Unknown attribute: %s", attrname); }
-
- // internal helpers
- template <typename T> std::vector<std::string> parse_attributes(const char **attributes, const T &attrlist);
- bool parse_name_and_value(const char **attributes, std::string &name, std::string &value);
- void add_rom_entry(std::string &&name, std::string &&hashdata, u32 offset, u32 length, u32 flags);
-
- // expat callbacks
- static void start_handler(void *data, const char *tagname, const char **attributes);
- static void data_handler(void *data, const char *s, int len);
- static void end_handler(void *data, const char *name);
-
- // internal parsing
- void parse_root_start(const char *tagname, const char **attributes);
- void parse_main_start(const char *tagname, const char **attributes);
- void parse_soft_start(const char *tagname, const char **attributes);
- void parse_part_start(const char *tagname, const char **attributes);
- void parse_data_start(const char *tagname, const char **attributes);
- void parse_soft_end(const char *name);
-
- // internal parsing state
- util::core_file & m_file;
- std::string m_filename;
- std::list<software_info> & m_infolist;
- std::ostringstream & m_errors;
- struct XML_ParserStruct * m_parser;
- bool m_done;
- std::string & m_description;
- bool m_data_accum_expected;
- std::string m_data_accum;
- software_info * m_current_info;
- software_part * m_current_part;
- parse_position m_pos;
-};
-
-
// ----- Helpers -----
+// parses a software list
+void parse_software_list(
+ util::core_file &file,
+ std::string_view filename,
+ std::string &listname,
+ std::string &description,
+ std::list<software_info> &infolist,
+ std::ostream &errors);
+
// parses a software identifier (e.g. - 'apple2e:agentusa:flop1') into its constituent parts (returns false if cannot parse)
bool software_name_parse(std::string_view identifier, std::string *list_name = nullptr, std::string *software_name = nullptr, std::string *part_name = nullptr);
diff --git a/src/emu/softlist_dev.cpp b/src/emu/softlist_dev.cpp
index 4da6c9069b0..286e6da6d4a 100644
--- a/src/emu/softlist_dev.cpp
+++ b/src/emu/softlist_dev.cpp
@@ -89,7 +89,6 @@ software_list_device::software_list_device(const machine_config &mconfig, const
m_list_type(softlist_type::ORIGINAL_SYSTEM),
m_filter(nullptr),
m_parsed(false),
- m_file(mconfig.options().hash_path(), OPEN_FLAG_READ),
m_description("")
{
}
@@ -176,8 +175,10 @@ void software_list_device::find_approx_matches(std::string_view name, int matche
void software_list_device::release()
{
- osd_printf_verbose("Resetting %s\n", m_file.filename());
+ osd_printf_verbose("%s: Resetting %s\n", tag(), m_list_name);
m_parsed = false;
+ m_filename.clear();
+ m_shortname.clear();
m_description.clear();
m_errors.clear();
m_infolist.clear();
@@ -286,17 +287,25 @@ void software_list_device::parse()
m_errors.clear();
// attempt to open the file
- const osd_file::error filerr = m_file.open(m_list_name + ".xml");
+ emu_file file(mconfig().options().hash_path(), OPEN_FLAG_READ);
+ const osd_file::error filerr = file.open(m_list_name + ".xml");
+ m_filename = file.filename();
if (filerr == osd_file::error::NONE)
{
// parse if no error
std::ostringstream errs;
- softlist_parser parser(m_file, m_file.filename(), m_description, m_infolist, errs);
- m_file.close();
+ parse_software_list(file, m_filename, m_shortname, m_description, m_infolist, errs);
+ file.close();
m_errors = errs.str();
}
+ else if (filerr == osd_file::error::NOT_FOUND)
+ {
+ osd_printf_verbose("%s: Software list %s not found\n", m_filename);
+ }
else
- m_errors = string_format("Error opening file: %s\n", filename());
+ {
+ m_errors = string_format("Error opening file: %s\n", m_filename);
+ }
// indicate that we've been parsed
m_parsed = true;
@@ -421,98 +430,115 @@ void software_list_device::device_validity_check(validity_checker &valid) const
void software_list_device::internal_validity_check(validity_checker &valid)
{
- enum { NAME_LEN_PARENT = 16, NAME_LEN_CLONE = 16, NAME_LEN_PART = 16 };
+ enum { NAME_LEN_LIST = 24, NAME_LEN_PARENT = 16, NAME_LEN_CLONE = 16, NAME_LEN_PART = 16 };
auto const valid_name_char = [] (char ch) { return ((ch >= '0') && (ch <= '9')) || ((ch >= 'a') && (ch <= 'z')) || (ch == '_'); };
auto const valid_tag_char = [] (char ch) { return ((ch >= '0') && (ch <= '9')) || ((ch >= 'a') && (ch <= 'z')) || strchr("$.:_", u8(ch)); };
auto const valid_year_char = [] (char ch) { return isdigit(u8(ch)) || (ch == '?') || (ch == '+'); };
auto const valid_label_char = [] (char ch) { return (ch >= ' ') && (ch <= '~') && !strchr("!$%/:\\", u8(ch)); };
+ // first parse and output core errors if any
+ auto const &info(get_info());
+ if (!m_errors.empty())
+ {
+ osd_printf_error("%s: Errors parsing software list:\n%s", m_filename, m_errors);
+ release();
+ return;
+ }
+
+ // ignore empty shortname to work around ignoring missing software lists
+ if (!m_shortname.empty())
+ {
+ if (m_list_name != m_shortname)
+ osd_printf_error("%s: Software list name %s does not match filename %s\n", m_filename, m_shortname, m_list_name);
+
+ if (m_shortname.length() > NAME_LEN_LIST)
+ osd_printf_error("%s: %s software list name must be %d characters or less\n", m_filename, m_shortname, NAME_LEN_LIST);
+ }
+
+ // now check the software items
softlist_map names;
softlist_map descriptions;
- for (const software_info &swinfo : get_info())
+ for (const software_info &swinfo : info)
{
- // first parse and output core errors if any
- if (m_errors.length() > 0)
- {
- osd_printf_error("%s: Errors parsing software list:\n%s", filename(), errors_string());
- break;
- }
-
- // Now check if the xml data is valid:
std::string const &shortname(swinfo.shortname());
if (swinfo.longname().empty())
- osd_printf_error("%s: %s has no description\n", filename(), shortname);
+ osd_printf_error("%s: %s has no description\n", m_filename, shortname);
if (swinfo.year().empty())
- osd_printf_error("%s: %s has no year\n", filename(), shortname);
+ osd_printf_error("%s: %s has no year\n", m_filename, shortname);
if (swinfo.publisher().empty())
- osd_printf_error("%s: %s has no publisher\n", filename(), shortname);
+ osd_printf_error("%s: %s has no publisher\n", m_filename, shortname);
// Did we lost the software parts?
if (swinfo.parts().empty())
- osd_printf_error("%s: %s has no parts\n", filename(), shortname);
+ osd_printf_error("%s: %s has no parts\n", m_filename, shortname);
// Second, since the xml is fine, run additional checks:
// check for duplicate names
auto const dupname(names.emplace(shortname, &swinfo));
if (!dupname.second)
- osd_printf_error("%s: %s is a duplicate name (%s)\n", filename(), shortname, dupname.first->second->shortname());
+ osd_printf_error("%s: %s is a duplicate name (%s)\n", m_filename, shortname, dupname.first->second->shortname());
// check for duplicate descriptions
auto const dupdesc(descriptions.emplace(swinfo.longname(), &swinfo));
if (!dupdesc.second)
- osd_printf_error("%s: %s has duplicate description '%s' (%s)\n", filename(), shortname, swinfo.longname(), dupdesc.first->second->shortname());
+ osd_printf_error("%s: %s has duplicate description '%s' (%s)\n", m_filename, shortname, swinfo.longname(), dupdesc.first->second->shortname());
bool const is_clone(!swinfo.parentname().empty());
if (is_clone)
{
if (swinfo.parentname() == shortname)
{
- osd_printf_error("%s: %s is set as a clone of itself\n", filename(), shortname);
+ osd_printf_error("%s: %s is set as a clone of itself\n", m_filename, shortname);
}
else
{
software_info const *const parent = find(swinfo.parentname());
if (!parent)
- osd_printf_error("%s: %s is a clone of non-existent parent %s\n", filename(), shortname, swinfo.parentname());
+ osd_printf_error("%s: %s is a clone of non-existent parent %s\n", m_filename, shortname, swinfo.parentname());
else if (!parent->parentname().empty())
- osd_printf_error("%s: %s is a clone %s which is a clone of %s\n", filename(), shortname, swinfo.parentname(), parent->parentname());
+ osd_printf_error("%s: %s is a clone %s which is a clone of %s\n", m_filename, shortname, swinfo.parentname(), parent->parentname());
}
}
// make sure the driver name isn't too long
if (shortname.length() > (is_clone ? NAME_LEN_CLONE : NAME_LEN_PARENT))
- osd_printf_error("%s: %s %s software name must be %d characters or less\n", filename(), shortname,
+ {
+ osd_printf_error(
+ "%s: %s %s software name must be %d characters or less\n",
+ m_filename,
+ shortname,
is_clone ? "clone" : "parent", is_clone ? NAME_LEN_CLONE : NAME_LEN_PARENT);
+ }
// make sure the driver name doesn't contain invalid characters
if (std::find_if_not(shortname.begin(), shortname.end(), valid_name_char) != shortname.end())
- osd_printf_error("%s: %s contains invalid characters\n", filename(), shortname);
+ osd_printf_error("%s: %s contains invalid characters\n", m_filename, shortname);
// make sure the year is only digits, '?' or '+'
if (std::find_if_not(swinfo.year().begin(), swinfo.year().end(), valid_year_char) != swinfo.year().end())
- osd_printf_error("%s: %s has an invalid year '%s'\n", filename(), shortname, swinfo.year());
+ osd_printf_error("%s: %s has an invalid year '%s'\n", m_filename, shortname, swinfo.year());
std::set<std::string> part_names;
for (software_part const &part : swinfo.parts())
{
if (part.interface().empty())
- osd_printf_error("%s: %s part %s has no interface\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s has no interface\n", m_filename, shortname, part.name());
if (part.romdata().empty())
- osd_printf_error("%s: %s part %s has no data areas\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s has no data areas\n", m_filename, shortname, part.name());
if (!part_names.emplace(part.name()).second)
- osd_printf_error("%s: %s part %s has duplicate name\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s has duplicate name\n", m_filename, shortname, part.name());
if (part.name().length() > NAME_LEN_PART)
- osd_printf_error("%s: %s part %s name must be %d characters or less\n", filename(), shortname, part.name(), NAME_LEN_PART);
+ osd_printf_error("%s: %s part %s name must be %d characters or less\n", m_filename, shortname, part.name(), NAME_LEN_PART);
if (std::find_if_not(part.name().begin(), part.name().end(), valid_name_char) != part.name().end())
- osd_printf_error("%s: %s part %s contains invalid characters\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s contains invalid characters\n", m_filename, shortname, part.name());
// validate data areas
// based on ROM validation code from validity.cpp but adapted to work with rom_entry and ignore unavailable features like BIOS
@@ -529,7 +555,7 @@ void software_list_device::internal_validity_check(validity_checker &valid)
{
// if we haven't seen any items since the last region, print a warning
if (!items_since_region)
- osd_printf_verbose("%s: %s part %s has empty data area '%s' (warning)\n", filename(), shortname, part.name(), last_region_name);
+ osd_printf_verbose("%s: %s part %s has empty data area '%s' (warning)\n", m_filename, shortname, part.name(), last_region_name);
// reset our region tracking states
items_since_region = (ROMREGION_ISERASE(romp) || ROMREGION_ISDISKDATA(romp)) ? 1 : 0;
@@ -537,31 +563,31 @@ void software_list_device::internal_validity_check(validity_checker &valid)
// check for a valid tag
if (romp->name().size() < MIN_TAG_LENGTH)
- osd_printf_error("%s: %s part %s data area name '%s' is too short (mut be at least %d characters)\n", filename(), shortname, part.name(), romp->name(), MIN_TAG_LENGTH);
+ osd_printf_error("%s: %s part %s data area name '%s' is too short (mut be at least %d characters)\n", m_filename, shortname, part.name(), romp->name(), MIN_TAG_LENGTH);
if (std::find_if_not(romp->name().begin(), romp->name().end(), valid_tag_char) != romp->name().end())
- osd_printf_error("%s: %s part %s data area name '%s' contains invalid characters\n", filename(), shortname, part.name(), romp->name());
+ osd_printf_error("%s: %s part %s data area name '%s' contains invalid characters\n", m_filename, shortname, part.name(), romp->name());
// attempt to add it to the map, reporting duplicates as errors
current_length = ROMREGION_GETLENGTH(romp);
if (!data_area_map.emplace(romp->name(), current_length).second)
- osd_printf_error("%s: %s part %s data area has duplicate name '%s'\n", filename(), shortname, part.name(), romp->name());
+ osd_printf_error("%s: %s part %s data area has duplicate name '%s'\n", m_filename, shortname, part.name(), romp->name());
}
else if (ROMENTRY_ISFILE(romp)) // if this is a file, make sure it is properly formatted
{
- // track the last filename we found
+ // track the last ROM label we found
last_name = romp->name().c_str();
// validate the name
if (romp->name().length() > 127)
- osd_printf_error("%s: %s part %s ROM label '%s' exceeds maximum 127 characters\n", filename(), shortname, part.name(), romp->name());
+ osd_printf_error("%s: %s part %s ROM label '%s' exceeds maximum 127 characters\n", m_filename, shortname, part.name(), romp->name());
if (std::find_if_not(romp->name().begin(), romp->name().end(), valid_label_char) != romp->name().end())
- osd_printf_error("%s: %s part %s ROM label '%s' contains invalid characters\n", filename(), shortname, part.name(), romp->name());
+ osd_printf_error("%s: %s part %s ROM label '%s' contains invalid characters\n", m_filename, shortname, part.name(), romp->name());
// make sure the hash is valid
util::hash_collection hashes;
if (!hashes.from_internal_string(romp->hashdata()))
- osd_printf_error("%s: %s part %s ROM '%s' has invalid hash string '%s'\n", filename(), shortname, part.name(), romp->name(), romp->hashdata());
+ osd_printf_error("%s: %s part %s ROM '%s' has invalid hash string '%s'\n", m_filename, shortname, part.name(), romp->name(), romp->hashdata());
}
// for any non-region ending entries, make sure they don't extend past the end
@@ -569,17 +595,17 @@ void software_list_device::internal_validity_check(validity_checker &valid)
{
items_since_region++;
if (!ROMENTRY_ISIGNORE(romp) && (ROM_GETOFFSET(romp) + ROM_GETLENGTH(romp) > current_length))
- osd_printf_error("%s: %s part %s ROM '%s' extends past the defined data area\n", filename(), shortname, part.name(), last_name);
+ osd_printf_error("%s: %s part %s ROM '%s' extends past the defined data area\n", m_filename, shortname, part.name(), last_name);
}
}
// if we haven't seen any items since the last region, print a warning
if (!items_since_region)
- osd_printf_verbose("%s: %s part %s has empty data area '%s' (warning)\n", filename(), shortname, part.name(), last_region_name);
+ osd_printf_verbose("%s: %s part %s has empty data area '%s' (warning)\n", m_filename, shortname, part.name(), last_region_name);
}
}
}
- // release all the memory
+ // discard parsed info
release();
}
diff --git a/src/emu/softlist_dev.h b/src/emu/softlist_dev.h
index 598ea413b4f..b0e774b9519 100644
--- a/src/emu/softlist_dev.h
+++ b/src/emu/softlist_dev.h
@@ -115,7 +115,6 @@ public:
bool is_original() const { return softlist_type::ORIGINAL_SYSTEM == m_list_type; }
bool is_compatible() const { return softlist_type::COMPATIBLE_SYSTEM == m_list_type; }
const char *filter() const { return m_filter; }
- const char *filename() { return m_file.filename(); }
// getters that may trigger a parse
const std::string &description() { if (!m_parsed) parse(); return m_description; }
@@ -152,7 +151,8 @@ private:
// internal state
bool m_parsed;
- emu_file m_file;
+ std::string m_filename;
+ std::string m_shortname;
std::string m_description;
std::string m_errors;
std::list<software_info> m_infolist;
diff --git a/src/frontend/mame/clifront.cpp b/src/frontend/mame/clifront.cpp
index 661337e4b51..47d3a6b3c2b 100644
--- a/src/frontend/mame/clifront.cpp
+++ b/src/frontend/mame/clifront.cpp
@@ -1090,9 +1090,9 @@ void cli_frontend::output_single_softlist(std::ostream &out, software_list_devic
util::stream_format(out, "\t\t<software name=\"%s\"", util::xml::normalize_string(swinfo.shortname().c_str()));
if (!swinfo.parentname().empty())
util::stream_format(out, " cloneof=\"%s\"", util::xml::normalize_string(swinfo.parentname().c_str()));
- if (swinfo.supported() == SOFTWARE_SUPPORTED_PARTIAL)
+ if (swinfo.supported() == software_support::PARTIALLY_SUPPORTED)
out << " supported=\"partial\"";
- if (swinfo.supported() == SOFTWARE_SUPPORTED_NO)
+ else if (swinfo.supported() == software_support::UNSUPPORTED)
out << " supported=\"no\"";
out << ">\n";
util::stream_format(out, "\t\t\t<description>%s</description>\n", util::xml::normalize_string(swinfo.longname().c_str()));
diff --git a/src/frontend/mame/ui/info.cpp b/src/frontend/mame/ui/info.cpp
index 3a57aac42c0..1c9e649dce7 100644
--- a/src/frontend/mame/ui/info.cpp
+++ b/src/frontend/mame/ui/info.cpp
@@ -576,13 +576,13 @@ void menu_image_info::image_info(device_image_interface *image)
// display supported information, if available
switch (swinfo.supported())
{
- case SOFTWARE_SUPPORTED_NO:
+ case software_support::UNSUPPORTED:
item_append(_("Not supported"), FLAG_DISABLE, nullptr);
break;
- case SOFTWARE_SUPPORTED_PARTIAL:
+ case software_support::PARTIALLY_SUPPORTED:
item_append(_("Partially supported"), FLAG_DISABLE, nullptr);
break;
- default:
+ case software_support::SUPPORTED:
break;
}
}
diff --git a/src/frontend/mame/ui/inifile.cpp b/src/frontend/mame/ui/inifile.cpp
index 089d58f3e77..f1e0346769a 100644
--- a/src/frontend/mame/ui/inifile.cpp
+++ b/src/frontend/mame/ui/inifile.cpp
@@ -237,7 +237,7 @@ favorite_manager::favorite_manager(ui_options &options)
file.gets(readbuf, 1024);
tmpmatches.publisher = chartrimcarriage(readbuf);
file.gets(readbuf, 1024);
- tmpmatches.supported = atoi(readbuf);
+ tmpmatches.supported = software_support(atoi(readbuf));
file.gets(readbuf, 1024);
tmpmatches.part = chartrimcarriage(readbuf);
file.gets(readbuf, 1024);
@@ -559,7 +559,7 @@ void favorite_manager::save_favorites()
buf << info.parentname << '\n';
buf << info.year << '\n';
buf << info.publisher << '\n';
- util::stream_format(buf, "%d\n", info.supported);
+ util::stream_format(buf, "%d\n", int(info.supported));
buf << info.part << '\n';
util::stream_format(buf, "%s\n", info.driver->name);
buf << info.listname << '\n';
diff --git a/src/frontend/mame/ui/selmenu.cpp b/src/frontend/mame/ui/selmenu.cpp
index b470291ab52..fb3f7087e27 100644
--- a/src/frontend/mame/ui/selmenu.cpp
+++ b/src/frontend/mame/ui/selmenu.cpp
@@ -683,12 +683,12 @@ void menu_select_launch::custom_render(void *selectedref, float top, float botto
tempbuf[2] = _("Software is parent");
// next line is supported status
- if (swinfo->supported == SOFTWARE_SUPPORTED_NO)
+ if (swinfo->supported == software_support::UNSUPPORTED)
{
tempbuf[3] = _("Supported: No");
color = UI_RED_COLOR;
}
- else if (swinfo->supported == SOFTWARE_SUPPORTED_PARTIAL)
+ else if (swinfo->supported == software_support::PARTIALLY_SUPPORTED)
{
tempbuf[3] = _("Supported: Partial");
color = UI_YELLOW_COLOR;
@@ -700,7 +700,7 @@ void menu_select_launch::custom_render(void *selectedref, float top, float botto
}
// last line is romset name
- tempbuf[4] = string_format(_("romset: %1$-.100s"), swinfo->shortname);
+ tempbuf[4] = string_format(_("Software list/item: %1$s:%2$s"), swinfo->listname, swinfo->shortname);
}
else if (driver)
{
diff --git a/src/frontend/mame/ui/selsoft.cpp b/src/frontend/mame/ui/selsoft.cpp
index 17d2461b20c..2ac32cce987 100644
--- a/src/frontend/mame/ui/selsoft.cpp
+++ b/src/frontend/mame/ui/selsoft.cpp
@@ -250,20 +250,8 @@ void menu_select_software::populate(float &customtop, float &custombottom)
icon.second.texture.reset();
uint32_t flags_ui = FLAG_LEFT_ARROW | FLAG_RIGHT_ARROW;
- m_has_empty_start = true;
int old_software = -1;
- // FIXME: why does it do this relatively expensive operation every time?
- machine_config config(m_driver, machine().options());
- for (device_image_interface &image : image_interface_enumerator(config.root_device()))
- {
- if (!image.filename() && image.must_be_loaded())
- {
- m_has_empty_start = false;
- break;
- }
- }
-
// start with an empty list
m_displaylist.clear();
filter_map::const_iterator const flt(m_filters.find(m_filter_type));
@@ -341,6 +329,17 @@ void menu_select_software::build_software_list()
machine_config config(m_driver, machine().options());
+ // see if any media devices require an image to be loaded
+ m_has_empty_start = true;
+ for (device_image_interface &image : image_interface_enumerator(config.root_device()))
+ {
+ if (!image.filename() && image.must_be_loaded())
+ {
+ m_has_empty_start = false;
+ break;
+ }
+ }
+
// iterate through all software lists
std::vector<std::size_t> orphans;
struct orphan_less
@@ -425,7 +424,7 @@ void menu_select_software::build_software_list()
}
std::string searchstr, curpath;
- for (auto & elem : m_filter_data.list_names())
+ for (auto &elem : m_filter_data.list_names())
{
path_iterator path(machine().options().media_path());
while (path.next(curpath))
diff --git a/src/frontend/mame/ui/utils.cpp b/src/frontend/mame/ui/utils.cpp
index ab1f3ae481e..794eae4bdef 100644
--- a/src/frontend/mame/ui/utils.cpp
+++ b/src/frontend/mame/ui/utils.cpp
@@ -20,7 +20,6 @@
#include "drivenum.h"
#include "rendfont.h"
#include "romload.h"
-#include "softlist.h"
#include "corestr.h"
@@ -1319,7 +1318,7 @@ class supported_software_filter : public simple_filter_impl_base<software_filter
public:
supported_software_filter(software_filter_data const &data, char const *value, emu_file *file, unsigned indent) { }
- virtual bool apply(ui_software_info const &info) const override { return SOFTWARE_SUPPORTED_YES == info.supported; }
+ virtual bool apply(ui_software_info const &info) const override { return software_support::SUPPORTED == info.supported; }
};
@@ -1329,7 +1328,7 @@ class partial_supported_software_filter : public simple_filter_impl_base<softwar
public:
partial_supported_software_filter(software_filter_data const &data, char const *value, emu_file *file, unsigned indent) { }
- virtual bool apply(ui_software_info const &info) const override { return SOFTWARE_SUPPORTED_PARTIAL == info.supported; }
+ virtual bool apply(ui_software_info const &info) const override { return software_support::PARTIALLY_SUPPORTED == info.supported; }
};
@@ -1338,7 +1337,7 @@ class unsupported_software_filter : public simple_filter_impl_base<software_filt
public:
unsupported_software_filter(software_filter_data const &data, char const *value, emu_file *file, unsigned indent) { }
- virtual bool apply(ui_software_info const &info) const override { return SOFTWARE_SUPPORTED_NO == info.supported; }
+ virtual bool apply(ui_software_info const &info) const override { return software_support::UNSUPPORTED == info.supported; }
};
diff --git a/src/frontend/mame/ui/utils.h b/src/frontend/mame/ui/utils.h
index b9a2f17dcfd..67320c19b6f 100644
--- a/src/frontend/mame/ui/utils.h
+++ b/src/frontend/mame/ui/utils.h
@@ -12,6 +12,9 @@
#pragma once
+#include "softlist.h"
+#include "unicode.h"
+
#include <algorithm>
#include <limits>
#include <memory>
@@ -19,8 +22,6 @@
#include <unordered_map>
#include <vector>
-#include "unicode.h"
-
class mame_ui_manager;
class render_container;
@@ -79,7 +80,7 @@ struct ui_software_info
std::string parentname;
std::string year;
std::string publisher;
- uint8_t supported = 0;
+ software_support supported = software_support::SUPPORTED;
std::string part;
game_driver const *driver = nullptr;
std::string listname;
diff --git a/src/mame/drivers/c128.cpp b/src/mame/drivers/c128.cpp
index 41022765674..262a8ad3988 100644
--- a/src/mame/drivers/c128.cpp
+++ b/src/mame/drivers/c128.cpp
@@ -44,6 +44,9 @@
#define CONTROL1_TAG "joy1"
#define CONTROL2_TAG "joy2"
+
+namespace {
+
class c128_state : public driver_device
{
public:
@@ -218,6 +221,7 @@ public:
int m_user_pa2;
int m_user_pb;
+ void softlists(machine_config &config, const char *filter);
void pal(machine_config &config);
void ntsc(machine_config &config);
void c128pal(machine_config &config);
@@ -1537,7 +1541,7 @@ WRITE_LINE_MEMBER( c128_state::exp_reset_w )
// SLOT_INTERFACE( c128dcr_iec_devices )
//-------------------------------------------------
-void c128dcr_iec_devices(device_slot_interface &device)
+[[maybe_unused]] void c128dcr_iec_devices(device_slot_interface &device)
{
device.option_add("c1571", C1571);
device.option_add("c1571cr", C1571CR);
@@ -1620,6 +1624,23 @@ void c128_state::machine_reset()
//**************************************************************************
//-------------------------------------------------
+// machine_config( softlists )
+//-------------------------------------------------
+
+void c128_state::softlists(machine_config &config, const char *filter)
+{
+ SOFTWARE_LIST(config, "cart_list").set_original("c128_cart").set_filter(filter);
+ SOFTWARE_LIST(config, "flop_list").set_original("c128_flop").set_filter(filter);
+ SOFTWARE_LIST(config, "from_list").set_original("c128_rom").set_filter(filter);
+ SOFTWARE_LIST(config, "cart_list_c64").set_original("c64_cart").set_filter(filter);
+ SOFTWARE_LIST(config, "cass_list_c64").set_original("c64_cass").set_filter(filter);
+ SOFTWARE_LIST(config, "cart_list_vic10").set_original("vic10").set_filter(filter);
+ SOFTWARE_LIST(config, "flop_list_c64_orig").set_compatible("c64_flop_orig").set_filter(filter);
+ SOFTWARE_LIST(config, "flop_list_c64_misc").set_compatible("c64_flop_misc").set_filter(filter);
+}
+
+
+//-------------------------------------------------
// machine_config( ntsc )
//-------------------------------------------------
@@ -1746,16 +1767,8 @@ void c128_state::ntsc(machine_config &config)
QUICKLOAD(config, "quickload", "p00,prg", CBM_QUICKLOAD_DELAY).set_load_callback(FUNC(c128_state::quickload_c128));
- // software list
- SOFTWARE_LIST(config, "cart_list").set_original("c128_cart").set_filter("NTSC");
- SOFTWARE_LIST(config, "flop_list").set_original("c128_flop").set_filter("NTSC");
- SOFTWARE_LIST(config, "from_list").set_original("c128_rom").set_filter("NTSC");
- SOFTWARE_LIST(config, "cart_list_c64").set_original("c64_cart").set_filter("NTSC");
- SOFTWARE_LIST(config, "cass_list_c64").set_original("c64_cass").set_filter("NTSC");
- SOFTWARE_LIST(config, "cart_list_vic10").set_original("vic10").set_filter("NTSC");
- // disk softlist split into originals and misc (homebrew and cracks)
- SOFTWARE_LIST(config, "flop525_orig").set_original("c64_flop_orig").set_filter("NTSC");
- SOFTWARE_LIST(config, "flop525_misc").set_compatible("c64_flop_misc").set_filter("NTSC");
+ // software lists
+ softlists(config, "NTSC");
// function ROM
GENERIC_SOCKET(config, "from", generic_plain_slot, "c128_rom", "bin,rom");
@@ -1934,20 +1947,7 @@ void c128_state::pal(machine_config &config)
QUICKLOAD(config, "quickload", "p00,prg", CBM_QUICKLOAD_DELAY).set_load_callback(FUNC(c128_state::quickload_c128));
// software list
- SOFTWARE_LIST(config, "cart_list_vic10").set_original("vic10");
- SOFTWARE_LIST(config, "cart_list_c64").set_original("c64_cart");
- SOFTWARE_LIST(config, "cart_list").set_original("c128_cart");
- SOFTWARE_LIST(config, "cass_list_c64").set_original("c64_cass");
- SOFTWARE_LIST(config, "flop_list_c64").set_original("c64_flop");
- SOFTWARE_LIST(config, "flop_list").set_original("c128_flop");
- SOFTWARE_LIST(config, "from_list").set_original("c128_rom");
- subdevice<software_list_device>("cart_list_vic10")->set_filter("PAL");
- subdevice<software_list_device>("cart_list_c64")->set_filter("PAL");
- subdevice<software_list_device>("cart_list")->set_filter("PAL");
- subdevice<software_list_device>("cass_list_c64")->set_filter("PAL");
- subdevice<software_list_device>("flop_list_c64")->set_filter("PAL");
- subdevice<software_list_device>("flop_list")->set_filter("PAL");
- subdevice<software_list_device>("from_list")->set_filter("PAL");
+ softlists(config, "PAL");
// function ROM
GENERIC_SOCKET(config, "from", generic_plain_slot, "c128_rom", "bin,rom");
@@ -2158,6 +2158,8 @@ ROM_START( c128dcr_se )
ROM_LOAD( "8721r3.u11", 0x000, 0xc88, BAD_DUMP CRC(154db186) SHA1(ccadcdb1db3b62c51dc4ce60fe6f96831586d297) )
ROM_END
+} // anonymous namespace
+
//**************************************************************************
diff --git a/src/mame/drivers/c64.cpp b/src/mame/drivers/c64.cpp
index dbaa50254f7..fdbcd20587d 100644
--- a/src/mame/drivers/c64.cpp
+++ b/src/mame/drivers/c64.cpp
@@ -1562,7 +1562,7 @@ void c64_state::ntsc(machine_config &config)
SOFTWARE_LIST(config, "cass_list").set_original("c64_cass").set_filter("NTSC");
// disk softlist split into originals and misc (homebrew and cracks)
SOFTWARE_LIST(config, "flop525_orig").set_original("c64_flop_orig").set_filter("NTSC");
- SOFTWARE_LIST(config, "flop525_misc").set_compatible("c64_flop_misc").set_filter("NTSC");
+ SOFTWARE_LIST(config, "flop525_misc").set_original("c64_flop_misc").set_filter("NTSC");
// internal ram
RAM(config, RAM_TAG).set_default_size("64K");
@@ -1735,7 +1735,7 @@ void c64_state::pal(machine_config &config)
SOFTWARE_LIST(config, "cass_list").set_original("c64_cass").set_filter("PAL");
// disk softlist split into originals and misc (homebrew and cracks)
SOFTWARE_LIST(config, "flop525_orig").set_original("c64_flop_orig").set_filter("PAL");
- SOFTWARE_LIST(config, "flop525_misc").set_compatible("c64_flop_misc").set_filter("PAL");
+ SOFTWARE_LIST(config, "flop525_misc").set_original("c64_flop_misc").set_filter("PAL");
// internal ram
RAM(config, RAM_TAG).set_default_size("64K");
diff --git a/src/mame/drivers/innotv_innotabmax.cpp b/src/mame/drivers/innotv_innotabmax.cpp
index 38ebc52d5f4..748f1aa6ca1 100644
--- a/src/mame/drivers/innotv_innotabmax.cpp
+++ b/src/mame/drivers/innotv_innotabmax.cpp
@@ -152,7 +152,7 @@ void vtech_innotv_innotabmax_state::vtech_innotv_innotabmax(machine_config &conf
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(vtech_innotv_innotabmax_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("vtech_innotv_innotabmax_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("vtech_innotv_cart");
}
ROM_START( innotv )
diff --git a/src/mame/drivers/leapfrog_iquest.cpp b/src/mame/drivers/leapfrog_iquest.cpp
index 0c7a03ee343..664522dc082 100644
--- a/src/mame/drivers/leapfrog_iquest.cpp
+++ b/src/mame/drivers/leapfrog_iquest.cpp
@@ -651,7 +651,7 @@ void leapfrog_turboextreme_state::leapfrog_turboex(machine_config &config)
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_turboextreme_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_turboextreme_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("turboextreme_cart");
}
void leapfrog_turbotwistmath_state::leapfrog_turbotwistmath(machine_config &config)
@@ -670,7 +670,7 @@ void leapfrog_turbotwistmath_state::leapfrog_turbotwistmath(machine_config &conf
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_turbotwistmath_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_turbotwistmath_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("ttwist_math_cart");
}
void leapfrog_turbotwistspelling_state::leapfrog_turbotwistspelling(machine_config &config)
@@ -689,7 +689,7 @@ void leapfrog_turbotwistspelling_state::leapfrog_turbotwistspelling(machine_conf
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_turbotwistspelling_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_turbotwistspelling_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("ttwist_spelling_cart");
}
void leapfrog_turbotwistvocabulator_state::leapfrog_turbotwistvocabulator(machine_config &config)
@@ -708,7 +708,7 @@ void leapfrog_turbotwistvocabulator_state::leapfrog_turbotwistvocabulator(machin
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_turbotwistvocabulator_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_turbotwistvocabulator_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("ttwist_vocabulator_cart");
}
@@ -728,7 +728,7 @@ void leapfrog_turbotwistbrainquest_state::leapfrog_turbotwistbrainquest(machine_
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_turbotwistbrainquest_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_turbotwistbrainquest_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("ttwist_brainquest_cart");
}
ROM_START( iquest )
diff --git a/src/mame/drivers/leapfrog_leapster_explorer.cpp b/src/mame/drivers/leapfrog_leapster_explorer.cpp
index af34683cb9c..27c63796f92 100644
--- a/src/mame/drivers/leapfrog_leapster_explorer.cpp
+++ b/src/mame/drivers/leapfrog_leapster_explorer.cpp
@@ -96,7 +96,7 @@ void leapfrog_leapster_explorer_state::leapfrog_leapster_explorer(machine_config
m_cart->set_width(GENERIC_ROM16_WIDTH);
m_cart->set_device_load(FUNC(leapfrog_leapster_explorer_state::cart_load));
- SOFTWARE_LIST(config, "cart_list").set_original("leapfrog_leapster_explorer_cart");
+ SOFTWARE_LIST(config, "cart_list").set_original("leapster_explorer_cart");
}
ROM_START( leapexpr )