Sfoglia il codice sorgente

Implemented another 6 Expression methods.

svn path=/trunk/mcs/; revision=84329
Federico Di Gregorio 18 anni fa
parent
commit
1e4e0fa64b

+ 4 - 0
mcs/class/System.Core/System.Core_test.dll.sources

@@ -9,12 +9,16 @@ System.Linq.Expressions/ExpressionTest_Call.cs
 System.Linq.Expressions/ExpressionTest_Constant.cs
 System.Linq.Expressions/ExpressionTest_Divide.cs
 System.Linq.Expressions/ExpressionTest_ExclusiveOr.cs
+System.Linq.Expressions/ExpressionTest_Field.cs
 System.Linq.Expressions/ExpressionTest_LeftShift.cs
 System.Linq.Expressions/ExpressionTest_Modulo.cs
 System.Linq.Expressions/ExpressionTest_Multiply.cs
 System.Linq.Expressions/ExpressionTest_MultiplyChecked.cs
 System.Linq.Expressions/ExpressionTest_Or.cs
 System.Linq.Expressions/ExpressionTest_OrElse.cs
+System.Linq.Expressions/ExpressionTest_Property.cs
+System.Linq.Expressions/ExpressionTest_PropertyOrField.cs
+System.Linq.Expressions/ExpressionTest_Quote.cs
 System.Linq.Expressions/ExpressionTest_RightShift.cs
 System.Linq.Expressions/ExpressionTest_Subtract.cs
 System.Linq.Expressions/ExpressionTest_SubtractChecked.cs

+ 9 - 0
mcs/class/System.Core/System.Linq.Expressions/ChangeLog

@@ -1,5 +1,14 @@
 2007-08-17  Federico Di Gregorio <[email protected]>
 
+	* Expression.cs: fixed Field() and Property() behaviour when accessing static
+	members (i.e., when expression is null). Also added the missing version for
+	Property().
+
+	* MemberExpression.cs: added missing BuildString() method that differentiates
+	between static and instance methods.
+
+	* Expression.cs: implemented Quote() and tests.
+
 	* Expression.cs: implemented RightShift(), added tests for it and for
 	LeftShift().
 

+ 105 - 54
mcs/class/System.Core/System.Linq.Expressions/Expression.cs

