示例#1
0
        internal SSMethodInfo(MethodInfo methodInfo)
        {
            this.Id            = methodInfo.Name;
            this.Signature     = MemberSignature.GetSignature(methodInfo);
            this.DeclaringType = HybTypeCache.GetHybType(methodInfo.DeclaringType);
            this.Target        = new Invokable(methodInfo);

            this.ReturnType = HybTypeCache.GetHybType(methodInfo.ReturnType);
            this.IsVaArg    =
                methodInfo.GetParameters().LastOrDefault()
                ?.IsDefined(typeof(ParamArrayAttribute), false) ?? false;

            var ps = methodInfo.GetParameters();

            this.Parameters = new SSParamInfo[ps.Length];
            for (int i = 0; i < this.Parameters.Length; i++)
            {
                var p = ps[i];
                this.Parameters[i] = new SSParamInfo()
                {
                    Id           = p.Name,
                    DefaultValue = p.HasDefaultValue ? HybInstance.Object(p.DefaultValue) : null,
                    IsParams     = this.IsVaArg && i == this.Parameters.Length - 1
                };
            }
        }
示例#2
0
        internal SSCompiledFieldInfo(FieldInfo field)
        {
            this.Origin    = SSMemberOrigin.InterpretScript;
            this.FieldType = HybTypeCache.GetHybType(field.FieldType);
            this.fieldInfo = field;

            this.IsStatic = field.IsStatic;
        }
示例#3
0
 public static HybInstance Object(object o)
 {
     if (o == null)
     {
         return(Null());
     }
     if (o is HybInstance hyb)
     {
         return(hyb);
     }
     return(new HybInstance(HybTypeCache.GetHybType(o.GetType()), o));
 }
示例#4
0
        public HybType MakeGenericType(HybType[] genericArgs)
        {
            if (genericArgs == null)
            {
                throw new ArgumentNullException(nameof(genericArgs));
            }

            if (IsCompiledType)
            {
                return(HybTypeCache.GetHybType(CompiledType.MakeGenericType(genericArgs.Unwrap())));
            }
            return(null);
        }
示例#5
0
 private HybType FindTypeFromAssembly(string id, Assembly assembly)
 {
     foreach (var type in assembly.GetTypesSafe())
     {
         if (type.Name == id &&
             namespaces.Contains(type.Namespace))
         {
             return(HybTypeCache.GetHybType(type));
         }
         if (type.FullName == id)
         {
             return(HybTypeCache.GetHybType(type));
         }
     }
     return(null);
 }
示例#6
0
        public HybType MakeArrayType(int rank)
        {
            if (rank < 1)
            {
                throw new ArgumentException(nameof(rank));
            }

            if (IsCompiledType)
            {
                if (rank == 1)
                {
                    return(HybTypeCache.GetHybType(CompiledType.MakeArrayType()));
                }
                return(HybTypeCache.GetHybType(CompiledType.MakeArrayType(rank)));
            }
            return(new HybType(InterpretKlass, this, ArrayRank));
        }
示例#7
0
        public virtual HybType GetGenericType(string id, int n)
        {
            id = $"{id}`{n}";

            foreach (var asm in Assemblies)
            {
                foreach (var type in asm.GetTypesSafe())
                {
                    if (type.Name.Split('[')[0] == id)
                    {
                        return(HybTypeCache.GetHybType(type));
                    }
                    if (type.FullName.Split('[')[0] == id)
                    {
                        return(HybTypeCache.GetHybType(type));
                    }
                }
            }

            return(null);
        }
示例#8
0
 public void CacheType(Type type)
 {
     cache[type.Name] = HybTypeCache.GetHybType(type);
 }
