/// <summary> /// Create a new GCRefernece computer from the stream of events 'source'. When 'source' is processed /// you can call 'GetReferenceForGCAddress' to get stable ids for GC references. /// </summary> /// <param name="source"></param> public TcpIpComputer(TraceEventDispatcher source) { m_source = source; var tcpParser = new MicrosoftWindowsTCPIPTraceEventParser(m_source); tcpParser.TcpRequestConnect += delegate(TcpRequestConnectArgs data) { }; tcpParser.TcpRequestConnect += delegate(TcpRequestConnectArgs data) { }; tcpParser.TcpDeliveryIndicated += delegate(TcpDisconnectTcbInjectFailedArgs data) { }; tcpParser.TcpDataTransferReceive += delegate(TcpDataTransferReceiveArgs data) { }; tcpParser.TcpSendPosted += delegate(TcpSendPostedArgs data) { }; tcpParser.TcpCloseTcbRequest += delegate(TcpAccpetListenerRouteLookupFailureArgs args) { }; }
/// <summary> /// TraceProcesses represents the entire ETL moduleFile log. At the node level it is organized by threads. /// /// The TraceProcesses also is where we put various caches that are independent of the process involved. /// These include a cache for TraceModuleFile that represent native images that can be loaded into a /// process, as well as the process lookup tables and a cache that remembers the last calls to /// GetNameForAddress(). /// </summary> internal TraceProcesses(TraceLog log, TraceEventDispatcher source) { this.log = log; this.source = source; this.processes = new GrowableArray <TraceProcess>(64); this.processesByPID = new GrowableArray <TraceProcess>(64); }
public static void AddCallbackOnProcessStart(this TraceEventDispatcher source, Action <TraceProcess> OnProcessStart) { var processes = source.Processes(); Debug.Assert(processes != null); processes.OnInitialized += OnProcessStart; }
public void Append(MemoryGraph memoryGraph, string etlName, string processNameOrId = null, double startTimeRelativeMSec = 0) { using (var source = TraceEventDispatcher.GetDispatcherFromFileName(etlName)) { Append(memoryGraph, source, processNameOrId, startTimeRelativeMSec); } }
/// <summary> /// Run the state machine to produce the stackSource given in the constructor. /// </summary> public void Execute() { // Get the trace log. TraceLog traceLog = m_Configuration.TraceLog; // Get the event dispatcher. TraceEventDispatcher eventDispatcher = traceLog.Events.GetSource(); // Register computing resource event handlers. if ((m_ViewType == ComputingResourceViewType.CPU) || (m_ViewType == ComputingResourceViewType.ThreadTime)) { eventDispatcher.Kernel.PerfInfoSample += OnCpuSample; } if (m_ViewType == ComputingResourceViewType.ThreadTime) { eventDispatcher.Kernel.ThreadStart += OnThreadStart; eventDispatcher.Kernel.ThreadStop += OnThreadEnd; eventDispatcher.Kernel.ThreadCSwitch += OnThreadCSwitch; } if (m_ViewType == ComputingResourceViewType.Allocations) { eventDispatcher.Clr.GCAllocationTick += OnGCAllocationTick; } // Register scenario event handlers. m_Configuration.ScenarioStateMachine.RegisterEventHandlers(eventDispatcher); // Process events. eventDispatcher.Process(); // Sort samples. m_OutputStackSource.DoneAddingSamples(); }
public bool LoadEvents(int procID, int sampleInterval100ns) { m_procID = procID; m_SampleInterval = sampleInterval100ns / 10000.0; // Filter to process TraceEvents processEvents = m_traceLog.Events.Filter(FilterEvent); // Get Dispatcher TraceEventDispatcher source = processEvents.GetSource(); kernelGuid = KernelTraceEventParser.ProviderGuid; // Hookup events source.Clr.All += OnClrEvent; ClrPrivateTraceEventParser clrPrivate = new ClrPrivateTraceEventParser(source); clrPrivate.All += OnClrPrivateEvent; KernelTraceEventParser kernel = source.Kernel; kernel.PerfInfoSample += delegate(SampledProfileTraceData data) { ThreadMemoryInfo thread = GetThread(data.ThreadID); thread.AddEvent(HeapEvents.CPUSample, data.TimeStampRelativeMSec); }; kernel.VirtualMemAlloc += OnVirtualMem; kernel.VirtualMemFree += OnVirtualMem; m_processLookup = new Dictionary <int, Microsoft.Diagnostics.Tracing.Analysis.TraceProcess>(); // Process all events into GCProcess lookup dictionary Microsoft.Diagnostics.Tracing.Analysis.TraceLoadedDotNetRuntimeExtensions.NeedLoadedDotNetRuntimes(source); Microsoft.Diagnostics.Tracing.Analysis.TraceProcessesExtensions.AddCallbackOnProcessStart(source, proc => { Microsoft.Diagnostics.Tracing.Analysis.TraceProcessesExtensions.SetSampleIntervalMSec(proc, sampleInterval100ns); proc.Log = m_traceLog; }); source.Process(); foreach (var proc in Microsoft.Diagnostics.Tracing.Analysis.TraceProcessesExtensions.Processes(source)) { if (Microsoft.Diagnostics.Tracing.Analysis.TraceLoadedDotNetRuntimeExtensions.LoadedDotNetRuntime(proc) != null) { m_processLookup.Add(proc.ProcessID, proc); } } // Get the process we want if (!m_processLookup.ContainsKey(procID)) { return(false); } m_process = m_processLookup[procID]; m_runtime = Microsoft.Diagnostics.Tracing.Analysis.TraceLoadedDotNetRuntimeExtensions.LoadedDotNetRuntime(m_process); return(true); }
public static int Main(string[] args) { // Additional assemblies will be seen, but these are ones we must see string[] AssembliesExpected = new string[] { "rundown", // this assembly "System.Runtime", "Microsoft.Diagnostics.Tracing.TraceEvent", "System.Diagnostics.Tracing", "System.Private.CoreLib" }; using (var netPerfFile = NetPerfFile.Create(args)) { Console.WriteLine("\tStart: Enable tracing."); TraceControl.EnableDefault(netPerfFile.Path); Console.WriteLine("\tEnd: Enable tracing.\n"); // Since all we care about is rundown, there is nothing to do there Console.WriteLine("\tStart: Disable tracing."); TraceControl.Disable(); Console.WriteLine("\tEnd: Disable tracing.\n"); Console.WriteLine("\tStart: Process the trace file."); var assembliesLoaded = new HashSet <string>(); int nonMatchingEventCount = 0; using (var trace = TraceEventDispatcher.GetDispatcherFromFileName(netPerfFile.Path)) { var rundownParser = new ClrRundownTraceEventParser(trace); rundownParser.LoaderAssemblyDCStop += delegate(AssemblyLoadUnloadTraceData data) { var nameIndex = Array.IndexOf(data.PayloadNames, ("FullyQualifiedAssemblyName")); if (nameIndex >= 0) { // Add the assembly name to a set to verify later assembliesLoaded.Add(((string)data.PayloadValue(nameIndex)).Split(',')[0]); } else { nonMatchingEventCount++; } }; trace.Process(); } Console.WriteLine("\tEnd: Processing events from file.\n"); foreach (var name in AssembliesExpected) { Assert.True($"Assembly {name} in loaded assemblies", assembliesLoaded.Contains(name)); } Assert.Equal(nameof(nonMatchingEventCount), nonMatchingEventCount, 0); } return(100); }
public static void SetupCallbacks(TraceEventDispatcher source) { // // Code lifted from TraceLog.cs to create the TraceProcess // // These parsers create state and we want to collect that so we put it on our 'parsers' list that we serialize. var kernelParser = source.Kernel; // Process level events. kernelParser.ProcessStartGroup += delegate(ProcessTraceData data) { // do not use .Process() to retrive the process, since you need to pass in a special flag indicating that // this is a process start event var process = data.source.Processes().GetOrCreateProcess(data.ProcessID, data.TimeStampQPC, data.Opcode == TraceEventOpcode.Start); process.ProcessStart(data); // Don't filter them out (not that many, useful for finding command line) }; kernelParser.ProcessEndGroup += delegate(ProcessTraceData data) { data.Process().ProcessEnd(data); // Don't filter them out (not that many, useful for finding command line) }; // Thread level events kernelParser.ThreadStartGroup += delegate(ThreadTraceData data) { data.Process(); }; kernelParser.ThreadEndGroup += delegate(ThreadTraceData data) { data.Process(); }; kernelParser.ImageGroup += delegate(ImageLoadTraceData data) { data.Process(); }; // Attribute CPU samples to processes. kernelParser.PerfInfoSample += delegate(SampledProfileTraceData data) { if (data.ThreadID == 0) // Don't count process 0 (idle) { return; } var process = data.Process(); process.CPUMSec += process.SampleIntervalMSec(); }; kernelParser.AddCallbackForEvents <ProcessCtrTraceData>(delegate(ProcessCtrTraceData data) { var process = data.Process(); process.PeakVirtual = (double)data.PeakVirtualSize; process.PeakWorkingSet = (double)data.PeakWorkingSetSize; }); }
private static void ProcessTrace(TraceEventDispatcher dispatcher) { dispatcher.Clr.All += ProcessEvent; dispatcher.Kernel.All += ProcessEvent; dispatcher.Dynamic.All += ProcessEvent; dispatcher.Process(); }
public MemoryGraph Read(TraceEventDispatcher source, string processNameOrId = null, double startTimeRelativeMSec = 0) { var ret = new MemoryGraph(10000); Append(ret, source, processNameOrId, startTimeRelativeMSec); ret.AllowReading(); return(ret); }
private static void RegisterCallbacks ( string providerName , string[] traceEvents , TraceEventDispatcher source , TraceEventSession session , Action < TraceEventDispatcher , TraceEventSession , TraceEvent > onOneEventTracedOnceProcessAction ) { int l = traceEvents.Length; for (int i = 0; i < l; i++) { var eventName = traceEvents[i]; var action = onOneEventTracedOnceProcessAction; if (action != null) { if (string.Compare(eventName, "*") == 0) { source .Dynamic .All += delegate(TraceEvent data) { action(source, session, data); }; } else if (string.Compare(eventName, "UnhandledEvents") == 0) { source .UnhandledEvents += delegate(TraceEvent data) { action(source, session, data); }; } else { source .Dynamic .AddCallbackForProviderEvent ( providerName , eventName , delegate(TraceEvent data) { action(source, session, data); } ); } } } }
private static void UpdateCommonInfo(string savedEtlFile, TraceEventDispatcher source, ClrCap.CAPAnalysisBase report) { report.TraceInfo.NumberOfLostEvents = source.EventsLost; report.TraceInfo.TraceDurationSeconds = source.SessionDuration.TotalSeconds; report.TraceInfo.TraceEnd = source.SessionEndTime; report.TraceInfo.TraceStart = source.SessionStartTime; report.TraceInfo.FileLocation = Path.GetFullPath(savedEtlFile); report.OSInfo.Version = (source.OSVersion != null) ? source.OSVersion.ToString() : ""; //report.EventStats.PopulateEventCounts(source.Stats); }
public PinningStackAnalysis(TraceEventDispatcher source, TraceProcess process, MutableTraceEventStackSource stackSource, TextWriter log) : base(source, process, stackSource, log) { var clrPrivateParser = new ClrPrivateTraceEventParser(source); clrPrivateParser.GCSetGCHandle += OnSetGCHandle; source.Clr.GCSetGCHandle += OnSetGCHandle; AllocateObject = () => new PinningStackAnalysisObject(); }
public void RunTests() { // Get the configuration and start tracing. TraceConfiguration traceConfig = GenerateConfiguration(); TraceControl.Enable(traceConfig); // Run the tests. foreach (EventSourceTest test in m_tests) { test.LogEvent(); } // Stop tracing. TraceControl.Disable(); // Open the trace file. string traceLogPath = TraceLog.CreateFromEventPipeDataFile(m_file.Path); using (TraceLog traceLog = new TraceLog(traceLogPath)) { TraceEventDispatcher dispatcher = traceLog.Events.GetSource(); dispatcher.Dynamic.All += delegate(TraceEvent data) { if (data.ProviderName.EndsWith("Rundown")) { return; } if (data.ProviderName.Equals("Microsoft-DotNETCore-EventPipe")) { return; } Assert.True($"m_nextTestVerificationIndex({m_nextTestVerificationIndex}) < m_tests.Count({m_tests.Count})", m_nextTestVerificationIndex < m_tests.Count); try { Console.WriteLine($"Verifying Event: {data.ToString()}"); m_tests[m_nextTestVerificationIndex].VerifyEvent(data); } catch { Console.WriteLine($"Failure during test '{m_tests[m_nextTestVerificationIndex].Name}'."); throw; } m_nextTestVerificationIndex++; }; dispatcher.Process(); Assert.Equal("Test Count", m_tests.Count, m_nextTestVerificationIndex); } }
private void RegisterListeners(TraceEventDispatcher source) { if ((_filter & EventFilter.Exception) == EventFilter.Exception) { // get exceptions source.Clr.ExceptionStart += OnExceptionStart; } if ((_filter & EventFilter.Finalizer) == EventFilter.Finalizer) { // get finalizers source.Clr.TypeBulkType += OnTypeBulkType; source.Clr.GCFinalizeObject += OnGCFinalizeObject; } if ((_filter & EventFilter.Contention) == EventFilter.Contention) { // get thread contention time source.Clr.ContentionStart += OnContentionStart; source.Clr.ContentionStop += OnContentionStop; } if ((_filter & EventFilter.ThreadStarvation) == EventFilter.ThreadStarvation) { // detect ThreadPool starvation source.Clr.ThreadPoolWorkerThreadAdjustmentAdjustment += OnThreadPoolWorkerAdjustment; } if ((_filter & EventFilter.GC) == EventFilter.GC) { source.NeedLoadedDotNetRuntimes(); source.AddCallbackOnProcessStart((TraceProcess proc) => { if (proc.ProcessID != _processId) { return; } proc.AddCallbackOnDotNetRuntimeLoad((TraceLoadedDotNetRuntime runtime) => { runtime.GCEnd += (TraceProcess p, TraceGC gc) => { NotifyCollection(gc); }; }); }); } if ((_filter & EventFilter.AllocationTick) == EventFilter.AllocationTick) { // sample every ~100 KB of allocations source.Clr.GCAllocationTick += OnGCAllocationTick; } }
public static int Main(string[] args) { using (var netPerfFile = NetPerfFile.Create(args)) { Console.WriteLine("\tStart: Enable tracing."); TraceControl.EnableDefault(netPerfFile.Path); Console.WriteLine("\tEnd: Enable tracing.\n"); Console.WriteLine("\tStart: Generate some events."); DynamicallyCompiledMethodInvoker invoker = BuildDynamicMethod(); invoker.Invoke(); Console.WriteLine("\tEnd: Generate some events.\n"); Console.WriteLine("\tStart: Disable tracing."); TraceControl.Disable(); Console.WriteLine("\tEnd: Disable tracing.\n"); Console.WriteLine("\tStart: Process the trace file."); int matchingEventCount = 0; int nonMatchingEventCount = 0; using (var trace = TraceEventDispatcher.GetDispatcherFromFileName(netPerfFile.Path)) { string methodNamespace = "dynamicClass"; string methodName = "DynamicallyCompiledMethod"; string methodSignature = "void ()"; string providerName = "Microsoft-Windows-DotNETRuntime"; string gcTriggeredEventName = "Method/JittingStarted"; trace.Clr.MethodJittingStarted += delegate(MethodJittingStartedTraceData data) { if (methodNamespace.Equals(data.MethodNamespace) && methodName.Equals(data.MethodName) && methodSignature.Equals(data.MethodSignature) && providerName.Equals(data.ProviderName) && gcTriggeredEventName.Equals(data.EventName)) { matchingEventCount++; } }; trace.Process(); } Console.WriteLine("\tEnd: Processing events from file.\n"); // CompiledMethod Assert.Equal(nameof(matchingEventCount), matchingEventCount, 1); } return(100); }
public static int Main(string[] args) { using (var netPerfFile = NetPerfFile.Create(args)) { Console.WriteLine("\tStart: Enable tracing."); TraceControl.EnableDefault(netPerfFile.Path); Console.WriteLine("\tEnd: Enable tracing.\n"); Console.WriteLine("\tStart: Generate some events."); for (int i = 0; i < InducedGCIterations; i++) { GC.Collect(); } Console.WriteLine("\tEnd: Generate some events.\n"); Console.WriteLine("\tStart: Disable tracing."); TraceControl.Disable(); Console.WriteLine("\tEnd: Disable tracing.\n"); Console.WriteLine("\tStart: Process the trace file."); int matchingEventCount = 0; int nonMatchingEventCount = 0; using (var trace = TraceEventDispatcher.GetDispatcherFromFileName(netPerfFile.Path)) { string gcReasonInduced = GCReason.Induced.ToString(); string providerName = "Microsoft-Windows-DotNETRuntime"; string gcTriggeredEventName = "GC/Triggered"; trace.Clr.GCTriggered += delegate(GCTriggeredTraceData data) { if (gcReasonInduced.Equals(data.Reason.ToString()) && providerName.Equals(data.ProviderName) && gcTriggeredEventName.Equals(data.EventName)) { matchingEventCount++; } else { nonMatchingEventCount++; } }; trace.Process(); } Console.WriteLine("\tEnd: Processing events from file.\n"); Assert.Equal(nameof(matchingEventCount), InducedGCIterations, matchingEventCount); Assert.Equal(nameof(nonMatchingEventCount), nonMatchingEventCount, 0); } return(100); }
protected override void InstallValidationCallbacks(TraceEventDispatcher trace) { string gcReasonInduced = GCReason.Induced.ToString(); trace.Clr.GCTriggered += delegate(GCTriggeredTraceData data) { if (gcReasonInduced.Equals(data.Reason.ToString())) { Console.WriteLine("Detected an induced GC"); pass = true; } }; }
protected PerformanceTestContext(TraceEventDispatcher source) { _source = source; _relogger = source as ETWReloggerTraceEventSource; IsWriteEnabled = _relogger != null; if (IsWriteEnabled) { _relogger.Dynamic.All += WriteEvent; _relogger.Kernel.All += WriteEvent; _relogger.Clr.All += WriteEvent; } }
public CLRRuntimeActivityComputer(TraceEventDispatcher source) { source.Clr.MethodJittingStarted += Clr_MethodJittingStarted; source.Clr.MethodR2RGetEntryPoint += Clr_MethodR2RGetEntryPoint; source.Clr.MethodLoadVerbose += Clr_MethodLoadVerbose; source.Clr.MethodLoad += Clr_MethodLoad; source.Clr.LoaderAssemblyLoad += Clr_LoaderAssemblyLoad; source.Clr.MethodR2RGetEntryPointStart += Clr_R2RGetEntryPointStart; source.Clr.TypeLoadStart += Clr_TypeLoadStart; source.Clr.TypeLoadStop += Clr_TypeLoadStop; source.Kernel.ProcessStop += Kernel_ProcessStop; source.Completed += ProcessingComplete; }
public static void NeedProcesses(this TraceEventDispatcher source) { TraceProcesses processes = source.Processes(); if (processes == null || m_currentSource != source) { processes = new TraceProcesses(null /* TraceLog */, source); // establish listeners SetupCallbacks(source); source.UserData["Computers/Processes"] = processes; } m_currentSource = source; }
/// <summary> /// Create a new GCRefernece computer from the stream of events 'source'. When 'source' is processed /// you can call 'GetReferenceForGCAddress' to get stable ids for GC references. /// </summary> /// <param name="source"></param> public GCReferenceComputer(TraceEventDispatcher source) { source.Clr.GCBulkMovedObjectRanges += delegate(GCBulkMovedObjectRangesTraceData data) { }; source.Clr.GCBulkSurvivingObjectRanges += delegate(GCBulkSurvivingObjectRangesTraceData data) { }; source.Clr.GCStart += delegate(GCStartTraceData data) { }; source.Clr.GCGenerationRange += delegate(GCGenerationRangeTraceData data) { }; }
public GCHeapSimulators(TraceLog traceLog, TraceEventDispatcher source, MutableTraceEventStackSource stackSource, TextWriter log) { m_simulators = new GCHeapSimulator[traceLog.Processes.Count]; m_source = source; m_stackSource = stackSource; m_log = log; // Save a symbol resolver for this trace log. s_typeNameSymbolResolvers[traceLog.FilePath] = new TypeNameSymbolResolver(traceLog.FilePath, log); var etwClrProfileTraceEventParser = new ETWClrProfilerTraceEventParser(source); etwClrProfileTraceEventParser.ClassIDDefintion += CheckForNewProcess; source.Clr.GCSampledObjectAllocation += CheckForNewProcess; source.Clr.GCAllocationTick += CheckForNewProcessForTick; }
public EventStats(TraceEventDispatcher source) : this() { Action <TraceEvent> StatsCollector = delegate(TraceEvent data) { this.Increment(data); }; // Add my parsers. source.Clr.All += StatsCollector; source.Kernel.All += StatsCollector; new ClrRundownTraceEventParser(source).All += StatsCollector; new ClrStressTraceEventParser(source).All += StatsCollector; new SymbolTraceEventParser(source).All += StatsCollector; source.UnhandledEvent += StatsCollector; source.Process(); }
private void Initialize(int processID, ProcessIndex processIndex, TraceEventDispatcher source) { ProcessID = processID; ParentID = -1; ProcessIndex = processIndex; endTimeQPC = long.MaxValue; CommandLine = ""; ImageFileName = ""; Source = source; Is64Bit = false; LoadedModules = null; Log = null; Parent = null; Threads = null; EventsInProcess = null; EventsDuringProcess = null; StartTime = EndTime = default(DateTime); StartTimeRelativeMsec = EndTimeRelativeMsec = -1; }
public static ProcessLookup <JitCapProcess> Collect(JitCapCollector collector) { TraceEventDispatcher source = collector.Source; ProcessLookup <JitCapProcess> perProc = new ProcessLookup <JitCapProcess>(); source.Kernel.PerfInfoSample += delegate(SampledProfileTraceData data) { JitCapProcess stats = perProc[data]; if (stats != null) { stats.ProcessCpuTimeMsec++; string name = stats.GetSampledMethodName(collector, data); stats.UpdateMethodCounts(name); } }; source.Process(); return(perProc); }
public static void SetupCapCollectors(TraceEventDispatcher source, ClrCap.CAPAnalysisBase report) { KernelTraceEventParser kernel = source.Kernel; source.Kernel.SystemConfigCPU += delegate(SystemConfigCPUTraceData data) { report.MachineInfo.MachineName = data.ComputerName; report.MachineInfo.Domain = data.DomainName; report.MachineInfo.MemorySizeMb = data.MemSize; report.MachineInfo.NumberOfProcessors = data.NumberOfProcessors; report.MachineInfo.ProcessorFrequencyMHz = data.MHz; report.MachineInfo.HyperThreadingFlag = (int)data.HyperThreadingFlag; report.MachineInfo.PageSize = data.PageSize; }; source.Kernel.SysConfigBuildInfo += delegate(BuildInfoTraceData data) { report.OSInfo.Name = data.ProductName; report.OSInfo.Build = data.BuildLab; }; }
public bool LoadEvents(int procID, int sampleInterval100ns) { m_procID = procID; m_SampleInterval = sampleInterval100ns / 10000.0; // Filter to process TraceEvents processEvents = m_traceLog.Events.Filter(FilterEvent); // Get Dispatcher TraceEventDispatcher source = processEvents.GetSource(); kernelGuid = KernelTraceEventParser.ProviderGuid; // Hookup events source.Clr.All += OnClrEvent; ClrPrivateTraceEventParser clrPrivate = new ClrPrivateTraceEventParser(source); clrPrivate.All += OnClrPrivateEvent; KernelTraceEventParser kernel = source.Kernel; kernel.PerfInfoSample += delegate(SampledProfileTraceData data) { ThreadMemoryInfo thread = GetThread(data.ThreadID); thread.AddEvent(HeapEvents.CPUSample, data.TimeStampRelativeMSec); }; kernel.VirtualMemAlloc += OnVirtualMem; kernel.VirtualMemFree += OnVirtualMem; m_processLookup = new ProcessLookup <GCProcess>(); // Process all events into GCProcess lookup dictionary GCProcess.Collect(source, sampleInterval100ns, m_processLookup, null, false, m_traceLog); // Get the process we want return(m_processLookup.TryGetByID(procID, out m_gcProcess)); }
/// <summary> /// Execute the pinned object analyzer. /// </summary> internal void Execute( GCPinnedObjectViewType viewType) { // Process the heap snapshot, and populate the root table and process id. ProcessHeapSnapshot(); // Instantiate the necessary trace event parsers. TraceEventDispatcher eventDispatcher = _TraceLog.Events.GetSource(); PerfViewTraceEventParser perfViewParser = new PerfViewTraceEventParser(eventDispatcher); // we want the state of the heap at the time the snapshot was taken. perfViewParser.TriggerHeapSnapshot += delegate(TriggerHeapSnapshotTraceData data) { eventDispatcher.StopProcessing(); }; var heapWithPinningInfo = new PinningStackAnalysis(eventDispatcher, _TraceLog.Processes.GetProcess(_ProcessID, _TraceLog.SessionDuration.TotalMilliseconds), _StackSource, _Log); // Process the ETL file up until we detect that the heap snapshot was taken. eventDispatcher.Process(); // Iterate through all pinned objects in the heap snapshot. foreach (KeyValuePair <Address, PinningRoot> pinnedPair in _RootTable) { // Try to match the object in the heap snapshot with an object in the ETL. PinningStackAnalysisObject liveObjectInfo = heapWithPinningInfo.GetPinningInfo(pinnedPair.Key); if (liveObjectInfo != null) { // Found a match, write the appropriate call stacks. if (viewType == GCPinnedObjectViewType.PinnedObjectAllocations) { WriteAllocationStack(pinnedPair.Key, pinnedPair.Value, liveObjectInfo); } else if (viewType == GCPinnedObjectViewType.PinnedHandles) { WritePinningStacks(pinnedPair.Key, pinnedPair.Value, liveObjectInfo); } } } }
public QuadrantTestContext(TraceEventDispatcher source) : base(source) { source.Dynamic.AddCallbackForProviderEvent( QuadrantPerformanceTestAttribute.QuadrantProvider, "AppSuspended", e => { source.StopProcessing(); _closeSemaphore.Release(); }); source.Dynamic.AddCallbackForProviderEvent( PerformanceTestAttribute.XamlProviderName, "ElementCreated", e => _elementCreationTimes.Add(e.TimeStampRelativeMSec)); source.Dynamic.AddCallbackForProviderEvent( PerformanceTestAttribute.XamlProviderName, "ResourceDictionaryAdd", e => _resourceDictionaryAddTimes.Add(e.TimeStampRelativeMSec)); }
private static void RegisterCallbacks ( string providerName , string[] traceEvents , TraceEventDispatcher source , TraceEventSession session , Action < TraceEventDispatcher , TraceEventSession , TraceEvent > onOneEventTracedOnceProcessAction ) { int l = traceEvents.Length; for (int i = 0; i < l; i++) { var eventName = traceEvents[i]; var action = onOneEventTracedOnceProcessAction; if (action != null) { if (string.Compare(eventName, "*") == 0) { source .Dynamic .All += delegate (TraceEvent data) { action(source, session, data); }; } else if (string.Compare(eventName, "UnhandledEvents") == 0) { source .UnhandledEvents += delegate (TraceEvent data) { action(source, session, data); }; } else { source .Dynamic .AddCallbackForProviderEvent ( providerName , eventName , delegate (TraceEvent data) { action(source, session, data); } ); } } } }