TreeIter InternalFillType(HeapSnapshot file, int type, out bool cancelled) { ReferenceNode node; cancelled = false; if (checkPurge.Active) { ProgressDialog dlg = new ProgressDialog((Gtk.Window) this.Toplevel, false); dlg.Show(); while (Gtk.Application.EventsPending()) { Gtk.Application.RunIteration(); } node = file.GetRootReferenceTree(dlg, type); cancelled = dlg.Cancelled; dlg.Destroy(); if (node == null) { return(TreeIter.Zero); } } else { node = file.GetReferenceTree(type, checkInverse.Active); } return(AddNode(TreeIter.Zero, node)); }
public void ReadSnapshot() { if (items == null) { model.heapEventProcessor.RecordAllocations = true; model.Reader.ReadBlock(heapBlock).Decode(model.heapEventProcessor, model.Reader); snapshot = model.heapEventProcessor.LastHeapSnapshot; items = new HeapObjectSetFromSnapshot(snapshot); model.Model.SetValue(TreeIter, 0, this); } }
public void Clear() { while (notebook.NPages > 2) notebook.Remove (notebook.Children [2]); baseMap = null; fileStore.Clear (); allObjectsTree.Clear (); notebook.Page = 0; labelCount.Text = ""; labelMemory.Text = ""; labelName.Text = ""; }
public void Clear() { while (notebook.NPages > 2) { notebook.Remove(notebook.Children [2]); } baseMap = null; fileStore.Clear(); allObjectsTree.Clear(); notebook.Page = 0; labelCount.Text = ""; labelMemory.Text = ""; labelName.Text = ""; }
public void FillType(HeapSnapshot file, string typeName) { bool cancelled; this.typeName = typeName; this.file = file; store.Clear(); boxFilter.Visible = false; treeview.Columns [TreeColRefs].Visible = InverseReferences; treeview.Columns [TreeColRefs + 1].Visible = InverseReferences; treeview.Columns [TreeColRefs + 2].Visible = InverseReferences; TreeIter iter = InternalFillType(file, file.GetTypeFromName(typeName), out cancelled); if (!iter.Equals(TreeIter.Zero)) { treeview.ExpandRow(store.GetPath(iter), false); } EnableWidgets(); }
public HeapSnapshot GetCurrentObjectMap() { Gtk.TreeModel foo; Gtk.TreeIter iter; if (!fileList.Selection.GetSelected(out foo, out iter)) { return(null); } HeapSnapshot map = (HeapSnapshot)fileStore.GetValue(iter, 0); if (baseMap != null && baseMap != map) { return(GetCombinedMap(map, baseMap)); } else { return(map); } }
HeapSnapshot GetCombinedMap(HeapSnapshot m1, HeapSnapshot m2) { if (m2.Timestamp < m1.Timestamp) { HeapSnapshot tmp = m1; m1 = m2; m2 = tmp; } foreach (HeapSnapshot[] dif in difs) { if (dif[0] == m1 && dif[1] == m2) { return(dif[2]); } } HeapSnapshot res = HeapSnapshot.GetDiff(m1, m2); difs.Add(new HeapSnapshot[] { m1, m2, res }); return(res); }
protected virtual void OnSelectionChanged(object sender, EventArgs args) { HeapSnapshot map = GetCurrentObjectMap(); if (map == lastMap) { return; } lastMap = map; if (map != null) { Application.Invoke(delegate { allObjectsTree.FillAllTypes(map); }); labelName.Text = System.IO.Path.GetFileName(map.Name); labelCount.Text = map.NumObjects.ToString("n0"); labelMemory.Text = map.TotalMemory.ToString("n0") + " bytes"; } }
void OnToggled(object s, ToggledArgs args) { Gtk.TreeIter toggledIter, iter; bool selected; bool value; if (!fileStore.GetIterFromString(out toggledIter, args.Path)) { return; } selected = (bool)fileStore.GetValue(toggledIter, 2); baseMap = null; if (fileStore.GetIterFirst(out iter)) { do { if (toggledIter.Equals(iter)) { // this is the node the user toggled, so toggle it value = !selected; if (value) { baseMap = (HeapSnapshot)fileStore.GetValue(iter, 0); } } else { // turn off all other nodes, we can only have one node selected at the same time. value = false; } fileStore.SetValue(iter, 2, value); }while (fileStore.IterNext(ref iter)); } }
public VisibleHeapAllocation( HeapSnapshot.Heap heap, int index, int rowIndex, int firstRowIndex, ref HeapSnapshot.Allocation allocation, RectangleF rectangle ) { Heap = heap; Index = index; RowIndex = rowIndex; FirstRowIndex = firstRowIndex; Allocation = allocation; Rectangle = rectangle; }
public void FillType(HeapSnapshot file, string typeName) { bool cancelled; this.typeName = typeName; this.file = file; store.Clear (); boxFilter.Visible = false; treeview.Columns [TreeColRefs].Visible = InverseReferences; treeview.Columns [TreeColRefs+1].Visible = InverseReferences; treeview.Columns [TreeColRefs+2].Visible = InverseReferences; TreeIter iter = InternalFillType (file, file.GetTypeFromName (typeName), out cancelled); if (!iter.Equals (TreeIter.Zero)) treeview.ExpandRow (store.GetPath (iter), false); EnableWidgets (); }
protected bool AllocationFromPoint(Point pt, out HeapSnapshot.Heap heap, out int allocationIndex) { if (Snapshot == null) { heap = null; allocationIndex = -1; return false; } var width = ClientSize.Width - ScrollBar.Width; var bytesPerRow = BytesPerRow; foreach (var vh in WalkHeaps(Snapshot, _ScrollOffset, bytesPerRow, width)) { if (((vh.FirstRow + vh.HeightInRows) * RowHeight) < pt.Y) continue; foreach (var vha in WalkHeapAllocations(vh.Heap, bytesPerRow, vh.FirstRow, width)) { if (vha.Rectangle.Bottom < pt.Y) continue; if (vha.Rectangle.Y > pt.Y) break; if (vha.Rectangle.Contains(pt)) { heap = vha.Heap; allocationIndex = vha.Index; return true; } } } heap = null; allocationIndex = -1; return false; }
protected Color SelectItemColor(HeapSnapshot.Allocation alloc) { var id = BitConverter.ToInt32(BitConverter.GetBytes(alloc.TracebackID), 0); int hue = (id & 0xFFFF) % (HSV.HueMax); int value = ((id & (0xFFFF << 16)) % (HSV.ValueMax * 70 / 100)) + (HSV.ValueMax * 25 / 100); return HSV.ColorFromHSV( (UInt16)hue, HSV.SaturationMax, (UInt16)value ); }
protected IEnumerator<object> ResolveSymbolsForSnapshot(HeapSnapshot snapshot) { TracebackFrame tf; SymbolResolveState.Count = 0; yield return Future.RunInThread(() => { for (int i = 0, c = snapshot.Tracebacks.Count; i < c; i++) { var traceback = snapshot.Tracebacks[i]; lock (SymbolResolveLock) foreach (var frame in traceback) ResolveFrame(frame, out tf); } }); }
protected static IEnumerable<VisibleHeapAllocation> WalkHeapAllocations( HeapSnapshot.Heap heap, int bytesPerRow, int rowY, int contentWidth ) { for (int i = 0, c = heap.Allocations.Count; i < c; i++) { var allocation = heap.Allocations[i]; var pos = (int)(allocation.Address - heap.Info.EstimatedStart); var nextPos = (int)(allocation.NextOffset - heap.Info.EstimatedStart); int y1 = (rowY + (pos / bytesPerRow)), y2 = (rowY + (nextPos / bytesPerRow)); float x1 = (pos % bytesPerRow) / (float)BytesPerPixel, x2 = (nextPos % bytesPerRow) / (float)BytesPerPixel; for (var barY = y1; barY <= y2; barY += 1) { var barX = (barY == y1) ? x1 : 0; yield return new VisibleHeapAllocation( heap, i, barY, y1, ref allocation, new RectangleF( barX, barY * RowHeight, (barY == y2) ? x2 - barX : contentWidth - barX, RowHeight ) ); } } }
protected static IEnumerable<UInt32> IndexTracebackByFrames(HeapSnapshot.Traceback traceback) { var a = traceback.Frames.Array; for (int i = 0, c = traceback.Frames.Count, o = traceback.Frames.Offset; i < c; i++) yield return a[i + o]; }
void OnToggled(object s, ToggledArgs args) { Gtk.TreeIter toggledIter, iter; bool selected; bool value; if (!fileStore.GetIterFromString (out toggledIter, args.Path)) return; selected = (bool) fileStore.GetValue (toggledIter, 2); baseMap = null; if (fileStore.GetIterFirst (out iter)) { do { if (toggledIter.Equals (iter)) { // this is the node the user toggled, so toggle it value = !selected; if (value) baseMap = (HeapSnapshot) fileStore.GetValue (iter, 0); } else { // turn off all other nodes, we can only have one node selected at the same time. value = false; } fileStore.SetValue (iter, 2, value); } while (fileStore.IterNext (ref iter)); } }
void AddShot(HeapSnapshot shot) { shots.Add (shot); if (HeapSnapshotAdded != null) HeapSnapshotAdded (this, new HeapShotEventArgs (shot)); }
private void ReadLogFileChunk_Object(HeapEvent he) { if (he.Type == HeapEvent.EventType.Start) { Console.WriteLine ("ppe: START"); return; } else if (he.Type == HeapEvent.EventType.End) { Console.WriteLine ("ppe: END"); HeapSnapshot shot = new HeapSnapshot (); shotCount++; shot.Build (shotCount.ToString (), currentData); AddShot (shot); } if (he.Type == HeapEvent.EventType.Object) { ObjectInfo ob = new ObjectInfo (); ob.Code = currentObjBase + he.Object; ob.Size = he.Size; ob.RefsIndex = currentData.ReferenceCodes.Count; ob.RefsCount = he.ObjectRefs != null ? he.ObjectRefs.Length : 0; currentData.ObjectTypeCodes.Add (currentPtrBase + he.Class); totalMemory += ob.Size; if (ob.Size != 0) currentData.RealObjectCount++; // Read referenceCodes ulong lastOff = 0; for (int n=0; n < ob.RefsCount; n++) { currentData.ReferenceCodes.Add (he.ObjectRefs [n] + currentObjBase); lastOff += he.RelOffset [n]; currentData.FieldReferenceCodes.Add (lastOff); } currentData.ObjectsList.Add (ob); } else if (he.Type == HeapEvent.EventType.Root) { for (int n=0; n<he.RootRefs.Length; n++) { ObjectInfo ob = new ObjectInfo (); ob.Size = 0; ob.RefsIndex = currentData.ReferenceCodes.Count; ob.RefsCount = 1; long type = UnknownTypeId; switch (he.RootRefTypes [n] & HeapEvent.RootType.TypeMask) { case HeapEvent.RootType.Stack: type = -2; ob.Code = StackObjectId; break; case HeapEvent.RootType.Finalizer: type = -3; ob.Code = --rootId; break; case HeapEvent.RootType.Handle: type = -4; ob.Code = --rootId; break; case HeapEvent.RootType.Other: type = -5; ob.Code = --rootId; break; case HeapEvent.RootType.Misc: type = -6; ob.Code = --rootId; break; default: Console.WriteLine ("pp1:"); break; } currentData.ObjectTypeCodes.Add (type); currentData.ReferenceCodes.Add (he.RootRefs [n] + currentObjBase); currentData.FieldReferenceCodes.Add (0); currentData.ObjectsList.Add (ob); currentData.RealObjectCount++; } } }
protected virtual void OnSelectionChanged(object sender, EventArgs args) { HeapSnapshot map = GetCurrentObjectMap (); if (map == lastMap) return; lastMap = map; if (map != null) { Application.Invoke (delegate { allObjectsTree.FillAllTypes (map); }); labelName.Text = System.IO.Path.GetFileName (map.Name); labelCount.Text = map.NumObjects.ToString ("n0"); labelMemory.Text = map.TotalMemory.ToString ("n0") + " bytes"; } }
private IEnumerator<object> SetCurrentSnapshot(HeapSnapshotInfo info) { var oldSnapshot = Snapshot; if (oldSnapshot != null) oldSnapshot.Info.ReleaseStrongReference(); using (Finally.Do(() => { UseWaitCursor = false; })) { var fSnapshot = Instance.GetSnapshot(info); yield return fSnapshot; Snapshot = fSnapshot.Result; RefreshHeap(); } }
public void AddSnapshot(HeapSnapshot map) { fileStore.AppendValues (map, System.IO.Path.GetFileName (map.Name), false); }
public override void HeapReportStart(HeapSnapshot snapshot) { lastHeapSnapshot = snapshot; }
static void DeserializeHeapList(ref DeserializationContext context, out HeapSnapshot.HeapInfo[] output) { var br = new BinaryReader(context.Stream); int count = br.ReadInt32(); output = new HeapSnapshot.HeapInfo[count]; uint offset = 4; uint size = BlittableSerializer<HeapSnapshot.HeapInfo>.Size; for (int i = 0; i < count; i++) { context.DeserializeValue(BlittableSerializer<HeapSnapshot.HeapInfo>.Deserialize, offset, size, out output[i]); offset += size; } }
public SnapshotNode(HeapExplorerTreeModel model, SeekableLogFileReader.Block heapBlock, AllocationsNode previousAllocationsNode) : base(model, null, previousAllocationsNode) { this.heapBlock = heapBlock; this.items = null; this.snapshot = null; }
static void SerializeHeapList(ref SerializationContext context, ref HeapSnapshot.HeapInfo[] input) { var bw = new BinaryWriter(context.Stream); bw.Write(input.Length); foreach (var heap in input) context.SerializeValue(BlittableSerializer<HeapSnapshot.HeapInfo>.Serialize, heap); bw.Flush(); }
protected IEnumerator<object> LoadSnapshotFromDatabase(HeapSnapshotInfo info) { var result = new HeapSnapshot(info); var fModules = Database.SnapshotModules.Get(info.Index); var fHeaps = Database.SnapshotHeaps.Get(info.Index); using (fModules) yield return fModules; var fModuleInfos = Database.Modules.Select(fModules.Result); using (fModuleInfos) yield return fModuleInfos; foreach (var module in fModuleInfos.Result) result.Modules.Add(module); using (fHeaps) yield return fHeaps; var heapIDs = from heap in fHeaps.Result select heap.HeapID; var fAllocations = Database.HeapAllocations.Select(heapIDs); using (fAllocations) yield return fAllocations; var allocations = SequenceUtils.ToDictionary(heapIDs, fAllocations.Result); var tracebackIDs = new HashSet<UInt32>(); foreach (var heapInfo in fHeaps.Result) { var theHeap = new HeapSnapshot.Heap(heapInfo); var allocationIds = allocations[heapInfo.HeapID]; theHeap.Allocations.Capacity = allocationIds.Length; var fRanges = Database.Allocations.Select(allocationIds); using (fRanges) yield return fRanges; yield return Future.RunInThread(() => SequenceUtils.Zip( allocationIds, fRanges.Result, (id, ranges) => { HeapSnapshot.AllocationRanges.Range range; if (ranges.Get(info.Index, out range)) { theHeap.Allocations.Add(new HeapSnapshot.Allocation( id, range.Size, range.Overhead, range.TracebackID )); tracebackIDs.Add(range.TracebackID); } } ) ); result.Heaps.Add(theHeap); } var fTracebacks = Database.FilteredTracebacks.CascadingSelect( new [] { Database.Tracebacks }, tracebackIDs ); using (fTracebacks) yield return fTracebacks; result.Tracebacks.ReplaceWith(fTracebacks.Result); yield return Result.New(result); }
public ReferenceNode(HeapSnapshot map, int type, bool inverse) { this.map = map; this.type = type; TypeName = map.GetTypeName (type); this.inverse = inverse; }
protected static int ComputeHeapHeightInRows(HeapSnapshot.Heap heap, float bytesPerRow) { return (int)(Math.Ceiling( heap.Info.EstimatedSize / bytesPerRow ) + 1); }
public ReferenceNode(HeapSnapshot map, int type, PathTree pathTree) { this.map = map; this.type = type; TypeName = map.GetTypeName (type); this.pathTree = pathTree; FillRootPaths (); }
protected static IEnumerable<VisibleHeap> WalkHeaps( HeapSnapshot snapshot, int scrollOffsetInRows, int bytesPerRow, int contentWidth ) { int rowY = -scrollOffsetInRows; foreach (var heapId in snapshot.Heaps.Keys) { var heap = snapshot.Heaps[heapId]; var itemHeight = ComputeHeapHeightInRows(heap, bytesPerRow); yield return new VisibleHeap( heap, rowY, itemHeight ); rowY += itemHeight; } }
public void FillAllTypes(HeapSnapshot file) { this.file = file; this.typeName = null; boxFilter.Visible = true; treeview.Columns [TreeColRefs].Visible = InverseReferences; treeview.Columns [TreeColRefs + 1].Visible = InverseReferences; treeview.Columns [TreeColRefs + 2].Visible = InverseReferences; EnableWidgets(); if (loading) { // If the tree is already being loaded, notify that loading // has to start again, since the file has changed. reloadRequested = true; return; } treeview.Model = null; DisableSorting(); treeview.FreezeChildNotify(); loading = true; store.Clear(); int n = 0; int tot = 0; foreach (int t in file.GetTypes()) { tot++; if (++n == 20) { // Console.WriteLine ("pp: " + tot); /* if (ProgressEvent != null) { * ProgressEvent (n, file.GetTypeCount (), null); * } * while (Gtk.Application.EventsPending ()) * Gtk.Application.RunIteration (); * if (reloadRequested) { * loading = false; * reloadRequested = false; * FillAllTypes (this.file); * return; * }*/ n = 0; } bool cancelled = false; if (file.GetObjectCountForType(t) > 0) { InternalFillType(file, t, out cancelled); if (cancelled) { break; } } } treeview.ThawChildNotify(); EnableSorting(); treeview.Model = store; loading = false; }
protected IEnumerator<object> FinishShowingTooltip( Point mouseLocation, HeapSnapshot.Heap heap, HeapSnapshot.Allocation allocation, HeapSnapshot.Traceback rawTraceback ) { var uniqueRawFrames = rawTraceback.Frames.AsEnumerable().Distinct(); var fSymbols = Instance.Database.SymbolCache.Select(uniqueRawFrames); using (fSymbols) yield return fSymbols; var symbolDict = SequenceUtils.ToDictionary( uniqueRawFrames, fSymbols.Result ); var tracebackInfo = HeapRecording.ConstructTracebackInfo( rawTraceback.ID, rawTraceback.Frames, symbolDict ); var renderParams = new DeltaInfo.RenderParams { BackgroundBrush = new SolidBrush(SystemColors.Info), BackgroundColor = SystemColors.Info, TextBrush = new SolidBrush(SystemColors.InfoText), IsExpanded = true, IsSelected = false, Font = Font, ShadeBrush = new SolidBrush(Color.FromArgb(31, 0, 0, 0)), StringFormat = CustomTooltip.GetDefaultStringFormat() }; var content = new HeapSnapshot.AllocationTooltipContent( ref allocation, ref tracebackInfo, ref renderParams ) { Location = mouseLocation, Font = Font }; using (var g = CreateGraphics()) CustomTooltip.FitContentOnScreen( g, content, ref content.RenderParams.Font, ref content.Location, ref content.Size ); Tooltip.SetContent(content); }
private void HeapViewer_FormClosed(object sender, FormClosedEventArgs e) { Dispose(); Snapshot.Info.ReleaseStrongReference(); Timeline.Items = new List<HeapSnapshotInfo>(); LayoutView.Snapshot = Snapshot = null; }
public VisibleHeap(HeapSnapshot.Heap heap, int firstRow, int heightInRows) { Heap = heap; FirstRow = firstRow; HeightInRows = heightInRows; }
TreeIter InternalFillType(HeapSnapshot file, int type, out bool cancelled) { ReferenceNode node; cancelled = false; if (checkPurge.Active) { ProgressDialog dlg = new ProgressDialog ((Gtk.Window) this.Toplevel, false); dlg.Show (); while (Gtk.Application.EventsPending ()) Gtk.Application.RunIteration (); node = file.GetRootReferenceTree (dlg, type); cancelled = dlg.Cancelled; dlg.Destroy (); if (node == null) return TreeIter.Zero; } else node = file.GetReferenceTree (type, checkInverse.Active); return AddNode (TreeIter.Zero, node); }
public Graph(HeapSnapshot map) { this.map = map; }
private IEnumerator<object> FinishLoadingSnapshotEpilogue(HeapSnapshot snapshot) { AddSnapshot(snapshot); foreach (var module in snapshot.Modules) SymbolModules.Add(module); yield return new Start( ResolveSymbolsForSnapshot(snapshot), TaskExecutionPolicy.RunAsBackgroundTask ); if (!snapshot.SavedToDatabase) yield return snapshot.SaveToRecording(this); Interlocked.Increment(ref SnapshotLoadState.Count); }
public override void HeapReportEnd(HeapSnapshot snapshot) { lastHeapSnapshot.InitializeBackReferences(); }
protected void AddSnapshot(HeapSnapshot snapshot) { Snapshots.Add(snapshot.Info); // Resort the loaded snapshots, since it's possible for the user to load // a subset of a full capture, or load snapshots in the wrong order Snapshots.Sort((lhs, rhs) => lhs.Timestamp.CompareTo(rhs.Timestamp)); OnSnapshotsChanged(); }
public void AddSnapshot(HeapSnapshot map) { fileStore.AppendValues(map, System.IO.Path.GetFileName(map.Name), false); }
protected bool FilterTraceback(HeapSnapshot.Traceback traceback, HashSet<uint> filteredFrames, out HeapSnapshot.Traceback filtered) { ArraySegment<uint>? newFrames = null; int count = 0; foreach (var frame in traceback) { if (filteredFrames.Contains(frame)) { if (!newFrames.HasValue) { newFrames = ImmutableArrayPool<uint>.Allocate(traceback.Frames.Count); Array.Copy( traceback.Frames.Array, traceback.Frames.Offset, newFrames.Value.Array, newFrames.Value.Offset, count ); } } else { if (newFrames.HasValue) newFrames.Value.Array[count + newFrames.Value.Offset] = frame; count++; } } if (newFrames.HasValue) { filtered = new HeapSnapshot.Traceback( traceback.ID, new ArraySegment<uint>( newFrames.Value.Array, newFrames.Value.Offset, count ) ); return true; } filtered = traceback; return false; }
HeapSnapshot GetCombinedMap(HeapSnapshot m1, HeapSnapshot m2) { if (m2.Timestamp < m1.Timestamp) { HeapSnapshot tmp = m1; m1 = m2; m2 = tmp; } foreach (HeapSnapshot[] dif in difs) { if (dif[0] == m1 && dif[1] == m2) return dif[2]; } HeapSnapshot res = HeapSnapshot.GetDiff (m1, m2); difs.Add (new HeapSnapshot[] { m1, m2, res }); return res; }