fix corner case in `collapse_vars` (#3699)
authorAlex Lam S.L <alexlamsl@gmail.com>
Wed, 29 Jan 2020 16:08:53 +0000 (00:08 +0800)
committerGitHub <noreply@github.com>
Wed, 29 Jan 2020 16:08:53 +0000 (00:08 +0800)
fixes #3698

lib/compress.js
test/compress/collapse_vars.js

index 85ad449..e6a064d 100644 (file)
@@ -1094,6 +1094,7 @@ merge(Compressor.prototype, {
                 collapse(statements, compressor);
             }
         } while (CHANGED && max_iter-- > 0);
+        return statements;
 
         function find_loop_scope_try() {
             var node = compressor.self(), level = 0;
@@ -1150,11 +1151,10 @@ merge(Compressor.prototype, {
                 if (node.single_use && parent instanceof AST_VarDef && parent.value === node) return node;
                 // Replace variable with assignment when found
                 var hit_rhs;
-                if (can_replace
-                    && !(node instanceof AST_SymbolDeclaration)
+                if (!(node instanceof AST_SymbolDeclaration)
                     && (scan_lhs && lhs.equivalent_to(node)
                         || scan_rhs && (hit_rhs = scan_rhs(node, this)))) {
-                    if (stop_if_hit && (hit_rhs || !lhs_local || !replace_all)) {
+                    if (!can_replace || stop_if_hit && (hit_rhs || !lhs_local || !replace_all)) {
                         if (!hit_rhs || !value_def) abort = true;
                         return node;
                     }
@@ -3854,12 +3854,12 @@ merge(Compressor.prototype, {
     });
 
     OPT(AST_Block, function(self, compressor) {
-        tighten_body(self.body, compressor);
+        self.body = tighten_body(self.body, compressor);
         return self;
     });
 
     OPT(AST_BlockStatement, function(self, compressor) {
-        tighten_body(self.body, compressor);
+        self.body = tighten_body(self.body, compressor);
         switch (self.body.length) {
           case 1: return self.body[0];
           case 0: return make_node(AST_EmptyStatement, self);
@@ -3868,7 +3868,7 @@ merge(Compressor.prototype, {
     });
 
     OPT(AST_Lambda, function(self, compressor) {
-        tighten_body(self.body, compressor);
+        self.body = tighten_body(self.body, compressor);
         if (compressor.option("side_effects")
             && self.body.length == 1
             && self.body[0] === compressor.has_directive("use strict")) {
@@ -5372,7 +5372,7 @@ merge(Compressor.prototype, {
     });
 
     OPT(AST_Try, function(self, compressor) {
-        tighten_body(self.body, compressor);
+        self.body = tighten_body(self.body, compressor);
         if (self.bcatch && self.bfinally && all(self.bfinally.body, is_empty)) self.bfinally = null;
         if (compressor.option("dead_code") && all(self.body, is_empty)) {
             var body = [];
index 4cd59a4..f109e93 100644 (file)
@@ -7658,3 +7658,79 @@ call_3_symbol: {
     }
     expect_stdout: "function"
 }
+
+issue_3698_1: {
+    options = {
+        collapse_vars: true,
+    }
+    input: {
+        var log = console.log;
+        var a, b = 0, c = 0;
+        (function() {
+            a = b;
+        })(b++, (b++, c++));
+        log(a, b, c);
+    }
+    expect: {
+        var log = console.log;
+        var a, b = 0, c = 0;
+        (function() {
+            a = b;
+        })(b++, (b++, c++));
+        log(a, b, c);
+    }
+    expect_stdout: "2 2 1"
+}
+
+issue_3698_2: {
+    options = {
+        collapse_vars: true,
+        reduce_vars: true,
+    }
+    input: {
+        var log = console.log;
+        var a, b = 0, c = 0, d = 1;
+        (function f() {
+            a = b;
+            d-- && f();
+        })(b++, (b++, c++));
+        log(a, b, c, d);
+    }
+    expect: {
+        var log = console.log;
+        var a, b = 0, c = 0, d = 1;
+        (function f() {
+            a = b;
+            d-- && f();
+        })(b++, (b++, c++));
+        log(a, b, c, d);
+    }
+    expect_stdout: "2 2 1 -1"
+}
+
+issue_3698_3: {
+    options = {
+        collapse_vars: true,
+        reduce_vars: true,
+    }
+    input: {
+        var a = 0, b = 0;
+        (function f(c) {
+            {
+                b++;
+                var bar_1 = (b = 1 + b, c = 0);
+                a-- && f();
+            }
+        })();
+        console.log(b);
+    }
+    expect: {
+        var a = 0, b = 0;
+        (function f(c) {
+            var bar_1 = (b = 1 + ++b, c = 0);
+            a-- && f();
+        })();
+        console.log(b);
+    }
+    expect_stdout: "2"
+}