[linker] We need to mark nested types even if the declaring type isn't marked.
[mono.git] / mcs / tools / linker / Mono.Linker.Steps / MarkStep.cs
index 0e99e810203cb39600c34ab5c6d2fc6c67ae4b35..bc04fc5c7c024087188ffee7b0c337305b6aae8f 100644 (file)
@@ -69,16 +69,21 @@ namespace Mono.Linker.Steps {
                protected virtual void InitializeAssembly (AssemblyDefinition assembly)
                {
                        MarkAssembly (assembly);
-                       foreach (TypeDefinition type in assembly.MainModule.Types) {
-                               if (!Annotations.IsMarked (type))
-                                       continue;
 
+                       foreach (TypeDefinition type in assembly.MainModule.Types)
                                InitializeType (type);
-                       }
                }
 
                void InitializeType (TypeDefinition type)
                {
+                       if (type.HasNestedTypes) {
+                               foreach (var nested in type.NestedTypes)
+                                       InitializeType (nested);
+                       }
+
+                       if (!Annotations.IsMarked (type))
+                               return;
+
                        MarkType (type);
 
                        if (type.HasFields)
@@ -520,13 +525,14 @@ namespace Mono.Linker.Steps {
                                MarkFields (type, type.IsEnum);
 
                        if (type.HasInterfaces) {
-                               foreach (TypeReference iface in type.Interfaces)
-                                       MarkType (iface);
+                               foreach (var iface in type.Interfaces)
+                                       MarkType (iface.InterfaceType);
                        }
 
                        if (type.HasMethods) {
                                MarkMethodsIf (type.Methods, IsVirtualAndHasPreservedParent);
                                MarkMethodsIf (type.Methods, IsStaticConstructorPredicate);
+                               MarkMethodsIf (type.Methods, HasSerializationAttribute);
                        }
 
                        DoAdditionalTypeProcessing (type);
@@ -740,6 +746,25 @@ namespace Mono.Linker.Steps {
                        return method.IsConstructor && method.IsStatic;
                }
 
+               static bool HasSerializationAttribute (MethodDefinition method)
+               {
+                       if (!method.HasCustomAttributes)
+                               return false;
+                       foreach (var ca in method.CustomAttributes) {
+                               var cat = ca.AttributeType;
+                               if (cat.Namespace != "System.Runtime.Serialization")
+                                       continue;
+                               switch (cat.Name) {
+                               case "OnDeserializedAttribute":
+                               case "OnDeserializingAttribute":
+                               case "OnSerializedAttribute":
+                               case "OnSerializingAttribute":
+                                       return true;
+                               }
+                       }
+                       return false;
+               }
+
                static bool IsSerializable (TypeDefinition td)
                {
                        return (td.Attributes & TypeAttributes.Serializable) != 0;