示例#9
0
        public static SSMethodInfo FindMethodWithArguments(
            TypeResolver resolver, SSMethodInfo[] members,
            HybType[] implicitGenercArgs,
            ref HybInstance[] args)
        {
            var originalArgs = (HybInstance[])args.Clone();

            foreach (var member in members)
            {
                if (member.Target.IsCompiled)
                {
                    args = originalArgs;

                    var genericBound = new Dictionary <string, Type>();
                    var genericArgs  = new List <HybType>(implicitGenercArgs);
                    var method       = member.Target.CompiledMethod;
                    var ps           = method.GetParameters();

                    if (args.Length > ps.Length)
                    {
                        continue;
                    }

                    bool match = true;
                    for (int i = 0; i < ps.Length; i++)
                    {
                        var p = ps[i].ParameterType;

                        if (args.Length <= i)
                        {
                            if (ps[i].IsOptional == false)
                            {
                                match = false;
                                break;
                            }
                            continue;
                        }

                        if (p.IsByRef)
                        {
                            p = p.GetElementType();
                        }

                        if (args[i] == null || args[i].IsNull())
                        {
                            if (p.IsValueType)
                            {
                                match = false;
                                break;
                            }
                            continue;
                        }

                        var argType = args[i].GetHybType();
                        if (!p.IsAssignableFromEx(argType, genericBound))
                        {
                            // Second change,
                            // Check whether parent can be assignable
                            if (args[i].IsVirtualDerived &&
                                p.IsAssignableFromEx(args[i].Parent.GetHybType(), genericBound))
                            {
                                args[i] = args[i].Parent;
                            }
                            else
                            {
                                match = false;
                                break;
                            }
                        }

                        if (p.IsGenericType || p.IsGenericTypeDefinition)
                        {
                            /*
                             * if (argType.isCompiledType)
                             * {
                             *  genericArgs.AddRange(
                             *      genericBound.Select(x => new HybType(x)));
                             * }
                             * else
                             *  genericArgs.Add(new HybType(typeof(HybInstance)));
                             */
                        }
                    }
                    if (match == false)
                    {
                        continue;
                    }

                    var methodGenericArgs = member.GetGenericArgumentsFromDefinition();
                    if (methodGenericArgs.Length > 0)
                    {
                        foreach (var arg in methodGenericArgs)
                        {
                            if (genericBound.ContainsKey(arg.Name))
                            {
                                genericArgs.Add(HybTypeCache.GetHybType(genericBound[arg.Name]));
                            }
                        }

                        if (methodGenericArgs.Length != genericArgs.Count)
                        {
                            throw new SemanticViolationException($"Insufficient generic arguments for `{member.Id}`");
                        }

                        return(member.MakeGenericMethod(genericArgs.ToArray()));
                    }
                    return(member);
                }
                else
                {
                    var ps = member.Target.InterpretMethod.ParameterList.Parameters;

                    if (member.IsVaArg == false &&
                        args.Length > ps.Count)
                    {
                        continue;
                    }

                    var match = true;
                    for (int i = 0; i < ps.Count; i++)
                    {
                        var p         = ps[i];
                        var paramType = resolver.GetType($"{p.Type}");

                        if (p.Modifiers.IsParams())
                        {
                            break;
                        }
                        if (args.Length <= i)
                        {
                            if (p.Default == null)
                            {
                                match = false;
                                break;
                            }
                            continue;
                        }

                        var argType = args[i].GetHybType();

                        if (paramType.IsAssignableFrom(argType) == false)
                        {
                            match = false;
                            break;
                        }
                    }

                    if (match == false)
                    {
                        continue;
                    }

                    return(member);
                }
            }

            return(null);
        }
示例#10
0
 internal SSCompiledPropertyInfo(PropertyInfo property)
 {
     this.Type      = HybTypeCache.GetHybType(property.PropertyType);
     this.GetMethod = property.CanRead ? new SSCompiledMethodInfo(property.GetMethod) : null;
     this.SetMethod = property.CanWrite ? new SSCompiledMethodInfo(property.SetMethod) : null;
 }
