Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Javaagent reports "redefineClasses is not supported in this environment"

I'm newbie on java agents. I created a simple HotswapAgent class (sniffing from Play! Framework):

  public class HotswapAgent {
        static Instrumentation instrumentation;
        public static boolean enabled = false;

        public static void premain(String agentArgs, Instrumentation instrumentation) 
        {
             HotswapAgent.instrumentation = instrumentation;
             HotswapAgent.enabled = true;
        }

        public static void reload(ClassDefinition... definitions) 
                             throws UnmodifiableClassException, ClassNotFoundException                         
        {
            instrumentation.redefineClasses(definitions);
        }
    } 

With this manifest:

Manifest-Version: 1.0
Premain-Class: path.to.HotswapAgent
Can-Redefine-Classes: true

And I try to reload a new class definition, in this way:

CtClass modelClass = .... 

...

byte [] bcode = modelClass.toBytecode();
Class c = modelClass.toClass();
modelClass.defrost();

ClassDefinition cdef = new ClassDefinition(c, bcode);
HotswapAgent.reload(cdef);

All this classes are in a jar, and finally I obtain this error (on reload() call):

redefineClasses is not supported in this environment

But in Manifest is declared Can-Redefine-Classes: true.

The JVM is standard MacOS X Java 1.6 VM. This JVM works good with JRebel, that uses the same agent mechanism.

What's wrong?

like image 368
g.annunziata Avatar asked Oct 11 '12 16:10

g.annunziata


1 Answers

According to the documentation:

Optional Functionality: might not be implemented for all virtual machines. The following capability (as returned by GetCapabilities) must be true to use this function.

You can try to addCapability to check if there is a problem with the manifest declaration.

Here is an example of addCapability in runtime.

like image 74
ssedano Avatar answered Nov 15 '22 10:11

ssedano