Skip to content

[Security] setup-dotnet/action.yml — dotnet-install.ps1 downloaded and executed without signature or hash verification #787

@Christophe-Rogiers

Description

@Christophe-Rogiers

Severity: Warning
File: .github/actions/setup-dotnet/action.yml lines 28-53

Description:

On every CI run the composite action downloads dotnet-install.ps1 from https://dot.net/v1/dotnet-install.ps1 and executes it without verifying what was returned:

$url = "https://dot.net/v1/dotnet-install.ps1"
...
curl.exe -L $url -o dotnet-install.ps1
...
powershell -ExecutionPolicy Bypass -File ./dotnet-install.ps1 `
  -JsonFile "$env:GITHUB_WORKSPACE\global.json" `
  -InstallDir $installDir

There is no Authenticode check (Get-AuthenticodeSignature), no SHA pin, and -ExecutionPolicy Bypass explicitly disables any local signing enforcement. curl.exe -L also silently follows redirects, so compromise of any host in the chain (DNS, CDN, a redirect target) gives an attacker arbitrary PowerShell execution inside the build environment with access to GITHUB_TOKEN and the signing secrets referenced later in the pipeline.

The pinned-version concern in #751 (closed) has been addressed via -JsonFile, but the script that consumes that file is still unverified — the pinning is only as strong as the script that interprets it.

This is in the same class as #607 (third-party actions pinned to mutable tags): for a release artefact signed with SignPath, every uncontrolled input into the build pipeline is in scope.

Suggested fix:

Either:

  1. Verify the Authenticode signature before executing:
    $sig = Get-AuthenticodeSignature ./dotnet-install.ps1
    if ($sig.Status -ne 'Valid' -or $sig.SignerCertificate.Subject -notmatch 'Microsoft Corporation') {
        throw "dotnet-install.ps1 signature check failed: $($sig.Status)"
    }
  2. Or vendor the script into the repo (pin a specific commit of dotnet-install.ps1), and update it deliberately via PR the same way third-party actions are pinned to SHAs today.

Option 2 is the lowest-risk option and matches the rest of the repo's hardening stance.

Metadata

Metadata

Assignees

Labels

ciCI/CD

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions