feat(jdk8): move files to new folder to avoid resources compiled.
This commit is contained in:
253
jdkSrc/jdk8/sun/tools/tree/AddExpression.java
Normal file
253
jdkSrc/jdk8/sun/tools/tree/AddExpression.java
Normal file
@@ -0,0 +1,253 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AddExpression extends BinaryArithmeticExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public AddExpression(long where, Expression left, Expression right) {
|
||||
super(ADD, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((left.type == Type.tString) && !right.type.isType(TC_VOID)) {
|
||||
type = Type.tString;
|
||||
return;
|
||||
} else if ((right.type == Type.tString) && !left.type.isType(TC_VOID)) {
|
||||
type = Type.tString;
|
||||
return;
|
||||
}
|
||||
super.selectType(env, ctx, tm);
|
||||
}
|
||||
|
||||
public boolean isNonNull() {
|
||||
// an addition expression cannot yield a null reference as a result
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a + b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a + b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new FloatExpression(where, a + b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new DoubleExpression(where, a + b);
|
||||
}
|
||||
Expression eval(String a, String b) {
|
||||
return new StringExpression(where, a + b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline the value of an AddExpression. If this AddExpression
|
||||
* represents a concatenation of compile-time constant strings,
|
||||
* dispatch to the special method inlineValueSB, which handles
|
||||
* the inlining more efficiently.
|
||||
*/
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (type == Type.tString && isConstant()) {
|
||||
StringBuffer buffer = inlineValueSB(env, ctx, new StringBuffer());
|
||||
if (buffer != null) {
|
||||
// We were able to evaluate the String concatenation.
|
||||
return new StringExpression(where, buffer.toString());
|
||||
}
|
||||
}
|
||||
// For some reason inlinValueSB() failed to produce a value.
|
||||
// Use the older, less efficient, inlining mechanism.
|
||||
return super.inlineValue(env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to evaluate this expression. If this expression
|
||||
* yields a value, append it to the StringBuffer `buffer'.
|
||||
* If this expression cannot be evaluated at this time (for
|
||||
* example if it contains a division by zero, a non-constant
|
||||
* subexpression, or a subexpression which "refuses" to evaluate)
|
||||
* then return `null' to indicate failure.
|
||||
*
|
||||
* It is anticipated that this method will be called to evaluate
|
||||
* concatenations of compile-time constant strings. The call
|
||||
* originates from AddExpression#inlineValue().
|
||||
*
|
||||
* This method does not use associativity to good effect in
|
||||
* folding string concatenations. This is room for improvement.
|
||||
*
|
||||
* -------------
|
||||
*
|
||||
* A bit of history: this method was added because an
|
||||
* expression like...
|
||||
*
|
||||
* "a" + "b" + "c" + "d"
|
||||
*
|
||||
* ...was evaluated at compile-time as...
|
||||
*
|
||||
* (new StringBuffer((new StringBuffer("a")).append("b").toString())).
|
||||
* append((new StringBuffer("c")).append("d").toString()).toString()
|
||||
*
|
||||
* Alex Garthwaite, in profiling the memory allocation of the
|
||||
* compiler, noticed this and suggested that the method inlineValueSB()
|
||||
* be added to evaluate constant string concatenations in a more
|
||||
* efficient manner. The compiler now builds the string in a
|
||||
* top-down fashion, by accumulating the result in a StringBuffer
|
||||
* which is allocated once and passed in as a parameter. The new
|
||||
* evaluation scheme is equivalent to...
|
||||
*
|
||||
* (new StringBuffer("a")).append("b").append("c").append("d")
|
||||
* .toString()
|
||||
*
|
||||
* ...which is more efficient. Since then, the code has been modified
|
||||
* to fix certain problems. Now, for example, it can return `null'
|
||||
* when it encounters a concatenation which it is not able to
|
||||
* evaluate.
|
||||
*
|
||||
* See also Expression#inlineValueSB() and ExprExpression#inlineValueSB().
|
||||
*/
|
||||
protected StringBuffer inlineValueSB(Environment env,
|
||||
Context ctx,
|
||||
StringBuffer buffer) {
|
||||
if (type != Type.tString) {
|
||||
// This isn't a concatenation. It is actually an addition
|
||||
// of some sort. Call the generic inlineValueSB()
|
||||
return super.inlineValueSB(env, ctx, buffer);
|
||||
}
|
||||
|
||||
buffer = left.inlineValueSB(env, ctx, buffer);
|
||||
if (buffer != null) {
|
||||
buffer = right.inlineValueSB(env, ctx, buffer);
|
||||
}
|
||||
return buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (!type.isType(TC_CLASS)) {
|
||||
// Can't simplify floating point add because of -0.0 strangeness
|
||||
if (type.inMask(TM_INTEGER)) {
|
||||
if (left.equals(0)) {
|
||||
return right;
|
||||
}
|
||||
if (right.equals(0)) {
|
||||
return left;
|
||||
}
|
||||
}
|
||||
} else if (right.type.isType(TC_NULL)) {
|
||||
right = new StringExpression(right.where, "null");
|
||||
} else if (left.type.isType(TC_NULL)) {
|
||||
left = new StringExpression(left.where, "null");
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return (type.isType(TC_CLASS) ? 12 : 1)
|
||||
+ left.costInline(thresh, env, ctx)
|
||||
+ right.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iadd + type.getTypeCodeOffset());
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert this expression to a string and append it to the string
|
||||
* buffer on the top of the stack.
|
||||
* If the needBuffer argument is true, the string buffer needs to be
|
||||
* created, initialized, and pushed on the stack, first.
|
||||
*/
|
||||
void codeAppend(Environment env, Context ctx, Assembler asm,
|
||||
ClassDeclaration sbClass, boolean needBuffer)
|
||||
throws ClassNotFound, AmbiguousMember {
|
||||
if (type.isType(TC_CLASS)) {
|
||||
left.codeAppend(env, ctx, asm, sbClass, needBuffer);
|
||||
right.codeAppend(env, ctx, asm, sbClass, false);
|
||||
} else {
|
||||
super.codeAppend(env, ctx, asm, sbClass, needBuffer);
|
||||
}
|
||||
}
|
||||
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (type.isType(TC_CLASS)) {
|
||||
try {
|
||||
// optimize (""+foo) or (foo+"") to String.valueOf(foo)
|
||||
if (left.equals("")) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
right.ensureString(env, ctx, asm);
|
||||
return;
|
||||
}
|
||||
if (right.equals("")) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
left.ensureString(env, ctx, asm);
|
||||
return;
|
||||
}
|
||||
|
||||
ClassDeclaration sbClass =
|
||||
env.getClassDeclaration(idJavaLangStringBuffer);
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
// Create the string buffer and append to it.
|
||||
codeAppend(env, ctx, asm, sbClass, true);
|
||||
// Convert the string buffer to a string
|
||||
MemberDefinition f =
|
||||
sbClass.getClassDefinition(env).matchMethod(env,
|
||||
sourceClass,
|
||||
idToString);
|
||||
asm.add(where, opc_invokevirtual, f);
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
} catch (AmbiguousMember e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
} else {
|
||||
super.codeValue(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
}
|
||||
115
jdkSrc/jdk8/sun/tools/tree/AndExpression.java
Normal file
115
jdkSrc/jdk8/sun/tools/tree/AndExpression.java
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AndExpression extends BinaryLogicalExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public AndExpression(long where, Expression left, Expression right) {
|
||||
super(AND, where, left, right);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check an "and" expression.
|
||||
*
|
||||
* cvars is modified so that
|
||||
* cvar.vsTrue indicates variables with a known value if
|
||||
* both the left and right hand side are true
|
||||
* cvars.vsFalse indicates variables with a known value
|
||||
* either the left or right hand side is false
|
||||
*/
|
||||
public void checkCondition(Environment env, Context ctx, Vset vset,
|
||||
Hashtable exp, ConditionVars cvars) {
|
||||
// Find out when the left side is true/false
|
||||
left.checkCondition(env, ctx, vset, exp, cvars);
|
||||
left = convert(env, ctx, Type.tBoolean, left);
|
||||
Vset vsTrue = cvars.vsTrue.copy();
|
||||
Vset vsFalse = cvars.vsFalse.copy();
|
||||
|
||||
// Only look at the right side if the left side is true
|
||||
right.checkCondition(env, ctx, vsTrue, exp, cvars);
|
||||
right = convert(env, ctx, Type.tBoolean, right);
|
||||
|
||||
// cvars.vsTrue already reports when both returned true
|
||||
// cvars.vsFalse must be set to either the left or right side
|
||||
// returning false
|
||||
cvars.vsFalse = cvars.vsFalse.join(vsFalse);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a && b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.equals(true)) {
|
||||
return right;
|
||||
}
|
||||
if (right.equals(false)) {
|
||||
// Preserve effects of left argument.
|
||||
return new CommaExpression(where, left, right).simplify();
|
||||
}
|
||||
if (right.equals(true)) {
|
||||
return left;
|
||||
}
|
||||
if (left.equals(false)) {
|
||||
return left;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
if (whenTrue) {
|
||||
Label lbl2 = new Label();
|
||||
left.codeBranch(env, ctx, asm, lbl2, false);
|
||||
right.codeBranch(env, ctx, asm, lbl, true);
|
||||
asm.add(lbl2);
|
||||
} else {
|
||||
left.codeBranch(env, ctx, asm, lbl, false);
|
||||
right.codeBranch(env, ctx, asm, lbl, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
271
jdkSrc/jdk8/sun/tools/tree/ArrayAccessExpression.java
Normal file
271
jdkSrc/jdk8/sun/tools/tree/ArrayAccessExpression.java
Normal file
@@ -0,0 +1,271 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ArrayAccessExpression extends UnaryExpression {
|
||||
|
||||
/**
|
||||
* The index expression for the array access. Note that
|
||||
* ArrayAccessExpression also `moonlights' as a structure for
|
||||
* storing array types (like Object[]) which are used as part
|
||||
* of cast expressions. For properly formed array types, the
|
||||
* value of index is null. We need to be on the lookout for
|
||||
* null indices in true array accesses, and non-null indices
|
||||
* in array types. We also need to make sure general purpose
|
||||
* methods (like copyInline(), which is called for both) are
|
||||
* prepared to handle either null or non-null indices.
|
||||
*/
|
||||
Expression index;
|
||||
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public ArrayAccessExpression(long where, Expression right, Expression index) {
|
||||
super(ARRAYACCESS, where, Type.tError, right);
|
||||
this.index = index;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check expression type
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
if (index == null) {
|
||||
env.error(where, "array.index.required");
|
||||
return vset;
|
||||
}
|
||||
vset = index.checkValue(env, ctx, vset, exp);
|
||||
index = convert(env, ctx, Type.tInt, index);
|
||||
|
||||
if (!right.type.isType(TC_ARRAY)) {
|
||||
if (!right.type.isType(TC_ERROR)) {
|
||||
env.error(where, "not.array", right.type);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
type = right.type.getElementType();
|
||||
return vset;
|
||||
}
|
||||
|
||||
public Vset checkAmbigName(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp,
|
||||
UnaryExpression loc) {
|
||||
if (index == null) {
|
||||
vset = right.checkAmbigName(env, ctx, vset, exp, this);
|
||||
if (right.type == Type.tPackage) {
|
||||
FieldExpression.reportFailedPackagePrefix(env, right);
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Nope. Is this field expression a type?
|
||||
if (right instanceof TypeExpression) {
|
||||
Type atype = Type.tArray(right.type);
|
||||
loc.right = new TypeExpression(where, atype);
|
||||
return vset;
|
||||
}
|
||||
|
||||
env.error(where, "array.index.required");
|
||||
return vset;
|
||||
}
|
||||
return super.checkAmbigName(env, ctx, vset, exp, loc);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check the array if it appears on the LHS of an assignment
|
||||
*/
|
||||
public Vset checkLHS(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check the array if it appears on the LHS of an op= expression
|
||||
*/
|
||||
public Vset checkAssignOp(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, Expression outside) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* An array access expression never requires the use of an access method to perform
|
||||
* an assignment to an array element, though an access method may be required to
|
||||
* fetch the array object itself.
|
||||
*/
|
||||
public FieldUpdater getAssigner(Environment env, Context ctx) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* An array access expression never requires a field updater.
|
||||
*/
|
||||
public FieldUpdater getUpdater(Environment env, Context ctx) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert to a type
|
||||
*/
|
||||
Type toType(Environment env, Context ctx) {
|
||||
return toType(env, right.toType(env, ctx));
|
||||
}
|
||||
Type toType(Environment env, Type t) {
|
||||
if (index != null) {
|
||||
env.error(index.where, "array.dim.in.type");
|
||||
}
|
||||
return Type.tArray(t);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
// It isn't possible to simply replace an array access
|
||||
// with a CommaExpression as happens with many binary
|
||||
// operators, because array accesses may have side effects
|
||||
// such as NullPointerException or IndexOutOfBoundsException.
|
||||
right = right.inlineValue(env, ctx);
|
||||
index = index.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
// inlineValue() should not end up being called when the index is
|
||||
// null. If it is null, we let this method fail with a
|
||||
// NullPointerException.
|
||||
|
||||
right = right.inlineValue(env, ctx);
|
||||
index = index.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
public Expression inlineLHS(Environment env, Context ctx) {
|
||||
return inlineValue(env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
ArrayAccessExpression e = (ArrayAccessExpression)clone();
|
||||
e.right = right.copyInline(ctx);
|
||||
if (index == null) {
|
||||
// The index can be null when this node is being used to
|
||||
// represent a type (e.g. Object[]) used in a cast expression.
|
||||
// We need to copy such structures without complaint.
|
||||
e.index = null;
|
||||
} else {
|
||||
e.index = index.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
// costInline() should not end up being called when the index is
|
||||
// null. If it is null, we let this method fail with a
|
||||
// NullPointerException.
|
||||
|
||||
return 1 + right.costInline(thresh, env, ctx)
|
||||
+ index.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
int codeLValue(Environment env, Context ctx, Assembler asm) {
|
||||
// codeLValue() should not end up being called when the index is
|
||||
// null. If it is null, we let this method fail with a
|
||||
// NullPointerException.
|
||||
|
||||
right.codeValue(env, ctx, asm);
|
||||
index.codeValue(env, ctx, asm);
|
||||
return 2;
|
||||
}
|
||||
void codeLoad(Environment env, Context ctx, Assembler asm) {
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
case TC_BYTE:
|
||||
asm.add(where, opc_baload);
|
||||
break;
|
||||
case TC_CHAR:
|
||||
asm.add(where, opc_caload);
|
||||
break;
|
||||
case TC_SHORT:
|
||||
asm.add(where, opc_saload);
|
||||
break;
|
||||
default:
|
||||
asm.add(where, opc_iaload + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
void codeStore(Environment env, Context ctx, Assembler asm) {
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
case TC_BYTE:
|
||||
asm.add(where, opc_bastore);
|
||||
break;
|
||||
case TC_CHAR:
|
||||
asm.add(where, opc_castore);
|
||||
break;
|
||||
case TC_SHORT:
|
||||
asm.add(where, opc_sastore);
|
||||
break;
|
||||
default:
|
||||
asm.add(where, opc_iastore + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeLValue(env, ctx, asm);
|
||||
codeLoad(env, ctx, asm);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
right.print(out);
|
||||
out.print(" ");
|
||||
if (index != null) {
|
||||
index.print(out);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
143
jdkSrc/jdk8/sun/tools/tree/ArrayExpression.java
Normal file
143
jdkSrc/jdk8/sun/tools/tree/ArrayExpression.java
Normal file
@@ -0,0 +1,143 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.*;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ArrayExpression extends NaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ArrayExpression(long where, Expression args[]) {
|
||||
super(ARRAY, where, Type.tError, null, args);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check expression type
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
env.error(where, "invalid.array.expr");
|
||||
return vset;
|
||||
}
|
||||
public Vset checkInitializer(Environment env, Context ctx, Vset vset, Type t, Hashtable exp) {
|
||||
if (!t.isType(TC_ARRAY)) {
|
||||
if (!t.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.array.init", t);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
type = t;
|
||||
t = t.getElementType();
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
vset = args[i].checkInitializer(env, ctx, vset, t, exp);
|
||||
args[i] = convert(env, ctx, t, args[i]);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
Expression e = null;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = args[i].inline(env, ctx);
|
||||
if (args[i] != null) {
|
||||
e = (e == null) ? args[i] : new CommaExpression(where, e, args[i]);
|
||||
}
|
||||
}
|
||||
return e;
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = args[i].inlineValue(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
int t = 0;
|
||||
asm.add(where, opc_ldc, new Integer(args.length));
|
||||
switch (type.getElementType().getTypeCode()) {
|
||||
case TC_BOOLEAN: asm.add(where, opc_newarray, new Integer(T_BOOLEAN)); break;
|
||||
case TC_BYTE: asm.add(where, opc_newarray, new Integer(T_BYTE)); break;
|
||||
case TC_SHORT: asm.add(where, opc_newarray, new Integer(T_SHORT)); break;
|
||||
case TC_CHAR: asm.add(where, opc_newarray, new Integer(T_CHAR)); break;
|
||||
case TC_INT: asm.add(where, opc_newarray, new Integer(T_INT)); break;
|
||||
case TC_LONG: asm.add(where, opc_newarray, new Integer(T_LONG)); break;
|
||||
case TC_FLOAT: asm.add(where, opc_newarray, new Integer(T_FLOAT)); break;
|
||||
case TC_DOUBLE: asm.add(where, opc_newarray, new Integer(T_DOUBLE)); break;
|
||||
|
||||
case TC_ARRAY:
|
||||
asm.add(where, opc_anewarray, type.getElementType());
|
||||
break;
|
||||
|
||||
case TC_CLASS:
|
||||
asm.add(where, opc_anewarray, env.getClassDeclaration(type.getElementType()));
|
||||
break;
|
||||
|
||||
default:
|
||||
throw new CompilerError("codeValue");
|
||||
}
|
||||
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
|
||||
// If the array element is the default initial value,
|
||||
// then don't bother generating code for this element.
|
||||
if (args[i].equalsDefault()) continue;
|
||||
|
||||
asm.add(where, opc_dup);
|
||||
asm.add(where, opc_ldc, new Integer(i));
|
||||
args[i].codeValue(env, ctx, asm);
|
||||
switch (type.getElementType().getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
case TC_BYTE:
|
||||
asm.add(where, opc_bastore);
|
||||
break;
|
||||
case TC_CHAR:
|
||||
asm.add(where, opc_castore);
|
||||
break;
|
||||
case TC_SHORT:
|
||||
asm.add(where, opc_sastore);
|
||||
break;
|
||||
default:
|
||||
asm.add(where, opc_iastore + type.getElementType().getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
149
jdkSrc/jdk8/sun/tools/tree/AssignAddExpression.java
Normal file
149
jdkSrc/jdk8/sun/tools/tree/AssignAddExpression.java
Normal file
@@ -0,0 +1,149 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignAddExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignAddExpression(long where, Expression left, Expression right) {
|
||||
super(ASGADD, where, left, right);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return type.isType(TC_CLASS) ? 25 : super.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void code(Environment env, Context ctx, Assembler asm, boolean valNeeded) {
|
||||
if (itype.isType(TC_CLASS)) {
|
||||
// Create code for String += <value>
|
||||
try {
|
||||
// Create new string buffer.
|
||||
Type argTypes[] = {Type.tString};
|
||||
ClassDeclaration c =
|
||||
env.getClassDeclaration(idJavaLangStringBuffer);
|
||||
|
||||
if (updater == null) {
|
||||
|
||||
// No access method is needed.
|
||||
|
||||
asm.add(where, opc_new, c);
|
||||
asm.add(where, opc_dup);
|
||||
// stack: ...<buffer><buffer>
|
||||
int depth = left.codeLValue(env, ctx, asm);
|
||||
codeDup(env, ctx, asm, depth, 2); // copy past 2 string buffers
|
||||
// stack: ...[<getter args>]<buffer><buffer>[<getter args>]
|
||||
// where <buffer> isn't yet initialized, and the <getter args>
|
||||
// has length depth and is whatever is needed to get/set the
|
||||
// value
|
||||
left.codeLoad(env, ctx, asm);
|
||||
left.ensureString(env, ctx, asm); // Why is this needed?
|
||||
// stack: ...[<getter args>]<buffer><buffer><string>
|
||||
// call .<init>(String)
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
MemberDefinition f = c.getClassDefinition(env)
|
||||
.matchMethod(env, sourceClass,
|
||||
idInit, argTypes);
|
||||
asm.add(where, opc_invokespecial, f);
|
||||
// stack: ...[<getter args>]<initialized buffer>
|
||||
// .append(value).toString()
|
||||
right.codeAppend(env, ctx, asm, c, false);
|
||||
f = c.getClassDefinition(env)
|
||||
.matchMethod(env, sourceClass, idToString);
|
||||
asm.add(where, opc_invokevirtual, f);
|
||||
// stack: ...[<getter args>]<string>
|
||||
// dup the string past the <getter args>, if necessary.
|
||||
if (valNeeded) {
|
||||
codeDup(env, ctx, asm, Type.tString.stackSize(), depth);
|
||||
// stack: ...<string>[<getter args>]<string>
|
||||
}
|
||||
// store
|
||||
left.codeStore(env, ctx, asm);
|
||||
|
||||
} else {
|
||||
|
||||
// Access method is required.
|
||||
// (Handling this case fixes 4102566.)
|
||||
|
||||
updater.startUpdate(env, ctx, asm, false);
|
||||
// stack: ...[<getter args>]<string>
|
||||
left.ensureString(env, ctx, asm); // Why is this needed?
|
||||
asm.add(where, opc_new, c);
|
||||
// stack: ...[<getter args>]<string><buffer>
|
||||
asm.add(where, opc_dup_x1);
|
||||
// stack: ...[<getter args>]<buffer><string><buffer>
|
||||
asm.add(where, opc_swap);
|
||||
// stack: ...[<getter args>]<buffer><buffer><string>
|
||||
// call .<init>(String)
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
MemberDefinition f = c.getClassDefinition(env)
|
||||
.matchMethod(env, sourceClass,
|
||||
idInit, argTypes);
|
||||
asm.add(where, opc_invokespecial, f);
|
||||
// stack: ...[<getter args>]<initialized buffer>
|
||||
// .append(value).toString()
|
||||
right.codeAppend(env, ctx, asm, c, false);
|
||||
f = c.getClassDefinition(env)
|
||||
.matchMethod(env, sourceClass, idToString);
|
||||
asm.add(where, opc_invokevirtual, f);
|
||||
// stack: .. [<getter args>]<string>
|
||||
updater.finishUpdate(env, ctx, asm, valNeeded);
|
||||
|
||||
}
|
||||
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
} catch (AmbiguousMember e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
} else {
|
||||
super.code(env, ctx, asm, valNeeded);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iadd + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
52
jdkSrc/jdk8/sun/tools/tree/AssignBitAndExpression.java
Normal file
52
jdkSrc/jdk8/sun/tools/tree/AssignBitAndExpression.java
Normal file
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignBitAndExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignBitAndExpression(long where, Expression left, Expression right) {
|
||||
super(ASGBITAND, where, left, right);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iand + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
52
jdkSrc/jdk8/sun/tools/tree/AssignBitOrExpression.java
Normal file
52
jdkSrc/jdk8/sun/tools/tree/AssignBitOrExpression.java
Normal file
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignBitOrExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignBitOrExpression(long where, Expression left, Expression right) {
|
||||
super(ASGBITOR, where, left, right);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ior + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignBitXorExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignBitXorExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignBitXorExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignBitXorExpression(long where, Expression left, Expression right) {
|
||||
super(ASGBITXOR, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ixor + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignDivideExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignDivideExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignDivideExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignDivideExpression(long where, Expression left, Expression right) {
|
||||
super(ASGDIV, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_idiv + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
157
jdkSrc/jdk8/sun/tools/tree/AssignExpression.java
Normal file
157
jdkSrc/jdk8/sun/tools/tree/AssignExpression.java
Normal file
@@ -0,0 +1,157 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignExpression extends BinaryAssignExpression {
|
||||
|
||||
private FieldUpdater updater = null;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignExpression(long where, Expression left, Expression right) {
|
||||
super(ASSIGN, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check an assignment expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
if (left instanceof IdentifierExpression) {
|
||||
// we don't want to mark an identifier as having a value
|
||||
// until having evaluated the right-hand side
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
vset = left.checkLHS(env, ctx, vset, exp);
|
||||
} else {
|
||||
// normally left to right evaluation.
|
||||
vset = left.checkLHS(env, ctx, vset, exp);
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
type = left.type;
|
||||
right = convert(env, ctx, type, right);
|
||||
|
||||
// Get field updater (access method) if needed, else null.
|
||||
updater = left.getAssigner(env, ctx);
|
||||
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inlineValue(env, ctx);
|
||||
// Must be 'inlineLHS' here. But compare with similar case in
|
||||
// 'AssignOpExpression' and 'IncDecExpression', which needs 'inlineValue'.
|
||||
left = left.inlineLHS(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
if (updater != null) {
|
||||
updater = updater.inline(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.copyInline(ctx);
|
||||
AssignExpression e = (AssignExpression)clone();
|
||||
e.left = left.copyInline(ctx);
|
||||
e.right = right.copyInline(ctx);
|
||||
if (updater != null) {
|
||||
e.updater = updater.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
/*----------*
|
||||
return 2 + super.costInline(thresh, env, ctx);
|
||||
*----------*/
|
||||
return (updater != null)
|
||||
// Cost of rhs expression + cost of access method call.
|
||||
// Access method call cost includes lhs cost.
|
||||
? right.costInline(thresh, env, ctx) +
|
||||
updater.costInline(thresh, env, ctx, false)
|
||||
// Cost of rhs expression + cost of lhs expression +
|
||||
// cost of store instruction.
|
||||
: right.costInline(thresh, env, ctx) +
|
||||
left.costInline(thresh, env, ctx) + 2;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (updater == null) {
|
||||
// Field is directly accessible.
|
||||
int depth = left.codeLValue(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeDup(env, ctx, asm, right.type.stackSize(), depth);
|
||||
left.codeStore(env, ctx, asm);
|
||||
} else {
|
||||
// Must use access method.
|
||||
// Left operand is always a 'FieldExpression', or
|
||||
// is rewritten as one via 'implementation'.
|
||||
updater.startAssign(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
updater.finishAssign(env, ctx, asm, true);
|
||||
}
|
||||
}
|
||||
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
if (updater == null) {
|
||||
// Field is directly accessible.
|
||||
left.codeLValue(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
left.codeStore(env, ctx, asm);
|
||||
} else {
|
||||
// Must use access method.
|
||||
// Left operand is always a 'FieldExpression', or
|
||||
// is rewritten as one via 'implementation'.
|
||||
updater.startAssign(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
updater.finishAssign(env, ctx, asm, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignMultiplyExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignMultiplyExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignMultiplyExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignMultiplyExpression(long where, Expression left, Expression right) {
|
||||
super(ASGMUL, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_imul + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
282
jdkSrc/jdk8/sun/tools/tree/AssignOpExpression.java
Normal file
282
jdkSrc/jdk8/sun/tools/tree/AssignOpExpression.java
Normal file
@@ -0,0 +1,282 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public abstract
|
||||
class AssignOpExpression extends BinaryAssignExpression {
|
||||
protected Type itype; // Type of intermediate result, before assigning
|
||||
final int NOINC = Integer.MAX_VALUE;
|
||||
|
||||
protected FieldUpdater updater = null; // Used also in 'AssignAddExpression'.
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignOpExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*
|
||||
*/
|
||||
|
||||
final void selectType(Environment env, Context ctx, int tm) {
|
||||
Type rtype = null; // special conversion type for RHS
|
||||
switch(op) {
|
||||
case ASGADD:
|
||||
if (left.type == Type.tString) {
|
||||
if (right.type == Type.tVoid) {
|
||||
// The type of the right hand side can be
|
||||
// anything except void. Fix for 4119864.
|
||||
env.error(where, "incompatible.type",
|
||||
opNames[op], Type.tVoid, Type.tString);
|
||||
type = Type.tError;
|
||||
} else {
|
||||
type = itype = Type.tString;
|
||||
}
|
||||
return;
|
||||
}
|
||||
/* Fall through */
|
||||
case ASGDIV: case ASGMUL: case ASGSUB: case ASGREM:
|
||||
if ((tm & TM_DOUBLE) != 0) {
|
||||
itype = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
itype = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
itype = Type.tLong;
|
||||
} else {
|
||||
itype = Type.tInt;
|
||||
}
|
||||
break;
|
||||
|
||||
case ASGBITAND: case ASGBITOR: case ASGBITXOR:
|
||||
if ((tm & TM_BOOLEAN) != 0) {
|
||||
itype = Type.tBoolean;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
itype = Type.tLong;
|
||||
} else {
|
||||
itype = Type.tInt;
|
||||
}
|
||||
break;
|
||||
|
||||
case ASGLSHIFT: case ASGRSHIFT: case ASGURSHIFT:
|
||||
rtype = Type.tInt;
|
||||
|
||||
// Fix for bug 4134459.
|
||||
// We allow any integral type (even long) to
|
||||
// be the right hand side of a shift operation.
|
||||
if (right.type.inMask(TM_INTEGER)) {
|
||||
right = new ConvertExpression(where, Type.tInt, right);
|
||||
}
|
||||
// The intermediate type of the expression is the
|
||||
// type of the left hand side after undergoing
|
||||
// unary (not binary) type promotion. We ignore
|
||||
// tm -- it contains information about both left
|
||||
// and right hand sides -- and we compute the
|
||||
// type only from the type of the lhs.
|
||||
if (left.type == Type.tLong) {
|
||||
itype = Type.tLong;
|
||||
} else {
|
||||
itype = Type.tInt;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
throw new CompilerError("Bad assignOp type: " + op);
|
||||
}
|
||||
if (rtype == null) {
|
||||
rtype = itype;
|
||||
}
|
||||
right = convert(env, ctx, rtype, right);
|
||||
// The result is always the type of the left operand.
|
||||
|
||||
type = left.type;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the increment, return NOINC if an increment is not possible
|
||||
*/
|
||||
int getIncrement() {
|
||||
if ((left.op == IDENT) && type.isType(TC_INT) && (right.op == INTVAL))
|
||||
if ((op == ASGADD) || (op == ASGSUB))
|
||||
if (((IdentifierExpression)left).field.isLocal()) {
|
||||
int val = ((IntExpression)right).value;
|
||||
if (op == ASGSUB)
|
||||
val = -val;
|
||||
if (val == (short)val)
|
||||
return val;
|
||||
}
|
||||
return NOINC;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Check an assignment expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = left.checkAssignOp(env, ctx, vset, exp, this);
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
int tm = left.type.getTypeMask() | right.type.getTypeMask();
|
||||
if ((tm & TM_ERROR) != 0) {
|
||||
return vset;
|
||||
}
|
||||
selectType(env, ctx, tm);
|
||||
if (!type.isType(TC_ERROR)) {
|
||||
convert(env, ctx, itype, left);
|
||||
}
|
||||
updater = left.getUpdater(env, ctx); // Must be called after 'checkAssignOp'.
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
// Why not inlineLHS? But that does not work.
|
||||
left = left.inlineValue(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
if (updater != null) {
|
||||
updater = updater.inline(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
AssignOpExpression e = (AssignOpExpression)clone();
|
||||
e.left = left.copyInline(ctx);
|
||||
e.right = right.copyInline(ctx);
|
||||
if (updater != null) {
|
||||
e.updater = updater.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
/*----------*
|
||||
return (getIncrement() != NOINC)
|
||||
? 2
|
||||
: (3 + super.costInline(thresh, env, ctx));
|
||||
*----------*/
|
||||
if (updater == null) {
|
||||
return (getIncrement() != NOINC)
|
||||
// Increment variable in place. Count 3 bytes for 'iinc'.
|
||||
? 3
|
||||
// Cost of rhs expression + cost of lhs expression + cost
|
||||
// of load/op/store instructions. E.g.: iload = 1 or 2,
|
||||
// istore = 1 or 2, iadd = 1. Cost could be higher if
|
||||
// getfield/putfield or conversions needed, lower if rhs is
|
||||
// a small constant. Costs are highly approximate.
|
||||
: right.costInline(thresh, env, ctx) +
|
||||
left.costInline(thresh, env, ctx) + 4;
|
||||
} else {
|
||||
// Cost of rhs expression + (2 * cost of access method call) +
|
||||
// cost of operator. Does not account for cost of conversions,
|
||||
// or duplications in value-needed context.
|
||||
return right.costInline(thresh, env, ctx) +
|
||||
updater.costInline(thresh, env, ctx, true) + 1;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void code(Environment env, Context ctx, Assembler asm, boolean valNeeded) {
|
||||
|
||||
// Handle cases in which a '+=' or '-=' operator can be optimized using
|
||||
// the 'iinc' instruction. See also 'IncDecExpression.codeIncDec'.
|
||||
// The 'iinc' instruction cannot be used if an access method call is required.
|
||||
int val = getIncrement();
|
||||
if (val != NOINC && updater == null) {
|
||||
int v = ((LocalMember)((IdentifierExpression)left).field).number;
|
||||
int[] operands = { v, val };
|
||||
asm.add(where, opc_iinc, operands);
|
||||
if (valNeeded) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (updater == null) {
|
||||
// Field is directly accessible.
|
||||
int depth = left.codeLValue(env, ctx, asm);
|
||||
codeDup(env, ctx, asm, depth, 0);
|
||||
left.codeLoad(env, ctx, asm);
|
||||
codeConversion(env, ctx, asm, left.type, itype);
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeOperation(env, ctx, asm);
|
||||
codeConversion(env, ctx, asm, itype, type);
|
||||
if (valNeeded) {
|
||||
codeDup(env, ctx, asm, type.stackSize(), depth);
|
||||
}
|
||||
left.codeStore(env, ctx, asm);
|
||||
} else {
|
||||
// Must use access methods.
|
||||
updater.startUpdate(env, ctx, asm, false);
|
||||
codeConversion(env, ctx, asm, left.type, itype);
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeOperation(env, ctx, asm);
|
||||
codeConversion(env, ctx, asm, itype, type);
|
||||
updater.finishUpdate(env, ctx, asm, valNeeded);
|
||||
}
|
||||
}
|
||||
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
code(env, ctx, asm, true);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
code(env, ctx, asm, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
left.print(out);
|
||||
out.print(" ");
|
||||
right.print(out);
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignRemainderExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignRemainderExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignRemainderExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignRemainderExpression(long where, Expression left, Expression right) {
|
||||
super(ASGREM, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_irem + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
52
jdkSrc/jdk8/sun/tools/tree/AssignShiftLeftExpression.java
Normal file
52
jdkSrc/jdk8/sun/tools/tree/AssignShiftLeftExpression.java
Normal file
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignShiftLeftExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignShiftLeftExpression(long where, Expression left, Expression right) {
|
||||
super(ASGLSHIFT, where, left, right);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ishl + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignShiftRightExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignShiftRightExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignShiftRightExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignShiftRightExpression(long where, Expression left, Expression right) {
|
||||
super(ASGRSHIFT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ishr + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/AssignSubtractExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/AssignSubtractExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignSubtractExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignSubtractExpression(long where, Expression left, Expression right) {
|
||||
super(ASGSUB, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_isub + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class AssignUnsignedShiftRightExpression extends AssignOpExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public AssignUnsignedShiftRightExpression(long where, Expression left, Expression right) {
|
||||
super(ASGURSHIFT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iushr + itype.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
60
jdkSrc/jdk8/sun/tools/tree/BinaryArithmeticExpression.java
Normal file
60
jdkSrc/jdk8/sun/tools/tree/BinaryArithmeticExpression.java
Normal file
@@ -0,0 +1,60 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryArithmeticExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryArithmeticExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left.type, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((tm & TM_DOUBLE) != 0) {
|
||||
type = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
type = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
left = convert(env, ctx, type, left);
|
||||
right = convert(env, ctx, type, right);
|
||||
}
|
||||
}
|
||||
101
jdkSrc/jdk8/sun/tools/tree/BinaryAssignExpression.java
Normal file
101
jdkSrc/jdk8/sun/tools/tree/BinaryAssignExpression.java
Normal file
@@ -0,0 +1,101 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryAssignExpression extends BinaryExpression {
|
||||
Expression implementation;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
BinaryAssignExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left.type, left, right);
|
||||
}
|
||||
|
||||
public Expression getImplementation() {
|
||||
if (implementation != null)
|
||||
return implementation;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Order the expression based on precedence
|
||||
*/
|
||||
public Expression order() {
|
||||
if (precedence() >= left.precedence()) {
|
||||
UnaryExpression e = (UnaryExpression)left;
|
||||
left = e.right;
|
||||
e.right = order();
|
||||
return e;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check void expression
|
||||
*/
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inline(env, ctx);
|
||||
return inlineValue(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inlineValue(env, ctx);
|
||||
left = left.inlineLHS(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Expression copyInline(Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.copyInline(ctx);
|
||||
return super.copyInline(ctx);
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.costInline(thresh, env, ctx);
|
||||
return super.costInline(thresh, env, ctx);
|
||||
}
|
||||
}
|
||||
69
jdkSrc/jdk8/sun/tools/tree/BinaryBitExpression.java
Normal file
69
jdkSrc/jdk8/sun/tools/tree/BinaryBitExpression.java
Normal file
@@ -0,0 +1,69 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
abstract public
|
||||
class BinaryBitExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryBitExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left.type, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((tm & TM_BOOLEAN) != 0) {
|
||||
type = Type.tBoolean;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
left = convert(env, ctx, type, left);
|
||||
right = convert(env, ctx, type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeOperation(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
59
jdkSrc/jdk8/sun/tools/tree/BinaryCompareExpression.java
Normal file
59
jdkSrc/jdk8/sun/tools/tree/BinaryCompareExpression.java
Normal file
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryCompareExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryCompareExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, Type.tBoolean, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
Type t = Type.tInt;
|
||||
if ((tm & TM_DOUBLE) != 0) {
|
||||
t = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
t = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
t = Type.tLong;
|
||||
}
|
||||
left = convert(env, ctx, t, left);
|
||||
right = convert(env, ctx, t, right);
|
||||
}
|
||||
}
|
||||
78
jdkSrc/jdk8/sun/tools/tree/BinaryEqualityExpression.java
Normal file
78
jdkSrc/jdk8/sun/tools/tree/BinaryEqualityExpression.java
Normal file
@@ -0,0 +1,78 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryEqualityExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryEqualityExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, Type.tBoolean, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
Type t;
|
||||
if ((tm & TM_ERROR) != 0) {
|
||||
// who cares. One of them is an error.
|
||||
return;
|
||||
} else if ((tm & (TM_CLASS | TM_ARRAY | TM_NULL)) != 0) {
|
||||
try {
|
||||
if (env.explicitCast(left.type, right.type) ||
|
||||
env.explicitCast(right.type, left.type)) {
|
||||
return;
|
||||
}
|
||||
env.error(where, "incompatible.type",
|
||||
left.type, left.type, right.type);
|
||||
} catch (ClassNotFound e) {
|
||||
env.error(where, "class.not.found", e.name, opNames[op]);
|
||||
}
|
||||
return;
|
||||
} else if ((tm & TM_DOUBLE) != 0) {
|
||||
t = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
t = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
t = Type.tLong;
|
||||
} else if ((tm & TM_BOOLEAN) != 0) {
|
||||
t = Type.tBoolean;
|
||||
} else {
|
||||
t = Type.tInt;
|
||||
}
|
||||
left = convert(env, ctx, t, left);
|
||||
right = convert(env, ctx, t, right);
|
||||
}
|
||||
}
|
||||
245
jdkSrc/jdk8/sun/tools/tree/BinaryExpression.java
Normal file
245
jdkSrc/jdk8/sun/tools/tree/BinaryExpression.java
Normal file
@@ -0,0 +1,245 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Label;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryExpression extends UnaryExpression {
|
||||
Expression left;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
BinaryExpression(int op, long where, Type type, Expression left, Expression right) {
|
||||
super(op, where, type, right);
|
||||
this.left = left;
|
||||
}
|
||||
|
||||
/**
|
||||
* Order the expression based on precedence
|
||||
*/
|
||||
public Expression order() {
|
||||
if (precedence() > left.precedence()) {
|
||||
UnaryExpression e = (UnaryExpression)left;
|
||||
left = e.right;
|
||||
e.right = order();
|
||||
return e;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check a binary expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = left.checkValue(env, ctx, vset, exp);
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
|
||||
int tm = left.type.getTypeMask() | right.type.getTypeMask();
|
||||
if ((tm & TM_ERROR) != 0) {
|
||||
return vset;
|
||||
}
|
||||
selectType(env, ctx, tm);
|
||||
|
||||
if (type.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.args", opNames[op]);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if constant
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
switch (op) {
|
||||
case MUL:
|
||||
case DIV:
|
||||
case REM:
|
||||
case ADD:
|
||||
case SUB:
|
||||
case LSHIFT:
|
||||
case RSHIFT:
|
||||
case URSHIFT:
|
||||
case LT:
|
||||
case LE:
|
||||
case GT:
|
||||
case GE:
|
||||
case EQ:
|
||||
case NE:
|
||||
case BITAND:
|
||||
case BITXOR:
|
||||
case BITOR:
|
||||
case AND:
|
||||
case OR:
|
||||
return left.isConstant() && right.isConstant();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval(String a, String b) {
|
||||
return this;
|
||||
}
|
||||
Expression eval() {
|
||||
// See also the eval() code in BinaryShiftExpression.java.
|
||||
if (left.op == right.op) {
|
||||
switch (left.op) {
|
||||
case BYTEVAL:
|
||||
case CHARVAL:
|
||||
case SHORTVAL:
|
||||
case INTVAL:
|
||||
return eval(((IntegerExpression)left).value, ((IntegerExpression)right).value);
|
||||
case LONGVAL:
|
||||
return eval(((LongExpression)left).value, ((LongExpression)right).value);
|
||||
case FLOATVAL:
|
||||
return eval(((FloatExpression)left).value, ((FloatExpression)right).value);
|
||||
case DOUBLEVAL:
|
||||
return eval(((DoubleExpression)left).value, ((DoubleExpression)right).value);
|
||||
case BOOLEANVAL:
|
||||
return eval(((BooleanExpression)left).value, ((BooleanExpression)right).value);
|
||||
case STRINGVAL:
|
||||
return eval(((StringExpression)left).value, ((StringExpression)right).value);
|
||||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
left = left.inline(env, ctx);
|
||||
right = right.inline(env, ctx);
|
||||
return (left == null) ? right : new CommaExpression(where, left, right);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
left = left.inlineValue(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
try {
|
||||
return eval().simplify();
|
||||
} catch (ArithmeticException e) {
|
||||
// Got rid of this error message. It isn't illegal to
|
||||
// have a program which does a constant division by
|
||||
// zero. We return `this' to make the compiler to
|
||||
// generate code here.
|
||||
// (bugs 4019304, 4089107).
|
||||
//
|
||||
// env.error(where, "arithmetic.exception");
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
BinaryExpression e = (BinaryExpression)clone();
|
||||
if (left != null) {
|
||||
e.left = left.copyInline(ctx);
|
||||
}
|
||||
if (right != null) {
|
||||
e.right = right.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1 + ((left != null) ? left.costInline(thresh, env, ctx) : 0) +
|
||||
((right != null) ? right.costInline(thresh, env, ctx) : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
throw new CompilerError("codeOperation: " + opNames[op]);
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (type.isType(TC_BOOLEAN)) {
|
||||
Label l1 = new Label();
|
||||
Label l2 = new Label();
|
||||
|
||||
codeBranch(env, ctx, asm, l1, true);
|
||||
asm.add(true, where, opc_ldc, new Integer(0));
|
||||
asm.add(true, where, opc_goto, l2);
|
||||
asm.add(l1);
|
||||
asm.add(true, where, opc_ldc, new Integer(1));
|
||||
asm.add(l2);
|
||||
} else {
|
||||
left.codeValue(env, ctx, asm);
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeOperation(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
if (left != null) {
|
||||
left.print(out);
|
||||
} else {
|
||||
out.print("<null>");
|
||||
}
|
||||
out.print(" ");
|
||||
if (right != null) {
|
||||
right.print(out);
|
||||
} else {
|
||||
out.print("<null>");
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
75
jdkSrc/jdk8/sun/tools/tree/BinaryLogicalExpression.java
Normal file
75
jdkSrc/jdk8/sun/tools/tree/BinaryLogicalExpression.java
Normal file
@@ -0,0 +1,75 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
abstract public
|
||||
class BinaryLogicalExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryLogicalExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, Type.tBoolean, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check a binary expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp) {
|
||||
ConditionVars cvars = new ConditionVars();
|
||||
// evaluate the logical expression, determining which variables are
|
||||
// set if the resulting value is true or false
|
||||
checkCondition(env, ctx, vset, exp, cvars);
|
||||
// return the intersection.
|
||||
return cvars.vsTrue.join(cvars.vsFalse);
|
||||
}
|
||||
|
||||
/*
|
||||
* Every subclass of this class must define a genuine implementation
|
||||
* of this method. It cannot inherit the method of Expression.
|
||||
*/
|
||||
abstract
|
||||
public void checkCondition(Environment env, Context ctx, Vset vset,
|
||||
Hashtable exp, ConditionVars cvars);
|
||||
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
left = left.inlineValue(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
}
|
||||
80
jdkSrc/jdk8/sun/tools/tree/BinaryShiftExpression.java
Normal file
80
jdkSrc/jdk8/sun/tools/tree/BinaryShiftExpression.java
Normal file
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BinaryShiftExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BinaryShiftExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left.type, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate the expression
|
||||
*/
|
||||
Expression eval() {
|
||||
// The eval code in BinaryExpression.java only works correctly
|
||||
// for arithmetic expressions. For shift expressions, we get cases
|
||||
// where the left and right operand may legitimately be of mixed
|
||||
// types (long and int). This is a fix for 4082814.
|
||||
if (left.op == LONGVAL && right.op == INTVAL) {
|
||||
return eval(((LongExpression)left).value,
|
||||
((IntExpression)right).value);
|
||||
}
|
||||
|
||||
// Delegate the rest of the cases to our parent, so as to minimize
|
||||
// impact on existing behavior.
|
||||
return super.eval();
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if (left.type == Type.tLong) {
|
||||
type = Type.tLong;
|
||||
} else if (left.type.inMask(TM_INTEGER)) {
|
||||
type = Type.tInt;
|
||||
left = convert(env, ctx, type, left);
|
||||
} else {
|
||||
type = Type.tError;
|
||||
}
|
||||
if (right.type.inMask(TM_INTEGER)) {
|
||||
right = new ConvertExpression(where, Type.tInt, right);
|
||||
} else {
|
||||
right = convert(env, ctx, Type.tInt, right);
|
||||
}
|
||||
}
|
||||
}
|
||||
79
jdkSrc/jdk8/sun/tools/tree/BitAndExpression.java
Normal file
79
jdkSrc/jdk8/sun/tools/tree/BitAndExpression.java
Normal file
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BitAndExpression extends BinaryBitExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BitAndExpression(long where, Expression left, Expression right) {
|
||||
super(BITAND, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a & b);
|
||||
}
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a & b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a & b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.equals(true))
|
||||
return right;
|
||||
if (right.equals(true))
|
||||
return left;
|
||||
if (left.equals(false) || left.equals(0))
|
||||
return new CommaExpression(where, right, left).simplify();
|
||||
if (right.equals(false) || right.equals(0))
|
||||
return new CommaExpression(where, left, right).simplify();
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iand + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
90
jdkSrc/jdk8/sun/tools/tree/BitNotExpression.java
Normal file
90
jdkSrc/jdk8/sun/tools/tree/BitNotExpression.java
Normal file
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BitNotExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public BitNotExpression(long where, Expression right) {
|
||||
super(BITNOT, where, right.type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
right = convert(env, ctx, type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a) {
|
||||
return new IntExpression(where, ~a);
|
||||
}
|
||||
Expression eval(long a) {
|
||||
return new LongExpression(where, ~a);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (right.op == BITNOT) {
|
||||
return ((BitNotExpression)right).right;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
if (type.isType(TC_INT)) {
|
||||
asm.add(where, opc_ldc, new Integer(-1));
|
||||
asm.add(where, opc_ixor);
|
||||
} else {
|
||||
asm.add(where, opc_ldc2_w, new Long(-1));
|
||||
asm.add(where, opc_lxor);
|
||||
}
|
||||
}
|
||||
}
|
||||
79
jdkSrc/jdk8/sun/tools/tree/BitOrExpression.java
Normal file
79
jdkSrc/jdk8/sun/tools/tree/BitOrExpression.java
Normal file
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BitOrExpression extends BinaryBitExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BitOrExpression(long where, Expression left, Expression right) {
|
||||
super(BITOR, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a | b);
|
||||
}
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a | b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a | b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.equals(false) || left.equals(0))
|
||||
return right;
|
||||
if (right.equals(false) || right.equals(0))
|
||||
return left;
|
||||
if (left.equals(true))
|
||||
return new CommaExpression(where, right, left).simplify();
|
||||
if (right.equals(true))
|
||||
return new CommaExpression(where, left, right).simplify();
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ior + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
84
jdkSrc/jdk8/sun/tools/tree/BitXorExpression.java
Normal file
84
jdkSrc/jdk8/sun/tools/tree/BitXorExpression.java
Normal file
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BitXorExpression extends BinaryBitExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public BitXorExpression(long where, Expression left, Expression right) {
|
||||
super(BITXOR, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a ^ b);
|
||||
}
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a ^ b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a ^ b);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.equals(true)) {
|
||||
return new NotExpression(where, right);
|
||||
}
|
||||
if (right.equals(true)) {
|
||||
return new NotExpression(where, left);
|
||||
}
|
||||
if (left.equals(false) || left.equals(0)) {
|
||||
return right;
|
||||
}
|
||||
if (right.equals(false) || right.equals(0)) {
|
||||
return left;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ixor + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
118
jdkSrc/jdk8/sun/tools/tree/BooleanExpression.java
Normal file
118
jdkSrc/jdk8/sun/tools/tree/BooleanExpression.java
Normal file
@@ -0,0 +1,118 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BooleanExpression extends ConstantExpression {
|
||||
boolean value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public BooleanExpression(long where, boolean value) {
|
||||
super(BOOLEANVAL, where, Type.tBoolean);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return new Integer(value ? 1 : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(boolean b) {
|
||||
return value == b;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
return !value;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Check a "not" expression.
|
||||
*
|
||||
* cvars is modified so that
|
||||
* cvar.vsTrue indicates variables with a known value if
|
||||
* the expression is true.
|
||||
* cvars.vsFalse indicates variables with a known value if
|
||||
* the expression is false
|
||||
*
|
||||
* For constant expressions, set the side that corresponds to our
|
||||
* already known value to vset. Set the side that corresponds to the
|
||||
* other way to "impossible"
|
||||
*/
|
||||
|
||||
public void checkCondition(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, ConditionVars cvars) {
|
||||
if (value) {
|
||||
cvars.vsFalse = Vset.DEAD_END;
|
||||
cvars.vsTrue = vset;
|
||||
} else {
|
||||
cvars.vsFalse = vset;
|
||||
cvars.vsTrue = Vset.DEAD_END;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
if (value == whenTrue) {
|
||||
asm.add(where, opc_goto, lbl);
|
||||
}
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc, new Integer(value ? 1 : 0));
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value ? "true" : "false");
|
||||
}
|
||||
}
|
||||
106
jdkSrc/jdk8/sun/tools/tree/BreakStatement.java
Normal file
106
jdkSrc/jdk8/sun/tools/tree/BreakStatement.java
Normal file
@@ -0,0 +1,106 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class BreakStatement extends Statement {
|
||||
Identifier lbl;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public BreakStatement(long where, Identifier lbl) {
|
||||
super(BREAK, where);
|
||||
this.lbl = lbl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
reach(env, vset);
|
||||
checkLabel(env, ctx);
|
||||
CheckContext destctx = (CheckContext)new CheckContext(ctx, this).getBreakContext(lbl);
|
||||
if (destctx != null) {
|
||||
if (destctx.frameNumber != ctx.frameNumber) {
|
||||
env.error(where, "branch.to.uplevel", lbl);
|
||||
}
|
||||
destctx.vsBreak = destctx.vsBreak.join(vset);
|
||||
} else {
|
||||
if (lbl != null) {
|
||||
env.error(where, "label.not.found", lbl);
|
||||
} else {
|
||||
env.error(where, "invalid.break");
|
||||
}
|
||||
}
|
||||
CheckContext exitctx = ctx.getTryExitContext();
|
||||
if (exitctx != null) {
|
||||
exitctx.vsTryExit = exitctx.vsTryExit.join(vset);
|
||||
}
|
||||
return DEAD_END;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
CodeContext destctx = (CodeContext)newctx.getBreakContext(lbl);
|
||||
codeFinally(env, ctx, asm, destctx, null);
|
||||
asm.add(where, opc_goto, destctx.breakLabel);
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("break");
|
||||
if (lbl != null) {
|
||||
out.print(" " + lbl);
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/ByteExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/ByteExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ByteExpression extends IntegerExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ByteExpression(long where, byte value) {
|
||||
super(BYTEVAL, where, Type.tByte, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value + "b");
|
||||
}
|
||||
}
|
||||
81
jdkSrc/jdk8/sun/tools/tree/CaseStatement.java
Normal file
81
jdkSrc/jdk8/sun/tools/tree/CaseStatement.java
Normal file
@@ -0,0 +1,81 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CaseStatement extends Statement {
|
||||
Expression expr;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public CaseStatement(long where, Expression expr) {
|
||||
super(CASE, where);
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
if (expr != null) {
|
||||
expr.checkValue(env, ctx, vset, exp);
|
||||
expr = convert(env, ctx, Type.tInt, expr);
|
||||
expr = expr.inlineValue(env, ctx);
|
||||
}
|
||||
return vset.clearDeadEnd();
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 6;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
if (expr == null) {
|
||||
out.print("default");
|
||||
} else {
|
||||
out.print("case ");
|
||||
expr.print(out);
|
||||
}
|
||||
out.print(":");
|
||||
}
|
||||
}
|
||||
135
jdkSrc/jdk8/sun/tools/tree/CastExpression.java
Normal file
135
jdkSrc/jdk8/sun/tools/tree/CastExpression.java
Normal file
@@ -0,0 +1,135 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CastExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public CastExpression(long where, Expression left, Expression right) {
|
||||
super(CAST, where, left.type, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
type = left.toType(env, ctx);
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
|
||||
if (type.isType(TC_ERROR) || right.type.isType(TC_ERROR)) {
|
||||
// An error was already reported
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (type.equals(right.type)) {
|
||||
// The types are already the same
|
||||
return vset;
|
||||
}
|
||||
|
||||
try {
|
||||
if (env.explicitCast(right.type, type)) {
|
||||
right = new ConvertExpression(where, type, right);
|
||||
return vset;
|
||||
}
|
||||
} catch (ClassNotFound e) {
|
||||
env.error(where, "class.not.found", e.name, opNames[op]);
|
||||
}
|
||||
|
||||
// The cast is not allowed
|
||||
env.error(where, "invalid.cast", right.type, type);
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if constant
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
if (type.inMask(TM_REFERENCE) && !type.equals(Type.tString)) {
|
||||
// must be a primitive type, or String
|
||||
return false;
|
||||
}
|
||||
return right.isConstant();
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return right.inline(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
return right.inlineValue(env, ctx);
|
||||
}
|
||||
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (ctx == null) {
|
||||
return 1 + right.costInline(thresh, env, ctx);
|
||||
}
|
||||
// sourceClass is the current class trying to inline this method
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
try {
|
||||
// We only allow the inlining if the current class can access
|
||||
// the casting class
|
||||
if (left.type.isType(TC_ARRAY) ||
|
||||
sourceClass.permitInlinedAccess(env,
|
||||
env.getClassDeclaration(left.type)))
|
||||
return 1 + right.costInline(thresh, env, ctx);
|
||||
} catch (ClassNotFound e) {
|
||||
}
|
||||
return thresh;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
if (type.isType(TC_ERROR)) {
|
||||
left.print(out);
|
||||
} else {
|
||||
out.print(type);
|
||||
}
|
||||
out.print(" ");
|
||||
right.print(out);
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
173
jdkSrc/jdk8/sun/tools/tree/CatchStatement.java
Normal file
173
jdkSrc/jdk8/sun/tools/tree/CatchStatement.java
Normal file
@@ -0,0 +1,173 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2004, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.LocalVariable;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CatchStatement extends Statement {
|
||||
int mod;
|
||||
Expression texpr;
|
||||
Identifier id;
|
||||
Statement body;
|
||||
LocalMember field;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public CatchStatement(long where, Expression texpr, IdentifierToken id, Statement body) {
|
||||
super(CATCH, where);
|
||||
this.mod = id.getModifiers();
|
||||
this.texpr = texpr;
|
||||
this.id = id.getName();
|
||||
this.body = body;
|
||||
}
|
||||
/** @deprecated */
|
||||
@Deprecated
|
||||
public CatchStatement(long where, Expression texpr, Identifier id, Statement body) {
|
||||
super(CATCH, where);
|
||||
this.texpr = texpr;
|
||||
this.id = id;
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = reach(env, vset);
|
||||
ctx = new Context(ctx, this);
|
||||
Type type = texpr.toType(env, ctx);
|
||||
|
||||
try {
|
||||
if (ctx.getLocalField(id) != null) {
|
||||
env.error(where, "local.redefined", id);
|
||||
}
|
||||
|
||||
if (type.isType(TC_ERROR)) {
|
||||
// error message printed out elsewhere
|
||||
} else if (!type.isType(TC_CLASS)) {
|
||||
env.error(where, "catch.not.throwable", type);
|
||||
} else {
|
||||
ClassDefinition def = env.getClassDefinition(type);
|
||||
if (!def.subClassOf(env,
|
||||
env.getClassDeclaration(idJavaLangThrowable))) {
|
||||
env.error(where, "catch.not.throwable", def);
|
||||
}
|
||||
}
|
||||
|
||||
field = new LocalMember(where, ctx.field.getClassDefinition(), mod, type, id);
|
||||
ctx.declare(env, field);
|
||||
vset.addVar(field.number);
|
||||
|
||||
return body.check(env, ctx, vset, exp);
|
||||
} catch (ClassNotFound e) {
|
||||
env.error(where, "class.not.found", e.name, opNames[op]);
|
||||
return vset;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
ctx = new Context(ctx, this);
|
||||
if (field.isUsed()) {
|
||||
ctx.declare(env, field);
|
||||
}
|
||||
if (body != null) {
|
||||
body = body.inline(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
CatchStatement s = (CatchStatement)clone();
|
||||
if (body != null) {
|
||||
s.body = body.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (field != null) {
|
||||
s.field = field.copyInline(ctx);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compute cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx){
|
||||
int cost = 1;
|
||||
if (body != null) {
|
||||
cost += body.costInline(thresh, env,ctx);
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
if (field.isUsed()) {
|
||||
newctx.declare(env, field);
|
||||
asm.add(where, opc_astore, new LocalVariable(field, field.number));
|
||||
} else {
|
||||
asm.add(where, opc_pop);
|
||||
}
|
||||
if (body != null) {
|
||||
body.code(env, newctx, asm);
|
||||
}
|
||||
//asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("catch (");
|
||||
texpr.print(out);
|
||||
out.print(" " + id + ") ");
|
||||
if (body != null) {
|
||||
body.print(out, indent);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/CharExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/CharExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CharExpression extends IntegerExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public CharExpression(long where, char value) {
|
||||
super(CHARVAL, where, Type.tChar, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value + "c");
|
||||
}
|
||||
}
|
||||
52
jdkSrc/jdk8/sun/tools/tree/CheckContext.java
Normal file
52
jdkSrc/jdk8/sun/tools/tree/CheckContext.java
Normal file
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CheckContext extends Context {
|
||||
public Vset vsBreak = Vset.DEAD_END;
|
||||
public Vset vsContinue = Vset.DEAD_END;
|
||||
|
||||
// Accumulate (join) all DA/DU state prior to
|
||||
// any abnormal exit from a try-statement.
|
||||
// This field is ignored unless this
|
||||
// context is associated with a try-statement.
|
||||
public Vset vsTryExit = Vset.DEAD_END;
|
||||
|
||||
/**
|
||||
* Create a new nested context, for a block statement
|
||||
*/
|
||||
CheckContext(Context ctx, Statement stat) {
|
||||
super(ctx, stat);
|
||||
}
|
||||
}
|
||||
66
jdkSrc/jdk8/sun/tools/tree/CodeContext.java
Normal file
66
jdkSrc/jdk8/sun/tools/tree/CodeContext.java
Normal file
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
class CodeContext extends Context {
|
||||
Label breakLabel;
|
||||
Label contLabel;
|
||||
|
||||
/**
|
||||
* Create a new nested context, for a block statement
|
||||
*/
|
||||
CodeContext(Context ctx, Node node) {
|
||||
super(ctx, node);
|
||||
switch (node.op) {
|
||||
case DO:
|
||||
case WHILE:
|
||||
case FOR:
|
||||
case FINALLY:
|
||||
case SYNCHRONIZED:
|
||||
this.breakLabel = new Label();
|
||||
this.contLabel = new Label();
|
||||
break;
|
||||
case SWITCH:
|
||||
case TRY:
|
||||
case INLINEMETHOD:
|
||||
case INLINENEWINSTANCE:
|
||||
this.breakLabel = new Label();
|
||||
break;
|
||||
default:
|
||||
if ((node instanceof Statement) && (((Statement)node).labels != null)) {
|
||||
this.breakLabel = new Label();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
150
jdkSrc/jdk8/sun/tools/tree/CommaExpression.java
Normal file
150
jdkSrc/jdk8/sun/tools/tree/CommaExpression.java
Normal file
@@ -0,0 +1,150 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CommaExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public CommaExpression(long where, Expression left, Expression right) {
|
||||
super(COMMA, where, (right != null) ? right.type : Type.tVoid, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check void expression
|
||||
*/
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = left.check(env, ctx, vset, exp);
|
||||
vset = right.check(env, ctx, vset, exp);
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
type = right.type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left == null) {
|
||||
return right;
|
||||
}
|
||||
if (right == null) {
|
||||
return left;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
if (left != null) {
|
||||
left = left.inline(env, ctx);
|
||||
}
|
||||
if (right != null) {
|
||||
right = right.inline(env, ctx);
|
||||
}
|
||||
return simplify();
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (left != null) {
|
||||
left = left.inline(env, ctx);
|
||||
}
|
||||
if (right != null) {
|
||||
right = right.inlineValue(env, ctx);
|
||||
}
|
||||
return simplify();
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
int codeLValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (right == null) {
|
||||
// throw an appropriate error
|
||||
return super.codeLValue(env, ctx, asm);
|
||||
} else {
|
||||
// Fully code the left-hand side. Do the LValue part of the
|
||||
// right-hand side now. The remainder will be done by codeLoad or
|
||||
// codeStore
|
||||
if (left != null) {
|
||||
left.code(env, ctx, asm);
|
||||
}
|
||||
return right.codeLValue(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
|
||||
void codeLoad(Environment env, Context ctx, Assembler asm) {
|
||||
// The left-hand part has already been handled by codeLValue.
|
||||
|
||||
if (right == null) {
|
||||
// throw an appropriate error
|
||||
super.codeLoad(env, ctx, asm);
|
||||
} else {
|
||||
right.codeLoad(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
|
||||
void codeStore(Environment env, Context ctx, Assembler asm) {
|
||||
// The left-hand part has already been handled by codeLValue.
|
||||
if (right == null) {
|
||||
// throw an appropriate error
|
||||
super.codeStore(env, ctx, asm);
|
||||
} else {
|
||||
right.codeStore(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (left != null) {
|
||||
left.code(env, ctx, asm);
|
||||
}
|
||||
right.codeValue(env, ctx, asm);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
if (left != null) {
|
||||
left.code(env, ctx, asm);
|
||||
}
|
||||
if (right != null) {
|
||||
right.code(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
}
|
||||
200
jdkSrc/jdk8/sun/tools/tree/CompoundStatement.java
Normal file
200
jdkSrc/jdk8/sun/tools/tree/CompoundStatement.java
Normal file
@@ -0,0 +1,200 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class CompoundStatement extends Statement {
|
||||
Statement args[];
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public CompoundStatement(long where, Statement args[]) {
|
||||
super(STAT, where);
|
||||
this.args = args;
|
||||
// To avoid the need for subsequent null checks:
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] == null) {
|
||||
args[i] = new CompoundStatement(where, new Statement[0]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Insert a new statement at the front.
|
||||
* This is used to introduce an implicit super-class constructor call.
|
||||
*/
|
||||
public void insertStatement(Statement s) {
|
||||
Statement newargs[] = new Statement[1+args.length];
|
||||
newargs[0] = s;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
newargs[i+1] = args[i];
|
||||
}
|
||||
this.args = newargs;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
if (args.length > 0) {
|
||||
vset = reach(env, vset);
|
||||
CheckContext newctx = new CheckContext(ctx, this);
|
||||
// In this environment, 'resolveName' will look for local classes.
|
||||
Environment newenv = Context.newEnvironment(env, newctx);
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
vset = args[i].checkBlockStatement(newenv, newctx, vset, exp);
|
||||
}
|
||||
vset = vset.join(newctx.vsBreak);
|
||||
}
|
||||
return ctx.removeAdditionalVars(vset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
ctx = new Context(ctx, this);
|
||||
boolean expand = false;
|
||||
int count = 0;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
Statement s = args[i];
|
||||
if (s != null) {
|
||||
if ((s = s.inline(env, ctx)) != null) {
|
||||
if ((s.op == STAT) && (s.labels == null)) {
|
||||
count += ((CompoundStatement)s).args.length;
|
||||
} else {
|
||||
count++;
|
||||
}
|
||||
expand = true;
|
||||
}
|
||||
args[i] = s;
|
||||
}
|
||||
}
|
||||
switch (count) {
|
||||
case 0:
|
||||
return null;
|
||||
|
||||
case 1:
|
||||
for (int i = args.length ; i-- > 0 ;) {
|
||||
if (args[i] != null) {
|
||||
return eliminate(env, args[i]);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (expand || (count != args.length)) {
|
||||
Statement newArgs[] = new Statement[count];
|
||||
for (int i = args.length ; i-- > 0 ;) {
|
||||
Statement s = args[i];
|
||||
if (s != null) {
|
||||
if ((s.op == STAT) && (s.labels == null)) {
|
||||
Statement a[] = ((CompoundStatement)s).args;
|
||||
for (int j = a.length ; j-- > 0 ; ) {
|
||||
newArgs[--count] = a[j];
|
||||
}
|
||||
} else {
|
||||
newArgs[--count] = s;
|
||||
}
|
||||
}
|
||||
}
|
||||
args = newArgs;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
CompoundStatement s = (CompoundStatement)clone();
|
||||
s.args = new Statement[args.length];
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
s.args[i] = args[i].copyInline(ctx, valNeeded);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
int cost = 0;
|
||||
for (int i = 0 ; (i < args.length) && (cost < thresh) ; i++) {
|
||||
cost += args[i].costInline(thresh, env, ctx);
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i].code(env, newctx, asm);
|
||||
}
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the first thing is a constructor invocation
|
||||
*/
|
||||
public Expression firstConstructor() {
|
||||
return (args.length > 0) ? args[0].firstConstructor() : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("{\n");
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
printIndent(out, indent+1);
|
||||
if (args[i] != null) {
|
||||
args[i].print(out, indent + 1);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
out.print("\n");
|
||||
}
|
||||
printIndent(out, indent);
|
||||
out.print("}");
|
||||
}
|
||||
}
|
||||
39
jdkSrc/jdk8/sun/tools/tree/ConditionVars.java
Normal file
39
jdkSrc/jdk8/sun/tools/tree/ConditionVars.java
Normal file
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
/**
|
||||
* This class is used to hold two sets of variables,
|
||||
* one for the true branch, one for the false branch.
|
||||
*
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
class ConditionVars {
|
||||
Vset vsTrue;
|
||||
Vset vsFalse;
|
||||
}
|
||||
235
jdkSrc/jdk8/sun/tools/tree/ConditionalExpression.java
Normal file
235
jdkSrc/jdk8/sun/tools/tree/ConditionalExpression.java
Normal file
@@ -0,0 +1,235 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ConditionalExpression extends BinaryExpression {
|
||||
Expression cond;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ConditionalExpression(long where, Expression cond, Expression left, Expression right) {
|
||||
super(COND, where, Type.tError, left, right);
|
||||
this.cond = cond;
|
||||
}
|
||||
|
||||
/**
|
||||
* Order the expression based on precedence
|
||||
*/
|
||||
public Expression order() {
|
||||
if (precedence() > cond.precedence()) {
|
||||
UnaryExpression e = (UnaryExpression)cond;
|
||||
cond = e.right;
|
||||
e.right = order();
|
||||
return e;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
ConditionVars cvars = cond.checkCondition(env, ctx, vset, exp);
|
||||
vset = left.checkValue(env, ctx, cvars.vsTrue, exp).join(
|
||||
right.checkValue(env, ctx, cvars.vsFalse, exp) );
|
||||
cond = convert(env, ctx, Type.tBoolean, cond);
|
||||
|
||||
int tm = left.type.getTypeMask() | right.type.getTypeMask();
|
||||
if ((tm & TM_ERROR) != 0) {
|
||||
type = Type.tError;
|
||||
return vset;
|
||||
}
|
||||
if (left.type.equals(right.type)) {
|
||||
type = left.type;
|
||||
} else if ((tm & TM_DOUBLE) != 0) {
|
||||
type = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
type = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else if ((tm & TM_REFERENCE) != 0) {
|
||||
try {
|
||||
// This is wrong. We should be using their most common
|
||||
// ancestor, instead.
|
||||
type = env.implicitCast(right.type, left.type)
|
||||
? left.type : right.type;
|
||||
} catch (ClassNotFound e) {
|
||||
type = Type.tError;
|
||||
}
|
||||
} else if (((tm & TM_CHAR) != 0) && left.fitsType(env, ctx, Type.tChar) && right.fitsType(env, ctx, Type.tChar)) {
|
||||
type = Type.tChar;
|
||||
} else if (((tm & TM_SHORT) != 0) && left.fitsType(env, ctx, Type.tShort) && right.fitsType(env, ctx, Type.tShort)) {
|
||||
type = Type.tShort;
|
||||
} else if (((tm & TM_BYTE) != 0) && left.fitsType(env, ctx, Type.tByte) && right.fitsType(env, ctx, Type.tByte)) {
|
||||
type = Type.tByte;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
|
||||
left = convert(env, ctx, type, left);
|
||||
right = convert(env, ctx, type, right);
|
||||
return vset;
|
||||
}
|
||||
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = cond.checkValue(env, ctx, vset, exp);
|
||||
cond = convert(env, ctx, Type.tBoolean, cond);
|
||||
return left.check(env, ctx, vset.copy(), exp).join(right.check(env, ctx, vset, exp));
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if constant
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
return cond.isConstant() && left.isConstant() && right.isConstant();
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (cond.equals(true)) {
|
||||
return left;
|
||||
}
|
||||
if (cond.equals(false)) {
|
||||
return right;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
left = left.inline(env, ctx);
|
||||
right = right.inline(env, ctx);
|
||||
if ((left == null) && (right == null)) {
|
||||
return cond.inline(env, ctx);
|
||||
}
|
||||
if (left == null) {
|
||||
left = right;
|
||||
right = null;
|
||||
cond = new NotExpression(where, cond);
|
||||
}
|
||||
cond = cond.inlineValue(env, ctx);
|
||||
return simplify();
|
||||
}
|
||||
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
cond = cond.inlineValue(env, ctx);
|
||||
left = left.inlineValue(env, ctx);
|
||||
right = right.inlineValue(env, ctx);
|
||||
return simplify();
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
// We need to check if right is null in case costInline()
|
||||
// is called after this expression has been inlined.
|
||||
// This call can happen, for example, in MemberDefinition#cleanup().
|
||||
// (Fix for 4069861).
|
||||
return 1 +
|
||||
cond.costInline(thresh, env, ctx) +
|
||||
left.costInline(thresh, env, ctx) +
|
||||
((right == null) ? 0 : right.costInline(thresh, env, ctx));
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
ConditionalExpression e = (ConditionalExpression)clone();
|
||||
e.cond = cond.copyInline(ctx);
|
||||
e.left = left.copyInline(ctx);
|
||||
|
||||
// If copyInline() is called after inlining is complete,
|
||||
// right could be null.
|
||||
e.right = (right == null) ? null : right.copyInline(ctx);
|
||||
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
Label l1 = new Label();
|
||||
Label l2 = new Label();
|
||||
|
||||
cond.codeBranch(env, ctx, asm, l1, false);
|
||||
left.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_goto, l2);
|
||||
asm.add(l1);
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(l2);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
Label l1 = new Label();
|
||||
cond.codeBranch(env, ctx, asm, l1, false);
|
||||
left.code(env, ctx, asm);
|
||||
if (right != null) {
|
||||
Label l2 = new Label();
|
||||
asm.add(where, opc_goto, l2);
|
||||
asm.add(l1);
|
||||
right.code(env, ctx, asm);
|
||||
asm.add(l2);
|
||||
} else {
|
||||
asm.add(l1);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
cond.print(out);
|
||||
out.print(" ");
|
||||
left.print(out);
|
||||
out.print(" ");
|
||||
if (right != null) {
|
||||
right.print(out);
|
||||
} else {
|
||||
out.print("<null>");
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
49
jdkSrc/jdk8/sun/tools/tree/ConstantExpression.java
Normal file
49
jdkSrc/jdk8/sun/tools/tree/ConstantExpression.java
Normal file
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
class ConstantExpression extends Expression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ConstantExpression(int op, long where, Type type) {
|
||||
super(op, where, type);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true if constant
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
861
jdkSrc/jdk8/sun/tools/tree/Context.java
Normal file
861
jdkSrc/jdk8/sun/tools/tree/Context.java
Normal file
@@ -0,0 +1,861 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class Context implements Constants {
|
||||
Context prev;
|
||||
Node node;
|
||||
int varNumber;
|
||||
LocalMember locals;
|
||||
LocalMember classes;
|
||||
MemberDefinition field;
|
||||
int scopeNumber;
|
||||
int frameNumber;
|
||||
|
||||
/**
|
||||
* Create the initial context for a method
|
||||
* The incoming context is inherited from
|
||||
*/
|
||||
public Context(Context ctx, MemberDefinition field) {
|
||||
this.field = field;
|
||||
if (ctx == null) {
|
||||
this.frameNumber = 1;
|
||||
this.scopeNumber = 2;
|
||||
this.varNumber = 0;
|
||||
} else {
|
||||
this.prev = ctx;
|
||||
this.locals = ctx.locals;
|
||||
this.classes = ctx.classes;
|
||||
if (field != null &&
|
||||
(field.isVariable() || field.isInitializer())) {
|
||||
// Variables and initializers are inlined into a constructor.
|
||||
// Model this by inheriting the frame number of the parent,
|
||||
// which will contain a "this" parameter.
|
||||
this.frameNumber = ctx.frameNumber;
|
||||
this.scopeNumber = ctx.scopeNumber + 1;
|
||||
} else {
|
||||
this.frameNumber = ctx.scopeNumber + 1;
|
||||
this.scopeNumber = this.frameNumber + 1;
|
||||
}
|
||||
this.varNumber = ctx.varNumber;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new context, for initializing a class.
|
||||
*/
|
||||
public Context(Context ctx, ClassDefinition c) {
|
||||
this(ctx, (MemberDefinition)null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new nested context, for a block statement
|
||||
*/
|
||||
Context(Context ctx, Node node) {
|
||||
if (ctx == null) {
|
||||
this.frameNumber = 1;
|
||||
this.scopeNumber = 2;
|
||||
this.varNumber = 0;
|
||||
} else {
|
||||
this.prev = ctx;
|
||||
this.locals = ctx.locals;
|
||||
// Inherit local classes from surrounding block,
|
||||
// just as for local variables. Fixes 4074421.
|
||||
this.classes = ctx.classes;
|
||||
this.varNumber = ctx.varNumber;
|
||||
this.field = ctx.field;
|
||||
this.frameNumber = ctx.frameNumber;
|
||||
this.scopeNumber = ctx.scopeNumber + 1;
|
||||
this.node = node;
|
||||
}
|
||||
}
|
||||
|
||||
public Context(Context ctx) {
|
||||
this(ctx, (Node)null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Declare local
|
||||
*/
|
||||
public int declare(Environment env, LocalMember local) {
|
||||
//System.out.println( "DECLARE= " + local.getName() + "=" + varNumber + ", read=" + local.readcount + ", write=" + local.writecount + ", hash=" + local.hashCode());
|
||||
local.scopeNumber = scopeNumber;
|
||||
if (this.field == null && idThis.equals(local.getName())) {
|
||||
local.scopeNumber += 1; // Anticipate variable or initializer.
|
||||
}
|
||||
if (local.isInnerClass()) {
|
||||
local.prev = classes;
|
||||
classes = local;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Originally the statement:
|
||||
//
|
||||
// local.subModifiers(M_INLINEABLE);
|
||||
//
|
||||
// was here with the comment:
|
||||
//
|
||||
// // prevent inlining across call sites
|
||||
//
|
||||
// This statement prevented constant local variables from
|
||||
// inlining. It didn't seem to do anything useful.
|
||||
//
|
||||
// The statement has been removed and an assertion has been
|
||||
// added which mandates that the only members which are marked
|
||||
// with M_INLINEABLE are the ones for which isConstant() is true.
|
||||
// (Fix for 4106244.)
|
||||
//
|
||||
// Addition to the above comment: they might also be
|
||||
// final variables initialized with 'this', 'super', or other
|
||||
// final identifiers. See VarDeclarationStatement.inline().
|
||||
// So I've removed the assertion. The original subModifiers
|
||||
// call appears to have been there to fix nested class translation
|
||||
// breakage, which has been fixed in VarDeclarationStatement
|
||||
// now instead. (Fix for 4073244.)
|
||||
|
||||
local.prev = locals;
|
||||
locals = local;
|
||||
local.number = varNumber;
|
||||
varNumber += local.getType().stackSize();
|
||||
return local.number;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a local variable by name
|
||||
*/
|
||||
public
|
||||
LocalMember getLocalField(Identifier name) {
|
||||
for (LocalMember f = locals ; f != null ; f = f.prev) {
|
||||
if (name.equals(f.getName())) {
|
||||
return f;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the scope number for a reference to a member of this class
|
||||
* (Larger scope numbers are more deeply nested.)
|
||||
* @see LocalMember#scopeNumber
|
||||
*/
|
||||
public
|
||||
int getScopeNumber(ClassDefinition c) {
|
||||
for (Context ctx = this; ctx != null; ctx = ctx.prev) {
|
||||
if (ctx.field == null) continue;
|
||||
if (ctx.field.getClassDefinition() == c) {
|
||||
return ctx.frameNumber;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
private
|
||||
MemberDefinition getFieldCommon(Environment env, Identifier name,
|
||||
boolean apparentOnly) throws AmbiguousMember, ClassNotFound {
|
||||
// Note: This is structured as a pair of parallel lookups.
|
||||
// If we were to redesign Context, we might prefer to walk
|
||||
// along a single chain of scopes.
|
||||
|
||||
LocalMember lf = getLocalField(name);
|
||||
int ls = (lf == null) ? -2 : lf.scopeNumber;
|
||||
|
||||
ClassDefinition thisClass = field.getClassDefinition();
|
||||
|
||||
// Also look for a class member in a shallower scope.
|
||||
for (ClassDefinition c = thisClass;
|
||||
c != null;
|
||||
c = c.getOuterClass()) {
|
||||
MemberDefinition f = c.getVariable(env, name, thisClass);
|
||||
if (f != null && getScopeNumber(c) > ls) {
|
||||
if (apparentOnly && f.getClassDefinition() != c) {
|
||||
continue;
|
||||
}
|
||||
return f;
|
||||
}
|
||||
}
|
||||
|
||||
return lf;
|
||||
}
|
||||
|
||||
/**
|
||||
* Assign a number to a class field.
|
||||
* (This is used to track definite assignment of some blank finals.)
|
||||
*/
|
||||
public int declareFieldNumber(MemberDefinition field) {
|
||||
return declare(null, new LocalMember(field));
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve a number previously assigned by declareMember().
|
||||
* Return -1 if there was no such assignment in this context.
|
||||
*/
|
||||
public int getFieldNumber(MemberDefinition field) {
|
||||
for (LocalMember f = locals ; f != null ; f = f.prev) {
|
||||
if (f.getMember() == field) {
|
||||
return f.number;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the local field or member field corresponding to a number.
|
||||
* Return null if there is no such field.
|
||||
*/
|
||||
public MemberDefinition getElement(int number) {
|
||||
for (LocalMember f = locals ; f != null ; f = f.prev) {
|
||||
if (f.number == number) {
|
||||
MemberDefinition field = f.getMember();
|
||||
return (field != null) ? field : f;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a local class by name
|
||||
*/
|
||||
public
|
||||
LocalMember getLocalClass(Identifier name) {
|
||||
for (LocalMember f = classes ; f != null ; f = f.prev) {
|
||||
if (name.equals(f.getName())) {
|
||||
return f;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private
|
||||
MemberDefinition getClassCommon(Environment env, Identifier name,
|
||||
boolean apparentOnly) throws ClassNotFound {
|
||||
LocalMember lf = getLocalClass(name);
|
||||
int ls = (lf == null) ? -2 : lf.scopeNumber;
|
||||
|
||||
// Also look for a class member in a shallower scope.
|
||||
for (ClassDefinition c = field.getClassDefinition();
|
||||
c != null;
|
||||
c = c.getOuterClass()) {
|
||||
// QUERY: We may need to get the inner class from a
|
||||
// superclass of 'c'. This call is prepared to
|
||||
// resolve the superclass if necessary. Can we arrange
|
||||
// to assure that it is always previously resolved?
|
||||
// This is one of a small number of problematic calls that
|
||||
// requires 'getSuperClass' to resolve superclasses on demand.
|
||||
// See 'ClassDefinition.getInnerClass(env, nm)'.
|
||||
MemberDefinition f = c.getInnerClass(env, name);
|
||||
if (f != null && getScopeNumber(c) > ls) {
|
||||
if (apparentOnly && f.getClassDefinition() != c) {
|
||||
continue;
|
||||
}
|
||||
return f;
|
||||
}
|
||||
}
|
||||
|
||||
return lf;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get either a local variable, or a field in a current class
|
||||
*/
|
||||
public final
|
||||
MemberDefinition getField(Environment env, Identifier name) throws AmbiguousMember, ClassNotFound {
|
||||
return getFieldCommon(env, name, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Like getField, except that it skips over inherited fields.
|
||||
* Used for error checking.
|
||||
*/
|
||||
public final
|
||||
MemberDefinition getApparentField(Environment env, Identifier name) throws AmbiguousMember, ClassNotFound {
|
||||
return getFieldCommon(env, name, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the given field is active in this context.
|
||||
*/
|
||||
public boolean isInScope(LocalMember field) {
|
||||
for (LocalMember f = locals ; f != null ; f = f.prev) {
|
||||
if (field == f) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Notice a reference (usually an uplevel one).
|
||||
* Update the references list of every enclosing class
|
||||
* which is enclosed by the scope of the target.
|
||||
* Update decisions about which uplevels to make into fields.
|
||||
* Return the uplevel reference descriptor, or null if it's local.
|
||||
* <p>
|
||||
* The target must be in scope in this context.
|
||||
* So, call this method only from the check phase.
|
||||
* (In other phases, the context may be less complete.)
|
||||
* <p>
|
||||
* This can and should be called both before and after classes are frozen.
|
||||
* It should be a no-op, and will raise a compiler error if not.
|
||||
*/
|
||||
public UplevelReference noteReference(Environment env, LocalMember target) {
|
||||
int targetScopeNumber = !isInScope(target) ? -1 : target.scopeNumber;
|
||||
|
||||
// Walk outward visiting each scope.
|
||||
// Note each distinct frame (i.e., enclosing method).
|
||||
// For each frame in which the variable is uplevel,
|
||||
// record the event in the references list of the enclosing class.
|
||||
UplevelReference res = null;
|
||||
int currentFrameNumber = -1;
|
||||
for (Context refctx = this; refctx != null; refctx = refctx.prev) {
|
||||
if (currentFrameNumber == refctx.frameNumber) {
|
||||
continue; // we're processing frames, not contexts
|
||||
}
|
||||
currentFrameNumber = refctx.frameNumber;
|
||||
if (targetScopeNumber >= currentFrameNumber) {
|
||||
break; // the target is native to this frame
|
||||
}
|
||||
|
||||
// process a frame which is using this variable as an uplevel
|
||||
ClassDefinition refc = refctx.field.getClassDefinition();
|
||||
UplevelReference r = refc.getReference(target);
|
||||
r.noteReference(env, refctx);
|
||||
|
||||
// remember the reference pertaining to the innermost frame
|
||||
if (res == null) {
|
||||
res = r;
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* Implement a reference (usually an uplevel one).
|
||||
* Call noteReference() first, to make sure the reference
|
||||
* lists are up to date.
|
||||
* <p>
|
||||
* The resulting expression tree does not need checking;
|
||||
* it can be code-generated right away.
|
||||
* If the reference is not uplevel, the result is an IDENT or THIS.
|
||||
*/
|
||||
public Expression makeReference(Environment env, LocalMember target) {
|
||||
UplevelReference r = noteReference(env, target);
|
||||
|
||||
// Now create a referencing expression.
|
||||
if (r != null) {
|
||||
return r.makeLocalReference(env, this);
|
||||
} else if (idThis.equals(target.getName())) {
|
||||
return new ThisExpression(0, target);
|
||||
} else {
|
||||
return new IdentifierExpression(0, target);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a local expression which can serve as the base reference
|
||||
* for the given field. If the field is a constructor, return an
|
||||
* expression for the implicit enclosing instance argument.
|
||||
* <p>
|
||||
* Return null if there is no need for such an argument,
|
||||
* or if there was an error.
|
||||
*/
|
||||
public Expression findOuterLink(Environment env, long where,
|
||||
MemberDefinition f) {
|
||||
// reqc is the base pointer type required to use f
|
||||
ClassDefinition fc = f.getClassDefinition();
|
||||
ClassDefinition reqc = f.isStatic() ? null
|
||||
: !f.isConstructor() ? fc
|
||||
: fc.isTopLevel() ? null
|
||||
: fc.getOuterClass();
|
||||
if (reqc == null) {
|
||||
return null;
|
||||
}
|
||||
return findOuterLink(env, where, reqc, f, false);
|
||||
}
|
||||
|
||||
private static boolean match(Environment env,
|
||||
ClassDefinition thisc, ClassDefinition reqc) {
|
||||
try {
|
||||
return thisc == reqc
|
||||
|| reqc.implementedBy(env, thisc.getClassDeclaration());
|
||||
} catch (ClassNotFound ee) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public Expression findOuterLink(Environment env, long where,
|
||||
ClassDefinition reqc,
|
||||
MemberDefinition f,
|
||||
boolean needExactMatch) {
|
||||
if (field.isStatic()) {
|
||||
if (f == null) {
|
||||
// say something like: undefined variable A.this
|
||||
Identifier nm = reqc.getName().getFlatName().getName();
|
||||
env.error(where, "undef.var", Identifier.lookup(nm,idThis));
|
||||
} else if (f.isConstructor()) {
|
||||
env.error(where, "no.outer.arg", reqc, f.getClassDeclaration());
|
||||
} else if (f.isMethod()) {
|
||||
env.error(where, "no.static.meth.access",
|
||||
f, f.getClassDeclaration());
|
||||
} else {
|
||||
env.error(where, "no.static.field.access", f.getName(),
|
||||
f.getClassDeclaration());
|
||||
}
|
||||
// This is an attempt at error recovery.
|
||||
// Unfortunately, the constructor may throw
|
||||
// a null pointer exception after failing to resolve
|
||||
// 'idThis'. Since an error message has already been
|
||||
// issued previously, this exception is caught and
|
||||
// silently ignored. Ideally, we should avoid throwing
|
||||
// the exception.
|
||||
Expression e = new ThisExpression(where, this);
|
||||
e.type = reqc.getType();
|
||||
return e;
|
||||
}
|
||||
|
||||
// use lp to scan for current instances (locals named "this")
|
||||
LocalMember lp = locals;
|
||||
|
||||
// thise is a link expression being built up
|
||||
Expression thise = null;
|
||||
|
||||
// root is the local variable (idThis) at the far left of thise
|
||||
LocalMember root = null;
|
||||
|
||||
// thisc is the class of the link expression thise
|
||||
ClassDefinition thisc = null;
|
||||
|
||||
// conCls is the class of the "this", in a constructor
|
||||
ClassDefinition conCls = null;
|
||||
if (field.isConstructor()) {
|
||||
conCls = field.getClassDefinition();
|
||||
}
|
||||
|
||||
if (!field.isMethod()) {
|
||||
thisc = field.getClassDefinition();
|
||||
thise = new ThisExpression(where, this);
|
||||
}
|
||||
|
||||
while (true) {
|
||||
if (thise == null) {
|
||||
// start fresh from lp
|
||||
while (lp != null && !idThis.equals(lp.getName())) {
|
||||
lp = lp.prev;
|
||||
}
|
||||
if (lp == null) {
|
||||
break;
|
||||
}
|
||||
thise = new ThisExpression(where, lp);
|
||||
thisc = lp.getClassDefinition();
|
||||
root = lp;
|
||||
lp = lp.prev;
|
||||
}
|
||||
|
||||
// Require exact class identity when called with
|
||||
// 'needExactMatch' true. This is done when checking
|
||||
// the '<class>.this' syntax. Fixes 4102393 and 4133457.
|
||||
if (thisc == reqc ||
|
||||
(!needExactMatch && match(env, thisc, reqc))) {
|
||||
break;
|
||||
}
|
||||
|
||||
// move out one step, if the current instance has an outer link
|
||||
|
||||
MemberDefinition outerMember = thisc.findOuterMember();
|
||||
if (outerMember == null) {
|
||||
thise = null;
|
||||
continue; // try to find more help in lp
|
||||
}
|
||||
ClassDefinition prevc = thisc;
|
||||
thisc = prevc.getOuterClass();
|
||||
|
||||
if (prevc == conCls) {
|
||||
// Must pick up "this$C" from the constructor argument,
|
||||
// not from "this.this$C", since the latter may not be
|
||||
// initialized properly. (This way is cheaper too.)
|
||||
Identifier nm = outerMember.getName();
|
||||
IdentifierExpression arg = new IdentifierExpression(where, nm);
|
||||
arg.bind(env, this);
|
||||
thise = arg;
|
||||
} else {
|
||||
thise = new FieldExpression(where, thise, outerMember);
|
||||
}
|
||||
}
|
||||
if (thise != null) {
|
||||
// mark crossed scopes
|
||||
// ?????
|
||||
//ensureAvailable(root);
|
||||
return thise;
|
||||
}
|
||||
|
||||
if (f == null) {
|
||||
// say something like: undefined variable A.this
|
||||
Identifier nm = reqc.getName().getFlatName().getName();
|
||||
env.error(where, "undef.var", Identifier.lookup(nm,idThis));
|
||||
} else if (f.isConstructor()) {
|
||||
env.error(where, "no.outer.arg", reqc, f.getClassDefinition());
|
||||
} else {
|
||||
env.error(where, "no.static.field.access", f, field);
|
||||
}
|
||||
|
||||
// avoid floodgating:
|
||||
Expression e = new ThisExpression(where, this);
|
||||
e.type = reqc.getType();
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Is there a "this" of type reqc in scope?
|
||||
*/
|
||||
public static boolean outerLinkExists(Environment env,
|
||||
ClassDefinition reqc,
|
||||
ClassDefinition thisc) {
|
||||
while (!match(env, thisc, reqc)) {
|
||||
if (thisc.isTopLevel()) {
|
||||
return false;
|
||||
}
|
||||
thisc = thisc.getOuterClass();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* From which enclosing class do members of this type come?
|
||||
*/
|
||||
public ClassDefinition findScope(Environment env, ClassDefinition reqc) {
|
||||
ClassDefinition thisc = field.getClassDefinition();
|
||||
while (thisc != null && !match(env, thisc, reqc)) {
|
||||
thisc = thisc.getOuterClass();
|
||||
}
|
||||
return thisc;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve a type name from within a local scope.
|
||||
* @see Environment#resolveName
|
||||
*/
|
||||
Identifier resolveName(Environment env, Identifier name) {
|
||||
// This logic is pretty much exactly parallel to that of
|
||||
// Environment.resolveName().
|
||||
if (name.isQualified()) {
|
||||
// Try to resolve the first identifier component,
|
||||
// because inner class names take precedence over
|
||||
// package prefixes. (Cf. Environment.resolveName.)
|
||||
Identifier rhead = resolveName(env, name.getHead());
|
||||
|
||||
if (rhead.hasAmbigPrefix()) {
|
||||
// The first identifier component refers to an
|
||||
// ambiguous class. Limp on. We throw away the
|
||||
// rest of the classname as it is irrelevant.
|
||||
// (part of solution for 4059855).
|
||||
return rhead;
|
||||
}
|
||||
|
||||
if (!env.classExists(rhead)) {
|
||||
return env.resolvePackageQualifiedName(name);
|
||||
}
|
||||
try {
|
||||
return env.getClassDefinition(rhead).
|
||||
resolveInnerClass(env, name.getTail());
|
||||
} catch (ClassNotFound ee) {
|
||||
// return partially-resolved name someone else can fail on
|
||||
return Identifier.lookupInner(rhead, name.getTail());
|
||||
}
|
||||
}
|
||||
|
||||
// Look for an unqualified name in enclosing scopes.
|
||||
try {
|
||||
MemberDefinition f = getClassCommon(env, name, false);
|
||||
if (f != null) {
|
||||
return f.getInnerClass().getName();
|
||||
}
|
||||
} catch (ClassNotFound ee) {
|
||||
// a missing superclass, or something catastrophic
|
||||
}
|
||||
|
||||
// look in imports, etc.
|
||||
return env.resolveName(name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the name of a lexically apparent type,
|
||||
* skipping inherited members, and ignoring
|
||||
* the current pacakge and imports.
|
||||
* This is used for error checking.
|
||||
*/
|
||||
public
|
||||
Identifier getApparentClassName(Environment env, Identifier name) {
|
||||
if (name.isQualified()) {
|
||||
// Try to resolve the first identifier component,
|
||||
// because inner class names take precedence over
|
||||
// package prefixes. (Cf. Environment.resolveName.)
|
||||
Identifier rhead = getApparentClassName(env, name.getHead());
|
||||
return (rhead == null) ? idNull
|
||||
: Identifier.lookup(rhead,
|
||||
name.getTail());
|
||||
}
|
||||
|
||||
// Look for an unqualified name in enclosing scopes.
|
||||
try {
|
||||
MemberDefinition f = getClassCommon(env, name, true);
|
||||
if (f != null) {
|
||||
return f.getInnerClass().getName();
|
||||
}
|
||||
} catch (ClassNotFound ee) {
|
||||
// a missing superclass, or something catastrophic
|
||||
}
|
||||
|
||||
// the enclosing class name is the only apparent package member:
|
||||
Identifier topnm = field.getClassDefinition().getTopClass().getName();
|
||||
if (topnm.getName().equals(name)) {
|
||||
return topnm;
|
||||
}
|
||||
return idNull;
|
||||
}
|
||||
|
||||
/**
|
||||
* Raise an error if a blank final was definitely unassigned
|
||||
* on entry to a loop, but has possibly been assigned on the
|
||||
* back-branch. If this is the case, the loop may be assigning
|
||||
* it multiple times.
|
||||
*/
|
||||
public void checkBackBranch(Environment env, Statement loop,
|
||||
Vset vsEntry, Vset vsBack) {
|
||||
for (LocalMember f = locals ; f != null ; f = f.prev) {
|
||||
if (f.isBlankFinal()
|
||||
&& vsEntry.testVarUnassigned(f.number)
|
||||
&& !vsBack.testVarUnassigned(f.number)) {
|
||||
env.error(loop.where, "assign.to.blank.final.in.loop",
|
||||
f.getName());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a field can reach another field (only considers
|
||||
* forward references, not the access modifiers).
|
||||
*/
|
||||
public boolean canReach(Environment env, MemberDefinition f) {
|
||||
return field.canReach(env, f);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the context that corresponds to a label, return null if
|
||||
* not found.
|
||||
*/
|
||||
public
|
||||
Context getLabelContext(Identifier lbl) {
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
if ((ctx.node != null) && (ctx.node instanceof Statement)) {
|
||||
if (((Statement)(ctx.node)).hasLabel(lbl))
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination context of a break
|
||||
*/
|
||||
public
|
||||
Context getBreakContext(Identifier lbl) {
|
||||
if (lbl != null) {
|
||||
return getLabelContext(lbl);
|
||||
}
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
if (ctx.node != null) {
|
||||
switch (ctx.node.op) {
|
||||
case SWITCH:
|
||||
case FOR:
|
||||
case DO:
|
||||
case WHILE:
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination context of a continue
|
||||
*/
|
||||
public
|
||||
Context getContinueContext(Identifier lbl) {
|
||||
if (lbl != null) {
|
||||
return getLabelContext(lbl);
|
||||
}
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
if (ctx.node != null) {
|
||||
switch (ctx.node.op) {
|
||||
case FOR:
|
||||
case DO:
|
||||
case WHILE:
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination context of a return (the method body)
|
||||
*/
|
||||
public
|
||||
CheckContext getReturnContext() {
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
// The METHOD node is set up by Statement.checkMethod().
|
||||
if (ctx.node != null && ctx.node.op == METHOD) {
|
||||
return (CheckContext)ctx;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the context of the innermost surrounding try-block.
|
||||
* Consider only try-blocks contained within the same method.
|
||||
* (There could be others when searching from within a method
|
||||
* of a local class, but they are irrelevant to our purpose.)
|
||||
* This is used for recording DA/DU information preceding
|
||||
* all abnormal transfers of control: break, continue, return,
|
||||
* and throw.
|
||||
*/
|
||||
public
|
||||
CheckContext getTryExitContext() {
|
||||
for (Context ctx = this;
|
||||
ctx != null && ctx.node != null && ctx.node.op != METHOD;
|
||||
ctx = ctx.prev) {
|
||||
if (ctx.node.op == TRY) {
|
||||
return (CheckContext)ctx;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the nearest inlined context
|
||||
*/
|
||||
Context getInlineContext() {
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
if (ctx.node != null) {
|
||||
switch (ctx.node.op) {
|
||||
case INLINEMETHOD:
|
||||
case INLINENEWINSTANCE:
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the context of a field that is being inlined
|
||||
*/
|
||||
Context getInlineMemberContext(MemberDefinition field) {
|
||||
for (Context ctx = this ; ctx != null ; ctx = ctx.prev) {
|
||||
if (ctx.node != null) {
|
||||
switch (ctx.node.op) {
|
||||
case INLINEMETHOD:
|
||||
if (((InlineMethodExpression)ctx.node).field.equals(field)) {
|
||||
return ctx;
|
||||
}
|
||||
break;
|
||||
case INLINENEWINSTANCE:
|
||||
if (((InlineNewInstanceExpression)ctx.node).field.equals(field)) {
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove variables from the vset set that are no longer part of
|
||||
* this context.
|
||||
*/
|
||||
public final Vset removeAdditionalVars(Vset vset) {
|
||||
return vset.removeAdditionalVars(varNumber);
|
||||
}
|
||||
|
||||
public final int getVarNumber() {
|
||||
return varNumber;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the number of the innermost current instance reference.
|
||||
*/
|
||||
public int getThisNumber() {
|
||||
LocalMember thisf = getLocalField(idThis);
|
||||
if (thisf != null
|
||||
&& thisf.getClassDefinition() == field.getClassDefinition()) {
|
||||
return thisf.number;
|
||||
}
|
||||
// this is a variable; there is no "this" (should not happen)
|
||||
return varNumber;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the field containing the present context.
|
||||
*/
|
||||
public final MemberDefinition getField() {
|
||||
return field;
|
||||
}
|
||||
|
||||
/**
|
||||
* Extend an environment with the given context.
|
||||
* The resulting environment behaves the same as
|
||||
* the given one, except that resolveName() takes
|
||||
* into account local class names in this context.
|
||||
*/
|
||||
public static Environment newEnvironment(Environment env, Context ctx) {
|
||||
return new ContextEnvironment(env, ctx);
|
||||
}
|
||||
}
|
||||
|
||||
final
|
||||
class ContextEnvironment extends Environment {
|
||||
Context ctx;
|
||||
Environment innerEnv;
|
||||
|
||||
ContextEnvironment(Environment env, Context ctx) {
|
||||
super(env, env.getSource());
|
||||
this.ctx = ctx;
|
||||
this.innerEnv = env;
|
||||
}
|
||||
|
||||
public Identifier resolveName(Identifier name) {
|
||||
return ctx.resolveName(innerEnv, name);
|
||||
}
|
||||
}
|
||||
116
jdkSrc/jdk8/sun/tools/tree/ContinueStatement.java
Normal file
116
jdkSrc/jdk8/sun/tools/tree/ContinueStatement.java
Normal file
@@ -0,0 +1,116 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ContinueStatement extends Statement {
|
||||
Identifier lbl;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ContinueStatement(long where, Identifier lbl) {
|
||||
super(CONTINUE, where);
|
||||
this.lbl = lbl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
reach(env, vset);
|
||||
// A new context is established here because the 'continue' statement
|
||||
// itself may be labelled, however erroneously. A 'CheckContext' must
|
||||
// be used here, as 'getContinueContext' is expected to return one.
|
||||
CheckContext destctx = (CheckContext)new CheckContext(ctx, this).getContinueContext(lbl);
|
||||
if (destctx != null) {
|
||||
switch (destctx.node.op) {
|
||||
case FOR:
|
||||
case DO:
|
||||
case WHILE:
|
||||
if (destctx.frameNumber != ctx.frameNumber) {
|
||||
env.error(where, "branch.to.uplevel", lbl);
|
||||
}
|
||||
destctx.vsContinue = destctx.vsContinue.join(vset);
|
||||
break;
|
||||
default:
|
||||
env.error(where, "invalid.continue");
|
||||
}
|
||||
} else {
|
||||
if (lbl != null) {
|
||||
env.error(where, "label.not.found", lbl);
|
||||
} else {
|
||||
env.error(where, "invalid.continue");
|
||||
}
|
||||
}
|
||||
CheckContext exitctx = ctx.getTryExitContext();
|
||||
if (exitctx != null) {
|
||||
exitctx.vsTryExit = exitctx.vsTryExit.join(vset);
|
||||
}
|
||||
return DEAD_END;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext destctx = (CodeContext)ctx.getContinueContext(lbl);
|
||||
codeFinally(env, ctx, asm, destctx, null);
|
||||
asm.add(where, opc_goto, destctx.contLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("continue");
|
||||
if (lbl != null) {
|
||||
out.print(" " + lbl);
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
158
jdkSrc/jdk8/sun/tools/tree/ConvertExpression.java
Normal file
158
jdkSrc/jdk8/sun/tools/tree/ConvertExpression.java
Normal file
@@ -0,0 +1,158 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ConvertExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ConvertExpression(long where, Type type, Expression right) {
|
||||
super(CONVERT, where, type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the value
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return right.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
switch (right.op) {
|
||||
case BYTEVAL:
|
||||
case CHARVAL:
|
||||
case SHORTVAL:
|
||||
case INTVAL: {
|
||||
int value = ((IntegerExpression)right).value;
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BYTE: return new ByteExpression(right.where, (byte)value);
|
||||
case TC_CHAR: return new CharExpression(right.where, (char)value);
|
||||
case TC_SHORT: return new ShortExpression(right.where, (short)value);
|
||||
case TC_INT: return new IntExpression(right.where, (int)value);
|
||||
case TC_LONG: return new LongExpression(right.where, (long)value);
|
||||
case TC_FLOAT: return new FloatExpression(right.where, (float)value);
|
||||
case TC_DOUBLE: return new DoubleExpression(right.where, (double)value);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case LONGVAL: {
|
||||
long value = ((LongExpression)right).value;
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BYTE: return new ByteExpression(right.where, (byte)value);
|
||||
case TC_CHAR: return new CharExpression(right.where, (char)value);
|
||||
case TC_SHORT: return new ShortExpression(right.where, (short)value);
|
||||
case TC_INT: return new IntExpression(right.where, (int)value);
|
||||
case TC_FLOAT: return new FloatExpression(right.where, (float)value);
|
||||
case TC_DOUBLE: return new DoubleExpression(right.where, (double)value);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case FLOATVAL: {
|
||||
float value = ((FloatExpression)right).value;
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BYTE: return new ByteExpression(right.where, (byte)value);
|
||||
case TC_CHAR: return new CharExpression(right.where, (char)value);
|
||||
case TC_SHORT: return new ShortExpression(right.where, (short)value);
|
||||
case TC_INT: return new IntExpression(right.where, (int)value);
|
||||
case TC_LONG: return new LongExpression(right.where, (long)value);
|
||||
case TC_DOUBLE: return new DoubleExpression(right.where, (double)value);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case DOUBLEVAL: {
|
||||
double value = ((DoubleExpression)right).value;
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BYTE: return new ByteExpression(right.where, (byte)value);
|
||||
case TC_CHAR: return new CharExpression(right.where, (char)value);
|
||||
case TC_SHORT: return new ShortExpression(right.where, (short)value);
|
||||
case TC_INT: return new IntExpression(right.where, (int)value);
|
||||
case TC_LONG: return new LongExpression(right.where, (long)value);
|
||||
case TC_FLOAT: return new FloatExpression(right.where, (float)value);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return right.equals(i);
|
||||
}
|
||||
public boolean equals(boolean b) {
|
||||
return right.equals(b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
// super.inline throws away the op.
|
||||
// This is sometimes incorrect, since casts can have side effects.
|
||||
if (right.type.inMask(TM_REFERENCE) && type.inMask(TM_REFERENCE)) {
|
||||
try {
|
||||
if (!env.implicitCast(right.type, type))
|
||||
return inlineValue(env, ctx);
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
}
|
||||
return super.inline(env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
codeConversion(env, ctx, asm, right.type, type);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " " + type.toString() + " ");
|
||||
right.print(out);
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
151
jdkSrc/jdk8/sun/tools/tree/DeclarationStatement.java
Normal file
151
jdkSrc/jdk8/sun/tools/tree/DeclarationStatement.java
Normal file
@@ -0,0 +1,151 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class DeclarationStatement extends Statement {
|
||||
int mod;
|
||||
Expression type;
|
||||
Statement args[];
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public DeclarationStatement(long where, int mod, Expression type, Statement args[]) {
|
||||
super(DECLARATION, where);
|
||||
this.mod = mod;
|
||||
this.type = type;
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
* Report an error unless the call is checkBlockStatement.
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
env.error(where, "invalid.decl");
|
||||
return checkBlockStatement(env, ctx, vset, exp);
|
||||
}
|
||||
Vset checkBlockStatement(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
if (labels != null) {
|
||||
env.error(where, "declaration.with.label", labels[0]);
|
||||
}
|
||||
vset = reach(env, vset);
|
||||
Type t = type.toType(env, ctx);
|
||||
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
vset = args[i].checkDeclaration(env, ctx, vset, mod, t, exp);
|
||||
}
|
||||
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
int n = 0;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if ((args[i] = args[i].inline(env, ctx)) != null) {
|
||||
n++;
|
||||
}
|
||||
}
|
||||
return (n == 0) ? null : this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
DeclarationStatement s = (DeclarationStatement)clone();
|
||||
if (type != null) {
|
||||
s.type = type.copyInline(ctx);
|
||||
}
|
||||
s.args = new Statement[args.length];
|
||||
for (int i = 0; i < args.length; i++){
|
||||
if (args[i] != null){
|
||||
s.args[i] = args[i].copyInline(ctx, valNeeded);
|
||||
}
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
int cost = 1;
|
||||
for (int i = 0; i < args.length; i++){
|
||||
if (args[i] != null){
|
||||
cost += args[i].costInline(thresh, env, ctx);
|
||||
}
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] != null) {
|
||||
args[i].code(env, ctx, asm);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
out.print("declare ");
|
||||
super.print(out, indent);
|
||||
type.print(out);
|
||||
out.print(" ");
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (i > 0) {
|
||||
out.print(", ");
|
||||
}
|
||||
if (args[i] != null) {
|
||||
args[i].print(out);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
72
jdkSrc/jdk8/sun/tools/tree/DivRemExpression.java
Normal file
72
jdkSrc/jdk8/sun/tools/tree/DivRemExpression.java
Normal file
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
* Copyright (c) 1995, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
abstract public
|
||||
class DivRemExpression extends BinaryArithmeticExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public DivRemExpression(int op, long where, Expression left, Expression right) {
|
||||
super(op, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
// Do not toss out integer divisions or remainders since they
|
||||
// can cause a division by zero.
|
||||
if (type.inMask(TM_INTEGER)) {
|
||||
right = right.inlineValue(env, ctx);
|
||||
if (right.isConstant() && !right.equals(0)) {
|
||||
// We know the division can be elided
|
||||
left = left.inline(env, ctx);
|
||||
return left;
|
||||
} else {
|
||||
left = left.inlineValue(env, ctx);
|
||||
try {
|
||||
return eval().simplify();
|
||||
} catch (ArithmeticException e) {
|
||||
env.error(where, "arithmetic.exception");
|
||||
return this;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// float & double divisions don't cause arithmetic errors
|
||||
return super.inline(env, ctx);
|
||||
}
|
||||
}
|
||||
}
|
||||
87
jdkSrc/jdk8/sun/tools/tree/DivideExpression.java
Normal file
87
jdkSrc/jdk8/sun/tools/tree/DivideExpression.java
Normal file
@@ -0,0 +1,87 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class DivideExpression extends DivRemExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public DivideExpression(long where, Expression left, Expression right) {
|
||||
super(DIV, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a / b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a / b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new FloatExpression(where, a / b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new DoubleExpression(where, a / b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
// This code here was wrong. What if the expression is a float?
|
||||
// In any case, if the expression throws an exception, we
|
||||
// should just throw the exception at run-time. Throwing
|
||||
// it at compile-time is not correct.
|
||||
// (Fix for 4019300)
|
||||
//
|
||||
// if (right.equals(0)) {
|
||||
// throw new ArithmeticException("/ by zero");
|
||||
// }
|
||||
if (right.equals(1)) {
|
||||
return left;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_idiv + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
135
jdkSrc/jdk8/sun/tools/tree/DoStatement.java
Normal file
135
jdkSrc/jdk8/sun/tools/tree/DoStatement.java
Normal file
@@ -0,0 +1,135 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class DoStatement extends Statement {
|
||||
Statement body;
|
||||
Expression cond;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public DoStatement(long where, Statement body, Expression cond) {
|
||||
super(DO, where);
|
||||
this.body = body;
|
||||
this.cond = cond;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env,ctx);
|
||||
CheckContext newctx = new CheckContext(ctx, this);
|
||||
// remember what was unassigned on entry
|
||||
Vset vsEntry = vset.copy();
|
||||
vset = body.check(env, newctx, reach(env, vset), exp);
|
||||
vset = vset.join(newctx.vsContinue);
|
||||
// get to the test either by falling through the body, or through
|
||||
// a "continue" statement.
|
||||
ConditionVars cvars =
|
||||
cond.checkCondition(env, newctx, vset, exp);
|
||||
cond = convert(env, newctx, Type.tBoolean, cond);
|
||||
// make sure the back-branch fits the entry of the loop
|
||||
ctx.checkBackBranch(env, this, vsEntry, cvars.vsTrue);
|
||||
// exit the loop through the test returning false, or a "break"
|
||||
vset = newctx.vsBreak.join(cvars.vsFalse);
|
||||
return ctx.removeAdditionalVars(vset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
ctx = new Context(ctx, this);
|
||||
if (body != null) {
|
||||
body = body.inline(env, ctx);
|
||||
}
|
||||
cond = cond.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
DoStatement s = (DoStatement)clone();
|
||||
s.cond = cond.copyInline(ctx);
|
||||
if (body != null) {
|
||||
s.body = body.copyInline(ctx, valNeeded);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1 + cond.costInline(thresh, env, ctx)
|
||||
+ ((body != null) ? body.costInline(thresh, env, ctx) : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
Label l1 = new Label();
|
||||
asm.add(l1);
|
||||
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
|
||||
if (body != null) {
|
||||
body.code(env, newctx, asm);
|
||||
}
|
||||
asm.add(newctx.contLabel);
|
||||
cond.codeBranch(env, newctx, asm, l1, true);
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("do ");
|
||||
body.print(out, indent);
|
||||
out.print(" while ");
|
||||
cond.print(out);
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
84
jdkSrc/jdk8/sun/tools/tree/DoubleExpression.java
Normal file
84
jdkSrc/jdk8/sun/tools/tree/DoubleExpression.java
Normal file
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class DoubleExpression extends ConstantExpression {
|
||||
double value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public DoubleExpression(long where, double value) {
|
||||
super(DOUBLEVAL, where, Type.tDouble);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return new Double(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return value == i;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
// don't allow -0.0
|
||||
return (Double.doubleToLongBits(value) == 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc2_w, new Double(value));
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value + "D");
|
||||
}
|
||||
}
|
||||
117
jdkSrc/jdk8/sun/tools/tree/EqualExpression.java
Normal file
117
jdkSrc/jdk8/sun/tools/tree/EqualExpression.java
Normal file
@@ -0,0 +1,117 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class EqualExpression extends BinaryEqualityExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public EqualExpression(long where, Expression left, Expression right) {
|
||||
super(EQ, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a == b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a == b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a == b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a == b);
|
||||
}
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a == b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new EqualExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmpeq : opc_if_icmpne, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpl);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpl);
|
||||
break;
|
||||
case TC_ARRAY:
|
||||
case TC_CLASS:
|
||||
case TC_NULL:
|
||||
if (right.equals(0)) {
|
||||
asm.add(where, whenTrue ? opc_ifnull : opc_ifnonnull, lbl, whenTrue);
|
||||
} else {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_acmpeq : opc_if_acmpne, lbl, whenTrue);
|
||||
}
|
||||
return;
|
||||
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_ifeq : opc_ifne, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
126
jdkSrc/jdk8/sun/tools/tree/ExprExpression.java
Normal file
126
jdkSrc/jdk8/sun/tools/tree/ExprExpression.java
Normal file
@@ -0,0 +1,126 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* Parenthesized expressions.
|
||||
*
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
|
||||
public
|
||||
class ExprExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ExprExpression(long where, Expression right) {
|
||||
super(EXPR, where, right.type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check a condition. We must pass it on to our unparenthesised form.
|
||||
*/
|
||||
public void checkCondition(Environment env, Context ctx, Vset vset,
|
||||
Hashtable exp, ConditionVars cvars) {
|
||||
right.checkCondition(env, ctx, vset, exp, cvars);
|
||||
type = right.type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression if it appears as an lvalue.
|
||||
* We just pass it on to our unparenthesized subexpression.
|
||||
* (Part of fix for 4090372)
|
||||
*/
|
||||
public Vset checkAssignOp(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, Expression outside) {
|
||||
vset = right.checkAssignOp(env, ctx, vset, exp, outside);
|
||||
type = right.type;
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Delegate to our subexpression.
|
||||
* (Part of fix for 4090372)
|
||||
*/
|
||||
public FieldUpdater getUpdater(Environment env, Context ctx) {
|
||||
return right.getUpdater(env, ctx);
|
||||
}
|
||||
|
||||
// Allow (x) = 9;
|
||||
//
|
||||
// I will hold off on this until I'm sure about it. Nobody's
|
||||
// going to clammer for this one.
|
||||
//
|
||||
// public Vset checkLHS(Environment env, Context ctx,
|
||||
// Vset vset, Hashtable exp) {
|
||||
// vset = right.check(env, ctx, vset, exp);
|
||||
// type = right.type;
|
||||
// return vset;
|
||||
// }
|
||||
|
||||
public boolean isNull() {
|
||||
return right.isNull();
|
||||
}
|
||||
|
||||
public boolean isNonNull() {
|
||||
return right.isNonNull();
|
||||
}
|
||||
|
||||
// Probably not necessary
|
||||
public Object getValue() {
|
||||
return right.getValue();
|
||||
}
|
||||
|
||||
/**
|
||||
* Delegate to our subexpression.
|
||||
* See the comment in AddExpression#inlineValueSB() for
|
||||
* information about this method.
|
||||
*/
|
||||
protected StringBuffer inlineValueSB(Environment env,
|
||||
Context ctx,
|
||||
StringBuffer buffer) {
|
||||
return right.inlineValueSB(env, ctx, buffer);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
type = right.type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
return right;
|
||||
}
|
||||
}
|
||||
775
jdkSrc/jdk8/sun/tools/tree/Expression.java
Normal file
775
jdkSrc/jdk8/sun/tools/tree/Expression.java
Normal file
@@ -0,0 +1,775 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2004, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Label;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class Expression extends Node {
|
||||
Type type;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
Expression(int op, long where, Type type) {
|
||||
super(op, where);
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Type checking may assign a more complex implementation
|
||||
* to an innocuous-looking expression (like an identifier).
|
||||
* Return that implementation, or the original expression itself
|
||||
* if there is no special implementation.
|
||||
* <p>
|
||||
* This appears at present to be dead code, and is not called
|
||||
* from within javac. Access to the implementation generally
|
||||
* occurs within the same class, and thus uses the underlying
|
||||
* field directly.
|
||||
*/
|
||||
public Expression getImplementation() {
|
||||
return this;
|
||||
}
|
||||
|
||||
public Type getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the precedence of the operator
|
||||
*/
|
||||
int precedence() {
|
||||
return (op < opPrecedence.length) ? opPrecedence[op] : 100;
|
||||
}
|
||||
|
||||
/**
|
||||
* Order the expression based on precedence
|
||||
*/
|
||||
public Expression order() {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true if constant, according to JLS 15.27.
|
||||
* A constant expression must inline away to a literal constant.
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the constant value.
|
||||
*/
|
||||
public Object getValue() {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is known to be equal to a given value.
|
||||
* Returns false for any expression other than a literal constant,
|
||||
* thus should be called only after simplification (inlining) has
|
||||
* been performed.
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return false;
|
||||
}
|
||||
public boolean equals(boolean b) {
|
||||
return false;
|
||||
}
|
||||
public boolean equals(Identifier id) {
|
||||
return false;
|
||||
}
|
||||
public boolean equals(String s) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression must be a null reference.
|
||||
*/
|
||||
public boolean isNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression cannot be a null reference.
|
||||
*/
|
||||
public boolean isNonNull() {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Convert an expresion to a type
|
||||
*/
|
||||
Type toType(Environment env, Context ctx) {
|
||||
env.error(where, "invalid.type.expr");
|
||||
return Type.tError;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert an expresion to a type in a context where a qualified
|
||||
* type name is expected, e.g., in the prefix of a qualified type
|
||||
* name.
|
||||
*/
|
||||
/*-----------------------------------------------------*
|
||||
Type toQualifiedType(Environment env, Context ctx) {
|
||||
env.error(where, "invalid.type.expr");
|
||||
return Type.tError;
|
||||
}
|
||||
*-----------------------------------------------------*/
|
||||
|
||||
/**
|
||||
* See if this expression fits in the given type.
|
||||
* This is useful because some larger numbers fit into
|
||||
* smaller types.
|
||||
* <p>
|
||||
* If it is an "int" constant expression, inline it, if necessary,
|
||||
* to examine its numerical value. See JLS 5.2 and 15.24.
|
||||
*/
|
||||
public boolean fitsType(Environment env, Context ctx, Type t) {
|
||||
try {
|
||||
if (env.isMoreSpecific(this.type, t)) {
|
||||
return true;
|
||||
}
|
||||
if (this.type.isType(TC_INT) && this.isConstant() && ctx != null) {
|
||||
// Tentative inlining is harmless for constant expressions.
|
||||
Expression n = this.inlineValue(env, ctx);
|
||||
if (n != this && n instanceof ConstantExpression) {
|
||||
return n.fitsType(env, ctx, t);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
} catch (ClassNotFound e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/** @deprecated (for backward compatibility) */
|
||||
@Deprecated
|
||||
public boolean fitsType(Environment env, Type t) {
|
||||
return fitsType(env, (Context) null, t);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check an expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return vset;
|
||||
}
|
||||
public Vset checkInitializer(Environment env, Context ctx, Vset vset, Type t, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
throw new CompilerError("check failed");
|
||||
}
|
||||
|
||||
public Vset checkLHS(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp) {
|
||||
env.error(where, "invalid.lhs.assignment");
|
||||
type = Type.tError;
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a <code>FieldUpdater</code> object to be used in updating the
|
||||
* value of the location denoted by <code>this</code>, which must be an
|
||||
* expression suitable for the left-hand side of an assignment.
|
||||
* This is used for implementing assignments to private fields for which
|
||||
* an access method is required. Returns null if no access method is
|
||||
* needed, in which case the assignment is handled in the usual way, by
|
||||
* direct access. Only simple assignment expressions are handled here
|
||||
* Assignment operators and pre/post increment/decrement operators are
|
||||
* are handled by 'getUpdater' below.
|
||||
* <p>
|
||||
* Called during the checking phase.
|
||||
*/
|
||||
|
||||
public FieldUpdater getAssigner(Environment env, Context ctx) {
|
||||
throw new CompilerError("getAssigner lhs");
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a <code>FieldUpdater</code> object to be used in updating the value of the
|
||||
* location denoted by <code>this</code>, which must be an expression suitable for the
|
||||
* left-hand side of an assignment. This is used for implementing the assignment
|
||||
* operators and the increment/decrement operators on private fields that require an
|
||||
* access method, e.g., uplevel from an inner class. Returns null if no access method
|
||||
* is needed.
|
||||
* <p>
|
||||
* Called during the checking phase.
|
||||
*/
|
||||
|
||||
public FieldUpdater getUpdater(Environment env, Context ctx) {
|
||||
throw new CompilerError("getUpdater lhs");
|
||||
}
|
||||
|
||||
public Vset checkAssignOp(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, Expression outside) {
|
||||
if (outside instanceof IncDecExpression)
|
||||
env.error(where, "invalid.arg", opNames[outside.op]);
|
||||
else
|
||||
env.error(where, "invalid.lhs.assignment");
|
||||
type = Type.tError;
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check something that might be an AmbiguousName (refman 6.5.2).
|
||||
* A string of dot-separated identifiers might be, in order of preference:
|
||||
* <nl>
|
||||
* <li> a variable name followed by fields or types
|
||||
* <li> a type name followed by fields or types
|
||||
* <li> a package name followed a type and then fields or types
|
||||
* </nl>
|
||||
* If a type name is found, it rewrites itself as a <tt>TypeExpression</tt>.
|
||||
* If a node decides it can only be a package prefix, it sets its
|
||||
* type to <tt>Type.tPackage</tt>. The caller must detect this
|
||||
* and act appropriately to verify the full package name.
|
||||
* @arg loc the expression containing the ambiguous expression
|
||||
*/
|
||||
public Vset checkAmbigName(Environment env, Context ctx, Vset vset, Hashtable exp,
|
||||
UnaryExpression loc) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check a condition. Return a ConditionVars(), which indicates when
|
||||
* which variables are set if the condition is true, and which are set if
|
||||
* the condition is false.
|
||||
*/
|
||||
public ConditionVars checkCondition(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp) {
|
||||
ConditionVars cvars = new ConditionVars();
|
||||
checkCondition(env, ctx, vset, exp, cvars);
|
||||
return cvars;
|
||||
}
|
||||
|
||||
/*
|
||||
* Check a condition.
|
||||
*
|
||||
* cvars is modified so that
|
||||
* cvar.vsTrue indicates variables with a known value if result = true
|
||||
* cvars.vsFalse indicates variables with a known value if !result
|
||||
*
|
||||
* The default action is to simply call checkValue on the expression, and
|
||||
* to see both vsTrue and vsFalse to the result.
|
||||
*/
|
||||
|
||||
public void checkCondition(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, ConditionVars cvars) {
|
||||
cvars.vsTrue = cvars.vsFalse = checkValue(env, ctx, vset, exp);
|
||||
// unshare side effects:
|
||||
cvars.vsFalse = cvars.vsFalse.copy();
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate.
|
||||
*
|
||||
* Attempt to compute the value of an expression node. If all operands are
|
||||
* literal constants of the same kind (e.g., IntegerExpression nodes), a
|
||||
* new constant node of the proper type is returned representing the value
|
||||
* as computed at compile-time. Otherwise, the original node 'this' is
|
||||
* returned.
|
||||
*/
|
||||
Expression eval() {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify.
|
||||
*
|
||||
* Attempt to simplify an expression node by returning a semantically-
|
||||
* equivalent expression that is presumably less costly to execute. There
|
||||
* is some overlap with the intent of 'eval', as compile-time evaluation of
|
||||
* conditional expressions and the short-circuit boolean operators is
|
||||
* performed here. Other simplifications include logical identities
|
||||
* involving logical negation and comparisons. If no simplification is
|
||||
* possible, the original node 'this' is returned. It is assumed that the
|
||||
* children of the node have previously been recursively simplified and
|
||||
* evaluated. A result of 'null' indicates that the expression may be
|
||||
* elided entirely.
|
||||
*/
|
||||
Expression simplify() {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline.
|
||||
*
|
||||
* Recursively simplify each child of an expression node, destructively
|
||||
* replacing the child with the simplified result. Also attempts to
|
||||
* simplify the current node 'this', and returns the simplified result.
|
||||
*
|
||||
* The name 'inline' is somthing of a misnomer, as these methods are
|
||||
* responsible for compile-time expression simplification in general.
|
||||
* The 'eval' and 'simplify' methods apply to a single expression node
|
||||
* only -- it is 'inline' and 'inlineValue' that drive the simplification
|
||||
* of entire expressions.
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return null;
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to evaluate this expression. If this expression
|
||||
* yields a value, append it to the StringBuffer `buffer'.
|
||||
* If this expression cannot be evaluated at this time (for
|
||||
* example if it contains a division by zero, a non-constant
|
||||
* subexpression, or a subexpression which "refuses" to evaluate)
|
||||
* then return `null' to indicate failure.
|
||||
*
|
||||
* It is anticipated that this method will be called to evaluate
|
||||
* concatenations of compile-time constant strings. The call
|
||||
* originates from AddExpression#inlineValue().
|
||||
*
|
||||
* See AddExpression#inlineValueSB() for detailed comments.
|
||||
*/
|
||||
protected StringBuffer inlineValueSB(Environment env,
|
||||
Context ctx,
|
||||
StringBuffer buffer) {
|
||||
Expression inlined = inlineValue(env, ctx);
|
||||
Object val = inlined.getValue();
|
||||
|
||||
if (val == null && !inlined.isNull()){
|
||||
// This (supposedly constant) expression refuses to yield
|
||||
// a value. This can happen, in particular, when we are
|
||||
// trying to evaluate a division by zero. It can also
|
||||
// happen in cases where isConstant() is able to classify
|
||||
// expressions as constant that the compiler's inlining
|
||||
// mechanisms aren't able to evaluate; this is rare,
|
||||
// and all such cases that we have found so far
|
||||
// (e.g. 4082814, 4106244) have been plugged up.
|
||||
//
|
||||
// We return a null to indicate that we have failed to
|
||||
// evaluate the concatenation.
|
||||
return null;
|
||||
}
|
||||
|
||||
// For boolean and character expressions, getValue() returns
|
||||
// an Integer. We need to take care, when appending the result
|
||||
// of getValue(), that we preserve the type.
|
||||
// Fix for 4103959, 4102672.
|
||||
if (type == Type.tChar) {
|
||||
buffer.append((char)((Integer)val).intValue());
|
||||
} else if (type == Type.tBoolean) {
|
||||
buffer.append(((Integer)val).intValue() != 0);
|
||||
} else {
|
||||
buffer.append(val);
|
||||
}
|
||||
|
||||
return buffer;
|
||||
}
|
||||
|
||||
public Expression inlineLHS(Environment env, Context ctx) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression.
|
||||
* This cost controls the inlining of methods, and does not determine
|
||||
* the compile-time simplifications performed by 'inline' and friends.
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
if (type.isType(TC_BOOLEAN)) {
|
||||
codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_ifne : opc_ifeq, lbl, whenTrue);
|
||||
} else {
|
||||
throw new CompilerError("codeBranch " + opNames[op]);
|
||||
}
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (type.isType(TC_BOOLEAN)) {
|
||||
Label l1 = new Label();
|
||||
Label l2 = new Label();
|
||||
|
||||
codeBranch(env, ctx, asm, l1, true);
|
||||
asm.add(true, where, opc_ldc, new Integer(0));
|
||||
asm.add(true, where, opc_goto, l2);
|
||||
asm.add(l1);
|
||||
asm.add(true, where, opc_ldc, new Integer(1));
|
||||
asm.add(l2);
|
||||
} else {
|
||||
throw new CompilerError("codeValue");
|
||||
}
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeValue(env, ctx, asm);
|
||||
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_VOID:
|
||||
break;
|
||||
|
||||
case TC_DOUBLE:
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_pop2);
|
||||
break;
|
||||
|
||||
default:
|
||||
asm.add(where, opc_pop);
|
||||
break;
|
||||
}
|
||||
}
|
||||
int codeLValue(Environment env, Context ctx, Assembler asm) {
|
||||
print(System.out);
|
||||
throw new CompilerError("invalid lhs");
|
||||
}
|
||||
void codeLoad(Environment env, Context ctx, Assembler asm) {
|
||||
print(System.out);
|
||||
throw new CompilerError("invalid load");
|
||||
}
|
||||
void codeStore(Environment env, Context ctx, Assembler asm) {
|
||||
print(System.out);
|
||||
throw new CompilerError("invalid store");
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert this expression to a string.
|
||||
*/
|
||||
void ensureString(Environment env, Context ctx, Assembler asm)
|
||||
throws ClassNotFound, AmbiguousMember
|
||||
{
|
||||
if (type == Type.tString && isNonNull()) {
|
||||
return;
|
||||
}
|
||||
// Make sure it's a non-null string.
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
ClassDeclaration stClass = env.getClassDeclaration(Type.tString);
|
||||
ClassDefinition stClsDef = stClass.getClassDefinition(env);
|
||||
// FIX FOR 4071548
|
||||
// We use 'String.valueOf' to do the conversion, in order to
|
||||
// correctly handle null references and efficiently handle
|
||||
// primitive types. For reference types, we force the argument
|
||||
// to be interpreted as of 'Object' type, thus avoiding the
|
||||
// the special-case overloading of 'valueOf' for character arrays.
|
||||
// This special treatment would conflict with JLS 15.17.1.1.
|
||||
if (type.inMask(TM_REFERENCE)) {
|
||||
// Reference type
|
||||
if (type != Type.tString) {
|
||||
// Convert non-string object to string. If object is
|
||||
// a string, we don't need to convert it, except in the
|
||||
// case that it is null, which is handled below.
|
||||
Type argType1[] = {Type.tObject};
|
||||
MemberDefinition f1 =
|
||||
stClsDef.matchMethod(env, sourceClass, idValueOf, argType1);
|
||||
asm.add(where, opc_invokestatic, f1);
|
||||
}
|
||||
// FIX FOR 4030173
|
||||
// If the argument was null, then value is "null", but if the
|
||||
// argument was not null, 'toString' was called and could have
|
||||
// returned null. We call 'valueOf' again to make sure that
|
||||
// the result is a non-null string. See JLS 15.17.1.1. The
|
||||
// approach taken here minimizes code size -- open code would
|
||||
// be faster. The 'toString' method for an array class cannot
|
||||
// be overridden, thus we know that it will never return null.
|
||||
if (!type.inMask(TM_ARRAY|TM_NULL)) {
|
||||
Type argType2[] = {Type.tString};
|
||||
MemberDefinition f2 =
|
||||
stClsDef.matchMethod(env, sourceClass, idValueOf, argType2);
|
||||
asm.add(where, opc_invokestatic, f2);
|
||||
}
|
||||
} else {
|
||||
// Primitive type
|
||||
Type argType[] = {type};
|
||||
MemberDefinition f =
|
||||
stClsDef.matchMethod(env, sourceClass, idValueOf, argType);
|
||||
asm.add(where, opc_invokestatic, f);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert this expression to a string and append it to the string
|
||||
* buffer on the top of the stack.
|
||||
* If the needBuffer argument is true, the string buffer needs to be
|
||||
* created, initialized, and pushed on the stack, first.
|
||||
*/
|
||||
void codeAppend(Environment env, Context ctx, Assembler asm,
|
||||
ClassDeclaration sbClass, boolean needBuffer)
|
||||
throws ClassNotFound, AmbiguousMember
|
||||
{
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
ClassDefinition sbClsDef = sbClass.getClassDefinition(env);
|
||||
MemberDefinition f;
|
||||
if (needBuffer) {
|
||||
// need to create the string buffer
|
||||
asm.add(where, opc_new, sbClass); // create the class
|
||||
asm.add(where, opc_dup);
|
||||
if (equals("")) {
|
||||
// make an empty string buffer
|
||||
f = sbClsDef.matchMethod(env, sourceClass, idInit);
|
||||
} else {
|
||||
// optimize by initializing the buffer with the string
|
||||
codeValue(env, ctx, asm);
|
||||
ensureString(env, ctx, asm);
|
||||
Type argType[] = {Type.tString};
|
||||
f = sbClsDef.matchMethod(env, sourceClass, idInit, argType);
|
||||
}
|
||||
asm.add(where, opc_invokespecial, f);
|
||||
} else {
|
||||
// append this item to the string buffer
|
||||
codeValue(env, ctx, asm);
|
||||
// FIX FOR 4071548
|
||||
// 'StringBuffer.append' converts its argument as if by
|
||||
// 'valueOf', treating character arrays specially. This
|
||||
// violates JLS 15.17.1.1, which requires that concatenation
|
||||
// convert non-primitive arguments using 'toString'. We force
|
||||
// the treatment of all reference types as type 'Object', thus
|
||||
// invoking an overloading of 'append' that has the required
|
||||
// semantics.
|
||||
Type argType[] =
|
||||
{ (type.inMask(TM_REFERENCE) && type != Type.tString)
|
||||
? Type.tObject
|
||||
: type };
|
||||
f = sbClsDef.matchMethod(env, sourceClass, idAppend, argType);
|
||||
asm.add(where, opc_invokevirtual, f);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeDup(Environment env, Context ctx, Assembler asm, int items, int depth) {
|
||||
switch (items) {
|
||||
case 0:
|
||||
return;
|
||||
|
||||
case 1:
|
||||
switch (depth) {
|
||||
case 0:
|
||||
asm.add(where, opc_dup);
|
||||
return;
|
||||
case 1:
|
||||
asm.add(where, opc_dup_x1);
|
||||
return;
|
||||
case 2:
|
||||
asm.add(where, opc_dup_x2);
|
||||
return;
|
||||
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
switch (depth) {
|
||||
case 0:
|
||||
asm.add(where, opc_dup2);
|
||||
return;
|
||||
case 1:
|
||||
asm.add(where, opc_dup2_x1);
|
||||
return;
|
||||
case 2:
|
||||
asm.add(where, opc_dup2_x2);
|
||||
return;
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
throw new CompilerError("can't dup: " + items + ", " + depth);
|
||||
}
|
||||
|
||||
void codeConversion(Environment env, Context ctx, Assembler asm, Type f, Type t) {
|
||||
int from = f.getTypeCode();
|
||||
int to = t.getTypeCode();
|
||||
|
||||
switch (to) {
|
||||
case TC_BOOLEAN:
|
||||
if (from != TC_BOOLEAN) {
|
||||
break;
|
||||
}
|
||||
return;
|
||||
case TC_BYTE:
|
||||
if (from != TC_BYTE) {
|
||||
codeConversion(env, ctx, asm, f, Type.tInt);
|
||||
asm.add(where, opc_i2b);
|
||||
}
|
||||
return;
|
||||
case TC_CHAR:
|
||||
if (from != TC_CHAR) {
|
||||
codeConversion(env, ctx, asm, f, Type.tInt);
|
||||
asm.add(where, opc_i2c);
|
||||
}
|
||||
return;
|
||||
case TC_SHORT:
|
||||
if (from != TC_SHORT) {
|
||||
codeConversion(env, ctx, asm, f, Type.tInt);
|
||||
asm.add(where, opc_i2s);
|
||||
}
|
||||
return;
|
||||
case TC_INT:
|
||||
switch (from) {
|
||||
case TC_BYTE:
|
||||
case TC_CHAR:
|
||||
case TC_SHORT:
|
||||
case TC_INT:
|
||||
return;
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_l2i);
|
||||
return;
|
||||
case TC_FLOAT:
|
||||
asm.add(where, opc_f2i);
|
||||
return;
|
||||
case TC_DOUBLE:
|
||||
asm.add(where, opc_d2i);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
switch (from) {
|
||||
case TC_BYTE:
|
||||
case TC_CHAR:
|
||||
case TC_SHORT:
|
||||
case TC_INT:
|
||||
asm.add(where, opc_i2l);
|
||||
return;
|
||||
case TC_LONG:
|
||||
return;
|
||||
case TC_FLOAT:
|
||||
asm.add(where, opc_f2l);
|
||||
return;
|
||||
case TC_DOUBLE:
|
||||
asm.add(where, opc_d2l);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
switch (from) {
|
||||
case TC_BYTE:
|
||||
case TC_CHAR:
|
||||
case TC_SHORT:
|
||||
case TC_INT:
|
||||
asm.add(where, opc_i2f);
|
||||
return;
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_l2f);
|
||||
return;
|
||||
case TC_FLOAT:
|
||||
return;
|
||||
case TC_DOUBLE:
|
||||
asm.add(where, opc_d2f);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
switch (from) {
|
||||
case TC_BYTE:
|
||||
case TC_CHAR:
|
||||
case TC_SHORT:
|
||||
case TC_INT:
|
||||
asm.add(where, opc_i2d);
|
||||
return;
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_l2d);
|
||||
return;
|
||||
case TC_FLOAT:
|
||||
asm.add(where, opc_f2d);
|
||||
return;
|
||||
case TC_DOUBLE:
|
||||
return;
|
||||
}
|
||||
break;
|
||||
|
||||
case TC_CLASS:
|
||||
switch (from) {
|
||||
case TC_NULL:
|
||||
return;
|
||||
case TC_CLASS:
|
||||
case TC_ARRAY:
|
||||
try {
|
||||
if (!env.implicitCast(f, t)) {
|
||||
asm.add(where, opc_checkcast, env.getClassDeclaration(t));
|
||||
}
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case TC_ARRAY:
|
||||
switch (from) {
|
||||
case TC_NULL:
|
||||
return;
|
||||
case TC_CLASS:
|
||||
case TC_ARRAY:
|
||||
try {
|
||||
if (!env.implicitCast(f, t)) {
|
||||
asm.add(where, opc_checkcast, t);
|
||||
}
|
||||
return;
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
throw new CompilerError("codeConversion: " + from + ", " + to);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the first thing is a constructor invocation
|
||||
*/
|
||||
public Expression firstConstructor() {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
return (Expression)clone();
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(opNames[op]);
|
||||
}
|
||||
}
|
||||
111
jdkSrc/jdk8/sun/tools/tree/ExpressionStatement.java
Normal file
111
jdkSrc/jdk8/sun/tools/tree/ExpressionStatement.java
Normal file
@@ -0,0 +1,111 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ExpressionStatement extends Statement {
|
||||
Expression expr;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ExpressionStatement(long where, Expression expr) {
|
||||
super(EXPRESSION, where);
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
return expr.check(env, ctx, reach(env, vset), exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
if (expr != null) {
|
||||
expr = expr.inline(env, ctx);
|
||||
return (expr == null) ? null : this;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
ExpressionStatement s = (ExpressionStatement)clone();
|
||||
s.expr = expr.copyInline(ctx);
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return expr.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
expr.code(env, ctx, asm);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the first thing is a constructor invocation
|
||||
*/
|
||||
public Expression firstConstructor() {
|
||||
return expr.firstConstructor();
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
if (expr != null) {
|
||||
expr.print(out);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
1282
jdkSrc/jdk8/sun/tools/tree/FieldExpression.java
Normal file
1282
jdkSrc/jdk8/sun/tools/tree/FieldExpression.java
Normal file
File diff suppressed because it is too large
Load Diff
242
jdkSrc/jdk8/sun/tools/tree/FieldUpdater.java
Normal file
242
jdkSrc/jdk8/sun/tools/tree/FieldUpdater.java
Normal file
@@ -0,0 +1,242 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* This class encapsulates the information required to generate an update to a private
|
||||
* field referenced from another class, e.g., an inner class. An expression denoting a
|
||||
* reference to the object to which the field belongs is associated with getter and
|
||||
* setter methods.
|
||||
* <p>
|
||||
* We use this class only for assignment, increment, and decrement operators, in which
|
||||
* the old value is first retrieved and then a new value is computed and stored.
|
||||
* Simple assignment expressions in which a value is copied without modification are
|
||||
* handled by another mechanism.
|
||||
*
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
|
||||
class FieldUpdater implements Constants {
|
||||
|
||||
// Location for reporting errors.
|
||||
// Errors will always indicate compiler failure, but these will be easier to diagnose
|
||||
// if the bogus error is localized to the offending assignment.
|
||||
private long where;
|
||||
|
||||
// The field to which this updater applies.
|
||||
// It would be easy to eliminate the need to store the field here, but we retain it for
|
||||
// diagnostic purposes.
|
||||
private MemberDefinition field;
|
||||
|
||||
// Expression denoting the object to which the getter and setter are applied.
|
||||
// If the field is static, 'base' may be null, but need not be, as a static field
|
||||
// may be selected from an object reference. Even though the value of the object
|
||||
// reference will be ignored, it may have side-effects.
|
||||
private Expression base;
|
||||
|
||||
// The getter and setter methods, generated by 'getAccessMember' and 'getUpdateMember'.
|
||||
private MemberDefinition getter;
|
||||
private MemberDefinition setter;
|
||||
|
||||
// The number of words occupied on the stack by the object reference.
|
||||
// For static fields, this is zero.
|
||||
private int depth;
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
*/
|
||||
|
||||
public FieldUpdater(long where, MemberDefinition field,
|
||||
Expression base, MemberDefinition getter, MemberDefinition setter) {
|
||||
this.where = where;
|
||||
this.field = field;
|
||||
this.base = base;
|
||||
this.getter = getter;
|
||||
this.setter = setter;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Since the object reference expression may be captured before it has been inlined,
|
||||
* we must inline it later. A <code>FieldUpdater</code> is inlined essentially as if
|
||||
* it were a child of the assignment node to which it belongs.
|
||||
*/
|
||||
|
||||
public FieldUpdater inline(Environment env, Context ctx) {
|
||||
if (base != null) {
|
||||
if (field.isStatic()) {
|
||||
base = base.inline(env, ctx);
|
||||
} else {
|
||||
base = base.inlineValue(env, ctx);
|
||||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public FieldUpdater copyInline(Context ctx) {
|
||||
return new FieldUpdater(where, field, base.copyInline(ctx), getter, setter);
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx, boolean needGet) {
|
||||
// Size of 'invokestatic' call for access method is 3 bytes.
|
||||
int cost = needGet ? 7 : 3; // getter needs extra invokestatic + dup
|
||||
// Size of expression to compute 'this' arg if needed.
|
||||
if (!field.isStatic() && base != null) {
|
||||
cost += base.costInline(thresh, env, ctx);
|
||||
}
|
||||
// We ignore the cost of duplicating value in value-needed context.
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Duplicate <code>items</code> words from the top of the stack, locating them
|
||||
* below the topmost <code>depth</code> words on the stack.
|
||||
*/
|
||||
|
||||
// This code was cribbed from 'Expression.java'. We cannot reuse that code here,
|
||||
// because we do not inherit from class 'Expression'.
|
||||
|
||||
private void codeDup(Assembler asm, int items, int depth) {
|
||||
switch (items) {
|
||||
case 0:
|
||||
return;
|
||||
case 1:
|
||||
switch (depth) {
|
||||
case 0:
|
||||
asm.add(where, opc_dup);
|
||||
return;
|
||||
case 1:
|
||||
asm.add(where, opc_dup_x1);
|
||||
return;
|
||||
case 2:
|
||||
asm.add(where, opc_dup_x2);
|
||||
return;
|
||||
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
switch (depth) {
|
||||
case 0:
|
||||
asm.add(where, opc_dup2);
|
||||
return;
|
||||
case 1:
|
||||
asm.add(where, opc_dup2_x1);
|
||||
return;
|
||||
case 2:
|
||||
asm.add(where, opc_dup2_x2);
|
||||
return;
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
throw new CompilerError("can't dup: " + items + ", " + depth);
|
||||
}
|
||||
|
||||
/**
|
||||
* Begin a field update by an assignment, increment, or decrement operator.
|
||||
* The current value of the field is left at the top of the stack.
|
||||
* If <code>valNeeded</code> is true, we arrange for the initial value to remain
|
||||
* on the stack after the update.
|
||||
*/
|
||||
|
||||
public void startUpdate(Environment env, Context ctx, Assembler asm, boolean valNeeded) {
|
||||
if (!(getter.isStatic() && setter.isStatic())) {
|
||||
throw new CompilerError("startUpdate isStatic");
|
||||
}
|
||||
if (!field.isStatic()) {
|
||||
// Provide explicit 'this' argument.
|
||||
base.codeValue(env, ctx, asm);
|
||||
depth = 1;
|
||||
} else {
|
||||
// May need to evaluate 'base' for effect.
|
||||
// If 'base' was a type expression, it should have previously been inlined away.
|
||||
if (base != null) {
|
||||
base.code(env, ctx, asm);
|
||||
}
|
||||
depth = 0;
|
||||
}
|
||||
codeDup(asm, depth, 0);
|
||||
asm.add(where, opc_invokestatic, getter);
|
||||
if (valNeeded) {
|
||||
codeDup(asm, field.getType().stackSize(), depth);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Complete a field update by an assignment, increment, or decrement operator.
|
||||
* The original value of the field left on the stack by <code>startUpdate</code>
|
||||
* must have been replaced with the updated value, with no other stack alterations.
|
||||
* If <code>valNeeded</code> is true, we arrange for the updated value to remain
|
||||
* on the stack after the update. The <code>valNeeded</code> argument must not be
|
||||
* true in both <code>startUpdate</code> and <code>finishUpdate</code>.
|
||||
*/
|
||||
|
||||
public void finishUpdate(Environment env, Context ctx, Assembler asm, boolean valNeeded) {
|
||||
if (valNeeded) {
|
||||
codeDup(asm, field.getType().stackSize(), depth);
|
||||
}
|
||||
asm.add(where, opc_invokestatic, setter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Like above, but used when assigning a new value independent of the
|
||||
* old, as in a simple assignment expression. After 'startAssign',
|
||||
* code must be emitted to leave one additional value on the stack without
|
||||
* altering any others, followed by 'finishAssign'.
|
||||
*/
|
||||
|
||||
public void startAssign(Environment env, Context ctx, Assembler asm) {
|
||||
if (!setter.isStatic()) {
|
||||
throw new CompilerError("startAssign isStatic");
|
||||
}
|
||||
if (!field.isStatic()) {
|
||||
// Provide explicit 'this' argument.
|
||||
base.codeValue(env, ctx, asm);
|
||||
depth = 1;
|
||||
} else {
|
||||
// May need to evaluate 'base' for effect.
|
||||
// If 'base' was a type expression, it should have previously been inlined away.
|
||||
if (base != null) {
|
||||
base.code(env, ctx, asm);
|
||||
}
|
||||
depth = 0;
|
||||
}
|
||||
}
|
||||
|
||||
public void finishAssign(Environment env, Context ctx, Assembler asm, boolean valNeeded) {
|
||||
if (valNeeded) {
|
||||
codeDup(asm, field.getType().stackSize(), depth);
|
||||
}
|
||||
asm.add(where, opc_invokestatic, setter);
|
||||
}
|
||||
|
||||
}
|
||||
360
jdkSrc/jdk8/sun/tools/tree/FinallyStatement.java
Normal file
360
jdkSrc/jdk8/sun/tools/tree/FinallyStatement.java
Normal file
@@ -0,0 +1,360 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2004, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import sun.tools.asm.TryData;
|
||||
import sun.tools.asm.CatchData;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
import java.util.Enumeration;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class FinallyStatement extends Statement {
|
||||
Statement body;
|
||||
Statement finalbody;
|
||||
boolean finallyCanFinish; // does finalBody never return?
|
||||
boolean needReturnSlot; // set by inner return statement
|
||||
Statement init; // try object expression or declaration from parser
|
||||
LocalMember tryTemp; // temp holding the try object, if any
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public FinallyStatement(long where, Statement body, Statement finalbody) {
|
||||
super(FINALLY, where);
|
||||
this.body = body;
|
||||
this.finalbody = finalbody;
|
||||
}
|
||||
|
||||
// /**
|
||||
// * Constructor for try (init) {body}
|
||||
// */
|
||||
// public FinallyStatement(long where, Statement init, Statement body, int junk) {
|
||||
// this(where, body, null);
|
||||
// this.init = init;
|
||||
// }
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = reach(env, vset);
|
||||
Hashtable newexp = new Hashtable();
|
||||
|
||||
// Handle the proposed 'try (init) { stmts } finally { stmts }' syntax.
|
||||
// This feature has not been adopted, and support is presently disabled.
|
||||
/*-----------------------------------------------------------*
|
||||
if (init != null) {
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
Expression tryExpr = null;
|
||||
DeclarationStatement tryDecl = null;
|
||||
long where = init.getWhere();
|
||||
// find out whether init is a simple expression or a declaration
|
||||
if (init.getOp() == EXPRESSION) {
|
||||
tryExpr = ((ExpressionStatement)init).expr;
|
||||
init = null; // restore it below
|
||||
vset = tryExpr.checkValue(env, ctx, vset, exp);
|
||||
} else if (init.getOp() == DECLARATION) {
|
||||
tryDecl = (DeclarationStatement) init;
|
||||
init = null; // restore it below
|
||||
vset = tryDecl.checkBlockStatement(env, ctx, vset, exp);
|
||||
if (tryDecl.args.length != 1) {
|
||||
env.error(where, "invalid.decl");
|
||||
} else {
|
||||
LocalMember field =
|
||||
((VarDeclarationStatement) tryDecl.args[0]).field;
|
||||
tryExpr = new IdentifierExpression(where, field);
|
||||
tryExpr.type = field.getType();
|
||||
}
|
||||
} else {
|
||||
env.error(where, "invalid.expr");
|
||||
vset = init.check(env, ctx, vset, exp);
|
||||
}
|
||||
Type type = (tryExpr == null) ? Type.tError : tryExpr.getType();
|
||||
|
||||
MemberDefinition tryEnter = null;
|
||||
MemberDefinition tryExit = null;
|
||||
if (!type.isType(TC_CLASS)) {
|
||||
if (!type.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.method.invoke", type);
|
||||
}
|
||||
} else {
|
||||
Identifier idTryEnter = Identifier.lookup("tryEnter");
|
||||
Identifier idTryExit = Identifier.lookup("tryExit");
|
||||
Type tTryMethod = Type.tMethod(Type.tVoid);
|
||||
try {
|
||||
ClassDefinition tryClass = env.getClassDefinition(type);
|
||||
tryEnter = tryClass.matchMethod(env, sourceClass, idTryEnter);
|
||||
tryExit = tryClass.matchMethod(env, sourceClass, idTryExit);
|
||||
if (tryEnter != null && !tryEnter.getType().equals(tTryMethod)) {
|
||||
tryEnter = null;
|
||||
}
|
||||
if (tryExit != null && !tryExit.getType().equals(tTryMethod)) {
|
||||
tryExit = null;
|
||||
}
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(where, "class.not.found", ee.name, ctx.field);
|
||||
} catch (AmbiguousMember ee) {
|
||||
Identifier id = ee.field1.getName();
|
||||
env.error(where, "ambig.field", id, ee.field1, ee.field2);
|
||||
}
|
||||
}
|
||||
if (tryEnter == null || tryExit == null) {
|
||||
// Make a better (more didactic) error here!
|
||||
env.error(where, "invalid.method.invoke", type);
|
||||
} else {
|
||||
tryTemp = new LocalMember(where, sourceClass, 0,
|
||||
type, Identifier.lookup("<try_object>"));
|
||||
ctx = new Context(ctx, this);
|
||||
ctx.declare(env, tryTemp);
|
||||
|
||||
Expression e;
|
||||
e = new IdentifierExpression(where, tryTemp);
|
||||
e = new AssignExpression(where, e, tryExpr);
|
||||
e = new MethodExpression(where, e, tryEnter, new Expression[0]);
|
||||
e.type = Type.tVoid;
|
||||
Statement enterCall = new ExpressionStatement(where, e);
|
||||
// store it on the init, for code generation
|
||||
if (tryDecl != null) {
|
||||
Statement args2[] = { tryDecl.args[0], enterCall };
|
||||
tryDecl.args = args2;
|
||||
init = tryDecl;
|
||||
} else {
|
||||
init = enterCall;
|
||||
}
|
||||
e = new IdentifierExpression(where, tryTemp);
|
||||
e = new MethodExpression(where, e, tryExit, new Expression[0]);
|
||||
e.type = Type.tVoid;
|
||||
Statement exitCall = new ExpressionStatement(where, e);
|
||||
finalbody = exitCall;
|
||||
}
|
||||
}
|
||||
*-----------------------------------------------------------*/
|
||||
|
||||
// Check the try part. We reach the end of the try part either by
|
||||
// finishing normally, or doing a break to the label of the try/finally.
|
||||
// NOTE: I don't think newctx1.vsBreak is ever used -- see TryStatement.
|
||||
CheckContext newctx1 = new CheckContext(ctx, this);
|
||||
Vset vset1 = body.check(env, newctx1, vset.copy(), newexp)
|
||||
.join(newctx1.vsBreak);
|
||||
// Check the finally part.
|
||||
CheckContext newctx2 = new CheckContext(ctx, this);
|
||||
// Should never access this field. The null indicates the finally part.
|
||||
newctx2.vsContinue = null;
|
||||
Vset vset2 = finalbody.check(env, newctx2, vset, exp);
|
||||
finallyCanFinish = !vset2.isDeadEnd();
|
||||
vset2 = vset2.join(newctx2.vsBreak);
|
||||
// If !finallyCanFinish, then the only possible exceptions that can
|
||||
// occur at this point are the ones preceding the try/finally, or
|
||||
// the ones generated by the finally. Anything in the try is
|
||||
// irrelevant. Otherwise, we have to merge in all the exceptions
|
||||
// generated by the body into exp.
|
||||
if (finallyCanFinish) {
|
||||
// Add newexp's back into exp; cf. ThrowStatement.check().
|
||||
for (Enumeration e = newexp.keys() ; e.hasMoreElements() ; ) {
|
||||
Object def = e.nextElement();
|
||||
exp.put(def, newexp.get(def));
|
||||
}
|
||||
}
|
||||
return ctx.removeAdditionalVars(vset1.addDAandJoinDU(vset2));
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
if (tryTemp != null) {
|
||||
ctx = new Context(ctx, this);
|
||||
ctx.declare(env, tryTemp);
|
||||
}
|
||||
if (init != null) {
|
||||
init = init.inline(env, ctx);
|
||||
}
|
||||
if (body != null) {
|
||||
body = body.inline(env, ctx);
|
||||
}
|
||||
if (finalbody != null) {
|
||||
finalbody = finalbody.inline(env, ctx);
|
||||
}
|
||||
if (body == null) {
|
||||
return eliminate(env, finalbody);
|
||||
}
|
||||
if (finalbody == null) {
|
||||
return eliminate(env, body);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
FinallyStatement s = (FinallyStatement)clone();
|
||||
if (tryTemp != null) {
|
||||
s.tryTemp = tryTemp.copyInline(ctx);
|
||||
}
|
||||
if (init != null) {
|
||||
s.init = init.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (body != null) {
|
||||
s.body = body.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (finalbody != null) {
|
||||
s.finalbody = finalbody.copyInline(ctx, valNeeded);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compute cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx){
|
||||
int cost = 4;
|
||||
if (init != null) {
|
||||
cost += init.costInline(thresh, env,ctx);
|
||||
if (cost >= thresh) return cost;
|
||||
}
|
||||
if (body != null) {
|
||||
cost += body.costInline(thresh, env,ctx);
|
||||
if (cost >= thresh) return cost;
|
||||
}
|
||||
if (finalbody != null) {
|
||||
cost += finalbody.costInline(thresh, env,ctx);
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
ctx = new Context(ctx);
|
||||
Integer num1 = null, num2 = null;
|
||||
Label endLabel = new Label();
|
||||
|
||||
if (tryTemp != null) {
|
||||
ctx.declare(env, tryTemp);
|
||||
}
|
||||
if (init != null) {
|
||||
CodeContext exprctx = new CodeContext(ctx, this);
|
||||
init.code(env, exprctx, asm);
|
||||
}
|
||||
|
||||
if (finallyCanFinish) {
|
||||
LocalMember f1, f2;
|
||||
ClassDefinition thisClass = ctx.field.getClassDefinition();
|
||||
|
||||
if (needReturnSlot) {
|
||||
Type returnType = ctx.field.getType().getReturnType();
|
||||
LocalMember localfield = new LocalMember(0, thisClass, 0,
|
||||
returnType,
|
||||
idFinallyReturnValue);
|
||||
ctx.declare(env, localfield);
|
||||
env.debugOutput("Assigning return slot to " + localfield.number);
|
||||
}
|
||||
|
||||
// allocate space for the exception and return address
|
||||
f1 = new LocalMember(where, thisClass, 0, Type.tObject, null);
|
||||
f2 = new LocalMember(where, thisClass, 0, Type.tInt, null);
|
||||
num1 = new Integer(ctx.declare(env, f1));
|
||||
num2 = new Integer(ctx.declare(env, f2));
|
||||
}
|
||||
|
||||
TryData td = new TryData();
|
||||
td.add(null);
|
||||
|
||||
// Main body
|
||||
CodeContext bodyctx = new CodeContext(ctx, this);
|
||||
asm.add(where, opc_try, td); // start of protected code
|
||||
body.code(env, bodyctx, asm);
|
||||
asm.add(bodyctx.breakLabel);
|
||||
asm.add(td.getEndLabel()); // end of protected code
|
||||
|
||||
// Cleanup afer body
|
||||
if (finallyCanFinish) {
|
||||
asm.add(where, opc_jsr, bodyctx.contLabel);
|
||||
asm.add(where, opc_goto, endLabel);
|
||||
} else {
|
||||
// just goto the cleanup code. It will never return.
|
||||
asm.add(where, opc_goto, bodyctx.contLabel);
|
||||
}
|
||||
|
||||
// Catch code
|
||||
CatchData cd = td.getCatch(0);
|
||||
asm.add(cd.getLabel());
|
||||
if (finallyCanFinish) {
|
||||
asm.add(where, opc_astore, num1); // store exception
|
||||
asm.add(where, opc_jsr, bodyctx.contLabel);
|
||||
asm.add(where, opc_aload, num1); // rethrow exception
|
||||
asm.add(where, opc_athrow);
|
||||
} else {
|
||||
// pop exception off stack. Fall through to finally code
|
||||
asm.add(where, opc_pop);
|
||||
}
|
||||
|
||||
// The finally part, which is marked by the contLabel. Update
|
||||
// breakLabel: since break's in the finally are different
|
||||
// contLabel: to null to indicate no longer in the protected code.
|
||||
asm.add(bodyctx.contLabel);
|
||||
bodyctx.contLabel = null;
|
||||
bodyctx.breakLabel = endLabel;
|
||||
if (finallyCanFinish) {
|
||||
asm.add(where, opc_astore, num2); // save the return address
|
||||
finalbody.code(env, bodyctx, asm); // execute the cleanup code
|
||||
asm.add(where, opc_ret, num2); // return
|
||||
} else {
|
||||
finalbody.code(env, bodyctx, asm); // execute the cleanup code
|
||||
}
|
||||
asm.add(endLabel); // breaks come here
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("try ");
|
||||
if (body != null) {
|
||||
body.print(out, indent);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
out.print(" finally ");
|
||||
if (finalbody != null) {
|
||||
finalbody.print(out, indent);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
}
|
||||
}
|
||||
84
jdkSrc/jdk8/sun/tools/tree/FloatExpression.java
Normal file
84
jdkSrc/jdk8/sun/tools/tree/FloatExpression.java
Normal file
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class FloatExpression extends ConstantExpression {
|
||||
float value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public FloatExpression(long where, float value) {
|
||||
super(FLOATVAL, where, Type.tFloat);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return new Float(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return value == i;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
// don't allow -0.0
|
||||
return (Float.floatToIntBits(value) == 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc, new Float(value));
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value +"F");
|
||||
}
|
||||
}
|
||||
216
jdkSrc/jdk8/sun/tools/tree/ForStatement.java
Normal file
216
jdkSrc/jdk8/sun/tools/tree/ForStatement.java
Normal file
@@ -0,0 +1,216 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ForStatement extends Statement {
|
||||
Statement init;
|
||||
Expression cond;
|
||||
Expression inc;
|
||||
Statement body;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ForStatement(long where, Statement init, Expression cond, Expression inc, Statement body) {
|
||||
super(FOR, where);
|
||||
this.init = init;
|
||||
this.cond = cond;
|
||||
this.inc = inc;
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
vset = reach(env, vset);
|
||||
Context initctx = new Context(ctx, this);
|
||||
if (init != null) {
|
||||
vset = init.checkBlockStatement(env, initctx, vset, exp);
|
||||
}
|
||||
CheckContext newctx = new CheckContext(initctx, this);
|
||||
// remember what was unassigned on entry
|
||||
Vset vsEntry = vset.copy();
|
||||
ConditionVars cvars;
|
||||
if (cond != null) {
|
||||
cvars = cond.checkCondition(env, newctx, vset, exp);
|
||||
cond = convert(env, newctx, Type.tBoolean, cond);
|
||||
} else {
|
||||
// a missing test is equivalent to "true"
|
||||
cvars = new ConditionVars();
|
||||
cvars.vsFalse = Vset.DEAD_END;
|
||||
cvars.vsTrue = vset;
|
||||
}
|
||||
vset = body.check(env, newctx, cvars.vsTrue, exp);
|
||||
vset = vset.join(newctx.vsContinue);
|
||||
if (inc != null) {
|
||||
vset = inc.check(env, newctx, vset, exp);
|
||||
}
|
||||
// Make sure the back-branch fits the entry of the loop.
|
||||
// Must include variables declared in the for-init part in the
|
||||
// set of variables visible upon loop entry that must be checked.
|
||||
initctx.checkBackBranch(env, this, vsEntry, vset);
|
||||
// exit by testing false or executing a break;
|
||||
vset = newctx.vsBreak.join(cvars.vsFalse);
|
||||
return ctx.removeAdditionalVars(vset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
ctx = new Context(ctx, this);
|
||||
if (init != null) {
|
||||
Statement body[] = {init, this};
|
||||
init = null;
|
||||
return new CompoundStatement(where, body).inline(env, ctx);
|
||||
}
|
||||
if (cond != null) {
|
||||
cond = cond.inlineValue(env, ctx);
|
||||
}
|
||||
if (body != null) {
|
||||
body = body.inline(env, ctx);
|
||||
}
|
||||
if (inc != null) {
|
||||
inc = inc.inline(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
ForStatement s = (ForStatement)clone();
|
||||
if (init != null) {
|
||||
s.init = init.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (cond != null) {
|
||||
s.cond = cond.copyInline(ctx);
|
||||
}
|
||||
if (body != null) {
|
||||
s.body = body.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (inc != null) {
|
||||
s.inc = inc.copyInline(ctx);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
int cost = 2;
|
||||
if (init != null) {
|
||||
cost += init.costInline(thresh, env, ctx);
|
||||
}
|
||||
if (cond != null) {
|
||||
cost += cond.costInline(thresh, env, ctx);
|
||||
}
|
||||
if (body != null) {
|
||||
cost += body.costInline(thresh, env, ctx);
|
||||
}
|
||||
if (inc != null) {
|
||||
cost += inc.costInline(thresh, env, ctx);
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
if (init != null) {
|
||||
init.code(env, newctx, asm);
|
||||
}
|
||||
|
||||
Label l1 = new Label();
|
||||
Label l2 = new Label();
|
||||
|
||||
asm.add(where, opc_goto, l2);
|
||||
|
||||
asm.add(l1);
|
||||
if (body != null) {
|
||||
body.code(env, newctx, asm);
|
||||
}
|
||||
|
||||
asm.add(newctx.contLabel);
|
||||
if (inc != null) {
|
||||
inc.code(env, newctx, asm);
|
||||
}
|
||||
|
||||
asm.add(l2);
|
||||
if (cond != null) {
|
||||
cond.codeBranch(env, newctx, asm, l1, true);
|
||||
} else {
|
||||
asm.add(where, opc_goto, l1);
|
||||
}
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("for (");
|
||||
if (init != null) {
|
||||
init.print(out, indent);
|
||||
out.print(" ");
|
||||
} else {
|
||||
out.print("; ");
|
||||
}
|
||||
if (cond != null) {
|
||||
cond.print(out);
|
||||
out.print(" ");
|
||||
}
|
||||
out.print("; ");
|
||||
if (inc != null) {
|
||||
inc.print(out);
|
||||
}
|
||||
out.print(") ");
|
||||
if (body != null) {
|
||||
body.print(out, indent);
|
||||
} else {
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
}
|
||||
102
jdkSrc/jdk8/sun/tools/tree/GreaterExpression.java
Normal file
102
jdkSrc/jdk8/sun/tools/tree/GreaterExpression.java
Normal file
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class GreaterExpression extends BinaryCompareExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public GreaterExpression(long where, Expression left, Expression right) {
|
||||
super(GT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a > b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a > b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a > b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a > b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new LessExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmpgt : opc_if_icmple, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpl);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpl);
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_ifgt : opc_ifle, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
102
jdkSrc/jdk8/sun/tools/tree/GreaterOrEqualExpression.java
Normal file
102
jdkSrc/jdk8/sun/tools/tree/GreaterOrEqualExpression.java
Normal file
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class GreaterOrEqualExpression extends BinaryCompareExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public GreaterOrEqualExpression(long where, Expression left, Expression right) {
|
||||
super(GE, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a >= b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a >= b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a >= b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a >= b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new LessOrEqualExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmpge : opc_if_icmplt, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpl);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpl);
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_ifge : opc_iflt, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
477
jdkSrc/jdk8/sun/tools/tree/IdentifierExpression.java
Normal file
477
jdkSrc/jdk8/sun/tools/tree/IdentifierExpression.java
Normal file
@@ -0,0 +1,477 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.LocalVariable;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class IdentifierExpression extends Expression {
|
||||
Identifier id;
|
||||
MemberDefinition field;
|
||||
Expression implementation;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public IdentifierExpression(long where, Identifier id) {
|
||||
super(IDENT, where, Type.tError);
|
||||
this.id = id;
|
||||
}
|
||||
public IdentifierExpression(IdentifierToken id) {
|
||||
this(id.getWhere(), id.getName());
|
||||
}
|
||||
public IdentifierExpression(long where, MemberDefinition field) {
|
||||
super(IDENT, where, field.getType());
|
||||
this.id = field.getName();
|
||||
this.field = field;
|
||||
}
|
||||
|
||||
public Expression getImplementation() {
|
||||
if (implementation != null)
|
||||
return implementation;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(Identifier id) {
|
||||
return this.id.equals(id);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Assign a value to this identifier. [It must already be "bound"]
|
||||
*/
|
||||
private Vset assign(Environment env, Context ctx, Vset vset) {
|
||||
if (field.isLocal()) {
|
||||
LocalMember local = (LocalMember)field;
|
||||
if (local.scopeNumber < ctx.frameNumber) {
|
||||
env.error(where, "assign.to.uplevel", id);
|
||||
}
|
||||
if (local.isFinal()) {
|
||||
// allow definite single assignment of blank finals
|
||||
if (!local.isBlankFinal()) {
|
||||
env.error(where, "assign.to.final", id);
|
||||
} else if (!vset.testVarUnassigned(local.number)) {
|
||||
env.error(where, "assign.to.blank.final", id);
|
||||
}
|
||||
}
|
||||
vset.addVar(local.number);
|
||||
local.writecount++;
|
||||
} else if (field.isFinal()) {
|
||||
vset = FieldExpression.checkFinalAssign(env, ctx, vset,
|
||||
where, field);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value of this identifier. [ It must already be "bound"]
|
||||
*/
|
||||
private Vset get(Environment env, Context ctx, Vset vset) {
|
||||
if (field.isLocal()) {
|
||||
LocalMember local = (LocalMember)field;
|
||||
if (local.scopeNumber < ctx.frameNumber && !local.isFinal()) {
|
||||
env.error(where, "invalid.uplevel", id);
|
||||
}
|
||||
if (!vset.testVar(local.number)) {
|
||||
env.error(where, "var.not.initialized", id);
|
||||
vset.addVar(local.number);
|
||||
}
|
||||
local.readcount++;
|
||||
} else {
|
||||
if (!field.isStatic()) {
|
||||
if (!vset.testVar(ctx.getThisNumber())) {
|
||||
env.error(where, "access.inst.before.super", id);
|
||||
implementation = null;
|
||||
}
|
||||
}
|
||||
if (field.isBlankFinal()) {
|
||||
int number = ctx.getFieldNumber(field);
|
||||
if (number >= 0 && !vset.testVar(number)) {
|
||||
env.error(where, "var.not.initialized", id);
|
||||
}
|
||||
}
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bind to a field
|
||||
*/
|
||||
boolean bind(Environment env, Context ctx) {
|
||||
try {
|
||||
field = ctx.getField(env, id);
|
||||
if (field == null) {
|
||||
for (ClassDefinition cdef = ctx.field.getClassDefinition();
|
||||
cdef != null; cdef = cdef.getOuterClass()) {
|
||||
if (cdef.findAnyMethod(env, id) != null) {
|
||||
env.error(where, "invalid.var", id,
|
||||
ctx.field.getClassDeclaration());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
env.error(where, "undef.var", id);
|
||||
return false;
|
||||
}
|
||||
|
||||
type = field.getType();
|
||||
|
||||
// Check access permission
|
||||
if (!ctx.field.getClassDefinition().canAccess(env, field)) {
|
||||
env.error(where, "no.field.access",
|
||||
id, field.getClassDeclaration(),
|
||||
ctx.field.getClassDeclaration());
|
||||
return false;
|
||||
}
|
||||
|
||||
// Find out how to access this variable.
|
||||
if (field.isLocal()) {
|
||||
LocalMember local = (LocalMember)field;
|
||||
if (local.scopeNumber < ctx.frameNumber) {
|
||||
// get a "val$x" copy via the current object
|
||||
implementation = ctx.makeReference(env, local);
|
||||
}
|
||||
} else {
|
||||
MemberDefinition f = field;
|
||||
|
||||
if (f.reportDeprecated(env)) {
|
||||
env.error(where, "warn.field.is.deprecated",
|
||||
id, f.getClassDefinition());
|
||||
}
|
||||
|
||||
ClassDefinition fclass = f.getClassDefinition();
|
||||
if (fclass != ctx.field.getClassDefinition()) {
|
||||
// Maybe an inherited field hides an apparent variable.
|
||||
MemberDefinition f2 = ctx.getApparentField(env, id);
|
||||
if (f2 != null && f2 != f) {
|
||||
ClassDefinition c = ctx.findScope(env, fclass);
|
||||
if (c == null) c = f.getClassDefinition();
|
||||
if (f2.isLocal()) {
|
||||
env.error(where, "inherited.hides.local",
|
||||
id, c.getClassDeclaration());
|
||||
} else {
|
||||
env.error(where, "inherited.hides.field",
|
||||
id, c.getClassDeclaration(),
|
||||
f2.getClassDeclaration());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Rewrite as a FieldExpression.
|
||||
// Access methods for private fields, if needed, will be added
|
||||
// during subsequent processing of the FieldExpression. See
|
||||
// method 'FieldExpression.checkCommon'. This division of labor
|
||||
// is somewhat awkward, as most further processing of a
|
||||
// FieldExpression during the checking phase is suppressed when
|
||||
// the referenced field is pre-set as it is here.
|
||||
|
||||
if (f.isStatic()) {
|
||||
Expression base = new TypeExpression(where,
|
||||
f.getClassDeclaration().getType());
|
||||
implementation = new FieldExpression(where, null, f);
|
||||
} else {
|
||||
Expression base = ctx.findOuterLink(env, where, f);
|
||||
if (base != null) {
|
||||
implementation = new FieldExpression(where, base, f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check forward reference
|
||||
if (!ctx.canReach(env, field)) {
|
||||
env.error(where, "forward.ref",
|
||||
id, field.getClassDeclaration());
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
} catch (ClassNotFound e) {
|
||||
env.error(where, "class.not.found", e.name, ctx.field);
|
||||
} catch (AmbiguousMember e) {
|
||||
env.error(where, "ambig.field", id,
|
||||
e.field1.getClassDeclaration(),
|
||||
e.field2.getClassDeclaration());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
if (field != null) {
|
||||
// An internally pre-set field, such as an argument copying
|
||||
// an uplevel value. Do not re-check it.
|
||||
return vset;
|
||||
}
|
||||
if (bind(env, ctx)) {
|
||||
vset = get(env, ctx, vset);
|
||||
ctx.field.getClassDefinition().addDependency(field.getClassDeclaration());
|
||||
if (implementation != null)
|
||||
vset = implementation.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression if it appears on the LHS of an assignment
|
||||
*/
|
||||
public Vset checkLHS(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp) {
|
||||
if (!bind(env, ctx))
|
||||
return vset;
|
||||
vset = assign(env, ctx, vset);
|
||||
if (implementation != null)
|
||||
vset = implementation.checkValue(env, ctx, vset, exp);
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression if it appears on the LHS of an op= expression
|
||||
*/
|
||||
public Vset checkAssignOp(Environment env, Context ctx,
|
||||
Vset vset, Hashtable exp, Expression outside) {
|
||||
if (!bind(env, ctx))
|
||||
return vset;
|
||||
vset = assign(env, ctx, get(env, ctx, vset));
|
||||
if (implementation != null)
|
||||
vset = implementation.checkValue(env, ctx, vset, exp);
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return an accessor if one is needed for assignments to this expression.
|
||||
*/
|
||||
public FieldUpdater getAssigner(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.getAssigner(env, ctx);
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return an updater if one is needed for assignments to this expression.
|
||||
*/
|
||||
public FieldUpdater getUpdater(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.getUpdater(env, ctx);
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the present name is part of a scoping prefix.
|
||||
*/
|
||||
public Vset checkAmbigName(Environment env, Context ctx, Vset vset, Hashtable exp,
|
||||
UnaryExpression loc) {
|
||||
try {
|
||||
if (ctx.getField(env, id) != null) {
|
||||
// if this is a local field, there's nothing more to do.
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
} catch (ClassNotFound ee) {
|
||||
} catch (AmbiguousMember ee) {
|
||||
}
|
||||
// Can this be interpreted as a type?
|
||||
ClassDefinition c = toResolvedType(env, ctx, true);
|
||||
// Is it a real type??
|
||||
if (c != null) {
|
||||
loc.right = new TypeExpression(where, c.getType());
|
||||
return vset;
|
||||
}
|
||||
// We hope it is a package prefix. Let the caller decide.
|
||||
type = Type.tPackage;
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert an identifier to a known type, or null.
|
||||
*/
|
||||
private ClassDefinition toResolvedType(Environment env, Context ctx,
|
||||
boolean pkgOK) {
|
||||
Identifier rid = ctx.resolveName(env, id);
|
||||
Type t = Type.tClass(rid);
|
||||
if (pkgOK && !env.classExists(t)) {
|
||||
return null;
|
||||
}
|
||||
if (env.resolve(where, ctx.field.getClassDefinition(), t)) {
|
||||
try {
|
||||
ClassDefinition c = env.getClassDefinition(t);
|
||||
|
||||
// Maybe an inherited class hides an apparent class.
|
||||
if (c.isMember()) {
|
||||
ClassDefinition sc = ctx.findScope(env, c.getOuterClass());
|
||||
if (sc != c.getOuterClass()) {
|
||||
Identifier rid2 = ctx.getApparentClassName(env, id);
|
||||
if (!rid2.equals(idNull) && !rid2.equals(rid)) {
|
||||
env.error(where, "inherited.hides.type",
|
||||
id, sc.getClassDeclaration());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!c.getLocalName().equals(id.getFlatName().getName())) {
|
||||
env.error(where, "illegal.mangled.name", id, c);
|
||||
}
|
||||
|
||||
return c;
|
||||
} catch (ClassNotFound ee) {
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert an identifier to a type.
|
||||
* If one is not known, use the current package as a qualifier.
|
||||
*/
|
||||
Type toType(Environment env, Context ctx) {
|
||||
ClassDefinition c = toResolvedType(env, ctx, false);
|
||||
if (c != null) {
|
||||
return c.getType();
|
||||
}
|
||||
return Type.tError;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert an expresion to a type in a context where a qualified
|
||||
* type name is expected, e.g., in the prefix of a qualified type
|
||||
* name. We do not necessarily know where the package prefix ends,
|
||||
* so we operate similarly to 'checkAmbiguousName'. This is the
|
||||
* base case -- the first component of the qualified name.
|
||||
*/
|
||||
/*-------------------------------------------------------*
|
||||
Type toQualifiedType(Environment env, Context ctx) {
|
||||
// We do not look for non-type fields. Is this correct?
|
||||
ClassDefinition c = toResolvedType(env, ctx, true);
|
||||
// Is it a real type?
|
||||
if (c != null) {
|
||||
return c.getType();
|
||||
}
|
||||
// We hope it is a package prefix. Let the caller decide.
|
||||
return Type.tPackage;
|
||||
}
|
||||
*-------------------------------------------------------*/
|
||||
|
||||
/**
|
||||
* Check if constant: Will it inline away?
|
||||
*/
|
||||
public boolean isConstant() {
|
||||
if (implementation != null)
|
||||
return implementation.isConstant();
|
||||
if (field != null) {
|
||||
return field.isConstant();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return null;
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inlineValue(env, ctx);
|
||||
if (field == null) {
|
||||
return this;
|
||||
}
|
||||
try {
|
||||
if (field.isLocal()) {
|
||||
if (field.isInlineable(env, false)) {
|
||||
Expression e = (Expression)field.getValue(env);
|
||||
return (e == null) ? this : e.inlineValue(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
return this;
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
}
|
||||
public Expression inlineLHS(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inlineLHS(env, ctx);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Expression copyInline(Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.copyInline(ctx);
|
||||
IdentifierExpression e =
|
||||
(IdentifierExpression)super.copyInline(ctx);
|
||||
if (field != null && field.isLocal()) {
|
||||
e.field = ((LocalMember)field).getCurrentInlineCopy(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.costInline(thresh, env, ctx);
|
||||
return super.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code local vars (object fields have been inlined away)
|
||||
*/
|
||||
int codeLValue(Environment env, Context ctx, Assembler asm) {
|
||||
return 0;
|
||||
}
|
||||
void codeLoad(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_iload + type.getTypeCodeOffset(),
|
||||
new Integer(((LocalMember)field).number));
|
||||
}
|
||||
void codeStore(Environment env, Context ctx, Assembler asm) {
|
||||
LocalMember local = (LocalMember)field;
|
||||
asm.add(where, opc_istore + type.getTypeCodeOffset(),
|
||||
new LocalVariable(local, local.number));
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeLValue(env, ctx, asm);
|
||||
codeLoad(env, ctx, asm);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(id + "#" + ((field != null) ? field.hashCode() : 0));
|
||||
if (implementation != null) {
|
||||
out.print("/IMPL=");
|
||||
implementation.print(out);
|
||||
}
|
||||
}
|
||||
}
|
||||
203
jdkSrc/jdk8/sun/tools/tree/IfStatement.java
Normal file
203
jdkSrc/jdk8/sun/tools/tree/IfStatement.java
Normal file
@@ -0,0 +1,203 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class IfStatement extends Statement {
|
||||
Expression cond;
|
||||
Statement ifTrue;
|
||||
Statement ifFalse;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public IfStatement(long where, Expression cond, Statement ifTrue, Statement ifFalse) {
|
||||
super(IF, where);
|
||||
this.cond = cond;
|
||||
this.ifTrue = ifTrue;
|
||||
this.ifFalse = ifFalse;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
CheckContext newctx = new CheckContext(ctx, this);
|
||||
// Vset vsExtra = vset.copy(); // See comment below.
|
||||
ConditionVars cvars =
|
||||
cond.checkCondition(env, newctx, reach(env, vset), exp);
|
||||
cond = convert(env, newctx, Type.tBoolean, cond);
|
||||
// The following code, now deleted, was apparently an erroneous attempt
|
||||
// at providing better error diagnostics. The comment read: 'If either
|
||||
// the true clause or the false clause is unreachable, do a reasonable
|
||||
// check on the child anyway.'
|
||||
// Vset vsTrue = cvars.vsTrue.isDeadEnd() ? vsExtra : cvars.vsTrue;
|
||||
// Vset vsFalse = cvars.vsFalse.isDeadEnd() ? vsExtra : cvars.vsFalse;
|
||||
// Unfortunately, this violates the rules laid out in the JLS, and leads to
|
||||
// blatantly incorrect results. For example, 'i' will not be recognized
|
||||
// as definitely assigned following the statement 'if (true) i = 1;'.
|
||||
// It is best to slavishly follow the JLS here. A cleverer approach could
|
||||
// only correctly issue warnings, as JLS 16.2.6 is quite explicit, and it
|
||||
// is OK for a dead branch of an if-statement to omit an assignment that
|
||||
// would be required in the other branch. A complication: This code also
|
||||
// had the effect of implementing the special-case rules for 'if-then' and
|
||||
// 'if-then-else' in JLS 14.19, "Unreachable Statements". We now use
|
||||
// 'Vset.clearDeadEnd' to remove the dead-end status of unreachable branches
|
||||
// without affecting the definite-assignment status of the variables, thus
|
||||
// maintaining a correct implementation of JLS 16.2.6. Fixes 4094353.
|
||||
// Note that the code below will not consider the branches unreachable if
|
||||
// the entire statement is unreachable. This is consistent with the error
|
||||
// recovery policy that reports the only the first unreachable statement
|
||||
// along an acyclic execution path.
|
||||
Vset vsTrue = cvars.vsTrue.clearDeadEnd();
|
||||
Vset vsFalse = cvars.vsFalse.clearDeadEnd();
|
||||
vsTrue = ifTrue.check(env, newctx, vsTrue, exp);
|
||||
if (ifFalse != null)
|
||||
vsFalse = ifFalse.check(env, newctx, vsFalse, exp);
|
||||
vset = vsTrue.join(vsFalse.join(newctx.vsBreak));
|
||||
return ctx.removeAdditionalVars(vset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
ctx = new Context(ctx, this);
|
||||
cond = cond.inlineValue(env, ctx);
|
||||
|
||||
// The compiler currently needs to perform inlining on both
|
||||
// branches of the if statement -- even if `cond' is a constant
|
||||
// true or false. Why? The compiler will later try to compile
|
||||
// all classes that it has seen; this includes classes that
|
||||
// appear in dead code. If we don't inline the dead branch here
|
||||
// then the compiler will never perform inlining on any local
|
||||
// classes appearing on the dead code. When the compiler tries
|
||||
// to compile an un-inlined local class with uplevel references,
|
||||
// it dies. (bug 4059492)
|
||||
//
|
||||
// A better solution to this would be to walk the dead branch and
|
||||
// mark any local classes appearing therein as unneeded. Then the
|
||||
// compilation phase could skip these classes.
|
||||
if (ifTrue != null) {
|
||||
ifTrue = ifTrue.inline(env, ctx);
|
||||
}
|
||||
if (ifFalse != null) {
|
||||
ifFalse = ifFalse.inline(env, ctx);
|
||||
}
|
||||
if (cond.equals(true)) {
|
||||
return eliminate(env, ifTrue);
|
||||
}
|
||||
if (cond.equals(false)) {
|
||||
return eliminate(env, ifFalse);
|
||||
}
|
||||
if ((ifTrue == null) && (ifFalse == null)) {
|
||||
return eliminate(env, new ExpressionStatement(where, cond).inline(env, ctx));
|
||||
}
|
||||
if (ifTrue == null) {
|
||||
cond = new NotExpression(cond.where, cond).inlineValue(env, ctx);
|
||||
return eliminate(env, new IfStatement(where, cond, ifFalse, null));
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
IfStatement s = (IfStatement)clone();
|
||||
s.cond = cond.copyInline(ctx);
|
||||
if (ifTrue != null) {
|
||||
s.ifTrue = ifTrue.copyInline(ctx, valNeeded);
|
||||
}
|
||||
if (ifFalse != null) {
|
||||
s.ifFalse = ifFalse.copyInline(ctx, valNeeded);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
int cost = 1 + cond.costInline(thresh, env, ctx);
|
||||
if (ifTrue != null) {
|
||||
cost += ifTrue.costInline(thresh, env, ctx);
|
||||
}
|
||||
if (ifFalse != null) {
|
||||
cost += ifFalse.costInline(thresh, env, ctx);
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
|
||||
Label l1 = new Label();
|
||||
cond.codeBranch(env, newctx, asm, l1, false);
|
||||
ifTrue.code(env, newctx, asm);
|
||||
if (ifFalse != null) {
|
||||
Label l2 = new Label();
|
||||
asm.add(true, where, opc_goto, l2);
|
||||
asm.add(l1);
|
||||
ifFalse.code(env, newctx, asm);
|
||||
asm.add(l2);
|
||||
} else {
|
||||
asm.add(l1);
|
||||
}
|
||||
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("if ");
|
||||
cond.print(out);
|
||||
out.print(" ");
|
||||
ifTrue.print(out, indent);
|
||||
if (ifFalse != null) {
|
||||
out.print(" else ");
|
||||
ifFalse.print(out, indent);
|
||||
}
|
||||
}
|
||||
}
|
||||
189
jdkSrc/jdk8/sun/tools/tree/IncDecExpression.java
Normal file
189
jdkSrc/jdk8/sun/tools/tree/IncDecExpression.java
Normal file
@@ -0,0 +1,189 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class IncDecExpression extends UnaryExpression {
|
||||
|
||||
private FieldUpdater updater = null;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public IncDecExpression(int op, long where, Expression right) {
|
||||
super(op, where, right.type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check an increment or decrement expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = right.checkAssignOp(env, ctx, vset, exp, this);
|
||||
if (right.type.inMask(TM_NUMBER)) {
|
||||
type = right.type;
|
||||
} else {
|
||||
if (!right.type.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.arg.type", right.type, opNames[op]);
|
||||
}
|
||||
type = Type.tError;
|
||||
}
|
||||
updater = right.getUpdater(env, ctx); // Must be called after 'checkAssignOp'.
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check void expression
|
||||
*/
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return inlineValue(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
// Why not inlineLHS? But that does not work.
|
||||
right = right.inlineValue(env, ctx);
|
||||
if (updater != null) {
|
||||
updater = updater.inline(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (updater == null) {
|
||||
if ((right.op == IDENT) && type.isType(TC_INT) &&
|
||||
(((IdentifierExpression)right).field.isLocal())) {
|
||||
// Increment variable in place. Count 3 bytes for 'iinc'.
|
||||
return 3;
|
||||
}
|
||||
// Cost to load lhs reference, fetch local, increment, and store.
|
||||
// Load/store cost will be higher if variable is a field. Note that
|
||||
// costs are highly approximate. See 'AssignOpExpression.costInline'
|
||||
// Does not account for cost of conversions,or duplications in
|
||||
// value-needed context..
|
||||
return right.costInline(thresh, env, ctx) + 4;
|
||||
} else {
|
||||
// Cost of two access method calls (get/set) + cost of increment.
|
||||
return updater.costInline(thresh, env, ctx, true) + 1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
|
||||
private void codeIncDecOp(Assembler asm, boolean inc) {
|
||||
switch (type.getTypeCode()) {
|
||||
case TC_BYTE:
|
||||
asm.add(where, opc_ldc, new Integer(1));
|
||||
asm.add(where, inc ? opc_iadd : opc_isub);
|
||||
asm.add(where, opc_i2b);
|
||||
break;
|
||||
case TC_SHORT:
|
||||
asm.add(where, opc_ldc, new Integer(1));
|
||||
asm.add(where, inc ? opc_iadd : opc_isub);
|
||||
asm.add(where, opc_i2s);
|
||||
break;
|
||||
case TC_CHAR:
|
||||
asm.add(where, opc_ldc, new Integer(1));
|
||||
asm.add(where, inc ? opc_iadd : opc_isub);
|
||||
asm.add(where, opc_i2c);
|
||||
break;
|
||||
case TC_INT:
|
||||
asm.add(where, opc_ldc, new Integer(1));
|
||||
asm.add(where, inc ? opc_iadd : opc_isub);
|
||||
break;
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_ldc2_w, new Long(1));
|
||||
asm.add(where, inc ? opc_ladd : opc_lsub);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
asm.add(where, opc_ldc, new Float(1));
|
||||
asm.add(where, inc ? opc_fadd : opc_fsub);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
asm.add(where, opc_ldc2_w, new Double(1));
|
||||
asm.add(where, inc ? opc_dadd : opc_dsub);
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("invalid type");
|
||||
}
|
||||
}
|
||||
|
||||
void codeIncDec(Environment env, Context ctx, Assembler asm, boolean inc, boolean prefix, boolean valNeeded) {
|
||||
|
||||
// The 'iinc' instruction cannot be used if an access method call is required.
|
||||
if ((right.op == IDENT) && type.isType(TC_INT) &&
|
||||
(((IdentifierExpression)right).field.isLocal()) && updater == null) {
|
||||
if (valNeeded && !prefix) {
|
||||
right.codeLoad(env, ctx, asm);
|
||||
}
|
||||
int v = ((LocalMember)((IdentifierExpression)right).field).number;
|
||||
int[] operands = { v, inc ? 1 : -1 };
|
||||
asm.add(where, opc_iinc, operands);
|
||||
if (valNeeded && prefix) {
|
||||
right.codeLoad(env, ctx, asm);
|
||||
}
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (updater == null) {
|
||||
// Field is directly accessible.
|
||||
int depth = right.codeLValue(env, ctx, asm);
|
||||
codeDup(env, ctx, asm, depth, 0);
|
||||
right.codeLoad(env, ctx, asm);
|
||||
if (valNeeded && !prefix) {
|
||||
codeDup(env, ctx, asm, type.stackSize(), depth);
|
||||
}
|
||||
codeIncDecOp(asm, inc);
|
||||
if (valNeeded && prefix) {
|
||||
codeDup(env, ctx, asm, type.stackSize(), depth);
|
||||
}
|
||||
right.codeStore(env, ctx, asm);
|
||||
} else {
|
||||
// Must use access methods.
|
||||
updater.startUpdate(env, ctx, asm, (valNeeded && !prefix));
|
||||
codeIncDecOp(asm, inc);
|
||||
updater.finishUpdate(env, ctx, asm, (valNeeded && prefix));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
109
jdkSrc/jdk8/sun/tools/tree/InlineMethodExpression.java
Normal file
109
jdkSrc/jdk8/sun/tools/tree/InlineMethodExpression.java
Normal file
@@ -0,0 +1,109 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Label;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class InlineMethodExpression extends Expression {
|
||||
MemberDefinition field;
|
||||
Statement body;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
InlineMethodExpression(long where, Type type, MemberDefinition field, Statement body) {
|
||||
super(INLINEMETHOD, where, type);
|
||||
this.field = field;
|
||||
this.body = body;
|
||||
}
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
body = body.inline(env, new Context(ctx, this));
|
||||
if (body == null) {
|
||||
return null;
|
||||
} else if (body.op == INLINERETURN) {
|
||||
Expression expr = ((InlineReturnStatement)body).expr;
|
||||
if (expr != null && type.isType(TC_VOID)) {
|
||||
throw new CompilerError("value on inline-void return");
|
||||
}
|
||||
return expr;
|
||||
} else {
|
||||
return this;
|
||||
}
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
// When this node was constructed, "copyInline" walked the body
|
||||
// with a "valNeeded" flag which made all returns either void
|
||||
// or value-bearing. The type of this node reflects that
|
||||
// earlier choice. The present inline/inlineValue distinction
|
||||
// is ignored.
|
||||
return inline(env, ctx);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
InlineMethodExpression e = (InlineMethodExpression)clone();
|
||||
if (body != null) {
|
||||
e.body = body.copyInline(ctx, true);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
// pop the result if there is any (usually, type is already void)
|
||||
super.code(env, ctx, asm);
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
body.code(env, newctx, asm);
|
||||
asm.add(newctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + "\n");
|
||||
body.print(out, 1);
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
118
jdkSrc/jdk8/sun/tools/tree/InlineNewInstanceExpression.java
Normal file
118
jdkSrc/jdk8/sun/tools/tree/InlineNewInstanceExpression.java
Normal file
@@ -0,0 +1,118 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Label;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Vector;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class InlineNewInstanceExpression extends Expression {
|
||||
MemberDefinition field;
|
||||
Statement body;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
InlineNewInstanceExpression(long where, Type type, MemberDefinition field, Statement body) {
|
||||
super(INLINENEWINSTANCE, where, type);
|
||||
this.field = field;
|
||||
this.body = body;
|
||||
}
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return inlineValue(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (body != null) {
|
||||
LocalMember v = (LocalMember)field.getArguments().elementAt(0);
|
||||
Context newctx = new Context(ctx, this);
|
||||
newctx.declare(env, v);
|
||||
body = body.inline(env, newctx);
|
||||
}
|
||||
if ((body != null) && (body.op == INLINERETURN)) {
|
||||
body = null;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
InlineNewInstanceExpression e = (InlineNewInstanceExpression)clone();
|
||||
e.body = body.copyInline(ctx, true);
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeCommon(env, ctx, asm, false);
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeCommon(env, ctx, asm, true);
|
||||
}
|
||||
private void codeCommon(Environment env, Context ctx, Assembler asm,
|
||||
boolean forValue) {
|
||||
asm.add(where, opc_new, field.getClassDeclaration());
|
||||
if (body != null) {
|
||||
LocalMember v = (LocalMember)field.getArguments().elementAt(0);
|
||||
CodeContext newctx = new CodeContext(ctx, this);
|
||||
newctx.declare(env, v);
|
||||
asm.add(where, opc_astore, new Integer(v.number));
|
||||
body.code(env, newctx, asm);
|
||||
asm.add(newctx.breakLabel);
|
||||
if (forValue) {
|
||||
asm.add(where, opc_aload, new Integer(v.number));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
LocalMember v = (LocalMember)field.getArguments().elementAt(0);
|
||||
out.println("(" + opNames[op] + "#" + v.hashCode() + "=" + field.hashCode());
|
||||
if (body != null) {
|
||||
body.print(out, 1);
|
||||
} else {
|
||||
out.print("<empty>");
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
113
jdkSrc/jdk8/sun/tools/tree/InlineReturnStatement.java
Normal file
113
jdkSrc/jdk8/sun/tools/tree/InlineReturnStatement.java
Normal file
@@ -0,0 +1,113 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class InlineReturnStatement extends Statement {
|
||||
Expression expr;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public InlineReturnStatement(long where, Expression expr) {
|
||||
super(INLINERETURN, where);
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination context of a break
|
||||
*/
|
||||
Context getDestination(Context ctx) {
|
||||
for (; ctx != null ; ctx = ctx.prev) {
|
||||
if ((ctx.node != null) && ((ctx.node.op == INLINEMETHOD) || (ctx.node.op == INLINENEWINSTANCE))) {
|
||||
return ctx;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
if (expr != null) {
|
||||
expr = expr.inlineValue(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
InlineReturnStatement s = (InlineReturnStatement)clone();
|
||||
if (expr != null) {
|
||||
s.expr = expr.copyInline(ctx);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1 + ((expr != null) ? expr.costInline(thresh, env, ctx) : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
if (expr != null) {
|
||||
expr.codeValue(env, ctx, asm);
|
||||
}
|
||||
CodeContext destctx = (CodeContext)getDestination(ctx);
|
||||
asm.add(where, opc_goto, destctx.breakLabel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("inline-return");
|
||||
if (expr != null) {
|
||||
out.print(" ");
|
||||
expr.print(out);
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
138
jdkSrc/jdk8/sun/tools/tree/InstanceOfExpression.java
Normal file
138
jdkSrc/jdk8/sun/tools/tree/InstanceOfExpression.java
Normal file
@@ -0,0 +1,138 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class InstanceOfExpression extends BinaryExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public InstanceOfExpression(long where, Expression left, Expression right) {
|
||||
super(INSTANCEOF, where, Type.tBoolean, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check the expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = left.checkValue(env, ctx, vset, exp);
|
||||
right = new TypeExpression(right.where, right.toType(env, ctx));
|
||||
|
||||
if (right.type.isType(TC_ERROR) || left.type.isType(TC_ERROR)) {
|
||||
// An error was already reported
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (!right.type.inMask(TM_CLASS|TM_ARRAY)) {
|
||||
env.error(right.where, "invalid.arg.type", right.type, opNames[op]);
|
||||
return vset;
|
||||
}
|
||||
try {
|
||||
if (!env.explicitCast(left.type, right.type)) {
|
||||
env.error(where, "invalid.instanceof", left.type, right.type);
|
||||
}
|
||||
} catch (ClassNotFound e) {
|
||||
env.error(where, "class.not.found", e.name, opNames[op]);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return left.inline(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
left = left.inlineValue(env, ctx);
|
||||
return this;
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (ctx == null) {
|
||||
return 1 + left.costInline(thresh, env, ctx);
|
||||
}
|
||||
// sourceClass is the current class trying to inline this method
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
try {
|
||||
// We only allow the inlining if the current class can access
|
||||
// the "instance of" class
|
||||
if (right.type.isType(TC_ARRAY) ||
|
||||
sourceClass.permitInlinedAccess(env, env.getClassDeclaration(right.type)))
|
||||
return 1 + left.costInline(thresh, env, ctx);
|
||||
} catch (ClassNotFound e) {
|
||||
}
|
||||
return thresh;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
if (right.type.isType(TC_CLASS)) {
|
||||
asm.add(where, opc_instanceof, env.getClassDeclaration(right.type));
|
||||
} else {
|
||||
asm.add(where, opc_instanceof, right.type);
|
||||
}
|
||||
}
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_ifne : opc_ifeq, lbl, whenTrue);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
left.code(env, ctx, asm);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + " ");
|
||||
left.print(out);
|
||||
out.print(" ");
|
||||
if (right.op == TYPE) {
|
||||
out.print(right.type.toString());
|
||||
} else {
|
||||
right.print(out);
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
70
jdkSrc/jdk8/sun/tools/tree/IntExpression.java
Normal file
70
jdkSrc/jdk8/sun/tools/tree/IntExpression.java
Normal file
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class IntExpression extends IntegerExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public IntExpression(long where, int value) {
|
||||
super(INTVAL, where, Type.tInt, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Equality, this is needed so that switch statements
|
||||
* can put IntExpressions in a hashtable
|
||||
*/
|
||||
public boolean equals(Object obj) {
|
||||
if ((obj != null) && (obj instanceof IntExpression)) {
|
||||
return value == ((IntExpression)obj).value;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Hashcode, this is needed so that switch statements
|
||||
* can put IntExpressions in a hashtable
|
||||
*/
|
||||
public int hashCode() {
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value);
|
||||
}
|
||||
}
|
||||
96
jdkSrc/jdk8/sun/tools/tree/IntegerExpression.java
Normal file
96
jdkSrc/jdk8/sun/tools/tree/IntegerExpression.java
Normal file
@@ -0,0 +1,96 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class IntegerExpression extends ConstantExpression {
|
||||
int value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
IntegerExpression(int op, long where, Type type, int value) {
|
||||
super(op, where, type);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* See if this number fits in the given type.
|
||||
*/
|
||||
public boolean fitsType(Environment env, Context ctx, Type t) {
|
||||
if (this.type.isType(TC_CHAR)) {
|
||||
// A char constant is not really an int constant,
|
||||
// so do not report that 'a' fits in a byte or short,
|
||||
// even if its value is in fact 7-bit ascii. See JLS 5.2.
|
||||
return super.fitsType(env, ctx, t);
|
||||
}
|
||||
switch (t.getTypeCode()) {
|
||||
case TC_BYTE:
|
||||
return value == (byte)value;
|
||||
case TC_SHORT:
|
||||
return value == (short)value;
|
||||
case TC_CHAR:
|
||||
return value == (char)value;
|
||||
}
|
||||
return super.fitsType(env, ctx, t);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return new Integer(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return value == i;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
return value == 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc, new Integer(value));
|
||||
}
|
||||
}
|
||||
64
jdkSrc/jdk8/sun/tools/tree/LengthExpression.java
Normal file
64
jdkSrc/jdk8/sun/tools/tree/LengthExpression.java
Normal file
@@ -0,0 +1,64 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class LengthExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public LengthExpression(long where, Expression right) {
|
||||
super(LENGTH, where, Type.tInt, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
if (!right.type.isType(TC_ARRAY)) {
|
||||
env.error(where, "invalid.length", right.type);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_arraylength);
|
||||
}
|
||||
}
|
||||
102
jdkSrc/jdk8/sun/tools/tree/LessExpression.java
Normal file
102
jdkSrc/jdk8/sun/tools/tree/LessExpression.java
Normal file
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class LessExpression extends BinaryCompareExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public LessExpression(long where, Expression left, Expression right) {
|
||||
super(LT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a < b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a < b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a < b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a < b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new GreaterExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmplt : opc_if_icmpge, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpg);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpg);
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_iflt : opc_ifge, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
102
jdkSrc/jdk8/sun/tools/tree/LessOrEqualExpression.java
Normal file
102
jdkSrc/jdk8/sun/tools/tree/LessOrEqualExpression.java
Normal file
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class LessOrEqualExpression extends BinaryCompareExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public LessOrEqualExpression(long where, Expression left, Expression right) {
|
||||
super(LE, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a <= b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a <= b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a <= b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a <= b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new GreaterOrEqualExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmple : opc_if_icmpgt, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpg);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpg);
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_ifle : opc_ifgt, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
231
jdkSrc/jdk8/sun/tools/tree/LocalMember.java
Normal file
231
jdkSrc/jdk8/sun/tools/tree/LocalMember.java
Normal file
@@ -0,0 +1,231 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.tree.*;
|
||||
import java.util.Vector;
|
||||
|
||||
/**
|
||||
* A local Field
|
||||
*
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
|
||||
public
|
||||
class LocalMember extends MemberDefinition {
|
||||
/**
|
||||
* The number of the variable
|
||||
*/
|
||||
int number = -1;
|
||||
|
||||
/**
|
||||
* Some statistics
|
||||
*/
|
||||
int readcount;
|
||||
int writecount;
|
||||
|
||||
/**
|
||||
* An indication of which block the variable comes from.
|
||||
* Helps identify uplevel references.
|
||||
*/
|
||||
int scopeNumber;
|
||||
|
||||
/**
|
||||
* Return current nesting level, i.e., the value of 'scopeNumber'.
|
||||
* Made public for the benefit of 'ClassDefinition.resolveName'.
|
||||
*/
|
||||
public int getScopeNumber() {
|
||||
return scopeNumber;
|
||||
}
|
||||
|
||||
/**
|
||||
* Used by copyInline to record the original of this copy.
|
||||
*/
|
||||
LocalMember originalOfCopy;
|
||||
|
||||
/**
|
||||
* The previous local variable, this list is used to build a nested
|
||||
* context of local variables.
|
||||
*/
|
||||
LocalMember prev;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public LocalMember(long where, ClassDefinition clazz, int modifiers, Type type,
|
||||
Identifier name) {
|
||||
super(where, clazz, modifiers, type, name, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for a block-inner class.
|
||||
*/
|
||||
public LocalMember(ClassDefinition innerClass) {
|
||||
super(innerClass);
|
||||
|
||||
// The class's "real" name is something like "foo$1$bar", but locally:
|
||||
name = innerClass.getLocalName();
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for a proxy to an instance or class variable.
|
||||
*/
|
||||
LocalMember(MemberDefinition field) {
|
||||
this(0, null, 0, field.getType(), idClass);
|
||||
// use this random slot to store the info:
|
||||
accessPeer = field;
|
||||
}
|
||||
|
||||
/**
|
||||
* Is this a proxy for the given field?
|
||||
*/
|
||||
final MemberDefinition getMember() {
|
||||
return (name == idClass) ? accessPeer : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Special checks
|
||||
*/
|
||||
public boolean isLocal() {
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Make a copy of this field, which is an argument to a method
|
||||
* or constructor. Arrange so that when occurrences of the field
|
||||
* are encountered in an immediately following copyInline() operation,
|
||||
* the expression nodes will replace the original argument by the
|
||||
* fresh copy.
|
||||
*/
|
||||
public LocalMember copyInline(Context ctx) {
|
||||
LocalMember copy = new LocalMember(where, clazz, modifiers, type, name);
|
||||
copy.readcount = this.readcount;
|
||||
copy.writecount = this.writecount;
|
||||
|
||||
copy.originalOfCopy = this;
|
||||
|
||||
// Make a temporary link from the original.
|
||||
// It only stays valid through the next call to copyInline().
|
||||
// (This means that recursive inlining won't work.)
|
||||
// To stay honest, we mark these inline copies:
|
||||
copy.addModifiers(M_LOCAL);
|
||||
if (this.accessPeer != null
|
||||
&& (this.accessPeer.getModifiers() & M_LOCAL) == 0) {
|
||||
throw new CompilerError("local copyInline");
|
||||
}
|
||||
this.accessPeer = copy;
|
||||
|
||||
return copy;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the previous result of copyInline(ctx).
|
||||
* Must be called in the course of an Expression.copyInline()
|
||||
* operation that immediately follows the LocalMember.copyInline().
|
||||
* Return "this" if there is no such copy.
|
||||
*/
|
||||
public LocalMember getCurrentInlineCopy(Context ctx) {
|
||||
MemberDefinition accessPeer = this.accessPeer;
|
||||
if (accessPeer != null && (accessPeer.getModifiers() & M_LOCAL) != 0) {
|
||||
LocalMember copy = (LocalMember)accessPeer;
|
||||
return copy;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* May inline copies of all the arguments of the given method.
|
||||
*/
|
||||
static public LocalMember[] copyArguments(Context ctx, MemberDefinition field) {
|
||||
Vector v = field.getArguments();
|
||||
LocalMember res[] = new LocalMember[v.size()];
|
||||
v.copyInto(res);
|
||||
for (int i = 0; i < res.length; i++) {
|
||||
res[i] = res[i].copyInline(ctx);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* Call this when finished with the result of a copyArguments() call.
|
||||
*/
|
||||
static public void doneWithArguments(Context ctx, LocalMember res[]) {
|
||||
for (int i = 0; i < res.length; i++) {
|
||||
if (res[i].originalOfCopy.accessPeer == res[i]) {
|
||||
res[i].originalOfCopy.accessPeer = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Is this local variable's value stable and simple enough to be directly
|
||||
* substituted for occurrences of the variable itself?
|
||||
* (This decision is made by VarDeclarationStatement.inline().)
|
||||
*/
|
||||
public boolean isInlineable(Environment env, boolean fromFinal) {
|
||||
return (getModifiers() & M_INLINEABLE) != 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if used
|
||||
*/
|
||||
public boolean isUsed() {
|
||||
return (readcount != 0) || (writecount != 0);
|
||||
}
|
||||
|
||||
// Used by class Context, only on members of MemberDefinition.available:
|
||||
LocalMember getAccessVar() {
|
||||
return (LocalMember)accessPeer;
|
||||
}
|
||||
void setAccessVar(LocalMember f) {
|
||||
accessPeer = f;
|
||||
}
|
||||
// Used by class Context, only on "AccessVar" constructor args
|
||||
MemberDefinition getAccessVarMember() {
|
||||
return accessPeer;
|
||||
}
|
||||
void setAccessVarMember(MemberDefinition f) {
|
||||
accessPeer = f;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Return value
|
||||
*/
|
||||
public Node getValue(Environment env) {
|
||||
return (Expression)getValue();
|
||||
}
|
||||
|
||||
/**
|
||||
* Value number for vsets, or -1 if none.
|
||||
*/
|
||||
public int getNumber(Context ctx) {
|
||||
return number;
|
||||
}
|
||||
}
|
||||
83
jdkSrc/jdk8/sun/tools/tree/LongExpression.java
Normal file
83
jdkSrc/jdk8/sun/tools/tree/LongExpression.java
Normal file
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class LongExpression extends ConstantExpression {
|
||||
long value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public LongExpression(long where, long value) {
|
||||
super(LONGVAL, where, Type.tLong);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return new Long(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return value == i;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to its default static value
|
||||
*/
|
||||
public boolean equalsDefault() {
|
||||
return value == 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc2_w, new Long(value));
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value + "L");
|
||||
}
|
||||
}
|
||||
949
jdkSrc/jdk8/sun/tools/tree/MethodExpression.java
Normal file
949
jdkSrc/jdk8/sun/tools/tree/MethodExpression.java
Normal file
@@ -0,0 +1,949 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class MethodExpression extends NaryExpression {
|
||||
Identifier id;
|
||||
ClassDefinition clazz; // The class in which the called method is defined
|
||||
MemberDefinition field;
|
||||
Expression implementation;
|
||||
|
||||
private boolean isSuper; // Set if qualified by 'super' or '<class>.super'.
|
||||
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public MethodExpression(long where, Expression right, Identifier id, Expression args[]) {
|
||||
super(METHOD, where, Type.tError, right, args);
|
||||
this.id = id;
|
||||
}
|
||||
public MethodExpression(long where, Expression right, MemberDefinition field, Expression args[]) {
|
||||
super(METHOD, where, field.getType().getReturnType(), right, args);
|
||||
this.id = field.getName();
|
||||
this.field = field;
|
||||
this.clazz = field.getClassDefinition();
|
||||
}
|
||||
|
||||
// This is a hack used only within certain access methods generated by
|
||||
// 'SourceClass.getAccessMember'. It allows an 'invokespecial' instruction
|
||||
// to be forced even though 'super' does not appear within the call.
|
||||
// Such access methods are needed for access to protected methods when using
|
||||
// the qualified '<class>.super.<method>(...)' notation.
|
||||
public MethodExpression(long where, Expression right,
|
||||
MemberDefinition field, Expression args[], boolean forceSuper) {
|
||||
this(where, right, field, args);
|
||||
this.isSuper = forceSuper;
|
||||
}
|
||||
|
||||
public Expression getImplementation() {
|
||||
if (implementation != null)
|
||||
return implementation;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check expression type
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
ClassDeclaration c = null;
|
||||
boolean isArray = false;
|
||||
boolean staticRef = false;
|
||||
|
||||
// Access method to use if required.
|
||||
MemberDefinition implMethod = null;
|
||||
|
||||
ClassDefinition ctxClass = ctx.field.getClassDefinition();
|
||||
|
||||
// When calling a constructor, we may need to add an
|
||||
// additional argument to transmit the outer instance link.
|
||||
Expression args[] = this.args;
|
||||
if (id.equals(idInit)){
|
||||
ClassDefinition conCls = ctxClass;
|
||||
try {
|
||||
Expression conOuter = null;
|
||||
if (right instanceof SuperExpression) {
|
||||
// outer.super(...)
|
||||
conCls = conCls.getSuperClass().getClassDefinition(env);
|
||||
conOuter = ((SuperExpression)right).outerArg;
|
||||
} else if (right instanceof ThisExpression) {
|
||||
// outer.this(...)
|
||||
conOuter = ((ThisExpression)right).outerArg;
|
||||
}
|
||||
args = NewInstanceExpression.
|
||||
insertOuterLink(env, ctx, where, conCls, conOuter, args);
|
||||
} catch (ClassNotFound ee) {
|
||||
// the same error is handled elsewhere
|
||||
}
|
||||
}
|
||||
|
||||
Type argTypes[] = new Type[args.length];
|
||||
|
||||
// The effective accessing class, for access checking.
|
||||
// This is normally the immediately enclosing class.
|
||||
ClassDefinition sourceClass = ctxClass;
|
||||
|
||||
try {
|
||||
if (right == null) {
|
||||
staticRef = ctx.field.isStatic();
|
||||
// Find the first outer scope that mentions the method.
|
||||
ClassDefinition cdef = ctxClass;
|
||||
MemberDefinition m = null;
|
||||
for (; cdef != null; cdef = cdef.getOuterClass()) {
|
||||
m = cdef.findAnyMethod(env, id);
|
||||
if (m != null) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (m == null) {
|
||||
// this is the scope for error diagnosis
|
||||
c = ctx.field.getClassDeclaration();
|
||||
} else {
|
||||
// found the innermost scope in which m occurs
|
||||
c = cdef.getClassDeclaration();
|
||||
|
||||
// Maybe an inherited method hides an apparent method.
|
||||
// Keep looking at enclosing scopes to find out.
|
||||
if (m.getClassDefinition() != cdef) {
|
||||
ClassDefinition cdef2 = cdef;
|
||||
while ((cdef2 = cdef2.getOuterClass()) != null) {
|
||||
MemberDefinition m2 = cdef2.findAnyMethod(env, id);
|
||||
if (m2 != null && m2.getClassDefinition() == cdef2) {
|
||||
env.error(where, "inherited.hides.method",
|
||||
id, cdef.getClassDeclaration(),
|
||||
cdef2.getClassDeclaration());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (id.equals(idInit)) {
|
||||
int thisN = ctx.getThisNumber();
|
||||
if (!ctx.field.isConstructor()) {
|
||||
env.error(where, "invalid.constr.invoke");
|
||||
return vset.addVar(thisN);
|
||||
}
|
||||
// As a consequence of the DA/DU rules in the JLS (draft of
|
||||
// forthcoming 2e), all variables are both definitely assigned
|
||||
// and definitely unassigned in unreachable code. Normally, this
|
||||
// correctly suppresses DA/DU-related errors in such code.
|
||||
// The use of the DA status of the 'this' variable for the extra
|
||||
// check below on correct constructor usage, however, does not quite
|
||||
// fit into this DA/DU scheme. The current representation of
|
||||
// Vsets for unreachable dead-ends, does not allow 'clearVar'
|
||||
// to work, as the DA/DU bits (all on) are implicitly represented
|
||||
// by the fact that the Vset is a dead-end. The DA/DU status
|
||||
// of the 'this' variable is supposed to be temporarily
|
||||
// cleared at the beginning of a constructor and during the
|
||||
// checking of constructor arguments (see below in this method).
|
||||
// Since 'clearVar' has no effect on dead-ends, we may
|
||||
// find the 'this' variable in an erroneously definitely-assigned state.
|
||||
// As a workaround, we suppress the following error message when
|
||||
// the Vset is a dead-end, i.e., when we are in unreachable code.
|
||||
// Unfortunately, the special-case treatment of reachability for
|
||||
// if-then and if-then-else allows unreachable code in some circumstances,
|
||||
// thus it is possible that no error message will be emitted at all.
|
||||
// While this behavior is strictly incorrect (thus we call this a
|
||||
// workaround), the problematic code is indeed unreachable and will
|
||||
// not be executed. In fact, it will be entirely omitted from the
|
||||
// translated program, and can cause no harm at runtime. A correct
|
||||
// solution would require modifying the representation of the DA/DU
|
||||
// analysis to use finite Vsets only, restricting the universe
|
||||
// of variables about which assertions are made (even in unreachable
|
||||
// code) to variables that are actually in scope. Alternatively, the
|
||||
// Vset extension and the dead-end marker (currently a reserved value
|
||||
// of the extension) could be represented orthogonally. In either case,
|
||||
// 'clearVar' could then be made to work on (non-canonical) dead ends.
|
||||
// See file 'Vset.java'.
|
||||
if (!vset.isReallyDeadEnd() && vset.testVar(thisN)) {
|
||||
env.error(where, "constr.invoke.not.first");
|
||||
return vset;
|
||||
}
|
||||
vset = vset.addVar(thisN);
|
||||
if (right instanceof SuperExpression) {
|
||||
// supers require this specific kind of checking
|
||||
vset = right.checkAmbigName(env, ctx, vset, exp, this);
|
||||
} else {
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
} else {
|
||||
vset = right.checkAmbigName(env, ctx, vset, exp, this);
|
||||
if (right.type == Type.tPackage) {
|
||||
FieldExpression.reportFailedPackagePrefix(env, right);
|
||||
return vset;
|
||||
}
|
||||
if (right instanceof TypeExpression) {
|
||||
staticRef = true;
|
||||
}
|
||||
}
|
||||
if (right.type.isType(TC_CLASS)) {
|
||||
c = env.getClassDeclaration(right.type);
|
||||
} else if (right.type.isType(TC_ARRAY)) {
|
||||
isArray = true;
|
||||
c = env.getClassDeclaration(Type.tObject);
|
||||
} else {
|
||||
if (!right.type.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.method.invoke", right.type);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Normally, the effective accessing class is the innermost
|
||||
// class surrounding the current method call, but, for calls
|
||||
// of the form '<class>.super.<method>(...)', it is <class>.
|
||||
// This allows access to protected members of a superclass
|
||||
// from within a class nested within one of its subclasses.
|
||||
// Otherwise, for example, the call below to 'matchMethod'
|
||||
// may fail due to the rules for visibility of inaccessible
|
||||
// members. For consistency, we treat qualified 'this' in
|
||||
// the same manner, as error diagnostics will be affected.
|
||||
// QUERY: Are there subtle unexplored language issues here?
|
||||
if (right instanceof FieldExpression) {
|
||||
Identifier id = ((FieldExpression)right).id;
|
||||
if (id == idThis) {
|
||||
sourceClass = ((FieldExpression)right).clazz;
|
||||
} else if (id == idSuper) {
|
||||
isSuper = true;
|
||||
sourceClass = ((FieldExpression)right).clazz;
|
||||
}
|
||||
} else if (right instanceof SuperExpression) {
|
||||
isSuper = true;
|
||||
}
|
||||
|
||||
// Fix for 4158650. When we extend a protected inner
|
||||
// class in a different package, we may not have access
|
||||
// to the type of our superclass. Allow the call to
|
||||
// the superclass constructor from within our constructor
|
||||
// Note that this check does not apply to constructor
|
||||
// calls in new instance expressions -- those are part
|
||||
// of NewInstanceExpression#check().
|
||||
if (id != idInit) {
|
||||
// Required by JLS 6.6.1. Fixes 4143715.
|
||||
// (See also 4094658.)
|
||||
if (!FieldExpression.isTypeAccessible(where, env,
|
||||
right.type,
|
||||
sourceClass)) {
|
||||
ClassDeclaration cdecl =
|
||||
sourceClass.getClassDeclaration();
|
||||
if (staticRef) {
|
||||
env.error(where, "no.type.access",
|
||||
id, right.type.toString(), cdecl);
|
||||
} else {
|
||||
env.error(where, "cant.access.member.type",
|
||||
id, right.type.toString(), cdecl);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Compose a list of argument types
|
||||
boolean hasErrors = false;
|
||||
|
||||
// "this" is not defined during argument checking
|
||||
if (id.equals(idInit)) {
|
||||
vset = vset.clearVar(ctx.getThisNumber());
|
||||
}
|
||||
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
vset = args[i].checkValue(env, ctx, vset, exp);
|
||||
argTypes[i] = args[i].type;
|
||||
hasErrors = hasErrors || argTypes[i].isType(TC_ERROR);
|
||||
}
|
||||
|
||||
// "this" is defined after the constructor invocation
|
||||
if (id.equals(idInit)) {
|
||||
vset = vset.addVar(ctx.getThisNumber());
|
||||
}
|
||||
|
||||
// Check if there are any type errors in the arguments
|
||||
if (hasErrors) {
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Get the method field, given the argument types
|
||||
clazz = c.getClassDefinition(env);
|
||||
|
||||
if (field == null) {
|
||||
|
||||
field = clazz.matchMethod(env, sourceClass, id, argTypes);
|
||||
|
||||
if (field == null) {
|
||||
if (id.equals(idInit)) {
|
||||
if (diagnoseMismatch(env, args, argTypes))
|
||||
return vset;
|
||||
String sig = clazz.getName().getName().toString();
|
||||
sig = Type.tMethod(Type.tError, argTypes).typeString(sig, false, false);
|
||||
env.error(where, "unmatched.constr", sig, c);
|
||||
return vset;
|
||||
}
|
||||
String sig = id.toString();
|
||||
sig = Type.tMethod(Type.tError, argTypes).typeString(sig, false, false);
|
||||
if (clazz.findAnyMethod(env, id) == null) {
|
||||
if (ctx.getField(env, id) != null) {
|
||||
env.error(where, "invalid.method", id, c);
|
||||
} else {
|
||||
env.error(where, "undef.meth", sig, c);
|
||||
}
|
||||
} else if (diagnoseMismatch(env, args, argTypes)) {
|
||||
} else {
|
||||
env.error(where, "unmatched.meth", sig, c);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
type = field.getType().getReturnType();
|
||||
|
||||
// Make sure that static references are allowed
|
||||
if (staticRef && !field.isStatic()) {
|
||||
env.error(where, "no.static.meth.access",
|
||||
field, field.getClassDeclaration());
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (field.isProtected()
|
||||
&& !(right == null)
|
||||
&& !(right instanceof SuperExpression
|
||||
// Extension of JLS 6.6.2 for qualified 'super'.
|
||||
|| (right instanceof FieldExpression &&
|
||||
((FieldExpression)right).id == idSuper))
|
||||
&& !sourceClass.protectedAccess(env, field, right.type)) {
|
||||
env.error(where, "invalid.protected.method.use",
|
||||
field.getName(), field.getClassDeclaration(),
|
||||
right.type);
|
||||
return vset;
|
||||
}
|
||||
|
||||
// In <class>.super.<method>(), we cannot simply evaluate
|
||||
// <class>.super to an object reference (as we would for
|
||||
// <class>.super.<field>) and then perform an 'invokespecial'.
|
||||
// An 'invokespecial' must be performed from within (a subclass of)
|
||||
// the class in which the target method is located.
|
||||
if (right instanceof FieldExpression &&
|
||||
((FieldExpression)right).id == idSuper) {
|
||||
if (!field.isPrivate()) {
|
||||
// The private case is handled below.
|
||||
// Use an access method unless the effective accessing class
|
||||
// (the class qualifying the 'super') is the same as the
|
||||
// immediately enclosing class, i.e., the qualification was
|
||||
// unnecessary.
|
||||
if (sourceClass != ctxClass) {
|
||||
implMethod = sourceClass.getAccessMember(env, ctx, field, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Access method for private field if not in the same class.
|
||||
if (implMethod == null && field.isPrivate()) {
|
||||
ClassDefinition cdef = field.getClassDefinition();
|
||||
if (cdef != ctxClass) {
|
||||
implMethod = cdef.getAccessMember(env, ctx, field, false);
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure that we are not invoking an abstract method
|
||||
if (field.isAbstract() && (right != null) && (right.op == SUPER)) {
|
||||
env.error(where, "invoke.abstract", field, field.getClassDeclaration());
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (field.reportDeprecated(env)) {
|
||||
if (field.isConstructor()) {
|
||||
env.error(where, "warn.constr.is.deprecated", field);
|
||||
} else {
|
||||
env.error(where, "warn.meth.is.deprecated",
|
||||
field, field.getClassDefinition());
|
||||
}
|
||||
}
|
||||
|
||||
// Check for recursive constructor
|
||||
if (field.isConstructor() && ctx.field.equals(field)) {
|
||||
env.error(where, "recursive.constr", field);
|
||||
}
|
||||
|
||||
// When a package-private class defines public or protected
|
||||
// members, those members may sometimes be accessed from
|
||||
// outside of the package in public subclasses. In these
|
||||
// cases, we need to massage the method call to refer to
|
||||
// to an accessible subclass rather than the package-private
|
||||
// parent class. Part of fix for 4135692.
|
||||
|
||||
// Find out if the class which contains this method
|
||||
// call has access to the class which declares the
|
||||
// public or protected method referent.
|
||||
// We don't perform this translation on constructor calls.
|
||||
if (sourceClass == ctxClass) {
|
||||
ClassDefinition declarer = field.getClassDefinition();
|
||||
if (!field.isConstructor() &&
|
||||
declarer.isPackagePrivate() &&
|
||||
!declarer.getName().getQualifier()
|
||||
.equals(sourceClass.getName().getQualifier())) {
|
||||
|
||||
//System.out.println("The access of member " +
|
||||
// field + " declared in class " +
|
||||
// declarer +
|
||||
// " is not allowed by the VM from class " +
|
||||
// accessor +
|
||||
// ". Replacing with an access of class " +
|
||||
// clazz);
|
||||
|
||||
// We cannot make this access at the VM level.
|
||||
// Construct a member which will stand for this
|
||||
// method in clazz and set `field' to refer to it.
|
||||
field =
|
||||
MemberDefinition.makeProxyMember(field, clazz, env);
|
||||
}
|
||||
}
|
||||
|
||||
sourceClass.addDependency(field.getClassDeclaration());
|
||||
if (sourceClass != ctxClass) {
|
||||
ctxClass.addDependency(field.getClassDeclaration());
|
||||
}
|
||||
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(where, "class.not.found", ee.name, ctx.field);
|
||||
return vset;
|
||||
|
||||
} catch (AmbiguousMember ee) {
|
||||
env.error(where, "ambig.field", id, ee.field1, ee.field2);
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Make sure it is qualified
|
||||
if ((right == null) && !field.isStatic()) {
|
||||
right = ctx.findOuterLink(env, where, field);
|
||||
vset = right.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
// Cast arguments
|
||||
argTypes = field.getType().getArgumentTypes();
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = convert(env, ctx, argTypes[i], args[i]);
|
||||
}
|
||||
|
||||
if (field.isConstructor()) {
|
||||
MemberDefinition m = field;
|
||||
if (implMethod != null) {
|
||||
m = implMethod;
|
||||
}
|
||||
int nargs = args.length;
|
||||
Expression[] newargs = args;
|
||||
if (nargs > this.args.length) {
|
||||
// Argument was added above.
|
||||
// Maintain the model for hidden outer args in outer.super(...):
|
||||
Expression rightI;
|
||||
if (right instanceof SuperExpression) {
|
||||
rightI = new SuperExpression(right.where, ctx);
|
||||
((SuperExpression)right).outerArg = args[0];
|
||||
} else if (right instanceof ThisExpression) {
|
||||
rightI = new ThisExpression(right.where, ctx);
|
||||
} else {
|
||||
throw new CompilerError("this.init");
|
||||
}
|
||||
if (implMethod != null) {
|
||||
// Need dummy argument for access method.
|
||||
// Dummy argument follows outer instance link.
|
||||
// Leave 'this.args' equal to 'newargs' but
|
||||
// without the outer instance link.
|
||||
newargs = new Expression[nargs+1];
|
||||
this.args = new Expression[nargs];
|
||||
newargs[0] = args[0]; // outer instance
|
||||
this.args[0] = newargs[1] = new NullExpression(where); // dummy argument
|
||||
for (int i = 1 ; i < nargs ; i++) {
|
||||
this.args[i] = newargs[i+1] = args[i];
|
||||
}
|
||||
} else {
|
||||
// Strip outer instance link from 'this.args'.
|
||||
// ASSERT(this.arg.length == nargs-1);
|
||||
for (int i = 1 ; i < nargs ; i++) {
|
||||
this.args[i-1] = args[i];
|
||||
}
|
||||
}
|
||||
implementation = new MethodExpression(where, rightI, m, newargs);
|
||||
implementation.type = type; // Is this needed?
|
||||
} else {
|
||||
// No argument was added.
|
||||
if (implMethod != null) {
|
||||
// Need dummy argument for access method.
|
||||
// Dummy argument is first, as there is no outer instance link.
|
||||
newargs = new Expression[nargs+1];
|
||||
newargs[0] = new NullExpression(where);
|
||||
for (int i = 0 ; i < nargs ; i++) {
|
||||
newargs[i+1] = args[i];
|
||||
}
|
||||
}
|
||||
implementation = new MethodExpression(where, right, m, newargs);
|
||||
}
|
||||
} else {
|
||||
// Have ordinary method.
|
||||
// Argument should have been added only for a constructor.
|
||||
if (args.length > this.args.length) {
|
||||
throw new CompilerError("method arg");
|
||||
}
|
||||
if (implMethod != null) {
|
||||
//System.out.println("Calling " + field + " via " + implMethod);
|
||||
Expression oldargs[] = this.args;
|
||||
if (field.isStatic()) {
|
||||
Expression call = new MethodExpression(where, null, implMethod, oldargs);
|
||||
implementation = new CommaExpression(where, right, call);
|
||||
} else {
|
||||
// Access method needs an explicit 'this' pointer.
|
||||
int nargs = oldargs.length;
|
||||
Expression newargs[] = new Expression[nargs+1];
|
||||
newargs[0] = right;
|
||||
for (int i = 0; i < nargs; i++) {
|
||||
newargs[i+1] = oldargs[i];
|
||||
}
|
||||
implementation = new MethodExpression(where, null, implMethod, newargs);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Follow super() by variable initializations
|
||||
if (ctx.field.isConstructor() &&
|
||||
field.isConstructor() && (right != null) && (right.op == SUPER)) {
|
||||
Expression e = makeVarInits(env, ctx);
|
||||
if (e != null) {
|
||||
if (implementation == null)
|
||||
implementation = (Expression)this.clone();
|
||||
implementation = new CommaExpression(where, implementation, e);
|
||||
}
|
||||
}
|
||||
|
||||
// Throw the declared exceptions.
|
||||
ClassDeclaration exceptions[] = field.getExceptions(env);
|
||||
if (isArray && (field.getName() == idClone) &&
|
||||
(field.getType().getArgumentTypes().length == 0)) {
|
||||
/* Arrays pretend that they have "public Object clone()" that doesn't
|
||||
* throw anything, according to the language spec.
|
||||
*/
|
||||
exceptions = new ClassDeclaration[0];
|
||||
/* See if there's a bogus catch for it, to issue a warning. */
|
||||
for (Context p = ctx; p != null; p = p.prev) {
|
||||
if (p.node != null && p.node.op == TRY) {
|
||||
((TryStatement) p.node).arrayCloneWhere = where;
|
||||
}
|
||||
}
|
||||
}
|
||||
for (int i = 0 ; i < exceptions.length ; i++) {
|
||||
if (exp.get(exceptions[i]) == null) {
|
||||
exp.put(exceptions[i], this);
|
||||
}
|
||||
}
|
||||
|
||||
// Mark all blank finals as definitely assigned following 'this(...)'.
|
||||
// Correctness follows inductively from the requirement that all blank finals
|
||||
// be definitely assigned at the completion of every constructor.
|
||||
if (ctx.field.isConstructor() &&
|
||||
field.isConstructor() && (right != null) && (right.op == THIS)) {
|
||||
ClassDefinition cls = field.getClassDefinition();
|
||||
for (MemberDefinition f = cls.getFirstMember() ; f != null ; f = f.getNextMember()) {
|
||||
if (f.isVariable() && f.isBlankFinal() && !f.isStatic()) {
|
||||
// Static variables should also be considered defined as well, but this
|
||||
// is handled in 'SourceClass.checkMembers', and we should not interfere.
|
||||
vset = vset.addVar(ctx.getFieldNumber(f));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check void expression
|
||||
*/
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* We're about to report a "unmatched method" error.
|
||||
* Try to issue a better diagnostic by comparing the actual argument types
|
||||
* with the method (or methods) available.
|
||||
* In particular, if there is an argument which fails to match <em>any</em>
|
||||
* method, we report a type mismatch error against that particular argument.
|
||||
* The diagnostic will report a target type taken from one of the methods.
|
||||
* <p>
|
||||
* Return false if we couldn't think of anything smart to say.
|
||||
*/
|
||||
boolean diagnoseMismatch(Environment env, Expression args[],
|
||||
Type argTypes[]) throws ClassNotFound {
|
||||
Type margType[] = new Type[1];
|
||||
boolean saidSomething = false;
|
||||
int start = 0;
|
||||
while (start < argTypes.length) {
|
||||
int code = clazz.diagnoseMismatch(env, id, argTypes, start, margType);
|
||||
String opName = (id.equals(idInit)) ? "constructor" : opNames[op];
|
||||
if (code == -2) {
|
||||
env.error(where, "wrong.number.args", opName);
|
||||
saidSomething = true;
|
||||
}
|
||||
if (code < 0) break;
|
||||
int i = code >> 2;
|
||||
boolean castOK = (code & 2) != 0;
|
||||
boolean ambig = (code & 1) != 0;
|
||||
Type targetType = margType[0];
|
||||
|
||||
// At least one argument is offensive to all overloadings.
|
||||
// targetType is one of the argument types it does not match.
|
||||
String ttype = ""+targetType;
|
||||
|
||||
// The message might be slightly misleading, if there are other
|
||||
// argument types that also would match. Hint at this:
|
||||
//if (ambig) ttype = "{"+ttype+";...}";
|
||||
|
||||
if (castOK)
|
||||
env.error(args[i].where, "explicit.cast.needed", opName, argTypes[i], ttype);
|
||||
else
|
||||
env.error(args[i].where, "incompatible.type", opName, argTypes[i], ttype);
|
||||
saidSomething = true;
|
||||
start = i+1; // look for other bad arguments, too
|
||||
}
|
||||
return saidSomething;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
static final int MAXINLINECOST = Statement.MAXINLINECOST;
|
||||
|
||||
private
|
||||
Expression inlineMethod(Environment env, Context ctx, Statement s, boolean valNeeded) {
|
||||
if (env.dump()) {
|
||||
System.out.println("INLINE METHOD " + field + " in " + ctx.field);
|
||||
}
|
||||
LocalMember v[] = LocalMember.copyArguments(ctx, field);
|
||||
Statement body[] = new Statement[v.length + 2];
|
||||
|
||||
int n = 0;
|
||||
if (field.isStatic()) {
|
||||
body[0] = new ExpressionStatement(where, right);
|
||||
} else {
|
||||
if ((right != null) && (right.op == SUPER)) {
|
||||
right = new ThisExpression(right.where, ctx);
|
||||
}
|
||||
body[0] = new VarDeclarationStatement(where, v[n++], right);
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
body[i + 1] = new VarDeclarationStatement(where, v[n++], args[i]);
|
||||
}
|
||||
//System.out.print("BEFORE:"); s.print(System.out); System.out.println();
|
||||
// Note: If !valNeeded, then all returns in the body of the method
|
||||
// change to void returns.
|
||||
body[body.length - 1] = (s != null) ? s.copyInline(ctx, valNeeded) : null;
|
||||
//System.out.print("COPY:"); body[body.length - 1].print(System.out); System.out.println();
|
||||
LocalMember.doneWithArguments(ctx, v);
|
||||
|
||||
// Make sure the type matches what the return statements are returning.
|
||||
Type type = valNeeded ? this.type : Type.tVoid;
|
||||
Expression e = new InlineMethodExpression(where, type, field, new CompoundStatement(where, body));
|
||||
return valNeeded ? e.inlineValue(env, ctx) : e.inline(env, ctx);
|
||||
}
|
||||
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inline(env, ctx);
|
||||
try {
|
||||
if (right != null) {
|
||||
right = field.isStatic() ? right.inline(env, ctx) : right.inlineValue(env, ctx);
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = args[i].inlineValue(env, ctx);
|
||||
}
|
||||
|
||||
// ctxClass is the current class trying to inline this method
|
||||
ClassDefinition ctxClass = ctx.field.getClassDefinition();
|
||||
|
||||
Expression e = this;
|
||||
if (env.opt() && field.isInlineable(env, clazz.isFinal()) &&
|
||||
|
||||
// Don't inline if a qualified non-static method: the call
|
||||
// itself might throw NullPointerException as a side effect
|
||||
((right == null) || (right.op==THIS) || field.isStatic()) &&
|
||||
|
||||
// We only allow the inlining if the current class can access
|
||||
// the field, the field's class, and right's declared type.
|
||||
ctxClass.permitInlinedAccess(env,
|
||||
field.getClassDeclaration()) &&
|
||||
ctxClass.permitInlinedAccess(env, field) &&
|
||||
(right==null || ctxClass.permitInlinedAccess(env,
|
||||
env.getClassDeclaration(right.type))) &&
|
||||
|
||||
((id == null) || !id.equals(idInit)) &&
|
||||
(!ctx.field.isInitializer()) && ctx.field.isMethod() &&
|
||||
(ctx.getInlineMemberContext(field) == null)) {
|
||||
Statement s = (Statement)field.getValue(env);
|
||||
if ((s == null) ||
|
||||
(s.costInline(MAXINLINECOST, env, ctx) < MAXINLINECOST)) {
|
||||
e = inlineMethod(env, ctx, s, false);
|
||||
}
|
||||
}
|
||||
return e;
|
||||
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.inlineValue(env, ctx);
|
||||
try {
|
||||
if (right != null) {
|
||||
right = field.isStatic() ? right.inline(env, ctx) : right.inlineValue(env, ctx);
|
||||
}
|
||||
if (field.getName().equals(idInit)) {
|
||||
ClassDefinition refc = field.getClassDefinition();
|
||||
UplevelReference r = refc.getReferencesFrozen();
|
||||
if (r != null) {
|
||||
r.willCodeArguments(env, ctx);
|
||||
}
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = args[i].inlineValue(env, ctx);
|
||||
}
|
||||
|
||||
// ctxClass is the current class trying to inline this method
|
||||
ClassDefinition ctxClass = ctx.field.getClassDefinition();
|
||||
|
||||
if (env.opt() && field.isInlineable(env, clazz.isFinal()) &&
|
||||
|
||||
// Don't inline if a qualified non-static method: the call
|
||||
// itself might throw NullPointerException as a side effect
|
||||
((right == null) || (right.op==THIS) || field.isStatic()) &&
|
||||
|
||||
// We only allow the inlining if the current class can access
|
||||
// the field, the field's class, and right's declared type.
|
||||
ctxClass.permitInlinedAccess(env,
|
||||
field.getClassDeclaration()) &&
|
||||
ctxClass.permitInlinedAccess(env, field) &&
|
||||
(right==null || ctxClass.permitInlinedAccess(env,
|
||||
env.getClassDeclaration(right.type))) &&
|
||||
|
||||
(!ctx.field.isInitializer()) && ctx.field.isMethod() &&
|
||||
(ctx.getInlineMemberContext(field) == null)) {
|
||||
Statement s = (Statement)field.getValue(env);
|
||||
if ((s == null) ||
|
||||
(s.costInline(MAXINLINECOST, env, ctx) < MAXINLINECOST)) {
|
||||
return inlineMethod(env, ctx, s, true);
|
||||
}
|
||||
}
|
||||
return this;
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Expression copyInline(Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.copyInline(ctx);
|
||||
return super.copyInline(ctx);
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (implementation != null)
|
||||
return implementation.costInline(thresh, env, ctx);
|
||||
|
||||
// for now, don't allow calls to super() to be inlined. We may fix
|
||||
// this later
|
||||
if ((right != null) && (right.op == SUPER)) {
|
||||
return thresh;
|
||||
}
|
||||
return super.costInline(thresh, env, ctx);
|
||||
}
|
||||
|
||||
/*
|
||||
* Grab all instance initializer code from the class definition,
|
||||
* and return as one bolus. Note that we are assuming the
|
||||
* the relevant fields have already been checked.
|
||||
* (See the pre-pass in SourceClass.checkMembers which ensures this.)
|
||||
*/
|
||||
private Expression makeVarInits(Environment env, Context ctx) {
|
||||
// insert instance initializers
|
||||
ClassDefinition clazz = ctx.field.getClassDefinition();
|
||||
Expression e = null;
|
||||
for (MemberDefinition f = clazz.getFirstMember() ; f != null ; f = f.getNextMember()) {
|
||||
if ((f.isVariable() || f.isInitializer()) && !f.isStatic()) {
|
||||
try {
|
||||
f.check(env);
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(f.getWhere(), "class.not.found", ee.name,
|
||||
f.getClassDefinition());
|
||||
}
|
||||
Expression val = null;
|
||||
if (f.isUplevelValue()) {
|
||||
if (f != clazz.findOuterMember()) {
|
||||
// it's too early to accumulate these
|
||||
continue;
|
||||
}
|
||||
IdentifierExpression arg =
|
||||
new IdentifierExpression(where, f.getName());
|
||||
if (!arg.bind(env, ctx)) {
|
||||
throw new CompilerError("bind "+arg.id);
|
||||
}
|
||||
val = arg;
|
||||
} else if (f.isInitializer()) {
|
||||
Statement s = (Statement)f.getValue();
|
||||
val = new InlineMethodExpression(where, Type.tVoid, f, s);
|
||||
} else {
|
||||
val = (Expression)f.getValue();
|
||||
}
|
||||
// append all initializers to "e":
|
||||
// This section used to check for variables which were
|
||||
// initialized to their default values and elide such
|
||||
// initialization. This is specifically disallowed by
|
||||
// JLS 12.5 numeral 4, which requires a textual ordering
|
||||
// on the execution of initializers.
|
||||
if ((val != null)) { // && !val.equals(0)) {
|
||||
long p = f.getWhere();
|
||||
val = val.copyInline(ctx);
|
||||
Expression init = val;
|
||||
if (f.isVariable()) {
|
||||
Expression v = new ThisExpression(p, ctx);
|
||||
v = new FieldExpression(p, v, f);
|
||||
init = new AssignExpression(p, v, val);
|
||||
}
|
||||
e = (e == null) ? init : new CommaExpression(p, e, init);
|
||||
}
|
||||
}
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
if (implementation != null)
|
||||
throw new CompilerError("codeValue");
|
||||
int i = 0; // argument index
|
||||
if (field.isStatic()) {
|
||||
if (right != null) {
|
||||
right.code(env, ctx, asm);
|
||||
}
|
||||
} else if (right == null) {
|
||||
asm.add(where, opc_aload, new Integer(0));
|
||||
} else if (right.op == SUPER) {
|
||||
// 'super.<method>(...)', 'super(...)', or '<expr>.super(...)'
|
||||
/*****
|
||||
isSuper = true;
|
||||
*****/
|
||||
right.codeValue(env, ctx, asm);
|
||||
if (idInit.equals(id)) {
|
||||
// 'super(...)' or '<expr>.super(...)' only
|
||||
ClassDefinition refc = field.getClassDefinition();
|
||||
UplevelReference r = refc.getReferencesFrozen();
|
||||
if (r != null) {
|
||||
// When calling a constructor for a class with
|
||||
// embedded uplevel references, add extra arguments.
|
||||
if (r.isClientOuterField()) {
|
||||
// the extra arguments are inserted after this one
|
||||
args[i++].codeValue(env, ctx, asm);
|
||||
}
|
||||
r.codeArguments(env, ctx, asm, where, field);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
right.codeValue(env, ctx, asm);
|
||||
/*****
|
||||
if (right.op == FIELD &&
|
||||
((FieldExpression)right).id == idSuper) {
|
||||
// '<class>.super.<method>(...)'
|
||||
isSuper = true;
|
||||
}
|
||||
*****/
|
||||
}
|
||||
|
||||
for ( ; i < args.length ; i++) {
|
||||
args[i].codeValue(env, ctx, asm);
|
||||
}
|
||||
|
||||
if (field.isStatic()) {
|
||||
asm.add(where, opc_invokestatic, field);
|
||||
} else if (field.isConstructor() || field.isPrivate() || isSuper) {
|
||||
asm.add(where, opc_invokespecial, field);
|
||||
} else if (field.getClassDefinition().isInterface()) {
|
||||
asm.add(where, opc_invokeinterface, field);
|
||||
} else {
|
||||
asm.add(where, opc_invokevirtual, field);
|
||||
}
|
||||
|
||||
if (right != null && right.op == SUPER && idInit.equals(id)) {
|
||||
// 'super(...)' or '<expr>.super(...)'
|
||||
ClassDefinition refc = ctx.field.getClassDefinition();
|
||||
UplevelReference r = refc.getReferencesFrozen();
|
||||
if (r != null) {
|
||||
// After calling a superclass constructor in a class with
|
||||
// embedded uplevel references, initialize uplevel fields.
|
||||
r.codeInitialization(env, ctx, asm, where, field);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the first thing is a constructor invocation
|
||||
*/
|
||||
public Expression firstConstructor() {
|
||||
return id.equals(idInit) ? this : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op]);
|
||||
if (right != null) {
|
||||
out.print(" ");
|
||||
right.print(out);
|
||||
}
|
||||
out.print(" " + ((id == null) ? idInit : id));
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
out.print(" ");
|
||||
if (args[i] != null) {
|
||||
args[i].print(out);
|
||||
} else {
|
||||
out.print("<null>");
|
||||
}
|
||||
}
|
||||
out.print(")");
|
||||
if (implementation != null) {
|
||||
out.print("/IMPL=");
|
||||
implementation.print(out);
|
||||
}
|
||||
}
|
||||
}
|
||||
80
jdkSrc/jdk8/sun/tools/tree/MultiplyExpression.java
Normal file
80
jdkSrc/jdk8/sun/tools/tree/MultiplyExpression.java
Normal file
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class MultiplyExpression extends BinaryArithmeticExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public MultiplyExpression(long where, Expression left, Expression right) {
|
||||
super(MUL, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a * b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a * b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new FloatExpression(where, a * b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new DoubleExpression(where, a * b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.equals(1)) {
|
||||
return right;
|
||||
}
|
||||
if (right.equals(1)) {
|
||||
return left;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_imul + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
99
jdkSrc/jdk8/sun/tools/tree/NaryExpression.java
Normal file
99
jdkSrc/jdk8/sun/tools/tree/NaryExpression.java
Normal file
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NaryExpression extends UnaryExpression {
|
||||
Expression args[];
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
NaryExpression(int op, long where, Type type, Expression right, Expression args[]) {
|
||||
super(op, where, type, right);
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the expression for method inlining
|
||||
*/
|
||||
public Expression copyInline(Context ctx) {
|
||||
NaryExpression e = (NaryExpression)clone();
|
||||
if (right != null) {
|
||||
e.right = right.copyInline(ctx);
|
||||
}
|
||||
e.args = new Expression[args.length];
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] != null) {
|
||||
e.args[i] = args[i].copyInline(ctx);
|
||||
}
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this expression
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
int cost = 3;
|
||||
if (right != null)
|
||||
cost += right.costInline(thresh, env, ctx);
|
||||
for (int i = 0 ; (i < args.length) && (cost < thresh) ; i++) {
|
||||
if (args[i] != null) {
|
||||
cost += args[i].costInline(thresh, env, ctx);
|
||||
}
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("(" + opNames[op] + "#" + hashCode());
|
||||
if (right != null) {
|
||||
out.print(" ");
|
||||
right.print(out);
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
out.print(" ");
|
||||
if (args[i] != null) {
|
||||
args[i].print(out);
|
||||
} else {
|
||||
out.print("<null>");
|
||||
}
|
||||
}
|
||||
out.print(")");
|
||||
}
|
||||
}
|
||||
94
jdkSrc/jdk8/sun/tools/tree/NegativeExpression.java
Normal file
94
jdkSrc/jdk8/sun/tools/tree/NegativeExpression.java
Normal file
@@ -0,0 +1,94 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NegativeExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public NegativeExpression(long where, Expression right) {
|
||||
super(NEG, where, right.type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((tm & TM_DOUBLE) != 0) {
|
||||
type = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
type = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
right = convert(env, ctx, type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a) {
|
||||
return new IntExpression(where, -a);
|
||||
}
|
||||
Expression eval(long a) {
|
||||
return new LongExpression(where, -a);
|
||||
}
|
||||
Expression eval(float a) {
|
||||
return new FloatExpression(where, -a);
|
||||
}
|
||||
Expression eval(double a) {
|
||||
return new DoubleExpression(where, -a);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (right.op == NEG) {
|
||||
return ((NegativeExpression)right).right;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_ineg + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
161
jdkSrc/jdk8/sun/tools/tree/NewArrayExpression.java
Normal file
161
jdkSrc/jdk8/sun/tools/tree/NewArrayExpression.java
Normal file
@@ -0,0 +1,161 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.ArrayData;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NewArrayExpression extends NaryExpression {
|
||||
Expression init;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public NewArrayExpression(long where, Expression right, Expression args[]) {
|
||||
super(NEWARRAY, where, Type.tError, right, args);
|
||||
}
|
||||
|
||||
public NewArrayExpression(long where, Expression right, Expression args[], Expression init) {
|
||||
this(where, right, args);
|
||||
this.init = init;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
type = right.toType(env, ctx);
|
||||
|
||||
boolean flag = (init != null); // flag says that dims are forbidden
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
Expression dim = args[i];
|
||||
if (dim == null) {
|
||||
if (i == 0 && !flag) {
|
||||
env.error(where, "array.dim.missing");
|
||||
}
|
||||
flag = true;
|
||||
} else {
|
||||
if (flag) {
|
||||
env.error(dim.where, "invalid.array.dim");
|
||||
}
|
||||
vset = dim.checkValue(env, ctx, vset, exp);
|
||||
args[i] = convert(env, ctx, Type.tInt, dim);
|
||||
}
|
||||
type = Type.tArray(type);
|
||||
}
|
||||
if (init != null) {
|
||||
vset = init.checkInitializer(env, ctx, vset, type, exp);
|
||||
init = convert(env, ctx, type, init);
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
public Expression copyInline(Context ctx) {
|
||||
NewArrayExpression e = (NewArrayExpression)super.copyInline(ctx);
|
||||
if (init != null) {
|
||||
e.init = init.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
Expression e = null;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] != null) {
|
||||
e = (e != null) ? new CommaExpression(where, e, args[i]) : args[i];
|
||||
}
|
||||
}
|
||||
if (init != null)
|
||||
e = (e != null) ? new CommaExpression(where, e, init) : init;
|
||||
return (e != null) ? e.inline(env, ctx) : null;
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (init != null)
|
||||
return init.inlineValue(env, ctx); // args are all null
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] != null) {
|
||||
args[i] = args[i].inlineValue(env, ctx);
|
||||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
int t = 0;
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
if (args[i] != null) {
|
||||
args[i].codeValue(env, ctx, asm);
|
||||
t++;
|
||||
}
|
||||
}
|
||||
if (args.length > 1) {
|
||||
asm.add(where, opc_multianewarray, new ArrayData(type, t));
|
||||
return;
|
||||
}
|
||||
|
||||
switch (type.getElementType().getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
asm.add(where, opc_newarray, new Integer(T_BOOLEAN)); break;
|
||||
case TC_BYTE:
|
||||
asm.add(where, opc_newarray, new Integer(T_BYTE)); break;
|
||||
case TC_SHORT:
|
||||
asm.add(where, opc_newarray, new Integer(T_SHORT)); break;
|
||||
case TC_CHAR:
|
||||
asm.add(where, opc_newarray, new Integer(T_CHAR)); break;
|
||||
case TC_INT:
|
||||
asm.add(where, opc_newarray, new Integer(T_INT)); break;
|
||||
case TC_LONG:
|
||||
asm.add(where, opc_newarray, new Integer(T_LONG)); break;
|
||||
case TC_FLOAT:
|
||||
asm.add(where, opc_newarray, new Integer(T_FLOAT)); break;
|
||||
case TC_DOUBLE:
|
||||
asm.add(where, opc_newarray, new Integer(T_DOUBLE)); break;
|
||||
case TC_ARRAY:
|
||||
asm.add(where, opc_anewarray, type.getElementType()); break;
|
||||
case TC_CLASS:
|
||||
asm.add(where, opc_anewarray,
|
||||
env.getClassDeclaration(type.getElementType()));
|
||||
break;
|
||||
default:
|
||||
throw new CompilerError("codeValue");
|
||||
}
|
||||
}
|
||||
}
|
||||
545
jdkSrc/jdk8/sun/tools/tree/NewInstanceExpression.java
Normal file
545
jdkSrc/jdk8/sun/tools/tree/NewInstanceExpression.java
Normal file
@@ -0,0 +1,545 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NewInstanceExpression extends NaryExpression {
|
||||
MemberDefinition field;
|
||||
Expression outerArg;
|
||||
ClassDefinition body;
|
||||
|
||||
// Access method for constructor, if needed.
|
||||
MemberDefinition implMethod = null;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public NewInstanceExpression(long where, Expression right, Expression args[]) {
|
||||
super(NEWINSTANCE, where, Type.tError, right, args);
|
||||
}
|
||||
public NewInstanceExpression(long where, Expression right,
|
||||
Expression args[],
|
||||
Expression outerArg, ClassDefinition body) {
|
||||
this(where, right, args);
|
||||
this.outerArg = outerArg;
|
||||
this.body = body;
|
||||
}
|
||||
|
||||
/**
|
||||
* From the "new" in an expression of the form outer.new InnerCls(...),
|
||||
* return the "outer" expression, or null if there is none.
|
||||
*/
|
||||
public Expression getOuterArg() {
|
||||
return outerArg;
|
||||
}
|
||||
|
||||
int precedence() {
|
||||
return 100;
|
||||
}
|
||||
|
||||
public Expression order() {
|
||||
// act like a method or field reference expression:
|
||||
if (outerArg != null && opPrecedence[FIELD] > outerArg.precedence()) {
|
||||
UnaryExpression e = (UnaryExpression)outerArg;
|
||||
outerArg = e.right;
|
||||
e.right = order();
|
||||
return e;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check expression type
|
||||
*/
|
||||
public Vset checkValue(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
// What type?
|
||||
ClassDefinition def = null;
|
||||
|
||||
Expression alreadyChecked = null;
|
||||
|
||||
try {
|
||||
if (outerArg != null) {
|
||||
vset = outerArg.checkValue(env, ctx, vset, exp);
|
||||
|
||||
// Remember the expression that we already checked
|
||||
// so that we don't attempt to check it again when
|
||||
// it appears as an argument to the constructor.
|
||||
// Fix for 4030426.
|
||||
alreadyChecked = outerArg;
|
||||
|
||||
// Check outerArg and the type name together.
|
||||
Identifier typeName = FieldExpression.toIdentifier(right);
|
||||
|
||||
// According to the inner classes spec, the type name in a
|
||||
// qualified 'new' expression must be a single identifier.
|
||||
if (typeName != null && typeName.isQualified()) {
|
||||
env.error(where, "unqualified.name.required", typeName);
|
||||
}
|
||||
|
||||
if (typeName == null || !outerArg.type.isType(TC_CLASS)) {
|
||||
if (!outerArg.type.isType(TC_ERROR)) {
|
||||
env.error(where, "invalid.field.reference",
|
||||
idNew, outerArg.type);
|
||||
}
|
||||
outerArg = null;
|
||||
} else {
|
||||
// Don't perform checks on components of qualified name
|
||||
// ('getQualifiedClassDefinition'), because a qualified
|
||||
// name is illegal in this context, and will have previously
|
||||
// been reported as an error.
|
||||
ClassDefinition oc = env.getClassDefinition(outerArg.type);
|
||||
Identifier nm = oc.resolveInnerClass(env, typeName);
|
||||
right = new TypeExpression(right.where, Type.tClass(nm));
|
||||
// Check access directly, since we're not calling toType().
|
||||
env.resolve(right.where, ctx.field.getClassDefinition(),
|
||||
right.type);
|
||||
// and fall through to env.getClassDefinition() below
|
||||
}
|
||||
}
|
||||
|
||||
if (!(right instanceof TypeExpression)) {
|
||||
// The call to 'toType' should perform component access checks.
|
||||
right = new TypeExpression(right.where, right.toType(env, ctx));
|
||||
}
|
||||
|
||||
if (right.type.isType(TC_CLASS))
|
||||
def = env.getClassDefinition(right.type);
|
||||
} catch (AmbiguousClass ee) {
|
||||
env.error(where, "ambig.class", ee.name1, ee.name2);
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(where, "class.not.found", ee.name, ctx.field);
|
||||
}
|
||||
|
||||
Type t = right.type;
|
||||
boolean hasErrors = t.isType(TC_ERROR);
|
||||
|
||||
if (!t.isType(TC_CLASS)) {
|
||||
if (!hasErrors) {
|
||||
env.error(where, "invalid.arg.type", t, opNames[op]);
|
||||
hasErrors = true;
|
||||
}
|
||||
}
|
||||
|
||||
// If we failed to find a class or a class was ambiguous, def
|
||||
// may be null. Bail out. This allows us to report multiple
|
||||
// unfound or ambiguous classes rather than tripping over an
|
||||
// internal compiler error.
|
||||
if (def == null) {
|
||||
type = Type.tError;
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Add an extra argument, maybe.
|
||||
Expression args[] = this.args;
|
||||
args = NewInstanceExpression.
|
||||
insertOuterLink(env, ctx, where, def, outerArg, args);
|
||||
if (args.length > this.args.length)
|
||||
outerArg = args[0]; // recopy the checked arg
|
||||
else if (outerArg != null)
|
||||
// else set it to void (maybe it has a side-effect)
|
||||
outerArg = new CommaExpression(outerArg.where, outerArg, null);
|
||||
|
||||
// Compose a list of argument types
|
||||
Type argTypes[] = new Type[args.length];
|
||||
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
// Don't check 'outerArg' again. Fix for 4030426.
|
||||
if (args[i] != alreadyChecked) {
|
||||
vset = args[i].checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
argTypes[i] = args[i].type;
|
||||
hasErrors = hasErrors || argTypes[i].isType(TC_ERROR);
|
||||
}
|
||||
|
||||
try {
|
||||
// Check if there are any type errors in the arguments
|
||||
if (hasErrors) {
|
||||
type = Type.tError;
|
||||
return vset;
|
||||
}
|
||||
|
||||
|
||||
// Get the source class that this declaration appears in.
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
|
||||
ClassDeclaration c = env.getClassDeclaration(t);
|
||||
|
||||
// If this is an anonymous class, handle it specially now.
|
||||
if (body != null) {
|
||||
// The current package.
|
||||
Identifier packageName = sourceClass.getName().getQualifier();
|
||||
|
||||
// This is an anonymous class.
|
||||
ClassDefinition superDef = null;
|
||||
if (def.isInterface()) {
|
||||
// For interfaces, our superclass is java.lang.Object.
|
||||
// We could just assume that java.lang.Object has
|
||||
// one constructor with no arguments in the code
|
||||
// that follows, but we don't. This way, if Object
|
||||
// grows a new constructor (unlikely) then the
|
||||
// compiler should handle it.
|
||||
superDef = env.getClassDefinition(idJavaLangObject);
|
||||
} else {
|
||||
// Otherwise, def is actually our superclass.
|
||||
superDef = def;
|
||||
}
|
||||
// Try to find a matching constructor in our superclass.
|
||||
MemberDefinition constructor =
|
||||
superDef.matchAnonConstructor(env, packageName, argTypes);
|
||||
if (constructor != null) {
|
||||
// We've found one. Process the body.
|
||||
//
|
||||
// Note that we are passing in the constructors' argument
|
||||
// types, rather than the argument types of the actual
|
||||
// expressions, to checkLocalClass(). Previously,
|
||||
// the expression types were passed in. This could
|
||||
// lead to trouble when one of the argument types was
|
||||
// the special internal type tNull. (bug 4054689).
|
||||
if (tracing)
|
||||
env.dtEvent(
|
||||
"NewInstanceExpression.checkValue: ANON CLASS " +
|
||||
body + " SUPER " + def);
|
||||
vset = body.checkLocalClass(env, ctx, vset,
|
||||
def, args,
|
||||
constructor.getType()
|
||||
.getArgumentTypes());
|
||||
|
||||
// Set t to be the true type of this expression.
|
||||
// (bug 4102056).
|
||||
t = body.getClassDeclaration().getType();
|
||||
|
||||
def = body;
|
||||
}
|
||||
} else {
|
||||
// Check if it is an interface
|
||||
if (def.isInterface()) {
|
||||
env.error(where, "new.intf", c);
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Check for abstract class
|
||||
if (def.mustBeAbstract(env)) {
|
||||
env.error(where, "new.abstract", c);
|
||||
return vset;
|
||||
}
|
||||
}
|
||||
|
||||
// Get the constructor that the "new" expression should call.
|
||||
field = def.matchMethod(env, sourceClass, idInit, argTypes);
|
||||
|
||||
// Report an error if there is no matching constructor.
|
||||
if (field == null) {
|
||||
MemberDefinition anyInit = def.findAnyMethod(env, idInit);
|
||||
if (anyInit != null &&
|
||||
new MethodExpression(where, right, anyInit, args)
|
||||
.diagnoseMismatch(env, args, argTypes))
|
||||
return vset;
|
||||
String sig = c.getName().getName().toString();
|
||||
sig = Type.tMethod(Type.tError, argTypes).typeString(sig, false, false);
|
||||
env.error(where, "unmatched.constr", sig, c);
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (field.isPrivate()) {
|
||||
ClassDefinition cdef = field.getClassDefinition();
|
||||
if (cdef != sourceClass) {
|
||||
// Use access method.
|
||||
implMethod = cdef.getAccessMember(env, ctx, field, false);
|
||||
}
|
||||
}
|
||||
|
||||
// Check for abstract anonymous class
|
||||
if (def.mustBeAbstract(env)) {
|
||||
env.error(where, "new.abstract", c);
|
||||
return vset;
|
||||
}
|
||||
|
||||
if (field.reportDeprecated(env)) {
|
||||
env.error(where, "warn.constr.is.deprecated",
|
||||
field, field.getClassDefinition());
|
||||
}
|
||||
|
||||
// According to JLS 6.6.2, a protected constructor may be accessed
|
||||
// by a class instance creation expression only from within the
|
||||
// package in which it is defined.
|
||||
if (field.isProtected() &&
|
||||
!(sourceClass.getName().getQualifier().equals(
|
||||
field.getClassDeclaration().getName().getQualifier()))) {
|
||||
env.error(where, "invalid.protected.constructor.use",
|
||||
sourceClass);
|
||||
}
|
||||
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(where, "class.not.found", ee.name, opNames[op]);
|
||||
return vset;
|
||||
|
||||
} catch (AmbiguousMember ee) {
|
||||
env.error(where, "ambig.constr", ee.field1, ee.field2);
|
||||
return vset;
|
||||
}
|
||||
|
||||
// Cast arguments
|
||||
argTypes = field.getType().getArgumentTypes();
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = convert(env, ctx, argTypes[i], args[i]);
|
||||
}
|
||||
if (args.length > this.args.length) {
|
||||
outerArg = args[0]; // recopy the checked arg
|
||||
// maintain an accurate tree
|
||||
for (int i = 1 ; i < args.length ; i++) {
|
||||
this.args[i-1] = args[i];
|
||||
}
|
||||
}
|
||||
|
||||
// Throw the declared exceptions.
|
||||
ClassDeclaration exceptions[] = field.getExceptions(env);
|
||||
for (int i = 0 ; i < exceptions.length ; i++) {
|
||||
if (exp.get(exceptions[i]) == null) {
|
||||
exp.put(exceptions[i], this);
|
||||
}
|
||||
}
|
||||
|
||||
type = t;
|
||||
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Given a list of arguments for a constructor,
|
||||
* return a possibly modified list which includes the hidden
|
||||
* argument which initializes the uplevel self pointer.
|
||||
* @arg def the class which perhaps contains an outer link.
|
||||
* @arg outerArg if non-null, an explicit location in which to construct.
|
||||
*/
|
||||
public static Expression[] insertOuterLink(Environment env, Context ctx,
|
||||
long where, ClassDefinition def,
|
||||
Expression outerArg,
|
||||
Expression args[]) {
|
||||
if (!def.isTopLevel() && !def.isLocal()) {
|
||||
Expression args2[] = new Expression[1+args.length];
|
||||
System.arraycopy(args, 0, args2, 1, args.length);
|
||||
try {
|
||||
if (outerArg == null)
|
||||
outerArg = ctx.findOuterLink(env, where,
|
||||
def.findAnyMethod(env, idInit));
|
||||
} catch (ClassNotFound e) {
|
||||
// die somewhere else
|
||||
}
|
||||
args2[0] = outerArg;
|
||||
args = args2;
|
||||
}
|
||||
return args;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check void expression
|
||||
*/
|
||||
public Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
final int MAXINLINECOST = Statement.MAXINLINECOST;
|
||||
|
||||
public Expression copyInline(Context ctx) {
|
||||
NewInstanceExpression e = (NewInstanceExpression)super.copyInline(ctx);
|
||||
if (outerArg != null) {
|
||||
e.outerArg = outerArg.copyInline(ctx);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
|
||||
Expression inlineNewInstance(Environment env, Context ctx, Statement s) {
|
||||
if (env.dump()) {
|
||||
System.out.println("INLINE NEW INSTANCE " + field + " in " + ctx.field);
|
||||
}
|
||||
LocalMember v[] = LocalMember.copyArguments(ctx, field);
|
||||
Statement body[] = new Statement[v.length + 2];
|
||||
|
||||
int o = 1;
|
||||
if (outerArg != null && !outerArg.type.isType(TC_VOID)) {
|
||||
o = 2;
|
||||
body[1] = new VarDeclarationStatement(where, v[1], outerArg);
|
||||
} else if (outerArg != null) {
|
||||
body[0] = new ExpressionStatement(where, outerArg);
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
body[i+o] = new VarDeclarationStatement(where, v[i+o], args[i]);
|
||||
}
|
||||
//System.out.print("BEFORE:"); s.print(System.out); System.out.println();
|
||||
body[body.length - 1] = (s != null) ? s.copyInline(ctx, false) : null;
|
||||
//System.out.print("COPY:"); body[body.length - 1].print(System.out); System.out.println();
|
||||
//System.out.print("AFTER:"); s.print(System.out); System.out.println();
|
||||
LocalMember.doneWithArguments(ctx, v);
|
||||
|
||||
return new InlineNewInstanceExpression(where, type, field, new CompoundStatement(where, body)).inline(env, ctx);
|
||||
}
|
||||
|
||||
public Expression inline(Environment env, Context ctx) {
|
||||
return inlineValue(env, ctx);
|
||||
}
|
||||
public Expression inlineValue(Environment env, Context ctx) {
|
||||
if (body != null) {
|
||||
body.inlineLocalClass(env);
|
||||
}
|
||||
ClassDefinition refc = field.getClassDefinition();
|
||||
UplevelReference r = refc.getReferencesFrozen();
|
||||
if (r != null) {
|
||||
r.willCodeArguments(env, ctx);
|
||||
}
|
||||
//right = right.inlineValue(env, ctx);
|
||||
|
||||
try {
|
||||
if (outerArg != null) {
|
||||
if (outerArg.type.isType(TC_VOID))
|
||||
outerArg = outerArg.inline(env, ctx);
|
||||
else
|
||||
outerArg = outerArg.inlineValue(env, ctx);
|
||||
}
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i] = args[i].inlineValue(env, ctx);
|
||||
}
|
||||
// This 'false' that fy put in is inexplicable to me
|
||||
// the decision to not inline new instance expressions
|
||||
// should be revisited. - dps
|
||||
if (false && env.opt() && field.isInlineable(env, false) &&
|
||||
(!ctx.field.isInitializer()) && ctx.field.isMethod() &&
|
||||
(ctx.getInlineMemberContext(field) == null)) {
|
||||
Statement s = (Statement)field.getValue(env);
|
||||
if ((s == null)
|
||||
|| (s.costInline(MAXINLINECOST, env, ctx) < MAXINLINECOST)) {
|
||||
return inlineNewInstance(env, ctx, s);
|
||||
}
|
||||
}
|
||||
} catch (ClassNotFound e) {
|
||||
throw new CompilerError(e);
|
||||
}
|
||||
if (outerArg != null && outerArg.type.isType(TC_VOID)) {
|
||||
Expression e = outerArg;
|
||||
outerArg = null;
|
||||
return new CommaExpression(where, e, this);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
if (body != null) {
|
||||
return thresh; // don't copy classes...
|
||||
}
|
||||
if (ctx == null) {
|
||||
return 2 + super.costInline(thresh, env, ctx);
|
||||
}
|
||||
// sourceClass is the current class trying to inline this method
|
||||
ClassDefinition sourceClass = ctx.field.getClassDefinition();
|
||||
try {
|
||||
// We only allow the inlining if the current class can access
|
||||
// the field and the field's class;
|
||||
if ( sourceClass.permitInlinedAccess(env, field.getClassDeclaration())
|
||||
&& sourceClass.permitInlinedAccess(env, field)) {
|
||||
return 2 + super.costInline(thresh, env, ctx);
|
||||
}
|
||||
} catch (ClassNotFound e) {
|
||||
}
|
||||
return thresh;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeCommon(env, ctx, asm, false);
|
||||
}
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeCommon(env, ctx, asm, true);
|
||||
}
|
||||
private void codeCommon(Environment env, Context ctx, Assembler asm,
|
||||
boolean forValue) {
|
||||
asm.add(where, opc_new, field.getClassDeclaration());
|
||||
if (forValue) {
|
||||
asm.add(where, opc_dup);
|
||||
}
|
||||
|
||||
ClassDefinition refc = field.getClassDefinition();
|
||||
UplevelReference r = refc.getReferencesFrozen();
|
||||
|
||||
if (r != null) {
|
||||
r.codeArguments(env, ctx, asm, where, field);
|
||||
}
|
||||
|
||||
if (outerArg != null) {
|
||||
outerArg.codeValue(env, ctx, asm);
|
||||
switch (outerArg.op) {
|
||||
case THIS:
|
||||
case SUPER:
|
||||
case NEW:
|
||||
// guaranteed non-null
|
||||
break;
|
||||
case FIELD: {
|
||||
MemberDefinition f = ((FieldExpression)outerArg).field;
|
||||
if (f != null && f.isNeverNull()) {
|
||||
break;
|
||||
}
|
||||
// else fall through:
|
||||
}
|
||||
default:
|
||||
// Test for nullity by invoking some trivial operation
|
||||
// that can throw a NullPointerException.
|
||||
try {
|
||||
ClassDefinition c = env.getClassDefinition(idJavaLangObject);
|
||||
MemberDefinition getc = c.getFirstMatch(idGetClass);
|
||||
asm.add(where, opc_dup);
|
||||
asm.add(where, opc_invokevirtual, getc);
|
||||
asm.add(where, opc_pop);
|
||||
} catch (ClassNotFound e) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (implMethod != null) {
|
||||
// Constructor call will be via an access method.
|
||||
// Pass 'null' as the value of the dummy argument.
|
||||
asm.add(where, opc_aconst_null);
|
||||
}
|
||||
|
||||
for (int i = 0 ; i < args.length ; i++) {
|
||||
args[i].codeValue(env, ctx, asm);
|
||||
}
|
||||
asm.add(where, opc_invokespecial,
|
||||
((implMethod != null) ? implMethod : field));
|
||||
}
|
||||
}
|
||||
124
jdkSrc/jdk8/sun/tools/tree/Node.java
Normal file
124
jdkSrc/jdk8/sun/tools/tree/Node.java
Normal file
@@ -0,0 +1,124 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class Node implements Constants, Cloneable {
|
||||
int op;
|
||||
long where;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
Node(int op, long where) {
|
||||
this.op = op;
|
||||
this.where = where;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the operator
|
||||
*/
|
||||
public int getOp() {
|
||||
return op;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get where
|
||||
*/
|
||||
public long getWhere() {
|
||||
return where;
|
||||
}
|
||||
|
||||
/**
|
||||
* Implicit conversions
|
||||
*/
|
||||
public Expression convert(Environment env, Context ctx, Type t, Expression e) {
|
||||
if (e.type.isType(TC_ERROR) || t.isType(TC_ERROR)) {
|
||||
// An error was already reported
|
||||
return e;
|
||||
}
|
||||
|
||||
if (e.type.equals(t)) {
|
||||
// The types are already the same
|
||||
return e;
|
||||
}
|
||||
|
||||
try {
|
||||
if (e.fitsType(env, ctx, t)) {
|
||||
return new ConvertExpression(where, t, e);
|
||||
}
|
||||
|
||||
if (env.explicitCast(e.type, t)) {
|
||||
env.error(where, "explicit.cast.needed", opNames[op], e.type, t);
|
||||
return new ConvertExpression(where, t, e);
|
||||
}
|
||||
} catch (ClassNotFound ee) {
|
||||
env.error(where, "class.not.found", ee.name, opNames[op]);
|
||||
}
|
||||
|
||||
// The cast is not allowed
|
||||
env.error(where, "incompatible.type", opNames[op], e.type, t);
|
||||
return new ConvertExpression(where, Type.tError, e);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
throw new CompilerError("print");
|
||||
}
|
||||
|
||||
/**
|
||||
* Clone this object.
|
||||
*/
|
||||
public Object clone() {
|
||||
try {
|
||||
return super.clone();
|
||||
} catch (CloneNotSupportedException e) {
|
||||
// this shouldn't happen, since we are Cloneable
|
||||
throw (InternalError) new InternalError().initCause(e);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Useful for simple debugging
|
||||
*/
|
||||
public String toString() {
|
||||
ByteArrayOutputStream bos = new ByteArrayOutputStream();
|
||||
print(new PrintStream(bos));
|
||||
return bos.toString();
|
||||
}
|
||||
|
||||
}
|
||||
116
jdkSrc/jdk8/sun/tools/tree/NotEqualExpression.java
Normal file
116
jdkSrc/jdk8/sun/tools/tree/NotEqualExpression.java
Normal file
@@ -0,0 +1,116 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NotEqualExpression extends BinaryEqualityExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public NotEqualExpression(long where, Expression left, Expression right) {
|
||||
super(NE, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new BooleanExpression(where, a != b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new BooleanExpression(where, a != b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new BooleanExpression(where, a != b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new BooleanExpression(where, a != b);
|
||||
}
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a != b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (left.isConstant() && !right.isConstant()) {
|
||||
return new NotEqualExpression(where, right, left);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
left.codeValue(env, ctx, asm);
|
||||
switch (left.type.getTypeCode()) {
|
||||
case TC_BOOLEAN:
|
||||
case TC_INT:
|
||||
if (!right.equals(0)) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_icmpne : opc_if_icmpeq, lbl, whenTrue);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case TC_LONG:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_lcmp);
|
||||
break;
|
||||
case TC_FLOAT:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_fcmpl);
|
||||
break;
|
||||
case TC_DOUBLE:
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_dcmpl);
|
||||
break;
|
||||
case TC_ARRAY:
|
||||
case TC_CLASS:
|
||||
case TC_NULL:
|
||||
if (right.equals(0)) {
|
||||
asm.add(where, whenTrue ? opc_ifnonnull : opc_ifnull, lbl, whenTrue);
|
||||
} else {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, whenTrue ? opc_if_acmpne : opc_if_acmpeq, lbl, whenTrue);
|
||||
}
|
||||
return;
|
||||
default:
|
||||
throw new CompilerError("Unexpected Type");
|
||||
}
|
||||
asm.add(where, whenTrue ? opc_ifne : opc_ifeq, lbl, whenTrue);
|
||||
}
|
||||
}
|
||||
146
jdkSrc/jdk8/sun/tools/tree/NotExpression.java
Normal file
146
jdkSrc/jdk8/sun/tools/tree/NotExpression.java
Normal file
@@ -0,0 +1,146 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NotExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public NotExpression(long where, Expression right) {
|
||||
super(NOT, where, Type.tBoolean, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
right = convert(env, ctx, Type.tBoolean, right);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check a "not" expression.
|
||||
*
|
||||
* cvars is modified so that
|
||||
* cvar.vsTrue indicates variables with a known value if
|
||||
* the expression is true.
|
||||
* cvars.vsFalse indicates variables with a known value if
|
||||
* the expression is false
|
||||
*
|
||||
* For "not" expressions, we look at the inside expression, and then
|
||||
* swap true and false.
|
||||
*/
|
||||
|
||||
public void checkCondition(Environment env, Context ctx, Vset vset,
|
||||
Hashtable exp, ConditionVars cvars) {
|
||||
right.checkCondition(env, ctx, vset, exp, cvars);
|
||||
right = convert(env, ctx, Type.tBoolean, right);
|
||||
// swap true and false
|
||||
Vset temp = cvars.vsFalse;
|
||||
cvars.vsFalse = cvars.vsTrue;
|
||||
cvars.vsTrue = temp;
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a) {
|
||||
return new BooleanExpression(where, !a);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
// Check if the expression can be optimized
|
||||
switch (right.op) {
|
||||
case NOT:
|
||||
return ((NotExpression)right).right;
|
||||
|
||||
case EQ:
|
||||
case NE:
|
||||
case LT:
|
||||
case LE:
|
||||
case GT:
|
||||
case GE:
|
||||
break;
|
||||
|
||||
default:
|
||||
return this;
|
||||
}
|
||||
|
||||
// Can't negate real comparisons
|
||||
BinaryExpression bin = (BinaryExpression)right;
|
||||
if (bin.left.type.inMask(TM_REAL)) {
|
||||
return this;
|
||||
}
|
||||
|
||||
// Negate comparison
|
||||
switch (right.op) {
|
||||
case EQ:
|
||||
return new NotEqualExpression(where, bin.left, bin.right);
|
||||
case NE:
|
||||
return new EqualExpression(where, bin.left, bin.right);
|
||||
case LT:
|
||||
return new GreaterOrEqualExpression(where, bin.left, bin.right);
|
||||
case LE:
|
||||
return new GreaterExpression(where, bin.left, bin.right);
|
||||
case GT:
|
||||
return new LessOrEqualExpression(where, bin.left, bin.right);
|
||||
case GE:
|
||||
return new LessExpression(where, bin.left, bin.right);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
right.codeBranch(env, ctx, asm, lbl, !whenTrue);
|
||||
}
|
||||
|
||||
/**
|
||||
* Instead of relying on the default code generation which uses
|
||||
* conditional branching, generate a simpler stream using XOR.
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
right.codeValue(env, ctx, asm);
|
||||
asm.add(where, opc_ldc, new Integer(1));
|
||||
asm.add(where, opc_ixor);
|
||||
}
|
||||
|
||||
}
|
||||
70
jdkSrc/jdk8/sun/tools/tree/NullExpression.java
Normal file
70
jdkSrc/jdk8/sun/tools/tree/NullExpression.java
Normal file
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class NullExpression extends ConstantExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public NullExpression(long where) {
|
||||
super(NULL, where, Type.tNull);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the expression is equal to a value
|
||||
*/
|
||||
public boolean equals(int i) {
|
||||
return i == 0;
|
||||
}
|
||||
|
||||
public boolean isNull() {
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_aconst_null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("null");
|
||||
}
|
||||
}
|
||||
115
jdkSrc/jdk8/sun/tools/tree/OrExpression.java
Normal file
115
jdkSrc/jdk8/sun/tools/tree/OrExpression.java
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class OrExpression extends BinaryLogicalExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public OrExpression(long where, Expression left, Expression right) {
|
||||
super(OR, where, left, right);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check an "or" expression.
|
||||
*
|
||||
* cvars is modified so that
|
||||
* cvar.vsTrue indicates variables with a known value if
|
||||
* either the left and right hand side isn true
|
||||
* cvars.vsFalse indicates variables with a known value if
|
||||
* both the left or right hand side are false
|
||||
*/
|
||||
public void checkCondition(Environment env, Context ctx, Vset vset,
|
||||
Hashtable exp, ConditionVars cvars) {
|
||||
// Find out when the left side is true/false
|
||||
left.checkCondition(env, ctx, vset, exp, cvars);
|
||||
left = convert(env, ctx, Type.tBoolean, left);
|
||||
Vset vsTrue = cvars.vsTrue.copy();
|
||||
Vset vsFalse = cvars.vsFalse.copy();
|
||||
|
||||
// Only look at the right side if the left side is false
|
||||
right.checkCondition(env, ctx, vsFalse, exp, cvars);
|
||||
right = convert(env, ctx, Type.tBoolean, right);
|
||||
|
||||
// cvars.vsFalse actually reports that both returned false
|
||||
// cvars.vsTrue must be set back to either left side or the right
|
||||
// side returning false;
|
||||
cvars.vsTrue = cvars.vsTrue.join(vsTrue);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(boolean a, boolean b) {
|
||||
return new BooleanExpression(where, a || b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (right.equals(false)) {
|
||||
return left;
|
||||
}
|
||||
if (left.equals(true)) {
|
||||
return left;
|
||||
}
|
||||
if (left.equals(false)) {
|
||||
return right;
|
||||
}
|
||||
if (right.equals(true)) {
|
||||
// Preserve effects of left argument.
|
||||
return new CommaExpression(where, left, right).simplify();
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeBranch(Environment env, Context ctx, Assembler asm, Label lbl, boolean whenTrue) {
|
||||
if (whenTrue) {
|
||||
left.codeBranch(env, ctx, asm, lbl, true);
|
||||
right.codeBranch(env, ctx, asm, lbl, true);
|
||||
} else {
|
||||
Label lbl2 = new Label();
|
||||
left.codeBranch(env, ctx, asm, lbl2, true);
|
||||
right.codeBranch(env, ctx, asm, lbl, false);
|
||||
asm.add(lbl2);
|
||||
}
|
||||
}
|
||||
}
|
||||
67
jdkSrc/jdk8/sun/tools/tree/PositiveExpression.java
Normal file
67
jdkSrc/jdk8/sun/tools/tree/PositiveExpression.java
Normal file
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class PositiveExpression extends UnaryExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public PositiveExpression(long where, Expression right) {
|
||||
super(POS, where, right.type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the type of the expression
|
||||
*/
|
||||
void selectType(Environment env, Context ctx, int tm) {
|
||||
if ((tm & TM_DOUBLE) != 0) {
|
||||
type = Type.tDouble;
|
||||
} else if ((tm & TM_FLOAT) != 0) {
|
||||
type = Type.tFloat;
|
||||
} else if ((tm & TM_LONG) != 0) {
|
||||
type = Type.tLong;
|
||||
} else {
|
||||
type = Type.tInt;
|
||||
}
|
||||
right = convert(env, ctx, type, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
return right;
|
||||
}
|
||||
}
|
||||
54
jdkSrc/jdk8/sun/tools/tree/PostDecExpression.java
Normal file
54
jdkSrc/jdk8/sun/tools/tree/PostDecExpression.java
Normal file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class PostDecExpression extends IncDecExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public PostDecExpression(long where, Expression right) {
|
||||
super(POSTDEC, where, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, false, false, true);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, false, false, false);
|
||||
}
|
||||
}
|
||||
54
jdkSrc/jdk8/sun/tools/tree/PostIncExpression.java
Normal file
54
jdkSrc/jdk8/sun/tools/tree/PostIncExpression.java
Normal file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class PostIncExpression extends IncDecExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public PostIncExpression(long where, Expression right) {
|
||||
super(POSTINC, where, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, true, false, true);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, true, false, false);
|
||||
}
|
||||
}
|
||||
54
jdkSrc/jdk8/sun/tools/tree/PreDecExpression.java
Normal file
54
jdkSrc/jdk8/sun/tools/tree/PreDecExpression.java
Normal file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class PreDecExpression extends IncDecExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public PreDecExpression(long where, Expression right) {
|
||||
super(PREDEC, where, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, false, true, true);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, false, true, false);
|
||||
}
|
||||
}
|
||||
54
jdkSrc/jdk8/sun/tools/tree/PreIncExpression.java
Normal file
54
jdkSrc/jdk8/sun/tools/tree/PreIncExpression.java
Normal file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class PreIncExpression extends IncDecExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public PreIncExpression(long where, Expression right) {
|
||||
super(PREINC, where, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, true, true, true);
|
||||
}
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
codeIncDec(env, ctx, asm, true, true, false);
|
||||
}
|
||||
}
|
||||
67
jdkSrc/jdk8/sun/tools/tree/RemainderExpression.java
Normal file
67
jdkSrc/jdk8/sun/tools/tree/RemainderExpression.java
Normal file
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class RemainderExpression extends DivRemExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public RemainderExpression(long where, Expression left, Expression right) {
|
||||
super(REM, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a % b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a % b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new FloatExpression(where, a % b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new DoubleExpression(where, a % b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_irem + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
181
jdkSrc/jdk8/sun/tools/tree/ReturnStatement.java
Normal file
181
jdkSrc/jdk8/sun/tools/tree/ReturnStatement.java
Normal file
@@ -0,0 +1,181 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ReturnStatement extends Statement {
|
||||
Expression expr;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ReturnStatement(long where, Expression expr) {
|
||||
super(RETURN, where);
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check statement
|
||||
*/
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
checkLabel(env, ctx);
|
||||
vset = reach(env, vset);
|
||||
if (expr != null) {
|
||||
vset = expr.checkValue(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
// Make sure the return isn't inside a static initializer
|
||||
if (ctx.field.isInitializer()) {
|
||||
env.error(where, "return.inside.static.initializer");
|
||||
return DEAD_END;
|
||||
}
|
||||
// Check return type
|
||||
if (ctx.field.getType().getReturnType().isType(TC_VOID)) {
|
||||
if (expr != null) {
|
||||
if (ctx.field.isConstructor()) {
|
||||
env.error(where, "return.with.value.constr", ctx.field);
|
||||
} else {
|
||||
env.error(where, "return.with.value", ctx.field);
|
||||
}
|
||||
expr = null;
|
||||
}
|
||||
} else {
|
||||
if (expr == null) {
|
||||
env.error(where, "return.without.value", ctx.field);
|
||||
} else {
|
||||
expr = convert(env, ctx, ctx.field.getType().getReturnType(), expr);
|
||||
}
|
||||
}
|
||||
CheckContext mctx = ctx.getReturnContext();
|
||||
if (mctx != null) {
|
||||
mctx.vsBreak = mctx.vsBreak.join(vset);
|
||||
}
|
||||
CheckContext exitctx = ctx.getTryExitContext();
|
||||
if (exitctx != null) {
|
||||
exitctx.vsTryExit = exitctx.vsTryExit.join(vset);
|
||||
}
|
||||
if (expr != null) {
|
||||
// see if we are returning a value out of a try or synchronized
|
||||
// statement. If so, find the outermost one. . . .
|
||||
Node outerFinallyNode = null;
|
||||
for (Context c = ctx; c != null; c = c.prev) {
|
||||
if (c.node == null) {
|
||||
continue;
|
||||
}
|
||||
if (c.node.op == METHOD) {
|
||||
// Don't search outside current method. Fixes 4084230.
|
||||
break;
|
||||
}
|
||||
if (c.node.op == SYNCHRONIZED) {
|
||||
outerFinallyNode = c.node;
|
||||
break;
|
||||
} else if (c.node.op == FINALLY
|
||||
&& ((CheckContext)c).vsContinue != null) {
|
||||
outerFinallyNode = c.node;
|
||||
}
|
||||
}
|
||||
if (outerFinallyNode != null) {
|
||||
if (outerFinallyNode.op == FINALLY) {
|
||||
((FinallyStatement)outerFinallyNode).needReturnSlot = true;
|
||||
} else {
|
||||
((SynchronizedStatement)outerFinallyNode).needReturnSlot = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return DEAD_END;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
if (expr != null) {
|
||||
expr = expr.inlineValue(env, ctx);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* The cost of inlining this statement
|
||||
*/
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return 1 + ((expr != null) ? expr.costInline(thresh, env, ctx) : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
Expression e = (expr != null) ? expr.copyInline(ctx) : null;
|
||||
if ((!valNeeded) && (e != null)) {
|
||||
Statement body[] = {
|
||||
new ExpressionStatement(where, e),
|
||||
new InlineReturnStatement(where, null)
|
||||
};
|
||||
return new CompoundStatement(where, body);
|
||||
}
|
||||
return new InlineReturnStatement(where, e);
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
if (expr == null) {
|
||||
codeFinally(env, ctx, asm, null, null);
|
||||
asm.add(where, opc_return);
|
||||
} else {
|
||||
expr.codeValue(env, ctx, asm);
|
||||
codeFinally(env, ctx, asm, null, expr.type);
|
||||
asm.add(where, opc_ireturn + expr.type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out, int indent) {
|
||||
super.print(out, indent);
|
||||
out.print("return");
|
||||
if (expr != null) {
|
||||
out.print(" ");
|
||||
expr.print(out);
|
||||
}
|
||||
out.print(";");
|
||||
}
|
||||
}
|
||||
73
jdkSrc/jdk8/sun/tools/tree/ShiftLeftExpression.java
Normal file
73
jdkSrc/jdk8/sun/tools/tree/ShiftLeftExpression.java
Normal file
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ShiftLeftExpression extends BinaryShiftExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public ShiftLeftExpression(long where, Expression left, Expression right) {
|
||||
super(LSHIFT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a << b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a << b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (right.equals(0)) {
|
||||
return left;
|
||||
}
|
||||
if (left.equals(0)) {
|
||||
return new CommaExpression(where, right, left).simplify();
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ishl + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
73
jdkSrc/jdk8/sun/tools/tree/ShiftRightExpression.java
Normal file
73
jdkSrc/jdk8/sun/tools/tree/ShiftRightExpression.java
Normal file
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ShiftRightExpression extends BinaryShiftExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public ShiftRightExpression(long where, Expression left, Expression right) {
|
||||
super(RSHIFT, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a >> b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a >> b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
if (right.equals(0)) {
|
||||
return left;
|
||||
}
|
||||
if (left.equals(0)) {
|
||||
return new CommaExpression(where, right, left).simplify();
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ishr + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
51
jdkSrc/jdk8/sun/tools/tree/ShortExpression.java
Normal file
51
jdkSrc/jdk8/sun/tools/tree/ShortExpression.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class ShortExpression extends IntegerExpression {
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public ShortExpression(long where, short value) {
|
||||
super(SHORTVAL, where, Type.tShort, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print(value + "s");
|
||||
}
|
||||
}
|
||||
342
jdkSrc/jdk8/sun/tools/tree/Statement.java
Normal file
342
jdkSrc/jdk8/sun/tools/tree/Statement.java
Normal file
@@ -0,0 +1,342 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import sun.tools.asm.Label;
|
||||
import java.io.PrintStream;
|
||||
import java.util.Hashtable;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class Statement extends Node {
|
||||
public static final Vset DEAD_END = Vset.DEAD_END;
|
||||
Identifier labels[] = null;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
Statement(int op, long where) {
|
||||
super(op, where);
|
||||
}
|
||||
|
||||
/**
|
||||
* An empty statement. Its costInline is infinite.
|
||||
*/
|
||||
public static final Statement empty = new Statement(STAT, 0);
|
||||
|
||||
/**
|
||||
* The largest possible interesting inline cost value.
|
||||
*/
|
||||
public static final int MAXINLINECOST =
|
||||
Integer.getInteger("javac.maxinlinecost",
|
||||
30).intValue();
|
||||
|
||||
/**
|
||||
* Insert a bit of code at the front of a statement.
|
||||
* Side-effect s2, if it is a CompoundStatement.
|
||||
*/
|
||||
public static Statement insertStatement(Statement s1, Statement s2) {
|
||||
if (s2 == null) {
|
||||
s2 = s1;
|
||||
} else if (s2 instanceof CompoundStatement) {
|
||||
// Do not add another level of block nesting.
|
||||
((CompoundStatement)s2).insertStatement(s1);
|
||||
} else {
|
||||
Statement body[] = { s1, s2 };
|
||||
s2 = new CompoundStatement(s1.getWhere(), body);
|
||||
}
|
||||
return s2;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the label of a statement
|
||||
*/
|
||||
public void setLabel(Environment env, Expression e) {
|
||||
if (e.op == IDENT) {
|
||||
if (labels == null) {
|
||||
labels = new Identifier[1];
|
||||
} else {
|
||||
// this should almost never happen. Multiple labels on
|
||||
// the same statement. But handle it gracefully.
|
||||
Identifier newLabels[] = new Identifier[labels.length + 1];
|
||||
System.arraycopy(labels, 0, newLabels, 1, labels.length);
|
||||
labels = newLabels;
|
||||
}
|
||||
labels[0] = ((IdentifierExpression)e).id;
|
||||
} else {
|
||||
env.error(e.where, "invalid.label");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Check a statement
|
||||
*/
|
||||
public Vset checkMethod(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
// Set up ctx.getReturnContext() for the sake of ReturnStatement.check().
|
||||
CheckContext mctx = new CheckContext(ctx, new Statement(METHOD, 0));
|
||||
ctx = mctx;
|
||||
|
||||
vset = check(env, ctx, vset, exp);
|
||||
|
||||
// Check for return
|
||||
if (!ctx.field.getType().getReturnType().isType(TC_VOID)) {
|
||||
// In general, we suppress further error messages due to
|
||||
// unreachable statements after reporting the first error
|
||||
// along a flow path (using 'clearDeadEnd'). Here, we
|
||||
// report an error anyway, because the end of the method
|
||||
// should be unreachable despite the earlier error. The
|
||||
// difference in treatment is due to the fact that, in this
|
||||
// case, the error is reachability, not unreachability.
|
||||
// NOTE: In addition to this subtle difference in the quality
|
||||
// of the error diagnostics, this treatment is essential to
|
||||
// preserve the correctness of using 'clearDeadEnd' to implement
|
||||
// the special-case reachability rules for if-then and if-then-else.
|
||||
if (!vset.isDeadEnd()) {
|
||||
env.error(ctx.field.getWhere(), "return.required.at.end", ctx.field);
|
||||
}
|
||||
}
|
||||
|
||||
// Simulate a return at the end.
|
||||
vset = vset.join(mctx.vsBreak);
|
||||
|
||||
return vset;
|
||||
}
|
||||
Vset checkDeclaration(Environment env, Context ctx, Vset vset, int mod, Type t, Hashtable exp) {
|
||||
throw new CompilerError("checkDeclaration");
|
||||
}
|
||||
|
||||
/**
|
||||
* Make sure the labels on this statement do not duplicate the
|
||||
* labels on any enclosing statement. Provided as a convenience
|
||||
* for subclasses.
|
||||
*/
|
||||
protected void checkLabel(Environment env, Context ctx) {
|
||||
if (labels != null) {
|
||||
loop: for (int i = 0; i < labels.length; i++) {
|
||||
// Make sure there is not a double label on this statement.
|
||||
for (int j = i+1; j < labels.length; j++) {
|
||||
if (labels[i] == labels[j]) {
|
||||
env.error(where, "nested.duplicate.label", labels[i]);
|
||||
continue loop;
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure no enclosing statement has the same label.
|
||||
CheckContext destCtx =
|
||||
(CheckContext) ctx.getLabelContext(labels[i]);
|
||||
|
||||
if (destCtx != null) {
|
||||
// Check to make sure the label is in not uplevel.
|
||||
if (destCtx.frameNumber == ctx.frameNumber) {
|
||||
env.error(where, "nested.duplicate.label", labels[i]);
|
||||
}
|
||||
}
|
||||
} // end loop
|
||||
}
|
||||
}
|
||||
|
||||
Vset check(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
throw new CompilerError("check");
|
||||
}
|
||||
|
||||
/** This is called in contexts where declarations are valid. */
|
||||
Vset checkBlockStatement(Environment env, Context ctx, Vset vset, Hashtable exp) {
|
||||
return check(env, ctx, vset, exp);
|
||||
}
|
||||
|
||||
Vset reach(Environment env, Vset vset) {
|
||||
if (vset.isDeadEnd()) {
|
||||
env.error(where, "stat.not.reached");
|
||||
vset = vset.clearDeadEnd();
|
||||
}
|
||||
return vset;
|
||||
}
|
||||
|
||||
/**
|
||||
* Inline
|
||||
*/
|
||||
public Statement inline(Environment env, Context ctx) {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Eliminate this statement, which is only possible if it has no label.
|
||||
*/
|
||||
public Statement eliminate(Environment env, Statement s) {
|
||||
if ((s != null) && (labels != null)) {
|
||||
Statement args[] = {s};
|
||||
s = new CompoundStatement(where, args);
|
||||
s.labels = labels;
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void code(Environment env, Context ctx, Assembler asm) {
|
||||
throw new CompilerError("code");
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate the code to call all finally's for a break, continue, or
|
||||
* return statement. We must call "jsr" on all the cleanup code between
|
||||
* the current context "ctx", and the destination context "stopctx".
|
||||
* If 'save' isn't null, there is also a value on the top of the stack
|
||||
*/
|
||||
void codeFinally(Environment env, Context ctx, Assembler asm,
|
||||
Context stopctx, Type save) {
|
||||
Integer num = null;
|
||||
boolean haveCleanup = false; // there is a finally or synchronize;
|
||||
boolean haveNonLocalFinally = false; // some finally doesn't return;
|
||||
|
||||
for (Context c = ctx; (c != null) && (c != stopctx); c = c.prev) {
|
||||
if (c.node == null)
|
||||
continue;
|
||||
if (c.node.op == SYNCHRONIZED) {
|
||||
haveCleanup = true;
|
||||
} else if (c.node.op == FINALLY
|
||||
&& ((CodeContext)c).contLabel != null) {
|
||||
// c.contLabel == null indicates we're in the "finally" part
|
||||
haveCleanup = true;
|
||||
FinallyStatement st = ((FinallyStatement)(c.node));
|
||||
if (!st.finallyCanFinish) {
|
||||
haveNonLocalFinally = true;
|
||||
// after hitting a non-local finally, no need generating
|
||||
// further code, because it won't get executed.
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!haveCleanup) {
|
||||
// there is no cleanup that needs to be done. Just quit.
|
||||
return;
|
||||
}
|
||||
if (save != null) {
|
||||
// This statement has a return value on the stack.
|
||||
ClassDefinition def = ctx.field.getClassDefinition();
|
||||
if (!haveNonLocalFinally) {
|
||||
// Save the return value in the register which should have
|
||||
// been reserved.
|
||||
LocalMember lf = ctx.getLocalField(idFinallyReturnValue);
|
||||
num = new Integer(lf.number);
|
||||
asm.add(where, opc_istore + save.getTypeCodeOffset(), num);
|
||||
} else {
|
||||
// Pop the return value.
|
||||
switch(ctx.field.getType().getReturnType().getTypeCode()) {
|
||||
case TC_VOID:
|
||||
break;
|
||||
case TC_DOUBLE: case TC_LONG:
|
||||
asm.add(where, opc_pop2); break;
|
||||
default:
|
||||
asm.add(where, opc_pop); break;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Call each of the cleanup functions, as necessary.
|
||||
for (Context c = ctx ; (c != null) && (c != stopctx) ; c = c.prev) {
|
||||
if (c.node == null)
|
||||
continue;
|
||||
if (c.node.op == SYNCHRONIZED) {
|
||||
asm.add(where, opc_jsr, ((CodeContext)c).contLabel);
|
||||
} else if (c.node.op == FINALLY
|
||||
&& ((CodeContext)c).contLabel != null) {
|
||||
FinallyStatement st = ((FinallyStatement)(c.node));
|
||||
Label label = ((CodeContext)c).contLabel;
|
||||
if (st.finallyCanFinish) {
|
||||
asm.add(where, opc_jsr, label);
|
||||
} else {
|
||||
// the code never returns, so we're done.
|
||||
asm.add(where, opc_goto, label);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Move the return value from the register back to the stack.
|
||||
if (num != null) {
|
||||
asm.add(where, opc_iload + save.getTypeCodeOffset(), num);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Return true if the statement has the given label
|
||||
*/
|
||||
public boolean hasLabel (Identifier lbl) {
|
||||
Identifier labels[] = this.labels;
|
||||
if (labels != null) {
|
||||
for (int i = labels.length; --i >= 0; ) {
|
||||
if (labels[i].equals(lbl)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the first thing is a constructor invocation
|
||||
*/
|
||||
public Expression firstConstructor() {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a copy of the statement for method inlining
|
||||
*/
|
||||
public Statement copyInline(Context ctx, boolean valNeeded) {
|
||||
return (Statement)clone();
|
||||
}
|
||||
|
||||
public int costInline(int thresh, Environment env, Context ctx) {
|
||||
return thresh;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
void printIndent(PrintStream out, int indent) {
|
||||
for (int i = 0 ; i < indent ; i++) {
|
||||
out.print(" ");
|
||||
}
|
||||
}
|
||||
public void print(PrintStream out, int indent) {
|
||||
if (labels != null) {
|
||||
for (int i = labels.length; --i >= 0; )
|
||||
out.print(labels[i] + ": ");
|
||||
}
|
||||
}
|
||||
public void print(PrintStream out) {
|
||||
print(out, 0);
|
||||
}
|
||||
}
|
||||
93
jdkSrc/jdk8/sun/tools/tree/StringExpression.java
Normal file
93
jdkSrc/jdk8/sun/tools/tree/StringExpression.java
Normal file
@@ -0,0 +1,93 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
import java.io.PrintStream;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class StringExpression extends ConstantExpression {
|
||||
String value;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public StringExpression(long where, String value) {
|
||||
super(STRINGVAL, where, Type.tString);
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public boolean equals(String s) {
|
||||
return value.equals(s);
|
||||
}
|
||||
public boolean isNonNull() {
|
||||
return true; // string literal is never null
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
public void codeValue(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_ldc, this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value
|
||||
*/
|
||||
public Object getValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Hashcode
|
||||
*/
|
||||
public int hashCode() {
|
||||
return value.hashCode() ^ 3213;
|
||||
}
|
||||
|
||||
/**
|
||||
* Equality
|
||||
*/
|
||||
public boolean equals(Object obj) {
|
||||
if ((obj != null) && (obj instanceof StringExpression)) {
|
||||
return value.equals(((StringExpression)obj).value);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print
|
||||
*/
|
||||
public void print(PrintStream out) {
|
||||
out.print("\"" + value + "\"");
|
||||
}
|
||||
}
|
||||
83
jdkSrc/jdk8/sun/tools/tree/SubtractExpression.java
Normal file
83
jdkSrc/jdk8/sun/tools/tree/SubtractExpression.java
Normal file
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright (c) 1994, 2003, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.tools.tree;
|
||||
|
||||
import sun.tools.java.*;
|
||||
import sun.tools.asm.Assembler;
|
||||
|
||||
/**
|
||||
* WARNING: The contents of this source file are not part of any
|
||||
* supported API. Code that depends on them does so at its own risk:
|
||||
* they are subject to change or removal without notice.
|
||||
*/
|
||||
public
|
||||
class SubtractExpression extends BinaryArithmeticExpression {
|
||||
/**
|
||||
* constructor
|
||||
*/
|
||||
public SubtractExpression(long where, Expression left, Expression right) {
|
||||
super(SUB, where, left, right);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate
|
||||
*/
|
||||
Expression eval(int a, int b) {
|
||||
return new IntExpression(where, a - b);
|
||||
}
|
||||
Expression eval(long a, long b) {
|
||||
return new LongExpression(where, a - b);
|
||||
}
|
||||
Expression eval(float a, float b) {
|
||||
return new FloatExpression(where, a - b);
|
||||
}
|
||||
Expression eval(double a, double b) {
|
||||
return new DoubleExpression(where, a - b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Simplify
|
||||
*/
|
||||
Expression simplify() {
|
||||
// Can't simplify floating point subtract because of -0.0 strangeness
|
||||
if (type.inMask(TM_INTEGER)) {
|
||||
if (left.equals(0)) {
|
||||
return new NegativeExpression(where, right);
|
||||
}
|
||||
if (right.equals(0)) {
|
||||
return left;
|
||||
}
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Code
|
||||
*/
|
||||
void codeOperation(Environment env, Context ctx, Assembler asm) {
|
||||
asm.add(where, opc_isub + type.getTypeCodeOffset());
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user