aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/ZipPackage.java2
-rw-r--r--poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/internal/InvalidZipException.java14
-rw-r--r--poi-ooxml/src/main/java/org/apache/poi/openxml4j/util/ZipSecureFile.java18
-rw-r--r--poi-ooxml/src/test/java/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java13
-rw-r--r--test-data/spreadsheet/duplicate-file.xlsxbin0 -> 10721 bytes
5 files changed, 47 insertions, 0 deletions
diff --git a/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/ZipPackage.java b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/ZipPackage.java
index 46b3fd3b7f..7811627c33 100644
--- a/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/ZipPackage.java
+++ b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/ZipPackage.java
@@ -187,6 +187,8 @@ public final class ZipPackage extends OPCPackage {
try {
final ZipFile zipFile = ZipHelper.openZipFile(file); // NOSONAR
ze = new ZipFileZipEntrySource(zipFile);
+ } catch (InvalidZipException e) {
+ throw new InvalidOperationException("Can't open the specified file: '" + file + "'", e);
} catch (IOException e) {
// probably not happening with write access - not sure how to handle the default read-write access ...
if (access == PackageAccess.WRITE) {
diff --git a/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/internal/InvalidZipException.java b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/internal/InvalidZipException.java
new file mode 100644
index 0000000000..9a788b2134
--- /dev/null
+++ b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/opc/internal/InvalidZipException.java
@@ -0,0 +1,14 @@
+package org.apache.poi.openxml4j.opc.internal;
+
+import java.io.IOException;
+
+/**
+ * Thrown if the zip file is invalid.
+ *
+ * @since 5.3.1
+ */
+public class InvalidZipException extends IOException {
+ public InvalidZipException(String message) {
+ super(message);
+ }
+}
diff --git a/poi-ooxml/src/main/java/org/apache/poi/openxml4j/util/ZipSecureFile.java b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/util/ZipSecureFile.java
index 60dcb1d53c..ff183a696e 100644
--- a/poi-ooxml/src/main/java/org/apache/poi/openxml4j/util/ZipSecureFile.java
+++ b/poi-ooxml/src/main/java/org/apache/poi/openxml4j/util/ZipSecureFile.java
@@ -19,11 +19,15 @@ package org.apache.poi.openxml4j.util;
import java.io.File;
import java.io.IOException;
+import java.util.Enumeration;
+import java.util.HashSet;
+import java.util.Set;
import org.apache.commons.compress.archivers.zip.ZipArchiveEntry;
import org.apache.commons.compress.archivers.zip.ZipFile;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
+import org.apache.poi.openxml4j.opc.internal.InvalidZipException;
import org.apache.poi.util.Internal;
import org.apache.poi.util.Removal;
@@ -205,6 +209,7 @@ public class ZipSecureFile extends ZipFile {
public ZipSecureFile(File file) throws IOException {
super(file);
this.fileName = file.getAbsolutePath();
+ validateEntryNames();
}
/**
@@ -214,6 +219,7 @@ public class ZipSecureFile extends ZipFile {
public ZipSecureFile(String name) throws IOException {
super(name);
this.fileName = new File(name).getAbsolutePath();
+ validateEntryNames();
}
/**
@@ -246,4 +252,16 @@ public class ZipSecureFile extends ZipFile {
public String getName() {
return fileName;
}
+
+ private void validateEntryNames() throws IOException {
+ Enumeration<ZipArchiveEntry> en = getEntries();
+ Set<String> filenames = new HashSet<>();
+ while (en.hasMoreElements()) {
+ String name = en.nextElement().getName();
+ if (filenames.contains(name)) {
+ throw new InvalidZipException("Input file contains more than 1 entry with the name " + name);
+ }
+ filenames.add(name);
+ }
+ }
}
diff --git a/poi-ooxml/src/test/java/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java b/poi-ooxml/src/test/java/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java
index 744887ff40..bd36492535 100644
--- a/poi-ooxml/src/test/java/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java
+++ b/poi-ooxml/src/test/java/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java
@@ -27,6 +27,7 @@ import org.apache.poi.hssf.HSSFTestDataSamples;
import org.apache.poi.ooxml.POIXMLProperties;
import org.apache.poi.ooxml.TrackingInputStream;
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
+import org.apache.poi.openxml4j.exceptions.InvalidOperationException;
import org.apache.poi.openxml4j.opc.ContentTypes;
import org.apache.poi.openxml4j.opc.OPCPackage;
import org.apache.poi.openxml4j.opc.PackageAccess;
@@ -1448,6 +1449,18 @@ public final class TestXSSFWorkbook extends BaseTestXWorkbook {
}
@Test
+ void testDuplicateFileReadAsFile() {
+ assertThrows(InvalidOperationException.class, () -> {
+ try (
+ OPCPackage pkg = OPCPackage.open(getSampleFile("duplicate-file.xlsx"), PackageAccess.READ);
+ XSSFWorkbook wb = new XSSFWorkbook(pkg)
+ ) {
+ // expect exception here
+ }
+ });
+ }
+
+ @Test
void testWorkbookCloseClosesInputStream() throws Exception {
try (TrackingInputStream stream = new TrackingInputStream(
HSSFTestDataSamples.openSampleFileStream("github-321.xlsx"))) {
diff --git a/test-data/spreadsheet/duplicate-file.xlsx b/test-data/spreadsheet/duplicate-file.xlsx
new file mode 100644
index 0000000000..5853cf1ded
--- /dev/null
+++ b/test-data/spreadsheet/duplicate-file.xlsx
Binary files differ