Обфускация кода JS | обратная серия js
Обфускация кода JS | обратная серия js

0x01 Введение

Статья относительно длинная и подготовлена ​​для всех, чтобы обеспечить эффективную передачу знаний. PDF версия, размещенная в конце статьи

Обфускация кода JavaScript — это метод, который преобразует и модифицирует код, чтобы усложнить его понимание и реверс-инжиниринг. Его основная цель — повысить сложность и запутанность кода, тем самым улучшая безопасность кода и возможности защиты интеллектуальной собственности.

Вот некоторые из основных последствий запутывания кода JavaScript:

  • Предотвращение обратного проектирования кода: обфускация делает логику кодирования неясной,Затруднить злоумышленникам понимание принципа работы кодиза. Это не позволяет злоумышленникам конкурировать с вами путем прямого анализа и изменения ваших файлов.
  • Защита интеллектуальной собственности: запутывание кода может предотвратить незаконное присвоение икопирование вашего исходного кода другими лицами. путаница,Вы можете лучше защитить свои права интеллектуальной собственности,Убедитесь, что ваш исходный код не используется не по назначению или без разрешения.
  • Уменьшите размер кода: технология обфускации может сжимать и оптимизировать код,тем самым уменьшая размер кодиз,Улучшите скорость загрузки и производительность.
  • Улучшите безопасность: используйте код обфускации,Может скрывать конфиденциальную информацию, алгоритмы и логику,Тем самым повышая безопасность. Это особенно важно для приложений, которые обрабатывают конфиденциальные данные и выполняют критически важные приложения.
  • Избегайте автоматических атак. Обфускация может затруднить выявление и анализ атаки инструментами автоматических атак. Это может эффективно предотвратить некоторые распространенные атаки.,Такие как внедрение кода, XSS (межсайтовый скриптинг) и CSRF (подделка межсайтовых запросов) и т. д.

0x02 обфускация и сжатие

Основная цель технологии сжатия кода — уменьшить размер файлов, чтобы веб-страницы или программы могли загружаться быстрее. Вообще говоря, пробелы, разрывы строк, комментарии и ненужные символы в коде будут удалены в процессе сжатия кода.

код Язык:javascript
копировать
// исходный код
let v = "Hello World";

function foo(param) {
    console.log(param);
}

foo(v);
код Язык:javascript
копировать
// После сжатия
let v="Hello World";function foo(param){console.log(param)}foo(v);

Хотя сжатый код не меняет имена переменных, функций и т. д., он становится «комком», что все равно мешает нам читать. К счастью, сжатый код в принципе можно отформатировать непосредственно на некоторых онлайн-сайтах.

https://c.runoob.com/front-end/51/ https://tool.ip138.com/javascript/ https://www.sojson.com/yasuojs.html

Технологии обфускации кода различаются. В зависимости от используемой технологии большинство из них делают исходный код длиннее, но суть не в этом. Суть в том, чтобы сделать код нечитабельным и вы вообще его не сможете понять.

код Язык:javascript
копировать
// исходный код
let v = "Hello World";

function foo(param) {
 console.log(param)
}
foo(v);
код Язык:javascript
копировать
// Простой После путаницы
eval(function(p,a,c,k,e,r){e=String;if(!''.replace(/^/,String)){while(c--)r[c]=k[c]||c;k=[function(e){return r[e]}];e=function(){return'\\w+'};c=1};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p}('3 0="4 5";6 1(2){7.8(2)}1(0);',9,9,'v|foo|a|let|Hello|World|function|console|log'.split('|'),0,{}))

Запутанный код выглядит несколько странно и не похож на что-то, созданное людьми, что мешает общему анализу. Однако этот тип кода можно деобфусцировать непосредственно на некоторых онлайн-сайтах.

https://matthewfl.com/unPacker.html

После деобфускации я обнаружил, что весь код восстановлен. Вы говорите, что это обфускация, а это бесполезно, вы говорите, что это сжатие, но размер кода оно, похоже, не уменьшает.

Попробуем посмотреть время выполнения кода до и после обфускации.

код Язык:javascript
копировать
// До путаницы
const t0 = performance.now();
let v = "Hello World";

function foo(param) {
    console.log(param);
}

foo(v)
const t1 = performance.now();
console.log(t1 - t0, 'milliseconds');
код Язык:javascript
копировать
// После путаницы
const t0 = performance.now();

eval(function(p,a,c,k,e,r){e=String;if(!''.replace(/^/,String)){while(c--)r[c]=k[c]||c;k=[function(e){return r[e]}];e=function(){return'\\w+'};c=1};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p}('3 0="4 5";6 1(2){7.8(2)}1(0);',9,9,'v|foo|a|let|Hello|World|function|console|log'.split('|'),0,{}))

const t1 = performance.now();
console.log(t1 - t0, 'milliseconds');

Судя по этому вольному тесту, кажется, что он не может ускорить выполнение кода.

Этот вид packer Технология, которая объединяет сжатие и обфускацию, хотя и не может эффективно защитить исходный код, но, по крайней мере, в определенной степени предотвращает автоматический анализ программы.

Далее мы рассмотрим немного более сложную путаницу.

код Язык:javascript
копировать
// исходный код
let v = "Hello World";

function foo(param) {
    console.log(param);
}

foo(v);
код Язык:javascript
копировать
// После путаницы
const _0x44c967=_0x635b;(function(_0x32c587,_0xad783a){const _0x5f038b=_0x635b,_0xdd5abd=_0x32c587();while(!![]){try{const _0x36db7d=parseInt(_0x5f038b(0x1a4))/0x1*(-parseInt(_0x5f038b(0x1b0))/0x2)+parseInt(_0x5f038b(0x1a8))/0x3+-parseInt(_0x5f038b(0x1a5))/0x4+parseInt(_0x5f038b(0x1aa))/0x5*(parseInt(_0x5f038b(0x1a7))/0x6)+-parseInt(_0x5f038b(0x1af))/0x7*(parseInt(_0x5f038b(0x1ad))/0x8)+-parseInt(_0x5f038b(0x1ae))/0x9+-parseInt(_0x5f038b(0x1a6))/0xa*(-parseInt(_0x5f038b(0x1a9))/0xb);if(_0x36db7d===_0xad783a)break;else _0xdd5abd['push'](_0xdd5abd['shift']());}catch(_0x32d69b){_0xdd5abd['push'](_0xdd5abd['shift']());}}}(_0x2573,0x793ce));let v=_0x44c967(0x1ab);function foo(_0xddf157){const _0x57965d=_0x44c967;console[_0x57965d(0x1ac)](_0xddf157);}function _0x2573(){const _0x160bca=['7054758QHxQzs','7RhaGlF','2gnZgYk','139201SpYUUf','3355792nqHQax','9583830DxWDsR','3389808yzigdv','413817ZWQdzF','22UIVwDV','5AHuxCv','Hello\x20World','log','2888576mOrpTw'];_0x2573=function(){return _0x160bca;};return _0x2573();}function _0x635b(_0x119657,_0x5aecf8){const _0x257388=_0x2573();return _0x635b=function(_0x635be2,_0x5b4e35){_0x635be2=_0x635be2-0x1a4;let _0xe244e9=_0x257388[_0x635be2];return _0xe244e9;},_0x635b(_0x119657,_0x5aecf8);}foo(v);

Если бы не несколько ключевых слов, я бы даже не был уверен, что это так. javascript код

правда, возможно, восстановить подобную путаницу будет сложнее Понятно,Но да, мы можем посмотреть, как приезжают,foo Название функции не изменено. Вероятно, она еще полезна, но стоит ли оно того — вопрос.

Из приведенных выше случаев мы видим, что приезжать,Путаница между сжатием кода и кодом не означает, что это две полностью две технологии.,Просто предметы разные,Эти два метода часто комбинируются.,Поэтому в следующих статьях не будут подробно различаться сжатие кода и путаница кода.,Все они вместе называются путаницей кода.

0x03 Обфускация кода на практике

В этой главе мы познакомим вас с некоторыми существующими методами обфускации. На мой взгляд, если нет готовых инструментов, временные затраты на решение сложных обфускаций слишком высоки, и оно того не стоит. Действительно, следующий контент более склонен понимать особенности языка и специальные методы, используемые при анализе различных методов.

1. UglifyJS

UglifyJS — это набор инструментов для парсера, минификатора, минификатора и украшения JavaScript. https://lisperator.net/uglifyjs/ https://github.com/mishoo/UglifyJS/ https://github.com/LiPinghai/UglifyJSDocCN/blob/master/README.md

Как использовать

код Язык:javascript
копировать
npm install uglify-js -g
uglifyjs example.js -c -m --mangle-props
  • -c сжатие кода
  • -m код запутать
  • --mangle-props Изменить имена свойств
  • -b Украсить отображение
код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name)
console.log(greeting);
console.log(greeting2);
код Язык:javascript
копировать
// -c После сжатия
const person={age:18,name:"Tom"};function greet(name){return"Hello, "+name+"!"}var userName="John",greeting=greet(userName),greeting2=greet(person.name);console.log(greeting),console.log(greeting2);

мы проходим -b Красивое отображение параметров

код Язык:javascript
копировать
// -c После сжатия -b Украсить вывод
const person = {
    age: 18,
    name: "Tom"
};

function greet(name) {
    return "Hello, " + name + "!";
}

var userName = "John", greeting = greet(userName), greeting2 = greet(person.name);

console.log(greeting), console.log(greeting2);

существовать -c После сжатия

  • функциявнутреннийизпеременнаянаделятьценитьзаявлениеодеялоудалить Понятно
  • Три строки из var наделятьценитьзаявление Объединить в Понятно в одну строку
  • два console.log Объединить в Понятно в одну строку
код Язык:javascript
копировать
// -m После путаницы -b Украсить вывод
const person = {
    age: 18,
    name: "Tom"
};

function greet(e) {
    var r = "Hello, " + e + "!";
    return r;
}

var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name);
console.log(greeting);
console.log(greeting2);

существовать -m После путаницы

  • Параметр Воляфункция изменен на Понятно. name -> e
  • Внутреннее измененное имя функции изменено на Понятное однобуквенное. message -> r
код Язык:javascript
копировать
// -m --mangle-props назад -b Украсить вывод
const person = {
    g: 18,
    name: "Tom"
};

function greet(e) {
    var r = "Hello, " + e + "!";
    return r;
}

var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name);
console.log(greeting);
console.log(greeting2);

существовать -m --mangle-props назад

  • Параметр Воляфункция изменен на Понятно. name -> e
  • Внутреннее измененное имя функции изменено на Понятное однобуквенное. message -> r
  • верно Внутреннее изображение из имени атрибута было изменено Понятно age -> g
код Язык:javascript
копировать
// -c -m --mangle-props назад -b Украсить вывод
const person = {
    g: 18,
    name: "Tom"
};

function greet(e) {
    return "Hello, " + e + "!";
}

var userName = "John", greeting = greet(userName), greeting2 = greet(person.name);

console.log(greeting), console.log(greeting2);

По сути, вышеуказанные эффекты суммируются, но вы можете видеть, что самые внешние переменные по-прежнему не перепутаны. Если вы хотите, чтобы самые высокие переменные были запутаны, вам нужно использовать . --toplevel параметр

код Язык:javascript
копировать
// --toplevel -c -m --mangle-props назад -b Украсить вывод
function o(o) {
    return "Hello, " + o + "!";
}

o("John"), o("Tom");
console.log("Hello, John!"), console.log("Hello, Tom!");

Если честно, это более жестоко, просто убейте нас напрямую. выполнения Все Даватьдавай разберемся Понятно,И нашверно слона убили прямо Понятно,Может быть, да, потому что в продолжении назад не используется правильный символ приезжать.,В настоящее время мы пытаемся изменить исходный код,существоватьвыходназад Снова Даватьвернослонвсвойствонаделятьценить

код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name)
console.log(greeting);
console.log(greeting2);
person.name = "Kevin"
код Язык:javascript
копировать
// --toplevel -c -m --mangle-props назад -b Украсить вывод
var o = {
    o: 18,
    name: "Tom"
};

function n(o) {
    return "Hello, " + o + "!";
}

n("John");

var e = n(o.name);

console.log("Hello, John!"), console.log(e), o.name = "Kevin";

на этот раз Поскольку наше свойство верноверно слонв выполняет операцию Понятное присвоениеценить, код помогает нам сохранить Понятноверно слон,использовать --toplevel назад,За исключением Понятно, результат выполнения тот же.,Большая часть контента становится Понятной

Однако, как вы можете видеть здесь, объект name свойства, а также console.log Судя по описанию на официальном сайте, он не изменился. UglifyJS верно javascript Имена собственных функций и свойств не запутаны.

проходитьверно UglifyJS Анализ результатов путаницы показал, что путаница может быть достигнута за счет следующих аспектов:

  • общая ситуация、местныйпеременнаяимя
  • верно Имя внутреннего атрибута Icon
  • Функция внутреннего превышения, предусмотренная изпеременная ценить операцию
  • Даже функция возврата к цене шагов также может быть изменена.

2. Домашняя растерянность вебмастера

https://tool.chinaz.com/tools/jscodeconfusion.aspx

