MaybeType() private method

private MaybeType ( object form, bool stringOk ) : Type
form object
stringOk bool
return System.Type
Example #1
0
        public InvokeExpr(string source, IPersistentMap spanMap, Symbol tag, Expr fexpr, IPersistentVector args, bool tailPosition)
        {
            _source       = source;
            _spanMap      = spanMap;
            _fexpr        = fexpr;
            _args         = args;
            _tailPosition = tailPosition;

            VarExpr varFexpr = fexpr as VarExpr;

            if (varFexpr != null)
            {
                Var fvar = varFexpr.Var;
                Var pvar = (Var)RT.get(fvar.meta(), Compiler.ProtocolKeyword);
                if (pvar != null && Compiler.ProtocolCallsitesVar.isBound)
                {
                    _isProtocol = true;
                    _siteIndex  = Compiler.RegisterProtocolCallsite(fvar);
                    Object pon = RT.get(pvar.get(), _onKey);
                    _protocolOn = HostExpr.MaybeType(pon, false);
                    if (_protocolOn != null)
                    {
                        IPersistentMap mmap    = (IPersistentMap)RT.get(pvar.get(), _methodMapKey);
                        Keyword        mmapVal = (Keyword)mmap.valAt(Keyword.intern(fvar.sym));
                        if (mmapVal == null)
                        {
                            throw new ArgumentException(String.Format("No method of interface: {0} found for function: {1} of protocol: {2} (The protocol method may have been defined before and removed.)",
                                                                      _protocolOn.FullName, fvar.Symbol, pvar.Symbol));
                        }
                        String mname = Compiler.munge(mmapVal.Symbol.ToString());

                        IList <MethodBase> methods = Reflector.GetMethods(_protocolOn, mname, null, args.count() - 1, false);
                        if (methods.Count != 1)
                        {
                            throw new ArgumentException(String.Format("No single method: {0} of interface: {1} found for function: {2} of protocol: {3}",
                                                                      mname, _protocolOn.FullName, fvar.Symbol, pvar.Symbol));
                        }
                        _onMethod = (MethodInfo)methods[0];
                    }
                }
            }

            if (tag != null)
            {
                _tag = tag;
            }
            else if (varFexpr != null)
            {
                Var v = varFexpr.Var;

                //object arglists = RT.get(RT.meta(v), Compiler.ArglistsKeyword);
                object sigTag = SigTag(_args.count(), v);
                _tag = sigTag ?? varFexpr.Tag;
            }
            else
            {
                _tag = null;
            }
        }
Example #2
0
        static List <Type> ParseGenericMethodTypeArgs(ISeq targs)
        {
            List <Type> types = new List <Type>();

            for (ISeq s = targs; s != null; s = s.next())
            {
                object arg = s.first();
                if (!(arg is Symbol))
                {
                    throw new ArgumentException("Malformed generic method designator: type arg must be a Symbol");
                }
                Type t = HostExpr.MaybeType(arg, false);
                if (t == null)
                {
                    throw new ArgumentException("Malformed generic method designator: invalid type arg");
                }
                types.Add(t);
            }

            return(types);
        }
Example #3
0
            public Expr Parse(ParserContext pcon, object frm)
            {
                //int line = (int)Compiler.LINE.deref();

                ISeq form = (ISeq)frm;

                // form => (new Typename args ... )

                if (form.count() < 2)
                {
                    throw new ParseException("wrong number of arguments, expecting: (new Typename args ...)");
                }

                Type t = HostExpr.MaybeType(RT.second(form), false);

                if (t == null)
                {
                    throw new ParseException("Unable to resolve classname: " + RT.second(form));
                }

                List <HostArg> args = HostExpr.ParseArgs(pcon, RT.next(RT.next(form)));

                return(new NewExpr(t, args, (IPersistentMap)Compiler.SourceSpanVar.deref()));
            }