示例#11
0
        private HybInstance RunParenthesizedLambda(ParenthesizedLambdaExpressionSyntax node)
        {
            // Detects the lambda is `Func` or `Action`.
            var hasReturn = node.DescendantNodes()
                            .Any(x => x is ReturnStatementSyntax);
            var ps      = node.ParameterList.Parameters;
            var retType = TypeDeduction.GetReturnType(Resolver, node.Body);

            MethodInfo converter = null;
            object     body      = null;

            // `Func`
            if (hasReturn)
            {
                converter = GetConverterF(ps.Count);

                var genericArgs = new Type[ps.Count + 1];
                for (int i = 0; i < ps.Count; i++)
                {
                    if (ps[i].Type == null)
                    {
                        throw new SemanticViolationException("Please provide a explicit type to all lambda parameters, this function is partialy implemented.");
                    }
                    genericArgs[i] = Resolver
                                     .GetType($"{ps[i].Type}")
                                     .Unwrap();
                }
                genericArgs[genericArgs.Length - 1] = retType.Unwrap();
                converter = converter
                            .MakeGenericMethod(genericArgs);

                if (ps.Count == 0)
                {
                    body = new Func <object>(() => {
                        RunBlock(node.Body as BlockSyntax);
                        if (Halt == HaltType.Return)
                        {
                            Halt = HaltType.None;
                        }
                        return(Ret.Unwrap());
                    });
                }
                else if (ps.Count == 1)
                {
                    body = new Func <object, object>((a) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a));
                    });
                }
                else if (ps.Count == 2)
                {
                    body = new Func <object, object, object>((a, b) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b));
                    });
                }
                else if (ps.Count == 3)
                {
                    body = new Func <object, object, object, object>((a, b, c) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b, c));
                    });
                }
                else if (ps.Count == 4)
                {
                    body = new Func <object, object, object, object, object>((a, b, c, d) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b, c, d));
                    });
                }
                else if (ps.Count == 5)
                {
                    body = new Func <object, object, object, object, object, object>((a, b, c, d, e) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b, c, d, e));
                    });
                }
                else if (ps.Count == 6)
                {
                    body = new Func <object, object, object, object, object, object, object>((a, b, c, d, e, f) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b, c, d, e, f));
                    });
                }
                else if (ps.Count == 7)
                {
                    body = new Func <object, object, object, object, object, object, object, object>((a, b, c, d, e, f, g) => {
                        return(FuncBody(ps, node.Body as BlockSyntax, a, b, c, d, e, f, g));
                    });
                }
            }
            // `Action`
            else
            {
                converter = GetConverterA(ps.Count);

                var genericArgs = new Type[ps.Count];
                for (int i = 0; i < ps.Count; i++)
                {
                    if (ps[i].Type == null)
                    {
                        throw new SemanticViolationException("Please provide a explicit type to all lambda parameters, this function is partialy implemented.");
                    }
                    genericArgs[i] = Resolver
                                     .GetType($"{ps[i].Type}")
                                     .Unwrap();
                }

                if (ps.Count > 0)
                {
                    converter = converter
                                .MakeGenericMethod(genericArgs);
                }

                if (ps.Count == 0)
                {
                    body = new Action(() => {
                        RunBlock(node.Body as BlockSyntax);
                        if (Halt == HaltType.Return)
                        {
                            Halt = HaltType.None;
                        }
                    });
                }
                else if (ps.Count == 1)
                {
                    body = new Action <object>((a) => {
                        ActionBody(ps, node.Body as BlockSyntax, a);
                    });
                }
                else if (ps.Count == 2)
                {
                    body = new Action <object, object>((a, b) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b);
                    });
                }
                else if (ps.Count == 3)
                {
                    body = new Action <object, object, object>((a, b, c) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b, c);
                    });
                }
                else if (ps.Count == 4)
                {
                    body = new Action <object, object, object, object>((a, b, c, d) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b, c, d);
                    });
                }
                else if (ps.Count == 5)
                {
                    body = new Action <object, object, object, object, object>((a, b, c, d, e) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b, c, d, e);
                    });
                }
                else if (ps.Count == 6)
                {
                    body = new Action <object, object, object, object, object, object>((a, b, c, d, e, f) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b, c, d, e, f);
                    });
                }
                else if (ps.Count == 7)
                {
                    body = new Action <object, object, object, object, object, object, object>((a, b, c, d, e, f, g) => {
                        ActionBody(ps, node.Body as BlockSyntax, a, b, c, d, e, f, g);
                    });
                }
            }

            var convertedDelegate = converter.Invoke(
                null, new object[] { body });

            return(new HybInstance(
                       HybTypeCache.GetHybType(convertedDelegate.GetType()),
                       convertedDelegate));
        }