provide archive name if anything goes wrong extracting stuff from 7z archives
git-svn-id: https://svn.apache.org/repos/asf/commons/proper/compress/trunk@1653264 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/AES256SHA256Decoder.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/AES256SHA256Decoder.java
index 91fb486..66d9d96 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/AES256SHA256Decoder.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/AES256SHA256Decoder.java
@@ -30,7 +30,7 @@
class AES256SHA256Decoder extends CoderBase {
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, final byte[] passwordBytes) throws IOException {
return new InputStream() {
private boolean isInitialized = false;
@@ -46,7 +46,7 @@
final int ivSize = ((byte0 >> 6) & 1) + (byte1 & 0x0f);
final int saltSize = ((byte0 >> 7) & 1) + (byte1 >> 4);
if (2 + saltSize + ivSize > coder.properties.length) {
- throw new IOException("Salt size + IV size too long");
+ throw new IOException("Salt size + IV size too long in " + archiveName);
}
final byte[] salt = new byte[saltSize];
System.arraycopy(coder.properties, 2, salt, 0, saltSize);
@@ -54,7 +54,7 @@
System.arraycopy(coder.properties, 2 + saltSize, iv, 0, ivSize);
if (passwordBytes == null) {
- throw new PasswordRequiredException();
+ throw new PasswordRequiredException(archiveName);
}
final byte[] aesKeyBytes;
if (numCyclesPower == 0x3f) {
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/CoderBase.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/CoderBase.java
index a871e52..286cc03 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/CoderBase.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/CoderBase.java
@@ -64,7 +64,8 @@
/**
* @return a stream that reads from in using the configured coder and password.
*/
- abstract InputStream decode(final InputStream in, long uncomressedLength,
+ abstract InputStream decode(final String archiveName,
+ final InputStream in, long uncomressedLength,
final Coder coder, byte[] password) throws IOException;
/**
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/Coders.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/Coders.java
index c488dea..fad904c 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/Coders.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/Coders.java
@@ -67,14 +67,15 @@
return CODER_MAP.get(method);
}
- static InputStream addDecoder(final InputStream is, long uncompressedLength,
+ static InputStream addDecoder(final String archiveName, final InputStream is, long uncompressedLength,
final Coder coder, final byte[] password) throws IOException {
CoderBase cb = findByMethod(SevenZMethod.byId(coder.decompressionMethodId));
if (cb == null) {
throw new IOException("Unsupported compression method " +
- Arrays.toString(coder.decompressionMethodId));
+ Arrays.toString(coder.decompressionMethodId)
+ + " used in " + archiveName);
}
- return cb.decode(is, uncompressedLength, coder, password);
+ return cb.decode(archiveName, is, uncompressedLength, coder, password);
}
static OutputStream addEncoder(final OutputStream out, final SevenZMethod method,
@@ -88,7 +89,7 @@
static class CopyDecoder extends CoderBase {
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, byte[] password) throws IOException {
return in;
}
@@ -100,7 +101,7 @@
static class LZMADecoder extends CoderBase {
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, byte[] password) throws IOException {
byte propsByte = coder.properties[0];
long dictSize = coder.properties[1];
@@ -108,7 +109,7 @@
dictSize |= (coder.properties[i + 1] & 0xffl) << (8 * i);
}
if (dictSize > LZMAInputStream.DICT_SIZE_MAX) {
- throw new IOException("Dictionary larger than 4GiB maximum size");
+ throw new IOException("Dictionary larger than 4GiB maximum size used in " + archiveName);
}
return new LZMAInputStream(in, uncompressedLength, propsByte, (int) dictSize);
}
@@ -121,12 +122,13 @@
}
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, byte[] password) throws IOException {
try {
return opts.getInputStream(in);
} catch (AssertionError e) {
- IOException ex = new IOException("BCJ filter needs XZ for Java > 1.4 - see "
+ IOException ex = new IOException("BCJ filter used in " + archiveName
+ + " needs XZ for Java > 1.4 - see "
+ "http://commons.apache.org/proper/commons-compress/limitations.html#7Z");
ex.initCause(e);
throw ex;
@@ -149,7 +151,7 @@
}
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, final byte[] password)
throws IOException {
return new InflaterInputStream(new DummyByteAddingInputStream(in),
@@ -168,7 +170,7 @@
}
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, final byte[] password)
throws IOException {
return new BZip2CompressorInputStream(in);
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/DeltaDecoder.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/DeltaDecoder.java
index 7951e71..e458334 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/DeltaDecoder.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/DeltaDecoder.java
@@ -30,7 +30,7 @@
}
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, byte[] password) throws IOException {
return new DeltaOptions(getOptionsFromCoder(coder)).getInputStream(in);
}
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/LZMA2Decoder.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/LZMA2Decoder.java
index 7df09f8..d3ffe31 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/LZMA2Decoder.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/LZMA2Decoder.java
@@ -32,7 +32,7 @@
}
@Override
- InputStream decode(final InputStream in, long uncompressedLength,
+ InputStream decode(final String archiveName, final InputStream in, long uncompressedLength,
final Coder coder, byte[] password) throws IOException {
try {
int dictionarySize = getDictionarySize(coder);
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/PasswordRequiredException.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/PasswordRequiredException.java
index 8814d3d..8352443 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/PasswordRequiredException.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/PasswordRequiredException.java
@@ -26,7 +26,7 @@
*/
public class PasswordRequiredException extends IOException {
- public PasswordRequiredException() {
- super("Cannot read encrypted files without a password");
+ public PasswordRequiredException(String archiveName) {
+ super("Cannot read encrypted archive " + archiveName + " without a password.");
}
}
diff --git a/src/main/java/org/apache/commons/compress/archivers/sevenz/SevenZFile.java b/src/main/java/org/apache/commons/compress/archivers/sevenz/SevenZFile.java
index a8c368c..398783f 100644
--- a/src/main/java/org/apache/commons/compress/archivers/sevenz/SevenZFile.java
+++ b/src/main/java/org/apache/commons/compress/archivers/sevenz/SevenZFile.java
@@ -67,6 +67,7 @@
public class SevenZFile implements Closeable {
static final int SIGNATURE_HEADER_SIZE = 32;
+ private final String fileName;
private RandomAccessFile file;
private final Archive archive;
private int currentEntryIndex = -1;
@@ -91,6 +92,7 @@
public SevenZFile(final File filename, final byte[] password) throws IOException {
boolean succeeded = false;
this.file = new RandomAccessFile(filename, "r");
+ this.fileName = filename.getAbsolutePath();
try {
archive = readHeaders(password);
if (password != null) {
@@ -276,8 +278,8 @@
if (coder.numInStreams != 1 || coder.numOutStreams != 1) {
throw new IOException("Multi input/output stream coders are not yet supported");
}
- inputStreamStack = Coders.addDecoder(inputStreamStack, folder.getUnpackSizeForCoder(coder),
- coder, password);
+ inputStreamStack = Coders.addDecoder(fileName, inputStreamStack,
+ folder.getUnpackSizeForCoder(coder), coder, password);
}
if (folder.hasCrc) {
inputStreamStack = new CRC32VerifyingInputStream(inputStreamStack,
@@ -859,8 +861,8 @@
throw new IOException("Multi input/output stream coders are not yet supported");
}
SevenZMethod method = SevenZMethod.byId(coder.decompressionMethodId);
- inputStreamStack = Coders.addDecoder(inputStreamStack, folder.getUnpackSizeForCoder(coder),
- coder, password);
+ inputStreamStack = Coders.addDecoder(fileName, inputStreamStack,
+ folder.getUnpackSizeForCoder(coder), coder, password);
methods.addFirst(new SevenZMethodConfiguration(method,
Coders.findByMethod(method).getOptionsFromCoder(coder, inputStreamStack)));
}
diff --git a/src/test/java/org/apache/commons/compress/archivers/sevenz/SevenZFileTest.java b/src/test/java/org/apache/commons/compress/archivers/sevenz/SevenZFileTest.java
index bc84d44..dd50de8 100644
--- a/src/test/java/org/apache/commons/compress/archivers/sevenz/SevenZFileTest.java
+++ b/src/test/java/org/apache/commons/compress/archivers/sevenz/SevenZFileTest.java
@@ -60,15 +60,6 @@
}
}
- public void test7zDecryptUnarchiveWithoutPassword() throws Exception {
- try {
- test7zUnarchive(getFile("bla.encrypted.7z"), SevenZMethod.LZMA);
- fail("Expected a PasswordRequiredException");
- } catch (PasswordRequiredException ex) {
- // expected
- }
- }
-
private void test7zUnarchive(File f, SevenZMethod m) throws Exception {
test7zUnarchive(f, m, null);
}
@@ -77,9 +68,14 @@
try {
new SevenZFile(getFile("bla.encrypted.7z"));
fail("shouldn't decrypt without a password");
- } catch (IOException ex) {
- assertEquals("Cannot read encrypted files without a password",
- ex.getMessage());
+ } catch (PasswordRequiredException ex) {
+ String msg = ex.getMessage();
+ assertTrue("Should start with whining about being unable to decrypt",
+ msg.startsWith("Cannot read encrypted archive "));
+ assertTrue("Should finish the sentence properly",
+ msg.endsWith(" without a password."));
+ assertTrue("Should contain archive's name",
+ msg.contains("bla.encrypted.7z"));
}
}