public static Expr Parse(ParserContext pcon, ISeq form)
{
bool tailPosition = Compiler.InTailCall(pcon.Rhc);
pcon = pcon.EvalOrExpr();
Expr fexpr = Compiler.Analyze(pcon, form.first());
VarExpr varFexpr = fexpr as VarExpr;
if (varFexpr != null && varFexpr.Var.Equals(Compiler.InstanceVar) && RT.count(form) == 3)
{
Expr sexpr = Compiler.Analyze(pcon.SetRhc(RHC.Expression), RT.second(form));
if (sexpr is ConstantExpr csexpr)
{
Type tval = csexpr.Val as Type;
if (tval != null)
{
return(new InstanceOfExpr((string)Compiler.SourceVar.deref(), (IPersistentMap)Compiler.SourceSpanVar.deref(), tval, Compiler.Analyze(pcon, RT.third(form))));
}
}
}
if (RT.booleanCast(Compiler.GetCompilerOption(Compiler.DirectLinkingKeyword)) &&
varFexpr != null &&
pcon.Rhc != RHC.Eval)
{
Var v = varFexpr.Var;
if (!v.isDynamic() && !RT.booleanCast(RT.get(v.meta(), Compiler.RedefKeyword, false)) && !RT.booleanCast(RT.get(v.meta(), RT.DeclaredKey, false)))
{
Symbol formTag = Compiler.TagOf(form);
//object arglists = RT.get(RT.meta(v), Compiler.ArglistsKeyword);
int arity = RT.count(form.next());
object sigtag = SigTag(arity, v);
object vtag = RT.get(RT.meta(v), RT.TagKey);
if (StaticInvokeExpr.Parse(v, RT.next(form), formTag ?? sigtag ?? vtag) is StaticInvokeExpr ret && !((Compiler.IsCompiling || Compiler.IsCompilingDefType) && GenContext.IsInternalAssembly(ret.Method.DeclaringType.Assembly)))
{
//Console.WriteLine("invoke direct: {0}", v);
return(ret);
}
//Console.WriteLine("NOT direct: {0}", v);
}
}
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,
((IObj)RT.listStar(Symbol.intern(".invokePrim"),
((Symbol)form.first()).withMeta(RT.map(RT.TagKey, Symbol.intern(primc))),
form.next())).withMeta((IPersistentMap)RT.conj(RT.meta(v), RT.meta(form)))));
}
break;
}
}
}
if (fexpr is KeywordExpr kwFexpr && 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,
tailPosition));
}