Path: blob/master/test/jdk/java/beans/PropertyEditor/MemoryClassLoader.java
41149 views
/*1* Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223import java.io.ByteArrayOutputStream;24import java.net.URI;25import java.net.URISyntaxException;26import java.util.ArrayList;27import java.util.HashMap;28import java.util.List;29import java.util.Map;30import javax.tools.FileObject;31import javax.tools.ForwardingJavaFileManager;32import javax.tools.JavaCompiler;33import javax.tools.JavaFileManager;34import javax.tools.JavaFileObject.Kind;35import javax.tools.SimpleJavaFileObject;36import javax.tools.ToolProvider;3738public final class MemoryClassLoader extends ClassLoader {39private final JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();40private final MemoryFileManager manager = new MemoryFileManager(this.compiler);4142public Class<?> compile(String name, String content) {43compile(new Source(name, content));44try {45return findClass(name);46}47catch (ClassNotFoundException exception) {48throw new Error(exception);49}50}5152public void compile(Source... sources) {53List<Source> list = new ArrayList<Source>();54if (sources != null) {55for (Source source : sources) {56if (source != null) {57list.add(source);58}59}60}61synchronized (this.manager) {62this.compiler.getTask(null, this.manager, null, null, null, list).call();63}64}6566@Override67protected Class<?> findClass(String name) throws ClassNotFoundException {68synchronized (this.manager) {69Output mc = this.manager.map.remove(name);70if (mc != null) {71byte[] array = mc.toByteArray();72return defineClass(name, array, 0, array.length);73}74}75return super.findClass(name);76}7778private static final class MemoryFileManager extends ForwardingJavaFileManager<JavaFileManager> {79private final Map<String, Output> map = new HashMap<String, Output>();8081MemoryFileManager(JavaCompiler compiler) {82super(compiler.getStandardFileManager(null, null, null));83}8485@Override86public Output getJavaFileForOutput(Location location, String name, Kind kind, FileObject source) {87Output mc = this.map.get(name);88if (mc == null) {89mc = new Output(name);90this.map.put(name, mc);91}92return mc;93}94}9596private static class MemoryFileObject extends SimpleJavaFileObject {97MemoryFileObject(String name, Kind kind) {98super(toURI(name, kind.extension), kind);99}100101private static URI toURI(String name, String extension) {102try {103return new URI("mfm:///" + name.replace('.', '/') + extension);104}105catch (URISyntaxException exception) {106throw new Error(exception);107}108}109}110111private static final class Output extends MemoryFileObject {112private final ByteArrayOutputStream baos = new ByteArrayOutputStream();113114Output(String name) {115super(name, Kind.CLASS);116}117118byte[] toByteArray() {119return this.baos.toByteArray();120}121122@Override123public ByteArrayOutputStream openOutputStream() {124this.baos.reset();125return this.baos;126}127}128129public static final class Source extends MemoryFileObject {130private final String content;131132Source(String name, String content) {133super(name, Kind.SOURCE);134this.content = content;135}136137@Override138public CharSequence getCharContent(boolean ignore) {139return this.content;140}141}142}143144145