Skip to content
Development
Skill

/build-perf-diagnostics

Diagnose MSBuild bottlenecks from binlog timelines and Target/Task Performance Summaries after build-perf-baseline establishes measurements. USE FOR: unknown build slowness, RAR >5s, analyzers >30% of Csc, one target >50% of build time, node utilization <80%, excessive Copy

From plugin
skills
5.8k106 skills20 agents

Claude Code

$ npx -y skills add dotnet/skills --skill build-perf-diagnostics --agent claude-code

SKILL.md

build-perf-diagnostics.SKILL.md
name: build-perf-diagnostics
description: "Diagnose MSBuild bottlenecks from binlog timelines and Target/Task Performance Summaries after baseline measurements. USE FOR: unknown build slowness, RAR >5s, analyzers >30% of Csc, a target >50% of build, node utilization below 80%, excessive Copy, restore overhead. DO NOT USE FOR: within-build duplicates (find-repeated-work-within-one-build), known repeated restores (eliminate-redundant-restores), initial baselines (build-perf-baseline), incremental rebuilds (incremental-build), parallelism tuning (build-parallelism), non-MSBuild builds."
license: MIT

Performance Analysis Methodology

1. **Generate a binlog**: `dotnet build /bl:{} -m` 2. Use the **binlog MCP server** (`Microsoft.AITools.BinlogMcp`, exposed under the `binlog` MCP namespace) which is bundled with this plugin

If the server cannot connect, use `troubleshoot-binlog-mcp` when startup repair is wanted. If repair is blocked, declined, or unnecessary, use the replay flow below.

Alternate flow when MCP is unavailable: binlog replay to text logs

1. **Generate a binlog**: `dotnet build /bl:{} -m` 2. **Replay to diagnostic log with performance summary**:

   dotnet msbuild build.binlog -noconlog -fl "-flp:v=diag;logfile=full.log;performancesummary"

3. **Read the performance summary** (at the end of `full.log`):

   grep "Target Performance Summary\|Task Performance Summary" -A 50 full.log

4. **Find expensive targets and tasks**: The PerformanceSummary section lists all targets/tasks sorted by cumulative time 5. **Check for node utilization**: grep for scheduling and node messages

   grep -i "node.*assigned\|building with\|scheduler" full.log | head -30

6. **Check analyzers**: grep for analyzer timing

   grep -i "analyzer.*elapsed\|Total analyzer execution time\|CompilerAnalyzerDriver" full.log

Key Metrics and Thresholds

  • **Build duration**: what's "normal" — small project <10s, medium <60s, large <5min
  • **Node utilization**: ideal is >80% active time across nodes. Low utilization = serialization bottleneck
  • **Single target domination**: if one target is >50% of build time, investigate
  • **Analyzer time vs compile time**: analyzers should be <30% of Csc task time. If higher, consider removing expensive analyzers
  • **RAR time**: ResolveAssemblyReference >5s is concerning. >15s is pathological

Common Bottlenecks