код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name)
console.log(greeting);
console.log(greeting2);
person.name = "Kevin"
код Язык:javascript
копировать
// После путаницыизкод
const person = {
 age: 18,
 name: '\x54\x6f\x6d'
}

function greet(ifBR1) {
 var rQnCc2 = "\x48\x65\x6c\x6c\x6f\x2c " + ifBR1 + "\x21";
 return rQnCc2;
}
var zj3 = "\x4a\x6f\x68\x6e";
var $t$4 = greet(zj3);
var HhUkMNt5 = greet(person["\x6e\x61\x6d\x65"]) 
console["\x6c\x6f\x67"]($t$4);
console["\x6c\x6f\x67"](HhUkMNt5);
person["\x6e\x61\x6d\x65"] = "\x4b\x65\x76\x69\x6e"
  • person вернослонв name Недвижимость переоценить Tom -> \x54\x6f\x6d
  • функция greet вформапараметрбыл переименован Понятно name -> ifBR1
  • функция greet внаделятьценитьзаявлениевнитьодеяло替换 Hello, -> \x48\x65\x6c\x6c\x6f\x2c , ! -> \x21
  • переменнаябыл переименован userName -> zj3, greeting ->
  • Верно, модель доступа к атрибутам объекта изменилась с точечной нотации на квадратную скобочную нотацию. person.name -> person['name']
  • верноLike атрибут доступа к атрибуту имя атрибута переименован name -> \x6e\x61\x6d\x65
  • javascript встроенные методы log был переименован log -> \x6e\x61\x6d\x65

Приведенное выше да основано на сводке изменений в предыдущем назадкодизе.,верно для переменного имени, если функция форма, изменение имени, все уверены, да думает, что это очень распространено Понятно,Потому что пока фронт назад последователен,Это не изменит значения кода. здесь нужно внимание изда,казатьсясуществовать javascript сама строка и ее ascii hex Эффект выражения из такой же, как да из (существовать во многих языках означает да как из)

Этот вид метода обфускации можно использовать по следующему адресу:

  • нитьценитьсередина
  • верно, как из имени атрибута

Этот вид запутывания Написать автоматическое восстановление не должно быть сложно, и, возможно, удастся завершить часть существующей онлайн-платформы.

https://www.sojson.com/jsjiemi.html

3. eval packer

https://tool.chinaz.com/js.aspx

код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name)
console.log(greeting);
console.log(greeting2);
person.name = "Kevin"
код Язык:javascript
копировать
// После путаницы
eval(function(p,a,c,k,e,d){e=function(c){return(c<a?"":e(parseInt(c/a)))+((c=c%a)>35?String.fromCharCode(c+29):c.toString(36))};if(!''.replace(/^/,String)){while(c--)d[e(c)]=k[c]||e(c);k=[function(e){return d[e]}];e=function(){return'\\w+'};c=1;};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p;}('c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"',19,19,'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|'),0,{}))

Сначала отформатируйте его

код Язык:javascript
копировать
eval(function(p, a, c, k, e, d) {
    e = function(c) {
        return (c < a ? "": e(parseInt(c / a))) + ((c = c % a) > 35 ? String.fromCharCode(c + 29) : c.toString(36))
    };
    if (!''.replace(/^/, String)) {
        while (c--) d[e(c)] = k[c] || e(c);
        k = [function(e) {
            return d[e]
        }];
        e = function() {
            return '\\w+'
        };
        c = 1;
    };
    while (c--) if (k[c]) p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), k[c]);
    return p;
} ('c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"', 19, 19, 'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|'), 0, {}))

Целое eval(code) Этот Форма вида фактически выполнена да code контент здесь code даодиннитьтипизпеременная,code Содержание следующее

код Язык:javascript
копировать
function(p, a, c, k, e, d) {
    e = function(c) {
        return (c < a ? "": e(parseInt(c / a))) + ((c = c % a) > 35 ? String.fromCharCode(c + 29) : c.toString(36))
    };
    if (!''.replace(/^/, String)) {
        while (c--) d[e(c)] = k[c] || e(c);
        k = [function(e) {
            return d[e]
        }];
        e = function() {
            return '\\w+'
        };
        c = 1;
    };
    while (c--) if (k[c]) p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), k[c]);
    return p;
} ('c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"', 19, 19, 'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|'), 0, {})

Абстрактно говоря, это function(param){}(params)Этот видформа,Этот вид формы немедленно вызвать выражение функции, просто прямой вызов анонимной функции, параметр просто да params , например

код Язык:javascript
копировать
(function(param){
   console.log(param);
})("Hello, World!");

Другими словами, eval функцияпараметрда Это выражение функции немедленного вызова возвращает результат, который следует данитьценить.

Понятное решение Понятное решение назад, мы Сначала посмотрели немедленно выражение вызова функции изпараметрдачто из

код Язык:javascript
копировать
'c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"', 19, 19, 'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|'), 0, {}

Связь с анонимной функцией в форме параметра будет следующей:

  • p -> 'c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"'
  • a -> 19
  • c -> 19
  • k ->'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|')
  • e -> 0
  • d -> {}

Парсинг для анализа анонимных функций

код Язык:javascript
копировать
function(p, a, c, k, e, d) {
    e = function(c) {
        return (c < a ? "": e(parseInt(c / a))) + ((c = c % a) > 35 ? String.fromCharCode(c + 29) : c.toString(36))
    };
    if (!''.replace(/^/, String)) {
        while (c--) d[e(c)] = k[c] || e(c);
        k = [function(e) {
            return d[e]
        }];
        e = function() {
            return '\\w+'
        };
        c = 1;
    };
    while (c--) if (k[c]) p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), k[c]);
    return p;
} 

Анонимные функции разделены на три части.

  • Давать e Назначенная функция
  • if суждениезаявление
  • while цикл

Сначала посмотри if заявление

код Язык:javascript
копировать
if (!''.replace(/^/, String)) {
    while (c--) d[e(c)] = k[c] || e(c);
    k = [function(e) {
        return d[e]
    }];
    e = function() {
        return '\\w+'
    };
    c = 1;
};

Заявление об условии true,Затем прочитайте содержание виз

код Язык:javascript
копировать
while (c--) d[e(c)] = k[c] || e(c);

c Значение 19, k[c]

очевидно,существоватьэтот пока циклсередина,k[c] Они все ценные, давайте посмотрим e(c) результат

while циклназад, на самом деле да Воля множество становится Понятно верный значок d

код Язык:javascript
копировать
k = [function(e) {
        return d[e]
    }];

Присвойте массив k Первый член — это функция, основанная на имени атрибута из d верно Получить атрибуты из изображения изценить

код Язык:javascript
копировать
e = function() {
        return '\\w+'
    };

c = 1;

Назначьте функцию e , эта функция очень проста, она просто возвращает \\w+ нить; дать переменную c Назначено 1

В это время каждыйпеременная Содержание следующее

  • p -> 'c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"'
  • a -> 19
  • c -> 1
  • k -> Набор
  • e -> функция
  • d -> настоящий слон
код Язык:javascript
копировать
while (c--) if (k[c]) p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), k[c]);

здесь while (c--) Это прикрытие, потому что выше уже было c установлен на 1 , поэтому он эквивалентен следующему коду абзаца

код Язык:javascript
копировать
c = 0
if (k[c]) p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), k[c]);

Судя по состоянию k[c] Эквивалент функции, курс заявления определения функции да true,Таким образом, код упрощается до

код Язык:javascript
копировать
c = 0 
func = function(e) {
        return d[e]
    }
p = p.replace(new RegExp('\\b' + e(c) + '\\b', 'g'), func);

в e На самом деле функция вообще не имеет параметра формы, поэтому e(c) в c вообще никакого смысла,e(c)Эквивалентно '\\w+',Таким образом, приведенный выше изкод эквивалентен

код Язык:javascript
копировать
p = 'c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"'
func = function(e) {
        return d[e]
    }
p = p.replace(new RegExp('\\b\\w+\\b', 'g'), func);

Код этого абзаца заменяет заявление, первое регулярное выражение дапроходить соответствует всем словам

  • \\b:Представлять словоизграница,используется для сопоставления словизначалоилиокончание。использоватьдвойная косая черта \\ дапотому что в существовании регулярное выражение, обратная косая черта \ да — специальный символ, который необходимо экранировать.
  • \\w+:表示одинилинесколько букв、числоили Подчеркнутый символ。\w да — это предопределенный класс символов, который соответствует буквам, цифрам и знакам подчеркивания.
  • \\b:Снова次Представлять словоизграница,Используется для обеспечения полного соответствия слова.

Что делать, если совпадение есть? Рассматривайте совпадающий контент как func изпараметр, выполнить func функция,и Воля возвращает ценить, заменяя контент, соответствующий приезжатьиз,Вернуться на замену

код Язык:javascript
копировать
return p

Окончательный возврат замены назадизнитьпеременная p

Так,Так как он был наконец выполнен изкод после того, как еда заменилась назад,возвращатьсянитьпеременнаяpДавать eval исполнение, если бы мы хотели p Что произойдет, если вы выведете его напрямую?

код Язык:javascript
копировать
// Изменить назад
console.log(функция(p,a,c,k,e,d){e=function(c){return(c<a?"":e(parseInt(c/a)))+((c=c%a)>35?String.fromCharCode(c+29):c.toString(36))};if(!''.replace(/^/,String)){while(c--)d[e(c)]=k[c]||e(c);k=[function(e){return d[e]}];e=function(){return'\\w+'};c=1;};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p;}('c 3={d:b,0:\'a\'}e 2(0){1 5="h, "+0+"!";i 5}1 7="f";1 4=2(7);1 6=2(3.0)8.9(4);8.9(6);3.0="g"',19,19,'name|var|greet|person|greeting|message|greeting2|userName|console|log|Tom|18|const|age|function|John|Kevin|Hello|return'.split('|'),0,{}))

нашисточниккод Просто восстановить Понятно

На этом этапе можно задуматься. А важно ли, как происходит процесс замены?

Это вообще не важно,Потому что его можно полностью превратить в черный ящик.,Не стесняйтесь настраиватьизверноисходный кодировать, чтобы изменить,назад обеспечивает окончательный и обратный процесс сокращения,финальныйпроходить eval Для реализации, возвращаясь к первоначальному намерению приезжатьнаш, мы анализируем Эту из Очки знаний, используемые при запутанном сжатии

  • eval Функция Волянит выполняется в виде кода
  • Выражение функции немедленного вызова function(param){}(params)

Нет, все остальное можно изменить.

4. JShaman

https://www.jshaman.com/ Отечественная компания JShaman разрабатывает коммерческие криптографические продукты из jscode

Бесплатная версия может быть использована напрямую

код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name);
console.log(greeting);
console.log(greeting2);
person.name = "Kevin";
код Язык:javascript
копировать
// После путаницы
const person={"\u0061\u0067\u0065":0x12,"\u006e\u0061\u006d\u0065":"\u0054\u006f\u006d"};function greet(_0x753eb2){var _0x4445de=" ,olleH".split("").reverse().join("")+_0x753eb2+"\u0021";return _0x4445de;}var userName="nhoJ".split("").reverse().join("");var greeting=greet(userName);var greeting2=greet(person["\u006e\u0061\u006d\u0065"]);console["\u006c\u006f\u0067"](greeting);console["\u006c\u006f\u0067"](greeting2);person["\u006e\u0061\u006d\u0065"]="niveK".split("").reverse().join("");

Давайте отформатируем его

код Язык:javascript
копировать
// Формат назад
const person = {
    "\u0061\u0067\u0065": 0x12,
    "\u006e\u0061\u006d\u0065": "\u0054\u006f\u006d"
};
function greet(_0x753eb2) {
    var _0x4445de = " ,olleH".split("").reverse().join("") + _0x753eb2 + "\u0021";
    return _0x4445de;
}
var userName = "nhoJ".split("").reverse().join("");
var greeting = greet(userName);
var greeting2 = greet(person["\u006e\u0061\u006d\u0065"]);
console["\u006c\u006f\u0067"](greeting);
console["\u006c\u006f\u0067"](greeting2);
person["\u006e\u0061\u006d\u0065"] = "niveK".split("").reverse().join("");

Unicode это имя таблицы кодировки Unicode кодирование на самом деле имеет разные формы реализации, в \u0000 Этот Форма вида — это escape-последовательность Юникода, форма выражения дав, которую часто называют Unicode кодировка, которая также будет использоваться ниже Unicode Вызывается по коду, надеюсь, это никому не доставляет хлопот.

  • верно из имя атрибута преобразуется в Понятно Unicode кодирование
  • вернослонизсвойствоверноотвечатьизценить Есть изменения
    • нитьодеяло转化для Понятно Unicode кодирование
    • Тип номера ценить преобразуется в Понятно 16 база из формы
  • параметр нефункционального формата заменен _0x Начиная с из формы из символов
  • Внутреннее изпеременное имя функции заменяется на _0x Начиная с из формы из символов
  • верно Внить Сращиваниеизграмматическая прогрессия Понятноболее одного изменения
    • "Hello, " -> " ,olleH".split("").reverse().join("") Говоря о прибытии, первоначальный характер даверно подвергается процессу Понимания, а результат остается неизменным.
    • ! -> \u0021 Некоторые персонажи становятся Unicode кодирование
  • общая ситуациянитьпеременнаяизценитьтакжеодеяло修改Понятно "John" -> "nhoJ".split("").reverse().join("")
  • вернослонсвойствовызовтакжедаиспользовать Unicode кодированиеформа

