public RXamlInt32VecLikeConstAstNode(
     IXamlLineInfo lineInfo,
     IXamlType type, IXamlConstructor constructor,
     IXamlType componentType, int[] values)
     : base(lineInfo, type, constructor, componentType, values)
 {
 }
示例#2
0
 public XamlAstNewClrObjectNode(IXamlLineInfo lineInfo,
                                XamlAstClrTypeReference type, IXamlConstructor ctor,
                                List <IXamlAstValueNode> arguments) : base(lineInfo)
 {
     Type        = type;
     Constructor = ctor;
     Arguments   = arguments;
 }
示例#3
0
 public XamlAstConstructableObjectNode(IXamlLineInfo lineInfo,
                                       XamlAstClrTypeReference type, IXamlConstructor ctor,
                                       List <IXamlAstValueNode> arguments,
                                       List <IXamlAstNode> children) : base(lineInfo)
 {
     Type        = type;
     Constructor = ctor;
     Arguments   = arguments;
     Children    = children;
 }
示例#4
0
        public AvaloniaXamlIlAvaloniaListConstantAstNode(IXamlLineInfo lineInfo, AvaloniaXamlIlWellKnownTypes types, IXamlType listType, IXamlType elementType, IReadOnlyList <IXamlAstValueNode> values) : base(lineInfo)
        {
            _constructor           = listType.GetConstructor();
            _listAddMethod         = listType.GetMethod(new FindMethodMethodSignature("Add", types.XamlIlTypes.Void, elementType));
            _listSetCapacityMethod = listType.GetMethod(new FindMethodMethodSignature("set_Capacity", types.XamlIlTypes.Void, types.Int));

            _elementType = elementType;
            _values      = values;

            Type = new XamlAstClrTypeReference(lineInfo, listType, false);
        }
        public RXamlVecLikeConstAstNode(
            IXamlLineInfo lineInfo,
            IXamlType type, IXamlConstructor constructor,
            IXamlType componentType, T[] values)
            : base(lineInfo)
        {
            _constructor = constructor;
            Values       = values;

            var @params = constructor.Parameters;

            if (@params.Count != values.Length)
            {
                throw new ArgumentException("Invalid amount of parameters");
            }

            if (@params.Any(c => c != componentType))
            {
                throw new ArgumentException("Invalid constructor: not all parameters match component type");
            }

            Type = new XamlAstClrTypeReference(lineInfo, type, false);
        }
        public AvaloniaXamlIlVectorLikeConstantAstNode(IXamlLineInfo lineInfo, AvaloniaXamlIlWellKnownTypes types, IXamlType type, IXamlConstructor constructor, double[] values) : base(lineInfo)
        {
            var parameters = constructor.Parameters;

            if (parameters.Count != values.Length)
            {
                throw new XamlTypeSystemException($"Constructor that takes {values.Length} parameters is expected, got {parameters.Count} instead.");
            }

            var elementType = types.XamlIlTypes.Double;

            foreach (var parameter in parameters)
            {
                if (parameter != elementType)
                {
                    throw new XamlTypeSystemException($"Expected parameter of type {elementType}, got {parameter} instead.");
                }
            }

            _constructor = constructor;
            _values      = values;

            Type = new XamlAstClrTypeReference(lineInfo, type, false);
        }
        public AvaloniaXamlIlWellKnownTypes(TransformerConfiguration cfg)
        {
            XamlIlTypes              = cfg.WellKnownTypes;
            AvaloniaObject           = cfg.TypeSystem.GetType("Avalonia.AvaloniaObject");
            IAvaloniaObject          = cfg.TypeSystem.GetType("Avalonia.IAvaloniaObject");
            AvaloniaObjectExtensions = cfg.TypeSystem.GetType("Avalonia.AvaloniaObjectExtensions");
            AvaloniaProperty         = cfg.TypeSystem.GetType("Avalonia.AvaloniaProperty");
            AvaloniaPropertyT        = cfg.TypeSystem.GetType("Avalonia.AvaloniaProperty`1");
            BindingPriority          = cfg.TypeSystem.GetType("Avalonia.Data.BindingPriority");
            IBinding                 = cfg.TypeSystem.GetType("Avalonia.Data.IBinding");
            IDisposable              = cfg.TypeSystem.GetType("System.IDisposable");
            Transitions              = cfg.TypeSystem.GetType("Avalonia.Animation.Transitions");
            AssignBindingAttribute   = cfg.TypeSystem.GetType("Avalonia.Data.AssignBindingAttribute");
            AvaloniaObjectBindMethod = AvaloniaObjectExtensions.FindMethod("Bind", IDisposable, false, IAvaloniaObject,
                                                                           AvaloniaProperty,
                                                                           IBinding, cfg.WellKnownTypes.Object);
            UnsetValueType     = cfg.TypeSystem.GetType("Avalonia.UnsetValueType");
            StyledElement      = cfg.TypeSystem.GetType("Avalonia.StyledElement");
            INameScope         = cfg.TypeSystem.GetType("Avalonia.Controls.INameScope");
            INameScopeRegister = INameScope.GetMethod(
                new FindMethodMethodSignature("Register", XamlIlTypes.Void,
                                              XamlIlTypes.String, XamlIlTypes.Object)
            {
                IsStatic      = false,
                DeclaringOnly = true,
                IsExactMatch  = true
            });
            INameScopeComplete = INameScope.GetMethod(
                new FindMethodMethodSignature("Complete", XamlIlTypes.Void)
            {
                IsStatic      = false,
                DeclaringOnly = true,
                IsExactMatch  = true
            });
            NameScope             = cfg.TypeSystem.GetType("Avalonia.Controls.NameScope");
            NameScopeSetNameScope = NameScope.GetMethod(new FindMethodMethodSignature("SetNameScope",
                                                                                      XamlIlTypes.Void, StyledElement, INameScope)
            {
                IsStatic = true
            });
            AvaloniaObjectSetValueMethod = AvaloniaObject.FindMethod("SetValue", XamlIlTypes.Void,
                                                                     false, AvaloniaProperty, XamlIlTypes.Object, BindingPriority);
            IPropertyInfo               = cfg.TypeSystem.GetType("Avalonia.Data.Core.IPropertyInfo");
            ClrPropertyInfo             = cfg.TypeSystem.GetType("Avalonia.Data.Core.ClrPropertyInfo");
            PropertyPath                = cfg.TypeSystem.GetType("Avalonia.Data.Core.PropertyPath");
            PropertyPathBuilder         = cfg.TypeSystem.GetType("Avalonia.Data.Core.PropertyPathBuilder");
            IPropertyAccessor           = cfg.TypeSystem.GetType("Avalonia.Data.Core.Plugins.IPropertyAccessor");
            PropertyInfoAccessorFactory = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.PropertyInfoAccessorFactory");
            CompiledBindingPathBuilder  = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.CompiledBindingPathBuilder");
            CompiledBindingPath         = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.CompiledBindingPath");
            CompiledBindingExtension    = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindingExtension");
            ResolveByNameExtension      = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.ResolveByNameExtension");
            DataTemplate                = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.Templates.DataTemplate");
            IDataTemplate               = cfg.TypeSystem.GetType("Avalonia.Controls.Templates.IDataTemplate");
            IItemsPresenterHost         = cfg.TypeSystem.GetType("Avalonia.Controls.Presenters.IItemsPresenterHost");
            ItemsRepeater               = cfg.TypeSystem.GetType("Avalonia.Controls.ItemsRepeater");
            ReflectionBindingExtension  = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.ReflectionBindingExtension");
            RelativeSource              = cfg.TypeSystem.GetType("Avalonia.Data.RelativeSource");
            UInt       = cfg.TypeSystem.GetType("System.UInt32");
            Long       = cfg.TypeSystem.GetType("System.Int64");
            Uri        = cfg.TypeSystem.GetType("System.Uri");
            FontFamily = cfg.TypeSystem.GetType("Avalonia.Media.FontFamily");
            FontFamilyConstructorUriName = FontFamily.GetConstructor(new List <IXamlType> {
                Uri, XamlIlTypes.String
            });

            (IXamlType, IXamlConstructor) GetNumericTypeInfo(string name, IXamlType componentType, int componentCount)
            {
                var type = cfg.TypeSystem.GetType(name);
                var ctor = type.GetConstructor(Enumerable.Range(0, componentCount).Select(_ => componentType).ToList());

                return(type, ctor);
            }

            (Thickness, ThicknessFullConstructor)       = GetNumericTypeInfo("Avalonia.Thickness", XamlIlTypes.Double, 4);
            (Point, PointFullConstructor)               = GetNumericTypeInfo("Avalonia.Point", XamlIlTypes.Double, 2);
            (Vector, VectorFullConstructor)             = GetNumericTypeInfo("Avalonia.Vector", XamlIlTypes.Double, 2);
            (Size, SizeFullConstructor)                 = GetNumericTypeInfo("Avalonia.Size", XamlIlTypes.Double, 2);
            (Matrix, MatrixFullConstructor)             = GetNumericTypeInfo("Avalonia.Matrix", XamlIlTypes.Double, 6);
            (CornerRadius, CornerRadiusFullConstructor) = GetNumericTypeInfo("Avalonia.CornerRadius", XamlIlTypes.Double, 4);

            GridLength = cfg.TypeSystem.GetType("Avalonia.Controls.GridLength");
            GridLengthConstructorValueType = GridLength.GetConstructor(new List <IXamlType> {
                XamlIlTypes.Double, cfg.TypeSystem.GetType("Avalonia.Controls.GridUnitType")
            });
            Color = cfg.TypeSystem.GetType("Avalonia.Media.Color");
            StandardCursorType    = cfg.TypeSystem.GetType("Avalonia.Input.StandardCursorType");
            Cursor                = cfg.TypeSystem.GetType("Avalonia.Input.Cursor");
            CursorTypeConstructor = Cursor.GetConstructor(new List <IXamlType> {
                StandardCursorType
            });
        }
