diff options
| author | AloXado320 <david.albujar.s.30@gmail.com> | 2026-01-24 00:46:11 -0500 |
|---|---|---|
| committer | Lywx <kiritodev01@gmail.com> | 2026-01-24 00:15:07 -0600 |
| commit | 9d468174cc752e31d06463a7fe7100a39ec86af7 (patch) | |
| tree | 2a1d6a39d4a95b7a8e89dd71be95084dd217c2c5 /src | |
| parent | 963a1f6830f1080a33f581c8b935c49060899214 (diff) | |
Build using C++17 and replace sha1 library
Diffstat (limited to 'src')
| -rw-r--r-- | src/Companion.cpp | 60 | ||||
| -rw-r--r-- | src/factories/CompressedTextureFactory.cpp | 9 | ||||
| -rw-r--r-- | src/factories/DisplayListOverrides.cpp | 3 | ||||
| -rw-r--r-- | src/factories/TextureFactory.cpp | 5 | ||||
| -rw-r--r-- | src/factories/fzerox/SequenceFactory.cpp | 8 | ||||
| -rw-r--r-- | src/factories/fzerox/SoundFontFactory.cpp | 2 | ||||
| -rw-r--r-- | src/factories/naudio/v0/AudioManager.cpp | 11 | ||||
| -rw-r--r-- | src/factories/naudio/v1/AudioContext.cpp | 1 | ||||
| -rw-r--r-- | src/factories/naudio/v1/AudioTableFactory.cpp | 3 | ||||
| -rw-r--r-- | src/factories/sf64/MessageFactory.cpp | 10 | ||||
| -rw-r--r-- | src/factories/sm64/GeoLayoutFactory.cpp | 2 | ||||
| -rw-r--r-- | src/utils/Decompressor.cpp | 5 | ||||
| -rw-r--r-- | src/utils/TorchUtils.h | 9 |
13 files changed, 78 insertions, 50 deletions
diff --git a/src/Companion.cpp b/src/Companion.cpp index 6f023e6..2ef7cf2 100644 --- a/src/Companion.cpp +++ b/src/Companion.cpp @@ -1,11 +1,12 @@ #include "Companion.h" #include "utils/Decompressor.h" +#include "utils/StringHelper.h" #include "utils/TorchUtils.h" #include "archive/SWrapper.h" #include "archive/ZWrapper.h" #include "spdlog/spdlog.h" -#include "hj/sha1.h" +#include "TinySHA1.hpp" #include <regex> #include <fstream> @@ -303,7 +304,7 @@ std::optional<ParseResultData> Companion::ParseNode(YAML::Node& node, std::strin bool executeDef = true; std::optional<std::shared_ptr<IParsedData>> result; - if(this->gConfig.modding && impl->SupportModdedAssets() && this->gModdedAssetPaths.contains(name)) { + if(this->gConfig.modding && impl->SupportModdedAssets() && Torch::contains(this->gModdedAssetPaths, name)) { auto path = fs::path(this->gConfig.moddingPath) / this->gModdedAssetPaths[name]; if(!exists(path)) { SPDLOG_ERROR("Modded asset {} not found", this->gModdedAssetPaths[name]); @@ -369,13 +370,13 @@ void Companion::ParseCurrentFileConfig(YAML::Node node) { } std::string externalFileName = (this->gSourceDirectory / externalFile.as<std::string>()).string(); - if (std::filesystem::relative(externalFileName, this->gAssetPath).string().starts_with("../")) { + if (StringHelper::StartsWith(std::filesystem::relative(externalFileName, this->gAssetPath).string(), "../")) { throw std::runtime_error("External File " + externalFileName + " Not In Asset Directory " + this->gAssetPath); } else if (std::filesystem::relative(externalFileName, this->gAssetPath).string() == "") { throw std::runtime_error("External File " + externalFileName + " Not In Asset Directory " + this->gAssetPath); } - if (!this->gAddrMap.contains(externalFileName)) { + if (!Torch::contains(this->gAddrMap, externalFileName)) { SPDLOG_INFO("Dependency on external file {}. Now processing {}", externalFileName, externalFileName); auto currentFile = this->gCurrentFile; auto currentDirectory = this->gCurrentDirectory; @@ -386,7 +387,7 @@ void Companion::ParseCurrentFileConfig(YAML::Node node) { YAML::Node root = YAML::LoadFile(externalFileName); - if (!this->gProcessedFiles.contains(this->gCurrentFile)) { + if (!Torch::contains(this->gProcessedFiles, this->gCurrentFile)) { ProcessFile(root); this->gProcessedFiles.insert(this->gCurrentFile); } @@ -1313,7 +1314,7 @@ void Companion::Process() { this->gCurrentDirectory = relative(entry.path(), this->gAssetPath).replace_extension(""); this->gCurrentFile = yamlPath; - if (!this->gProcessedFiles.contains(this->gCurrentFile)) { + if (!Torch::contains(this->gProcessedFiles, this->gCurrentFile)) { ProcessFile(root); this->gProcessedFiles.insert(this->gCurrentFile); } @@ -1440,7 +1441,7 @@ void Companion::RegisterFactory(const std::string& type, const std::shared_ptr<B } std::optional<std::shared_ptr<BaseFactory>> Companion::GetFactory(const std::string &type) { - if(!this->gFactories.contains(type)){ + if(!Torch::contains(this->gFactories, type)){ return std::nullopt; } @@ -1458,11 +1459,11 @@ std::optional<Table> Companion::SearchTable(uint32_t addr){ } std::optional<std::string> Companion::GetEnumFromValue(const std::string& key, int32_t id) { - if(!this->gEnums.contains(key)){ + if(!Torch::contains(this->gEnums, key)){ return std::nullopt; } - if(!this->gEnums[key].contains(id)){ + if(!Torch::contains(this->gEnums[key], id)){ return std::nullopt; } @@ -1473,15 +1474,15 @@ std::optional<std::uint32_t> Companion::GetFileOffsetFromSegmentedAddr(const uin auto segments = this->gConfig.segment; - if(segments.temporal.contains(segment)) { + if(Torch::contains(segments.temporal, segment)) { return segments.temporal[segment]; } - if(segments.local.contains(segment)) { + if(Torch::contains(segments.local, segment)) { return segments.local[segment]; } - if(segments.global.contains(segment)) { + if(Torch::contains(segments.global, segment)) { return segments.global[segment]; } @@ -1490,7 +1491,7 @@ std::optional<std::uint32_t> Companion::GetFileOffsetFromSegmentedAddr(const uin uint32_t Companion::PatchVirtualAddr(uint32_t addr) { if (addr & 0x80000000) { - if (gVirtualAddrMap.contains(gCurrentFile)) { + if (Torch::contains(gVirtualAddrMap, gCurrentFile)) { addr -= std::get<0>(gVirtualAddrMap[gCurrentFile]); addr += std::get<1>(gVirtualAddrMap[gCurrentFile]); } @@ -1500,21 +1501,21 @@ uint32_t Companion::PatchVirtualAddr(uint32_t addr) { } std::optional<std::tuple<std::string, YAML::Node>> Companion::GetNodeByAddr(uint32_t addr){ - if(!this->gAddrMap.contains(this->gCurrentFile)){ + if(!Torch::contains(this->gAddrMap, this->gCurrentFile)){ return std::nullopt; } // HACK: Adjust address to rom address if virtual address addr = PatchVirtualAddr(addr); - if(!this->gAddrMap[this->gCurrentFile].contains(addr)){ + if(!Torch::contains(this->gAddrMap[this->gCurrentFile], addr)){ for (auto &file : this->gCurrentExternalFiles) { - if (!this->gAddrMap.contains(file)) { + if (!Torch::contains(this->gAddrMap, file)) { SPDLOG_WARN("GetNodeByAddr: External File {} Not Found.", file); continue; } - if (!this->gAddrMap[file].contains(addr)) { + if (!Torch::contains(this->gAddrMap[file], addr)) { continue; } return this->gAddrMap[file][addr]; @@ -1526,7 +1527,7 @@ std::optional<std::tuple<std::string, YAML::Node>> Companion::GetNodeByAddr(uint } std::optional<std::string> Companion::GetStringByAddr(const uint32_t addr) { - if(this->gManualSegments.contains(addr)) { + if(Torch::contains(this->gManualSegments, addr)) { return this->gManualSegments[addr]; } @@ -1558,7 +1559,7 @@ std::optional<std::tuple<std::string, YAML::Node>> Companion::GetSafeNodeByAddr( } std::optional<std::string> Companion::GetSafeStringByAddr(const uint32_t addr, std::string type) { - if(this->gManualSegments.contains(addr)) { + if(Torch::contains(this->gManualSegments, addr)) { return this->gManualSegments[addr]; } @@ -1596,9 +1597,9 @@ std::string Companion::GetSymbolFromAddr(uint32_t address, bool validZero) { } std::optional<ParseResultData> Companion::GetParseDataByAddr(uint32_t addr) { - if(!this->gParseResults.contains(this->gCurrentFile)){ + if(!Torch::contains(this->gParseResults, this->gCurrentFile)){ for (auto &file : this->gCurrentExternalFiles) { - if (!this->gParseResults.contains(file)) { + if (!Torch::contains(this->gParseResults, file)) { SPDLOG_INFO("GetParseDataByAddr: External File {} Not Found.", file); continue; } @@ -1622,7 +1623,7 @@ std::optional<ParseResultData> Companion::GetParseDataByAddr(uint32_t addr) { } std::optional<ParseResultData> Companion::GetParseDataBySymbol(const std::string& symbol) { - if(!this->gParseResults.contains(this->gCurrentFile)){ + if(!Torch::contains(this->gParseResults, this->gCurrentFile)){ return std::nullopt; } @@ -1641,7 +1642,7 @@ std::optional<ParseResultData> Companion::GetParseDataBySymbol(const std::string std::optional<std::vector<std::tuple<std::string, YAML::Node>>> Companion::GetNodesByType(const std::string& type){ std::vector<std::tuple<std::string, YAML::Node>> nodes; - if(!this->gAddrMap.contains(this->gCurrentFile)){ + if(!Torch::contains(this->gAddrMap, this->gCurrentFile)){ return nodes; } @@ -1695,7 +1696,18 @@ std::string Companion::RelativePathToSrcDir(const std::string& path) const { } std::string Companion::CalculateHash(const std::vector<uint8_t>& data) { - return Chocobo1::SHA1().addData(data).finalize().toString(); + sha1::SHA1 s; + s.processBytes(data.data(), data.size()); + + uint32_t hash[5]; + s.getDigest(hash); + + char buf[41]; + std::snprintf(buf, sizeof(buf), + "%08x%08x%08x%08x%08x", + hash[0], hash[1], hash[2], hash[3], hash[4]); + + return std::string(buf); } std::optional<YAML::Node> Companion::AddAsset(YAML::Node asset) { diff --git a/src/factories/CompressedTextureFactory.cpp b/src/factories/CompressedTextureFactory.cpp index 34ccc61..685bc53 100644 --- a/src/factories/CompressedTextureFactory.cpp +++ b/src/factories/CompressedTextureFactory.cpp @@ -1,5 +1,6 @@ #include "CompressedTextureFactory.h" #include "utils/Decompressor.h" +#include "utils/TorchUtils.h" #include "spdlog/spdlog.h" #include "Companion.h" #include <iomanip> @@ -372,7 +373,7 @@ std::optional<std::shared_ptr<IParsedData>> CompressedTextureFactory::parse(std: uint32_t size; auto compression = GetSafeNode<std::string>(node, "compression"); CompressionType compressionType; - if (!sCompressionTypes.contains(compression)) { + if (!Torch::contains(sCompressionTypes, compression)) { SPDLOG_ERROR("Compresed Texture entry at {:X} in yaml missing compression type\n\ Please add one of the following compression types\n\ MIO0, YAY0, YAY1, YAZ0 (Unsupported)", offset); @@ -399,7 +400,7 @@ std::optional<std::shared_ptr<IParsedData>> CompressedTextureFactory::parse(std: return std::nullopt; } - if(!sTextureFormats.contains(format)) { + if(!Torch::contains(sTextureFormats, format)) { return std::nullopt; } @@ -469,7 +470,7 @@ std::optional<std::shared_ptr<IParsedData>> CompressedTextureFactory::parse_modd auto offset = GetSafeNode<uint32_t>(node, "offset"); auto compression = GetSafeNode<std::string>(node, "compression"); CompressionType compressionType; - if (!sCompressionTypes.contains(compression)) { + if (!Torch::contains(sCompressionTypes, compression)) { SPDLOG_ERROR("Compresed Texture entry at {:X} in yaml missing compression type\n\ Please add one of the following compression types\n\ MIO0, YAY0, YAY1, YAZ0 (Unsupported)", offset); @@ -484,7 +485,7 @@ std::optional<std::shared_ptr<IParsedData>> CompressedTextureFactory::parse_modd return std::nullopt; } - if(!sTextureFormats.contains(format)) { + if(!Torch::contains(sTextureFormats, format)) { return std::nullopt; } diff --git a/src/factories/DisplayListOverrides.cpp b/src/factories/DisplayListOverrides.cpp index 59a7344..5dc6086 100644 --- a/src/factories/DisplayListOverrides.cpp +++ b/src/factories/DisplayListOverrides.cpp @@ -1,6 +1,7 @@ #include "DisplayListOverrides.h" #include "utils/Decompressor.h" +#include "utils/TorchUtils.h" #include "DisplayListFactory.h" #include "spdlog/spdlog.h" #include "Companion.h" @@ -203,7 +204,7 @@ int Matrix(uint32_t ptr) { #endif std::optional<std::tuple<std::string, YAML::Node>> GetVtxOverlap(uint32_t ptr){ - if(mVtxOverlaps.contains(ptr)){ + if(Torch::contains(mVtxOverlaps, ptr)){ SPDLOG_INFO("Found overlap for ptr 0x{:X}", ptr); return mVtxOverlaps[ptr]; } diff --git a/src/factories/TextureFactory.cpp b/src/factories/TextureFactory.cpp index 8e9d53c..b7d555b 100644 --- a/src/factories/TextureFactory.cpp +++ b/src/factories/TextureFactory.cpp @@ -1,5 +1,6 @@ #include "TextureFactory.h" #include "utils/Decompressor.h" +#include "utils/TorchUtils.h" #include "spdlog/spdlog.h" #include "Companion.h" #include <iomanip> @@ -286,7 +287,7 @@ std::optional<std::shared_ptr<IParsedData>> TextureFactory::parse(std::vector<ui return std::nullopt; } - if(!sTextureFormats.contains(format)) { + if(!Torch::contains(sTextureFormats, format)) { return std::nullopt; } @@ -362,7 +363,7 @@ std::optional<std::shared_ptr<IParsedData>> TextureFactory::parse_modding(std::v return std::nullopt; } - if(!sTextureFormats.contains(format)) { + if(!Torch::contains(sTextureFormats, format)) { return std::nullopt; } diff --git a/src/factories/fzerox/SequenceFactory.cpp b/src/factories/fzerox/SequenceFactory.cpp index bacdfe0..74d2a6a 100644 --- a/src/factories/fzerox/SequenceFactory.cpp +++ b/src/factories/fzerox/SequenceFactory.cpp @@ -325,7 +325,7 @@ ExportResult FZX::SequenceCodeExporter::Export(std::ostream &write, std::shared_ } lastEndPos = command.pos + command.size; - if (data->mLabels.contains(command.pos)) { + if (Torch::contains(data->mLabels,command.pos)) { write << "// L____" << FORMAT_HEX2(command.pos, 3) << ":\n"; } @@ -1336,10 +1336,10 @@ std::optional<std::shared_ptr<IParsedData>> FZX::SequenceFactory::parse(std::vec command.channel = channel; command.layer = layer; - if (!existingPositions.contains(command.pos) && command.pos < size) { + if (!Torch::contains(existingPositions, command.pos) && command.pos < size) { existingPositions.insert(command.pos); } else { - while (!posStack.empty() && existingPositions.contains(posStack.back().pos)) { + while (!posStack.empty() && Torch::contains(existingPositions, posStack.back().pos)) { SPDLOG_INFO("POP BACK 0x{:X}", posStack.back().pos); posStack.pop_back(); } @@ -1990,7 +1990,7 @@ std::optional<std::shared_ptr<IParsedData>> FZX::SequenceFactory::parse(std::vec uint16_t addr = envAddr; reader.Seek(addr, LUS::SeekOffsetType::Start); - while (!existingPositions.contains(addr) && addr < size) { + while (!Torch::contains(existingPositions, addr) && addr < size) { auto delay = READ_S16; auto arg = READ_S16; command.args.emplace_back(delay); diff --git a/src/factories/fzerox/SoundFontFactory.cpp b/src/factories/fzerox/SoundFontFactory.cpp index 86fb250..1c95121 100644 --- a/src/factories/fzerox/SoundFontFactory.cpp +++ b/src/factories/fzerox/SoundFontFactory.cpp @@ -376,7 +376,7 @@ ExportResult FZX::SoundFontBinaryExporter::Export(std::ostream &write, std::shar std::string FZX::SoundFontFactory::RegisterSoundFontData(std::string symbol, FZX::DataType dataType, uint32_t offset, std::map<uint32_t, std::pair<FZX::DataType, std::string>>& dataMap, std::unordered_map<FZX::DataType, uint32_t>& dataCountMap) { std::string dataName; - if (dataMap.contains(offset)) { + if (Torch::contains(dataMap, offset)) { return dataMap.at(offset).second; } diff --git a/src/factories/naudio/v0/AudioManager.cpp b/src/factories/naudio/v0/AudioManager.cpp index 1e7fc9a..51b44d5 100644 --- a/src/factories/naudio/v0/AudioManager.cpp +++ b/src/factories/naudio/v0/AudioManager.cpp @@ -13,6 +13,7 @@ #include "spdlog/spdlog.h" #include "lib/binarytools/BinaryReader.h" #include "spdlog/spdlog.h" +#include "utils/TorchUtils.h" std::unordered_map<std::string, uint32_t> name_table; std::unordered_map<uint32_t, std::string> sample_table; @@ -27,7 +28,7 @@ std::vector<uint32_t> PyUtils::range(uint32_t start, uint32_t end) { } std::string gen_name(const std::string& prefix){ - if(!name_table.contains(prefix)){ + if(!Torch::contains(name_table, prefix)){ name_table[prefix] = 0; } return prefix + std::to_string(name_table[prefix]++); @@ -42,7 +43,7 @@ AudioBankSample* SampleBank::AddSample(uint32_t addr, size_t sampleSize, const A AudioBankSample* entry; - if(this->entries.contains(addr)){ + if(Torch::contains(this->entries, addr)){ entry = this->entries[addr]; assert(entry->book == book); assert(entry->loop == loop); @@ -428,7 +429,7 @@ TBLFile AudioManager::parse_tbl(std::vector<uint8_t>& data, std::vector<Entry>& TBLFile tbl; std::unordered_map<uint32_t, std::string> cache; for(auto &entry : entries){ - if(!cache.contains(entry.offset)){ + if(!Torch::contains(cache, entry.offset)){ std::string name = gen_name("sample_bank"); auto* sampleBank = new SampleBank{ name, entry.offset, PyUtils::slice(data, entry.offset, entry.offset + entry.length) @@ -494,7 +495,7 @@ void AudioManager::bind_sample(YAML::Node& node, const std::string& path){ } std::string& AudioManager::get_sample(uint32_t id) { - if(!sample_table.contains(id)) { + if(!Torch::contains(sample_table, id)) { throw std::runtime_error("Failed to find sample with id " + std::to_string(id)); } return sample_table[id]; @@ -535,7 +536,7 @@ AudioBankSample AudioManager::get_aifc(int32_t index) { } uint32_t AudioManager::get_index(AudioBankSample* entry) { - if(!this->sampleMap.contains(entry)){ + if(!Torch::contains(this->sampleMap, entry)){ return -1; } return this->sampleMap[entry]; diff --git a/src/factories/naudio/v1/AudioContext.cpp b/src/factories/naudio/v1/AudioContext.cpp index f2b0dd0..6529a58 100644 --- a/src/factories/naudio/v1/AudioContext.cpp +++ b/src/factories/naudio/v1/AudioContext.cpp @@ -1,7 +1,6 @@ #include "AudioContext.h" #include "spdlog/spdlog.h" #include "Companion.h" -#include "utils/StringHelper.h" std::unordered_map<AudioTableType, TableEntry> AudioContext::tables; NAudioDrivers AudioContext::driver = NAudioDrivers::UNKNOWN; diff --git a/src/factories/naudio/v1/AudioTableFactory.cpp b/src/factories/naudio/v1/AudioTableFactory.cpp index 5f82b8c..f6e37dd 100644 --- a/src/factories/naudio/v1/AudioTableFactory.cpp +++ b/src/factories/naudio/v1/AudioTableFactory.cpp @@ -1,5 +1,6 @@ #include "AudioTableFactory.h" #include "utils/Decompressor.h" +#include "utils/TorchUtils.h" #include "spdlog/spdlog.h" #include "AudioContext.h" #include "Companion.h" @@ -109,7 +110,7 @@ std::optional<std::shared_ptr<IParsedData>> AudioTableFactory::parse(std::vector auto format = GetSafeNode<std::string>(node, "format"); std::transform(format.begin(), format.end(), format.begin(), ::toupper); - if(!gTableTypes.contains(format)) { + if(!Torch::contains(gTableTypes, format)) { return std::nullopt; } diff --git a/src/factories/sf64/MessageFactory.cpp b/src/factories/sf64/MessageFactory.cpp index ca1a624..0d1b527 100644 --- a/src/factories/sf64/MessageFactory.cpp +++ b/src/factories/sf64/MessageFactory.cpp @@ -1,6 +1,8 @@ #include "MessageFactory.h" #include "utils/Decompressor.h" +#include "utils/StringHelper.h" +#include "utils/TorchUtils.h" #include "spdlog/spdlog.h" #include "Companion.h" #include <regex> @@ -201,9 +203,9 @@ std::optional<std::shared_ptr<IParsedData>> SF64::MessageFactory::parse(std::vec mesgStr << whitespace; whitespace = ""; } - if(enumCode.starts_with("_")){ + if (StringHelper::StartsWith(enumCode, "_")) { mesgStr << enumCode.substr(1); - } else if(ASCIITable.contains(enumCode)){ + } else if (Torch::contains(ASCIITable, enumCode)){ mesgStr << ASCIITable[enumCode]; } @@ -276,9 +278,9 @@ std::optional<std::shared_ptr<IParsedData>> SF64::MessageFactory::parse_modding( mesgStr << whitespace; whitespace = ""; } - if(enumCode.starts_with("_")){ + if (StringHelper::StartsWith(enumCode, "_")) { mesgStr << enumCode.substr(1); - } else if(ASCIITable.contains(enumCode)){ + } else if (Torch::contains(ASCIITable, enumCode)){ mesgStr << ASCIITable[enumCode]; } } diff --git a/src/factories/sm64/GeoLayoutFactory.cpp b/src/factories/sm64/GeoLayoutFactory.cpp index 37d0e74..73e4a2e 100644 --- a/src/factories/sm64/GeoLayoutFactory.cpp +++ b/src/factories/sm64/GeoLayoutFactory.cpp @@ -28,7 +28,7 @@ uint64_t RegisterAutoGen(uint32_t ptr, std::string type) { void StoreFunc(uint32_t vram) { return; - if(!gFunctionMap.contains(vram)) { + if(!Torch::contains(gFunctionMap, vram)) { return; } diff --git a/src/utils/Decompressor.cpp b/src/utils/Decompressor.cpp index 934a84f..9181099 100644 --- a/src/utils/Decompressor.cpp +++ b/src/utils/Decompressor.cpp @@ -1,4 +1,5 @@ #include "Decompressor.h" +#include "TorchUtils.h" #include <stdexcept> #include "spdlog/spdlog.h" @@ -15,7 +16,7 @@ std::unordered_map<uint32_t, DataChunk*> gCachedChunks; DataChunk* Decompressor::Decode(const std::vector<uint8_t>& buffer, const uint32_t offset, const CompressionType type, bool ignoreCache) { - if(!ignoreCache && gCachedChunks.contains(offset)){ + if(!ignoreCache && Torch::contains(gCachedChunks, offset)){ return gCachedChunks[offset]; } @@ -61,7 +62,7 @@ DataChunk* Decompressor::Decode(const std::vector<uint8_t>& buffer, const uint32 } DataChunk* Decompressor::DecodeTKMK00(const std::vector<uint8_t>& buffer, const uint32_t offset, const uint32_t size, const uint32_t alpha) { - if(gCachedChunks.contains(offset)){ + if(Torch::contains(gCachedChunks, offset)){ return gCachedChunks[offset]; } diff --git a/src/utils/TorchUtils.h b/src/utils/TorchUtils.h index 8b7a3f1..275ec47 100644 --- a/src/utils/TorchUtils.h +++ b/src/utils/TorchUtils.h @@ -24,6 +24,15 @@ std::string to_hex(T number, const bool append0x = true) { return format; } +template <typename Container, typename Key> +constexpr bool contains(const Container& c, const Key& k) { +#if __cplusplus >= 202002L + return c.contains(k); +#else + return c.find(k) != c.end(); +#endif +} + uint32_t translate(uint32_t offset); std::vector<std::filesystem::directory_entry> getRecursiveEntries(const std::filesystem::path baseDir); |
