Additional check when unpacking archives. Contributed by Wilfred Spiegelenburg.
This commit is contained in:
parent
d5708bbcdc
commit
65e55097da
|
@ -109,6 +109,7 @@ public class RunJar {
|
||||||
throws IOException {
|
throws IOException {
|
||||||
try (JarFile jar = new JarFile(jarFile)) {
|
try (JarFile jar = new JarFile(jarFile)) {
|
||||||
int numOfFailedLastModifiedSet = 0;
|
int numOfFailedLastModifiedSet = 0;
|
||||||
|
String targetDirPath = toDir.getCanonicalPath() + File.separator;
|
||||||
Enumeration<JarEntry> entries = jar.entries();
|
Enumeration<JarEntry> entries = jar.entries();
|
||||||
while (entries.hasMoreElements()) {
|
while (entries.hasMoreElements()) {
|
||||||
final JarEntry entry = entries.nextElement();
|
final JarEntry entry = entries.nextElement();
|
||||||
|
@ -117,6 +118,10 @@ public class RunJar {
|
||||||
try (InputStream in = jar.getInputStream(entry)) {
|
try (InputStream in = jar.getInputStream(entry)) {
|
||||||
File file = new File(toDir, entry.getName());
|
File file = new File(toDir, entry.getName());
|
||||||
ensureDirectory(file.getParentFile());
|
ensureDirectory(file.getParentFile());
|
||||||
|
if (!file.getCanonicalPath().startsWith(targetDirPath)) {
|
||||||
|
throw new IOException("expanding " + entry.getName()
|
||||||
|
+ " would create file outside of " + toDir);
|
||||||
|
}
|
||||||
try (OutputStream out = new FileOutputStream(file)) {
|
try (OutputStream out = new FileOutputStream(file)) {
|
||||||
IOUtils.copyBytes(in, out, BUFFER_SIZE);
|
IOUtils.copyBytes(in, out, BUFFER_SIZE);
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,12 +20,15 @@ package org.apache.hadoop.util;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
import static org.junit.Assert.assertTrue;
|
import static org.junit.Assert.assertTrue;
|
||||||
|
import static org.junit.Assert.fail;
|
||||||
import static org.mockito.Mockito.spy;
|
import static org.mockito.Mockito.spy;
|
||||||
import static org.mockito.Mockito.when;
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.util.jar.JarEntry;
|
||||||
import java.util.jar.JarOutputStream;
|
import java.util.jar.JarOutputStream;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
import java.util.zip.ZipEntry;
|
import java.util.zip.ZipEntry;
|
||||||
|
@ -165,4 +168,37 @@ public class TestRunJar {
|
||||||
runJar.run(args);
|
runJar.run(args);
|
||||||
// it should not throw an exception
|
// it should not throw an exception
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testUnJar2() throws IOException {
|
||||||
|
// make a simple zip
|
||||||
|
File jarFile = new File(TEST_ROOT_DIR, TEST_JAR_NAME);
|
||||||
|
JarOutputStream jstream =
|
||||||
|
new JarOutputStream(new FileOutputStream(jarFile));
|
||||||
|
JarEntry je = new JarEntry("META-INF/MANIFEST.MF");
|
||||||
|
byte[] data = "Manifest-Version: 1.0\nCreated-By: 1.8.0_1 (Manual)"
|
||||||
|
.getBytes(StandardCharsets.UTF_8);
|
||||||
|
je.setSize(data.length);
|
||||||
|
jstream.putNextEntry(je);
|
||||||
|
jstream.write(data);
|
||||||
|
jstream.closeEntry();
|
||||||
|
je = new JarEntry("../outside.path");
|
||||||
|
data = "any data here".getBytes(StandardCharsets.UTF_8);
|
||||||
|
je.setSize(data.length);
|
||||||
|
jstream.putNextEntry(je);
|
||||||
|
jstream.write(data);
|
||||||
|
jstream.closeEntry();
|
||||||
|
jstream.close();
|
||||||
|
|
||||||
|
File unjarDir = getUnjarDir("unjar-path");
|
||||||
|
|
||||||
|
// Unjar everything
|
||||||
|
try {
|
||||||
|
RunJar.unJar(jarFile, unjarDir);
|
||||||
|
fail("unJar should throw IOException.");
|
||||||
|
} catch (IOException e) {
|
||||||
|
GenericTestUtils.assertExceptionContains(
|
||||||
|
"would create file outside of", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
Loading…
Reference in New Issue