Romhacking => Newcomer's Board => Topic started by: MysteryMan3D on April 14, 2021, 01:18:51 pm

Title: What's an easy way to permanently inject a Gameshark code into a PS1 ISO?
Post by: MysteryMan3D on April 14, 2021, 01:18:51 pm
I've been using the Infinite Health Gameshark code for Batman & Robin so I actually have a chance to beat the game (I may use the Level Select code as well), but I'd like to actually inject the code into the ISO so it's on permanently (Like Game Genie Guy does for cartridge ROMs). This way I can benefit from the code on emulators that don't support Gameshark codes (such as on the PS3 or the PocketGo).

Is there an easy way to go about this? Because from what I've seen online at this point, the process looks too complex for me to even bother with...
Title: Re: What's an easy way to permanently inject a Gameshark code into a PS1 ISO?
Post by: Jorpho on April 14, 2021, 04:12:55 pm
Because from what I've seen online at this point, the process looks too complex for me to even bother with...
Yes, that's probably accurate.

Gameshark codes work by modifying values in RAM, and it's not easy to find out what particular bytes in the vastness of an ISO is responsible for setting particular values in RAM.  It can be done – but it's probably too complex to bother with.
Title: Re: What's an easy way to permanently inject a Gameshark code into a PS1 ISO?
Post by: FAST6191 on April 14, 2021, 09:33:08 pm
I am not aware of any universal injectors like we have for the GBA (see gabsharky and GBAATM, and I guess now GBAatm-rebirth), DS (see DSATM) and more limited but never the less sort of available for the N64. I am not sure why the PS1 does not have such things -- generally speaking it can support enough overhead and is coded similarly enough between games I can see a path. Though I could have missed one. Likewise the PS1 did not have anything like a hypervisor or underlying OS you can attack, though if emulator limitations are causing this then that would not have been an option anyway.

That then leaves three things to consider.

Traditionally hardcoding cheats works in two ways.

1) You find what instruction(s) are doing things to your chosen area of memory (which the cheats tell you exactly where it is and what needs to go there) and edit said instructions. Can sometimes get lucky with a blind disassembly and an instruction* doing the deed. Other times you will have to run a basic tracing session.

*or multiple. I usually use an example of mario platformers. Things that might edit the lives counter are pits, hazards, crushing, enemies, time running out, poison mushrooms... theoretically you might have to attack all of those where the simple cheat that just holds it at a value needs but one. Can think a bit outside the box and just do one but have it add -- jumping in a pit gains you a life sort of thing.

2) You hook the game (which is likely what your average RAM editor approach is doing) and have it inject once per frame (and it is usually that -- vblank routines are usually easily found and used for just this reason) as an extra instruction saying "write this to this area". Can also look at button combos, ranges and more if you really wanted here as it is just a few more instructions. Said once per frame can also be a limiting factor if the game does calculations before your RAM write comes back in (ever had an infinite health code work most of the time but occasionally a big bad rocket/mega attack/explosion still kills you as it does enough damage... might well be this) to "fix" things or maybe keeps a value in the stack and operates from that but no reason not to at least attempt it.

The third thing in this is a thing to consider on more modern systems.
The CD is a blistering 2x read speed (whole 300 kilobytes a second which was not fast by the time the PS1 hit, and that is a theoretical ideal not having to reposition the laser or consider latency). To that end games don't run from the CD like they did on earlier cartridge based devices (GBA had very limited run from RAM but mostly ran from cart. DS copied binaries to RAM) and instead copy things to RAM. You can even demonstrate this by popping the lid (maybe with spring or mod chip) and removing the CD in various games -- you might just lose the music, not to mention various multi disc games even required it. Cheat makers knew this and so the cheat that targets RAM may in essence be acting like the game genie codes of old.
Find out where the binary lands in RAM (often will be readable with a header viewer, or indeed simple emulator) and if the apparent RAM code code targets that then you can hardpatch the code into the binary, give or take any compression that might have been done (and it is dubious whether compression was necessary/beneficial on the PS1**). I don't know offhand what the PS1 does for binary expansion purposes (see dynamic libraries, overlays and whatever other means there are to have extra code land in RAM just for a little while to be ejected when it is no longer any use, like a minigame or credits or something the game rarely displays) but if it is such a setup then you also have that.

**one of the various Sony requirements at points was time from power on to first useful button press had to be low. If compression allowed a faster binary load (again 300kb a second theoretical) then maybe. It would appear back again for things on the DS though so who knows.
Title: Re: What's an easy way to permanently inject a Gameshark code into a PS1 ISO?
Post by: MysticLord on April 15, 2021, 03:12:02 am
The laziest way to find a region of code in a game file that correspond to a region of code in RAM is to open up likely looking game files (SCUS, the bigger non-video/audio/image files) in a hex editor and search for a distinct bit of code from RAM in those game files.

Gameshark codes are just RAM addresses with a prefix, so long as they're not conditional (Joker, IIRC the username of someone who was involved in that scene in the 90s) gameshark codes. Joker codes execute the gameshark code on the next line if a condition in the Joker code is set, and there is a subset of Joker codes that increments parts of the gameshark code on the next line as well.

30012EA0 00FF //gameshark
0x12EA0 //RAM

With the PS1, you can use psxfin.exe's R3000 debugger - specifically the memory viewer - or you can use Duckstation's debugger. Make sure you prefix 0x to any address you go to (Ctrl + g) in the former's debugger.

Go to the address where the code is found, highlight maybe 16 bytes that are distinct (not all 00 or FF), copy them, open the most likely game file in your hex editor (I recommend XVI32), hit Ctrl + f in the hex editor, paste the bytes into that, and see what you can find.

You can accomplish quite a lot if you're clever with search terms and wildcards.