X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=mcs%2Fmcs%2Fcfold.cs;h=96062f2748e744c51360f607ad2de8f492dc889d;hb=009d937c1df7d8949b7671c89426e33a11c6d284;hp=36211cd12b8c30d7775d64f7072fb046d93f1e4b;hpb=bdf6dee0fac9de8c9032deed0111d6bd238f298b;p=mono.git diff --git a/mcs/mcs/cfold.cs b/mcs/mcs/cfold.cs index 36211cd12b8..96062f2748e 100644 --- a/mcs/mcs/cfold.cs +++ b/mcs/mcs/cfold.cs @@ -6,31 +6,20 @@ // Marek Safar (marek.safar@seznam.cz) // // Copyright 2002, 2003 Ximian, Inc. -// Copyright 2003-2008, Novell, Inc. +// Copyright 2003-2011, Novell, Inc. // using System; namespace Mono.CSharp { - public class ConstantFold { - - static TypeSpec[] binary_promotions; - - public static TypeSpec[] BinaryPromotionsTypes { - get { - if (binary_promotions == null) { - binary_promotions = new TypeSpec[] { - TypeManager.decimal_type, TypeManager.double_type, TypeManager.float_type, - TypeManager.uint64_type, TypeManager.int64_type, TypeManager.uint32_type }; - } - - return binary_promotions; - } - } - - public static void Reset () + public static class ConstantFold + { + public static TypeSpec[] CreateBinaryPromotionsTypes (BuiltinTypes types) { - binary_promotions = null; + return new TypeSpec[] { + types.Decimal, types.Double, types.Float, + types.ULong, types.Long, types.UInt + }; } // @@ -48,7 +37,7 @@ namespace Mono.CSharp { TypeSpec ltype = left.Type; TypeSpec rtype = right.Type; - foreach (TypeSpec t in BinaryPromotionsTypes) { + foreach (TypeSpec t in rc.BuiltinTypes.BinaryPromotionsTypes) { if (t == ltype) return t == rtype || ConvertPromotion (rc, ref right, ref left, t); @@ -56,23 +45,23 @@ namespace Mono.CSharp { return t == ltype || ConvertPromotion (rc, ref left, ref right, t); } - left = left.ConvertImplicitly (rc, TypeManager.int32_type); - right = right.ConvertImplicitly (rc, TypeManager.int32_type); + left = left.ConvertImplicitly (rc.BuiltinTypes.Int); + right = right.ConvertImplicitly (rc.BuiltinTypes.Int); return left != null && right != null; } static bool ConvertPromotion (ResolveContext rc, ref Constant prim, ref Constant second, TypeSpec type) { - Constant c = prim.ConvertImplicitly (rc, type); + Constant c = prim.ConvertImplicitly (type); if (c != null) { prim = c; return true; } - if (type == TypeManager.uint32_type) { - type = TypeManager.int64_type; - prim = prim.ConvertImplicitly (rc, type); - second = second.ConvertImplicitly (rc, type); + if (type.BuiltinType == BuiltinTypeSpec.Type.UInt) { + type = rc.BuiltinTypes.Long; + prim = prim.ConvertImplicitly (type); + second = second.ConvertImplicitly (type); return prim != null && second != null; } @@ -118,22 +107,22 @@ namespace Mono.CSharp { TypeSpec rt = right.Type; bool bool_res; - if (lt == TypeManager.bool_type && lt == rt) { + if (lt.BuiltinType == BuiltinTypeSpec.Type.Bool && lt == rt) { bool lv = (bool) left.GetValue (); bool rv = (bool) right.GetValue (); switch (oper) { case Binary.Operator.BitwiseAnd: case Binary.Operator.LogicalAnd: - return new BoolConstant (lv && rv, left.Location); + return new BoolConstant (ec.BuiltinTypes, lv && rv, left.Location); case Binary.Operator.BitwiseOr: case Binary.Operator.LogicalOr: - return new BoolConstant (lv || rv, left.Location); + return new BoolConstant (ec.BuiltinTypes, lv || rv, left.Location); case Binary.Operator.ExclusiveOr: - return new BoolConstant (lv ^ rv, left.Location); + return new BoolConstant (ec.BuiltinTypes, lv ^ rv, left.Location); case Binary.Operator.Equality: - return new BoolConstant (lv == rv, left.Location); + return new BoolConstant (ec.BuiltinTypes, lv == rv, left.Location); case Binary.Operator.Inequality: - return new BoolConstant (lv != rv, left.Location); + return new BoolConstant (ec.BuiltinTypes, lv != rv, left.Location); } return null; } @@ -160,7 +149,7 @@ namespace Mono.CSharp { case Binary.Operator.ExclusiveOr: result = BinaryFold (ec, oper, ((EnumConstant)left).Child, ((EnumConstant)right).Child, loc); if (result != null) - result = result.Resolve (ec).TryReduce (ec, lt, loc); + result = result.Reduce (ec, lt); return result; /// @@ -169,7 +158,7 @@ namespace Mono.CSharp { case Binary.Operator.Subtraction: result = BinaryFold (ec, oper, ((EnumConstant)left).Child, ((EnumConstant)right).Child, loc); if (result != null) - result = result.Resolve (ec).TryReduce (ec, EnumSpec.GetUnderlyingType (lt), loc); + result = result.Reduce (ec, EnumSpec.GetUnderlyingType (lt)); return result; /// @@ -194,11 +183,11 @@ namespace Mono.CSharp { switch (oper){ case Binary.Operator.BitwiseOr: // - // bool? operator &(bool? x, bool? y); + // bool? operator |(bool? x, bool? y); // - if ((lt == TypeManager.bool_type && right is NullLiteral) || - (rt == TypeManager.bool_type && left is NullLiteral)) { - var b = new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + if ((lt.BuiltinType == BuiltinTypeSpec.Type.Bool && right is NullLiteral) || + (rt.BuiltinType == BuiltinTypeSpec.Type.Bool && left is NullLiteral)) { + var b = new Binary (oper, left, right).ResolveOperator (ec); // false | null => null // null | false => null @@ -207,7 +196,7 @@ namespace Mono.CSharp { // true | null => true // null | true => true - return ReducedExpression.Create (new BoolConstant (true, loc).Resolve (ec), b); + return ReducedExpression.Create (new BoolConstant (ec.BuiltinTypes, true, loc), b); } if (!DoBinaryNumericPromotions (ec, ref left, ref right)) @@ -215,24 +204,24 @@ namespace Mono.CSharp { if (left is IntConstant){ int res = ((IntConstant) left).Value | ((IntConstant) right).Value; - - return new IntConstant (res, left.Location); + + return new IntConstant (ec.BuiltinTypes, res, left.Location); } if (left is UIntConstant){ uint res = ((UIntConstant)left).Value | ((UIntConstant)right).Value; - - return new UIntConstant (res, left.Location); + + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } if (left is LongConstant){ long res = ((LongConstant)left).Value | ((LongConstant)right).Value; - - return new LongConstant (res, left.Location); + + return new LongConstant (ec.BuiltinTypes, res, left.Location); } if (left is ULongConstant){ ulong res = ((ULongConstant)left).Value | ((ULongConstant)right).Value; - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } break; @@ -240,14 +229,14 @@ namespace Mono.CSharp { // // bool? operator &(bool? x, bool? y); // - if ((lt == TypeManager.bool_type && right is NullLiteral) || - (rt == TypeManager.bool_type && left is NullLiteral)) { - var b = new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + if ((lt.BuiltinType == BuiltinTypeSpec.Type.Bool && right is NullLiteral) || + (rt.BuiltinType == BuiltinTypeSpec.Type.Bool && left is NullLiteral)) { + var b = new Binary (oper, left, right).ResolveOperator (ec); // false & null => false // null & false => false if ((right is NullLiteral && left.IsDefaultValue) || (left is NullLiteral && right.IsDefaultValue)) - return ReducedExpression.Create (new BoolConstant (false, loc).Resolve (ec), b); + return ReducedExpression.Create (new BoolConstant (ec.BuiltinTypes, false, loc), b); // true & null => null // null & true => null @@ -265,21 +254,21 @@ namespace Mono.CSharp { /// if (left is IntConstant){ int res = ((IntConstant) left).Value & ((IntConstant) right).Value; - return new IntConstant (res, left.Location); + return new IntConstant (ec.BuiltinTypes, res, left.Location); } if (left is UIntConstant){ uint res = ((UIntConstant)left).Value & ((UIntConstant)right).Value; - return new UIntConstant (res, left.Location); + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } if (left is LongConstant){ long res = ((LongConstant)left).Value & ((LongConstant)right).Value; - return new LongConstant (res, left.Location); + return new LongConstant (ec.BuiltinTypes, res, left.Location); } if (left is ULongConstant){ ulong res = ((ULongConstant)left).Value & ((ULongConstant)right).Value; - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } break; @@ -289,46 +278,72 @@ namespace Mono.CSharp { if (left is IntConstant){ int res = ((IntConstant) left).Value ^ ((IntConstant) right).Value; - return new IntConstant (res, left.Location); + return new IntConstant (ec.BuiltinTypes, res, left.Location); } if (left is UIntConstant){ uint res = ((UIntConstant)left).Value ^ ((UIntConstant)right).Value; - - return new UIntConstant (res, left.Location); + + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } if (left is LongConstant){ long res = ((LongConstant)left).Value ^ ((LongConstant)right).Value; - - return new LongConstant (res, left.Location); + + return new LongConstant (ec.BuiltinTypes, res, left.Location); } if (left is ULongConstant){ ulong res = ((ULongConstant)left).Value ^ ((ULongConstant)right).Value; - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } break; case Binary.Operator.Addition: - if (lt == InternalType.Null) - return right; - - if (rt == InternalType.Null) - return left; - // - // If both sides are strings, then concatenate, if - // one is a string, and the other is not, then defer - // to runtime concatenation + // If both sides are strings, then concatenate + // + // string operator + (string x, string y) // - if (lt == TypeManager.string_type || rt == TypeManager.string_type){ + if (lt.BuiltinType == BuiltinTypeSpec.Type.String || rt.BuiltinType == BuiltinTypeSpec.Type.String){ if (lt == rt) - return new StringConstant ((string)left.GetValue () + (string)right.GetValue (), + return new StringConstant (ec.BuiltinTypes, (string)left.GetValue () + (string)right.GetValue (), left.Location); - + + if (lt == InternalType.NullLiteral) + return new StringConstant (ec.BuiltinTypes, "" + right.GetValue (), left.Location); + + if (rt == InternalType.NullLiteral) + return new StringConstant (ec.BuiltinTypes, left.GetValue () + "", left.Location); + return null; } + // + // string operator + (string x, object y) + // + if (lt == InternalType.NullLiteral) { + if (rt.BuiltinType == BuiltinTypeSpec.Type.Object) + return new StringConstant (ec.BuiltinTypes, "" + right.GetValue (), left.Location); + + if (lt == rt) { + ec.Report.Error (34, loc, "Operator `{0}' is ambiguous on operands of type `{1}' and `{2}'", + "+", lt.GetSignatureForError (), rt.GetSignatureForError ()); + return null; + } + + return right; + } + + // + // string operator + (object x, string y) + // + if (rt == InternalType.NullLiteral) { + if (lt.BuiltinType == BuiltinTypeSpec.Type.Object) + return new StringConstant (ec.BuiltinTypes, right.GetValue () + "", left.Location); + + return left; + } + // // handle "E operator + (E x, U y)" // handle "E operator + (Y y, E x)" @@ -343,7 +358,7 @@ namespace Mono.CSharp { } // U has to be implicitly convetible to E.base - right = right.ConvertImplicitly (ec, lc.Child.Type); + right = right.ConvertImplicitly (lc.Child.Type); if (right == null) return null; @@ -351,7 +366,7 @@ namespace Mono.CSharp { if (result == null) return null; - result = result.Resolve (ec).TryReduce (ec, lt, loc); + result = result.Reduce (ec, lt); if (result == null) return null; @@ -371,8 +386,8 @@ namespace Mono.CSharp { else res = unchecked (((DoubleConstant) left).Value + ((DoubleConstant) right).Value); - - return new DoubleConstant (res, left.Location); + + return new DoubleConstant (ec.BuiltinTypes, res, left.Location); } if (left is FloatConstant){ float res; @@ -383,8 +398,8 @@ namespace Mono.CSharp { else res = unchecked (((FloatConstant) left).Value + ((FloatConstant) right).Value); - - result = new FloatConstant (res, left.Location); + + result = new FloatConstant (ec.BuiltinTypes, res, left.Location); } else if (left is ULongConstant){ ulong res; @@ -395,7 +410,7 @@ namespace Mono.CSharp { res = unchecked (((ULongConstant) left).Value + ((ULongConstant) right).Value); - result = new ULongConstant (res, left.Location); + result = new ULongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is LongConstant){ long res; @@ -405,8 +420,8 @@ namespace Mono.CSharp { else res = unchecked (((LongConstant) left).Value + ((LongConstant) right).Value); - - result = new LongConstant (res, left.Location); + + result = new LongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is UIntConstant){ uint res; @@ -416,8 +431,8 @@ namespace Mono.CSharp { else res = unchecked (((UIntConstant) left).Value + ((UIntConstant) right).Value); - - result = new UIntConstant (res, left.Location); + + result = new UIntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is IntConstant){ int res; @@ -428,7 +443,7 @@ namespace Mono.CSharp { res = unchecked (((IntConstant) left).Value + ((IntConstant) right).Value); - result = new IntConstant (res, left.Location); + result = new IntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is DecimalConstant) { decimal res; @@ -439,7 +454,7 @@ namespace Mono.CSharp { res = unchecked (((DecimalConstant) left).Value + ((DecimalConstant) right).Value); - result = new DecimalConstant (res, left.Location); + result = new DecimalConstant (ec.BuiltinTypes, res, left.Location); } } catch (OverflowException){ Error_CompileTimeOverflow (ec, loc); @@ -462,7 +477,7 @@ namespace Mono.CSharp { } // U has to be implicitly convetible to E.base - right = right.ConvertImplicitly (ec, lc.Child.Type); + right = right.ConvertImplicitly (lc.Child.Type); if (right == null) return null; @@ -470,7 +485,7 @@ namespace Mono.CSharp { if (result == null) return null; - result = result.Resolve (ec).TryReduce (ec, lt, loc); + result = result.Reduce (ec, lt); if (result == null) return null; @@ -478,8 +493,9 @@ namespace Mono.CSharp { } if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } if (!DoBinaryNumericPromotions (ec, ref left, ref right)) @@ -495,8 +511,8 @@ namespace Mono.CSharp { else res = unchecked (((DoubleConstant) left).Value - ((DoubleConstant) right).Value); - - result = new DoubleConstant (res, left.Location); + + result = new DoubleConstant (ec.BuiltinTypes, res, left.Location); } else if (left is FloatConstant){ float res; @@ -506,8 +522,8 @@ namespace Mono.CSharp { else res = unchecked (((FloatConstant) left).Value - ((FloatConstant) right).Value); - - result = new FloatConstant (res, left.Location); + + result = new FloatConstant (ec.BuiltinTypes, res, left.Location); } else if (left is ULongConstant){ ulong res; @@ -517,8 +533,8 @@ namespace Mono.CSharp { else res = unchecked (((ULongConstant) left).Value - ((ULongConstant) right).Value); - - result = new ULongConstant (res, left.Location); + + result = new ULongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is LongConstant){ long res; @@ -528,8 +544,8 @@ namespace Mono.CSharp { else res = unchecked (((LongConstant) left).Value - ((LongConstant) right).Value); - - result = new LongConstant (res, left.Location); + + result = new LongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is UIntConstant){ uint res; @@ -539,8 +555,8 @@ namespace Mono.CSharp { else res = unchecked (((UIntConstant) left).Value - ((UIntConstant) right).Value); - - result = new UIntConstant (res, left.Location); + + result = new UIntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is IntConstant){ int res; @@ -551,7 +567,7 @@ namespace Mono.CSharp { res = unchecked (((IntConstant) left).Value - ((IntConstant) right).Value); - result = new IntConstant (res, left.Location); + result = new IntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is DecimalConstant) { decimal res; @@ -562,7 +578,7 @@ namespace Mono.CSharp { res = unchecked (((DecimalConstant) left).Value - ((DecimalConstant) right).Value); - return new DecimalConstant (res, left.Location); + return new DecimalConstant (ec.BuiltinTypes, res, left.Location); } else { throw new Exception ( "Unexepected subtraction input: " + left); } @@ -574,8 +590,9 @@ namespace Mono.CSharp { case Binary.Operator.Multiply: if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } if (!DoBinaryNumericPromotions (ec, ref left, ref right)) @@ -591,8 +608,8 @@ namespace Mono.CSharp { else res = unchecked (((DoubleConstant) left).Value * ((DoubleConstant) right).Value); - - return new DoubleConstant (res, left.Location); + + return new DoubleConstant (ec.BuiltinTypes, res, left.Location); } else if (left is FloatConstant){ float res; @@ -602,8 +619,8 @@ namespace Mono.CSharp { else res = unchecked (((FloatConstant) left).Value * ((FloatConstant) right).Value); - - return new FloatConstant (res, left.Location); + + return new FloatConstant (ec.BuiltinTypes, res, left.Location); } else if (left is ULongConstant){ ulong res; @@ -613,8 +630,8 @@ namespace Mono.CSharp { else res = unchecked (((ULongConstant) left).Value * ((ULongConstant) right).Value); - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is LongConstant){ long res; @@ -624,8 +641,8 @@ namespace Mono.CSharp { else res = unchecked (((LongConstant) left).Value * ((LongConstant) right).Value); - - return new LongConstant (res, left.Location); + + return new LongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is UIntConstant){ uint res; @@ -635,8 +652,8 @@ namespace Mono.CSharp { else res = unchecked (((UIntConstant) left).Value * ((UIntConstant) right).Value); - - return new UIntConstant (res, left.Location); + + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is IntConstant){ int res; @@ -647,7 +664,7 @@ namespace Mono.CSharp { res = unchecked (((IntConstant) left).Value * ((IntConstant) right).Value); - return new IntConstant (res, left.Location); + return new IntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is DecimalConstant) { decimal res; @@ -658,7 +675,7 @@ namespace Mono.CSharp { res = unchecked (((DecimalConstant) left).Value * ((DecimalConstant) right).Value); - return new DecimalConstant (res, left.Location); + return new DecimalConstant (ec.BuiltinTypes, res, left.Location); } else { throw new Exception ( "Unexepected multiply input: " + left); } @@ -669,8 +686,9 @@ namespace Mono.CSharp { case Binary.Operator.Division: if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } if (!DoBinaryNumericPromotions (ec, ref left, ref right)) @@ -686,8 +704,8 @@ namespace Mono.CSharp { else res = unchecked (((DoubleConstant) left).Value / ((DoubleConstant) right).Value); - - return new DoubleConstant (res, left.Location); + + return new DoubleConstant (ec.BuiltinTypes, res, left.Location); } else if (left is FloatConstant){ float res; @@ -697,8 +715,8 @@ namespace Mono.CSharp { else res = unchecked (((FloatConstant) left).Value / ((FloatConstant) right).Value); - - return new FloatConstant (res, left.Location); + + return new FloatConstant (ec.BuiltinTypes, res, left.Location); } else if (left is ULongConstant){ ulong res; @@ -708,8 +726,8 @@ namespace Mono.CSharp { else res = unchecked (((ULongConstant) left).Value / ((ULongConstant) right).Value); - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is LongConstant){ long res; @@ -719,8 +737,8 @@ namespace Mono.CSharp { else res = unchecked (((LongConstant) left).Value / ((LongConstant) right).Value); - - return new LongConstant (res, left.Location); + + return new LongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is UIntConstant){ uint res; @@ -730,8 +748,8 @@ namespace Mono.CSharp { else res = unchecked (((UIntConstant) left).Value / ((UIntConstant) right).Value); - - return new UIntConstant (res, left.Location); + + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is IntConstant){ int res; @@ -742,7 +760,7 @@ namespace Mono.CSharp { res = unchecked (((IntConstant) left).Value / ((IntConstant) right).Value); - return new IntConstant (res, left.Location); + return new IntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is DecimalConstant) { decimal res; @@ -753,7 +771,7 @@ namespace Mono.CSharp { res = unchecked (((DecimalConstant) left).Value / ((DecimalConstant) right).Value); - return new DecimalConstant (res, left.Location); + return new DecimalConstant (ec.BuiltinTypes, res, left.Location); } else { throw new Exception ( "Unexepected division input: " + left); } @@ -768,8 +786,9 @@ namespace Mono.CSharp { case Binary.Operator.Modulus: if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } if (!DoBinaryNumericPromotions (ec, ref left, ref right)) @@ -785,8 +804,8 @@ namespace Mono.CSharp { else res = unchecked (((DoubleConstant) left).Value % ((DoubleConstant) right).Value); - - return new DoubleConstant (res, left.Location); + + return new DoubleConstant (ec.BuiltinTypes, res, left.Location); } else if (left is FloatConstant){ float res; @@ -796,8 +815,8 @@ namespace Mono.CSharp { else res = unchecked (((FloatConstant) left).Value % ((FloatConstant) right).Value); - - return new FloatConstant (res, left.Location); + + return new FloatConstant (ec.BuiltinTypes, res, left.Location); } else if (left is ULongConstant){ ulong res; @@ -807,8 +826,8 @@ namespace Mono.CSharp { else res = unchecked (((ULongConstant) left).Value % ((ULongConstant) right).Value); - - return new ULongConstant (res, left.Location); + + return new ULongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is LongConstant){ long res; @@ -818,8 +837,8 @@ namespace Mono.CSharp { else res = unchecked (((LongConstant) left).Value % ((LongConstant) right).Value); - - return new LongConstant (res, left.Location); + + return new LongConstant (ec.BuiltinTypes, res, left.Location); } else if (left is UIntConstant){ uint res; @@ -829,8 +848,8 @@ namespace Mono.CSharp { else res = unchecked (((UIntConstant) left).Value % ((UIntConstant) right).Value); - - return new UIntConstant (res, left.Location); + + return new UIntConstant (ec.BuiltinTypes, res, left.Location); } else if (left is IntConstant){ int res; @@ -841,7 +860,7 @@ namespace Mono.CSharp { res = unchecked (((IntConstant) left).Value % ((IntConstant) right).Value); - return new IntConstant (res, left.Location); + return new IntConstant (ec.BuiltinTypes, res, left.Location); } else { throw new Exception ( "Unexepected modulus input: " + left); } @@ -857,31 +876,34 @@ namespace Mono.CSharp { // case Binary.Operator.LeftShift: if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } - IntConstant ic = right.ConvertImplicitly (ec, TypeManager.int32_type) as IntConstant; + IntConstant ic = right.ConvertImplicitly (ec.BuiltinTypes.Int) as IntConstant; if (ic == null){ Binary.Error_OperatorCannotBeApplied (ec, left, right, oper, loc); return null; } int lshift_val = ic.Value; - if (left.Type == TypeManager.uint64_type) - return new ULongConstant (((ULongConstant)left).Value << lshift_val, left.Location); - if (left.Type == TypeManager.int64_type) - return new LongConstant (((LongConstant)left).Value << lshift_val, left.Location); - if (left.Type == TypeManager.uint32_type) - return new UIntConstant (((UIntConstant)left).Value << lshift_val, left.Location); + switch (left.Type.BuiltinType) { + case BuiltinTypeSpec.Type.ULong: + return new ULongConstant (ec.BuiltinTypes, ((ULongConstant) left).Value << lshift_val, left.Location); + case BuiltinTypeSpec.Type.Long: + return new LongConstant (ec.BuiltinTypes, ((LongConstant) left).Value << lshift_val, left.Location); + case BuiltinTypeSpec.Type.UInt: + return new UIntConstant (ec.BuiltinTypes, ((UIntConstant) left).Value << lshift_val, left.Location); + } // null << value => null if (left is NullLiteral) - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + return (Constant) new Binary (oper, left, right).ResolveOperator (ec); - left = left.ConvertImplicitly (ec, TypeManager.int32_type); - if (left.Type == TypeManager.int32_type) - return new IntConstant (((IntConstant)left).Value << lshift_val, left.Location); + left = left.ConvertImplicitly (ec.BuiltinTypes.Int); + if (left.Type.BuiltinType == BuiltinTypeSpec.Type.Int) + return new IntConstant (ec.BuiltinTypes, ((IntConstant) left).Value << lshift_val, left.Location); Binary.Error_OperatorCannotBeApplied (ec, left, right, oper, loc); break; @@ -891,46 +913,49 @@ namespace Mono.CSharp { // case Binary.Operator.RightShift: if (left is NullLiteral && right is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } - IntConstant sic = right.ConvertImplicitly (ec, TypeManager.int32_type) as IntConstant; + IntConstant sic = right.ConvertImplicitly (ec.BuiltinTypes.Int) as IntConstant; if (sic == null){ - Binary.Error_OperatorCannotBeApplied (ec, left, right, oper, loc); ; + Binary.Error_OperatorCannotBeApplied (ec, left, right, oper, loc); return null; } int rshift_val = sic.Value; - if (left.Type == TypeManager.uint64_type) - return new ULongConstant (((ULongConstant)left).Value >> rshift_val, left.Location); - if (left.Type == TypeManager.int64_type) - return new LongConstant (((LongConstant)left).Value >> rshift_val, left.Location); - if (left.Type == TypeManager.uint32_type) - return new UIntConstant (((UIntConstant)left).Value >> rshift_val, left.Location); + switch (left.Type.BuiltinType) { + case BuiltinTypeSpec.Type.ULong: + return new ULongConstant (ec.BuiltinTypes, ((ULongConstant) left).Value >> rshift_val, left.Location); + case BuiltinTypeSpec.Type.Long: + return new LongConstant (ec.BuiltinTypes, ((LongConstant) left).Value >> rshift_val, left.Location); + case BuiltinTypeSpec.Type.UInt: + return new UIntConstant (ec.BuiltinTypes, ((UIntConstant) left).Value >> rshift_val, left.Location); + } // null >> value => null if (left is NullLiteral) - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + return (Constant) new Binary (oper, left, right).ResolveOperator (ec); - left = left.ConvertImplicitly (ec, TypeManager.int32_type); - if (left.Type == TypeManager.int32_type) - return new IntConstant (((IntConstant)left).Value >> rshift_val, left.Location); + left = left.ConvertImplicitly (ec.BuiltinTypes.Int); + if (left.Type.BuiltinType == BuiltinTypeSpec.Type.Int) + return new IntConstant (ec.BuiltinTypes, ((IntConstant) left).Value >> rshift_val, left.Location); Binary.Error_OperatorCannotBeApplied (ec, left, right, oper, loc); break; case Binary.Operator.Equality: - if (TypeManager.IsReferenceType (lt) && TypeManager.IsReferenceType (rt) || + if (TypeSpec.IsReferenceType (lt) && TypeSpec.IsReferenceType (rt) || (left is Nullable.LiftedNull && right.IsNull) || (right is Nullable.LiftedNull && left.IsNull)) { if (left.IsNull || right.IsNull) { return ReducedExpression.Create ( - new BoolConstant (left.IsNull == right.IsNull, left.Location).Resolve (ec), - new Binary (oper, left, right, loc)); + new BoolConstant (ec.BuiltinTypes, left.IsNull == right.IsNull, left.Location), + new Binary (oper, left, right)); } if (left is StringConstant && right is StringConstant) - return new BoolConstant ( + return new BoolConstant (ec.BuiltinTypes, ((StringConstant) left).Value == ((StringConstant) right).Value, left.Location); return null; @@ -961,20 +986,20 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); case Binary.Operator.Inequality: - if (TypeManager.IsReferenceType (lt) && TypeManager.IsReferenceType (rt) || + if (TypeSpec.IsReferenceType (lt) && TypeSpec.IsReferenceType (rt) || (left is Nullable.LiftedNull && right.IsNull) || (right is Nullable.LiftedNull && left.IsNull)) { if (left.IsNull || right.IsNull) { return ReducedExpression.Create ( - new BoolConstant (left.IsNull != right.IsNull, left.Location).Resolve (ec), - new Binary (oper, left, right, loc)); + new BoolConstant (ec.BuiltinTypes, left.IsNull != right.IsNull, left.Location), + new Binary (oper, left, right)); } if (left is StringConstant && right is StringConstant) - return new BoolConstant ( + return new BoolConstant (ec.BuiltinTypes, ((StringConstant) left).Value != ((StringConstant) right).Value, left.Location); return null; @@ -1005,17 +1030,14 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); case Binary.Operator.LessThan: if (right is NullLiteral) { if (left is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); - } - - if (left is Nullable.LiftedNull) { - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } } @@ -1044,17 +1066,14 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); case Binary.Operator.GreaterThan: if (right is NullLiteral) { if (left is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); - } - - if (left is Nullable.LiftedNull) { - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } } @@ -1083,17 +1102,14 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); case Binary.Operator.GreaterThanOrEqual: if (right is NullLiteral) { if (left is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); - } - - if (left is Nullable.LiftedNull) { - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } } @@ -1122,17 +1138,14 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); case Binary.Operator.LessThanOrEqual: if (right is NullLiteral) { if (left is NullLiteral) { - var lifted_int = new Nullable.NullableType (TypeManager.int32_type, loc).ResolveAsTypeTerminal (ec, false); - return (Constant) new Nullable.LiftedBinaryOperator (oper, lifted_int, right, loc).Resolve (ec); - } - - if (left is Nullable.LiftedNull) { - return (Constant) new Nullable.LiftedBinaryOperator (oper, left, right, loc).Resolve (ec); + var lifted_int = new Nullable.NullableType (ec.BuiltinTypes.Int, loc); + lifted_int.ResolveAsType (ec); + return (Constant) new Binary (oper, lifted_int, right).ResolveOperator (ec); } } @@ -1161,7 +1174,7 @@ namespace Mono.CSharp { else return null; - return new BoolConstant (bool_res, left.Location); + return new BoolConstant (ec.BuiltinTypes, bool_res, left.Location); } return null;