Skip to content

Commit

Permalink
load mwiii assets from Cordycep
Browse files Browse the repository at this point in the history
  • Loading branch information
ate47 committed Jul 31, 2024
1 parent f06f45b commit 21d6c4e
Show file tree
Hide file tree
Showing 8 changed files with 1,115 additions and 4 deletions.
9 changes: 8 additions & 1 deletion config/common_hashes/path.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6554,4 +6554,11 @@ leaderboards/mp_leaderboards_reset.csv
gamedata/tables/common/countrytable.csv
scripts/core_common/encounters/wave_manager.gsc
scripts/core_common/ai/systems/ai_interactables.gsc
scripts/core_common/ai/systems/ai_interactables.csc
scripts/core_common/ai/systems/ai_interactables.csc
scripts/mp/gametypes/ob_season1.gsc
scripts/mp/gametypes/ob_season2.gsc
scripts/mp/gametypes/ob_season3.gsc
scripts/mp/gametypes/ob_season4.gsc
scripts/mp/gametypes/ob_season5.gsc
scripts/unittest/private.gsc
scripts/unittest/callback.gsc
2 changes: 1 addition & 1 deletion src/acts/hashutils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -283,7 +283,7 @@ char* hashutils::ExtractTmp(const char* type, uint64_t hash) {

const char* hashutils::ExtractPtr(uint64_t hash) {
ReadDefaultFile();
const auto res = g_hashMap.find(hash);
const auto res = g_hashMap.find(hash & 0x7FFFFFFFFFFFFFFF);
if (res == g_hashMap.end()) {
return NULL;
}
Expand Down
2 changes: 1 addition & 1 deletion src/acts/tools/hash.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ namespace {
int lookuptool(Process& proc, int argc, const char* argv[]) {
hashutils::ReadDefaultFile();
for (int i = 2; i < argc; i++) {
int64_t v = strtoull(argv[i], nullptr, 0x10);
uint64_t v = strtoull(argv[i], nullptr, 0x10);
const char* extract = hashutils::ExtractPtr(v);
if (extract) {
LOG_INFO("{:x}={}", v, extract);
Expand Down
135 changes: 135 additions & 0 deletions src/acts/tools/hashes/compiled_files.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
#include <includes.hpp>
#include "compiled_files.hpp"
#include <regex>

namespace {
using namespace tool::hashes::compiled_files;

int cfd(Process& proc, int argc, const char* argv[]) {
if (argc < 3) {
return tool::BAD_USAGE;
}
const char* input{ argv[2] };

const char* output{ argc < 4 ? "output_raw" : argv[3] };

std::vector<std::filesystem::path> files{};

utils::GetFileRecurse(input, files, [](const std::filesystem::path& p) {
auto s = p.string();
return s.ends_with(".cf");
});

hashutils::ReadDefaultFile();

std::string buff{};
std::filesystem::path outputDir{ output };
for (const std::filesystem::path& file : files) {
if (!utils::ReadFile(file, buff)) {
LOG_ERROR("Can't read file {}", file.string());
continue;
}

const CompiledFileHeader& header = *reinterpret_cast<CompiledFileHeader*>(buff.data());

if (header.magic != MAGIC) {
LOG_ERROR("Can't read file {}: invalid magic", file.string());
continue;
}

const char* n = hashutils::ExtractPtr(header.name);

std::filesystem::path out;
if (n) {
// script bundle thing
n = utils::MapString(utils::CloneString(n), [](char c) -> char { return c == ':' ? '/' : c; });
if (header.isSpecial) {
out = outputDir / header.type / n;
} else{
out = outputDir / n;
}
}
else {
char* fileName;
if (*header.preferedExtension) {
fileName = utils::va("file_%llx.%s", header.name, header.preferedExtension);
}
else {
fileName = utils::va("file_%llx", header.name);
}
if (header.isSpecial) {
out = outputDir / header.type / fileName;
}
else {
if (*header.type) {
out = outputDir / "hashed" / header.type / fileName;
}
else {
out = outputDir / fileName;
}
}
}

std::filesystem::create_directories(out.parent_path());


if (header.isString) {
std::string strBuff{ buff.data() + sizeof(header), buff.size() - sizeof(header) };

static std::regex pattern{ "hash_([0-9a-fA-F]{1,16})" };

size_t idx{};
while (idx < strBuff.size()) {
auto rbegin = std::sregex_iterator(strBuff.begin() + idx, strBuff.end(), pattern);

if (rbegin == std::sregex_iterator()) {
break; // nothing else
}

std::smatch match = *rbegin;
size_t mstart = match.position() + idx;
size_t mlen = match.length();

try {
uint64_t hash = std::stoull(match[1].str(), nullptr, 16);
const char* ptr = hashutils::ExtractPtr(hash);
if (ptr) {
std::string before = strBuff.substr(0, mstart);
std::string after = strBuff.substr(mstart + mlen, strBuff.size() - mstart - mlen);

strBuff = before + ptr + after;
mlen = strlen(ptr);
LOG_TRACE("{} REPLACED {:x} -> {}", out.string(), hash, ptr);
}
}
catch (std::runtime_error& e) {
LOG_WARNING("Ignored bad hash: {}", e.what());
}
//LOG_TRACE("{} old {} -> {}", idx, mstart + mlen, out.string());
idx = mstart + mlen;
}


if (!utils::WriteFile(out, strBuff.data(), strBuff.size())) {
LOG_ERROR("Can't write file {}", out.string());
}
else {
LOG_INFO("Write {} -> {}", file.string(), out.string());
}
}
else {
if (!utils::WriteFile(out, buff.data() + sizeof(header), buff.size() - sizeof(header))) {
LOG_ERROR("Can't write file {}", out.string());
}
else {
LOG_INFO("Write {} -> {}", file.string(), out.string());
}
}

}
return tool::OK;
}

ADD_TOOL("cfd", "hash", " [dir] (output)", "decompile raw compiled file (.cf)", nullptr, cfd);

}
13 changes: 13 additions & 0 deletions src/acts/tools/hashes/compiled_files.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#pragma once
namespace tool::hashes::compiled_files {
constexpr uint64_t MAGIC = 0x123456ACCF10;

struct CompiledFileHeader {
uint64_t magic{ 0x123456ACCF10 };
uint64_t name;
uint8_t isString{};
uint8_t isSpecial{};
char type[0x10]{ 0 };
char preferedExtension[0x10]{ 0 };
};
}
Loading

0 comments on commit 21d6c4e

Please sign in to comment.