wins1ey / LibreSplit

Free speedrun timer with auto splitting and load removal for Linux.
GNU General Public License v3.0
21 stars 7 forks source link

Add signature scanning #58

Open Loomeh opened 3 months ago

Loomeh commented 3 months ago

This PR adds a signature scanning function to LibreSplit.

Signature scanning scans the process for a specific byte array and returns the address of where that byte array is located. This is useful for executables that are frequently updated.

The sig_scan function takes a string of an IDA-style byte array and can also take an integer offset as a second parameter.

Example: signature = sig_scan("89 5C 24 ?? 89 44 24 ?? 74 ?? 48 8D 15", 4)

Returns: 14123ce19

Here is a small demo script for SPRAWL, which is game that uses signature scanning in its autosplitter:

process('Sprawl-Win64-Shipping.exe')

local featuretest = 0

function state()
    -- Perform the signature scan to find the initial address
    featuretest = sig_scan("89 5C 24 ?? 89 44 24 ?? 74 ?? 48 8D 15", 4)

    if featuretest == 0 then
        print("Signature scan did not find the address.")
    else
        -- Read an integer value from the found address
        local readValue = readAddress('int', 'Sprawl-Win64-Shipping.exe', featuretest)
        print("Feature test address: ", featuretest)
        print("Read value: ", readValue)
    end
end
EXtremeExploit commented 3 months ago

what did you do to docs?? :sob:

Loomeh commented 3 months ago

I used a website for editing the Markdown file, I guess it screwed up the formatting 😭

Loomeh commented 3 months ago

@EXtremeExploit I think I've fixed this in my latest commit? I ran with your idea of turning it into a uint16_t. An FF byte in the string should now be converted to 0x00FF and an ?? byte in the string should be converted to 0xFF00. A pretty big oversight and I'm surprised I didn't catch it, sorry :(

EXtremeExploit commented 3 months ago

Would also be cool to also add the example you provided in the PR comment on the docs, just a thought i had while reviewing

Loomeh commented 3 months ago

Would also be cool to also add the example you provided in the PR comment on the docs, just a thought i had while reviewing

Done :)

Loomeh commented 3 months ago

Im a bit confused, i could be wrong or right and sig_scan has to return a number

@EXtremeExploit Lua seems to automatically handle the conversion of hexadecimal strings to numbers.

Example:

current.isLoading = readAddress('bool', "0x58FAAC")

I replaced the hex number in this line in the Jet Set Radio autosplitter with a string representation of the same hex number, and it still worked perfectly fine.

I think it would be better to just leave the conversion to Lua as trying to do it in C can lead to lots of unnecessary complications (with hex numbers containing letters and whatnot).

I'll add a note in the documentation about this to prevent any confusion.

EXtremeExploit commented 3 months ago

I replaced the hex number in this line in the Jet Set Radio autosplitter with a string representation of the same hex number, and it still worked perfectly fine.

does it still work if you remove the "0x"? beause thats what sig_func is returning, if it works fine then i think it can get approved. My guess is that it works because you specifically specified the 0x saying the string is a hexadecimal number, but without it it would treat it as a base10 number

i asked wins1ey and told me to just approve it and not merge it yet because of the other open PR if thats fine

IogaMaster commented 3 months ago

Any update?

Loomeh commented 3 months ago

It seems like Lua only recognizes hexadecimal numbers if they're prefixed with "0x", so I've modified the code to prefix the found address with "0x" and I've changed it so that it returns a string instead of an integer.