Example #4
0
        public static Expr Parse(ParserContext pcon, ISeq form)
        {
            pcon = pcon.EvalOrExpr();

            Expr    fexpr    = Compiler.Analyze(pcon, form.first());
            VarExpr varFexpr = fexpr as VarExpr;

            if (varFexpr != null && varFexpr.Var.Equals(Compiler.InstanceVar))
            {
                if (RT.second(form) is Symbol)
                {
                    Type t = HostExpr.MaybeType(RT.second(form), false);
                    if (t != null)
                    {
                        return(new InstanceOfExpr((string)Compiler.SourceVar.deref(), (IPersistentMap)Compiler.SourceSpanVar.deref(), t, Compiler.Analyze(pcon, RT.third(form))));
                    }
                }
            }

            if (varFexpr != null && pcon.Rhc != RHC.Eval)
            {
                Var    v        = varFexpr.Var;
                object arglists = RT.get(RT.meta(v), Compiler.ArglistsKeyword);
                int    arity    = RT.count(form.next());
                for (ISeq s = RT.seq(arglists); s != null; s = s.next())
                {
                    IPersistentVector sargs = (IPersistentVector)s.first();
                    if (sargs.count() == arity)
                    {
                        string primc = FnMethod.PrimInterface(sargs);
                        if (primc != null)
                        {
                            return(Compiler.Analyze(pcon,
                                                    RT.listStar(Symbol.intern(".invokePrim"),
                                                                ((Symbol)form.first()).withMeta(RT.map(RT.TagKey, Symbol.intern(primc))),
                                                                form.next())));
                        }
                        break;
                    }
                }
            }

            KeywordExpr kwFexpr = fexpr as KeywordExpr;

            if (kwFexpr != null && RT.count(form) == 2 && Compiler.KeywordCallsitesVar.isBound)
            {
                Expr target = Compiler.Analyze(pcon, RT.second(form));
                return(new KeywordInvokeExpr((string)Compiler.SourceVar.deref(), (IPersistentMap)Compiler.SourceSpanVar.deref(), Compiler.TagOf(form), kwFexpr, target));
            }

            IPersistentVector args = PersistentVector.EMPTY;

            for (ISeq s = RT.seq(form.next()); s != null; s = s.next())
            {
                args = args.cons(Compiler.Analyze(pcon, s.first()));
            }

            //if (args.count() > Compiler.MAX_POSITIONAL_ARITY)
            //    throw new ArgumentException(String.Format("No more than {0} args supported", Compiler.MAX_POSITIONAL_ARITY));

            return(new InvokeExpr((string)Compiler.SourceVar.deref(),
                                  (IPersistentMap)Compiler.SourceSpanVar.deref(), //Compiler.GetSourceSpanMap(form),
                                  Compiler.TagOf(form),
                                  fexpr,
                                  args));
        }
