1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 import java.lang.reflect.Method; 18 import java.lang.reflect.InvocationTargetException; 19 20 import dalvik.system.PathClassLoader; 21 22 // ClassLoader not delegating for non java. packages. 23 class DelegateLastPathClassLoader extends PathClassLoader { 24 DelegateLastPathClassLoader(String dexPath, ClassLoader parent)25 public DelegateLastPathClassLoader(String dexPath, ClassLoader parent) { 26 super(dexPath, parent); 27 } 28 29 @Override loadClass(String name, boolean resolve)30 protected Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException { 31 if (!name.startsWith("java.")) { 32 try { 33 return findClass(name); 34 } catch (ClassNotFoundException ignore) { 35 // Ignore and fall through to parent class loader. 36 } 37 } 38 return super.loadClass(name, resolve); 39 } 40 } 41 42 public class Main { 43 classFromDifferentLoader()44 private static Class<?> classFromDifferentLoader() throws Exception { 45 final String DEX_FILE = System.getenv("DEX_LOCATION") + "/612-jit-dex-cache-ex.jar"; 46 ClassLoader loader = new DelegateLastPathClassLoader(DEX_FILE, Main.class.getClassLoader()); 47 return loader.loadClass("LoadedByAppClassLoader"); 48 } 49 main(String[] args)50 public static void main(String[] args) throws Exception { 51 System.loadLibrary(args[0]); 52 Class<?> cls = classFromDifferentLoader(); 53 Method m = cls.getDeclaredMethod("letMeInlineYou", A.class); 54 B b = new B(); 55 // Invoke the method enough times to get an inline cache and get JITted. 56 for (int i = 0; i < 10000; ++i) { 57 m.invoke(null, b); 58 } 59 m = cls.getDeclaredMethod("areYouB", null); 60 ClassLoader loader = (ClassLoader) m.invoke(null); 61 if (loader != cls.getClassLoader()) { 62 throw new Error("Wrong class loader"); 63 } 64 } 65 ensureJitCompiled(Class<?> cls, String method_name)66 public static native void ensureJitCompiled(Class<?> cls, String method_name); 67 } 68