Пример #1
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = new DependencyList();
            
            if (factory.TypeSystemContext.HasEagerStaticConstructor(_type))
            {
                dependencyList.Add(factory.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
            }

            dependencyList.Add(factory.GCStaticsRegion, "GCStatics Region");
            dependencyList.Add(GetGCStaticEETypeNode(factory), "GCStatic EEType");
            dependencyList.Add(factory.GCStaticIndirection(_type), "GC statics indirection");
            return dependencyList;
        }
Пример #2
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DefType closestDefType = _type.GetClosestDefType();

            DependencyList dependencyList = new DependencyList();
            if (_type.RuntimeInterfaces.Length > 0)
            {
                dependencyList.Add(factory.InterfaceDispatchMap(_type), "Interface dispatch map");

                // If any of the implemented interfaces have variance, calls against compatible interface methods
                // could result in interface methods of this type being used (e.g. IEnumberable<object>.GetEnumerator()
                // can dispatch to an implementation of IEnumerable<string>.GetEnumerator()).
                // For now, we will not try to optimize this and we will pretend all interface methods are necessary.
                
                foreach (var implementedInterface in _type.RuntimeInterfaces)
                {
                    if (implementedInterface.HasVariance)
                    {
                        foreach (var interfaceMethod in implementedInterface.GetAllMethods())
                        {
                            if (interfaceMethod.Signature.IsStatic)
                                continue;

                            MethodDesc implMethod = closestDefType.ResolveInterfaceMethodToVirtualMethodOnType(interfaceMethod);
                            if (implMethod != null)
                            {
                                dependencyList.Add(factory.VirtualMethodUse(interfaceMethod), "Variant interface method");
                                dependencyList.Add(factory.VirtualMethodUse(implMethod), "Variant interface method");
                            }
                        }
                    }
                }
            }

            if (_type.IsArray)
            {
                // Array EEType depends on System.Array's virtuals. Array EETypes don't point to
                // their base type (i.e. there's no reloc based dependency making this "just work").
                dependencyList.Add(factory.ConstructedTypeSymbol(_type.BaseType), "Array base type");
            }

            dependencyList.Add(factory.VTable(_type), "VTable");

            if (closestDefType.HasGenericDictionarySlot())
            {
                // Generic dictionary pointer is part of the vtable and as such it gets only laid out
                // at the final data emission phase. We need to report it as a non-relocation dependency.
                dependencyList.Add(factory.TypeGenericDictionary(closestDefType), "Type generic dictionary");
            }

            // Include the optional fields by default. We don't know if optional fields will be needed until
            // all of the interface usage has been stabilized. If we end up not needing it, the EEType node will not
            // generate any relocs to it, and the optional fields node will instruct the object writer to skip
            // emitting it.
            dependencyList.Add(_optionalFieldsNode, "Optional fields");
            
            return dependencyList;
        }
Пример #3
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            if (factory.TypeSystemContext.HasEagerStaticConstructor(_type))
            {
                var result = new DependencyList();
                result.Add(factory.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
                return result;
            }

            return null;
        }
Пример #4
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = new DependencyList();
            if (_type.RuntimeInterfaces.Length > 0)
            {
                dependencyList.Add(factory.InterfaceDispatchMap(_type), "Interface dispatch map");

                // If any of the implemented interfaces have variance, calls against compatible interface methods
                // could result in interface methods of this type being used (e.g. IEnumberable<object>.GetEnumerator()
                // can dispatch to an implementation of IEnumerable<string>.GetEnumerator()).
                // For now, we will not try to optimize this and we will pretend all interface methods are necessary.
                DefType defType = _type.GetClosestDefType();
                foreach (var implementedInterface in defType.RuntimeInterfaces)
                {
                    if (implementedInterface.HasVariance)
                    {
                        foreach (var interfaceMethod in implementedInterface.GetAllVirtualMethods())
                        {
                            MethodDesc implMethod = defType.ResolveInterfaceMethodToVirtualMethodOnType(interfaceMethod);
                            if (implMethod != null)
                            {
                                dependencyList.Add(factory.VirtualMethodUse(interfaceMethod), "Variant interface method");
                                dependencyList.Add(factory.VirtualMethodUse(implMethod), "Variant interface method");
                            }
                        }
                    }
                }
            }

            if (_type.IsArray)
            {
                // Array EEType depends on System.Array's virtuals. Array EETypes don't point to
                // their base type (i.e. there's no reloc based dependency making this "just work").
                dependencyList.Add(factory.ConstructedTypeSymbol(_type.BaseType), "Array base type");
            }

            dependencyList.Add(factory.VTable(_type), "VTable");

            return dependencyList;
        }
