安卓防止反编译

<strong><span style="font-size:24px;">众所周知安卓很容易被反编译,即使做了防止反编译处理许多代码也可以看的到,目前用的比较多的手段是jni,即:把核心代码放到c++中,然后做出so库,这样的话安全性提高不少,但如果不对so库进行特殊处理的话,通过查看反编译后的java代码就会推测出你定义的调用so库的接口,别人就可以仿造你的接口,然后调用你的so库。
其实我们可以再每次调用so库时都在so库中的函数中判断一下安卓的公钥是不是你的,从而阻止他们使用你的so库,具体代码及工程如下</span></strong>

#include"com_example_singjni_MainActivity.h"
#include <stdio.h>
#include <stdlib.h>

//
//获取公钥的java代码
//public void getSingInfo() {
//        try {
//        	String pn=getPackageName();
//
//            PackageInfo packageInfo = getPackageManager().getPackageInfo(
//                    pn, PackageManager.GET_SIGNATURES);
//            Signature[] signs = packageInfo.signatures;
//            Signature sign = signs[0];
//            parseSignature(sign.toByteArray());
//        } catch (Exception e) {
//            e.printStackTrace();
//        }
//    }
//
//    public void parseSignature(byte[] signature) {
//    	ByteArrayInputStream bi=new ByteArrayInputStream(signature);
//        try {
//            CertificateFactory certFactory = CertificateFactory
//                    .getInstance("X.509");
//            X509Certificate cert = (X509Certificate) certFactory
//                    .generateCertificate(new ByteArrayInputStream(signature));
//            String pubKey = cert.getPublicKey().toString();
//            String signNumber = cert.getSerialNumber().toString();
//
//
//            System.out.println("signName:" + cert.getSigAlgName());
//            System.out.println("pubKey:" + pubKey);
//            System.out.println("signNumber:" + signNumber);
//            System.out.println("subjectDN:"+cert.getSubjectDN().toString());
//			 } catch ( Exception e) {
//				e.printStackTrace();
//			}
//		}

//核心代码如下    ,其他可以忽略
JNIEXPORT jstring JNICALL Java_com_example_singjni_MainActivity_sing__Landroid_content_Context_2
  (JNIEnv * env, jobject ob1, jobject thiz){

	jclass thisClass=env->GetObjectClass(thiz);
	jmethodID getPNId=env->GetMethodID(thisClass,"getPackageName","()Ljava/lang/String;");
	jstring packName=(jstring)env->CallObjectMethod(thiz,getPNId);

	jmethodID getPMId=env->GetMethodID(thisClass,"getPackageManager","()Landroid/content/pm/PackageManager;");
	jobject packManger=env->CallObjectMethod(thiz,getPMId);

	jmethodID getPIId=env->GetMethodID(env->GetObjectClass(packManger),"getPackageInfo","(Ljava/lang/String;I)Landroid/content/pm/PackageInfo;");
	jobject packageInfo=env->CallObjectMethod(packManger,getPIId,packName,0x00000040);

	jfieldID signaturesId=env->GetFieldID(env->GetObjectClass(packageInfo),"signatures","[Landroid/content/pm/Signature;");
	jobject signatures=env->GetObjectField(packageInfo,signaturesId);
	jobjectArray signaturesArray=(jobjectArray)signatures;

	//signature=signs[0]
	jobject signature=env->GetObjectArrayElement(signaturesArray,0);
	jmethodID signatureBytesMId=env->GetMethodID(env->GetObjectClass(signature),"toByteArray","()[B");
	//sign.toByteArray()
	jobject signatureBytes=env->CallObjectMethod(signature,signatureBytesMId);
///////////////// public void parseSignature(byte[] signature) {}/////////////////////////////////////////////////////////////////

	jclass certificateFactoryClass=env->FindClass("java/security/cert/CertificateFactory");
	jmethodID getInstanceMId=env->GetStaticMethodID(certificateFactoryClass,"getInstance","(Ljava/lang/String;)Ljava/security/cert/CertificateFactory;");
	jobject certFactory=env->CallStaticObjectMethod(certificateFactoryClass,getInstanceMId,env->NewStringUTF("X.509"));
///////////////////////////////////
	jclass byteInStreamClass=env->FindClass("java/io/ByteArrayInputStream");
	jmethodID byteArrayInStreamConMId= env->GetMethodID(byteInStreamClass,"<init>","([B)V");
	jobject byteArrayInStream=env->NewObject(byteInStreamClass,byteArrayInStreamConMId,signatureBytes);

	jmethodID generateCertificateMId=env->GetMethodID(certificateFactoryClass,"generateCertificate","(Ljava/io/InputStream;)Ljava/security/cert/Certificate;");
	jobject certificate=env->CallObjectMethod(certFactory,generateCertificateMId,byteArrayInStream);

	jmethodID getPKMId=env->GetMethodID(env->GetObjectClass(certificate),"getPublicKey","()Ljava/security/PublicKey;");

	jobject publicKey=env->CallObjectMethod(certificate,getPKMId);
	jmethodID toStringMId=env->GetMethodID(env->GetObjectClass(publicKey),"toString","()Ljava/lang/String;");
	jstring publickeyStr=(jstring)env->CallObjectMethod(publicKey,toStringMId);
///////////////////////
	jmethodID equalsMId=env->GetMethodID(env->GetObjectClass(publickeyStr),"equals","(Ljava/lang/Object;)Z");
	jboolean isCorrect=env->CallBooleanMethod(publickeyStr,equalsMId,env->NewStringUTF("OpenSSLRSAPublicKey{modulus=123..你的公钥...,publicExponent=10001}"));
	if(!isCorrect)
		return env->NewStringUTF( "wrong");

	jstring jstr=env->NewStringUTF( "correct");
		return jstr;

}

