Code:
/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / fx / src / Core / Microsoft / Scripting / Ast / DynamicExpression.cs / 1305376 / DynamicExpression.cs
/* **************************************************************************** * * Copyright (c) Microsoft Corporation. * * This source code is subject to terms and conditions of the Microsoft Public License. A * copy of the license can be found in the License.html file at the root of this distribution. If * you cannot locate the Microsoft Public License, please send an email to * dlr@microsoft.com. By using this source code in any fashion, you are agreeing to be bound * by the terms of the Microsoft Public License. * * You must not remove this notice, or any other, from this software. * * * ***************************************************************************/ using System.Collections.Generic; using System.Collections.ObjectModel; using System.Diagnostics; using System.Dynamic.Utils; using System.Linq.Expressions.Compiler; using System.Reflection; using System.Runtime.CompilerServices; #if SILVERLIGHT using System.Core; #endif namespace System.Linq.Expressions { ////// Represents a dynamic operation. /// #if !SILVERLIGHT [DebuggerTypeProxy(typeof(Expression.DynamicExpressionProxy))] #endif public class DynamicExpression : Expression, IArgumentProvider { private readonly CallSiteBinder _binder; private readonly Type _delegateType; internal DynamicExpression(Type delegateType, CallSiteBinder binder) { Debug.Assert(delegateType.GetMethod("Invoke").GetReturnType() == typeof(object) || GetType() != typeof(DynamicExpression)); _delegateType = delegateType; _binder = binder; } internal static DynamicExpression Make(Type returnType, Type delegateType, CallSiteBinder binder, ReadOnlyCollectionarguments) { if (returnType == typeof(object)) { return new DynamicExpressionN(delegateType, binder, arguments); } else { return new TypedDynamicExpressionN(returnType, delegateType, binder, arguments); } } internal static DynamicExpression Make(Type returnType, Type delegateType, CallSiteBinder binder, Expression arg0) { if (returnType == typeof(object)) { return new DynamicExpression1(delegateType, binder, arg0); } else { return new TypedDynamicExpression1(returnType, delegateType, binder, arg0); } } internal static DynamicExpression Make(Type returnType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1) { if (returnType == typeof(object)) { return new DynamicExpression2(delegateType, binder, arg0, arg1); } else { return new TypedDynamicExpression2(returnType, delegateType, binder, arg0, arg1); } } internal static DynamicExpression Make(Type returnType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2) { if (returnType == typeof(object)) { return new DynamicExpression3(delegateType, binder, arg0, arg1, arg2); } else { return new TypedDynamicExpression3(returnType, delegateType, binder, arg0, arg1, arg2); } } internal static DynamicExpression Make(Type returnType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2, Expression arg3) { if (returnType == typeof(object)) { return new DynamicExpression4(delegateType, binder, arg0, arg1, arg2, arg3); } else { return new TypedDynamicExpression4(returnType, delegateType, binder, arg0, arg1, arg2, arg3); } } /// /// Gets the static type of the expression that this ///represents. /// The public override Type Type { get { return typeof(object); } } ///that represents the static type of the expression. /// Returns the node type of this Expression. Extension nodes should return /// ExpressionType.Extension when overriding this method. /// ///The public sealed override ExpressionType NodeType { get { return ExpressionType.Dynamic; } } ///of the expression. /// Gets the public CallSiteBinder Binder { get { return _binder; } } ///, which determines the runtime behavior of the /// dynamic site. /// /// Gets the type of the delegate used by the public Type DelegateType { get { return _delegateType; } } ///. /// /// Gets the arguments to the dynamic operation. /// public ReadOnlyCollectionArguments { get { return GetOrMakeArguments(); } } internal virtual ReadOnlyCollection GetOrMakeArguments() { throw ContractUtils.Unreachable; } /// /// Dispatches to the specific visit method for this node type. /// protected internal override Expression Accept(ExpressionVisitor visitor) { return visitor.VisitDynamic(this); } ////// Makes a copy of this node replacing the args with the provided values. The /// number of the args needs to match the number of the current block. /// /// This helper is provided to allow re-writing of nodes to not depend on the specific optimized /// subclass of DynamicExpression which is being used. /// internal virtual DynamicExpression Rewrite(Expression[] args) { throw ContractUtils.Unreachable; } ////// Creates a new expression that is like this one, but using the /// supplied children. If all of the children are the same, it will /// return this expression. /// /// Theproperty of the result. /// This expression if no children changed, or an expression with the updated children. public DynamicExpression Update(IEnumerablearguments) { if (arguments == Arguments) { return this; } return Expression.MakeDynamic(DelegateType, Binder, arguments); } #region IArgumentProvider Members Expression IArgumentProvider.GetArgument(int index) { throw ContractUtils.Unreachable; } int IArgumentProvider.ArgumentCount { get { throw ContractUtils.Unreachable; } } #endregion } #region Specialized Subclasses internal class DynamicExpressionN : DynamicExpression, IArgumentProvider { private IList _arguments; // storage for the original IList or readonly collection. See IArgumentProvider for more info. internal DynamicExpressionN(Type delegateType, CallSiteBinder binder, IList arguments) : base(delegateType, binder) { _arguments = arguments; } Expression IArgumentProvider.GetArgument(int index) { return _arguments[index]; } int IArgumentProvider.ArgumentCount { get { return _arguments.Count; } } internal override ReadOnlyCollection GetOrMakeArguments() { return ReturnReadOnly(ref _arguments); } internal override DynamicExpression Rewrite(Expression[] args) { Debug.Assert(args.Length == ((IArgumentProvider)this).ArgumentCount); return Expression.MakeDynamic(DelegateType, Binder, args); } } internal class TypedDynamicExpressionN : DynamicExpressionN { private readonly Type _returnType; internal TypedDynamicExpressionN(Type returnType, Type delegateType, CallSiteBinder binder, IList arguments) : base(delegateType, binder, arguments) { Debug.Assert(delegateType.GetMethod("Invoke").GetReturnType() == returnType); _returnType = returnType; } public sealed override Type Type { get { return _returnType; } } } internal class DynamicExpression1 : DynamicExpression, IArgumentProvider { private object _arg0; // storage for the 1st argument or a readonly collection. See IArgumentProvider for more info. internal DynamicExpression1(Type delegateType, CallSiteBinder binder, Expression arg0) : base(delegateType, binder) { _arg0 = arg0; } Expression IArgumentProvider.GetArgument(int index) { switch (index) { case 0: return ReturnObject (_arg0); default: throw new InvalidOperationException(); } } int IArgumentProvider.ArgumentCount { get { return 1; } } internal override ReadOnlyCollection GetOrMakeArguments() { return ReturnReadOnly(this, ref _arg0); } internal override DynamicExpression Rewrite(Expression[] args) { Debug.Assert(args.Length == 1); return Expression.MakeDynamic(DelegateType, Binder, args[0]); } } internal sealed class TypedDynamicExpression1 : DynamicExpression1 { private readonly Type _retType; internal TypedDynamicExpression1(Type retType, Type delegateType, CallSiteBinder binder, Expression arg0) : base(delegateType, binder, arg0) { _retType = retType; } public sealed override Type Type { get { return _retType; } } } internal class DynamicExpression2 : DynamicExpression, IArgumentProvider { private object _arg0; // storage for the 1st argument or a readonly collection. See IArgumentProvider for more info. private readonly Expression _arg1; // storage for the 2nd argument internal DynamicExpression2(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1) : base(delegateType, binder) { _arg0 = arg0; _arg1 = arg1; } Expression IArgumentProvider.GetArgument(int index) { switch (index) { case 0: return ReturnObject (_arg0); case 1: return _arg1; default: throw new InvalidOperationException(); } } int IArgumentProvider.ArgumentCount { get { return 2; } } internal override ReadOnlyCollection GetOrMakeArguments() { return ReturnReadOnly(this, ref _arg0); } internal override DynamicExpression Rewrite(Expression[] args) { Debug.Assert(args.Length == 2); return Expression.MakeDynamic(DelegateType, Binder, args[0], args[1]); } } internal sealed class TypedDynamicExpression2 : DynamicExpression2 { private readonly Type _retType; internal TypedDynamicExpression2(Type retType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1) : base(delegateType, binder, arg0, arg1) { _retType = retType; } public sealed override Type Type { get { return _retType; } } } internal class DynamicExpression3 : DynamicExpression, IArgumentProvider { private object _arg0; // storage for the 1st argument or a readonly collection. See IArgumentProvider for more info. private readonly Expression _arg1, _arg2; // storage for the 2nd & 3rd arguments internal DynamicExpression3(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2) : base(delegateType, binder) { _arg0 = arg0; _arg1 = arg1; _arg2 = arg2; } Expression IArgumentProvider.GetArgument(int index) { switch (index) { case 0: return ReturnObject (_arg0); case 1: return _arg1; case 2: return _arg2; default: throw new InvalidOperationException(); } } int IArgumentProvider.ArgumentCount { get { return 3; } } internal override ReadOnlyCollection GetOrMakeArguments() { return ReturnReadOnly(this, ref _arg0); } internal override DynamicExpression Rewrite(Expression[] args) { Debug.Assert(args.Length == 3); return Expression.MakeDynamic(DelegateType, Binder, args[0], args[1], args[2]); } } internal sealed class TypedDynamicExpression3 : DynamicExpression3 { private readonly Type _retType; internal TypedDynamicExpression3(Type retType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2) : base(delegateType, binder, arg0, arg1, arg2) { _retType = retType; } public sealed override Type Type { get { return _retType; } } } internal class DynamicExpression4 : DynamicExpression, IArgumentProvider { private object _arg0; // storage for the 1st argument or a readonly collection. See IArgumentProvider for more info. private readonly Expression _arg1, _arg2, _arg3; // storage for the 2nd - 4th arguments internal DynamicExpression4(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2, Expression arg3) : base(delegateType, binder) { _arg0 = arg0; _arg1 = arg1; _arg2 = arg2; _arg3 = arg3; } Expression IArgumentProvider.GetArgument(int index) { switch (index) { case 0: return ReturnObject (_arg0); case 1: return _arg1; case 2: return _arg2; case 3: return _arg3; default: throw new InvalidOperationException(); } } int IArgumentProvider.ArgumentCount { get { return 4; } } internal override ReadOnlyCollection GetOrMakeArguments() { return ReturnReadOnly(this, ref _arg0); } internal override DynamicExpression Rewrite(Expression[] args) { Debug.Assert(args.Length == 4); return Expression.MakeDynamic(DelegateType, Binder, args[0], args[1], args[2], args[3]); } } internal sealed class TypedDynamicExpression4 : DynamicExpression4 { private readonly Type _retType; internal TypedDynamicExpression4(Type retType, Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2, Expression arg3) : base(delegateType, binder, arg0, arg1, arg2, arg3) { _retType = retType; } public sealed override Type Type { get { return _retType; } } } #endregion public partial class Expression { /// /// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided . /// . /// The runtime binder for the dynamic operation. /// The arguments to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, params Expression[] arguments) { return MakeDynamic(delegateType, binder, (IEnumerablethat has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ///)arguments); } /// /// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided . /// . /// The runtime binder for the dynamic operation. /// The arguments to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, IEnumerablethat has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ///arguments) { ContractUtils.RequiresNotNull(delegateType, "delegateType"); ContractUtils.RequiresNotNull(binder, "binder"); if (!delegateType.IsSubclassOf(typeof(Delegate))) throw Error.TypeMustBeDerivedFromSystemDelegate(); var method = GetValidMethodForDynamic(delegateType); var args = arguments.ToReadOnly(); ValidateArgumentTypes(method, ExpressionType.Dynamic, ref args); return DynamicExpression.Make(method.GetReturnType(), delegateType, binder, args); } /// /// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided and one argument. /// . /// The runtime binder for the dynamic operation. /// The argument to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, Expression arg0) { ContractUtils.RequiresNotNull(delegateType, "delegatType"); ContractUtils.RequiresNotNull(binder, "binder"); if (!delegateType.IsSubclassOf(typeof(Delegate))) throw Error.TypeMustBeDerivedFromSystemDelegate(); var method = GetValidMethodForDynamic(delegateType); var parameters = method.GetParametersCached(); ValidateArgumentCount(method, ExpressionType.Dynamic, 2, parameters); ValidateDynamicArgument(arg0); ValidateOneArgument(method, ExpressionType.Dynamic, arg0, parameters[1]); return DynamicExpression.Make(method.GetReturnType(), delegateType, binder, arg0); } ///that has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ////// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided and two arguments. /// . /// The runtime binder for the dynamic operation. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1) { ContractUtils.RequiresNotNull(delegateType, "delegatType"); ContractUtils.RequiresNotNull(binder, "binder"); if (!delegateType.IsSubclassOf(typeof(Delegate))) throw Error.TypeMustBeDerivedFromSystemDelegate(); var method = GetValidMethodForDynamic(delegateType); var parameters = method.GetParametersCached(); ValidateArgumentCount(method, ExpressionType.Dynamic, 3, parameters); ValidateDynamicArgument(arg0); ValidateOneArgument(method, ExpressionType.Dynamic, arg0, parameters[1]); ValidateDynamicArgument(arg1); ValidateOneArgument(method, ExpressionType.Dynamic, arg1, parameters[2]); return DynamicExpression.Make(method.GetReturnType(), delegateType, binder, arg0, arg1); } ///that has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ////// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided and three arguments. /// . /// The runtime binder for the dynamic operation. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. /// The third argument to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2) { ContractUtils.RequiresNotNull(delegateType, "delegatType"); ContractUtils.RequiresNotNull(binder, "binder"); if (!delegateType.IsSubclassOf(typeof(Delegate))) throw Error.TypeMustBeDerivedFromSystemDelegate(); var method = GetValidMethodForDynamic(delegateType); var parameters = method.GetParametersCached(); ValidateArgumentCount(method, ExpressionType.Dynamic, 4, parameters); ValidateDynamicArgument(arg0); ValidateOneArgument(method, ExpressionType.Dynamic, arg0, parameters[1]); ValidateDynamicArgument(arg1); ValidateOneArgument(method, ExpressionType.Dynamic, arg1, parameters[2]); ValidateDynamicArgument(arg2); ValidateOneArgument(method, ExpressionType.Dynamic, arg2, parameters[3]); return DynamicExpression.Make(method.GetReturnType(), delegateType, binder, arg0, arg1, arg2); } ///that has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ////// Creates a /// The type of the delegate used by thethat represents a dynamic operation bound by the provided and four arguments. /// . /// The runtime binder for the dynamic operation. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. /// The third argument to the dynamic operation. /// The fourth argument to the dynamic operation. /// /// A public static DynamicExpression MakeDynamic(Type delegateType, CallSiteBinder binder, Expression arg0, Expression arg1, Expression arg2, Expression arg3) { ContractUtils.RequiresNotNull(delegateType, "delegatType"); ContractUtils.RequiresNotNull(binder, "binder"); if (!delegateType.IsSubclassOf(typeof(Delegate))) throw Error.TypeMustBeDerivedFromSystemDelegate(); var method = GetValidMethodForDynamic(delegateType); var parameters = method.GetParametersCached(); ValidateArgumentCount(method, ExpressionType.Dynamic, 5, parameters); ValidateDynamicArgument(arg0); ValidateOneArgument(method, ExpressionType.Dynamic, arg0, parameters[1]); ValidateDynamicArgument(arg1); ValidateOneArgument(method, ExpressionType.Dynamic, arg1, parameters[2]); ValidateDynamicArgument(arg2); ValidateOneArgument(method, ExpressionType.Dynamic, arg2, parameters[3]); ValidateDynamicArgument(arg3); ValidateOneArgument(method, ExpressionType.Dynamic, arg3, parameters[4]); return DynamicExpression.Make(method.GetReturnType(), delegateType, binder, arg0, arg1, arg2, arg3); } private static MethodInfo GetValidMethodForDynamic(Type delegateType) { var method = delegateType.GetMethod("Invoke"); var pi = method.GetParametersCached(); if (pi.Length == 0 || pi[0].ParameterType != typeof(CallSite)) throw Error.FirstArgumentMustBeCallSite(); return method; } ///that has equal to /// Dynamic and has the ///DelegateType , ///Binder , and ///Arguments set to the specified values. ////// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The arguments to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, params Expression[] arguments) { return Dynamic(binder, returnType, (IEnumerableDelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ///)arguments); } /// /// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The first argument to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, Expression arg0) { ContractUtils.RequiresNotNull(binder, "binder"); ValidateDynamicArgument(arg0); DelegateHelpers.TypeInfo info = DelegateHelpers.GetNextTypeInfo( returnType, DelegateHelpers.GetNextTypeInfo( arg0.Type, DelegateHelpers.NextTypeInfo(typeof(CallSite)) ) ); Type delegateType = info.DelegateType; if (delegateType == null) { delegateType = info.MakeDelegateType(returnType, arg0); } return DynamicExpression.Make(returnType, delegateType, binder, arg0); } ///DelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ////// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, Expression arg0, Expression arg1) { ContractUtils.RequiresNotNull(binder, "binder"); ValidateDynamicArgument(arg0); ValidateDynamicArgument(arg1); DelegateHelpers.TypeInfo info = DelegateHelpers.GetNextTypeInfo( returnType, DelegateHelpers.GetNextTypeInfo( arg1.Type, DelegateHelpers.GetNextTypeInfo( arg0.Type, DelegateHelpers.NextTypeInfo(typeof(CallSite)) ) ) ); Type delegateType = info.DelegateType; if (delegateType == null) { delegateType = info.MakeDelegateType(returnType, arg0, arg1); } return DynamicExpression.Make(returnType, delegateType, binder, arg0, arg1); } ///DelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ////// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. /// The third argument to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, Expression arg0, Expression arg1, Expression arg2) { ContractUtils.RequiresNotNull(binder, "binder"); ValidateDynamicArgument(arg0); ValidateDynamicArgument(arg1); ValidateDynamicArgument(arg2); DelegateHelpers.TypeInfo info = DelegateHelpers.GetNextTypeInfo( returnType, DelegateHelpers.GetNextTypeInfo( arg2.Type, DelegateHelpers.GetNextTypeInfo( arg1.Type, DelegateHelpers.GetNextTypeInfo( arg0.Type, DelegateHelpers.NextTypeInfo(typeof(CallSite)) ) ) ) ); Type delegateType = info.DelegateType; if (delegateType == null) { delegateType = info.MakeDelegateType(returnType, arg0, arg1, arg2); } return DynamicExpression.Make(returnType, delegateType, binder, arg0, arg1, arg2); } ///DelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ////// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The first argument to the dynamic operation. /// The second argument to the dynamic operation. /// The third argument to the dynamic operation. /// The fourth argument to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, Expression arg0, Expression arg1, Expression arg2, Expression arg3) { ContractUtils.RequiresNotNull(binder, "binder"); ValidateDynamicArgument(arg0); ValidateDynamicArgument(arg1); ValidateDynamicArgument(arg2); ValidateDynamicArgument(arg3); DelegateHelpers.TypeInfo info = DelegateHelpers.GetNextTypeInfo( returnType, DelegateHelpers.GetNextTypeInfo( arg3.Type, DelegateHelpers.GetNextTypeInfo( arg2.Type, DelegateHelpers.GetNextTypeInfo( arg1.Type, DelegateHelpers.GetNextTypeInfo( arg0.Type, DelegateHelpers.NextTypeInfo(typeof(CallSite)) ) ) ) ) ); Type delegateType = info.DelegateType; if (delegateType == null) { delegateType = info.MakeDelegateType(returnType, arg0, arg1, arg2, arg3); } return DynamicExpression.Make(returnType, delegateType, binder, arg0, arg1, arg2, arg3); } ///DelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ////// Creates a /// The runtime binder for the dynamic operation. /// The result type of the dynamic expression. /// The arguments to the dynamic operation. ///that represents a dynamic operation bound by the provided . /// /// A ///that has equal to /// Dynamic and has the ///Binder and ///Arguments set to the specified values. ////// The public static DynamicExpression Dynamic(CallSiteBinder binder, Type returnType, IEnumerableDelegateType property of the /// result will be inferred from the types of the arguments and the specified return type. ///arguments) { ContractUtils.RequiresNotNull(arguments, "arguments"); ContractUtils.RequiresNotNull(returnType, "returnType"); var args = arguments.ToReadOnly(); ContractUtils.RequiresNotEmpty(args, "args"); return MakeDynamic(binder, returnType, args); } private static DynamicExpression MakeDynamic(CallSiteBinder binder, Type returnType, ReadOnlyCollection args) { ContractUtils.RequiresNotNull(binder, "binder"); for (int i = 0; i < args.Count; i++) { Expression arg = args[i]; ValidateDynamicArgument(arg); } Type delegateType = DelegateHelpers.MakeCallSiteDelegate(args, returnType); // Since we made a delegate with argument types that exactly match, // we can skip delegate and argument validation switch (args.Count) { case 1: return DynamicExpression.Make(returnType, delegateType, binder, args[0]); case 2: return DynamicExpression.Make(returnType, delegateType, binder, args[0], args[1]); case 3: return DynamicExpression.Make(returnType, delegateType, binder, args[0], args[1], args[2]); case 4: return DynamicExpression.Make(returnType, delegateType, binder, args[0], args[1], args[2], args[3]); default: return DynamicExpression.Make(returnType, delegateType, binder, args); } } private static void ValidateDynamicArgument(Expression arg) { RequiresCanRead(arg, "arguments"); var type = arg.Type; ContractUtils.RequiresNotNull(type, "type"); TypeUtils.ValidateType(type); if (type == typeof(void)) throw Error.ArgumentTypeCannotBeVoid(); } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- DesignTimeResourceProviderFactoryAttribute.cs
- TreeViewBindingsEditorForm.cs
- IDictionary.cs
- RegexReplacement.cs
- TrackingParticipant.cs
- PointLightBase.cs
- GridViewUpdatedEventArgs.cs
- AssemblyResourceLoader.cs
- OutputCache.cs
- ResourceProviderFactory.cs
- MatrixValueSerializer.cs
- TextContainerChangeEventArgs.cs
- Timer.cs
- FilterableAttribute.cs
- IntMinMaxAggregationOperator.cs
- DebugView.cs
- WorkflowRuntime.cs
- AttributeCollection.cs
- RepeatBehavior.cs
- ResXDataNode.cs
- hwndwrapper.cs
- XpsFilter.cs
- DataControlImageButton.cs
- XslTransform.cs
- EntityContainerEntitySet.cs
- LinqDataSourceStatusEventArgs.cs
- SessionStateSection.cs
- TextRange.cs
- UrlMapping.cs
- TraceHelpers.cs
- PixelFormatConverter.cs
- InternalConfigConfigurationFactory.cs
- RequestUriProcessor.cs
- PointHitTestResult.cs
- Ref.cs
- WsdlExporter.cs
- ThreadAbortException.cs
- Serializer.cs
- MessageUtil.cs
- DataBindEngine.cs
- Canvas.cs
- recordstatescratchpad.cs
- DataGridViewAdvancedBorderStyle.cs
- LowerCaseStringConverter.cs
- Effect.cs
- OptimalTextSource.cs
- EventLogEntry.cs
- CodeGenerator.cs
- PixelFormat.cs
- PersonalizationStateQuery.cs
- COM2Enum.cs
- DbConnectionFactory.cs
- RefreshPropertiesAttribute.cs
- ManageRequest.cs
- DebugInfoExpression.cs
- ResourceContainerWrapper.cs
- TableChangeProcessor.cs
- IdleTimeoutMonitor.cs
- XPathNodePointer.cs
- DataServiceException.cs
- UserControl.cs
- CharEntityEncoderFallback.cs
- XmlJsonWriter.cs
- RC2.cs
- ExtentKey.cs
- SimpleMailWebEventProvider.cs
- MDIWindowDialog.cs
- WorkflowInstance.cs
- ColorTranslator.cs
- SuppressIldasmAttribute.cs
- BaseTemplateCodeDomTreeGenerator.cs
- CultureMapper.cs
- DrawTreeNodeEventArgs.cs
- Internal.cs
- StylusDevice.cs
- WebPartVerbsEventArgs.cs
- IPPacketInformation.cs
- BaseCodeDomTreeGenerator.cs
- AmbientValueAttribute.cs
- RemotingConfiguration.cs
- FormatConvertedBitmap.cs
- SystemGatewayIPAddressInformation.cs
- SizeConverter.cs
- RewritingSimplifier.cs
- PackageStore.cs
- SqlClientPermission.cs
- LineBreak.cs
- StoragePropertyMapping.cs
- ResourceSetExpression.cs
- SHA384Managed.cs
- FieldToken.cs
- XpsDigitalSignature.cs
- Clipboard.cs
- XmlCharacterData.cs
- ConfigXmlCDataSection.cs
- OleAutBinder.cs
- DotExpr.cs
- SeparatorAutomationPeer.cs
- WorkflowStateRollbackService.cs
- AsyncContentLoadedEventArgs.cs