diff --git a/src/ZoneCommon/Game/IW3/ZoneConstantsIW3.h b/src/ZoneCommon/Game/IW3/ZoneConstantsIW3.h index c8749356..db0e8333 100644 --- a/src/ZoneCommon/Game/IW3/ZoneConstantsIW3.h +++ b/src/ZoneCommon/Game/IW3/ZoneConstantsIW3.h @@ -38,7 +38,8 @@ namespace IW3 static constexpr size_t AUTHED_CHUNK_SIZE = 0x2000; static constexpr unsigned AUTHED_CHUNK_COUNT_PER_GROUP = 256; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 4u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 28u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 4u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace IW3 diff --git a/src/ZoneCommon/Game/IW4/ZoneConstantsIW4.h b/src/ZoneCommon/Game/IW4/ZoneConstantsIW4.h index 598230cd..2153fb42 100644 --- a/src/ZoneCommon/Game/IW4/ZoneConstantsIW4.h +++ b/src/ZoneCommon/Game/IW4/ZoneConstantsIW4.h @@ -60,7 +60,8 @@ namespace IW4 static constexpr size_t AUTHED_CHUNK_SIZE = 0x2000; static constexpr unsigned AUTHED_CHUNK_COUNT_PER_GROUP = 256; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 4u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 28u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 4u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace IW4 diff --git a/src/ZoneCommon/Game/IW5/ZoneConstantsIW5.h b/src/ZoneCommon/Game/IW5/ZoneConstantsIW5.h index 0e56f83d..c3f70d91 100644 --- a/src/ZoneCommon/Game/IW5/ZoneConstantsIW5.h +++ b/src/ZoneCommon/Game/IW5/ZoneConstantsIW5.h @@ -40,7 +40,8 @@ namespace IW5 static constexpr size_t AUTHED_CHUNK_SIZE = 0x2000; static constexpr unsigned AUTHED_CHUNK_COUNT_PER_GROUP = 256; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 4u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 28u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 4u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace IW5 diff --git a/src/ZoneCommon/Game/QOS/ZoneConstantsQOS.h b/src/ZoneCommon/Game/QOS/ZoneConstantsQOS.h index 59d6dd34..37c6adc5 100644 --- a/src/ZoneCommon/Game/QOS/ZoneConstantsQOS.h +++ b/src/ZoneCommon/Game/QOS/ZoneConstantsQOS.h @@ -16,7 +16,8 @@ namespace QOS static constexpr size_t FILE_HEADER_SIZE = 28; static constexpr size_t AUTHED_CHUNK_SIZE = 0x20000; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 3u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 29u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 3u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace QOS diff --git a/src/ZoneCommon/Game/T4/ZoneConstantsT4.h b/src/ZoneCommon/Game/T4/ZoneConstantsT4.h index 4b3ff034..7401473a 100644 --- a/src/ZoneCommon/Game/T4/ZoneConstantsT4.h +++ b/src/ZoneCommon/Game/T4/ZoneConstantsT4.h @@ -18,7 +18,8 @@ namespace T4 static_assert(std::char_traits::length(MAGIC_UNSIGNED) == sizeof(ZoneHeader::m_magic)); static constexpr size_t AUTHED_CHUNK_SIZE = 0x2000; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 3u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 29u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 3u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace T4 diff --git a/src/ZoneCommon/Game/T5/ZoneConstantsT5.h b/src/ZoneCommon/Game/T5/ZoneConstantsT5.h index b36559ea..cc0b2d0f 100644 --- a/src/ZoneCommon/Game/T5/ZoneConstantsT5.h +++ b/src/ZoneCommon/Game/T5/ZoneConstantsT5.h @@ -20,7 +20,8 @@ namespace T5 static constexpr size_t AUTHED_CHUNK_SIZE = 0x2000; static constexpr unsigned AUTHED_CHUNK_COUNT_PER_GROUP = 256; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 3u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 29u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 3u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; }; } // namespace T5 diff --git a/src/ZoneCommon/Game/T6/ZoneConstantsT6.h b/src/ZoneCommon/Game/T6/ZoneConstantsT6.h index 8eae1291..ada75eac 100644 --- a/src/ZoneCommon/Game/T6/ZoneConstantsT6.h +++ b/src/ZoneCommon/Game/T6/ZoneConstantsT6.h @@ -33,7 +33,8 @@ namespace T6 static constexpr unsigned XCHUNK_SIZE = 0x8000; static constexpr unsigned XCHUNK_MAX_WRITE_SIZE = XCHUNK_SIZE - 0x40; static constexpr unsigned VANILLA_BUFFER_SIZE = 0x80000; - static constexpr unsigned OFFSET_BLOCK_BIT_COUNT = 3u; + static constexpr unsigned ZONE_POINTER_OFFSET_BIT_COUNT = 29u; + static constexpr unsigned ZONE_POINTER_BLOCK_BIT_COUNT = 3u; static constexpr block_t INSERT_BLOCK = XFILE_BLOCK_VIRTUAL; static constexpr size_t FILE_SUFFIX_ZERO_MIN_SIZE = 0x40; diff --git a/src/ZoneLoading/Game/IW3/ZoneLoaderFactoryIW3.cpp b/src/ZoneLoading/Game/IW3/ZoneLoaderFactoryIW3.cpp index dd68de71..97d02ecd 100644 --- a/src/ZoneLoading/Game/IW3/ZoneLoaderFactoryIW3.cpp +++ b/src/ZoneLoading/Game/IW3/ZoneLoaderFactoryIW3.cpp @@ -208,7 +208,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/IW4/ZoneLoaderFactoryIW4.cpp b/src/ZoneLoading/Game/IW4/ZoneLoaderFactoryIW4.cpp index 4033eb5e..c5731ed1 100644 --- a/src/ZoneLoading/Game/IW4/ZoneLoaderFactoryIW4.cpp +++ b/src/ZoneLoading/Game/IW4/ZoneLoaderFactoryIW4.cpp @@ -376,7 +376,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, variant->GetWordSize() == GameWordSize::ARCH_64 ? 64u : 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/IW5/ZoneLoaderFactoryIW5.cpp b/src/ZoneLoading/Game/IW5/ZoneLoaderFactoryIW5.cpp index cb090a49..d265b45a 100644 --- a/src/ZoneLoading/Game/IW5/ZoneLoaderFactoryIW5.cpp +++ b/src/ZoneLoading/Game/IW5/ZoneLoaderFactoryIW5.cpp @@ -277,7 +277,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, variant->GetWordSize() == GameWordSize::ARCH_64 ? 64u : 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/QOS/ZoneLoaderFactoryQOS.cpp b/src/ZoneLoading/Game/QOS/ZoneLoaderFactoryQOS.cpp index f376fefb..1acfe7d3 100644 --- a/src/ZoneLoading/Game/QOS/ZoneLoaderFactoryQOS.cpp +++ b/src/ZoneLoading/Game/QOS/ZoneLoaderFactoryQOS.cpp @@ -82,7 +82,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/T4/ZoneLoaderFactoryT4.cpp b/src/ZoneLoading/Game/T4/ZoneLoaderFactoryT4.cpp index 877209c4..4666639d 100644 --- a/src/ZoneLoading/Game/T4/ZoneLoaderFactoryT4.cpp +++ b/src/ZoneLoading/Game/T4/ZoneLoaderFactoryT4.cpp @@ -85,7 +85,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/T5/ZoneLoaderFactoryT5.cpp b/src/ZoneLoading/Game/T5/ZoneLoaderFactoryT5.cpp index 40456815..53a560e2 100644 --- a/src/ZoneLoading/Game/T5/ZoneLoaderFactoryT5.cpp +++ b/src/ZoneLoading/Game/T5/ZoneLoaderFactoryT5.cpp @@ -91,7 +91,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Game/T6/ZoneLoaderFactoryT6.cpp b/src/ZoneLoading/Game/T6/ZoneLoaderFactoryT6.cpp index fb5933c6..480be412 100644 --- a/src/ZoneLoading/Game/T6/ZoneLoaderFactoryT6.cpp +++ b/src/ZoneLoading/Game/T6/ZoneLoaderFactoryT6.cpp @@ -348,7 +348,8 @@ std::unique_ptr ZoneLoaderFactory::CreateLoaderForHeader(ZoneDataPee return std::make_unique(*zonePtr, stream); }, 32u, - ZoneConstants::OFFSET_BLOCK_BIT_COUNT, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK, zonePtr, std::move(progressCallback))); diff --git a/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.cpp b/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.cpp index c82a35af..8ec3fcd7 100644 --- a/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.cpp +++ b/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.cpp @@ -9,13 +9,15 @@ namespace public: StepLoadZoneContent(std::function(ZoneInputStream&)> entryPointFactory, const unsigned pointerBitCount, - const unsigned offsetBlockBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, const block_t insertBlock, Zone* zone, std::optional> progressCallback) : m_entry_point_factory(std::move(entryPointFactory)), m_pointer_bit_count(pointerBitCount), - m_offset_block_bit_count(offsetBlockBitCount), + m_zone_pointer_offset_bit_count(zonePointerOffsetBitCount), + m_zone_pointer_block_bit_count(zonePointerBlockBitCount), m_insert_block(insertBlock), m_zone(zone), m_progress_callback(std::move(progressCallback)) @@ -31,8 +33,14 @@ namespace for (size_t i = 0; i < blockCount; ++i) m_blocks.emplace_back(zoneMemory.GetBlock(i)); - const auto inputStream = ZoneInputStream::Create( - m_pointer_bit_count, m_offset_block_bit_count, m_blocks, m_insert_block, stream, m_zone->Memory(), std::move(m_progress_callback)); + const auto inputStream = ZoneInputStream::Create(m_pointer_bit_count, + m_zone_pointer_offset_bit_count, + m_zone_pointer_block_bit_count, + m_blocks, + m_insert_block, + stream, + m_zone->Memory(), + std::move(m_progress_callback)); const auto entryPoint = m_entry_point_factory(*inputStream); assert(entryPoint); @@ -43,7 +51,8 @@ namespace private: std::function(ZoneInputStream&)> m_entry_point_factory; unsigned m_pointer_bit_count; - unsigned m_offset_block_bit_count; + unsigned m_zone_pointer_offset_bit_count; + unsigned m_zone_pointer_block_bit_count; block_t m_insert_block; Zone* m_zone; std::vector m_blocks; @@ -55,12 +64,13 @@ namespace step { std::unique_ptr CreateStepLoadZoneContent(std::function(ZoneInputStream&)> entryPointFactory, const unsigned pointerBitCount, - const unsigned offsetBlockBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, const block_t insertBlock, Zone* zone, std::optional> progressCallback) { return std::make_unique( - std::move(entryPointFactory), pointerBitCount, offsetBlockBitCount, insertBlock, zone, std::move(progressCallback)); + std::move(entryPointFactory), pointerBitCount, zonePointerOffsetBitCount, zonePointerBlockBitCount, insertBlock, zone, std::move(progressCallback)); } } // namespace step diff --git a/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.h b/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.h index 52bc6ee9..c7bded9d 100644 --- a/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.h +++ b/src/ZoneLoading/Loading/Steps/StepLoadZoneContent.h @@ -11,7 +11,8 @@ namespace step { std::unique_ptr CreateStepLoadZoneContent(std::function(ZoneInputStream&)> entryPointFactory, unsigned pointerBitCount, - unsigned offsetBlockBitCount, + unsigned zonePointerOffsetBitCount, + unsigned zonePointerBlockBitCount, block_t insertBlock, Zone* zone, std::optional> progressCallback); diff --git a/src/ZoneLoading/Zone/Stream/ZoneInputStream.cpp b/src/ZoneLoading/Zone/Stream/ZoneInputStream.cpp index 58b44655..678792ea 100644 --- a/src/ZoneLoading/Zone/Stream/ZoneInputStream.cpp +++ b/src/ZoneLoading/Zone/Stream/ZoneInputStream.cpp @@ -46,7 +46,8 @@ namespace { public: XBlockInputStream(const unsigned pointerBitCount, - const unsigned blockBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, std::vector& blocks, const block_t insertBlock, ILoadingStream& stream, @@ -57,15 +58,17 @@ namespace m_stream(stream), m_memory(memory), m_pointer_byte_count(pointerBitCount / 8u), - m_block_mask((std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - blockBitCount)) << (pointerBitCount - blockBitCount)), - m_block_shift(pointerBitCount - blockBitCount), - m_offset_mask(std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - (pointerBitCount - blockBitCount))), + m_zone_pointer_block_mask((std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - zonePointerBlockBitCount)) + << zonePointerOffsetBitCount), + m_zone_pointer_block_shift(zonePointerOffsetBitCount), + m_zone_pointer_offset_mask(std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - zonePointerOffsetBitCount)), m_last_fill_size(0), m_has_progress_callback(false), m_progress_current_size(0uz), m_progress_total_size(0uz) { assert(pointerBitCount % 8u == 0u); + assert(zonePointerOffsetBitCount + zonePointerBlockBitCount <= pointerBitCount); assert(insertBlock < static_cast(blocks.size())); std::memset(m_block_offsets.data(), 0, sizeof(decltype(m_block_offsets)::value_type) * m_block_offsets.size()); @@ -292,7 +295,7 @@ namespace const auto blockNum = m_insert_block->m_index; const auto blockOffset = static_cast(m_block_offsets[m_insert_block->m_index]); - const auto zonePtr = (static_cast(blockNum) << m_block_shift) | (blockOffset & m_offset_mask); + const auto zonePtr = (static_cast(blockNum) << m_zone_pointer_block_shift) | (blockOffset & m_zone_pointer_offset_mask); IncBlockPos(*m_insert_block, m_pointer_byte_count); @@ -301,7 +304,7 @@ namespace void SetInsertedPointerAliasLookup(const uintptr_t zonePtr, void* value) override { - assert((static_cast((zonePtr & m_block_mask) >> m_block_shift)) < m_blocks.size()); + assert((static_cast((zonePtr & m_zone_pointer_block_mask) >> m_zone_pointer_block_shift)) < m_blocks.size()); m_alias_redirect_lookup.emplace(zonePtr, value); } @@ -311,8 +314,8 @@ namespace // So all offsets are moved by 1. const auto offsetInt = reinterpret_cast(offset) - 1u; - const auto blockNum = static_cast((offsetInt & m_block_mask) >> m_block_shift); - const auto blockOffset = static_cast(offsetInt & m_offset_mask); + const auto blockNum = static_cast((offsetInt & m_zone_pointer_block_mask) >> m_zone_pointer_block_shift); + const auto blockOffset = static_cast(offsetInt & m_zone_pointer_offset_mask); if (blockNum < 0 || blockNum >= static_cast(m_blocks.size())) throw InvalidOffsetBlockException(blockNum); @@ -330,8 +333,8 @@ namespace // For details see ConvertOffsetToPointer const auto offsetInt = reinterpret_cast(offset) - 1u; - const auto blockNum = static_cast((offsetInt & m_block_mask) >> m_block_shift); - const auto blockOffset = static_cast(offsetInt & m_offset_mask); + const auto blockNum = static_cast((offsetInt & m_zone_pointer_block_mask) >> m_zone_pointer_block_shift); + const auto blockOffset = static_cast(offsetInt & m_zone_pointer_offset_mask); if (blockNum < 0 || blockNum >= static_cast(m_blocks.size())) throw InvalidOffsetBlockException(blockNum); @@ -356,7 +359,7 @@ namespace const auto blockNum = block->m_index; const auto blockOffset = static_cast(static_cast(blockPtr) - block->m_buffer.get()); - const auto zonePtr = (static_cast(blockNum) << m_block_shift) | (blockOffset & m_offset_mask); + const auto zonePtr = (static_cast(blockNum) << m_zone_pointer_block_shift) | (blockOffset & m_zone_pointer_offset_mask); m_pointer_redirect_lookup.emplace(zonePtr, alias); } @@ -365,8 +368,8 @@ namespace // For details see ConvertOffsetToPointer const auto offsetInt = reinterpret_cast(offset) - 1u; - const auto blockNum = static_cast((offsetInt & m_block_mask) >> m_block_shift); - const auto blockOffset = static_cast(offsetInt & m_offset_mask); + const auto blockNum = static_cast((offsetInt & m_zone_pointer_block_mask) >> m_zone_pointer_block_shift); + const auto blockOffset = static_cast(offsetInt & m_zone_pointer_offset_mask); if (blockNum < 0 || blockNum >= static_cast(m_blocks.size())) throw InvalidOffsetBlockException(blockNum); @@ -388,8 +391,8 @@ namespace // For details see ConvertOffsetToPointer const auto offsetInt = reinterpret_cast(offset) - 1u; - const auto blockNum = static_cast((offsetInt & m_block_mask) >> m_block_shift); - const auto blockOffset = static_cast(offsetInt & m_offset_mask); + const auto blockNum = static_cast((offsetInt & m_zone_pointer_block_mask) >> m_zone_pointer_block_shift); + const auto blockOffset = static_cast(offsetInt & m_zone_pointer_offset_mask); if (blockNum < 0 || blockNum >= static_cast(m_blocks.size())) throw InvalidOffsetBlockException(blockNum); @@ -496,9 +499,9 @@ namespace MemoryManager& m_memory; unsigned m_pointer_byte_count; - uintptr_t m_block_mask; - unsigned m_block_shift; - uintptr_t m_offset_mask; + uintptr_t m_zone_pointer_block_mask; + unsigned m_zone_pointer_block_shift; + uintptr_t m_zone_pointer_offset_mask; XBlock* m_insert_block; std::vector m_fill_buffer; @@ -515,12 +518,14 @@ namespace } // namespace std::unique_ptr ZoneInputStream::Create(const unsigned pointerBitCount, - const unsigned blockBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, std::vector& blocks, const block_t insertBlock, ILoadingStream& stream, MemoryManager& memory, std::optional> progressCallback) { - return std::make_unique(pointerBitCount, blockBitCount, blocks, insertBlock, stream, memory, std::move(progressCallback)); + return std::make_unique( + pointerBitCount, zonePointerOffsetBitCount, zonePointerBlockBitCount, blocks, insertBlock, stream, memory, std::move(progressCallback)); } diff --git a/src/ZoneLoading/Zone/Stream/ZoneInputStream.h b/src/ZoneLoading/Zone/Stream/ZoneInputStream.h index 2007d7fd..fdc76125 100644 --- a/src/ZoneLoading/Zone/Stream/ZoneInputStream.h +++ b/src/ZoneLoading/Zone/Stream/ZoneInputStream.h @@ -240,8 +240,21 @@ public: virtual void DebugOffsets(size_t assetIndex) const = 0; #endif + /** + * \brief Creates a new ZoneInputStream with given parameters. + * \param pointerBitCount The bit count of a pointer of the platform the zone data comes from. + * \param zonePointerBlockBitCount The bit count of the offset in a zone pointer. offsetBitCount + blockBitCount <= pointerBitCount + * \param zonePointerOffsetBitCount The bitcount of a block index in a zone pointer. offsetBitCount + blockBitCount <= pointerBitCount + * \param blocks The blocks of the zone. + * \param insertBlock The block index that is used when inserting a pointer. Should be the default normal block. + * \param stream The stream to load data from. + * \param memory The memory manager to use for allocating new memory. + * \param progressCallback An optional callback to call on progress. + * \return + */ static std::unique_ptr Create(unsigned pointerBitCount, - unsigned blockBitCount, + unsigned zonePointerOffsetBitCount, + unsigned zonePointerBlockBitCount, std::vector& blocks, block_t insertBlock, ILoadingStream& stream, diff --git a/src/ZoneWriting/Game/IW3/ZoneWriterFactoryIW3.cpp b/src/ZoneWriting/Game/IW3/ZoneWriterFactoryIW3.cpp index 8554bfd7..63f748b8 100644 --- a/src/ZoneWriting/Game/IW3/ZoneWriterFactoryIW3.cpp +++ b/src/ZoneWriting/Game/IW3/ZoneWriterFactoryIW3.cpp @@ -52,8 +52,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/IW4/ZoneWriterFactoryIW4.cpp b/src/ZoneWriting/Game/IW4/ZoneWriterFactoryIW4.cpp index b65e6080..6b31ac50 100644 --- a/src/ZoneWriting/Game/IW4/ZoneWriterFactoryIW4.cpp +++ b/src/ZoneWriting/Game/IW4/ZoneWriterFactoryIW4.cpp @@ -67,8 +67,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/IW5/ZoneWriterFactoryIW5.cpp b/src/ZoneWriting/Game/IW5/ZoneWriterFactoryIW5.cpp index 2721a139..c002697c 100644 --- a/src/ZoneWriting/Game/IW5/ZoneWriterFactoryIW5.cpp +++ b/src/ZoneWriting/Game/IW5/ZoneWriterFactoryIW5.cpp @@ -68,8 +68,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/QOS/ZoneWriterFactoryQOS.cpp b/src/ZoneWriting/Game/QOS/ZoneWriterFactoryQOS.cpp index d5f817f3..54f4a7ed 100644 --- a/src/ZoneWriting/Game/QOS/ZoneWriterFactoryQOS.cpp +++ b/src/ZoneWriting/Game/QOS/ZoneWriterFactoryQOS.cpp @@ -54,8 +54,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/T4/ZoneWriterFactoryT4.cpp b/src/ZoneWriting/Game/T4/ZoneWriterFactoryT4.cpp index d065bcd1..c99ffad2 100644 --- a/src/ZoneWriting/Game/T4/ZoneWriterFactoryT4.cpp +++ b/src/ZoneWriting/Game/T4/ZoneWriterFactoryT4.cpp @@ -50,8 +50,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/T5/ZoneWriterFactoryT5.cpp b/src/ZoneWriting/Game/T5/ZoneWriterFactoryT5.cpp index 786d5488..ed6bc581 100644 --- a/src/ZoneWriting/Game/T5/ZoneWriterFactoryT5.cpp +++ b/src/ZoneWriting/Game/T5/ZoneWriterFactoryT5.cpp @@ -50,8 +50,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Game/T6/ZoneWriterFactoryT6.cpp b/src/ZoneWriting/Game/T6/ZoneWriterFactoryT6.cpp index 60ed2c25..8ef45a68 100644 --- a/src/ZoneWriting/Game/T6/ZoneWriterFactoryT6.cpp +++ b/src/ZoneWriting/Game/T6/ZoneWriterFactoryT6.cpp @@ -106,8 +106,12 @@ std::unique_ptr ZoneWriterFactory::CreateWriter(const Zone& zone) co SetupBlocks(*writer); - auto contentInMemory = std::make_unique( - std::make_unique(zone), zone, 32u, ZoneConstants::OFFSET_BLOCK_BIT_COUNT, ZoneConstants::INSERT_BLOCK); + auto contentInMemory = std::make_unique(std::make_unique(zone), + zone, + 32u, + ZoneConstants::ZONE_POINTER_OFFSET_BIT_COUNT, + ZoneConstants::ZONE_POINTER_BLOCK_BIT_COUNT, + ZoneConstants::INSERT_BLOCK); auto* contentInMemoryPtr = contentInMemory.get(); writer->AddWritingStep(std::move(contentInMemory)); diff --git a/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.cpp b/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.cpp index 01cbc332..accb313e 100644 --- a/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.cpp +++ b/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.cpp @@ -5,13 +5,15 @@ StepWriteZoneContentToMemory::StepWriteZoneContentToMemory(std::unique_ptr entryPoint, const Zone& zone, const unsigned pointerBitCount, - const unsigned offsetBlockBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, const block_t insertBlock) : m_content_loader(std::move(entryPoint)), m_zone_data(std::make_unique()), m_zone(zone), m_pointer_bit_count(pointerBitCount), - m_offset_block_bit_count(offsetBlockBitCount), + m_zone_pointer_offset_bit_count(zonePointerOffsetBitCount), + m_zone_pointer_block_bit_count(zonePointerBlockBitCount), m_insert_block(insertBlock) { } @@ -22,7 +24,8 @@ void StepWriteZoneContentToMemory::PerformStep(ZoneWriter* zoneWriter, IWritingS for (const auto& block : zoneWriter->m_blocks) m_blocks.emplace_back(block.get()); - const auto zoneOutputStream = ZoneOutputStream::Create(m_pointer_bit_count, m_offset_block_bit_count, m_blocks, m_insert_block, *m_zone_data); + const auto zoneOutputStream = + ZoneOutputStream::Create(m_pointer_bit_count, m_zone_pointer_offset_bit_count, m_zone_pointer_block_bit_count, m_blocks, m_insert_block, *m_zone_data); m_content_loader->WriteContent(*zoneOutputStream); } diff --git a/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.h b/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.h index 89f38ba7..5bacc6e5 100644 --- a/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.h +++ b/src/ZoneWriting/Writing/Steps/StepWriteZoneContentToMemory.h @@ -9,8 +9,12 @@ class StepWriteZoneContentToMemory final : public IWritingStep { public: - StepWriteZoneContentToMemory( - std::unique_ptr entryPoint, const Zone& zone, unsigned pointerBitCount, unsigned offsetBlockBitCount, block_t insertBlock); + StepWriteZoneContentToMemory(std::unique_ptr entryPoint, + const Zone& zone, + unsigned pointerBitCount, + unsigned zonePointerOffsetBitCount, + unsigned zonePointerBlockBitCount, + block_t insertBlock); void PerformStep(ZoneWriter* zoneWriter, IWritingStream* stream) override; [[nodiscard]] InMemoryZoneData* GetData() const; @@ -22,6 +26,7 @@ private: std::vector m_blocks; unsigned m_pointer_bit_count; - unsigned m_offset_block_bit_count; + unsigned m_zone_pointer_offset_bit_count; + unsigned m_zone_pointer_block_bit_count; block_t m_insert_block; }; diff --git a/src/ZoneWriting/Zone/Stream/ZoneOutputStream.cpp b/src/ZoneWriting/Zone/Stream/ZoneOutputStream.cpp index 2075773a..0080c045 100644 --- a/src/ZoneWriting/Zone/Stream/ZoneOutputStream.cpp +++ b/src/ZoneWriting/Zone/Stream/ZoneOutputStream.cpp @@ -38,12 +38,19 @@ namespace class InMemoryZoneOutputStream final : public ZoneOutputStream { public: - InMemoryZoneOutputStream( - const unsigned pointerBitCount, const unsigned blockBitCount, std::vector& blocks, const block_t insertBlock, InMemoryZoneData& zoneData) + InMemoryZoneOutputStream(const unsigned pointerBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, + std::vector& blocks, + const block_t insertBlock, + InMemoryZoneData& zoneData) : m_zone_data(zoneData), m_blocks(blocks), - m_block_bit_count(blockBitCount), m_pointer_byte_count(pointerBitCount / 8u), + m_zone_pointer_block_mask((std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - zonePointerBlockBitCount)) + << zonePointerOffsetBitCount), + m_zone_pointer_block_shift(zonePointerOffsetBitCount), + m_zone_pointer_offset_mask(std::numeric_limits::max() >> (sizeof(uintptr_t) * 8 - zonePointerOffsetBitCount)), // -1 m_zone_ptr_following(std::numeric_limits::max() >> ((sizeof(std::uintptr_t) * 8u) - pointerBitCount)), @@ -52,6 +59,7 @@ namespace m_zone_ptr_insert((std::numeric_limits::max() >> ((sizeof(std::uintptr_t) * 8u) - pointerBitCount)) - 1u) { assert(pointerBitCount % 8u == 0u); + assert(zonePointerOffsetBitCount + zonePointerBlockBitCount <= pointerBitCount); assert(insertBlock < static_cast(blocks.size())); m_insert_block = blocks[insertBlock]; @@ -288,8 +296,8 @@ namespace assert(m_block_stack.top()->m_type == XBlockType::BLOCK_TYPE_NORMAL); uintptr_t ptr = 0; - ptr |= static_cast(m_block_stack.top()->m_index) << (m_pointer_byte_count * 8 - m_block_bit_count); - ptr |= m_block_stack.top()->m_buffer_size & (UINTPTR_MAX >> (m_block_bit_count + (sizeof(uintptr_t) - m_pointer_byte_count) * 8)); + ptr |= (static_cast(m_block_stack.top()->m_index) << m_zone_pointer_block_shift) & m_zone_pointer_block_mask; + ptr |= m_block_stack.top()->m_buffer_size & m_zone_pointer_offset_mask; ptr++; return ptr; @@ -314,8 +322,10 @@ namespace std::stack m_block_stack; std::stack m_temp_sizes; - unsigned m_block_bit_count; unsigned m_pointer_byte_count; + uintptr_t m_zone_pointer_block_mask; + unsigned m_zone_pointer_block_shift; + uintptr_t m_zone_pointer_offset_mask; XBlock* m_insert_block; uintptr_t m_zone_ptr_following; @@ -350,10 +360,14 @@ void* ZoneOutputOffset::Offset() const return m_offset; } -std::unique_ptr - ZoneOutputStream::Create(unsigned pointerBitCount, unsigned blockBitCount, std::vector& blocks, block_t insertBlock, InMemoryZoneData& zoneData) +std::unique_ptr ZoneOutputStream::Create(const unsigned pointerBitCount, + const unsigned zonePointerOffsetBitCount, + const unsigned zonePointerBlockBitCount, + std::vector& blocks, + const block_t insertBlock, + InMemoryZoneData& zoneData) { - return std::make_unique(pointerBitCount, blockBitCount, blocks, insertBlock, zoneData); + return std::make_unique(pointerBitCount, zonePointerOffsetBitCount, zonePointerBlockBitCount, blocks, insertBlock, zoneData); } ZoneStreamFillWriteAccessor::ZoneStreamFillWriteAccessor(void* blockBuffer, const size_t bufferSize) diff --git a/src/ZoneWriting/Zone/Stream/ZoneOutputStream.h b/src/ZoneWriting/Zone/Stream/ZoneOutputStream.h index 34d9bcc7..7c1e816a 100644 --- a/src/ZoneWriting/Zone/Stream/ZoneOutputStream.h +++ b/src/ZoneWriting/Zone/Stream/ZoneOutputStream.h @@ -143,6 +143,10 @@ public: return WriteDataInBlock(dst, size); } - static std::unique_ptr - Create(unsigned pointerBitCount, unsigned blockBitCount, std::vector& blocks, block_t insertBlock, InMemoryZoneData& zoneData); + static std::unique_ptr Create(unsigned pointerBitCount, + unsigned zonePointerOffsetBitCount, + unsigned zonePointerBlockBitCount, + std::vector& blocks, + block_t insertBlock, + InMemoryZoneData& zoneData); };