Example #5
0
            public Expr Parse(ParserContext pcon, object form)
            {
                ISeq sform = (ISeq)form;

                // form is one of:
                //  (. x fieldname-sym)
                //  (. x 0-ary-method)
                //  (. x propertyname-sym)
                //  (. x methodname-sym args)+
                //  (. x (methodname-sym args?))
                //  (. x (generic-m

                if (RT.Length(sform) < 3)
                {
                    throw new ParseException("Malformed member expression, expecting (. target member ... )");
                }

                string         source  = (string)Compiler.SourceVar.deref();
                IPersistentMap spanMap = (IPersistentMap)Compiler.SourceSpanVar.deref();  // Compiler.GetSourceSpanMap(form);

                Symbol tag = Compiler.TagOf(sform);

                // determine static or instance
                // static target must be symbol, either fully.qualified.Typename or Typename that has been imported

                Type t = HostExpr.MaybeType(RT.second(sform), false);
                // at this point, t will be non-null if static

                Expr instance = null;

                if (t == null)
                {
                    instance = Compiler.Analyze(pcon.EvalOrExpr(), RT.second(sform));
                }

                bool isZeroArityCall = RT.Length(sform) == 3 && RT.third(sform) is Symbol;

                if (isZeroArityCall)
                {
                    PropertyInfo pinfo = null;
                    FieldInfo    finfo = null;

                    // TODO: Figure out if we want to handle the -propname otherwise.

                    bool   isPropName = false;
                    Symbol sym        = (Symbol)RT.third(sform);
                    if (sym.Name[0] == '-')
                    {
                        isPropName = true;
                        sym        = Symbol.intern(sym.Name.Substring(1));
                    }

                    string fieldName = Compiler.munge(sym.Name);
                    // The JVM version does not have to worry about Properties.  It captures 0-arity methods under fields.
                    // We have to put in special checks here for this.
                    // Also, when reflection is required, we have to capture 0-arity methods under the calls that
                    //   are generated by StaticFieldExpr and InstanceFieldExpr.
                    if (t != null)
                    {
                        if ((finfo = Reflector.GetField(t, fieldName, true)) != null)
                        {
                            return(new StaticFieldExpr(source, spanMap, tag, t, fieldName, finfo));
                        }
                        if ((pinfo = Reflector.GetProperty(t, fieldName, true)) != null)
                        {
                            return(new StaticPropertyExpr(source, spanMap, tag, t, fieldName, pinfo));
                        }
                        if (!isPropName && Reflector.GetArityZeroMethod(t, fieldName, true) != null)
                        {
                            return(new StaticMethodExpr(source, spanMap, tag, t, fieldName, null, new List <HostArg>()));
                        }
                        throw new MissingMemberException(t.Name, fieldName);
                    }
                    else if (instance != null && instance.HasClrType && instance.ClrType != null)
                    {
                        Type instanceType = instance.ClrType;
                        if ((finfo = Reflector.GetField(instanceType, fieldName, false)) != null)
                        {
                            return(new InstanceFieldExpr(source, spanMap, tag, instance, fieldName, finfo));
                        }
                        if ((pinfo = Reflector.GetProperty(instanceType, fieldName, false)) != null)
                        {
                            return(new InstancePropertyExpr(source, spanMap, tag, instance, fieldName, pinfo));
                        }
                        if (!isPropName && Reflector.GetArityZeroMethod(instanceType, fieldName, false) != null)
                        {
                            return(new InstanceMethodExpr(source, spanMap, tag, instance, fieldName, null, new List <HostArg>()));
                        }
                        if (pcon.IsAssignContext)
                        {
                            return(new InstanceFieldExpr(source, spanMap, tag, instance, fieldName, null)); // same as InstancePropertyExpr when last arg is null
                        }
                        else
                        {
                            return(new InstanceZeroArityCallExpr(source, spanMap, tag, instance, fieldName));
                        }
                    }
                    else
                    {
                        //  t is null, so we know this is not a static call
                        //  If instance is null, we are screwed anyway.
                        //  If instance is not null, then we don't have a type.
                        //  So we must be in an instance call to a property, field, or 0-arity method.
                        //  The code generated by InstanceFieldExpr/InstancePropertyExpr with a null FieldInfo/PropertyInfo
                        //     will generate code to do a runtime call to a Reflector method that will check all three.
                        //return new InstanceFieldExpr(source, spanMap, tag, instance, fieldName, null); // same as InstancePropertyExpr when last arg is null
                        //return new InstanceZeroArityCallExpr(source, spanMap, tag, instance, fieldName);
                        if (pcon.IsAssignContext)
                        {
                            return(new InstanceFieldExpr(source, spanMap, tag, instance, fieldName, null)); // same as InstancePropertyExpr when last arg is null
                        }
                        else
                        {
                            return(new InstanceZeroArityCallExpr(source, spanMap, tag, instance, fieldName));
                        }
                    }
                }

                //ISeq call = RT.third(form) is ISeq ? (ISeq)RT.third(form) : RT.next(RT.next(form));

                ISeq        call;
                List <Type> typeArgs = null;

                object fourth = RT.fourth(sform);

                if (fourth is ISeq && RT.first(fourth) is Symbol && ((Symbol)RT.first(fourth)).Equals(TypeArgsSym))
                {
                    // We have a type args supplied for a generic method call
                    // (. thing methodname (type-args type1 ... ) args ...)
                    typeArgs = ParseGenericMethodTypeArgs(RT.next(fourth));
                    call     = RT.listStar(RT.third(sform), RT.next(RT.next(RT.next(RT.next(sform)))));
                }
                else
                {
                    call = RT.third(sform) is ISeq ? (ISeq)RT.third(sform) : RT.next(RT.next(sform));
                }

                if (!(RT.first(call) is Symbol))
                {
                    throw new ParseException("Malformed member exception");
                }

                string methodName = Compiler.munge(((Symbol)RT.first(call)).Name);

                List <HostArg> args = ParseArgs(pcon, RT.next(call));

                return(t != null
                    ? (MethodExpr)(new StaticMethodExpr(source, spanMap, tag, t, methodName, typeArgs, args))
                    : (MethodExpr)(new InstanceMethodExpr(source, spanMap, tag, instance, methodName, typeArgs, args)));
            }
