summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Userland/Utilities/CMakeLists.txt2
-rw-r--r--Userland/Utilities/unzip.cpp11
2 files changed, 11 insertions, 2 deletions
diff --git a/Userland/Utilities/CMakeLists.txt b/Userland/Utilities/CMakeLists.txt
index 601885305b..c4582aea8d 100644
--- a/Userland/Utilities/CMakeLists.txt
+++ b/Userland/Utilities/CMakeLists.txt
@@ -121,7 +121,7 @@ target_link_libraries(test-fuzz PRIVATE LibGemini LibGfx LibHTTP LibIPC LibJS Li
target_link_libraries(test-imap PRIVATE LibIMAP)
target_link_libraries(test-pthread PRIVATE LibThreading)
target_link_libraries(unveil PRIVATE LibMain)
-target_link_libraries(unzip PRIVATE LibArchive LibCompress)
+target_link_libraries(unzip PRIVATE LibArchive LibCompress LibCrypto)
target_link_libraries(update-cpp-test-results PRIVATE LibCpp)
target_link_libraries(useradd PRIVATE LibCrypt)
target_link_libraries(wallpaper PRIVATE LibGfx LibGUI)
diff --git a/Userland/Utilities/unzip.cpp b/Userland/Utilities/unzip.cpp
index ebf1171131..39c7b1e07c 100644
--- a/Userland/Utilities/unzip.cpp
+++ b/Userland/Utilities/unzip.cpp
@@ -14,6 +14,7 @@
#include <LibCore/File.h>
#include <LibCore/MappedFile.h>
#include <LibCore/System.h>
+#include <LibCrypto/Checksum/CRC32.h>
#include <sys/stat.h>
static bool unpack_zip_member(Archive::ZipMember zip_member, bool quiet)
@@ -37,13 +38,14 @@ static bool unpack_zip_member(Archive::ZipMember zip_member, bool quiet)
if (!quiet)
outln(" extracting: {}", zip_member.name);
- // TODO: verify CRC32s match!
+ Crypto::Checksum::CRC32 checksum;
switch (zip_member.compression_method) {
case Archive::ZipCompressionMethod::Store: {
if (!new_file->write(zip_member.compressed_data.data(), zip_member.compressed_data.size())) {
warnln("Can't write file contents in {}: {}", zip_member.name, new_file->error_string());
return false;
}
+ checksum.update({ zip_member.compressed_data.data(), zip_member.compressed_data.size() });
break;
}
case Archive::ZipCompressionMethod::Deflate: {
@@ -60,6 +62,7 @@ static bool unpack_zip_member(Archive::ZipMember zip_member, bool quiet)
warnln("Can't write file contents in {}: {}", zip_member.name, new_file->error_string());
return false;
}
+ checksum.update({ decompressed_data.value().data(), decompressed_data.value().size() });
break;
}
default:
@@ -71,6 +74,12 @@ static bool unpack_zip_member(Archive::ZipMember zip_member, bool quiet)
return false;
}
+ if (checksum.digest() != zip_member.crc32) {
+ warnln("Failed decompressing file {}: CRC32 mismatch", zip_member.name);
+ MUST(new_file->remove(zip_member.name, Core::File::RecursionMode::Disallowed, true));
+ return false;
+ }
+
return true;
}