From d610534575402e515bac0e3579451fd3dff71286 Mon Sep 17 00:00:00 2001 From: sanex3339 Date: Thu, 15 Dec 2016 01:22:58 +0300 Subject: [PATCH] binary expression replacer algorithm update wip --- dist/index.js | 21 +++++++++-- .../FunctionControlFlowTransformer.ts | 9 +++++ .../BinaryExpressionControlFlowReplacer.ts | 35 +++++++++++++++++-- test/dev/dev.ts | 15 ++------ 4 files changed, 63 insertions(+), 17 deletions(-) diff --git a/dist/index.js b/dist/index.js index d854b32e..1cbb0c15 100644 --- a/dist/index.js +++ b/dist/index.js @@ -4215,6 +4215,9 @@ var FunctionControlFlowTransformer = FunctionControlFlowTransformer_1 = function } estraverse.replace(functionNode.body, { enter: function enter(node, parentNode) { + if (Math.random() > FunctionControlFlowTransformer_1.controlFlowReplacersThreshold) { + return; + } var controlFlowReplacerName = FunctionControlFlowTransformer_1.controlFlowReplacersMap.get(node.type); if (controlFlowReplacerName === undefined) { return; @@ -4282,6 +4285,7 @@ var FunctionControlFlowTransformer = FunctionControlFlowTransformer_1 = function return FunctionControlFlowTransformer; }(AbstractNodeTransformer_1.AbstractNodeTransformer); FunctionControlFlowTransformer.controlFlowReplacersMap = new Map([[NodeType_1.NodeType.BinaryExpression, NodeControlFlowReplacers_1.NodeControlFlowReplacers.BinaryExpressionControlFlowReplacer]]); +FunctionControlFlowTransformer.controlFlowReplacersThreshold = 0.75; FunctionControlFlowTransformer.hostNodeSearchMinDepth = 2; FunctionControlFlowTransformer.hostNodeSearchMaxDepth = 10; FunctionControlFlowTransformer = FunctionControlFlowTransformer_1 = __decorate([inversify_1.injectable(), __param(0, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers['Factory>'])), __param(1, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers['Factory'])), __param(2, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers['Factory'])), __param(3, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers.IOptions)), __metadata("design:paramtypes", [Function, Function, Function, Object])], FunctionControlFlowTransformer); @@ -4378,6 +4382,7 @@ var __param = undefined && undefined.__param || function (paramIndex, decorator) var inversify_1 = __webpack_require__(0); var ServiceIdentifiers_1 = __webpack_require__(1); var escodegen = __webpack_require__(17); +var _ = __webpack_require__(34); var CustomNodes_1 = __webpack_require__(12); var AbstractControlFlowReplacer_1 = __webpack_require__(69); var Node_1 = __webpack_require__(4); @@ -4389,6 +4394,7 @@ var BinaryExpressionControlFlowReplacer = BinaryExpressionControlFlowReplacer_1 var _this = _possibleConstructorReturn(this, (BinaryExpressionControlFlowReplacer.__proto__ || Object.getPrototypeOf(BinaryExpressionControlFlowReplacer)).call(this, options)); + _this.existingBinaryExpressionKeys = new Map(); _this.customNodeFactory = customNodeFactory; return _this; } @@ -4396,12 +4402,22 @@ var BinaryExpressionControlFlowReplacer = BinaryExpressionControlFlowReplacer_1 _createClass(BinaryExpressionControlFlowReplacer, [{ key: "replace", value: function replace(binaryExpressionNode, parentNode, controlFlowStorage, controlFlowStorageCustomNodeName) { - var key = AbstractControlFlowReplacer_1.AbstractControlFlowReplacer.getStorageKey(); var binaryExpressionFunctionNode = this.customNodeFactory(CustomNodes_1.CustomNodes.BinaryExpressionFunctionNode); + var binaryExpressionOperatorKeys = this.existingBinaryExpressionKeys.get(controlFlowStorageCustomNodeName) || {}; var controlFlowStorageCallNode = this.customNodeFactory(CustomNodes_1.CustomNodes.ControlFlowStorageCallNode); + var key = AbstractControlFlowReplacer_1.AbstractControlFlowReplacer.getStorageKey(); + if (!binaryExpressionOperatorKeys[binaryExpressionNode.operator]) { + binaryExpressionOperatorKeys[binaryExpressionNode.operator] = []; + } binaryExpressionFunctionNode.initialize(binaryExpressionNode.operator); + if (Math.random() > BinaryExpressionControlFlowReplacer_1.useExistingOperatorKeyThreshold && binaryExpressionOperatorKeys[binaryExpressionNode.operator].length) { + key = _.sample(binaryExpressionOperatorKeys[binaryExpressionNode.operator]); + } else { + binaryExpressionOperatorKeys[binaryExpressionNode.operator].push(key); + this.existingBinaryExpressionKeys.set(controlFlowStorageCustomNodeName, binaryExpressionOperatorKeys); + controlFlowStorage.set(key, binaryExpressionFunctionNode); + } controlFlowStorageCallNode.initialize(controlFlowStorageCustomNodeName, key, BinaryExpressionControlFlowReplacer_1.getExpressionValue(binaryExpressionNode.left), BinaryExpressionControlFlowReplacer_1.getExpressionValue(binaryExpressionNode.right)); - controlFlowStorage.set(key, binaryExpressionFunctionNode); var statementNode = controlFlowStorageCallNode.getNode()[0]; if (!statementNode || !Node_1.Node.isExpressionStatementNode(statementNode)) { throw new Error("`controlFlowStorageCallCustomNode.getNode()` should returns array with `ExpressionStatement` node"); @@ -4419,6 +4435,7 @@ var BinaryExpressionControlFlowReplacer = BinaryExpressionControlFlowReplacer_1 return BinaryExpressionControlFlowReplacer; }(AbstractControlFlowReplacer_1.AbstractControlFlowReplacer); +BinaryExpressionControlFlowReplacer.useExistingOperatorKeyThreshold = 0.5; BinaryExpressionControlFlowReplacer = BinaryExpressionControlFlowReplacer_1 = __decorate([inversify_1.injectable(), __param(0, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers['Factory'])), __param(1, inversify_1.inject(ServiceIdentifiers_1.ServiceIdentifiers.IOptions)), __metadata("design:paramtypes", [Function, Object])], BinaryExpressionControlFlowReplacer); exports.BinaryExpressionControlFlowReplacer = BinaryExpressionControlFlowReplacer; var BinaryExpressionControlFlowReplacer_1; diff --git a/src/node-transformers/node-control-flow-transformers/FunctionControlFlowTransformer.ts b/src/node-transformers/node-control-flow-transformers/FunctionControlFlowTransformer.ts index 9352da93..9cf56fa7 100644 --- a/src/node-transformers/node-control-flow-transformers/FunctionControlFlowTransformer.ts +++ b/src/node-transformers/node-control-flow-transformers/FunctionControlFlowTransformer.ts @@ -35,6 +35,11 @@ export class FunctionControlFlowTransformer extends AbstractNodeTransformer { [NodeType.BinaryExpression, NodeControlFlowReplacers.BinaryExpressionControlFlowReplacer] ]); + /** + * @type {number} + */ + private static readonly controlFlowReplacersThreshold: number = 0.75; + /** * @type {number} */ @@ -173,6 +178,10 @@ export class FunctionControlFlowTransformer extends AbstractNodeTransformer { estraverse.replace(functionNode.body, { enter: (node: ESTree.Node, parentNode: ESTree.Node): any => { + if (Math.random() > FunctionControlFlowTransformer.controlFlowReplacersThreshold) { + return; + } + const controlFlowReplacerName: NodeControlFlowReplacers | undefined = FunctionControlFlowTransformer .controlFlowReplacersMap.get(node.type); diff --git a/src/node-transformers/node-control-flow-transformers/control-flow-replacers/BinaryExpressionControlFlowReplacer.ts b/src/node-transformers/node-control-flow-transformers/control-flow-replacers/BinaryExpressionControlFlowReplacer.ts index 91837cec..a3fc6de3 100644 --- a/src/node-transformers/node-control-flow-transformers/control-flow-replacers/BinaryExpressionControlFlowReplacer.ts +++ b/src/node-transformers/node-control-flow-transformers/control-flow-replacers/BinaryExpressionControlFlowReplacer.ts @@ -3,6 +3,7 @@ import { ServiceIdentifiers } from '../../../container/ServiceIdentifiers'; import * as escodegen from 'escodegen'; import * as ESTree from 'estree'; +import * as _ from 'lodash'; import { TCustomNodeFactory } from '../../../types/container/TCustomNodeFactory'; import { TStatement } from '../../../types/node/TStatement'; @@ -18,6 +19,16 @@ import { Node } from '../../../node/Node'; @injectable() export class BinaryExpressionControlFlowReplacer extends AbstractControlFlowReplacer { + /** + * @type {number} + */ + private static readonly useExistingOperatorKeyThreshold: number = 0.5; + + /** + * @type {Map} + */ + private readonly existingBinaryExpressionKeys: Map = new Map (); + /** * @type {TCustomNodeFactory} */ @@ -59,11 +70,31 @@ export class BinaryExpressionControlFlowReplacer extends AbstractControlFlowRepl controlFlowStorage: IStorage , controlFlowStorageCustomNodeName: string ): ESTree.Node { - const key: string = AbstractControlFlowReplacer.getStorageKey(); const binaryExpressionFunctionNode: ICustomNode = this.customNodeFactory(CustomNodes.BinaryExpressionFunctionNode); + const binaryExpressionOperatorKeys: { + [key: string]: string[] + } = this.existingBinaryExpressionKeys.get(controlFlowStorageCustomNodeName) || {}; const controlFlowStorageCallNode: ICustomNode = this.customNodeFactory(CustomNodes.ControlFlowStorageCallNode); + let key: string = AbstractControlFlowReplacer.getStorageKey(); + + if (!binaryExpressionOperatorKeys[binaryExpressionNode.operator]) { + binaryExpressionOperatorKeys[binaryExpressionNode.operator] = []; + } + binaryExpressionFunctionNode.initialize(binaryExpressionNode.operator); + + if ( + Math.random() > BinaryExpressionControlFlowReplacer.useExistingOperatorKeyThreshold && + binaryExpressionOperatorKeys[binaryExpressionNode.operator].length + ) { + key = _.sample(binaryExpressionOperatorKeys[binaryExpressionNode.operator]); + } else { + binaryExpressionOperatorKeys[binaryExpressionNode.operator].push(key); + this.existingBinaryExpressionKeys.set(controlFlowStorageCustomNodeName, binaryExpressionOperatorKeys); + controlFlowStorage.set(key, binaryExpressionFunctionNode); + } + controlFlowStorageCallNode.initialize( controlFlowStorageCustomNodeName, key, @@ -71,8 +102,6 @@ export class BinaryExpressionControlFlowReplacer extends AbstractControlFlowRepl BinaryExpressionControlFlowReplacer.getExpressionValue(binaryExpressionNode.right) ); - controlFlowStorage.set(key, binaryExpressionFunctionNode); - const statementNode: TStatement = controlFlowStorageCallNode.getNode()[0]; if (!statementNode || !Node.isExpressionStatementNode(statementNode)) { diff --git a/test/dev/dev.ts b/test/dev/dev.ts index da841371..d25a77c3 100644 --- a/test/dev/dev.ts +++ b/test/dev/dev.ts @@ -14,18 +14,9 @@ if (!(global)._babelPolyfill) { function foo () { return function () { var sum = 1 + 2; - - function foo () { - return function () { - var sum = 1 - 2; - - function foo () { - return function () { - var sum = 1 * 2; - } - } - } - } + var sum = 3 + 4; + var sum = 5 + 6; + var sum = 8 - 6; } } })();