Технология, используемая в бесплатной версии, также относительно проста. Основные моменты, которые можно резюмировать:

  • верно, из имени атрибута инициировать можно не только использовать шестнадцатеричное число, но и использовать Unicode формавыражать

5. JavaScript obfuscator

https://obfuscator.io/ https://github.com/javascript-obfuscator/javascript-obfuscator Бесплатный и эффективный JavaScript Обфускаторы (в том числе верно ES2022 из поддержки). Усложняет копирование и не позволяет людям украсть вашу работу. Этот инструмент является отличным веб-сайтом. Пользовательский интерфейс (и открытый исходный код)

img

Размещение этого значка на официальном сайте может означать, что этот проект зашифрован и заставляет людей выглядеть так, будто им хочется плакать.

1) Конфигурация по умолчанию

Для этого инструмента существует множество настраиваемых элементов. Давайте сначала воспользуемся формой по умолчанию на официальном сайте, чтобы увидеть эффект.

код Язык:javascript
копировать
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}
  
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name);
console.log(greeting);
console.log(greeting2);
person.name = "Kevin";
код Язык:javascript
копировать
// После путаницы
var _0x5665ce=_0x1ec8;(function(_0x24a0fc,_0x32277b){var _0x470fc7=_0x1ec8,_0x314734=_0x24a0fc();while(!![]){try{var _0x19fb94=-parseInt(_0x470fc7(0xca))/0x1+parseInt(_0x470fc7(0xc8))/0x2+parseInt(_0x470fc7(0xc9))/0x3+-parseInt(_0x470fc7(0xc5))/0x4+-parseInt(_0x470fc7(0xc4))/0x5+-parseInt(_0x470fc7(0xcb))/0x6+parseInt(_0x470fc7(0xcd))/0x7;if(_0x19fb94===_0x32277b)break;else _0x314734['push'](_0x314734['shift']());}catch(_0x11f2da){_0x314734['push'](_0x314734['shift']());}}}(_0xd8be,0xcb4d8));const person={'age':0x12,'name':'Tom'};function greet(_0x232d03){var _0x158862='Hello,\x20'+_0x232d03+'!';return _0x158862;}function _0x1ec8(_0x200d59,_0x33a7d8){var _0xd8be2c=_0xd8be();return _0x1ec8=function(_0x1ec879,_0x3bf5b6){_0x1ec879=_0x1ec879-0xc4;var _0x4acfea=_0xd8be2c[_0x1ec879];return _0x4acfea;},_0x1ec8(_0x200d59,_0x33a7d8);}var userName=_0x5665ce(0xc6),greeting=greet(userName),greeting2=greet(person[_0x5665ce(0xcc)]);function _0xd8be(){var _0x303cd1=['4525950NEPdZY','5502416viTywx','John','log','2506568dDijWh','1830627XxDgMI','46606dGrOiI','2093556sEUamv','name','11518927TWTtrQ'];_0xd8be=function(){return _0x303cd1;};return _0xd8be();}console['log'](greeting),console[_0x5665ce(0xc7)](greeting2),person[_0x5665ce(0xcc)]='Kevin';

Попробуйте отформатировать его

код Язык:javascript
копировать
// Формат назад
var _0x5665ce = _0x1ec8; (function(_0x24a0fc, _0x32277b) {
    var _0x470fc7 = _0x1ec8,
    _0x314734 = _0x24a0fc();
    while ( !! []) {
        try {
            var _0x19fb94 = -parseInt(_0x470fc7(0xca)) / 0x1 + parseInt(_0x470fc7(0xc8)) / 0x2 + parseInt(_0x470fc7(0xc9)) / 0x3 + -parseInt(_0x470fc7(0xc5)) / 0x4 + -parseInt(_0x470fc7(0xc4)) / 0x5 + -parseInt(_0x470fc7(0xcb)) / 0x6 + parseInt(_0x470fc7(0xcd)) / 0x7;
            if (_0x19fb94 === _0x32277b) break;
            else _0x314734['push'](_0x314734['shift']());
        } catch(_0x11f2da) {
            _0x314734['push'](_0x314734['shift']());
        }
    }
} (_0xd8be, 0xcb4d8));
const person = {
    'age': 0x12,
    'name': 'Tom'
};
function greet(_0x232d03) {
    var _0x158862 = 'Hello,\x20' + _0x232d03 + '!';
    return _0x158862;
}
function _0x1ec8(_0x200d59, _0x33a7d8) {
    var _0xd8be2c = _0xd8be();
    return _0x1ec8 = function(_0x1ec879, _0x3bf5b6) {
        _0x1ec879 = _0x1ec879 - 0xc4;
        var _0x4acfea = _0xd8be2c[_0x1ec879];
        return _0x4acfea;
    },
    _0x1ec8(_0x200d59, _0x33a7d8);
}
var userName = _0x5665ce(0xc6),
greeting = greet(userName),
greeting2 = greet(person[_0x5665ce(0xcc)]);
function _0xd8be() {
    var _0x303cd1 = ['4525950NEPdZY', '5502416viTywx', 'John', 'log', '2506568dDijWh', '1830627XxDgMI', '46606dGrOiI', '2093556sEUamv', 'name', '11518927TWTtrQ'];
    _0xd8be = function() {
        return _0x303cd1;
    };
    return _0xd8be();
}
console['log'](greeting),
console[_0x5665ce(0xc7)](greeting2),
person[_0x5665ce(0xcc)] = 'Kevin';

Если мы не знаем исход кодда Что?,Кажется, да в полном отчаянии,ноданассуществовать Знатьисходный кодизкейс,Это также можно проанализировать

код Язык:javascript
копировать
// верная часть определения изображения
// исходный код
const person = {
    age: 18,
    name: 'Tom'
}

// После путаницы
const person = {
    'age': 0x12,
    'name': 'Tom'
};

верная часть определения изображенияосновнойда Волясвойствоценитьсередина数ценитьформаиспользовать Понятно 16 шестнадцатеричное представление

код Язык:javascript
копировать
// Часть определения функции
// исходный код
function greet(name) {
    var message = "Hello, " + name + "!";
    return message;
}

// После путаницы
function greet(_0x232d03) {
    var _0x158862 = 'Hello,\x20' + _0x232d03 + '!';
    return _0x158862;
}

Основные изменения в определении функции заключаются в следующем:

  • Параметр формы изменяется на _0x из формы
  • Внутреннее переменное имя функции изменено на _0x из формы
  • нитьнекоторые персонажииспользовать Понятно 16 Выражено в базовой форме ' ' -> \x20
код Язык:javascript
копировать
// Глобальная переменная часть определения
// исходный код
var userName = "John";
var greeting = greet(userName);
var greeting2 = greet(person.name);

// После путаницы
var userName = _0x5665ce(0xc6),
greeting = greet(userName),
greeting2 = greet(person[_0x5665ce(0xcc)]);

Обычно это нормально настроить. _0x5665ce(0xc6) ,А также параметр,параметр еще не является оригинальным и его различное кодирование,Давайте наклеим Функционкод

код Язык:javascript
копировать
var _0x5665ce = _0x1ec8; 

_0x5665ceизценитьравный _0x1ec8 , давайте посмотрим _0x1ec8

код Язык:javascript
копировать
function _0x1ec8(_0x200d59, _0x33a7d8) {
    var _0xd8be2c = _0xd8be();
    return _0x1ec8 = function(_0x1ec879, _0x3bf5b6) {
        _0x1ec879 = _0x1ec879 - 0xc4;
        var _0x4acfea = _0xd8be2c[_0x1ec879];
        return _0x4acfea;
    },
    _0x1ec8(_0x200d59, _0x33a7d8);
}

Эта форма функции немного интересна. Придумайте вызов функции, и результату выполнения Воляфункции присваивается переменная, а затем возвращается назад. return Понятно,по-видимомуreturn Два возвращаемых значения, первое возвращаемое значение новое. _0x1ec8 Функция второго возвратаценитьдаверно в новом; _0x1ec8 Возвращаемое значение вызова функции, Передать isparameter Нарихара _0x1ec8 Функция в параметре, без изменений

код Язык:javascript
копировать
var userName = _0x5665ce(0xc6)

мы знаем userName Значение John,нода В настоящее время кажется userName Значение должно быть определением функции. Давайте выведем его.

здесь мы действительно можем сравнить eval packer Понятно,Это всего лишь простая замена замены,Несмотря на то Воляисходный коды извлечены частично,Хранение, сращивание, замена и т.п. в различных формах, таких как множество, словари и т.п.,Наконец восстановить,здесь Поверхность не используетсяприезжатьсложныйиз Грамматика иjs Характеристики самого языка, поэтому мы не можем ничему научиться, разгадывая его постепенно; этоткод Это другое Понятно,Давайте разгадаем это шаг за шагом,Попробуйте изучить идеи виз

В настоящее время я уже выполнил некоторые из вышеперечисленных результатов, например, из назначенной цены, функции и т. д., что привело к понятным сомнениям.,Это отличается от моего предыдущего понимания,такнас Воля После путаницыизкод аннотация

код Язык:javascript
копировать
// Частичный кодAbstract назад
function func1(param1, param2) {
    var var_1 = 'test';
    return func1 = function(new_param1, new_param2) {
        new_param1 = new_param1 - 0xc4;
        var var_2 = new_param1;
        return var_2;
    },
    func1(param1, param2);
}

var a, b = func1(0xc6)
console.log(a)   // Результат выполненияда undefined
console.log(b)   // Результат выполненияда 2 , то есть да — это число ценить, а не определенная функция

Если мы используем две переменные для получения func1 Каков будет результат выполнения

На этот раз это стало переменной b Значение 2 ,aдля undefined

Если мы используем три переменные для получения func1 Каков будет результат выполнения

код Язык:javascript
копировать
// Частичный кодAbstract назад
function func1(param1, param2) {
    var var_1 = 'test';
    return func1 = function(new_param1, new_param2) {
        new_param1 = new_param1 - 0xc4;
        var var_2 = new_param1;
        return var_2;
    },
    func1(param1, param2);
}

var a, b, c = func1(0xc6)
console.log(a)   
console.log(b)  
console.log(b)

на этот раз c Значение 2 Понятно

Если у нас есть только переменные a получать func1 возвращаемое значение, но изменить func1 Возвращаемое значение оставляет только новое определение функции.

код Язык:javascript
копировать
function func1(param1, param2) {
    var var_1 = 'test';
    return func1 = function(new_param1, new_param2) {
        new_param1 = new_param1 - 0xc4;
        var var_2 = new_param1;
        return var_2;
    }
}

var a = func1(0xc6)
console.log(a)

на этот раз возвращает результат определения функции, в этот раз, если мы используем двепеременную получение func1 результат выполнения

код Язык:javascript
копировать
function func1(param1, param2) {
    var var_1 = 'test';
    return func1 = function(new_param1, new_param2) {
        new_param1 = new_param1 - 0xc4;
        var var_2 = new_param1;
        return var_2;
    }
}

var a, b = func1(0xc6)
console.log(a)
console.log(b)

Переменные в это время b Значениефункцияопределение Понятно

Итак, здесь есть два измерения сложной сцены.,Мы снова абстрагируемся,Новое определение изфункции больше не имеет того же имени, что и исходная Функция Понятно.

код Язык:javascript
копировать
function func1(o1) {
    return func2 = function(n1) {
        return n1;
    }, 2
}

var a, b, c = func1(0xc6)
console.log(a)
console.log(b)
console.log(c)

Кажется, что результат не изменился. Может быть, когда определение функции и другие типы возвращаются одновременно, ее значение автоматически становится равным. undefined Понятно??

код Язык:javascript
копировать
function func1(o1) {
    return () => {}, 2, "3"
}

var a, b, c = func1(0xc6)
console.log(a)
console.log(b)
console.log(c)

На этот раз мы создадим три возвращаемых значения, а именно: определение функции, числовое значение и строку.

Посмотри на это,Я в замешательстве,После запроса информации,Я ищу место Понятнодва измерения сложности по причине

В JavaScript функция может иметь только один возврат ценить.,Просто скажите, что если вы еще не изучали этот материал раньше jsкто бы мог подуматьприезжать Бар!而且 return 1, 2 также Нет会报错,Да будет реализовано в соответствии с определенными спецификациями.,В конце концов вернуть больше всего назад аценить

На этом этапе нам не нужна абстракция. Понятно, и мы можем продолжить рассмотрение. _0x1ec8 Задействована еще одна функция _0xd8beПонятно

код Язык:javascript
копировать
function _0xd8be() {
    var _0x303cd1 = ['4525950NEPdZY', '5502416viTywx', 'John', 'log', '2506568dDijWh', '1830627XxDgMI', '46606dGrOiI', '2093556sEUamv', 'name', '11518927TWTtrQ'];
    _0xd8be = function() {
        return _0x303cd1;
    };
    return _0xd8be();
}

Эта функция возвращает массив, и следующий процесс выполнения такой же, как и eval packer Никакой разницы. Понятно, как бороться с ничьими вещами.

код Язык:javascript
копировать
console['log'](greeting),
console[_0x5665ce(0xc7)](greeting2),
person[_0x5665ce(0xcc)] = 'Kevin';

