Skip to content

Latest commit

 

History

History
365 lines (284 loc) · 13.5 KB

逆向WeApp准备工作.md

File metadata and controls

365 lines (284 loc) · 13.5 KB

逆向WeApp系列分享主要有两个目的:

  1. 分享微信小程序框架-WeApp逆向的全流程,以及涉及到的一些常用的iOS逆向工具及实战技巧.
  2. 分析微信小程序框架-WeApp实现原理, 研究其中用到的一些实用技术,以及怎么把这些实用的技术应用到我们自己的项目中去,具体会以demo的方式分享到GitHub.

[TOC]

目标

这次分享主要是给我们后续分析研究微信小程序框架-WeApp做准备,后续的文章我们将逐渐展开并深入到细节.

准备分为两个阶段:

阶段一:

  1. 越狱iPhone手机
  2. 逆向工具
  3. 砸壳,拿到App的可执行文件

阶段二:

  • 导出头文件
  • tweak编写动态库,进行hook
  • IDA自动分析App的可执行文件

越狱iPhone手机

我们直接用爱思助手进行iPhone越狱,我用的机型是:iPhone7(系统13.4.1).

image

  • 越狱步骤如下图:

image image

  • 看到iPhone上多了个checkra1n就说明越狱成功了.

image
其它机型越狱直接看爱思助手-教程中心.

  • 温馨提示
  1. 断电或重启之后需要重新越狱, 不然Cydia无法工作.
  2. 重新越狱之后, 之前装的一些越狱插件才能恢复正常使用.

逆向工具

在逆向过程中, 涉及到Mac命令, iPhone命令切换操作,对于小白来说,第一次可能会晕掉,先提示一下.

  • Mac命令格式
$ 命令 args
  • iPhone命令格式,因为是以root权限访问iPhone,所以会带有一个root标识.
~ root# 命令 args

Cydia

Cydia的主要目的是为越狱的iOS用户提供一个高级包装工具的图形界面前端以安装不被App Store接受的程序。

  1. 安装

    • VPN下, 打开checkra1n, 安装Cydia.
    • 没有VPN的话,直接下载一个奇游手游加速器, 开启一个韩服游戏加速,可以蹭半个小时VPN去下载安装Cydia. (这也可以,服~)
  2. Cydia 必备插件

    • Apple File Conduit "2" 开启整个手机文件系统(越狱)访问权限; 越狱安装这个插件后,爱思助手可以看到文件管理多了个文件系统(越狱)选项.
    • OpenSSH 用于Mac(客户端)远程登录iPhone(服务器). 从而可以通过Mac(客户端)通过命令操作iPhone(服务器).
  3. 查看Cydia插件,也可以搜索安装 (请确保必备插件安装好后,再往下走流程)

image

USB登录

Mac(客户端)远程登录iPhone(服务器)

//1. USB端口映射
$ python ~/jbScript/.usbmuxd/tcprelay.py -t 22:10010 //服务器端口22 映射到 客户端10010
Forwarding local port 10010 to remote port 22

//2. 新开一个命令窗口,再进行SSH登录
$ ssh root@localhost -p 10010
LionVoom:~ root#_  //此时已登录(第一次会弹授权框),可以用命令控制iPhone了
  • 登录步骤,使用脚本方式(推荐)
    • iOS逆向过程中,上面登录步骤,使用非常频繁,我们最好弄成脚本的形式.
    • jbScript 文件夹放到Mac用户目录下,上面的登录步骤直接简化为脚本调用:
$ sh ~/jbScript/usb.sh
Forwarding local port 10010 to remote port 22

//新开一个命令窗口
$ sh ~/jbScript/login.sh
LionVoom:~ root#_

查找目标App包 MJAppTools

  • MJAppTools命令可以列举出iPhone中的包名、bundleid、App包路径、沙盒路径、是否加壳等信息.
  • 安装 MJAppTools(李明杰)
  • 命令使用
~ root# MJAppTools
  -l  <regex>	列出用户安装的应用
  -le <regex>	列出用户安装的加壳应用
  -ld <regex>	列出用户安装的未加壳应用
  -ls <regex>	列出系统的应用
