コード例 #1
0
ファイル: lambda.cs プロジェクト: MilkTool/kiezellisp
        public override DynamicMetaObject BindInvoke(InvokeBinder binder, DynamicMetaObject[] args)
        {
            MethodInfo method = typeof(IApply).GetMethod("Apply");
            var        list   = new List <Expression>();

            foreach (var arg in args)
            {
                list.Add(Runtime.ConvertArgument(arg, typeof(object)));
            }
            var callArg      = Expression.NewArrayInit(typeof(object), list);
            var expr         = Expression.Call(Expression.Convert(Expression, typeof(T)), method, callArg);
            var restrictions = BindingRestrictions.GetTypeRestriction(Expression, typeof(T));

            return(new DynamicMetaObject(Runtime.EnsureObjectResult(expr), restrictions));
        }
コード例 #2
0
        public override DynamicMetaObject FallbackSetIndex(
            DynamicMetaObject target, DynamicMetaObject[] indexes,
            DynamicMetaObject value, DynamicMetaObject errorSuggestion)
        {
            var deferArgs = Runtime.CheckDeferArgs(target, indexes);

            if (deferArgs != null)
            {
                return(Defer(deferArgs));
            }

            if (target.Value == null)
            {
                return(Runtime.CheckTargetNullReference(target, "Cannot set index on null reference: "
                                                        + target.LimitType.FullName + Runtime.CollectParameterInfo(target, indexes)));
            }

            Debug.Assert(target.HasValue && target.LimitType != typeof(Array));
            Type valueType;
            var  indexingExpr = Runtime.GetIndexingExpression(target, indexes, out valueType);

            if (indexingExpr == null)
            {
                return(errorSuggestion ??
                       Runtime.CreateThrow(
                           target, indexes, BindingRestrictions.Empty,
                           typeof(InvalidOperationException),
                           "No set indexer found: " + target.LimitType.FullName + Runtime.CollectParameterInfo(target, indexes)));
            }

            var setIndexExpr = Expression.Assign(indexingExpr, Runtime.ConvertArgument(value, valueType));

            BindingRestrictions restrictions = Runtime.GetTargetArgsRestrictions(target, indexes, false);

            return(new DynamicMetaObject(Runtime.EnsureObjectResult(setIndexExpr), restrictions));
        }
コード例 #3
0
        public override DynamicMetaObject FallbackSetMember(
            DynamicMetaObject target, DynamicMetaObject value,
            DynamicMetaObject errorSuggestion)
        {
            // Used by (set-attr obj name value)

            if (!target.HasValue)
            {
                return(Defer(target));
            }

            var name = Name.LispToPascalCaseName();

            if (target.Value == null)
            {
                var id = target.LimitType.Name + "." + name;
                return(Runtime.CheckTargetNullReference(target, "Cannot set property on null reference:" + id + "(null)"));
            }

            var flags   = BindingFlags.IgnoreCase | BindingFlags.Instance | BindingFlags.Public | BindingFlags.FlattenHierarchy;
            var members = target.LimitType.GetMember(name, flags);

            if (members.Length == 1 && members[0] is PropertyInfo)
            {
                var prop = (PropertyInfo)members[0];
                var val  = Runtime.ConvertArgument(value, prop.PropertyType);
                var expr = Expression.Assign(Expression.MakeMemberAccess(Expression.Convert(target.Expression, prop.DeclaringType), prop), val);
                return(new DynamicMetaObject(Runtime.EnsureObjectResult(expr),
                                             BindingRestrictions.GetTypeRestriction(target.Expression, target.LimitType)));
            }
            else if (members.Length == 1 && members[0] is FieldInfo)
            {
                var field = (FieldInfo)members[0];
                var val   = Runtime.ConvertArgument(value, field.FieldType);
                var expr  = Expression.Assign(Expression.MakeMemberAccess(Expression.Convert(target.Expression, field.DeclaringType), field), val);
                return(new DynamicMetaObject(Runtime.EnsureObjectResult(expr),
                                             BindingRestrictions.GetTypeRestriction(target.Expression, target.LimitType)));
            }
            else if (members.Length == 1 && members[0] is EventInfo)
            {
                //public static void AddEventHandler( System.Reflection.EventInfo eventinfo, object target, object func )

                var evt  = (EventInfo)members[0];
                var expr = Expression.Call(Runtime.AddEventHandlerMethod,
                                           Expression.Constant(evt, typeof(EventInfo)),
                                           Expression.Convert(target.Expression, evt.DeclaringType),
                                           Expression.Convert(value.Expression, typeof(IApply)));
                return(new DynamicMetaObject(Runtime.EnsureObjectResult(expr),
                                             BindingRestrictions.GetTypeRestriction(target.Expression, target.LimitType)));
            }
            else
            {
                return(errorSuggestion ??
                       Runtime.CreateThrow(
                           target, null,
                           BindingRestrictions.GetTypeRestriction(target.Expression,
                                                                  target.LimitType),
                           typeof(MissingMemberException),
                           "Property or field not found: " + target.LimitType.Name + "." + name + Runtime.CollectParameterInfo(target)));
            }
        }