public void DrawMarkers(int y, List <HeapEventData> events) { int count = events.Count; Brush brush1 = Brushes.Blue; Brush brush2 = Brushes.Brown; for (int i = 0; i < count; i++) { HeapEventData data = events[i]; double t = data.m_time; if (t < m_barT0) { continue; } if (t > m_barT1) { break; } if ((data.m_event >= HeapEvents.GCMarkerFirst) && (data.m_event <= HeapEvents.GCMarkerLast)) { DrawRect(brush1, MapX(t), y - 1, 1, 10); } else if ((data.m_event >= HeapEvents.BGCMarkerFirst) && (data.m_event <= HeapEvents.BGCMarkerLast)) { DrawRect(brush2, MapX(t), y - 1, 1, 10); } } }
public void AddEvent(HeapEvents evt, double time, object obj = null) { switch (evt) { case HeapEvents.GCAllocationTick: if (m_name == null) { m_name = ".Net"; } break; case HeapEvents.GCFinalizersBegin: m_name = ".Net Finalizer"; break; case HeapEvents.BGCBegin: m_name = ".Net BGC"; break; case HeapEvents.GCJoin: if (m_name == null) { m_name = ".Net GC"; } break; default: break; } if (m_events == null) { m_events = new List <HeapEventData>(); m_histogram = new int[(int)HeapEvents.GCEventMax]; } HeapEventData data = new HeapEventData(); data.m_event = evt; data.m_time = time; data.m_data = obj; m_histogram[(int)evt]++; m_events.Add(data); }
public void DrawThread(int y, ThreadMemoryInfo thread, bool drawLegend, bool drawMarker) { List <HeapEventData> events = thread.m_events; int count = events.Count; m_barY = y; if (count > 1) { double start = events[0].m_time; double end = events[count - 1].m_time; if (drawLegend) { string name = thread.Name; if (!String.IsNullOrEmpty(name)) { if (name.StartsWith(".Net ", StringComparison.OrdinalIgnoreCase)) { name = name.Substring(5); } } DrawText(5, y + 8, String.Format("{0}, {1}, {2} ms", thread.ThreadID, name, thread.CpuSample), 9); return; } if ((start > m_barT1) || (end < m_barT0)) { return; } if (end > m_barT1) { end = m_barT1; } DrawText(MapX(end) + 5, y, String.Format("Thread {0}, {1}, {2} ms", thread.ThreadID, thread.Name, thread.CpuSample), 8); DrawRect(m_blue25, MapX(start), y, MapXDelta(end - start), m_barH); BarInterval cpuSample = new BarInterval(this, Brushes.Black); BarInterval contention = new BarInterval(this, Brushes.Red); BarInterval waitBgc = new BarInterval(this, Brushes.Yellow); double half = thread.SampleInterval / 2; for (int i = 0; i < count; i++) { HeapEventData evt = events[i]; double tick = evt.m_time; switch (evt.m_event) { case HeapEvents.CPUSample: cpuSample.Start(tick - half); cpuSample.End(tick + half); break; case HeapEvents.ContentionStart: contention.Start(tick); break; case HeapEvents.ContentionStop: contention.End(tick); break; case HeapEvents.BGCAllocWaitStart: waitBgc.Start(tick); break; case HeapEvents.BGCAllocWaitStop: waitBgc.End(tick); break; default: break; } } cpuSample.Draw(); contention.Draw(); waitBgc.Draw(); if (drawMarker) { DrawMarkers(y, events); } } }