private bool IsFilteredType(TypeEntry typeEntry) { string key = HeapSnapshot.GetKey(typeEntry); return (_filteredEntries.Any(e => (string.Compare(HeapSnapshot.GetKey(e), key) == 0))); }
private TypeEntryListViewItem GetItemFromEntry(ListView listview, TypeEntry entry) { foreach (TypeEntryListViewItem item in listview.Items) { TypeEntry tagEntry = (TypeEntry)item.Tag; if (string.Compare(HeapSnapshot.GetKey(tagEntry), HeapSnapshot.GetKey(entry)) == 0) { return(item); } } return(null); }
public static HeapSnapshot Compare(HeapSnapshot reference, HeapSnapshot current) { HeapSnapshot compare = new HeapSnapshot(); // loop on each entry in the current snapshot and compare with the reference foreach (var item in current.TypeStats) { // look for this class in the reference if (reference.TypeStats.ContainsKey(item.Key)) { TypeEntry referenceEntry = reference.TypeStats[item.Key]; if (referenceEntry.Count < item.Value.Count) { var entry = new TypeEntry(); entry.Name = string.Intern(referenceEntry.Name); entry.MethodTable = referenceEntry.MethodTable; entry.Count = item.Value.Count - referenceEntry.Count; entry.TotalSize = item.Value.TotalSize - referenceEntry.TotalSize; compare.TypeStats.Add(HeapSnapshot.GetKey(entry), entry); compare.ObjectCount += entry.Count; compare.Size += entry.TotalSize; } } else // don't forget the case where brand new type instances appear in current snapshot { var entry = new TypeEntry(); entry.Name = string.Intern(item.Value.Name); entry.MethodTable = item.Value.MethodTable; entry.Count = item.Value.Count; entry.TotalSize = item.Value.TotalSize; compare.TypeStats.Add(HeapSnapshot.GetKey(entry), entry); compare.ObjectCount += entry.Count; compare.Size += entry.TotalSize; } } return(compare); }
private static HeapSnapshot Compute(ClrHeap heap) { var snapshot = new HeapSnapshot(); foreach (ulong objAddress in heap.EnumerateObjectAddresses()) { ClrType type = heap.GetObjectType(objAddress); if (type == null) { continue; } var mt = type.MethodTable.ToString(); var name = type.Name; var key = HeapSnapshot.GetKey(name, mt); if (!snapshot.TypeStats.TryGetValue(key, out var entry)) { entry = new TypeEntry() { Name = name, MethodTable = mt }; snapshot.TypeStats[key] = entry; } entry.Count = entry.Count + 1; snapshot.ObjectCount = snapshot.ObjectCount + 1; var size = type.GetSize(objAddress); entry.TotalSize = entry.TotalSize + (long)size; snapshot.Size = snapshot.Size + (long)size; } return(snapshot); }
private static DumpHeapParsingState ParseAndAddTypeEntry(string line, HeapSnapshot snapshot) { if (line.StartsWith("Total")) { return(DumpHeapParsingState.End); } // MT Count TotalSize Class Name // 651d7ffc 1 12 System.Configuration.Internal.ConfigurationManagerInternal // // or in x64 // // 0x000007ff01221408 1,448 57,920 System.Xml.XmlQualifiedName // TypeEntry entry = new TypeEntry(); var pos = 0; var end = 0; string field; // 1. look for the MT end = line.IndexOf(SPACE); if (end == -1) { Debug.WriteLine("impossible to find the end of the MT field"); return(DumpHeapParsingState.Error); } field = line.Substring(pos, end - pos); entry.MethodTable = field; if (!SkipSpaces(line, ref end)) { Debug.WriteLine("impossible to find the start of the Count field"); return(DumpHeapParsingState.Error); } pos = end; // 2. look for the count end = line.IndexOf(SPACE, pos); if (end == -1) { Debug.WriteLine("impossible to find the end of the Count field"); return(DumpHeapParsingState.Error); } field = line.Substring(pos, end - pos); if (!long.TryParse(GetNumberFromString(field), out var count)) { Debug.WriteLine("invalid decimal value for the Count field"); return(DumpHeapParsingState.Error); } entry.Count = count; if (!SkipSpaces(line, ref end)) { Debug.WriteLine("impossible to find the start of the TotalSize field"); return(DumpHeapParsingState.Error); } pos = end; // 3. look for the total size end = line.IndexOf(SPACE, pos); if (end == -1) { Debug.WriteLine("impossible to find the end of the MT field"); return(DumpHeapParsingState.Error); } field = line.Substring(pos, end - pos); if (!long.TryParse(GetNumberFromString(field), out var totalSize)) { Debug.WriteLine("invalid decimal value for the TotalSize field"); return(DumpHeapParsingState.Error); } entry.TotalSize = totalSize; if (!SkipSpaces(line, ref end)) { Debug.WriteLine("impossible to find the start of the TotalSize field"); return(DumpHeapParsingState.Error); } pos = end; // 4. look for the class name field = line.Substring(pos); entry.Name = string.Intern(field); snapshot.ObjectCount += entry.Count; snapshot.Size += entry.TotalSize; string key = HeapSnapshot.GetKey(entry); if (!snapshot.TypeStats.ContainsKey(key)) { snapshot.TypeStats.Add(key, entry); } else { Debug.Fail("This should never happen"); throw new InvalidOperationException($"Impossible to find {key} for the entry"); } return(DumpHeapParsingState.TypeEntries); }