Example #6
0
            public Expr Parse(ParserContext pcon, object frm)
            {
                ISeq form = (ISeq)frm;

                if (pcon.Rhc != RHC.Return)
                {
                    return(Compiler.Analyze(pcon, RT.list(RT.list(Compiler.FnOnceSym, PersistentVector.EMPTY, form)), "try__" + RT.nextID()));
                }

                // (try try-expr* catch-expr* finally-expr?)
                // catch-expr: (catch class sym expr*)
                // finally-expr: (finally expr*)

                IPersistentVector body    = PersistentVector.EMPTY;
                IPersistentVector catches = PersistentVector.EMPTY;
                Expr bodyExpr             = null;
                Expr finallyExpr          = null;
                bool caught = false;

                ParserContext recursePcon = new ParserContext(RHC.Expression, false);

                int retLocal     = Compiler.GetAndIncLocalNum();
                int finallyLocal = Compiler.GetAndIncLocalNum();

                for (ISeq fs = form.next(); fs != null; fs = fs.next())
                {
                    object f    = fs.first();
                    ISeq   fSeq = f as ISeq;
                    object op   = fSeq != null?fSeq.first() : null;

                    if (!Util.equals(op, Compiler.CatchSym) && !Util.equals(op, Compiler.FinallySym))
                    {
                        if (caught)
                        {
                            throw new ParseException("Only catch or finally clause can follow catch in try expression");
                        }
                        body = body.cons(f);
                    }
                    else
                    {
                        if (bodyExpr == null)
                        {
                            try
                            {
                                Var.pushThreadBindings(RT.map(Compiler.NoRecurVar, true));
                                bodyExpr = new BodyExpr.Parser().Parse(pcon, RT.seq(body));
                            }
                            finally
                            {
                                Var.popThreadBindings();
                            }
                        }
                        if (Util.equals(op, Compiler.CatchSym))
                        {
                            Type t = HostExpr.MaybeType(RT.second(f), false);
                            if (t == null)
                            {
                                throw new ParseException("Unable to resolve classname: " + RT.second(f));
                            }
                            if (!(RT.third(f) is Symbol))
                            {
                                throw new ParseException("Bad binding form, expected symbol, got: " + RT.third(f));
                            }
                            Symbol sym = (Symbol)RT.third(f);
                            if (sym.Namespace != null)
                            {
                                throw new ParseException("Can't bind qualified name: " + sym);
                            }

                            IPersistentMap dynamicBindings = RT.map(
                                Compiler.LocalEnvVar, Compiler.LocalEnvVar.deref(),
                                Compiler.NextLocalNumVar, Compiler.NextLocalNumVar.deref(),
                                Compiler.InCatchFinallyVar, true);

                            try
                            {
                                Var.pushThreadBindings(dynamicBindings);
                                LocalBinding lb = Compiler.RegisterLocal(sym,
                                                                         (Symbol)(RT.second(f) is Symbol ? RT.second(f) : null),
                                                                         null, false);
                                Expr handler = (new BodyExpr.Parser()).Parse(recursePcon, RT.next(RT.next(RT.next(f))));
                                catches = catches.cons(new CatchClause(t, lb, handler));;
                            }
                            finally
                            {
                                Var.popThreadBindings();
                            }
                            caught = true;
                        }
                        else // finally
                        {
                            if (fs.next() != null)
                            {
                                throw new InvalidOperationException("finally clause must be last in try expression");
                            }
                            try
                            {
                                //Var.pushThreadBindings(RT.map(Compiler.IN_CATCH_FINALLY, RT.T));
                                Var.pushThreadBindings(RT.map(Compiler.InCatchFinallyVar, true));
                                finallyExpr = (new BodyExpr.Parser()).Parse(pcon.SetRhc(RHC.Statement).SetAssign(false), RT.next(f));
                            }
                            finally
                            {
                                Var.popThreadBindings();
                            }
                        }
                    }
                }

                if (bodyExpr == null)
                {
                    try
                    {
                        Var.pushThreadBindings(RT.map(Compiler.NoRecurVar, true));
                        bodyExpr = (new BodyExpr.Parser()).Parse(recursePcon, RT.seq(body));
                    }
                    finally
                    {
                        Var.popThreadBindings();
                    }
                }
                return(new TryExpr(bodyExpr, catches, finallyExpr, retLocal, finallyLocal));
            }
