Obfuscator 混淆学习

本文介绍了使用Obfuscator进行JS代码混淆的方法,并通过一个示例详细解释了混淆前后代码的变化及去混淆过程。文章还提供了用于去混淆的脚本代码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 前言

          最近正式工作了,这段时间比较忙,上篇android脱壳机可能要等一段时间,不过看雪已经有人公布android7.1的脱壳机的源码了。之前验证了android8.1的脱壳,感觉android8.1增加了参数解引用的问题,会有一些坑点导致程序会crash。所以暂时先放弃android8.1,过段时间先复现android7.1的脱壳机。然后工作这段时间,有遇到js混淆,打算学习一下。

js混淆比较出名的工具就有Obfuscator,但是Obfuscator缺点在于平坦化做的一般,有些企业会自己做一下平坦化,再用Obfuscator来混淆。所以先学习Obfuscator很有必要性。

js混淆学习前置知识

        建议先学习了解AST树和解析AST树的框架,可以先看下面的参考链接,补充前置知识。

Obfuscator混淆解析

         Obfuscator 在线混淆网站https://obfuscator.io/ 底下有介绍相关混淆内容,这里直接看提供例子来解析的代码。

var _0x3ed0 = ['1241023ikpdYM', 'Hello\x20World!', '291190xIUkft', '1251274vQVPdI', '124952hgHyOi', '1983KQSSIW', '247DipWFn', '7354VgseoG', '49680CQWPxl', '1ZTWTUo', '648lISKkF'];

function _0x4ed9(_0x475ec5, _0x372034) {
  return _0x4ed9 = function (_0x3ed0df, _0x4ed9c4) {
    _0x3ed0df = _0x3ed0df - 0x96;
    var _0x5a22f3 = _0x3ed0[_0x3ed0df];
    return _0x5a22f3;
  }, _0x4ed9(_0x475ec5, _0x372034);
}

(function (_0xa942b4, _0x57410c) {
  var _0x4e4980 = _0x4ed9;

  while (!![]) {
    try {
      var _0x1e86fa = parseInt(_0x4e4980(0x9b)) + parseInt(_0x4e4980(0x9e)) + -parseInt(_0x4e4980(0x97)) + -parseInt(_0x4e4980(0x9c)) * -parseInt(_0x4e4980(0xa0)) + -parseInt(_0x4e4980(0x98)) * parseInt(_0x4e4980(0x9d)) + -parseInt(_0x4e4980(0x96)) + parseInt(_0x4e4980(0x99)) * parseInt(_0x4e4980(0x9a));

      if (_0x1e86fa === _0x57410c) break;else _0xa942b4['push'](_0xa942b4['shift']());
    } catch (_0x178fbf) {
      _0xa942b4['push'](_0xa942b4['shift']());
    }
  }
})(_0x3ed0, 0xb3f61);

function hi() {
  var _0x81b55a = _0x4ed9;
  console['log'](_0x81b55a(0x9f));
}

hi();

/*
source code
function hi() {
  console.log("Hello World!");
}
hi();
*/

暂时可以看出Obfuscator有如下特点:

1.大数组变量

2.位移大数组函数

3.自解密函数

由于代码较短,还未看出平坦化,不过不着急,先尝试把这个还原。

解析ast推荐在线网站: https://astexplorer.net/

通过分析ast和混淆代码的分析,现在去混淆思路:

1.抠出自解密函数和解密函数的name

2.遍历调用函数和初始化赋值操作,获取解密函数的结果并且替代节点

3.修复函数调用方式,比如console['log']修复成console.log

修复办法:

1.使用ast来解析出body,转化成相关代码,获取到解密函数

2.遍历并判断调用解密函数的点,来进行获取最后结果

3.使用ast在线解析网站,对比二者不同,来进行修复

去混淆脚本如下

const fs=require('fs');
const parser=require('@babel/parser');
const traverse=require('@babel/traverse').default;
const types =require('@babel/types');
const generator=require('@babel/generator').default;
const { type } = require('os');
const { exit } = require('process');

var arguments=process.argv;
if(arguments.length<4)
{
  console.log("need input file and output file path");
  exit();
}
const inputFilePath = arguments[2];
const outputFilePath=arguments[3];

const jscode=fs.readFileSync(inputFilePath,
{
    encoding:"utf-8"
});

var globalArrayName;
var globalDecode;
var DecodeFunName;
var globalDecodeList=new Array();


/*

function getVariableName(path)
{
    var node = path.node;
    if(!types.isArrayExpression(node.init))
    {
      return;
    }
    //console.log(node.id.name);
    globalArrayName=node.id.name;
    
}
*/

