我如何将那个 framenode 插入到字节码中?
FRAME FULL [java/lang/String [C java/lang/String T I I [C] []
我的第一个尝试是:
mn.instructions.insertBefore(random, new FrameNode(Opcodes.F_FULL, 1 /**IDK**/,
new Object[]{ "java/lang/String", "[C", "java/lang/String", "T", "I", "I", "[C]" },
1/**IDK**/, new Object[] { "[C]","[]" }));
效果不佳。输出:
FRAME FULL [[java/lang/String] [java/lang/String]
最佳答案
栈帧由一些局部变量和操作数栈上的一些值组成。您要重现的内容显然是将该状态转换为形式为人类可读字符串的结果
FRAME FULL [<em>list of local variables types</em>] [<em>list of operand stack time types</em>]
您要做的第一件事是从输出格式中识别括号,这需要理解包含的类型签名,作为以左括号开头的签名,如 [C
表示数组类型,即字符数组。换句话说,一些左括号是类型签名的一部分,其他是输出格式的一部分,而右括号始终是输出格式的一部分,从不出现在类型签名中。
然后,当您确定了两组中的类型签名后,提供适当的局部变量和操作数堆栈项计数。在你的情况下你有:
FRAME FULL // frame type
[ // start local variables
java/lang/String
[C
java/lang/String
T
I
I
[C
] // seven local variables specified
[ // start of operand stack
] // empty operand stack
但随后您必须开始考虑类型项的含义,不幸的是,它无法从打印输出中推导出来,仅仅重现相同的打印输出并不一定意味着正确的代码。
即项目 T
和 I
可以引用具有完整限定名称的类 T
和 I
,分别在这种情况下传递 "T"
和 "I"
至 FrameNode
会是正确的。然而,它们更可能指的是非类堆栈帧类型 ‹top› 和 int
必须使用预定义的 Integer
来引用它ASM 中的常量:
new FrameNode(Opcodes.F_FULL, 7, new Object[] {
"java/lang/String", "[C", "java/lang/String",
Opcodes.TOP, Opcodes.INTEGER, Opcodes.INTEGER, "[C" }, 0, new Object[0]);
关于java - 使用 ASM 插入 FrameNode,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36939802/