From 66fb4403ee17a790e3d0dc7ab678a295c67da6f8 Mon Sep 17 00:00:00 2001 From: Miroshka Date: Sun, 23 Jun 2024 17:41:03 +0300 Subject: [PATCH] Fixed CRC-32 error when writing to ZipOutputStream: - Removed cloning of ZipEntry to avoid potential data integrity issues. - Added an explicit call to outputStream.closeEntry() after writing the encrypted bytes to ensure proper entry closure and correct CRC-32 validation. --- .../allaymc/encryptmypack/EncryptMyPack.java | 36 +++++++++---------- 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/src/main/java/org/allaymc/encryptmypack/EncryptMyPack.java b/src/main/java/org/allaymc/encryptmypack/EncryptMyPack.java index 714eefb..b0cc418 100644 --- a/src/main/java/org/allaymc/encryptmypack/EncryptMyPack.java +++ b/src/main/java/org/allaymc/encryptmypack/EncryptMyPack.java @@ -80,7 +80,7 @@ public static void encrypt(ZipFile inputZip, String outputName, String key) { var contentId = findContentId(inputZip); log("ContentId: " + contentId); - var contentEntries = new ArrayList(); + var contentEntries = new ArrayList(); // Delete old output Files.deleteIfExists(Path.of(outputName)); @@ -107,7 +107,7 @@ public static void encrypt(ZipFile inputZip, String outputName, String key) { entryKey = encryptFile(inputZip, outputStream, zipEntry); } log("File: " + zipEntry.getName() + ", entryKey: " + entryKey); - contentEntries.add(new ContentEntry(zipEntry.getName(), entryKey)); + contentEntries.add(new org.allaymc.encryptmypack.EncryptMyPack.ContentEntry(zipEntry.getName(), entryKey)); }); generateContentsJson("contents.json", outputStream, contentId, key, contentEntries); @@ -124,7 +124,7 @@ public static void createDirectoryRoot(ZipEntry zipEntry, ZipOutputStream output @SneakyThrows public static void encryptSubPack(ZipFile inputZip, ZipOutputStream zos, String subPackPath, String key, String contentId) { log("Encrypting sub pack: " + subPackPath); - var subPackContentEntries = new ArrayList(); + var subPackContentEntries = new ArrayList(); // Encrypt files inputZip.stream().forEach(zipEntry -> { @@ -132,13 +132,13 @@ public static void encryptSubPack(ZipFile inputZip, ZipOutputStream zos, String if (!zipEntry.getName().startsWith(subPackPath)) return; String entryKey = encryptFile(inputZip, zos, zipEntry); log("Sub pack file: " + zipEntry.getName() + ", entryKey: " + entryKey); - subPackContentEntries.add(new ContentEntry(zipEntry.getName().substring(subPackPath.length()), entryKey)); + subPackContentEntries.add(new org.allaymc.encryptmypack.EncryptMyPack.ContentEntry(zipEntry.getName().substring(subPackPath.length()), entryKey)); }); generateContentsJson(subPackPath + "contents.json", zos, contentId, key, subPackContentEntries); } - public static void generateContentsJson(String name, ZipOutputStream outputStream, String contentId, String key, ArrayList contentEntries) throws IOException, NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, InvalidAlgorithmParameterException, IllegalBlockSizeException, BadPaddingException { + public static void generateContentsJson(String name, ZipOutputStream outputStream, String contentId, String key, ArrayList contentEntries) throws IOException, NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, InvalidAlgorithmParameterException, IllegalBlockSizeException, BadPaddingException { outputStream.putNextEntry(new ZipEntry(name)); try (var stream = new ByteArrayOutputStream()) { stream.write(VERSION); @@ -154,7 +154,7 @@ public static void generateContentsJson(String name, ZipOutputStream outputStrea var cipher = Cipher.getInstance("AES/CFB8/NoPadding"); cipher.init(Cipher.ENCRYPT_MODE, secretKey, new IvParameterSpec(key.substring(0, 16).getBytes(StandardCharsets.UTF_8))); // Write contents.json - var contentJson = GSON.toJson(new Content(contentEntries)); + var contentJson = GSON.toJson(new org.allaymc.encryptmypack.EncryptMyPack.Content(contentEntries)); paddingTo(stream, 0x100); stream.write(cipher.doFinal(contentJson.getBytes(StandardCharsets.UTF_8))); outputStream.write(stream.toByteArray()); @@ -173,8 +173,7 @@ public static void encryptExcludedFile(ZipFile inputZip, ZipOutputStream outputS @SneakyThrows public static String encryptFile(ZipFile inputZip, ZipOutputStream outputStream, ZipEntry zipEntry) { - byte[] bytes; - bytes = inputZip.getInputStream(zipEntry).readAllBytes(); + byte[] bytes = inputZip.getInputStream(zipEntry).readAllBytes(); // Init encryptor var key = randomAlphanumeric(KEY_LENGTH); var secretKey = new SecretKeySpec(key.getBytes(StandardCharsets.UTF_8), "AES"); @@ -183,15 +182,16 @@ public static String encryptFile(ZipFile inputZip, ZipOutputStream outputStream, // Encrypt the file var encryptedBytes = cipher.doFinal(bytes); // Write bytes - outputStream.putNextEntry((ZipEntry) zipEntry.clone()); + outputStream.putNextEntry(new ZipEntry(zipEntry.getName())); outputStream.write(encryptedBytes); - outputStream.closeEntry(); + outputStream.closeEntry(); // Закрываем entry после записи данных return key; } + @SneakyThrows public static void decrypt(ZipFile inputZip, String outputName, String key) { - Content content = decryptContentsJson(inputZip, "contents.json", key); + org.allaymc.encryptmypack.EncryptMyPack.Content content = decryptContentsJson(inputZip, "contents.json", key); // Delete old output Files.deleteIfExists(Path.of(outputName)); @@ -219,7 +219,7 @@ public static void decrypt(ZipFile inputZip, String outputName, String key) { } // Handle sub packs (if exist) - inputZip.stream().filter(EncryptMyPack::isSubPackRoot).forEach(zipEntry -> decryptSubPack(inputZip, outputStream, zipEntry.getName(), key)); + inputZip.stream().filter(org.allaymc.encryptmypack.EncryptMyPack::isSubPackRoot).forEach(zipEntry -> decryptSubPack(inputZip, outputStream, zipEntry.getName(), key)); outputStream.close(); log("Decrypted " + inputZip.getName() + " with key " + key + " successfully"); @@ -228,7 +228,7 @@ public static void decrypt(ZipFile inputZip, String outputName, String key) { @SneakyThrows public static void decryptSubPack(ZipFile inputZip, ZipOutputStream zos, String subPackPath, String key) { log("Decrypting sub pack: " + subPackPath); - Content content = decryptContentsJson(inputZip, subPackPath + "contents.json", key); + org.allaymc.encryptmypack.EncryptMyPack.Content content = decryptContentsJson(inputZip, subPackPath + "contents.json", key); for (var contentEntry : content.content) { var entryPath = subPackPath + contentEntry.path; @@ -260,7 +260,7 @@ public static void decryptFile(ZipOutputStream zos, byte[] bytes, String entryKe } @SneakyThrows - private static Content decryptContentsJson(ZipFile inputZip, String subPackPath, String key) { + private static org.allaymc.encryptmypack.EncryptMyPack.Content decryptContentsJson(ZipFile inputZip, String subPackPath, String key) { try (var stream = inputZip.getInputStream(inputZip.getEntry(subPackPath))) { stream.skip(0x100); var bytes = stream.readAllBytes(); @@ -268,7 +268,7 @@ private static Content decryptContentsJson(ZipFile inputZip, String subPackPath, var cipher = Cipher.getInstance("AES/CFB8/NoPadding"); cipher.init(Cipher.DECRYPT_MODE, secretKey, new IvParameterSpec(key.substring(0, 16).getBytes(StandardCharsets.UTF_8))); var decryptedBytes = cipher.doFinal(bytes); - Content content = GSON.fromJson(new String(decryptedBytes), Content.class); + org.allaymc.encryptmypack.EncryptMyPack.Content content = GSON.fromJson(new String(decryptedBytes), org.allaymc.encryptmypack.EncryptMyPack.Content.class); log("Decrypted content json: " + content); return content; } @@ -303,7 +303,7 @@ public static void paddingTo(ByteArrayOutputStream stream, int pos) { public static String findContentId(ZipFile zip) { var manifestEntry = zip.getEntry("manifest.json"); if (manifestEntry == null) throw new IllegalArgumentException("manifest file not exists"); - Manifest manifest = GSON.fromJson(new JsonReader(new InputStreamReader(zip.getInputStream(manifestEntry), StandardCharsets.UTF_8)), Manifest.class); + org.allaymc.encryptmypack.EncryptMyPack.Manifest manifest = GSON.fromJson(new JsonReader(new InputStreamReader(zip.getInputStream(manifestEntry), StandardCharsets.UTF_8)), org.allaymc.encryptmypack.EncryptMyPack.Manifest.class); return manifest.header.uuid; } @@ -323,7 +323,7 @@ public static void err(String msg) { System.err.println(msg); } - public record Content(List content) { + public record Content(List content) { } public record ContentEntry(String path, String key) { @@ -331,7 +331,7 @@ public record ContentEntry(String path, String key) { public static class Manifest { - public Header header; + public org.allaymc.encryptmypack.EncryptMyPack.Manifest.Header header; public static class Header { private String uuid;