zoukankan      html  css  js  c++  java
  • 微信DAT图片解密实现

    PC版的微信将用户接收到的所有图片加密为DAT文件并保存在本地,具体保存位置就看各自的微信-文件管理设置了。

    DAT格式文件不能直接打开,强行查看也就只能看到一些乱码。如果能够找到解密的方式,就可以很方便在本地筛选图片了,虽然大部分可能只是聊天吹水的内容。

    加密方式

    首先我尝试一下在微信中发送一张新图片(如果是转发图片,并不会有新的文件记录。换句话说,微信去重了),然后在微信加密存储目录中找到新增的记录,可以看到这两个文件的文件大小是一模一样的。

    微信需要处理用户接收到的所有图片,加密方式势必不能是特别复杂并且是可逆的。如果用AES、DES等加密算法,这么多群开起车来你扛的住,CPU也扛不住啊~

    公布答案,其实是”异或加密“,对每位字节使用同一个值进行异或计算得到加密文件。

    解密原理

    现在我们只需要知道“密钥”就可以对文件进行解密还原了。至于为啥,可以参考下异或运算的”自反法则 ( a ⊕ b ⊕ a == b )“。

    假设 a 为原文,b为密钥,c为密文,则有 c = a ⊕ b。

    则 c ⊕ a = a ⊕ b ⊕ a = b

    所以我们只需要知道一个图片原本的字节,就能计算”密钥“了。

    总所周知(好吧,我也是刚查了才知道),JPEG文件的开始2个字节都是FF D8,这是JPEG协议规定的SOI文件头。

    通过程序读取加密文件的前两个字节为11 36,分别和FF D8进行异或计算,可以得到结果都为EE,就是加密的密钥了。

    11 ⊕ FF = EE

    36 ⊕ D8 = EE

    以此类推jpg/png/gif格式也就可以通过相同方法计算出密钥。

    图片标识字节

    • jpg FF D8
    • png 89 50
    • gif 47 49

    代码实现

    func Format(filePath string) byte {
    	buf, _ := ioutil.ReadFile(filePath)
    	imgbytes := [3][]byte{
    		{0xff, 0xd8},
    		{0x89, 0x50},
    		{0x47, 0x49},
    	}
    	for _, xor := range imgbytes {
    		if xor[0]^buf[0] == xor[1]^buf[1] {
    			return byte(xor[0] ^ buf[0])
    		}
    	}
    	return byte(0)
    }
    

    最后解密就只需要对加密文件的每个字节用”密钥“进行异或计算就好了,自己去尝试吧

    PS:不同图片的后缀名别忘了处理

  • 相关阅读:
    oracle导入脚本sh
    spring事件
    mysqls数据库中 数据存在则更新,不存在则插入
    mysql中字符串的数据类型
    PHP实现从文本域textarea输入数据库并保持格式输出到html页面
    PHP实现返回上一页不刷新 和刷新的方法
    KSweb 中如何使用桌面的navicat链接数据库?
    KSweb不能上传文档?
    错误:Parse error: syntax error, unexpected '[' in D:phpStudyWWWdw_newplug-in
    PHP在使用MVC模式编写页面时,include的view页面后加载不上CSS样式问题的原因及解决方法?
  • 原文地址:https://www.cnblogs.com/cplemom/p/15785254.html
Copyright © 2011-2022 走看看