Java Code Examples for javassist.bytecode.ClassFile#getConstPool()

The following examples show how to use javassist.bytecode.ClassFile#getConstPool() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: FieldTransformer.java    From cacheonix-core with GNU Lesser General Public License v2.1 6 votes vote down vote up
private void addSetFieldHandlerMethod(ClassFile classfile)
		throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	int this_class_index = cp.getThisClassInfo();
	MethodInfo minfo = new MethodInfo(cp, SETFIELDHANDLER_METHOD_NAME,
	                                  SETFIELDHANDLER_METHOD_DESCRIPTOR);
	/* local variables | this | callback | */
	Bytecode code = new Bytecode(cp, 3, 3);
	// aload_0 // load this
	code.addAload(0);
	// aload_1 // load callback
	code.addAload(1);
	// putfield // put field "$JAVASSIST_CALLBACK" defined already
	code.addOpcode(Opcode.PUTFIELD);
	int field_index = cp.addFieldrefInfo(this_class_index,
	                                     HANDLER_FIELD_NAME, HANDLER_FIELD_DESCRIPTOR);
	code.addIndex(field_index);
	// return
	code.addOpcode(Opcode.RETURN);
	minfo.setCodeAttribute(code.toCodeAttribute());
	minfo.setAccessFlags(AccessFlag.PUBLIC);
	classfile.addMethod(minfo);
}
 
Example 2
Source File: CtClassBuilder.java    From japicmp with Apache License 2.0 6 votes vote down vote up
public CtClass addToClassPool(ClassPool classPool) {
	CtClass ctClass;
	if (this.superclass.isPresent()) {
		ctClass = classPool.makeClass(this.name, this.superclass.get());
	} else {
		ctClass = classPool.makeClass(this.name);
	}
	ctClass.setModifiers(this.modifier);
	for (String annotation : annotations) {
		ClassFile classFile = ctClass.getClassFile();
		ConstPool constPool = classFile.getConstPool();
		AnnotationsAttribute attr = new AnnotationsAttribute(constPool, AnnotationsAttribute.visibleTag);
		Annotation annot = new Annotation(annotation, constPool);
		attr.setAnnotation(annot);
		ctClass.getClassFile2().addAttribute(attr);
	}
	for (CtClass interfaceCtClass : interfaces) {
		ctClass.addInterface(interfaceCtClass);
	}
	return ctClass;
}
 
Example 3
Source File: JavassistUtils.java    From statefulj with Apache License 2.0 6 votes vote down vote up
public static void addClassAnnotation(CtClass clazz, Class<?> annotationClass, Object... values) {
	ClassFile ccFile = clazz.getClassFile();
	ConstPool constPool = ccFile.getConstPool();
	AnnotationsAttribute attr = getAnnotationsAttribute(ccFile);
	Annotation annot = new Annotation(annotationClass.getName(), constPool);
	
	for(int i = 0; i < values.length; i = i + 2) {
		String valueName = (String)values[i];
		Object value = values[i+1];
		if (valueName != null && value != null) {
			MemberValue memberValue = createMemberValue(constPool, value);
			annot.addMemberValue(valueName, memberValue);
		}
	}
	
	attr.addAnnotation(annot);
}
 
Example 4
Source File: CtMethodBuilder.java    From japicmp with Apache License 2.0 6 votes vote down vote up
public CtMethod addToClass(CtClass declaringClass) throws CannotCompileException {
	if (this.returnType == null) {
		this.returnType = declaringClass;
	}
	CtMethod ctMethod = CtNewMethod.make(this.modifier, this.returnType, this.name, this.parameters, this.exceptions, this.body, declaringClass);
	ctMethod.setModifiers(this.modifier);
	declaringClass.addMethod(ctMethod);
	for (String annotation : annotations) {
		ClassFile classFile = declaringClass.getClassFile();
		ConstPool constPool = classFile.getConstPool();
		AnnotationsAttribute attr = new AnnotationsAttribute(constPool, AnnotationsAttribute.visibleTag);
		Annotation annot = new Annotation(annotation, constPool);
		attr.setAnnotation(annot);
		ctMethod.getMethodInfo().addAttribute(attr);
	}
	return ctMethod;
}
 
