Tag: 字节码操作

Java字节码操作和JavareflectionAPI?

我最近遇到了“字节码操作”这个术语(为了研究这个问题,我偶然看到了字节码提供程序,同时在使用Hibernate的应用程序中看到了日志)。 我也知道(有点)Java Reflection API。 这两个概念是否相似? 它们之间有什么区别? 什么时候用哪个?

在try-finally块中嵌入方法的现有代码(2)

前段时间,我在try-finally块中嵌入了一个方法的现有代码,如何使用ASM将方法的主体包装在try-finally块中。 解决方案是在visitCode()中visitCode()方法体开头的try块的标签,并在visitCode()访问带有返回操作码的指令时完成try-finally块。 我知道如果方法没有返回指令,如果方法总是离开并且exception,则解决方案将不起作用。 虽然,我发现前一种解决方案有时也不适用于带有返回指令的方法。 如果方法有多个返回指令,它将无法工作。 原因是它生成了无效的字节码,因为在方法的开头添加了一个try-finally块,但是完成了多个try-finally块。 通常(但可能取决于javac编译器),字节码方法包含单个返回指令,并且所有返回路径通过跳转在该指令处结束。 但是,使用Eclipse编译以下代码将导致字节代码带有两个返回指令: public boolean isEven(int x) { return x % 2 == 0; } 用Eclipse编译的字节代码: 0: iload_1 1: iconst_2 2: irem 3: ifne 8 6: iconst_1 7: ireturn // javac compilation: goto 9 8: iconst_0 9: ireturn 因此,我想知道包装方法代码的整个代码的正确方法是什么。

如何使用gradle复制classes文件夹中的资源文件?

环境 我正在使用需要字节码检测的第三方库。 执行字节码检测的工具需要一些描述文件,这些文件必须与编译的.class文件位于相同的文件夹结构中。 这些文件只在编译时才需要。 问题 我以为gradle会将所有文件(资源和类)暂时放在同一个文件夹中,然后从该文件夹创建一个jar。 但是在组装jar之前,gradle似乎有两个不同的资源和类文件位置。 就像之前提到的第三方代码检测工具一样,需要在类文件结构中使用相同文件夹结构中的描述文件。 题 简单地说:我该如何解决这个问题? 思路 将描述文件放在src/main/java 。 不是很“干净”,但可能是一个解决方案。 遗憾的是,gradle会忽略这些文件。 我试图以某种方式包括它们,但还没有让它工作。 暂时将描述文件复制到正确的位置。 也不是一个非常“干净”的方式

JAXB是否使用字节码检测?

我工作的人注意到(在堆栈跟踪中)当使用-javaagent运行jvm时:spring-instrumentation.jar我的JAXB注释类中有一些我们没有编写的奇怪的新方法:例如SomeJaxbAnnotatedClass $ JaxbAccessorM_getFields_setFields_java_util_Set.get 这是否意味着jaxb在可用时使用字节码检测? 我在哪里可以阅读有关此function的更多信息 谢谢,Yuval

在已编译的类中更改字符串常量

我需要在已部署的Java程序中更改字符串常量,即编译的.class -files中的值。 它可以重新启动,但不容易重新编译(虽然如果这个问题没有答案,这是一个不方便的选择)。 这可能吗? 更新:我只是用hex编辑器查看了文件,看起来我可以轻松地在那里更改字符串。 这会起作用,即不会使文件的某种签名无效吗? 旧字符串和新字符串都是字母数字,如果需要,可以是相同的长度。 更新2:我修复了它。 因为我需要更改的特定类非常小并且在新版本的项目中没有更改,所以我可以编译它并从那里获取新类。 出于教育目的,仍然对不涉及编译的答案感兴趣。

将字段添加到使用Javassist创建的Proxy类

我正在使用Javassist ProxyFactory创建一个Proxy类,其代码如下: ProxyFactory factory = new ProxyFactory(); factory.setSuperclass(entity.getClass()); factory.setInterfaces(new Class[] { MyCustomInterface.class }); ….. Class clazz = factory.createClass(); Object result = clazz.newInstance(); 问题是我还需要在类中添加一个字段。 但是,如果我做CtClass proxy = ClassPool.getDefault().get(clazz.getName()); 它会引发NotFoundException 如何添加使用createClass创建的类的字段? 有没有更好的方法来做我想做的事情?

在编译的Java类中重写方法调用

我希望在解析编译的类文件时,在方法体内调用anther类来替换对给定类的调用… 换句话说,是否有一种方法可以检测方法中给定类的用法,并使用类似javaassist的方法替换方法的那一部分。 例如..如果我有编译版本的 class A { public int m() { int i = 2; B.multiply(i,i); return i; } } 有没有一种方法可以检测B的使用,然后改变要执行的代码 class A { public int m() { int i = 2; C.divide(i,i); return i; } } 我知道另一种方法是编写一个解析器来grep源文件以供使用,但我更喜欢更优雅的解决方案,例如使用reflection生成新的编译类文件。 有什么想法吗 ?

Javassist:重新创建一个类 – 先删除,还是解冻()并修改?

我使用Javassist创建一个类。 在测试套件中,当第二个测试尝试创建相同的类时,它在pool.makeClass( … )处失败,因为该类被冻结(即已经通过toClass()创建。 克服这个问题的方法是什么? 理想情况下,第一个测试应该以某种方式删除类 – 也许从类加载器中卸载 – 但是当我在JLS中读取时 ,卸载操作是不可靠的。 因此,或许解决方法是检查创建代码的类是否存在,如果存在,则defrost()它,删除所有成员等,然后重新创建它。 还有其他想法吗? 或者是否有一些通过Javassist删除类的可靠方法?

Java字节码操作库建议

我正在寻找一个维护良好的Java字节码操作库和一个直观的API。 那里似乎有很多人。 有关哪些尝试的建议?

是否有java类文件/字节码编辑器来编辑指令?

是否有用于编辑java类文件的实用程序(或eclipse插件)? 我想操纵java类文件的字节码而不重新编译它也没有完整的构建路径。 例如,重命名方法,添加/删除指令,更改常量等。 我发现的唯一工具是: 但是它的function非常有限( 例如,重命名事物和操纵指令是不可能的 )。 jbe不保存更改(可能因为类validation失败 – 在我进行任何更改之前,尽管类运行完美) (jbe最初有一个类路径问题,将jbe.bat文件的类路径添加到了帮助中)