Пример #5
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = new DependencyList();

            if (factory.TypeSystemContext.HasEagerStaticConstructor(_type))
            {
                dependencyList.Add(factory.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
            }

            dependencyList.Add(factory.GCStaticsRegion, "GCStatics Region");
            if (factory.Target.Abi == TargetAbi.CoreRT)
            {
                dependencyList.Add(GetGCStaticEETypeNode(factory), "GCStatic EEType");
                if (_preInitFieldInfos != null)
                {
                    dependencyList.Add(factory.GCStaticsPreInitDataNode(_type), "PreInitData node");
                }
            }
            else
            {
                dependencyList.Add(((UtcNodeFactory)factory).TypeGCStaticDescSymbol(_type), "GC Desc");
            }

            dependencyList.Add(factory.GCStaticIndirection(_type), "GC statics indirection");
            EETypeNode.AddDependenciesForStaticsNode(factory, _type, ref dependencyList);

            return(dependencyList);
        }
Пример #6
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory context)
        {
            DependencyList dependencies = new DependencyList();

            dependencies.Add(new DependencyListEntry(_methodSig, "NativeLayoutMethodEntryVertexNode method signature"));
            if ((_flags & MethodEntryFlags.CreateInstantiatedSignature) != 0)
            {
                dependencies.Add(new DependencyListEntry(context.NecessaryTypeSymbol(_method.OwningType), "NativeLayoutMethodEntryVertexNode containing type"));
                foreach (var arg in _method.Instantiation)
                {
                    dependencies.Add(new DependencyListEntry(context.NecessaryTypeSymbol(arg), "NativeLayoutMethodEntryVertexNode instantiation argument type"));
                }
            }
            else
            {
                dependencies.Add(new DependencyListEntry(_containingTypeSig, "NativeLayoutMethodEntryVertexNode containing type signature"));
                if (_method.HasInstantiation)
                {
                    foreach (var arg in _instantiationArgsSig)
                    {
                        dependencies.Add(new DependencyListEntry(arg, "NativeLayoutMethodEntryVertexNode instantiation argument signature"));
                    }
                }
            }

            if ((_flags & MethodEntryFlags.SaveEntryPoint) != 0)
            {
                bool        getUnboxingStub      = _method.OwningType.IsValueType && !_method.Signature.IsStatic;
                IMethodNode methodEntryPointNode = context.MethodEntrypoint(_method, getUnboxingStub);
                dependencies.Add(new DependencyListEntry(methodEntryPointNode, "NativeLayoutMethodEntryVertexNode entrypoint"));
            }

            return(dependencies);
        }
Пример #7
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory factory)
        {
            DependencyList dependencies = new DependencyList();

            // TODO: https://github.com/dotnet/corert/issues/3224
            // Reflection invoke stub handling is here because in the current reflection model we reflection-enable
            // all methods that are compiled. Ideally the list of reflection enabled methods should be known before
            // we even start the compilation process (with the invocation stubs being compilation roots like any other).
            // The existing model has it's problems: e.g. the invocability of the method depends on inliner decisions.
            if (factory.MetadataManager.IsReflectionInvokable(_decl) && _decl.IsAbstract)
            {
                if (factory.MetadataManager.HasReflectionInvokeStubForInvokableMethod(_decl) && !_decl.IsCanonicalMethod(CanonicalFormKind.Any))
                {
                    MethodDesc invokeStub      = factory.MetadataManager.GetReflectionInvokeStub(_decl);
                    MethodDesc canonInvokeStub = invokeStub.GetCanonMethodTarget(CanonicalFormKind.Specific);
                    if (invokeStub != canonInvokeStub)
                    {
                        dependencies.Add(new DependencyListEntry(factory.MetadataManager.DynamicInvokeTemplateData, "Reflection invoke template data"));
                        factory.MetadataManager.DynamicInvokeTemplateData.AddDependenciesDueToInvokeTemplatePresence(ref dependencies, factory, canonInvokeStub);
                    }
                    else
                    {
                        dependencies.Add(new DependencyListEntry(factory.MethodEntrypoint(invokeStub), "Reflection invoke"));
                    }
                }

                dependencies.AddRange(ReflectionVirtualInvokeMapNode.GetVirtualInvokeMapDependencies(factory, _decl));
            }

            MethodDesc canonDecl = _decl.GetCanonMethodTarget(CanonicalFormKind.Specific);

            if (canonDecl != _decl)
            {
                dependencies.Add(new DependencyListEntry(factory.VirtualMethodUse(canonDecl), "Canonical method"));
            }

            dependencies.Add(new DependencyListEntry(factory.VTable(_decl.OwningType), "VTable of a VirtualMethodUse"));

            return(dependencies);
        }
Пример #8
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            if (_constructed)
            {
                DependencyList dependencyList = new DependencyList();
                if (_type.RuntimeInterfaces.Length > 0)
                {
                    dependencyList.Add(factory.InterfaceDispatchMap(_type), "Interface dispatch map");
                }

                if (_type.IsArray)
                {
                    // Array EEType depends on System.Array's virtuals. Array EETypes don't point to
                    // their base type (i.e. there's no reloc based dependency making this "just work").
                    dependencyList.Add(factory.ConstructedTypeSymbol(_type.BaseType), "Array base type");
                }

                return(dependencyList);
            }

            return(null);
        }
