前言

最近我冤种堂哥给我提了一个需求,要下载他买的付费课程,要过期了。我脑子第一件事就是蹦出来,这不就找m3u8下载嘛,立马动手。但是随之而来第一个问题,那个网站的m3u8播放地址是通过点击播放触发js随机生成的,没法找规律(后面深入观察,其实有规律的),于是想到通过Python的seleniumwire模拟浏览器访问,并通过代理,抓到所有请求,过滤到自己要的,顺利的是,出来了。

第一次的M3U8链接

原来以为就这么结束了,很简单的需求,扔文件给他自己拿工具下载。结果过了几天,他说,有些下载不了,我去试了一下,妹的,原来是大部分视频做了m3u8加密,只有前几个没有加密,我服了,我说我咋试了没问题呢。刚好最近要进实习公司的渗透部门,于是就开始了下面,漫天头发飘舞的过程(JS逆向)。

溯源

首先,打开开发者工具找到m3u8文件,可以看到有两个链接

清晰度

一个链接其中有三个清晰度不同多的m3u8的文件,下面的一个链接就是我们加载的m3u8的文件

小辣鸡

这里可以看到,它是使用的AES-128加密,秘钥链接和iv值都给出了。但是事情真的那么简单吗?

直接访问key链接,发现无法访问这个链接。看来key的链接是加密了。

无法访问

搜索key,可以看到,key的链接确实是加密了,后面加了个token。我们请求一下这个链接看看

加密后的地址

得到了一个32字节的文件,但是按照道理来说AES加密,这个文件应该是16字节的才对。看来这个key是加密过的。没办法,只能去看js了

key文件大小

从堆栈里看到,是由这个js完成的工作

堆栈调用

可以看到这个请求都是从poliy player里面发出来的,那我们把js拉下来进里面看看这家伙究竟在搞什么鬼东西。因为是aes加密,所以搜索一下decrypt,找到了这个最可疑函数。

JS内容

这个bt函数就是key的解密了。那不是简单了,直接本地映射调试这个玩意,而且是AES是吧。直接charles代理映射本地,小样,整不死你(其实找中途很长时间)。

加自定义调试

这不就出来了嘛

解密key和iv

但是咋都有32位,妹的看来是key和iv二次加密了,而且看起来是还套了一层Hex编码,我去,真牛。

后来

经过研究了整个页面和JS,和查资料才知道,这是比较流行的某威AES二次加密,问网上大佬,开口就要300块才给你结果,也不教你原理,唉,我还是自己搞定吧。经过几天折腾,总结核心是有个JSON,得二次解密(JS生成的某个很重要的id转的md5作为密钥)转Hex编码才可以拿到请求体,再从里面拿到重要数据。才能去解开那个key文件,再拿key去解开m3u8里的内容。(涉及法律就不细说步骤了)

json内容

针对这个我写了个加解密类,但只是针对该类网站

# 加密类封装
class Crypto:
    def __init__(self, key, iv):
        self.key = key
        self.iv = iv

    # md5加密
    @staticmethod
    def encryptMD5(data):
        md5 = hashlib.md5()
        seed_const = data.encode()
        md5.update(seed_const)
        str_md5 = md5.hexdigest()
        return str_md5

    # AES解密
    def decryptAES(self, data):
        decode = AES.new(self.key, AES.MODE_CBC, self.iv)
        xxx = lambda s: s[:-ord(s[len(s) - 1])]
        plain_text = base64.b64decode(xxx(decode.decrypt(a2b_hex(data)).decode())).decode()
        return plain_text

从该过程就看出来多麻烦,都是不断踩坑得出来的,最大最大的坑就是每次习惯性直接拿着字符串直接加密,导致一直报错,后面才知道是要编码一下。

大概的解密过程

​ 经过排查,好多网站都使用了他家的视频加密方案,还能说通用吧(看了好几个网站都可以用哈哈),至少我老哥这个需求完美完成了,榨得一滴都不剩了。

结果

爬下来的M3u8以及密钥

将它放入逍遥批量下载器嘎嘎下

批量下载结果

别问我为什么不用Java写这个玩意,我一开始就是拿java写的加解密,直接痛苦死,AES的自定义偏移量计算,脑子都要炸了,不像Python导包怪,直接用。

总结

  • 编码是有特征的,比如hex十六进制加密json时就会eyJw开头、unicode就会\u和\x,能分辨编码和转换是渗透最基础的基本功。
  • 各种加密方法也是得不断学习得知。
  • 无论生活还是学习要善于观察,勇于尝试。