Example 5
Source File: FieldTransformer.java    From cacheonix-core with GNU Lesser General Public License v2.1 6 votes vote down vote up
private int transformInvokevirtualsIntoGetfields(ClassFile classfile,
                                                 CodeIterator iter, int pos) {
	ConstPool cp = classfile.getConstPool();
	int c = iter.byteAt(pos);
	if (c != Opcode.GETFIELD) {
		return pos;
	}
	int index = iter.u16bitAt(pos + 1);
	String fieldName = cp.getFieldrefName(index);
	String className = cp.getFieldrefClassName(index);
	if ((!classfile.getName().equals(className))
	    || (!readableFields.containsKey(fieldName))) {
		return pos;
	}
	String desc = "()" + (String) readableFields.get(fieldName);
	int read_method_index = cp.addMethodrefInfo(cp.getThisClassInfo(),
	                                            EACH_READ_METHOD_PREFIX + fieldName, desc);
	iter.writeByte(Opcode.INVOKEVIRTUAL, pos);
	iter.write16bit(read_method_index, pos + 1);
	return pos;
}
 
Example 6
Source File: BulkAccessorFactory.java    From lams with GNU General Public License v2.0 6 votes vote down vote up
/**
 * Declares a constructor that takes no parameter.
 *
 * @param classfile The class descriptor
 *
 * @throws CannotCompileException Indicates trouble with the underlying Javassist calls
 */
private void addDefaultConstructor(ClassFile classfile) throws CannotCompileException {
	final ConstPool constPool = classfile.getConstPool();
	final String constructorSignature = "()V";
	final MethodInfo constructorMethodInfo = new MethodInfo( constPool, MethodInfo.nameInit, constructorSignature );

	final Bytecode code = new Bytecode( constPool, 0, 1 );
	// aload_0
	code.addAload( 0 );
	// invokespecial
	code.addInvokespecial( BulkAccessor.class.getName(), MethodInfo.nameInit, constructorSignature );
	// return
	code.addOpcode( Opcode.RETURN );

	constructorMethodInfo.setCodeAttribute( code.toCodeAttribute() );
	constructorMethodInfo.setAccessFlags( AccessFlag.PUBLIC );
	classfile.addMethod( constructorMethodInfo );
}
 
Example 7
Source File: CtClassBuilder.java    From japicmp with Apache License 2.0 6 votes vote down vote up
public CtClass addToClassPool(ClassPool classPool) {
	CtClass ctClass;
	if (this.superclass.isPresent()) {
		ctClass = classPool.makeClass(this.name, this.superclass.get());
	} else {
		ctClass = classPool.makeClass(this.name);
	}
	ctClass.setModifiers(this.modifier);
	for (String annotation : annotations) {
		ClassFile classFile = ctClass.getClassFile();
		ConstPool constPool = classFile.getConstPool();
		AnnotationsAttribute attr = new AnnotationsAttribute(constPool, AnnotationsAttribute.visibleTag);
		Annotation annot = new Annotation(annotation, constPool);
		attr.setAnnotation(annot);
		ctClass.getClassFile2().addAttribute(attr);
	}
	for (CtClass interfaceCtClass : interfaces) {
		ctClass.addInterface(interfaceCtClass);
	}
	return ctClass;
}
 
Example 8
Source File: FieldTransformer.java    From cacheonix-core with GNU Lesser General Public License v2.1 6 votes vote down vote up
private void addGetFieldHandlerMethod(ClassFile classfile)
		throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	int this_class_index = cp.getThisClassInfo();
	MethodInfo minfo = new MethodInfo(cp, GETFIELDHANDLER_METHOD_NAME,
	                                  GETFIELDHANDLER_METHOD_DESCRIPTOR);
	/* local variable | this | */
	Bytecode code = new Bytecode(cp, 2, 1);
	// aload_0 // load this
	code.addAload(0);
	// getfield // get field "$JAVASSIST_CALLBACK" defined already
	code.addOpcode(Opcode.GETFIELD);
	int field_index = cp.addFieldrefInfo(this_class_index,
	                                     HANDLER_FIELD_NAME, HANDLER_FIELD_DESCRIPTOR);
	code.addIndex(field_index);
	// areturn // return the value of the field
	code.addOpcode(Opcode.ARETURN);
	minfo.setCodeAttribute(code.toCodeAttribute());
	minfo.setAccessFlags(AccessFlag.PUBLIC);
	classfile.addMethod(minfo);
}
 