示例#8
0
 public static IXamlILEmitter Newobj(this IXamlILEmitter emitter, IXamlConstructor ctor)
 => emitter.Emit(OpCodes.Newobj, ctor);
示例#9
0
 public IXamlILEmitter Emit(OpCode code, IXamlConstructor ctor)
 {
     _ilg.Emit(code, ((SreConstructor)ctor).Constuctor);
     return(this);
 }
示例#10
0
 public bool Equals(IXamlConstructor other)
 => ((SreConstructor)other)?.Constuctor.Equals(Constuctor) == true;
 public IXamlILEmitter Emit(OpCode code, IXamlConstructor ctor)
 {
     Record(code, ctor);
     _inner.Emit(code, ctor);
     return(this);
 }
 public AvaloniaXamlIlWellKnownTypes(TransformerConfiguration cfg)
 {
     XamlIlTypes              = cfg.WellKnownTypes;
     AvaloniaObject           = cfg.TypeSystem.GetType("Avalonia.AvaloniaObject");
     IAvaloniaObject          = cfg.TypeSystem.GetType("Avalonia.IAvaloniaObject");
     AvaloniaObjectExtensions = cfg.TypeSystem.GetType("Avalonia.AvaloniaObjectExtensions");
     AvaloniaProperty         = cfg.TypeSystem.GetType("Avalonia.AvaloniaProperty");
     AvaloniaPropertyT        = cfg.TypeSystem.GetType("Avalonia.AvaloniaProperty`1");
     BindingPriority          = cfg.TypeSystem.GetType("Avalonia.Data.BindingPriority");
     IBinding                 = cfg.TypeSystem.GetType("Avalonia.Data.IBinding");
     IDisposable              = cfg.TypeSystem.GetType("System.IDisposable");
     Transitions              = cfg.TypeSystem.GetType("Avalonia.Animation.Transitions");
     AssignBindingAttribute   = cfg.TypeSystem.GetType("Avalonia.Data.AssignBindingAttribute");
     AvaloniaObjectBindMethod = AvaloniaObjectExtensions.FindMethod("Bind", IDisposable, false, IAvaloniaObject,
                                                                    AvaloniaProperty,
                                                                    IBinding, cfg.WellKnownTypes.Object);
     UnsetValueType     = cfg.TypeSystem.GetType("Avalonia.UnsetValueType");
     StyledElement      = cfg.TypeSystem.GetType("Avalonia.StyledElement");
     INameScope         = cfg.TypeSystem.GetType("Avalonia.Controls.INameScope");
     INameScopeRegister = INameScope.GetMethod(
         new FindMethodMethodSignature("Register", XamlIlTypes.Void,
                                       XamlIlTypes.String, XamlIlTypes.Object)
     {
         IsStatic      = false,
         DeclaringOnly = true,
         IsExactMatch  = true
     });
     INameScopeComplete = INameScope.GetMethod(
         new FindMethodMethodSignature("Complete", XamlIlTypes.Void)
     {
         IsStatic      = false,
         DeclaringOnly = true,
         IsExactMatch  = true
     });
     NameScope             = cfg.TypeSystem.GetType("Avalonia.Controls.NameScope");
     NameScopeSetNameScope = NameScope.GetMethod(new FindMethodMethodSignature("SetNameScope",
                                                                               XamlIlTypes.Void, StyledElement, INameScope)
     {
         IsStatic = true
     });
     AvaloniaObjectSetValueMethod = AvaloniaObject.FindMethod("SetValue", XamlIlTypes.Void,
                                                              false, AvaloniaProperty, XamlIlTypes.Object, BindingPriority);
     IPropertyInfo               = cfg.TypeSystem.GetType("Avalonia.Data.Core.IPropertyInfo");
     ClrPropertyInfo             = cfg.TypeSystem.GetType("Avalonia.Data.Core.ClrPropertyInfo");
     PropertyPath                = cfg.TypeSystem.GetType("Avalonia.Data.Core.PropertyPath");
     PropertyPathBuilder         = cfg.TypeSystem.GetType("Avalonia.Data.Core.PropertyPathBuilder");
     IPropertyAccessor           = cfg.TypeSystem.GetType("Avalonia.Data.Core.Plugins.IPropertyAccessor");
     PropertyInfoAccessorFactory = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.PropertyInfoAccessorFactory");
     CompiledBindingPathBuilder  = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.CompiledBindingPathBuilder");
     CompiledBindingPath         = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindings.CompiledBindingPath");
     CompiledBindingExtension    = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.CompiledBindingExtension");
     ResolveByNameExtension      = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.ResolveByNameExtension");
     DataTemplate                = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.Templates.DataTemplate");
     IDataTemplate               = cfg.TypeSystem.GetType("Avalonia.Controls.Templates.IDataTemplate");
     IItemsPresenterHost         = cfg.TypeSystem.GetType("Avalonia.Controls.Presenters.IItemsPresenterHost");
     ItemsRepeater               = cfg.TypeSystem.GetType("Avalonia.Controls.ItemsRepeater");
     ReflectionBindingExtension  = cfg.TypeSystem.GetType("Avalonia.Markup.Xaml.MarkupExtensions.ReflectionBindingExtension");
     RelativeSource              = cfg.TypeSystem.GetType("Avalonia.Data.RelativeSource");
     Long       = cfg.TypeSystem.GetType("System.Int64");
     Uri        = cfg.TypeSystem.GetType("System.Uri");
     FontFamily = cfg.TypeSystem.GetType("Avalonia.Media.FontFamily");
     FontFamilyConstructorUriName = FontFamily.FindConstructor(new List <IXamlType> {
         Uri, XamlIlTypes.String
     });
 }
