1 /* ****************************************************************************
3 * Copyright (c) Microsoft Corporation.
5 * This source code is subject to terms and conditions of the Apache License, Version 2.0. A
6 * copy of the license can be found in the License.html file at the root of this distribution. If
7 * you cannot locate the Apache License, Version 2.0, please send an email to
8 * dlr@microsoft.com. By using this source code in any fashion, you are agreeing to be bound
9 * by the terms of the Apache License, Version 2.0.
11 * You must not remove this notice, or any other, from this software.
14 * ***************************************************************************/
17 using System.Dynamic.Utils;
18 using System.Reflection;
25 namespace Microsoft.Scripting.Ast {
27 namespace System.Linq.Expressions {
30 /// Represents assignment to a member of an object.
32 public sealed class MemberAssignment : MemberBinding {
33 Expression _expression;
34 internal MemberAssignment(MemberInfo member, Expression expression)
35 #pragma warning disable 618
36 : base(MemberBindingType.Assignment, member) {
37 #pragma warning restore 618
38 _expression = expression;
41 /// Gets the <see cref="Expression"/> which represents the object whose member is being assigned to.
43 public Expression Expression {
44 get { return _expression; }
48 /// Creates a new expression that is like this one, but using the
49 /// supplied children. If all of the children are the same, it will
50 /// return this expression.
52 /// <param name="expression">The <see cref="Expression" /> property of the result.</param>
53 /// <returns>This expression if no children changed, or an expression with the updated children.</returns>
54 public MemberAssignment Update(Expression expression) {
55 if (expression == Expression) {
58 return Expression.Bind(Member, expression);
63 public partial class Expression {
65 /// Creates a <see cref="MemberAssignment"/> binding the specified value to the given member.
67 /// <param name="member">The <see cref="MemberInfo"/> for the member which is being assigned to.</param>
68 /// <param name="expression">The value to be assigned to <paramref name="member"/>.</param>
69 /// <returns>The created <see cref="MemberAssignment"/>.</returns>
70 public static MemberAssignment Bind(MemberInfo member, Expression expression) {
71 ContractUtils.RequiresNotNull(member, "member");
72 RequiresCanRead(expression, "expression");
74 ValidateSettableFieldOrPropertyMember(member, out memberType);
75 if (!memberType.IsAssignableFrom(expression.Type)) {
76 throw Error.ArgumentTypesMustMatch();
78 return new MemberAssignment(member, expression);
82 /// Creates a <see cref="MemberAssignment"/> binding the specified value to the given property.
84 /// <param name="propertyAccessor">The <see cref="PropertyInfo"/> for the property which is being assigned to.</param>
85 /// <param name="expression">The value to be assigned to <paramref name="propertyAccessor"/>.</param>
86 /// <returns>The created <see cref="MemberAssignment"/>.</returns>
87 public static MemberAssignment Bind(MethodInfo propertyAccessor, Expression expression) {
88 ContractUtils.RequiresNotNull(propertyAccessor, "propertyAccessor");
89 ContractUtils.RequiresNotNull(expression, "expression");
90 ValidateMethodInfo(propertyAccessor);
91 return Bind(GetProperty(propertyAccessor), expression);
95 private static void ValidateSettableFieldOrPropertyMember(MemberInfo member, out Type memberType) {
96 FieldInfo fi = member as FieldInfo;
98 PropertyInfo pi = member as PropertyInfo;
100 throw Error.ArgumentMustBeFieldInfoOrPropertInfo();
103 throw Error.PropertyDoesNotHaveSetter(pi);
105 memberType = pi.PropertyType;
107 memberType = fi.FieldType;