Об этой части особо сказать нечего, это просто компенсационная проблема.

Кроме Понятно, мы обсуждали изкод,И абзац никогда не обсуждался,Но да, это работает Понятно

код Язык:javascript
копировать
(function(_0x24a0fc, _0x32277b) {
    var _0x470fc7 = _0x1ec8,
    _0x314734 = _0x24a0fc();
    while ( !! []) {
        try {
            var _0x19fb94 = -parseInt(_0x470fc7(0xca)) / 0x1 + parseInt(_0x470fc7(0xc8)) / 0x2 + parseInt(_0x470fc7(0xc9)) / 0x3 + -parseInt(_0x470fc7(0xc5)) / 0x4 + -parseInt(_0x470fc7(0xc4)) / 0x5 + -parseInt(_0x470fc7(0xcb)) / 0x6 + parseInt(_0x470fc7(0xcd)) / 0x7;
            if (_0x19fb94 === _0x32277b) break;
            else _0x314734['push'](_0x314734['shift']());
        } catch(_0x11f2da) {
            _0x314734['push'](_0x314734['shift']());
        }
    }
} (_0xd8be, 0xcb4d8));

этот абзацкод Кажетсядаодин Выражение функции немедленного вызова,Он включает в себя много содержания и труден для понимания.,Но когда удали этот абзац кодназад,верно Весь результат выполнения не имеет никакого влияния,Итак, этот абзац да Дават. Давайте добавим код блокировки и смерти.


Далее мы можем подвести итог JavaScript obfuscator Конфигурация по По умолчанию запутывание с использованием некоторых методов Понятно

  • Добавить бессмысленноеиз Выражение функции немедленного вызоваумеретькод,Запутанная информация
  • Измените верный атрибут объекта ценить на числовой тип ценить на шестнадцатеричную форму.
  • Измените параметр формата функции и имя внутреннего параметра.
  • Изменить часть нить на 16 базовое представление
  • Воляобщая ситуацияпеременнаяизнитьценить、вернослонсвойствовызовизвызовимя等нитьпроходить функция(параметр) извернутьценить, чтобы получить Как выполнить функцию,не важно,это может измениться,нодафункциясередина涉及Понятно Точка вмешательства
    • Разделен на несколько функций, и название функции бессмысленно из-за _0x ,При этом функция внутренне предполагает выездные расчеты.,Процесс расчета включает в себя использование шестнадцатеричных чисел (0x).,так _0x и 0x Легко спутать, как плохо ты говоришь
    • Внутренняя часть существованияфункции будет аналогична конструкции закрытияиз, охватывающей исходное определение изфункции.
    • Функциональный параметр содержит бессмысленный параметр
    • функциявозвращатьсяценитьиспользовать Понятноjavascript Функция имеет только одно возвращаемое свойство ценитьиз, что сбивает с толку.

Давайте посмотрим дальше JavaScript obfuscator Какое влияние окажут эти элементы конфигурации?

https://obfuscator.io/#code

Официальный сайт предоставляет понятные графические элементы конфигурации и достоверный анализ элементов конфигурации. Вы также можете просмотреть их на официальном сайте.

2) Options Preset

существоватьпредварительнонастраиватьсередина,На картинке четыре пресета,Индивидуальных пунктов настройки должно быть несколько десятков.,Четыре пресета используют разные конфигурации,Немногокартинасередина杯、Большая чашка、догонять Большая чашкаизиметь в виду

Элементов конфигурации много и скриншоты недостаточно полные. Для их просмотра можно зайти на официальный сайт.

3) Target

среда выполнения отображаемого кодирования

  • Браузер
  • Браузерникто eval
  • nodejs

Это зависит от конкретной среды выполнения. Понятно

4) seed

тип: string|number по умолчанию: 0

Начальное число случайных чисел, хотя в официальном описании существования говорится да. string|number , но судя по настройкам официального сайта, он должен поддерживать только number , Настройка начального значения случайного числа может сделать случайность более безопасной. К счастью, некоторое время назад мастер проанализировал уязвимости, вызванные некоторыми алгоритмами генерации случайных чисел.

5) disableConsoleOutput

Boolean Тип опций конфигурации

Эта опция глобально отключает вызовы консоли для всех скриптов.

добавив console.log、console.info、console.error、console.warn、console.debug、console.exception и console.trace Замените их пустыми функциями, чтобы отключить их. Это усложняет использование отладчика.

Давайте проверим эту опцию и попробуем отменить другие опции на данный момент.

код Язык:javascript
копировать
// исходный код
console.log("Hello World!");
код Язык:javascript
копировать
// После путаницы
var b = (function () {
    var c = !![];
    return function (d, e) {
        var f = c ? function () {
            if (e) {
                var g = e['apply'](d, arguments);
                e = null;
                return g;
            }
        } : function () {
        };
        c = ![];
        return f;
    };
}());
var a = b(this, function () {
    var c;
    try {
        var d = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
        c = d();
    } catch (l) {
        c = window;
    }
    var f = c['console'] = c['console'] || {};
    var g = [
        'log',
        'warn',
        'info',
        'error',
        'exception',
        'table',
        'trace'
    ];
    for (var h = 0x0; h < g['length']; h++) {
        var i = b['constructor']['prototype']['bind'](b);
        var j = g[h];
        var k = f[j] || i;
        i['__proto__'] = b['bind'](b);
        i['toString'] = k['toString']['bind'](k);
        f[j] = i;
    }
});
a();
console['log']('Hello\x20World!');

Давайте выполним это путаницыизкод

Можно смотреть приезжать, ведь да Воля вывод на консоль запрещен Понятно

Кратко разберем, как это делается

Кодобщий состоит из четырех частей,Последняя часть не означает «Понятно».,前面основнойдасоздавать Понятнодвапеременная,назадвызов Понятноводинсвойстводляфункцияизпеременная,заставить его выполнить,нас Можетсуществовать a и b Вывод между переменными, чтобы узнать, были ли они заблокированы в данный момент.

существовать a Попробуйте сделать то же самое перед выполнением

Видно, что все предыдущие шаги — это предзнаменование и исполнение. a Функцияназад вывод на консоль отключен Понятно

иметь Понятновозможноиз Понятноразвязатьназад,Вы можете начать анализировать шаг за шагом,Да b часть

код Язык:javascript
копировать
// b часть
var b = (function () {
    var c = !![];
    return function (d, e) {
        var f = c ? function () {
            if (e) {
                var g = e['apply'](d, arguments);
                e = null;
                return g;
            }
        } : function () {
        };
        c = ![];
        return f;
    };
}());

С этим должен быть знаком каждый: Понятно,Также дано выражение функции немедленного вызова.,Тогда мы сможем напрямую посмотреть, что выполняет это выражение назадрезультатда

Вы можете посмотреть приезжать,Это выражение дает анонимную функцию,Воля匿имяфункциянаделятьценитьдать переменную b

Конкретное выполнение данного пункта зависит от c Стоимость a часть

код Язык:javascript
копировать
// a часть
var a = b(this, function () {
    var c;  
    try {
        var d = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
        c = d();
    } catch (l) {
        c = window;
    }
    var f = c['console'] = c['console'] || {};
    var g = [
        'log',
        'warn',
        'info',
        'error',
        'exception',
        'table',
        'trace'
    ];
    for (var h = 0x0; h < g['length']; h++) {
        var i = b['constructor']['prototype']['bind'](b);
        var j = g[h];
        var k = f[j] || i;
        i['__proto__'] = b['bind'](b);
        i['toString'] = k['toString']['bind'](k);
        f[j] = i;
    }
});

общий a да b Возвращаемое значение вызова функции, параметр (this, function)

код Язык:javascript
копировать
function (d, e) {
        var f = c ? function () {
            if (e) {
                var g = e['apply'](d, arguments);
                e = null;
                return g;
            }
        } : function () {
        };
        c = ![];
        return f;
};

здесь интересно, Понятно, а да — тернарный оператор. f = c ? func1(){} : func2(){} , здесь согласно c судить о ценности f конечное значение переменной

Людям легко усомниться в изде, c приезжатьконецсуществоватьгде,хорошийкартина没иметь c изDefinition, параметра нет, но да b в выражении немедленного вызова return раньше имел это значение

код Язык:javascript
копировать
(function(){
   var c = !![];
  return function(){}
})

Но даздесьиз c Хотя мы влюблены друг в друга return Она относится к внешнему слою с точки зрения изфункции, но да в целом является также дасуществоватьфункцию внутри тела из, существующего в настоящее время. Является ли это все еще эффективным в обстоятельствах вида?

здесьизграмматикасуществовать javascript По-китайски это называется закрытие, также считается да. javascript языковые особенности

закрытие(closure)дафункцияи его комплектиз Состояние окружающей среды(lexical environment,лексическая среда)из Цитироватьизкомбинация。换而言Из,закрытиепозволять开发者Может从внутреннийфункциядоступ к внешнемуфункцияиз Объем。существовать JavaScript , замыкание будет создано одновременно с созданием функции. https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Closures

код Язык:javascript
копировать
function outer() {
  var outerVar = 'Hello';

  function inner() {
    var innerVar = ' World';
    console.log(outerVar + innerVar);
  }

  return inner;
}

var closure = outer();
closure();

здесь выглядит как closure переменнаяравныйизда inner функция,Зависит от Взакрытиеграмматикаизжитьсуществовать,На самом деле, это условие inner А сочетание его верхнего окружения (включая переменные) и эффект замыкания можно проверить по результатам выполнения.

Так позвони b Функциивремя,c Значение true,Поэтому это упрощается до

код Язык:javascript
копировать
function (d, e) {
        var f = function () {
            if (e) {
                var g = e['apply'](d, arguments);
                e = null;
                return g;
            }
        };
        c = ![];
        return f;
};

Вы можете видеть приезжать, на самом деле здесь также дазакрытие, существует анонимная функция, встроенная внутри. Понятно анонимная функция, пройдите, дайте переменную f 跟нас上面из案例没иметь区别,здесьтак называемыйиз Окружающая средадаd и e, d В принципе, это такая же общая картина, e даафункция и, конечно же, ручной сброс на falseиз c

Дальше идет большая часть приезжать a() , на самом деле, это просто да f(),Упрощено следующим образом

код Язык:javascript
копировать
var d = window;
var e = function () {
    var c;
    try {
        var d = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
        c = d();
    } catch (l) {
        c = window;
    }
    var f = c['console'] = c['console'] || {};
    var g = [
        'log',
        'warn',
        'info',
        'error',
        'exception',
        'table',
        'trace'
    ];
    for (var h = 0x0; h < g['length']; h++) {
        var i = b['constructor']['prototype']['bind'](b);
        var j = g[h];
        var k = f[j] || i;
        i['__proto__'] = b['bind'](b);
        i['toString'] = k['toString']['bind'](k);
        f[j] = i;
    }
};

var a = function () {
            if (e) {
                var g = e['apply'](d, arguments);
                e = null;
                return g;
            }
        };

a();

очевидно e изценить Нетда false,Итак, условие входазаявлениесередина, на самом деле, это просто даслово

код Язык:javascript
копировать
var g = e['apply'](d, arguments);

наш e даафункция, афункцияиз apply Что означает атрибут да?

здесь Это снова включает в себяприезжатьjavascript функцияизхарактеристика Понятно —— apply

Function пример apply() метод примет заданное this ценитьи作длямножество(илидобрыймножествовернослон)поставлятьиз arguments Вызовите эту функцию. https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Function/apply

код Язык:javascript
копировать
apply(thisArg)
apply(thisArg, argsArray)
  • thisArg

вызов func предоставлено на this ценить. Если функция не в строгом режиме (Strict_mode), то null и undefined 会одеяло替换дляобщая ситуациявернослон,Исходная цена будет преобразована в «верно слон».

  • argsArray Необязательный

Иконка класса множествоверно для изображенныхвызов func Если параметр отсутствует или не требуется указывать параметр для функции, тогда null или undefined

Приведите пример

код Язык:javascript
копировать
function greet(msg) {
    console.log(`Hello, ${this.name}!`);
    console.log(msg)
  }
  
  var person1 = {
    name: 'John'
  };
  
  var persion2 = {
    name: 'Alice'
  };
  
greet.apply(person1, ["John is best!"]);
console.log("----------")
greet.apply(persion2, ["Alice, come on."]);

здесь greet Функция От кого именно здоровается зависит this Кого оно представляет? apply из Эффектдаобозначениефункциявызовкогдаизthis ценить.

Анонимнаяфункцияда Нет apply методический

arguments да — это специальный значок изверно, который содержит Понятнофункциявызов при передаче всех параметров, независимо от того, определена ли да или существующая функция в определении Понятно для этих параметров. Оно похоже на множество, но не является настоящим измножеством. Он имеет такие свойства и методы, как множество, например length Доступ к свойствам и индексам, но других методов у него нет.

Итак, вышеизкодиззначениедаобозначение Понятноe Когда функция выполняется this даобщая ситуациявернослон,назад выполняется по оригинальной версии.

Далее мы посмотрим e функция