function parserAst(ast)
{
    globalArrayName=ast.program.body[0].declarations[0].id.name;
    DecodeFunName=ast.program.body[1].id.name;
    globalDecodeList.push(DecodeFunName);
    var runCode=ast.program.body.slice(3,);
    ast.program.body=ast.program.body.slice(0,3);
    globalDecode=generator(ast).code;
    ast.program.body=runCode;
    return ast;
}

function getDecodeList(path) {
    var node=path.node;
    if(!types.isIdentifier(node.id)||!types.isIdentifier(node.init)||node.init.name!=DecodeFunName)
    {
        return;
    }
    globalDecodeList.push(node.id.name);
    path.remove();
}

function funToStr(path)
{
    var node =path.node;
    if (!types.isIdentifier(node.callee)||globalDecodeList.indexOf(node.callee.name)==-1)
    {
                return;
    }
    //console.log(path.toString());
    node.callee.name=DecodeFunName;
    let value = eval(globalDecode+path.toString());
    //console.log(value);
    path.replaceWith(types.valueToNode(value));
    
}

function fixFunCall(path)
{
    var node =path.node;
    if(!types.isIdentifier(node.property))
    {
        return;
    }
    let name =node.property.name;
    path.node.property=types.stringLiteral(name);
    path.node.computed=true;
}

function solveOb(ast)
{
    //eval(globalDecode);

    traverse(ast,{
        VariableDeclarator:getDecodeList,
        CallExpression:funToStr,
        MemberExpression:fixFunCall
      });
      return ast;
}

let ast=parser.parse(jscode);
ast=parserAst(ast);
ast=solveOb(ast);

let code=generator(ast).code;
console.log(code);

总结

        多在ast在线网站查看相关数据,多加对比。后续会写长的代码来去混淆,使其体现出平坦化,并且让脚本尽量通用化。

参考链接

Js Ast一部曲:高完整度还原某V5的加密

https://bbs.nightteam.cn/thread-417.htm

  

        

   

淘宝花钱买的最新版!需要的拿去! This asset obfuscates your code to make it harder for bad guys to reverse engineer your projects. Specifically designed for Unity, it seamlessly links in with its build process. The top priority of this package is to work straight out of the box with no extra steps required. While other obfuscators can stop a game from working, Beebyte's obfuscator looks for specific Unity related code that must be protected. The contents of your source files are unchanged, the obfuscation targets the compiled assembly. Features: - Supports IL2CPP - Supports Assembly Definition Files (Unity 2017.3+) - Removes Namespaces without any conflicts - Recognises Unity related code that must not be changed - Renames Classes (including MonoBehaviours) - Renames Methods - Renames Parameters - Renames Fields - Renames Properties - Renames Events - String literal obfuscation - Adds fake methods - Easy and extensive customisation using the Unity inspector window - Consistent name translations are possible across multiple builds and developers - Semantically secure cryptographic naming convention for renamed members The asset works for both Unity Free and Unity Pro version 4.2.0 onwards (including Unity 5 & 2017 & 2018). Build targets include Standalone, Android, iOS, WebGL, UWP. Other platforms are not guaranteed or supported but may become supported at a future date. IL2CPP builds are much harder to reverse engineer but strings and member information (class, method names etc) are visible in the global-metadata.dat file. Obfuscation will apply to this file adding further security. Why not complement your security with the Anti-Cheat Toolkit - a great third party asset. For more information about the Obfuscator, please see the FAQ
This asset obfuscates your code to make it harder for bad guys to reverse engineer your projects. Specifically designed for Unity, it seamlessly links in with its build process. The top priority of this package is to work straight out of the box with no extra steps required. While other obfuscators can stop a game from working, Beebyte's obfuscator looks for specific Unity related code that must be protected. The contents of your source files are unchanged, the obfuscation targets the compiled assembly. Features: - Supports IL2CPP - Supports Assembly Definition Files (Unity 2017.3+) - Removes Namespaces without any conflicts - Recognises Unity related code that must not be changed - Renames Classes (including MonoBehaviours†) - Renames Methods - Renames Parameters - Renames Fields - Renames Properties - Renames Events - String literal obfuscation - Adds fake methods - Easy and extensive customisation using the Unity inspector window - Consistent name translations are possible across multiple builds and developers - Semantically secure cryptographic naming convention for renamed members The asset works for both Unity Free and Unity Pro version 4.2.0 onwards (including Unity 5 & 2017 & 2018). Build targets include Standalone, Android, iOS, WebGL, UWP. Other platforms are not guaranteed or supported but may become supported at a future date. † There is currently a bug with renaming MonoBehaviour classes on Unity 2018.2. A bug report has been submitted to Unity. IL2CPP builds are much harder to reverse engineer but strings and member information (class, method names etc) are visible in the global-metadata.dat file. Obfuscation will apply to this file adding further security. Why not complement your security with the Anti-Cheat Toolkit - a great third party asset. For more information about the Obfuscator, please see the FAQ
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值