Пример #9
0
 protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory context)
 {
     if (_id == ReadyToRunHelperId.VirtualCall)
     {
         DependencyList dependencyList = new DependencyList();
         dependencyList.Add(context.VirtualMethodUse((MethodDesc)_target), "ReadyToRun Virtual Method Call");
         return(dependencyList);
     }
     else
     {
         return(null);
     }
 }
Пример #10
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory context)
        {
            TypeDesc owningType = _method.OwningType;

            if (context.TypeInitializationManager.HasEagerStaticConstructor(owningType))
            {
                var result = new DependencyList();
                result.Add(context.EagerCctorIndirection(owningType.GetStaticConstructor()), "Eager .cctor");
                return(result);
            }

            return(null);
        }
Пример #11
0
 protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory context)
 {
     if (Helper.Id == ReadyToRunHelperId.VirtualCall)
     {
         DependencyList dependencyList = new DependencyList();
         dependencyList.Add(context.VirtualMethodUse((MethodDesc)Helper.Target), "ReadyToRun Virtual Method Call");
         return dependencyList;
     }
     else
     {
         return null;
     }
 }
Пример #12
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory factory)
        {
            var dependencies = new DependencyList();

            foreach (Object node in _dependencies)
            {
                dependencies.Add(node, "Wasm code ");
            }

            CodeBasedDependencyAlgorithm.AddDependenciesDueToMethodCodePresence(ref dependencies, factory, _method);

            return(dependencies);
        }
Пример #13
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory factory)
        {
            DependencyList dependencies = new DependencyList();

            CustomAttributeBasedDependencyAlgorithm.AddDependenciesDueToCustomAttributes(ref dependencies, factory, ((EcmaType)_type));

            DefType containingType = _type.ContainingType;

            if (containingType != null)
            {
                dependencies.Add(factory.TypeMetadata((MetadataType)containingType), "Containing type of a reflectable type");
            }
            else
            {
                dependencies.Add(factory.ModuleMetadata(_type.Module), "Containing module of a reflectable type");
            }

            var mdManager = (UsageBasedMetadataManager)factory.MetadataManager;

            if (_type.IsDelegate)
            {
                // A delegate type metadata is rather useless without the Invoke method.
                // If someone reflects on a delegate, chances are they're going to look at the signature.
                var invokeMethod = _type.GetMethod("Invoke", null);
                if (!mdManager.IsReflectionBlocked(invokeMethod))
                {
                    dependencies.Add(factory.MethodMetadata(invokeMethod), "Delegate invoke method metadata");
                }
            }

            if (_type.IsEnum)
            {
                // A lot of the enum reflection actually happens on top of the respective EEType (e.g. getting the underlying type),
                // so for enums also include their EEType.
                dependencies.Add(factory.MaximallyConstructableType(_type), "Reflectable enum");
            }

            // If the user asked for complete metadata to be generated for all types that are getting metadata, ensure that.
            if ((mdManager._generationOptions & UsageBasedMetadataGenerationOptions.CompleteTypesOnly) != 0)
            {
                foreach (MethodDesc method in _type.GetMethods())
                {
                    if (!mdManager.IsReflectionBlocked(method))
                    {
                        dependencies.Add(factory.MethodMetadata(method), "Complete metadata for type");
                    }
                }

                foreach (FieldDesc field in _type.GetFields())
                {
                    if (!mdManager.IsReflectionBlocked(field))
                    {
                        dependencies.Add(factory.FieldMetadata(field), "Complete metadata for type");
                    }
                }
            }

            return(dependencies);
        }
Пример #14
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList result = new DependencyList();

            if (!factory.VTable(_targetMethod.OwningType).HasFixedSlots)
            {
                result.Add(factory.VirtualMethodUse(_targetMethod), "Interface method use");
            }

            factory.MetadataManager.GetDependenciesDueToVirtualMethodReflectability(ref result, factory, _targetMethod);

            return(result);
        }
