在前面关于Substrate的介绍中我们已经讲了用Substrate hook java代码,现在我们讲下怎么用它hook native代码。hook native代码我们需要编写Substrate extensions,它跟native库一样被视作标准的android包的一部分, 将作为一个共享库被编译 (使用复合扩展名.cy.so)。

一、相关API

(1)MSConfig
 
名称 描述
Filter:Executable 开发者试图hook的可执行文件的完整路径。一般为zygote, "/system/bin/app_process"。
Filter:Library 开发者试图hook的lib库的名称,比如hook __android_log, 则指定 "liblog.so".
如:
MSConfig(MSFilterExecutable, "/system/bin/app_process")
MSConfig(MSFilterLibrary, "liblog.so")

(2)void MSHookFunction(void *symbol, void *hook, void **old);

参数 描述
symbol   被替换代码的地址,一般是一个函数
hook The address of an ABI-compatible replacement for the code at the address referenced by symbol.
old 指向函数指针的指针,用来调用原函数的实现。如果不需要对原函数进行处理则为NULL
示例:
 void *(*oldConnect)(int, const sockaddr *, socklen_t);

 void *newConnect(
int socket, const sockaddr *address, socklen_t length
) {
if (address->sa_family == AF_INET) {
sockaddr_in *address_in = address;
if (address_in->sin_port == htons()) {
sockaddr_in copy = *address_in;
address_in->sin_port = htons();
return oldConnect(socket, &copy, length);
}
} return oldConnect(socket, address, length);
} MSHookFunction(&connect, &newConnect, &oldConnect);

(3)void *MSFindSymbol(MSImageRef image, const char *name);

参数 描述
image 指定一个有效的image引用(通过调用MSGetImageByName返回的结果)。如果为NULL,则会搜索所有image
name 待查找的原始镜像符号的名称。这并非如dlopen所加载的高级符号,它可能需要以下划线为前缀或其他特定平台的编码。
return 符号的地址(调整为ARM/Thumb类型),如果不能定位符号则返回NULL
示例:
 MSImageRef image;
image = MSGetImageByName("/usr/lib/libSystem.B.dylib"); void *(*palloc)(size_t);
palloc = (void *(*)(size_t)) MSFindSymbol(image, "_malloc"); void *data = (*palloc)();
free(data);

(4)MSImageRef MSGetImageByName(const char *file);

参数 描述
file 根据so或者动态库的完整路径加载image
return 可以被其它API使用的image引用,如果image没有加载则为NULL
示例:
 MSImageRef image;
image = MSGetImageByName("/system/lib/libc.so");
if (image != NULL)
/* image is loaded */;

二、使用示例

下面以前一篇过签名验证的hook代码为例讲解native hook的代码编写过程:

1.创建android native工程HookVerify,so层hook并不需要界面(作为Cydia Substrate的扩展模块),所以在新建工程时无需建activity。接下来在工程目录下新建jni文件夹,并将libsubstrate.so,libsubstrate-dvm.so,substrate.h三个文件拷贝至jni文件夹下。
在jni目录下创建HookVerify.cy.cpp文件。

2.配置Manifest文件
需要添加权限:<uses-permission android:name="cydia.permission.SUBSTRATE"/>
由于我们只使用native code,将android:hasCode设为false。
3.Android.mk文件编写:
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := substrate
LOCAL_SRC_FILES := libsubstrate.so
include $(PREBUILT_SHARED_LIBRARY)
include $(CLEAR_VARS)
LOCAL_MODULE := substrate-dvm
LOCAL_SRC_FILES := libsubstrate-dvm.so
include $(PREBUILT_SHARED_LIBRARY)
include $(CLEAR_VARS)
LOCAL_MODULE := HookVerify
#一定要有.cy作后缀
LOCAL_SRC_FILES := HookVerify.cy.cpp
LOCAL_LDLIBS := -llog
LOCAL_ARM_MODE := arm
LOCAL_LDLIBS += -L$(LOCAL_PATH) -lsubstrate-dvm -lsubstrate
include $(BUILD_SHARED_LIBRARY)
4.HookVerify.cy.cpp代码:
 #include <jni.h>
