防:
通过注册文件控制程序的使用权限和使用期限
攻:
反编译得到源代码,将注册验证去掉
防:
将读取注册文件的部分通过C++写成本地方法
攻:
反编译得到源代码,去掉读取注册文件的代码,然后直接返回正确的注册参数和注册验证
防:
将部分贯穿始终的功能也通过C++写成本地方法,只能通过注册验证才能调用,注册参数放弃,通过不同发行版来实现注册参数
攻:
将C++本地方法通过Java重新实现,基于Java和C++的生态考量,并且可改写为C++本地方法的范围有限,又要处处考虑到对接Java的因素,Java的实现成本绝对是远远低于C++的实现成本,想办法拿到具有所有注册参数的发行版来做破解
防:
将class文件加密发布,然后通过C++本地方法解密
攻:
不得已注册一次,通过注册验证之后,通过解密的C++本地方法逐一得到解密的class文件后保存下来
防:
在C++本地方法中解密,加载,返回
jbyte* bytes = 解密后的class文件数据
jsize size = bytes的字节数
//构造一个空的URL
jclass URLclass = env->FindClass("java/net/URL");
jobjectArray URLArray = env->NewObjectArray(0, URLclass, jobject());
//得到ContextClassLoader
jclass Threadclass = env->FindClass("java/lang/Thread");
jmethodID ThreadMethodID = env->GetStaticMethodID(Threadclass, "currentThread","()Ljava/lang/Thread;");
jobject currentThread = env->CallStaticObjectMethod(Threadclass, ThreadMethodID);
jmethodID getContextClassLoader = env->GetMethodID(Threadclass, "getContextClassLoader","()Ljava/lang/ClassLoader;");
jobject classLoader = env->CallObjectMethod(currentThread, getContextClassLoader);
//得到URLClassLoader
jclass URLClassLoader_class=env->FindClass("java/net/URLClassLoader");
jmethodID URLClassLoader_newInstance = env->GetStaticMethodID(
URLClassLoader_class, "newInstance","([Ljava/net/URL;Ljava/lang/ClassLoader;)Ljava/net/URLClassLoader;");
jobject URLClassLoaderInstance = env->CallStaticObjectMethod(
URLClassLoader_class, URLClassLoader_newInstance, URLArray, classLoader);
//通过DefineClass直接加载类定义信息
jclass _class = env->DefineClass("cn/test/HelloWorld", URLClassLoaderInstance, bytes, size);
攻:
C++本地方法中始终是需要DefineClass来加载,伪造jvm环境,自定义DefineClass函数,其他jvm函数都可以是空壳,然后供给C++本地方法调用DefineClass加载的时候,将解密后的class文件保存下来
防:
除了第三方库,其他部分全部用C++本地方法实现
攻:
换一家符合功能要求产品的公司,继续薅羊毛