Repository: mishoo/UglifyJS (language: javascript)

Issue:
ufuzz failure
```js
// original code
// (beautified)
var _calls_ = 10, a = 100, b = 10, c = 0;

function f0(a_1) {
    function* f1(a) {
        switch (typeof a_1 == "function" && --_calls_ >= 0 && a_1(5)) {
          case a++ + (typeof f2 == "function" && --_calls_ >= 0 && f2(/[a2][^e]+$/)):
            break;

          case a++ + (a && typeof a.var == "function" && --_calls_ >= 0 && a.var(a && a[c = 1 + c, 
            (23..toString() >= null <= ({} == "bar")) / ((a_1 && (a_1[c = 1 + c, 
            (undefined + "function") / (-4 & null) >>> delete ([ , 0 ][1] === Infinity)] = -5 * -1)) !== (null !== -3))])):
            try {
                {
                    var brake3 = 5;
                    do {
                        c = 1 + c, (a && (a[c = 1 + c, (2 ^ "") % ("" && undefined) & "c" / -4 != 4 + "a"] = -2 >= this)) - (-0 != /[a2][^e]+$/) >>> ((a && (a.var = "function" > "c")) === -2 << []);
                    } while ((c = 1 + c, (a && ({
                        next: a.Infinity
                    } = {
                        next: 1 > Infinity && 4 * 38..toString()
                    })) !== ("bar" > [ , 0 ][1]) + ([ , 0 ][1] << 38..toString())) && --brake3 > 0);
                }
            } catch (foo_2) {
                c = 1 + c, (NaN ^ [ , 0 ][1]) << (false ^ -4) <= ((true == 5) <= (-4 && null));
                c = 1 + c, (-1 ^ "bar") & (this && -1) && (c = c + 1, true) % (5 || "object");
                c = 1 + c, +(foo_2 && (foo_2[c = 1 + c, (a && (a[c = 1 + c, (4 ^ -1 || -5 === 22) % (({} && "number") <= ([] || -0))] |= [ , 0 ][1] ^ Infinity)) != 1 << [] && ("undefined" == 25) >> [ , 0 ][1] % []] = "a" && [ , 0 ][1])) - (1 - [ , 0 ][1] > ("number" < "function"));
            } finally {
                c = 1 + c, ("number" == [] | (-5 | true)) === ([] < 3) >> ("undefined" && 5);
            }
            try {
                c = c + 1;
            } catch (let_2) {
                c = 1 + c, ("a" << -0) - "" % "foo" & (true, 2, "foo" << null);
            } finally {
                c = 1 + c, (c = c + 1, -5 + 5) * (a_1 &= (4 >>> this) % ("undefined" >= "function"));
            }
            break;

          default:
            (c = c + 1) + -2;

          case a++ + -a:
            {
                c = 1 + c, a_1 && (a_1[void a] = (c = c + 1, "foo") ^ (-3 || -2) || /[a2][^e]+$/ <= ([ , 0 ].length === 2) < -0 / 5);
                c = 1 + c, ~(("number" || [ , 0 ][1]) ^ "object" >= this);
                c = 1 + c, ((a_1 = "number" && null) == (24..toString() ^ [ , 0 ].length === 2)) % ("c" > 22 >= (a_1 && (a_1.c = "function" < 1)));
                c = 1 + c, (c = c + 1, ~"undefined") < (true <= 3) + (a_1 && (a_1[c = 1 + c, 
                !("b" / ([ , 0 ].length === 2)) >>> +("a" / -0)] = 0 | false));
                c = 1 + c, a_1 += (-0 * "function" != "b" % "a") <= (null !== [] !== (a = NaN >= 4));
            }
            break;
        }
    }
    var a_1_1 = f1(..."" + a_1_1);
    function f2(foo) {
        {
            return;
            a_1_1;
        }
    }
    function f3(a_1_2, let_1, arguments_1) {
        class C0 {
            done(undefined_2) {}
            get ""() {
                return /[abc4]/g.exec(((c = c + 1) + {
                    value: (c = 1 + c, (c = c + 1, true == []) / (Object.isExtensible(a_1) && (a_1[--b + (Object.isExtensible(a_1_2) && (a_1_2.in = (c = c + 1, 
                    1 >>> -3) | (-0 === "number" | -3 == 2)))] = 23..toString() >>> -3 === (4 || /[a2][^e]+$/))))
                }[a_1_2] || b || 5).toString());
            }
        }
        return b + 1 - .1 - .1 - .1;
    }
    var a = f3("bar", 3);
    function f4() {
        {
            var brake23 = 5;
            do {
                {
                    var brake24 = 5;
                    L23982: do {
                        (c = c + 1) + ((c = 1 + c, true >> 1 >>> (25, 0) >= ((-2 != Infinity) > ("bar" != "bar"))) || 3).toString()[c = 1 + c, 
                        (undefined >= false != (22 === [])) + ((this != 3) >= 24..toString() * [])];
                    } while ((c = c + 1) + (typeof f3 == "function" && --_calls_ >= 0 && f3((c = 1 + c, 
                    ((a = -1 == -4) | ("" | "")) === "c" - 25 < "bar" % -3), (c = 1 + c, 
                    ("function" || "undefined") >>> ("function" !== 25) ^ "number" * false <= ("foo" === undefined)), 5)) && --brake24 > 0);
                }
            } while ((c = c + 1) + (a_1_1 /= --b + (a_1_1 && typeof a_1_1.b == "function" && --_calls_ >= 0 && a_1_1.b(22))) && --brake23 > 0);
        }
        try {
            {
                var bar = function f5(yield, NaN_2) {
                    c = 1 + c, (/[a2][^e]+$/ >> -0 && 5 < 25) >>> ("number" != 22 !== 22 <= 3);
                }(this);
            }
        } catch (bar) {
            {
                c = 1 + c, (([ , 0 ].length === 2) > "foo" || true && NaN) - ((a_1 && (a_1.b = 4 > "object")) + "a" % 5);
                c = 1 + c, ((/[a2][^e]+$/ | 4) ^ (c = c + 1, "number")) * (24..toString() >>> "object" >> delete -0);
            }
            {
                var b = function bar_2() {
                }((c = 1 + c, ([] > "undefined" > "c" + 38..toString()) / (([ , 0 ][1] || -4) >= (25 ^ []))));
            }
        }
        L23983: {
            {
                c = 1 + c, (([], "function") === {} * -0) - ("foo" >>> "c" === ("function" || 38..toString()));
            }
            {
                var brake36 = 5;
                while ((c = c + 1) + [] && --brake36 > 0) {
                    var expr37 = (c = 1 + c, (c = c + 1, 1 << 1) ^ "" <= 1 <= "c" - -4);
                    for (var key37 in expr37) {
                        c = 1 + c, (key37 && (key37[c = 1 + c, ("function" >> 4 && 23..toString() / "function") >= (23..toString() <= -5 == -5 >>> "a")] *= 23..toString() & [])) >= (4 === 3) && (c = c + 1, 
                        2 - -5);
                    }
                }
            }
        }
    }
    var a = f4(--b + (a_1 += (c = c + 1) + {
        [-0]: b += a,
        "": typeof a == "function" && --_calls_ >= 0 && a(22, [ , 0 ].length === 2)
    }.value));
}

var bar_1 = f0();

console.log(null, a, b, c, Infinity, NaN, undefined);
```
```js
// uglified code
// (beautified)
var e, n = e = 10, _ = 0;

(function f0(a_1) {
    var i, c;
    function f3(a_1_2, let_1, arguments_1) {
        return n + 1 - .1 - .1 - .1;
    }
    i = function* f1(a) {
        switch ("function" == typeof a_1 && 0 <= --e && a_1(5)) {
          case a++ + (0 <= --e && void 0):
            break;

          case a++ + (a && "function" == typeof a.var && 0 <= --e && a.var(a && a[_ = 1 + _, 
            !1 / (!0 !== (a_1 && (a_1[_ = 1 + _, 0] = 5)))])):
            try {
                for (var n = 5; _ = 1 + _, a && (a[_ = 1 + _, 0] = this <= -2), 
                a && (a.var = !0), _ = 1 + _, 0 !== (a && ({
                    next: a.Infinity
                } = {
                    next: !1
                })) && 0 < --n; ) {}
            } catch (n) {
                _ = 1 + (_ = 1 + _), -1 & (this && -1) && (_ += 1), _ = 1 + _, n && (n[_ = 1 + _, 
                1 != (a && (a[_ = 1 + _, NaN] |= 0)) && 0] = 0);
            } finally {
                _ = 1 + _;
            }
            try {
                _ += 1;
            } catch (a) {
                _ = 1 + _;
            } finally {
                _ = 1 + _, _ += 1, a_1 &= (4 >>> this) % !0;
            }
            break;

          default:
            _ += 1;

          case a++ - a:
            _ = 1 + _, a_1 && (a_1[void 0] = -3 ^ (_ += 1, "foo")), _ = 1 + (_ = 1 + _), 
            (a_1 = null) && (a_1.c = !1), _ = 1 + _, _ += 1, a_1 && (a_1[_ = 1 + _, 
            !("b" / (2 === [ , 0 ].length)) >>> NaN] = 0), _ = 1 + _, a_1 += !0 <= (1 != (a = !1));
        }
    }(..."" + i), c = function f4() {
        var a, n, t, f, o = 5;
        do {
            for (a = 5; _ = 1 + (_ = 1 + (_ += 1)), (_ += 1) + (0 <= --e && f3(c = !1, _ = 1 + (_ = 1 + _))) && 0 < --a; ) {}
        } while ((_ += 1) + (i /= --n + (i && "function" == typeof i.b && 0 <= --e && i.b(22))) && 0 < --o);
        try {
            !function f5(yield, NaN_2) {
                _ = 1 + _;
            }();
        } catch (a) {
            _ = 1 + _, a_1 && (a_1.b = !1), _ = 1 + _, n = void (_ = 1 + (_ += 1));
        }
        for (_ = 1 + _, t = 5; (_ += 1) + [] && 0 < --t; ) {
            for (f in _ = 1 + _, _ += 1, 2) {
                _ = 1 + _, !1 <= (f && (f[_ = 1 + _, !0] *= 0)) && (_ += 1);
            }
        }
    }((--n, a_1 += (_ += 1) + {
        [0]: n += c = f3(),
        "": "function" == typeof c && 0 <= --e && c(22, 2 === [ , 0 ].length)
    }.value));
})(), console.log(null, 100, n, _, Infinity, NaN, void 0);
```
```
original result:
null 100 19.700000000000003 47 Infinity NaN undefined

uglified result:
null 100 18.700000000000003 47 Infinity NaN undefined
```
```js
// reduced test case (output will differ)

// (beautified)
var b = 0;

function f3() {
    return b + 0 - 0;
}

var a = f3();

f3;

--b + console.log(a);
// output: 0
// 
// minify: -1
// 
// options: {
//   "compress": {
//     "hoist_vars": true,
//     "keep_infinity": true,
//     "passes": 1000000,
//     "unsafe": true
//   },
//   "keep_fargs": true,
//   "keep_fnames": true,
//   "module": false,
//   "toplevel": true,
//   "mangle": {
//     "v8": true
//   },
//   "output": {
//     "v8": true
//   },
//   "validate": true
// }
```
```
minify(options):
{
  "compress": {
    "hoist_vars": true,
    "keep_infinity": true,
    "passes": 1000000,
    "unsafe": true
  },
  "keep_fargs": true,
  "keep_fnames": true,
  "module": false,
  "toplevel": true,
  "mangle": {
    "v8": true
  },
  "output": {
    "v8": true
  }
}

Suspicious compress options:
  collapse_vars
  inline
  passes
  reduce_vars
  unused
```



