am cc5e69e4: Inject anonymous inner classes of injected classes [DO NOT MERGE]
* commit 'cc5e69e4fed8bb797dc3f83c1de32eaf4a52f324': Inject anonymous inner classes of injected classes [DO NOT MERGE]
This commit is contained in:
@@ -24,9 +24,11 @@ import java.io.ByteArrayOutputStream;
|
|||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.HashSet;
|
import java.util.HashSet;
|
||||||
|
import java.util.ListIterator;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Map.Entry;
|
import java.util.Map.Entry;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
@@ -86,7 +88,23 @@ public class AsmGenerator {
|
|||||||
public AsmGenerator(Log log, String osDestJar, ICreateInfo createInfo) {
|
public AsmGenerator(Log log, String osDestJar, ICreateInfo createInfo) {
|
||||||
mLog = log;
|
mLog = log;
|
||||||
mOsDestJar = osDestJar;
|
mOsDestJar = osDestJar;
|
||||||
mInjectClasses = createInfo.getInjectedClasses();
|
ArrayList<Class<?>> injectedClasses =
|
||||||
|
new ArrayList<Class<?>>(Arrays.asList(createInfo.getInjectedClasses()));
|
||||||
|
// Search for and add anonymous inner classes also.
|
||||||
|
ListIterator<Class<?>> iter = injectedClasses.listIterator();
|
||||||
|
while (iter.hasNext()) {
|
||||||
|
Class<?> clazz = iter.next();
|
||||||
|
try {
|
||||||
|
int i = 1;
|
||||||
|
while(i < 100) {
|
||||||
|
iter.add(Class.forName(clazz.getName() + "$" + i));
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
} catch (ClassNotFoundException ignored) {
|
||||||
|
// Expected.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mInjectClasses = injectedClasses.toArray(new Class<?>[0]);
|
||||||
mStubMethods = new HashSet<String>(Arrays.asList(createInfo.getOverriddenMethods()));
|
mStubMethods = new HashSet<String>(Arrays.asList(createInfo.getOverriddenMethods()));
|
||||||
|
|
||||||
// Create the map/set of methods to change to delegates
|
// Create the map/set of methods to change to delegates
|
||||||
@@ -290,13 +308,7 @@ public class AsmGenerator {
|
|||||||
* e.g. it returns something like "com/foo/OuterClass$InnerClass1$InnerClass2.class"
|
* e.g. it returns something like "com/foo/OuterClass$InnerClass1$InnerClass2.class"
|
||||||
*/
|
*/
|
||||||
private String classToEntryPath(Class<?> clazz) {
|
private String classToEntryPath(Class<?> clazz) {
|
||||||
String name = "";
|
return classNameToEntryPath(clazz.getName());
|
||||||
Class<?> parent;
|
|
||||||
while ((parent = clazz.getEnclosingClass()) != null) {
|
|
||||||
name = "$" + clazz.getSimpleName() + name;
|
|
||||||
clazz = parent;
|
|
||||||
}
|
|
||||||
return classNameToEntryPath(clazz.getCanonicalName() + name);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -136,6 +136,8 @@ public final class CreateInfo implements ICreateInfo {
|
|||||||
ICreateInfo.class,
|
ICreateInfo.class,
|
||||||
CreateInfo.class,
|
CreateInfo.class,
|
||||||
LayoutlibDelegate.class,
|
LayoutlibDelegate.class,
|
||||||
|
InjectMethodRunnable.class,
|
||||||
|
InjectMethodRunnables.class,
|
||||||
/* Java package classes */
|
/* Java package classes */
|
||||||
AutoCloseable.class,
|
AutoCloseable.class,
|
||||||
Objects.class,
|
Objects.class,
|
||||||
@@ -304,4 +306,3 @@ public final class CreateInfo implements ICreateInfo {
|
|||||||
InjectMethodRunnables.CONTEXT_GET_FRAMEWORK_CLASS_LOADER);
|
InjectMethodRunnables.CONTEXT_GET_FRAMEWORK_CLASS_LOADER);
|
||||||
}};
|
}};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -85,6 +85,12 @@ public interface ICreateInfo {
|
|||||||
Map<String, InjectMethodRunnable> getInjectedMethodsMap();
|
Map<String, InjectMethodRunnable> getInjectedMethodsMap();
|
||||||
|
|
||||||
abstract class InjectMethodRunnable {
|
abstract class InjectMethodRunnable {
|
||||||
public abstract void generateMethods(ClassVisitor cv);
|
/**
|
||||||
|
* @param cv Must be {@link ClassVisitor}. However, the param type is object so that when
|
||||||
|
* loading the class, ClassVisitor is not loaded. This is because when injecting
|
||||||
|
* CreateInfo in LayoutLib (see {@link #getInjectedClasses()}, we don't want to inject
|
||||||
|
* asm classes also, but still keep CreateInfo loadable.
|
||||||
|
*/
|
||||||
|
public abstract void generateMethods(Object cv);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -30,7 +30,9 @@ public class InjectMethodRunnables {
|
|||||||
public static final ICreateInfo.InjectMethodRunnable CONTEXT_GET_FRAMEWORK_CLASS_LOADER
|
public static final ICreateInfo.InjectMethodRunnable CONTEXT_GET_FRAMEWORK_CLASS_LOADER
|
||||||
= new InjectMethodRunnable() {
|
= new InjectMethodRunnable() {
|
||||||
@Override
|
@Override
|
||||||
public void generateMethods(ClassVisitor cv) {
|
public void generateMethods(Object classVisitor) {
|
||||||
|
assert classVisitor instanceof ClassVisitor;
|
||||||
|
ClassVisitor cv = (ClassVisitor) classVisitor;
|
||||||
// generated by compiling the class:
|
// generated by compiling the class:
|
||||||
// class foo { public ClassLoader getFrameworkClassLoader() { return getClass().getClassLoader(); } }
|
// class foo { public ClassLoader getFrameworkClassLoader() { return getClass().getClassLoader(); } }
|
||||||
// and then running ASMifier on it:
|
// and then running ASMifier on it:
|
||||||
|
|||||||
Reference in New Issue
Block a user