一,特殊混淆的还原
1.1 还原 AAEncode 与 JJEncode
AAEncode是一种JavaScript代码混淆算法,利用它,可以将代码转换成 颜文字 表示的JavaScript代码。
去掉代码最后的 (‘‘),这是函数的自调用,去除后就是函数的声明。也可以在去掉 (’’)后,加上 .toString(),进一步将方法转化成字符串。
JJEncode 的还原方法与 AAEncode 一致。
1.2 还原JSFuck
JSFuck是一种基于JavaScript的极简编程语言,它使用六个不同的字符来表示所有可能的JavaScript代码。这六个字符是:! + - * . /。由于其极简的语法,JSFuck通常用于教学目的,展示编程语言的基本概念,如运算符优先级和变量声明等。
下面是JSFuck的一些基本操作:
- “!” 代表 NOT 操作,用于翻转布尔值。
- “+” 代表 ADD 操作,用于加法运算。
- “-” 代表 SUBTRACT 操作,用于减法运算。
- “*” 代表 MULTIPLY 操作,用于乘法运算。
- “.” 代表 DECIMAL POINT 操作,用于在数字中表示小数点。
- “/” 代表 DIVIDE 操作,用于除法运算。
虽然JSFuck只使用六个字符,但它可以表达复杂的JavaScript代码。例如,下面是一个简单的JSFuck程序,它将两个数字相加并输出结果:
js复制代码+!!.++[+[+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!+!]
虽然JSFuck的语法非常简单,但它并不适合编写复杂的程序。由于其可读性和可维护性较差,因此在实际开发中很少使用。
JSFuck能够使用六个不同的字符来表示所有可能的JavaScript代码,主要基于以下几个原因:
- 递归和链式操作:JSFuck利用了JavaScript中的递归和链式操作特性。通过连续使用相同的字符,JSFuck可以表示复杂的操作和逻辑。例如,连续的"+“字符可以表示多次的加法操作,连续的”*"字符可以表示多次的乘法操作。
- 位运算:JSFuck也利用了JavaScript中的位运算。通过将数字转换为二进制位,然后进行一系列的位运算(如NOT、AND、OR等),JSFuck可以表示几乎所有的数字和布尔逻辑操作。
- 字符编码:JSFuck还利用了字符编码的知识。通过将不同的字符组合表示特定的编码值,JSFuck可以创建出任何想要的字符串或标识符。
- 堆栈操作:JSFuck还利用了堆栈的概念。通过连续的".“和”/"字符,JSFuck可以模拟出堆栈的行为,如入栈、出栈等。
因此,尽管JSFuck只使用六个不同的字符,但它通过递归、链式操作、位运算、字符编码和堆栈操作等方式,能够表示所有可能的JavaScript代码。
还原JSFuck:
找到代码最后的一个右括号和其对应的左括号,将中间的内容粘贴到控制台打印出来,其内容就是传入的参数,将这部分内容删除,剩下的过程就和 AAEncode 一样了。
二,WebAssembly 分析
WebAssembly 是一种可以使用非 JavaScript 编程语言编写代码并且能在浏览器上运行的技术方案。常见的呈现形式就是 wasm 后缀的文件,即原生代码被编译成了 wasm 后缀的文件,JavaScript 通过调用 wasm 文件得到对应的计算结果,然后配合其他 JavaScript 代码实现页面数据的加载和页面的渲染。
示例使用如下:
进入 wasm 文件的 encrypt 方法后,代码如下:
这里面的逻辑原本是用 C++ 编写的,通过 Emscripten 转化为 wasm文 件,就成了上面的代码形式。
此时已经看不懂了,但可以通过模拟执行的方式得到加密结果:将 wasm 文件下载下来,要使用 python 模拟执行 wasm,可以使用两个 python 库,一个是 pywasm,另一个是 wasmer-python,具体内容见崔庆才第11章节内容。
三,绕过无限 debugger
debugger 是 JavaScript 中定义的一个专门用于断点调试的关键字,只要遇到它,JavaScript 的执行便会在此处中断,进入调试模式。
绕过方式有:
禁用全局断点,禁用局部断点(在断点行右键),条件断点(在断点行右键),替换原始文件等。
禁用全局断点图示: