// Returns a list of paths. Each path is a sequence of objects, starting // on an object of type 'type' and ending on a root. public PathTree GetRoots(IProgressListener listener, int type) { RootInfo rootInfo = new RootInfo(); PathTree pathTree = new PathTree(this); foreach (int obj in GetObjectsByType(type)) { rootInfo.BaseObjects [obj] = obj; } int nc = 0; foreach (int obj in GetObjectsByType(type)) { if (listener.Cancelled) { return(null); } rootInfo.nc = 0; FindRoot(rootInfo, pathTree, obj); // Register partial paths to the root, to avoid having to // recalculate them again // if (nc % 100 == 0) // Console.WriteLine ("NC: " + nc + " " + rootInfo.Roots.Count); pathTree.AddBaseObject(obj); foreach (KeyValuePair <int, int[]> e in rootInfo.Roots) { pathTree.AddPath(e.Value); } rootInfo.Visited.Clear(); rootInfo.Roots.Clear(); nc++; double newp = (double)nc / (double)rootInfo.BaseObjects.Count; listener.ReportProgress("Looking for roots", newp); } pathTree.Flush(); return(pathTree); }
// // Code to read the log files generated at runtime // private void ReadLogFile(IProgressListener progress) { BufferHeader bheader; long start_position = reader.Position; long last_pct = 0; if (header == null) { header = Header.Read(reader); } if (header == null) { return; } while (!reader.IsEof) { // We check if we must cancel before reading more data (and after processing all the data we've read). // This way we don't cancel in the middle of event processing (since we store data at class level // we may end up with corruption the next time we read the same buffer otherwise). if (progress != null) { if (progress.Cancelled) { return; } long pct = (reader.Position - start_position) * 100 / (reader.Length - start_position); if (pct != last_pct) { last_pct = pct; progress.ReportProgress("Loading profiler log", pct / 100.0f); } } bheader = BufferHeader.Read(reader); if (bheader == null) { // entire buffer isn't available (yet) return; } //Console.WriteLine ("BUFFER ThreadId: " + bheader.ThreadId + " Len:" + bheader.Length); currentObjBase = bheader.ObjBase; currentPtrBase = bheader.PtrBase; while (!reader.IsBufferEmpty) { MetadataEvent me; HeapEvent he; GcEvent ge; Event e = Event.Read(reader); //Console.WriteLine ("Event: {0}", e); if ((me = e as MetadataEvent) != null) { ReadLogFileChunk_Type(me); } else if ((he = e as HeapEvent) != null) { ReadLogFileChunk_Object(he); } else if ((ge = e as GcEvent) != null) { ReadGcEvent(ge); } } } }
// // Code to read the log files generated at runtime // private void ReadLogFile(IProgressListener progress) { BufferHeader bheader; long start_position = reader.Position; long last_pct = 0; if (header == null) header = Header.Read (reader); if (header == null) return; reader.Header = header; while (!reader.IsEof) { // We check if we must cancel before reading more data (and after processing all the data we've read). // This way we don't cancel in the middle of event processing (since we store data at class level // we may end up with corruption the next time we read the same buffer otherwise). if (progress != null) { if (progress.Cancelled) return; long pct = (reader.Position - start_position) * 100 / (reader.Length - start_position); if (pct != last_pct) { last_pct = pct; progress.ReportProgress ("Loading profiler log", pct / 100.0f); } } bheader = BufferHeader.Read (reader); if (bheader == null) { // entire buffer isn't available (yet) return; } //Console.WriteLine ("BUFFER ThreadId: " + bheader.ThreadId + " Len:" + bheader.Length); currentObjBase = bheader.ObjBase; currentPtrBase = bheader.PtrBase; while (!reader.IsBufferEmpty) { MetadataEvent me; HeapEvent he; GcEvent ge; Event e = Event.Read (reader); if ((me = e as MetadataEvent) != null) ReadLogFileChunk_Type (me); else if ((he = e as HeapEvent) != null) ReadLogFileChunk_Object (he); else if ((ge = e as GcEvent) != null) ReadGcEvent (ge); } } }