From: Richard van Velzen Date: Sat, 23 Apr 2016 21:48:33 +0000 (+0200) Subject: Hoist functions when reversing if (x) return; ... vs. if (!x) ... X-Git-Url: https://git.ndcode.org/public/gitweb.cgi?a=commitdiff_plain;h=4fe630431c37ffb81466959e9ea9797d6d2de21a;p=UglifyJS.git Hoist functions when reversing if (x) return; ... vs. if (!x) ... Fixes #1052 --- diff --git a/lib/compress.js b/lib/compress.js index 53618ae1..2bcfcf30 100644 --- a/lib/compress.js +++ b/lib/compress.js @@ -578,11 +578,13 @@ merge(Compressor.prototype, { CHANGED = true; stat = stat.clone(); stat.condition = stat.condition.negate(compressor); + var body = as_statement_array(stat.alternative).concat(ret); + var funs = extract_functions_from_statement_array(body); stat.body = make_node(AST_BlockStatement, stat, { - body: as_statement_array(stat.alternative).concat(ret) + body: body }); stat.alternative = null; - ret = [ stat.transform(compressor) ]; + ret = funs.concat([ stat.transform(compressor) ]); continue loop; } //--- @@ -840,6 +842,18 @@ merge(Compressor.prototype, { }; + function extract_functions_from_statement_array(statements) { + var funs = []; + for (var i = statements.length - 1; i >= 0; --i) { + var stat = statements[i]; + if (stat instanceof AST_Defun) { + statements.splice(i, 1); + funs.unshift(stat); + } + } + return funs; + } + function extract_declarations_from_unreachable_code(compressor, stat, target) { if (!(stat instanceof AST_Defun)) { compressor.warn("Dropping unreachable code [{file}:{line},{col}]", stat.start); diff --git a/test/compress/issue-1052.js b/test/compress/issue-1052.js new file mode 100644 index 00000000..067eea4a --- /dev/null +++ b/test/compress/issue-1052.js @@ -0,0 +1,27 @@ +hoist_funs_when_handling_if_return_rerversal: { + options = { if_return: true, hoist_funs: false }; + input: { + "use strict"; + + ( function() { + if ( !window ) { + return; + } + + function f() {} + function g() {} + } )(); + } + expect: { + "use strict"; + + ( function() { + function f() {} + function g() {} + + // NOTE: other compression steps will reduce this + // down to just `window`. + if ( window ); + } )(); + } +}