4d30aa99d740cb54062035bb47bd4f2afe4320bb
[mono.git] / mcs / tools / corcompare / ToDoAssembly.cs
1 // Mono.Util.CorCompare.ToDoAssembly
2 //
3 // Author(s):
4 //   Nick Drochak (ndrochak@gol.com)
5 //
6 // (C) 2001-2002 Nick Drochak
7
8 using System;
9 using System.Collections;
10 using System.IO;
11 using System.Text;
12 using System.Xml;
13 using Mono.Cecil;
14
15 namespace Mono.Util.CorCompare {
16
17         /// <summary>
18         ///     Represents an assembly that has missing or MonoTODO classes
19         /// </summary>
20         /// <remarks>
21         ///     created by - Nick
22         ///     created on - 2/20/2002 10:43:57 PM
23         /// </remarks>
24         class ToDoAssembly : MissingBase
25         {
26                 // these types are in mono corlib, but not in the dll we are going to examine.
27                 ArrayList MissingTypes = new ArrayList();
28                 ArrayList rgNamespaces = new ArrayList();
29                 string strName;
30                 AssemblyDefinition assMono;
31                 AssemblyDefinition assMS;
32                 TypeDefinitionCollection rgTypesMono;
33                 TypeDefinitionCollection rgTypesMS;
34
35                 protected static Hashtable htGhostTypes;
36                 private static string[] rgstrGhostTypes = {"System.Object", "System.ValueType", "System.Delegate", "System.Enum"};
37
38
39                 static ToDoAssembly ()
40                 {
41                         htGhostTypes = new Hashtable ();
42
43                         foreach (string strGhostType in rgstrGhostTypes)
44                         {
45                                 htGhostTypes.Add (strGhostType, null);
46                         }
47                 }
48
49                 public static ToDoAssembly Load (string strFileMono, string strName, string strNameMS)
50                 {
51                         AssemblyDefinition assemblyMono = null;//TODO AssemblyDefinition.LoadFrom (strFileMono);
52                         AssemblyDefinition assemblyMS = null;//TODO AssemblyDefinition.LoadWithPartialName (strNameMS);
53
54                         return new ToDoAssembly (strName, assemblyMono, assemblyMS);
55                 }
56
57                 public ToDoAssembly (string _strName, AssemblyDefinition _assMono, AssemblyDefinition _assMS)
58                 {
59                         strName = _strName;
60                         assMono = _assMono;
61                         assMS = _assMS;
62
63                         rgTypesMono = assMono.MainModule.Types;
64                         rgTypesMS = assMS.MainModule.Types;
65                         m_nodeStatus = new NodeStatus (_assMono, _assMS);
66                 }
67
68                 public override string Name {
69                         get {
70                                 return strName;
71                         }
72                 }
73
74                 public override string Type
75                 {
76                         get { return "assembly"; }
77                 }
78
79                 private Hashtable GetNamespaceMap (TypeDefinitionCollection rgTypes)
80                 {
81                         Hashtable mapTypes = new Hashtable ();
82                         foreach (TypeDefinition t in rgTypes)
83                         {
84                                 if (t != null)
85                                 {
86                                         string strName = t.FullName;
87                                         string strNamespace = t.Namespace;
88                                         if (strNamespace != null && strNamespace.Length > 0 &&
89                                                 strName != null && strName.Length > 0 &&
90                                                 !htGhostTypes.Contains (strName))
91                                         {
92                                                 TypeDefinitionCollection rgContainedTypes = (TypeDefinitionCollection) mapTypes [strNamespace];
93                                                 if (rgContainedTypes == null)
94                                                 {
95                                                         rgContainedTypes = new TypeDefinitionCollection (t.Module);
96                                                         mapTypes [strNamespace] = rgContainedTypes;
97                                                 }
98                                                 rgContainedTypes.Add (t);
99                                         }
100                                 }
101                         }
102                         return mapTypes;
103                 }
104
105                 public override NodeStatus Analyze ()
106                 {
107                         Hashtable mapTypesMono = GetNamespaceMap (rgTypesMono);
108                         Hashtable mapTypesMS = GetNamespaceMap (rgTypesMS);
109
110                         foreach (string strNamespaceMS in mapTypesMS.Keys)
111                         {
112                                 if (strNamespaceMS != null)
113                                 {
114                                         TypeDefinitionCollection rgContainedTypesMS = (TypeDefinitionCollection) mapTypesMS [strNamespaceMS];
115                                         TypeDefinitionCollection rgContainedTypesMono = (TypeDefinitionCollection) mapTypesMono [strNamespaceMS];
116                                         MissingNameSpace mns = new MissingNameSpace (strNamespaceMS, rgContainedTypesMono, rgContainedTypesMS);
117                                         NodeStatus nsNamespace = mns.Analyze ();
118                                         m_nodeStatus.AddChildren (nsNamespace);
119                                         if (rgTypesMono != null)
120                                                 mapTypesMono.Remove (strNamespaceMS);
121                                         rgNamespaces.Add (mns);
122                                 }
123                         }
124                         foreach (string strNamespaceMono in mapTypesMono.Keys)
125                         {
126                                 if (strNamespaceMono != null)
127                                 {
128                                         TypeDefinitionCollection rgContainedTypesMono = (TypeDefinitionCollection) mapTypesMono [strNamespaceMono];
129                                         MissingNameSpace mns = new MissingNameSpace (strNamespaceMono, rgContainedTypesMono, null);
130                                         NodeStatus nsNamespace = mns.Analyze ();
131                                         m_nodeStatus.AddChildren (nsNamespace);
132                                         rgNamespaces.Add (mns);
133                                 }
134                         }
135
136                         rgAttributes = new ArrayList ();
137                         NodeStatus nsAttributes = MissingAttribute.AnalyzeAttributes (
138                                 assMono.CustomAttributes,
139                                 assMS.CustomAttributes,
140                                 rgAttributes);
141                         m_nodeStatus.Add (nsAttributes);
142
143                         return m_nodeStatus;
144                 }
145
146
147                 public string CreateClassListReport() {
148                         Analyze ();
149                         if (rgNamespaces.Count == 0) return "";
150
151                         StringBuilder output = new StringBuilder();
152                         foreach (MissingNameSpace ns in rgNamespaces)
153                         {
154                                 string[] missingTypes = ns.MissingTypeNames(true);
155                                 if (missingTypes != null && missingTypes.Length > 0) {
156                                         string joinedNames = String.Join("\n", missingTypes);
157                                         output.Append(joinedNames + "\n");
158                                 }
159                         }
160                         return output.ToString();
161                 }
162
163                 public override XmlElement CreateXML (XmlDocument doc)
164                 {
165                         XmlElement assemblyElem = base.CreateXML (doc);
166
167                         if (rgNamespaces.Count > 0)
168                         {
169                                 XmlElement eltNamespaces = doc.CreateElement ("namespaces");
170                                 assemblyElem.AppendChild (eltNamespaces);
171
172                                 foreach (MissingNameSpace ns in rgNamespaces)
173                                 {
174                                         XmlElement eltNameSpace = ns.CreateXML (doc);
175                                         if (eltNameSpace != null)
176                                                 eltNamespaces.AppendChild (eltNameSpace);
177                                 }
178                         }
179                         return assemblyElem;
180                 }
181
182                 public void CreateXMLReport(string filename) {
183                         Analyze();
184
185                         XmlDocument outDoc;
186                         outDoc = new XmlDocument();
187                         outDoc.AppendChild(outDoc.CreateXmlDeclaration("1.0", null, null));
188
189                         XmlElement assembliesElem = outDoc.CreateElement("assemblies");
190                         outDoc.AppendChild(assembliesElem);
191
192                         XmlElement assemblyElem = CreateXML (outDoc);
193                         assembliesElem.AppendChild(assemblyElem);
194
195                         outDoc.Save(filename);
196                 }
197         }
198 }