summaryrefslogtreecommitdiffstats
path: root/third_party/zlib
diff options
context:
space:
mode:
authorjoaoe@opera.com <joaoe@opera.com@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-07 20:53:02 +0000
committerjoaoe@opera.com <joaoe@opera.com@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-07 20:53:02 +0000
commit764f0715d75c8d49339aa73d0ee2feb75d63473f (patch)
tree64db37d95535eed176ca2a055b8307476cb2a993 /third_party/zlib
parent7d3d28ad1c1deb690ed1510eacc684375c10cc10 (diff)
downloadchromium_src-764f0715d75c8d49339aa73d0ee2feb75d63473f.zip
chromium_src-764f0715d75c8d49339aa73d0ee2feb75d63473f.tar.gz
chromium_src-764f0715d75c8d49339aa73d0ee2feb75d63473f.tar.bz2
Fixed uncompressing files with wrong uncompressed size set.
A zip file carries some metadata for each archived file, including the total uncompressed size. If that size was incorrect, therefore the compressed file being different in size when unpacking, the minizip code would fail with a CRC error. Every other zip utility handles these files, so should the minizip code for safety sake. BUG=359516 Review URL: https://codereview.chromium.org/222243003 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@268940 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'third_party/zlib')
-rw-r--r--third_party/zlib/contrib/minizip/unzip.c5
-rw-r--r--third_party/zlib/google/test/data/test_mismatch_size.zipbin0 -> 886 bytes
-rw-r--r--third_party/zlib/google/zip_reader.h2
-rw-r--r--third_party/zlib/google/zip_unittest.cc29
4 files changed, 31 insertions, 5 deletions
diff --git a/third_party/zlib/contrib/minizip/unzip.c b/third_party/zlib/contrib/minizip/unzip.c
index 22481a2..af59b80 100644
--- a/third_party/zlib/contrib/minizip/unzip.c
+++ b/third_party/zlib/contrib/minizip/unzip.c
@@ -1705,11 +1705,6 @@ extern int ZEXPORT unzReadCurrentFile (unzFile file, voidp buf, unsigned len)
pfile_in_zip_read_info->stream.avail_out = (uInt)len;
- if ((len>pfile_in_zip_read_info->rest_read_uncompressed) &&
- (!(pfile_in_zip_read_info->raw)))
- pfile_in_zip_read_info->stream.avail_out =
- (uInt)pfile_in_zip_read_info->rest_read_uncompressed;
-
if ((len>pfile_in_zip_read_info->rest_read_compressed+
pfile_in_zip_read_info->stream.avail_in) &&
(pfile_in_zip_read_info->raw))
diff --git a/third_party/zlib/google/test/data/test_mismatch_size.zip b/third_party/zlib/google/test/data/test_mismatch_size.zip
new file mode 100644
index 0000000..b83c66f
--- /dev/null
+++ b/third_party/zlib/google/test/data/test_mismatch_size.zip
Binary files differ
diff --git a/third_party/zlib/google/zip_reader.h b/third_party/zlib/google/zip_reader.h
index e16a2fb..60b53ee 100644
--- a/third_party/zlib/google/zip_reader.h
+++ b/third_party/zlib/google/zip_reader.h
@@ -64,6 +64,8 @@ class ZipReader {
// Returns the size of the original file (i.e. after uncompressed).
// Returns 0 if the entry is a directory.
+ // Note: this value should not be trusted, because it is stored as metadata
+ // in the zip archive and can be different from the real uncompressed size.
int64 original_size() const { return original_size_; }
// Returns the last modified time. If the time stored in the zip file was
diff --git a/third_party/zlib/google/zip_unittest.cc b/third_party/zlib/google/zip_unittest.cc
index 22e350f..c606434 100644
--- a/third_party/zlib/google/zip_unittest.cc
+++ b/third_party/zlib/google/zip_unittest.cc
@@ -13,6 +13,7 @@
#include "base/files/scoped_temp_dir.h"
#include "base/path_service.h"
#include "base/strings/string_util.h"
+#include "base/strings/stringprintf.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/platform_test.h"
#include "third_party/zlib/google/zip.h"
@@ -302,4 +303,32 @@ TEST_F(ZipTest, ZipFiles) {
}
#endif // defined(OS_POSIX)
+TEST_F(ZipTest, UnzipFilesWithIncorrectSize) {
+ base::FilePath test_data_folder;
+ ASSERT_TRUE(GetTestDataDirectory(&test_data_folder));
+
+ // test_mismatch_size.zip contains files with names from 0.txt to 7.txt with
+ // sizes from 0 to 7 bytes respectively, but the metadata in the zip file says
+ // the uncompressed size is 3 bytes. The ZipReader and minizip code needs to
+ // be clever enough to get all the data out.
+ base::FilePath test_zip_file =
+ test_data_folder.AppendASCII("test_mismatch_size.zip");
+
+ base::ScopedTempDir scoped_temp_dir;
+ ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir());
+ const base::FilePath& temp_dir = scoped_temp_dir.path();
+
+ ASSERT_TRUE(zip::Unzip(test_zip_file, temp_dir));
+ EXPECT_TRUE(base::DirectoryExists(temp_dir.AppendASCII("d")));
+
+ for (int i = 0; i < 8; i++) {
+ SCOPED_TRACE(base::StringPrintf("Processing %d.txt", i));
+ base::FilePath file_path = temp_dir.AppendASCII(
+ base::StringPrintf("%d.txt", i));
+ int64 file_size = -1;
+ EXPECT_TRUE(base::GetFileSize(file_path, &file_size));
+ EXPECT_EQ(static_cast<int64>(i), file_size);
+ }
+}
+
} // namespace