1 /* 2 * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 package jdk.tools.jlink.internal; 26 27 import java.lang.reflect.Layer; 28 import java.nio.ByteOrder; 29 import java.nio.file.Path; 30 import java.util.Collections; 31 import java.util.List; 32 import java.util.Map; 33 import java.util.Objects; 34 import java.util.Set; 35 import jdk.tools.jlink.plugin.Plugin; 36 import jdk.tools.jlink.plugin.PluginException; 37 import jdk.tools.jlink.builder.ImageBuilder; 38 39 /** 40 * API to call jlink. 41 */ 42 public final class Jlink { 43 44 /** 45 * Create a plugin. 46 * 47 * @param name Plugin name 48 * @param configuration Plugin configuration. 49 * @param pluginsLayer Plugins Layer. null means boot layer. 50 * @return A new plugin or null if plugin is unknown. 51 */ 52 public static Plugin newPlugin(String name, 53 Map<String, String> configuration, Layer pluginsLayer) { 54 Objects.requireNonNull(name); 55 Objects.requireNonNull(configuration); 56 pluginsLayer = pluginsLayer == null ? Layer.boot() : pluginsLayer; 57 return PluginRepository.newPlugin(configuration, name, pluginsLayer); 58 } 59 60 /** 61 * A complete plugin configuration. Instances of this class are used to 62 * configure jlink. 63 */ 64 public static final class PluginsConfiguration { 65 66 private final List<Plugin> plugins; 67 private final ImageBuilder imageBuilder; 68 private final String lastSorterPluginName; 69 70 /** 71 * Empty plugins configuration. 72 */ 73 public PluginsConfiguration() { 74 this(Collections.emptyList()); 75 } 76 77 /** 78 * Plugins configuration. 79 * 80 * @param plugins List of plugins. 81 */ 82 public PluginsConfiguration(List<Plugin> plugins) { 83 this(plugins, null, null); 84 } 85 86 /** 87 * Plugins configuration with a last sorter and an ImageBuilder. No 88 * sorting can occur after the last sorter plugin. The ImageBuilder is 89 * in charge to layout the image content on disk. 90 * 91 * @param plugins List of transformer plugins. 92 * @param imageBuilder Image builder. 93 * @param lastSorterPluginName Name of last sorter plugin, no sorting 94 * can occur after it. 95 */ 96 public PluginsConfiguration(List<Plugin> plugins, 97 ImageBuilder imageBuilder, String lastSorterPluginName) { 98 this.plugins = plugins == null ? Collections.emptyList() 99 : plugins; 100 this.imageBuilder = imageBuilder; 101 this.lastSorterPluginName = lastSorterPluginName; 102 } 103 104 /** 105 * @return the plugins 106 */ 107 public List<Plugin> getPlugins() { 108 return plugins; 109 } 110 111 /** 112 * @return the imageBuilder 113 */ 114 public ImageBuilder getImageBuilder() { 115 return imageBuilder; 116 } 117 118 /** 119 * @return the lastSorterPluginName 120 */ 121 public String getLastSorterPluginName() { 122 return lastSorterPluginName; 123 } 124 125 @Override 126 public String toString() { 127 StringBuilder builder = new StringBuilder(); 128 builder.append("imagebuilder=").append(imageBuilder).append("\n"); 129 StringBuilder pluginsBuilder = new StringBuilder(); 130 for (Plugin p : plugins) { 131 pluginsBuilder.append(p).append(","); 132 } 133 builder.append("plugins=").append(pluginsBuilder).append("\n"); 134 builder.append("lastsorter=").append(lastSorterPluginName).append("\n"); 135 136 return builder.toString(); 137 } 138 } 139 140 /** 141 * Jlink configuration. Instances of this class are used to configure jlink. 142 */ 143 public static final class JlinkConfiguration { 144 145 private final List<Path> modulepaths; 146 private final Path output; 147 private final Set<String> modules; 148 private final Set<String> limitmods; 149 150 private final ByteOrder endian; 151 152 /** 153 * jlink configuration, 154 * 155 * @param output Output directory, must not exist. 156 * @param modulepaths Modules paths 157 * @param modules Root modules to resolve 158 * @param limitmods Limit the universe of observable modules 159 * @param endian Jimage byte order. Native order by default 160 */ 161 public JlinkConfiguration(Path output, 162 List<Path> modulepaths, 163 Set<String> modules, 164 Set<String> limitmods, 165 ByteOrder endian) { 166 this.output = output; 167 this.modulepaths = modulepaths == null ? Collections.emptyList() : modulepaths; 168 this.modules = modules == null ? Collections.emptySet() : modules; 169 this.limitmods = limitmods == null ? Collections.emptySet() : limitmods; 170 this.endian = endian == null ? ByteOrder.nativeOrder() : endian; 171 } 172 173 /** 174 * jlink configuration, 175 * 176 * @param output Output directory, must not exist. 177 * @param modulepaths Modules paths 178 * @param modules Root modules to resolve 179 * @param limitmods Limit the universe of observable modules 180 */ 181 public JlinkConfiguration(Path output, 182 List<Path> modulepaths, 183 Set<String> modules, 184 Set<String> limitmods) { 185 this(output, modulepaths, modules, limitmods, 186 ByteOrder.nativeOrder()); 187 } 188 189 /** 190 * @return the modulepaths 191 */ 192 public List<Path> getModulepaths() { 193 return modulepaths; 194 } 195 196 /** 197 * @return the byte ordering 198 */ 199 public ByteOrder getByteOrder() { 200 return endian; 201 } 202 203 /** 204 * @return the output 205 */ 206 public Path getOutput() { 207 return output; 208 } 209 210 /** 211 * @return the modules 212 */ 213 public Set<String> getModules() { 214 return modules; 215 } 216 217 /** 218 * @return the limitmods 219 */ 220 public Set<String> getLimitmods() { 221 return limitmods; 222 } 223 224 @Override 225 public String toString() { 226 StringBuilder builder = new StringBuilder(); 227 228 builder.append("output=").append(output).append("\n"); 229 StringBuilder pathsBuilder = new StringBuilder(); 230 for (Path p : modulepaths) { 231 pathsBuilder.append(p).append(","); 232 } 233 builder.append("modulepaths=").append(pathsBuilder).append("\n"); 234 235 StringBuilder modsBuilder = new StringBuilder(); 236 for (String p : modules) { 237 modsBuilder.append(p).append(","); 238 } 239 builder.append("modules=").append(modsBuilder).append("\n"); 240 241 StringBuilder limitsBuilder = new StringBuilder(); 242 for (String p : limitmods) { 243 limitsBuilder.append(p).append(","); 244 } 245 builder.append("limitmodules=").append(limitsBuilder).append("\n"); 246 builder.append("endian=").append(endian).append("\n"); 247 return builder.toString(); 248 } 249 } 250 251 /** 252 * Jlink instance constructor, if a security manager is set, the jlink 253 * permission is checked. 254 */ 255 public Jlink() { 256 if (System.getSecurityManager() != null) { 257 System.getSecurityManager(). 258 checkPermission(new JlinkPermission("jlink")); 259 } 260 } 261 262 /** 263 * Build the image. 264 * 265 * @param config Jlink config, must not be null. 266 * @throws PluginException 267 */ 268 public void build(JlinkConfiguration config) { 269 build(config, null); 270 } 271 272 /** 273 * Build the image with a plugin configuration. 274 * 275 * @param config Jlink config, must not be null. 276 * @param pluginsConfig Plugins config, can be null 277 * @throws PluginException 278 */ 279 public void build(JlinkConfiguration config, PluginsConfiguration pluginsConfig) { 280 Objects.requireNonNull(config); 281 try { 282 JlinkTask.createImage(config, pluginsConfig); 283 } catch (Exception ex) { 284 throw new PluginException(ex); 285 } 286 } 287 288 /** 289 * Post process the image with a plugin configuration. 290 * 291 * @param image Existing image. 292 * @param plugins Plugins cannot be null 293 */ 294 public void postProcess(ExecutableImage image, List<Plugin> plugins) { 295 Objects.requireNonNull(image); 296 Objects.requireNonNull(plugins); 297 try { 298 JlinkTask.postProcessImage(image, plugins); 299 } catch (Exception ex) { 300 throw new PluginException(ex); 301 } 302 } 303 } --- EOF ---