JNIEXPORT jstring JNICALL Java_com_example_singjni_MainActivity_sing
  (JNIEnv * env, jobject thiz){

	jstring jstr=env->NewStringUTF( "");
	return jstr;

}
java端代码 

package com.example.singjni;

import java.io.ByteArrayInputStream;
import java.io.File;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.security.cert.Certificate;
import java.security.cert.CertificateFactory;
import java.security.cert.X509Certificate;
import java.text.SimpleDateFormat;
import java.util.Date;

import android.app.Activity;
import android.app.Application;
import android.content.Context;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.Signature;
import android.os.Bundle;
import android.util.DisplayMetrics;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends  Activity {

	static{
		System.loadLibrary("jniso");
	}
	EditText et;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		et=(EditText) findViewById(R.id.et);

		String s=sing(this);

		et.setText(s);

		System.out.println(s);

	}

	public native String  sing();
	public native String  sing(Context context);

}

工程下载地址   点击打开链接

时间: 2024-11-25 09:56:17

安卓防止反编译的相关文章

安卓apk反编译

在win环境反编译安卓APP的.apk文件 安卓apk 反编译为 Java源码图文教程 Android安全攻防战,反编译与混淆技术完全解析(上) 原文地址:https://www.cnblogs.com/jing1617/p/11429822.html

Android安卓APK反编译逆向

关于安卓APK程序的逆向比WindowsPE文件的逆向要简单太多了 1.安卓的APK程序其实就是一个zip,可以用winrar打开,解压后会看到很熟悉的目录,还有AndroidManifest.xml文件,各种资源和图片 2.xml用记事本打开,会看到有乱码,所以需要使用AXMLPrinter2.jar工具来进行处理一下,命令如下: java -jar AXMLPrinter2.jar AndroidManifest.xml > AndroidManifest.txt 这时打开AndroidMa

安卓应用反编译(二)-APK包反编译

