summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNarayan Kamath <narayan@google.com>2017-08-09 18:32:09 +0100
committerandroid-build-team Robot <android-build-team-robot@google.com>2017-11-08 22:41:06 +0000
commit4d885746554d875376e66cb622a73e3982adc76b (patch)
tree8abb946600f74db7ecf52becc50a9d3d48406631
parent26cfad5c8b0764583d5854a099275478d286fe65 (diff)
downloadcore-4d885746554d875376e66cb622a73e3982adc76b.tar.gz
zip_archive: reject files that don't start with an LFH signature.
Bug: 64211847 Test: zip_archive_test (cherry picked from commit c1a56dcab711a7ee238c0af865920ca51b1408a6) Merged-In: I275e7c4da05ceeb20401b560c72294f29ef63642 Change-Id: Ib89f0def696206ff427be27764c158fab88e4b5d (cherry picked from commit 9dced1626219d47c75a9d37156ed7baeef8f6403)
-rw-r--r--libziparchive/zip_archive.cc16
-rw-r--r--libziparchive/zip_archive_test.cc49
2 files changed, 65 insertions, 0 deletions
diff --git a/libziparchive/zip_archive.cc b/libziparchive/zip_archive.cc
index 78de40aed..d0bbd7220 100644
--- a/libziparchive/zip_archive.cc
+++ b/libziparchive/zip_archive.cc
@@ -441,6 +441,22 @@ static int32_t ParseZipArchive(ZipArchive* archive) {
return -1;
}
}
+
+ uint32_t lfh_start_bytes;
+ if (!archive->mapped_zip.ReadAtOffset(reinterpret_cast<uint8_t*>(&lfh_start_bytes),
+ sizeof(uint32_t), 0)) {
+ ALOGW("Zip: Unable to read header for entry at offset == 0.");
+ return -1;
+ }
+
+ if (lfh_start_bytes != LocalFileHeader::kSignature) {
+ ALOGW("Zip: Entry at offset zero has invalid LFH signature %" PRIx32, lfh_start_bytes);
+#if defined(__ANDROID__)
+ android_errorWriteLog(0x534e4554, "64211847");
+#endif
+ return -1;
+ }
+
ALOGV("+++ zip good scan %" PRIu16 " entries", num_entries);
return 0;
diff --git a/libziparchive/zip_archive_test.cc b/libziparchive/zip_archive_test.cc
index 493a0ce86..3035a5e82 100644
--- a/libziparchive/zip_archive_test.cc
+++ b/libziparchive/zip_archive_test.cc
@@ -642,6 +642,55 @@ TEST(ziparchive, StreamUncompressedBadCrc) {
CloseArchive(handle);
}
+// A zip file whose local file header at offset zero is corrupted.
+//
+// ---------------
+// cat foo > a.txt
+// zip a.zip a.txt
+// cat a.zip | xxd -i
+//
+// Manual changes :
+// [2] = 0xff // Corrupt the LFH signature of entry 0.
+// [3] = 0xff // Corrupt the LFH signature of entry 0.
+static const std::vector<uint8_t> kZipFileWithBrokenLfhSignature{
+ //[lfh-sig-----------], [lfh contents---------------------------------
+ 0x50, 0x4b, 0xff, 0xff, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x80,
+ //--------------------------------------------------------------------
+ 0x09, 0x4b, 0xa8, 0x65, 0x32, 0x7e, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00,
+ //-------------------------------] [file-name-----------------], [---
+ 0x00, 0x00, 0x05, 0x00, 0x1c, 0x00, 0x61, 0x2e, 0x74, 0x78, 0x74, 0x55,
+ // entry-contents------------------------------------------------------
+ 0x54, 0x09, 0x00, 0x03, 0x51, 0x24, 0x8b, 0x59, 0x51, 0x24, 0x8b, 0x59,
+ //--------------------------------------------------------------------
+ 0x75, 0x78, 0x0b, 0x00, 0x01, 0x04, 0x89, 0x42, 0x00, 0x00, 0x04, 0x88,
+ //-------------------------------------], [cd-record-sig-------], [---
+ 0x13, 0x00, 0x00, 0x66, 0x6f, 0x6f, 0x0a, 0x50, 0x4b, 0x01, 0x02, 0x1e,
+ // cd-record-----------------------------------------------------------
+ 0x03, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x77, 0x80, 0x09, 0x4b, 0xa8,
+ //--------------------------------------------------------------------
+ 0x65, 0x32, 0x7e, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x05,
+ //--------------------------------------------------------------------
+ 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xa0,
+ //-] [lfh-file-header-off-], [file-name-----------------], [extra----
+ 0x81, 0x00, 0x00, 0x00, 0x00, 0x61, 0x2e, 0x74, 0x78, 0x74, 0x55, 0x54,
+ //--------------------------------------------------------------------
+ 0x05, 0x00, 0x03, 0x51, 0x24, 0x8b, 0x59, 0x75, 0x78, 0x0b, 0x00, 0x01,
+ //-------------------------------------------------------], [eocd-sig-
+ 0x04, 0x89, 0x42, 0x00, 0x00, 0x04, 0x88, 0x13, 0x00, 0x00, 0x50, 0x4b,
+ //-------], [---------------------------------------------------------
+ 0x05, 0x06, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x4b, 0x00,
+ //-------------------------------------------]
+ 0x00, 0x00, 0x43, 0x00, 0x00, 0x00, 0x00, 0x00};
+
+TEST(ziparchive, BrokenLfhSignature) {
+ TemporaryFile tmp_file;
+ ASSERT_NE(-1, tmp_file.fd);
+ ASSERT_TRUE(android::base::WriteFully(tmp_file.fd, &kZipFileWithBrokenLfhSignature[0],
+ kZipFileWithBrokenLfhSignature.size()));
+ ZipArchiveHandle handle;
+ ASSERT_EQ(-1, OpenArchiveFd(tmp_file.fd, "LeadingNonZipBytes", &handle));
+}
+
int main(int argc, char** argv) {
::testing::InitGoogleTest(&argc, argv);