#include "substrate.h"
#include <android/log.h>
#include <unistd.h>
#include <stdio.h>
#include <fcntl.h>
#include <sys/types.h>
#include <string.h>
#include <sys/stat.h>
#define TAG "HOOKDEMO"
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, TAG, __VA_ARGS__)
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO, TAG, __VA_ARGS__)
char* AppName = NULL;
//指定要hook的lib 库:
MSConfig(MSFilterLibrary, "/system/lib/libdvm.so");
//保留原来的地址:
void *(*oldUnzOpen64)(const char* filepath);
//替换的函数
void *newUnzOpen64(const char* filepath){
return oldUnzOpen64("/sdcard/myapk.apk");
}
//Hook dvmLoadNativeCode
bool (*_dvmLoadNativeCode)(char* pathName, void* classLoader, char** detail);
bool My_dvmLoadNativeCode(char* pathName, void* classLoader, char** detail){
bool b_Result = _dvmLoadNativeCode(pathName,classLoader,detail); //进行原来的调用,不影响程序运行
//LOGD("dvmLoadNativeCode AppName:%s", AppName);
if(strstr(pathName,"AppVerify") != NULL){
LOGD("dvmLoadNativeCode Find Hook");
MSImageRef image = MSGetImageByName(pathName);
if(image != NULL){
void* mFun = MSFindSymbol(image, "unzOpen64");
//开始Hook fork
if(mFun != NULL){
LOGD("dvmLoadNativeCode Hook");
//MSHookFunction(mFun,(void*)&My_fork,(void**)&_fork);
36             MSHookFunction(mFun, (void*)&newUnzOpen64, (void**)&oldUnzOpen64);
}
}
}
return b_Result;
}
//在初始化的时候进行hook,具体如下:
//Substrate entry point
MSInitialize{
__android_log_print(ANDROID_LOG_ERROR, TAG, "Substrate initialized.");
MSImageRef image;
image = MSGetImageByName("/system/lib/libdvm.so"); //载入lib
if (image != NULL)
{
//注意这个是个c++函数,可以通过objdump来获取
void * dvmload = MSFindSymbol(image, "_Z17dvmLoadNativeCodePKcP6ObjectPPc");
if(dvmload == NULL)
{
LOGD("error find dvmLoadNativeCode ");
}
else{
MSHookFunction(dvmload,(void*)&My_dvmLoadNativeCode,(void **)&_dvmLoadNativeCode);
}
}
else{
LOGD("ERROR FIND LIBDVM");
}
}

这样就完成了hook代码的编写。安装运行就行了。

利用Cydia Substrate进行Android HOOK(二)的更多相关文章

  1. 利用Cydia Substrate进行Android HOOK

    Cydia Substrate是一个代码修改平台.它可以修改任何主进程的代码,不管是用Java还是C/C++(native代码)编写的.而Xposed只支持HOOK app_process中的java ...

  2. 使用Cydia Substrate 从Native Hook Android Native世界

    同系列文章: 使用Cydia Substrate 从Native Hook Android Java世界 使用Cydia Substrate Hook Android Java世界 一.建立工程 手机 ...

  3. 使用Cydia Substrate 从Native Hook Android Java世界

    这里介绍了如何使用Cydia Substrate Hook安卓Java世界.这篇文章介绍如何从Native中Hook 安卓Java世界. 手机端配置见之前文章. 一.建立工程 建立一个Android工 ...

  4. Android上玩玩Hook:Cydia Substrate实战

    作者简介:周圣韬,百度高级Android开发工程师,博客地址:http://blog.csdn.net/yzzst 了解Hook 还没有接触过Hook技术读者一定会对Hook一词感觉到特别的陌生,Ho ...

  5. Cydia Substrate based DexDumper's weakness

    得益于Cydia Substrate框架,HOOK Native函数变得简单,也给脱壳带来方便. 像ijiami免费版,360,classes.dex被加密到so文件并运行时释放到内存,因此针对相关函 ...

  6. Android逆向之旅---Native层的Hook神器Cydia Substrate使用详解

    一.前言 在之前已经介绍过了Android中一款hook神器Xposed,那个框架使用非常简单,方法也就那几个,其实最主要的是我们如何找到一个想要hook的应用的那个突破点.需要逆向分析app即可.不 ...

  7. Android HOOK工具Cydia Substrate使用详解

    目录(?)[+] Substrate几个重要API介绍 MShookClassLoad MShookMethod 使用方法 短信监控实例   Cydia Substrate是一个代码修改平台.它可以修 ...

  8. 使用Cydia Substrate Hook Android Java世界

    从来没接触过Android的HOOK,在看雪上找到了一篇HOOK 的文章,但是太复杂了,应该是本地环境问题,测试不成功. 后来搜到Cydia Substrate,看了几篇文章,进入官网查看了一下文档, ...

  9. 利用FFmpeg玩转Android视频录制与压缩(二)<转>

    转载出处:http://blog.csdn.net/mabeijianxi/article/details/72983362 预热 时光荏苒,光阴如梭,离上一次吹牛逼已经过去了两三个月,身边很多人的女 ...