第二章 APK包反编译 被编译器处理过的代码和资源已经打包成了APK,有的甚至被转化成了二进制文件.但是我们也有一些方法,把这些编译过的内容给变回原来的样子,这个过程叫做-反编译. 反编译分为两个部分:一个是资源文件,一个是java文件.so文件是c++编译的结果,可以认为是不可反编译的(反编译成汇编指令,估计大部分人也看不懂). 2.1 反编译资源文件 APK tool是反编译的有力工具,据说是谷歌提供的官方的反编译工具,可以把APK目录解包,资源文件全部还原成编译前的样子,而dex文件反编译

关于安卓Apk反编译 再编译回来不能正常安装的问题

使用apktool反编译apk之后,再编译回去,发现不能正常安装,而使用ApkToolKitV3.0反编译,再编译回去就可以正常安装. 主要原因是因为使用apktool编译回没有签名. 所以不能安装, 而ApkToolKitV3.0 编译回去是签名了的. 用apktool编译后, 再使用signapk.jar签名就可以了. java -jar signapk.jar testkey.x509.pem testkey.pk8 test.apk test-signed.apk 以下是我打包好的apk

安卓程序防止反编译的方式

1. 加壳 apk的加壳:在程序外面再包裹一层代码,保护里面的代码不被非法修改或者反编译. 被保护的程序用加密算法加密,解密逻辑写在作为壳的APK中,实际执行的是被保护的程序. 大多是通过DexClassLoader或者隐藏的函数openDexFile将源dex(即被保护的app)加载进来,然后动态替换Application来启动源程序.跟Windows上传统的PE文件加壳有一定区别. 要破解传统的壳,需要跟踪控制流找到OEP,然后把源程序从内存中dump下来,重建输入表,最困难的就是要跟着外壳

安卓App安全保护,如何防止app反编译!

先进的移动设备具有各种奇妙的功能,从长远来看可以节省大量的时间和金钱.但这些设备真是太新了,所以他们具有"不可预料的弱点和保护不当的价值." 手机方面,恶意软件大约99%的目标是针对Android的,而Java编程语言里的漏洞被人利用的机会最高.文章出处!www.ijiami.cn 基于可理解的原因,尽管中国已是智能手机生产大国和消费大国,但智能手机的"大脑"即操作系统还全靠"外援",目前主要有谷歌的安卓系统和苹果的IOS系统.两者中,开放的安卓

如何防止Android反编译apk,爱加密进行安卓加密保护!

近年来,针对网购.交友网站,发送伪装成"样品"或"私照"的钓鱼.木马链接类诈骗逐渐增多:套取个人信息类诈骗手法有所升级,如借卡转账.机票退订等,要求提供银行卡卡号.身份证号及短信验证码:大家熟悉的网络买卖,买家可能"易容",网上的店铺也可能是"僵尸".尤其是近日<E天下>头条报道<小心!不明链接勿乱按>后,引来众多读者反馈:骗子是怎样伪装的呢?常用的伎俩有哪些?现在,爱加密就来为大家一一揭晓,帮助大家在

【Android】记录反编译安卓程序步骤

主要是为了分析一个 App 里面用到的接口,以后移植 UWP 用. 1.http://jd.benow.ca/ 下载 JD-GUI. 2.https://github.com/pxb1988/dex2jar 下载 dex2jar. 3.打开 cmd 并输入命令. 跳转到 dex2jar 的目录后,输入 d2j-dex2jar XXX.XXX 为 apk 的路径.完成后会在 dex2jar 的目录中找到 XXX-dex2jar.jar 这个文件. 4.打开 jar 文件. 使用 JD-GUI 打开

安卓反编译揭秘!!

apk反编译生成程序的源代码和图片.XML配置.语言资源等文件 Android应用的UI越来越漂亮,遇到喜欢的我们可以通过反编译,得到应用的源代码借鉴下别人的思想. 具体步骤: 1.下载 apktool 下载地址:http://www.ijiami.cn/newsInfo?id=514&v=2 2.解压 apktool,打开DOS命令行工具,进入解压目录. 3.命令行中输入以下命令:apktool.bat  d  -f   com.phonedog.activity.apk 反编译APK文件 a