summaryrefslogtreecommitdiffstatshomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/devices/bus/intv/slot.cpp2
-rw-r--r--src/emu/diimage.cpp26
-rw-r--r--src/emu/romload.cpp189
-rw-r--r--src/emu/romload.h5
-rw-r--r--src/emu/softlist_dev.cpp140
-rw-r--r--src/emu/validity.cpp2
-rw-r--r--src/frontend/mame/audit.cpp28
-rw-r--r--src/mame/drivers/gsword.cpp2
8 files changed, 195 insertions, 199 deletions
diff --git a/src/devices/bus/intv/slot.cpp b/src/devices/bus/intv/slot.cpp
index 0adca238eb1..c0c39d5613d 100644
--- a/src/devices/bus/intv/slot.cpp
+++ b/src/devices/bus/intv/slot.cpp
@@ -385,7 +385,7 @@ image_init_result intv_cart_slot_device::call_load()
else
{
uint16_t offset[] = { 0x400, 0x2000, 0x4000, 0x4800, 0x5000, 0x6000, 0x7000, 0x8000, 0x8800, 0x9000, 0xa000, 0xb000, 0xc000, 0xd000, 0xe000, 0xf000};
- const char* region_name[] = {"0400", "2000", "4000", "4800", "5000", "6000", "7000", "8000", "8800", "9000", "A000", "B000", "C000", "D000", "E000", "F000"};
+ const char* region_name[] = {"0400", "2000", "4000", "4800", "5000", "6000", "7000", "8000", "8800", "9000", "a000", "b000", "c000", "d000", "e000", "f000"};
const char *pcb_name = get_feature("slot");
bool extra_bank = false;
diff --git a/src/emu/diimage.cpp b/src/emu/diimage.cpp
index 4ec5ff7898c..8a38739933a 100644
--- a/src/emu/diimage.cpp
+++ b/src/emu/diimage.cpp
@@ -906,31 +906,7 @@ bool device_image_interface::load_software(software_list_device &swlist, const c
u32 crc = 0;
const bool has_crc = util::hash_collection(ROM_GETHASHDATA(romp)).crc(crc);
std::vector<const software_info *> parents;
- std::vector<std::string> searchpath;
-
- // search <rompath>/<list>/<software> following parents
- searchpath.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), swname));
- for (const software_info *i = swinfo; i && !i->parentname().empty(); i = swlist.find(i->parentname()))
- {
- if (std::find(parents.begin(), parents.end(), i) != parents.end())
- {
- osd_printf_warning("WARNING: parent/clone relationships form a loop for software %s (in list %s)\n", swname, swlist.list_name());
- break;
- }
- parents.emplace_back(i);
- searchpath.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), i->parentname()));
- }
-
- // search <rompath>/<software> following parents
- searchpath.emplace_back(swname);
- parents.clear();
- for (software_info const *i = swinfo; i && !i->parentname().empty(); i = swlist.find(i->parentname()))
- {
- if (std::find(parents.begin(), parents.end(), i) != parents.end())
- break;
- parents.emplace_back(i);
- searchpath.emplace_back(i->parentname());
- }
+ std::vector<std::string> searchpath = rom_load_manager::get_software_searchpath(swlist, *swinfo);
// for historical reasons, add the search path for the software list device's owner
const device_t *const listowner = swlist.owner();
diff --git a/src/emu/romload.cpp b/src/emu/romload.cpp
index 4018cdf923e..63c518a13fb 100644
--- a/src/emu/romload.cpp
+++ b/src/emu/romload.cpp
@@ -1,5 +1,5 @@
// license:BSD-3-Clause
-// copyright-holders:Nicola Salmoria,Paul Priest,Aaron Giles
+// copyright-holders:Nicola Salmoria,Paul Priest,Aaron Giles,Vas Crabb
/*********************************************************************
romload.cpp
@@ -30,27 +30,72 @@
#define TEMPBUFFER_MAX_SIZE (1024 * 1024 * 1024)
/***************************************************************************
- HELPERS (also used by diimage.cpp)
+ HELPERS
***************************************************************************/
namespace {
-rom_entry const *next_parent_system(game_driver const *&system, std::vector<rom_entry> &rom_entries)
+auto next_parent_system(game_driver const &system)
{
- if (!system)
- return nullptr;
- int const parent(driver_list::find(system->parent));
- if (0 > parent)
- {
- system = nullptr;
- return nullptr;
- }
- else
+ return
+ [sys = &system, roms = std::vector<rom_entry>()] () mutable -> rom_entry const *
+ {
+ if (!sys)
+ return nullptr;
+ int const parent(driver_list::find(sys->parent));
+ if (0 > parent)
+ {
+ sys = nullptr;
+ return nullptr;
+ }
+ else
+ {
+ sys = &driver_list::driver(parent);
+ roms = rom_build_entries(sys->rom);
+ return &roms[0];
+ }
+ };
+}
+
+
+auto next_parent_software(std::vector<software_info const *> const &parents)
+{
+ auto part(parents.front()->parts().end());
+ return
+ [&parents, current = parents.cbegin(), part, end = part] () mutable -> const rom_entry *
+ {
+ if (part == end)
+ {
+ if (parents.end() == current)
+ return nullptr;
+ part = (*current)->parts().cbegin();
+ end = (*current)->parts().cend();
+ do { ++current; } while ((parents.cend() != current) && (*current)->parts().empty());
+ }
+ return &(*part++).romdata()[0];
+ };
+}
+
+
+std::vector<std::string> make_software_searchpath(software_list_device &swlist, software_info const &swinfo, std::vector<software_info const *> &parents)
+{
+ std::vector<std::string> result;
+
+ // search <rompath>/<list>/<software> following parents
+ for (software_info const *i = &swinfo; i; )
{
- system = &driver_list::driver(parent);
- rom_entries = rom_build_entries(system->rom);
- return &rom_entries[0];
+ if (std::find(parents.begin(), parents.end(), i) != parents.end())
+ break;
+ parents.emplace_back(i);
+ result.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), i->shortname()));
+ i = i->parentname().empty() ? nullptr : swlist.find(i->parentname());
}
+
+ // search <rompath>/<software> following parents
+ for (software_info const *i : parents)
+ result.emplace_back(i->shortname());
+
+ return result;
}
@@ -1068,6 +1113,23 @@ void rom_load_manager::process_disk_entries(std::initializer_list<std::reference
}
+/*-------------------------------------------------
+ get_software_searchpath - get search path
+ for a software list item
+-------------------------------------------------*/
+
+std::vector<std::string> rom_load_manager::get_software_searchpath(software_list_device &swlist, const software_info &swinfo)
+{
+ std::vector<software_info const *> parents;
+ return make_software_searchpath(swlist, swinfo, parents);
+}
+
+
+/*-------------------------------------------------
+ open_disk_image - open a disk image for a
+ device
+-------------------------------------------------*/
+
chd_error rom_load_manager::open_disk_image(const emu_options &options, const device_t &device, const rom_entry *romp, chd_file &image_chd)
{
const std::vector<std::string> searchpath(device.searchpath());
@@ -1075,47 +1137,24 @@ chd_error rom_load_manager::open_disk_image(const emu_options &options, const de
driver_device const *const driver(dynamic_cast<driver_device const *>(&device));
std::function<const rom_entry * ()> next_parent;
if (driver)
- next_parent = [sys = &driver->system(), roms = std::vector<rom_entry>()] () mutable { return next_parent_system(sys, roms); };
+ next_parent = next_parent_system(driver->system());
else
next_parent = [] () { return nullptr; };
return do_open_disk(options, { searchpath }, romp, image_chd, std::move(next_parent));
}
+/*-------------------------------------------------
+ open_disk_image - open a disk image for a
+ software item
+-------------------------------------------------*/
+
chd_error rom_load_manager::open_disk_image(const emu_options &options, software_list_device &swlist, const software_info &swinfo, const rom_entry *romp, chd_file &image_chd)
{
std::vector<software_info const *> parents;
- std::vector<std::string> listsearch, freesearch, disksearch;
- disksearch.emplace_back(swlist.list_name());
-
- for (software_info const *i = &swinfo; i; )
- {
- if (std::find(parents.begin(), parents.end(), i) != parents.end())
- break;
- parents.emplace_back(i);
- listsearch.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), i->shortname()));
- freesearch.emplace_back(i->shortname());
- i = i->parentname().empty() ? nullptr : swlist.find(i->parentname());
- }
-
- auto part(parents.front()->parts().end());
- return do_open_disk(
- options,
- { listsearch, freesearch, disksearch },
- romp,
- image_chd,
- [&parents, current = parents.cbegin(), part, end = part] () mutable -> const rom_entry *
- {
- if (part == end)
- {
- if (parents.end() == current)
- return nullptr;
- part = (*current)->parts().cbegin();
- end = (*current)->parts().cend();
- do { ++current; } while ((parents.cend() != current) && (*current)->parts().empty());
- }
- return &(*part++).romdata()[0];
- });
+ std::vector<std::string> searchpath = make_software_searchpath(swlist, swinfo, parents);
+ searchpath.emplace_back(swlist.list_name()); // look for loose disk images in software list directory
+ return do_open_disk(options, { searchpath }, romp, image_chd, next_parent_software(parents));
}
@@ -1175,10 +1214,8 @@ void rom_load_manager::load_software_part_region(device_t &device, software_list
m_romsloadedsize = 0;
std::vector<const software_info *> parents;
- std::vector<std::string> listsearch, freesearch, disksearch, devsearch;
- listsearch.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), swname));
- freesearch.emplace_back(swname);
- const software_info *swinfo = swlist.find(swname);
+ std::vector<std::string> swsearch, disksearch, devsearch;
+ const software_info *const swinfo = swlist.find(swname);
if (swinfo)
{
// dispay a warning for unsupported software
@@ -1196,21 +1233,12 @@ void rom_load_manager::load_software_part_region(device_t &device, software_list
}
// walk the chain of parents and add them to the search path
- parents.emplace_back(swinfo);
- swinfo = !swinfo->parentname().empty() ? swlist.find(swinfo->parentname()) : nullptr;
- while (swinfo)
- {
- if (std::find(parents.begin(), parents.end(), swinfo) != parents.end())
- {
- m_errorstring.append(util::string_format("WARNING: parent/clone relationships form a loop for software %s (in list %s)\n", swname, swlist.list_name()));
- m_softwarningstring.append(util::string_format("Parent/clone relationships from a loop for software %s (in list %s)\n", swname, swlist.list_name()));
- break;
- }
- parents.emplace_back(swinfo);
- listsearch.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), swinfo->shortname()));
- freesearch.emplace_back(swinfo->shortname());
- swinfo = !swinfo->parentname().empty() ? swlist.find(swinfo->parentname()) : nullptr;
- }
+ swsearch = make_software_searchpath(swlist, *swinfo, parents);
+ }
+ else
+ {
+ swsearch.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), swname));
+ swsearch.emplace_back(swname);
}
// this is convenient for CD-only lists so you don't need an extra level of directories containing one file each
@@ -1269,40 +1297,23 @@ void rom_load_manager::load_software_part_region(device_t &device, software_list
if (ROMREGION_ISROMDATA(region))
{
if (devsearch.empty())
- process_rom_entries({ listsearch, freesearch }, 0U, region, region + 1, true);
+ process_rom_entries({ swsearch }, 0U, region, region + 1, true);
else
- process_rom_entries({ listsearch, freesearch, devsearch }, 0U, region, region + 1, true);
+ process_rom_entries({ swsearch, devsearch }, 0U, region, region + 1, true);
}
else if (ROMREGION_ISDISKDATA(region))
{
if (!next_parent)
{
if (!parents.empty())
- {
- auto part(parents.front()->parts().end());
- next_parent =
- [&parents, current = parents.cbegin(), part, end = part] () mutable -> const rom_entry *
- {
- if (part == end)
- {
- if (parents.end() == current)
- return nullptr;
- part = (*current)->parts().cbegin();
- end = (*current)->parts().cend();
- do { ++current; } while ((parents.cend() != current) && (*current)->parts().empty());
- }
- return &(*part++).romdata()[0];
- };
- }
+ next_parent = next_parent_software(parents);
else
- {
next_parent = [] () { return nullptr; };
- }
}
if (devsearch.empty())
- process_disk_entries({ listsearch, freesearch, disksearch }, regiontag.c_str(), region + 1, next_parent);
+ process_disk_entries({ swsearch, disksearch }, regiontag.c_str(), region + 1, next_parent);
else
- process_disk_entries({ listsearch, freesearch, disksearch, devsearch }, regiontag.c_str(), region + 1, next_parent);
+ process_disk_entries({ swsearch, disksearch, devsearch }, regiontag.c_str(), region + 1, next_parent);
}
}
@@ -1373,7 +1384,7 @@ void rom_load_manager::process_region_list()
{
driver_device const *const driver(dynamic_cast<driver_device const *>(&device));
if (driver)
- next_parent = [sys = &driver->system(), roms = std::vector<rom_entry>()] () mutable { return next_parent_system(sys, roms); };
+ next_parent = next_parent_system(driver->system());
else
next_parent = [] () { return nullptr; };
}
diff --git a/src/emu/romload.h b/src/emu/romload.h
index 7db106a52ce..ca725f0e0fb 100644
--- a/src/emu/romload.h
+++ b/src/emu/romload.h
@@ -1,5 +1,5 @@
// license:BSD-3-Clause
-// copyright-holders:Nicola Salmoria,Aaron Giles
+// copyright-holders:Nicola Salmoria,Aaron Giles,Vas Crabb
/*********************************************************************
romload.h
@@ -423,6 +423,9 @@ public:
void load_software_part_region(device_t &device, software_list_device &swlist, const char *swname, const rom_entry *start_region);
+ /* get search path for a software item */
+ static std::vector<std::string> get_software_searchpath(software_list_device &swlist, const software_info &swinfo);
+
/* open a disk image, searching up the parent and loading by checksum */
static chd_error open_disk_image(const emu_options &options, const device_t &device, const rom_entry *romp, chd_file &image_chd);
static chd_error open_disk_image(const emu_options &options, software_list_device &swlist, const software_info &swinfo, const rom_entry *romp, chd_file &image_chd);
diff --git a/src/emu/softlist_dev.cpp b/src/emu/softlist_dev.cpp
index d33e357ebc7..f3c584d1c4a 100644
--- a/src/emu/softlist_dev.cpp
+++ b/src/emu/softlist_dev.cpp
@@ -421,14 +421,15 @@ 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 };
+ enum { 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 == '+'); };
softlist_map names;
softlist_map descriptions;
for (const software_info &swinfo : get_info())
{
- std::string const &shortname(swinfo.shortname());
-
// first parse and output core errors if any
if (m_errors.length() > 0)
{
@@ -437,48 +438,32 @@ void software_list_device::internal_validity_check(validity_checker &valid)
}
// Now check if the xml data is valid:
+ std::string const &shortname(swinfo.shortname());
- // Did we lost any description?
if (swinfo.longname().empty())
- {
osd_printf_error("%s: %s has no description\n", filename(), shortname);
- break;
- }
- // Did we lost any year?
if (swinfo.year().empty())
- {
osd_printf_error("%s: %s has no year\n", filename(), shortname);
- break;
- }
- // Did we lost any publisher?
if (swinfo.publisher().empty())
- {
osd_printf_error("%s: %s has no publisher\n", filename(), shortname);
- break;
- }
// Did we lost the software parts?
if (swinfo.parts().empty())
- {
- osd_printf_error("%s: %s has no part\n", filename(), shortname);
- break;
- }
+ osd_printf_error("%s: %s has no parts\n", filename(), shortname);
// Second, since the xml is fine, run additional checks:
// check for duplicate names
- if (!names.insert(std::make_pair(shortname, &swinfo)).second)
- {
- const software_info *match = names.find(shortname)->second;
- osd_printf_error("%s: %s is a duplicate name (%s)\n", filename(), shortname, match->shortname());
- }
+ 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());
// check for duplicate descriptions
- std::string longname(swinfo.longname());
- if (!descriptions.insert(std::make_pair(strmakelower(longname), &swinfo)).second)
- osd_printf_error("%s: %s is a duplicate description (%s)\n", filename(), swinfo.longname(), shortname);
+ 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());
bool const is_clone(!swinfo.parentname().empty());
if (is_clone)
@@ -486,16 +471,15 @@ void software_list_device::internal_validity_check(validity_checker &valid)
if (swinfo.parentname() == shortname)
{
osd_printf_error("%s: %s is set as a clone of itself\n", filename(), shortname);
- break;
}
-
- // make sure the parent exists
- const software_info *swinfo2 = find(swinfo.parentname());
-
- if (swinfo2 == nullptr)
- osd_printf_error("%s: parent '%s' software for '%s' not found\n", filename(), swinfo.parentname(), shortname);
- else if (!swinfo2->parentname().empty())
- osd_printf_error("%s: %s is a clone of a clone\n", 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());
+ 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());
+ }
}
// make sure the driver name isn't too long
@@ -504,32 +488,80 @@ void software_list_device::internal_validity_check(validity_checker &valid)
is_clone ? "clone" : "parent", is_clone ? NAME_LEN_CLONE : NAME_LEN_PARENT);
// make sure the driver name doesn't contain invalid characters
- for (char ch : shortname)
- if (((ch < '0') || (ch > '9')) && ((ch < 'a') || (ch > 'z')) && (ch != '_'))
- {
- osd_printf_error("%s: %s contains invalid characters\n", filename(), shortname);
- break;
- }
+ 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);
// make sure the year is only digits, '?' or '+'
- for (char ch : swinfo.year())
- if (!isdigit(u8(ch)) && (ch != '?') && (ch != '+'))
- {
- osd_printf_error("%s: %s has an invalid year '%s'\n", filename(), shortname, swinfo.year());
- break;
- }
+ 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());
- softlist_map part_names;
- for (const software_part &part : swinfo.parts())
+ std::set<std::string> part_names;
+ for (software_part const &part : swinfo.parts())
{
if (part.interface().empty())
- osd_printf_error("%s: %s has a part (%s) without interface\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s has no interface\n", filename(), shortname, part.name());
if (part.romdata().empty())
- osd_printf_error("%s: %s has a part (%s) with no data\n", filename(), shortname, part.name());
+ osd_printf_error("%s: %s part %s has no data areas\n", 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());
+
+ 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);
+
+ 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());
+
+ // validate data areas
+ // based on ROM validation code from validity.cpp but adapted to work with rom_entry and ignore unavailable features like BIOS
+ if (!part.romdata().empty())
+ {
+ std::map<std::string, u32> data_area_map;
+ char const *last_region_name = "???";
+ char const *last_name = "???";
+ u32 current_length = 0;
+ int items_since_region = 1;
+ for (rom_entry const *romp = &part.romdata().front(); romp && !ROMENTRY_ISEND(romp); ++romp)
+ {
+ if (ROMENTRY_ISREGION(romp)) // if this is a region, make sure it's valid, and record the length
+ {
+ // reset our region tracking states
+ items_since_region = (ROMREGION_ISERASE(romp) || ROMREGION_ISDISKDATA(romp)) ? 1 : 0;
+ last_region_name = romp->name().c_str();
- if (!part_names.insert(std::make_pair(part.name(), &swinfo)).second)
- osd_printf_error("%s: %s has a part (%s) whose name is duplicate\n", filename(), shortname, part.name());
+ // 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);
+
+ 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());
+
+ // 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());
+ }
+ else if (ROMENTRY_ISFILE(romp)) // if this is a file, make sure it is properly formatted
+ {
+ // track the last filename we found
+ last_name = romp->name().c_str();
+
+ // make sure the hash is valid
+ util::hash_collection hashes;
+ if (!hashes.from_internal_string(romp->hashdata().c_str()))
+ osd_printf_error("%s: %s part %s ROM '%s' has invalid hash string '%s'\n", filename(), shortname, part.name(), romp->name(), romp->hashdata());
+ }
+
+ // for any non-region ending entries, make sure they don't extend past the end
+ if (!ROMENTRY_ISREGIONEND(romp) && current_length > 0)
+ {
+ 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);
+ }
+ }
+ }
}
}
diff --git a/src/emu/validity.cpp b/src/emu/validity.cpp
index 868f7c96935..3c402487bf4 100644
--- a/src/emu/validity.cpp
+++ b/src/emu/validity.cpp
@@ -1550,7 +1550,7 @@ void validity_checker::validate_roms(device_t &root)
// attempt to add it to the map, reporting duplicates as errors
current_length = ROMREGION_GETLENGTH(romp);
- if (!m_region_map.insert(std::make_pair(fulltag, current_length)).second)
+ if (!m_region_map.emplace(fulltag, current_length).second)
osd_printf_error("Multiple ROM_REGIONs with the same tag '%s' defined\n", fulltag);
}
else if (ROMENTRY_ISSYSTEM_BIOS(romp)) // If this is a system bios, make sure it is using the next available bios number
diff --git a/src/frontend/mame/audit.cpp b/src/frontend/mame/audit.cpp
index 3ff706d2c8a..6f2157a3ac4 100644
--- a/src/frontend/mame/audit.cpp
+++ b/src/frontend/mame/audit.cpp
@@ -187,33 +187,7 @@ media_auditor::summary media_auditor::audit_software(software_list_device &swlis
if (ROMREGION_ISROMDATA(region))
{
if (searchpath.empty())
- {
- std::vector<software_info const *> parents;
-
- // search <rompath>/<list>/<software> following parents
- searchpath.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), swinfo.shortname()));
- for (software_info const *i = &swinfo; i && !i->parentname().empty(); i = swlist.find(i->parentname()))
- {
- if (std::find(parents.begin(), parents.end(), i) != parents.end())
- {
- osd_printf_warning("WARNING: software parent/clone relationships form a loop (%s:%s)\n", swlist.list_name(), swinfo.shortname());
- break;
- }
- parents.emplace_back(i);
- searchpath.emplace_back(util::string_format("%s" PATH_SEPARATOR "%s", swlist.list_name(), i->parentname()));
- }
-
- // search <rompath>/<software> following parents
- searchpath.emplace_back(swinfo.shortname());
- parents.clear();
- for (software_info const *i = &swinfo; i && !i->parentname().empty(); i = swlist.find(i->parentname()))
- {
- if (std::find(parents.begin(), parents.end(), i) != parents.end())
- break;
- parents.emplace_back(i);
- searchpath.emplace_back(i->parentname());
- }
- }
+ searchpath = rom_load_manager::get_software_searchpath(swlist, swinfo);
return &audit_one_rom(searchpath, rom);
}
else if (ROMREGION_ISDISKDATA(region))
diff --git a/src/mame/drivers/gsword.cpp b/src/mame/drivers/gsword.cpp
index 6183e5ef561..a8f31293a9c 100644
--- a/src/mame/drivers/gsword.cpp
+++ b/src/mame/drivers/gsword.cpp
@@ -230,7 +230,7 @@ clock is supplied to both communication MCUs on T0. Outputs are set
after detecting a rising edge on T0, and inputs are read after detecting
a falling edge on T0.
-A frame consists to five bytes send LSB first. Each byte is followed by
+A frame consists to five bytes sent LSB first. Each byte is followed by
an odd parity bit. Useful addresses for debugging communication:
* $12A: Function for sending a frame from $21..$25
* $159: Function for receiving a frame to $29..$2D