BTrace dynamic tracking technology

Direct operation bytecode

Java is a software developer can read the language, class JVM bytecode is able to read the language, class bytecode JVM will eventually be interpreted into machine language can read. Whatever the language, all human creation. So, in theory (actually true) who can read any of these languages, since it can read, modify naturally. As long as we wish, we can skip the Java compiler, byte code directly to write the file, but this is not in line with the times nothing, after all, the beginning of high-level language design is to serve our humanity, its development efficiency than a machine many high language.

For humans, readable byte code file is far higher Java code. Nevertheless, there are still some outstanding programmers have created a framework that can be used to directly edit the byte code, provides the interface allows us to easily operate the bytecode file by injecting modify the class progresses, creating a new dynamic class, etc. operations. The most famous of the frame should be the ASM, cglib, Spring Framework for other operations on the byte code based on ASM.

We all know, Spring's AOP is, Spring dynamically creates dynamic proxy implementation at runtime proxy class, proxy class is referenced in the proxy class, some mysterious operation before and after the execution method based on proxy. Well, Spring is how to create a proxy class at runtime it? The beauty of dynamic proxies, is that we do not need to be manually for each agent class to write the proxy class code that will create a class dynamically at runtime as required Spring, the process here is not to write Java file created by a string then compiled into class files, and then loaded. Spring will direct "create" a class file and then load, create tools class file is the ASM.

Here, we know the ASM framework with direct manipulation class file, add a piece of print logs in the class code, and then call retransformClasses it.

BTrace

Up to now, we are all staying at the level of theoretical description. So how to achieve it? First look at a few questions:

  1. In our project, who will do this to find the byte code, modify the byte code, and then reTransform action it? We are not prophets, can not know the future is not likely to encounter this problem at the beginning of the article. Considering the price, we could not have developed in each project to make these changes for some special byte code, reload code byte code.
  2. If the JVM is not local, remote in it?
  3. If even the ASM will not use it? Can some of the more common and more "fool" Some.

Fortunately, because of the existence of BTrace, we do not have to write their own set of such tool. BTrace What is it? BTrace already open, very brief description of the project:

A safe, dynamic tracing tool for the Java platform.

BTrace tool is based on a secure Java language, providing dynamic tracking services. BTrace based ASM, Java Attach Api, Instruments developed to provide users with a lot of notes. Rely on these notes, we can write BTrace script (simple Java code) to achieve the results we want, without having to operate deep in the ASM bytecode can not extricate themselves.

Look at a simple example of BTrace official: block all java.io package to all class methods starting read, print the class name, method name and parameter name. When the program IO load is relatively high, you can see from the information output of which is caused by the class, it is not very convenient?


package com.sun.btrace.samples;

import com.sun.btrace.annotations.*;
import com.sun.btrace.AnyType;
import static com.sun.btrace.BTraceUtils.*; /** * This sample demonstrates regular expression * probe matching and getting input arguments * as an array - so that any overload variant * can be traced in "one place". This example * traces any "readXX" method on any class in * java.io package. Probed class, method and arg * array is printed in the action. */ @BTrace public class ArgArray { @OnMethod( clazz="/java\\.io\\..*/", method="/read.*/" ) public static void anyRead(@ProbeClassName String pcn, @ProbeMethodName String pmn, AnyType[] args) { println(pcn); println(pmn); printArray(args); } } 

Let's look at another example: every 2 seconds to print off the number of threads currently created before.


package com.sun.btrace.samples;

import com.sun.btrace.annotations.*;
import static com.sun.btrace.BTraceUtils.*;
import com.sun.btrace.annotations.Export; /** * This sample creates a jvmstat counter and * increments it everytime Thread.start() is * called. This thread count may be accessed * from outside the process. The @Export annotated * fields are mapped to jvmstat counters. The counter * name is "btrace." + <className> + "." + <fieldName> */ @BTrace public class ThreadCounter { // create a jvmstat counter using @Export @Export private static long count; @OnMethod( clazz="java.lang.Thread", method="start" ) public static void onnewThread(@Self Thread t) { // updating counter is easy. Just assign to // the static field! count++; } @OnTimer(2000) public static void ontimer() { // we can access counter as "count" as well // as from jvmstat counter directly. println(count); // or equivalently ... println(Counters.perfLong("btrace.com.sun.btrace.samples.ThreadCounter.count")); } } 

Read the above usage is not inspire? I could not help but come up many ideas. Such as viewing HashMap when it will trigger rehash, and this time the container how many elements and so on.

With BTrace, problems at the beginning of the article can be the perfect solution. As BTrace which specific functions, how to write a script, Git on BTrace these projects have a lot of explanation and example, the use of online presentation BTrace article is countless, not repeat them here.

We understand the principle, but also easy to use tool support, and the rest is to play our creativity, and can only reasonably use in the appropriate scene.

Since BTrace can solve all the problems we mentioned above, the BTrace architecture is what is it?

BTrace are the following modules:

  1. BTrace script: use BTrace defined annotation, we can easily develop scripts as needed.
  2. Compiler: The BTrace script compiled into BTrace class file.
  3. Client: send the file to the class Agent.
  4. Agent: Java-based Attach Api, Agent can be dynamically attached to the JVM a run, and then open a BTrace Server, the receiving client sent me BTrace script; parsing the script, and then you want to modify the class according to the script of the rules; modify the word after the code section, call Java Instrument of reTransform interface takes effect on the behavior of objects and make modifications.

BTrace entire architecture is as follows:

BTrace workflow

BTrace workflow

 

BTrace eventually replaced by Instruments to achieve the class. As noted earlier, for security reasons, Instruments many restrictions exist on the use, BTrace no exception. BTrace the JVM is "read-only", thus limiting BTrace script is as follows:

  1. Not allowed to create objects
  2. Not allowed to create an array
  3. Not allowed to throw an exception
  4. Not allowed to catch abnormalities
  5. Do not allow to call other object or class methods, static methods only allow calls com.sun.btrace.BTraceUtils provided (some data processing and information output means)
  6. It is not allowed to change the properties of the class
  7. Does not allow member variables and methods, allows only static public void method
  8. It does not allow inner classes, nested classes
  9. The method does not allow synchronization and sync blocks
  10. It does not allow circulation
  11. Do not allow to inherit from other classes (of course, except java.lang.Object)
  12. Do not allow to implement the interface
  13. Not allowed assert
  14. Class objects are not allowed

So many restrictions, in fact, can be understood. BTrace to do that, although modified bytecode, but in addition to the information required output, the normal operation of the entire program is not affected.

 

Original: https: //tech.meituan.com/2019/02/28/java-dynamic-trace.html

Guess you like

Origin www.cnblogs.com/yx88/p/11291655.html