Example 9
Source File: JavasisstUnitTest.java    From tutorials with MIT License 6 votes vote down vote up
@Test
public void givenTableOfInstructions_whenAddNewInstruction_thenShouldConstructProperSequence() throws NotFoundException, BadBytecode, CannotCompileException, IllegalAccessException, InstantiationException {
    // given
    ClassFile cf = ClassPool.getDefault().get("com.baeldung.javasisst.ThreeDimensionalPoint").getClassFile();

    // when
    FieldInfo f = new FieldInfo(cf.getConstPool(), "id", "I");
    f.setAccessFlags(AccessFlag.PUBLIC);
    cf.addField(f);

    ClassPool classPool = ClassPool.getDefault();
    Field[] fields = classPool.makeClass(cf).toClass().getFields();
    List<String> fieldsList = Stream.of(fields).map(Field::getName).collect(Collectors.toList());
    assertTrue(fieldsList.contains("id"));

}
 
Example 10
Source File: BulkAccessorFactory.java    From cacheonix-core with GNU Lesser General Public License v2.1 6 votes vote down vote up
/**
 * Declares a constructor that takes no parameter.
 *
 * @param classfile
 * @throws CannotCompileException
 */
private void addDefaultConstructor(ClassFile classfile) throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	String cons_desc = "()V";
	MethodInfo mi = new MethodInfo( cp, MethodInfo.nameInit, cons_desc );

	Bytecode code = new Bytecode( cp, 0, 1 );
	// aload_0
	code.addAload( 0 );
	// invokespecial
	code.addInvokespecial( BulkAccessor.class.getName(), MethodInfo.nameInit, cons_desc );
	// return
	code.addOpcode( Opcode.RETURN );

	mi.setCodeAttribute( code.toCodeAttribute() );
	mi.setAccessFlags( AccessFlag.PUBLIC );
	classfile.addMethod( mi );
}
 
Example 11
Source File: JavasisstUnitTest.java    From tutorials with MIT License 6 votes vote down vote up
@Test
public void givenLoadedClass_whenAddConstructorToClass_shouldCreateClassWithConstructor() throws NotFoundException, CannotCompileException, BadBytecode {
    // given
    ClassFile cf = ClassPool.getDefault().get("com.baeldung.javasisst.Point").getClassFile();
    Bytecode code = new Bytecode(cf.getConstPool());
    code.addAload(0);
    code.addInvokespecial("java/lang/Object", MethodInfo.nameInit, "()V");
    code.addReturn(null);

    // when
    MethodInfo minfo = new MethodInfo(cf.getConstPool(), MethodInfo.nameInit, "()V");
    minfo.setCodeAttribute(code.toCodeAttribute());
    cf.addMethod(minfo);

    // then
    CodeIterator ci = code.toCodeAttribute().iterator();
    List<String> operations = new LinkedList<>();
    while (ci.hasNext()) {
        int index = ci.next();
        int op = ci.byteAt(index);
        operations.add(Mnemonic.OPCODE[op]);
    }

    assertEquals(operations, Arrays.asList("aload_0", "invokespecial", "return"));

}
 
Example 12
Source File: CtMethodBuilder.java    From japicmp with Apache License 2.0 6 votes vote down vote up
public CtMethod addToClass(CtClass declaringClass) throws CannotCompileException {
	if (this.returnType == null) {
		this.returnType = declaringClass;
	}
	CtMethod ctMethod = CtNewMethod.make(this.modifier, this.returnType, this.name, this.parameters, this.exceptions, this.body, declaringClass);
	ctMethod.setModifiers(this.modifier);
	declaringClass.addMethod(ctMethod);
	for (String annotation : annotations) {
		ClassFile classFile = declaringClass.getClassFile();
		ConstPool constPool = classFile.getConstPool();
		AnnotationsAttribute attr = new AnnotationsAttribute(constPool, AnnotationsAttribute.visibleTag);
		Annotation annot = new Annotation(annotation, constPool);
		attr.setAnnotation(annot);
		ctMethod.getMethodInfo().addAttribute(attr);
	}
	return ctMethod;
}
 
