diff --git a/dist/index.js b/dist/index.js index 3e5f7fa6..87960ea8 100644 --- a/dist/index.js +++ b/dist/index.js @@ -22,6 +22,7 @@ JavaScriptObfuscator.defaultOptions = { debugProtection: false, debugProtectionInterval: false, disableConsoleOutput: true, + encodeUnicodeArray: false, rotateUnicodeArray: true, wrapUnicodeArrayCalls: true }; diff --git a/dist/src/node-groups/UnicodeArrayNodesGroup.js b/dist/src/node-groups/UnicodeArrayNodesGroup.js index 7ac8d030..4cc2bddc 100644 --- a/dist/src/node-groups/UnicodeArrayNodesGroup.js +++ b/dist/src/node-groups/UnicodeArrayNodesGroup.js @@ -1,6 +1,7 @@ "use strict"; const NodesGroup_1 = require('./NodesGroup'); const UnicodeArrayCallsWrapper_1 = require("../custom-nodes/unicode-array-nodes/UnicodeArrayCallsWrapper"); +const UnicodeArrayDecodeNode_1 = require("../custom-nodes/unicode-array-nodes/UnicodeArrayDecodeNode"); const UnicodeArrayNode_1 = require('../custom-nodes/unicode-array-nodes/UnicodeArrayNode'); const UnicodeArrayRotateFunctionNode_1 = require('../custom-nodes/unicode-array-nodes/UnicodeArrayRotateFunctionNode'); const Utils_1 = require('../Utils'); @@ -18,6 +19,9 @@ class UnicodeArrayNodesGroup extends NodesGroup_1.NodesGroup { if (this.options['rotateUnicodeArray']) { this.nodes.set('unicodeArrayRotateFunctionNode', new UnicodeArrayRotateFunctionNode_1.UnicodeArrayRotateFunctionNode(this.unicodeArrayName, unicodeArray, this.unicodeArrayRotateValue)); } + if (this.options['encodeUnicodeArray']) { + this.nodes.set('unicodeArrayDecodeNode', new UnicodeArrayDecodeNode_1.UnicodeArrayDecodeNode(this.unicodeArrayName, unicodeArray)); + } } } exports.UnicodeArrayNodesGroup = UnicodeArrayNodesGroup; diff --git a/dist/src/node-obfuscators/NodeObfuscator.js b/dist/src/node-obfuscators/NodeObfuscator.js index 20efde40..92760d47 100644 --- a/dist/src/node-obfuscators/NodeObfuscator.js +++ b/dist/src/node-obfuscators/NodeObfuscator.js @@ -30,7 +30,11 @@ class NodeObfuscator { return `${prefix}${Utils_1.Utils.decToHex(nodeValue)}`; } replaceLiteralStringByUnicodeArrayCall(nodeValue) { - let value = Utils_1.Utils.stringToUnicode(nodeValue); + let value = nodeValue; + if (this.options['encodeUnicodeArray']) { + value = new Buffer(value).toString('base64'); + } + value = Utils_1.Utils.stringToUnicode(value); let unicodeArray = this.nodes.get('unicodeArrayNode').getNodeData(), sameIndex = unicodeArray.indexOf(value), index, hexadecimalIndex; if (sameIndex < 0) { index = unicodeArray.length; diff --git a/dist/tests/dev-test.js b/dist/tests/dev-test.js index 4cab2bc9..bfb4ae4a 100644 --- a/dist/tests/dev-test.js +++ b/dist/tests/dev-test.js @@ -45,7 +45,9 @@ let JavaScriptObfuscator = require('../index'), obfuscatedCode = JavaScriptObfus console.log(true, false); })(); `, { - disableConsoleOutput: false + disableConsoleOutput: false, + encodeUnicodeArray: true, + rotateUnicodeArray: false }); console.log(obfuscatedCode); console.log(eval(obfuscatedCode)); diff --git a/index.ts b/index.ts index 783b3476..195487c6 100644 --- a/index.ts +++ b/index.ts @@ -17,6 +17,7 @@ class JavaScriptObfuscator { debugProtection: false, debugProtectionInterval: false, disableConsoleOutput: true, + encodeUnicodeArray: false, rotateUnicodeArray: true, wrapUnicodeArrayCalls: true }; diff --git a/src/custom-nodes/unicode-array-nodes/UnicodeArrayDecodeNode.ts b/src/custom-nodes/unicode-array-nodes/UnicodeArrayDecodeNode.ts new file mode 100644 index 00000000..5534bf02 --- /dev/null +++ b/src/custom-nodes/unicode-array-nodes/UnicodeArrayDecodeNode.ts @@ -0,0 +1,87 @@ +import * as esprima from 'esprima'; + +import { INode } from "../../interfaces/nodes/INode"; + +import { TBlockScopeNode } from "../../types/TBlockScopeNode"; + +import { AppendState } from "../../enums/AppendState"; + +import { Node } from '../Node'; +import { NodeUtils } from "../../NodeUtils"; +import { Utils } from "../../Utils"; + +export class UnicodeArrayDecodeNode extends Node { + /** + * @type {AppendState} + */ + protected appendState: AppendState = AppendState.AfterObfuscation; + + /** + * @type {string[]} + */ + private unicodeArray: string[]; + + /** + * @type {string} + */ + private unicodeArrayName: string; + + /** + * @param unicodeArrayName + * @param unicodeArray + */ + constructor ( + unicodeArrayName: string, + unicodeArray: string[] + ) { + super(); + + this.unicodeArrayName = unicodeArrayName; + this.unicodeArray = unicodeArray; + + this.node = this.getNodeStructure(); + } + + /** + * @param blockScopeNode + */ + public appendNode (blockScopeNode: TBlockScopeNode): void { + NodeUtils.insertNodeAtIndex(blockScopeNode.body, this.getNode(), 1); + } + + /** + * @returns {INode} + */ + public getNode (): INode { + if (!this.unicodeArray.length) { + return; + } + + return super.getNode(); + } + + /** + * @returns {INode} + */ + protected getNodeStructure (): INode { + let decodedTempArrayName: string = Utils.getRandomVariableName(), + indexVariableName: string = Utils.getRandomVariableName(), + node: INode = esprima.parse(` + (function () { + !function(){function t(t){this.message=t}var r=[]["filter"]["constructor"]("return this")(),e="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";t.prototype=new Error,t.prototype.name="InvalidCharacterError",r.atob||(r.atob=function(r){var o=String(r).replace(/=+$/,"");if(o.length%4==1)throw new t("Have a nice day!");for(var n,a,i=0,c=0,d="";a=o.charAt(c++);~a&&(n=i%4?64*n+a:a,i++%4)?d+=String.fromCharCode(255&n>>(-2*i&6)):0)a=e.indexOf(a);return d})}(); + + var ${decodedTempArrayName} = []; + + for (var ${indexVariableName} in ${this.unicodeArrayName}) { + ${decodedTempArrayName}[${Utils.stringToUnicode('push')}](atob(${this.unicodeArrayName}[${indexVariableName}])); + } + + ${this.unicodeArrayName} = ${decodedTempArrayName}; + })(); + `); + + NodeUtils.addXVerbatimPropertyToLiterals(node); + + return NodeUtils.getBlockScopeNodeByIndex(node); + } +} diff --git a/src/interfaces/IOptions.d.ts b/src/interfaces/IOptions.d.ts index 0cf38876..2b7ad1bd 100644 --- a/src/interfaces/IOptions.d.ts +++ b/src/interfaces/IOptions.d.ts @@ -3,6 +3,7 @@ export interface IOptions { debugProtection?: boolean; debugProtectionInterval?: boolean; disableConsoleOutput?: boolean; + encodeUnicodeArray?: boolean; rotateUnicodeArray?: boolean; wrapUnicodeArrayCalls?: boolean; } diff --git a/src/node-groups/UnicodeArrayNodesGroup.ts b/src/node-groups/UnicodeArrayNodesGroup.ts index c5545810..ee6df78d 100644 --- a/src/node-groups/UnicodeArrayNodesGroup.ts +++ b/src/node-groups/UnicodeArrayNodesGroup.ts @@ -2,6 +2,7 @@ import { IOptions } from "../interfaces/IOptions"; import { NodesGroup } from './NodesGroup'; import { UnicodeArrayCallsWrapper } from "../custom-nodes/unicode-array-nodes/UnicodeArrayCallsWrapper"; +import { UnicodeArrayDecodeNode } from "../custom-nodes/unicode-array-nodes/UnicodeArrayDecodeNode"; import { UnicodeArrayNode } from '../custom-nodes/unicode-array-nodes/UnicodeArrayNode'; import { UnicodeArrayRotateFunctionNode } from '../custom-nodes/unicode-array-nodes/UnicodeArrayRotateFunctionNode'; import { Utils } from '../Utils'; @@ -60,5 +61,15 @@ export class UnicodeArrayNodesGroup extends NodesGroup { ) ); } + + if (this.options['encodeUnicodeArray']) { + this.nodes.set( + 'unicodeArrayDecodeNode', + new UnicodeArrayDecodeNode ( + this.unicodeArrayName, + unicodeArray + ) + ); + } } } diff --git a/src/node-obfuscators/NodeObfuscator.ts b/src/node-obfuscators/NodeObfuscator.ts index f59b7b48..905bbdaf 100644 --- a/src/node-obfuscators/NodeObfuscator.ts +++ b/src/node-obfuscators/NodeObfuscator.ts @@ -86,7 +86,13 @@ export abstract class NodeObfuscator implements INodeObfuscator { * @returns {string} */ protected replaceLiteralStringByUnicodeArrayCall (nodeValue: string): string { - let value: string = Utils.stringToUnicode(nodeValue); + let value: string = nodeValue; + + if (this.options['encodeUnicodeArray']) { + value = new Buffer(value).toString('base64') + } + + value = Utils.stringToUnicode(value); let unicodeArray: string[] = this.nodes.get('unicodeArrayNode').getNodeData(), sameIndex: number = unicodeArray.indexOf(value), diff --git a/tests/dev-test.ts b/tests/dev-test.ts index 4332c8e6..8b041689 100644 --- a/tests/dev-test.ts +++ b/tests/dev-test.ts @@ -48,7 +48,9 @@ let JavaScriptObfuscator: any = require('../index'), })(); `, { - disableConsoleOutput: false + disableConsoleOutput: false, + encodeUnicodeArray: true, + rotateUnicodeArray: false } );