Skip to content

Commit

Permalink
fix corner case in hoist_vars (#5627)
Browse files Browse the repository at this point in the history
fixes #5626
  • Loading branch information
alexlamsl authored Aug 23, 2022
1 parent 4653e8a commit 4db8106
Show file tree
Hide file tree
Showing 6 changed files with 119 additions and 65 deletions.
52 changes: 1 addition & 51 deletions lib/compress.js
Original file line number Diff line number Diff line change
Expand Up @@ -8221,59 +8221,9 @@ Compressor.prototype.compress = function(node) {
vars.set(name, defn);
defn.name.definition().orig.unshift(defn.name);
});
if (defns.length > 0) {
// try to merge in assignments
insert_vars(self.body);
hoisted.push(make_node(AST_Var, self, { definitions: defns }));
}
if (defns.length > 0) hoisted.push(make_node(AST_Var, self, { definitions: defns }));
}
self.body = dirs.concat(hoisted, self.body);

function insert_vars(body) {
while (body.length) {
var stat = body[0];
if (stat instanceof AST_SimpleStatement) {
var expr = stat.body, sym, assign;
if (expr instanceof AST_Assign
&& expr.operator == "="
&& (sym = expr.left) instanceof AST_Symbol
&& vars.has(sym.name)) {
var defn = vars.get(sym.name);
if (defn.value) break;
var value = expr.right;
if (value instanceof AST_Sequence) value = value.clone();
defn.value = value;
remove(defns, defn);
defns.push(defn);
body.shift();
continue;
}
if (expr instanceof AST_Sequence
&& (assign = expr.expressions[0]) instanceof AST_Assign
&& assign.operator == "="
&& (sym = assign.left) instanceof AST_Symbol
&& vars.has(sym.name)) {
var defn = vars.get(sym.name);
if (defn.value) break;
defn.value = assign.right;
remove(defns, defn);
defns.push(defn);
stat.body = make_sequence(expr, expr.expressions.slice(1));
continue;
}
}
if (stat instanceof AST_EmptyStatement) {
body.shift();
continue;
}
if (stat instanceof AST_BlockStatement && !insert_vars(stat.body)) {
body.shift();
continue;
}
break;
}
return body.length;
}
});