1. ResolveAssemblyReference (RAR) Slowness

  • **Symptoms**: RAR taking >5s per project
  • **Root causes**: too many assembly references, network-based reference paths, large assembly search paths
  • **Fixes**: reduce reference count, use `<DesignTimeBuild>false</DesignTimeBuild>` for RAR-heavy analysis, set `<ResolveAssemblyReferencesSilent>true</ResolveAssemblyReferencesSilent>` for diagnostic
  • **Advanced**: `<DesignTimeBuild>` and `<ResolveAssemblyWarnOrErrorOnTargetArchitectureMismatch>`
  • **Key insight**: RAR runs unconditionally even on incremental builds because users may have installed targeting packs or GACed assemblies (see dotnet/msbuild#2015). With .NET Core micro-assemblies, the reference count is often very high.
  • **Reduce transitive references**: Set `<DisableTransitiveProjectReferences>true</DisableTransitiveProjectReferences>` to avoid pulling in the full transitive closure (note: projects may need to add direct references for any types they consume). Use `ReferenceOutputAssembly="false"` on ProjectReferences that are only needed at build time (not API surface). Trim unused PackageReferences.

2. Roslyn Analyzers and Source Generators

  • **Symptoms**: Csc task takes much longer than expected for file count (>2× clean compile time)
  • **Diagnosis**: Check the Task Performance Summary in the replayed log for Csc task time; grep for analyzer timing messages; compare Csc duration with and without analyzers (`/p:RunAnalyzers=false`)
  • **Fixes**:
  • Conditionally disable in dev: `<RunAnalyzers Condition="'$(ContinuousIntegrationBuild)' != 'true'">false</RunAnalyzers>`
  • Per-configuration: `<RunAnalyzers Condition="'$(Configuration)' == 'Debug'">false</RunAnalyzers>`
  • Code-style only: `<EnforceCodeStyleInBuild Condition="'$(ContinuousIntegrationBuild)' == 'true'">true</EnforceCodeStyleInBuild>`
  • Remove genuinely redundant analyzers from inner loop
  • Severity config in .editorconfig for less critical rules
  • **Key principle**: Preserve analyzer enforcement in CI. Never just "remove" analyzers — configure them conditionally.
  • **GlobalPackageReference**: Analyzers added via `GlobalPackageReference` in `Directory.Packages.props` apply to ALL projects. Consider if test projects need the same analyzer set as production code.
  • **EnforceCodeStyleInBuild**: When set to `true` in `Directory.Build.props`, forces code-style analysis on every build. Should be conditional on CI environment (`ContinuousIntegrationBuild`) to avoid slowing dev inner loop.

3. Serialization Bottlenecks (Single-threaded targets)

  • **Symptoms**: Performance summary shows most build time concentrated in a single project; diagnostic log shows idle nodes while one works
  • **Common culprits**: targets without proper dependency declaration, single project on critical path
  • **Fixes**: split large projects, optimize the critical path project, ensure proper `BuildInParallel`

4. Excessive File I/O (Copy tasks)

  • **Symptoms**: Copy task shows high aggregate time
  • **Root causes**: copying thousands of files, copying across network drives, Copy task unintentionally running once per item (per-file) instead of as a single batch (see dotnet/msbuild#12884)
  • **Fixes**: use hardlinks (`<CreateHardLinksForCopyFilesToOutputDirectoryIfPossible>true</CreateHardLinksForCopyFilesToOutputDirectoryIfPossible>`), reduce CopyToOutputDirectory items, use `<UseCommonOutputDirectory>true</UseCommonOutputDirectory>` when appropriate, set `<SkipCopyUnchangedFiles>true</SkipCopyUnchangedFiles>`, consider `--art
Read more
@dotnet
Ships withskills

This repository contains the .NET team's curated set of portable skills and host-specific custom agents for coding agents. For information about the Agent Skills standard, see agentskills.io.

5.8k106 skills20 agents
Get the whole plugin

Stars on GitHub

Momentum

stars in total
5.8k
Star history of dotnet/skills on GitHub, a chart by star-history.com

Other skills on skills.

csharp-scripts

csharp-scripts

Run file-based C# apps with the .NET CLI when the user explicitly wants C#/.NET code without creating a project. Use for C#…

@dotnet@dotnetInstall Skill
dotnet-pinvoke

dotnet-pinvoke

Correctly call native (C/C++) libraries from .NET using P/Invoke and LibraryImport. Covers function signatures, string…

@dotnet@dotnetInstall Skill
nuget-trusted-publishing

nuget-trusted-publishi…

Set up NuGet trusted publishing (OIDC) on a GitHub Actions repo — replaces long-lived API keys with short-lived tokens. USE FOR:…

@dotnet@dotnetInstall Skill
vectorization

vectorization

Design, implement, optimize, and review SIMD code in .NET. USE FOR: vectorizing scalar loops with TensorPrimitives,…

@dotnet@dotnetInstall Skill
technology-selection

technology-selection

Guides technology selection and implementation of AI and ML features in .NET 8+ applications using ML.NET,…

@dotnet@dotnetInstall Skill

More skills from other plugins.

brainstorming
Auto-invoked

brainstorming

You MUST use this before any creative work - creating features, building components, adding functionality, modifying behavior, or…

@obra@obraInstall Skill
ask-matt

ask-matt

Ask which skill or flow fits your situation. A router over the skills in this repo.

skills11d309k
@mattpocock@mattpocockInstall Skill
accessibility
Auto-invoked

accessibility

Design, implement, and audit accessible UI to WCAG 2.2 Level AA across Web, iOS, and Android — semantic ARIA roles and labels,…

ecc12d293k
@affaan-m@affaan-mInstall Skill
compiler-commit

compiler-commit

Use when you want to verify compiler changes and commit with the correct convention. Runs tests, lint, and format, then commits…

react2d252k
@facebook@facebookInstall Skill

Questions about build-perf-diagnostics.

Which coding agents can use build-perf-diagnostics?
build-perf-diagnostics installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.