Пример #15
0
        /// <summary>
        /// Helper method to compute the dependencies that would be needed for reflection field lookup.
        /// </summary>
        public static void AddReflectionFieldMapEntryDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            if (!factory.MetadataManager.SupportsReflection)
            {
                return;
            }

            // TODO: https://github.com/dotnet/corert/issues/3224
            // Reflection static field bases handling is here because in the current reflection model we reflection-enable
            // all fields of types that are compiled. Ideally the list of reflection enabled fields should be known before
            // we even start the compilation process (with the static bases being compilation roots like any other).
            if (type is MetadataType && !type.IsCanonicalSubtype(CanonicalFormKind.Any))
            {
                MetadataType metadataType = (MetadataType)type;

                // For instantiated types, we write the static fields offsets directly into the table, and we do not reference the gc/non-gc statics nodes
                if (!type.HasInstantiation)
                {
                    if (metadataType.GCStaticFieldSize.AsInt > 0)
                    {
                        dependencies.Add(factory.TypeGCStaticsSymbol(metadataType), "GC statics for ReflectionFieldMap entry");
                    }

                    if (metadataType.NonGCStaticFieldSize.AsInt > 0)
                    {
                        dependencies.Add(factory.TypeNonGCStaticsSymbol(metadataType), "Non-GC statics for ReflectionFieldMap entry");
                    }
                }

                if (metadataType.ThreadStaticFieldSize.AsInt > 0)
                {
                    if (factory.Target.Abi == TargetAbi.ProjectN)
                    {
                        dependencies.Add(((UtcNodeFactory)factory).TypeThreadStaticsOffsetSymbol(metadataType), "Thread statics for ReflectionFieldMap entry");
                    }
                    // TODO: TLS for CoreRT
                }
            }
        }
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencies = new DependencyList();

            foreach (DependencyNodeCore <NodeFactory> dependency in _lookupSignature.NonRelocDependenciesFromUsage(factory))
            {
                dependencies.Add(new DependencyListEntry(dependency, "GenericLookupResultDependency"));
            }

            // Root the template for the type while we're hitting its dictionary cells. In the future, we may
            // want to control this via type reflectability instead.
            if (_dictionaryOwner is MethodDesc)
            {
                dependencies.Add(factory.NativeLayout.TemplateMethodLayout((MethodDesc)_dictionaryOwner), "Type loader template");
            }
            else
            {
                dependencies.Add(factory.NativeLayout.TemplateTypeLayout((TypeDesc)_dictionaryOwner), "Type loader template");
            }

            return(dependencies);
        }
Пример #17
0
        public static void GetTemplateTypeDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            if (!factory.MetadataManager.SupportsReflection)
            {
                return;
            }

            TypeDesc templateType = ConvertArrayOfTToRegularArray(factory, type);

            if (!IsEligibleToHaveATemplate(templateType))
            {
                return;
            }

            if ((factory.Target.Abi == TargetAbi.ProjectN) && !ProjectNDependencyBehavior.EnableFullAnalysis)
            {
                // If the type does not have fully constructed type, don't track its dependencies.
                // TODO: Remove the workaround once we stop using the STS dependency analysis.
                IDependencyNode node;
                if (ConstructedEETypeNode.CreationAllowed(templateType))
                {
                    node = factory.ConstructedTypeSymbol(templateType);
                }
                else
                {
                    node = factory.NecessaryTypeSymbol(templateType);
                }

                if (!node.Marked)
                {
                    return;
                }
            }

            dependencies = dependencies ?? new DependencyList();
            dependencies.Add(new DependencyListEntry(factory.NecessaryTypeSymbol(templateType), "Template type"));
            dependencies.Add(new DependencyListEntry(factory.NativeLayout.TemplateTypeLayout(templateType), "Template Type Layout"));
        }
Пример #18
0
        public static void GetVirtualInvokeMapDependencies(ref DependencyList dependencies, NodeFactory factory, MethodDesc method)
        {
            if (!factory.MetadataManager.SupportsReflection)
            {
                return;
            }

            if (NeedsVirtualInvokeInfo(method))
            {
                dependencies = dependencies ?? new DependencyList();

                if (factory.Target.Abi == TargetAbi.ProjectN)
                {
                    dependencies.Add(
                        factory.NecessaryTypeSymbol(method.OwningType.GetTypeDefinition()),
                        "Reflection virtual invoke owning type");
                }
                else
                {
                    dependencies.Add(
                        factory.NecessaryTypeSymbol(method.OwningType.ConvertToCanonForm(CanonicalFormKind.Specific)),
                        "Reflection virtual invoke owning type");
                }

                NativeLayoutMethodNameAndSignatureVertexNode nameAndSig       = factory.NativeLayout.MethodNameAndSignatureVertex(method.GetTypicalMethodDefinition());
                NativeLayoutPlacedSignatureVertexNode        placedNameAndSig = factory.NativeLayout.PlacedSignatureVertex(nameAndSig);
                dependencies.Add(placedNameAndSig, "Reflection virtual invoke method signature");

                if (!method.HasInstantiation)
                {
                    MethodDesc slotDefiningMethod = MetadataVirtualMethodAlgorithm.FindSlotDefiningMethodForVirtualMethod(method);
                    if (!factory.VTable(slotDefiningMethod.OwningType).HasFixedSlots)
                    {
                        dependencies.Add(factory.VirtualMethodUse(slotDefiningMethod), "Reflection virtual invoke method");
                    }
                }
            }
        }
