Arthas: 增加 retransform 命令

Created on 4 Jan 2021  ·  9Comments  ·  Source: alibaba/arthas

目前 redefine功能会和 trace/watch/ jad 等功能冲突。

reset命令对redefine的类无效。如果想重置,需要redefine原始的字节码。

redefine命令和jad/watch/trace/monitor/tt等命令会冲突。执行完redefine之后,如果再执行上面提到的命令,则会把redefine的字节码重置。
原因是jdk本身redefine和Retransform是不同的机制,同时使用两种机制来更新字节码,只有最后修改的会生效。

尽管是因为jdk自身机制问题,但考虑基于retransform重新实现一个redefine功能。 新的实现,可以让 redefine 和 watch/jad 等功能不冲突。

现在问题是:

一、是否直接以 retransform 的方式重新实现 redefine命令?

  • 如果直接替换掉原来的 redefine 命令,那么是否还有必要提供旧的 redefine 功能?
  • 旧的 redefine 命令改为叫什么?
  • 用户是否会有疑惑?因为原生的jdk redefine 和 retransform 是两套机制

二、是否使用新命令名?

  • 新命令的名字叫什么?比如 update / replace/ redefine2 等
disscuss

Most helpful comment

我觉得可以搞个新命令就叫retransform(虽然不太好记),然后把原来的redefine命令加上@Hidden隐藏起来弃用掉,文档中也去掉redefine命令。当用户使用旧的redefine命令时输出一段警告,提示用户此命令可能带来的问题并链接到某个 issue 或 wiki 中,并且推荐用户使用retransform。这样新旧命令都能用,而且还能和 JDK 自身的机制名称保持一致

All 9 comments

目前的 watch/trace/monitor/tt 是针对原始的字节码进行增强, 如果redefine之后缓存一份字节码,后续的 watch/trace/monitor/tt 基于这个来做呢?

只是解决redefine 和 watch/jad 等功能的冲突?

目前的 watch/trace/monitor/tt 是针对原始的字节码进行增强, 如果redefine之后缓存一份字节码,后续的 watch/trace/monitor/tt 基于这个来做呢?

这个容易起冲突。 watch 和 redefine 命令可能多次执行,并且执行的顺序也不一样。

只是解决redefine 和 watch/jad 等功能的冲突?

现在一个常见的问题,就是 redefine 之后,用户再用 jad 来确认是否生效,结果就失效了。

我觉得可以搞个新命令就叫retransform(虽然不太好记),然后把原来的redefine命令加上@Hidden隐藏起来弃用掉,文档中也去掉redefine命令。当用户使用旧的redefine命令时输出一段警告,提示用户此命令可能带来的问题并链接到某个 issue 或 wiki 中,并且推荐用户使用retransform。这样新旧命令都能用,而且还能和 JDK 自身的机制名称保持一致

目前的 watch/trace/monitor/tt 是针对原始的字节码进行增强, 如果redefine之后缓存一份字节码,后续的 watch/trace/monitor/tt 基于这个来做呢?

这个容易起冲突。 watch 和 redefine 命令可能多次执行,并且执行的顺序也不一样。

每次redefine生成一个快照/版本信息, 其他非redefine优先取快照,没有就取jvm的字节码. reset可以针对版本恢复

不过这种场景有一个缺陷就是,字节码的存储问题

增加了retransform 命令,测试包:

arthas-bin.zip

参考: https://github.com/alibaba/arthas/blob/master/site/src/site/sphinx/retransform.md


更新了下,打印 TransformCount,表示被触发的次数

@hengyunabc 测试了三次 最后一次故意增加field retransform -l 也会存在 ,jad 反编译时最后一次的增加field的代码 这个有点奇怪。

@hengyunabc 测试了三次 最后一次故意增加field retransform -l 也会存在 ,jad 反编译时最后一次的增加field的代码 这个有点奇怪。

这里好像没有太好的办法。因为只能先记录,再触发 retransform 。尽管 retransform 可能失败。

Was this page helpful?
0 / 5 - 0 ratings