예제 #1
0
 public void WriteStackTree(StackTree tree)
 {
     _totalTreeWeight = tree.Root.Weight;
     WriteStackTreeNode(tree.Root, 0, 0); // TODO Find the real offsets based on the headers
 }
예제 #2
0
        static void Main(string[] args)
        {
            string filename;
            string processName;

            if (args.Length < 2)
            {
                filename    = @"C:\Temp\final.etl";
                processName = "devenv";
            }
            else
            {
                filename    = args[0];
                processName = args[1];
            }

            var output    = Console.Error;
            var symOutput = TextWriter.Null;

            var traceLog = TraceLog.OpenOrConvert(filename,
                                                  new TraceLogOptions()
            {
                ConversionLog = output
            });

            var simpleTraceLogProcess = traceLog.Processes.LastProcessWithName(processName);

            if (simpleTraceLogProcess == null)
            {
                Console.Error.WriteLine("Could not find process with name {0}", processName);
                Environment.Exit(1);
            }

            var symbolReader = new SymbolReader(symOutput, SymbolPath.SymbolPathFromEnvironment);

            symbolReader.SecurityCheck = (path => true);

            Stopwatch sw = Stopwatch.StartNew();

            foreach (var module in simpleTraceLogProcess.LoadedModules)
            {
                if (ShouldLoadSymbolsForModule(module.FilePath))
                {
                    traceLog.CodeAddresses.LookupSymbolsForModule(symbolReader, module.ModuleFile);
                }
            }
            Console.Error.WriteLine($"Loaded symbols in {sw.ElapsedMilliseconds} ms");

            bool buildFlameGraphNatively = true;    // TODO Make configurable

            if (buildFlameGraphNatively)
            {
                sw.Restart();
                var stackTree = new StackTree(simpleTraceLogProcess.EventsInProcess.ByEventType <SampledProfileTraceData>());
                Console.Error.WriteLine($"Built stack tree in {sw.ElapsedMilliseconds} ms");
                // stackTree.Dump(Console.Out);

                var writer = new SVGWriter(Console.Out, 1024, stackTree.MaxDepth);
                writer.WriteHeader();
                writer.WriteEmbeddedJavaScript();
                writer.WriteStackTree(stackTree);
                writer.WriteFooter();
            }
            else
            {
                CreateFoldedStacksForFlameGraphScript(simpleTraceLogProcess.EventsInProcess.ByEventType <SampledProfileTraceData>());
            }

            // TODO Make this a PerfView UserCommand -- but don't use the PerfView 'Stacks' API
            // because that would lock us in to only using this tool from within PerfView. Instead,
            // just use CommandEnvironment.OpenETLFile("file.etl").TraceLog to get a TraceLog instance
            // and work from there as above.
        }