如何分析一个Android程序(反编译+重新编译+签名)

如何分析一个Android程序

这是参照《Android软件安全与逆向分析》中的一个例子,主要就是如何分析一个Android应用程序,是一个非常简单的例子。


首先:
默认各位已经安装JDK,并且环境变量已经正确配置。
已经有安装有Android开发环境。
默认各位都不是Android零基础。。(这个好像有点多余,,嘿嘿。。)

所需工具:
Android 反编译工具下载:http://download.csdn.net/download/xyz326547445/6691679 (不要积分哦,亲)

正文:
1、新建一个Android项目,名字叫 CrackMe01,界面为这样:


2 、 接着编写MainActivity 里面的代码,先写一个checkSN ( String userName , String sn )方法,代码如下:

private boolean checkSN(String userName ,String sn) {
		// TODO Auto-generated method stub
    	boolean result = false;
    	if(userName == null || userName.length() == 0){//如果 userName == null 或者 userName == "";
    		return false;
    	}
    	if(sn == null || sn.length() != 16){//如果注册码 sn == null 或者 sn 的长度不等于 16
    		return false;
    	}
    	try {
			MessageDigest digest = MessageDigest.getInstance("MD5");
			digest.reset();
			digest.update(userName.getBytes());
			byte[] userNameBytes = digest.digest(); // 采用 MD5 对用用户名进行 Hash
			String strBytes = new String(userNameBytes,"UTF-8"); // 将计算结果转化为字符串
			
			StringBuffer strBuffer = new StringBuffer();
			for (int i = 0; i < strBytes.length(); i+=2) {
				strBuffer.append(strBytes.charAt(i));
			}
			String userSN = strBuffer.toString();//计算出的userSN
			result = userSN.equalsIgnoreCase(sn);//比较注册码(sn)是否正确
		} catch (NoSuchAlgorithmException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (UnsupportedEncodingException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
    	return result;
}



接着在 MainActivity 的 onCreate() 方法中注册监听 Button 点击事件:

private EditText etUserName;//用户名输入框
	private EditText etRegisterCode;//注册码输入框
	private Button btnRegister;//注册按钮
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        setTitle(R.string.unregister);//设置标题
        initView();//初始化界面控件
        initListener();//注册监听
    }

	private void initView() {
		// TODO Auto-generated method stub
    	etUserName = (EditText)findViewById(R.id.et_user_name);
    	etRegisterCode = (EditText)findViewById(R.id.et_register_code);
    	btnRegister = (Button)findViewById(R.id.btn_regist);
	}
	
	private void initListener() {
		// TODO Auto-generated method stub
		btnRegister.setOnClickListener(new View.OnClickListener() {//注册按钮点击监听
			
			@Override
			public void onClick(View v) {
				// TODO Auto-generated method stub
				String userName = etUserName.getText().toString().trim();
				String sn = etRegisterCode.getText().toString().trim();
				if(checkSN(userName, sn)){//调用checkSN方法进行注册码比较
					Toast.makeText(MainActivity.this, R.string.register_succeed, 0).show();
					setTitle(R.string.register);
				}else{
					Toast.makeText(MainActivity.this, R.string.register_failed, 0).show();
					setTitle(R.string.unregister);
				}
			}
		});
	}


写好之后进行编译,生成 apk 文件,测试:

好了,接下来我们用 反编译工具 进行反编译,得到的文件列表如下图:

我们先找一个突破口: 就以 "无效用户名或注册码,注册失败" 这句话为突破口,在资源文件里面找:
在 /res/values/string.xml 中:

接下来我们在 /res/values/public.xml 中寻找 register_failed:
可以看出它的对应的id = "0x7f050009";

现在我们去MainActivity$1.smali代码中寻找这个id:
这是smali语言,if-eqz 如果为真 就顺序执行,否则跳到 cond_0
和它相对应的是 if-nez,所以我们将它 替换为 if-nez。然后在用ApkTools即反编译工具 Rebuild APK ,重新生成新的apk,这时候别忘了要对新的apk进行签名:


最后再运行签名后的apk,运行结果:
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值