1

有人真的有任何使用 OSGi Weaving Hook 服务的例子吗?
我正在对其进行一些测试。但遇到一些问题。我要做的是修改Bundle中类的字节码。例如:Bundle A 注册 Weaving Hook Service 并使用 ASM 修改 Bundle B 中的类。

套装 A:

import org.apache.felix.ipojo.annotations.Component;
import org.apache.felix.ipojo.annotations.Instantiate;
import org.apache.felix.ipojo.annotations.Provides;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassVisitor;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.Opcodes;
import org.osgi.framework.hooks.weaving.WeavingHook;
import org.osgi.framework.hooks.weaving.WovenClass;

 @Component
 @Provides
 @Instantiate
 public class TWMethodCallsHook implements WeavingHook {

public void weave(WovenClass wovenClass) {
    // TODO Auto-generated method stub
        if(inInstrumented(wovenClass.getClassName())){
            
            System.out.println("Instrumenting{}");
            System.out.println(wovenClass.getBundleWiring().getBundle().getBundleId());
            final ClassReader cr=new ClassReader(wovenClass.getBytes());
            final ClassWriter cw=new ClassWriter(cr,ClassWriter.COMPUTE_MAXS);
            final ClassVisitor v=new TClassVisitor(cw);
            System.out.println(wovenClass.getBytes());
            cr.accept(v,Opcodes.ASM5);
            byte[]code= cw.toByteArray();
            System.out.println(code.toString());
            wovenClass.setBytes(cw.toByteArray());
        }
}

private boolean inInstrumented(String className) {

    return className.contains("people");
    
}

 }

=======================

package per.osgi.weavingHookText.Adapter;

import org.objectweb.asm.ClassVisitor;

import org.objectweb.asm.MethodVisitor;
import org.objectweb.asm.Opcodes;

public class TClassVisitor extends ClassVisitor {

private final ClassVisitor cw;

public TClassVisitor(final ClassVisitor cw) {
    super(Opcodes.ASM5, cw);
    this.cw = cw;
    // TODO Auto-generated constructor stub
}
 @Override
    public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) {
     super.visit(version, access, name, signature, name, interfaces);
    }
@Override
public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) {
    
    if("say".equals(name)){
        
        MethodVisitor mv=cw.visitMethod(access, name, desc, signature, exceptions);
        return new TMethodVisitor(mv);
        
    }
    return null;
}

}

====================================

package per.osgi.weavingHookText.Adapter;

import org.objectweb.asm.MethodVisitor;
import org.objectweb.asm.Opcodes;

public class TMethodVisitor extends MethodVisitor {

public TMethodVisitor(MethodVisitor mv){
    super(Opcodes.ASM5,mv);
}

@Override
public void visitCode(){
    
    mv.visitFieldInsn(Opcodes.GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");
    mv.visitLdcInsn("========start=========");
    mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, "java/io/PrintStream", "println", "(Ljava/lang/String;)V", false);
    super.visitCode();
}
 }

============================= BUNDLE b

package per.osgi.weavingHookTest.Target;

import org.osgi.framework.BundleActivator;
import org.osgi.framework.BundleContext;

public class Target implements BundleActivator {
    //public people a=new people();
public void start(BundleContext context) throws Exception {
    // TODO Auto-generated method stub
    //a.say();
}

public void stop(BundleContext context) throws Exception {
    // TODO Auto-generated method stub
    
}

 }

===========================

package per.osgi.weavingHookTest.Target;

public class people {
public void say(){
    
}
}

================================== 我想向班级人员插入一些代码。

但是发生了一些错误。Bundle B 无法启动...我想知道实际发生了什么...

实际上我不知道是否可以将代码插入另一个 BUNDLE

[控制台][1]

[错误][2]

Instrumenting{}
16
[B@2269ab25
[B@6192f5fb
gogo: BundleException: Error starting module.

谢谢您的帮助。

当我启动 budnle B 时,发生了一些事情。[1]:https ://i.stack.imgur.com/SRPvH.png [2]:https ://i.stack.imgur.com/EnrrD.png

4

0 回答 0