上一篇博文: CGLIB学习札记---生成CLASS的命名规则 介绍了生成之类的命名规则, 在这个博文里面主要分析了下面3点:
1)Cglib如何生成的Class的二进制文件
2)Cglib生成的Class二进制(byte[])放哪
3)Cglib如何把二进制Load生成的Class
泛泛而谈,整个过程如下
- 就是Cglib根据父类,Callback, Filter 及一些相关信息生成key.
- 然后根据key 生成对应的子类的二进制表现形式
- 使用ClassLoader装载对应的二进制,生成Class对象,并缓存
- 最后实例化Class对象,并缓存
下面是相对应的关键代码.
1)Cglib如何生成的Class的二进制文件
针对不同场景, CGlib准备了不同的Class生成方法, 他们都实现了接口: ClassGenerator. 下面我们只针对默认的Enhancer来分析.
//此函数会被AbstractClassGenerator.create间接调用,并会在create函数中将结果缓存. Enhancer.generateClass(ClassVisitor v) //AbstractClassGenerator.create(Object key) protected Object create(Object key) { try { Class gen = null; synchronized (source) { ClassLoader loader = getClassLoader(); Map cache2 = null; cache2 = (Map)source.cache.get(loader); if (cache2 == null) { cache2 = new HashMap(); cache2.put(NAME_KEY, new HashSet()); source.cache.put(loader, cache2); } else if (useCache) { Reference ref = (Reference)cache2.get(key); gen = (Class) (( ref == null ) ? null : ref.get()); } if (gen == null) { Object save = CURRENT.get(); CURRENT.set(this); try { this.key = key; if (attemptLoad) { try { gen = loader.loadClass(getClassName()); } catch (ClassNotFoundException e) { // ignore } } if (gen == null) { //生成的Class的二进制存储 byte[] b = strategy.generate(this); String className = ClassNameReader.getClassName(new ClassReader(b)); //将类名放入Cache中,Cache实际上是一个Hashset的实例 getClassNameCache(loader).add(className); //将生成的类装载路JVM gen = ReflectUtils.defineClass(className, b, loader); } if (useCache) { //将装载的类放入cache cache2.put(key, new WeakReference(gen)); } return firstInstance(gen); } finally { CURRENT.set(save); } } } return firstInstance(gen); } catch (RuntimeException e) { throw e; } catch (Error e) { throw e; } catch (Exception e) { throw new CodeGenerationException(e); } }
2)Cglib生成的Class二进制(byte[])放哪
放在byte数组中,下面这行代码就截取于方法AbstractClassGenerator.create(Object key)
byte[] b = strategy.generate(this);
然后通过 ReflectUtils.defineClass(className, b, loader) 生成对应的Class实例,并缓存入cache2
3)Cglib如何把二进制Load生成的Class
//ReflectUtils.defineClass(className, b, loader) public static Class defineClass(String className, byte[] b, ClassLoader loader) throws Exception { Object[] args = new Object[]{className, b, new Integer(0), new Integer(b.length), PROTECTION_DOMAIN }; //DEFINE_CLASS 是通过静态块来实例化的一个java.lang.ClassLoader.defineClass的方法对象 Class c = (Class)DEFINE_CLASS.invoke(loader, args); // Force static initializers to run. Class.forName(className, true, loader); return c; }
相关推荐
cglib-full-2.0及及cglib-full-2.0.2,亲测有效,必备工具,廉价分享
spring源码缺失jar。spring-cglib-repack-3.2.5.jar,spring-objenesis-repack-2.6.jar
spring源码编译之后,各个项目可能缺失jar包 spring-cglib-repack-3.2.4.jar和spring-objenesis-repack-2.5.1.jar
cglib-full-2.0.2.jar cglib-full-2.0.2.jar cglib-full-2.0.2.jar
spring-cglib-repack-3.2.6.jar和spring-objenesis-repack-2.6.jar 需要的拿走吧
spring4.0源码编译时缺失的两个jar包,spring-cglib-repack-3.1.jar,spring-objenesis-repack-2.1.jar
spring源码导入SpringObjenesis类报错解决,缺少jar包spring-cglib-repack-3.2.0.jar和spring-objenesis-repack-2.1.jar
赠送jar包:cglib-nodep-3.2.4.jar; 赠送原API文档:cglib-nodep-3.2.4-javadoc.jar; 赠送源代码:cglib-nodep-3.2.4-sources.jar; 赠送Maven依赖信息文件:cglib-nodep-3.2.4.pom; 包含翻译后的API文档:cglib-...
hibernate-cglib-repack-2.1_3.jar
Spring源码阅读环境缺少的jar包
赠送jar包:cglib-3.1.jar; 赠送原API文档:cglib-3.1-javadoc.jar; 赠送源代码:cglib-3.1-sources.jar; 赠送Maven依赖信息文件:cglib-3.1.pom; 包含翻译后的API文档:cglib-3.1-javadoc-API文档-中文(简体)版...
里面包含完整的cglib-nodep-2.2.jar和asm-2.2.3.jar,放心下载
Spring源码缺失的spring-cglib-repack-3.2.6.jar和spring-objenesis-repack-2.6.jar
spring源码深度分析源码依赖,将cglib和objenesis重新打包处理。同时添加grandle依赖:compile fileTree(dir: 'libs', include: ['*.jar'])
赠送jar包:cglib-3.3.0.jar; 赠送原API文档:cglib-3.3.0-javadoc.jar; 赠送源代码:cglib-3.3.0-sources.jar; 赠送Maven依赖信息文件:cglib-3.3.0.pom; 包含翻译后的API文档:cglib-3.3.0-javadoc-API文档-...
2018-02-08从git_hub上拉取的Spring源码打成的jar,构建Spring-beans5.0以上源码所缺失的两个jar包spring-cglib-repack-3.2.6.jar,spring-objenesis-repack-2.6.jar
com.springsource.net.sf.cglib-sources-2.2.0.jar
Spring是一个开放源代码的设计层面框架,他解决的是业务逻辑...从框架入口开始抽丝剥茧,理解其每一个核心概念以及作用,并将这些核心技术点融汇起来 探究每一个核心的实现细节(UML图、跑单元测试用例、DEBUG,体悟)
spring查看源码所需要的jar包之一 spring-cglib-repack-3.2.8.jar
spring-cglib-repack-3.2.6.jar 放在spring-core/build/libs下