예제 #1
0
xml_data_node *xml_string_read(const char *string, xml_parse_options *opts)
{
	xml_parse_info parse_info;
	int length = strlen(string);

	/* set up the parser */
	if (!setup_parser(&parse_info, opts))
		return NULL;

	/* parse the data */
	if (XML_Parse(parse_info.parser, string, length, TRUE) == XML_STATUS_ERROR)
	{
		if (opts && opts->error)
		{
			opts->error->error_message = XML_ErrorString(XML_GetErrorCode(parse_info.parser));
			opts->error->error_line = XML_GetCurrentLineNumber(parse_info.parser);
			opts->error->error_column = XML_GetCurrentColumnNumber(parse_info.parser);
	}

		xml_file_free(parse_info.rootnode);
		XML_ParserFree(parse_info.parser);
		return NULL;
	}

	/* free the parser */
	XML_ParserFree(parse_info.parser);

	/* return the root node */
	return parse_info.rootnode;
}
예제 #2
0
파일: config.c 프로젝트: crazii/mameplus
static int config_save_xml(running_machine &machine, emu_file &file, int which_type)
{
	xml_data_node *root = xml_file_create();
	xml_data_node *confignode, *systemnode;
	config_type *type;

	/* if we don't have a root, bail */
	if (!root)
		return 0;

	/* create a config node */
	confignode = xml_add_child(root, "mameconfig", NULL);
	if (!confignode)
		goto error;
	xml_set_attribute_int(confignode, "version", CONFIG_VERSION);

	/* create a system node */
	systemnode = xml_add_child(confignode, "system", NULL);
	if (!systemnode)
		goto error;
	xml_set_attribute(systemnode, "name", (which_type == CONFIG_TYPE_DEFAULT) ? "default" : machine.system().name);

	/* create the input node and write it out */
	/* loop over all registrants and call their save function */
	for (type = typelist; type; type = type->next)
	{
		xml_data_node *curnode = xml_add_child(systemnode, type->name, NULL);
		if (!curnode)
			goto error;
		type->save(which_type, curnode);

		/* if nothing was added, just nuke the node */
		if (!curnode->value && !curnode->child)
			xml_delete_node(curnode);
	}

	/* flush the file */
	xml_file_write(root, file);

	/* free and get out of here */
	xml_file_free(root);
	return 1;

error:
	xml_file_free(root);
	return 0;
}
예제 #3
0
xml_data_node *xml_file_read(mame_file *file, xml_parse_options *opts)
{
	xml_parse_info parse_info;
	int done;

	/* set up the parser */
	if (!setup_parser(&parse_info, opts))
		return NULL;

	/* loop through the file and parse it */
	do
	{
		char tempbuf[TEMP_BUFFER_SIZE];

		/* read as much as we can */
		int bytes = mame_fread(file, tempbuf, sizeof(tempbuf));
		done = mame_feof(file);

		/* parse the data */
		if (XML_Parse(parse_info.parser, tempbuf, bytes, done) == XML_STATUS_ERROR)
		{
			if (opts && opts->error)
		{
				opts->error->error_message = XML_ErrorString(XML_GetErrorCode(parse_info.parser));
				opts->error->error_line = XML_GetCurrentLineNumber(parse_info.parser);
				opts->error->error_column = XML_GetCurrentColumnNumber(parse_info.parser);
			}

			xml_file_free(parse_info.rootnode);
			XML_ParserFree(parse_info.parser);
			return NULL;
		}

	} while (!done);

	/* free the parser */
	XML_ParserFree(parse_info.parser);

	/* return the root node */
	return parse_info.rootnode;
}
예제 #4
0
파일: config.c 프로젝트: crazii/mameplus
static int config_load_xml(running_machine &machine, emu_file &file, int which_type)
{
	xml_data_node *root, *confignode, *systemnode;
	config_type *type;
	const char *srcfile;
	int version, count;

	/* read the file */
	root = xml_file_read(file, NULL);
	if (!root)
		goto error;

	/* find the config node */
	confignode = xml_get_sibling(root->child, "mameconfig");
	if (!confignode)
		goto error;

	/* validate the config data version */
	version = xml_get_attribute_int(confignode, "version", 0);
	if (version != CONFIG_VERSION)
		goto error;

	/* strip off all the path crap from the source filename */
	srcfile = strrchr(machine.system().source_file, '/');
	if (!srcfile)
		srcfile = strrchr(machine.system().source_file, '\\');
	if (!srcfile)
		srcfile = strrchr(machine.system().source_file, ':');
	if (!srcfile)
		srcfile = machine.system().source_file;
	else
		srcfile++;

	/* loop over all system nodes in the file */
	count = 0;
	for (systemnode = xml_get_sibling(confignode->child, "system"); systemnode; systemnode = xml_get_sibling(systemnode->next, "system"))
	{
		/* look up the name of the system here; skip if none */
		const char *name = xml_get_attribute_string(systemnode, "name", "");

		/* based on the file type, determine whether we have a match */
		switch (which_type)
		{
			case CONFIG_TYPE_GAME:
				/* only match on the specific game name */
				if (strcmp(name, machine.system().name) != 0)
					continue;
				break;

			case CONFIG_TYPE_DEFAULT:
				/* only match on default */
				if (strcmp(name, "default") != 0)
					continue;
				break;

			case CONFIG_TYPE_CONTROLLER:
			{
				int clone_of;
				/* match on: default, game name, source file name, parent name, grandparent name */
				if (strcmp(name, "default") != 0 &&
					strcmp(name, machine.system().name) != 0 &&
					strcmp(name, srcfile) != 0 &&
					((clone_of = driver_list::clone(machine.system())) == -1 || strcmp(name, driver_list::driver(clone_of).name) != 0) &&
					(clone_of == -1 || ((clone_of = driver_list::clone(clone_of)) == -1) || strcmp(name, driver_list::driver(clone_of).name) != 0))
					continue;
				break;
			}
		}

		/* log that we are processing this entry */
		if (DEBUG_CONFIG)
			osd_printf_debug("Entry: %s -- processing\n", name);

		/* loop over all registrants and call their load function */
		for (type = typelist; type; type = type->next)
			type->load(which_type, xml_get_sibling(systemnode->child, type->name));
		count++;
	}

	/* error if this isn't a valid game match */
	if (count == 0)
		goto error;

	/* free the parser */
	xml_file_free(root);
	return 1;

error:
	if (root)
		xml_file_free(root);
	return 0;
}
예제 #5
0
파일: cheat.c 프로젝트: jiangzhonghui/mame
void cheat_manager::load_cheats(const char *filename)
{
	xml_data_node *rootnode = NULL;
	emu_file cheatfile(machine().options().cheat_path(), OPEN_FLAG_READ);
	try
	{
		// open the file with the proper name
		file_error filerr = cheatfile.open(filename, ".xml");

		// loop over all instrances of the files found in our search paths
		while (filerr == FILERR_NONE)
		{
			mame_printf_verbose("Loading cheats file from %s\n", cheatfile.fullpath());

			// read the XML file into internal data structures
			xml_parse_options options = { 0 };
			xml_parse_error error;
			options.error = &error;
			rootnode = xml_file_read(cheatfile, &options);

			// if unable to parse the file, just bail
			if (rootnode == NULL)
				throw emu_fatalerror("%s.xml(%d): error parsing XML (%s)\n", filename, error.error_line, error.error_message);

			// find the layout node
			xml_data_node *mamecheatnode = xml_get_sibling(rootnode->child, "mamecheat");
			if (mamecheatnode == NULL)
				throw emu_fatalerror("%s.xml: missing mamecheatnode node", filename);

			// validate the config data version
			int version = xml_get_attribute_int(mamecheatnode, "version", 0);
			if (version != CHEAT_VERSION)
				throw emu_fatalerror("%s.xml(%d): Invalid cheat XML file: unsupported version", filename, mamecheatnode->line);

			// parse all the elements
			for (xml_data_node *cheatnode = xml_get_sibling(mamecheatnode->child, "cheat"); cheatnode != NULL; cheatnode = xml_get_sibling(cheatnode->next, "cheat"))
			{
				// load this entry
				cheat_entry *curcheat = global_alloc(cheat_entry(*this, m_symtable, filename, *cheatnode));

				// make sure we're not a duplicate
				cheat_entry *scannode = NULL;
				if (REMOVE_DUPLICATE_CHEATS)
					for (scannode = m_cheatlist.first(); scannode != NULL; scannode = scannode->next())
						if (strcmp(scannode->description(), curcheat->description()) == 0)
						{
							mame_printf_verbose("Ignoring duplicate cheat '%s' from file %s\n", curcheat->description(), cheatfile.fullpath());
							break;
						}

				// add to the end of the list
				if (scannode == NULL)
					m_cheatlist.append(*curcheat);
				else
					global_free(curcheat);
			}

			// free the file and loop for the next one
			xml_file_free(rootnode);

			// open the next file in sequence
			filerr = cheatfile.open_next();
		}
	}

	// handle errors cleanly
	catch (emu_fatalerror &err)
	{
		mame_printf_error("%s\n", err.string());
		m_cheatlist.reset();
		if (rootnode != NULL)
			xml_file_free(rootnode);
	}
}
예제 #6
0
multicart_open_error multicart_open(emu_options &options, const char *filename, const char *gamedrv, multicart_load_flags load_flags, multicart_t **cart)
{
	multicart_open_error err;
	zip_error ziperr;
	object_pool *pool;
	multicart_load_state state = {0, };
	const zip_file_header *header;
	const char *pcb_type;
	char *layout_text = NULL;

	/* allocate an object pool */
	pool = pool_alloc_lib(NULL);
	if (pool == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}

	/* allocate the multicart */
	state.multicart = (multicart_t*)pool_malloc_lib(pool, sizeof(*state.multicart));
	if (state.multicart == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}
	memset(state.multicart, 0, sizeof(*state.multicart));

	/* allocate the multicart's private data */
	state.multicart->data = (multicart_private*)pool_malloc_lib(pool, sizeof(*state.multicart->data));
	if (state.multicart->data == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}
	memset(state.multicart->data, 0, sizeof(*state.multicart->data));
	state.multicart->data->pool = pool;
	pool = NULL;

	/* open the ZIP file */
	ziperr = zip_file_open(filename, &state.zip);
	if (ziperr != ZIPERR_NONE)
	{
		err = MCERR_NOT_MULTICART;
		goto done;
	}

	/* find the layout.xml file */
	header = find_file(state.zip, "layout.xml");
	if (header == NULL)
	{
		err = MCERR_MISSING_LAYOUT;
		goto done;
	}

	/* reserve space for the layout text */
	layout_text = (char*)malloc(header->uncompressed_length + 1);
	if (layout_text == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}

	/* uncompress the layout text */
	ziperr = zip_file_decompress(state.zip, layout_text, header->uncompressed_length);
	if (ziperr != ZIPERR_NONE)
	{
		err = MCERR_ZIP_ERROR;
		goto done;
	}
	layout_text[header->uncompressed_length] = '\0';

	/* parse the layout text */
	state.layout_xml = xml_string_read(layout_text, NULL);
	if (state.layout_xml == NULL)
	{
		err = MCERR_XML_ERROR;
		goto done;
	}

	/* locate the PCB node */
	if (!find_pcb_and_resource_nodes(state.layout_xml, &state.pcb_node, &state.resources_node))
	{
		err = MCERR_NO_PCB_OR_RESOURCES;
		goto done;
	}

	/* get the PCB resource_type */
	pcb_type = xml_get_attribute_string(state.pcb_node, "type", "");
	state.multicart->pcb_type = pool_strdup_lib(state.multicart->data->pool, pcb_type);
	if (state.multicart->pcb_type == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}

	state.multicart->gamedrv_name = pool_strdup_lib(state.multicart->data->pool, gamedrv);
	if (state.multicart->gamedrv_name == NULL)
	{
		err = MCERR_OUT_OF_MEMORY;
		goto done;
	}

	/* do we have to load resources? */
	if (load_flags & MULTICART_FLAGS_LOAD_RESOURCES)
	{
		err = load_all_resources(options, &state);
		if (err != MCERR_NONE)
			goto done;

		err = load_all_sockets(&state);
		if (err != MCERR_NONE)
			goto done;
	}

	err = MCERR_NONE;

done:
	if (pool != NULL)
		pool_free_lib(pool);
	if (state.zip != NULL)
		zip_file_close(state.zip);
	if (layout_text != NULL)
		free(layout_text);
	if (state.layout_xml != NULL)
		xml_file_free(state.layout_xml);

	if ((err != MCERR_NONE) && (state.multicart != NULL))
	{
		multicart_close(options, state.multicart);
		state.multicart = NULL;
	}
	*cart = state.multicart;
	return err;
}
예제 #7
0
static int debug_comment_load_xml(mame_file *fp)
{
	int i, j;
	xml_data_node *root, *commentnode, *systemnode, *cpunode, *datanode;
	const char *name;
	int version;

	/* read the file */
	root = xml_file_read(fp, NULL);
	if (!root)
		goto error;

	/* find the config node */
	commentnode = xml_get_sibling(root->child, "mamecommentfile");
	if (!commentnode)
		goto error;

	/* validate the config data version */
	version = xml_get_attribute_int(commentnode, "version", 0);
	if (version != COMMENT_VERSION)
		goto error;

	/* check to make sure the file is applicable */
	systemnode = xml_get_sibling(commentnode->child, "system");
	name = xml_get_attribute_string(systemnode, "name", "");
	if (strcmp(name, Machine->gamedrv->name) != 0)
		goto error;

	i = 0;

	for (cpunode = xml_get_sibling(systemnode->child, "cpu"); cpunode; cpunode = xml_get_sibling(cpunode->next, "cpu"))
	{
		j = 0;

		for (datanode = xml_get_sibling(cpunode->child, "comment"); datanode; datanode = xml_get_sibling(datanode->next, "comment"))
		{
			/* Malloc the comment */
			debug_comments[i].comment_info[j] = (debug_comment*) malloc(sizeof(debug_comment));

			debug_comments[i].comment_info[j]->address = xml_get_attribute_int(datanode, "address", 0);
			debug_comments[i].comment_info[j]->color = xml_get_attribute_int(datanode, "color", 0);
			sscanf(xml_get_attribute_string(datanode, "crc", 0), "%08X", &debug_comments[i].comment_info[j]->crc);
			strcpy(debug_comments[i].comment_info[j]->text, datanode->value);
			debug_comments[i].comment_info[j]->is_valid = 1;

			j++;
		}

		debug_comments[i].comment_count = j;

		i++;
	}

	/* free the parser */
	xml_file_free(root);

	return 1;

error:
	if (root)
		xml_file_free(root);
	return 0;
}
예제 #8
0
int debug_comment_save(void)
{
	int i, j;
	char crc_buf[20];
	xml_data_node *root = xml_file_create();
	xml_data_node *commentnode, *systemnode;
	int total_comments = 0;

	/* if we don't have a root, bail */
	if (!root)
		return 0;

	/* create a comment node */
	commentnode = xml_add_child(root, "mamecommentfile", NULL);
	if (!commentnode)
		goto error;
	xml_set_attribute_int(commentnode, "version", COMMENT_VERSION);

	/* create a system node */
	systemnode = xml_add_child(commentnode, "system", NULL);
	if (!systemnode)
		goto error;
	xml_set_attribute(systemnode, "name", Machine->gamedrv->name);

	/* for each cpu */
	for (i = 0; i < cpu_gettotalcpu(); i++)
	{
		xml_data_node *curnode = xml_add_child(systemnode, "cpu", NULL);
		if (!curnode)
			goto error;
		xml_set_attribute_int(curnode, "num", i);

		for (j = 0; j < debug_comments[i].comment_count; j++)
		{
			xml_data_node *datanode = xml_add_child(curnode, "comment", debug_comments[i].comment_info[j]->text);
			if (!datanode)
				goto error;
			xml_set_attribute_int(datanode, "address", debug_comments[i].comment_info[j]->address);
			xml_set_attribute_int(datanode, "color", debug_comments[i].comment_info[j]->color);
			sprintf(crc_buf, "%08X", debug_comments[i].comment_info[j]->crc);
			xml_set_attribute(datanode, "crc", crc_buf);
			total_comments++;
		}
	}

	/* flush the file */
	if (total_comments > 0)
	{
 		mame_file *fp = mame_fopen(Machine->gamedrv->name, 0, FILETYPE_COMMENT, 1);
 		xml_file_write(root, fp);
		mame_fclose(fp);
	}

	/* free and get out of here */
	xml_file_free(root);
	return 1;

error:
	xml_file_free(root);
	return 0;
}
예제 #9
0
파일: cheat.cpp 프로젝트: bmunger/mame
void cheat_manager::load_cheats(const char *filename)
{
	xml_data_node *rootnode = nullptr;
	std::string searchstr(machine().options().cheat_path());
	path_iterator path(searchstr.c_str());
	std::string curpath;
	while (path.next(curpath))
	{
		searchstr.append(";").append(curpath).append(PATH_SEPARATOR).append("cheat");
	}
	emu_file cheatfile(searchstr.c_str(), OPEN_FLAG_READ);
	try
	{
		// open the file with the proper name
		osd_file::error filerr = cheatfile.open(filename, ".xml");

		// loop over all instrances of the files found in our search paths
		while (filerr == osd_file::error::NONE)
		{
			osd_printf_verbose("Loading cheats file from %s\n", cheatfile.fullpath());

			// read the XML file into internal data structures
			xml_parse_options options = { nullptr };
			xml_parse_error error;
			options.error = &error;
			rootnode = xml_file_read(cheatfile, &options);

			// if unable to parse the file, just bail
			if (rootnode == nullptr)
				throw emu_fatalerror("%s.xml(%d): error parsing XML (%s)\n", filename, error.error_line, error.error_message);

			// find the layout node
			xml_data_node *mamecheatnode = xml_get_sibling(rootnode->child, "mamecheat");
			if (mamecheatnode == nullptr)
				throw emu_fatalerror("%s.xml: missing mamecheatnode node", filename);

			// validate the config data version
			int version = xml_get_attribute_int(mamecheatnode, "version", 0);
			if (version != CHEAT_VERSION)
				throw emu_fatalerror("%s.xml(%d): Invalid cheat XML file: unsupported version", filename, mamecheatnode->line);

			// parse all the elements
			for (xml_data_node *cheatnode = xml_get_sibling(mamecheatnode->child, "cheat"); cheatnode != nullptr; cheatnode = xml_get_sibling(cheatnode->next, "cheat"))
			{
				// load this entry
				auto curcheat = std::make_unique<cheat_entry>(*this, m_symtable, filename, *cheatnode);

				// make sure we're not a duplicate
				if (REMOVE_DUPLICATE_CHEATS && curcheat->is_duplicate())
				{
					osd_printf_verbose("Ignoring duplicate cheat '%s' from file %s\n", curcheat->description(), cheatfile.fullpath());
				}
				else // add to the end of the list
					m_cheatlist.push_back(std::move(curcheat));
			}

			// free the file and loop for the next one
			xml_file_free(rootnode);

			// open the next file in sequence
			filerr = cheatfile.open_next();
		}
	}

	// handle errors cleanly
	catch (emu_fatalerror &err)
	{
		osd_printf_error("%s\n", err.string());
		m_cheatlist.clear();
		if (rootnode != nullptr)
			xml_file_free(rootnode);
	}
}