示例#13
0
 public bool Equals(IXamlConstructor other) =>
 other is RoslynConstructor roslynConstructor &&
示例#14
0
 public IXamlILEmitter Emit(SreOpCode code, IXamlConstructor ctor)
 => Emit(Instruction.Create(Dic[code], M.ImportReference(((CecilConstructor)ctor).IlReference)));
示例#15
0
        private XamlILContextDefinition(IXamlTypeBuilder <IXamlILEmitter> parentBuilder,
                                        IXamlTypeSystem typeSystem, XamlLanguageTypeMappings mappings,
                                        XamlLanguageEmitMappings <IXamlILEmitter, XamlILNodeEmitResult> emitMappings)
        {
            var so      = typeSystem.GetType("System.Object");
            var builder = parentBuilder.DefineSubType(so, "Context", true);

            builder.DefineGenericParameters(new[]
            {
                new KeyValuePair <string, XamlGenericParameterConstraint>("TTarget",
                                                                          new XamlGenericParameterConstraint
                {
                    IsClass = true
                })
            });
            var rootObjectField             = builder.DefineField(builder.GenericParameters[0], "RootObject", true, false);
            var intermediateRootObjectField = builder.DefineField(so, XamlRuntimeContextDefintion.IntermediateRootObjectFieldName, true, false);

            _parentServiceProviderField = builder.DefineField(mappings.ServiceProvider, "_sp", false, false);
            if (mappings.InnerServiceProviderFactoryMethod != null)
            {
                _innerServiceProviderField = builder.DefineField(mappings.ServiceProvider, "_innerSp", false, false);
            }

            var staticProvidersField = builder.DefineField(typeSystem.GetType("System.Object").MakeArrayType(1),
                                                           "_staticProviders", false, false);


            var systemType   = typeSystem.GetType("System.Type");
            var systemUri    = typeSystem.GetType("System.Uri");
            var systemString = typeSystem.GetType("System.String");
            var getServiceInterfaceMethod = mappings.ServiceProvider.FindMethod("GetService", so, false, systemType);

            var ownServices   = new List <IXamlType>();
            var ctorCallbacks = new List <Action <IXamlILEmitter> >();

            if (mappings.RootObjectProvider != null)
            {
                builder.AddInterfaceImplementation(mappings.RootObjectProvider);
                var rootGen = ImplementInterfacePropertyGetter(builder, mappings.RootObjectProvider, XamlRuntimeContextDefintion.RootObjectFieldName)
                              .Generator;
                var tryParent          = rootGen.DefineLabel();
                var fail               = rootGen.DefineLabel();
                var parentRootProvider = rootGen.DefineLocal(mappings.RootObjectProvider);
                rootGen
                // if(RootObject!=null) return RootObject;
                .LdThisFld(rootObjectField)
                .Box(rootObjectField.FieldType)
                .Brfalse(tryParent)
                .LdThisFld(rootObjectField)
                .Box(rootObjectField.FieldType)
                .Ret()
                // if(_sp == null) goto fail;
                .MarkLabel(tryParent)
                .LdThisFld(_parentServiceProviderField)
                .Brfalse(fail)
                // parentProv =  (IRootObjectProvider)_sp.GetService(typeof(IRootObjectProvider));
                .LdThisFld(_parentServiceProviderField)
                .Ldtype(mappings.RootObjectProvider)
                .EmitCall(getServiceInterfaceMethod)
                .Castclass(mappings.RootObjectProvider)
                .Stloc(parentRootProvider)
                // if(parentProv == null) goto fail;
                .Ldloc(parentRootProvider)
                .Brfalse(fail)
                // return parentProv.Root;
                .Ldloc(parentRootProvider)
                .EmitCall(mappings.RootObjectProvider.FindMethod(m => m.Name == "get_RootObject"))
                .Ret()
                // fail:
                .MarkLabel(fail)
                .Ldnull()
                .Ret();

                if (mappings.RootObjectProviderIntermediateRootPropertyName != null)
                {
                    ImplementInterfacePropertyGetter(builder, mappings.RootObjectProvider, mappings.RootObjectProviderIntermediateRootPropertyName)
                    .Generator
                    .LdThisFld(intermediateRootObjectField)
                    .Ret();
                }

                ownServices.Add(mappings.RootObjectProvider);
            }

            if (mappings.ParentStackProvider != null)
            {
                builder.AddInterfaceImplementation(mappings.ParentStackProvider);
                var objectListType = typeSystem.GetType("System.Collections.Generic.List`1")
                                     .MakeGenericType(new[] { typeSystem.GetType("System.Object") });
                ParentListField = builder.DefineField(objectListType, XamlRuntimeContextDefintion.ParentListFieldName, true, false);

                var enumerator = EmitParentEnumerable(typeSystem, parentBuilder, mappings);
                CreateCallbacks.Add(enumerator.createCallback);
                var parentStackEnumerableField = builder.DefineField(
                    typeSystem.GetType("System.Collections.Generic.IEnumerable`1").MakeGenericType(new[] { so }),
                    "_parentStackEnumerable", false, false);

                ImplementInterfacePropertyGetter(builder, mappings.ParentStackProvider, "Parents")
                .Generator.LdThisFld(parentStackEnumerableField).Ret();

                ctorCallbacks.Add(g => g
                                  .Emit(OpCodes.Ldarg_0)
                                  .Emit(OpCodes.Newobj, objectListType.FindConstructor(new List <IXamlType>()))
                                  .Emit(OpCodes.Stfld, ParentListField)
                                  .Emit(OpCodes.Ldarg_0)
                                  .LdThisFld(ParentListField)
                                  .LdThisFld(_parentServiceProviderField)
                                  .Emit(OpCodes.Newobj, enumerator.ctor)
                                  .Emit(OpCodes.Stfld, parentStackEnumerableField));
                ownServices.Add(mappings.ParentStackProvider);
            }

            ownServices.Add(EmitTypeDescriptorContextStub(typeSystem, builder, mappings));

            if (mappings.ProvideValueTarget != null)
            {
                builder.AddInterfaceImplementation(mappings.ProvideValueTarget);
                PropertyTargetObject   = builder.DefineField(so, XamlRuntimeContextDefintion.ProvideTargetObjectName, true, false);
                PropertyTargetProperty = builder.DefineField(so, XamlRuntimeContextDefintion.ProvideTargetPropertyName, true, false);
                ImplementInterfacePropertyGetter(builder, mappings.ProvideValueTarget, "TargetObject")
                .Generator.LdThisFld(PropertyTargetObject).Ret();
                ImplementInterfacePropertyGetter(builder, mappings.ProvideValueTarget, "TargetProperty")
                .Generator.LdThisFld(PropertyTargetProperty).Ret();
                ownServices.Add(mappings.ProvideValueTarget);
            }

            IXamlField baseUriField = null;

            if (mappings.UriContextProvider != null)
            {
                baseUriField = builder.DefineField(systemUri, "_baseUri", false, false);
                builder.AddInterfaceImplementation(mappings.UriContextProvider);
                var getter = builder.DefineMethod(systemUri, new IXamlType[0], "get_BaseUri", true, false, true);
                var setter = builder.DefineMethod(typeSystem.GetType("System.Void"), new[] { systemUri },
                                                  "set_BaseUri", true, false, true);

                getter.Generator
                .LdThisFld(baseUriField)
                .Ret();

                setter.Generator
                .Ldarg_0()
                .Ldarg(1)
                .Stfld(baseUriField)
                .Ret();
                builder.DefineProperty(systemUri, "BaseUri", setter, getter);


                ownServices.Add(mappings.UriContextProvider);
            }

            builder.AddInterfaceImplementation(mappings.ServiceProvider);
            var getServiceMethod = builder.DefineMethod(so,
                                                        new[] { systemType },
                                                        "GetService", true, false, true);

            ownServices = ownServices.Where(s => s != null).ToList();


            if (_innerServiceProviderField != null)
            {
                var next        = getServiceMethod.Generator.DefineLabel();
                var innerResult = getServiceMethod.Generator.DefineLocal(so);
                getServiceMethod.Generator
                //if(_inner == null) goto next;
                .LdThisFld(_innerServiceProviderField)
                .Brfalse(next)
                // var innerRes = _inner.GetService(type);
                .LdThisFld(_innerServiceProviderField)
                .Ldarg(1)
                .EmitCall(getServiceInterfaceMethod)
                .Stloc(innerResult)
                // if(innerRes == null) goto next;
                .Ldloc(innerResult)
                .Brfalse(next)
                // return innerRes
                .Ldloc(innerResult)
                .Ret()
                .MarkLabel(next);
            }
            var compare = systemType.FindMethod("Equals", typeSystem.GetType("System.Boolean"),
                                                false, systemType);
            var isAssignableFrom = systemType.FindMethod("IsAssignableFrom", typeSystem.GetType("System.Boolean"),
                                                         false, systemType);
            var fromHandle        = systemType.Methods.First(m => m.Name == "GetTypeFromHandle");
            var getTypeFromObject = so.Methods.First(m => m.Name == "GetType" && m.Parameters.Count == 0);

            if (ownServices.Count != 0)
            {
                for (var c = 0; c < ownServices.Count; c++)
                {
                    var next = getServiceMethod.Generator.DefineLabel();
                    getServiceMethod.Generator
                    .Emit(OpCodes.Ldtoken, ownServices[c])
                    .EmitCall(fromHandle)
                    .Emit(OpCodes.Ldarg_1)
                    .Emit(OpCodes.Callvirt, compare)
                    .Emit(OpCodes.Brfalse, next)
                    .Emit(OpCodes.Ldarg_0)
                    .Emit(OpCodes.Ret)
                    .MarkLabel(next);
                }
            }

            var staticProviderIndex   = getServiceMethod.Generator.DefineLocal(typeSystem.GetType("System.Int32"));
            var staticProviderNext    = getServiceMethod.Generator.DefineLabel();
            var staticProviderFailed  = getServiceMethod.Generator.DefineLabel();
            var staticProviderEnd     = getServiceMethod.Generator.DefineLabel();
            var staticProviderElement = getServiceMethod.Generator.DefineLocal(so);

            getServiceMethod.Generator
            //start: if(_staticProviders == null) goto: end
            .LdThisFld(staticProvidersField)
            .Brfalse(staticProviderEnd)
            // var c = 0
            .Ldc_I4(0)
            .Stloc(staticProviderIndex)
            // next:
            .MarkLabel(staticProviderNext)
            // if(c >= _staticProviders.Length) goto: end
            .Ldloc(staticProviderIndex)
            .LdThisFld(staticProvidersField)
            .Ldlen()
            .Bge(staticProviderEnd)
            // var obj = _staticProviders[c]
            .LdThisFld(staticProvidersField)
            .Ldloc(staticProviderIndex)
            .Ldelem_ref()
            // dup
            .Stloc(staticProviderElement)
            .Ldarg(1)
            .Ldloc(staticProviderElement)
            // if(obj.GetType().Equals(arg1)) return obj; else goto failed;
            .EmitCall(getTypeFromObject)
            .EmitCall(isAssignableFrom)
            .Brfalse(staticProviderFailed)
            .Ldloc(staticProviderElement)
            .Ret()
            // failed:
            .MarkLabel(staticProviderFailed)
            // c++
            .Ldloc(staticProviderIndex)
            .Ldc_I4(1)
            .Add()
            .Stloc(staticProviderIndex)
            // goto: start
            .Br(staticProviderNext)
            // end:
            .MarkLabel(staticProviderEnd);

            var noParentProvider = getServiceMethod.Generator.DefineLabel();

            getServiceMethod.Generator
            .LdThisFld(_parentServiceProviderField)
            .Brfalse(noParentProvider)
            .LdThisFld(_parentServiceProviderField)
            .Ldarg(1)
            .EmitCall(getServiceInterfaceMethod)
            .Emit(OpCodes.Ret)
            .MarkLabel(noParentProvider)
            .Ldnull()
            .Ret();

            var ctor = builder.DefineConstructor(false,
                                                 mappings.ServiceProvider,
                                                 staticProvidersField.FieldType,
                                                 systemString);

            ctor.Generator
            .Emit(OpCodes.Ldarg_0)
            .Emit(OpCodes.Call, so.Constructors.First())
            .Emit(OpCodes.Ldarg_0)
            .Emit(OpCodes.Ldarg_1)
            .Emit(OpCodes.Stfld, _parentServiceProviderField)
            .Emit(OpCodes.Ldarg_0)
            .Emit(OpCodes.Ldarg_2)
            .Emit(OpCodes.Stfld, staticProvidersField);
            if (baseUriField != null)
            {
                var noUri = ctor.Generator.DefineLabel();
                ctor.Generator
                .Emit(OpCodes.Ldarg_3)
                .Brfalse(noUri)
                .Emit(OpCodes.Ldarg_0)
                .Emit(OpCodes.Ldarg_3)
                .Newobj(systemUri.FindConstructor(new List <IXamlType>
                {
                    typeSystem.GetType("System.String")
                }))
                .Emit(OpCodes.Stfld, baseUriField)
                .MarkLabel(noUri);
            }

            foreach (var feature in ctorCallbacks)
            {
                feature(ctor.Generator);
            }

            emitMappings.ContextTypeBuilderCallback?.Invoke(builder, ctor.Generator);

            // We are calling this last to ensure that our own services are ready
            if (_innerServiceProviderField != null)
            {
                ctor.Generator
                // _innerSp = InnerServiceProviderFactory(this)
                .Ldarg_0()
                .Ldarg_0()
                .EmitCall(mappings.InnerServiceProviderFactoryMethod)
                .Stfld(_innerServiceProviderField);
            }

            ctor.Generator.Emit(OpCodes.Ret);

            Constructor = ctor;
            CreateCallbacks.Add(() => { parentBuilder.CreateType(); });

            if (ParentListField != null)
            {
                EmitPushPopParent(builder, typeSystem);
            }

            CreateAllTypes();
            ContextType = builder.CreateType();
        }
示例#16
0
 public bool Equals(IXamlConstructor other) => other is CecilConstructor cm &&