Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Upgrading VS can cause projects to appear out-of-date, triggering lots of builds #9515

Open
drewnoakes opened this issue Jul 30, 2024 · 1 comment
Labels
Area-External Owned by another feature area and not this repo. Likely be closed in lieu of issue against it. Feature-Up-to-date Build up-to-date check that avoids shelling out to MSBuild unless necessary. Performance-Scenario-Build This issue affects build performance. Tenet-Performance This issue affects the "Performance" tenet. Triage-Approved Reviewed and prioritized
Milestone

Comments

@drewnoakes
Copy link
Member

Steps

  1. Enable fast up-to-date check logging
  2. Create a .NET project and build it a few times, ensuring the project is up-to-date
  3. Close VS
  4. Upgrade VS
  5. Re-open the project
  6. Build the project

Expected

Project is still up-to-date.

Actual

Changes to MSBuild in the VS directory cause project(s) to appear out of date.

Logs show:

FastUpToDate: Input 'C:\Program Files\Microsoft Visual Studio\2022\Preview\MSBuild\Current\Microsoft.Common.targets\ImportAfter\Microsoft.LiveUnitTesting.targets' is newer (2024-07-29 09:35:47.859) than earliest output 'C:\myproject\some-file.cs' (2024-07-26 10:25:17.495), not up-to-date.

Analysis

We already have code that attempts to exclude certain inputs from the FUTDC based on folder location. These are files that we do not reasonably expect to change, such as files in NuGet packages and files in Program Files. That feature has either regressed, or should be extended to handle this case.

@drewnoakes drewnoakes added Bug Tenet-Performance This issue affects the "Performance" tenet. Feature-Up-to-date Build up-to-date check that avoids shelling out to MSBuild unless necessary. Performance-Scenario-Build This issue affects build performance. labels Jul 30, 2024
@drewnoakes drewnoakes added the Triage-Approved Reviewed and prioritized label Aug 8, 2024
@drewnoakes drewnoakes added this to the 17.12 milestone Aug 8, 2024
@drewnoakes
Copy link
Member Author

A more detailed log, showing why this file is being checked:

FastUpToDate: Comparing timestamps of inputs and outputs:
FastUpToDate:     Adding UpToDateCheckBuilt outputs:
FastUpToDate:         C:\MyProject\bin\MyProject\Debug\net8.0\MyProject.dll
FastUpToDate:         C:\MyProject\obj\MyProject\Debug\net8.0\MyProject.dll
FastUpToDate:         C:\MyProject\bin\MyProject\Debug\net8.0\MyProject.xml
FastUpToDate:         C:\MyProject\obj\MyProject\Debug\net8.0\MyProject.xml
FastUpToDate:     Adding newest import input:
FastUpToDate:         C:\Program Files\Microsoft Visual Studio\2022\Preview\MSBuild\Current\Microsoft.Common.targets\ImportAfter\Microsoft.LiveUnitTesting.targets
FastUpToDate: Input 'C:\Program Files\Microsoft Visual Studio\2022\Preview\MSBuild\Current\Microsoft.Common.targets\ImportAfter\Microsoft.LiveUnitTesting.targets' is newer (2024-09-19 10:15:54.924) than earliest output 'C:\MyProject\bin\MyProject\Debug\net8.0\MyProject.xml' (2024-09-19 09:47:41.324), not up-to-date.
FastUpToDate: Up-to-date check completed in 1.4 ms
------ Build started: Project: MyProject, Configuration: Debug Any CPU ------

The newest import input is the most recently edited project file (i.e. .props/.targets/.csproj/etc), and MSBuild tells us this during DTBs (via the first item in MSBuildAllProjects). This means that we don't have to check every single project file, only the newest. Unfortunately, if the newest file is one of these "read-only" files, it may be that another important change was made to a different project file that is invisible to the FUTD check.

All that to say that unfortunately it won't be 100% reliable to ignore a "read-only" in this case, purely with changes to the FUTDC.

To pursue this, we could change MSBuild to optionally exclude these items when computing the newest project file, but that'd require a change to MSBuild.

The relevant code in MSbuild is:

https://github.com/dotnet/msbuild/blob/5bab860b2477f03050f170473a2563c5217d546f/src/Build/Evaluation/Evaluator.cs#L2170-L2173

And we would apply the policy defined in:

/// <summary>
/// Gets whether a file is expected to not be modified in place on disk once it has been created.
/// </summary>
/// <param name="filePath">The path to the file to test.</param>
/// <returns><see langword="true"/> if the file is non-modifiable, otherwise <see langword="false"/>.</returns>
public bool IsNonModifiable(string filePath)
{
return (s_programFiles64 is not null && filePath.StartsWith(s_programFiles64, StringComparisons.Paths))
|| (s_programFiles86 is not null && filePath.StartsWith(s_programFiles86, StringComparisons.Paths))
|| (s_windows is not null && filePath.StartsWith(s_windows, StringComparisons.Paths))
|| _nuGetPackageFolders.Any(static (nuGetFolder, filePath) => filePath.StartsWith(nuGetFolder, StringComparisons.Paths), filePath)
|| (s_vsInstallationDirectory is not null && filePath.StartsWith(s_vsInstallationDirectory, StringComparisons.Paths));
}

@drewnoakes drewnoakes modified the milestones: 17.12, Backlog Sep 19, 2024
@drewnoakes drewnoakes added the Area-External Owned by another feature area and not this repo. Likely be closed in lieu of issue against it. label Sep 19, 2024
@drewnoakes drewnoakes removed the Bug label Oct 16, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-External Owned by another feature area and not this repo. Likely be closed in lieu of issue against it. Feature-Up-to-date Build up-to-date check that avoids shelling out to MSBuild unless necessary. Performance-Scenario-Build This issue affects build performance. Tenet-Performance This issue affects the "Performance" tenet. Triage-Approved Reviewed and prioritized
Projects
None yet
Development

No branches or pull requests

1 participant