Example 13
Source File: FieldTransformer.java    From cacheonix-core with GNU Lesser General Public License v2.1 5 votes vote down vote up
private void addFieldHandlerField(ClassFile classfile)
		throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	FieldInfo finfo = new FieldInfo(cp, HANDLER_FIELD_NAME,
	                                HANDLER_FIELD_DESCRIPTOR);
	finfo.setAccessFlags(AccessFlag.PRIVATE | AccessFlag.TRANSIENT);
	classfile.addField(finfo);
}
 
Example 14
Source File: MapperEnhancer.java    From tsharding with MIT License 5 votes vote down vote up
/**
     * 对mapper进行增强,生成新的mapper,并主动加载新mapper类到classloader
     *
     * @param mapperClassName
     */
    public static void enhanceMapperClass(String mapperClassName) throws Exception {

        Class originClass = Class.forName(mapperClassName);
        Method[] originMethods = originClass.getDeclaredMethods();

        CtClass cc = pool.get(mapperClassName);

        for (CtMethod ctMethod : cc.getDeclaredMethods()) {
            CtClass enhanceClass = pool.makeInterface(mapperClassName + "Sharding" + ctMethod.getName());
            for (long i = 0L; i < 512; i++) {
                CtMethod newMethod = new CtMethod(ctMethod.getReturnType(), ctMethod.getName() + ShardingCaculator.getNumberWithZeroSuffix(i), ctMethod.getParameterTypes(), enhanceClass);

                Method method = getOriginMethod(newMethod, originMethods);
                if(method.getParameterAnnotations()[0].length > 0) {
                    ClassFile ccFile = enhanceClass.getClassFile();
                    ConstPool constPool = ccFile.getConstPool();

                    //拷贝注解信息和注解内容,以支持mybatis mapper类的动态绑定
                    newMethod.getMethodInfo().addAttribute(MapperAnnotationEnhancer.duplicateParameterAnnotationsAttribute(constPool, method));
                }
                enhanceClass.addMethod(newMethod);
            }
            Class<?> loadThisClass = enhanceClass.toClass();

            //2015.09.22后不再输出类到本地
//            enhanceClass.writeFile(".");
        }
    }
 
Example 15
Source File: IgniteExamplesMLTestSuite.java    From ignite with Apache License 2.0 5 votes vote down vote up
/**
 * Creates test class for given example.
 *
 * @param exampleCls Class of the example to be tested.
 * @return Test class.
 */
private static Class<?> makeTestClass(Class<?> exampleCls) {
    ClassPool cp = ClassPool.getDefault();
    cp.insertClassPath(new ClassClassPath(IgniteExamplesMLTestSuite.class));

    CtClass cl = cp.makeClass(basePkgForTests + "." + exampleCls.getSimpleName() + "SelfTest");

    try {
        cl.setSuperclass(cp.get(GridAbstractExamplesTest.class.getName()));

        CtMethod mtd = CtNewMethod.make("public void testExample() { "
            + exampleCls.getCanonicalName()
            + ".main("
            + MLExamplesCommonArgs.class.getName()
            + ".EMPTY_ARGS_ML); }", cl);

        // Create and add annotation.
        ClassFile ccFile = cl.getClassFile();
        ConstPool constpool = ccFile.getConstPool();

        AnnotationsAttribute attr = new AnnotationsAttribute(constpool, AnnotationsAttribute.visibleTag);
        Annotation annot = new Annotation("org.junit.Test", constpool);

        attr.addAnnotation(annot);
        mtd.getMethodInfo().addAttribute(attr);

        cl.addMethod(mtd);

        return cl.toClass();
    }
    catch (Exception e) {
        throw new RuntimeException(e);
    }
}
 
