Skip to content

Commit 9beb716

Browse files
committed
[1.7.0-feature] ASM示例
1 parent f98cbd5 commit 9beb716

File tree

5 files changed

+54
-147
lines changed

5 files changed

+54
-147
lines changed

lib_bytecode/src/main/groovy/com.performance.optimize/ATransform.groovy

Lines changed: 26 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ package com.performance.optimize
33
import com.android.build.api.transform.*
44
import com.android.build.gradle.internal.pipeline.TransformManager
55
import groovy.io.FileType
6-
import org.ninetripods.lib_bytecode.asm.AClassVisitor
76
import org.ninetripods.lib_bytecode.BConstant
7+
import org.ninetripods.lib_bytecode.asm.demo.ATimeCostClassVisitor
88
import org.objectweb.asm.ClassReader
99
import org.objectweb.asm.ClassVisitor
1010
import org.objectweb.asm.ClassWriter
@@ -28,21 +28,43 @@ class ATransform extends Transform {
2828
File dir = dInput.file
2929
if (dir) {
3030
dir.traverse(type: FileType.FILES, nameFilter: ~/.*\.class/) { File file ->
31+
/**
32+
* 1、ClassReader: 它负责读取我们传入的类文件中的字节流数据,并提供解析流中包含的一切类属性信息的操作。
33+
* 2、ClassVisitor: 当在 accept 方法中 ClassVisitor 访问 ClassReader 时,ClassReader 便会先开始字节码的解析工作,并将保存在内存中的结果源源不断地通过调用各种 visitxxx 方法传入到 ClassVisitor 之中。
34+
* 3、ClassWriter: 是 ClassVisitor 的一个子类,它并不会储存信息,而是马上会将传入的信息转译成字节码,并在之后随时输出它们。
35+
*/
3136
ClassReader classReader = new ClassReader(file.bytes)
32-
ClassVisitor classVisitor = new AClassVisitor(BConstant.ASM9, new ClassWriter(ClassWriter.COMPUTE_MAXS))
37+
//ClassWriter.COMPUTE_MAXS 自动计算帧栈信息(操作数栈 & 局部变量表)
38+
//ClassVisitor classVisitor = new AClassVisitor(BConstant.ASM9, new ClassWriter(ClassWriter.COMPUTE_MAXS))
39+
ClassVisitor classVisitor = new ATimeCostClassVisitor(BConstant.ASM9, new ClassWriter(classReader,ClassWriter.COMPUTE_FRAMES))
40+
//访问者模式:将ClassVisitor传入ClassReader中,从而可以访问ClassReader中的私有信息;类似一个接口回调。
3341
classReader.accept(classVisitor, ClassReader.EXPAND_FRAMES)
3442
System.out.println("find class: " + file.name)
3543
}
3644
}
37-
3845
//处理完文件把输出传给下一个文件
3946
def dest = invocation.outputProvider.getContentLocation(dInput.name,
4047
dInput.contentTypes, dInput.scopes, Format.DIRECTORY)
4148
FileUtils.copyDirectory(dInput.file, dest)
4249
}
4350

4451
//jarInputs表示以jar包方式参与项目编译的文件
45-
input.jarInputs.each { JarInput jarInput -> }
52+
// input.jarInputs.each { JarInput jarInput ->
53+
// File jar = jarInput.file
54+
// if (jar) {
55+
// jar.traverse(type: FileType.FILES, nameFilter: ~/.*\.class/) { File file ->
56+
// ClassReader classReader = new ClassReader(file.bytes)
57+
// ClassVisitor classVisitor = new AClassVisitor(BConstant.ASM9, new ClassWriter(ClassWriter.COMPUTE_MAXS))
58+
// classReader.accept(classVisitor, ClassReader.EXPAND_FRAMES)
59+
// System.out.println("find class1: " + file.name)
60+
// }
61+
// }
62+
//
63+
// //处理完文件把输出传给下一个文件
64+
// def dest = invocation.outputProvider.getContentLocation(dInput.name,
65+
// dInput.contentTypes, dInput.scopes, Format.DIRECTORY)
66+
// FileUtils.copyDirectory(dInput.file, dest)
67+
// }
4668
}
4769
}
4870

