vfsfitvnm / frida-il2cpp-bridge

A Frida module to dump, trace or hijack any Il2Cpp application at runtime, without needing the global-metadata.dat file.
https://github.com/vfsfitvnm/frida-il2cpp-bridge/wiki
MIT License
946 stars 194 forks source link

Generating Ghidra/IDA scripts like Il2CppDumper #322

Open LeonLeonPotato opened 1 year ago

LeonLeonPotato commented 1 year ago

It would help reverse engineering the source code instead of having to guess based on trace and dump.cs

commonuserlol commented 1 year ago

actually il2cppdumper just copy ready2use script. for example you can use script from https://github.com/vfsfitvnm/frida-il2cpp-bridge/discussions/113, but it sets only method name, for fields, strings, etc metadata dump still needed

vfsfitvnm commented 1 year ago

Agree, but I doubt I'll work on this anytime soon. I made few attempts in the past, but I always gave up at a certain point. PS: I won't (personally) support IDA (can't test/use it).

If you want to contribute, this is your chance :smile:

vfsfitvnm commented 1 year ago

For instance, the solution would consist in generating a machine readable metadata file (i.e. a json file or a db) so that we can use the target disassembler scripting language to load the metadata into the project.

OT: We could make things even bigger by using the very same metadata to generate some sort of type safe typescript bindings, so that:

Il2Cpp.corlib.class("System.Int32").new();

becomes:

new mscorlib.System.Int32();
commonuserlol commented 1 year ago

Agree, but I doubt I'll work on this anytime soon. I made few attempts in the past, but I always gave up at a certain point. PS: I won't (personally) support IDA (can't test/use it).

If you want to contribute, this is your chance smile

actually i dont have idea how to find metadata in memory.. im tried this on 3 apps (android), but no one found metadata... also im tried this one but cannot find il2cpp_build_metadata export

vfsfitvnm commented 1 year ago

il2cpp_build_metadata was a CModule function I implemented by my own. By "metadata" I didn't mean global-metadata.dat, but just a machine readable file that contains any metadata of the application we can retrieve (just like global-metadata.dat). It's just like Il2Cpp::dump, but generate a json file instead of a pseudo cs file.

commonuserlol commented 1 year ago

yes i understood this, but first need to find metadata in memory.. i have one idea and I'll try implement it soon as I can

commonuserlol commented 1 year ago

yeah, im generated pseudo metadata .json file, now need figure how to correctly generate .h file and apply c++ signatures..

commonuserlol commented 1 year ago

unfortunately I have very little knowledge about the internals of il2cpp so I'll leave it here, maybe it will be useful to someone for further development (this is not the final version) and yes, the code is not really good src/il2cpp/dump.ts

let Metadata = {
                "ScriptMethod": [],
                "ScriptString": [],
                "ScriptMetadata": [],
                "Addresses": [] //not used right now
            };

            for (const assembly of Il2Cpp.domain.assemblies) {
                inform(`dumping ${assembly.name}...`);

                for (const klass of assembly.image.classes) {

                    for (const method of klass.methods) {

                        //@ts-ignore
                        Metadata.ScriptMethod.push({
                            "Address": method.relativeVirtualAddress.toUInt32(),
                            "Name": `${method.class.type.name}$$${method.name}`,
                            "Signature": "soon",
                            "TypeSignature": "soon"
                        });
                    }

                    for (const field of klass.fields) {
                        //@ts-ignore
                        Metadata.ScriptMetadata.push({
                            "Address": klass.handle.sub(Il2Cpp.module.base).add(field.offset).toUInt32(),
                            "Name": field.type.name,
                            "Signature": "soon"
                        });
                    }
                }
            }

            //NOTE: this wont dump ALL strings, only which in memory right now
            inform("dumping strings...");
            for (const str of (Il2Cpp.gc.choose(Il2Cpp.corlib.class("System.String")))) {

                //@ts-ignore
                Metadata.ScriptString.push({
                    "Address": str.handle.sub(Il2Cpp.module.base).toUInt32(),
                    "Value": (new Il2Cpp.String(str)).content ?? ""
                });
            }
            file.write(JSON.stringify(Metadata, null, 4));
            file.flush();
            file.close();
            ok(`dump saved to ${destination}`);