Repository: mishoo/UglifyJS (JavaScript)

Issue:
ufuzz failure
```js
// original code
// (beautified)
var _calls_ = 10, a = 100, b = 10, c = 0;

L45116: {
    {
        var expr2 = typeof (--b + [ (c = c + 1) + [].in ][{
            var: function() {
                {
                    var a_1 = function f0(b_1) {
                    }();
                }
                typeof a_1 == "function" && --_calls_ >= 0 && a_1(1);
                if (!b) {}
            },
            3: --b + (a && typeof a.c == "function" && --_calls_ >= 0 && a.c(a++ + [ (c = 1 + c, 
            (c = c + 1, "c") >>> ("" < "b") >= ((0 == [ , 0 ][1]) < (c = c + 1, "b"))), (c = 1 + c, 
            ("object" ^ -4) * ("c" << true) | (-0 === Infinity, "number" > "foo")), (c = 1 + c, 
            a ^= (a = 24..toString() * Infinity / (a && (a.undefined ^= (-4, null)))) / ((0 | NaN) <= (-0 | 0))), , (c = 1 + c, 
            a = (a && (a.null += 2 > 25 > (a && (a.NaN *= -2 != 3)))) ^ (5 && -1) << 24..toString() - null) ])),
            length: --b,
            b: --b + (typeof f1 == "function" && --_calls_ >= 0 && f1(-5)),
            Infinity: "function"
        }]);
        for (var key2 in expr2) {
            break L45116;
        }
    }
    var undefined = {
        in: a++ + /[abc4]/.test((--b + (a && typeof a.c == "function" && --_calls_ >= 0 && a.c((c = c + 1) + {
            1.5: --b
        }[+a])) || b || 5).toString())
    }, foo = ++a;
    var Math = a && a.b, b = --b + (b + 1 - .1 - .1 - .1);
}

c = c + 1;

console.log(null, a, b, c, Infinity, NaN, undefined);
```
```js
// uglified code
// (beautified)
var t = 10, n = 100, i = 10, f = 0;

n: {
    var o, c = typeof (--i + [ (f += 1) + []["in"] ][{
        var: function() {
            var n = void 0;
            "function" == typeof n && 0 <= --t && n(1);
        },
        3: --i + (n && "function" == typeof n.c && 0 <= --t && n.c(n++ + [ (f = 1 + f, f += 1, 
        !0 < "b" <= 0), (f = 1 + (f += 1), -0 | (Infinity, !0)), (f = 1 + f, n ^= (n = 24..toString() * Infinity / (n && (n.undefined ^= null))) / ((0 | NaN) <= 0)), , (f = 1 + f, 
        n = (n && (n["null"] += (n && (n.NaN *= !0)) < !1)) ^ -1 << 24..toString() - null) ])),
        length: --i,
        b: --i + ("function" == typeof f1 && 0 <= --t && f1(-5)),
        Infinity: "function"
    }]);
    for (o in c) {
        break n;
    }
    var c = {
        in: n++ + /[abc4]/.test((--i + (n && "function" == typeof n.c && 0 <= --t && n.c((f += 1) + {
            1.5: --i
        }[+n])) || i || 5).toString())
    }, i = (++n, n && n.b, --i + (i + 1 - .1 - .1 - .1));
}

f += 1, console.log(null, n, i, f, Infinity, NaN, c);
```
```
original result:
null 100 6 2 Infinity NaN undefined

uglified result:
null 100 6 2 Infinity NaN 'number'
```
```js
// reduced test case (output will differ)

// (beautified)
var a = 0;

L45116: {
    var expr2 = typeof (0).in;
    for (var key2 in expr2) {
        break L45116;
    }
    var undefined = 0;
}

console.log(a, undefined);
// output: 0 undefined
// 
// minify: 0 'undefined'
// 
// options: {
//   "ie8": true,
//   "toplevel": true,
//   "validate": true
// }
```
```
minify(options):
{
  "ie8": true,
  "toplevel": true
}

Suspicious compress options:
  merge_vars

Suspicious options:
  toplevel
```


Discussion:

Patch:
diff --git a/lib/compress.js b/lib/compress.js
index a79b909d224..e3139054e2d 100644
--- a/lib/compress.js
+++ b/lib/compress.js
@@ -4376,6 +4376,12 @@ merge(Compressor.prototype, {
                 pop();
                 return true;
             }
+            if (node instanceof AST_LabeledStatement) {
+                push();
+                node.body.walk(tw);
+                pop();
+                return true;
+            }
             if (node instanceof AST_Scope) {
                 if (node instanceof AST_Lambda) {
                     references[node.variables.get("arguments").id] = false;


Test patch:
diff --git a/test/compress/merge_vars.js b/test/compress/merge_vars.js
index fd650f9d0ef..c63f33d08ee 100644
--- a/test/compress/merge_vars.js
+++ b/test/compress/merge_vars.js
@@ -486,3 +486,29 @@ issue_4112: {
     }
     expect_stdout: "function"
 }
+
+issue_4115: {
+    options = {
+        merge_vars: true,
+        toplevel: true,
+    }
+    input: {
+        L: {
+            var o = typeof console;
+            for (var k in o)
+                break L;
+            var a = 0;
+        }
+        console.log(typeof a);
+    }
+    expect: {
+        L: {
+            var o = typeof console;
+            for (var k in o)
+                break L;
+            var a = 0;
+        }
+        console.log(typeof a);
+    }
+    expect_stdout: "undefined"
+}