Skip to content

GSC decompiler

Antoine Willerval edited this page Nov 10, 2024 · 2 revisions

The GSC decompiler is here to decompile the compiled GSC scripts from a dump. It supports different kind of game version.

Options

To get the full list of options you can use:

acts gscd -h

The most important options are:

  • -g Produce GSC: Decompile the scripts
  • -a Produce ASM: Disassemble the scripts
  • -t [type] Set type: Tell to the decompiler the platform to use, pc, ps4 or pc_alpha (by default PC)
  • -o [directory] Set output dir: Tell the decompiler the output directory

Debug options

For all the dev options you need to enable the debug logger:

acts -l d gscd -h

The most important options are:

  • -l or -L Write relative location: Write the relative locations inside the scripts (-L) or inside the function (-l)
  • --rawhash Add raw hashes to export dump: Add raw hash to decompiled header
  • --hashmap [f] Write hash map: Write all the extracted hashes into f
  • --dumpstrings [f] Write strings: Write all the extracted strings into f

Decompile scripts

Assuming you have a dump in the directory gsc_dump, you might want to decompile all of them into gsc_dump_decomp. The base command to do that is:

acts gscd gsc_dump -o gsc_dump_decomp -g

If the dump is from a PS4 game, only -t ps4 should be added

acts gscd gsc_dump -o gsc_dump_decomp -g -t ps4

Using non-public VMs

If the decompiler for the VM you are using isn't public or fully public, you might have InvalidOpCode lines in the decompilation, for example

// Namespace emp_debuff
// Params 0, eflags: 0x2 linked
// Offset: 0x53b
// Size: 0x50
function function_3a7131767e718c6f() {
    if (vehicle::is_killstreak()) {
        InvalidOpCode(0x61);
        // Unknown operator (0x61, t10_6, PC)
    }
    return true;
}

It means that the code cannot be properly decompiled.

Using encrypted scripts

All the VMs after BO4 are encrypted (except the scripts from the MWIII vm before June), for BO4 the decryption function is available inside acts, but for the other VMs, you need first to decrypt the scripts.

If the script isn't decrypted first, the strings won't be available, giving results like:

// Namespace emp_debuff
// Params 0, eflags: 0x2 linked
// Offset: 0x98c
// Size: 0x29
function function_3e4ae1cf64f66600() {
    level utility::waittill_any_3("7_+\242\247Qp\233\2078", "\306\340\363M\371\257\311\30<)\375\314u'.\253\35\311", "\222\303@:\3\220\367\267\237\353\270Zn\320I\317");
    self.victim notify("]\355\213083\260\220\330J\337\365@\242\\323\233x\264x");
}

To decrypt the scripts, you need first to get a dump of the game, then you can use the tool scripts_decrypt.

For example to decrypt the directory gsc_dump into gsc_dump_dec for Black Ops Cold War(cw) using the dumped exe BlackOpsColdWar.exe, you can use this command

acts scripts_decrypt BlackOpsColdWar.exe cw gsc_dump gsc_dump_dec

By decompiling again you will have all the strings decrypted:

// Namespace emp_debuff
// Params 0, eflags: 0x2 linked
// Offset: 0x98c
// Size: 0x29
function function_3e4ae1cf64f66600() {
    level utility::waittill_any_3("game_ended", "round_end_finished", "start_game_ended");
    self.victim notify("buttonComboEarlyExit");
}
Clone this wiki locally