随机推荐

  1. MySQL分区表

    当数据库数据量涨到一定数量时,性能就成为我们不能不关注的问题,如何优化呢? 常用的方式不外乎那么几种: 1.分表,即把一个很大的表达数据分到几个表中,这样每个表数据都不多. 优点:提高并发量,减小锁的 ...

  2. 【1】CommonCode快速代码集

    阅读目录 CommonCode是什么? CommonCode包括哪些内容? 版本信息   回到顶部 CommonCode是什么? 简单的说,CommonCode是作者在经历各种"试错&quo ...

  3. Xcode中iPhone iPad模拟器调整大小的方法

    Xcode中调试iPad程序默认的iPad模拟器非常小,如何方法iPad模拟器的显示尺寸呢? 选中iOS模拟器,在“Window -> 缩放比例”中就可以调整了. 快捷键: Command + ...

  4. 滑动返回类库SwipeBackLayout的使用问题,解决返回黑屏,和看到桌面

    SwipeBackLayout是一个很好的类库,它可以让Android实现类似iOS系统的右滑返回效果,但是很多用户在使用官方提供的Demo会发现,可能出现黑屏或者返回只是看到桌面背景而没有看到上一个 ...

  5. 2014中国软件开发者调查(一):Java最受欢迎 第二语言JS使用比例最高

    2014 年 3 月 20 日到 4 月 25 日期间,CSDN 通过在线问卷渠道进行了中国软件开发者调查,本次调查问卷得到了近万名开发者踊跃支持.日前这份调查报告已经出炉,CSDN 将就调查结果连续 ...

  6. CSS计数器的趣味时光

    CSS计数器是“啊太好了,竟不知道CSS可以做这啊”这类非常有趣的众多特性之一.简言之,用CSS使你持续某增加某个量,而无需JavaScript. 简单计数器 我们从这个简单的分页示例开始: 你见到的 ...

  7. Scala 深入浅出实战经典 第62讲:Scala中上下文界定内幕中的隐式参数实战详解

    王家林亲授<DT大数据梦工厂>大数据实战视频 Scala 深入浅出实战经典(1-87讲)完整视频.PPT.代码下载: 百度云盘:http://pan.baidu.com/s/1c0noOt ...

  8. 解决部份机型toast不显示问题

    问题:部份机型不显示toast 解决方案: 1.自己在设置里面去允许通知,但是显然客户会说别的app都可以,so 2.自定义解决.查看toast的源码发现其附着在window上 源码下载地址:http ...

  9. 【转帖】ECLIPSE-JEE-LUNA-SR2官方汉化教程

    ECLIPSE-JEE-LUNA-SR2官方汉化教程 工具/原料 Eclipse-jee-luna-SR2 步骤/方法 1.在浏览器输入网址http://www.eclipse.org/babel/d ...

  10. [知识库分享系列] 四、ASP.NET MVC and Winform

    知识库分享系列: [知识库分享系列] 三.Web(高性能Web站点建设) [知识库分享系列] 二..NET(ASP.NET) [知识库分享系列] 一.开篇 分享介绍本篇分享两个知识库节点,分别为“AS ...