Android下的Hook初探

1丶Android下的常用Hook框架

android下的Hook框架有很多,比较出名的就是XposedCydia Substrate,当然都各有不足,Xposed只能Hook Java层,面对native层就显得无力了;Substrate和Java层和native层都可以Hook,但作者好像很久没更新了,只能在dalvik上Hook,在android5.0及以上版本就不能用了,而且兼容性也不是很好,在几款模拟器上都没配置成功。

当然还有其它一些和新出的hook框架也是不错的,就不一一介绍了,下面给出Hook 框架的项目地址

Xposed:https://github.com/rovo89/Xposed
Cydia Substrate官网:http://www.cydiasubstrate.com/
Android Inline Hook:https://github.com/ele7enxxh/Android-Inline-Hook
StormHook:Android侵入式Java Hook框架:https://github.com/woxihuannisja/StormHook
免RootHook框架:https://github.com/asLody/legend
基于VirtualApp和YAHFA的免RootHook框架:https://github.com/rk700/VirtualHook

2丶Xposed框架的使用-进入Java的世界

环境:

开发工具:Android studio3.0.1
运行环境:Genymotion模拟器,系统安卓4.4.4
Xposed版本:v2.7
XposedBridgeApi版本:v54
注意:Android 5.0以下Xposed版本用v2.7,Android5.0用v3.+

实验目的

二个app,一个点击按钮获取imei,另一个完成Hook系统imie操作

操作步骤

①在Android studio中新建个Poriect,删除掉原有的app module,新建一个名为hook和一个名为getImei的module

Android下的Hook初探_第1张图片

②用getImei实现获取imei的功能

添加权限:

<uses-permission android:name="android.permission.READ_PHONE_STATE"/>

layout:


<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:gravity="center"
    tools:context="com.banyan.imei.MainActivity">

    <TextView
        android:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textSize="20dp"
        android:text="获取到的imei值为:" />
    <Button
        android:layout_marginTop="18dp"
        android:id="@+id/button1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="获取imei"/>

LinearLayout>

Activity:

package com.banyan.imei;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.telephony.TelephonyManager;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {

    private Button button1;
    private TextView textView1;
    private TelephonyManager tm;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        button1 = findViewById(R.id.button1);
        textView1 = findViewById(R.id.textView1);

        tm = (TelephonyManager) this.getSystemService(TELEPHONY_SERVICE);
        button1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                //获取imei
                String imei = tm.getDeviceId();
                //设置文本框的内容为获取的imei
                textView1.setText("获取到的imei值为:");
                textView1.setText(textView1.getText() + imei);
            }
        });

    }
}

运行效果如下:
Android下的Hook初探_第2张图片
因为是模拟器,这imei有点奇怪^_^
好,下面我们来完成Hook imei操作。。

③用hook实现获取Hook imei的功能

使用Xposed hook的必要配置

在AndroidManifest.xml里添加这三项:


<meta-data android:name="xposedmodule" android:value="ture"/>

<meta-data android:name="xposeddescription" android:value="Hook imei测试" />

<meta-data android:name="xposedminversion" android:value="54" />

添加XposedBridgeApi

新建个lib文件夹,拷贝XposedBridgeApi-54.jar到此目录,然后右键点击lib文件夹中的jar文件选择-> add as Library,这个有个坑,添加完之后还要更改一下配置,不然编译的时候会把XposedBridgeApi也编译进去,会导致很多问题,所以要配置一下使之编译的时候不参加编译。
Ctrl+Shift+Alt+s快捷键来到Project Structure界面,更改 jar的implementation 为compileOnly:
Android下的Hook初探_第3张图片

添加Hook的入口类

新建assetc文件夹,在文件夹下新建xposed_init文件,然后向文件添加入口类信息。如下图:
Android下的Hook初探_第4张图片

实现Hook imie功能

新建MianHook,代码如下:

package com.banyan.hook;

import android.telephony.TelephonyManager;

import de.robv.android.xposed.IXposedHookLoadPackage;
import de.robv.android.xposed.XC_MethodHook;
import de.robv.android.xposed.XposedHelpers;
import de.robv.android.xposed.callbacks.XC_LoadPackage;

/**
 * Created by banyan on 2018/1/1.
 */

//实现IXposedHookLoadPackage接口
public class MainHook implements IXposedHookLoadPackage{
    //执行接口的handleLoadPackage方法
    @Override
    public void handleLoadPackage(XC_LoadPackage.LoadPackageParam loadPackageParam) throws Throwable {
        /***
         * 用XposedHelpers类的findAndHookMethod方法查找需要hook的方法并进行hook
         * 第一个参数:需要Hook的类
         * 第二个参数:需要Hook的方法
         * 第三个参数:hook到了方法后要进行的操作
         * */
        XposedHelpers.findAndHookMethod(TelephonyManager.class, "getDeviceId", new XC_MethodHook() {
            /***
             * 在被Hook的方法执行之前要进行的操作
             * 比如改变参数之类的
             */
            @Override
            protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
                super.beforeHookedMethod(param);
            }
            /***
             * 在被Hook的方法执行后要进行的操作
             * 比如改变返回值之类的
             */
            @Override
            protected void afterHookedMethod(MethodHookParam param) throws Throwable {
                String primary = (String) param.getResult();
                //改变被Hook的方法getDeviceId()的返回值
                param.setResult("我是etDeviceId方法,我被Hook了,返回值由" + primary + "改成了:88888888888888");
            }


        });

    }
}

执行效果图:

Android下的Hook初探_第5张图片

结语

Hook是种优雅的利器^-^。。

你可能感兴趣的:(Android)