код Язык:javascript
копировать
var e = function () {
    var c;
    try {
        var d = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
        c = d();
    } catch (l) {
        c = window;
    }
    var f = c['console'] = c['console'] || {};
    var g = [
        'log',
        'warn',
        'info',
        'error',
        'exception',
        'table',
        'trace'
    ];
    for (var h = 0x0; h < g['length']; h++) {
        var i = b['constructor']['prototype']['bind'](b);
        var j = g[h];
        var k = f[j] || i;
        i['__proto__'] = b['bind'](b);
        i['toString'] = k['toString']['bind'](k);
        f[j] = i;
    }
};

сначала дапроходить try...catchДавать c руководить Понятнонаделятьценить

Сначала посмотриодин разtry внутренний код

код Язык:javascript
копировать
var d = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
c = d();

Кажется, что да создаёт Понятно функцию d ,Изназадсновавызов d функция,и Волявозвращатьсяценитьнаделятьценить Давать c

Этот абзац кодиспользовать Понятно Javascript Встроенная структурная функция Function , он может принять нитпараметр и преобразовать его в объект-функцию, что случается очень редко, Поскольку такой способ написания сделает читабельность очень плохой, я не ожидал, что приезжать будут путать с существованием, здесь Понятно, а также да JavaScript изхарактеристика Понятно

bf976b12gy1ghfo72u6qlg206m05ydg2

Воля 16 шестнадцатеричное представление символа восстанавливается следующим образом: назад

код Язык:javascript
копировать
var d = Function('return (function() ' + '{}.constructor("return this")( )' + ');');
c = d();

Этот абзац на самом деле возвращает Понятное выражение немедленной функции вызова, используемое для получения глобального истинного объекта, поэтому c Значениеобщая ситуациявернослон

Фактически, из catch вкод также может видеть подсказки

код Язык:javascript
копировать
var f = c['console'] = c['console'] || {};
var g = [
    'log',
    'warn',
    'info',
    'error',
    'exception',
    'table',
    'trace'
];

определениедвапеременнаяfиg, f даиндивидуальныйвернослон;g да Набор, на самом деле, это просто да f из一些成员свойствоимя称,f[g] Сразудахотетьодеяло禁止из,Поэтому следующий исход следует сочетать с да Воля,назадпроходить Несколько способов запретить это

код Язык:javascript
копировать
for (var h = 0x0; h < g['length']; h++) {
        var i = b['constructor']['prototype']['bind'](b);
        var j = g[h];
        var k = f[j] || i;
        i['__proto__'] = b['bind'](b);
        i['toString'] = k['toString']['bind'](k);
        f[j] = i;
    }

абзац for циклкод,определение Понятно i j k три переменные

код Язык:javascript
копировать
var i = b['constructor']['prototype']['bind'](b);

b Первая часть выражения «да немедленно вызвать» возвращает функцию, поэтому здесь также есть «да». func.constructor.prototype.bind(func)

здесьсновада javascript изхарактеристика Понятно

здесь涉及几индивидуальный概念constructorprototypeproto

img

constructor даструктурафункция,prototype Конструктивная функция имеет prototypeсвойство,Указывает на экземпляр верного объекта и прототип верного объекта. Экземплярное изображение имеет атрибут proto.,Указатель на экземпляр

Это выглядит сложно,Особенно их имя так сбивает с толку.,Заставляет людей терять желание помнить,Просто картинаяверно в память о старшинстве и памяти,Вы можете надеть его только при использовании приезжатьиз

Картинки из следующей статьи https://www.cnblogs.com/xiaohuochai/p/5721552.html https://blog.csdn.net/cc18868876837/article/details/81211729

Теперь мы начинаем анализировать приведенный выше код абзаца.

b['constructor'] Также дасуществовать в поисках силы верно слон b изструктурировать функцию, она просто изструктурировать функцию Function

b['constructor']['prototype'] эквивалентно Function из prototype свойство,это указывает на экземплярвернослонbиз原формавернослон

b['constructor']['prototype']['bind'](b) вызов Понятно bind метод, этот метод Function.prototypeсерединажитьсуществовать,Чтосуществовать Пример b Мы живем в Китае

bind Метод заключается в изменении окружения (это) ,具体Сразуда Воляthis Укажите на параметр, например

код Язык:javascript
копировать
const obj = {
    x: 1
}

x = 0
var b = function() {
    console.log("1111")
    console.log(this.x)
}

console.log('-- 1 --')
var i = b
i()
console.log('-- 2 --')
i = b.bind(obj)
i()

Это можно увидеть сквозь bind метод, функция Воля нового поколения iизthisЗависит отwindow/global становиться Понятно obj

Далее я расширю этот случай

код Язык:javascript
копировать
const obj = {
    x: 1
}

x = 0
var b = function() {
    console.log("1111")
    console.log(this.x)
}

console.log('-- 1 --')
var i = b
i()
console.log('-- 2 --')
i = b.bind(obj)
i()
console.log('-- 3 --')
i = b.constructor.prototype.bind(obj)
i()

здесь интересно Понятно, зачем приезжать b.constructor.prototype.bind(obj) здесь не выводится Понятно?

Эту модель я придумал назад и абстрагировал ее из,Я ищу любую информацию,Я уже давно об этом думаю и до сих пор не понимаю.,Я тоже не понимаю Понятно

на самом деледа因длявызов bind методический Нетда b Да Function.prototype , так что приезжай i Нисколько b Функция является основой для изменения Понятной среды из, что приводит к вышеописанной ситуации из

Теперь мы можем вернуться и проанализировать этот абзац кода Понятно.

код Язык:javascript
копировать
var i = b['constructor']['prototype']['bind'](b);

Хотя сначала да b,передачаизпараметртакжеда b , но на самом деле генерирует новый шаблон Функций, это не так. b,так i Естественно b Функции разные Понятно

код Язык:javascript
копировать
var j = g[h];
var k = f[j] || i;

j Просто да вспомогательная переменная - имя атрибута, подскажите k获取свойствоизценить,Например console.log переоценить, поэтому k Просто да, чтобы меня забанили из метода Понятно

код Язык:javascript
копировать
i['__proto__'] = b['bind'](b);
i['toString'] = k['toString']['bind'](k);
f[j] = i;

банда Шинда i Функция добавляет некоторые атрибуты, такие как цепные связи, символы кода и т. д., но да на самом деле не имеет особого смысла. Удаление первых двух строк напрямую почти не влияет. Главное, это самая задняя строка да, Воля. i Функция назначает ценить Давать, чтобы заблокировать метод из, то есть указанный вызов. console.log 等эквивалентновызов i ,Конечно, выхода не будет.,Доехать Понятно экранировать из-за эффекта

Эта часть анализа немного длинная. Следующий шаг — это, главным образом, понимание элементов конфигурации.

6) selfDefending

тип:Boolean значение по умолчанию:false⚠️ использоватьэтот вариант После путаницы, ни в коем случае не меняйте обфускационный изкод, потому что любое из изменений, например, очернение кода, вызовет самозащиту, код Воля больше не будет работать! ⚠️этот вариант强制Воляcompactустановлен наtrue Эта опция делает выходной код устойчивым к форматированию и переименованию. Если попытаться существовать, запутайтесь в исходном коде onuse. JavaScript Украшатель,код Воля больше не работает,Это усложняет понимание и модификацию.

код Язык:javascript
копировать
// исходный код
console.log(123)
код Язык:javascript
копировать
// После путаницы
var b=(function(){var c=!![];return function(d,e){var f=c?function(){if(e){var g=e['apply'](d,arguments);e=null;return g;}}:function(){};c=![];return f;};}());var a=b(this,function(){return a['toString']()['search']('(((.+)+)+)+$')['toString']()['constructor'](a)['search']('(((.+)+)+)+$');});a();console['log'](0x7b);

код работает нормально

Попробуйте украсить/отформатировать код.

код Язык:javascript
копировать
// 美化назад
вар б = (функция() {
    вар c = !![];
    возвращаемая функция(d, e) {
        вар ж = с?
        функция() {
            если (е) {
                var g = e['apply'](d, аргументы);
                е = ноль;
                вернуть г;
            }
        }: функция() {};
        с = ![];
        вернуть f;
    };
} ());
var a = b(это,
функция() {
    return a['toString']()['search']('(((.+)+)+)+$')['toString']()['constructor'](a)['search'] ('(((.+)+)+)+$');
});
а();
консоль['журнал'](0x7b);

В это время выполнение будет остановлено и результат не будет возвращен.

проходить top Мы обнаружили, что компьютеры CPUЗаполняемость node Почти до места проживания Понятно 100%

Поскольку мы знаемисходный код,То есть, самая задняя линия,Поэтому он должен зависнуть по вышеуказанным причинам.,он продолжает выводить,Посмотрите, в чем проблема

финальный发сейчасдаэтот абзацкодпозволятьнашкомпьютерCPU Заполняемость растет

код Язык:javascript
копировать
return a['toString']()['search']('(((.+)+)+)+$')['toString']()['constructor'](a)['search']('(((.+)+)+)+$');

Это метод защиты, использующий регулярное сопоставление,Формат назадизнить Зависит от В换行、空格等字符出сейчас,Заставит обычное сопоставление войти в бесконечный цикл,Фактически, такого рода проблемы иногда возникают во время обычных функций.,Все называют это обычной бомбой,Подробности можно найти в《разговор в белой шляпеwebБезопасность 第二版》370Страница

7) debugProtection

тип:Boolean значение по умолчанию:false⚠️ Если вы откроете инструменты разработчика, вы можете получить зависание. Этот вариант вряд ли использует инструменты разработчика из функций отладчика (независимо от того, на чем основано WebKit извозвращатьсяда Mozilla Firefox начальство).

код Язык:javascript
копировать
// исходный код
console.log(123)
код Язык:javascript
копировать
// После путаницы
var H = (function () {
    var m = !![];
    return function (I, T) {
        var s = m ? function () {
            if (T) {
                var y = T['apply'](I, arguments);
                T = null;
                return y;
            }
        } : function () {
        };
        m = ![];
        return s;
    };
}());
(function () {
    H(this, function () {
        var m = new RegExp('function\x20*\x5c(\x20*\x5c)');
        var I = new RegExp('\x5c+\x5c+\x20*(?:[a-zA-Z_$][0-9a-zA-Z_$]*)', 'i');
        var T = a('init');
        if (!m['test'](T + 'chain') || !I['test'](T + 'input')) {
            T('0');
        } else {
            a();
        }
    })();
}());
console['log'](0x7b);
function a(m) {
    function I(T) {
        if (typeof T === 'string') {
            return function (s) {
            }['constructor']('while\x20(true)\x20{}')['apply']('counter');
        } else {
            if (('' + T / T)['length'] !== 0x1 || T % 0x14 === 0x0) {
                (function () {
                    return !![];
                }['constructor']('debu' + 'gger')['call']('action'));
            } else {
                (function () {
                    return ![];
                }['constructor']('debu' + 'gger')['apply']('stateObject'));
            }
        }
        I(++T);
    }
    try {
        if (m) {
            return I;
        } else {
            I(0x0);
        }
    } catch (T) {
    }
}

анализ стека результатов можно увидеть,debug да вызвано кодом на картинке из

Если вы смотрите код прибытия, проанализируйте его сами,Вместо того, чтобы просто смотреть на следующий контент и слова,У вас также может возникнуть вопрос: С логической точки зрения,Обычно вы должны иметь возможность передвигаться пешком.,Что ж, в изображении не рассматривалось, где приезжать, хранятся условия оценки, позволяющие определить, является ли да средой отладки?

Это верно,датакиз,Меня тоже этот вопрос беспокоит уже давно,После анализа,я发сейчас Понятноob использоватьизтехника

Он собирается поехать сюда, и здесь I Функция рекурсии, поэтому эти debug код Сразуда Выполнюиз,и будет продолжать выполнять,существование Внешняя страница кажется ничем,Но как только да войдет в инструменты разработчика,застрянет

Но здесь есть другая проблема,как остановить,Если вы продолжите выполнять из,Пустая трата пользовательских ресурсов, заявили в министерстве,Это также может привести к тому, что код не сможет продолжить выполнение.

здесь я должен сказать, что во всех языках разработки есть что-то Понятное —— аномальное

Рекурсивный вызов debug приведет к Страница面аномальный,Если исключение не перехвачено,вызовет прерывание кода,Давайте посмотрим на этот клип ниже:

код Язык:javascript
копировать
try {
    if (m) {
        return I;
    } else {
        I(0x0);
    }
} catch (T) {
}

Если вы посмотрите на «Понятно» выше и «Изкод», вы должны знать, что код вводится первым. return I ; Вторая запись назад I(0x0),этот时开始进入никто休止из debug , но система да тупо не допустит сбоя операционной системы, поэтому это вызовет аномальное событие. Из кода видно, что при возникновении аномального события оно будет. try...catch захватыватьприезжать,Тогда назад ничего не сделал,Продолжайте выполнять оставшийся логический код.

Как доказать это, два шага

Прежде всего, необходимо доказать, что существование не открывает консоль из,назадбашнясуществовать Нет断изосуществлятьdebug。нас Можетсуществовать debug Добавлено в исходник alert(1) код, анализ найден кодоназад alert(T) самый подходящийиз

здесь требует внимания,В качестве кода возврата назад используется выражение немедленного вызова.,такздесь Должно быть добавлено ; , в противном случае будет сообщено об ошибке