lib_bytecode/src/main/java/org/ninetripods/lib_bytecode/asm/demo/AAdviceAdapter.kt

Lines changed: 0 additions & 133 deletions
This file was deleted.

lib_bytecode/src/main/java/org/ninetripods/lib_bytecode/asm/demo/ATimeCostClassVisitor.kt

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,11 +107,28 @@ class CustomAdviceAdapter(
107107
super.visitFieldInsn(opcode, owner, name, descriptor)
108108
}
109109

110+
override fun visitVarInsn(opcode: Int, `var`: Int) {
111+
super.visitVarInsn(opcode, `var`)
112+
}
113+
110114
override fun onMethodEnter() {
111115
log("onMethodEnter():")
116+
/**
117+
* @see FIELD_NAME_ADD
118+
* 1、访问FIELD_NAME_ADD变量
119+
*/
112120
mv.visitFieldInsn(GETSTATIC, owner, FIELD_NAME_ADD, "J")
121+
/**
122+
* 2、System.currentTimeMillis()
123+
*/
113124
mv.visitMethodInsn(INVOKESTATIC, "java/lang/System", "currentTimeMillis", "()J", false)
125+
/**
126+
* 上述1、2步的值进行相减
127+
*/
114128
mv.visitInsn(LSUB)
129+
/**
130+
* @see FIELD_NAME_ADD 将相减的结果重新赋值给变量FIELD_NAME_ADD
131+
*/
115132
mv.visitFieldInsn(PUTSTATIC, owner, FIELD_NAME_ADD, "J")
116133
}
117134

lib_bytecode/src/main/java/org/ninetripods/lib_bytecode/asm/demo/ProduceClz.kt

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ import org.objectweb.asm.ClassWriter
77
import org.objectweb.asm.Opcodes.*
88

99
/**
10-
* ASM使用示例
10+
* ASM自动生成代码示例
1111
*/
1212
object ProduceClz {
1313

@@ -22,20 +22,20 @@ object ProduceClz {
2222

2323
/**
2424
* 产生类
25-
package pkg;
26-
public interface Comparable extends Mesurable {
27-
int LESS = -1;
28-
int EQUAL = 0;
29-
int GREATER = 1;
30-
int compareTo(Object o);
31-
}
25+
package pkg;
26+
public interface Comparable extends Measurable {
27+
int LESS = -1;
28+
int EQUAL = 0;
29+
int GREATER = 1;
30+
int compareTo(Object o);
31+
}
3232
*/
3333
private fun produceClass() {
3434
val cw = ClassWriter(0)
3535
//access:修饰字段
3636
//signature: 泛型
3737
cw.visit(V1_8, ACC_PUBLIC + ACC_ABSTRACT + ACC_INTERFACE,
38-
"pkg/Comparable", null, "java/lang/Object", arrayOf("pkg/Mesurable"))
38+
"pkg/Comparable", null, "java/lang/Object", arrayOf("pkg/Measurable"))
3939
cw.visitField(ACC_PUBLIC + ACC_FINAL + ACC_STATIC, "LESS", "I",
4040
null, -1).visitEnd()
4141
cw.visitField(ACC_PUBLIC + ACC_FINAL + ACC_STATIC, "EQUAL", "I",
@@ -46,6 +46,6 @@ object ProduceClz {
4646
cw.visitMethod(ACC_PUBLIC + ACC_ABSTRACT, "compareTo",
4747
"(Ljava/lang/Object;)I", null, null).visitEnd()
4848
cw.visitEnd()
49-
FileUtil.byte2File("AndroidStudy/build/demo/GenerAuto.java",cw.toByteArray())
49+
FileUtil.byte2File("lib_bytecode/files/Comparable.class",cw.toByteArray())
5050
}
5151
}

lib_bytecode/src/main/java/org/ninetripods/lib_bytecode/util/FileUtil.kt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ object FileUtil {
1515
if (file.exists()) {
1616
file.delete()
1717
} else {
18+
file.parentFile.mkdir()
1819
file.createNewFile()
1920
}
2021

0 commit comments

Comments
 (0)