private static void EmitNameScopeField(XamlIlLanguageTypeMappings mappings, IXamlIlTypeSystem typeSystem, IXamlIlTypeBuilder typebuilder, IXamlIlEmitter constructor) { var nameScopeType = typeSystem.FindType("Avalonia.Controls.INameScope"); var field = typebuilder.DefineField(nameScopeType, ContextNameScopeFieldName, true, false); constructor .Ldarg_0() .Ldarg(1) .Ldtype(nameScopeType) .EmitCall(mappings.ServiceProvider.GetMethod(new FindMethodMethodSignature("GetService", typeSystem.FindType("System.Object"), typeSystem.FindType("System.Type")))) .Stfld(field); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { var res = context.Emit(Value, codeGen, Value.Type.GetClrType()); var supportInitType = context.Configuration.TypeMappings.SupportInitialize; var supportsInitialize = supportInitType != null && context.Configuration.TypeMappings.SupportInitialize .IsAssignableFrom(Value.Type.GetClrType()); if (supportsInitialize) { codeGen .Dup() .EmitCall(supportInitType.FindMethod(m => m.Name == "BeginInit")); } return(res); }
public static IXamlIlEmitter EmitCall(this IXamlIlEmitter emitter, IXamlIlMethod method, bool swallowResult = false) { if (method is IXamlIlCustomEmitMethod custom) { custom.EmitCall(emitter); } else { emitter.Emit(method.IsStatic ? OpCodes.Call : OpCodes.Callvirt, method); } if (swallowResult && !(method.ReturnType.Namespace == "System" && method.ReturnType.Name == "Void")) { emitter.Pop(); } return(emitter); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { var type = Value.GetClrType(); var method = _systemType.Methods.FirstOrDefault(m => m.Name == "GetTypeFromHandle" && m.Parameters.Count == 1 && m.Parameters[0].Name == "RuntimeTypeHandle"); if (method == null) { throw new XamlIlTypeSystemException( $"Unable to find GetTypeFromHandle(RuntimeTypeHandle) on {_systemType.GetFqn()}"); } codeGen .Emit(OpCodes.Ldtoken, type) .Emit(OpCodes.Call, method); return(XamlIlNodeEmitResult.Type(0, _systemType)); }
/// <summary> /// /// T Build(IServiceProvider sp); /// </summary> XamlIlEmitContext InitCodeGen(Func <string, IXamlIlType, IXamlIlTypeBuilder> createSubType, IXamlIlEmitter codeGen, XamlIlContext context, bool needContextLocal) { IXamlIlLocal contextLocal = null; if (needContextLocal) { contextLocal = codeGen.DefineLocal(context.ContextType); codeGen .Emit(OpCodes.Ldarg_0) .Emit(OpCodes.Newobj, context.Constructor) .Emit(OpCodes.Stloc, contextLocal); } var emitContext = new XamlIlEmitContext(codeGen, _configuration, context, contextLocal, createSubType, Emitters); return(emitContext); }
void CompileBuild(IXamlIlAstValueNode rootInstance, Func <string, IXamlIlType, IXamlIlTypeBuilder> createSubType, IXamlIlEmitter codeGen, XamlIlContext context, IXamlIlMethod compiledPopulate) { var needContextLocal = !(rootInstance is XamlIlAstNewClrObjectNode newObj && newObj.Arguments.Count == 0); var emitContext = InitCodeGen(createSubType, codeGen, context, needContextLocal); var rv = codeGen.DefineLocal(rootInstance.Type.GetClrType()); emitContext.Emit(rootInstance, codeGen, rootInstance.Type.GetClrType()); codeGen .Emit(OpCodes.Stloc, rv) .Emit(OpCodes.Ldarg_0) .Emit(OpCodes.Ldloc, rv) .Emit(OpCodes.Call, compiledPopulate) .Emit(OpCodes.Ldloc, rv) .Emit(OpCodes.Ret); }
public static bool Emit(XamlIlEmitContext context, IXamlIlEmitter emitter, XamlIlAstClrProperty property) { if (property is IXamlIlAvaloniaProperty ap) { emitter.Ldsfld(ap.AvaloniaProperty); return(true); } var type = property.DeclaringType; var name = property.Name + "Property"; var found = type.Fields.FirstOrDefault(f => f.IsStatic && f.Name == name); if (found == null) { return(false); } emitter.Ldsfld(found); return(true); }
public void Emit(IXamlIlEmitter emitter) { var locals = new Stack <XamlIlLocalsPool.PooledLocal>(); // Save all "setter" parameters for (var c = Parameters.Count - 1; c >= 0; c--) { var loc = emitter.LocalsPool.GetLocal(Parameters[c]); locals.Push(loc); emitter.Stloc(loc.Local); } emitter.EmitCall(_getter); while (locals.Count > 0) { using (var loc = locals.Pop()) emitter.Ldloc(loc.Local); } emitter.EmitCall(_adder, true); }
public XamlIlNodeEmitResult Emit(IXamlIlAstNode value, IXamlIlEmitter codeGen, IXamlIlType expectedType) { XamlIlNodeEmitResult res = null; if (_currentNode != null) { PushParent(_currentNode); _currentNode = value; res = EmitCore(value, codeGen, expectedType); _currentNode = PopParent(); } else { _currentNode = value; res = EmitCore(value, codeGen, expectedType); _currentNode = null; } return(res); }
public static void EmitConvert(XamlIlEmitContext context, IXamlIlEmitter ilgen, IXamlIlLineInfo node, IXamlIlType what, IXamlIlType to) { XamlIlLocalsPool.PooledLocal local = null; EmitConvert(context, node, what, to, lda => { if (!lda) { return(ilgen); } local = ilgen.LocalsPool.GetLocal(what); ilgen .Stloc(local.Local) .Ldloca(local.Local); return(ilgen); }); local?.Dispose(); }
public void EmitCall(IXamlIlEmitter emitter) { var method = Parent._avaloniaObject .FindMethod(m => m.IsPublic && !m.IsStatic && m.Name == "GetValue" && m.Parameters.Count == 1 && m.Parameters[0].Equals(Parent._avaloniaPropertyType)); if (method == null) { throw new XamlIlTypeSystemException( "Unable to find T GetValue<T>(AvaloniaProperty<T>) on AvaloniaObject"); } emitter .Ldsfld(Parent._field) .EmitCall(method); if (Parent.PropertyType.IsValueType) { emitter.Unbox_Any(Parent.PropertyType); } }
XamlIlEmitContext InitCodeGen( IFileSource file, Func <string, IXamlIlType, IXamlIlTypeBuilder> createSubType, IXamlIlEmitter codeGen, XamlIlContext context, bool needContextLocal) { IXamlIlLocal contextLocal = null; if (needContextLocal) { contextLocal = codeGen.DefineLocal(context.ContextType); // Pass IService provider as the first argument to context factory codeGen .Emit(OpCodes.Ldarg_0); context.Factory(codeGen); codeGen.Emit(OpCodes.Stloc, contextLocal); } var emitContext = new XamlIlEmitContext(codeGen, _configuration, context, contextLocal, createSubType, file, Emitters); return(emitContext); }
public void EmitCall(IXamlIlEmitter codeGen) { int firstCast = -1; for (var c = Parameters.Count - 1; c >= 0; c--) { if (!_baseParametersWithThis[c].Equals(Parameters[c])) { firstCast = c; } } if (firstCast != -1) { var locals = new Stack <XamlIlLocalsPool.PooledLocal>(); for (var c = Parameters.Count - 1; c >= firstCast; c--) { codeGen.Castclass(_baseParametersWithThis[c]); if (c > firstCast) { var l = codeGen.LocalsPool.GetLocal(_baseParametersWithThis[c]); codeGen.Stloc(l.Local); locals.Push(l); } } while (locals.Count != 0) { using (var l = locals.Pop()) { codeGen.Ldloc(l.Local); l.Dispose(); } } } codeGen.EmitCall(_method); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { var scopeField = context.RuntimeContext.ContextType.Fields.First(f => f.Name == AvaloniaXamlIlLanguage.ContextNameScopeFieldName); using (var targetLoc = context.GetLocal(context.Configuration.WellKnownTypes.Object)) { codeGen // var target = {pop} .Stloc(targetLoc.Local) // _context.NameScope.Register(Name, target) .Ldloc(context.ContextLocal) .Ldfld(scopeField); context.Emit(Name, codeGen, Name.Type.GetClrType()); codeGen .Ldloc(targetLoc.Local) .EmitCall(_types.INameScopeRegister, true); } return(XamlIlNodeEmitResult.Void(1)); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { if (Constant is string) { codeGen.Emit(OpCodes.Ldstr, (string)Constant); } else if (Constant is long || Constant is ulong) { codeGen.Emit(OpCodes.Ldc_I8, TypeSystemHelpers.ConvertLiteralToLong(Constant)); } else if (Constant is float f) { codeGen.Emit(OpCodes.Ldc_R4, f); } else if (Constant is double d) { codeGen.Emit(OpCodes.Ldc_R8, d); } else { codeGen.Emit(OpCodes.Ldc_I4, TypeSystemHelpers.ConvertLiteralToInt(Constant)); } return(XamlIlNodeEmitResult.Type(0, Type.GetClrType())); }
protected override void DoEmit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { context.Emit(Argument, codeGen, Type.GetClrType()); EmitCall(context, codeGen, m => m.Name == "Not" && m.Parameters.Count == 2 && m.Parameters[1].Equals(Type.GetClrType())); }
protected override void DoEmit(XamlIlEmitContext context, IXamlIlEmitter codeGen) => codeGen.Ldnull();
protected abstract void DoEmit(XamlIlEmitContext context, IXamlIlEmitter codeGen);
public XamlIlNodeEmitResult Emit(IXamlIlAstNode node, XamlIlEmitContext context, IXamlIlEmitter codeGen) { if (!(node is XamlIlValueWithManipulationNode vwm)) { return(null); } var created = context.Emit(vwm.Value, codeGen, vwm.Type.GetClrType()); if (vwm.Manipulation != null && !(vwm.Manipulation is XamlIlManipulationGroupNode grp && grp.Children.Count == 0)) { codeGen.Emit(OpCodes.Dup); context.Emit(vwm.Manipulation, codeGen, null); } return(XamlIlNodeEmitResult.Type(0, created.ReturnType)); }
public XamlIlNodeEmitResult Emit(IXamlIlAstNode node, XamlIlEmitContext context, IXamlIlEmitter codeGen) { if (!(node is XamlIlMethodCallBaseNode mc)) { return(null); } bool thisArgFromArgs = node is XamlIlStaticOrTargetedReturnMethodCallNode; bool expectsVoid = node is XamlIlNoReturnMethodCallNode; for (var c = 0; c < mc.Arguments.Count; c++) { var off = thisArgFromArgs ? 0 : 1; var expectedType = mc.Method.ParametersWithThis[c + off]; context.Emit(mc.Arguments[c], codeGen, expectedType); } mc.Method.Emit(context, codeGen, expectsVoid); var isVoid = mc.Method.ReturnType.Equals(context.Configuration.WellKnownTypes.Void); if (!expectsVoid && isVoid) { throw new XamlIlLoadException( $"XamlIlStaticReturnMethodCallNode expects a value while {mc.Method.Name} returns void", node); } var consumed = thisArgFromArgs ? 0 : 1; return(isVoid || expectsVoid ? XamlIlNodeEmitResult.Void(consumed) : XamlIlNodeEmitResult.Type(consumed, mc.Method.ReturnType)); }
public XamlIlNodeEmitResult Emit(IXamlIlAstNode node, XamlIlEmitContext context, IXamlIlEmitter codeGen) { if (!(node is XamlIlPropertyValueManipulationNode pvm)) { return(null); } codeGen.EmitCall(pvm.Property.Getter); context.Emit(pvm.Manipulation, codeGen, null); return(XamlIlNodeEmitResult.Void(1)); }
public static IXamlIlEmitter Pop(this IXamlIlEmitter emitter) => emitter.Emit(OpCodes.Pop);
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { context.LdLocal(this, codeGen); return(XamlIlNodeEmitResult.Type(0, Type)); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { XamlIlNeedsParentStackCache.Verify(context, this); return(context.Emit(Value, codeGen, Value.Type.GetClrType())); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { codeGen.Ldloc(context.ContextLocal); return(XamlIlNodeEmitResult.Type(0, Type.GetClrType())); }
public XamlIlNodeEmitResult Emit(XamlIlEmitContext context, IXamlIlEmitter codeGen) { context.Emit(Value, codeGen, Value.Type.GetClrType()); context.Emit(Manipulation, codeGen, null); return(XamlIlNodeEmitResult.Void(0)); }
public static IXamlIlEmitter Ldtoken(this IXamlIlEmitter emitter, IXamlIlMethod method) => emitter.Emit(OpCodes.Ldtoken, method);
public abstract void Emit(IXamlIlEmitter codegen);
public static IXamlIlEmitter Ldtoken(this IXamlIlEmitter emitter, IXamlIlType type) => emitter.Emit(OpCodes.Ldtoken, type);
public static IXamlIlEmitter Dup(this IXamlIlEmitter emitter) => emitter.Emit(OpCodes.Dup);