~ root# MJAppTools -l
# 一共2个应用
-----
# 01 【AsTools pro】 <rn.notes.best>
  /private/var/containers/Bundle/Application/0B5401E6-8B4B-4473-A65E-EEC24024D3EB/AsTools.app
  /private/var/mobile/Containers/Data/Application/C556815E-9C98-460B-A094-521CD9D73FE9
  arm_64 加壳
-----
# 02 【WeChat】 <com.tencent.xin> //包名,bundleid
  /private/var/containers/Bundle/Application/72F2FFD2-2170-477E-99A8-D2DDE6E19A2D/WeChat.app   //微信安装包路径
  /private/var/mobile/Containers/Data/Application/3B0E96A7-9E82-4545-B730-8CDDC44707E2         //微信沙盒路径
  arm_64 加壳

脱壳工具 dumpdecrypted

  • 下载并编译dumpdecrypted.dylib
~ root# DYLD_INSERT_LIBRARIES=dumpdecrypted.dylib /private/var/containers/Bundle/Application/72F2FFD2-2170-477E-99A8-D2DDE6E19A2D/WeChat.app/WeChat
dyld: warning: could not load inserted library 'dumpdecrypted.dylib' into hardened process because no suitable image found.  Did find:
	dumpdecrypted.dylib: code signature in (dumpdecrypted.dylib) not valid for use in process using Library Validation: mapped file has no cdhash, completely unsigned? Code has to be at least ad-hoc signed.
...
//重签名步骤

//1.找到Mac上的可用签名证书
$ security find-identity -v -p codesigning
  1) 8ED1967EFED619841FCF9DA4B08B6EAB5E58FD1B "xxxxxxxxxxx" (CSSMERR_TP_CERT_REVOKED)
  2) ...

//2.进入下载好的dumpdecrypted目录
$ cd ~/Download/dumpdecrypted-master/

//3.重签名
$ codesign --force --verify --verbose --sign "xxxxxxxxxxx" dumpdecrypted.dylib
dumpdecrypted.dylib: signed Mach-O universal (armv7 armv7s arm64) [dumpdecrypted]
// xxx   //App可执行文件路径,可通过MJAppTools工具快速找到这个路径
~ root# DYLD_INSERT_LIBRARIES=dumpdecrypted.dylib xxx

// 例如: 脱壳 WeChat
~ root# DYLD_INSERT_LIBRARIES=dumpdecrypted.dylib /private/var/containers/Bundle/Application/72F2FFD2-2170-477E-99A8-D2DDE6E19A2D/WeChat.app/WeChat 

image

至此,我们已成功脱壳微信,得到WeChat.decrypted.通过爱思助手导出到Mac,去掉后缀得到WeChat(可执行文件).

第一阶段大功告成.


导出头文件 class-dump

终端能直接敲出来的命令会去两个地方找: /usr/bin(系统级) /usr/local/bin/(用户级)

  • class-dump命令
$ class-dump -H Mach-O文件路径 -o 头文件存放目录
  • 导出微信头文件,WeChat(可执行文件)目录下
$ class-dump -H WeChat -o WeChatHeaders
  • 导出App的Mach-O(可执行文件)的头文件, 方便我们后续去hook类中的方法.

  • 微信小程序框架,是以WeApp前缀WA去命名各个实现的类的,例如:WAAppContactPreLoader WAAppTask.h WAJSCoreService.h WAWebViewController.h等等

image

hook工具 theos/tweak

  • 增加环境配置
$ vim ~/.bash_profile

// 增加如下配置, 并保存
export THEOS=~/theos
export PATH=$THEOS/bin:${PATH}
  • 使配置生效
$ source ~/.bash_profile

//验证配置, 能打印出来说明生效了,没打印出来说明还不行,尝试重启终端再执行上述 source 命令
$ echo $THEOS
/Users/xxxx/theos 
  • 创建tweak项目
$ nic.pl
NIC 2.0 - New Instance Creator
------------------------------
  [1.] iphone/activator_event
  [2.] iphone/activator_listener
  [3.] iphone/application_modern
  [4.] iphone/application_swift
  [5.] iphone/cydget
  [6.] iphone/flipswitch_switch
  [7.] iphone/framework
  [8.] iphone/library
  [9.] iphone/notification_center_widget
  [10.] iphone/notification_center_widget-7up
  [11.] iphone/preference_bundle_modern
  [12.] iphone/theme
  [13.] iphone/tool
  [14.] iphone/tool_swift
  [15.] iphone/tweak
  [16.] iphone/tweak_with_simple_preferences
  [17.] iphone/xpc_service
