# HG changeset patch # User sundar # Date 1559217633 -19800 # Node ID 931a4d5367a66275cf07d1f88fae883656842e97 # Parent ebc4e5a625e28b5b28e1b543a11120082cf1edf4 8224946: jrtfs URI to Path and Path to URI conversions are wrong Reviewed-by: alanb diff -r ebc4e5a625e2 -r 931a4d5367a6 src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystemProvider.java --- a/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystemProvider.java Thu May 30 12:36:04 2019 +0100 +++ b/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystemProvider.java Thu May 30 17:30:33 2019 +0530 @@ -190,10 +190,11 @@ throw new IllegalArgumentException("Fragment component present"); } String path = uri.getPath(); - if (path == null || path.charAt(0) != '/') { + if (path == null || path.charAt(0) != '/' || path.contains("..")) { throw new IllegalArgumentException("Invalid path component"); } - return getTheFileSystem().getPath(path); + + return getTheFileSystem().getPath("/modules" + path); } private FileSystem getTheFileSystem() { diff -r ebc4e5a625e2 -r 931a4d5367a6 src/java.base/share/classes/jdk/internal/jrtfs/JrtPath.java --- a/src/java.base/share/classes/jdk/internal/jrtfs/JrtPath.java Thu May 30 12:36:04 2019 +0100 +++ b/src/java.base/share/classes/jdk/internal/jrtfs/JrtPath.java Thu May 30 17:30:33 2019 +0530 @@ -25,6 +25,7 @@ package jdk.internal.jrtfs; import java.io.File; +import java.io.IOError; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; @@ -170,7 +171,16 @@ @Override public final URI toUri() { try { - return new URI("jrt", toAbsolutePath().path, null); + String p = toAbsolutePath().path; + if (!p.startsWith("/modules") || p.contains("..")) { + throw new IOError(new RuntimeException(p + " cannot be represented as URI")); + } + + p = p.substring("/modules".length()); + if (p.isEmpty()) { + p = "/"; + } + return new URI("jrt", p, null); } catch (URISyntaxException ex) { throw new AssertionError(ex); } diff -r ebc4e5a625e2 -r 931a4d5367a6 test/jdk/jdk/internal/jrtfs/Basic.java --- a/test/jdk/jdk/internal/jrtfs/Basic.java Thu May 30 12:36:04 2019 +0100 +++ b/test/jdk/jdk/internal/jrtfs/Basic.java Thu May 30 17:30:33 2019 +0530 @@ -28,6 +28,7 @@ */ import java.io.InputStream; +import java.io.IOError; import java.io.IOException; import java.io.DataInputStream; import java.nio.file.DirectoryStream; @@ -271,17 +272,60 @@ Path top = fs.getPath("/"); try (Stream stream = Files.walk(top)) { stream.forEach(path -> { - URI u = path.toUri(); + String pathStr = path.toAbsolutePath().toString(); + URI u = null; + try { + u = path.toUri(); + } catch (IOError e) { + assertFalse(pathStr.startsWith("/modules")); + return; + } + assertTrue(u.getScheme().equalsIgnoreCase("jrt")); assertFalse(u.isOpaque()); assertTrue(u.getAuthority() == null); - assertEquals(u.getPath(), path.toAbsolutePath().toString()); + + pathStr = pathStr.substring("/modules".length()); + if (pathStr.isEmpty()) { + pathStr = "/"; + } + assertEquals(u.getPath(), pathStr); Path p = Paths.get(u); assertEquals(p, path); }); } } + // @bug 8216553: JrtFIleSystemProvider getPath(URI) omits /modules element from file path + @Test + public void testPathToURIConversion() throws Exception { + var uri = URI.create("jrt:/java.base/module-info.class"); + var path = Path.of(uri); + assertTrue(Files.exists(path)); + + uri = URI.create("jrt:/java.base/../java.base/module-info.class"); + boolean seenIAE = false; + try { + Path.of(uri); + } catch (IllegalArgumentException iaExp) { + seenIAE = true; + } + assertTrue(seenIAE); + + // check round-trip + var jrtfs = FileSystems.getFileSystem(URI.create("jrt:/")); + assertTrue(Files.exists(jrtfs.getPath(path.toString()))); + + path = jrtfs.getPath("/modules/../modules/java.base/"); + boolean seenIOError = false; + try { + path.toUri(); + } catch (IOError ioError) { + seenIOError = true; + } + assertTrue(seenIOError); + } + @Test public void testDirectoryNames() throws Exception { FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/")); diff -r ebc4e5a625e2 -r 931a4d5367a6 test/jdk/tools/jlink/plugins/ExcludeVMPluginTest.java --- a/test/jdk/tools/jlink/plugins/ExcludeVMPluginTest.java Thu May 30 12:36:04 2019 +0100 +++ b/test/jdk/tools/jlink/plugins/ExcludeVMPluginTest.java Thu May 30 17:30:33 2019 +0530 @@ -228,7 +228,7 @@ // read java.base/module-info.class from jrt-fs private static Path getJavaBaseModuleInfo() { - return Paths.get(URI.create("jrt:/modules/java.base/module-info.class")); + return Paths.get(URI.create("jrt:/java.base/module-info.class")); } private static boolean isWindows() { diff -r ebc4e5a625e2 -r 931a4d5367a6 test/jdk/tools/jlink/plugins/SystemModuleDescriptors/ModuleTargetHelper.java --- a/test/jdk/tools/jlink/plugins/SystemModuleDescriptors/ModuleTargetHelper.java Thu May 30 12:36:04 2019 +0100 +++ b/test/jdk/tools/jlink/plugins/SystemModuleDescriptors/ModuleTargetHelper.java Thu May 30 17:30:33 2019 +0530 @@ -49,7 +49,7 @@ } public static ModuleTarget getJavaBaseTarget() throws IOException { - Path p = Paths.get(URI.create("jrt:/modules/java.base/module-info.class")); + Path p = Paths.get(URI.create("jrt:/java.base/module-info.class")); try (InputStream in = Files.newInputStream(p)) { return read(in); } diff -r ebc4e5a625e2 -r 931a4d5367a6 test/langtools/tools/lib/toolbox/JarTask.java --- a/test/langtools/tools/lib/toolbox/JarTask.java Thu May 30 12:36:04 2019 +0100 +++ b/test/langtools/tools/lib/toolbox/JarTask.java Thu May 30 17:30:33 2019 +0530 @@ -377,9 +377,9 @@ private final Pattern jarEntry = Pattern.compile(".*!/(?:META-INF/sym/[^/]+/)?(.*)"); /* - * A jrt: URL is of the form jrt:/modules/// + * A jrt: URL is of the form jrt:/// */ - private final Pattern jrtEntry = Pattern.compile("/modules/([^/]+)/(.*)"); + private final Pattern jrtEntry = Pattern.compile("/([^/]+)/(.*)"); /* * A file: URL is of the form file:/path/to/{modules,patches}///