Example #7
0
        public InvokeExpr(string source, IPersistentMap spanMap, Symbol tag, Expr fexpr, IPersistentVector args)
        {
            _source  = source;
            _spanMap = spanMap;
            _fexpr   = fexpr;
            _args    = args;

            VarExpr varFexpr = fexpr as VarExpr;

            if (varFexpr != null)
            {
                Var fvar = varFexpr.Var;
                Var pvar = (Var)RT.get(fvar.meta(), Compiler.ProtocolKeyword);
                if (pvar != null && Compiler.ProtocolCallsitesVar.isBound)
                {
                    _isProtocol = true;
                    _siteIndex  = Compiler.RegisterProtocolCallsite(fvar);
                    Object pon = RT.get(pvar.get(), _onKey);
                    _protocolOn = HostExpr.MaybeType(pon, false);
                    if (_protocolOn != null)
                    {
                        IPersistentMap mmap    = (IPersistentMap)RT.get(pvar.get(), _methodMapKey);
                        Keyword        mmapVal = (Keyword)mmap.valAt(Keyword.intern(fvar.sym));
                        if (mmapVal == null)
                        {
                            throw new ArgumentException(String.Format("No method of interface: {0} found for function: {1} of protocol: {2} (The protocol method may have been defined before and removed.)",
                                                                      _protocolOn.FullName, fvar.Symbol, pvar.Symbol));
                        }
                        String mname = Compiler.munge(mmapVal.Symbol.ToString());

                        IList <MethodBase> methods = Reflector.GetMethods(_protocolOn, mname, null, args.count() - 1, false);
                        if (methods.Count != 1)
                        {
                            throw new ArgumentException(String.Format("No single method: {0} of interface: {1} found for function: {2} of protocol: {3}",
                                                                      mname, _protocolOn.FullName, fvar.Symbol, pvar.Symbol));
                        }
                        _onMethod = (MethodInfo)methods[0];
                    }
                }
            }

            //_tag = tag ?? (varFexpr != null ? varFexpr.Tag : null);
            if (tag != null)
            {
                _tag = tag;
            }
            else if (varFexpr != null)
            {
                object arglists = RT.get(RT.meta(varFexpr.Var), Compiler.ArglistsKeyword);
                object sigTag   = null;
                for (ISeq s = RT.seq(arglists); s != null; s = s.next())
                {
                    APersistentVector sig = (APersistentVector)s.first();
                    int restOffset        = sig.IndexOf(Compiler.AmpersandSym);
                    if (args.count() == sig.count() || (restOffset > -1 && args.count() >= restOffset))
                    {
                        sigTag = Compiler.TagOf(sig);
                        break;
                    }
                }
                _tag = sigTag ?? varFexpr.Tag;
            }
            else
            {
                _tag = null;
            }
        }