< prev index next >
src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/codegen/CodeGenerator.java
Print this page
@@ -186,12 +186,10 @@
private static final Call CREATE_REWRITE_EXCEPTION_REST_OF = CompilerConstants.staticCallNoLookup(RewriteException.class,
"create", RewriteException.class, UnwarrantedOptimismException.class, Object[].class, String[].class, int[].class);
private static final Call ENSURE_INT = CompilerConstants.staticCallNoLookup(OptimisticReturnFilters.class,
"ensureInt", int.class, Object.class, int.class);
- private static final Call ENSURE_LONG = CompilerConstants.staticCallNoLookup(OptimisticReturnFilters.class,
- "ensureLong", long.class, Object.class, int.class);
private static final Call ENSURE_NUMBER = CompilerConstants.staticCallNoLookup(OptimisticReturnFilters.class,
"ensureNumber", double.class, Object.class, int.class);
private static final Call CREATE_FUNCTION_OBJECT = CompilerConstants.staticCallNoLookup(ScriptFunction.class,
"create", ScriptFunction.class, Object[].class, int.class, ScriptObject.class);
@@ -1724,11 +1722,11 @@
return false;
}
enterStatement(expressionStatement);
loadAndDiscard(expressionStatement.getExpression());
- assert method.getStackSize() == 0;
+ assert method.getStackSize() == 0 : "stack not empty in " + expressionStatement;
return false;
}
@Override
@@ -2239,11 +2237,11 @@
*
* @param arrayLiteralNode the array of contents
* @param arrayType the type of the array, e.g. ARRAY_NUMBER or ARRAY_OBJECT
*/
private void loadArray(final ArrayLiteralNode arrayLiteralNode, final ArrayType arrayType) {
- assert arrayType == Type.INT_ARRAY || arrayType == Type.LONG_ARRAY || arrayType == Type.NUMBER_ARRAY || arrayType == Type.OBJECT_ARRAY;
+ assert arrayType == Type.INT_ARRAY || arrayType == Type.NUMBER_ARRAY || arrayType == Type.OBJECT_ARRAY;
final Expression[] nodes = arrayLiteralNode.getValue();
final Object presets = arrayLiteralNode.getPresets();
final int[] postsets = arrayLiteralNode.getPostsets();
final List<Splittable.SplitRange> ranges = arrayLiteralNode.getSplitRanges();
@@ -2387,24 +2385,13 @@
if(!resultBounds.canBeNarrowerThan(Type.OBJECT)) {
method.load((Integer)value);
method.convert(Type.OBJECT);
} else if(!resultBounds.canBeNarrowerThan(Type.NUMBER)) {
method.load(((Integer)value).doubleValue());
- } else if(!resultBounds.canBeNarrowerThan(Type.LONG)) {
- method.load(((Integer)value).longValue());
} else {
method.load((Integer)value);
}
- } else if (value instanceof Long) {
- if(!resultBounds.canBeNarrowerThan(Type.OBJECT)) {
- method.load((Long)value);
- method.convert(Type.OBJECT);
- } else if(!resultBounds.canBeNarrowerThan(Type.NUMBER)) {
- method.load(((Long)value).doubleValue());
- } else {
- method.load((Long)value);
- }
} else if (value instanceof Double) {
if(!resultBounds.canBeNarrowerThan(Type.OBJECT)) {
method.load((Double)value);
method.convert(Type.OBJECT);
} else {
@@ -3648,12 +3635,10 @@
}
private void loadMinusOne() {
if (type.isInteger()) {
method.load(isIncrement ? 1 : -1);
- } else if (type.isLong()) {
- method.load(isIncrement ? 1L : -1L);
} else {
method.load(isIncrement ? 1.0 : -1.0);
}
}
@@ -4031,27 +4016,70 @@
}
}.store();
}
private void loadASSIGN_SHR(final BinaryNode binaryNode) {
- new BinarySelfAssignment(binaryNode) {
+ new SelfModifyingStore<BinaryNode>(binaryNode, binaryNode.lhs()) {
@Override
- protected void op() {
- doSHR();
+ protected void evaluate() {
+ new OptimisticOperation(assignNode, new TypeBounds(Type.INT, Type.NUMBER)) {
+ @Override
+ void loadStack() {
+ assert assignNode.getWidestOperandType() == Type.INT;
+ if (isRhsZero(binaryNode)) {
+ loadExpressionAsType(binaryNode.lhs(), Type.INT);
+ } else {
+ loadBinaryOperands(binaryNode.lhs(), binaryNode.rhs(), TypeBounds.INT, true, false);
+ method.shr();
+ }
}
+ @Override
+ void consumeStack() {
+ if (isOptimistic(binaryNode)) {
+ toUint32Optimistic(binaryNode.getProgramPoint());
+ } else {
+ toUint32Double();
+ }
+ }
+ }.emit(getOptimisticIgnoreCountForSelfModifyingExpression(binaryNode.lhs()));
+ method.convert(assignNode.getType());
+ }
}.store();
}
- private void doSHR() {
- // TODO: make SHR optimistic
+ private void doSHR(final BinaryNode binaryNode) {
+ new OptimisticOperation(binaryNode, new TypeBounds(Type.INT, Type.NUMBER)) {
+ @Override
+ void loadStack() {
+ if (isRhsZero(binaryNode)) {
+ loadExpressionAsType(binaryNode.lhs(), Type.INT);
+ } else {
+ loadBinaryOperands(binaryNode);
method.shr();
- toUint();
+ }
+ }
+
+ @Override
+ void consumeStack() {
+ if (isOptimistic(binaryNode)) {
+ toUint32Optimistic(binaryNode.getProgramPoint());
+ } else {
+ toUint32Double();
+ }
+ }
+ }.emit();
+
+ }
+
+ private void toUint32Optimistic(final int programPoint) {
+ method.load(programPoint);
+ JSType.TO_UINT32_OPTIMISTIC.invoke(method);
}
- private void toUint() {
- JSType.TO_UINT32_I.invoke(method);
+ private void toUint32Double() {
+ JSType.TO_UINT32_DOUBLE.invoke(method);
}
private void loadASSIGN_SUB(final BinaryNode binaryNode) {
new BinaryOptimisticSelfAssignment(binaryNode) {
@Override
@@ -4085,11 +4113,11 @@
operandBounds = new TypeBounds(node.getType(), Type.NUMBER);
} else {
// Non-optimistic, non-FP subtraction or multiplication. Allow them to overflow.
operandBounds = new TypeBounds(Type.narrowest(node.getWidestOperandType(),
numericBounds.widest), Type.NUMBER);
- forceConversionSeparation = node.getWidestOperationType().narrowerThan(numericBounds.widest);
+ forceConversionSeparation = true;
}
}
loadBinaryOperands(node.lhs(), node.rhs(), operandBounds, false, forceConversionSeparation);
}
@@ -4187,18 +4215,11 @@
loadBinaryOperands(binaryNode);
method.shl();
}
private void loadSHR(final BinaryNode binaryNode) {
- // Optimize x >>> 0 to (uint)x
- if (isRhsZero(binaryNode)) {
- loadExpressionAsType(binaryNode.lhs(), Type.INT);
- toUint();
- } else {
- loadBinaryOperands(binaryNode);
- doSHR();
- }
+ doSHR(binaryNode);
}
private void loadSUB(final BinaryNode binaryNode, final TypeBounds resultBounds) {
new BinaryArith() {
@Override
@@ -4465,10 +4486,11 @@
} else {
method.dynamicSet(node.getName(), flags, false);
}
} else {
final Type storeType = assignNode.getType();
+ assert storeType != Type.LONG;
if (symbol.hasSlotFor(storeType)) {
// Only emit a convert for a store known to be live; converts for dead stores can
// give us an unnecessary ClassCastException.
method.convert(storeType);
}
@@ -4849,12 +4871,10 @@
final Type optimisticType = getOptimisticCoercedType();
if(!optimisticType.isObject()) {
method.load(optimistic.getProgramPoint());
if(optimisticType.isInteger()) {
method.invoke(ENSURE_INT);
- } else if(optimisticType.isLong()) {
- method.invoke(ENSURE_LONG);
} else if(optimisticType.isNumber()) {
method.invoke(ENSURE_NUMBER);
} else {
throw new AssertionError(optimisticType);
}
< prev index next >