Example 16
Source File: DefaultRepositoryGenerator.java    From business with Mozilla Public License 2.0 5 votes vote down vote up
Class<? extends T> generate(Class<? extends Repository> baseImpl) {
    try {
        CtClass cc = createClass(
                getClassName(baseImpl, getCounter(repositoryInterface).incrementAndGet()),
                baseImpl
        );
        ClassFile cf = cc.getClassFile();
        ConstPool constPool = cf.getConstPool();

        cc.setModifiers(Modifier.PUBLIC);

        cc.setInterfaces(new CtClass[]{classPool.getCtClass(repositoryInterface.getName())});

        if (hasGenericConstructor(baseImpl)) {
            cc.addConstructor(createConstructor(constPool, cc));
        } else {
            cc.addConstructor(createDefaultConstructor(cc));
        }

        cf.addAttribute(createQualifierAttribute(constPool, getQualifier(baseImpl)
                .orElseThrow(() -> new NotFoundException("Qualifier annotation not found"))));

        return cast(cc.toClass(
                classLoader,
                DefaultRepositoryCollector.class.getProtectionDomain())
        );
    } catch (CannotCompileException | NotFoundException e) {
        throw BusinessException.wrap(e, BusinessErrorCode.UNABLE_TO_CREATE_DEFAULT_IMPLEMENTATION)
                .put("interface", repositoryInterface)
                .put("base", baseImpl);
    }
}
 
Example 17
Source File: FieldTransformer.java    From cacheonix-core with GNU Lesser General Public License v2.1 4 votes vote down vote up
private void addWriteMethod(ClassFile classfile, FieldInfo finfo)
		throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	int this_class_index = cp.getThisClassInfo();
	String desc = "(" + finfo.getDescriptor() + ")V";
	MethodInfo minfo = new MethodInfo(cp, EACH_WRITE_METHOD_PREFIX
	                                      + finfo.getName(), desc);
	/* local variables | target obj | each oldvalue | */
	Bytecode code = new Bytecode(cp, 6, 3);
	// aload_0
	code.addAload(0);
	// invokeinterface // enabled.getInterceptFieldCallback()
	int enabled_class_index = cp.addClassInfo(FIELD_HANDLED_TYPE_NAME);
	code.addInvokeinterface(enabled_class_index,
	                        GETFIELDHANDLER_METHOD_NAME, GETFIELDHANDLER_METHOD_DESCRIPTOR,
	                        1);
	// ifnonnull (label1)
	code.addOpcode(Opcode.IFNONNULL);
	code.addIndex(9);
	// aload_0
	code.addAload(0);
	// *load_1
	addTypeDependDataLoad(code, finfo.getDescriptor(), 1);
	// putfield
	code.addOpcode(Opcode.PUTFIELD);
	int base_field_index = cp.addFieldrefInfo(this_class_index, finfo
			.getName(), finfo.getDescriptor());
	code.addIndex(base_field_index);
	code.growStack(-Descriptor.dataSize(finfo.getDescriptor()));
	// return ;
	code.addOpcode(Opcode.RETURN);
	// aload_0
	code.addAload(0);
	// dup
	code.addOpcode(Opcode.DUP);
	// invokeinterface // enabled.getInterceptFieldCallback()
	code.addInvokeinterface(enabled_class_index,
	                        GETFIELDHANDLER_METHOD_NAME, GETFIELDHANDLER_METHOD_DESCRIPTOR,
	                        1);
	// aload_0
	code.addAload(0);
	// ldc // field name
	code.addLdc(finfo.getName());
	// aload_0
	code.addAload(0);
	// getfield // old value of the field
	code.addOpcode(Opcode.GETFIELD);
	code.addIndex(base_field_index);
	code.growStack(Descriptor.dataSize(finfo.getDescriptor()) - 1);
	// *load_1
	addTypeDependDataLoad(code, finfo.getDescriptor(), 1);
	// invokeinterface // callback.write*(..)
	addInvokeFieldHandlerMethod(classfile, code, finfo.getDescriptor(),
	                            false);
	// putfield // new value of the field
	code.addOpcode(Opcode.PUTFIELD);
	code.addIndex(base_field_index);
	code.growStack(-Descriptor.dataSize(finfo.getDescriptor()));
	// return
	code.addOpcode(Opcode.RETURN);

	minfo.setCodeAttribute(code.toCodeAttribute());
	minfo.setAccessFlags(AccessFlag.PUBLIC);
	classfile.addMethod(minfo);
}
 
