X-Git-Url: http://secure.phpeclipse.com diff --git a/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/ast/CastExpression.java b/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/ast/CastExpression.java index 950716d..ad9c88a 100644 --- a/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/ast/CastExpression.java +++ b/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/ast/CastExpression.java @@ -25,44 +25,43 @@ import net.sourceforge.phpdt.internal.compiler.lookup.TypeBinding; public class CastExpression extends Expression { public Expression expression; + public Expression type; + public boolean needRuntimeCheckcast; - //expression.implicitConversion holds the cast for baseType casting + // expression.implicitConversion holds the cast for baseType casting public CastExpression(Expression e, Expression t) { expression = e; type = t; - //due to the fact an expression may start with ( and that a cast also start with ( - //the field is an expression....it can be a TypeReference OR a NameReference Or - //an expression <--this last one is invalid....... + // due to the fact an expression may start with ( and that a cast also + // start with ( + // the field is an expression....it can be a TypeReference OR a + // NameReference Or + // an expression <--this last one is invalid....... // :-( ............. - //if (type instanceof TypeReference ) - // flag = IsTypeReference ; - //else - // if (type instanceof NameReference) - // flag = IsNameReference ; - // else - // flag = IsExpression ; + // if (type instanceof TypeReference ) + // flag = IsTypeReference ; + // else + // if (type instanceof NameReference) + // flag = IsNameReference ; + // else + // flag = IsExpression ; } - public FlowInfo analyseCode( - BlockScope currentScope, - FlowContext flowContext, - FlowInfo flowInfo) { + public FlowInfo analyseCode(BlockScope currentScope, + FlowContext flowContext, FlowInfo flowInfo) { - return expression - .analyseCode(currentScope, flowContext, flowInfo) - .unconditionalInits(); + return expression.analyseCode(currentScope, flowContext, flowInfo) + .unconditionalInits(); } - public final void areTypesCastCompatible( - BlockScope scope, - TypeBinding castType, - TypeBinding expressionType) { + public final void areTypesCastCompatible(BlockScope scope, + TypeBinding castType, TypeBinding expressionType) { // see specifications 5.5 // handle errors and process constant when needed @@ -72,141 +71,174 @@ public class CastExpression extends Expression { // we then do not report an obvious-cascade-error. needRuntimeCheckcast = false; - if (castType == null || expressionType == null) return; + if (castType == null || expressionType == null) + return; // identity conversion cannot be performed upfront, due to side-effects // like constant propagation - + if (castType.isBaseType()) { if (expressionType.isBaseType()) { if (expressionType == castType) { expression.implicitWidening(castType, expressionType); - constant = expression.constant; //use the same constant + constant = expression.constant; // use the same constant return; } if (expressionType.isCompatibleWith(castType) - || BaseTypeBinding.isNarrowing(castType.id, expressionType.id)) { - expression.implicitConversion = (castType.id << 4) + expressionType.id; + || BaseTypeBinding.isNarrowing(castType.id, + expressionType.id)) { + expression.implicitConversion = (castType.id << 4) + + expressionType.id; if (expression.constant != Constant.NotAConstant) - constant = expression.constant.castTo(expression.implicitConversion); + constant = expression.constant + .castTo(expression.implicitConversion); return; } } - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } - //-----------cast to something which is NOT a base type-------------------------- + // -----------cast to something which is NOT a base + // type-------------------------- if (expressionType == NullBinding) { - // if (castType.isArrayType()){ // 26903 - need checkcast when casting null to array type - // needRuntimeCheckcast = true; - // } - return; //null is compatible with every thing + // if (castType.isArrayType()){ // 26903 - need checkcast when + // casting null to array type + // needRuntimeCheckcast = true; + // } + return; // null is compatible with every thing } if (expressionType.isBaseType()) { - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } if (expressionType.isArrayType()) { - if (castType == expressionType) return; // identity conversion + if (castType == expressionType) + return; // identity conversion if (castType.isArrayType()) { - //------- (castType.isArray) expressionType.isArray ----------- - TypeBinding exprElementType = ((ArrayBinding) expressionType).elementsType(scope); + // ------- (castType.isArray) expressionType.isArray ----------- + TypeBinding exprElementType = ((ArrayBinding) expressionType) + .elementsType(scope); if (exprElementType.isBaseType()) { - // <---stop the recursion------- + // <---stop the recursion------- if (((ArrayBinding) castType).elementsType(scope) == exprElementType) needRuntimeCheckcast = true; else - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } // recursively on the elements... - areTypesCastCompatible( - scope, - ((ArrayBinding) castType).elementsType(scope), - exprElementType); + areTypesCastCompatible(scope, ((ArrayBinding) castType) + .elementsType(scope), exprElementType); return; - } else if ( - castType.isClass()) { - //------(castType.isClass) expressionType.isArray --------------- + } else if (castType.isClass()) { + // ------(castType.isClass) expressionType.isArray + // --------------- if (scope.isJavaLangObject(castType)) return; - } else { //------- (castType.isInterface) expressionType.isArray ----------- - if (scope.isJavaLangCloneable(castType) || scope.isJavaIoSerializable(castType)) { + } else { // ------- (castType.isInterface) expressionType.isArray + // ----------- + if (scope.isJavaLangCloneable(castType) + || scope.isJavaIoSerializable(castType)) { needRuntimeCheckcast = true; return; } } - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } if (expressionType.isClass()) { if (castType.isArrayType()) { // ---- (castType.isArray) expressionType.isClass ------- - if (scope.isJavaLangObject(expressionType)) { // potential runtime error + if (scope.isJavaLangObject(expressionType)) { // potential + // runtime error needRuntimeCheckcast = true; return; } - } else if (castType.isClass()) { // ----- (castType.isClass) expressionType.isClass ------ - if (expressionType.isCompatibleWith(castType)){ // no runtime error - if (castType.id == T_String) constant = expression.constant; // (String) cst is still a constant + } else if (castType.isClass()) { // ----- (castType.isClass) + // expressionType.isClass ------ + if (expressionType.isCompatibleWith(castType)) { // no + // runtime + // error + if (castType.id == T_String) + constant = expression.constant; // (String) cst is still + // a constant return; } if (castType.isCompatibleWith(expressionType)) { - // potential runtime error + // potential runtime error needRuntimeCheckcast = true; return; } - } else { // ----- (castType.isInterface) expressionType.isClass ------- + } else { // ----- (castType.isInterface) expressionType.isClass + // ------- if (((ReferenceBinding) expressionType).isFinal()) { - // no subclass for expressionType, thus compile-time check is valid - if (expressionType.isCompatibleWith(castType)) + // no subclass for expressionType, thus compile-time check + // is valid + if (expressionType.isCompatibleWith(castType)) return; - } else { // a subclass may implement the interface ==> no check at compile time + } else { // a subclass may implement the interface ==> no + // check at compile time needRuntimeCheckcast = true; return; } } - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } - // if (expressionType.isInterface()) { cannot be anything else + // if (expressionType.isInterface()) { cannot be anything else if (castType.isArrayType()) { // ----- (castType.isArray) expressionType.isInterface ------ if (scope.isJavaLangCloneable(expressionType) - || scope.isJavaIoSerializable(expressionType)) // potential runtime error + || scope.isJavaIoSerializable(expressionType)) // potential + // runtime + // error needRuntimeCheckcast = true; else - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; - } else if (castType.isClass()) { // ----- (castType.isClass) expressionType.isInterface -------- + } else if (castType.isClass()) { // ----- (castType.isClass) + // expressionType.isInterface + // -------- if (scope.isJavaLangObject(castType)) // no runtime error return; if (((ReferenceBinding) castType).isFinal()) { // no subclass for castType, thus compile-time check is valid if (!castType.isCompatibleWith(expressionType)) { // potential runtime error - scope.problemReporter().typeCastError(this, castType, expressionType); + scope.problemReporter().typeCastError(this, castType, + expressionType); return; } } - } else { // ----- (castType.isInterface) expressionType.isInterface ------- - if (castType == expressionType) return; // identity conversion + } else { // ----- (castType.isInterface) expressionType.isInterface + // ------- + if (castType == expressionType) + return; // identity conversion if (Scope.compareTypes(castType, expressionType) == NotRelated) { - MethodBinding[] castTypeMethods = ((ReferenceBinding) castType).methods(); - MethodBinding[] expressionTypeMethods = - ((ReferenceBinding) expressionType).methods(); + MethodBinding[] castTypeMethods = ((ReferenceBinding) castType) + .methods(); + MethodBinding[] expressionTypeMethods = ((ReferenceBinding) expressionType) + .methods(); int exprMethodsLength = expressionTypeMethods.length; for (int i = 0, castMethodsLength = castTypeMethods.length; i < castMethodsLength; i++) for (int j = 0; j < exprMethodsLength; j++) { if ((castTypeMethods[i].returnType != expressionTypeMethods[j].returnType) && (castTypeMethods[i].selector == expressionTypeMethods[j].selector) - && castTypeMethods[i].areParametersEqual(expressionTypeMethods[j])) { - scope.problemReporter().typeCastError(this, castType, expressionType); + && castTypeMethods[i] + .areParametersEqual(expressionTypeMethods[j])) { + scope.problemReporter().typeCastError(this, + castType, expressionType); } } } @@ -217,52 +249,56 @@ public class CastExpression extends Expression { /** * Cast expression code generation - * - * @param currentScope net.sourceforge.phpdt.internal.compiler.lookup.BlockScope - * @param codeStream net.sourceforge.phpdt.internal.compiler.codegen.CodeStream - * @param valueRequired boolean + * + * @param currentScope + * net.sourceforge.phpdt.internal.compiler.lookup.BlockScope + * @param codeStream + * net.sourceforge.phpdt.internal.compiler.codegen.CodeStream + * @param valueRequired + * boolean */ -// public void generateCode( -// BlockScope currentScope, -// CodeStream codeStream, -// boolean valueRequired) { -// -// int pc = codeStream.position; -// if (constant != NotAConstant) { -// if (valueRequired -// || needRuntimeCheckcast) { // Added for: 1F1W9IG: IVJCOM:WINNT - Compiler omits casting check -// codeStream.generateConstant(constant, implicitConversion); -// if (needRuntimeCheckcast) { -// codeStream.checkcast(this.resolvedType); -// if (!valueRequired) -// codeStream.pop(); -// } -// } -// codeStream.recordPositionsFrom(pc, this.sourceStart); -// return; -// } -// expression.generateCode( -// currentScope, -// codeStream, -// valueRequired || needRuntimeCheckcast); -// if (needRuntimeCheckcast) { -// codeStream.checkcast(this.resolvedType); -// if (!valueRequired) -// codeStream.pop(); -// } else { -// if (valueRequired) -// codeStream.generateImplicitConversion(implicitConversion); -// } -// codeStream.recordPositionsFrom(pc, this.sourceStart); -// } - - public Expression innermostCastedExpression(){ + // public void generateCode( + // BlockScope currentScope, + // CodeStream codeStream, + // boolean valueRequired) { + // + // int pc = codeStream.position; + // if (constant != NotAConstant) { + // if (valueRequired + // || needRuntimeCheckcast) { // Added for: 1F1W9IG: IVJCOM:WINNT - Compiler + // omits casting check + // codeStream.generateConstant(constant, implicitConversion); + // if (needRuntimeCheckcast) { + // codeStream.checkcast(this.resolvedType); + // if (!valueRequired) + // codeStream.pop(); + // } + // } + // codeStream.recordPositionsFrom(pc, this.sourceStart); + // return; + // } + // expression.generateCode( + // currentScope, + // codeStream, + // valueRequired || needRuntimeCheckcast); + // if (needRuntimeCheckcast) { + // codeStream.checkcast(this.resolvedType); + // if (!valueRequired) + // codeStream.pop(); + // } else { + // if (valueRequired) + // codeStream.generateImplicitConversion(implicitConversion); + // } + // codeStream.recordPositionsFrom(pc, this.sourceStart); + // } + public Expression innermostCastedExpression() { Expression current = this.expression; while (current instanceof CastExpression) { current = ((CastExpression) current).expression; } return current; } + public StringBuffer printExpression(int indent, StringBuffer output) { output.append('('); @@ -273,8 +309,10 @@ public class CastExpression extends Expression { public TypeBinding resolveType(BlockScope scope) { // compute a new constant if the cast is effective - // due to the fact an expression may start with ( and that a cast can also start with ( - // the field is an expression....it can be a TypeReference OR a NameReference Or + // due to the fact an expression may start with ( and that a cast can + // also start with ( + // the field is an expression....it can be a TypeReference OR a + // NameReference Or // any kind of Expression <-- this last one is invalid....... constant = Constant.NotAConstant; @@ -283,12 +321,14 @@ public class CastExpression extends Expression { this.resolvedType = type.resolveType(scope); TypeBinding castedExpressionType = expression.resolveType(scope); if (this.resolvedType != null && castedExpressionType != null) { - areTypesCastCompatible(scope, this.resolvedType, castedExpressionType); + areTypesCastCompatible(scope, this.resolvedType, + castedExpressionType); } return this.resolvedType; } else { // expression as a cast !!!!!!!! TypeBinding castedExpressionType = expression.resolveType(scope); - if (castedExpressionType == null) return null; + if (castedExpressionType == null) + return null; scope.problemReporter().invalidTypeReference(type); return null; } @@ -297,12 +337,10 @@ public class CastExpression extends Expression { public String toStringExpression() { return "(" + type.toString(0) + ") " + //$NON-NLS-2$ //$NON-NLS-1$ - expression.toStringExpression(); + expression.toStringExpression(); } - public void traverse( - ASTVisitor visitor, - BlockScope blockScope) { + public void traverse(ASTVisitor visitor, BlockScope blockScope) { if (visitor.visit(this, blockScope)) { type.traverse(visitor, blockScope);