Пример #19
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory factory)
        {
            DependencyList dependencies = new DependencyList();

            // Make sure the canonical body gets generated
            dependencies.Add(new DependencyListEntry(CanonicalMethodNode, "Canonical body"));

            // Instantiate the runtime determined dependencies of the canonical method body
            // with the concrete instantiation of the method to get concrete dependencies.
            Instantiation typeInst   = Method.OwningType.Instantiation;
            Instantiation methodInst = Method.Instantiation;
            IEnumerable <DependencyListEntry> staticDependencies = CanonicalMethodNode.GetStaticDependencies(factory);

            if (staticDependencies != null)
            {
                foreach (DependencyListEntry canonDep in staticDependencies)
                {
                    var runtimeDep = canonDep.Node as INodeWithRuntimeDeterminedDependencies;
                    if (runtimeDep != null)
                    {
                        dependencies.AddRange(runtimeDep.InstantiateDependencies(factory, typeInst, methodInst));
                    }
                }
            }

            if (Method.HasInstantiation)
            {
                if (Method.IsVirtual)
                {
                    dependencies.Add(new DependencyListEntry(factory.GVMDependencies(Method), "GVM Dependencies Support for method dictionary"));
                }

                // Dictionary dependency
                dependencies.Add(new DependencyListEntry(factory.MethodGenericDictionary(Method), "Method dictionary"));
            }

            return(dependencies);
        }
Пример #20
0
        /// <summary>
        /// Helper method to compute the dependencies that would be needed by a hashtable entry for statics info lookup.
        /// This helper is used by EETypeNode, which is used by the dependency analysis to compute the statics hashtable
        /// entries for the compiled types.
        /// </summary>
        public static void AddStaticsInfoDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            if (!factory.MetadataManager.SupportsReflection)
            {
                return;
            }

            if (type is MetadataType && type.HasInstantiation && !type.IsCanonicalSubtype(CanonicalFormKind.Any))
            {
                MetadataType metadataType = (MetadataType)type;

                // NOTE: The StaticsInfoHashtable entries need to reference the gc and non-gc static nodes through an indirection cell.
                // The StaticsInfoHashtable entries only exist for static fields on generic types.

                if (metadataType.GCStaticFieldSize.AsInt > 0)
                {
                    dependencies.Add(factory.Indirection(factory.TypeGCStaticsSymbol(metadataType)), "GC statics indirection for StaticsInfoHashtable");
                }

                if (metadataType.NonGCStaticFieldSize.AsInt > 0 || factory.TypeSystemContext.HasLazyStaticConstructor(type))
                {
                    // The entry in the StaticsInfoHashtable points at the beginning of the static fields data, rather than the cctor
                    // context offset.
                    dependencies.Add(factory.Indirection(factory.TypeNonGCStaticsSymbol(metadataType)), "Non-GC statics indirection for StaticsInfoHashtable");
                }

                if (metadataType.ThreadStaticFieldSize.AsInt > 0)
                {
                    if (factory.Target.Abi == TargetAbi.ProjectN)
                    {
                        UtcNodeFactory utcFactory = (UtcNodeFactory)factory;
                        dependencies.Add(utcFactory.TypeThreadStaticsIndexSymbol(metadataType), "Thread statics index indirection for StaticsInfoHashtable");
                        dependencies.Add(utcFactory.TypeThreadStaticsOffsetSymbol(metadataType), "Thread statics offset indirection for StaticsInfoHashtable");
                    }
                    // TODO: TLS for CoreRT
                }
            }
        }
Пример #21
0
        /// <summary>
        /// Helper method to compute the dependencies that would be needed for reflection field lookup.
        /// </summary>
        public static void AddReflectionFieldMapEntryDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            // TODO: https://github.com/dotnet/corert/issues/3224
            // Reflection static field bases handling is here because in the current reflection model we reflection-enable
            // all fields of types that are compiled. Ideally the list of reflection enabled fields should be known before
            // we even start the compilation process (with the static bases being compilation roots like any other).
            if (type is MetadataType && !type.HasInstantiation && !type.IsCanonicalSubtype(CanonicalFormKind.Any))
            {
                MetadataType metadataType = (MetadataType)type;

                if (metadataType.GCStaticFieldSize.AsInt > 0)
                {
                    dependencies.Add(factory.TypeGCStaticsSymbol(metadataType), "GC statics for ReflectionFieldMap entry");
                }

                if (metadataType.NonGCStaticFieldSize.AsInt > 0)
                {
                    dependencies.Add(factory.TypeNonGCStaticsSymbol(metadataType), "Non-GC statics for ReflectionFieldMap entry");
                }

                // TODO: TLS dependencies
            }
        }