@@ -227,7 +227,7 @@ namespace System.Linq.Expressions
         {
             // If the method has the hidebysig and specialname attributes it can be a property accessor;
             // if that's the case we try to extract the type of the property and then we use it and the
-            // property name (derived from the method name) to find the right ProprtyInfo.
+            // property name (derived from the method name) to find the right PropertyInfo.
             
             if (mi.IsHideBySig && mi.IsSpecialName) {
                 Type propertyType = null;
@@ -269,13 +269,29 @@ namespace System.Linq.Expressions
         private static void ValidateSettableFieldOrPropertyMember (MemberInfo member, out Type memberType)
         {
             if (member.MemberType == MemberTypes.Field) {
-                memberType = typeof (FieldInfo);
+                memberType = (member as FieldInfo).FieldType;
             }
             else if (member.MemberType == MemberTypes.Property) {
                 PropertyInfo pi = (PropertyInfo)member;
                 if (!pi.CanWrite)
                     throw new ArgumentException (String.Format ("The property '{0}' has no 'set' accessor", pi));
-                memberType = typeof (PropertyInfo);
+                memberType = (member as PropertyInfo).PropertyType;
+            }
+            else {
+                throw new ArgumentException ("Argument must be either a FieldInfo or PropertyInfo");   
+            }
+        }
+
+        private static void ValidateGettableFieldOrPropertyMember (MemberInfo member, out Type memberType)
+        {
+            if (member.MemberType == MemberTypes.Field) {
+                memberType = (member as FieldInfo).FieldType;
+            }
+            else if (member.MemberType == MemberTypes.Property) {
+                PropertyInfo pi = (PropertyInfo)member;
+                if (!pi.CanRead)
+                    throw new ArgumentException (String.Format ("The property '{0}' has no 'get' accessor", pi));
+                memberType = (member as PropertyInfo).PropertyType;
             }
             else {
                 throw new ArgumentException ("Argument must be either a FieldInfo or PropertyInfo");   
@@ -680,25 +696,36 @@ namespace System.Linq.Expressions
         }
         #endregion
         
-        public static MemberExpression Field(Expression expression, FieldInfo field)
+        #region Field
+        public static MemberExpression Field (Expression expression, FieldInfo field)
         {
+            // Note that expression can be (and should be) null when the access is to a static field.
+
             if (field == null)
                 throw new ArgumentNullException("field");
 
-            return new MemberExpression(expression, field, field.FieldType);
+            Type fieldType;
+            ValidateGettableFieldOrPropertyMember(field, out fieldType);
+
+            return new MemberExpression(expression, field, fieldType);
         }
 
-        public static MemberExpression Field(Expression expression, string fieldName)
+        public static MemberExpression Field (Expression expression, string fieldName)
         {
             if (expression == null)
                 throw new ArgumentNullException("expression");
+            if (fieldName == null)
+                throw new ArgumentNullException("fieldName");
 
-            FieldInfo field = expression.Type.GetField(fieldName, BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic);
+            FieldInfo field = expression.Type.GetField(fieldName,
+                BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
             if (field == null)
-                throw new ArgumentException();
+                throw new ArgumentException (String.Format ("Field {0} is not defined for type {1}",
+                    fieldName, expression.type.FullName));
 
             return Field(expression, field);
         }
+        #endregion
 
         public static FuncletExpression Funclet(Funclet funclet, Type type)
         {
@@ -861,19 +888,6 @@ namespace System.Linq.Expressions
         }
         #endregion
         
-        public static MemberExpression Property(Expression expression, PropertyInfo property)
-        {
-            if (property == null)
-                throw new ArgumentNullException("property");
-
-            MethodInfo getMethod = property.GetGetMethod(true);
-            if (getMethod == null)
-                throw new ArgumentException(); // to access the property we need to have
-                                               // a get method...
-
-            return new MemberExpression(expression, property, property.PropertyType);
-        }
-        
         #region Or
         public static BinaryExpression Or (Expression left, Expression right, MethodInfo method)
         {
@@ -939,37 +953,78 @@ namespace System.Linq.Expressions
             return new UnaryExpression(ExpressionType.Quote, expression, expression.GetType());
         }
 
+        #region Property
+        public static MemberExpression Property (Expression expression, MethodInfo propertyAccessor)
+        {
+            if (propertyAccessor == null)
+                throw new ArgumentNullException("propertyAccessor");
+        
+            return Property(expression, GetProperty(propertyAccessor));
+        }
 
+        public static MemberExpression Property (Expression expression, PropertyInfo property)
+        {
+            if (property == null)
+                throw new ArgumentNullException("property");
+
+            Type propertyType;
+            ValidateGettableFieldOrPropertyMember(property, out propertyType);
+            
+            return new MemberExpression(expression, property, propertyType);
+        }
+        
+        
         public static MemberExpression Property(Expression expression, string propertyName)
         {
             if (expression == null)
-                throw new ArgumentNullException("expression");
+                throw new ArgumentNullException ("expression");
+            if (propertyName == null)
+                throw new ArgumentNullException ("propertyName");
 
-            PropertyInfo property = expression.Type.GetProperty(propertyName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
+            PropertyInfo property = expression.Type.GetProperty (propertyName,
+                BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
 
             if (property == null)
-                throw new ArgumentException();
+                throw new ArgumentException (String.Format ("{0} is not a member of type {1}",
+                    propertyName, expression.type.FullName));
 
-            return Property(expression, property);
+            return Property (expression, property);
         }
-
+        #endregion
+        
+        #region PropertyOrField
         public static MemberExpression PropertyOrField(Expression expression, string propertyOrFieldName)
         {
             if (expression == null)
-                throw new ArgumentNullException("expression");
+                throw new ArgumentNullException ("expression");
+            if (propertyOrFieldName == null)
+                throw new ArgumentNullException ("propertyOrFieldName");
 
-            PropertyInfo property = expression.Type.GetProperty(propertyOrFieldName, BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic);
+            PropertyInfo property = expression.type.GetProperty (propertyOrFieldName,
+                BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
             if (property != null)
-                return Property(expression, property);
+                return Property (expression, property);
 
-            FieldInfo field = expression.Type.GetField(propertyOrFieldName, BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic);
+            FieldInfo field = expression.type.GetField (propertyOrFieldName,
+                BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
             if (field != null)
-                return Field(expression, field);
+                return Field (expression, field);
+
+            throw new ArgumentException (String.Format ("{0} is not a member of type {1}",
+                propertyOrFieldName, expression.type.FullName));
+        }
+        #endregion
+        
+        #region Quote
+        public static UnaryExpression QUote(Expression expression)
+        {
+            if (expression == null)
+                throw new ArgumentNullException ("expression");
                 
-            //TODO: should we return <null> here?
-            // the name is not defined in the Type of the expression given...
-            throw new ArgumentException();
+            return new UnaryExpression (ExpressionType.Quote, expression, expression.GetType());
+        
         }
+        #endregion
 
         #region RightShift
         public static BinaryExpression RightShift (Expression left, Expression right, MethodInfo method)
@@ -980,12 +1035,12 @@ namespace System.Linq.Expressions
                 throw new ArgumentNullException ("right");
 
             if (method != null)
-                return new BinaryExpression(ExpressionType.RightShift, left, right, method, method.ReturnType);
+                return new BinaryExpression (ExpressionType.RightShift, left, right, method, method.ReturnType);
             
             // If the left side is any kind of integer and the right is int32 we don't have
             // to look for the "op_Addition" method.
             if (IsInteger(left.type) && right.type == typeof(Int32))
-                return new BinaryExpression(ExpressionType.RightShift, left, right, left.type);
+                return new BinaryExpression (ExpressionType.RightShift, left, right, left.type);
 
             // Else we try for a user-defined operator.
             return GetUserDefinedBinaryOperatorOrThrow (ExpressionType.RightShift, "op_RightShift", left, right);
@@ -1006,12 +1061,12 @@ namespace System.Linq.Expressions
                 throw new ArgumentNullException ("right");
 
             if (method != null)
-                return new BinaryExpression(ExpressionType.Subtract, left, right, method, method.ReturnType);
+                return new BinaryExpression (ExpressionType.Subtract, left, right, method, method.ReturnType);
             
             // Since both the expressions define the same numeric type we don't have
             // to look for the "op_Addition" method.
             if (left.type == right.type && IsNumeric (left.type))
-                return new BinaryExpression(ExpressionType.Subtract, left, right, left.type);
+                return new BinaryExpression (ExpressionType.Subtract, left, right, left.type);
 
             // Else we try for a user-defined operator.
             return GetUserDefinedBinaryOperatorOrThrow (ExpressionType.Subtract, "op_Subtraction", left, right);        
@@ -1032,25 +1087,21 @@ namespace System.Linq.Expressions
                 throw new ArgumentNullException ("right");
 
             if (method != null)
-                return new BinaryExpression(ExpressionType.SubtractChecked, left, right, method, method.ReturnType);
+                return new BinaryExpression (ExpressionType.SubtractChecked, left, right, method, method.ReturnType);
 
             // Since both the expressions define the same numeric type we don't have
             // to look for the "op_Addition" method.
             if (left.type == right.type && IsNumeric (left.type))
-                return new BinaryExpression(ExpressionType.SubtractChecked, left, right, left.type);
+                return new BinaryExpression (ExpressionType.SubtractChecked, left, right, left.type);
 
             method = GetUserDefinedBinaryOperator (left.type, right.type, "op_Subtraction");
             if (method == null)
-                throw new InvalidOperationException(String.Format(
+                throw new InvalidOperationException (String.Format (
                     "The binary operator AddChecked is not defined for the types '{0}' and '{1}'.", left.type, right.type));
             
             Type retType = method.ReturnType;
 
-            // Note: here the code did some very strange checks for bool (but note that bool does
-            // not define an addition operator) and created nullables for value types (but the new
-            // MS code does not do that). All that has been removed.
-
-            return new BinaryExpression(ExpressionType.SubtractChecked, left, right, method, retType);
+            return new BinaryExpression (ExpressionType.SubtractChecked, left, right, method, retType);
         }
         
         public static BinaryExpression SubtractChecked (Expression left, Expression right)
@@ -1060,26 +1111,26 @@ namespace System.Linq.Expressions
         #endregion
 
         #region TypeAs
-        public static UnaryExpression TypeAs(Expression expression, Type type)
+        public static UnaryExpression TypeAs (Expression expression, Type type)
         {
             if (expression == null)
-                throw new ArgumentNullException("expression");
+                throw new ArgumentNullException ("expression");
             if (type == null)
-                throw new ArgumentNullException("type");
+                throw new ArgumentNullException ("type");
 
-            return new UnaryExpression(ExpressionType.TypeAs, expression, type);
+            return new UnaryExpression (ExpressionType.TypeAs, expression, type);
         }
         #endregion
 
         #region TypeIs
-        public static TypeBinaryExpression TypeIs(Expression expression, Type type)
+        public static TypeBinaryExpression TypeIs (Expression expression, Type type)
         {
             if (expression == null)
-                throw new ArgumentNullException("expression");
+                throw new ArgumentNullException ("expression");
             if (type == null)
-                throw new ArgumentNullException("type"); 
+                throw new ArgumentNullException ("type"); 
             
-            return new TypeBinaryExpression(ExpressionType.TypeIs, expression, type, typeof(bool));
+            return new TypeBinaryExpression (ExpressionType.TypeIs, expression, type, typeof(bool));
         }
         #endregion
     }

+ 2 - 2
mcs/class/System.Core/System.Linq.Expressions/MemberAssignment.cs

@@ -46,10 +46,10 @@ namespace System.Linq.Expressions
         #endregion
 
         #region Internal Methods
-        internal override void BuildString(StringBuilder builder)
+        internal override void BuildString (StringBuilder builder)
         {
             builder.Append (Member.Name).Append (" = ");
-            expression.BuildString(builder);
+            expression.BuildString (builder);
         }
         #endregion
     }

+ 14 - 1
mcs/class/System.Core/System.Linq.Expressions/MemberExpression.cs

@@ -18,16 +18,18 @@
 //
 // Authors:
 //        Antonello Provenzano  <[email protected]>
+//        Federico Di Gregorio  <[email protected]>
 //
 
 using System.Reflection;
+using System.Text;
 
 namespace System.Linq.Expressions
 {
     public sealed class MemberExpression : Expression
     {
         #region .ctor
-        internal MemberExpression(Expression expression, MemberInfo member, Type type)
+        internal MemberExpression (Expression expression, MemberInfo member, Type type)
             : base(ExpressionType.MemberAccess, type)
         {
             this.expr = expression;
@@ -49,5 +51,16 @@ namespace System.Linq.Expressions
             get { return member; }
         }
         #endregion
+
+        #region Internal Methods
+        internal override void BuildString (StringBuilder builder)
+        {
+            if (expr != null)
+                expr.BuildString (builder);
+            else
+                builder.Append (member.DeclaringType.Name);
+            builder.Append (".").Append (member.Name);
+        }
+        #endregion
     }
 }

+ 4 - 0
mcs/class/System.Core/System.Linq.Expressions/UnaryExpression.cs

@@ -78,6 +78,10 @@ namespace System.Linq.Expressions
                 builder.Append (")");
                 break;
 
+            case ExpressionType.Quote:
+                operand.BuildString (builder);
+                break;
+
             case ExpressionType.TypeAs:
                 builder.Append ("(");
                 operand.BuildString (builder);

+ 89 - 0
mcs/class/System.Core/Test/System.Linq.Expressions/ExpressionTest_Field.cs

@@ -0,0 +1,89 @@
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+//
+// Authors:
+//        Federico Di Gregorio <[email protected]>
+
+using System;
+using System.Reflection;
+using System.Linq;
+using System.Linq.Expressions;
+using NUnit.Framework;
+
+namespace MonoTests.System.Linq.Expressions
+{        
+    [TestFixture]
+    public class ExpressionTest_Field
+    {
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg1Null ()
+        {
+            Expression.Field (null, "NoField");
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null1 ()
+        {
+            Expression.Field (Expression.Constant (new MemberClass()), (string)null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null2 ()
+        {
+            Expression.Field (Expression.Constant (new MemberClass()), (FieldInfo)null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentException))]
+        public void NoField ()
+        {
+            Expression.Field (Expression.Constant (new MemberClass()), "NoField");
+        }
+
+        [Test]
+        public void InstanceField ()
+        {
+            MemberExpression expr = Expression.Field (Expression.Constant (new MemberClass()), "TestField1");
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Field#01");
+            Assert.AreEqual (typeof (int), expr.Type, "Field#02");
+            Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestField1", expr.ToString(), "Field#03");
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentException))]
+        public void StaticField1 ()
+        {
+            // This will fail because access to a static field should be created using a FieldInfo and
+            // not an instance plus the field name.
+            Expression.Field (Expression.Constant (new MemberClass()), "StaticField");
+        }
+
+        [Test]
+        public void StaticField2 ()
+        {
+            MemberExpression expr = Expression.Field (null, MemberClass.GetStaticFieldInfo());
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Field#07");
+            Assert.AreEqual (typeof (int), expr.Type, "Field#08");
+            Assert.AreEqual ("MemberClass.StaticField", expr.ToString(), "Field#09");
+        }
+
+    }
+}

+ 128 - 0
mcs/class/System.Core/Test/System.Linq.Expressions/ExpressionTest_Property.cs

@@ -0,0 +1,128 @@
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+//
+// Authors:
+//        Federico Di Gregorio <[email protected]>
+
+using System;
+using System.Reflection;
+using System.Linq;
+using System.Linq.Expressions;
+using NUnit.Framework;
+
+namespace MonoTests.System.Linq.Expressions
+{        
+    [TestFixture]
+    public class ExpressionTest_Property
+    {
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg1Null ()
+        {
+            Expression.Property (null, "NoProperty");
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null1 ()
+        {
+            Expression.Property (Expression.Constant (new MemberClass()), (string)null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null2 ()
+        {
+            Expression.Property (Expression.Constant (new MemberClass()), (PropertyInfo)null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null3 ()
+        {
+            Expression.Property (Expression.Constant (new MemberClass()), (MethodInfo)null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentException))]
+        public void NoProperty ()
+        {
+            Expression.Property (Expression.Constant (new MemberClass()), "NoProperty");
+        }
+
+        [Test]
+        public void InstanceProperty1 ()
+        {
+            MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), "TestProperty1");
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#01");
+            Assert.AreEqual (typeof (int), expr.Type, "Property#02");
+            Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#03");
+        }
+
+        [Test]
+        public void InstanceProperty2 ()
+        {
+            MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), MemberClass.GetRoPropertyInfo());
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#04");
+            Assert.AreEqual (typeof (int), expr.Type, "Property#05");
+            Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#06");
+        }
+
+        [Test]
+        public void InstanceProperty3 ()
+        {
+            MethodInfo mi = typeof(MemberClass).GetMethod("get_TestProperty1");
+            
+            MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), mi);
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#07");
+            Assert.AreEqual (typeof (int), expr.Type, "Property#08");
+            Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#09");
+            Assert.AreEqual (MemberClass.GetRoPropertyInfo(), expr.Member, "Property#10");
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentException))]
+        public void StaticProperty1 ()
+        {
+            // This will fail because access to a static field should be created using a PropertyInfo and
+            // not an instance plus the field name.
+            Expression.Property (Expression.Constant (new MemberClass()), "StaticProperty");
+        }
+
+        [Test]
+        public void StaticProperty2 ()
+        {
+            MemberExpression expr = Expression.Property (null, MemberClass.GetStaticPropertyInfo());
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#11");
+            Assert.AreEqual (typeof (int), expr.Type, "Property#12");
+            Assert.AreEqual ("MemberClass.StaticProperty", expr.ToString(), "Property#13");
+        }
+
+        [Test]
+        public void StaticProperty3 ()
+        {
+            MethodInfo mi = typeof(MemberClass).GetMethod("get_StaticProperty");
+            
+            MemberExpression expr = Expression.Property (null, mi);
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#14");
+            Assert.AreEqual (typeof (int), expr.Type, "Property#15");
+            Assert.AreEqual ("MemberClass.StaticProperty", expr.ToString(), "Property#16");
+            Assert.AreEqual (MemberClass.GetStaticPropertyInfo(), expr.Member, "Property#17");
+        }
+    }
+}

+ 63 - 0
mcs/class/System.Core/Test/System.Linq.Expressions/ExpressionTest_PropertyOrField.cs

@@ -0,0 +1,63 @@
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+//
+// Authors:
+//        Federico Di Gregorio <[email protected]>
+
+using System;
+using System.Reflection;
+using System.Linq;
+using System.Linq.Expressions;
+using NUnit.Framework;
+
+namespace MonoTests.System.Linq.Expressions
+{        
+    [TestFixture]
+    public class ExpressionTest_PropertyOrField
+    {
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg1Null ()
+        {
+            Expression.PropertyOrField (null, "NoPropertyOrField");
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg2Null ()
+        {
+            Expression.PropertyOrField (Expression.Constant (new MemberClass()), null);
+        }
+
+        [Test]
+        [ExpectedException (typeof (ArgumentException))]
+        public void NoPropertyOrField ()
+        {
+            Expression.PropertyOrField (Expression.Constant (new MemberClass()), "NoPropertyOrField");
+        }
+
+        [Test]
+        public void InstanceProperty ()
+        {
+            MemberExpression expr = Expression.PropertyOrField (Expression.Constant (new MemberClass()), "TestProperty1");
+            Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "PropertyOrField#01");
+            Assert.AreEqual (typeof (int), expr.Type, "PropertyOrField#02");
+            Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "PropertyOrField#04");
+        }
+    }
+}

+ 49 - 0
mcs/class/System.Core/Test/System.Linq.Expressions/ExpressionTest_Quote.cs

@@ -0,0 +1,49 @@
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+//
+// Authors:
+//        Federico Di Gregorio <[email protected]>
+
+using System;
+using System.Reflection;
+using System.Linq;
+using System.Linq.Expressions;
+using NUnit.Framework;
+
+namespace MonoTests.System.Linq.Expressions
+{        
+    [TestFixture]
+    public class ExpressionTest_Quote
+    {
+        [Test]
+        [ExpectedException (typeof (ArgumentNullException))]
+        public void Arg1Null ()
+        {
+            Expression.Quote (null);
+        }
+
+        [Test]
+        public void Constant ()
+        {
+            UnaryExpression expr = Expression.Quote (Expression.Constant (1));
+            Assert.AreEqual (ExpressionType.Quote, expr.NodeType, "Quote#01");
+            Assert.AreEqual (typeof (ConstantExpression), expr.Type, "Quote#02");
+            Assert.AreEqual ("1", expr.ToString(), "Quote#03");
+        }
+    }
+}