function scan_local_returns(fn, transform) {
Expand Down
8 changes: 5 additions & 3 deletions test/compress/default-values.js
Original file line number Diff line number Diff line change
Expand Up @@ -668,15 +668,16 @@ drop_fargs: {
hoist_vars: {
options = {
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
var a = "PASS";
var [ b = 42 ] = [];
console.log(a, b);
}
expect: {
var a = "PASS";
var [ b = 42 ] = [];
var a = "PASS", [ b = 42 ] = [];
console.log(a, b);
}
expect_stdout: "PASS 42"
Expand Down Expand Up @@ -3035,7 +3036,8 @@ issue_5566_5: {
(function(a, f = function() {
return a;
}) {
var b, a = "foo";
var a, b;
a = "foo";
console.log(a, f());
})("bar");
}
Expand Down
5 changes: 3 additions & 2 deletions test/compress/destructured.js
Original file line number Diff line number Diff line change
Expand Up @@ -1652,15 +1652,16 @@ fn_name_unused: {
hoist_vars: {
options = {
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
var a = "PASS";
var [ b ] = [ 42 ];
console.log(a, b);
}
expect: {
var a = "PASS";
var [ b ] = [ 42 ];
var a = "PASS", b = [ 42 ][0];
console.log(a, b);
}
expect_stdout: "PASS 42"
Expand Down
112 changes: 105 additions & 7 deletions test/compress/hoist_vars.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ statements: {
options = {
hoist_funs: false,
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
function f() {
Expand All @@ -25,6 +27,8 @@ statements_funs: {
options = {
hoist_funs: true,
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
function f() {
Expand All @@ -48,6 +52,8 @@ sequences: {
options = {
hoist_funs: false,
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
function f() {
Expand All @@ -71,6 +77,8 @@ sequences_funs: {
options = {
hoist_funs: true,
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
function f() {
Expand Down Expand Up @@ -108,7 +116,8 @@ catch_var: {
console.log(a);
}
expect: {
var a = "PASS";
a = "PASS";
var a;
console.log(a);
}
expect_stdout: "PASS"
Expand All @@ -118,6 +127,8 @@ issue_2295: {
options = {
collapse_vars: true,
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
function foo(o) {
Expand All @@ -139,6 +150,7 @@ issue_4487_1: {
options = {
functions: true,
hoist_vars: true,
join_vars: true,
keep_fnames: true,
reduce_vars: true,
toplevel: true,
Expand All @@ -163,6 +175,7 @@ issue_4487_2: {
options = {
functions: true,
hoist_vars: true,
join_vars: true,
keep_fnames: true,
passes: 2,
reduce_vars: true,
Expand All @@ -188,6 +201,7 @@ issue_4487_3: {
options = {
functions: true,
hoist_vars: true,
join_vars: true,
keep_fnames: true,
passes: 3,
reduce_vars: true,
Expand Down Expand Up @@ -248,8 +262,7 @@ issue_4517: {
}
expect: {
console.log(function() {
var a = 2;
return (A = a) + typeof !1;
return (A = 2) + typeof !1;
}());
}
expect_stdout: "2boolean"
Expand All @@ -260,6 +273,7 @@ issue_4736: {
collapse_vars: true,
evaluate: true,
hoist_vars: true,
join_vars: true,
merge_vars: true,
reduce_vars: true,
toplevel: true,
Expand All @@ -279,7 +293,7 @@ issue_4736: {
expect: {
(function() {
(function() {
0,
0;
console.log(1 << 30);
})();
})();
Expand All @@ -291,6 +305,7 @@ issue_4839: {
options = {
evaluate: true,
hoist_vars: true,
join_vars: true,
keep_fargs: false,
reduce_vars: true,
toplevel: true,
Expand All @@ -317,6 +332,7 @@ issue_4859: {
options = {
evaluate: true,
hoist_vars: true,
join_vars: true,
keep_infinity: true,
merge_vars: true,
reduce_vars: true,
Expand Down Expand Up @@ -441,7 +457,7 @@ issue_4898: {
expect_stdout: "PASS"
}

issue_5187: {
issue_5187_1: {
options = {
hoist_props: true,
hoist_vars: true,
Expand All @@ -459,6 +475,37 @@ issue_5187: {
}
f();
}
expect: {
(function() {
var a, b;
a = 42;
do {
b = { 0: a++ };
} while (console.log(b[b ^= 0]));
})();
}
expect_stdout: "42"
}

issue_5187_2: {
options = {
hoist_props: true,
hoist_vars: true,
join_vars: true,
reduce_vars: true,
side_effects: true,
toplevel: true,
unused: true,
}
input: {
function f() {
var a = 42;
do {
var b = { 0: a++ };
} while (console.log(b[b ^= 0]));
}
f();
}
expect: {
(function() {
var b, a = 42;
Expand Down Expand Up @@ -547,9 +594,9 @@ issue_5411_1: {
console.log(b);
}
expect: {
var b, c, a = "PASS";
var a, b, c;
b++;
b = a;
b = a = "PASS";
c = c && c[b];
console.log(b);
}
Expand Down Expand Up @@ -596,10 +643,61 @@ issue_5411_3: {
var a = A = a;
console.log(A);
}
expect: {
var a;
a = console;
a = A = ++a;
console.log(A);
}
expect_stdout: "NaN"
}

issue_5411_4: {
options = {
collapse_vars: true,
hoist_vars: true,
join_vars: true,
reduce_vars: true,
toplevel: true,
unused: true,
}
input: {
var a = console;
a++;
var a = A = a;
console.log(A);
}
expect: {
var a = console;
a = A = ++a;
console.log(A);
}
expect_stdout: "NaN"
}

issue_5626: {
options = {
conditionals: true,
evaluate: true,
hoist_vars: true,
reduce_vars: true,
side_effects: true,
toplevel: true,
unused: true,
}
input: {
var a = function() {
return console.log(arguments[0]), 42;
}("PASS") ? null : "foo";
for (var b in a)
FAIL;
}
expect: {
(function() {
console.log(arguments[0]);
}("PASS"));
for (var b in null)
FAIL;
}
expect_stdout: "PASS"
}
5 changes: 3 additions & 2 deletions test/compress/issue-913.js
Original file line number Diff line number Diff line change
@@ -1,17 +1,18 @@
keep_var_for_in: {
options = {
hoist_vars: true,
join_vars: true,
unused: true,
}
input: {
(function(obj){
(function(obj) {
var foo = 5;
for (var i in obj)
return foo;
})();
}
expect: {
(function(obj){
(function(obj) {
var i, foo = 5;
for (i in obj)
return foo;
Expand Down
2 changes: 2 additions & 0 deletions test/compress/pure_getters.js
Original file line number Diff line number Diff line change
Expand Up @@ -1540,10 +1540,12 @@ this_toString: {
issue_4803: {
options = {
hoist_vars: true,
join_vars: true,
pure_getters: "strict",
reduce_vars: true,
side_effects: true,
toplevel: true,
unused: true,
}
input: {
var o = {
Expand Down

0 comments on commit 4db8106

Please sign in to comment.