Если браузер не открывает инструмент отладки браузера, обновите его и посмотрите эффект.

Нажмите «ОК», и надпись «Назад» будет появляться постоянно.

Это подтвердит, что первый шаг Понятно, и действительно, был выполнен назадбашнясуществовать. debug

Во-вторых, нам нужно убедиться, что неограниченное debug приведет каномальный

Мы напрямую выводим аномальную информацию,Если вы ввели аномальныйиз,Сразу会以弹窗из формыобратная связьприезжать Страница面上

обновить страницу

аномальный信息 RangeError: Maximum call stack size exceeded,Нажмите «ОК», чтобы продолжить выполнение.

Это второй шаг для проверки Понятнонаша, поэтому ob и没иметьиспользовать Что高深技术,Просто дацикл,Изназадверноциклруководить Понятно Запутать

debugProtectionInterval

Тип: номер Значение по умолчанию: 0 ⚠️ Могу заморозить тебя из Браузер! использовать Используйте на свой страх и риск. При настройке используйте временные интервалы в миллисекундах из модели принудительной отладки на вкладке «Консоль», что затрудняет использование других функций инструментов разработчика. Если вы включите Понятно debugProtection, это действительно так. Предложенияценитьсуществовать 2000 приезжать 4000 между миллисекундами.

о debugger из Атака и защита,Уже есть очень зрелые статьи, обучающие всех, как обходить,Можно обратиться к

https://cloud.tencent.com/developer/article/2176916

8) ignoreRequireImports

тип:Boolean значение по умолчанию:false防止Запутать require импортировать。существовать某些случай,Когда по какой-то причине среда выполнения требует использовать только статические данные для импорта,Это может помочь.

9) domainLock

Тип: строковый массив значение по умолчанию:[]⚠️ этот вариант Нет适用В目标:'node'разрешено толькосуществоватьконкретный домени/или子域上运行Запутатьизисточниккод。Кому-то это мешаеткопироватьи粘贴您изисточниккодисуществоватьзапустить его в другом месте。 Если исходный код не работает на этом варианте обозначениеиз домена, то Браузер Воля перенаправляет приезжать, пропускает приезжать. domainLockRedirectUrl Опции из URL。 Несколько доменов и поддоменов Вы можете заблокировать несколько доменов и поддоменов. Например, заблокировать его, чтобы существовал только код. www.example.com Для продолжения добавьте www.example.com。сделать этосуществоватьвключать любые поддомены(example.com、sub.example.com)из Запуск в корневом домене,пожалуйстаиспользовать .example.com

код Язык:javascript
копировать
// исходный код
console.log(123)

настройкиrunizдоменное имя vvvvvvv.com

код Язык:javascript
копировать
// После путаницы

var b = (function () {
        var c = !![];
        return function (d, e) {
            var f = c ? function () {
                if (e) {
                    var g = e['apply'](d, arguments);
                    return e = null, g;
                }
            } : function () {
            };
            return c = ![], f;
        };
    }()), a = b(this, function () {
        var c;
        try {
            var f = Function('return\x20(function()\x20' + '{}.constructor(\x22return\x20this\x22)(\x20)' + ');');
            c = f();
        } catch (G) {
            c = window;
        }
        var g = new RegExp('[BXLZnQeBEYJRfanRwqdJEWKiMKnktgsV]', 'g'), h = 'vBvXvvvvvLZn.QecBEYoJRfanmRwqdJEWKiMKnktgsV'['replace'](g, '')['split'](';'), j, k, l, m, n = function (H, I, J) {
                if (H['length'] != I)
                    return ![];
                for (var K = 0x0; K < I; K++) {
                    for (var L = 0x0; L < J['length']; L += 0x2) {
                        if (K == J[L] && H['charCodeAt'](K) != J[L + 0x1])
                            return ![];
                    }
                }
                return !![];
            }, o = function (H, I, J) {
                return n(I, J, H);
            }, p = function (H, I, J) {
                return o(I, H, J);
            }, q = function (H, I, J) {
                return p(I, J, H);
            };
        for (var r in c) {
            if (n(r, 0x8, [
                    0x7,
                    0x74,
                    0x5,
                    0x65,
                    0x3,
                    0x75,
                    0x0,
                    0x64
                ])) {
                j = r;
                break;
            }
        }
        for (var s in c[j]) {
            if (q(0x6, s, [
                    0x5,
                    0x6e,
                    0x0,
                    0x64
                ])) {
                k = s;
                break;
            }
        }
        for (var t in c[j]) {
            if (p(t, [
                    0x7,
                    0x6e,
                    0x0,
                    0x6c
                ], 0x8)) {
                l = t;
                break;
            }
        }
        if (!('~' > k))
            for (var u in c[j][l]) {
                if (o([
                        0x7,
                        0x65,
                        0x0,
                        0x68
                    ], u, 0x8)) {
                    m = u;
                    break;
                }
            }
        if (!j || !c[j])
            return;
        var v = c[j][k], w = !!c[j][l] && c[j][l][m], x = v || w;
        if (!x)
            return;
        var y = ![];
        for (var z = 0x0; z < h['length']; z++) {
            var k = h[z], A = k[0x0] === String['fromCharCode'](0x2e) ? k['slice'](0x1) : k, B = x['length'] - A['length'], C = x['indexOf'](A, B), D = C !== -0x1 && C === B;
            D && ((x['length'] == k['length'] || k['indexOf']('.') === 0x0) && (y = !![]));
        }
        if (!y) {
            var E = new RegExp('[yRfrmZJUPqRCIfxNmCiQpmppBKF]', 'g'), F = 'aybRfourtm:ZJUbPlanqkRCIfxNmCiQpmppBKF'['replace'](E, '');
            c[j][l] = F;
        }
    });
a(), console['log'](0x7b);

Это не должно быть слишком сложно,здесь Волянаш域имя混入Понятнонитьсередина,Затем индекс назадсуществоватьпрохождения отфильтровывается.,Изназадисредапеременнаяидтиверно Сравнивать,Просто выполните то же самое,Если другое, прыгайте

10) Domain Lock Redirect Url

Перейдите по URL-адресу в предыдущей статье.

11) sourceMap

тип:Boolean значение по умолчанию:falseдавать возможность Запутатькодизисточник映射генерировать。 Карты исходных кодов помогают устранять обфускации JavaScript источниккод。если ты хочешьилинуждатьсясуществовать生产серединаруководить调试,Вы можете Воля отделить исходные файлы карты и загрузить приехать в секретную локацию.,Тогда назад Воля Браузер указывает туда.

Это не имеет прямого отношения к технологии обфускации. В основном это зависит от требований отладки.

Следующие несколько из них связаны с изменениями персонажей, в основном с различными изменениями.

12) stringArray

тип:Boolean значение по умолчанию:trueудалитьнитьхарактери Воляони ставят специальныемножествосередина。Например,var m = "Hello World"; внить“Hello World”Воляодеяло替换для var m = _0x12c456[0x1];

существовало до того, как мы увидели этот вид. Понятно, что персонаж Воля становится множеством индексов для получения ценить.

13) stringArrayRotate

тип:Boolean значение по умолчанию:true⚠️ stringArray Должно быть включено Воля stringArray множество мобильных фиксированных и случайных (существоватькод, генерируемый при путанице) позиций. Из-за этого удаленному заказу на изнесение Воля становится сложнее соответствовать исходному положению.

Проще говоря, выбор да из ценитьиз должен быть более случайным.

14) stringArrayShuffle

тип:Boolean значение по умолчанию:true⚠️ stringArray Должно быть включено перетасовать в случайном порядке stringArray Элементы массива.

15) stringArrayThreshold

Тип: номер Значение по умолчанию: 0.8 Минимальное значение: 0 Максимальное значение: 1 ⚠️ stringArray Параметры Должно быть включено Вы можете использовать эту настройку, чтобы настроить вставку текста Волянить. stringArray из вероятности (от 0 приезжать 1)。 этотнастраиватьверно В大формакод特别иметь用,因для它会重复вызовнитьмножествои会减медленныйкодскорость。stringArrayThreshold: 0 равный stringArray: false

Элементы конфигурации на официальном сайте по умолчанию да. 0.75 , не да 0.8

16) stringArrayIndexShift

тип:Boolean значение по умолчанию:true⚠️ stringArray Параметры Должно быть включено Включить дополнительное смещение индекса для всех нит множествовызов

17) stringArrayIndexesType

Тип: строковый массив значение по умолчанию:['hexadecimal-number']⚠️ stringArray Параметры Должно быть включено Позволяет управлять индексом нитьмножествовызов по типу. каждый stringArray Индексы вызовов преобразуются по случайно выбранному типу из переданного списка. Это делает возможными многие виды использования. Доступные значения:

  • 'hexadecimal-number'(по умолчанию):Волянитьмножествовызов索引Конвертироватьдля十六进制число
  • 'hexadecimal-numeric-string':Волянитьмножествовызов索引Конвертироватьдля十六进制числонить

существовать 2.9.0 版本Из前,javascript-obfuscator Воля Все индексы нитмножествовызов преобразуются в шестнадцатеричный тип нит. Это немного усложняет ручную деобфускацию, но позволяет автоматическим деобфускаторам легко их обнаружить. Новый тип шестнадцатеричных чисел усложняет автоматическое обнаружение кода в нить множествовызовмодели. В будущем Воля добавит больше типов.

18) stringArrayCallsTransform

тип:Boolean значение по умолчанию:false⚠️ stringArray Параметры Должно быть включено давать возможностьверно stringArray извызовиз конверсии. в соответствии с stringArrayCallsTransformThreshold ценить,Эти параметры вызова могут извлекать различные изверно слоны. поэтому,Автоматически становится сложнее найти верность множествоизвызов.

stringArrayCallsTransformThreshold

Тип: номер Значение по умолчанию: 0.5 ⚠️ stringArray и stringArrayCallsTransformThreshold Параметры Должно быть включено ты можешьиспользоватьэтотнастраиватькорректироватьвернонитьмножествоизвызоводеяло Конвертироватьиз вероятности (от 0 приезжать 1)。

код Язык:javascript
копировать
// исходный код
function hi() {
  console.log("Hello World!");
}
hi();
код Язык:javascript
копировать
// Проверить этот товар путаницы
function hi() {
    var c = {
        d: 0x0,
        e: 0x1
    };
    console[b(c.d)](b(c.e));
}
function b(c, d) {
    var e = a();
    b = function (f, g) {
        f = f - 0x0;
        var h = e[f];
        return h;
    };
    return b(c, d);
}
hi();
function a() {
    var d = [
        'log',
        'Hello\x20World!'
    ];
    a = function () {
        return d;
    };
    return a();
}
код Язык:javascript
копировать
// еще нет Проверить этот товар путаницы
function hi() {
    console[b(0x0)](b(0x1));
}
function b(c, d) {
    var e = a();
    b = function (f, g) {
        f = f - 0x0;
        var h = e[f];
        return h;
    };
    return b(c, d);
}
function a() {
    var c = [
        'log',
        'Hello\x20World!'
    ];
    a = function () {
        return c;
    };
    return a();
}
hi();

Вы можете увидеть проверку прибытия назад и появиться Понятно несколько похожих. c.d、c.e Этот видвызов путь

19) stringArrayWrappersCount

Тип: номер Значение по умолчанию: 1 ⚠️ stringArray Параметры Должно быть включено область настройки корневого корня или функции нить множества оберток. Фактическое количество оберток в диапазоне каждый ограничено количеством литеральных узлов в диапазоне.

Я также поискал некоторую информацию, чтобы понять этот вариант.,obРучка проектанитьжить储существоватьмножествовнутри,Вопрос о том, чтобы снова взять цену, уже обсуждался ранее.,здесьиз обертки,Просто обратитесь к дафункции,Эта функция отвечает за получение цен из множества по индексу.,具体нравиться何包装Сразу看 ob Понятно, этот элемент конфигурации сообщает вам, сколько Этих будет в настройке. видфункция, а не сколько используется для хранения измножество га

20) stringArrayWrappersType

Тип: строка значение по умолчанию:variable⚠️ stringArray и stringArrayWrappersCount Параметры Должно быть включено Разрешить выбор по stringArrayWrappersCount Опции прилагаются из типа обертки. Доступные значения:

  • 'variable':существоватькаждый Объемиз Верхнее креплениепеременнаяобертка。Высокая производительность。
  • 'function':существоватькаждый Объем内из Добавление случайного местоположения Функциональная оболочка。性能Сравниватьпеременнаямедленный,Но обеспечивает более строгую запутывание.

Когда потеря производительности действительно запутывает приложение, оно мало влияет,Настоятельно рекомендуетсяиспользовать Функциональная оболочкаруководить更高程度из Запутать。

тип обертки с изображением,Я выше сказал, что обертка - это просто дафункция,Из официальной конфигурации,Только один тип,Также дапеременная обертка,Но официального случая Давать переменную обертку не существует.,官网возвращатьсядабрать Функциональная оболочка Примериз

Тогда давайте попрактикуемся сами

код Язык:javascript
копировать
// исходный код
const foo = 'foo';

function test () {
    const bar = 'bar';
    console.log(foo, bar);
}