Example 18
Source File: BulkAccessorFactory.java    From cacheonix-core with GNU Lesser General Public License v2.1 4 votes vote down vote up
private void addGetter(ClassFile classfile, final Method[] getters) throws CannotCompileException {
	ConstPool cp = classfile.getConstPool();
	int target_type_index = cp.addClassInfo( this.targetBean.getName() );
	String desc = GET_SETTER_DESC;
	MethodInfo mi = new MethodInfo( cp, GENERATED_GETTER_NAME, desc );

	Bytecode code = new Bytecode( cp, 6, 4 );
	/* | this | bean | args | raw bean | */
	if ( getters.length >= 0 ) {
		// aload_1 // load bean
		code.addAload( 1 );
		// checkcast // cast bean
		code.addCheckcast( this.targetBean.getName() );
		// astore_3 // store bean
		code.addAstore( 3 );
		for ( int i = 0; i < getters.length; ++i ) {
			if ( getters[i] != null ) {
				Method getter = getters[i];
				// aload_2 // args
				code.addAload( 2 );
				// iconst_i // continue to aastore
				code.addIconst( i ); // growing stack is 1
				Class returnType = getter.getReturnType();
				int typeIndex = -1;
				if ( returnType.isPrimitive() ) {
					typeIndex = FactoryHelper.typeIndex( returnType );
					// new
					code.addNew( FactoryHelper.wrapperTypes[typeIndex] );
					// dup
					code.addOpcode( Opcode.DUP );
				}

				// aload_3 // load the raw bean
				code.addAload( 3 );
				String getter_desc = RuntimeSupport.makeDescriptor( getter );
				String getterName = getter.getName();
				if ( this.targetBean.isInterface() ) {
					// invokeinterface
					code.addInvokeinterface( target_type_index, getterName, getter_desc, 1 );
				}
				else {
					// invokevirtual
					code.addInvokevirtual( target_type_index, getterName, getter_desc );
				}

				if ( typeIndex >= 0 ) {       // is a primitive type
					// invokespecial
					code.addInvokespecial(
							FactoryHelper.wrapperTypes[typeIndex],
					        MethodInfo.nameInit,
					        FactoryHelper.wrapperDesc[typeIndex]
					);
				}

				// aastore // args
				code.add( Opcode.AASTORE );
				code.growStack( -3 );
			}
		}
	}
	// return
	code.addOpcode( Opcode.RETURN );

	mi.setCodeAttribute( code.toCodeAttribute() );
	mi.setAccessFlags( AccessFlag.PUBLIC );
	classfile.addMethod( mi );
}
 
Example 19
Source File: AsmRest.java    From fastquery with Apache License 2.0 4 votes vote down vote up
/**
 * 自动生成Repository接口的实现类并以字节的形式返回.
 * 
 * @param repositoryClazz repository class
 * @return 生成的类字节码
 */
public static byte[] generateBytes(Class<?> repositoryClazz) {

	// 生成类
	ClassPool pool = ClassPool.getDefault();
	// web容器中的repository 需要增加classPath
	ClassClassPath classClassPath = new ClassClassPath(repositoryClazz);
	pool.removeClassPath(classClassPath);
	pool.insertClassPath(classClassPath);
	String className = repositoryClazz.getName() + Placeholder.REST_SUF;
	CtClass ctClass = pool.makeClass(className);

	ClassFile ccFile = ctClass.getClassFile();
	ConstPool constpool = ccFile.getConstPool();

	try {
		// 增加接口
		ctClass.setInterfaces(new CtClass[] { pool.get(repositoryClazz.getName()) });

		// 增加字段
		CtClass executor = pool.get(repositoryClazz.getName());
		CtField field = new CtField(executor, "d", ctClass);
		field.setModifiers(Modifier.PRIVATE);
		FieldInfo fieldInfo = field.getFieldInfo();
		// 标识属性注解
		AnnotationsAttribute fieldAttr = new AnnotationsAttribute(constpool, AnnotationsAttribute.visibleTag);
		javassist.bytecode.annotation.Annotation autowired = new javassist.bytecode.annotation.Annotation(
				"javax.inject.Inject", constpool);
		fieldAttr.addAnnotation(autowired);
		fieldInfo.addAttribute(fieldAttr);
		ctClass.addField(field);
		
		AsmRepository.addGetInterfaceClassMethod(repositoryClazz, ctClass);
		
		// 标识类注解
		AnnotationsAttribute classAttr = new AnnotationsAttribute(constpool, AnnotationsAttribute.visibleTag);
		javassist.bytecode.annotation.Annotation singAnn = new javassist.bytecode.annotation.Annotation(
				"javax.inject.Singleton", constpool);
		classAttr.addAnnotation(singAnn);
		ccFile.addAttribute(classAttr);

		// 实现抽象方法
		Method[] methods = repositoryClazz.getMethods();
		for (Method method : methods) {
			if (!method.isDefault()) {
				CtMethod cm = CtMethod.make(AsmRepository.getMethodDef(method) + "{return d."+method.getName()+"($$);}", ctClass);
				// 标识方法注解
				AnnotationsAttribute methodAttr = new AnnotationsAttribute(constpool,
						AnnotationsAttribute.visibleTag);
				javassist.bytecode.annotation.Annotation extendsAnn = new javassist.bytecode.annotation.Annotation(
						"org.fastquery.core.Extends", constpool);
				ArrayMemberValue arrayMemberValue = new ArrayMemberValue(constpool);
				Annotation[] mas = method.getAnnotations();
				ClassMemberValue[] cmvs = new ClassMemberValue[mas.length];
				for (int i = 0; i < mas.length; i++) {
					cmvs[i] = new ClassMemberValue(mas[i].annotationType().getName(), constpool);
				}
				arrayMemberValue.setValue(cmvs);
				extendsAnn.addMemberValue("value", arrayMemberValue);
				methodAttr.addAnnotation(extendsAnn);
				MethodInfo info = cm.getMethodInfo();
				info.addAttribute(methodAttr);
				ctClass.addMethod(cm);
			}
		}
		
		return ctClass.toBytecode();

	} catch (Exception e) {
		throw new ExceptionInInitializerError(e);
	}
}
 