Choose a Template (required): 15        //选择[15.] iphone/tweak
Project Name (required): tweakwechat    //项目名
Package Name [com.yourcompany.tweakwechat]: com.lionvoom.tweakwechat
Author/Maintainer Name [lionvoom]: wu   //作者
[iphone/tweak] MobileSubstrate Bundle filter [com.apple.springboard]: com.tencent.xin //⚠️hook项目的bundleid
[iphone/tweak] List of applications to terminate upon installation (space-separated, '-' for none) [SpringBoard]:
Instantiating iphone/tweak in tweakwechat/...
Done.
  • tweak项目结构
$ tree
.
├── Makefile    //需要配置
├── Tweak.x     //编写hook代码
├── control
└── tweakwappalert.plist
  • Makefile 配置域名和端口号,跟SSH登录iPhone的配置保持一致.因为SSH登录用的是localhost,所以这里配置127.0.0.1.
export THEOS_DEVICE_IP = 127.0.0.1  
export THEOS_DEVICE_PORT = 10010

TARGET := iphone:clang:latest:7.0
INSTALL_TARGET_PROCESSES = SpringBoard


include $(THEOS)/makefiles/common.mk

TWEAK_NAME = tweakwappalertwu

tweakwappalert_FILES = Tweak.x
tweakwappalert_CFLAGS = -fobjc-arc

include $(THEOS_MAKE_PATH)/tweak.mk
  • Tweak.x 模版,我们可以在这里编写hook代码.其中使用的Logos语法非常简单, 相信大家看一次就会了.初始化模版里基本的Logos语法注释写的非常清楚.
//要hook的类
%hook ClassName 

// hook类方法
// Hooking a class method
+ (id)sharedInstance {
	return %orig;
}

// hook带参数的实例方法
// Hooking an instance method with an argument.
- (void)messageName:(int)argument {
    // 打印这个对象的方法调用
	%log; // Write a message about this call, including its class, name and arguments, to the system log. 

    //用原参数调用hook的原方法
	%orig; // Call through to the original function with its original arguments.
	
	//用自定义调用hook的原方法
	%orig(nil); // Call through to the original function with a custom argument.

    //如果使用%orig(),则必须提供所有参数(除了self和_cmd,它们都是自动生成的)。
	// If you use %orig(), you MUST supply all arguments (except for self and _cmd, the automatically generated ones.)
}

// Hooking an instance method with no arguments.
// hook不带参数的实例方法(注意这里带了返回值)
- (id)noArguments {
	%log;
	//hook返回值,做一些事情,再return
	id awesome = %orig;
	[awesome doSomethingElse];

	return awesome;
}

// 
// Always make sure you clean up after yourself; Not doing so could have grave consequences!
%end
  • 在tweek项目下,编译->打包->安装
//1.编译
$ make

//2.打包
$ make package

//3.安装
$ make install
  • 在tweek项目下,编译->打包->安装,将 jbScript 文件夹放到Mac用户目录下,简化为脚本调用:
$ sh ~/jbScript/tweak.sh

默认手机会重启SpringBoard。


  • 热身项目,hook微信小程序启动入口,不启动小程序,改成弹框. tweakwappalert项目

Tweak.x代码

%hook WAAppContactPreLoader
- (void)openApp:(id)arg1 taskExtInfo:(id)arg2 handlerWrapper:(id)arg3 {
	UIAlertView *alert = [[UIAlertView alloc]initWithTitle:m_nsAppId message:@"hook微信小程序启动入口" 
     delegate:nil cancelButtonTitle:@"取消" otherButtonTitles: nil];
	[alert show];
	
	// 不调用hook的原方法,不会启动小程序了
	// %orig 
}
%end

image

  • Cydia里可以查看tweak项目插件,点击进去可以卸载.

image

伪代码分析工具 IDA

image

  • 安装IDA,也可以找个破解版本.
  • 导入WeChat(可执行文件),让IDA自动分析(预计耗时一天),分析完毕后保存结果.
  • F5快捷键,可以转伪代码,比如:微信小程序入口方法实现.

image

第二阶段也大功告成了.