Question

I am working with asm (here the docs http://asm.ow2.org/asm40/javadoc/user/), more specifically I am trying to dynamic instrument some code. My problem is that I don't know how and if I am able through what offers asm to read the actual variables of the instrumented code. i.e I am able to retrieve the LocalVariableNode of the corresponding stores that I compute in the instrumented code, at this point I would like to know the value I am storing (not just the type which can be easily taken with methods provided in LocalVariableNode class but the actual value (if it is a boolean I would like to get true or false)). Similarly it would be interesting to get the value when a load bytecode instruction happens.

Hope I have been specific enough, I checked if something similar has already been asked but seemed it hasn't.

Thanks in advance. Nicolas

Était-ce utile?

La solution

I did something similar a while before, kind of forgetting the detail, but I think I can give you some pointers on that.

Of course, like creichen said in his answer, it's impossible to get the exact value associate with the LocalVariable, but it's possible to sort of get the whole Abstract Syntax Tree of the bytecode and get know what kind possible value is going to assign to that LocalVariable at some point of the program.

For each LocalVariableNode is assigned with an index, so in bytecode, the value is not statically associate with the LocalVariable because Java allow mutable on that. So in order to know the value associate with the LocalVariable at some point of the program, you have to basically simulate the stack execution of the bytecode (JVM) and then have a table to trace the value assignment for each LocalVariable. The stack execution is through simulate the instruction (Opcode), basically the bytecode. And then you gradually build up a Tree structure to store the Abstract Syntax Tree.

I do have a code for that, but pretty ugly, you can take a look: https://github.com/davidlau325/BytecodeASTGenerator

Autres conseils

What you are asking for is impossible in general. A boolean store (astore, bastore, putfield, putstatic) pops off the top-of-stack value and stores it in the specified location. However, this top-of-stack value can be the result of any arbitrary computation. For example:

boolean b = MyClass.decideWhetherProgramPHalts();

So you're depending on a method call that may or may not even terminate. Your bytecode might look something like this (just briefly from memory):

invokestatic "MyClass.decideWhetherProgramPHalts()Z"
istore 1

So the value that gets stored comes in from the previous invokestatic, which can be anything from a simple return true to a network call to some attempt at solving a problem that we know to be undecidable.

If you need an analysis that can tell you true or false or I-do-not-know, you can try static analysis frameworks such as WALA (http://wala.sourceforge.net). But be warned that most of the time you'll get I-do-not-know. Here are the main techniques you may want to look into:

  1. Dataflow Analysis
  2. Abstract Interpretation

Note that you may be able to hack up a trivial dataflow analysis yourself, by visiting the instructions in your MethodNode, but your recall is going to be inferior to using existing tools (unless you pour a lot of work into this).

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top