test();
код Язык:javascript
копировать
// Живописные снежинки
константа d = б;
функция а() {
    константа е = [
        'фу',
        'бар',
        'бревно'
    ];
    а = функция() {
        вернуть f;
    };
    вернуть ( ) ;
} }
const foo = d(0x0);
функция б(с, d) {
    константа е = а();
    б = функция (f, g) {
        е = е -- 0x0;
        пусть h = e[f];
        вернуть ч;
    };
    вернуть б (в, г);
} }
функция тест() {
    константа е = б;
    константа с = е (0x1);
    консоль [e (0x2)] (foo, c);
} }
тест ( ) ;
код Язык:javascript
копировать
// После путаницы Функциональная оболочка
function b(c, d) {
    const e = a();
    b = function (f, g) {
        f = f - 0x0;
        let h = e[f];
        return h;
    };
    return b(c, d);
}
const foo = 'foo';
function test() {
    const c = d(0xe4, 0xe5);
    function d(c, e) {
        return b(e - 0xe5, c);
    }
    console[d(0xe5, 0xe6)](foo, c);
}
function a() {
    const f = [
        'bar',
        'log'
    ];
    a = function () {
        return f;
    };
    return a();
}
test();

По сравнению с проведением, основные отличия изкода заключаются в следующем:

код Язык:javascript
копировать
// переменнаяобертка
function test() {
    const e = b;
    const c = e(0x1);
    console[e(0x2)](foo, c);
}

// Функциональная оболочка
function test() {
    const c = d(0xe4, 0xe5);
    function d(c, e) {
        return b(e - 0xe5, c);
    }
    console[d(0xe5, 0xe6)](foo, c);
}

Я не думаю, что это имеет какой-либо смысл

21) stringArrayWrappersParametersMaxCount

Тип: номер Значение по умолчанию: 2 ⚠️ stringArray Параметры Должно быть включено ⚠️ В настоящее время эта опция влияет только stringArrayWrappersType Опция функцииценить добавить из оболочки Позволяет контролировать максимальное количество множество оберток параметров. Минимальная цена по умолчанию составляет 2. Рекомендуемое значение находится между 2 и 5 между.

этотда Функциональная оболочка才иметьиз

22) stringArrayWrappersChainedCalls

тип:Boolean значение по умолчанию:true⚠️ stringArray и stringArrayWrappersCount Параметры Должно быть включено Включает цепочку между обертками нитмножество.

23) stringArrayEncoding

Тип: строковый массив значение по умолчанию:[]⚠️ stringArray Параметры Должно быть включено Эта опция может замедлить работу вашего скрипта. использовать base64 или rc4 верно stringArray Из всего текста есть кодирование, вставленное в существующую среду выполнения, которая декодируется из специального кода. каждый stringArray ценить Воляпроходить случайным образом выбрать изкодирование из списка доставки для кодирования. Это делает возможным использование разнообразного кодирования. Доступные значения:

  • 'none'(логическое значениеценить):Неткодирование stringArray ценить
  • 'base64'(нить):использовать base64 кодирование stringArray ценить
  • 'rc4'(нить):использовать rc4 верно stringArray ценитьруководитькодирование。Сравнивать base64 Назначайте встречу медленно 30-50%, но получить первоначальную цену сложнее. Предложения rc4 Отключено при кодировании unicodeEscapeSequence Параметр предотвращения путаницы. Код слишком велик.

Это должен быть даверно магазин изнить кодирование магазина

24) splitStrings

тип:Boolean значение по умолчанию:falseВоляхарактернить拆分для长度для splitStringsChunkLength Опции ценитьиз блока.

25) splitStringsChunkLength

Тип: номер Значение по умолчанию: 10 настраивать splitStrings Опции издлина блока。

26) unicodeEscapeSequence

тип:Boolean значение по умолчанию:falseпозволятьдавать возможность/Запрещатьнить Конвертироватьдля unicode последовательность выхода. Unicode Escape-последовательности значительно увеличивают размер Понятнокода, и нить может легко восстановить исходный вид. Рекомендуется включать это только для небольших источников.

Я это уже видел, в этом нет ничего нового.

27) forceTransformStrings

Тип: строковый массив значение по умолчанию:[]давать возможностьнитьхарактеризбросать,Долженнитьхарактерипередачаиз RegExp совпадения шаблонов. ⚠️ Эта опция влияет только на stringArrayThreshold (или Воля может из другого порогаценить) Конверсия изнить Должен Параметры优Первый ВreservedStringsПараметры,Но не имеет приоритета над условными комментариями.

Если такие есть, обязательно запутайте изнинить,Можно добавить в жильё множество,Принудительное преобразование

28) reservedStrings

Тип: строковый массив значение по умолчанию:[]Запрещатьнитьхарактериз Конвертировать,Долженнитьхарактерипередачаиз RegExp совпадения шаблонов.

Обязательно сохраните изнить, можно поместить в существующее множество

Далее введите часть имени идентификатора Понятно, которая также является именем дапеременной и так далее.

29) identifierNamesGenerator

Тип: строка значение по умолчанию:hexadecimalнастраивать标识符имя称генерировать器。 Доступные значения:

  • dictionary из списка идентификаторов Список словарей из имени идентификатора
  • hexadecimal картина Имена идентификаторов, такие как _0xabc123,
  • manged:短标识符имя称,нравиться a、b、c
  • mangled-shuffled:и mangled То же самое, но алфавитный порядок нарушен.

Это очень важно,В какой форме генерируются эти переменные имена?,Предыдущий из Демонстрация как понятно просто,Все选择из manged

30) identifiersDictionary

Тип: строковый массив значение по умолчанию:[]дляidentifierNamesGeneratorнастраиватьсловарь идентификаторов:dictionarydictionaryвкаждый标识符Все Воля用В几индивидуальный变体середина,Символы каждый и из имеют разный регистр. поэтому,dictionaryсередина标识符из数量отвечать Должен取决В原始источниккодвколичество идентификаторов。

Если у вас есть словарь (множество символов),Там куча персонажей,Таким образом вы можете обозначииеиспользовать этот словарь для замены тех идентификаторов, которые подлежат замене.

31) identifiersPrefix

Тип: строка значение по умолчанию:''настраивать所иметьобщая идентификатор ситуации из префикса. 当您想хотеть Запутать多индивидуальныйдокумент时,пожалуйстаиспользоватьэтотпараметры.этот вариантиметь助В避免这些документизобщая ситуация标识符Из间изконфликт。каждыйдокументиз前缀отвечать Должен Нет同。

32) renameGlobals

тип:Boolean значение по умолчанию:false⚠️этот Параметры可能会破坏你изкод。仅当您Знать它из作用时才давать возможность它! давать возможностьобщая ситуацияпеременнаяифункцияимя称и声明из Запутать。

33) renameProperties

тип:Boolean значение по умолчанию:false⚠️этот вариант可能会破坏您изкод。仅当您Знать它из作用时才давать возможность它! Включает переименование имени атрибута. Все встроенное DOM Свойства и ядро JavaScript Атрибуты класса В игнорируются.

  • хотетьсуществоватьэтот Опции из Безопасностьмодельи Нет Безопасностьмодель Из间切换,пожалуйстаиспользовать renamePropertiesMode параметры.
  • Для настройки переименуйте имя атрибута из формата,пожалуйстаиспользоватьidentifierNamesGeneratorпараметры.
  • Какими свойствами управлять Волябыл переименован,пожалуйстаиспользоватьreservedNamesпараметры.
34) renamePropertiesMode

Тип: строка значение по умолчанию: safe⚠️ Несмотря на тосуществоватьsafeмодель Вниз,renameProperties Опции также могут испортить вам исходник. обозначение renameProperties Режим опций:

  • safe 2.11.0 Отпустите назадиз поведения по умолчанию. Попробуйте переименовать свойства более безопасным способом, чтобы предотвратить ошибки во время выполнения. При использовании этой модели некоторые атрибуты Воля исключены из существующего переименования.
  • unsafe 2.11.0 Поведение по умолчанию до версий. Переименовывайте свойства небезопасным способом, без каких-либо ограничений.

Если один файл имеет тот же атрибут «из существования», что и другой файл, используйте опцию «использовать_идентификаторы_кэша», чтобы сохранить одинаковое имя атрибута «из» между этими файлами.

35) reservedNames

Тип: строковый массив значение по умолчанию:[]Запрещать标识符из Запутатьигенерировать,这些标识符ипередачаиз RegExp совпадения шаблонов.

36) compact

тип:Boolean значение по умолчанию:trueкомпактныйизкодвыходсуществоватьна одной линии。

Просто сжимаем код в одну строку

37) simplify

тип:Boolean значение по умолчанию:trueпроходить简化давать возможность额外изкод Запутать。 ⚠️ существуетFuture из версии, логический литерал запутан (true => !![]) Воля перешёл по этому варианту.

Этот вариант упрощен,Измените некоторую легко читаемую логику исходного кодирования на троичные операторы и т. д.,Есть некоторые детали,Вы можете изучить это.

38) transformObjectKeys

тип:Boolean значение по умолчанию:falseдавать возможностьвернослон键из Конвертировать。

код Язык:javascript
копировать
// исходный код
var object = {
  foo: 'test1',
  bar: {
    baz: 'test2'
  }
};
код Язык:javascript
копировать
// После путаницы
var a = {};
a['baz'] = 'test2';
var b = {};
b['foo'] = 'test1';
b['bar'] = a;
var object = b;

Похоже, что преобразование ключа верверно в из не очень очевидно и не дает официального эффекта приезжать.

Возможно, да придется открыть другие опции, а не только настройки "шестнадцатеричной модели"

39) numbersToExpressions

тип:Boolean значение по умолчанию:false

Разрешить преобразование чисел в выражения

код Язык:javascript
копировать
// исходный код
var demo1 = 23;
var demo2 = 24;

var result = demo1 + demo2;
код Язык:javascript
копировать
// После путаницы
var demo1 = 0x29d * -0x2 + -0x22f7 + -0x2 * -0x1424;
var demo2 = -0x17b8 * 0x1 + -0x1933 * 0x1 + 0x3103;
var result = demo1 + demo2;

Сначала я отметил не тот вариант Понятно,Я все еще думаю, что это немного просто,сейчассуществовать Может Понятно

40) controlFlowFlattening

тип:Boolean значение по умолчанию:false⚠️ Эта опция сильно влияет на производительность, работая максимально медленно, 1.5 раз。использовать controlFlowFlatteningThreshold настройки Процент узлов, на которые влияет выравнивание потока управления. Включает выравнивание потока управления. Сглаживание потока управления — это преобразование, которое не позволяет программе понять исходную структуру.

окодвыравнивание потока управления Можно обратиться кнекоторые статьи

https://www.cnblogs.com/ichunqiu/p/7383045.html

Посмотри на этоиндивидуальный扁平化,Я всегда могу вспомнить строчку из «Китайского партнера»: «Мать двадцать лет потратила на то, чтобы вырастить его.,А другой женщине понадобилось всего двадцать минут, чтобы снова превратить его в Понимаемого дурака.

41) controlFlowFlatteningThreshold

Тип: номер Значение по умолчанию: 0.75 Минимальное значение: 0 Максимальное значение: 1controlFlowFlattening Преобразование Воля применяется к любому заданному узлу вероятности. этотнастраиватьверно В大формакод特别иметь用,因для大量控制流Конвертировать会减медленныйкодскоростьи增加кодразмер。controlFlowFlatteningThreshold: 0 равный controlFlowFlattening: false

42) deadCodeInjection

тип:Boolean значение по умолчанию:false⚠️ Значительно увеличена путаница в размере кода (до 200%), только если путаница в размере кодирования не важна. использовать deadCodeInjectionThreshold настройки Процент узлов, затронутых внедрением мертвого кода. ⚠️ Эта опция должна быть включена принудительно stringArray параметры. использовать С помощью этой опции добавляются случайные блоки мертвого кода Воля.

Код смерти тоже раздражает

код Язык:javascript
копировать
// исходный код
console.log(1)
код Язык:javascript
копировать
// После путаницы
var _0x54c615 = _0x4d77;
(function (_0x2f01cd, _0x282040) {
    var _0xfd38d6 = _0x4d77;
    var _0x418071 = _0x2f01cd();
    while (!![]) {
        try {
            var _0x5384d1 = parseInt(_0xfd38d6(0x1ed)) / 0x1 + -parseInt(_0xfd38d6(0x1f2)) / 0x2 + -parseInt(_0xfd38d6(0x1eb)) / 0x3 + -parseInt(_0xfd38d6(0x1e9)) / 0x4 * (-parseInt(_0xfd38d6(0x1f1)) / 0x5) + -parseInt(_0xfd38d6(0x1ec)) / 0x6 * (parseInt(_0xfd38d6(0x1f0)) / 0x7) + parseInt(_0xfd38d6(0x1ef)) / 0x8 + parseInt(_0xfd38d6(0x1ea)) / 0x9;
            if (_0x5384d1 === _0x282040) {
                break;
            } else {
                _0x418071['push'](_0x418071['shift']());
            }
        } catch (_0x99f199) {
            _0x418071['push'](_0x418071['shift']());
        }
    }
}(_0x2499, 0x8b99e));
function _0x4d77(_0x53739e, _0x427c10) {
    var _0x249929 = _0x2499();
    _0x4d77 = function (_0x4d7790, _0x3cb070) {
        _0x4d7790 = _0x4d7790 - 0x1e9;
        var _0x4fc869 = _0x249929[_0x4d7790];
        return _0x4fc869;
    };
    return _0x4d77(_0x53739e, _0x427c10);
}
console[_0x54c615(0x1ee)](0x1);
function _0x2499() {
    var _0x3c0042 = [
        '4uTkwuQ',
        '8809173qEYNab',
        '1628760aaOeDK',
        '84qlULXN',
        '99299HMwqSP',
        'log',
        '4523368ohaBbo',
        '437311NMYccT',
        '1998515lIAtLG',
        '107744EAbXbU'
    ];
    _0x2499 = function () {
        return _0x3c0042;
    };
    return _0x2499();
}
43) deadCodeInjectionThreshold

