static void Main(string[] args)
    {
        if (args.Length != 3)
        {
            Console.Error.WriteLine("Usage: GetCpuSampleDuration.exe <trace.etl> <imageName> <functionName>");
            return;
        }

        string tracePath    = args[0];
        string imageName    = args[1];
        string functionName = args[2];

        Dictionary <string, Duration> matchDurationByCommandLine = new Dictionary <string, Duration>();

        using (ITraceProcessor trace = TraceProcessor.Create(tracePath))
        {
            IPendingResult <ISymbolDataSource>    pendingSymbolData      = trace.UseSymbols();
            IPendingResult <ICpuSampleDataSource> pendingCpuSamplingData = trace.UseCpuSamplingData();

            trace.Process();

            ISymbolDataSource    symbolData      = pendingSymbolData.Result;
            ICpuSampleDataSource cpuSamplingData = pendingCpuSamplingData.Result;

            symbolData.LoadSymbolsForConsoleAsync(SymCachePath.Automatic, SymbolPath.Automatic).GetAwaiter().GetResult();
            Console.WriteLine();

            IThreadStackPattern pattern = AnalyzerThreadStackPattern.Parse($"{imageName}!{functionName}");

            foreach (ICpuSample sample in cpuSamplingData.Samples)
            {
                if (sample.IsExecutingDeferredProcedureCall == true || sample.IsExecutingInterruptServicingRoutine == true)
                {
                    continue;
                }

                if (sample.Stack != null && sample.Stack.Matches(pattern))
                {
                    string commandLine = sample.Process.CommandLine;

                    if (!matchDurationByCommandLine.ContainsKey(commandLine))
                    {
                        matchDurationByCommandLine.Add(commandLine, Duration.Zero);
                    }

                    matchDurationByCommandLine[commandLine] += sample.Weight;
                }
            }
        }

        foreach (string commandLine in matchDurationByCommandLine.Keys)
        {
            Console.WriteLine($"{commandLine}: {matchDurationByCommandLine[commandLine]}");
        }
    }
Exemplo n.º 2
0
 private void GatherCpuSampleData(ICpuSampleDataSource cpuSampleDataSource)
 {
     foreach (ICpuSample sample in cpuSampleDataSource.Samples)
     {
         Process process = new Process(sample.Process.Id, sample.Process.ImageName);
         if (!SampledProfileCounts.ContainsKey(process))
         {
             SampledProfileCounts.Add(process, 1);
         }
         else
         {
             ++SampledProfileCounts[process];
         }
     }
 }
Exemplo n.º 3
0
        static void RunWithOptions(Options opts)
        {
            using (ITraceProcessor trace = TraceProcessor.Create(opts.etlFileName))
            {
                IPendingResult <ICpuSampleDataSource> pendingCpuSampleData = trace.UseCpuSamplingData();
                IPendingResult <ISymbolDataSource>    pendingSymbolData    = trace.UseSymbols();

                trace.Process();

                ISymbolDataSource    symbolData    = pendingSymbolData.Result;
                ICpuSampleDataSource cpuSampleData = pendingCpuSampleData.Result;

                var symbolProgress = new Progress <SymbolLoadingProgress>(progress =>
                {
                    Console.Write("\r{0:P} {1} of {2} symbols processed ({3} loaded)",
                                  (double)progress.ImagesProcessed / progress.ImagesTotal,
                                  progress.ImagesProcessed,
                                  progress.ImagesTotal,
                                  progress.ImagesLoaded);
                });
                symbolData.LoadSymbolsAsync(
                    SymCachePath.Automatic, SymbolPath.Automatic, symbolProgress)
                .GetAwaiter().GetResult();
                Console.WriteLine();

                var profileWriter = new ProfileWriter(opts.etlFileName,
                                                      opts.includeInlinedFunctions,
                                                      opts.includeProcessAndThreadIds,
                                                      opts.stripSourceFileNamePrefix);

                var timeStart = opts.timeStart ?? 0;
                var timeEnd   = opts.timeEnd ?? decimal.MaxValue;

                var exportAllProcesses = opts.processFilter == "*";
                var processFilterSet   = new HashSet <string>(
                    opts.processFilter.Trim().Split(",", StringSplitOptions.RemoveEmptyEntries));

                for (int i = 0; i < cpuSampleData.Samples.Count; i++)
                {
                    if (i % 100 == 0)
                    {
                        Console.Write("\r{0:P} {1} of {2} samples processed",
                                      (double)i / cpuSampleData.Samples.Count, i, cpuSampleData.Samples.Count);
                    }

                    var cpuSample = cpuSampleData.Samples[i];

                    if ((cpuSample.IsExecutingDeferredProcedureCall ?? false) ||
                        (cpuSample.IsExecutingInterruptServicingRoutine ?? false))
                    {
                        continue;
                    }

                    if (!exportAllProcesses)
                    {
                        var processImage = cpuSample.Process.Images
                                           .FirstOrDefault(image => image.FileName == cpuSample.Process.ImageName);

                        string imagePath = processImage?.Path ?? cpuSample.Process.ImageName;

                        if (!processFilterSet.Any(filter => imagePath.Contains(filter.Replace("/", "\\"))))
                        {
                            continue;
                        }
                    }

                    var timestamp = cpuSample.Timestamp.RelativeTimestamp.TotalSeconds;
                    if (timestamp < timeStart || timestamp > timeEnd)
                    {
                        continue;
                    }

                    profileWriter.AddSample(cpuSample);
                }
                Console.WriteLine();

                long outputSize = profileWriter.Write(opts.outputFileName);
                Console.WriteLine("Wrote {0:N0} bytes to {1}", outputSize, opts.outputFileName);
            }
        }