8147794: Jlink's ModuleEntry.stream can't be consumed more than once and ModuleEntry content should be read only if needed
Reviewed-by: jlaskey, psandoz
This commit is contained in:
parent
2146bab54f
commit
72d2e8594f
jdk
src/jdk.jlink/share/classes/jdk/tools/jlink
internal
AbstractModuleEntry.javaArchiveEntryModuleEntry.javaByteArrayModuleEntry.javaImageFileCreator.javaImagePluginStack.javaModuleEntryFactory.javaModulePoolImpl.javaPathModuleEntry.java
plugins
plugin
test/tools/jlink
@ -25,9 +25,7 @@
|
||||
|
||||
package jdk.tools.jlink.internal;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.UncheckedIOException;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
|
||||
@ -44,103 +42,39 @@ import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
* {@literal bin|conf|native}/{dir1}>/.../{dirN}/{file name}</li>
|
||||
* </ul>
|
||||
*/
|
||||
public class ModuleEntryImpl implements ModuleEntry {
|
||||
|
||||
private final Type type;
|
||||
abstract class AbstractModuleEntry implements ModuleEntry {
|
||||
private final String path;
|
||||
private final String module;
|
||||
private final long length;
|
||||
private final InputStream stream;
|
||||
private byte[] buffer;
|
||||
private final Type type;
|
||||
|
||||
/**
|
||||
* Create a new LinkModuleEntry.
|
||||
* Create a new AbstractModuleEntry.
|
||||
*
|
||||
* @param module The module name.
|
||||
* @param path The data path identifier.
|
||||
* @param type The data type.
|
||||
* @param stream The data content stream.
|
||||
* @param length The stream length.
|
||||
*/
|
||||
public ModuleEntryImpl(String module, String path, Type type, InputStream stream, long length) {
|
||||
Objects.requireNonNull(module);
|
||||
Objects.requireNonNull(path);
|
||||
Objects.requireNonNull(type);
|
||||
Objects.requireNonNull(stream);
|
||||
this.path = path;
|
||||
this.type = type;
|
||||
this.module = module;
|
||||
this.stream = stream;
|
||||
this.length = length;
|
||||
AbstractModuleEntry(String module, String path, Type type) {
|
||||
this.module = Objects.requireNonNull(module);
|
||||
this.path = Objects.requireNonNull(path);
|
||||
this.type = Objects.requireNonNull(type);
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry module name.
|
||||
*
|
||||
* @return The module name.
|
||||
*/
|
||||
@Override
|
||||
public final String getModule() {
|
||||
return module;
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry path.
|
||||
*
|
||||
* @return The module path.
|
||||
*/
|
||||
@Override
|
||||
public final String getPath() {
|
||||
return path;
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry's type.
|
||||
*
|
||||
* @return The data type.
|
||||
*/
|
||||
@Override
|
||||
public final Type getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry content as an array of byte.
|
||||
*
|
||||
* @return An Array of bytes.
|
||||
*/
|
||||
@Override
|
||||
public byte[] getBytes() {
|
||||
if (buffer == null) {
|
||||
try (InputStream is = stream) {
|
||||
buffer = is.readAllBytes();
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
return buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry content length.
|
||||
*
|
||||
* @return The length.
|
||||
*/
|
||||
@Override
|
||||
public long getLength() {
|
||||
return length;
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry stream.
|
||||
*
|
||||
* @return The module data stream.
|
||||
*/
|
||||
@Override
|
||||
public InputStream stream() {
|
||||
return stream;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int hash = 7;
|
||||
@ -150,10 +84,10 @@ public class ModuleEntryImpl implements ModuleEntry {
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
if (!(other instanceof ModuleEntryImpl)) {
|
||||
if (!(other instanceof AbstractModuleEntry)) {
|
||||
return false;
|
||||
}
|
||||
ModuleEntryImpl f = (ModuleEntryImpl) other;
|
||||
AbstractModuleEntry f = (AbstractModuleEntry) other;
|
||||
return f.path.equals(path);
|
||||
}
|
||||
|
||||
@ -161,4 +95,4 @@ public class ModuleEntryImpl implements ModuleEntry {
|
||||
public String toString() {
|
||||
return getPath();
|
||||
}
|
||||
}
|
||||
}
|
82
jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ArchiveEntryModuleEntry.java
Normal file
82
jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ArchiveEntryModuleEntry.java
Normal file
@ -0,0 +1,82 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package jdk.tools.jlink.internal;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.UncheckedIOException;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
|
||||
/**
|
||||
* A ModuleEntry backed by a given Archive Entry.
|
||||
*/
|
||||
final class ArchiveEntryModuleEntry extends AbstractModuleEntry {
|
||||
private final Archive.Entry entry;
|
||||
|
||||
/**
|
||||
* Create a new ArchiveModuleEntry.
|
||||
*
|
||||
* @param module The module name.
|
||||
* @param path The data path identifier.
|
||||
* @param entry The archive Entry.
|
||||
*/
|
||||
ArchiveEntryModuleEntry(String module, String path, Archive.Entry entry) {
|
||||
super(module, path, getImageFileType(entry));
|
||||
this.entry = entry;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream stream() {
|
||||
try {
|
||||
return entry.stream();
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getLength() {
|
||||
return entry.size();
|
||||
}
|
||||
|
||||
private static ModuleEntry.Type getImageFileType(Archive.Entry entry) {
|
||||
Objects.requireNonNull(entry);
|
||||
switch(entry.type()) {
|
||||
case CLASS_OR_RESOURCE:
|
||||
return ModuleEntry.Type.CLASS_OR_RESOURCE;
|
||||
case CONFIG:
|
||||
return ModuleEntry.Type.CONFIG;
|
||||
case NATIVE_CMD:
|
||||
return ModuleEntry.Type.NATIVE_CMD;
|
||||
case NATIVE_LIB:
|
||||
return ModuleEntry.Type.NATIVE_LIB;
|
||||
default:
|
||||
return ModuleEntry.Type.OTHER;
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,78 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package jdk.tools.jlink.internal;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.io.UncheckedIOException;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
|
||||
/**
|
||||
* A ModuleEntry backed by a given byte[].
|
||||
*/
|
||||
class ByteArrayModuleEntry extends AbstractModuleEntry {
|
||||
private final byte[] buffer;
|
||||
|
||||
/**
|
||||
* Create a new ByteArrayModuleEntry.
|
||||
*
|
||||
* @param module The module name.
|
||||
* @param path The data path identifier.
|
||||
* @param type The data type.
|
||||
* @param buf The byte buffer.
|
||||
*/
|
||||
ByteArrayModuleEntry(String module, String path, Type type, byte[] buffer) {
|
||||
super(module, path, type);
|
||||
this.buffer = Objects.requireNonNull(buffer);
|
||||
}
|
||||
|
||||
@Override
|
||||
public byte[] getBytes() {
|
||||
return buffer.clone();
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream stream() {
|
||||
return new ByteArrayInputStream(buffer);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(OutputStream out) {
|
||||
try {
|
||||
out.write(buffer);
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getLength() {
|
||||
return buffer.length;
|
||||
}
|
||||
}
|
@ -233,8 +233,7 @@ public final class ImageFileCreator {
|
||||
|
||||
// write module content
|
||||
for (ModuleEntry res : content) {
|
||||
byte[] buf = res.getBytes();
|
||||
out.write(buf, 0, buf.length);
|
||||
res.write(out);
|
||||
}
|
||||
|
||||
tree.addContent(out);
|
||||
@ -244,21 +243,6 @@ public final class ImageFileCreator {
|
||||
return resultResources;
|
||||
}
|
||||
|
||||
private static ModuleEntry.Type mapImageFileType(EntryType type) {
|
||||
switch(type) {
|
||||
case CONFIG: {
|
||||
return ModuleEntry.Type.CONFIG;
|
||||
}
|
||||
case NATIVE_CMD: {
|
||||
return ModuleEntry.Type.NATIVE_CMD;
|
||||
}
|
||||
case NATIVE_LIB: {
|
||||
return ModuleEntry.Type.NATIVE_LIB;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private static ModulePoolImpl createPools(Set<Archive> archives,
|
||||
Map<String, List<Entry>> entriesForModule,
|
||||
ByteOrder byteOrder,
|
||||
@ -278,34 +262,22 @@ public final class ImageFileCreator {
|
||||
for (Archive archive : archives) {
|
||||
String mn = archive.moduleName();
|
||||
for (Entry entry : entriesForModule.get(mn)) {
|
||||
|
||||
String path;
|
||||
if (entry.type() == EntryType.CLASS_OR_RESOURCE) {
|
||||
// Removal of "classes/" radical.
|
||||
String path = entry.name();
|
||||
try (InputStream stream = entry.stream()) {
|
||||
byte[] bytes = readAllBytes(stream);
|
||||
if (path.endsWith("module-info.class")) {
|
||||
path = "/" + path;
|
||||
} else {
|
||||
path = "/" + mn + "/" + path;
|
||||
}
|
||||
try {
|
||||
resources.add(ModuleEntry.create(path, bytes));
|
||||
} catch (Exception ex) {
|
||||
throw new IOException(ex);
|
||||
}
|
||||
path = entry.name();
|
||||
if (path.endsWith("module-info.class")) {
|
||||
path = "/" + path;
|
||||
} else {
|
||||
path = "/" + mn + "/" + path;
|
||||
}
|
||||
} else {
|
||||
try {
|
||||
// Entry.path() contains the kind of file native, conf, bin, ...
|
||||
// Keep it to avoid naming conflict (eg: native/jvm.cfg and config/jvm.cfg
|
||||
resources.add(ModuleEntry.create(mn,
|
||||
"/" + mn + "/" + entry.path(), mapImageFileType(entry.type()),
|
||||
entry.stream(), entry.size()));
|
||||
} catch (Exception ex) {
|
||||
throw new IOException(ex);
|
||||
}
|
||||
// Entry.path() contains the kind of file native, conf, bin, ...
|
||||
// Keep it to avoid naming conflict (eg: native/jvm.cfg and config/jvm.cfg
|
||||
path = "/" + mn + "/" + entry.path();
|
||||
}
|
||||
|
||||
resources.add(new ArchiveEntryModuleEntry(mn, path, entry));
|
||||
}
|
||||
}
|
||||
return resources;
|
||||
|
@ -443,9 +443,7 @@ public final class ImagePluginStack {
|
||||
byte[] bytes = decompressor.decompressResource(getByteOrder(),
|
||||
(int offset) -> pool.getStringTable().getString(offset),
|
||||
res.getBytes());
|
||||
res = ModuleEntry.create(res.getPath(),
|
||||
new ByteArrayInputStream(bytes),
|
||||
bytes.length);
|
||||
res = res.create(bytes);
|
||||
} catch (IOException ex) {
|
||||
throw new PluginException(ex);
|
||||
}
|
||||
|
@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
package jdk.tools.jlink.internal;
|
||||
|
||||
import java.io.InputStream;
|
||||
import java.nio.file.Path;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
|
||||
public final class ModuleEntryFactory {
|
||||
private ModuleEntryFactory() {}
|
||||
|
||||
public static ModuleEntry create(String path,
|
||||
ModuleEntry.Type type, byte[] content) {
|
||||
return new ByteArrayModuleEntry(moduleFrom(path), path, type, content);
|
||||
}
|
||||
|
||||
public static ModuleEntry create(String path,
|
||||
ModuleEntry.Type type, Path file) {
|
||||
return new PathModuleEntry(moduleFrom(path), path, type, file);
|
||||
}
|
||||
|
||||
public static ModuleEntry create(ModuleEntry original, byte[] content) {
|
||||
return new ByteArrayModuleEntry(original.getModule(),
|
||||
original.getPath(), original.getType(), content);
|
||||
}
|
||||
|
||||
public static ModuleEntry create(ModuleEntry original, Path file) {
|
||||
return new PathModuleEntry(original.getModule(),
|
||||
original.getPath(), original.getType(), file);
|
||||
}
|
||||
|
||||
private static String moduleFrom(String path) {
|
||||
Objects.requireNonNull(path);
|
||||
if (path.isEmpty() || path.charAt(0) != '/') {
|
||||
throw new IllegalArgumentException(path + " must start with /");
|
||||
}
|
||||
String noRoot = path.substring(1);
|
||||
int idx = noRoot.indexOf('/');
|
||||
if (idx == -1) {
|
||||
throw new IllegalArgumentException("/ missing after module: " + path);
|
||||
}
|
||||
return noRoot.substring(0, idx);
|
||||
}
|
||||
}
|
@ -95,7 +95,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
@Override
|
||||
public void add(ModuleEntry data) {
|
||||
if (isReadOnly()) {
|
||||
throw new PluginException("LinkConfiguration is readonly");
|
||||
throw new PluginException("ModulePool is readonly");
|
||||
}
|
||||
Objects.requireNonNull(data);
|
||||
if (!data.getModule().equals(name)) {
|
||||
@ -180,7 +180,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
@Override
|
||||
public void add(ModuleEntry data) {
|
||||
if (isReadOnly()) {
|
||||
throw new PluginException("LinkConfiguration is readonly");
|
||||
throw new PluginException("ModulePool is readonly");
|
||||
}
|
||||
Objects.requireNonNull(data);
|
||||
if (resources.get(data.getPath()) != null) {
|
||||
@ -215,7 +215,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* The stream of modules contained in this LinkConfiguration.
|
||||
* The stream of modules contained in this ModulePool.
|
||||
*
|
||||
* @return The stream of modules.
|
||||
*/
|
||||
@ -225,7 +225,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the number of LinkModule count in this LinkConfiguration.
|
||||
* Return the number of LinkModule count in this ModulePool.
|
||||
*
|
||||
* @return the module count.
|
||||
*/
|
||||
@ -235,7 +235,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all ModuleEntry contained in this LinkConfiguration instance.
|
||||
* Get all ModuleEntry contained in this ModulePool instance.
|
||||
*
|
||||
* @return The stream of LinkModuleEntries.
|
||||
*/
|
||||
@ -245,7 +245,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the number of ModuleEntry count in this LinkConfiguration.
|
||||
* Return the number of ModuleEntry count in this ModulePool.
|
||||
*
|
||||
* @return the entry count.
|
||||
*/
|
||||
@ -267,7 +267,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the LinkConfiguration contains the given ModuleEntry.
|
||||
* Check if the ModulePool contains the given ModuleEntry.
|
||||
*
|
||||
* @param data The module data to check existence for.
|
||||
* @return The module data or null if not found.
|
||||
@ -279,7 +279,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the LinkConfiguration contains some content at all.
|
||||
* Check if the ModulePool contains some content at all.
|
||||
*
|
||||
* @return True, no content, false otherwise.
|
||||
*/
|
||||
@ -289,16 +289,16 @@ public class ModulePoolImpl implements ModulePool {
|
||||
}
|
||||
|
||||
/**
|
||||
* Visit each ModuleEntry in this LinkConfiguration to transform it and
|
||||
* copy the transformed ModuleEntry to the output LinkConfiguration.
|
||||
* Visit each ModuleEntry in this ModulePool to transform it and
|
||||
* copy the transformed ModuleEntry to the output ModulePool.
|
||||
*
|
||||
* @param transform The function called for each ModuleEntry found in
|
||||
* the LinkConfiguration. The transform function should return a
|
||||
* the ModulePool. The transform function should return a
|
||||
* ModuleEntry instance which will be added to the output or it should
|
||||
* return null if the passed ModuleEntry is to be ignored for the
|
||||
* output.
|
||||
*
|
||||
* @param output The LinkConfiguration to be filled with Visitor returned
|
||||
* @param output The ModulePool to be filled with Visitor returned
|
||||
* ModuleEntry.
|
||||
*/
|
||||
@Override
|
||||
@ -351,14 +351,13 @@ public class ModulePoolImpl implements ModulePool {
|
||||
/**
|
||||
* A resource that has been compressed.
|
||||
*/
|
||||
public static final class CompressedModuleData extends ModuleEntryImpl {
|
||||
public static final class CompressedModuleData extends ByteArrayModuleEntry {
|
||||
|
||||
final long uncompressed_size;
|
||||
|
||||
private CompressedModuleData(String module, String path,
|
||||
InputStream stream, long size,
|
||||
long uncompressed_size) {
|
||||
super(module, path, ModuleEntry.Type.CLASS_OR_RESOURCE, stream, size);
|
||||
byte[] content, long uncompressed_size) {
|
||||
super(module, path, ModuleEntry.Type.CLASS_OR_RESOURCE, content);
|
||||
this.uncompressed_size = uncompressed_size;
|
||||
}
|
||||
|
||||
@ -413,8 +412,7 @@ public class ModulePoolImpl implements ModulePool {
|
||||
|
||||
CompressedModuleData compressedResource
|
||||
= new CompressedModuleData(original.getModule(), original.getPath(),
|
||||
new ByteArrayInputStream(contentWithHeader),
|
||||
contentWithHeader.length, uncompressed_size);
|
||||
contentWithHeader, uncompressed_size);
|
||||
return compressedResource;
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,75 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classfile" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package jdk.tools.jlink.internal;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.UncheckedIOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
|
||||
/**
|
||||
* A ModuleEntry backed by a given nio Path.
|
||||
*/
|
||||
public class PathModuleEntry extends AbstractModuleEntry {
|
||||
private final Path file;
|
||||
|
||||
/**
|
||||
* Create a new PathModuleEntry.
|
||||
*
|
||||
* @param module The module name.
|
||||
* @param file The data file identifier.
|
||||
* @param type The data type.
|
||||
* @param file The Path for the resource content.
|
||||
*/
|
||||
public PathModuleEntry(String module, String path, Type type, Path file) {
|
||||
super(module, path, type);
|
||||
this.file = Objects.requireNonNull(file);
|
||||
if (!Files.isRegularFile(file)) {
|
||||
throw new IllegalArgumentException(file + " not a file");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public final InputStream stream() {
|
||||
try {
|
||||
return Files.newInputStream(file);
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public final long getLength() {
|
||||
try {
|
||||
return Files.size(file);
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
}
|
@ -244,10 +244,7 @@ public final class ExcludeVMPlugin implements TransformerPlugin {
|
||||
|
||||
byte[] content = builder.toString().getBytes(StandardCharsets.UTF_8);
|
||||
|
||||
return ModuleEntry.create(orig.getModule(),
|
||||
orig.getPath(),
|
||||
orig.getType(),
|
||||
new ByteArrayInputStream(content), content.length);
|
||||
return orig.create(content);
|
||||
}
|
||||
|
||||
private static String jvmlib() {
|
||||
|
@ -39,7 +39,7 @@ import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.internal.ModuleEntryImpl;
|
||||
import jdk.tools.jlink.internal.PathModuleEntry;
|
||||
import jdk.tools.jlink.plugin.PluginException;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
import jdk.tools.jlink.plugin.ModulePool;
|
||||
@ -66,13 +66,13 @@ public class FileCopierPlugin implements TransformerPlugin {
|
||||
/**
|
||||
* Symbolic link to another path.
|
||||
*/
|
||||
public static abstract class SymImageFile extends ModuleEntryImpl {
|
||||
public static abstract class SymImageFile extends PathModuleEntry {
|
||||
|
||||
private final String targetPath;
|
||||
|
||||
public SymImageFile(String targetPath, String module, String path,
|
||||
ModuleEntry.Type type, InputStream stream, long size) {
|
||||
super(module, path, type, stream, size);
|
||||
ModuleEntry.Type type, Path file) {
|
||||
super(module, path, type, file);
|
||||
this.targetPath = targetPath;
|
||||
}
|
||||
|
||||
@ -85,23 +85,7 @@ public class FileCopierPlugin implements TransformerPlugin {
|
||||
|
||||
public SymImageFileImpl(String targetPath, Path file, String module,
|
||||
String path, ModuleEntry.Type type) {
|
||||
super(targetPath, module, path, type, newStream(file), length(file));
|
||||
}
|
||||
}
|
||||
|
||||
private static long length(Path file) {
|
||||
try {
|
||||
return Files.size(file);
|
||||
} catch (IOException ex) {
|
||||
throw new RuntimeException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
private static InputStream newStream(Path file) {
|
||||
try {
|
||||
return Files.newInputStream(file);
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
super(targetPath, module, path, type, file);
|
||||
}
|
||||
}
|
||||
|
||||
@ -175,9 +159,9 @@ public class FileCopierPlugin implements TransformerPlugin {
|
||||
Objects.requireNonNull(pool);
|
||||
Objects.requireNonNull(file);
|
||||
Objects.requireNonNull(path);
|
||||
ModuleEntry impl = ModuleEntry.create(FAKE_MODULE,
|
||||
ModuleEntry impl = ModuleEntry.create(
|
||||
"/" + FAKE_MODULE + "/other/" + path,
|
||||
ModuleEntry.Type.OTHER, newStream(file), length(file));
|
||||
ModuleEntry.Type.OTHER, file);
|
||||
try {
|
||||
pool.add(impl);
|
||||
} catch (Exception ex) {
|
||||
|
@ -171,10 +171,9 @@ public final class GenerateJLIClassesPlugin implements TransformerPlugin {
|
||||
byte[] bytes = result.getValue();
|
||||
|
||||
// Add class to pool
|
||||
ModuleEntry ndata = ModuleEntry.create(data.getModule(),
|
||||
ModuleEntry ndata = ModuleEntry.create(
|
||||
"/java.base/" + className + ".class",
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(bytes), bytes.length);
|
||||
bytes);
|
||||
if (!out.contains(ndata)) {
|
||||
out.add(ndata);
|
||||
}
|
||||
|
@ -123,9 +123,7 @@ public final class IncludeLocalesPlugin implements TransformerPlugin, ResourcePr
|
||||
if (Arrays.stream(cr.getInterfaces())
|
||||
.anyMatch(i -> i.contains(METAINFONAME)) &&
|
||||
stripUnsupportedLocales(bytes, cr)) {
|
||||
resource = ModuleEntry.create(MODULENAME, path,
|
||||
resource.getType(),
|
||||
new ByteArrayInputStream(bytes), bytes.length);
|
||||
resource = resource.create(bytes);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -75,7 +75,7 @@ public final class StripDebugPlugin implements TransformerPlugin {
|
||||
ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS);
|
||||
reader.accept(writer, ClassReader.SKIP_DEBUG);
|
||||
byte[] content = writer.toByteArray();
|
||||
res = ModuleEntry.create(path, new ByteArrayInputStream(content), content.length);
|
||||
res = resource.create(content);
|
||||
}
|
||||
}
|
||||
} else if (predicate.test(res.getPath())) {
|
||||
|
17
jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/SystemModuleDescriptorPlugin.java
17
jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/SystemModuleDescriptorPlugin.java
@ -139,11 +139,7 @@ public final class SystemModuleDescriptorPlugin implements TransformerPlugin {
|
||||
ModuleInfoRewriter minfoWriter =
|
||||
new ModuleInfoRewriter(bain, mbuilder.conceals());
|
||||
// replace with the overridden version
|
||||
data = ModuleEntry.create(data.getModule(),
|
||||
data.getPath(),
|
||||
data.getType(),
|
||||
minfoWriter.stream(),
|
||||
minfoWriter.size());
|
||||
data = data.create(minfoWriter.getBytes());
|
||||
}
|
||||
out.add(data);
|
||||
} catch (IOException e) {
|
||||
@ -158,12 +154,7 @@ public final class SystemModuleDescriptorPlugin implements TransformerPlugin {
|
||||
return;
|
||||
if (builder.isOverriddenClass(data.getPath())) {
|
||||
byte[] bytes = cwriter.toByteArray();
|
||||
ModuleEntry ndata =
|
||||
ModuleEntry.create(data.getModule(),
|
||||
data.getPath(),
|
||||
data.getType(),
|
||||
new ByteArrayInputStream(bytes),
|
||||
bytes.length);
|
||||
ModuleEntry ndata = data.create(bytes);
|
||||
out.add(ndata);
|
||||
} else {
|
||||
out.add(data);
|
||||
@ -183,8 +174,8 @@ public final class SystemModuleDescriptorPlugin implements TransformerPlugin {
|
||||
this.extender.write(this);
|
||||
}
|
||||
|
||||
InputStream stream() {
|
||||
return new ByteArrayInputStream(buf);
|
||||
byte[] getBytes() {
|
||||
return buf;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -93,8 +93,7 @@ final class AsmPoolImpl implements AsmModulePool {
|
||||
}
|
||||
|
||||
byte[] content = writer.toByteArray();
|
||||
ModuleEntry res = ModuleEntry.create(path,
|
||||
new ByteArrayInputStream(content), content.length);
|
||||
ModuleEntry res = ModuleEntry.create(path, content);
|
||||
transformedClasses.put(className, res);
|
||||
}
|
||||
|
||||
|
@ -26,16 +26,18 @@ package jdk.tools.jlink.plugin;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.InputStream;
|
||||
import java.util.Objects;
|
||||
import jdk.tools.jlink.internal.ImageFileCreator;
|
||||
import jdk.tools.jlink.internal.ModuleEntryImpl;
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.io.UncheckedIOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import jdk.tools.jlink.internal.ModuleEntryFactory;
|
||||
|
||||
/**
|
||||
* A LinkModuleEntry is the elementary unit of data inside an image. It is
|
||||
* generally a file. e.g.: a java class file, a resource file, a shared library,
|
||||
* ...
|
||||
* A ModuleEntry is the elementary unit of data inside an image. It is
|
||||
* generally a file. e.g.: a java class file, a resource file, a shared library.
|
||||
* <br>
|
||||
* A LinkModuleEntry is identified by a path of the form:
|
||||
* A ModuleEntry is identified by a path of the form:
|
||||
* <ul>
|
||||
* <li>For jimage content: /{module name}/{package1}/.../{packageN}/{file
|
||||
* name}</li>
|
||||
@ -63,93 +65,133 @@ public interface ModuleEntry {
|
||||
OTHER
|
||||
}
|
||||
/**
|
||||
* The LinkModuleEntry module name.
|
||||
* The ModuleEntry module name.
|
||||
*
|
||||
* @return The module name.
|
||||
*/
|
||||
public String getModule();
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry path.
|
||||
* The ModuleEntry path.
|
||||
*
|
||||
* @return The module path.
|
||||
*/
|
||||
public String getPath();
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry's type.
|
||||
* The ModuleEntry's type.
|
||||
*
|
||||
* @return The data type.
|
||||
*/
|
||||
public Type getType();
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry content as an array of byte.
|
||||
* The ModuleEntry content as an array of bytes.
|
||||
*
|
||||
* @return An Array of bytes.
|
||||
*/
|
||||
public byte[] getBytes();
|
||||
public default byte[] getBytes() {
|
||||
try (InputStream is = stream()) {
|
||||
return is.readAllBytes();
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry content length.
|
||||
* The ModuleEntry content length.
|
||||
*
|
||||
* @return The length.
|
||||
*/
|
||||
public long getLength();
|
||||
|
||||
/**
|
||||
* The LinkModuleEntry stream.
|
||||
* The ModuleEntry stream.
|
||||
*
|
||||
* @return The module data stream.
|
||||
*/
|
||||
public InputStream stream();
|
||||
|
||||
|
||||
/**
|
||||
* Create a LinkModuleEntry located inside a jimage file. Such
|
||||
* LinkModuleEntry has a Type being equals to CLASS_OR_RESOURCE.
|
||||
* Write the content of this ModuleEntry to stream.
|
||||
*
|
||||
* @param path The complete resource path (contains the module radical).
|
||||
* @param content The resource content.
|
||||
* @param size The content size.
|
||||
* @return A new LinkModuleEntry.
|
||||
* @param out the output stream
|
||||
*/
|
||||
public static ModuleEntry create(String path, InputStream content, long size) {
|
||||
Objects.requireNonNull(path);
|
||||
Objects.requireNonNull(content);
|
||||
String[] split = ImageFileCreator.splitPath(path);
|
||||
String module = split[0];
|
||||
return new ModuleEntryImpl(module, path, Type.CLASS_OR_RESOURCE, content, size);
|
||||
public default void write(OutputStream out) {
|
||||
try {
|
||||
out.write(getBytes());
|
||||
} catch (IOException ex) {
|
||||
throw new UncheckedIOException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a LinkModuleEntry for a file that will be located inside a jimage
|
||||
* file.
|
||||
* Create a ModuleEntry with new content but other information
|
||||
* copied from this ModuleEntry.
|
||||
*
|
||||
* @param content The new resource content.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public default ModuleEntry create(byte[] content) {
|
||||
return ModuleEntryFactory.create(this, content);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a ModuleEntry with new content but other information
|
||||
* copied from this ModuleEntry.
|
||||
*
|
||||
* @param file The new resource content.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public default ModuleEntry create(Path file) {
|
||||
return ModuleEntryFactory.create(this, file);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a ModuleEntry for a resource of the given type.
|
||||
*
|
||||
* @param path The resource path.
|
||||
* @param type The ModuleEntry type.
|
||||
* @param content The resource content.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public static ModuleEntry create(String path,
|
||||
ModuleEntry.Type type, byte[] content) {
|
||||
return ModuleEntryFactory.create(path, type, content);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a ModuleEntry for a resource of type {@link Type#CLASS_OR_RESOURCE}.
|
||||
*
|
||||
* @param path The resource path.
|
||||
* @param content The resource content.
|
||||
* @return A new LinkModuleEntry.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public static ModuleEntry create(String path, byte[] content) {
|
||||
return create(path, new ByteArrayInputStream(content),
|
||||
content.length);
|
||||
return create(path, Type.CLASS_OR_RESOURCE, content);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a LinkModuleEntry for a file that will be located outside a jimage
|
||||
* file.
|
||||
* Create a ModuleEntry for a resource of the given type.
|
||||
*
|
||||
* @param module The module in which this files is located.
|
||||
* @param path The file path locator (doesn't contain the module name).
|
||||
* @param type The LinkModuleEntry type.
|
||||
* @param content The file content.
|
||||
* @param size The content size.
|
||||
* @return A new LinkModuleEntry.
|
||||
* @param path The resource path.
|
||||
* @param type The ModuleEntry type.
|
||||
* @param file The resource file.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public static ModuleEntry create(String module, String path, ModuleEntry.Type type,
|
||||
InputStream content, long size) {
|
||||
Objects.requireNonNull(path);
|
||||
Objects.requireNonNull(content);
|
||||
return new ModuleEntryImpl(module, path, type, content, size);
|
||||
public static ModuleEntry create(String path,
|
||||
ModuleEntry.Type type, Path file) {
|
||||
return ModuleEntryFactory.create(path, type, file);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a ModuleEntry for a resource of type {@link Type#CLASS_OR_RESOURCE}.
|
||||
*
|
||||
* @param path The resource path.
|
||||
* @param file The resource file.
|
||||
* @return A new ModuleEntry.
|
||||
*/
|
||||
public static ModuleEntry create(String path, Path file) {
|
||||
return create(path, Type.CLASS_OR_RESOURCE, file);
|
||||
}
|
||||
}
|
||||
|
@ -33,7 +33,7 @@
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.util.Optional;
|
||||
import java.util.function.Function;
|
||||
import jdk.tools.jlink.internal.ModuleEntryImpl;
|
||||
import jdk.tools.jlink.internal.ModuleEntryFactory;
|
||||
import jdk.tools.jlink.internal.ModulePoolImpl;
|
||||
import jdk.tools.jlink.plugin.ModuleEntry;
|
||||
import jdk.tools.jlink.plugin.ModulePool;
|
||||
@ -54,7 +54,7 @@ public class ImageFilePoolTest {
|
||||
ModulePool input = new ModulePoolImpl();
|
||||
for (int i = 0; i < 1000; ++i) {
|
||||
String module = "module" + (i / 100);
|
||||
input.add(new InMemoryImageFile(module, "/" + module + "/java/class" + i,
|
||||
input.add(newInMemoryImageFile("/" + module + "/java/class" + i,
|
||||
ModuleEntry.Type.CONFIG, "class" + i));
|
||||
}
|
||||
if (input.getEntryCount() != 1000) {
|
||||
@ -94,11 +94,11 @@ public class ImageFilePoolTest {
|
||||
switch (index) {
|
||||
case 0:
|
||||
++amountAfter;
|
||||
return new InMemoryImageFile(file.getModule(), file.getPath() + SUFFIX,
|
||||
return newInMemoryImageFile(file.getPath() + SUFFIX,
|
||||
file.getType(), file.getPath());
|
||||
case 1:
|
||||
++amountAfter;
|
||||
return new InMemoryImageFile(file.getModule(), file.getPath(),
|
||||
return newInMemoryImageFile(file.getPath(),
|
||||
file.getType(), file.getPath());
|
||||
}
|
||||
return null;
|
||||
@ -130,28 +130,27 @@ public class ImageFilePoolTest {
|
||||
if (input.findEntry("unknown").isPresent()) {
|
||||
throw new AssertionError("ImageFileModulePool does not return null for unknown file");
|
||||
}
|
||||
if (input.contains(new InMemoryImageFile("", "unknown", ModuleEntry.Type.CONFIG, "unknown"))) {
|
||||
throw new AssertionError("'contain' returns true for unknown file");
|
||||
if (input.contains(newInMemoryImageFile("/unknown/foo", ModuleEntry.Type.CONFIG, "unknown"))) {
|
||||
throw new AssertionError("'contain' returns true for /unknown/foo file");
|
||||
}
|
||||
input.add(new InMemoryImageFile("", "/aaa/bbb", ModuleEntry.Type.CONFIG, ""));
|
||||
input.add(newInMemoryImageFile("/aaa/bbb", ModuleEntry.Type.CONFIG, ""));
|
||||
try {
|
||||
input.add(new InMemoryImageFile("", "/aaa/bbb", ModuleEntry.Type.CONFIG, ""));
|
||||
input.add(newInMemoryImageFile("/aaa/bbb", ModuleEntry.Type.CONFIG, ""));
|
||||
throw new AssertionError("Exception expected");
|
||||
} catch (Exception e) {
|
||||
// expected
|
||||
}
|
||||
input.setReadOnly();
|
||||
try {
|
||||
input.add(new InMemoryImageFile("", "/aaa/ccc", ModuleEntry.Type.CONFIG, ""));
|
||||
input.add(newInMemoryImageFile("/aaa/ccc", ModuleEntry.Type.CONFIG, ""));
|
||||
throw new AssertionError("Exception expected");
|
||||
} catch (Exception e) {
|
||||
// expected
|
||||
}
|
||||
}
|
||||
|
||||
private static class InMemoryImageFile extends ModuleEntryImpl {
|
||||
public InMemoryImageFile(String module, String path, ModuleEntry.Type type, String content) {
|
||||
super(module, path, type, new ByteArrayInputStream(content.getBytes()), content.getBytes().length);
|
||||
}
|
||||
private static ModuleEntry newInMemoryImageFile(String path,
|
||||
ModuleEntry.Type type, String content) {
|
||||
return ModuleEntryFactory.create(path, type, content.getBytes());
|
||||
}
|
||||
}
|
||||
|
@ -66,9 +66,7 @@ public class ResourcePoolTest {
|
||||
String module = "/module" + (i / 10);
|
||||
String resourcePath = module + "/java/package" + i;
|
||||
byte[] bytes = resourcePath.getBytes();
|
||||
input.add(ModuleEntry.create(module, resourcePath,
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(bytes), bytes.length));
|
||||
input.add(ModuleEntry.create(resourcePath, bytes));
|
||||
}
|
||||
ModulePool output = new ModulePoolImpl();
|
||||
ResourceVisitor visitor = new ResourceVisitor();
|
||||
@ -103,12 +101,11 @@ public class ResourcePoolTest {
|
||||
switch (index) {
|
||||
case 0:
|
||||
++amountAfter;
|
||||
return ModuleEntry.create(resource.getModule(), resource.getPath() + SUFFIX,
|
||||
resource.getType(), resource.stream(), resource.getLength());
|
||||
return ModuleEntry.create(resource.getPath() + SUFFIX,
|
||||
resource.getType(), resource.getBytes());
|
||||
case 1:
|
||||
++amountAfter;
|
||||
return ModuleEntry.create(resource.getModule(), resource.getPath(),
|
||||
resource.getType(), resource.stream(), resource.getLength());
|
||||
return resource.create(resource.getBytes());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@ -132,9 +129,7 @@ public class ResourcePoolTest {
|
||||
samples.add("javax/management/ObjectName");
|
||||
test(samples, (resources, module, path) -> {
|
||||
try {
|
||||
resources.add(ModuleEntry.create(module, path,
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(new byte[0]), 0));
|
||||
resources.add(ModuleEntry.create(path, new byte[0]));
|
||||
} catch (Exception ex) {
|
||||
throw new RuntimeException(ex);
|
||||
}
|
||||
@ -142,9 +137,7 @@ public class ResourcePoolTest {
|
||||
test(samples, (resources, module, path) -> {
|
||||
try {
|
||||
resources.add(ModulePoolImpl.
|
||||
newCompressedResource(ModuleEntry.create(module, path,
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(new byte[0]), 0),
|
||||
newCompressedResource(ModuleEntry.create(path, new byte[0]),
|
||||
ByteBuffer.allocate(99), "bitcruncher", null,
|
||||
((ModulePoolImpl)resources).getStringTable(), ByteOrder.nativeOrder()));
|
||||
} catch (Exception ex) {
|
||||
@ -203,20 +196,14 @@ public class ResourcePoolTest {
|
||||
|
||||
private void checkResourcesAfterCompression() throws Exception {
|
||||
ModulePoolImpl resources1 = new ModulePoolImpl();
|
||||
ModuleEntry res1 = ModuleEntry.create("module1", "/module1/toto1",
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(new byte[0]), 0);
|
||||
ModuleEntry res2 = ModuleEntry.create("module2", "/module2/toto1",
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(new byte[0]), 0);
|
||||
ModuleEntry res1 = ModuleEntry.create("/module1/toto1", new byte[0]);
|
||||
ModuleEntry res2 = ModuleEntry.create("/module2/toto1", new byte[0]);
|
||||
resources1.add(res1);
|
||||
resources1.add(res2);
|
||||
|
||||
checkResources(resources1, res1, res2);
|
||||
ModulePool resources2 = new ModulePoolImpl();
|
||||
ModuleEntry res3 = ModuleEntry.create("module2", "/module2/toto1",
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE,
|
||||
new ByteArrayInputStream(new byte[7]), 7);
|
||||
ModuleEntry res3 = ModuleEntry.create("/module2/toto1", new byte[7]);
|
||||
resources2.add(res3);
|
||||
resources2.add(ModulePoolImpl.newCompressedResource(res1,
|
||||
ByteBuffer.allocate(7), "zip", null, resources1.getStringTable(),
|
||||
@ -260,8 +247,7 @@ public class ResourcePoolTest {
|
||||
|
||||
((ModulePoolImpl) resources).setReadOnly();
|
||||
try {
|
||||
resources.add(ModuleEntry.create("module2", "/module2/toto1",
|
||||
ModuleEntry.Type.CLASS_OR_RESOURCE, new ByteArrayInputStream(new byte[0]), 0));
|
||||
resources.add(ModuleEntry.create("/module2/toto1", new byte[0]));
|
||||
throw new AssertionError("ModulePool is read-only, but an exception is not thrown");
|
||||
} catch (Exception ex) {
|
||||
// Expected
|
||||
|
@ -74,8 +74,8 @@ public class ExcludeFilesPluginTest {
|
||||
fplug.configure(prop);
|
||||
ModulePoolImpl files = new ModulePoolImpl();
|
||||
ModulePoolImpl fresult = new ModulePoolImpl();
|
||||
ModuleEntry f = ModuleEntry.create(module, "/" + module + "/" + sample,
|
||||
ModuleEntry.Type.CONFIG, new ByteArrayInputStream(new byte[0]), 0);
|
||||
ModuleEntry f = ModuleEntry.create("/" + module + "/" + sample,
|
||||
ModuleEntry.Type.CONFIG, new byte[0]);
|
||||
files.add(f);
|
||||
|
||||
fplug.visit(files, fresult);
|
||||
|
@ -48,16 +48,16 @@ public class ExcludePluginTest {
|
||||
|
||||
public void test() throws Exception {
|
||||
check("**.jcov", "/num/toto.jcov", true);
|
||||
check("**.jcov", "//toto.jcov", true);
|
||||
check("**.jcov", "/toto.jcov/", true);
|
||||
check("**.jcov", "/toto.jcov/tutu/tata", false);
|
||||
check("/java.base/*.jcov", "/java.base/toto.jcov", true);
|
||||
check("/java.base/toto.jcov", "t/java.base/iti.jcov", false);
|
||||
check("/java.base/toto.jcov", "/tjava.base/iti.jcov", false);
|
||||
check("/java.base/*/toto.jcov", "/java.base/toto.jcov", false);
|
||||
check("/java.base/*/toto.jcov", "/java.base/tutu/toto.jcov", true);
|
||||
check("**/java.base/*/toto.jcov", "/tutu/java.base/tutu/toto.jcov", true);
|
||||
check("/META-INF/**", "/META-INF/services/ MyProvider ", true);
|
||||
check("/META-INF/**", "/META-INF/services/MyProvider", true);
|
||||
check("**/META-INF", " /META-INF/services/MyProvider", false);
|
||||
check("**/META-INF", "/ META-INF/services/MyProvider", false);
|
||||
check("**/META-INF/**", "/java.base//META-INF/services/MyProvider", true);
|
||||
check("/java.base/*/Toto$Titi.class", "/java.base/tutu/Toto$Titi.class", true);
|
||||
check("/**$**.class", "/java.base/tutu/Toto$Titi.class", true);
|
||||
|
@ -165,11 +165,11 @@ public class ExcludeVMPluginTest {
|
||||
// Create a pool with jvm.cfg and the input paths.
|
||||
byte[] jvmcfgContent = jvmcfg.getBytes();
|
||||
ModulePool pool = new ModulePoolImpl();
|
||||
pool.add(ModuleEntry.create("java.base", "/java.base/native/jvm.cfg",
|
||||
ModuleEntry.Type.NATIVE_LIB, new ByteArrayInputStream(jvmcfgContent), jvmcfgContent.length));
|
||||
pool.add(ModuleEntry.create("/java.base/native/jvm.cfg",
|
||||
ModuleEntry.Type.NATIVE_LIB, jvmcfgContent));
|
||||
for (String in : input) {
|
||||
pool.add(ModuleEntry.create("java.base", in,
|
||||
ModuleEntry.Type.NATIVE_LIB, new ByteArrayInputStream(new byte[0]), 0));
|
||||
pool.add(ModuleEntry.create(in,
|
||||
ModuleEntry.Type.NATIVE_LIB, new byte[0]));
|
||||
}
|
||||
ModulePool out = new ModulePoolImpl();
|
||||
|
||||
|
@ -106,6 +106,9 @@ public class StringSharingPluginTest {
|
||||
byte[] content = Files.readAllBytes(p);
|
||||
String path = p.toString().replace('\\', '/');
|
||||
path = path.substring("/modules".length());
|
||||
if (path.charAt(0) != '/') {
|
||||
path = "/" + path;
|
||||
}
|
||||
ModuleEntry res = ModuleEntry.create(path, content);
|
||||
resources.add(res);
|
||||
} catch (Exception ex) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user