iOS 逆向去除视频广告
让人头疼的T讯视频广告,网上一大把逆向去除方案。既然是学习,就试着自己摸索一把
实验基于app版本: version 7.6.5
前半部分是实验学习过程,可以当做无聊吹水,后半部分是最终方案,嫌啰嗦的可以直接看后半部分.
逆向过程
按照往常的套路,先用reveal找出包含视频广告所在页面的UI结构,找出广告view,在创建广告组件的时候进行拦截或者主动移除广告组件应该是可行的,在reveal的结果中找到广告组件的类名:QNBPlayerVideoAdsView
, 很遗憾在ipa文件解包出来的头文件列表里面并没有这样一个文件,说明这个类是跟其它类共用了一个文件。试着找一下QNBPlayerVideoAdsView
的superView
, QLSmallPlayerHeaderView
作为 QNBPlayerVideoAdsView
的superView
也很快让人失望,因为它的头文件极其简单:
#import "UIView.h"
@interface QLSmallPlayerHeaderView : UIView
{
}
- (id)hitTest:(struct CGPoint)arg1 withEvent:(id)arg2; // IMP=0x000000010094d668
@end
从reveal这个方向被终结。
换个角度,试着从VC里面进行处理?那么首要任务就是找到播放视频所在的控制器VC类名,这里有两个方案
前提是使用cycript进行动态调试
方案一:
cy# [UIApplication sharedApplication].keyWindow.rootViewController
#"<QLTabBarController: 0x1088e8000>"
cy# #0x1088e8000.childViewControllers
@[#"<QLNavigationController: 0x1088fb200>",#"<QLNavigationController: 0x109991200>",#"<QLNavigationController: 0x1099f8600>",#"<QLNavigationController: 0x1099f9c00>",#"<QLNavigationController: 0x108887c00>"]
cy# #0x1088fb200.viewControllers
@[#"<QLHomeController: 0x1088ce400>"]
cy# #0x1088fb200.viewControllers
@[#"<QLHomeController: 0x1088ce400>",#"<QLVideoDetailViewController: 0x108b78600>"]
很明显QLVideoDetailViewController
就是我们的目标类
方案二:
来自iosre
我们的大概方向是找到一些有关ad(广告)的方法,根据方法名猜测方法的作用,hook方法进行验证,在
QLVideoDetailViewController
里面找了一些可疑方法进行hook,没生效。在QLVideoDetailViewController
的基类QLBaseVideoDetailViewController
中进行同样的尝试, 下面方法引起了我的注意,很有可能突破点就在这里
- (id)dicInfoWithUserIsLogin:(_Bool)arg1 videoPayType:(long long)arg2 needCoupon:(_Bool)arg3 isVip:(_Bool)arg4 displayStyle:(int)arg5; // IMP=0x0000000100d1e7e8
尝试了几下,目前还不清楚arg2、arg5的参数应该如何传递,以及返回值该如何构造,略显麻烦,暂时放弃这个方法。小黄书上说编写tweak通过hook相关方法查看日志是可以知道arg2、arg5、以及返回参数的,有兴趣的可以自己尝试。
再换个方向,可否直接修改全局的信息管理类、会员管理类?
查找userinfo、vip等关键词,在文件QLAdsBusiness
,QLVideoDetailLinkageAdsHelper
中hook了一些可疑方法,均以失败告终。
继续寻找,QLVipManager
里面的几个方法让我有了一点兴奋,方法的作用是判断是否vip, T讯视频vip是自动跳广告的呀,说干就干,再试一把
cy# QLVipManager.prototype['isVipOrVipVisitor'] = function(){return YES};
function (){return YES}
cy# QLVipManager.prototype['isValid'] = function(){return YES};
function (){return YES}
cy# QLVipManager.prototype['isAnnualVipWithCache'] = function(){return YES};
function (){return YES}
cy# QLVipManager.prototype['isVipOrVipVisitorWithCache'] = function(){return YES};
function (){return YES}
cy# QLVipManager.prototype['isVipVisitorWithCache'] = function(){return YES};
function (){return YES}
cy# QLVipManager.prototype['isVipWithCache'] = function(){return YES};
function (){return YES}
再尝试一下,广告已经去掉!
逆向方案
编写tweak
首先创建工程
➜ theosProject nic.pl
NIC 2.0 - New Instance Creator
------------------------------
[1.] iphone/activator_event
[2.] iphone/application_modern
[3.] iphone/application_swift
[4.] iphone/flipswitch_switch
[5.] iphone/framework
[6.] iphone/library
[7.] iphone/preference_bundle_modern
[8.] iphone/tool
[9.] iphone/tool_swift
[10.] iphone/tweak
[11.] iphone/xpc_service
Choose a Template (required): 10
Project Name (required): removeAd
Package Name [com.yourcompany.removead]: com.pengyin.removead
Author/Maintainer Name [whw]: whw
[iphone/tweak] MobileSubstrate Bundle filter [com.apple.springboard]: com.tencent.live4iphone
[iphone/tweak] List of applications to terminate upon installation (space-separated, '-' for none) [SpringBoard]: live4iphone
Instantiating iphone/tweak in removead/...
Done.
然后编辑tweak.x文件
%hook QLVipManager
- (BOOL)isVipOrVipVisitor{
return YES;
}
- (BOOL)isValid{
return YES;
}
- (BOOL)isAnnualVipWithCache{
return YES;
}
- (BOOL)isVipOrVipVisitorWithCache{
return YES;
}
- (BOOL)isVipVisitorWithCache{
return YES;
}
- (BOOL)isVipWithCache{
return YES;
}
%end
最后
➜ removead make package install
可能大家注意到我这里并没有指定targetip,targetport,是因为我将这些东西放到了环境变量里面,具体可参考: 里面关于theos的模块儿
这样动态库就注入到app里面啦,畅享无广告的爽快,虽然我们hook的方法强制指定为会员,事实上vip视频还是看不了的(服务端做了认证)
第一次实践,还是感叹cycript的强大,感觉跟个狗杂一样的东西,包含OC、也有js,就是这样一个狗杂,就是这样强大,安利一波cycript官网