跳至内容

Jixun's Blog 填坑还是开坑,这是个好问题。

QQ 音乐文件解密 (QMCv2)

支持目前(2021.12)最新的 mflac / mflac0 / mflac1 / mgg / mgg0 / mgg1 后缀的 QQ 音乐的下载加密文件。

项目 #

C++ 实现使用 MIT 授权协议、Rust 实现使用 MIT + Apache 2.0 双协议。

链接:

基本使用方法 #

打开终端,键入:

./QMC2-decoder "加密文件路径.mflac" "解密文件储存路径.flac"

等待数秒后就完成了!

使用 CLI 工具进行解密的实例

或者,使用转译到 WASM 的网页版:

网页版的解密应用

直接选择文件,或将文件拖放到网页即可。每次一个文件。

碎碎念 #

一开始只是想着学学 rust,移植下以前写的 qmc-decode(毕竟代码简单),然后就发现了 unlock-music 这个项目,以及彼时尚未解决的 MGG/FLAC 加密分析

分析过程略。大致分析出加密流程,和 QMCv1 类似的情况是,二者都依赖当前的偏移位置来计算对应的 xor key。

于是初步整理了一些逆向出来的代码片段,如下方的参与 TEA Key 生成的一部分:

void SimpleMakeKey(uint8_t salt, int len, uint8_t *key_buf) {
  for (size_t i = 0LL; len > i; ++i) {
    key_buf[i] = (uint8_t)(fabs(tan((float)salt + (double)i * 0.1)) * 100.0);
  }
}

  uint8_t simple_key_buf[8] = {0};
  SimpleMakeKey(106, 8, simple_key_buf);

// 本地跑出来的结果
// 69 56 46 38 2b 20 15 0b

(为什么这么喜欢这种用利用浮点运算做 key 呢?)

整理完毕后就开了个项目,恰好发现 Visual Studio 2022 竟然支持 CMake 跨平台项目了… 那这必须体验一波。

… 发现问题并不少:

  1. 编译器的不同
    • MSVC 似乎会自动 #include 一部分标准库的定义,在 Windows 下编译成功后到 WSL2 下编译会失败。
    • 部分头文件缺失,如 endian.h。自己最后做了个简单的 polyfill
    • #include 路径解析。有时候明明自动填充都能正常提示,却无法 ctrl-左键 跳到对应的文件。
  2. 重构Refactor)不够智能。
  • 需要头文件和实现放在同一个目录下… 否则就会失败。

不过都是小问题,面向编译器开发一个一个解决即可。

然后就开始各种折腾了:

  • 加了 emscripten 工具链,现在可以编译到 wasm/js 格式了。上线了个实验性质的网页版解密应用
    • 比想象中的要容易一些,但也有麻烦的地方,例如不可以直接传递 primitive 数据的指针(如 char*),必须声明为 uintptr_t 并在代码内利用 reinterpret_cast 之类的类型转换强行更改为正确的类型后调用库导出的函数;
    • 缝缝补补,发了个 @jixun/qmc2-crypto 的包,可以直接在别的 Node 或网页中零配置调用了(不过没有做高级封装,使用者需要手动调用 emscripten 提供的一些底层运行时接口)。随包提供了 TypeScript 定义文件。
    • 折腾了下 GitHub Actions,自动编译 + 提交到 gh-pages 分支。
  • 折腾了 GitHub Actions 跨平台编译(Linux 下编译各平台二进制文件)+ 自动添加发布草稿。

奇怪的知识增加了!.jpg