首页
社区
课程
招聘
[原创] Thunder.app 2.x 逆向分析,实现免登录 + 会员加速
发表于: 2017-3-15 11:25 7416

[原创] Thunder.app 2.x 逆向分析,实现免登录 + 会员加速

2017-3-15 11:25
7416
收藏
免费 0
支持
分享
最新回复 (13)
雪    币: 3190
活跃值: (1816)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
感谢分享 下载支持
2017-3-15 12:08
0
雪    币: 225
活跃值: (136)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
感谢干货!!
2017-3-15 14:40
0
雪    币: 258
活跃值: (68)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4

    测试下,希望不要介意

2017-3-25 16:55
0
雪    币: 23
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
帖子内容呢??
2017-3-31 17:36
0
雪    币: 376
活跃值: (92)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
被删了吗
2017-3-31 18:17
0
雪    币: 3366
活跃值: (1358)
能力值: ( LV4,RANK:40 )
在线值:
发帖
回帖
粉丝
7
貌似升级被吞了?
2017-3-31 18:47
0
雪    币: 27
活跃值: (1698)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8
好可惜,希望内容可以恢复
2017-4-6 16:06
0
雪    币: 1
活跃值: (19)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
9
为啥看不到?
2017-4-9 20:49
0
雪    币: 573
活跃值: (1009)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
10
来晚喽。干货没有喽
2017-4-26 11:41
0
雪    币: 878
活跃值: (496)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
11
https://blog.chichou.me/某软件防篡改分析-2e8d891bacb2
2017-4-26 12:00
0
雪    币: 139
活跃值: (1175)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
12
看不到文章。
2017-5-3 15:54
0
雪    币: 105
活跃值: (30)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
13
#!/usr/bin/env python3
# requires XCode
import subprocess, sys, os, hashlib, plistlib
package = '/Applications/Thunder.app/Contents'
executable = os.path.join(package, 'MacOS/Thunder')
plugins_dir = os.path.join(package, 'BrowserPlugins')
def backup():
    from shutil import copyfile
    backup = executable + '.bak'
    if os.path.isfile(backup):
        print('Backup found, maybe the file has already been patched.')
        sys.exit(-1)
    copyfile(executable, backup)
def patch_exec():
    try:
        output = subprocess.check_output(['nm', executable])
    except:
        print('Failed to execute nm, please install XCode.')
        sys.exit(-1)
    ret_1 = b'\x48\xc7\xc0\x01\x00\x00\x00\xc3'
    ret_0 = b'\x48\x31\xc0\xc3'
    ret = b'\xc3'
    patches = {
        ret_1: [
            '-[LocalTask isValidLixianTask]',
            '-[UserController isVip]',
            '-[UserController isPlatinum]',
            '-[UserController isDiamond]',
            '-[UserController isLogined]'
        ],
        ret_0: [
            '-[AutoLiveUpdateController _shouldCheckUpdate:]',
        ],
        ret: [
            '-[MainWndCtrl checkUpdate:]'
        ]
    }
    lookup = {}
    for code, symbols in patches.items():
        for symbol in symbols:
            lookup[symbol] = code
    base = None
    output = output.decode('utf8')
    with open(executable, 'r+b') as f:
        for line in output.splitlines():
            if '__mh_execute_header' in line:
                base, *_ = line.split()
                base = int(base, 16)
        if not base:
            print('Failed to retrive base address')
            sys.exit(-1)
        for line in output.splitlines():
            if not len(lookup):
                break
            for symbol, code in lookup.items():
                if symbol in line:
                    addr, *_ = line.split()
                    addr = int(addr, 16)
                    offset = addr - base
                    f.seek(offset, 0)
                    f.write(code)  # patch function
                    print('%s has been patched.' % symbol)
                    lookup.pop(symbol)
                    break
    print('remove signature')
    args = ['codesign', executable, '--remove-signature']
    try:
        subprocess.check_output(args)
    except:
        print('failed to remove signature, try run following command manually:')
        print(' '.join(args))
    print('Successfully patched %s' % executable)
def patch_self_check():
    m = hashlib.md5()
    with open(executable, 'rb+') as f:
        while True:
            buf = f.read(1)
            if not buf:
                break
            m.update(buf)
            f.seek(1023, 1)
    digest = m.digest()
    lookup = (15, 4, 6, 3, 1, 0, 7, 8, 2, 11, 10, 13, 12, 14, 9, 5)
    hexdigest = ''.join(['%0.2X' % digest[index] for index in lookup])
    dirname = os.path.join(plugins_dir, hexdigest)
    if not os.path.isdir(dirname):
        os.mkdir(dirname)
def clear_quit_flag():
    plist_path = os.path.join(os.environ.get(
        'HOME'), 'Library/Preferences/com.xunlei.Thunder.plist')
    with open(plist_path, 'rb+') as f:
        pref = plistlib.load(f)
        force_quit = pref.get('ForceQuit')
        if force_quit:
            pref.update({'ForceQuit': True})
            plistlib.dump(pref, f)
            print('Clear quit flag')
if __name__ == '__main__':
    backup()
    patch_exec()
    patch_self_check()
    clear_quit_flag()


顺带去除检查更新。解析符号和偏移使用了 nm,需要安装 Xcode

2017-5-5 10:27
0
雪    币: 259
活跃值: (41)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
14
膜拜
2017-5-5 13:25
0
游客
登录 | 注册 方可回帖
返回
//