diff --git a/lib/init.luau b/lib/init.luau index 36af5e5..12ad5d1 100644 --- a/lib/init.luau +++ b/lib/init.luau @@ -531,10 +531,9 @@ function ZipReader.parseEocdRecord(self: ZipReader, pos: number): EocdRecord local cdSize = buffer.readu32(self.data, pos + 12) local cdOffset = buffer.readu32(self.data, pos + 16) - -- Validate CD boundaries and entry count; Ensure minimum size is at least 30 bytes and - -- total size after the local header is not larger than the buffer size + -- Validate CD boundaries and entry count local bufSize = buffer.len(self.data) - if cdOffset >= bufSize or cdOffset < 30 or cdOffset + cdSize > bufSize then + if cdOffset >= bufSize or cdOffset + cdSize > bufSize then error("Invalid Central Directory offset or size") end diff --git a/tests/edge_cases.luau b/tests/edge_cases.luau index a7f6a1a..3b4c43a 100644 --- a/tests/edge_cases.luau +++ b/tests/edge_cases.luau @@ -79,5 +79,12 @@ return function(test: typeof(frktest.test)) -- Check that the comment is the same as the one in the ZIP file (only compare hashes) check.equal(serde.hash("blake3", commentData), serde.hash("blake3", zip.comment)) end) + + test.case("Does not over alllocate based on declared entry count in EoCD", function() + local data = fs.readFile("tests/data/invalid_cde_number_of_files_allocation_smaller_offset.zip") + local zip = ZipReader.load(buffer.fromstring(data)) + + check.is_true(#zip.entries == 0) + end) end) end diff --git a/tests/extract.luau b/tests/extract.luau index 9abd748..7953c56 100644 --- a/tests/extract.luau +++ b/tests/extract.luau @@ -10,7 +10,7 @@ local ZipReader = require("../lib") local ZIPS = fs.readDir("tests/data") local FALLIBLES = { "invalid_cde_number_of_files_allocation_greater_offset.zip", - "invalid_cde_number_of_files_allocation_smaller_offset.zip", + -- "invalid_cde_number_of_files_allocation_smaller_offset.zip", -- Tested separately in edge cases "invalid_offset.zip", "invalid_offset2.zip", "chinese.zip", -- Contains non local specific encoding which can't be parsed without OS APIs