metaforce/DataSpec/AssetNameMap.cpp

96 lines
3.2 KiB
C++
Raw Normal View History

2017-07-13 04:39:52 -07:00
#include "AssetNameMap.hpp"
#include "athena/Compression.hpp"
2017-07-13 04:39:52 -07:00
#include "athena/MemoryReader.hpp"
2018-01-01 02:15:26 -08:00
extern "C" const uint8_t ASSET_NAME_MP32[];
extern "C" const size_t ASSET_NAME_MP32_SZ;
extern "C" const size_t ASSET_NAME_MP32_DECOMPRESSED_SZ;
2018-01-01 02:15:26 -08:00
extern "C" const uint8_t ASSET_NAME_MP64[];
extern "C" const size_t ASSET_NAME_MP64_SZ;
extern "C" const size_t ASSET_NAME_MP64_DECOMPRESSED_SZ;
2017-07-13 04:39:52 -07:00
2018-12-07 21:30:43 -08:00
namespace DataSpec::AssetNameMap {
2017-07-13 04:39:52 -07:00
logvisor::Module Log("AssetNameMap");
2018-12-07 21:30:43 -08:00
struct SAsset {
std::string name;
std::string directory;
hecl::FourCC type;
SAsset() = default;
SAsset(const hecl::FourCC& typeIn, athena::io::IStreamReader& in) : type(typeIn) {
uint32_t nameLen = in.readUint32Big();
name = in.readString(nameLen);
uint32_t dirLen = in.readUint32Big();
directory = in.readString(dirLen);
}
2017-07-13 04:39:52 -07:00
};
static std::unordered_map<uint64_t, SAsset> g_AssetNameMap;
static bool g_AssetNameMapInit = false;
2018-12-07 21:30:43 -08:00
void LoadAssetMap(athena::io::MemoryReader& ar) {
if (!ar.hasError()) {
hecl::FourCC magic;
if (ar.length() >= 4)
ar.readBytesToBuf(&magic, 4);
if (magic != FOURCC('AIDM'))
2021-06-07 12:29:18 -07:00
Log.report(
logvisor::Warning,
FMT_STRING("Unable to load asset map; Assets will not have proper filenames for most files."));
2018-12-07 21:30:43 -08:00
else {
uint32_t assetCount = ar.readUint32Big();
g_AssetNameMap.reserve(assetCount);
for (uint32_t i = 0; i < assetCount; ++i) {
hecl::FourCC type;
ar.readBytesToBuf(&type, 4);
uint64_t id = ar.readUint64Big();
g_AssetNameMap[id] = SAsset(type, ar);
}
2017-07-13 04:39:52 -07:00
}
2018-12-07 21:30:43 -08:00
}
2017-07-13 04:39:52 -07:00
}
2018-12-07 21:30:43 -08:00
void InitAssetNameMap() {
if (g_AssetNameMapInit)
return;
2017-07-13 04:39:52 -07:00
2020-04-11 15:51:39 -07:00
Log.report(logvisor::Info, FMT_STRING("Initializing asset name database..."));
2017-07-23 02:21:18 -07:00
2018-12-07 21:30:43 -08:00
/* First load the 32bit map for MP1/2 */
2020-04-23 23:49:40 -07:00
if (ASSET_NAME_MP32_DECOMPRESSED_SZ != 0u) {
auto* decompressed = new uint8_t[ASSET_NAME_MP32_DECOMPRESSED_SZ];
athena::io::Compression::decompressZlib(ASSET_NAME_MP32, ASSET_NAME_MP32_SZ, decompressed,
ASSET_NAME_MP32_DECOMPRESSED_SZ);
athena::io::MemoryReader ar(decompressed, ASSET_NAME_MP32_DECOMPRESSED_SZ);
2018-12-07 21:30:43 -08:00
LoadAssetMap(ar);
delete[](decompressed);
} else {
2021-06-07 12:29:18 -07:00
Log.report(
logvisor::Warning,
FMT_STRING("AssetNameMap32 unavailable; Assets will not have proper filenames for most files."));
2018-12-07 21:30:43 -08:00
}
/* Now load the 64bit map for MP3 */
2020-04-23 23:49:40 -07:00
if (ASSET_NAME_MP64_DECOMPRESSED_SZ != 0u) {
auto* decompressed = new uint8_t[ASSET_NAME_MP64_DECOMPRESSED_SZ];
athena::io::Compression::decompressZlib(ASSET_NAME_MP64, ASSET_NAME_MP64_SZ, decompressed,
ASSET_NAME_MP64_DECOMPRESSED_SZ);
athena::io::MemoryReader ar(decompressed, ASSET_NAME_MP64_DECOMPRESSED_SZ);
2018-12-07 21:30:43 -08:00
LoadAssetMap(ar);
delete[](decompressed);
} else {
2021-06-07 12:29:18 -07:00
Log.report(
logvisor::Warning,
FMT_STRING("AssetNameMap64 unavailable; Assets will not have proper filenames for most files."));
2018-12-07 21:30:43 -08:00
}
g_AssetNameMapInit = true;
2017-07-13 04:39:52 -07:00
}
2018-12-07 21:30:43 -08:00
const std::string* TranslateIdToName(const UniqueID32& id) {
if (g_AssetNameMap.find(id.toUint64()) == g_AssetNameMap.cend())
2018-12-07 21:30:43 -08:00
return nullptr;
2017-07-13 04:39:52 -07:00
2018-12-07 21:30:43 -08:00
return &g_AssetNameMap[id.toUint64()].name;
2017-07-13 04:39:52 -07:00
}
2018-12-07 21:30:43 -08:00
} // namespace DataSpec::AssetNameMap