From 897f88a88ef0836259a703dfdac68dd4ca6030c8 Mon Sep 17 00:00:00 2001 From: Robin Gustafsson Date: Mon, 31 Jul 2023 18:20:07 +0200 Subject: [PATCH 1/2] Support reading of Godot4 .pck files --- src/pck/PckFile.cpp | 16 +++++++++++++++- src/pck/PckFile.h | 7 ++++++- 2 files changed, 21 insertions(+), 2 deletions(-) diff --git a/src/pck/PckFile.cpp b/src/pck/PckFile.cpp index a4cee8d..c178b3d 100644 --- a/src/pck/PckFile.cpp +++ b/src/pck/PckFile.cpp @@ -46,6 +46,16 @@ bool PckFile::Load() return false; } + if(FormatVersion == 2) { + Flags = Read32(); + FileOffsetBase = Read64(); + } + + if(Flags & PACK_DIR_ENCRYPTED) { + std::cout << "ERROR: pck is encrypted\n"; + return false; + } + // Reserved for(int i = 0; i < 16; i++) { Read32(); @@ -70,11 +80,15 @@ bool PckFile::Load() while(!entry.Path.empty() && entry.Path.back() == '\0') entry.Path.pop_back(); - entry.Offset = Read64(); + entry.Offset = FileOffsetBase + Read64(); entry.Size = Read64(); File->read(reinterpret_cast(entry.MD5.data()), sizeof(entry.MD5)); + if(FormatVersion == 2) { + entry.Flags = Read32(); + } + entry.GetData = [offset = entry.Offset, size = entry.Size, this]() { return ReadContainedFileContents(offset, size); }; diff --git a/src/pck/PckFile.h b/src/pck/PckFile.h index 43a14d5..68b13be 100644 --- a/src/pck/PckFile.h +++ b/src/pck/PckFile.h @@ -14,9 +14,10 @@ namespace pcktool { // Pck magic constexpr uint32_t PCK_HEADER_MAGIC = 0x43504447; +constexpr uint32_t PACK_DIR_ENCRYPTED = 1; // Highest pck version supported by this tool -constexpr int MAX_SUPPORTED_PCK_VERSION = 1; +constexpr int MAX_SUPPORTED_PCK_VERSION = 2; //! \brief A single pck file object. Handles reading and writing //! @@ -28,6 +29,7 @@ class PckFile { uint64_t Offset; uint64_t Size; std::array MD5 = {0}; + uint32_t Flags = 0; std::function GetData; }; @@ -109,6 +111,9 @@ class PckFile { uint32_t MinorGodotVersion = 0; uint32_t PatchGodotVersion = 0; + uint32_t Flags = 0; + uint64_t FileOffsetBase = 0; + //! Add trailing null bytes to the length of a path until it is a multiple of this size size_t PadPathsToMultipleWithNULLS = 4; From d9800c1a28499d31d3bfd31ad010f225a9956a99 Mon Sep 17 00:00:00 2001 From: Robin Gustafsson Date: Tue, 1 Aug 2023 18:23:03 +0200 Subject: [PATCH 2/2] Block saving of Godot4 .pck files The PCK version 2 format is implemented for reading but not for writing. --- src/pck/PckFile.cpp | 7 ++++++- src/pck/PckFile.h | 3 ++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/src/pck/PckFile.cpp b/src/pck/PckFile.cpp index c178b3d..0e4c551 100644 --- a/src/pck/PckFile.cpp +++ b/src/pck/PckFile.cpp @@ -41,7 +41,7 @@ bool PckFile::Load() MinorGodotVersion = Read32(); PatchGodotVersion = Read32(); - if(FormatVersion > MAX_SUPPORTED_PCK_VERSION) { + if(FormatVersion > MAX_SUPPORTED_PCK_VERSION_LOAD) { std::cout << "ERROR: pck is unsupported version: " << FormatVersion << "\n"; return false; } @@ -112,6 +112,11 @@ bool PckFile::Load() // ------------------------------------ // bool PckFile::Save() { + if(FormatVersion > MAX_SUPPORTED_PCK_VERSION_SAVE) { + std::cout << "ERROR: cannot save pck version: " << FormatVersion << "\n"; + return false; + } + const auto tmpWrite = Path + ".write"; File = std::fstream(tmpWrite, std::ios::trunc | std::ios::out | std::ios::binary); diff --git a/src/pck/PckFile.h b/src/pck/PckFile.h index 68b13be..bb4cd12 100644 --- a/src/pck/PckFile.h +++ b/src/pck/PckFile.h @@ -17,7 +17,8 @@ constexpr uint32_t PCK_HEADER_MAGIC = 0x43504447; constexpr uint32_t PACK_DIR_ENCRYPTED = 1; // Highest pck version supported by this tool -constexpr int MAX_SUPPORTED_PCK_VERSION = 2; +constexpr int MAX_SUPPORTED_PCK_VERSION_LOAD = 2; +constexpr int MAX_SUPPORTED_PCK_VERSION_SAVE = 1; //! \brief A single pck file object. Handles reading and writing //!