123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308 |
- import { assert } from 'chai';
- import { NO_ADDITIONAL_NODES_PRESET } from '../../../../src/options/presets/NoCustomNodes';
- import { readFileAsString } from '../../../helpers/readFileAsString';
- import { JavaScriptObfuscator } from '../../../../src/JavaScriptObfuscatorFacade';
- describe('StringArrayStorage', () => {
- describe('Rotate string array', function () {
- this.timeout(100000);
- describe('Variant #1: single string array value', () => {
- const samples: number = 1000;
- const delta: number = 0.1;
- const expectedVariantProbability: number = 1;
- const stringArrayVariant1RegExp1: RegExp = /var _0x([a-f0-9]){4} *= *\['test'];/g;
- const literalNodeVariant1RegExp: RegExp = /var test *= *_0x([a-f0-9]){4}\('0x0'\);/g;
- let stringArrayVariant1Probability: number,
- literalNodeVariant1Probability: number;
- before(() => {
- const code: string = readFileAsString(__dirname + '/fixtures/one-string.js');
- let stringArrayVariant1MatchesLength: number = 0;
- let literalNodeVariant1MatchesLength: number = 0;
- for (let i = 0; i < samples; i++) {
- const obfuscatedCode: string = JavaScriptObfuscator.obfuscate(
- code,
- {
- ...NO_ADDITIONAL_NODES_PRESET,
- rotateStringArray: true,
- stringArray: true,
- stringArrayThreshold: 1
- }
- ).getObfuscatedCode();
- if (obfuscatedCode.match(stringArrayVariant1RegExp1)) {
- stringArrayVariant1MatchesLength++;
- }
- if (obfuscatedCode.match(literalNodeVariant1RegExp)) {
- literalNodeVariant1MatchesLength++;
- }
- }
- stringArrayVariant1Probability = stringArrayVariant1MatchesLength / samples;
- literalNodeVariant1Probability = literalNodeVariant1MatchesLength / samples;
- });
- describe('String array probability', () => {
- it('Variant #1: should create single string array variant', () => {
- assert.closeTo(stringArrayVariant1Probability, expectedVariantProbability, delta);
- });
- });
- describe('Literal node probability', () => {
- it('Variant #1: should replace literal node with call to string array variant', () => {
- assert.closeTo(literalNodeVariant1Probability, expectedVariantProbability, delta);
- });
- });
- });
- describe('Variant #2: Three string array values', () => {
- const samples: number = 1000;
- const delta: number = 0.1;
- const expectedStringArrayVariantProbability: number = 0.33;
- const expectedLiteralNodeVariantProbability: number = 1;
- const stringArrayVariantsCount: number = 3;
- const literalNodeVariantsCount: number = 1;
- const stringArrayVariantRegExps: RegExp[] = [
- /var _0x([a-f0-9]){4} *= *\['foo', *'bar', *'baz'];/g,
- /var _0x([a-f0-9]){4} *= *\['bar', *'baz', *'foo'];/g,
- /var _0x([a-f0-9]){4} *= *\['baz', *'foo', *'bar'];/g
- ];
- const literalNodeVariantRegExps: RegExp[] = [
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x0'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x1'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x2'\\);`
- )
- ];
- const stringArrayVariantProbabilities: number[] = new Array(stringArrayVariantsCount).fill(0);
- const literalNodeVariantProbabilities: number[] = new Array(literalNodeVariantsCount).fill(0);
- const stringArrayVariantMatchesLength: number[] = new Array(stringArrayVariantsCount).fill(0);
- const literalNodeVariantMatchesLength: number[] = new Array(literalNodeVariantsCount).fill(0);
- before(() => {
- const code: string = readFileAsString(__dirname + '/fixtures/three-strings.js');
- for (let i = 0; i < samples; i++) {
- const obfuscatedCode: string = JavaScriptObfuscator.obfuscate(
- code,
- {
- ...NO_ADDITIONAL_NODES_PRESET,
- rotateStringArray: true,
- stringArray: true,
- stringArrayThreshold: 1
- }
- ).getObfuscatedCode();
- for (let variantIndex = 0; variantIndex < stringArrayVariantsCount; variantIndex++) {
- if (obfuscatedCode.match(stringArrayVariantRegExps[variantIndex])) {
- stringArrayVariantMatchesLength[variantIndex]++;
- }
- if (obfuscatedCode.match(literalNodeVariantRegExps[variantIndex])) {
- literalNodeVariantMatchesLength[variantIndex]++;
- }
- }
- }
- for (let variantIndex = 0; variantIndex < stringArrayVariantsCount; variantIndex++) {
- stringArrayVariantProbabilities[variantIndex] = stringArrayVariantMatchesLength[variantIndex] / samples;
- }
- for (let variantIndex = 0; variantIndex < literalNodeVariantsCount; variantIndex++) {
- literalNodeVariantProbabilities[variantIndex] = literalNodeVariantMatchesLength[variantIndex] / samples;
- }
- });
- describe('String array probability', () => {
- for (let variantIndex = 0; variantIndex < stringArrayVariantsCount; variantIndex++) {
- const variantNumber: number = variantIndex + 1;
- it(`Variant #${variantNumber}: should create string array variant`, () => {
- assert.closeTo(stringArrayVariantProbabilities[variantIndex], expectedStringArrayVariantProbability, delta);
- });
- }
- });
- describe('Literal node probability', () => {
- for (let variantIndex = 0; variantIndex < literalNodeVariantsCount; variantIndex++) {
- const variantNumber: number = variantIndex + 1;
- it(`Variant #${variantNumber}: should replace literal node with call to string array variant`, () => {
- assert.closeTo(literalNodeVariantProbabilities[variantIndex], expectedLiteralNodeVariantProbability, delta);
- });
- }
- });
- });
- });
- describe('Shuffle string array', function () {
- this.timeout(100000);
- describe('Variant #1: single string array value', () => {
- const samples: number = 1000;
- const delta: number = 0.1;
- const expectedVariantProbability: number = 1;
- const stringArrayVariantRegExp1: RegExp = /var _0x([a-f0-9]){4} *= *\['test'];/g;
- const literalNodeVariant1RegExp: RegExp = /var test *= *_0x([a-f0-9]){4}\('0x0'\);/g;
- let stringArrayVariant1Probability: number,
- literalNodeVariant1Probability: number;
- before(() => {
- const code: string = readFileAsString(__dirname + '/fixtures/one-string.js');
- let stringArrayVariant1MatchesLength: number = 0;
- let literalNodeVariant1MatchesLength: number = 0;
- for (let i = 0; i < samples; i++) {
- const obfuscatedCode: string = JavaScriptObfuscator.obfuscate(
- code,
- {
- ...NO_ADDITIONAL_NODES_PRESET,
- shuffleStringArray: true,
- stringArray: true,
- stringArrayThreshold: 1
- }
- ).getObfuscatedCode();
- if (obfuscatedCode.match(stringArrayVariantRegExp1)) {
- stringArrayVariant1MatchesLength++;
- }
- if (obfuscatedCode.match(literalNodeVariant1RegExp)) {
- literalNodeVariant1MatchesLength++;
- }
- }
- stringArrayVariant1Probability = stringArrayVariant1MatchesLength / samples;
- literalNodeVariant1Probability = literalNodeVariant1MatchesLength / samples;
- });
- describe('String array probability', () => {
- it('Variant #1: should create string array variant', () => {
- assert.closeTo(stringArrayVariant1Probability, expectedVariantProbability, delta);
- });
- });
- describe('Literal node probability', () => {
- it('Variant #1: should replace literal node with call to string array variant', () => {
- assert.closeTo(literalNodeVariant1Probability, expectedVariantProbability, delta);
- });
- });
- });
- describe('Variant #2: Three string array values', () => {
- const samples: number = 1000;
- const delta: number = 0.1;
- const expectedVariantProbability: number = 0.166;
- const variantsCount: number = 6;
- const stringArrayVariantRegExps: RegExp[] = [
- /var _0x([a-f0-9]){4} *= *\['foo', *'bar', *'baz'];/g,
- /var _0x([a-f0-9]){4} *= *\['foo', *'baz', *'bar'];/g,
- /var _0x([a-f0-9]){4} *= *\['bar', *'foo', *'baz'];/g,
- /var _0x([a-f0-9]){4} *= *\['bar', *'baz', *'foo'];/g,
- /var _0x([a-f0-9]){4} *= *\['baz', *'foo', *'bar'];/g,
- /var _0x([a-f0-9]){4} *= *\['baz', *'bar', *'foo'];/g
- ];
- const literalNodeVariantRegExps: RegExp[] = [
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x0'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x1'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x2'\\);`
- ),
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x0'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x2'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x1'\\);`
- ),
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x1'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x0'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x2'\\);`
- ),
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x1'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x2'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x0'\\);`
- ),
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x2'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x0'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x1'\\);`
- ),
- new RegExp(
- `var foo *= *_0x([a-f0-9]){4}\\('0x2'\\); *` +
- `var bar *= *_0x([a-f0-9]){4}\\('0x1'\\); *` +
- `var baz *= *_0x([a-f0-9]){4}\\('0x0'\\);`
- )
- ];
- const stringArrayVariantProbabilities: number[] = new Array(variantsCount).fill(0);
- const literalNodeVariantProbabilities: number[] = new Array(variantsCount).fill(0);
- const stringArrayVariantMatchesLength: number[] = new Array(variantsCount).fill(0);
- const literalNodeVariantMatchesLength: number[] = new Array(variantsCount).fill(0);
- before(() => {
- const code: string = readFileAsString(__dirname + '/fixtures/three-strings.js');
- for (let i = 0; i < samples; i++) {
- const obfuscatedCode: string = JavaScriptObfuscator.obfuscate(
- code,
- {
- ...NO_ADDITIONAL_NODES_PRESET,
- shuffleStringArray: true,
- stringArray: true,
- stringArrayThreshold: 1
- }
- ).getObfuscatedCode();
- for (let variantIndex = 0; variantIndex < variantsCount; variantIndex++) {
- if (obfuscatedCode.match(stringArrayVariantRegExps[variantIndex])) {
- stringArrayVariantMatchesLength[variantIndex]++;
- }
- if (obfuscatedCode.match(literalNodeVariantRegExps[variantIndex])) {
- literalNodeVariantMatchesLength[variantIndex]++;
- }
- }
- }
- for (let variantIndex = 0; variantIndex < variantsCount; variantIndex++) {
- stringArrayVariantProbabilities[variantIndex] = stringArrayVariantMatchesLength[variantIndex] / samples;
- literalNodeVariantProbabilities[variantIndex] = literalNodeVariantMatchesLength[variantIndex] / samples;
- }
- });
- for (let variantIndex = 0; variantIndex < variantsCount; variantIndex++) {
- const variantNumber: number = variantIndex + 1;
- it(`Variant #${variantNumber}: should create string array variant`, () => {
- assert.closeTo(stringArrayVariantProbabilities[variantIndex], expectedVariantProbability, delta);
- });
- it(`Variant #${variantNumber}: should replace literal node with call to string array variant`, () => {
- assert.closeTo(literalNodeVariantProbabilities[variantIndex], expectedVariantProbability, delta);
- });
- }
- });
- });
- });
|