simplify AST (idea like)
This commit is contained in:
@@ -11,93 +11,92 @@ import com.google.dart.compiler.backend.js.ast.*;
|
||||
* normally be surrounded by parentheses.
|
||||
*/
|
||||
public class JsConstructExpressionVisitor extends JsVisitor {
|
||||
|
||||
public static boolean exec(JsExpression expression) {
|
||||
if (JsPrecedenceVisitor.exec(expression) < JsPrecedenceVisitor.PRECEDENCE_NEW) {
|
||||
return true;
|
||||
public static boolean exec(JsExpression expression) {
|
||||
if (JsPrecedenceVisitor.exec(expression) < JsPrecedenceVisitor.PRECEDENCE_NEW) {
|
||||
return true;
|
||||
}
|
||||
JsConstructExpressionVisitor visitor = new JsConstructExpressionVisitor();
|
||||
visitor.accept(expression);
|
||||
return visitor.containsInvocation;
|
||||
}
|
||||
JsConstructExpressionVisitor visitor = new JsConstructExpressionVisitor();
|
||||
visitor.accept(expression);
|
||||
return visitor.containsInvocation;
|
||||
}
|
||||
|
||||
private boolean containsInvocation = false;
|
||||
private boolean containsInvocation;
|
||||
|
||||
private JsConstructExpressionVisitor() {
|
||||
}
|
||||
|
||||
/**
|
||||
* We only look at the array expression since the index has its own scope.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsArrayAccess x, JsContext ctx) {
|
||||
accept(x.getArrayExpression());
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Array literals have their own scoping.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsArrayLiteral x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Functions have their own scoping.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsFunction x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsInvocation x, JsContext ctx) {
|
||||
containsInvocation = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNameRef x, JsContext ctx) {
|
||||
if (!x.isLeaf()) {
|
||||
accept(x.getQualifier());
|
||||
private JsConstructExpressionVisitor() {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* New constructs bind to the nearest set of parentheses.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsNew x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Object literals have their own scope.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsObjectLiteral x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* We only look at nodes that would not normally be surrounded by parentheses.
|
||||
*/
|
||||
@Override
|
||||
public <T extends JsVisitable> T accept(T node) {
|
||||
// Assign to Object to prevent 'inconvertible types' compile errors due
|
||||
// to http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6548436
|
||||
// reproducible in jdk1.6.0_02.
|
||||
if (node instanceof JsExpression) {
|
||||
JsExpression expression = (JsExpression) node;
|
||||
int precedence = JsPrecedenceVisitor.exec(expression);
|
||||
// Only visit expressions that won't automatically be surrounded by
|
||||
// parentheses
|
||||
if (precedence < JsPrecedenceVisitor.PRECEDENCE_NEW) {
|
||||
return node;
|
||||
}
|
||||
/**
|
||||
* We only look at the array expression since the index has its own scope.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsArrayAccess x, JsContext ctx) {
|
||||
accept(x.getArrayExpression());
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Array literals have their own scoping.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsArrayLiteral x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Functions have their own scoping.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsFunction x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsInvocation x, JsContext ctx) {
|
||||
containsInvocation = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNameRef x, JsContext ctx) {
|
||||
if (!x.isLeaf()) {
|
||||
accept(x.getQualifier());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* New constructs bind to the nearest set of parentheses.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsNew x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Object literals have their own scope.
|
||||
*/
|
||||
@Override
|
||||
public boolean visit(JsObjectLiteral x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* We only look at nodes that would not normally be surrounded by parentheses.
|
||||
*/
|
||||
@Override
|
||||
public <T extends JsNode> T accept(T node) {
|
||||
// Assign to Object to prevent 'inconvertible types' compile errors due
|
||||
// to http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6548436
|
||||
// reproducible in jdk1.6.0_02.
|
||||
if (node instanceof JsExpression) {
|
||||
JsExpression expression = (JsExpression) node;
|
||||
int precedence = JsPrecedenceVisitor.exec(expression);
|
||||
// Only visit expressions that won't automatically be surrounded by
|
||||
// parentheses
|
||||
if (precedence < JsPrecedenceVisitor.PRECEDENCE_NEW) {
|
||||
return node;
|
||||
}
|
||||
}
|
||||
return super.accept(node);
|
||||
}
|
||||
return super.accept(node);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -112,9 +112,4 @@ public class JsFirstExpressionVisitor extends JsVisitor {
|
||||
public boolean visit(JsPrefixOperation x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsRegExp x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10,271 +10,267 @@ import com.google.dart.compiler.backend.js.ast.JsVars.JsVar;
|
||||
/**
|
||||
* Precedence indices from "JavaScript - The Definitive Guide" 4th Edition (page
|
||||
* 57)
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 17 is for indivisible primaries that either don't have children,
|
||||
* or provide their own delimiters.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 16 is for really important things that have their own AST classes.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 15 is for the new construct.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 14 is for unary operators.
|
||||
*
|
||||
* <p/>
|
||||
* Precedences 12 through 4 are for non-assigning binary operators.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 3 is for the tertiary conditional.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 2 is for assignments.
|
||||
*
|
||||
* <p/>
|
||||
* Precedence 1 is for comma operations.
|
||||
*/
|
||||
class JsPrecedenceVisitor extends JsVisitor {
|
||||
static final int PRECEDENCE_NEW = 15;
|
||||
static final int PRECEDENCE_NEW = 15;
|
||||
|
||||
public static int exec(JsExpression expression) {
|
||||
JsPrecedenceVisitor visitor = new JsPrecedenceVisitor();
|
||||
visitor.accept(expression);
|
||||
if (visitor.answer < 0) {
|
||||
throw new RuntimeException("Precedence must be >= 0!");
|
||||
public static int exec(JsExpression expression) {
|
||||
JsPrecedenceVisitor visitor = new JsPrecedenceVisitor();
|
||||
visitor.accept(expression);
|
||||
if (visitor.answer < 0) {
|
||||
throw new RuntimeException("Precedence must be >= 0!");
|
||||
}
|
||||
return visitor.answer;
|
||||
}
|
||||
return visitor.answer;
|
||||
}
|
||||
|
||||
private int answer = -1;
|
||||
private int answer = -1;
|
||||
|
||||
private JsPrecedenceVisitor() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsArrayAccess x, JsContext ctx) {
|
||||
answer = 16;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsArrayLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsBinaryOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsBlock x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsLiteral.JsBooleanLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsBreak x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsCase x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsCatch x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsConditional x, JsContext ctx) {
|
||||
answer = 3;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsContinue x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsDebugger x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsDefault x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsDoWhile x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsEmpty x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsExpressionStatement x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsFor x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsForIn x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsFunction x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsIf x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsInvocation x, JsContext ctx) {
|
||||
answer = 16;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsLabel x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNameRef x, JsContext ctx) {
|
||||
if (x.isLeaf()) {
|
||||
answer = 17; // primary
|
||||
} else {
|
||||
answer = 16; // property access
|
||||
private JsPrecedenceVisitor() {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNew x, JsContext ctx) {
|
||||
answer = PRECEDENCE_NEW;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNullLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNumberLiteral.JsIntLiteral x, JsContext ctx) {
|
||||
public boolean visit(JsArrayAccess x, JsContext ctx) {
|
||||
answer = 16;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsArrayLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNumberLiteral.JsDoubleLiteral x, JsContext ctx) {
|
||||
public boolean visit(JsBinaryOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsBlock x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsLiteral.JsBooleanLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsObjectLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsBreak x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsParameter x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsCase x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPostfixOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsCatch x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPrefixOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsConditional x, JsContext ctx) {
|
||||
answer = 3;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsProgram x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsContinue x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPropertyInitializer x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsDebugger x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsRegExp x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsDefault x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsReturn x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsDoWhile x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsStringLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public void visit(JsEmpty x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsSwitch x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsExpressionStatement x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsLiteral.JsThisRef x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsFor x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsThrow x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsForIn x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsTry x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsFunction x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsVar x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsIf x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsVars x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsInvocation x, JsContext ctx) {
|
||||
answer = 16;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsWhile x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
@Override
|
||||
public boolean visit(JsLabel x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNameRef x, JsContext ctx) {
|
||||
if (x.isLeaf()) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
else {
|
||||
answer = 16; // property access
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNew x, JsContext ctx) {
|
||||
answer = PRECEDENCE_NEW;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(JsNullLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(JsNumberLiteral.JsIntLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(JsNumberLiteral.JsDoubleLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsObjectLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsParameter x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPostfixOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPrefixOperation x, JsContext ctx) {
|
||||
answer = x.getOperator().getPrecedence();
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsProgram x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsPropertyInitializer x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(JsRegExp x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsReturn x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(JsStringLiteral x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsSwitch x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsLiteral.JsThisRef x, JsContext ctx) {
|
||||
answer = 17; // primary
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsThrow x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsTry x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsVar x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsVars x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsWhile x, JsContext ctx) {
|
||||
throw new RuntimeException("Only expressions have precedence.");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -55,11 +55,6 @@ public class JsRequiresSemiVisitor extends JsVisitor {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsEmpty x, JsContext ctx) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsExpressionStatement x, JsContext ctx) {
|
||||
return false;
|
||||
|
||||
@@ -323,7 +323,7 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
public boolean visit(JsCase x, JsContext ctx) {
|
||||
p.print(CHARS_CASE);
|
||||
space();
|
||||
accept(x.getCaseExpr());
|
||||
accept(x.getCaseExpression());
|
||||
_colon();
|
||||
newlineOpt();
|
||||
|
||||
@@ -450,8 +450,7 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsEmpty x, JsContext ctx) {
|
||||
return false;
|
||||
public void visit(JsEmpty x, JsContext ctx) {
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -650,12 +649,12 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
p.print(CHARS_NEW);
|
||||
space();
|
||||
|
||||
JsExpression ctorExpr = x.getConstructorExpression();
|
||||
boolean needsParens = JsConstructExpressionVisitor.exec(ctorExpr);
|
||||
JsExpression constructorExpression = x.getConstructorExpression();
|
||||
boolean needsParens = JsConstructExpressionVisitor.exec(constructorExpression);
|
||||
if (needsParens) {
|
||||
leftParen();
|
||||
}
|
||||
accept(ctorExpr);
|
||||
accept(constructorExpression);
|
||||
if (needsParens) {
|
||||
rightParen();
|
||||
}
|
||||
@@ -668,21 +667,18 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsNullLiteral x, JsContext ctx) {
|
||||
public void visit(JsNullLiteral x, JsContext ctx) {
|
||||
p.print(CHARS_NULL);
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsIntLiteral x, JsContext ctx) {
|
||||
public void visit(JsIntLiteral x, JsContext ctx) {
|
||||
p.print(x.value);
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsDoubleLiteral x, JsContext ctx) {
|
||||
public void visit(JsDoubleLiteral x, JsContext ctx) {
|
||||
p.print(x.value);
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -788,7 +784,7 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsRegExp x, JsContext ctx) {
|
||||
public void visit(JsRegExp x, JsContext ctx) {
|
||||
_slash();
|
||||
p.print(x.getPattern());
|
||||
_slash();
|
||||
@@ -796,13 +792,12 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
if (flags != null) {
|
||||
p.print(flags);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsReturn x, JsContext ctx) {
|
||||
p.print(CHARS_RETURN);
|
||||
JsExpression expr = x.getExpr();
|
||||
JsExpression expr = x.getExpression();
|
||||
if (expr != null) {
|
||||
space();
|
||||
accept(expr);
|
||||
@@ -811,9 +806,8 @@ public class JsToStringGenerationVisitor extends JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean visit(JsStringLiteral x, JsContext ctx) {
|
||||
public void visit(JsStringLiteral x, JsContext ctx) {
|
||||
p.print(javaScriptString(x.getValue()));
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import com.google.dart.compiler.common.SourceInfo;
|
||||
|
||||
public class ChameleonJsExpression implements JsExpression {
|
||||
private JsExpression expression;
|
||||
|
||||
@@ -47,8 +45,13 @@ public class ChameleonJsExpression implements JsExpression {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor visitor, JsContext context) {
|
||||
expression.traverse(visitor, context);
|
||||
public void accept(JsVisitor visitor, JsContext context) {
|
||||
expression.accept(visitor, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
expression.acceptChildren(visitor, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -10,6 +10,5 @@ import java.util.List;
|
||||
* Implemented by JavaScript objects that accept arguments.
|
||||
*/
|
||||
public interface HasArguments extends JsExpression {
|
||||
|
||||
List<JsExpression> getArguments();
|
||||
}
|
||||
|
||||
@@ -8,60 +8,62 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* Represents a javascript expression for array access.
|
||||
*/
|
||||
public final class JsArrayAccess extends JsExpressionImpl {
|
||||
private JsExpression arrayExpression;
|
||||
private JsExpression indexExpression;
|
||||
private JsExpression arrayExpression;
|
||||
private JsExpression indexExpression;
|
||||
|
||||
public JsArrayAccess() {
|
||||
super();
|
||||
}
|
||||
|
||||
public JsArrayAccess(JsExpression arrayExpression, JsExpression indexExpression) {
|
||||
this.arrayExpression = arrayExpression;
|
||||
this.indexExpression = indexExpression;
|
||||
}
|
||||
|
||||
public JsExpression getArrayExpression() {
|
||||
return arrayExpression;
|
||||
}
|
||||
|
||||
public JsExpression getIndexExpression() {
|
||||
return indexExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
return arrayExpression.hasSideEffects() || indexExpression.hasSideEffects();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
public void setArrayExpression(JsExpression arrayExpression) {
|
||||
this.arrayExpression = arrayExpression;
|
||||
}
|
||||
|
||||
public void setIndexExpression(JsExpression indexExpression) {
|
||||
this.indexExpression = indexExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
arrayExpression = v.accept(arrayExpression);
|
||||
indexExpression = v.accept(indexExpression);
|
||||
public JsArrayAccess() {
|
||||
super();
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.ARRAY_ACCESS;
|
||||
}
|
||||
public JsArrayAccess(JsExpression arrayExpression, JsExpression indexExpression) {
|
||||
this.arrayExpression = arrayExpression;
|
||||
this.indexExpression = indexExpression;
|
||||
}
|
||||
|
||||
public JsExpression getArrayExpression() {
|
||||
return arrayExpression;
|
||||
}
|
||||
|
||||
public JsExpression getIndexExpression() {
|
||||
return indexExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
return arrayExpression.hasSideEffects() || indexExpression.hasSideEffects();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
public void setArrayExpression(JsExpression arrayExpression) {
|
||||
this.arrayExpression = arrayExpression;
|
||||
}
|
||||
|
||||
public void setIndexExpression(JsExpression indexExpression) {
|
||||
this.indexExpression = indexExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
arrayExpression = visitor.accept(arrayExpression);
|
||||
indexExpression = visitor.accept(indexExpression);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.ARRAY_ACCESS;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -57,11 +57,13 @@ public final class JsArrayLiteral extends JsLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(expressions);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(expressions);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -10,91 +10,82 @@ import org.jetbrains.annotations.Nullable;
|
||||
* Represents a JavaScript binary operation.
|
||||
*/
|
||||
public final class JsBinaryOperation extends JsExpressionImpl {
|
||||
private JsExpression arg1;
|
||||
private JsExpression arg2;
|
||||
private final JsBinaryOperator op;
|
||||
private JsExpression arg1;
|
||||
private JsExpression arg2;
|
||||
private final JsBinaryOperator op;
|
||||
|
||||
public JsBinaryOperation(JsBinaryOperator op) {
|
||||
this(op, null, null);
|
||||
}
|
||||
|
||||
public JsBinaryOperation(JsBinaryOperator op, @Nullable JsExpression arg1, @Nullable JsExpression arg2) {
|
||||
this.op = op;
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public JsExpression getArg1() {
|
||||
return arg1;
|
||||
}
|
||||
|
||||
public JsExpression getArg2() {
|
||||
return arg2;
|
||||
}
|
||||
|
||||
public JsBinaryOperator getOperator() {
|
||||
return op;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
return op.isAssignment() || arg1.hasSideEffects() || arg2.hasSideEffects();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
// Precarious coding, but none of these can have null results.
|
||||
if (op.getPrecedence() > 5) {
|
||||
return true;
|
||||
public JsBinaryOperation(JsBinaryOperator op) {
|
||||
this(op, null, null);
|
||||
}
|
||||
if (op == JsBinaryOperator.OR) {
|
||||
if (arg1 instanceof CanBooleanEval) {
|
||||
if (((CanBooleanEval) arg1).isBooleanTrue()) {
|
||||
assert arg1.isDefinitelyNotNull();
|
||||
return true;
|
||||
|
||||
public JsBinaryOperation(JsBinaryOperator op, @Nullable JsExpression arg1, @Nullable JsExpression arg2) {
|
||||
this.op = op;
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public JsExpression getArg1() {
|
||||
return arg1;
|
||||
}
|
||||
|
||||
public JsExpression getArg2() {
|
||||
return arg2;
|
||||
}
|
||||
|
||||
public JsBinaryOperator getOperator() {
|
||||
return op;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
return op.isAssignment() || arg1.hasSideEffects() || arg2.hasSideEffects();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
// Precarious coding, but none of these can have null results.
|
||||
if (op.getPrecedence() > 5) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
// AND and OR can return nulls
|
||||
if (op.isAssignment()) {
|
||||
if (op == JsBinaryOperator.ASG) {
|
||||
return arg2.isDefinitelyNotNull();
|
||||
} else {
|
||||
// All other ASG's are math ops.
|
||||
return true;
|
||||
}
|
||||
if (op == JsBinaryOperator.OR) {
|
||||
if (arg1 instanceof CanBooleanEval) {
|
||||
if (((CanBooleanEval) arg1).isBooleanTrue()) {
|
||||
assert arg1.isDefinitelyNotNull();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
// AND and OR can return nulls
|
||||
if (op.isAssignment()) {
|
||||
return op != JsBinaryOperator.ASG || arg2.isDefinitelyNotNull();
|
||||
}
|
||||
|
||||
return op == JsBinaryOperator.COMMA && arg2.isDefinitelyNotNull();
|
||||
}
|
||||
|
||||
if (op == JsBinaryOperator.COMMA) {
|
||||
return arg2.isDefinitelyNotNull();
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
return op == JsBinaryOperator.AND && arg1.isDefinitelyNull();
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
if (op == JsBinaryOperator.AND) {
|
||||
return arg1.isDefinitelyNull();
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
if (op.isAssignment()) {
|
||||
arg1 = v.acceptLvalue(arg1);
|
||||
} else {
|
||||
arg1 = v.accept(arg1);
|
||||
}
|
||||
arg2 = v.accept(arg2);
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (op.isAssignment()) {
|
||||
arg1 = visitor.acceptLvalue(arg1);
|
||||
}
|
||||
else {
|
||||
arg1 = visitor.accept(arg1);
|
||||
}
|
||||
arg2 = visitor.accept(arg2);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.BINARY_OP;
|
||||
}
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.BINARY_OP;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -44,11 +44,13 @@ public class JsBlock extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(statements);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(statements);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -22,8 +22,7 @@ public final class JsBreak extends JsContinue {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,32 +8,33 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* Represents the JavaScript case statement.
|
||||
*/
|
||||
public final class JsCase extends JsSwitchMember {
|
||||
private JsExpression caseExpression;
|
||||
|
||||
private JsExpression caseExpr;
|
||||
|
||||
public JsCase() {
|
||||
super();
|
||||
}
|
||||
|
||||
public JsExpression getCaseExpr() {
|
||||
return caseExpr;
|
||||
}
|
||||
|
||||
public void setCaseExpr(JsExpression caseExpr) {
|
||||
this.caseExpr = caseExpr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
caseExpr = v.accept(caseExpr);
|
||||
v.acceptWithInsertRemove(statements);
|
||||
public JsCase() {
|
||||
super();
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.CASE;
|
||||
}
|
||||
public JsExpression getCaseExpression() {
|
||||
return caseExpression;
|
||||
}
|
||||
|
||||
public void setCaseExpression(JsExpression caseExpression) {
|
||||
this.caseExpression = caseExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
caseExpression = visitor.accept(caseExpression);
|
||||
super.acceptChildren(visitor, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.CASE;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,58 +9,60 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
*/
|
||||
public class JsCatch extends JsNodeImpl implements HasCondition {
|
||||
|
||||
protected final JsCatchScope scope;
|
||||
private JsBlock body;
|
||||
private JsExpression condition;
|
||||
private JsParameter param;
|
||||
protected final JsCatchScope scope;
|
||||
private JsBlock body;
|
||||
private JsExpression condition;
|
||||
private JsParameter param;
|
||||
|
||||
public JsCatch(JsScope parent, String ident) {
|
||||
super();
|
||||
assert (parent != null);
|
||||
scope = new JsCatchScope(parent, ident);
|
||||
param = new JsParameter(scope.findName(ident));
|
||||
}
|
||||
|
||||
public JsBlock getBody() {
|
||||
return body;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsExpression getCondition() {
|
||||
return condition;
|
||||
}
|
||||
|
||||
public JsParameter getParameter() {
|
||||
return param;
|
||||
}
|
||||
|
||||
public JsScope getScope() {
|
||||
return scope;
|
||||
}
|
||||
|
||||
public void setBody(JsBlock body) {
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCondition(JsExpression condition) {
|
||||
this.condition = condition;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
param = v.accept(param);
|
||||
if (condition != null) {
|
||||
condition = v.accept(condition);
|
||||
}
|
||||
body = v.accept(body);
|
||||
public JsCatch(JsScope parent, String ident) {
|
||||
super();
|
||||
assert (parent != null);
|
||||
scope = new JsCatchScope(parent, ident);
|
||||
param = new JsParameter(scope.findName(ident));
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.CATCH;
|
||||
}
|
||||
public JsBlock getBody() {
|
||||
return body;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsExpression getCondition() {
|
||||
return condition;
|
||||
}
|
||||
|
||||
public JsParameter getParameter() {
|
||||
return param;
|
||||
}
|
||||
|
||||
public JsScope getScope() {
|
||||
return scope;
|
||||
}
|
||||
|
||||
public void setBody(JsBlock body) {
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCondition(JsExpression condition) {
|
||||
this.condition = condition;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
param = visitor.accept(param);
|
||||
if (condition != null) {
|
||||
condition = visitor.accept(condition);
|
||||
}
|
||||
body = visitor.accept(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.CATCH;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -61,13 +61,15 @@ public final class JsConditional extends JsExpressionImpl {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
testExpr = v.accept(testExpr);
|
||||
thenExpr = v.accept(thenExpr);
|
||||
elseExpr = v.accept(elseExpr);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
testExpr = visitor.accept(testExpr);
|
||||
thenExpr = visitor.accept(thenExpr);
|
||||
elseExpr = visitor.accept(elseExpr);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -14,13 +14,13 @@ public interface JsContext {
|
||||
|
||||
boolean canRemove();
|
||||
|
||||
void insertAfter(JsVisitable node);
|
||||
void insertAfter(JsNode node);
|
||||
|
||||
void insertBefore(JsVisitable node);
|
||||
void insertBefore(JsNode node);
|
||||
|
||||
boolean isLvalue();
|
||||
|
||||
void removeMe();
|
||||
|
||||
void replaceMe(JsVisitable node);
|
||||
void replaceMe(JsNode node);
|
||||
}
|
||||
|
||||
@@ -6,9 +6,6 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* Represents the JavaScript continue statement.
|
||||
*/
|
||||
public class JsContinue extends JsNodeImpl implements JsStatement {
|
||||
protected final String label;
|
||||
|
||||
@@ -26,9 +23,13 @@ public class JsContinue extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -13,12 +13,16 @@ public class JsDebugger extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.DEBUGGER;
|
||||
}
|
||||
|
||||
@@ -8,17 +8,9 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* Represents the default option in a JavaScript swtich statement.
|
||||
*/
|
||||
public final class JsDefault extends JsSwitchMember {
|
||||
|
||||
public JsDefault() {
|
||||
super();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(statements);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -21,11 +21,10 @@ public class JsDoWhile extends JsWhile {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
condition = v.accept(condition);
|
||||
body = v.accept(body);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,10 +28,15 @@ public class JsDocComment extends JsExpressionImpl {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
return false;
|
||||
|
||||
@@ -4,22 +4,21 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
/**
|
||||
* Represents an empty statement in JavaScript.
|
||||
*/
|
||||
public class JsEmpty extends JsNodeImpl implements JsStatement {
|
||||
// Interned by JsProgram
|
||||
JsEmpty() {
|
||||
}
|
||||
JsEmpty() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.EMPTY;
|
||||
}
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.EMPTY;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import com.google.dart.compiler.common.HasSourceInfo;
|
||||
|
||||
public interface JsExpression extends JsNode, HasSourceInfo, JsVisitable {
|
||||
public interface JsExpression extends JsNode, HasSourceInfo {
|
||||
/**
|
||||
* Determines whether the expression can cause side effects.
|
||||
*/
|
||||
|
||||
@@ -4,6 +4,8 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
abstract class JsExpressionImpl extends JsNodeImpl implements JsExpression {
|
||||
protected JsExpressionImpl() {
|
||||
}
|
||||
@@ -24,4 +26,17 @@ abstract class JsExpressionImpl extends JsNodeImpl implements JsExpression {
|
||||
public JsStatement makeStmt() {
|
||||
return new JsExpressionStatement(this);
|
||||
}
|
||||
|
||||
protected abstract static class JsExpressionHasArguments extends JsExpressionImpl implements HasArguments {
|
||||
protected final List<JsExpression> arguments;
|
||||
|
||||
public JsExpressionHasArguments(List<JsExpression> arguments) {
|
||||
this.arguments = arguments;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<JsExpression> getArguments() {
|
||||
return arguments;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,11 +16,13 @@ public final class JsExpressionStatement extends AbstractNode implements JsState
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
expression = v.accept(expression);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
expression = visitor.accept(expression);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -71,27 +71,29 @@ public class JsFor extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
assert (!(initExpression != null && initVars != null));
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
if (initExpression != null) {
|
||||
initExpression = v.accept(initExpression);
|
||||
}
|
||||
else if (initVars != null) {
|
||||
initVars = v.accept(initVars);
|
||||
}
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
assert (!(initExpression != null && initVars != null));
|
||||
|
||||
if (condition != null) {
|
||||
condition = v.accept(condition);
|
||||
}
|
||||
|
||||
if (incrementExpression != null) {
|
||||
incrementExpression = v.accept(incrementExpression);
|
||||
}
|
||||
body = v.accept(body);
|
||||
if (initExpression != null) {
|
||||
initExpression = visitor.accept(initExpression);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
else if (initVars != null) {
|
||||
initVars = visitor.accept(initVars);
|
||||
}
|
||||
|
||||
if (condition != null) {
|
||||
condition = visitor.accept(condition);
|
||||
}
|
||||
|
||||
if (incrementExpression != null) {
|
||||
incrementExpression = visitor.accept(incrementExpression);
|
||||
}
|
||||
body = visitor.accept(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -8,64 +8,67 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* Represents a JavaScript for..in statement.
|
||||
*/
|
||||
public class JsForIn extends JsNodeImpl implements JsStatement {
|
||||
private JsStatement body;
|
||||
private JsExpression iterExpr;
|
||||
private JsExpression objExpr;
|
||||
|
||||
private JsStatement body;
|
||||
private JsExpression iterExpr;
|
||||
private JsExpression objExpr;
|
||||
// Optional: the name of a new iterator variable to introduce
|
||||
private final JsName iterVarName;
|
||||
|
||||
// Optional: the name of a new iterator variable to introduce
|
||||
private final JsName iterVarName;
|
||||
|
||||
public JsForIn() {
|
||||
this(null);
|
||||
}
|
||||
|
||||
public JsForIn(JsName iterVarName) {
|
||||
this.iterVarName = iterVarName;
|
||||
}
|
||||
|
||||
public JsStatement getBody() {
|
||||
return body;
|
||||
}
|
||||
|
||||
public JsExpression getIterExpr() {
|
||||
return iterExpr;
|
||||
}
|
||||
|
||||
public JsName getIterVarName() {
|
||||
return iterVarName;
|
||||
}
|
||||
|
||||
public JsExpression getObjExpr() {
|
||||
return objExpr;
|
||||
}
|
||||
|
||||
public void setBody(JsStatement body) {
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
public void setIterExpr(JsExpression iterExpr) {
|
||||
this.iterExpr = iterExpr;
|
||||
}
|
||||
|
||||
public void setObjExpr(JsExpression objExpr) {
|
||||
this.objExpr = objExpr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
if (iterExpr != null) {
|
||||
iterExpr = v.acceptLvalue(iterExpr);
|
||||
}
|
||||
objExpr = v.accept(objExpr);
|
||||
body = v.accept(body);
|
||||
public JsForIn() {
|
||||
this(null);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.FOR_IN;
|
||||
}
|
||||
public JsForIn(JsName iterVarName) {
|
||||
this.iterVarName = iterVarName;
|
||||
}
|
||||
|
||||
public JsStatement getBody() {
|
||||
return body;
|
||||
}
|
||||
|
||||
public JsExpression getIterExpr() {
|
||||
return iterExpr;
|
||||
}
|
||||
|
||||
public JsName getIterVarName() {
|
||||
return iterVarName;
|
||||
}
|
||||
|
||||
public JsExpression getObjExpr() {
|
||||
return objExpr;
|
||||
}
|
||||
|
||||
public void setBody(JsStatement body) {
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
public void setIterExpr(JsExpression iterExpr) {
|
||||
this.iterExpr = iterExpr;
|
||||
}
|
||||
|
||||
public void setObjExpr(JsExpression objExpr) {
|
||||
this.objExpr = objExpr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (iterExpr != null) {
|
||||
iterExpr = visitor.acceptLvalue(iterExpr);
|
||||
}
|
||||
objExpr = visitor.accept(objExpr);
|
||||
body = visitor.accept(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.FOR_IN;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -90,12 +90,14 @@ public final class JsFunction extends JsLiteral implements HasName {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(params);
|
||||
body = v.accept(body);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(params);
|
||||
body = visitor.accept(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -51,15 +51,17 @@ public final class JsIf extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
ifExpression = v.accept(ifExpression);
|
||||
thenStatement = v.accept(thenStatement);
|
||||
if (elseStatement != null) {
|
||||
elseStatement = v.accept(elseStatement);
|
||||
}
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
ifExpression = visitor.accept(ifExpression);
|
||||
thenStatement = visitor.accept(thenStatement);
|
||||
if (elseStatement != null) {
|
||||
elseStatement = visitor.accept(elseStatement);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -13,17 +13,16 @@ import java.util.List;
|
||||
/**
|
||||
* Represents a JavaScript invocation.
|
||||
*/
|
||||
public final class JsInvocation extends JsExpressionImpl implements HasArguments {
|
||||
private final List<JsExpression> arguments;
|
||||
public final class JsInvocation extends JsExpressionImpl.JsExpressionHasArguments {
|
||||
private JsExpression qualifier;
|
||||
|
||||
public JsInvocation() {
|
||||
arguments = new SmartList<JsExpression>();
|
||||
super(new SmartList<JsExpression>());
|
||||
}
|
||||
|
||||
public JsInvocation(JsExpression qualifier, List<JsExpression> arguments) {
|
||||
super(arguments);
|
||||
this.qualifier = qualifier;
|
||||
this.arguments = arguments;
|
||||
}
|
||||
|
||||
public JsInvocation(JsExpression qualifier, JsExpression arg) {
|
||||
@@ -68,12 +67,14 @@ public final class JsInvocation extends JsExpressionImpl implements HasArguments
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
qualifier = v.accept(qualifier);
|
||||
v.acceptList(arguments);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
qualifier = visitor.accept(qualifier);
|
||||
visitor.acceptList(arguments);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -42,12 +42,14 @@ public class JsLabel extends JsNodeImpl implements JsStatement, HasName {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
statement = v.accept(statement);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
statement = visitor.accept(statement);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
|
||||
@@ -43,9 +43,8 @@ public abstract class JsLiteral extends JsExpressionImpl implements CanBooleanEv
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -87,9 +86,8 @@ public abstract class JsLiteral extends JsExpressionImpl implements CanBooleanEv
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -97,4 +95,26 @@ public abstract class JsLiteral extends JsExpressionImpl implements CanBooleanEv
|
||||
return NodeKind.BOOLEAN;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A JavaScript string literal expression.
|
||||
*/
|
||||
public abstract static class JsValueLiteral extends JsLiteral {
|
||||
protected JsValueLiteral() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean hasSideEffects() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean isLeaf() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -56,14 +56,7 @@ public final class JsNameRef extends JsExpressionImpl implements CanBooleanEval,
|
||||
|
||||
@Override
|
||||
public boolean hasSideEffects() {
|
||||
if (qualifier == null) {
|
||||
return false;
|
||||
}
|
||||
if (!qualifier.isDefinitelyNotNull()) {
|
||||
// Could trigger NPE.
|
||||
return true;
|
||||
}
|
||||
return qualifier.hasSideEffects();
|
||||
return qualifier != null && (!qualifier.isDefinitelyNotNull() || qualifier.hasSideEffects());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -83,25 +76,17 @@ public final class JsNameRef extends JsExpressionImpl implements CanBooleanEval,
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
if (name != null) {
|
||||
return (JsLiteral.UNDEFINED.getName() == name);
|
||||
}
|
||||
return false;
|
||||
return name != null && (JsLiteral.UNDEFINED.getName() == name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLeaf() {
|
||||
if (qualifier == null) {
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
}
|
||||
return qualifier == null;
|
||||
}
|
||||
|
||||
public void resolve(JsName name) {
|
||||
this.name = name;
|
||||
this.ident = null;
|
||||
ident = null;
|
||||
}
|
||||
|
||||
public void setQualifier(JsExpression qualifier) {
|
||||
@@ -109,13 +94,15 @@ public final class JsNameRef extends JsExpressionImpl implements CanBooleanEval,
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
if (qualifier != null) {
|
||||
qualifier = v.accept(qualifier);
|
||||
}
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (qualifier != null) {
|
||||
qualifier = visitor.accept(qualifier);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -8,29 +8,20 @@ import com.intellij.util.SmartList;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Represents the JavaScript new expression.
|
||||
*/
|
||||
public final class JsNew extends JsExpressionImpl implements HasArguments {
|
||||
private final List<JsExpression> arguments;
|
||||
private JsExpression ctorExpression;
|
||||
public final class JsNew extends JsExpressionImpl.JsExpressionHasArguments {
|
||||
private JsExpression constructorExpression;
|
||||
|
||||
public JsNew(JsExpression ctorExpression) {
|
||||
this(ctorExpression, new SmartList<JsExpression>());
|
||||
public JsNew(JsExpression constructorExpression) {
|
||||
this(constructorExpression, new SmartList<JsExpression>());
|
||||
}
|
||||
|
||||
public JsNew(JsExpression ctorExpression, List<JsExpression> arguments) {
|
||||
this.ctorExpression = ctorExpression;
|
||||
this.arguments = arguments;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<JsExpression> getArguments() {
|
||||
return arguments;
|
||||
public JsNew(JsExpression constructorExpression, List<JsExpression> arguments) {
|
||||
super(arguments);
|
||||
this.constructorExpression = constructorExpression;
|
||||
}
|
||||
|
||||
public JsExpression getConstructorExpression() {
|
||||
return ctorExpression;
|
||||
return constructorExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -51,12 +42,14 @@ public final class JsNew extends JsExpressionImpl implements HasArguments {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
ctorExpression = v.accept(ctorExpression);
|
||||
v.acceptList(arguments);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
constructorExpression = visitor.accept(constructorExpression);
|
||||
visitor.acceptList(arguments);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -4,6 +4,16 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
public interface JsNode extends JsVisitable {
|
||||
public interface JsNode {
|
||||
NodeKind getKind();
|
||||
|
||||
/**
|
||||
* Causes this object to have the visitor visit itself and its children.
|
||||
*
|
||||
* @param visitor the visitor that should traverse this node
|
||||
* @param context the context of an existing traversal
|
||||
*/
|
||||
void accept(JsVisitor visitor, JsContext context);
|
||||
|
||||
void acceptChildren(JsVisitor visitor, JsContext context);
|
||||
}
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import com.google.dart.compiler.common.SourceInfo;
|
||||
|
||||
abstract class JsNodeImpl extends AbstractNode {
|
||||
private Object sourceInfo;
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
public final class JsNullLiteral extends JsValueLiteral {
|
||||
public final class JsNullLiteral extends JsLiteral.JsValueLiteral {
|
||||
JsNullLiteral() {
|
||||
}
|
||||
|
||||
@@ -29,9 +29,8 @@ public final class JsNullLiteral extends JsValueLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
public abstract class JsNumberLiteral extends JsValueLiteral {
|
||||
public abstract class JsNumberLiteral extends JsLiteral.JsValueLiteral {
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
return true;
|
||||
@@ -38,9 +38,8 @@ public abstract class JsNumberLiteral extends JsValueLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
@@ -66,9 +65,8 @@ public abstract class JsNumberLiteral extends JsValueLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
|
||||
@@ -69,11 +69,13 @@ public final class JsObjectLiteral extends JsLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(properties);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(properties);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -10,30 +10,34 @@ import com.google.dart.compiler.common.Symbol;
|
||||
* A JavaScript parameter.
|
||||
*/
|
||||
public final class JsParameter extends JsNodeImpl implements HasName {
|
||||
private final JsName name;
|
||||
private final JsName name;
|
||||
|
||||
public JsParameter(JsName name) {
|
||||
this.name = name;
|
||||
}
|
||||
public JsParameter(JsName name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsName getName() {
|
||||
return name;
|
||||
}
|
||||
@Override
|
||||
public JsName getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Symbol getSymbol() {
|
||||
return name;
|
||||
}
|
||||
@Override
|
||||
public Symbol getSymbol() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.PARAMETER;
|
||||
}
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.PARAMETER;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,11 +28,8 @@ public final class JsPostfixOperation extends JsUnaryOperation {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
super.traverse(v, context);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -4,9 +4,6 @@
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
/**
|
||||
* A JavaScript prefix operation.
|
||||
*/
|
||||
public final class JsPrefixOperation extends JsUnaryOperation implements CanBooleanEval {
|
||||
|
||||
public JsPrefixOperation(JsUnaryOperator op) {
|
||||
@@ -35,18 +32,12 @@ public final class JsPrefixOperation extends JsUnaryOperation implements CanBool
|
||||
CanBooleanEval eval = (CanBooleanEval) getArg();
|
||||
return eval.isBooleanFalse();
|
||||
}
|
||||
if (getOperator() == JsUnaryOperator.TYPEOF) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
return getOperator() == JsUnaryOperator.TYPEOF;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
if (getOperator() == JsUnaryOperator.TYPEOF) {
|
||||
return true;
|
||||
}
|
||||
return getOperator() != JsUnaryOperator.VOID;
|
||||
return getOperator() == JsUnaryOperator.TYPEOF || getOperator() != JsUnaryOperator.VOID;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -55,11 +46,8 @@ public final class JsPrefixOperation extends JsUnaryOperation implements CanBool
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
super.traverse(v, context);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -18,7 +18,7 @@ import static com.google.dart.compiler.backend.js.ast.JsNumberLiteral.JsIntLiter
|
||||
* A JavaScript program.
|
||||
*/
|
||||
public final class JsProgram extends JsNodeImpl {
|
||||
private final JsEmpty emptyStmt;
|
||||
private final JsEmpty emptyStatement;
|
||||
|
||||
private JsProgramFragment[] fragments;
|
||||
|
||||
@@ -29,19 +29,16 @@ public final class JsProgram extends JsNodeImpl {
|
||||
private final Map<String, JsStringLiteral> stringLiteralMap = new THashMap<String, JsStringLiteral>();
|
||||
private final JsScope topScope;
|
||||
|
||||
/**
|
||||
* Constructs a JavaScript program object.
|
||||
*/
|
||||
public JsProgram(String unitId) {
|
||||
rootScope = new JsRootScope(this);
|
||||
topScope = new JsScope(rootScope, "Global", unitId);
|
||||
setFragmentCount(1);
|
||||
|
||||
emptyStmt = new JsEmpty();
|
||||
emptyStatement = new JsEmpty();
|
||||
}
|
||||
|
||||
public JsEmpty getEmptyStmt() {
|
||||
return emptyStmt;
|
||||
public JsEmpty getEmptyStatement() {
|
||||
return emptyStatement;
|
||||
}
|
||||
|
||||
public JsBlock getFragmentBlock(int fragment) {
|
||||
@@ -112,13 +109,15 @@ public final class JsProgram extends JsNodeImpl {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, @Nullable JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
for (JsProgramFragment fragment : fragments) {
|
||||
v.accept(fragment);
|
||||
}
|
||||
public void accept(JsVisitor v, @Nullable JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
for (JsProgramFragment fragment : fragments) {
|
||||
visitor.accept(fragment);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -8,27 +8,28 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* One independently loadable fragment of a {@link JsProgram}.
|
||||
*/
|
||||
public class JsProgramFragment extends JsNodeImpl {
|
||||
private final JsGlobalBlock globalBlock;
|
||||
|
||||
private final JsGlobalBlock globalBlock;
|
||||
|
||||
public JsProgramFragment() {
|
||||
this.globalBlock = new JsGlobalBlock();
|
||||
}
|
||||
|
||||
public JsBlock getGlobalBlock() {
|
||||
return globalBlock;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.accept(globalBlock);
|
||||
public JsProgramFragment() {
|
||||
globalBlock = new JsGlobalBlock();
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.PROGRAM_FRAGMENT;
|
||||
}
|
||||
public JsBlock getGlobalBlock() {
|
||||
return globalBlock;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.accept(globalBlock);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.PROGRAM_FRAGMENT;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -39,12 +39,14 @@ public class JsPropertyInitializer extends JsNodeImpl {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
labelExpr = v.accept(labelExpr);
|
||||
valueExpr = v.accept(valueExpr);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
labelExpr = visitor.accept(labelExpr);
|
||||
valueExpr = visitor.accept(valueExpr);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -7,58 +7,56 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
/**
|
||||
* A JavaScript regular expression.
|
||||
*/
|
||||
public final class JsRegExp extends JsValueLiteral {
|
||||
public final class JsRegExp extends JsLiteral.JsValueLiteral {
|
||||
private String flags;
|
||||
private String pattern;
|
||||
|
||||
private String flags;
|
||||
private String pattern;
|
||||
public JsRegExp() {
|
||||
}
|
||||
|
||||
public JsRegExp() {
|
||||
}
|
||||
public String getFlags() {
|
||||
return flags;
|
||||
}
|
||||
|
||||
public String getFlags() {
|
||||
return flags;
|
||||
}
|
||||
public String getPattern() {
|
||||
return pattern;
|
||||
}
|
||||
|
||||
public String getPattern() {
|
||||
return pattern;
|
||||
}
|
||||
@Override
|
||||
public boolean isBooleanFalse() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isBooleanFalse() {
|
||||
return false;
|
||||
}
|
||||
@Override
|
||||
public boolean isBooleanTrue() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isBooleanTrue() {
|
||||
return true;
|
||||
}
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNotNull() {
|
||||
return true;
|
||||
}
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDefinitelyNull() {
|
||||
return false;
|
||||
}
|
||||
public void setFlags(String suffix) {
|
||||
flags = suffix;
|
||||
}
|
||||
|
||||
public void setFlags(String suffix) {
|
||||
this.flags = suffix;
|
||||
}
|
||||
public void setPattern(String re) {
|
||||
pattern = re;
|
||||
}
|
||||
|
||||
public void setPattern(String re) {
|
||||
this.pattern = re;
|
||||
}
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.REGEXP;
|
||||
}
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.REGEXP;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,36 +8,37 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
* A JavaScript return statement.
|
||||
*/
|
||||
public final class JsReturn extends JsNodeImpl implements JsStatement {
|
||||
private JsExpression expression;
|
||||
|
||||
private JsExpression expr;
|
||||
|
||||
public JsReturn() {
|
||||
}
|
||||
|
||||
public JsReturn(JsExpression expr) {
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
public JsExpression getExpr() {
|
||||
return expr;
|
||||
}
|
||||
|
||||
public void setExpr(JsExpression expr) {
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
if (expr != null) {
|
||||
expr = v.accept(expr);
|
||||
}
|
||||
public JsReturn() {
|
||||
}
|
||||
|
||||
public JsReturn(JsExpression expression) {
|
||||
this.expression = expression;
|
||||
}
|
||||
|
||||
public JsExpression getExpression() {
|
||||
return expression;
|
||||
}
|
||||
|
||||
public void setExpression(JsExpression expression) {
|
||||
this.expression = expression;
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.RETURN;
|
||||
}
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (expression != null) {
|
||||
expression = visitor.accept(expression);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.RETURN;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -67,8 +67,8 @@ public class JsScope {
|
||||
|
||||
protected JsScope(@Nullable String description) {
|
||||
this.description = description;
|
||||
this.parent = null;
|
||||
this.scopeId = null;
|
||||
parent = null;
|
||||
scopeId = null;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -7,7 +7,7 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
/**
|
||||
* A JavaScript string literal expression.
|
||||
*/
|
||||
public final class JsStringLiteral extends JsValueLiteral {
|
||||
public final class JsStringLiteral extends JsLiteral.JsValueLiteral {
|
||||
|
||||
private final String value;
|
||||
|
||||
@@ -41,9 +41,8 @@ public final class JsStringLiteral extends JsValueLiteral {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -12,36 +12,38 @@ import java.util.List;
|
||||
*/
|
||||
public class JsSwitch extends JsNodeImpl implements JsStatement {
|
||||
|
||||
private final List<JsSwitchMember> cases = new ArrayList<JsSwitchMember>();
|
||||
private JsExpression expr;
|
||||
private final List<JsSwitchMember> cases = new ArrayList<JsSwitchMember>();
|
||||
private JsExpression expr;
|
||||
|
||||
public JsSwitch() {
|
||||
super();
|
||||
}
|
||||
|
||||
public List<JsSwitchMember> getCases() {
|
||||
return cases;
|
||||
}
|
||||
|
||||
public JsExpression getExpr() {
|
||||
return expr;
|
||||
}
|
||||
|
||||
public void setExpr(JsExpression expr) {
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
expr = v.accept(expr);
|
||||
v.acceptWithInsertRemove(cases);
|
||||
public JsSwitch() {
|
||||
super();
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.SWITCH;
|
||||
}
|
||||
public List<JsSwitchMember> getCases() {
|
||||
return cases;
|
||||
}
|
||||
|
||||
public JsExpression getExpr() {
|
||||
return expr;
|
||||
}
|
||||
|
||||
public void setExpr(JsExpression expr) {
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
expr = visitor.accept(expr);
|
||||
visitor.acceptWithInsertRemove(cases);
|
||||
}
|
||||
|
||||
@Override
|
||||
public NodeKind getKind() {
|
||||
return NodeKind.SWITCH;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,4 +21,9 @@ public abstract class JsSwitchMember extends JsNodeImpl {
|
||||
public List<JsStatement> getStatements() {
|
||||
return statements;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(statements);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,11 +23,13 @@ public class JsThrow extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
expression = v.accept(expression);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.accept(expression);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -40,7 +40,7 @@ public class JsTry extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
public void setFinallyBlock(JsBlock block) {
|
||||
this.finallyBlock = block;
|
||||
finallyBlock = block;
|
||||
}
|
||||
|
||||
public void setTryBlock(JsBlock block) {
|
||||
@@ -48,15 +48,17 @@ public class JsTry extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
tryBlock = v.accept(tryBlock);
|
||||
v.acceptWithInsertRemove(catches);
|
||||
if (finallyBlock != null) {
|
||||
finallyBlock = v.accept(finallyBlock);
|
||||
}
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
tryBlock = visitor.accept(tryBlock);
|
||||
visitor.acceptWithInsertRemove(catches);
|
||||
if (finallyBlock != null) {
|
||||
finallyBlock = visitor.accept(finallyBlock);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -9,45 +9,46 @@ package com.google.dart.compiler.backend.js.ast;
|
||||
*/
|
||||
public abstract class JsUnaryOperation extends JsExpressionImpl {
|
||||
|
||||
private JsExpression arg;
|
||||
private JsExpression arg;
|
||||
|
||||
private final JsUnaryOperator op;
|
||||
private final JsUnaryOperator op;
|
||||
|
||||
public JsUnaryOperation(JsUnaryOperator op) {
|
||||
this(op, null);
|
||||
}
|
||||
|
||||
public JsUnaryOperation(JsUnaryOperator op, JsExpression arg) {
|
||||
super();
|
||||
this.op = op;
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public JsExpression getArg() {
|
||||
return arg;
|
||||
}
|
||||
|
||||
public JsUnaryOperator getOperator() {
|
||||
return op;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean hasSideEffects() {
|
||||
return op.isModifying() || arg.hasSideEffects();
|
||||
}
|
||||
|
||||
public void setArg(JsExpression arg) {
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (op.isModifying()) {
|
||||
// The delete operator is practically like an assignment of undefined, so
|
||||
// for practical purposes we're treating it as an lvalue.
|
||||
arg = v.acceptLvalue(arg);
|
||||
} else {
|
||||
arg = v.accept(arg);
|
||||
public JsUnaryOperation(JsUnaryOperator op) {
|
||||
this(op, null);
|
||||
}
|
||||
|
||||
public JsUnaryOperation(JsUnaryOperator op, JsExpression arg) {
|
||||
super();
|
||||
this.op = op;
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public JsExpression getArg() {
|
||||
return arg;
|
||||
}
|
||||
|
||||
public JsUnaryOperator getOperator() {
|
||||
return op;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean hasSideEffects() {
|
||||
return op.isModifying() || arg.hasSideEffects();
|
||||
}
|
||||
|
||||
public void setArg(JsExpression arg) {
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (op.isModifying()) {
|
||||
// The delete operator is practically like an assignment of undefined, so
|
||||
// for practical purposes we're treating it as an lvalue.
|
||||
arg = visitor.acceptLvalue(arg);
|
||||
}
|
||||
else {
|
||||
arg = visitor.accept(arg);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,23 +0,0 @@
|
||||
// Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
|
||||
// for details. All rights reserved. Use of this source code is governed by a
|
||||
// BSD-style license that can be found in the LICENSE file.
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
/**
|
||||
* A JavaScript string literal expression.
|
||||
*/
|
||||
public abstract class JsValueLiteral extends JsLiteral {
|
||||
protected JsValueLiteral() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean hasSideEffects() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean isLeaf() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -81,13 +81,15 @@ public class JsVars extends JsNodeImpl implements JsStatement, Iterable<JsVars.J
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
if (initExpression != null) {
|
||||
initExpression = v.accept(initExpression);
|
||||
}
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
if (initExpression != null) {
|
||||
initExpression = visitor.accept(initExpression);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -116,11 +118,13 @@ public class JsVars extends JsNodeImpl implements JsStatement, Iterable<JsVars.J
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
v.acceptWithInsertRemove(vars);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
visitor.acceptWithInsertRemove(vars);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -1,17 +0,0 @@
|
||||
// Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
|
||||
// for details. All rights reserved. Use of this source code is governed by a
|
||||
// BSD-style license that can be found in the LICENSE file.
|
||||
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
import com.google.dart.compiler.common.HasSourceInfo;
|
||||
|
||||
public interface JsVisitable extends HasSourceInfo {
|
||||
/**
|
||||
* Causes this object to have the visitor visit itself and its children.
|
||||
*
|
||||
* @param visitor the visitor that should traverse this node
|
||||
* @param context the context of an existing traversal
|
||||
*/
|
||||
void traverse(JsVisitor visitor, JsContext context);
|
||||
}
|
||||
@@ -8,10 +8,7 @@ import com.google.dart.compiler.backend.js.ast.JsVars.JsVar;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Implemented by nodes that will visit child nodes.
|
||||
*/
|
||||
abstract public class JsVisitor {
|
||||
public abstract class JsVisitor {
|
||||
protected static final JsContext LVALUE_CONTEXT = new JsContext() {
|
||||
@Override
|
||||
public boolean canInsert() {
|
||||
@@ -24,12 +21,12 @@ abstract public class JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void insertAfter(JsVisitable node) {
|
||||
public void insertAfter(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void insertBefore(JsVisitable node) {
|
||||
public void insertBefore(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@@ -44,13 +41,12 @@ abstract public class JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void replaceMe(JsVisitable node) {
|
||||
public void replaceMe(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
};
|
||||
|
||||
protected static final JsContext UNMODIFIABLE_CONTEXT = new JsContext() {
|
||||
|
||||
@Override
|
||||
public boolean canInsert() {
|
||||
return false;
|
||||
@@ -62,12 +58,12 @@ abstract public class JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void insertAfter(JsVisitable node) {
|
||||
public void insertAfter(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void insertBefore(JsVisitable node) {
|
||||
public void insertBefore(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@@ -82,17 +78,17 @@ abstract public class JsVisitor {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void replaceMe(JsVisitable node) {
|
||||
public void replaceMe(JsNode node) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
};
|
||||
|
||||
public <T extends JsVisitable> T accept(T node) {
|
||||
public <T extends JsNode> T accept(T node) {
|
||||
doTraverse(node, UNMODIFIABLE_CONTEXT);
|
||||
return node;
|
||||
}
|
||||
|
||||
public final <T extends JsVisitable> void acceptList(List<T> collection) {
|
||||
public final <T extends JsNode> void acceptList(List<T> collection) {
|
||||
for (T node : collection) {
|
||||
doTraverse(node, UNMODIFIABLE_CONTEXT);
|
||||
}
|
||||
@@ -103,138 +99,12 @@ abstract public class JsVisitor {
|
||||
return expr;
|
||||
}
|
||||
|
||||
public final <T extends JsVisitable> void acceptWithInsertRemove(List<T> collection) {
|
||||
public final <T extends JsNode> void acceptWithInsertRemove(List<T> collection) {
|
||||
for (T node : collection) {
|
||||
doTraverse(node, UNMODIFIABLE_CONTEXT);
|
||||
}
|
||||
}
|
||||
|
||||
public void endVisit(JsArrayAccess x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsArrayLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsBinaryOperation x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsBlock x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsLiteral.JsBooleanLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsBreak x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsCase x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsCatch x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsConditional x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsContinue x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsDebugger x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsDefault x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsDoWhile x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsEmpty x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsExpressionStatement x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsFor x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsForIn x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsFunction x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsIf x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsInvocation x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsLabel x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsNameRef x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsNew x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsNullLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsNumberLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsObjectLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsParameter x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsPostfixOperation x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsPrefixOperation x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsProgram x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsProgramFragment x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsPropertyInitializer x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsRegExp x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsReturn x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsStringLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsSwitch x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsLiteral.JsThisRef x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsThrow x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsTry x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsVar x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsVars x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public void endVisit(JsWhile x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsArrayAccess x, JsContext ctx) {
|
||||
return true;
|
||||
}
|
||||
@@ -287,8 +157,7 @@ abstract public class JsVisitor {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean visit(JsEmpty x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsEmpty x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsExpressionStatement x, JsContext ctx) {
|
||||
@@ -327,16 +196,13 @@ abstract public class JsVisitor {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean visit(JsNullLiteral x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsNullLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsNumberLiteral.JsIntLiteral x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsNumberLiteral.JsIntLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsNumberLiteral.JsDoubleLiteral x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsNumberLiteral.JsDoubleLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsObjectLiteral x, JsContext ctx) {
|
||||
@@ -367,16 +233,14 @@ abstract public class JsVisitor {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean visit(JsRegExp x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsRegExp x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsReturn x, JsContext ctx) {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean visit(JsStringLiteral x, JsContext ctx) {
|
||||
return true;
|
||||
public void visit(JsStringLiteral x, JsContext ctx) {
|
||||
}
|
||||
|
||||
public boolean visit(JsSwitch x, JsContext ctx) {
|
||||
@@ -411,7 +275,7 @@ abstract public class JsVisitor {
|
||||
return true;
|
||||
}
|
||||
|
||||
protected void doTraverse(JsVisitable node, JsContext context) {
|
||||
node.traverse(this, context);
|
||||
protected void doTraverse(JsNode node, JsContext context) {
|
||||
node.accept(this, context);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -36,12 +36,14 @@ public class JsWhile extends JsNodeImpl implements JsStatement {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void traverse(JsVisitor v, JsContext context) {
|
||||
if (v.visit(this, context)) {
|
||||
condition = v.accept(condition);
|
||||
body = v.accept(body);
|
||||
}
|
||||
v.endVisit(this, context);
|
||||
public void accept(JsVisitor v, JsContext context) {
|
||||
v.visit(this, context);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void acceptChildren(JsVisitor visitor, JsContext context) {
|
||||
condition = visitor.accept(condition);
|
||||
body = visitor.accept(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -0,0 +1,4 @@
|
||||
package com.google.dart.compiler.backend.js.ast;
|
||||
|
||||
public abstract class RecursiveJsVisitor extends JsVisitor {
|
||||
}
|
||||
Reference in New Issue
Block a user