Пример #22
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory context)
        {
            DependencyList dependencies = new DependencyList();

            foreach (MethodDesc method in Type.GetAllMethods())
            {
                if (!method.IsGenericMethodDefinition && context.CompilationModuleGroup.VersionsWithMethodBody(method))
                {
                    dependencies.Add(context.MethodEntrypoint(method), $"Method on type {Type.ToString()}");
                }
            }

            return(dependencies);
        }
Пример #23
0
        public static void GetTemplateTypeDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            TypeDesc templateType = ConvertArrayOfTToRegularArray(factory, type);

            if (!IsEligibleToHaveATemplate(templateType))
            {
                return;
            }

            if (factory.Target.Abi == TargetAbi.ProjectN)
            {
                // If the type does not have fully constructed type, don't track its dependencies.
                // TODO: Remove the workaround once we stop using the STS dependency analysis.
                if (!factory.ConstructedTypeSymbol(templateType).Marked)
                {
                    return;
                }
            }

            dependencies = dependencies ?? new DependencyList();
            dependencies.Add(new DependencyListEntry(factory.NecessaryTypeSymbol(templateType), "Template type"));
            dependencies.Add(new DependencyListEntry(factory.NativeLayout.TemplateTypeLayout(templateType), "Template Type Layout"));
        }
Пример #24
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = null;

            if (factory.TypeSystemContext.HasEagerStaticConstructor(_type))
            {
                dependencyList = new DependencyList();
                dependencyList.Add(factory.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
            }

            EETypeNode.AddDependenciesForStaticsNode(factory, _type, ref dependencyList);

            return(dependencyList);
        }
Пример #25
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencies = null;

            if (!_targetMethod.IsMethodDefinition && !_targetMethod.OwningType.IsGenericDefinition &&
                _targetMethod.HasInstantiation && _targetMethod.IsVirtual)
            {
                dependencies = dependencies ?? new DependencyList();
                dependencies.Add(factory.GVMDependencies(_targetMethod), "GVM dependencies for runtime method handle");
            }

            // TODO: https://github.com/dotnet/corert/issues/3224
            // We should figure out reflectable methods when scanning for reflection
            MethodDesc methodDefinition = _targetMethod.GetTypicalMethodDefinition();

            if (factory.MetadataManager.CanGenerateMetadata(methodDefinition))
            {
                dependencies = dependencies ?? new DependencyList();
                dependencies.Add(factory.MethodMetadata(methodDefinition), "LDTOKEN");
            }

            return(dependencies);
        }
        public static void GetVirtualInvokeMapDependencies(ref DependencyList dependencies, NodeFactory factory, MethodDesc method)
        {
            if (NeedsVirtualInvokeInfo(method))
            {
                dependencies = dependencies ?? new DependencyList();

                if (factory.Target.Abi == TargetAbi.ProjectN)
                {
                    dependencies.Add(
                        factory.NecessaryTypeSymbol(method.OwningType.GetTypeDefinition()),
                        "Reflection virtual invoke owning type");
                }
                else
                {
                    dependencies.Add(
                        factory.NecessaryTypeSymbol(method.OwningType.ConvertToCanonForm(CanonicalFormKind.Specific)),
                        "Reflection virtual invoke owning type");
                }

                NativeLayoutMethodNameAndSignatureVertexNode nameAndSig       = factory.NativeLayout.MethodNameAndSignatureVertex(method.GetTypicalMethodDefinition());
                NativeLayoutPlacedSignatureVertexNode        placedNameAndSig = factory.NativeLayout.PlacedSignatureVertex(nameAndSig);
                dependencies.Add(placedNameAndSig, "Reflection virtual invoke method signature");
            }
        }
Пример #27
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = new DependencyList();

            if (factory.PreinitializationManager.HasEagerStaticConstructor(_type))
            {
                dependencyList.Add(factory.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
            }

            ModuleUseBasedDependencyAlgorithm.AddDependenciesDueToModuleUse(ref dependencyList, factory, _type.Module);

            EETypeNode.AddDependenciesForStaticsNode(factory, _type, ref dependencyList);

            return(dependencyList);
        }
Пример #28
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencies = null;

            if (!_targetMethod.IsMethodDefinition && !_targetMethod.OwningType.IsGenericDefinition &&
                _targetMethod.HasInstantiation && _targetMethod.IsVirtual)
            {
                dependencies = dependencies ?? new DependencyList();
                dependencies.Add(factory.GVMDependencies(_targetMethod.GetCanonMethodTarget(CanonicalFormKind.Specific)), "GVM dependencies for runtime method handle");
            }

            factory.MetadataManager.GetDependenciesDueToLdToken(ref dependencies, factory, _targetMethod);

            return(dependencies);
        }
