hotspot/test/testlibrary/ClassFileInstaller.java
changeset 40819 d9f374de0160
parent 40818 9c2079cba606
parent 40817 4f5fb115676d
child 40820 535c39eb136d
--- a/hotspot/test/testlibrary/ClassFileInstaller.java	Mon Sep 12 15:00:58 2016 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,257 +0,0 @@
-/*
- * 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.
- *
- * 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.
- */
-
-import java.io.ByteArrayInputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileOutputStream;
-import java.io.FileNotFoundException;
-import java.io.InputStream;
-import java.io.ByteArrayInputStream;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.nio.file.Paths;
-import java.nio.file.StandardCopyOption;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipOutputStream;
-
-/**
- * Dump a class file for a class on the class path in the current directory, or
- * in the specified JAR file. This class is usually used when you build a class
- * from a test library, but want to use this class in a sub-process.
- *
- * For example, to build the following library class:
- * test/lib/sun/hotspot/WhiteBox.java
- *
- * You would use the following tags:
- *
- * @library /test/lib
- * @build sun.hotspot.WhiteBox
- *
- * JTREG would build the class file under
- * ${JTWork}/classes/test/lib/sun/hotspot/WhiteBox.class
- *
- * With you run your main test class using "@run main MyMainClass", JTREG would setup the
- * -classpath to include "${JTWork}/classes/test/lib/", so MyMainClass would be able to
- * load the WhiteBox class.
- *
- * However, if you run a sub process, and do not wish to use the exact same -classpath,
- * You can use ClassFileInstaller to ensure that WhiteBox is available in the current
- * directory of your test:
- *
- * @run main ClassFileInstaller sun.hotspot.WhiteBox
- *
- * Or, you can use the -jar option to store the class in the specified JAR file. If a relative
- * path name is given, the JAR file would be relative to the current directory of
- *
- * @run main ClassFileInstaller -jar myjar.jar sun.hotspot.WhiteBox
- */
-public class ClassFileInstaller {
-    /**
-     * You can enable debug tracing of ClassFileInstaller by running JTREG with
-     * jtreg -DClassFileInstaller.debug=true ... <names of tests>
-     */
-    public static boolean DEBUG = Boolean.getBoolean("ClassFileInstaller.debug");
-
-    /**
-     * @param args The names of the classes to dump
-     * @throws Exception
-     */
-    public static void main(String... args) throws Exception {
-        if (args.length > 1 && args[0].equals("-jar")) {
-            if (args.length < 2) {
-                throw new RuntimeException("Usage: ClassFileInstaller <options> <classes>\n" +
-                                           "where possible options include:\n" +
-                                           "  -jar <path>             Write to the JAR file <path>");
-            }
-            writeJar(args[1], null, args, 2, args.length);
-        } else {
-            if (DEBUG) {
-                System.out.println("ClassFileInstaller: Writing to " + System.getProperty("user.dir"));
-            }
-            for (String arg : args) {
-                writeClassToDisk(arg);
-            }
-        }
-    }
-
-    public static class Manifest {
-        private InputStream in;
-
-        private Manifest(InputStream in) {
-            this.in = in;
-        }
-
-        static Manifest fromSourceFile(String fileName) throws Exception {
-            String pathName = System.getProperty("test.src") + File.separator + fileName;
-            return new Manifest(new FileInputStream(pathName));
-        }
-
-        // Example:
-        //  String manifest = "Premain-Class: RedefineClassHelper\n" +
-        //                "Can-Redefine-Classes: true\n";
-        //  ClassFileInstaller.writeJar("redefineagent.jar",
-        //    ClassFileInstaller.Manifest.fromString(manifest),
-        //    "RedefineClassHelper");
-        static Manifest fromString(String manifest) throws Exception {
-            return new Manifest(new ByteArrayInputStream(manifest.getBytes()));
-        }
-
-        public InputStream getInputStream() {
-            return in;
-        }
-    }
-
-    private static void writeJar(String jarFile, Manifest manifest, String classes[], int from, int to) throws Exception {
-        if (DEBUG) {
-            System.out.println("ClassFileInstaller: Writing to " + getJarPath(jarFile));
-        }
-
-        (new File(jarFile)).delete();
-        FileOutputStream fos = new FileOutputStream(jarFile);
-        ZipOutputStream zos = new ZipOutputStream(fos);
-
-        // The manifest must be the first or second entry. See comments in JarInputStream
-        // constructor and JDK-5046178.
-        if (manifest != null) {
-            writeToDisk(zos, "META-INF/MANIFEST.MF", manifest.getInputStream());
-        }
-
-        for (int i=from; i<to; i++) {
-            writeClassToDisk(zos, classes[i]);
-        }
-
-        zos.close();
-        fos.close();
-    }
-
-    /*
-     * You can call ClassFileInstaller.writeJar() from your main test class instead of
-     * using "@run ClassFileInstaller -jar ...". E.g.,
-     *
-     * String jarPath = ClassFileInstaller.getJarPath("myjar.jar", "sun.hotspot.WhiteBox")
-     *
-     * If you call this API, make sure you build ClassFileInstaller with the following tags:
-     *
-     * @library testlibrary
-     * @build ClassFileInstaller
-     */
-    public static String writeJar(String jarFile, String... classes) throws Exception {
-        writeJar(jarFile, null, classes, 0, classes.length);
-        return getJarPath(jarFile);
-    }
-
-    public static String writeJar(String jarFile, Manifest manifest, String... classes) throws Exception {
-        writeJar(jarFile, manifest, classes, 0, classes.length);
-        return getJarPath(jarFile);
-    }
-
-    /**
-     * This returns the absolute path to the file specified in "@ClassFileInstaller -jar myjar.jar",
-     * In your test program, instead of using the JAR file name directly:
-     *
-     * String jarPath = "myjar.jar";
-     *
-     * you should call this function, like:
-     *
-     * String jarPath = ClassFileInstaller.getJarPath("myjar.jar")
-     *
-     * The reasons are:
-     * (1) Using absolute path makes it easy to cut-and-paste from the JTR file and rerun your
-     *     test in any directory.
-     * (2) In the future, we may make the JAR file name unique to avoid clobbering
-     *     during parallel JTREG execution.
-     *
-     */
-    public static String getJarPath(String jarFileName) {
-        return new File(jarFileName).getAbsolutePath();
-    }
-
-    public static void writeClassToDisk(String className) throws Exception {
-        writeClassToDisk((ZipOutputStream)null, className);
-    }
-    private static void writeClassToDisk(ZipOutputStream zos, String className) throws Exception {
-        writeClassToDisk(zos, className, "");
-    }
-
-    public static void writeClassToDisk(String className, String prependPath) throws Exception {
-        writeClassToDisk(null, className, prependPath);
-    }
-    private static void writeClassToDisk(ZipOutputStream zos, String className, String prependPath) throws Exception {
-        ClassLoader cl = ClassFileInstaller.class.getClassLoader();
-
-        // Convert dotted class name to a path to a class file
-        String pathName = className.replace('.', '/').concat(".class");
-        InputStream is = cl.getResourceAsStream(pathName);
-        if (is == null) {
-            throw new RuntimeException("Failed to find " + pathName);
-        }
-        if (prependPath.length() > 0) {
-            pathName = prependPath + "/" + pathName;
-        }
-        writeToDisk(zos, pathName, is);
-    }
-
-    public static void writeClassToDisk(String className, byte[] bytecode) throws Exception {
-        writeClassToDisk(null, className, bytecode);
-    }
-    private static void writeClassToDisk(ZipOutputStream zos, String className, byte[] bytecode) throws Exception {
-        writeClassToDisk(zos, className, bytecode, "");
-    }
-
-    public static void writeClassToDisk(String className, byte[] bytecode, String prependPath) throws Exception {
-        writeClassToDisk(null, className, bytecode, prependPath);
-    }
-    private static void writeClassToDisk(ZipOutputStream zos, String className, byte[] bytecode, String prependPath) throws Exception {
-        // Convert dotted class name to a path to a class file
-        String pathName = className.replace('.', '/').concat(".class");
-        if (prependPath.length() > 0) {
-            pathName = prependPath + "/" + pathName;
-        }
-        writeToDisk(zos, pathName, new ByteArrayInputStream(bytecode));
-    }
-
-    private static void writeToDisk(ZipOutputStream zos, String pathName, InputStream is) throws Exception {
-        if (DEBUG) {
-            System.out.println("ClassFileInstaller: Writing " + pathName);
-        }
-        if (zos != null) {
-            ZipEntry ze = new ZipEntry(pathName);
-            zos.putNextEntry(ze);
-            byte[] buf = new byte[1024];
-            int len;
-            while ((len = is.read(buf))>0){
-                zos.write(buf, 0, len);
-            }
-        } else {
-            // Create the class file's package directory
-            Path p = Paths.get(pathName);
-            if (pathName.contains("/")) {
-                Files.createDirectories(p.getParent());
-            }
-            // Create the class file
-            Files.copy(is, p, StandardCopyOption.REPLACE_EXISTING);
-        }
-        is.close();
-    }
-}