def plugin_get_version(self, handle, path): """Retrieves version information from the plugin.""" try: type_ptr = C.pointer(C.c_int()) ver_ptr = C.pointer(C.c_int()) api_ptr = C.pointer(C.c_int()) name_ptr = C.pointer(C.c_char_p()) cap_ptr = C.pointer(C.c_int()) rval = handle.PluginGetVersion( type_ptr, ver_ptr, api_ptr, name_ptr, cap_ptr) except AttributeError: unload_library(handle) log.warn("library '%s' is invalid, no PluginGetVersion() function found." % ( os.path.basename(path))) except OSError as err: log.debug("plugin_get_version()") log.warn(str(err)) else: if rval == M64ERR_SUCCESS: return (type_ptr.contents.value, ver_ptr.contents.value, api_ptr.contents.value, name_ptr.contents.value.decode(), cap_ptr.contents.value) else: log.debug("plugin_get_version()") log.warn(self.error_message(rval)) return None
def delete_section(self, section): """Deletes a section from the config.""" rval = self.m64p.ConfigDeleteSection(C.c_char_p(section.encode())) if rval != M64ERR_SUCCESS: log.debug("delete_section()") log.warn(self.core.error_message(rval)) return rval
def get_parameter(self, param_name): """Retrieves the value of one of the emulator's parameters.""" try: param_type = self.parameters[self.section][param_name.encode()] param_ctype = M64_CTYPE[param_type] except KeyError: return if param_ctype != C.c_char_p: maxsize = C.sizeof(M64_CTYPE[param_type]) param_value = C.pointer(param_ctype()) else: maxsize = 256 param_value = C.create_string_buffer(maxsize) self.m64p.ConfigGetParameter.argtypes = [ C.c_void_p, C.c_char_p, C.c_int, C.c_void_p, C.c_int ] rval = self.m64p.ConfigGetParameter(self.config_handle, C.c_char_p(param_name.encode()), C.c_int(param_type), param_value, C.c_int(maxsize)) if rval != M64ERR_SUCCESS: log.debug("get_parameter()") log.warn(self.core.error_message(rval)) return rval else: if param_ctype == C.c_char_p: return param_value.value else: return param_value.contents.value
def save_file(self): """Saves config file to disk.""" rval = self.m64p.ConfigSaveFile() if rval != M64ERR_SUCCESS: log.debug("save_file()") log.warn(self.core.error_message(rval)) return rval
def attach_plugins(self, plugins): """Attaches plugins to the emulator core.""" self.plugins = plugins for plugin_type in PLUGIN_ORDER: plugin = self.plugins[plugin_type] if not plugin: plugin_maps = list(self.plugin_map[plugin_type].values()) if not plugin_maps: continue plugin_map = plugin_maps[0] else: plugin_map = self.plugin_map[plugin_type][plugin] (plugin_handle, plugin_path, plugin_name, plugin_desc, plugin_version) = plugin_map rval = self.m64p.CoreAttachPlugin( C.c_int(plugin_type), C.c_void_p(plugin_handle._handle)) if rval != M64ERR_SUCCESS: log.debug("attach_plugins()") log.warn(self.error_message(rval)) log.warn("core failed to attach %s plugin." % (plugin_name)) else: log.info("using %s plugin: '%s' v%s" % (plugin_name.decode(), plugin_desc, version_split(plugin_version)))
def reset(self, soft=False): """Reset the emulated machine.""" rval = self.m64p.CoreDoCommand(M64CMD_RESET, C.c_int(int(soft))) if rval != M64ERR_SUCCESS: log.debug("reset()") log.warn(self.error_message(rval)) return rval
def take_next_screenshot(self): """Saves a screenshot at the next possible opportunity.""" rval = self.m64p.CoreDoCommand(M64CMD_TAKE_NEXT_SCREENSHOT) if rval != M64ERR_SUCCESS: log.debug("take_next_screenshot()") log.warn(self.error_message(rval)) return rval
def state_set_slot(self, slot): """Sets the currently selected save slot index.""" rval = self.m64p.CoreDoCommand(M64CMD_STATE_SET_SLOT, C.c_int(slot)) if rval != M64ERR_SUCCESS: log.debug("state_set_slot()") log.warn(self.error_message(rval)) return rval
def resume(self): """Resumes execution of the emulator if it is paused.""" rval = self.m64p.CoreDoCommand(M64CMD_RESUME, 0, None) if rval != M64ERR_SUCCESS: log.debug("resume()") log.warn(self.error_message(rval)) return rval
def attach_plugins(self, plugins): """Attaches plugins to the emulator core.""" self.plugins = plugins for plugin_type in PLUGIN_ORDER: plugin = self.plugins[plugin_type] if not plugin: plugin_map = list(self.plugin_map[plugin_type].values())[0] else: try: plugin_map = self.plugin_map[plugin_type][plugin] except KeyError: continue (plugin_handle, plugin_path, plugin_name, plugin_desc, plugin_version) = plugin_map rval = self.m64p.CoreAttachPlugin( C.c_int(plugin_type), C.c_void_p(plugin_handle._handle)) if rval != M64ERR_SUCCESS: log.debug("attach_plugins()") log.warn(self.error_message(rval)) log.warn("core failed to attach %s plugin." % ( plugin_name)) else: log.info("using %s plugin: '%s' v%s" % ( plugin_name.decode(), plugin_desc, version_split(plugin_version)))
def get_parameter(self, param_name): """Retrieves the value of one of the emulator's parameters.""" try: param_type = self.parameters[self.section][param_name.encode()] param_ctype = M64_CTYPE[param_type] except KeyError: return if param_ctype != C.c_char_p: maxsize = C.sizeof(M64_CTYPE[param_type]) param_value = C.pointer(param_ctype()) else: maxsize = 256 param_value = C.create_string_buffer(maxsize) self.m64p.ConfigGetParameter.argtypes = [ C.c_void_p, C.c_char_p, C.c_int, C.c_void_p, C.c_int] rval = self.m64p.ConfigGetParameter( self.config_handle, C.c_char_p(param_name.encode()), C.c_int(param_type), param_value, C.c_int(maxsize)) if rval != M64ERR_SUCCESS: log.debug("get_parameter()") log.warn(self.core.error_message(rval)) return rval else: if param_ctype == C.c_char_p: return param_value.value else: return param_value.contents.value
def pause(self): """Pause the emulator if it is running.""" rval = self.m64p.CoreDoCommand(M64CMD_PAUSE, 0, None) if rval != M64ERR_SUCCESS: log.debug("pause()") log.warn(self.error_message(rval)) return rval
def stop(self): """Stops the emulator, if it is currently running.""" rval = self.m64p.CoreDoCommand(M64CMD_STOP, 0, None) if rval != M64ERR_SUCCESS: log.debug("stop()") log.warn(self.error_message(rval)) return rval
def plugin_get_version(self, handle, path): """Retrieves version information from the plugin.""" try: type_ptr = C.pointer(C.c_int()) ver_ptr = C.pointer(C.c_int()) api_ptr = C.pointer(C.c_int()) name_ptr = C.pointer(C.c_char_p()) cap_ptr = C.pointer(C.c_int()) rval = handle.PluginGetVersion(type_ptr, ver_ptr, api_ptr, name_ptr, cap_ptr) except AttributeError: unload_library(handle) log.warn( "library '%s' is invalid, no PluginGetVersion() function found." % (os.path.basename(path))) except OSError as err: log.debug("plugin_get_version()") log.warn(str(err)) else: if rval == M64ERR_SUCCESS: return (type_ptr.contents.value, ver_ptr.contents.value, api_ptr.contents.value, name_ptr.contents.value.decode(), cap_ptr.contents.value) else: log.debug("plugin_get_version()") log.warn(self.error_message(rval)) return None
def set_parameter(self, param_name, param_value): """Sets the value of one of the emulator's parameters.""" try: param_type = self.parameters[self.section][param_name.encode()] param_ctype = M64_CTYPE[param_type] except KeyError: return if param_ctype != C.c_char_p: param_value = C.byref(param_ctype(param_value)) param_arg_type = C.POINTER(param_ctype) else: param_value = param_ctype(param_value) param_arg_type = param_ctype self.m64p.ConfigSetParameter.argtypes = [ C.c_void_p, C.c_char_p, C.c_int, param_arg_type ] rval = self.m64p.ConfigSetParameter(self.config_handle, C.c_char_p(param_name.encode()), C.c_int(param_type), param_value) if rval != M64ERR_SUCCESS: log.debug("set_parameter()") log.warn(self.core.error_message(rval)) return rval
def resume(self): """Resumes execution of the emulator if it is paused.""" rval = self.m64p.CoreDoCommand( M64CMD_RESUME, 0, None) if rval != M64ERR_SUCCESS: log.debug("resume()") log.warn(self.error_message(rval)) return rval
def stop(self): """Stops the emulator, if it is currently running.""" rval = self.m64p.CoreDoCommand( M64CMD_STOP, 0, None) if rval != M64ERR_SUCCESS: log.debug("stop()") log.warn(self.error_message(rval)) return rval
def send_sdl_keyup(self, key): """Injects an SDL_KEYUP event into the emulator's core event loop.""" rval = self.m64p.CoreDoCommand(M64CMD_SEND_SDL_KEYUP, C.c_int(key)) if rval != M64ERR_SUCCESS: log.debug("send_sdl_keyup()") log.warn(self.error_message(rval)) return rval
def save_section(self, section): """Saves one section of the current configuration to disk, while leaving the other sections unmodified.""" rval = self.m64p.ConfigSaveSection(C.c_char_p(section.encode())) if rval != M64ERR_SUCCESS: log.debug("save_section()") log.warn(self.core.error_message(rval)) return rval
def state_load(self, state_path=None): """Loads a saved state file from the current slot.""" path = C.c_char_p(state_path.encode()) if state_path else None rval = self.m64p.CoreDoCommand(M64CMD_STATE_LOAD, C.c_int(1), path) if rval != M64ERR_SUCCESS: log.debug("state_load()") log.warn(self.error_message(rval)) return rval
def reset(self, soft=False): """Reset the emulated machine.""" rval = self.m64p.CoreDoCommand( M64CMD_RESET, C.c_int(int(soft))) if rval != M64ERR_SUCCESS: log.debug("reset()") log.warn(self.error_message(rval)) return rval
def rom_close(self): """Closes any currently open ROM.""" rval = self.m64p.CoreDoCommand(M64CMD_ROM_CLOSE) if rval != M64ERR_SUCCESS: log.debug("rom_close()") log.warn(self.error_message(rval)) log.error("core failed to close ROM image file.") return rval
def state_set_slot(self, slot): """Sets the currently selected save slot index.""" rval = self.m64p.CoreDoCommand( M64CMD_STATE_SET_SLOT, C.c_int(slot)) if rval != M64ERR_SUCCESS: log.debug("state_set_slot()") log.warn(self.error_message(rval)) return rval
def pause(self): """Pause the emulator if it is running.""" rval = self.m64p.CoreDoCommand( M64CMD_PAUSE, 0, None) if rval != M64ERR_SUCCESS: log.debug("pause()") log.warn(self.error_message(rval)) return rval
def plugin_shutdown(self, handle, desc): """This function destroys data structures and releases memory allocated by the plugin library. """ rval = handle.PluginShutdown() if rval != M64ERR_SUCCESS: log.debug("plugin_shutdown()") log.warn(self.error_message(rval)) log.warn("%s failed to stop." % desc)
def take_next_screenshot(self): """Saves a screenshot at the next possible opportunity.""" rval = self.m64p.CoreDoCommand( M64CMD_TAKE_NEXT_SCREENSHOT) if rval != M64ERR_SUCCESS: log.debug("take_next_screenshot()") log.warn(self.error_message(rval)) return rval
def rom_close(self): """Closes any currently open ROM.""" rval = self.m64p.CoreDoCommand( M64CMD_ROM_CLOSE) if rval != M64ERR_SUCCESS: log.debug("rom_close()") log.warn(self.error_message(rval)) log.error("core failed to close ROM image file.") return rval
def rom_get_header(self): """Retrieves the header data of the currently open ROM.""" rval = self.m64p.CoreDoCommand(M64CMD_ROM_GET_HEADER, C.c_int(C.sizeof(self.rom_header)), C.pointer(self.rom_header)) if rval != M64ERR_SUCCESS: log.debug("rom_get_header()") log.warn("core failed to get ROM header.") return rval
def rom_get_settings(self): """Retrieves the settings data of the currently open ROM.""" rval = self.m64p.CoreDoCommand(M64CMD_ROM_GET_SETTINGS, C.c_int(C.sizeof(self.rom_settings)), C.pointer(self.rom_settings)) if rval != M64ERR_SUCCESS: log.debug("rom_get_settings()") log.warn("core failed to get ROM settings.") return rval
def list_sections(self): """Enumerates the list of sections in config file.""" self.m64p.ConfigListSections.argtypes = [C.c_void_p, C.c_void_p] rval = self.m64p.ConfigListSections( C.c_void_p(), SECTIONS_FUNC(self.list_sections_callback)) if rval != M64ERR_SUCCESS: log.debug("list_sections()") log.warn(self.core.error_message(rval)) return rval
def state_save(self, state_path=None, state_type=1): """Saves a state file to the current slot.""" path = C.c_char_p(state_path.encode()) if state_path else None rval = self.m64p.CoreDoCommand(M64CMD_STATE_SAVE, C.c_int(state_type), path) if rval != M64ERR_SUCCESS: log.debug("state_save()") log.warn(self.error_message(rval)) return rval
def override_vidext(self): """Overrides the core's internal SDL-based OpenGL functions.""" rval = self.m64p.CoreOverrideVidExt(C.pointer(vidext)) if rval != M64ERR_SUCCESS: log.debug("override_vidext()") log.warn(self.error_message(rval)) else: log.info("video extension enabled") return rval
def revert_changes(self, section): """Reverts changes previously made to one section of the current configuration file, so that it will match with the configuration at the last time that it was loaded from or saved to disk. """ rval = self.m64p.ConfigRevertChanges(C.c_char_p(section.encode())) if rval != M64ERR_SUCCESS: log.debug("revert_changes()") log.warn(self.core.error_message(rval)) return rval
def advance_frame(self): """Advance one frame. The emulator will run until the next frame, then pause.""" rval = self.m64p.CoreDoCommand(M64CMD_ADVANCE_FRAME, C.c_int(), C.c_int()) if rval != M64ERR_SUCCESS: log.debug("advance_frame()") log.warn(self.error_message(rval)) return rval
def plugin_startup(self, handle, name, desc): """This function initializes plugin for use by allocating memory, creating data structures, and loading the configuration data.""" rval = handle.PluginStartup(C.c_void_p(self.m64p._handle), name, DEBUG_CALLBACK) if rval != M64ERR_SUCCESS: log.debug("plugin_startup()") log.warn(self.error_message(rval)) log.warn("%s failed to start." % desc)
def send_sdl_keyup(self, key): """Injects an SDL_KEYUP event into the emulator's core event loop.""" rval = self.m64p.CoreDoCommand( M64CMD_SEND_SDL_KEYUP, C.c_int(key)) if rval != M64ERR_SUCCESS: log.debug("send_sdl_keyup()") log.warn(self.error_message(rval)) return rval
def advance_frame(self): """Advance one frame. The emulator will run until the next frame, then pause.""" rval = self.m64p.CoreDoCommand( M64CMD_ADVANCE_FRAME, C.c_int(), C.c_int()) if rval != M64ERR_SUCCESS: log.debug("advance_frame()") log.warn(self.error_message(rval)) return rval
def state_save(self, state_path=None, state_type=1): """Saves a state file to the current slot.""" path = C.c_char_p(state_path.encode()) if state_path else None rval = self.m64p.CoreDoCommand( M64CMD_STATE_SAVE, C.c_int(state_type), path) if rval != M64ERR_SUCCESS: log.debug("state_save()") log.warn(self.error_message(rval)) return rval
def state_load(self, state_path=None): """Loads a saved state file from the current slot.""" path = C.c_char_p(state_path.encode()) if state_path else None rval = self.m64p.CoreDoCommand( M64CMD_STATE_LOAD, C.c_int(1), path) if rval != M64ERR_SUCCESS: log.debug("state_load()") log.warn(self.error_message(rval)) return rval
def core_state_query(self, state): """Query the emulator core for the value of a state parameter.""" state_ptr = C.pointer(C.c_int()) rval = self.m64p.CoreDoCommand(M64CMD_CORE_STATE_QUERY, C.c_int(state), state_ptr) if rval != M64ERR_SUCCESS: log.debug("core_state_query()") log.warn(self.error_message(rval)) return state_ptr.contents.value
def core_state_set(self, state, value): """Sets the value of a state parameter in the emulator core.""" value_ptr = C.pointer(C.c_int(value)) rval = self.m64p.CoreDoCommand(M64CMD_CORE_STATE_SET, C.c_int(state), value_ptr) if rval != M64ERR_SUCCESS: log.debug("core_state_set()") log.warn(self.error_message(rval)) return value_ptr.contents.value
def rom_get_header(self): """Retrieves the header data of the currently open ROM.""" rval = self.m64p.CoreDoCommand( M64CMD_ROM_GET_HEADER, C.c_int(C.sizeof(self.rom_header)), C.pointer(self.rom_header)) if rval != M64ERR_SUCCESS: log.debug("rom_get_header()") log.warn("core failed to get ROM header.") return rval
def rom_get_settings(self): """Retrieves the settings data of the currently open ROM.""" rval = self.m64p.CoreDoCommand( M64CMD_ROM_GET_SETTINGS, C.c_int(C.sizeof(self.rom_settings)), C.pointer(self.rom_settings)) if rval != M64ERR_SUCCESS: log.debug("rom_get_settings()") log.warn("core failed to get ROM settings.") return rval
def core_state_set(self, state, value): """Sets the value of a state parameter in the emulator core.""" value_ptr = C.pointer(C.c_int(value)) rval = self.m64p.CoreDoCommand( M64CMD_CORE_STATE_SET, C.c_int(state), value_ptr) if rval != M64ERR_SUCCESS: log.debug("core_state_set()") log.warn(self.error_message(rval)) return value_ptr.contents.value
def core_state_query(self, state): """Query the emulator core for the value of a state parameter.""" state_ptr = C.pointer(C.c_int()) rval = self.m64p.CoreDoCommand( M64CMD_CORE_STATE_QUERY, C.c_int(state), state_ptr) if rval != M64ERR_SUCCESS: log.debug("core_state_query()") log.warn(self.error_message(rval)) return state_ptr.contents.value
def list_parameters(self): """Enumerates the list of parameters in a section.""" self.m64p.ConfigListParameters.argtypes = [ C.c_void_p, C.c_void_p, C.c_void_p] rval = self.m64p.ConfigListParameters( self.config_handle, C.c_void_p(), PARAMETERS_FUNC(self.list_parameters_callback)) if rval != M64ERR_SUCCESS: log.debug("list_parameters()") log.warn(self.core.error_message(rval)) return rval
def cheat_enabled(self, cheat_name, enabled=True): """Enables or disables a specified Cheat Function""" rval = self.m64p.CoreCheatEnabled( C.c_char_p(cheat_name.encode()), C.c_int(enabled)) if rval != M64ERR_SUCCESS: log.debug("cheat_enabled()") log.info("CoreCheatEnabled() failed for cheat code '%s'" % cheat_name) log.warn(self.error_message(rval)) else: state = 'activated' if enabled else 'deactivated' log.info("cheat code '%s' %s" % (cheat_name, state)) return rval
def get_parameter_type(self, param_name): """Retrieves the type of one of the emulator's parameters.""" param_type = C.byref(C.c_int()) self.m64p.ConfigGetParameterHelp.argtypes = [ C.c_void_p, C.c_char_p, C.POINTER(C.c_int)] rval = self.m64p.ConfigGetParameterType( self.config_handle, C.c_char_p(param_name), param_type) if rval != M64ERR_SUCCESS: log.debug("get_parameter_type()") log.warn(self.core.error_message(rval)) return rval return param_type.value
def get_parameter_type(self, param_name): """Retrieves the type of one of the emulator's parameters.""" param_type = C.byref(C.c_int()) self.m64p.ConfigGetParameterHelp.argtypes = [ C.c_void_p, C.c_char_p, C.POINTER(C.c_int)] rval = self.m64p.ConfigGetParameterType( self.config_handle, C.c_char_p(param_name.encode()), param_type) if rval != M64ERR_SUCCESS: log.debug("get_parameter_type()") log.warn(self.core.error_message(rval)) return rval return param_type.value
def add_cheat(self, cheat_name, cheat_code): """Adds a Cheat Function to a list of currently active cheats which are applied to the open ROM, and set its state to Enabled""" rval = self.m64p.CoreAddCheat( C.c_char_p(cheat_name.encode()), C.pointer(cheat_code), C.c_int(C.sizeof(cheat_code))) if rval != M64ERR_SUCCESS: log.debug("add_cheat()") log.info("CoreAddCheat() failed for cheat code '%s'" % cheat_name) log.warn(self.error_message(rval)) else: log.info("cheat code '%s' activated" % cheat_name) return rval