validate against multiple parents on AST_Node (#4032)

- fix related issues in `global_defs`, `ie8` & `reduce_vars`
This commit is contained in:
Alex Lam S.L
2020-07-31 01:09:19 +01:00
committed by GitHub
parent ee632a5519
commit 88423f2574
7 changed files with 63 additions and 11 deletions

View File

@@ -120,6 +120,13 @@ var AST_Node = DEFNODE("Node", "start end", {
ctor.prototype._validate.call(this);
} while (ctor = ctor.BASE);
},
validate_ast: function() {
var marker = {};
this.walk(new TreeWalker(function(node) {
if (node.validate_visited === marker) throw new Error("invalid node reuse: " + node);
node.validate_visited = marker;
}));
},
}, null);
(AST_Node.log_function = function(fn, verbose) {

View File

@@ -3072,7 +3072,7 @@ merge(Compressor.prototype, {
(function(def) {
function to_node(value, orig) {
if (value instanceof AST_Node) return make_node(value.CTOR, orig, value);
if (value instanceof AST_Node) return value.clone(true);
if (Array.isArray(value)) return make_node(AST_Array, orig, {
elements: value.map(function(value) {
return to_node(value, orig);
@@ -7642,6 +7642,8 @@ merge(Compressor.prototype, {
single_use = false;
} else if (recursive_ref(compressor, def)) {
single_use = false;
} else if (compressor.option("ie8") && fixed.name && def !== fixed.name.definition()) {
single_use = false;
} else if (def.scope !== self.scope || def.orig[0] instanceof AST_SymbolFunarg) {
single_use = fixed.is_constant_expression(self.scope);
if (single_use == "f") {
@@ -7650,8 +7652,6 @@ merge(Compressor.prototype, {
scope.inlined = true;
} while (scope = scope.parent_scope);
}
} else if (compressor.option("ie8") && fixed.name && def !== fixed.name.definition()) {
single_use = false;
}
if (single_use) fixed.parent_scope = self.scope;
} else if (!fixed || !fixed.is_constant_expression()) {

View File

@@ -178,13 +178,17 @@ function minify(files, options) {
toplevel = toplevel[action](option);
files[toplevel.start.file] = toplevel.print_to_string().replace(orig, "");
});
if (options.validate) toplevel.validate_ast();
if (timings) timings.rename = Date.now();
if (options.rename) {
toplevel.figure_out_scope(options.mangle);
toplevel.expand_names(options.mangle);
}
if (timings) timings.compress = Date.now();
if (options.compress) toplevel = new Compressor(options.compress).compress(toplevel);
if (options.compress) {
toplevel = new Compressor(options.compress).compress(toplevel);
if (options.validate) toplevel.validate_ast();
}
if (timings) timings.scope = Date.now();
if (options.mangle) toplevel.figure_out_scope(options.mangle);
if (timings) timings.mangle = Date.now();