Example 20
Source File: BulkAccessorFactory.java    From lams with GNU General Public License v2.0 4 votes vote down vote up
private void addGetter(ClassFile classfile, final Method[] getters) throws CannotCompileException {
	final ConstPool constPool = classfile.getConstPool();
	final int targetBeanConstPoolIndex = constPool.addClassInfo( this.targetBean.getName() );
	final String desc = GET_SETTER_DESC;
	final MethodInfo getterMethodInfo = new MethodInfo( constPool, GENERATED_GETTER_NAME, desc );

	final Bytecode code = new Bytecode( constPool, 6, 4 );
	/* | this | bean | args | raw bean | */
	if ( getters.length >= 0 ) {
		// aload_1 // load bean
		code.addAload( 1 );
		// checkcast // cast bean
		code.addCheckcast( this.targetBean.getName() );
		// astore_3 // store bean
		code.addAstore( 3 );
		for ( int i = 0; i < getters.length; ++i ) {
			if ( getters[i] != null ) {
				final Method getter = getters[i];
				// aload_2 // args
				code.addAload( 2 );
				// iconst_i // continue to aastore
				// growing stack is 1
				code.addIconst( i );
				final Class returnType = getter.getReturnType();
				int typeIndex = -1;
				if ( returnType.isPrimitive() ) {
					typeIndex = FactoryHelper.typeIndex( returnType );
					// new
					code.addNew( FactoryHelper.wrapperTypes[typeIndex] );
					// dup
					code.addOpcode( Opcode.DUP );
				}

				// aload_3 // load the raw bean
				code.addAload( 3 );
				final String getterSignature = RuntimeSupport.makeDescriptor( getter );
				final String getterName = getter.getName();
				if ( this.targetBean.isInterface() ) {
					// invokeinterface
					code.addInvokeinterface( targetBeanConstPoolIndex, getterName, getterSignature, 1 );
				}
				else {
					// invokevirtual
					code.addInvokevirtual( targetBeanConstPoolIndex, getterName, getterSignature );
				}

				if ( typeIndex >= 0 ) {
					// is a primitive type
					// invokespecial
					code.addInvokespecial(
							FactoryHelper.wrapperTypes[typeIndex],
							MethodInfo.nameInit,
							FactoryHelper.wrapperDesc[typeIndex]
					);
				}

				// aastore // args
				code.add( Opcode.AASTORE );
				code.growStack( -3 );
			}
		}
	}
	// return
	code.addOpcode( Opcode.RETURN );

	getterMethodInfo.setCodeAttribute( code.toCodeAttribute() );
	getterMethodInfo.setAccessFlags( AccessFlag.PUBLIC );
	classfile.addMethod( getterMethodInfo );
}