Use AST.Node instead of AST_Node
This commit is contained in:
parent
1ce651ee14
commit
13196026eb
21
bin/uglifyjs
21
bin/uglifyjs
|
|
@ -10,6 +10,7 @@ var info = require("../package.json");
|
|||
var path = require("path");
|
||||
var program = require("commander");
|
||||
var UglifyJS = require("../tools/node");
|
||||
var AST = UglifyJS.AST;
|
||||
|
||||
var skip_keys = [ "cname", "inlined", "parent_scope", "scope", "uses_eval", "uses_with" ];
|
||||
var files = {};
|
||||
|
|
@ -182,11 +183,11 @@ if (program.self) {
|
|||
}
|
||||
|
||||
function convert_ast(fn) {
|
||||
return UglifyJS.ast.AST_Node.from_mozilla_ast(Object.keys(files).reduce(fn, null));
|
||||
return AST.Node.from_mozilla_ast(Object.keys(files).reduce(fn, null));
|
||||
}
|
||||
|
||||
function run() {
|
||||
UglifyJS.ast.AST_Node.warn_function = function(msg) {
|
||||
AST.Node.warn_function = function(msg) {
|
||||
print_error("WARN: " + msg);
|
||||
};
|
||||
var content = program.sourceMap && program.sourceMap.content;
|
||||
|
|
@ -260,11 +261,11 @@ function run() {
|
|||
return value.size() ? value.map(symdef) : undefined;
|
||||
}
|
||||
if (skip_key(key)) return;
|
||||
if (value instanceof UglifyJS.ast.AST_Token) return;
|
||||
if (value instanceof AST.Token) return;
|
||||
if (value instanceof UglifyJS.Dictionary) return;
|
||||
if (value instanceof UglifyJS.ast.AST_Node) {
|
||||
if (value instanceof AST.Node) {
|
||||
var result = {
|
||||
_class: "AST_" + value.TYPE
|
||||
_class: "AST." + value.TYPE
|
||||
};
|
||||
value.CTOR.PROPS.forEach(function(prop) {
|
||||
result[prop] = value[prop];
|
||||
|
|
@ -359,27 +360,27 @@ function parse_js(flag) {
|
|||
code: false
|
||||
}
|
||||
}).ast.walk(new UglifyJS.TreeWalker(function(node) {
|
||||
if (node instanceof UglifyJS.ast.AST_Assign) {
|
||||
if (node instanceof AST.Assign) {
|
||||
var name = node.left.print_to_string();
|
||||
var value = node.right;
|
||||
if (flag) {
|
||||
options[name] = value;
|
||||
} else if (value instanceof UglifyJS.ast.AST_Array) {
|
||||
} else if (value instanceof AST.Array) {
|
||||
options[name] = value.elements.map(to_string);
|
||||
} else {
|
||||
options[name] = to_string(value);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
if (node instanceof UglifyJS.ast.AST_Symbol || node instanceof UglifyJS.ast.AST_PropAccess) {
|
||||
if (node instanceof AST.Symbol || node instanceof AST.PropAccess) {
|
||||
var name = node.print_to_string();
|
||||
options[name] = true;
|
||||
return true;
|
||||
}
|
||||
if (!(node instanceof UglifyJS.ast.AST_Sequence)) throw node;
|
||||
if (!(node instanceof AST.Sequence)) throw node;
|
||||
|
||||
function to_string(value) {
|
||||
return value instanceof UglifyJS.ast.AST_Constant ? value.getValue() : value.print_to_string({
|
||||
return value instanceof AST.Constant ? value.getValue() : value.print_to_string({
|
||||
quote_keys: true
|
||||
});
|
||||
}
|
||||
|
|
|
|||
85
lib/ast.js
85
lib/ast.js
|
|
@ -1193,4 +1193,89 @@ merge(exports, {
|
|||
TreeWalker : TreeWalker,
|
||||
TreeTransformer : TreeTransformer,
|
||||
first_in_statement : first_in_statement,
|
||||
Token : AST_Token,
|
||||
Node : AST_Node,
|
||||
Statement : AST_Statement,
|
||||
Debugger : AST_Debugger,
|
||||
Directive : AST_Directive,
|
||||
SimpleStatement : AST_SimpleStatement,
|
||||
Block : AST_Block,
|
||||
BlockStatement : AST_BlockStatement,
|
||||
EmptyStatement : AST_EmptyStatement,
|
||||
StatementWithBody : AST_StatementWithBody,
|
||||
LabeledStatement : AST_LabeledStatement,
|
||||
IterationStatement : AST_IterationStatement,
|
||||
DWLoop : AST_DWLoop,
|
||||
Do : AST_Do,
|
||||
While : AST_While,
|
||||
For : AST_For,
|
||||
ForIn : AST_ForIn,
|
||||
With : AST_With,
|
||||
Scope : AST_Scope,
|
||||
Toplevel : AST_Toplevel,
|
||||
Lambda : AST_Lambda,
|
||||
Accessor : AST_Accessor,
|
||||
Function : AST_Function,
|
||||
Defun : AST_Defun,
|
||||
Jump : AST_Jump,
|
||||
Exit : AST_Exit,
|
||||
Return : AST_Return,
|
||||
Throw : AST_Throw,
|
||||
LoopControl : AST_LoopControl,
|
||||
Break : AST_Break,
|
||||
Continue : AST_Continue,
|
||||
If : AST_If,
|
||||
Switch : AST_Switch,
|
||||
SwitchBranch : AST_SwitchBranch,
|
||||
Default : AST_Default,
|
||||
Case : AST_Case,
|
||||
Try : AST_Try,
|
||||
Catch : AST_Catch,
|
||||
Finally : AST_Finally,
|
||||
Definitions : AST_Definitions,
|
||||
Var : AST_Var,
|
||||
VarDef : AST_VarDef,
|
||||
Call : AST_Call,
|
||||
New : AST_New,
|
||||
Sequence : AST_Sequence,
|
||||
PropAccess : AST_PropAccess,
|
||||
Dot : AST_Dot,
|
||||
Sub : AST_Sub,
|
||||
Unary : AST_Unary,
|
||||
UnaryPrefix : AST_UnaryPrefix,
|
||||
UnaryPostfix : AST_UnaryPostfix,
|
||||
Binary : AST_Binary,
|
||||
Conditional : AST_Conditional,
|
||||
Assign : AST_Assign,
|
||||
Array : AST_Array,
|
||||
Object : AST_Object,
|
||||
ObjectProperty : AST_ObjectProperty,
|
||||
ObjectKeyVal : AST_ObjectKeyVal,
|
||||
ObjectSetter : AST_ObjectSetter,
|
||||
ObjectGetter : AST_ObjectGetter,
|
||||
Symbol : AST_Symbol,
|
||||
SymbolAccessor : AST_SymbolAccessor,
|
||||
SymbolDeclaration : AST_SymbolDeclaration,
|
||||
SymbolVar : AST_SymbolVar,
|
||||
SymbolFunarg : AST_SymbolFunarg,
|
||||
SymbolDefun : AST_SymbolDefun,
|
||||
SymbolLambda : AST_SymbolLambda,
|
||||
SymbolCatch : AST_SymbolCatch,
|
||||
Label : AST_Label,
|
||||
SymbolRef : AST_SymbolRef,
|
||||
LabelRef : AST_LabelRef,
|
||||
This : AST_This,
|
||||
Constant : AST_Constant,
|
||||
String : AST_String,
|
||||
Number : AST_Number,
|
||||
RegExp : AST_RegExp,
|
||||
Atom : AST_Atom,
|
||||
Null : AST_Null,
|
||||
NaN : AST_NaN,
|
||||
Undefined : AST_Undefined,
|
||||
Hole : AST_Hole,
|
||||
Infinity : AST_Infinity,
|
||||
Boolean : AST_Boolean,
|
||||
False : AST_False,
|
||||
True : AST_True,
|
||||
});
|
||||
|
|
|
|||
2190
lib/compress.js
2190
lib/compress.js
File diff suppressed because it is too large
Load Diff
|
|
@ -7,11 +7,8 @@ var HOP = utils.HOP;
|
|||
var MAP = utils.MAP;
|
||||
var merge = utils.merge;
|
||||
|
||||
var ast = require("./ast");
|
||||
var AST_Node = ast.AST_Node;
|
||||
var AST_Toplevel = ast.AST_Toplevel;
|
||||
var AST_Directive = ast.AST_Directive;
|
||||
var TreeTransformer = ast.TreeTransformer;
|
||||
var AST = require("./ast");
|
||||
var TreeTransformer = AST.TreeTransformer;
|
||||
|
||||
var parse = require("./parse");
|
||||
var parse = parse.parse;
|
||||
|
|
@ -35,7 +32,7 @@ var to_base64 = typeof btoa == "undefined" ? function(str) {
|
|||
function read_source_map(name, code) {
|
||||
var match = /\n\/\/# sourceMappingURL=data:application\/json(;.*?)?;base64,(.*)/.exec(code);
|
||||
if (!match) {
|
||||
AST_Node.warn("inline source map not found: " + name);
|
||||
AST.Node.warn("inline source map not found: " + name);
|
||||
return null;
|
||||
}
|
||||
return to_ascii(match[2]);
|
||||
|
|
@ -81,7 +78,7 @@ function minify(files, options) {
|
|||
var wrapped_tl = "(function(exports){'$ORIG';})(typeof " + name + "=='undefined'?(" + name + "={}):" + name + ");";
|
||||
wrapped_tl = parse(wrapped_tl);
|
||||
wrapped_tl = wrapped_tl.transform(new TreeTransformer(function before(node) {
|
||||
if (node instanceof AST_Directive && node.value == "$ORIG") {
|
||||
if (node instanceof AST.Directive && node.value == "$ORIG") {
|
||||
return MAP.splice(body);
|
||||
}
|
||||
}));
|
||||
|
|
@ -99,13 +96,13 @@ function minify(files, options) {
|
|||
args_values.slice(index + 1),
|
||||
")"
|
||||
].join("")).transform(new TreeTransformer(function(node) {
|
||||
if (node instanceof AST_Directive && node.value == "$ORIG") {
|
||||
if (node instanceof AST.Directive && node.value == "$ORIG") {
|
||||
return MAP.splice(body);
|
||||
}
|
||||
}));
|
||||
}
|
||||
|
||||
var warn_function = AST_Node.warn_function;
|
||||
var warn_function = AST.Node.warn_function;
|
||||
try {
|
||||
options = defaults(options, {
|
||||
compress: {},
|
||||
|
|
@ -170,14 +167,14 @@ function minify(files, options) {
|
|||
}, true);
|
||||
}
|
||||
var warnings = [];
|
||||
if (options.warnings && !AST_Node.warn_function) {
|
||||
AST_Node.warn_function = function(warning) {
|
||||
if (options.warnings && !AST.Node.warn_function) {
|
||||
AST.Node.warn_function = function(warning) {
|
||||
warnings.push(warning);
|
||||
};
|
||||
}
|
||||
if (timings) timings.parse = Date.now();
|
||||
var source_maps, toplevel;
|
||||
if (files instanceof AST_Toplevel) {
|
||||
if (files instanceof AST.Toplevel) {
|
||||
toplevel = files;
|
||||
} else {
|
||||
if (typeof files == "string") {
|
||||
|
|
@ -246,7 +243,7 @@ function minify(files, options) {
|
|||
root: options.sourceMap.root
|
||||
});
|
||||
if (options.sourceMap.includeSources) {
|
||||
if (files instanceof AST_Toplevel) {
|
||||
if (files instanceof AST.Toplevel) {
|
||||
throw new Error("original source content unavailable");
|
||||
} else for (var name in files) if (HOP(files, name)) {
|
||||
options.output.source_map.get().setSourceContent(name, files[name]);
|
||||
|
|
@ -295,7 +292,7 @@ function minify(files, options) {
|
|||
} catch (ex) {
|
||||
return { error: ex };
|
||||
} finally {
|
||||
AST_Node.warn_function = warn_function;
|
||||
AST.Node.warn_function = warn_function;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -43,95 +43,20 @@
|
|||
|
||||
"use strict";
|
||||
|
||||
var ast = require("./ast");
|
||||
var TreeWalker = ast.TreeWalker;
|
||||
var AST_Token = ast.AST_Token;
|
||||
var AST_Node = ast.AST_Node;
|
||||
var AST_Statement = ast.AST_Statement;
|
||||
var AST_Debugger = ast.AST_Debugger;
|
||||
var AST_Directive = ast.AST_Directive;
|
||||
var AST_SimpleStatement = ast.AST_SimpleStatement;
|
||||
var AST_Block = ast.AST_Block;
|
||||
var AST_BlockStatement = ast.AST_BlockStatement;
|
||||
var AST_EmptyStatement = ast.AST_EmptyStatement;
|
||||
var AST_LabeledStatement = ast.AST_LabeledStatement;
|
||||
var AST_Do = ast.AST_Do;
|
||||
var AST_While = ast.AST_While;
|
||||
var AST_For = ast.AST_For;
|
||||
var AST_ForIn = ast.AST_ForIn;
|
||||
var AST_With = ast.AST_With;
|
||||
var AST_Scope = ast.AST_Scope;
|
||||
var AST_Toplevel = ast.AST_Toplevel;
|
||||
var AST_Lambda = ast.AST_Lambda;
|
||||
var AST_Accessor = ast.AST_Accessor;
|
||||
var AST_Function = ast.AST_Function;
|
||||
var AST_Defun = ast.AST_Defun;
|
||||
var AST_Return = ast.AST_Return;
|
||||
var AST_Throw = ast.AST_Throw;
|
||||
var AST_Break = ast.AST_Break;
|
||||
var AST_Continue = ast.AST_Continue;
|
||||
var AST_If = ast.AST_If;
|
||||
var AST_Switch = ast.AST_Switch;
|
||||
var AST_SwitchBranch = ast.AST_SwitchBranch;
|
||||
var AST_Default = ast.AST_Default;
|
||||
var AST_Case = ast.AST_Case;
|
||||
var AST_Try = ast.AST_Try;
|
||||
var AST_Catch = ast.AST_Catch;
|
||||
var AST_Finally = ast.AST_Finally;
|
||||
var AST_Definitions = ast.AST_Definitions;
|
||||
var AST_Var = ast.AST_Var;
|
||||
var AST_VarDef = ast.AST_VarDef;
|
||||
var AST_Call = ast.AST_Call;
|
||||
var AST_New = ast.AST_New;
|
||||
var AST_Sequence = ast.AST_Sequence;
|
||||
var AST_PropAccess = ast.AST_PropAccess;
|
||||
var AST_Dot = ast.AST_Dot;
|
||||
var AST_Sub = ast.AST_Sub;
|
||||
var AST_Unary = ast.AST_Unary;
|
||||
var AST_UnaryPrefix = ast.AST_UnaryPrefix;
|
||||
var AST_UnaryPostfix = ast.AST_UnaryPostfix;
|
||||
var AST_Binary = ast.AST_Binary;
|
||||
var AST_Conditional = ast.AST_Conditional;
|
||||
var AST_Assign = ast.AST_Assign;
|
||||
var AST_Array = ast.AST_Array;
|
||||
var AST_Object = ast.AST_Object;
|
||||
var AST_ObjectProperty = ast.AST_ObjectProperty;
|
||||
var AST_ObjectKeyVal = ast.AST_ObjectKeyVal;
|
||||
var AST_ObjectSetter = ast.AST_ObjectSetter;
|
||||
var AST_ObjectGetter = ast.AST_ObjectGetter;
|
||||
var AST_Symbol = ast.AST_Symbol;
|
||||
var AST_SymbolAccessor = ast.AST_SymbolAccessor;
|
||||
var AST_SymbolVar = ast.AST_SymbolVar;
|
||||
var AST_SymbolFunarg = ast.AST_SymbolFunarg;
|
||||
var AST_SymbolDefun = ast.AST_SymbolDefun;
|
||||
var AST_SymbolLambda = ast.AST_SymbolLambda;
|
||||
var AST_SymbolCatch = ast.AST_SymbolCatch;
|
||||
var AST_Label = ast.AST_Label;
|
||||
var AST_SymbolRef = ast.AST_SymbolRef;
|
||||
var AST_LabelRef = ast.AST_LabelRef;
|
||||
var AST_This = ast.AST_This;
|
||||
var AST_Constant = ast.AST_Constant;
|
||||
var AST_String = ast.AST_String;
|
||||
var AST_Number = ast.AST_Number;
|
||||
var AST_RegExp = ast.AST_RegExp;
|
||||
var AST_Atom = ast.AST_Atom;
|
||||
var AST_Null = ast.AST_Null;
|
||||
var AST_Hole = ast.AST_Hole;
|
||||
var AST_Boolean = ast.AST_Boolean;
|
||||
var AST_False = ast.AST_False;
|
||||
var AST_True = ast.AST_True;
|
||||
var AST = require("./ast");
|
||||
var TreeWalker = AST.TreeWalker;
|
||||
|
||||
(function() {
|
||||
function normalize_directives(body) {
|
||||
var in_directive = true;
|
||||
for (var i = 0; i < body.length; i++) {
|
||||
if (in_directive && body[i] instanceof AST_Statement && body[i].body instanceof AST_String) {
|
||||
body[i] = new AST_Directive({
|
||||
if (in_directive && body[i] instanceof AST.Statement && body[i].body instanceof AST.String) {
|
||||
body[i] = new AST.Directive({
|
||||
start: body[i].start,
|
||||
end: body[i].end,
|
||||
value: body[i].body.value
|
||||
});
|
||||
} else if (in_directive && !(body[i] instanceof AST_Statement && body[i].body instanceof AST_String)) {
|
||||
} else if (in_directive && !(body[i] instanceof AST.Statement && body[i].body instanceof AST.String)) {
|
||||
in_directive = false;
|
||||
}
|
||||
}
|
||||
|
|
@ -140,14 +65,14 @@ var AST_True = ast.AST_True;
|
|||
|
||||
var MOZ_TO_ME = {
|
||||
Program: function(M) {
|
||||
return new AST_Toplevel({
|
||||
return new AST.Toplevel({
|
||||
start: my_start_token(M),
|
||||
end: my_end_token(M),
|
||||
body: normalize_directives(M.body.map(from_moz))
|
||||
});
|
||||
},
|
||||
FunctionDeclaration: function(M) {
|
||||
return new AST_Defun({
|
||||
return new AST.Defun({
|
||||
start: my_start_token(M),
|
||||
end: my_end_token(M),
|
||||
name: from_moz(M.id),
|
||||
|
|
@ -156,7 +81,7 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
},
|
||||
FunctionExpression: function(M) {
|
||||
return new AST_Function({
|
||||
return new AST.Function({
|
||||
start: my_start_token(M),
|
||||
end: my_end_token(M),
|
||||
name: from_moz(M.id),
|
||||
|
|
@ -165,7 +90,7 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
},
|
||||
ExpressionStatement: function(M) {
|
||||
return new AST_SimpleStatement({
|
||||
return new AST.SimpleStatement({
|
||||
start: my_start_token(M),
|
||||
end: my_end_token(M),
|
||||
body: from_moz(M.expression)
|
||||
|
|
@ -176,12 +101,12 @@ var AST_True = ast.AST_True;
|
|||
if (handlers.length > 1 || M.guardedHandlers && M.guardedHandlers.length) {
|
||||
throw new Error("Multiple catch clauses are not supported.");
|
||||
}
|
||||
return new AST_Try({
|
||||
return new AST.Try({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
body : from_moz(M.block).body,
|
||||
bcatch : from_moz(handlers[0]),
|
||||
bfinally : M.finalizer ? new AST_Finally(from_moz(M.finalizer)) : null
|
||||
bfinally : M.finalizer ? new AST.Finally(from_moz(M.finalizer)) : null
|
||||
});
|
||||
},
|
||||
Property: function(M) {
|
||||
|
|
@ -192,25 +117,25 @@ var AST_True = ast.AST_True;
|
|||
key : key.type == "Identifier" ? key.name : key.value,
|
||||
value : from_moz(M.value)
|
||||
};
|
||||
if (M.kind == "init") return new AST_ObjectKeyVal(args);
|
||||
args.key = new AST_SymbolAccessor({
|
||||
if (M.kind == "init") return new AST.ObjectKeyVal(args);
|
||||
args.key = new AST.SymbolAccessor({
|
||||
name: args.key
|
||||
});
|
||||
args.value = new AST_Accessor(args.value);
|
||||
if (M.kind == "get") return new AST_ObjectGetter(args);
|
||||
if (M.kind == "set") return new AST_ObjectSetter(args);
|
||||
args.value = new AST.Accessor(args.value);
|
||||
if (M.kind == "get") return new AST.ObjectGetter(args);
|
||||
if (M.kind == "set") return new AST.ObjectSetter(args);
|
||||
},
|
||||
ArrayExpression: function(M) {
|
||||
return new AST_Array({
|
||||
return new AST.Array({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
elements : M.elements.map(function(elem) {
|
||||
return elem === null ? new AST_Hole() : from_moz(elem);
|
||||
return elem === null ? new AST.Hole() : from_moz(elem);
|
||||
})
|
||||
});
|
||||
},
|
||||
ObjectExpression: function(M) {
|
||||
return new AST_Object({
|
||||
return new AST.Object({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
properties : M.properties.map(function(prop) {
|
||||
|
|
@ -220,14 +145,14 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
},
|
||||
SequenceExpression: function(M) {
|
||||
return new AST_Sequence({
|
||||
return new AST.Sequence({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
expressions: M.expressions.map(from_moz)
|
||||
});
|
||||
},
|
||||
MemberExpression: function(M) {
|
||||
return new (M.computed ? AST_Sub : AST_Dot)({
|
||||
return new (M.computed ? AST.Sub : AST.Dot)({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
property : M.computed ? from_moz(M.property) : M.property.name,
|
||||
|
|
@ -235,7 +160,7 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
},
|
||||
SwitchCase: function(M) {
|
||||
return new (M.test ? AST_Case : AST_Default)({
|
||||
return new (M.test ? AST.Case : AST.Default)({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
expression : from_moz(M.test),
|
||||
|
|
@ -243,7 +168,7 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
},
|
||||
VariableDeclaration: function(M) {
|
||||
return new AST_Var({
|
||||
return new AST.Var({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
definitions : M.declarations.map(from_moz)
|
||||
|
|
@ -254,38 +179,38 @@ var AST_True = ast.AST_True;
|
|||
start : my_start_token(M),
|
||||
end : my_end_token(M)
|
||||
};
|
||||
if (val === null) return new AST_Null(args);
|
||||
if (val === null) return new AST.Null(args);
|
||||
var rx = M.regex;
|
||||
if (rx && rx.pattern) {
|
||||
// RegExpLiteral as per ESTree AST spec
|
||||
args.value = new RegExp(rx.pattern, rx.flags);
|
||||
args.value.raw_source = rx.pattern;
|
||||
return new AST_RegExp(args);
|
||||
return new AST.RegExp(args);
|
||||
} else if (rx) {
|
||||
// support legacy RegExp
|
||||
args.value = M.regex && M.raw ? M.raw : val;
|
||||
return new AST_RegExp(args);
|
||||
return new AST.RegExp(args);
|
||||
}
|
||||
switch (typeof val) {
|
||||
case "string":
|
||||
args.value = val;
|
||||
return new AST_String(args);
|
||||
return new AST.String(args);
|
||||
case "number":
|
||||
args.value = val;
|
||||
return new AST_Number(args);
|
||||
return new AST.Number(args);
|
||||
case "boolean":
|
||||
return new (val ? AST_True : AST_False)(args);
|
||||
return new (val ? AST.True : AST.False)(args);
|
||||
}
|
||||
},
|
||||
Identifier: function(M) {
|
||||
var p = FROM_MOZ_STACK[FROM_MOZ_STACK.length - 2];
|
||||
return new ( p.type == "LabeledStatement" ? AST_Label
|
||||
: p.type == "VariableDeclarator" && p.id === M ? AST_SymbolVar
|
||||
: p.type == "FunctionExpression" ? (p.id === M ? AST_SymbolLambda : AST_SymbolFunarg)
|
||||
: p.type == "FunctionDeclaration" ? (p.id === M ? AST_SymbolDefun : AST_SymbolFunarg)
|
||||
: p.type == "CatchClause" ? AST_SymbolCatch
|
||||
: p.type == "BreakStatement" || p.type == "ContinueStatement" ? AST_LabelRef
|
||||
: AST_SymbolRef)({
|
||||
return new ( p.type == "LabeledStatement" ? AST.Label
|
||||
: p.type == "VariableDeclarator" && p.id === M ? AST.SymbolVar
|
||||
: p.type == "FunctionExpression" ? (p.id === M ? AST.SymbolLambda : AST.SymbolFunarg)
|
||||
: p.type == "FunctionDeclaration" ? (p.id === M ? AST.SymbolDefun : AST.SymbolFunarg)
|
||||
: p.type == "CatchClause" ? AST.SymbolCatch
|
||||
: p.type == "BreakStatement" || p.type == "ContinueStatement" ? AST.LabelRef
|
||||
: AST.SymbolRef)({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
name : M.name
|
||||
|
|
@ -297,7 +222,7 @@ var AST_True = ast.AST_True;
|
|||
MOZ_TO_ME.UnaryExpression = function To_Moz_Unary(M) {
|
||||
var prefix = "prefix" in M ? M.prefix
|
||||
: M.type == "UnaryExpression" ? true : false;
|
||||
return new (prefix ? AST_UnaryPrefix : AST_UnaryPostfix)({
|
||||
return new (prefix ? AST.UnaryPrefix : AST.UnaryPostfix)({
|
||||
start : my_start_token(M),
|
||||
end : my_end_token(M),
|
||||
operator : M.operator,
|
||||
|
|
@ -305,37 +230,37 @@ var AST_True = ast.AST_True;
|
|||
});
|
||||
};
|
||||
|
||||
map("EmptyStatement", AST_EmptyStatement);
|
||||
map("BlockStatement", AST_BlockStatement, "body@body");
|
||||
map("IfStatement", AST_If, "test>condition, consequent>body, alternate>alternative");
|
||||
map("LabeledStatement", AST_LabeledStatement, "label>label, body>body");
|
||||
map("BreakStatement", AST_Break, "label>label");
|
||||
map("ContinueStatement", AST_Continue, "label>label");
|
||||
map("WithStatement", AST_With, "object>expression, body>body");
|
||||
map("SwitchStatement", AST_Switch, "discriminant>expression, cases@body");
|
||||
map("ReturnStatement", AST_Return, "argument>value");
|
||||
map("ThrowStatement", AST_Throw, "argument>value");
|
||||
map("WhileStatement", AST_While, "test>condition, body>body");
|
||||
map("DoWhileStatement", AST_Do, "test>condition, body>body");
|
||||
map("ForStatement", AST_For, "init>init, test>condition, update>step, body>body");
|
||||
map("ForInStatement", AST_ForIn, "left>init, right>object, body>body");
|
||||
map("DebuggerStatement", AST_Debugger);
|
||||
map("VariableDeclarator", AST_VarDef, "id>name, init>value");
|
||||
map("CatchClause", AST_Catch, "param>argname, body%body");
|
||||
map("EmptyStatement", AST.EmptyStatement);
|
||||
map("BlockStatement", AST.BlockStatement, "body@body");
|
||||
map("IfStatement", AST.If, "test>condition, consequent>body, alternate>alternative");
|
||||
map("LabeledStatement", AST.LabeledStatement, "label>label, body>body");
|
||||
map("BreakStatement", AST.Break, "label>label");
|
||||
map("ContinueStatement", AST.Continue, "label>label");
|
||||
map("WithStatement", AST.With, "object>expression, body>body");
|
||||
map("SwitchStatement", AST.Switch, "discriminant>expression, cases@body");
|
||||
map("ReturnStatement", AST.Return, "argument>value");
|
||||
map("ThrowStatement", AST.Throw, "argument>value");
|
||||
map("WhileStatement", AST.While, "test>condition, body>body");
|
||||
map("DoWhileStatement", AST.Do, "test>condition, body>body");
|
||||
map("ForStatement", AST.For, "init>init, test>condition, update>step, body>body");
|
||||
map("ForInStatement", AST.ForIn, "left>init, right>object, body>body");
|
||||
map("DebuggerStatement", AST.Debugger);
|
||||
map("VariableDeclarator", AST.VarDef, "id>name, init>value");
|
||||
map("CatchClause", AST.Catch, "param>argname, body%body");
|
||||
|
||||
map("ThisExpression", AST_This);
|
||||
map("BinaryExpression", AST_Binary, "operator=operator, left>left, right>right");
|
||||
map("LogicalExpression", AST_Binary, "operator=operator, left>left, right>right");
|
||||
map("AssignmentExpression", AST_Assign, "operator=operator, left>left, right>right");
|
||||
map("ConditionalExpression", AST_Conditional, "test>condition, consequent>consequent, alternate>alternative");
|
||||
map("NewExpression", AST_New, "callee>expression, arguments@args");
|
||||
map("CallExpression", AST_Call, "callee>expression, arguments@args");
|
||||
map("ThisExpression", AST.This);
|
||||
map("BinaryExpression", AST.Binary, "operator=operator, left>left, right>right");
|
||||
map("LogicalExpression", AST.Binary, "operator=operator, left>left, right>right");
|
||||
map("AssignmentExpression", AST.Assign, "operator=operator, left>left, right>right");
|
||||
map("ConditionalExpression", AST.Conditional, "test>condition, consequent>consequent, alternate>alternative");
|
||||
map("NewExpression", AST.New, "callee>expression, arguments@args");
|
||||
map("CallExpression", AST.Call, "callee>expression, arguments@args");
|
||||
|
||||
def_to_moz(AST_Toplevel, function To_Moz_Program(M) {
|
||||
def_to_moz(AST.Toplevel, function To_Moz_Program(M) {
|
||||
return to_moz_scope("Program", M);
|
||||
});
|
||||
|
||||
def_to_moz(AST_Defun, function To_Moz_FunctionDeclaration(M) {
|
||||
def_to_moz(AST.Defun, function To_Moz_FunctionDeclaration(M) {
|
||||
return {
|
||||
type: "FunctionDeclaration",
|
||||
id: to_moz(M.name),
|
||||
|
|
@ -344,7 +269,7 @@ var AST_True = ast.AST_True;
|
|||
}
|
||||
});
|
||||
|
||||
def_to_moz(AST_Function, function To_Moz_FunctionExpression(M) {
|
||||
def_to_moz(AST.Function, function To_Moz_FunctionExpression(M) {
|
||||
return {
|
||||
type: "FunctionExpression",
|
||||
id: to_moz(M.name),
|
||||
|
|
@ -353,7 +278,7 @@ var AST_True = ast.AST_True;
|
|||
}
|
||||
});
|
||||
|
||||
def_to_moz(AST_Directive, function To_Moz_Directive(M) {
|
||||
def_to_moz(AST.Directive, function To_Moz_Directive(M) {
|
||||
return {
|
||||
type: "ExpressionStatement",
|
||||
expression: {
|
||||
|
|
@ -363,14 +288,14 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_SimpleStatement, function To_Moz_ExpressionStatement(M) {
|
||||
def_to_moz(AST.SimpleStatement, function To_Moz_ExpressionStatement(M) {
|
||||
return {
|
||||
type: "ExpressionStatement",
|
||||
expression: to_moz(M.body)
|
||||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_SwitchBranch, function To_Moz_SwitchCase(M) {
|
||||
def_to_moz(AST.SwitchBranch, function To_Moz_SwitchCase(M) {
|
||||
return {
|
||||
type: "SwitchCase",
|
||||
test: to_moz(M.expression),
|
||||
|
|
@ -378,7 +303,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Try, function To_Moz_TryStatement(M) {
|
||||
def_to_moz(AST.Try, function To_Moz_TryStatement(M) {
|
||||
return {
|
||||
type: "TryStatement",
|
||||
block: to_moz_block(M),
|
||||
|
|
@ -388,7 +313,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Catch, function To_Moz_CatchClause(M) {
|
||||
def_to_moz(AST.Catch, function To_Moz_CatchClause(M) {
|
||||
return {
|
||||
type: "CatchClause",
|
||||
param: to_moz(M.argname),
|
||||
|
|
@ -397,7 +322,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Definitions, function To_Moz_VariableDeclaration(M) {
|
||||
def_to_moz(AST.Definitions, function To_Moz_VariableDeclaration(M) {
|
||||
return {
|
||||
type: "VariableDeclaration",
|
||||
kind: "var",
|
||||
|
|
@ -405,15 +330,15 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Sequence, function To_Moz_SequenceExpression(M) {
|
||||
def_to_moz(AST.Sequence, function To_Moz_SequenceExpression(M) {
|
||||
return {
|
||||
type: "SequenceExpression",
|
||||
expressions: M.expressions.map(to_moz)
|
||||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_PropAccess, function To_Moz_MemberExpression(M) {
|
||||
var isComputed = M instanceof AST_Sub;
|
||||
def_to_moz(AST.PropAccess, function To_Moz_MemberExpression(M) {
|
||||
var isComputed = M instanceof AST.Sub;
|
||||
return {
|
||||
type: "MemberExpression",
|
||||
object: to_moz(M.expression),
|
||||
|
|
@ -422,16 +347,16 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Unary, function To_Moz_Unary(M) {
|
||||
def_to_moz(AST.Unary, function To_Moz_Unary(M) {
|
||||
return {
|
||||
type: M.operator == "++" || M.operator == "--" ? "UpdateExpression" : "UnaryExpression",
|
||||
operator: M.operator,
|
||||
prefix: M instanceof AST_UnaryPrefix,
|
||||
prefix: M instanceof AST.UnaryPrefix,
|
||||
argument: to_moz(M.expression)
|
||||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Binary, function To_Moz_BinaryExpression(M) {
|
||||
def_to_moz(AST.Binary, function To_Moz_BinaryExpression(M) {
|
||||
return {
|
||||
type: M.operator == "&&" || M.operator == "||" ? "LogicalExpression" : "BinaryExpression",
|
||||
left: to_moz(M.left),
|
||||
|
|
@ -440,33 +365,33 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Array, function To_Moz_ArrayExpression(M) {
|
||||
def_to_moz(AST.Array, function To_Moz_ArrayExpression(M) {
|
||||
return {
|
||||
type: "ArrayExpression",
|
||||
elements: M.elements.map(to_moz)
|
||||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Object, function To_Moz_ObjectExpression(M) {
|
||||
def_to_moz(AST.Object, function To_Moz_ObjectExpression(M) {
|
||||
return {
|
||||
type: "ObjectExpression",
|
||||
properties: M.properties.map(to_moz)
|
||||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_ObjectProperty, function To_Moz_Property(M) {
|
||||
def_to_moz(AST.ObjectProperty, function To_Moz_Property(M) {
|
||||
var key = {
|
||||
type: "Literal",
|
||||
value: M.key instanceof AST_SymbolAccessor ? M.key.name : M.key
|
||||
value: M.key instanceof AST.SymbolAccessor ? M.key.name : M.key
|
||||
};
|
||||
var kind;
|
||||
if (M instanceof AST_ObjectKeyVal) {
|
||||
if (M instanceof AST.ObjectKeyVal) {
|
||||
kind = "init";
|
||||
} else
|
||||
if (M instanceof AST_ObjectGetter) {
|
||||
if (M instanceof AST.ObjectGetter) {
|
||||
kind = "get";
|
||||
} else
|
||||
if (M instanceof AST_ObjectSetter) {
|
||||
if (M instanceof AST.ObjectSetter) {
|
||||
kind = "set";
|
||||
}
|
||||
return {
|
||||
|
|
@ -477,7 +402,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Symbol, function To_Moz_Identifier(M) {
|
||||
def_to_moz(AST.Symbol, function To_Moz_Identifier(M) {
|
||||
var def = M.definition();
|
||||
return {
|
||||
type: "Identifier",
|
||||
|
|
@ -485,7 +410,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_RegExp, function To_Moz_RegExpLiteral(M) {
|
||||
def_to_moz(AST.RegExp, function To_Moz_RegExpLiteral(M) {
|
||||
var flags = M.value.toString().match(/[gimuy]*$/)[0];
|
||||
var value = "/" + M.value.raw_source + "/" + flags;
|
||||
return {
|
||||
|
|
@ -499,7 +424,7 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Constant, function To_Moz_Literal(M) {
|
||||
def_to_moz(AST.Constant, function To_Moz_Literal(M) {
|
||||
var value = M.value;
|
||||
if (typeof value === 'number' && (value < 0 || (value === 0 && 1 / value < 0))) {
|
||||
return {
|
||||
|
|
@ -520,19 +445,19 @@ var AST_True = ast.AST_True;
|
|||
};
|
||||
});
|
||||
|
||||
def_to_moz(AST_Atom, function To_Moz_Atom(M) {
|
||||
def_to_moz(AST.Atom, function To_Moz_Atom(M) {
|
||||
return {
|
||||
type: "Identifier",
|
||||
name: String(M.value)
|
||||
};
|
||||
});
|
||||
|
||||
AST_Boolean.DEFMETHOD("to_mozilla_ast", AST_Constant.prototype.to_mozilla_ast);
|
||||
AST_Null.DEFMETHOD("to_mozilla_ast", AST_Constant.prototype.to_mozilla_ast);
|
||||
AST_Hole.DEFMETHOD("to_mozilla_ast", function To_Moz_ArrayHole() { return null });
|
||||
AST.Boolean.DEFMETHOD("to_mozilla_ast", AST.Constant.prototype.to_mozilla_ast);
|
||||
AST.Null.DEFMETHOD("to_mozilla_ast", AST.Constant.prototype.to_mozilla_ast);
|
||||
AST.Hole.DEFMETHOD("to_mozilla_ast", function To_Moz_ArrayHole() { return null });
|
||||
|
||||
AST_Block.DEFMETHOD("to_mozilla_ast", AST_BlockStatement.prototype.to_mozilla_ast);
|
||||
AST_Lambda.DEFMETHOD("to_mozilla_ast", AST_Function.prototype.to_mozilla_ast);
|
||||
AST.Block.DEFMETHOD("to_mozilla_ast", AST.BlockStatement.prototype.to_mozilla_ast);
|
||||
AST.Lambda.DEFMETHOD("to_mozilla_ast", AST.Function.prototype.to_mozilla_ast);
|
||||
|
||||
/* -----[ tools ]----- */
|
||||
|
||||
|
|
@ -545,7 +470,7 @@ var AST_True = ast.AST_True;
|
|||
function my_start_token(moznode) {
|
||||
var loc = moznode.loc, start = loc && loc.start;
|
||||
var range = moznode.range;
|
||||
return new AST_Token({
|
||||
return new AST.Token({
|
||||
file : loc && loc.source,
|
||||
line : start && start.line,
|
||||
col : start && start.column,
|
||||
|
|
@ -560,7 +485,7 @@ var AST_True = ast.AST_True;
|
|||
function my_end_token(moznode) {
|
||||
var loc = moznode.loc, end = loc && loc.end;
|
||||
var range = moznode.range;
|
||||
return new AST_Token({
|
||||
return new AST.Token({
|
||||
file : loc && loc.source,
|
||||
line : end && end.line,
|
||||
col : end && end.column,
|
||||
|
|
@ -618,7 +543,7 @@ var AST_True = ast.AST_True;
|
|||
//console.log(moz_to_me);
|
||||
|
||||
moz_to_me = new Function("U2", "my_start_token", "my_end_token", "from_moz", "return(" + moz_to_me + ")")(
|
||||
ast, my_start_token, my_end_token, from_moz
|
||||
AST, my_start_token, my_end_token, from_moz
|
||||
);
|
||||
me_to_moz = new Function("to_moz", "to_moz_block", "to_moz_scope", "return(" + me_to_moz + ")")(
|
||||
to_moz, to_moz_block, to_moz_scope
|
||||
|
|
@ -636,16 +561,16 @@ var AST_True = ast.AST_True;
|
|||
return ret;
|
||||
}
|
||||
|
||||
AST_Node.from_mozilla_ast = function(node) {
|
||||
AST.Node.from_mozilla_ast = function(node) {
|
||||
var save_stack = FROM_MOZ_STACK;
|
||||
FROM_MOZ_STACK = [];
|
||||
var ast = from_moz(node);
|
||||
FROM_MOZ_STACK = save_stack;
|
||||
ast.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_LabelRef) {
|
||||
if (node instanceof AST.LabelRef) {
|
||||
for (var level = 0, parent; parent = this.parent(level); level++) {
|
||||
if (parent instanceof AST_Scope) break;
|
||||
if (parent instanceof AST_LabeledStatement && parent.label.name == node.name) {
|
||||
if (parent instanceof AST.Scope) break;
|
||||
if (parent instanceof AST.LabeledStatement && parent.label.name == node.name) {
|
||||
node.thedef = parent.label;
|
||||
break;
|
||||
}
|
||||
|
|
@ -696,8 +621,8 @@ var AST_True = ast.AST_True;
|
|||
|
||||
function to_moz_scope(type, node) {
|
||||
var body = node.body.map(to_moz);
|
||||
if (node.body[0] instanceof AST_SimpleStatement && node.body[0].body instanceof AST_String) {
|
||||
body.unshift(to_moz(new AST_EmptyStatement(node.body[0])));
|
||||
if (node.body[0] instanceof AST.SimpleStatement && node.body[0].body instanceof AST.String) {
|
||||
body.unshift(to_moz(new AST.EmptyStatement(node.body[0])));
|
||||
}
|
||||
return {
|
||||
type: type,
|
||||
|
|
|
|||
390
lib/output.js
390
lib/output.js
|
|
@ -53,69 +53,9 @@ var makePredicate = utils.makePredicate;
|
|||
var all = utils.all;
|
||||
var merge = utils.merge;
|
||||
|
||||
var ast = require("./ast");
|
||||
var first_in_statement = ast.first_in_statement;
|
||||
var TreeWalker = ast.TreeWalker;
|
||||
var AST_Node = ast.AST_Node;
|
||||
var AST_Statement = ast.AST_Statement;
|
||||
var AST_Debugger = ast.AST_Debugger;
|
||||
var AST_Directive = ast.AST_Directive;
|
||||
var AST_SimpleStatement = ast.AST_SimpleStatement;
|
||||
var AST_BlockStatement = ast.AST_BlockStatement;
|
||||
var AST_EmptyStatement = ast.AST_EmptyStatement;
|
||||
var AST_StatementWithBody = ast.AST_StatementWithBody;
|
||||
var AST_LabeledStatement = ast.AST_LabeledStatement;
|
||||
var AST_Do = ast.AST_Do;
|
||||
var AST_While = ast.AST_While;
|
||||
var AST_For = ast.AST_For;
|
||||
var AST_ForIn = ast.AST_ForIn;
|
||||
var AST_With = ast.AST_With;
|
||||
var AST_Scope = ast.AST_Scope;
|
||||
var AST_Toplevel = ast.AST_Toplevel;
|
||||
var AST_Lambda = ast.AST_Lambda;
|
||||
var AST_Function = ast.AST_Function;
|
||||
var AST_Jump = ast.AST_Jump;
|
||||
var AST_Exit = ast.AST_Exit;
|
||||
var AST_Return = ast.AST_Return;
|
||||
var AST_Throw = ast.AST_Throw;
|
||||
var AST_Break = ast.AST_Break;
|
||||
var AST_Continue = ast.AST_Continue;
|
||||
var AST_If = ast.AST_If;
|
||||
var AST_Switch = ast.AST_Switch;
|
||||
var AST_SwitchBranch = ast.AST_SwitchBranch;
|
||||
var AST_Default = ast.AST_Default;
|
||||
var AST_Case = ast.AST_Case;
|
||||
var AST_Try = ast.AST_Try;
|
||||
var AST_Catch = ast.AST_Catch;
|
||||
var AST_Finally = ast.AST_Finally;
|
||||
var AST_Definitions = ast.AST_Definitions;
|
||||
var AST_Var = ast.AST_Var;
|
||||
var AST_VarDef = ast.AST_VarDef;
|
||||
var AST_Call = ast.AST_Call;
|
||||
var AST_New = ast.AST_New;
|
||||
var AST_Sequence = ast.AST_Sequence;
|
||||
var AST_PropAccess = ast.AST_PropAccess;
|
||||
var AST_Dot = ast.AST_Dot;
|
||||
var AST_Sub = ast.AST_Sub;
|
||||
var AST_Unary = ast.AST_Unary;
|
||||
var AST_UnaryPrefix = ast.AST_UnaryPrefix;
|
||||
var AST_UnaryPostfix = ast.AST_UnaryPostfix;
|
||||
var AST_Binary = ast.AST_Binary;
|
||||
var AST_Conditional = ast.AST_Conditional;
|
||||
var AST_Assign = ast.AST_Assign;
|
||||
var AST_Array = ast.AST_Array;
|
||||
var AST_Object = ast.AST_Object;
|
||||
var AST_ObjectProperty = ast.AST_ObjectProperty;
|
||||
var AST_ObjectKeyVal = ast.AST_ObjectKeyVal;
|
||||
var AST_ObjectSetter = ast.AST_ObjectSetter;
|
||||
var AST_ObjectGetter = ast.AST_ObjectGetter;
|
||||
var AST_Symbol = ast.AST_Symbol;
|
||||
var AST_This = ast.AST_This;
|
||||
var AST_Constant = ast.AST_Constant;
|
||||
var AST_String = ast.AST_String;
|
||||
var AST_Number = ast.AST_Number;
|
||||
var AST_RegExp = ast.AST_RegExp;
|
||||
var AST_Hole = ast.AST_Hole;
|
||||
var AST = require("./ast");
|
||||
var first_in_statement = AST.first_in_statement;
|
||||
var TreeWalker = AST.TreeWalker;
|
||||
|
||||
var parse = require("./parse");
|
||||
var is_surrogate_pair_head = parse.is_surrogate_pair_head;
|
||||
|
|
@ -299,7 +239,7 @@ function OutputStream(options) {
|
|||
!mapping.name && mapping.token.type == "name" ? mapping.token.value : mapping.name
|
||||
);
|
||||
} catch(ex) {
|
||||
AST_Node.warn("Couldn't figure out mapping for {file}:{line},{col} → {cline},{ccol} [{name}]", {
|
||||
AST.Node.warn("Couldn't figure out mapping for {file}:{line},{col} → {cline},{ccol} [{name}]", {
|
||||
file: mapping.token.file,
|
||||
line: mapping.token.line,
|
||||
col: mapping.token.col,
|
||||
|
|
@ -330,7 +270,7 @@ function OutputStream(options) {
|
|||
current_col = right.length;
|
||||
}
|
||||
if (current_col > options.max_line_len) {
|
||||
AST_Node.warn("Output exceeds {max_line_len} characters", options);
|
||||
AST.Node.warn("Output exceeds {max_line_len} characters", options);
|
||||
}
|
||||
}
|
||||
if (might_add_newline) {
|
||||
|
|
@ -559,17 +499,17 @@ function OutputStream(options) {
|
|||
}
|
||||
comments._dumped = self;
|
||||
|
||||
if (node instanceof AST_Exit && node.value) {
|
||||
if (node instanceof AST.Exit && node.value) {
|
||||
var tw = new TreeWalker(function(node) {
|
||||
var parent = tw.parent();
|
||||
if (parent instanceof AST_Exit
|
||||
|| parent instanceof AST_Binary && parent.left === node
|
||||
if (parent instanceof AST.Exit
|
||||
|| parent instanceof AST.Binary && parent.left === node
|
||||
|| parent.TYPE == "Call" && parent.expression === node
|
||||
|| parent instanceof AST_Conditional && parent.condition === node
|
||||
|| parent instanceof AST_Dot && parent.expression === node
|
||||
|| parent instanceof AST_Sequence && parent.expressions[0] === node
|
||||
|| parent instanceof AST_Sub && parent.expression === node
|
||||
|| parent instanceof AST_UnaryPostfix) {
|
||||
|| parent instanceof AST.Conditional && parent.condition === node
|
||||
|| parent instanceof AST.Dot && parent.expression === node
|
||||
|| parent instanceof AST.Sequence && parent.expressions[0] === node
|
||||
|| parent instanceof AST.Sub && parent.expression === node
|
||||
|| parent instanceof AST.UnaryPostfix) {
|
||||
var text = node.start.comments_before;
|
||||
if (text && text._dumped !== self) {
|
||||
text._dumped = self;
|
||||
|
|
@ -632,7 +572,7 @@ function OutputStream(options) {
|
|||
if (!token) return;
|
||||
var comments = token[tail ? "comments_before" : "comments_after"];
|
||||
if (!comments || comments._dumped === self) return;
|
||||
if (!(node instanceof AST_Statement || all(comments, function(c) {
|
||||
if (!(node instanceof AST.Statement || all(comments, function(c) {
|
||||
return !/comment[134]/.test(c.type);
|
||||
}))) return;
|
||||
comments._dumped = self;
|
||||
|
|
@ -725,12 +665,12 @@ function OutputStream(options) {
|
|||
var active_scope = null;
|
||||
var use_asm = null;
|
||||
|
||||
AST_Node.DEFMETHOD("print", function(stream, force_parens) {
|
||||
AST.Node.DEFMETHOD("print", function(stream, force_parens) {
|
||||
var self = this, generator = self._codegen;
|
||||
if (self instanceof AST_Scope) {
|
||||
if (self instanceof AST.Scope) {
|
||||
active_scope = self;
|
||||
}
|
||||
else if (!use_asm && self instanceof AST_Directive && self.value == "use asm") {
|
||||
else if (!use_asm && self instanceof AST.Directive && self.value == "use asm") {
|
||||
use_asm = active_scope;
|
||||
}
|
||||
function doit() {
|
||||
|
|
@ -750,9 +690,9 @@ function OutputStream(options) {
|
|||
use_asm = null;
|
||||
}
|
||||
});
|
||||
AST_Node.DEFMETHOD("_print", AST_Node.prototype.print);
|
||||
AST.Node.DEFMETHOD("_print", AST.Node.prototype.print);
|
||||
|
||||
AST_Node.DEFMETHOD("print_to_string", function(options) {
|
||||
AST.Node.DEFMETHOD("print_to_string", function(options) {
|
||||
var s = OutputStream(options);
|
||||
this.print(s);
|
||||
return s.get();
|
||||
|
|
@ -770,25 +710,25 @@ function OutputStream(options) {
|
|||
}
|
||||
}
|
||||
|
||||
PARENS(AST_Node, return_false);
|
||||
PARENS(AST.Node, return_false);
|
||||
|
||||
// a function expression needs parens around it when it's provably
|
||||
// the first token to appear in a statement.
|
||||
PARENS(AST_Function, function(output) {
|
||||
PARENS(AST.Function, function(output) {
|
||||
if (!output.has_parens() && first_in_statement(output)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (output.option('webkit')) {
|
||||
var p = output.parent();
|
||||
if (p instanceof AST_PropAccess && p.expression === this) {
|
||||
if (p instanceof AST.PropAccess && p.expression === this) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (output.option('wrap_iife')) {
|
||||
var p = output.parent();
|
||||
return p instanceof AST_Call && p.expression === this;
|
||||
return p instanceof AST.Call && p.expression === this;
|
||||
}
|
||||
|
||||
return false;
|
||||
|
|
@ -796,43 +736,43 @@ function OutputStream(options) {
|
|||
|
||||
// same goes for an object literal, because otherwise it would be
|
||||
// interpreted as a block of code.
|
||||
PARENS(AST_Object, function(output) {
|
||||
PARENS(AST.Object, function(output) {
|
||||
return !output.has_parens() && first_in_statement(output);
|
||||
});
|
||||
|
||||
PARENS(AST_Unary, function(output) {
|
||||
PARENS(AST.Unary, function(output) {
|
||||
var p = output.parent();
|
||||
return p instanceof AST_PropAccess && p.expression === this
|
||||
|| p instanceof AST_Call && p.expression === this;
|
||||
return p instanceof AST.PropAccess && p.expression === this
|
||||
|| p instanceof AST.Call && p.expression === this;
|
||||
});
|
||||
|
||||
PARENS(AST_Sequence, function(output) {
|
||||
PARENS(AST.Sequence, function(output) {
|
||||
var p = output.parent();
|
||||
return p instanceof AST_Call // (foo, bar)() or foo(1, (2, 3), 4)
|
||||
|| p instanceof AST_Unary // !(foo, bar, baz)
|
||||
|| p instanceof AST_Binary // 1 + (2, 3) + 4 ==> 8
|
||||
|| p instanceof AST_VarDef // var a = (1, 2), b = a + a; ==> b == 4
|
||||
|| p instanceof AST_PropAccess // (1, {foo:2}).foo or (1, {foo:2})["foo"] ==> 2
|
||||
|| p instanceof AST_Array // [ 1, (2, 3), 4 ] ==> [ 1, 3, 4 ]
|
||||
|| p instanceof AST_ObjectProperty // { foo: (1, 2) }.foo ==> 2
|
||||
|| p instanceof AST_Conditional /* (false, true) ? (a = 10, b = 20) : (c = 30)
|
||||
return p instanceof AST.Call // (foo, bar)() or foo(1, (2, 3), 4)
|
||||
|| p instanceof AST.Unary // !(foo, bar, baz)
|
||||
|| p instanceof AST.Binary // 1 + (2, 3) + 4 ==> 8
|
||||
|| p instanceof AST.VarDef // var a = (1, 2), b = a + a; ==> b == 4
|
||||
|| p instanceof AST.PropAccess // (1, {foo:2}).foo or (1, {foo:2})["foo"] ==> 2
|
||||
|| p instanceof AST.Array // [ 1, (2, 3), 4 ] ==> [ 1, 3, 4 ]
|
||||
|| p instanceof AST.ObjectProperty // { foo: (1, 2) }.foo ==> 2
|
||||
|| p instanceof AST.Conditional /* (false, true) ? (a = 10, b = 20) : (c = 30)
|
||||
* ==> 20 (side effect, set a := 10 and b := 20) */
|
||||
;
|
||||
});
|
||||
|
||||
PARENS(AST_Binary, function(output) {
|
||||
PARENS(AST.Binary, function(output) {
|
||||
var p = output.parent();
|
||||
// (foo && bar)()
|
||||
if (p instanceof AST_Call && p.expression === this)
|
||||
if (p instanceof AST.Call && p.expression === this)
|
||||
return true;
|
||||
// typeof (foo && bar)
|
||||
if (p instanceof AST_Unary)
|
||||
if (p instanceof AST.Unary)
|
||||
return true;
|
||||
// (foo && bar)["prop"], (foo && bar).prop
|
||||
if (p instanceof AST_PropAccess && p.expression === this)
|
||||
if (p instanceof AST.PropAccess && p.expression === this)
|
||||
return true;
|
||||
// this deals with precedence: 3 * (2 + 1)
|
||||
if (p instanceof AST_Binary) {
|
||||
if (p instanceof AST.Binary) {
|
||||
var po = p.operator, pp = PRECEDENCE[po];
|
||||
var so = this.operator, sp = PRECEDENCE[so];
|
||||
if (pp > sp
|
||||
|
|
@ -843,9 +783,9 @@ function OutputStream(options) {
|
|||
}
|
||||
});
|
||||
|
||||
PARENS(AST_PropAccess, function(output) {
|
||||
PARENS(AST.PropAccess, function(output) {
|
||||
var p = output.parent();
|
||||
if (p instanceof AST_New && p.expression === this) {
|
||||
if (p instanceof AST.New && p.expression === this) {
|
||||
// i.e. new (foo.bar().baz)
|
||||
//
|
||||
// if there's one call into this subtree, then we need
|
||||
|
|
@ -854,8 +794,8 @@ function OutputStream(options) {
|
|||
// expression.
|
||||
var parens = false;
|
||||
this.walk(new TreeWalker(function(node) {
|
||||
if (parens || node instanceof AST_Scope) return true;
|
||||
if (node instanceof AST_Call) {
|
||||
if (parens || node instanceof AST.Scope) return true;
|
||||
if (node instanceof AST.Call) {
|
||||
parens = true;
|
||||
return true;
|
||||
}
|
||||
|
|
@ -864,31 +804,31 @@ function OutputStream(options) {
|
|||
}
|
||||
});
|
||||
|
||||
PARENS(AST_Call, function(output) {
|
||||
PARENS(AST.Call, function(output) {
|
||||
var p = output.parent(), p1;
|
||||
if (p instanceof AST_New && p.expression === this)
|
||||
if (p instanceof AST.New && p.expression === this)
|
||||
return true;
|
||||
|
||||
// workaround for Safari bug.
|
||||
// https://bugs.webkit.org/show_bug.cgi?id=123506
|
||||
return this.expression instanceof AST_Function
|
||||
&& p instanceof AST_PropAccess
|
||||
return this.expression instanceof AST.Function
|
||||
&& p instanceof AST.PropAccess
|
||||
&& p.expression === this
|
||||
&& (p1 = output.parent(1)) instanceof AST_Assign
|
||||
&& (p1 = output.parent(1)) instanceof AST.Assign
|
||||
&& p1.left === p;
|
||||
});
|
||||
|
||||
PARENS(AST_New, function(output) {
|
||||
PARENS(AST.New, function(output) {
|
||||
var p = output.parent();
|
||||
if (!need_constructor_parens(this, output)
|
||||
&& (p instanceof AST_PropAccess // (new Date).getTime(), (new Date)["getTime"]()
|
||||
|| p instanceof AST_Call && p.expression === this)) // (new foo)(bar)
|
||||
&& (p instanceof AST.PropAccess // (new Date).getTime(), (new Date)["getTime"]()
|
||||
|| p instanceof AST.Call && p.expression === this)) // (new foo)(bar)
|
||||
return true;
|
||||
});
|
||||
|
||||
PARENS(AST_Number, function(output) {
|
||||
PARENS(AST.Number, function(output) {
|
||||
var p = output.parent();
|
||||
if (p instanceof AST_PropAccess && p.expression === this) {
|
||||
if (p instanceof AST.PropAccess && p.expression === this) {
|
||||
var value = this.getValue();
|
||||
if (value < 0 || /^0/.test(make_num(value))) {
|
||||
return true;
|
||||
|
|
@ -896,32 +836,32 @@ function OutputStream(options) {
|
|||
}
|
||||
});
|
||||
|
||||
PARENS([ AST_Assign, AST_Conditional ], function(output) {
|
||||
PARENS([ AST.Assign, AST.Conditional ], function(output) {
|
||||
var p = output.parent();
|
||||
// !(a = false) → true
|
||||
if (p instanceof AST_Unary)
|
||||
if (p instanceof AST.Unary)
|
||||
return true;
|
||||
// 1 + (a = 2) + 3 → 6, side effect setting a = 2
|
||||
if (p instanceof AST_Binary && !(p instanceof AST_Assign))
|
||||
if (p instanceof AST.Binary && !(p instanceof AST.Assign))
|
||||
return true;
|
||||
// (a = func)() —or— new (a = Object)()
|
||||
if (p instanceof AST_Call && p.expression === this)
|
||||
if (p instanceof AST.Call && p.expression === this)
|
||||
return true;
|
||||
// (a = foo) ? bar : baz
|
||||
if (p instanceof AST_Conditional && p.condition === this)
|
||||
if (p instanceof AST.Conditional && p.condition === this)
|
||||
return true;
|
||||
// (a = foo)["prop"] —or— (a = foo).prop
|
||||
if (p instanceof AST_PropAccess && p.expression === this)
|
||||
if (p instanceof AST.PropAccess && p.expression === this)
|
||||
return true;
|
||||
});
|
||||
|
||||
/* -----[ PRINTERS ]----- */
|
||||
|
||||
DEFPRINT(AST_Directive, function(self, output) {
|
||||
DEFPRINT(AST.Directive, function(self, output) {
|
||||
output.print_string(self.value, self.quote);
|
||||
output.semicolon();
|
||||
});
|
||||
DEFPRINT(AST_Debugger, function(self, output) {
|
||||
DEFPRINT(AST.Debugger, function(self, output) {
|
||||
output.print("debugger");
|
||||
output.semicolon();
|
||||
});
|
||||
|
|
@ -932,13 +872,13 @@ function OutputStream(options) {
|
|||
var last = body.length - 1;
|
||||
in_directive = allow_directives;
|
||||
body.forEach(function(stmt, i) {
|
||||
if (in_directive === true && !(stmt instanceof AST_Directive ||
|
||||
stmt instanceof AST_EmptyStatement ||
|
||||
(stmt instanceof AST_SimpleStatement && stmt.body instanceof AST_String)
|
||||
if (in_directive === true && !(stmt instanceof AST.Directive ||
|
||||
stmt instanceof AST.EmptyStatement ||
|
||||
(stmt instanceof AST.SimpleStatement && stmt.body instanceof AST.String)
|
||||
)) {
|
||||
in_directive = false;
|
||||
}
|
||||
if (!(stmt instanceof AST_EmptyStatement)) {
|
||||
if (!(stmt instanceof AST.EmptyStatement)) {
|
||||
output.indent();
|
||||
stmt.print(output);
|
||||
if (!(i == last && is_toplevel)) {
|
||||
|
|
@ -947,8 +887,8 @@ function OutputStream(options) {
|
|||
}
|
||||
}
|
||||
if (in_directive === true &&
|
||||
stmt instanceof AST_SimpleStatement &&
|
||||
stmt.body instanceof AST_String
|
||||
stmt instanceof AST.SimpleStatement &&
|
||||
stmt.body instanceof AST.String
|
||||
) {
|
||||
in_directive = false;
|
||||
}
|
||||
|
|
@ -956,24 +896,24 @@ function OutputStream(options) {
|
|||
in_directive = false;
|
||||
}
|
||||
|
||||
AST_StatementWithBody.DEFMETHOD("_do_print_body", function(output) {
|
||||
AST.StatementWithBody.DEFMETHOD("_do_print_body", function(output) {
|
||||
force_statement(this.body, output);
|
||||
});
|
||||
|
||||
DEFPRINT(AST_Statement, function(self, output) {
|
||||
DEFPRINT(AST.Statement, function(self, output) {
|
||||
self.body.print(output);
|
||||
output.semicolon();
|
||||
});
|
||||
DEFPRINT(AST_Toplevel, function(self, output) {
|
||||
DEFPRINT(AST.Toplevel, function(self, output) {
|
||||
display_body(self.body, true, output, true);
|
||||
output.print("");
|
||||
});
|
||||
DEFPRINT(AST_LabeledStatement, function(self, output) {
|
||||
DEFPRINT(AST.LabeledStatement, function(self, output) {
|
||||
self.label.print(output);
|
||||
output.colon();
|
||||
self.body.print(output);
|
||||
});
|
||||
DEFPRINT(AST_SimpleStatement, function(self, output) {
|
||||
DEFPRINT(AST.SimpleStatement, function(self, output) {
|
||||
self.body.print(output);
|
||||
output.semicolon();
|
||||
});
|
||||
|
|
@ -991,13 +931,13 @@ function OutputStream(options) {
|
|||
});
|
||||
} else print_braced_empty(self, output);
|
||||
}
|
||||
DEFPRINT(AST_BlockStatement, function(self, output) {
|
||||
DEFPRINT(AST.BlockStatement, function(self, output) {
|
||||
print_braced(self, output);
|
||||
});
|
||||
DEFPRINT(AST_EmptyStatement, function(self, output) {
|
||||
DEFPRINT(AST.EmptyStatement, function(self, output) {
|
||||
output.semicolon();
|
||||
});
|
||||
DEFPRINT(AST_Do, function(self, output) {
|
||||
DEFPRINT(AST.Do, function(self, output) {
|
||||
output.print("do");
|
||||
output.space();
|
||||
make_block(self.body, output);
|
||||
|
|
@ -1009,7 +949,7 @@ function OutputStream(options) {
|
|||
});
|
||||
output.semicolon();
|
||||
});
|
||||
DEFPRINT(AST_While, function(self, output) {
|
||||
DEFPRINT(AST.While, function(self, output) {
|
||||
output.print("while");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1018,12 +958,12 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
self._do_print_body(output);
|
||||
});
|
||||
DEFPRINT(AST_For, function(self, output) {
|
||||
DEFPRINT(AST.For, function(self, output) {
|
||||
output.print("for");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
if (self.init) {
|
||||
if (self.init instanceof AST_Definitions) {
|
||||
if (self.init instanceof AST.Definitions) {
|
||||
self.init.print(output);
|
||||
} else {
|
||||
parenthesize_for_noin(self.init, output, true);
|
||||
|
|
@ -1047,7 +987,7 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
self._do_print_body(output);
|
||||
});
|
||||
DEFPRINT(AST_ForIn, function(self, output) {
|
||||
DEFPRINT(AST.ForIn, function(self, output) {
|
||||
output.print("for");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1060,7 +1000,7 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
self._do_print_body(output);
|
||||
});
|
||||
DEFPRINT(AST_With, function(self, output) {
|
||||
DEFPRINT(AST.With, function(self, output) {
|
||||
output.print("with");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1071,7 +1011,7 @@ function OutputStream(options) {
|
|||
});
|
||||
|
||||
/* -----[ functions ]----- */
|
||||
AST_Lambda.DEFMETHOD("_do_print", function(output, nokeyword) {
|
||||
AST.Lambda.DEFMETHOD("_do_print", function(output, nokeyword) {
|
||||
var self = this;
|
||||
if (!nokeyword) {
|
||||
output.print("function");
|
||||
|
|
@ -1089,7 +1029,7 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
print_braced(self, output, true);
|
||||
});
|
||||
DEFPRINT(AST_Lambda, function(self, output) {
|
||||
DEFPRINT(AST.Lambda, function(self, output) {
|
||||
self._do_print(output);
|
||||
});
|
||||
|
||||
|
|
@ -1103,16 +1043,16 @@ function OutputStream(options) {
|
|||
output.semicolon();
|
||||
}
|
||||
|
||||
DEFPRINT(AST_Return, function(self, output) {
|
||||
DEFPRINT(AST.Return, function(self, output) {
|
||||
print_jump(output, "return", self.value);
|
||||
});
|
||||
DEFPRINT(AST_Throw, function(self, output) {
|
||||
DEFPRINT(AST.Throw, function(self, output) {
|
||||
print_jump(output, "throw", self.value);
|
||||
});
|
||||
DEFPRINT(AST_Break, function(self, output) {
|
||||
DEFPRINT(AST.Break, function(self, output) {
|
||||
print_jump(output, "break", self.label);
|
||||
});
|
||||
DEFPRINT(AST_Continue, function(self, output) {
|
||||
DEFPRINT(AST.Continue, function(self, output) {
|
||||
print_jump(output, "continue", self.label);
|
||||
});
|
||||
|
||||
|
|
@ -1120,7 +1060,7 @@ function OutputStream(options) {
|
|||
function make_then(self, output) {
|
||||
var b = self.body;
|
||||
if (output.option("braces")
|
||||
|| output.option("ie8") && b instanceof AST_Do)
|
||||
|| output.option("ie8") && b instanceof AST.Do)
|
||||
return make_block(b, output);
|
||||
// The squeezer replaces "block"-s that contain only a single
|
||||
// statement with the statement itself; technically, the AST
|
||||
|
|
@ -1131,21 +1071,21 @@ function OutputStream(options) {
|
|||
// adds the block braces if needed.
|
||||
if (!b) return output.force_semicolon();
|
||||
while (true) {
|
||||
if (b instanceof AST_If) {
|
||||
if (b instanceof AST.If) {
|
||||
if (!b.alternative) {
|
||||
make_block(self.body, output);
|
||||
return;
|
||||
}
|
||||
b = b.alternative;
|
||||
}
|
||||
else if (b instanceof AST_StatementWithBody) {
|
||||
else if (b instanceof AST.StatementWithBody) {
|
||||
b = b.body;
|
||||
}
|
||||
else break;
|
||||
}
|
||||
force_statement(self.body, output);
|
||||
}
|
||||
DEFPRINT(AST_If, function(self, output) {
|
||||
DEFPRINT(AST.If, function(self, output) {
|
||||
output.print("if");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1157,7 +1097,7 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
output.print("else");
|
||||
output.space();
|
||||
if (self.alternative instanceof AST_If)
|
||||
if (self.alternative instanceof AST.If)
|
||||
self.alternative.print(output);
|
||||
else
|
||||
force_statement(self.alternative, output);
|
||||
|
|
@ -1167,7 +1107,7 @@ function OutputStream(options) {
|
|||
});
|
||||
|
||||
/* -----[ switch ]----- */
|
||||
DEFPRINT(AST_Switch, function(self, output) {
|
||||
DEFPRINT(AST.Switch, function(self, output) {
|
||||
output.print("switch");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1185,7 +1125,7 @@ function OutputStream(options) {
|
|||
});
|
||||
});
|
||||
});
|
||||
AST_SwitchBranch.DEFMETHOD("_do_print_body", function(output) {
|
||||
AST.SwitchBranch.DEFMETHOD("_do_print_body", function(output) {
|
||||
output.newline();
|
||||
this.body.forEach(function(stmt) {
|
||||
output.indent();
|
||||
|
|
@ -1193,11 +1133,11 @@ function OutputStream(options) {
|
|||
output.newline();
|
||||
});
|
||||
});
|
||||
DEFPRINT(AST_Default, function(self, output) {
|
||||
DEFPRINT(AST.Default, function(self, output) {
|
||||
output.print("default:");
|
||||
self._do_print_body(output);
|
||||
});
|
||||
DEFPRINT(AST_Case, function(self, output) {
|
||||
DEFPRINT(AST.Case, function(self, output) {
|
||||
output.print("case");
|
||||
output.space();
|
||||
self.expression.print(output);
|
||||
|
|
@ -1206,7 +1146,7 @@ function OutputStream(options) {
|
|||
});
|
||||
|
||||
/* -----[ exceptions ]----- */
|
||||
DEFPRINT(AST_Try, function(self, output) {
|
||||
DEFPRINT(AST.Try, function(self, output) {
|
||||
output.print("try");
|
||||
output.space();
|
||||
print_braced(self, output);
|
||||
|
|
@ -1219,7 +1159,7 @@ function OutputStream(options) {
|
|||
self.bfinally.print(output);
|
||||
}
|
||||
});
|
||||
DEFPRINT(AST_Catch, function(self, output) {
|
||||
DEFPRINT(AST.Catch, function(self, output) {
|
||||
output.print("catch");
|
||||
output.space();
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1228,13 +1168,13 @@ function OutputStream(options) {
|
|||
output.space();
|
||||
print_braced(self, output);
|
||||
});
|
||||
DEFPRINT(AST_Finally, function(self, output) {
|
||||
DEFPRINT(AST.Finally, function(self, output) {
|
||||
output.print("finally");
|
||||
output.space();
|
||||
print_braced(self, output);
|
||||
});
|
||||
|
||||
DEFPRINT(AST_Var, function(self, output) {
|
||||
DEFPRINT(AST.Var, function(self, output) {
|
||||
output.print("var");
|
||||
output.space();
|
||||
self.definitions.forEach(function(def, i) {
|
||||
|
|
@ -1242,7 +1182,7 @@ function OutputStream(options) {
|
|||
def.print(output);
|
||||
});
|
||||
var p = output.parent();
|
||||
if (p.init !== self || !(p instanceof AST_For || p instanceof AST_ForIn)) output.semicolon();
|
||||
if (p.init !== self || !(p instanceof AST.For || p instanceof AST.ForIn)) output.semicolon();
|
||||
});
|
||||
|
||||
function parenthesize_for_noin(node, output, noin) {
|
||||
|
|
@ -1250,8 +1190,8 @@ function OutputStream(options) {
|
|||
// need to take some precautions here:
|
||||
// https://github.com/mishoo/UglifyJS2/issues/60
|
||||
if (noin) node.walk(new TreeWalker(function(node) {
|
||||
if (parens || node instanceof AST_Scope) return true;
|
||||
if (node instanceof AST_Binary && node.operator == "in") {
|
||||
if (parens || node instanceof AST.Scope) return true;
|
||||
if (node instanceof AST.Binary && node.operator == "in") {
|
||||
parens = true;
|
||||
return true;
|
||||
}
|
||||
|
|
@ -1259,24 +1199,24 @@ function OutputStream(options) {
|
|||
node.print(output, parens);
|
||||
}
|
||||
|
||||
DEFPRINT(AST_VarDef, function(self, output) {
|
||||
DEFPRINT(AST.VarDef, function(self, output) {
|
||||
self.name.print(output);
|
||||
if (self.value) {
|
||||
output.space();
|
||||
output.print("=");
|
||||
output.space();
|
||||
var p = output.parent(1);
|
||||
var noin = p instanceof AST_For || p instanceof AST_ForIn;
|
||||
var noin = p instanceof AST.For || p instanceof AST.ForIn;
|
||||
parenthesize_for_noin(self.value, output, noin);
|
||||
}
|
||||
});
|
||||
|
||||
/* -----[ other expressions ]----- */
|
||||
DEFPRINT(AST_Call, function(self, output) {
|
||||
DEFPRINT(AST.Call, function(self, output) {
|
||||
self.expression.print(output);
|
||||
if (self instanceof AST_New && !need_constructor_parens(self, output))
|
||||
if (self instanceof AST.New && !need_constructor_parens(self, output))
|
||||
return;
|
||||
if (self.expression instanceof AST_Call || self.expression instanceof AST_Lambda) {
|
||||
if (self.expression instanceof AST.Call || self.expression instanceof AST.Lambda) {
|
||||
output.add_mapping(self.start);
|
||||
}
|
||||
output.with_parens(function() {
|
||||
|
|
@ -1286,12 +1226,12 @@ function OutputStream(options) {
|
|||
});
|
||||
});
|
||||
});
|
||||
DEFPRINT(AST_New, function(self, output) {
|
||||
DEFPRINT(AST.New, function(self, output) {
|
||||
output.print("new");
|
||||
output.space();
|
||||
AST_Call.prototype._codegen(self, output);
|
||||
AST.Call.prototype._codegen(self, output);
|
||||
});
|
||||
DEFPRINT(AST_Sequence, function(self, output) {
|
||||
DEFPRINT(AST.Sequence, function(self, output) {
|
||||
self.expressions.forEach(function(node, index) {
|
||||
if (index > 0) {
|
||||
output.comma();
|
||||
|
|
@ -1303,7 +1243,7 @@ function OutputStream(options) {
|
|||
node.print(output);
|
||||
});
|
||||
});
|
||||
DEFPRINT(AST_Dot, function(self, output) {
|
||||
DEFPRINT(AST.Dot, function(self, output) {
|
||||
var expr = self.expression;
|
||||
expr.print(output);
|
||||
var prop = self.property;
|
||||
|
|
@ -1313,7 +1253,7 @@ function OutputStream(options) {
|
|||
output.print_string(prop);
|
||||
output.print("]");
|
||||
} else {
|
||||
if (expr instanceof AST_Number && expr.getValue() >= 0) {
|
||||
if (expr instanceof AST.Number && expr.getValue() >= 0) {
|
||||
if (!/[xa-f.)]/i.test(output.last())) {
|
||||
output.print(".");
|
||||
}
|
||||
|
|
@ -1324,32 +1264,32 @@ function OutputStream(options) {
|
|||
output.print_name(prop);
|
||||
}
|
||||
});
|
||||
DEFPRINT(AST_Sub, function(self, output) {
|
||||
DEFPRINT(AST.Sub, function(self, output) {
|
||||
self.expression.print(output);
|
||||
output.print("[");
|
||||
self.property.print(output);
|
||||
output.print("]");
|
||||
});
|
||||
DEFPRINT(AST_UnaryPrefix, function(self, output) {
|
||||
DEFPRINT(AST.UnaryPrefix, function(self, output) {
|
||||
var op = self.operator;
|
||||
output.print(op);
|
||||
if (/^[a-z]/i.test(op)
|
||||
|| (/[+-]$/.test(op)
|
||||
&& self.expression instanceof AST_UnaryPrefix
|
||||
&& self.expression instanceof AST.UnaryPrefix
|
||||
&& /^[+-]/.test(self.expression.operator))) {
|
||||
output.space();
|
||||
}
|
||||
self.expression.print(output);
|
||||
});
|
||||
DEFPRINT(AST_UnaryPostfix, function(self, output) {
|
||||
DEFPRINT(AST.UnaryPostfix, function(self, output) {
|
||||
self.expression.print(output);
|
||||
output.print(self.operator);
|
||||
});
|
||||
DEFPRINT(AST_Binary, function(self, output) {
|
||||
DEFPRINT(AST.Binary, function(self, output) {
|
||||
var op = self.operator;
|
||||
self.left.print(output);
|
||||
if (op[0] == ">" /* ">>" ">>>" ">" ">=" */
|
||||
&& self.left instanceof AST_UnaryPostfix
|
||||
&& self.left instanceof AST.UnaryPostfix
|
||||
&& self.left.operator == "--") {
|
||||
// space is mandatory to avoid outputting -->
|
||||
output.print(" ");
|
||||
|
|
@ -1359,9 +1299,9 @@ function OutputStream(options) {
|
|||
}
|
||||
output.print(op);
|
||||
if ((op == "<" || op == "<<")
|
||||
&& self.right instanceof AST_UnaryPrefix
|
||||
&& self.right instanceof AST.UnaryPrefix
|
||||
&& self.right.operator == "!"
|
||||
&& self.right.expression instanceof AST_UnaryPrefix
|
||||
&& self.right.expression instanceof AST.UnaryPrefix
|
||||
&& self.right.expression.operator == "--") {
|
||||
// space is mandatory to avoid outputting <!--
|
||||
output.print(" ");
|
||||
|
|
@ -1371,7 +1311,7 @@ function OutputStream(options) {
|
|||
}
|
||||
self.right.print(output);
|
||||
});
|
||||
DEFPRINT(AST_Conditional, function(self, output) {
|
||||
DEFPRINT(AST.Conditional, function(self, output) {
|
||||
self.condition.print(output);
|
||||
output.space();
|
||||
output.print("?");
|
||||
|
|
@ -1383,7 +1323,7 @@ function OutputStream(options) {
|
|||
});
|
||||
|
||||
/* -----[ literals ]----- */
|
||||
DEFPRINT(AST_Array, function(self, output) {
|
||||
DEFPRINT(AST.Array, function(self, output) {
|
||||
output.with_square(function() {
|
||||
var a = self.elements, len = a.length;
|
||||
if (len > 0) output.space();
|
||||
|
|
@ -1393,13 +1333,13 @@ function OutputStream(options) {
|
|||
// If the final element is a hole, we need to make sure it
|
||||
// doesn't look like a trailing comma, by inserting an actual
|
||||
// trailing comma.
|
||||
if (i === len - 1 && exp instanceof AST_Hole)
|
||||
if (i === len - 1 && exp instanceof AST.Hole)
|
||||
output.comma();
|
||||
});
|
||||
if (len > 0) output.space();
|
||||
});
|
||||
});
|
||||
DEFPRINT(AST_Object, function(self, output) {
|
||||
DEFPRINT(AST.Object, function(self, output) {
|
||||
if (self.properties.length > 0) output.with_block(function() {
|
||||
self.properties.forEach(function(prop, i) {
|
||||
if (i) {
|
||||
|
|
@ -1430,38 +1370,38 @@ function OutputStream(options) {
|
|||
}
|
||||
}
|
||||
|
||||
DEFPRINT(AST_ObjectKeyVal, function(self, output) {
|
||||
DEFPRINT(AST.ObjectKeyVal, function(self, output) {
|
||||
print_property_name(self.key, self.quote, output);
|
||||
output.colon();
|
||||
self.value.print(output);
|
||||
});
|
||||
AST_ObjectProperty.DEFMETHOD("_print_getter_setter", function(type, output) {
|
||||
AST.ObjectProperty.DEFMETHOD("_print_getter_setter", function(type, output) {
|
||||
output.print(type);
|
||||
output.space();
|
||||
print_property_name(this.key.name, this.quote, output);
|
||||
this.value._do_print(output, true);
|
||||
});
|
||||
DEFPRINT(AST_ObjectSetter, function(self, output) {
|
||||
DEFPRINT(AST.ObjectSetter, function(self, output) {
|
||||
self._print_getter_setter("set", output);
|
||||
});
|
||||
DEFPRINT(AST_ObjectGetter, function(self, output) {
|
||||
DEFPRINT(AST.ObjectGetter, function(self, output) {
|
||||
self._print_getter_setter("get", output);
|
||||
});
|
||||
DEFPRINT(AST_Symbol, function(self, output) {
|
||||
DEFPRINT(AST.Symbol, function(self, output) {
|
||||
var def = self.definition();
|
||||
output.print_name(def ? def.mangled_name || def.name : self.name);
|
||||
});
|
||||
DEFPRINT(AST_Hole, noop);
|
||||
DEFPRINT(AST_This, function(self, output) {
|
||||
DEFPRINT(AST.Hole, noop);
|
||||
DEFPRINT(AST.This, function(self, output) {
|
||||
output.print("this");
|
||||
});
|
||||
DEFPRINT(AST_Constant, function(self, output) {
|
||||
DEFPRINT(AST.Constant, function(self, output) {
|
||||
output.print(self.getValue());
|
||||
});
|
||||
DEFPRINT(AST_String, function(self, output) {
|
||||
DEFPRINT(AST.String, function(self, output) {
|
||||
output.print_string(self.getValue(), self.quote, in_directive);
|
||||
});
|
||||
DEFPRINT(AST_Number, function(self, output) {
|
||||
DEFPRINT(AST.Number, function(self, output) {
|
||||
if (use_asm && self.start && self.start.raw != null) {
|
||||
output.print(self.start.raw);
|
||||
} else {
|
||||
|
|
@ -1469,7 +1409,7 @@ function OutputStream(options) {
|
|||
}
|
||||
});
|
||||
|
||||
DEFPRINT(AST_RegExp, function(self, output) {
|
||||
DEFPRINT(AST.RegExp, function(self, output) {
|
||||
var regexp = self.getValue();
|
||||
var str = regexp.toString();
|
||||
if (regexp.raw_source) {
|
||||
|
|
@ -1478,7 +1418,7 @@ function OutputStream(options) {
|
|||
str = output.to_utf8(str);
|
||||
output.print(str);
|
||||
var p = output.parent();
|
||||
if (p instanceof AST_Binary && /^in/.test(p.operator) && p.left === self)
|
||||
if (p instanceof AST.Binary && /^in/.test(p.operator) && p.left === self)
|
||||
output.print(" ");
|
||||
});
|
||||
|
||||
|
|
@ -1486,14 +1426,14 @@ function OutputStream(options) {
|
|||
if (output.option("braces")) {
|
||||
make_block(stat, output);
|
||||
} else {
|
||||
if (!stat || stat instanceof AST_EmptyStatement)
|
||||
if (!stat || stat instanceof AST.EmptyStatement)
|
||||
output.force_semicolon();
|
||||
else
|
||||
stat.print(output);
|
||||
}
|
||||
}
|
||||
|
||||
// self should be AST_New. decide if we want to show parens or not.
|
||||
// self should be AST.New. decide if we want to show parens or not.
|
||||
function need_constructor_parens(self, output) {
|
||||
// Always print parentheses with arguments
|
||||
if (self.args.length > 0) return true;
|
||||
|
|
@ -1537,9 +1477,9 @@ function OutputStream(options) {
|
|||
}
|
||||
|
||||
function make_block(stmt, output) {
|
||||
if (!stmt || stmt instanceof AST_EmptyStatement)
|
||||
if (!stmt || stmt instanceof AST.EmptyStatement)
|
||||
output.print("{}");
|
||||
else if (stmt instanceof AST_BlockStatement)
|
||||
else if (stmt instanceof AST.BlockStatement)
|
||||
stmt.print(output);
|
||||
else output.with_block(function() {
|
||||
output.indent();
|
||||
|
|
@ -1559,44 +1499,44 @@ function OutputStream(options) {
|
|||
DEFMAP([
|
||||
// We could easily add info for ALL nodes, but it seems to me that
|
||||
// would be quite wasteful, hence this noop in the base class.
|
||||
AST_Node,
|
||||
AST.Node,
|
||||
// since the label symbol will mark it
|
||||
AST_LabeledStatement,
|
||||
AST_Toplevel,
|
||||
AST.LabeledStatement,
|
||||
AST.Toplevel,
|
||||
], noop);
|
||||
|
||||
// XXX: I'm not exactly sure if we need it for all of these nodes,
|
||||
// or if we should add even more.
|
||||
DEFMAP([
|
||||
AST_Array,
|
||||
AST_BlockStatement,
|
||||
AST_Catch,
|
||||
AST_Constant,
|
||||
AST_Debugger,
|
||||
AST_Definitions,
|
||||
AST_Directive,
|
||||
AST_Finally,
|
||||
AST_Jump,
|
||||
AST_Lambda,
|
||||
AST_New,
|
||||
AST_Object,
|
||||
AST_StatementWithBody,
|
||||
AST_Symbol,
|
||||
AST_Switch,
|
||||
AST_SwitchBranch,
|
||||
AST_Try,
|
||||
AST.Array,
|
||||
AST.BlockStatement,
|
||||
AST.Catch,
|
||||
AST.Constant,
|
||||
AST.Debugger,
|
||||
AST.Definitions,
|
||||
AST.Directive,
|
||||
AST.Finally,
|
||||
AST.Jump,
|
||||
AST.Lambda,
|
||||
AST.New,
|
||||
AST.Object,
|
||||
AST.StatementWithBody,
|
||||
AST.Symbol,
|
||||
AST.Switch,
|
||||
AST.SwitchBranch,
|
||||
AST.Try,
|
||||
], function(output) {
|
||||
output.add_mapping(this.start);
|
||||
});
|
||||
|
||||
DEFMAP([
|
||||
AST_ObjectGetter,
|
||||
AST_ObjectSetter,
|
||||
AST.ObjectGetter,
|
||||
AST.ObjectSetter,
|
||||
], function(output) {
|
||||
output.add_mapping(this.start, this.key.name);
|
||||
});
|
||||
|
||||
DEFMAP([ AST_ObjectProperty ], function(output) {
|
||||
DEFMAP([ AST.ObjectProperty ], function(output) {
|
||||
output.add_mapping(this.start, this.key);
|
||||
});
|
||||
})();
|
||||
|
|
|
|||
205
lib/parse.js
205
lib/parse.js
|
|
@ -54,72 +54,7 @@ var all = utils.all;
|
|||
var HOP = utils.HOP;
|
||||
var merge = utils.merge;
|
||||
|
||||
var ast = require("./ast");
|
||||
var AST_Token = ast.AST_Token;
|
||||
var AST_Debugger = ast.AST_Debugger;
|
||||
var AST_Directive = ast.AST_Directive;
|
||||
var AST_SimpleStatement = ast.AST_SimpleStatement;
|
||||
var AST_BlockStatement = ast.AST_BlockStatement;
|
||||
var AST_EmptyStatement = ast.AST_EmptyStatement;
|
||||
var AST_LabeledStatement = ast.AST_LabeledStatement;
|
||||
var AST_IterationStatement = ast.AST_IterationStatement;
|
||||
var AST_Do = ast.AST_Do;
|
||||
var AST_While = ast.AST_While;
|
||||
var AST_For = ast.AST_For;
|
||||
var AST_ForIn = ast.AST_ForIn;
|
||||
var AST_With = ast.AST_With;
|
||||
var AST_Toplevel = ast.AST_Toplevel;
|
||||
var AST_Lambda = ast.AST_Lambda;
|
||||
var AST_Accessor = ast.AST_Accessor;
|
||||
var AST_Function = ast.AST_Function;
|
||||
var AST_Defun = ast.AST_Defun;
|
||||
var AST_Return = ast.AST_Return;
|
||||
var AST_Throw = ast.AST_Throw;
|
||||
var AST_Break = ast.AST_Break;
|
||||
var AST_Continue = ast.AST_Continue;
|
||||
var AST_If = ast.AST_If;
|
||||
var AST_Switch = ast.AST_Switch;
|
||||
var AST_Default = ast.AST_Default;
|
||||
var AST_Case = ast.AST_Case;
|
||||
var AST_Try = ast.AST_Try;
|
||||
var AST_Catch = ast.AST_Catch;
|
||||
var AST_Finally = ast.AST_Finally;
|
||||
var AST_Var = ast.AST_Var;
|
||||
var AST_VarDef = ast.AST_VarDef;
|
||||
var AST_Call = ast.AST_Call;
|
||||
var AST_New = ast.AST_New;
|
||||
var AST_Sequence = ast.AST_Sequence;
|
||||
var AST_PropAccess = ast.AST_PropAccess;
|
||||
var AST_Dot = ast.AST_Dot;
|
||||
var AST_Sub = ast.AST_Sub;
|
||||
var AST_UnaryPrefix = ast.AST_UnaryPrefix;
|
||||
var AST_UnaryPostfix = ast.AST_UnaryPostfix;
|
||||
var AST_Binary = ast.AST_Binary;
|
||||
var AST_Conditional = ast.AST_Conditional;
|
||||
var AST_Assign = ast.AST_Assign;
|
||||
var AST_Array = ast.AST_Array;
|
||||
var AST_Object = ast.AST_Object;
|
||||
var AST_ObjectKeyVal = ast.AST_ObjectKeyVal;
|
||||
var AST_ObjectSetter = ast.AST_ObjectSetter;
|
||||
var AST_ObjectGetter = ast.AST_ObjectGetter;
|
||||
var AST_SymbolAccessor = ast.AST_SymbolAccessor;
|
||||
var AST_SymbolDeclaration = ast.AST_SymbolDeclaration;
|
||||
var AST_SymbolVar = ast.AST_SymbolVar;
|
||||
var AST_SymbolFunarg = ast.AST_SymbolFunarg;
|
||||
var AST_SymbolDefun = ast.AST_SymbolDefun;
|
||||
var AST_SymbolLambda = ast.AST_SymbolLambda;
|
||||
var AST_SymbolCatch = ast.AST_SymbolCatch;
|
||||
var AST_Label = ast.AST_Label;
|
||||
var AST_SymbolRef = ast.AST_SymbolRef;
|
||||
var AST_LabelRef = ast.AST_LabelRef;
|
||||
var AST_This = ast.AST_This;
|
||||
var AST_String = ast.AST_String;
|
||||
var AST_Number = ast.AST_Number;
|
||||
var AST_RegExp = ast.AST_RegExp;
|
||||
var AST_Null = ast.AST_Null;
|
||||
var AST_Hole = ast.AST_Hole;
|
||||
var AST_False = ast.AST_False;
|
||||
var AST_True = ast.AST_True;
|
||||
var AST = require("./ast");
|
||||
|
||||
var KEYWORDS = 'break case catch const continue debugger default delete do else finally for function if in instanceof new return switch throw try typeof var void while with';
|
||||
var KEYWORDS_ATOM = 'false null true';
|
||||
|
|
@ -399,7 +334,7 @@ function tokenizer($TEXT, filename, html5_comments, shebang) {
|
|||
ret.comments_after = S.comments_before = [];
|
||||
}
|
||||
S.newline_before = false;
|
||||
return new AST_Token(ret);
|
||||
return new AST.Token(ret);
|
||||
}
|
||||
|
||||
function skip_whitespace() {
|
||||
|
|
@ -910,7 +845,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
}
|
||||
var dir = S.in_directives, stat = simple_statement();
|
||||
return dir ? new AST_Directive(stat.body) : stat;
|
||||
return dir ? new AST.Directive(stat.body) : stat;
|
||||
case "num":
|
||||
case "regexp":
|
||||
case "operator":
|
||||
|
|
@ -925,7 +860,7 @@ function parse($TEXT, options) {
|
|||
case "punc":
|
||||
switch (S.token.value) {
|
||||
case "{":
|
||||
return new AST_BlockStatement({
|
||||
return new AST.BlockStatement({
|
||||
start : S.token,
|
||||
body : block_(),
|
||||
end : prev()
|
||||
|
|
@ -936,7 +871,7 @@ function parse($TEXT, options) {
|
|||
case ";":
|
||||
S.in_directives = false;
|
||||
next();
|
||||
return new AST_EmptyStatement();
|
||||
return new AST.EmptyStatement();
|
||||
default:
|
||||
unexpected();
|
||||
}
|
||||
|
|
@ -945,16 +880,16 @@ function parse($TEXT, options) {
|
|||
switch (S.token.value) {
|
||||
case "break":
|
||||
next();
|
||||
return break_cont(AST_Break);
|
||||
return break_cont(AST.Break);
|
||||
|
||||
case "continue":
|
||||
next();
|
||||
return break_cont(AST_Continue);
|
||||
return break_cont(AST.Continue);
|
||||
|
||||
case "debugger":
|
||||
next();
|
||||
semicolon();
|
||||
return new AST_Debugger();
|
||||
return new AST.Debugger();
|
||||
|
||||
case "do":
|
||||
next();
|
||||
|
|
@ -962,14 +897,14 @@ function parse($TEXT, options) {
|
|||
expect_token("keyword", "while");
|
||||
var condition = parenthesised();
|
||||
semicolon(true);
|
||||
return new AST_Do({
|
||||
return new AST.Do({
|
||||
body : body,
|
||||
condition : condition
|
||||
});
|
||||
|
||||
case "while":
|
||||
next();
|
||||
return new AST_While({
|
||||
return new AST.While({
|
||||
condition : parenthesised(),
|
||||
body : in_loop(statement)
|
||||
});
|
||||
|
|
@ -983,7 +918,7 @@ function parse($TEXT, options) {
|
|||
croak("In strict mode code, functions can only be declared at top level or immediately within another function.");
|
||||
}
|
||||
next();
|
||||
return function_(AST_Defun);
|
||||
return function_(AST.Defun);
|
||||
|
||||
case "if":
|
||||
next();
|
||||
|
|
@ -1000,13 +935,13 @@ function parse($TEXT, options) {
|
|||
value = expression(true);
|
||||
semicolon();
|
||||
}
|
||||
return new AST_Return({
|
||||
return new AST.Return({
|
||||
value: value
|
||||
});
|
||||
|
||||
case "switch":
|
||||
next();
|
||||
return new AST_Switch({
|
||||
return new AST.Switch({
|
||||
expression : parenthesised(),
|
||||
body : in_loop(switch_body_)
|
||||
});
|
||||
|
|
@ -1017,7 +952,7 @@ function parse($TEXT, options) {
|
|||
croak("Illegal newline after 'throw'");
|
||||
var value = expression(true);
|
||||
semicolon();
|
||||
return new AST_Throw({
|
||||
return new AST.Throw({
|
||||
value: value
|
||||
});
|
||||
|
||||
|
|
@ -1036,7 +971,7 @@ function parse($TEXT, options) {
|
|||
croak("Strict mode may not include a with statement");
|
||||
}
|
||||
next();
|
||||
return new AST_With({
|
||||
return new AST.With({
|
||||
expression : parenthesised(),
|
||||
body : statement()
|
||||
});
|
||||
|
|
@ -1046,7 +981,7 @@ function parse($TEXT, options) {
|
|||
});
|
||||
|
||||
function labeled_statement() {
|
||||
var label = as_symbol(AST_Label);
|
||||
var label = as_symbol(AST.Label);
|
||||
if (!all(S.labels, function(l) {
|
||||
return l.name != label.name;
|
||||
})) {
|
||||
|
|
@ -1060,29 +995,29 @@ function parse($TEXT, options) {
|
|||
S.labels.push(label);
|
||||
var stat = statement();
|
||||
S.labels.pop();
|
||||
if (!(stat instanceof AST_IterationStatement)) {
|
||||
if (!(stat instanceof AST.IterationStatement)) {
|
||||
// check for `continue` that refers to this label.
|
||||
// those should be reported as syntax errors.
|
||||
// https://github.com/mishoo/UglifyJS2/issues/287
|
||||
label.references.forEach(function(ref) {
|
||||
if (ref instanceof AST_Continue) {
|
||||
if (ref instanceof AST.Continue) {
|
||||
ref = ref.label.start;
|
||||
croak("Continue label `" + label.name + "` refers to non-IterationStatement.",
|
||||
ref.line, ref.col, ref.pos);
|
||||
}
|
||||
});
|
||||
}
|
||||
return new AST_LabeledStatement({ body: stat, label: label });
|
||||
return new AST.LabeledStatement({ body: stat, label: label });
|
||||
}
|
||||
|
||||
function simple_statement(tmp) {
|
||||
return new AST_SimpleStatement({ body: (tmp = expression(true), semicolon(), tmp) });
|
||||
return new AST.SimpleStatement({ body: (tmp = expression(true), semicolon(), tmp) });
|
||||
}
|
||||
|
||||
function break_cont(type) {
|
||||
var label = null, ldef;
|
||||
if (!can_insert_semicolon()) {
|
||||
label = as_symbol(AST_LabelRef, true);
|
||||
label = as_symbol(AST.LabelRef, true);
|
||||
}
|
||||
if (label != null) {
|
||||
ldef = find_if(function(l) {
|
||||
|
|
@ -1105,7 +1040,7 @@ function parse($TEXT, options) {
|
|||
? (next(), var_(true))
|
||||
: expression(true, true);
|
||||
if (is("operator", "in")) {
|
||||
if (init instanceof AST_Var) {
|
||||
if (init instanceof AST.Var) {
|
||||
if (init.definitions.length > 1)
|
||||
croak("Only one variable declaration allowed in for..in loop", init.start.line, init.start.col, init.start.pos);
|
||||
} else if (!is_assignable(init)) {
|
||||
|
|
@ -1124,7 +1059,7 @@ function parse($TEXT, options) {
|
|||
expect(";");
|
||||
var step = is("punc", ")") ? null : expression(true);
|
||||
expect(")");
|
||||
return new AST_For({
|
||||
return new AST.For({
|
||||
init : init,
|
||||
condition : test,
|
||||
step : step,
|
||||
|
|
@ -1135,7 +1070,7 @@ function parse($TEXT, options) {
|
|||
function for_in(init) {
|
||||
var obj = expression(true);
|
||||
expect(")");
|
||||
return new AST_ForIn({
|
||||
return new AST.ForIn({
|
||||
init : init,
|
||||
object : obj,
|
||||
body : in_loop(statement)
|
||||
|
|
@ -1143,17 +1078,17 @@ function parse($TEXT, options) {
|
|||
}
|
||||
|
||||
var function_ = function(ctor) {
|
||||
var in_statement = ctor === AST_Defun;
|
||||
var name = is("name") ? as_symbol(in_statement ? AST_SymbolDefun : AST_SymbolLambda) : null;
|
||||
var in_statement = ctor === AST.Defun;
|
||||
var name = is("name") ? as_symbol(in_statement ? AST.SymbolDefun : AST.SymbolLambda) : null;
|
||||
if (in_statement && !name)
|
||||
unexpected();
|
||||
if (name && ctor !== AST_Accessor && !(name instanceof AST_SymbolDeclaration))
|
||||
if (name && ctor !== AST.Accessor && !(name instanceof AST.SymbolDeclaration))
|
||||
unexpected(prev());
|
||||
expect("(");
|
||||
var argnames = [];
|
||||
for (var first = true; !is("punc", ")");) {
|
||||
if (first) first = false; else expect(",");
|
||||
argnames.push(as_symbol(AST_SymbolFunarg));
|
||||
argnames.push(as_symbol(AST.SymbolFunarg));
|
||||
}
|
||||
next();
|
||||
var loop = S.in_loop;
|
||||
|
|
@ -1185,7 +1120,7 @@ function parse($TEXT, options) {
|
|||
next();
|
||||
belse = statement();
|
||||
}
|
||||
return new AST_If({
|
||||
return new AST.If({
|
||||
condition : cond,
|
||||
body : body,
|
||||
alternative : belse
|
||||
|
|
@ -1211,7 +1146,7 @@ function parse($TEXT, options) {
|
|||
if (is("keyword", "case")) {
|
||||
if (branch) branch.end = prev();
|
||||
cur = [];
|
||||
branch = new AST_Case({
|
||||
branch = new AST.Case({
|
||||
start : (tmp = S.token, next(), tmp),
|
||||
expression : expression(true),
|
||||
body : cur
|
||||
|
|
@ -1222,7 +1157,7 @@ function parse($TEXT, options) {
|
|||
else if (is("keyword", "default")) {
|
||||
if (branch) branch.end = prev();
|
||||
cur = [];
|
||||
branch = new AST_Default({
|
||||
branch = new AST.Default({
|
||||
start : (tmp = S.token, next(), expect(":"), tmp),
|
||||
body : cur
|
||||
});
|
||||
|
|
@ -1244,9 +1179,9 @@ function parse($TEXT, options) {
|
|||
var start = S.token;
|
||||
next();
|
||||
expect("(");
|
||||
var name = as_symbol(AST_SymbolCatch);
|
||||
var name = as_symbol(AST.SymbolCatch);
|
||||
expect(")");
|
||||
bcatch = new AST_Catch({
|
||||
bcatch = new AST.Catch({
|
||||
start : start,
|
||||
argname : name,
|
||||
body : block_(),
|
||||
|
|
@ -1256,7 +1191,7 @@ function parse($TEXT, options) {
|
|||
if (is("keyword", "finally")) {
|
||||
var start = S.token;
|
||||
next();
|
||||
bfinally = new AST_Finally({
|
||||
bfinally = new AST.Finally({
|
||||
start : start,
|
||||
body : block_(),
|
||||
end : prev()
|
||||
|
|
@ -1264,7 +1199,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
if (!bcatch && !bfinally)
|
||||
croak("Missing catch/finally blocks");
|
||||
return new AST_Try({
|
||||
return new AST.Try({
|
||||
body : body,
|
||||
bcatch : bcatch,
|
||||
bfinally : bfinally
|
||||
|
|
@ -1274,9 +1209,9 @@ function parse($TEXT, options) {
|
|||
function vardefs(no_in) {
|
||||
var a = [];
|
||||
for (;;) {
|
||||
a.push(new AST_VarDef({
|
||||
a.push(new AST.VarDef({
|
||||
start : S.token,
|
||||
name : as_symbol(AST_SymbolVar),
|
||||
name : as_symbol(AST.SymbolVar),
|
||||
value : is("operator", "=") ? (next(), expression(false, no_in)) : null,
|
||||
end : prev()
|
||||
}));
|
||||
|
|
@ -1288,7 +1223,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
|
||||
var var_ = function(no_in) {
|
||||
return new AST_Var({
|
||||
return new AST.Var({
|
||||
start : prev(),
|
||||
definitions : vardefs(no_in),
|
||||
end : prev()
|
||||
|
|
@ -1305,7 +1240,7 @@ function parse($TEXT, options) {
|
|||
} else {
|
||||
args = [];
|
||||
}
|
||||
var call = new AST_New({
|
||||
var call = new AST.New({
|
||||
start : start,
|
||||
expression : newexp,
|
||||
args : args,
|
||||
|
|
@ -1319,13 +1254,13 @@ function parse($TEXT, options) {
|
|||
var tok = S.token, ret;
|
||||
switch (tok.type) {
|
||||
case "name":
|
||||
ret = _make_symbol(AST_SymbolRef);
|
||||
ret = _make_symbol(AST.SymbolRef);
|
||||
break;
|
||||
case "num":
|
||||
ret = new AST_Number({ start: tok, end: tok, value: tok.value });
|
||||
ret = new AST.Number({ start: tok, end: tok, value: tok.value });
|
||||
break;
|
||||
case "string":
|
||||
ret = new AST_String({
|
||||
ret = new AST.String({
|
||||
start : tok,
|
||||
end : tok,
|
||||
value : tok.value,
|
||||
|
|
@ -1333,18 +1268,18 @@ function parse($TEXT, options) {
|
|||
});
|
||||
break;
|
||||
case "regexp":
|
||||
ret = new AST_RegExp({ start: tok, end: tok, value: tok.value });
|
||||
ret = new AST.RegExp({ start: tok, end: tok, value: tok.value });
|
||||
break;
|
||||
case "atom":
|
||||
switch (tok.value) {
|
||||
case "false":
|
||||
ret = new AST_False({ start: tok, end: tok });
|
||||
ret = new AST.False({ start: tok, end: tok });
|
||||
break;
|
||||
case "true":
|
||||
ret = new AST_True({ start: tok, end: tok });
|
||||
ret = new AST.True({ start: tok, end: tok });
|
||||
break;
|
||||
case "null":
|
||||
ret = new AST_Null({ start: tok, end: tok });
|
||||
ret = new AST.Null({ start: tok, end: tok });
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
|
@ -1382,7 +1317,7 @@ function parse($TEXT, options) {
|
|||
[].push.apply(ex.end.comments_after, end.comments_after);
|
||||
end.comments_after = ex.end.comments_after;
|
||||
ex.end = end;
|
||||
if (ex instanceof AST_Call) mark_pure(ex);
|
||||
if (ex instanceof AST.Call) mark_pure(ex);
|
||||
return subscripts(ex, allow_calls);
|
||||
case "[":
|
||||
return subscripts(array_(), allow_calls);
|
||||
|
|
@ -1393,7 +1328,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
if (is("keyword", "function")) {
|
||||
next();
|
||||
var func = function_(AST_Function);
|
||||
var func = function_(AST.Function);
|
||||
func.start = start;
|
||||
func.end = prev();
|
||||
return subscripts(func, allow_calls);
|
||||
|
|
@ -1410,7 +1345,7 @@ function parse($TEXT, options) {
|
|||
if (first) first = false; else expect(",");
|
||||
if (allow_trailing_comma && is("punc", closing)) break;
|
||||
if (is("punc", ",") && allow_empty) {
|
||||
a.push(new AST_Hole({ start: S.token, end: S.token }));
|
||||
a.push(new AST.Hole({ start: S.token, end: S.token }));
|
||||
} else {
|
||||
a.push(expression(false));
|
||||
}
|
||||
|
|
@ -1421,13 +1356,13 @@ function parse($TEXT, options) {
|
|||
|
||||
var array_ = embed_tokens(function() {
|
||||
expect("[");
|
||||
return new AST_Array({
|
||||
return new AST.Array({
|
||||
elements: expr_list("]", !options.strict, true)
|
||||
});
|
||||
});
|
||||
|
||||
var create_accessor = embed_tokens(function() {
|
||||
return function_(AST_Accessor);
|
||||
return function_(AST.Accessor);
|
||||
});
|
||||
|
||||
var object_ = embed_tokens(function() {
|
||||
|
|
@ -1442,13 +1377,13 @@ function parse($TEXT, options) {
|
|||
var type = start.type;
|
||||
var name = as_property_name();
|
||||
if (type == "name" && !is("punc", ":")) {
|
||||
var key = new AST_SymbolAccessor({
|
||||
var key = new AST.SymbolAccessor({
|
||||
start: S.token,
|
||||
name: "" + as_property_name(),
|
||||
end: prev()
|
||||
});
|
||||
if (name == "get") {
|
||||
a.push(new AST_ObjectGetter({
|
||||
a.push(new AST.ObjectGetter({
|
||||
start : start,
|
||||
key : key,
|
||||
value : create_accessor(),
|
||||
|
|
@ -1457,7 +1392,7 @@ function parse($TEXT, options) {
|
|||
continue;
|
||||
}
|
||||
if (name == "set") {
|
||||
a.push(new AST_ObjectSetter({
|
||||
a.push(new AST.ObjectSetter({
|
||||
start : start,
|
||||
key : key,
|
||||
value : create_accessor(),
|
||||
|
|
@ -1467,7 +1402,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
}
|
||||
expect(":");
|
||||
a.push(new AST_ObjectKeyVal({
|
||||
a.push(new AST.ObjectKeyVal({
|
||||
start : start,
|
||||
quote : start.quote,
|
||||
key : "" + name,
|
||||
|
|
@ -1476,7 +1411,7 @@ function parse($TEXT, options) {
|
|||
}));
|
||||
}
|
||||
next();
|
||||
return new AST_Object({ properties: a });
|
||||
return new AST.Object({ properties: a });
|
||||
});
|
||||
|
||||
function as_property_name() {
|
||||
|
|
@ -1505,7 +1440,7 @@ function parse($TEXT, options) {
|
|||
|
||||
function _make_symbol(type) {
|
||||
var name = S.token.value;
|
||||
return new (name == "this" ? AST_This : type)({
|
||||
return new (name == "this" ? AST.This : type)({
|
||||
name : String(name),
|
||||
start : S.token,
|
||||
end : S.token
|
||||
|
|
@ -1523,7 +1458,7 @@ function parse($TEXT, options) {
|
|||
return null;
|
||||
}
|
||||
var sym = _make_symbol(type);
|
||||
if (S.input.has_directive("use strict") && sym instanceof AST_SymbolDeclaration) {
|
||||
if (S.input.has_directive("use strict") && sym instanceof AST.SymbolDeclaration) {
|
||||
strict_verify_symbol(sym);
|
||||
}
|
||||
next();
|
||||
|
|
@ -1547,7 +1482,7 @@ function parse($TEXT, options) {
|
|||
var start = expr.start;
|
||||
if (is("punc", ".")) {
|
||||
next();
|
||||
return subscripts(new AST_Dot({
|
||||
return subscripts(new AST.Dot({
|
||||
start : start,
|
||||
expression : expr,
|
||||
property : as_name(),
|
||||
|
|
@ -1558,7 +1493,7 @@ function parse($TEXT, options) {
|
|||
next();
|
||||
var prop = expression(true);
|
||||
expect("]");
|
||||
return subscripts(new AST_Sub({
|
||||
return subscripts(new AST.Sub({
|
||||
start : start,
|
||||
expression : expr,
|
||||
property : prop,
|
||||
|
|
@ -1567,7 +1502,7 @@ function parse($TEXT, options) {
|
|||
}
|
||||
if (allow_calls && is("punc", "(")) {
|
||||
next();
|
||||
var call = new AST_Call({
|
||||
var call = new AST.Call({
|
||||
start : start,
|
||||
expression : expr,
|
||||
args : expr_list(")"),
|
||||
|
|
@ -1584,14 +1519,14 @@ function parse($TEXT, options) {
|
|||
if (is("operator") && UNARY_PREFIX[start.value]) {
|
||||
next();
|
||||
handle_regexp();
|
||||
var ex = make_unary(AST_UnaryPrefix, start, maybe_unary(allow_calls));
|
||||
var ex = make_unary(AST.UnaryPrefix, start, maybe_unary(allow_calls));
|
||||
ex.start = start;
|
||||
ex.end = prev();
|
||||
return ex;
|
||||
}
|
||||
var val = expr_atom(allow_calls);
|
||||
while (is("operator") && UNARY_POSTFIX[S.token.value] && !has_newline_before(S.token)) {
|
||||
val = make_unary(AST_UnaryPostfix, S.token, val);
|
||||
val = make_unary(AST.UnaryPostfix, S.token, val);
|
||||
val.start = start;
|
||||
val.end = S.token;
|
||||
next();
|
||||
|
|
@ -1608,7 +1543,7 @@ function parse($TEXT, options) {
|
|||
croak("Invalid use of " + op + " operator", token.line, token.col, token.pos);
|
||||
break;
|
||||
case "delete":
|
||||
if (expr instanceof AST_SymbolRef && S.input.has_directive("use strict"))
|
||||
if (expr instanceof AST.SymbolRef && S.input.has_directive("use strict"))
|
||||
croak("Calling delete on expression not allowed in strict mode", expr.start.line, expr.start.col, expr.start.pos);
|
||||
break;
|
||||
}
|
||||
|
|
@ -1622,7 +1557,7 @@ function parse($TEXT, options) {
|
|||
if (prec != null && prec > min_prec) {
|
||||
next();
|
||||
var right = expr_op(maybe_unary(true), prec, no_in);
|
||||
return expr_op(new AST_Binary({
|
||||
return expr_op(new AST.Binary({
|
||||
start : left.start,
|
||||
left : left,
|
||||
operator : op,
|
||||
|
|
@ -1644,7 +1579,7 @@ function parse($TEXT, options) {
|
|||
next();
|
||||
var yes = expression(false);
|
||||
expect(":");
|
||||
return new AST_Conditional({
|
||||
return new AST.Conditional({
|
||||
start : start,
|
||||
condition : expr,
|
||||
consequent : yes,
|
||||
|
|
@ -1656,7 +1591,7 @@ function parse($TEXT, options) {
|
|||
};
|
||||
|
||||
function is_assignable(expr) {
|
||||
return expr instanceof AST_PropAccess || expr instanceof AST_SymbolRef;
|
||||
return expr instanceof AST.PropAccess || expr instanceof AST.SymbolRef;
|
||||
}
|
||||
|
||||
var maybe_assign = function(no_in) {
|
||||
|
|
@ -1665,7 +1600,7 @@ function parse($TEXT, options) {
|
|||
if (is("operator") && ASSIGNMENT[val]) {
|
||||
if (is_assignable(left)) {
|
||||
next();
|
||||
return new AST_Assign({
|
||||
return new AST.Assign({
|
||||
start : start,
|
||||
left : left,
|
||||
operator : val,
|
||||
|
|
@ -1687,7 +1622,7 @@ function parse($TEXT, options) {
|
|||
next();
|
||||
commas = true;
|
||||
}
|
||||
return exprs.length == 1 ? exprs[0] : new AST_Sequence({
|
||||
return exprs.length == 1 ? exprs[0] : new AST.Sequence({
|
||||
start : start,
|
||||
expressions : exprs,
|
||||
end : peek()
|
||||
|
|
@ -1718,7 +1653,7 @@ function parse($TEXT, options) {
|
|||
toplevel.body = toplevel.body.concat(body);
|
||||
toplevel.end = end;
|
||||
} else {
|
||||
toplevel = new AST_Toplevel({ start: start, body: body, end: end });
|
||||
toplevel = new AST.Toplevel({ start: start, body: body, end: end });
|
||||
}
|
||||
return toplevel;
|
||||
}();
|
||||
|
|
|
|||
|
|
@ -52,17 +52,9 @@ var merge = utils.merge;
|
|||
var scope = require("./scope");
|
||||
var base54 = scope.base54;
|
||||
|
||||
var ast = require("./ast");
|
||||
var TreeWalker = ast.TreeWalker;
|
||||
var TreeTransformer = ast.TreeTransformer;
|
||||
var AST_Call = ast.AST_Call;
|
||||
var AST_Sequence = ast.AST_Sequence;
|
||||
var AST_Dot = ast.AST_Dot;
|
||||
var AST_Sub = ast.AST_Sub;
|
||||
var AST_Conditional = ast.AST_Conditional;
|
||||
var AST_ObjectProperty = ast.AST_ObjectProperty;
|
||||
var AST_ObjectKeyVal = ast.AST_ObjectKeyVal;
|
||||
var AST_String = ast.AST_String;
|
||||
var AST = require("./ast");
|
||||
var TreeWalker = AST.TreeWalker;
|
||||
var TreeTransformer = AST.TreeTransformer;
|
||||
|
||||
function find_builtins(reserved) {
|
||||
// NaN will be included due to Number.NaN
|
||||
|
|
@ -94,9 +86,9 @@ function reserve_quoted_keys(ast, reserved) {
|
|||
}
|
||||
|
||||
ast.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_ObjectKeyVal && node.quote) {
|
||||
if (node instanceof AST.ObjectKeyVal && node.quote) {
|
||||
add(node.key);
|
||||
} else if (node instanceof AST_Sub) {
|
||||
} else if (node instanceof AST.Sub) {
|
||||
addStrings(node.property, add);
|
||||
}
|
||||
}));
|
||||
|
|
@ -104,11 +96,11 @@ function reserve_quoted_keys(ast, reserved) {
|
|||
|
||||
function addStrings(node, add) {
|
||||
node.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_Sequence) {
|
||||
if (node instanceof AST.Sequence) {
|
||||
addStrings(node.tail_node(), add);
|
||||
} else if (node instanceof AST_String) {
|
||||
} else if (node instanceof AST.String) {
|
||||
add(node.value);
|
||||
} else if (node instanceof AST_Conditional) {
|
||||
} else if (node instanceof AST.Conditional) {
|
||||
addStrings(node.consequent, add);
|
||||
addStrings(node.alternative, add);
|
||||
}
|
||||
|
|
@ -158,20 +150,20 @@ function mangle_properties(ast, options) {
|
|||
|
||||
// step 1: find candidates to mangle
|
||||
ast.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_ObjectKeyVal) {
|
||||
if (node instanceof AST.ObjectKeyVal) {
|
||||
add(node.key);
|
||||
}
|
||||
else if (node instanceof AST_ObjectProperty) {
|
||||
else if (node instanceof AST.ObjectProperty) {
|
||||
// setter or getter, since KeyVal is handled above
|
||||
add(node.key.name);
|
||||
}
|
||||
else if (node instanceof AST_Dot) {
|
||||
else if (node instanceof AST.Dot) {
|
||||
add(node.property);
|
||||
}
|
||||
else if (node instanceof AST_Sub) {
|
||||
else if (node instanceof AST.Sub) {
|
||||
addStrings(node.property, add);
|
||||
}
|
||||
else if (node instanceof AST_Call
|
||||
else if (node instanceof AST.Call
|
||||
&& node.expression.print_to_string() == "Object.defineProperty") {
|
||||
addStrings(node.args[1], add);
|
||||
}
|
||||
|
|
@ -179,20 +171,20 @@ function mangle_properties(ast, options) {
|
|||
|
||||
// step 2: transform the tree, renaming properties
|
||||
return ast.transform(new TreeTransformer(function(node) {
|
||||
if (node instanceof AST_ObjectKeyVal) {
|
||||
if (node instanceof AST.ObjectKeyVal) {
|
||||
node.key = mangle(node.key);
|
||||
}
|
||||
else if (node instanceof AST_ObjectProperty) {
|
||||
else if (node instanceof AST.ObjectProperty) {
|
||||
// setter or getter
|
||||
node.key.name = mangle(node.key.name);
|
||||
}
|
||||
else if (node instanceof AST_Dot) {
|
||||
else if (node instanceof AST.Dot) {
|
||||
node.property = mangle(node.property);
|
||||
}
|
||||
else if (!options.keep_quoted && node instanceof AST_Sub) {
|
||||
else if (!options.keep_quoted && node instanceof AST.Sub) {
|
||||
node.property = mangleStrings(node.property);
|
||||
}
|
||||
else if (node instanceof AST_Call
|
||||
else if (node instanceof AST.Call
|
||||
&& node.expression.print_to_string() == "Object.defineProperty") {
|
||||
node.args[1] = mangleStrings(node.args[1]);
|
||||
}
|
||||
|
|
@ -256,14 +248,14 @@ function mangle_properties(ast, options) {
|
|||
|
||||
function mangleStrings(node) {
|
||||
return node.transform(new TreeTransformer(function(node) {
|
||||
if (node instanceof AST_Sequence) {
|
||||
if (node instanceof AST.Sequence) {
|
||||
var last = node.expressions.length - 1;
|
||||
node.expressions[last] = mangleStrings(node.expressions[last]);
|
||||
}
|
||||
else if (node instanceof AST_String) {
|
||||
else if (node instanceof AST.String) {
|
||||
node.value = mangle(node.value);
|
||||
}
|
||||
else if (node instanceof AST_Conditional) {
|
||||
else if (node instanceof AST.Conditional) {
|
||||
node.consequent = mangleStrings(node.consequent);
|
||||
node.alternative = mangleStrings(node.alternative);
|
||||
}
|
||||
|
|
|
|||
166
lib/scope.js
166
lib/scope.js
|
|
@ -52,32 +52,8 @@ var makePredicate = utils.makePredicate;
|
|||
var Dictionary = utils.Dictionary;
|
||||
var merge = utils.merge;
|
||||
|
||||
var ast = require("./ast");
|
||||
var TreeWalker = ast.TreeWalker;
|
||||
var AST_Node = ast.AST_Node;
|
||||
var AST_LabeledStatement = ast.AST_LabeledStatement;
|
||||
var AST_With = ast.AST_With;
|
||||
var AST_Scope = ast.AST_Scope;
|
||||
var AST_Toplevel = ast.AST_Toplevel;
|
||||
var AST_Lambda = ast.AST_Lambda;
|
||||
var AST_Function = ast.AST_Function;
|
||||
var AST_Defun = ast.AST_Defun;
|
||||
var AST_LoopControl = ast.AST_LoopControl;
|
||||
var AST_Catch = ast.AST_Catch;
|
||||
var AST_Call = ast.AST_Call;
|
||||
var AST_Sequence = ast.AST_Sequence;
|
||||
var AST_Dot = ast.AST_Dot;
|
||||
var AST_Sub = ast.AST_Sub;
|
||||
var AST_Conditional = ast.AST_Conditional;
|
||||
var AST_Symbol = ast.AST_Symbol;
|
||||
var AST_SymbolVar = ast.AST_SymbolVar;
|
||||
var AST_SymbolFunarg = ast.AST_SymbolFunarg;
|
||||
var AST_SymbolDefun = ast.AST_SymbolDefun;
|
||||
var AST_SymbolLambda = ast.AST_SymbolLambda;
|
||||
var AST_SymbolCatch = ast.AST_SymbolCatch;
|
||||
var AST_Label = ast.AST_Label;
|
||||
var AST_SymbolRef = ast.AST_SymbolRef;
|
||||
var AST_String = ast.AST_String;
|
||||
var AST = require("./ast");
|
||||
var TreeWalker = AST.TreeWalker;
|
||||
|
||||
var parse = require("./parse");
|
||||
var is_identifier = parse.is_identifier;
|
||||
|
|
@ -107,8 +83,8 @@ SymbolDef.prototype = {
|
|||
|| this.undeclared
|
||||
|| !options.eval && this.scope.pinned()
|
||||
|| options.keep_fnames
|
||||
&& (this.orig[0] instanceof AST_SymbolLambda
|
||||
|| this.orig[0] instanceof AST_SymbolDefun);
|
||||
&& (this.orig[0] instanceof AST.SymbolLambda
|
||||
|| this.orig[0] instanceof AST.SymbolDefun);
|
||||
},
|
||||
mangle: function(options) {
|
||||
var cache = options.cache && options.cache.props;
|
||||
|
|
@ -131,7 +107,7 @@ SymbolDef.prototype = {
|
|||
}
|
||||
};
|
||||
|
||||
AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
||||
AST.Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
||||
options = defaults(options, {
|
||||
cache: null,
|
||||
ie8: false,
|
||||
|
|
@ -142,15 +118,15 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
var scope = self.parent_scope = null;
|
||||
var defun = null;
|
||||
var tw = new TreeWalker(function(node, descend) {
|
||||
if (node instanceof AST_Catch) {
|
||||
if (node instanceof AST.Catch) {
|
||||
var save_scope = scope;
|
||||
scope = new AST_Scope(node);
|
||||
scope = new AST.Scope(node);
|
||||
scope.init_scope_vars(save_scope);
|
||||
descend();
|
||||
scope = save_scope;
|
||||
return true;
|
||||
}
|
||||
if (node instanceof AST_Scope) {
|
||||
if (node instanceof AST.Scope) {
|
||||
node.init_scope_vars(scope);
|
||||
var save_scope = scope;
|
||||
var save_defun = defun;
|
||||
|
|
@ -160,30 +136,30 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
defun = save_defun;
|
||||
return true; // don't descend again in TreeWalker
|
||||
}
|
||||
if (node instanceof AST_With) {
|
||||
if (node instanceof AST.With) {
|
||||
for (var s = scope; s; s = s.parent_scope)
|
||||
s.uses_with = true;
|
||||
return;
|
||||
}
|
||||
if (node instanceof AST_Symbol) {
|
||||
if (node instanceof AST.Symbol) {
|
||||
node.scope = scope;
|
||||
}
|
||||
if (node instanceof AST_Label) {
|
||||
if (node instanceof AST.Label) {
|
||||
node.thedef = node;
|
||||
node.references = [];
|
||||
}
|
||||
if (node instanceof AST_SymbolLambda) {
|
||||
if (node instanceof AST.SymbolLambda) {
|
||||
defun.def_function(node, node.name == "arguments" ? undefined : defun);
|
||||
}
|
||||
else if (node instanceof AST_SymbolDefun) {
|
||||
else if (node instanceof AST.SymbolDefun) {
|
||||
// Careful here, the scope where this should be defined is
|
||||
// the parent scope. The reason is that we enter a new
|
||||
// scope when we encounter the AST_Defun node (which is
|
||||
// instanceof AST_Scope) but we get to the symbol a bit
|
||||
// scope when we encounter the AST.Defun node (which is
|
||||
// instanceof AST.Scope) but we get to the symbol a bit
|
||||
// later.
|
||||
(node.scope = defun.parent_scope).def_function(node, defun);
|
||||
}
|
||||
else if (node instanceof AST_SymbolVar) {
|
||||
else if (node instanceof AST.SymbolVar) {
|
||||
defun.def_variable(node, node.TYPE == "SymbolVar" ? null : undefined);
|
||||
if (defun !== scope) {
|
||||
node.mark_enclosed(options);
|
||||
|
|
@ -194,7 +170,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
node.reference(options);
|
||||
}
|
||||
}
|
||||
else if (node instanceof AST_SymbolCatch) {
|
||||
else if (node instanceof AST.SymbolCatch) {
|
||||
scope.def_variable(node).defun = defun;
|
||||
}
|
||||
});
|
||||
|
|
@ -203,13 +179,13 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
// pass 2: find back references and eval
|
||||
self.globals = new Dictionary();
|
||||
var tw = new TreeWalker(function(node, descend) {
|
||||
if (node instanceof AST_LoopControl && node.label) {
|
||||
if (node instanceof AST.LoopControl && node.label) {
|
||||
node.label.thedef.references.push(node);
|
||||
return true;
|
||||
}
|
||||
if (node instanceof AST_SymbolRef) {
|
||||
if (node instanceof AST.SymbolRef) {
|
||||
var name = node.name;
|
||||
if (name == "eval" && tw.parent() instanceof AST_Call) {
|
||||
if (name == "eval" && tw.parent() instanceof AST.Call) {
|
||||
for (var s = node.scope; s && !s.uses_eval; s = s.parent_scope) {
|
||||
s.uses_eval = true;
|
||||
}
|
||||
|
|
@ -217,7 +193,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
var sym = node.scope.find_variable(name);
|
||||
if (!sym) {
|
||||
sym = self.def_global(node);
|
||||
} else if (sym.scope instanceof AST_Lambda && name == "arguments") {
|
||||
} else if (sym.scope instanceof AST.Lambda && name == "arguments") {
|
||||
sym.scope.uses_arguments = true;
|
||||
}
|
||||
node.thedef = sym;
|
||||
|
|
@ -226,7 +202,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
}
|
||||
// ensure mangling works if catch reuses a scope variable
|
||||
var def;
|
||||
if (node instanceof AST_SymbolCatch && (def = node.definition().redefined())) {
|
||||
if (node instanceof AST.SymbolCatch && (def = node.definition().redefined())) {
|
||||
var s = node.scope;
|
||||
while (s) {
|
||||
push_uniq(s.enclosed, def);
|
||||
|
|
@ -240,7 +216,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
// pass 3: fix up any scoping issue with IE8
|
||||
if (options.ie8) {
|
||||
self.walk(new TreeWalker(function(node, descend) {
|
||||
if (node instanceof AST_SymbolCatch) {
|
||||
if (node instanceof AST.SymbolCatch) {
|
||||
var name = node.name;
|
||||
var refs = node.thedef.references;
|
||||
var scope = node.thedef.defun;
|
||||
|
|
@ -257,7 +233,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Toplevel.DEFMETHOD("def_global", function(node) {
|
||||
AST.Toplevel.DEFMETHOD("def_global", function(node) {
|
||||
var globals = this.globals, name = node.name;
|
||||
if (globals.has(name)) {
|
||||
return globals.get(name);
|
||||
|
|
@ -270,9 +246,9 @@ AST_Toplevel.DEFMETHOD("def_global", function(node) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Scope.DEFMETHOD("init_scope_vars", function(parent_scope) {
|
||||
this.variables = new Dictionary(); // map name to AST_SymbolVar (variables defined in this scope; includes functions)
|
||||
this.functions = new Dictionary(); // map name to AST_SymbolDefun (functions defined in this scope)
|
||||
AST.Scope.DEFMETHOD("init_scope_vars", function(parent_scope) {
|
||||
this.variables = new Dictionary(); // map name to AST.SymbolVar (variables defined in this scope; includes functions)
|
||||
this.functions = new Dictionary(); // map name to AST.SymbolDefun (functions defined in this scope)
|
||||
this.uses_with = false; // will be set to true if this or some nested scope uses the `with` statement
|
||||
this.uses_eval = false; // will be set to true if this or nested scope uses the global `eval`
|
||||
this.parent_scope = parent_scope; // the parent scope
|
||||
|
|
@ -280,17 +256,17 @@ AST_Scope.DEFMETHOD("init_scope_vars", function(parent_scope) {
|
|||
this.cname = -1; // the current index for mangling functions/variables
|
||||
});
|
||||
|
||||
AST_Lambda.DEFMETHOD("init_scope_vars", function() {
|
||||
AST_Scope.prototype.init_scope_vars.apply(this, arguments);
|
||||
AST.Lambda.DEFMETHOD("init_scope_vars", function() {
|
||||
AST.Scope.prototype.init_scope_vars.apply(this, arguments);
|
||||
this.uses_arguments = false;
|
||||
this.def_variable(new AST_SymbolFunarg({
|
||||
this.def_variable(new AST.SymbolFunarg({
|
||||
name: "arguments",
|
||||
start: this.start,
|
||||
end: this.end
|
||||
}));
|
||||
});
|
||||
|
||||
AST_Symbol.DEFMETHOD("mark_enclosed", function(options) {
|
||||
AST.Symbol.DEFMETHOD("mark_enclosed", function(options) {
|
||||
var def = this.definition();
|
||||
var s = this.scope;
|
||||
while (s) {
|
||||
|
|
@ -305,29 +281,29 @@ AST_Symbol.DEFMETHOD("mark_enclosed", function(options) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Symbol.DEFMETHOD("reference", function(options) {
|
||||
AST.Symbol.DEFMETHOD("reference", function(options) {
|
||||
this.definition().references.push(this);
|
||||
this.mark_enclosed(options);
|
||||
});
|
||||
|
||||
AST_Scope.DEFMETHOD("find_variable", function(name) {
|
||||
if (name instanceof AST_Symbol) name = name.name;
|
||||
AST.Scope.DEFMETHOD("find_variable", function(name) {
|
||||
if (name instanceof AST.Symbol) name = name.name;
|
||||
return this.variables.get(name)
|
||||
|| (this.parent_scope && this.parent_scope.find_variable(name));
|
||||
});
|
||||
|
||||
AST_Scope.DEFMETHOD("def_function", function(symbol, init) {
|
||||
AST.Scope.DEFMETHOD("def_function", function(symbol, init) {
|
||||
var def = this.def_variable(symbol, init);
|
||||
if (!def.init || def.init instanceof AST_Defun) def.init = init;
|
||||
if (!def.init || def.init instanceof AST.Defun) def.init = init;
|
||||
this.functions.set(symbol.name, def);
|
||||
return def;
|
||||
});
|
||||
|
||||
AST_Scope.DEFMETHOD("def_variable", function(symbol, init) {
|
||||
AST.Scope.DEFMETHOD("def_variable", function(symbol, init) {
|
||||
var def = this.variables.get(symbol.name);
|
||||
if (def) {
|
||||
def.orig.push(symbol);
|
||||
if (def.init && (def.scope !== symbol.scope || def.init instanceof AST_Function)) {
|
||||
if (def.init && (def.scope !== symbol.scope || def.init instanceof AST.Function)) {
|
||||
def.init = init;
|
||||
}
|
||||
} else {
|
||||
|
|
@ -357,7 +333,7 @@ function next_mangled_name(scope, options, def) {
|
|||
// #179, #326
|
||||
// in Safari strict mode, something like (function x(x){...}) is a syntax error;
|
||||
// a function expression's argument cannot shadow the function expression's name
|
||||
if (scope instanceof AST_Function && scope.name && def.orig[0] instanceof AST_SymbolFunarg) {
|
||||
if (scope instanceof AST.Function && scope.name && def.orig[0] instanceof AST.SymbolFunarg) {
|
||||
var tricky_def = scope.name.definition();
|
||||
// the function's mangled_name is null when keep_fnames is true
|
||||
names[tricky_def.mangled_name || tricky_def.name] = true;
|
||||
|
|
@ -389,29 +365,29 @@ function next_mangled_name(scope, options, def) {
|
|||
holes.push(scope.cname);
|
||||
}
|
||||
scope.names_in_use[name] = true;
|
||||
if (options.ie8 && def.orig[0] instanceof AST_SymbolLambda) {
|
||||
if (options.ie8 && def.orig[0] instanceof AST.SymbolLambda) {
|
||||
names_in_use(scope.parent_scope, options)[name] = true;
|
||||
}
|
||||
return name;
|
||||
}
|
||||
|
||||
AST_Symbol.DEFMETHOD("unmangleable", function(options) {
|
||||
AST.Symbol.DEFMETHOD("unmangleable", function(options) {
|
||||
var def = this.definition();
|
||||
return !def || def.unmangleable(options);
|
||||
});
|
||||
|
||||
// labels are always mangleable
|
||||
AST_Label.DEFMETHOD("unmangleable", return_false);
|
||||
AST.Label.DEFMETHOD("unmangleable", return_false);
|
||||
|
||||
AST_Symbol.DEFMETHOD("unreferenced", function() {
|
||||
AST.Symbol.DEFMETHOD("unreferenced", function() {
|
||||
return !this.definition().references.length && !this.scope.pinned();
|
||||
});
|
||||
|
||||
AST_Symbol.DEFMETHOD("definition", function() {
|
||||
AST.Symbol.DEFMETHOD("definition", function() {
|
||||
return this.thedef;
|
||||
});
|
||||
|
||||
AST_Symbol.DEFMETHOD("global", function() {
|
||||
AST.Symbol.DEFMETHOD("global", function() {
|
||||
return this.definition().global;
|
||||
});
|
||||
|
||||
|
|
@ -430,13 +406,13 @@ function _default_mangler_options(options) {
|
|||
return options;
|
||||
}
|
||||
|
||||
AST_Toplevel.DEFMETHOD("mangle_names", function(options) {
|
||||
AST.Toplevel.DEFMETHOD("mangle_names", function(options) {
|
||||
options = _default_mangler_options(options);
|
||||
|
||||
// We only need to mangle declaration nodes. Special logic wired
|
||||
// into the code generator will display the mangled name if it's
|
||||
// present (and for AST_SymbolRef-s it'll use the mangled name of
|
||||
// the AST_SymbolDeclaration that it points to).
|
||||
// present (and for AST.SymbolRef-s it'll use the mangled name of
|
||||
// the AST.SymbolDeclaration that it points to).
|
||||
var lname = -1;
|
||||
|
||||
if (options.cache && options.cache.props) {
|
||||
|
|
@ -448,28 +424,28 @@ AST_Toplevel.DEFMETHOD("mangle_names", function(options) {
|
|||
|
||||
var redefined = [];
|
||||
var tw = new TreeWalker(function(node, descend) {
|
||||
if (node instanceof AST_LabeledStatement) {
|
||||
// lname is incremented when we get to the AST_Label
|
||||
if (node instanceof AST.LabeledStatement) {
|
||||
// lname is incremented when we get to the AST.Label
|
||||
var save_nesting = lname;
|
||||
descend();
|
||||
lname = save_nesting;
|
||||
return true; // don't descend again in TreeWalker
|
||||
}
|
||||
if (node instanceof AST_Scope) {
|
||||
if (node instanceof AST.Scope) {
|
||||
descend();
|
||||
if (options.cache && node instanceof AST_Toplevel) {
|
||||
if (options.cache && node instanceof AST.Toplevel) {
|
||||
node.globals.each(mangle);
|
||||
}
|
||||
node.variables.each(mangle);
|
||||
return true;
|
||||
}
|
||||
if (node instanceof AST_Label) {
|
||||
if (node instanceof AST.Label) {
|
||||
var name;
|
||||
do name = base54(++lname); while (!is_identifier(name));
|
||||
node.mangled_name = name;
|
||||
return true;
|
||||
}
|
||||
if (!options.ie8 && node instanceof AST_Catch) {
|
||||
if (!options.ie8 && node instanceof AST.Catch) {
|
||||
var def = node.argname.definition();
|
||||
var redef = def.redefined();
|
||||
if (redef) {
|
||||
|
|
@ -497,14 +473,14 @@ AST_Toplevel.DEFMETHOD("mangle_names", function(options) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Toplevel.DEFMETHOD("find_colliding_names", function(options) {
|
||||
AST.Toplevel.DEFMETHOD("find_colliding_names", function(options) {
|
||||
var cache = options.cache && options.cache.props;
|
||||
var avoid = Object.create(null);
|
||||
options.reserved.forEach(to_avoid);
|
||||
this.globals.each(add_def);
|
||||
this.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_Scope) node.variables.each(add_def);
|
||||
if (node instanceof AST_SymbolCatch) add_def(node.definition());
|
||||
if (node instanceof AST.Scope) node.variables.each(add_def);
|
||||
if (node instanceof AST.SymbolCatch) add_def(node.definition());
|
||||
}));
|
||||
return avoid;
|
||||
|
||||
|
|
@ -520,7 +496,7 @@ AST_Toplevel.DEFMETHOD("find_colliding_names", function(options) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Toplevel.DEFMETHOD("expand_names", function(options) {
|
||||
AST.Toplevel.DEFMETHOD("expand_names", function(options) {
|
||||
base54.reset();
|
||||
base54.sort();
|
||||
options = _default_mangler_options(options);
|
||||
|
|
@ -528,8 +504,8 @@ AST_Toplevel.DEFMETHOD("expand_names", function(options) {
|
|||
var cname = 0;
|
||||
this.globals.each(rename);
|
||||
this.walk(new TreeWalker(function(node) {
|
||||
if (node instanceof AST_Scope) node.variables.each(rename);
|
||||
if (node instanceof AST_SymbolCatch) rename(node.definition());
|
||||
if (node instanceof AST.Scope) node.variables.each(rename);
|
||||
if (node instanceof AST.SymbolCatch) rename(node.definition());
|
||||
}));
|
||||
|
||||
function next_name() {
|
||||
|
|
@ -555,40 +531,40 @@ AST_Toplevel.DEFMETHOD("expand_names", function(options) {
|
|||
}
|
||||
});
|
||||
|
||||
AST_Node.DEFMETHOD("tail_node", return_this);
|
||||
AST_Sequence.DEFMETHOD("tail_node", function() {
|
||||
AST.Node.DEFMETHOD("tail_node", return_this);
|
||||
AST.Sequence.DEFMETHOD("tail_node", function() {
|
||||
return this.expressions[this.expressions.length - 1];
|
||||
});
|
||||
|
||||
AST_Toplevel.DEFMETHOD("compute_char_frequency", function(options) {
|
||||
AST.Toplevel.DEFMETHOD("compute_char_frequency", function(options) {
|
||||
options = _default_mangler_options(options);
|
||||
base54.reset();
|
||||
try {
|
||||
AST_Node.prototype.print = function(stream, force_parens) {
|
||||
AST.Node.prototype.print = function(stream, force_parens) {
|
||||
this._print(stream, force_parens);
|
||||
if (this instanceof AST_Symbol && !this.unmangleable(options)) {
|
||||
if (this instanceof AST.Symbol && !this.unmangleable(options)) {
|
||||
base54.consider(this.name, -1);
|
||||
} else if (options.properties) {
|
||||
if (this instanceof AST_Dot) {
|
||||
if (this instanceof AST.Dot) {
|
||||
base54.consider(this.property, -1);
|
||||
} else if (this instanceof AST_Sub) {
|
||||
} else if (this instanceof AST.Sub) {
|
||||
skip_string(this.property);
|
||||
}
|
||||
}
|
||||
};
|
||||
base54.consider(this.print_to_string(), 1);
|
||||
} finally {
|
||||
AST_Node.prototype.print = AST_Node.prototype._print;
|
||||
AST.Node.prototype.print = AST.Node.prototype._print;
|
||||
}
|
||||
base54.sort();
|
||||
|
||||
function skip_string(node) {
|
||||
if (node instanceof AST_String) {
|
||||
if (node instanceof AST.String) {
|
||||
base54.consider(node.value, -1);
|
||||
} else if (node instanceof AST_Conditional) {
|
||||
} else if (node instanceof AST.Conditional) {
|
||||
skip_string(node.consequent);
|
||||
skip_string(node.alternative);
|
||||
} else if (node instanceof AST_Sequence) {
|
||||
} else if (node instanceof AST.Sequence) {
|
||||
skip_string(node.tail_node());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -594,7 +594,7 @@ describe("bin/uglifyjs", function() {
|
|||
exec(command, function(err, stdout) {
|
||||
if (err) throw err;
|
||||
var ast = JSON.parse(stdout);
|
||||
assert.strictEqual(ast._class, "AST_Toplevel");
|
||||
assert.strictEqual(ast._class, "AST.Toplevel");
|
||||
assert.ok(Array.isArray(ast.body));
|
||||
done();
|
||||
});
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ describe("spidermonkey export/import sanity test", function() {
|
|||
var command = uglifyjs + " --self -cm --wrap SpiderUglify -o spidermonkey | " +
|
||||
uglifyjs + " -p spidermonkey -cm";
|
||||
|
||||
exec(command, function(err, stdout) {
|
||||
exec(command, {maxBuffer: 1024 * 300}, function(err, stdout) {
|
||||
if (err) throw err;
|
||||
|
||||
eval(stdout);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,4 @@
|
|||
var orig = require("../tools/node");
|
||||
// Get all AST-nodes
|
||||
orig.utils.merge(orig, orig.ast);
|
||||
orig.SourceMap = require("../lib/sourcemap").SourceMap;
|
||||
orig.base54 = orig.utils.base54;
|
||||
orig.defaults = orig.utils.defaults;
|
||||
|
|
|
|||
|
|
@ -38,9 +38,11 @@ UglifyJS.FILES.forEach(function(filepath){
|
|||
if (exportNames.length == 0)
|
||||
return;
|
||||
// Use (utils.)merge instead of Object.assign for (very) old node
|
||||
var exports = "merge(exports, {\n" + exportNames.map(function(name){
|
||||
return UglifyJS.string_template(' {name} : {name},', { name: name });
|
||||
}).join("\n") + "\n});";
|
||||
var exports = "merge(exports, {\n" + exportNames.map(
|
||||
name => UglifyJS.string_template(' {name} : {name},', { name: name })
|
||||
).concat(exportNames.filter(name => name.indexOf("AST_") == 0).map(
|
||||
name => UglifyJS.string_template(' {expName} : {name},', { expName: name.substr(4), name: name })
|
||||
)).join("\n") + "\n});";
|
||||
var imports = exportNames.map(function(name){
|
||||
return UglifyJS.string_template(UglifyJS.string_template('var {name} = {fn}.{name};', { name: name, fn: filename}));
|
||||
});
|
||||
|
|
|
|||
|
|
@ -17,22 +17,11 @@ var FILES = UglifyJS.FILES = [
|
|||
return require.resolve(file);
|
||||
});
|
||||
|
||||
/*new Function("MOZ_SourceMap", "exports", function() {
|
||||
var code = FILES.map(function(file) {
|
||||
return fs.readFileSync(file, "utf8");
|
||||
});
|
||||
code.push("exports.describe_ast = " + describe_ast.toString());
|
||||
return code.join("\n\n");
|
||||
}())(
|
||||
require("source-map"),
|
||||
UglifyJS
|
||||
);*/
|
||||
|
||||
var utils = require("../lib/utils");
|
||||
var output = require("../lib/output");
|
||||
var OutputStream = output.OutputStream;
|
||||
var minify = require("../lib/minify").minify;
|
||||
var ast = require("../lib/ast");
|
||||
var AST = require("../lib/ast");
|
||||
var compress = require("../lib/compress");
|
||||
var parse = require("../lib/parse");
|
||||
var propmangle = require("../lib/propmangle");
|
||||
|
|
@ -42,22 +31,28 @@ require("../lib/mozilla-ast");
|
|||
exports.utils = utils;
|
||||
exports.OutputStream = OutputStream;
|
||||
exports.minify = minify;
|
||||
exports.ast = ast;
|
||||
exports.AST = AST;
|
||||
exports.parser = parse;
|
||||
exports.parse = parse.parse;
|
||||
exports.Compressor = compress.Compressor;
|
||||
exports.Dictionary = utils.Dictionary;
|
||||
exports.TreeWalker = ast.TreeWalker;
|
||||
exports.TreeTransformer = ast.TreeTransformer;
|
||||
exports.TreeWalker = AST.TreeWalker;
|
||||
exports.TreeTransformer = AST.TreeTransformer;
|
||||
exports.push_uniq = utils.push_uniq;
|
||||
exports.string_template = utils.string_template;
|
||||
exports.describe_ast = describe_ast;
|
||||
exports.propmangle = propmangle;
|
||||
|
||||
// Backwards compatibility: Add all AST_
|
||||
for (var name in AST) if (utils.HOP(AST, name)) {
|
||||
if (name.indexOf("AST_") == 0)
|
||||
exports[name] = AST[name];
|
||||
}
|
||||
|
||||
function describe_ast() {
|
||||
var out = OutputStream({ beautify: true });
|
||||
function doitem(ctor) {
|
||||
out.print("AST_" + ctor.TYPE);
|
||||
out.print("AST." + ctor.TYPE);
|
||||
var props = ctor.SELF_PROPS.filter(function(prop) {
|
||||
return !/^\$/.test(prop);
|
||||
});
|
||||
|
|
@ -85,7 +80,7 @@ function describe_ast() {
|
|||
});
|
||||
}
|
||||
};
|
||||
doitem(AST_Node);
|
||||
doitem(AST.Node);
|
||||
return out + "\n";
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user