Discussion / hints:

Fix patch:
diff --git a/lib/compress.js b/lib/compress.js
index 19b7256049..0fea284d93 100644
--- a/lib/compress.js
+++ b/lib/compress.js
@@ -3409,6 +3409,7 @@ Compressor.prototype.compress = function(node) {
                 var find_arguments = scope.uses_arguments && !compressor.has_directive("use strict");
                 var scan_toplevel = scope instanceof AST_Toplevel;
                 var tw = new TreeWalker(function(node) {
+                    if (node.inlined_node) node.inlined_node.walk(tw);
                     var value;
                     if (node instanceof AST_SymbolRef) {
                         value = node.fixed_value();


Test patch:
diff --git a/test/compress/functions.js b/test/compress/functions.js
index d900d32809..c8b5b532c1 100644
--- a/test/compress/functions.js
+++ b/test/compress/functions.js
@@ -9076,3 +9076,68 @@ issue_5895_2: {
         "foo",
     ]
 }
+
+issue_5924: {
+    options = {
+        collapse_vars: true,
+        inline: true,
+        reduce_vars: true,
+        toplevel: true,
+    }
+    input: {
+        var a = 42;
+        function f() {
+            return a - 41;
+        }
+        function g() {
+            return f;
+        }
+        var b = f();
+        a--;
+        console.log(b ? "PASS" : "FAIL");
+    }
+    expect: {
+        var a = 42;
+        function f() {
+            return a - 41;
+        }
+        function g() {
+            return f;
+        }
+        var b = f();
+        a--;
+        console.log(b ? "PASS" : "FAIL");
+    }
+    expect_stdout: "PASS"
+}
+
+issue_5925: {
+    options = {
+        collapse_vars: true,
+        inline: true,
+        reduce_vars: true,
+    }
+    input: {
+        var a = 42;
+        console.log(function() {
+            function f() {
+                return +a - 41;
+            }
+            var b = f(f);
+            a--;
+            return b;
+        }() ? "PASS" : "FAIL");
+    }
+    expect: {
+        var a = 42;
+        console.log(function() {
+            function f() {
+                return +a - 41;
+            }
+            var b = f(f);
+            a--;
+            return b;
+        }() ? "PASS" : "FAIL");
+    }
+    expect_stdout: "PASS"
+}