bool S9xIsValidCheatCode(const char *codestring) { std::string codes(codestring); if (codes.empty() || codes[codes.length() - 1] == '+') return false; // std::getline cannot handle this case std::istringstream iss(codes); std::string code; while(std::getline(iss, code, '+')) { uint32 address; uint8 byte; if (S9xProActionReplayToRaw(code.c_str(), address, byte) != NULL && S9xGameGenieToRaw(code.c_str(), address, byte) != NULL) { uint8 bytes[3]; uint8 num_bytes; if (S9xGoldFingerToRaw(code.c_str(), address, num_bytes, bytes) != NULL) return false; // invalid format } } return true; }
void retro_cheat_set(unsigned index, bool enabled, const char *code) { uint32 address; uint8 val; bool8 sram; uint8 bytes[3];//used only by GoldFinger, ignored for now if (S9xGameGenieToRaw(code, &address, &val)!=NULL && S9xProActionReplayToRaw(code, &address, &val)!=NULL && S9xGoldFingerToRaw(code, &address, &sram, &val, bytes)!=NULL) { // bad code, ignore return; } if (index>Cheat.num_cheats) return; // cheat added in weird order, ignore if (index==Cheat.num_cheats) Cheat.num_cheats++; Cheat.c[index].address = address; Cheat.c[index].byte = val; Cheat.c[index].enabled = enabled; Cheat.c[index].saved = FALSE; // it'll be saved next time cheats run anyways Settings.ApplyCheats=true; S9xApplyCheats(); }
static inline bool S9xCompileCheat(struct SCheatItem& cheat, bool8 save_current_value) { std::string codes(cheat.code); std::vector<SCheat> cheatVector; if (codes.empty() || codes[codes.length() - 1] == '+') return false; // std::getline cannot handle this case std::istringstream iss(codes); std::string code; while(std::getline(iss, code, '+')) { SCheat c; if (S9xProActionReplayToRaw(code.c_str(), c.address, c.byte) == NULL || S9xGameGenieToRaw(code.c_str(), c.address, c.byte) == NULL) { c.saved = save_current_value; if (c.saved) { c.saved_byte = S9xGetByteFree(c.address); } cheatVector.push_back(c); } else { uint32 address; uint8 bytes[3]; uint8 num_bytes; if (S9xGoldFingerToRaw(code.c_str(), address, num_bytes, bytes) == NULL) { for (int i = 0; i < num_bytes; i++) { c.address = address + i; c.byte = bytes[i]; c.saved = save_current_value; if (c.saved) { c.saved_byte = S9xGetByteFree(c.address); } cheatVector.push_back(c); } } else return false; // invalid format } } cheat.c.clear(); copy(cheatVector.begin(), cheatVector.end(), std::back_inserter(cheat.c)); return true; }
char * S9xParseArgs (char **argv, int argc) { for (int i = 1; i < argc; i++) { if (*argv[i] == '-') { if (!strcasecmp(argv[i], "-help")) S9xUsage(); else // SOUND OPTIONS if (!strcasecmp(argv[i], "-soundsync")) Settings.SoundSync = TRUE; else if (!strcasecmp(argv[i], "-playbackrate")) { if (i + 1 < argc) { Settings.SoundPlaybackRate = atoi(argv[++i]); if (Settings.SoundPlaybackRate < 8192) Settings.SoundPlaybackRate = 8192; } else S9xUsage(); } else if (!strcasecmp(argv[i], "-inputrate")) { if (i + 1 < argc) { Settings.SoundInputRate = atoi(argv[++i]); if (Settings.SoundInputRate < 8192) Settings.SoundInputRate = 8192; } else S9xUsage(); } else if (!strcasecmp(argv[i], "-reversestereo")) Settings.ReverseStereo = TRUE; else if (!strcasecmp(argv[i], "-nostereo")) Settings.Stereo = FALSE; else if (!strcasecmp(argv[i], "-eightbit")) Settings.SixteenBitSound = FALSE; else if (!strcasecmp(argv[i], "-mute")) Settings.Mute = TRUE; else // DISPLAY OPTIONS if (!strcasecmp(argv[i], "-displayframerate")) Settings.DisplayFrameRate = TRUE; else if (!strcasecmp(argv[i], "-displaykeypress")) Settings.DisplayPressedKeys = TRUE; else if (!strcasecmp(argv[i], "-nohires")) Settings.SupportHiRes = FALSE; else if (!strcasecmp(argv[i], "-notransparency")) Settings.Transparency = FALSE; else if (!strcasecmp(argv[i], "-nowindows")) Settings.DisableGraphicWindows = TRUE; else // CONTROLLER OPTIONS if (!strcasecmp(argv[i], "-nomp5")) Settings.MultiPlayer5Master = FALSE; else if (!strcasecmp(argv[i], "-nomouse")) Settings.MouseMaster = FALSE; else if (!strcasecmp(argv[i], "-nosuperscope")) Settings.SuperScopeMaster = FALSE; else if (!strcasecmp(argv[i], "-nojustifier")) Settings.JustifierMaster = FALSE; else if (!strcasecmp(argv[i], "-port1") || !strcasecmp(argv[i], "-port2")) { if (i + 1 < argc) { i++; if (!parse_controller_spec(argv[i - 1][5] - '1', argv[i])) S9xUsage(); } else S9xUsage(); } else // ROM OPTIONS if (!strcasecmp(argv[i], "-hirom")) Settings.ForceHiROM = TRUE; else if (!strcasecmp(argv[i], "-lorom")) Settings.ForceLoROM = TRUE; else if (!strcasecmp(argv[i], "-ntsc")) Settings.ForceNTSC = TRUE; else if (!strcasecmp(argv[i], "-pal")) Settings.ForcePAL = TRUE; else if (!strcasecmp(argv[i], "-nointerleave")) Settings.ForceNotInterleaved = TRUE; else if (!strcasecmp(argv[i], "-interleaved")) Settings.ForceInterleaved = TRUE; else if (!strcasecmp(argv[i], "-interleaved2")) Settings.ForceInterleaved2 = TRUE; else if (!strcasecmp(argv[i], "-interleavedgd24")) Settings.ForceInterleaveGD24 = TRUE; else if (!strcasecmp(argv[i], "-noheader")) Settings.ForceNoHeader = TRUE; else if (!strcasecmp(argv[i], "-header")) Settings.ForceHeader = TRUE; else if (!strcasecmp(argv[i], "-bsxbootup")) Settings.BSXBootup = TRUE; else // PATCH/CHEAT OPTIONS if (!strcasecmp(argv[i], "-nopatch")) Settings.NoPatch = TRUE; else if (!strcasecmp(argv[i], "-cheat")) Settings.ApplyCheats = TRUE; else if (!strcasecmp(argv[i], "-gamegenie")) { if (i + 1 < argc) { uint32 address; uint8 byte; const char *error; if ((error = S9xGameGenieToRaw(argv[++i], address, byte)) == NULL) S9xAddCheat(TRUE, FALSE, address, byte); else S9xMessage(S9X_ERROR, S9X_GAME_GENIE_CODE_ERROR, error); } else S9xUsage(); } else if (!strcasecmp(argv[i], "-actionreplay")) { if (i + 1 < argc) { uint32 address; uint8 byte; const char *error; if ((error = S9xProActionReplayToRaw(argv[++i], address, byte)) == NULL) S9xAddCheat(TRUE, FALSE, address, byte); else S9xMessage(S9X_ERROR, S9X_ACTION_REPLY_CODE_ERROR, error); } else S9xUsage(); } else if (!strcasecmp(argv[i], "-goldfinger")) { if (i + 1 < argc) { uint32 address; uint8 bytes[3]; bool8 sram; uint8 num_bytes; const char *error; if ((error = S9xGoldFingerToRaw(argv[++i], address, sram, num_bytes, bytes)) == NULL) { for (int c = 0; c < num_bytes; c++) S9xAddCheat(TRUE, FALSE, address + c, bytes[c]); } else S9xMessage(S9X_ERROR, S9X_GOLD_FINGER_CODE_ERROR, error); } else S9xUsage(); } else // NETPLAY OPTIONS #ifdef NETPLAY_SUPPORT if (!strcasecmp(argv[i], "-net")) Settings.NetPlay = TRUE; else if (!strcasecmp(argv[i], "-port")) { if (i + 1 < argc) Settings.Port = -atoi(argv[++i]); else S9xUsage(); } else if (!strcasecmp(argv[i], "-server")) { if (i + 1 < argc) { strncpy(Settings.ServerName, argv[++i], 127); Settings.ServerName[127] = 0; } else S9xUsage(); } else #endif // HACKING OR DEBUGGING OPTIONS #ifdef DEBUGGER if (!strcasecmp(argv[i], "-debug")) CPU.Flags |= DEBUG_MODE_FLAG; else if (!strcasecmp(argv[i], "-trace")) { ENSURE_TRACE_OPEN(trace,"trace.log","wb") CPU.Flags |= TRACE_FLAG; } else #endif if (!strcasecmp(argv[i], "-hdmatiming")) { if (i + 1 < argc) { int p = atoi(argv[++i]); if (p > 0 && p < 200) Settings.HDMATimingHack = p; } else S9xUsage(); } else if (!strcasecmp(argv[i], "-invalidvramaccess")) Settings.BlockInvalidVRAMAccessMaster = FALSE; else // OTHER OPTIONS if (!strcasecmp(argv[i], "-frameskip")) { if (i + 1 < argc) Settings.SkipFrames = atoi(argv[++i]) + 1; else S9xUsage(); } else if (!strcasecmp(argv[i], "-frametime")) { if (i + 1 < argc) Settings.FrameTimePAL = Settings.FrameTimeNTSC = atoi(argv[++i]); else S9xUsage(); } else if (!strcasecmp(argv[i], "-upanddown")) Settings.UpAndDown = TRUE; else if (!strcasecmp(argv[i], "-conf")) { if (++i >= argc) S9xUsage(); // Else do nothing, S9xLoadConfigFiles() handled it. } else if (!strcasecmp(argv[i], "-nostdconf")) { // Do nothing, S9xLoadConfigFiles() handled it. } else S9xParseArg(argv, i, argc); } else rom_filename = argv[i]; } S9xVerifyControllers(); return (rom_filename); }