// // CSC 2 has this behavior, it allows structs to be compared // with the null literal *outside* of a generics context and // inlines that as true or false. // private Expression CreateNullConstant(ParseContext ec, Expression expr) { // FIXME: Handle side effect constants var c = new ConstantExpression <bool>(Operator == ExpressionType.NotEqual, Span); if (Operator.IsEquality()) { ec.ReportError( 472, string.Format( "The result of comparing value type '{0}' with null is '{1}'.", TypeManager.GetCSharpName(expr.Type), c), Severity.Warning, Span); } else { ec.ReportError( 464, string.Format( "The result of comparing type '{0}' with null is always '{1}'.", TypeManager.GetCSharpName(expr.Type), c), Severity.Warning, Span); } return(ReducedExpression.Create(c, this)); }
public static Expression CreateFromExpression(ParseContext ec, Expression e) { ec.ReportError( 458, string.Format( "The result of the expression is always 'null' of type '{0}'.", TypeManager.GetCSharpName(e.Type)), Severity.Warning, e.Span); return(ReducedExpression.Create( Create(e.Type, e.Span), e)); }
public override Expression DoResolve(ParseContext ec) { var typeExpression = _requestedType.ResolveAsTypeTerminal(ec, false); if (typeExpression == null) { return(null); } Type = _resolvedType = typeExpression.Type; if (Arguments == null) { var c = Constantify(_resolvedType); if (c != null) { return(ReducedExpression.Create(c, this)); } } if (TypeManager.IsGenericParameter(_resolvedType)) { var gc = TypeManager.GetTypeParameterConstraints(_resolvedType); if ((gc == null) || (!gc.HasConstructorConstraint && !gc.IsValueType)) { ec.ReportError( 304, string.Format( "Cannot create an instance of the variable type '{0}' because it doesn't have the new() constraint.", TypeManager.GetCSharpName(_resolvedType)), Span); return(null); } if ((_arguments != null) && (_arguments.Count != 0)) { ec.ReportError( 417, string.Format( "'{0}': cannot provide arguments when creating an instance of a variable type.", TypeManager.GetCSharpName(_resolvedType)), Span); return(null); } ExpressionClass = ExpressionClass.Value; return(this); } if (_resolvedType.IsAbstract && _resolvedType.IsSealed) { ec.ReportError( 712, string.Format( "Cannot create an instance of the static class '{0}'.", TypeManager.GetCSharpName(_resolvedType)), Span); return(null); } if (_resolvedType.IsInterface || _resolvedType.IsAbstract) { ec.ReportError( 144, string.Format( "Cannot create an instance of the abstract class or interface '{0}'.", TypeManager.GetCSharpName(_resolvedType)), Span); return(null); } var isStruct = TypeManager.IsStruct(_resolvedType); ExpressionClass = ExpressionClass.Value; // // SRE returns a match for .ctor () on structs (the object constructor), // so we have to manually ignore it. // if (isStruct && (_arguments != null) && !_arguments.Any()) { return(this); } // For member-lookup, treat 'new Foo (bar)' as call to 'foo.ctor (bar)', where 'foo' is of type 'Foo'. var memberLookup = MemberLookupFinal( ec, _resolvedType, _resolvedType, ConstructorInfo.ConstructorName, MemberTypes.Constructor, AllBindingFlags | BindingFlags.DeclaredOnly, Span); if (_arguments != null) { _arguments.Resolve(ec); } if (memberLookup == null) { return(null); } _constructor = memberLookup as MethodGroupExpression; if (_constructor == null) { memberLookup.OnErrorUnexpectedKind(ec, ResolveFlags.MethodGroup, Span); return(null); } _constructor = _constructor.OverloadResolve(ec, ref _arguments, false, Span); return((_constructor == null) ? null : this); }
public override Expression DoResolve(ParseContext parseContext) { Test = Test.Resolve(parseContext); IfTrue = IfTrue.Resolve(parseContext); IfFalse = IfFalse.Resolve(parseContext); if (Test == null || IfTrue == null || IfFalse == null) { return(null); } ExpressionClass = ExpressionClass.Value; var trueType = IfTrue.Type; var falseType = IfFalse.Type; Type = trueType; // First, if an implicit conversion exists from IfTrue to IfFalse, then the result type is of type IfFalse.Type if (!TypeManager.IsEqual(trueType, falseType)) { var conv = ConvertExpression.MakeImplicitConversion(parseContext, IfTrue, falseType, Span); if (conv != null) { // Check if both can convert implicitly to each other's type Type = falseType; if (ConvertExpression.MakeImplicitConversion(parseContext, IfFalse, trueType, Span) != null) { parseContext.ReportError( CompilerErrors.ConditionalOperandsBothHaveImplicitConversions, IfTrue.Span, trueType, falseType); return(null); } IfTrue = conv; } else if ((conv = ConvertExpression.MakeImplicitConversion(parseContext, IfFalse, trueType, Span)) != null) { IfFalse = conv; } else { parseContext.ReportError( CompilerErrors.ConditionalOperandsHaveNoImplicitConversion, IfTrue.Span, trueType, falseType); return(null); } } // Dead code optimalization var c = Test as ConstantExpression; if (c != null) { var isFalse = c.IsDefaultValue; parseContext.ReportError( CompilerErrors.UnreachableExpression, isFalse ? IfTrue.Span : IfFalse.Span); return(ReducedExpression.Create(isFalse ? IfFalse : IfTrue, this).Resolve(parseContext)); } return(this); }