Пример #29
0
        public static DependencyList GetTemplateTypeDependencies(NodeFactory factory, TypeDesc type)
        {
            if (!IsEligibleToHaveATemplate(type))
            {
                return(null);
            }

            if (factory.Target.Abi == TargetAbi.ProjectN)
            {
                // If the type does not have fully constructed type, don't track its dependencies.
                // TODO: Remove the workaround once we stop using the STS dependency analysis.
                if (!factory.ConstructedTypeSymbol(type).Marked)
                {
                    return(null);
                }
            }

            DependencyList dependencies = new DependencyList();

            dependencies.Add(new DependencyListEntry(factory.NecessaryTypeSymbol(type), "Template type"));
            dependencies.Add(new DependencyListEntry(factory.NativeLayout.TemplateTypeLayout(GetActualTemplateTypeForType(factory, type)), "Template Type Layout"));

            return(dependencies);
        }
Пример #30
0
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory context)
        {
            DependencyList dependencies = null;

            context.MetadataManager.GetDependenciesDueToVirtualMethodReflectability(ref dependencies, context, _method);

            if (!_method.IsAbstract)
            {
                bool validInstantiation =
                    _method.IsSharedByGenericInstantiations || (      // Non-exact methods are always valid instantiations (always pass constraints check)
                        _method.Instantiation.CheckValidInstantiationArguments() &&
                        _method.OwningType.Instantiation.CheckValidInstantiationArguments() &&
                        _method.CheckConstraints());

                if (validInstantiation)
                {
                    if (context.TypeSystemContext.SupportsUniversalCanon && _method.IsGenericDepthGreaterThan(UniversalCanonGVMDepthHeuristic_CanonDepth))
                    {
                        // fall back to using the universal generic variant of the generic method
                        return(dependencies);
                    }

                    bool getUnboxingStub = _method.OwningType.IsValueType;
                    dependencies = dependencies ?? new DependencyList();
                    dependencies.Add(context.MethodEntrypoint(_method, getUnboxingStub), "GVM Dependency - Canon method");

                    if (_method.IsSharedByGenericInstantiations)
                    {
                        dependencies.Add(context.NativeLayout.TemplateMethodEntry(_method), "GVM Dependency - Template entry");
                        dependencies.Add(context.NativeLayout.TemplateMethodLayout(_method), "GVM Dependency - Template");
                    }
                }
            }

            return(dependencies);
        }
        public void InitializeDependencies(NodeFactory factory, IEnumerable <DependencyListEntry> dependencies)
        {
            _dependencies = new DependencyList(dependencies);
            CodeBasedDependencyAlgorithm.AddDependenciesDueToMethodCodePresence(ref _dependencies, factory, _method);

            if (factory.TypeSystemContext.IsSpecialUnboxingThunk(_method))
            {
                // Special unboxing thunks reference a MethodAssociatedDataNode that points to the non-unboxing version.
                // This dependency is redundant with the dependency list we constructed above, with a notable
                // exception of special unboxing thunks for byref-like types. Those don't actually unbox anything
                // and their body is a dummy. We capture the dependency here.
                MethodDesc nonUnboxingMethod = factory.TypeSystemContext.GetTargetOfSpecialUnboxingThunk(_method);
                _dependencies.Add(new DependencyListEntry(factory.MethodEntrypoint(nonUnboxingMethod, false), "Non-unboxing method"));
            }
        }
Пример #32
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencyList = base.ComputeNonRelocationBasedDependencies(factory);

            // Ensure that we track the necessary type symbol if we are working with a constructed type symbol.
            // The emitter will ensure we don't emit both, but this allows us assert that we only generate
            // relocs to nodes we emit.
            dependencyList.Add(factory.NecessaryTypeSymbol(_type), "Necessary type symbol related to CanonicalEETypeNode");

            DefType closestDefType = _type.GetClosestDefType();

            if (_type.RuntimeInterfaces.Length > 0)
            {
                dependencyList.Add(factory.InterfaceDispatchMap(_type), "Canonical interface dispatch map");
            }

            dependencyList.Add(factory.VTable(_type), "VTable");

            // TODO: native layout dependencies (template type entries)

            // TODO: other dependencies needed by the dynamic type loader?

            return(dependencyList);
        }
Пример #33
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            DependencyList dependencies = new DependencyList();

            // Include the optional fields by default. We don't know if optional fields will be needed until
            // all of the interface usage has been stabilized. If we end up not needing it, the EEType node will not
            // generate any relocs to it, and the optional fields node will instruct the object writer to skip
            // emitting it.
            dependencies.Add(new DependencyListEntry(_optionalFieldsNode, "Optional fields"));

            StaticsInfoHashtableNode.AddStaticsInfoDependencies(ref dependencies, factory, _type);
            ReflectionFieldMapNode.AddReflectionFieldMapEntryDependencies(ref dependencies, factory, _type);

            return(dependencies);
        }
