protected internal override void TraverseEval(Eval eval) { var m = eval.InvokedMethod(); eval.InvocationArgs().ForEach(Traverse); var lam = eval.InvokedLambda(); if (lam.InvokedAsCtor) { il.newobj(m); } else if (lam.InvokedAsVirtual) { il.callvirt(m); } else { il.call(m); } var rets_smth = lam.Sig.Ret != typeof(void); var ret_aint_used = !(Stack.SecondOrDefault() is Expression); if (rets_smth && ret_aint_used) { il.pop(); } }
public Eval Redirect(Eval eval) { var m = eval.InvokedMethod(); var a = eval.InvocationArgs().ToReadOnly(); var redirectors = _redirects.Select(kvp => kvp.Key(m) ? kvp.Value : null).Where(f => f != null); var f_mredir = redirectors.AssertSingle().Item1; var m_redir = f_mredir(m, a); var f_aredir = redirectors.AssertSingle().Item2; var a_redir = f_aredir(m, a); if (m_redir == null || a_redir == null) return null; // todo. this doesn't preserve virtuality of the call! return new Eval(new Apply(new Lambda(m_redir), a_redir)); }
public Eval Redirect(Eval eval) { var m = eval.InvokedMethod(); var a = eval.InvocationArgs().ToReadOnly(); var redirectors = _redirects.Select(kvp => kvp.Key(m) ? kvp.Value : null).Where(f => f != null); var f_mredir = redirectors.AssertSingle().Item1; var m_redir = f_mredir(m, a); var f_aredir = redirectors.AssertSingle().Item2; var a_redir = f_aredir(m, a); if (m_redir == null || a_redir == null) { return(null); } // todo. this doesn't preserve virtuality of the call! return(new Eval(new Apply(new Lambda(m_redir), a_redir))); }
protected override void TraverseEval(Eval eval) { var m = eval.InvokedMethod(); eval.InvocationArgs().ForEach(Traverse); var lam = eval.InvokedLambda(); if (lam.InvokedAsCtor) il.newobj(m); else if (lam.InvokedAsVirtual) il.callvirt(m); else il.call(m); var rets_smth = lam.Sig.Ret != typeof(void); var ret_aint_used = !(Stack.SecondOrDefault() is Expression); if (rets_smth && ret_aint_used) il.pop(); }
protected override void TraverseEval(Eval eval) { var m = eval.InvokedMethod(); var args = eval.InvocationArgsInfo(); if (m.DeclaringType == typeof(Ctm) && m.Name == "Malloc") { throw AssertionHelper.Fail(); } else if (m.DeclaringType.IsArray || m.DeclaringType == typeof(Array)) { var @this = args.First().Item1; if (m.Name == "GetLength") { var e_dim = args.Skip(1).AssertSingle().Item1; var dim = e_dim.AssertCast<Const>().Value.AssertCoerce<int>(); _ptx.ld(@this).arrdim(dim); } else if (m.IsArrayGetter()) { _ptx.ld(@this); args.Skip(1).ForEach(idx => _ptx.ld(idx.Item1)); _ptx.arrget(m); } else if (m.IsArraySetter()) { _ptx.ld(@this); args.Skip(1).ForEach(idx => _ptx.ld(idx.Item1)); _ptx.arrset(m); } else { throw AssertionHelper.Fail(); } } else { var a_ptx = m.AttrOrNull<PtxAttribute>(); if (a_ptx == null) { var p_m = m.EnclosingProperty(); if (p_m != null) a_ptx = p_m.AttrOrNull<PtxAttribute>(); } a_ptx.AssertNotNull(); (a_ptx.Version <= _cfg.Version).AssertTrue(); (a_ptx.Target <= _cfg.Target).AssertTrue(); var s_code = a_ptx.Code.Trim(); var is_literal = !s_code.Contains(" "); is_literal.AssertEquiv(args.IsEmpty()); if (is_literal) { _ptx.op(s_code); } else { var splits = s_code.Split(" ".MkArray(), StringSplitOptions.RemoveEmptyEntries); splits.AssertThat(seq => seq.Count() >= 3); var cop = splits.AssertFirst(); splits.AssertSecond().AssertThat(s => s == "%"); splits.Skip(2).ForEach(s_arg => { if (!s_arg.StartsWith("%")) { _ptx.ld(s_arg); } else { var p_name = s_arg.AssertExtract("$%(?<name>.*)^"); var p = m.GetParameters().AssertSingle(p1 => p1.Name == p_name); _ptx.ld(args[p]); } }); _ptx.op(cop); } } }
protected override void TraverseEval(Eval eval) { var m = eval.InvokedMethod(); var args = eval.InvocationArgsInfo(); if (m.DeclaringType == typeof(Ctm) && m.Name == "Malloc") { throw AssertionHelper.Fail(); } else if (m.DeclaringType.IsArray || m.DeclaringType == typeof(Array)) { var @this = args.First().Item1; if (m.Name == "GetLength") { var e_dim = args.Skip(1).AssertSingle().Item1; var dim = e_dim.AssertCast <Const>().Value.AssertCoerce <int>(); _ptx.ld(@this).arrdim(dim); } else if (m.IsArrayGetter()) { _ptx.ld(@this); args.Skip(1).ForEach(idx => _ptx.ld(idx.Item1)); _ptx.arrget(m); } else if (m.IsArraySetter()) { _ptx.ld(@this); args.Skip(1).ForEach(idx => _ptx.ld(idx.Item1)); _ptx.arrset(m); } else { throw AssertionHelper.Fail(); } } else { var a_ptx = m.AttrOrNull <PtxAttribute>(); if (a_ptx == null) { var p_m = m.EnclosingProperty(); if (p_m != null) { a_ptx = p_m.AttrOrNull <PtxAttribute>(); } } a_ptx.AssertNotNull(); (a_ptx.Version <= _cfg.Version).AssertTrue(); (a_ptx.Target <= _cfg.Target).AssertTrue(); var s_code = a_ptx.Code.Trim(); var is_literal = !s_code.Contains(" "); is_literal.AssertEquiv(args.IsEmpty()); if (is_literal) { _ptx.op(s_code); } else { var splits = s_code.Split(" ".MkArray(), StringSplitOptions.RemoveEmptyEntries); splits.AssertThat(seq => seq.Count() >= 3); var cop = splits.AssertFirst(); splits.AssertSecond().AssertThat(s => s == "%"); splits.Skip(2).ForEach(s_arg => { if (!s_arg.StartsWith("%")) { _ptx.ld(s_arg); } else { var p_name = s_arg.AssertExtract("$%(?<name>.*)^"); var p = m.GetParameters().AssertSingle(p1 => p1.Name == p_name); _ptx.ld(args[p]); } }); _ptx.op(cop); } } }