Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Fix invalid drop variable

Close #60
  • Loading branch information...
commit d4281569b1c9d270c35824f9a97d5d76507cfa20 1 parent 900ea4e
@Constellation Constellation authored
View
59 lib/pass/drop-variable-definition.js
@@ -58,7 +58,7 @@
}
function isRemovableDefinition(slot, scope) {
- var i, iz, ref;
+ var i, iz, ref, parent;
if (slot.identifiers.length !== 1) {
return false;
}
@@ -76,6 +76,14 @@
if (!ref.writeExpr) {
return false;
}
+ parent = ref.writeExpr.__$parent$__;
+ if (!parent) {
+ return false;
+ }
+ if (parent.type !== Syntax.AssignmentExpression &&
+ parent.type !== Syntax.VariableDeclarator) {
+ return false;
+ }
if (evaluator.hasSideEffect(ref.writeExpr, ref.from)) {
return false;
}
@@ -85,6 +93,50 @@
return true;
}
+ function overrideExpression(from, to) {
+ var key;
+ for (key in from) {
+ delete from[key];
+ }
+ for (key in to) {
+ from[key] = to[key];
+ }
+ return from;
+ }
+
+ function removeDefinition(node, index, slot, scope) {
+ var i, iz, ref, slot, parent;
+
+ // remove from declaration list
+ node.declarations.splice(index, 1);
+ for (i = 0, iz = slot.references.length; i < iz; ++i) {
+ ref = slot.references[i];
+ common.assert(!ref.isRead());
+ if (ref.isWrite()) {
+ parent = ref.writeExpr.__$parent$__;
+ if (parent.type === Syntax.AssignmentExpression) {
+ overrideExpression(ref.writeExpr.__$parent$__, ref.writeExpr);
+ }
+ }
+ }
+ }
+
+ function attachParent(tree) {
+ return common.traverse(tree, {
+ enter: function (node, parent) {
+ node.__$parent$__ = parent;
+ }
+ });
+ }
+
+ function removeParent(tree) {
+ return common.traverse(tree, {
+ enter: function (node, parent) {
+ delete node.__$parent$__;
+ }
+ });
+ }
+
function dropVariableDefinition(tree, options) {
var result, manager, scope, candidates;
@@ -95,8 +147,10 @@
result = options.destructive ? tree : common.deepCopy(tree);
modified = false;
scope = null;
+
manager = escope.analyze(result);
manager.attach();
+ attachParent(tree);
result = common.replace(result, {
enter: function enter(node, parent) {
@@ -117,7 +171,7 @@
if (isRemovableDefinition(slot, scope)) {
// ok, remove this variable
modified = true;
- node.declarations.splice(i, 1);
+ removeDefinition(node, i, slot, scope);
continue;
}
}
@@ -157,6 +211,7 @@
}
});
+ removeParent(result);
manager.detach();
return {
View
1  test/compare/drop-variable-definition-10.expected.js
@@ -0,0 +1 @@
+void function(){}.call(this)
View
7 test/compare/drop-variable-definition-10.js
@@ -0,0 +1,7 @@
+// reported from issue #60
+void function () {
+ var foo; // this foo should be dropped
+ foo = function () { // this should be transformed to non-assignment expression
+ return 99;
+ };
+}.call(this);
Please sign in to comment.
Something went wrong with that request. Please try again.