Пример #34
0
        /// <summary>
        /// Helper method to compute the dependencies that would be needed by a hashtable entry for statics info lookup.
        /// This helper is used by EETypeNode, which is used by the dependency analysis to compute the statics hashtable
        /// entries for the compiled types.
        /// </summary>
        public static void AddStaticsInfoDependencies(ref DependencyList dependencies, NodeFactory factory, TypeDesc type)
        {
            if (type is MetadataType && type.HasInstantiation && !type.IsCanonicalSubtype(CanonicalFormKind.Any))
            {
                MetadataType metadataType = (MetadataType)type;

                // NOTE: The StaticsInfoHashtable entries need to reference the gc and non-gc static nodes through an indirection cell.
                // The StaticsInfoHashtable entries only exist for static fields on generic types.

                if (metadataType.GCStaticFieldSize.AsInt > 0)
                {
                    dependencies.Add(factory.Indirection(factory.TypeGCStaticsSymbol(metadataType)), "GC statics indirection for StaticsInfoHashtable");
                }

                if (metadataType.NonGCStaticFieldSize.AsInt > 0 || factory.TypeSystemContext.HasLazyStaticConstructor(type))
                {
                    // The entry in the StaticsInfoHashtable points at the beginning of the static fields data, rather than the cctor
                    // context offset.
                    dependencies.Add(factory.Indirection(factory.TypeNonGCStaticsSymbol(metadataType)), "Non-GC statics indirection for StaticsInfoHashtable");
                }

                // TODO: TLS dependencies
            }
        }
        public override IEnumerable <DependencyListEntry> GetStaticDependencies(NodeFactory factory)
        {
            DependencyList dependencies = null;

            factory.MetadataManager.GetDependenciesDueToReflectability(ref dependencies, factory, _method);

            MethodDesc canonMethod = _method.GetCanonMethodTarget(CanonicalFormKind.Specific);

            if (canonMethod != _method)
            {
                dependencies = dependencies ?? new DependencyList();
                dependencies.Add(factory.ReflectableMethod(canonMethod), "Canonical version of the reflectable method");
            }

            return(dependencies);
        }
Пример #36
0
 protected override DependencyList InitExpectedDependencies()
 {
     DependencyList result = new DependencyList();
     foreach (var input in Inputs)
     {
         result.Add(input.Type);
     }
     return result;
 }
Пример #37
0
 protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
 {
     if (_id == ReadyToRunHelperId.VirtualCall)
     {
         DependencyList dependencyList = new DependencyList();
         dependencyList.Add(factory.VirtualMethodUse((MethodDesc)_target), "ReadyToRun Virtual Method Call");
         dependencyList.Add(factory.VTable(((MethodDesc)_target).OwningType), "ReadyToRun Virtual Method Call Target VTable");
         return dependencyList;
     }
     else if (_id == ReadyToRunHelperId.ResolveVirtualFunction)
     {
         DependencyList dependencyList = new DependencyList();
         dependencyList.Add(factory.VirtualMethodUse((MethodDesc)_target), "ReadyToRun Virtual Method Address Load");
         return dependencyList;
     }
     else
     {
         return null;
     }
 }
Пример #38
0
 protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
 {
     DependencyList result = new DependencyList();
     result.Add(new DependencyListEntry(factory.ShadowConcreteMethod(Method), "Method represented"));
     return result;
 }
Пример #39
0
        /// <summary>
        /// Runs any required bootstrapper tasks.
        /// </summary>
        private static void RunTasks()
        {
            var tasks = Container.GetExports<IBootstrapperTask, INamedDependencyMetadata>();
            var list = new DependencyList<Lazy<IBootstrapperTask, INamedDependencyMetadata>, string>(
                l => l.Metadata.Name,
                l => l.Metadata.Dependencies);

            foreach (var task in tasks)
                list.Add(task);

            foreach (var task in list)
                task.Value.Run(Container);
        }
Пример #40
0
 protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
 {
     var result = new DependencyList();
     result.Add(factory.InterfaceDispatchMapIndirection(_type), "Interface dispatch map indirection node");
     return result;
 }
Пример #41
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory context)
        {
            if (context.TypeInitializationManager.HasEagerStaticConstructor(_type))
            {
                var result = new DependencyList();
                result.Add(context.EagerCctorIndirection(_type.GetStaticConstructor()), "Eager .cctor");
                return result;
            }

            return null;
        }
Пример #42
0
        protected override DependencyList ComputeNonRelocationBasedDependencies(NodeFactory factory)
        {
            if (_constructed)
            {
                DependencyList dependencyList = new DependencyList();
                if (_type.RuntimeInterfaces.Length > 0)
                {
                    dependencyList.Add(factory.InterfaceDispatchMap(_type), "Interface dispatch map");
                }

                if (_type.IsArray)
                {
                    // Array EEType depends on System.Array's virtuals. Array EETypes don't point to
                    // their base type (i.e. there's no reloc based dependency making this "just work").
                    dependencyList.Add(factory.ConstructedTypeSymbol(_type.BaseType), "Array base type");
                }

                return dependencyList;
            }

            return null;
        }