diff options
author | 2010-06-20 19:25:53 +0000 | |
---|---|---|
committer | 2010-06-20 19:25:53 +0000 | |
commit | 869144aa7031357e8a653069b9136ef27e72f014 (patch) | |
tree | 415949d39caa86f64737328a025f039a4f7eb536 /src/emu/clifront.c | |
parent | cbe7260a5953492a372699aab4bd5ca8e46c0cf8 (diff) |
Moved listsofware command line option from MESS, and added softlist in XML output [Miodrag Milanovic]
Diffstat (limited to 'src/emu/clifront.c')
-rw-r--r-- | src/emu/clifront.c | 282 |
1 files changed, 273 insertions, 9 deletions
diff --git a/src/emu/clifront.c b/src/emu/clifront.c index 6a08cb7de1a..6879351f4b5 100644 --- a/src/emu/clifront.c +++ b/src/emu/clifront.c @@ -19,6 +19,7 @@ #include "validity.h" #include "sound/samples.h" #include "clifront.h" +#include "xmlfile.h" #include <new> #include <ctype.h> @@ -56,6 +57,7 @@ static int info_verifyroms(core_options *options, const char *gamename); static int info_verifysamples(core_options *options, const char *gamename); static int info_romident(core_options *options, const char *gamename); static int info_listmedia(core_options *opts, const char *gamename); +static int info_listsoftware(core_options *options, const char *gamename); /* utilities */ static void romident(core_options *options, const char *filename, romident_status *status); @@ -97,10 +99,8 @@ static const options_entry cli_options[] = { "romident", "0", OPTION_COMMAND, "compare files with known MAME roms" }, { "listdevices;ld", "0", OPTION_COMMAND, "list available devices" }, { "listmedia;lm", "0", OPTION_COMMAND, "list available media for the system" }, -#ifdef MESS { "listsoftware", "0", OPTION_COMMAND, "list known software for the system" }, -#endif - + { NULL } }; @@ -275,9 +275,7 @@ static int execute_commands(core_options *options, const char *exename, const ga { CLIOPTION_VERIFYROMS, info_verifyroms }, { CLIOPTION_VERIFYSAMPLES, info_verifysamples }, { CLIOPTION_LISTMEDIA, info_listmedia }, -#ifdef MESS { CLIOPTION_LISTSOFTWARE, info_listsoftware }, -#endif { CLIOPTION_ROMIDENT, info_romident } }; int i; @@ -776,6 +774,274 @@ static int info_verifyroms(core_options *options, const char *gamename) } } +/*------------------------------------------------- + info_listsoftware - output the list of + software supported by a given game or set of + games + TODO: Add all information read from the source files + Possible improvement: use a sorted list for + identifying duplicate lists. +-------------------------------------------------*/ + +static int info_listsoftware(core_options *options, const char *gamename) +{ + FILE *out = stdout; + int nr_lists = 0; + char ** lists = NULL; + int list_idx = 0; + + /* First determine the maximum number of lists we might encounter */ + for ( int drvindex = 0; drivers[drvindex] != NULL; drvindex++ ) + { + if ( mame_strwildcmp( gamename, drivers[drvindex]->name ) == 0 ) + { + /* allocate the machine config */ + machine_config *config = machine_config_alloc( drivers[drvindex]->machine_config ); + + for (const device_config *dev = config->devicelist.first(); dev != NULL; dev = dev->next()) + { + if ( ! strcmp( dev->tag(), __SOFTWARE_LIST_TAG ) ) + { + software_list_config *swlist = (software_list_config *)downcast<const legacy_device_config_base *>(dev)->inline_config(); + + for ( int i = 0; i < DEVINFO_STR_SWLIST_MAX - DEVINFO_STR_SWLIST_0; i++ ) + { + if ( swlist->list_name[i] && *swlist->list_name[i] ) + nr_lists++; + } + } + } + + /* free the machine config */ + machine_config_free( config ); + } + } + + lists = global_alloc_array( char *, nr_lists ); + + fprintf( out, + "<?xml version=\"1.0\"?>\n" + "<!DOCTYPE softwarelist [\n" + "<!ELEMENT softwarelists (softwarelist*)>\n" + "\t<!ELEMENT softwarelist (software+)>\n" + "\t\t<!ATTLIST softwarelist name CDATA #REQUIRED>\n" + "\t\t<!ATTLIST softwarelist description CDATA #IMPLIED>\n" + "\t\t<!ELEMENT software (description, year?, publisher, part*)>\n" + "\t\t\t<!ATTLIST software name CDATA #REQUIRED>\n" + "\t\t\t<!ATTLIST software cloneof CDATA #IMPLIED>\n" + "\t\t\t<!ATTLIST software supported (yes|partial|no) \"yes\">\n" + "\t\t\t<!ELEMENT description (#PCDATA)>\n" + "\t\t\t<!ELEMENT year (#PCDATA)>\n" + "\t\t\t<!ELEMENT publisher (#PCDATA)>\n" + "\t\t\t<!ELEMENT part (dataarea*)>\n" + "\t\t\t\t<!ATTLIST part name CDATA #REQUIRED>\n" + "\t\t\t\t<!ATTLIST part interface CDATA #REQUIRED>\n" + "\t\t\t\t<!ATTLIST part feature CDATA #IMPLIED>\n" + "\t\t\t\t<!ELEMENT dataarea (rom*)>\n" + "\t\t\t\t\t<!ATTLIST dataarea name CDATA #REQUIRED>\n" + "\t\t\t\t\t<!ATTLIST dataarea size CDATA #REQUIRED>\n" + "\t\t\t\t\t<!ATTLIST dataarea databits (8|16|32|64) \"8\">\n" + "\t\t\t\t\t<!ATTLIST dataarea endian (big|little) \"little\">\n" + "\t\t\t\t\t<!ELEMENT rom EMPTY>\n" + "\t\t\t\t\t\t<!ATTLIST rom name CDATA #IMPLIED>\n" + "\t\t\t\t\t\t<!ATTLIST rom size CDATA #REQUIRED>\n" + "\t\t\t\t\t\t<!ATTLIST rom crc CDATA #IMPLIED>\n" + "\t\t\t\t\t\t<!ATTLIST rom md5 CDATA #IMPLIED>\n" + "\t\t\t\t\t\t<!ATTLIST rom sha1 CDATA #IMPLIED>\n" + "\t\t\t\t\t\t<!ATTLIST rom offset CDATA #IMPLIED>\n" + "\t\t\t\t\t\t<!ATTLIST rom status (baddump|nodump|good) \"good\">\n" + "\t\t\t\t\t\t<!ATTLIST rom loadflag (load16_byte|load16_word|load16_word_swap|load32_byte|load32_word|load32_word_swap|load32_dword|load64_word|load64_word_swap|reload) #IMPLIED>\n" + "]>\n\n" + "<softwarelists>\n" + ); + + for ( int drvindex = 0; drivers[drvindex] != NULL; drvindex++ ) + { + if ( mame_strwildcmp( gamename, drivers[drvindex]->name ) == 0 ) + { + /* allocate the machine config */ + machine_config *config = machine_config_alloc( drivers[drvindex]->machine_config ); + + for (const device_config *dev = config->devicelist.first(); dev != NULL; dev = dev->next()) + { + if ( ! strcmp( dev->tag(), __SOFTWARE_LIST_TAG ) ) + { + software_list_config *swlist = (software_list_config *)downcast<const legacy_device_config_base *>(dev)->inline_config(); + + for ( int i = 0; i < DEVINFO_STR_SWLIST_MAX - DEVINFO_STR_SWLIST_0; i++ ) + { + if ( swlist->list_name[i] && *swlist->list_name[i] ) + { + software_list *list = software_list_open( options, swlist->list_name[i], FALSE, NULL ); + + if ( list ) + { + /* Verify if we have encountered this list before */ + bool seen_before = false; + for ( int l = 0; l < list_idx && !seen_before; l++ ) + { + if ( ! strcmp( swlist->list_name[i], lists[l] ) ) + { + seen_before = true; + } + } + + if ( ! seen_before ) + { + lists[list_idx] = core_strdup( swlist->list_name[i] ); + list_idx++; + + fprintf(out, "\t<softwarelist name=\"%s\">\n", swlist->list_name[i] ); + + for ( software_info *swinfo = software_list_first( list ); swinfo != NULL; swinfo = software_list_next( list ) ) + { + fprintf( out, "\t\t<software name=\"%s\"", swinfo->shortname ); + if ( swinfo->parentname != NULL ) + fprintf( out, " cloneof=\"%s\"", swinfo->parentname ); + if ( swinfo->supported == SOFTWARE_SUPPORTED_PARTIAL ) + fprintf( out, " supported=\"partial\"" ); + if ( swinfo->supported == SOFTWARE_SUPPORTED_NO ) + fprintf( out, " supported=\"no\"" ); + fprintf( out, ">\n" ); + fprintf( out, "\t\t\t<description>%s</description>\n", xml_normalize_string(swinfo->longname) ); + fprintf( out, "\t\t\t<year>%s</year>\n", xml_normalize_string( swinfo->year ) ); + fprintf( out, "\t\t\t<publisher>%s</publisher>\n", xml_normalize_string( swinfo->publisher ) ); + + for ( software_part *part = software_find_part( swinfo, NULL, NULL ); part != NULL; part = software_part_next( part ) ) + { + fprintf( out, "\t\t\t<part name=\"%s\"", part->name ); + if ( part->interface_ ) + fprintf( out, " interface=\"%s\"", part->interface_ ); +// if ( part->feature ) +// fprintf( out, " features=\"%s\"", part->feature ); + fprintf( out, ">\n"); + + /* TODO: display rom region information */ + for ( const rom_entry *region = part->romdata; region; region = rom_next_region( region ) ) + { + fprintf( out, "\t\t\t\t<dataarea name=\"%s\" size=\"%x\">\n", ROMREGION_GETTAG(region), ROMREGION_GETLENGTH(region) ); + + for ( const rom_entry *rom = rom_first_file( region ); rom && !ROMENTRY_ISREGIONEND(rom); rom++ ) + { + if ( ROMENTRY_ISFILE(rom) ) + { + fprintf( out, "\t\t\t\t\t<rom name=\"%s\" size=\"%d\"", xml_normalize_string(ROM_GETNAME(rom)), rom_file_size(rom) ); + + /* dump checksum information only if there is a known dump */ + if (!hash_data_has_info(ROM_GETHASHDATA(rom), HASH_INFO_NO_DUMP)) + { + char checksum[HASH_BUF_SIZE]; + int hashtype; + + /* iterate over hash function types and print out their values */ + for (hashtype = 0; hashtype < HASH_NUM_FUNCTIONS; hashtype++) + if (hash_data_extract_printable_checksum(ROM_GETHASHDATA(rom), 1 << hashtype, checksum)) + fprintf(out, " %s=\"%s\"", hash_function_name(1 << hashtype), checksum); + } + + fprintf( out, " offset=\"%x\"", ROM_GETOFFSET(rom) ); + + if ( hash_data_has_info(ROM_GETHASHDATA(rom), HASH_INFO_BAD_DUMP) ) + fprintf( out, " status=\"baddump\"" ); + if ( hash_data_has_info(ROM_GETHASHDATA(rom), HASH_INFO_NO_DUMP) ) + fprintf( out, " status=\"nodump\"" ); + + fprintf( out, "/>\n" ); + } + else if ( ROMENTRY_ISRELOAD(rom) ) + { + fprintf( out, "\t\t\t\t\t<rom size=\"%d\" offset=\"%x\" loadflag=\"reload\" />\n", ROM_GETLENGTH(rom), ROM_GETOFFSET(rom) ); + } + } + + fprintf( out, "\t\t\t\t</dataarea>\n" ); + } + + fprintf( out, "\t\t\t</part>\n" ); + } + + fprintf( out, "\t\t</software>\n" ); + } + + fprintf(out, "\t</softwarelist>\n" ); + } + + software_list_close( list ); + } + } + } + } + } + + machine_config_free( config ); + } + } + + fprintf( out, "</softwarelists>\n" ); + + global_free( lists ); + + return MAMERR_NONE; +} + + +/*------------------------------------------------- + softlist_match_roms - scan for a matching + software ROM by hash +-------------------------------------------------*/ +static void softlist_match_roms(core_options *options, const char *hash, int length, int *found) +{ + int drvindex; + + /* iterate over drivers */ + for (drvindex = 0; drivers[drvindex] != NULL; drvindex++) + { + machine_config *config = machine_config_alloc(drivers[drvindex]->machine_config); + + for (const device_config *dev = config->devicelist.first(); dev != NULL; dev = dev->next()) + { + if ( ! strcmp( dev->tag(), __SOFTWARE_LIST_TAG ) ) + { + software_list_config *swlist = (software_list_config *)downcast<const legacy_device_config_base *>(dev)->inline_config(); + + for ( int i = 0; i < DEVINFO_STR_SWLIST_MAX - DEVINFO_STR_SWLIST_0; i++ ) + { + if ( swlist->list_name[i] ) + { + software_list *list = software_list_open( options, swlist->list_name[i], FALSE, NULL ); + + for ( software_info *swinfo = software_list_first( list ); swinfo != NULL; swinfo = software_list_next( list ) ) + { + for ( software_part *part = software_find_part( swinfo, NULL, NULL ); part != NULL; part = software_part_next( part ) ) + { + for ( const rom_entry *region = part->romdata; region != NULL; region = rom_next_region(region) ) + { + for ( const rom_entry *rom = rom_first_file(region); rom != NULL; rom = rom_next_file(rom) ) + { + if ( hash_data_is_equal(hash, ROM_GETHASHDATA(rom), 0) ) + { + int baddump = hash_data_has_info(ROM_GETHASHDATA(rom), HASH_INFO_BAD_DUMP); + + /* output information about the match */ + if (*found != 0) + mame_printf_info(" "); + mame_printf_info("= %s%-20s %s:%s %s\n", baddump ? "(BAD) " : "", ROM_GETNAME(rom), swlist->list_name[i], swinfo->shortname, swinfo->longname); + (*found)++; + } + } + } + } + } + + software_list_close( list ); + } + } + } + } + + machine_config_free(config); + } +} /*------------------------------------------------- info_listmedia - output the list of image @@ -1213,7 +1479,5 @@ static void match_roms(core_options *options, const char *hash, int length, int machine_config_free(config); } -#ifdef MESS - mess_match_roms( options, hash, length, found ); -#endif -} + softlist_match_roms( options, hash, length, found ); +}
\ No newline at end of file |