Тип: номер Значение по умолчанию: 0.4 Минимальное значение: 0 Максимальное значение: 1 позволятьнастраивать受 deadCodeInjection 影响из节点百分Сравнивать。


Если вы подпишетесь на меня и посмотрите Понятное дело целиком. ob из Запутать方式,поздравления,По сути, уже верно, что путаница означает, что существует Понятное Понятное решение.,ob даиндивидуальный优秀изпроект,Если у проекта есть способ оценить,Вся признательность за эту статью будет удвоена за передачу этого проекта.

Дальше контент будет намного проще Понятно,Интересно, но не депрессивно,Кажется, я только что вышел ob из你尤其нуждаться它,если не нужно,Вы также можете пропустить

6. jjencode

https://utf-8.jp/public/jjencode.html

Поверьте, судя по названию,ты уже знаешь,Это метод кодирования, позволяющий добиться путаницы из,Но я не думаю, что это может выглядеть странно.

код Язык:javascript
копировать
// исходный код
console.log("Hello, JavaScript")
код Язык:javascript
копировать
// кодированиеназад
$=~[];$={___:++$,$$$$:(![]+"")[$],__$:++$,$_$_:(![]+"")[$],_$_:++$,$_$$:({}+"")[$],$$_$:($[$]+"")[$],_$$:++$,$$$_:(!""+"")[$],$__:++$,$_$:++$,$$__:({}+"")[$],$$_:++$,$$$:++$,$___:++$,$__$:++$};$.$_=($.$_=$+"")[$.$_$]+($._$=$.$_[$.__$])+($.$$=($.$+"")[$.__$])+((!$)+"")[$._$$]+($.__=$.$_[$.$$_])+($.$=(!""+"")[$.__$])+($._=(!""+"")[$._$_])+$.$_[$.$_$]+$.__+$._$+$.$;$.$$=$.$+(!""+"")[$._$$]+$.__+$._+$.$+$.$$;$.$=($.___)[$.$_][$.$_];$.$($.$($.$$+"\""+$.$$__+$._$+"\\"+$.__$+$.$_$+$.$$_+"\\"+$.__$+$.$$_+$._$$+$._$+(![]+"")[$._$_]+$.$$$_+"."+(![]+"")[$._$_]+$._$+"\\"+$.__$+$.$__+$.$$$+"(\\\"\\"+$.__$+$.__$+$.___+$.$$$_+(![]+"")[$._$_]+(![]+"")[$._$_]+$._$+",\\"+$.$__+$.___+"\\"+$.__$+$.__$+$._$_+$.$_$_+"\\"+$.__$+$.$$_+$.$$_+$.$_$_+"\\"+$.__$+$._$_+$._$$+$.$$__+"\\"+$.__$+$.$$_+$._$_+"\\"+$.__$+$.$_$+$.__$+"\\"+$.__$+$.$$_+$.___+$.__+"\\\")"+"\"")())();

Принцип на самом деле не сложный,Но если он создан людьми, это должно быть весьма интересно.,Если вы хотите узнать больше о том, как проектировать Понятно,Можно обратиться к以Вниз文章

https://yuanbug.github.io/2019/08/14/2019/my-js-obfuscation-encode/

Метод расшифровки этого вида также очень прост. Существует множество существующих платформ, которые могут обеспечить расшифровку.

http://www.hiencode.com/jjencode.html

7. AAencode

https://utf-8.jp/public/aaencode.html

код Язык:javascript
копировать
// исходный код
console.log("Hello, JavaScript")
код Язык:javascript
копировать
// После путаницы
゚ω゚ノ= /`m´)ノ ~┻━┻   //*´∇`*/ ['_']; o=(゚ー゚)  =_=3; c=(゚Θ゚) =(゚ー゚)-(゚ー゚); (゚Д゚) =(゚Θ゚)= (o^_^o)/ (o^_^o);(゚Д゚)={゚Θ゚: '_' ,゚ω゚ノ : ((゚ω゚ノ==3) +'_') [゚Θ゚] ,゚ー゚ノ :(゚ω゚ノ+ '_')[o^_^o -(゚Θ゚)] ,゚Д゚ノ:((゚ー゚==3) +'_')[゚ー゚] }; (゚Д゚) [゚Θ゚] =((゚ω゚ノ==3) +'_') [c^_^o];(゚Д゚) ['c'] = ((゚Д゚)+'_') [ (゚ー゚)+(゚ー゚)-(゚Θ゚) ];(゚Д゚) ['o'] = ((゚Д゚)+'_') [゚Θ゚];(゚o゚)=(゚Д゚) ['c']+(゚Д゚) ['o']+(゚ω゚ノ +'_')[゚Θ゚]+ ((゚ω゚ノ==3) +'_') [゚ー゚] + ((゚Д゚) +'_') [(゚ー゚)+(゚ー゚)]+ ((゚ー゚==3) +'_') [゚Θ゚]+((゚ー゚==3) +'_') [(゚ー゚) - (゚Θ゚)]+(゚Д゚) ['c']+((゚Д゚)+'_') [(゚ー゚)+(゚ー゚)]+ (゚Д゚) ['o']+((゚ー゚==3) +'_') [゚Θ゚];(゚Д゚) ['_'] =(o^_^o) [゚o゚] [゚o゚];(゚ε゚)=((゚ー゚==3) +'_') [゚Θ゚]+ (゚Д゚) .゚Д゚ノ+((゚Д゚)+'_') [(゚ー゚) + (゚ー゚)]+((゚ー゚==3) +'_') [o^_^o -゚Θ゚]+((゚ー゚==3) +'_') [゚Θ゚]+ (゚ω゚ノ +'_') [゚Θ゚]; (゚ー゚)+=(゚Θ゚); (゚Д゚)[゚ε゚]='\\'; (゚Д゚).゚Θ゚ノ=(゚Д゚+ ゚ー゚)[o^_^o -(゚Θ゚)];(o゚ー゚o)=(゚ω゚ノ +'_')[c^_^o];(゚Д゚) [゚o゚]='\"';(゚Д゚) ['_'] ( (゚Д゚) ['_'] (゚ε゚+(゚Д゚)[゚o゚]+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ (o^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ ((゚ー゚) + (o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ ((o^_^o) +(o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) +(o^_^o))+ (o^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ ((゚ー゚) + (o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ ((゚ー゚) + (゚Θ゚))+ (゚Д゚)[゚ε゚]+((゚ー゚) + (゚Θ゚))+ ((o^_^o) +(o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ ((゚ー゚) + (o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ ((゚ー゚) + (o^_^o))+ (゚Д゚)[゚ε゚]+((゚ー゚) + (゚Θ゚))+ (c^_^o)+ (゚Д゚)[゚ε゚]+(゚ー゚)+ ((o^_^o) - (゚Θ゚))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚Θ゚)+ (c^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ ((゚ー゚) + (゚Θ゚))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ ((゚ー゚) + (o^_^o))+ (゚Д゚)[゚ε゚]+((゚ー゚) + (゚Θ゚))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚ー゚)+ (c^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚Θ゚)+ ((o^_^o) - (゚Θ゚))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ (゚Θ゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) +(o^_^o))+ ((o^_^o) +(o^_^o))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ (゚Θ゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) - (゚Θ゚))+ (o^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ (゚ー゚)+ (o^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) +(o^_^o))+ ((o^_^o) - (゚Θ゚))+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((゚ー゚) + (゚Θ゚))+ (゚Θ゚)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) +(o^_^o))+ (c^_^o)+ (゚Д゚)[゚ε゚]+(゚Θ゚)+ ((o^_^o) +(o^_^o))+ (゚ー゚)+ (゚Д゚)[゚ε゚]+(゚ー゚)+ ((o^_^o) - (゚Θ゚))+ (゚Д゚)[゚ε゚]+((゚ー゚) + (゚Θ゚))+ (゚Θ゚)+ (゚Д゚)[゚o゚]) (゚Θ゚)) ('_');

декодировать веб-сайт

http://www.metools.info/code/aaencode214.html

8. jsfuck

https://jsfuck.com/

код Язык:javascript
копировать
// исходный код
console.log(1)
код Язык:javascript
копировать
// После путаницы
[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]][([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]]((!![]+[])[+!+[]]+(!![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+([][[]]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+!+[]]+(+[![]]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]+(+(!+[]+!+[]+!+[]+[+!+[]]))[(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([]+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]][([][[]]+[])[+!+[]]+(![]+[])[+!+[]]+((+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]]+[])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]]](!+[]+!+[]+!+[]+[!+[]+!+[]])+(![]+[])[+!+[]]+(![]+[])[!+[]+!+[]])()(([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(![]+[])[!+[]+!+[]]+(!![]+[])[!+[]+!+[]+!+[]]+(+(+!+[]+[+!+[]]+(!![]+[])[!+[]+!+[]+!+[]]+[!+[]+!+[]]+[+[]])+[])[+!+[]]+(![]+[])[!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(![]+[+[]]+([]+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]])[!+[]+!+[]+[+[]]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[+!+[]+[!+[]+!+[]+!+[]]]+[+!+[]]+([+[]]+![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[!+[]+!+[]+[+[]]])

0x04 некоторые мысли

обфускация кода да защита кода и предотвращение обратного проектирования изоптимизации,Но я не чувствую себя окончательным решением,Я считаю, что обфускация кода будет продолжать играть важную роль в окончательном решении проблемы существования.

Спасибо за создание инструмента для обфускации кода.、Методы и способы борьбы с людьми, добивающимися расшифровки

boy illustration
[Спецификация] Результаты и исключения возврата интерфейса SpringBoot обрабатываются единообразно, поэтому инкапсуляция является элегантной.
boy illustration
Интерпретация каталога веб-проекта Flask
boy illustration
Что такое подробное объяснение файла WSDL_wsdl
boy illustration
Как запустить большую модель ИИ локально
boy illustration
Подведение итогов десяти самых популярных веб-фреймворков для Go
boy illustration
5 рекомендуемых проектов CMS с открытым исходным кодом на базе .Net Core
boy illustration
Java использует httpclient для отправки запросов HttpPost (отправка формы, загрузка файлов и передача данных Json)
boy illustration
Руководство по развертыванию Nginx в Linux (Centos)
boy illustration
Интервью с Alibaba по Java: можно ли использовать @Transactional и @Async вместе?
boy illustration
Облачный шлюз Spring реализует примеры балансировки нагрузки и проверки входа в систему.
boy illustration
Используйте Nginx для решения междоменных проблем
boy illustration
Произошла ошибка, когда сервер веб-сайта установил соединение с базой данных. WordPress предложил решение проблемы с установкой соединения с базой данных... [Легко понять]
boy illustration
Новый адрес java-библиотеки_16 топовых Java-проектов с открытым исходным кодом, достойных вашего внимания! Обязательно к просмотру новичкам
boy illustration
Лучшие практики Kubernetes для устранения несоответствий часовых поясов внутри контейнеров
boy illustration
Введение в проект удаления водяных знаков из коротких видео на GitHub Douyin_TikTok_Download_API
boy illustration
Весенние аннотации: подробное объяснение @Service!
boy illustration
Пожалуйста, не используйте foreach для пакетной вставки в MyBatis. Для 5000 фрагментов данных потребовалось 14 минут. .
boy illustration
Как создать проект Node.js с помощью npm?
boy illustration
Mybatis-plus использует typeHandler для преобразования объединенных строк String в списки списков.
boy illustration
Не удалось установить программное обеспечение Mitsubishi. Возможно, возникла проблема с реестром.
boy illustration
Разрешение ошибок проекта SpringBoot 3 mybatis-plus: org.apache.ibatis.binding.BindingException: неверный оператор привязки
boy illustration
Более краткая проверка параметров. Для проверки параметров используйте SpringBoot Validation.
boy illustration
Поиграйтесь с интеграцией Spring Boot (платформа запланированных задач Quartz)
boy illustration
Несколько популярных режимов интерфейса API: RESTful, GraphQL, gRPC, WebSocket, Webhook.
boy illustration
Redis: практика публикации (pub) и подписки (sub)
boy illustration
Подробное объяснение пакета Golang Context
boy illustration
Краткое руководство: создайте свое первое приложение .NET Aspire
boy illustration
Краткое обсуждение метода пакетной вставки MyBatis: обработка 100 000 фрагментов данных занимает всего 2 секунды.
boy illustration
[Инструмент] Используйте nvm для управления переключением версий nodejs, это так здорово!
boy illustration
HTML можно преобразовать в word_html для отображения текстовых документов.