Skip to content

Conversation

@aw0lid
Copy link

@aw0lid aw0lid commented Jan 20, 2026

Summary
This PR disables full assembly signing by default for non-Windows builds in src/libraries. This change addresses build failures on Linux distributions (like RHEL 9/10 and CentOS Stream) where SHA-1 is disabled for security reasons, preventing RSA+SHA-1 strong name signing.

Context
As reported in #123010, the runtime build fails on modern Linux environments because the build system attempts to use SHA-1 for assembly signing. Following the suggestion from @jkotas, instead of targeting specific Linux distros, we are disabling full signing by default on all non-Windows platforms. Full signing is typically only required for official Microsoft builds.

Changes
Modified src/libraries/Directory.Build.props to set FullAssemblySigningSupported to false when the OS is not Windows_NT.

Ensured that users can still manually override this property if needed by using a conditional check.

Impact
Linux/macOS: Improved developer experience by preventing "invalid digest" errors during local builds.

Windows: No change in behavior; full signing remains enabled by default.

Fixes #123010

@github-actions github-actions bot added the needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners label Jan 20, 2026
@dotnet-policy-service dotnet-policy-service bot added the community-contribution Indicates that the PR has been added by a community member label Jan 20, 2026
@jkotas
Copy link
Member

jkotas commented Jan 20, 2026

I think we want to change the default for all .NET runtime and SDK projects in https://github.com/dotnet/arcade/ . @dotnet/runtime-infrastructure Do you agree?

@jkotas jkotas removed the needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners label Jan 20, 2026
@aw0lid
Copy link
Author

aw0lid commented Jan 20, 2026

I see the CI failures on Linux. It seems some tests/components still strictly expect a strong name.

I agree with @jkotas that moving this to Arcade is the right way to go. It feels like a more robust architectural solution rather than just a local patch in the runtime. By fixing it in Arcade, we ensure a consistent 'build law' across all .NET products and handle Public Signing defaults more gracefully.

That said, would you prefer I investigate a Public Signing middle-ground here to unblock the CI, or should we focus our efforts on the Arcade migration instead?

@jkotas
Copy link
Member

jkotas commented Jan 20, 2026

The error is:

 error FS2014: (NETCORE_ENGINEERING_TELEMETRY=Build) A problem occurred writing the binary '/__w/1/s/artifacts/obj/System.Formats.Cbor.Tests.DataModel/Debug/net11.0/System.Formats.Cbor.Tests.DataModel.dll': A call to StrongNameSignatureSize failed (Invalid Public Key blob)
2026-01-20T23:20:03.0908368Z FSC : error FS2014: A problem occurred writing the binary '/__w/1/s/artifacts/obj/System.Formats.Cbor.Tests.DataModel/Debug/net11.0/System.Formats.Cbor.Tests.DataModel.dll': A call to StrongNameSignatureSize failed (Invalid Public Key blob) [/__w/1/s/src/libraries/System.Formats.Cbor/tests/CborDocument/System.Formats.Cbor.Tests.DataModel.fsproj]

Looks like a problem with F# compiler (F# compiler lives in http://github.com/dotnet/fsharp so the fix may need to be done there. Could you please investigate that?

@aw0lid
Copy link
Author

aw0lid commented Jan 21, 2026

The error is:

 error FS2014: (NETCORE_ENGINEERING_TELEMETRY=Build) A problem occurred writing the binary '/__w/1/s/artifacts/obj/System.Formats.Cbor.Tests.DataModel/Debug/net11.0/System.Formats.Cbor.Tests.DataModel.dll': A call to StrongNameSignatureSize failed (Invalid Public Key blob)
2026-01-20T23:20:03.0908368Z FSC : error FS2014: A problem occurred writing the binary '/__w/1/s/artifacts/obj/System.Formats.Cbor.Tests.DataModel/Debug/net11.0/System.Formats.Cbor.Tests.DataModel.dll': A call to StrongNameSignatureSize failed (Invalid Public Key blob) [/__w/1/s/src/libraries/System.Formats.Cbor/tests/CborDocument/System.Formats.Cbor.Tests.DataModel.fsproj]

Looks like a problem with F# compiler (F# compiler lives in http://github.com/dotnet/fsharp so the fix may need to be done there. Could you please investigate that?

I’ve been looking into src/Compiler/AbstractIL/ilwrite.fs in the F# repo, and it appears that the logic in writeBinaryAux might be automatically setting up a signer if a PublicKey is present, even without an explicit signer. This likely leads to the call in signImage where s.SignStream is invoked, which potentially triggers the StrongNameSignatureSize error.
However, I believe we should also wait for the infrastructure team's input. If this can be addressed globally within Arcade, it would be a much more robust solution than patching it in a single place. If they have concerns about potential side effects in other areas, we can then proceed with the localized fix in the F# compiler or the runtime tests.

@jkotas
Copy link
Member

jkotas commented Jan 21, 2026

It would be best to fix the F# compiler. To make progress, it is ok to do a temporary local workaround for tests until the fixed F# compiler propagates to the toolset that the repo is compiled with.

@vcsjones
Copy link
Member

vcsjones commented Jan 21, 2026

There is an existing issue for the F# compiler here dotnet/fsharp#17451

This issue was found when the Red Hat folks were using FullAssemblySigningSupported in their own CI.

The PublicSign option does not work when you give it a full public/private key pair. It only works with the public key. Roslyn on the other hand uses just the public part even if you give it a full key pair.

@agocke
Copy link
Member

agocke commented Jan 21, 2026

where SHA-1 is disabled for security reasons, preventing RSA+SHA-1 strong name signing.

Disabling full-signing seems OK, but we need to make sure to replace it with public signing, not delay signing. There are various tools and utilities out there that balk at delay-signed binaries.

We should also confirm that SHA-1 is only needed in the implementation, not in generating signatures. If it's needed for generating signatures then I don't think disabling full signing will actually remove all calls to SHA1.

@vcsjones
Copy link
Member

We should also confirm that SHA-1 is only needed in the implementation, not in generating signatures. If it's needed for generating signatures then I don't think disabling full signing will actually remove all calls to SHA1

FullAssemblySigningSupported makes the build problem "go away" on Red Hat so whatever is needed, this is sufficient to at least make Red Hat-like development feasible.

@jkotas
Copy link
Member

jkotas commented Jan 21, 2026

remove all calls to SHA1.

SHA1 alone is not blocked (yet?). RSA+SHA-1 is the blocked algorithm that needs to be avoided.

@aw0lid
Copy link
Author

aw0lid commented Jan 21, 2026

Done
The F# signing issues are resolved.

Most checks passed. The osx-x64 job timed out due to a lost agent (Agent 58), and the WASM failure appears to be the global issue tracked in #123421. Ready for review. @jkotas

<PropertyGroup>
<!-- Default any assembly not specifying a key to use the Open Key -->
<StrongNameKeyId>Open</StrongNameKeyId>
<FullAssemblySigningSupported Condition="'$(FullAssemblySigningSupported)' == '' and '$(OS)' != 'Windows_NT'">false</FullAssemblySigningSupported>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it be better to have this in the top-level Directory.Build.props file so that it applied to the whole repo?

@jkotas
Copy link
Member

jkotas commented Jan 21, 2026

@dotnet/runtime-infrastructure What is the best way to ensure that this does not break dotnet/dotnet official build? Or should we just give this a try and revert if it breaks the dotnet/dotnet official build?

@jkoritzinsky
Copy link
Member

I have a request out to create the new VMR validation pipeline we talked about, but in the meantime the best way to validate would be with a PR into the VMR with the changes.

Co-authored-by: Jan Kotas <jkotas@microsoft.com>
@aw0lid
Copy link
Author

aw0lid commented Jan 22, 2026

If we decide to move forward with a VMR PR for validation as @jkoritzinsky suggested, I was wondering if it might make more sense to implement this fix in Arcade instead of a local override in the Runtime.
​My thinking is:
​There might be other assemblies in the ecosystem (like SDK or ASP.NET) that could face the same SHA-1 issues on RHEL 9.
​If we address this in Arcade, we might avoid chasing the same issue across multiple repositories later.
​The VMR PR could be a good opportunity to see if an Arcade-level change consistently solves this for the entire stack.
​What do you think? Does it make sense to consider a more global approach in Arcade if we go with the VMR validation?
​/cc @jkotas @jkoritzinsky

@jkotas
Copy link
Member

jkotas commented Jan 22, 2026

Yes, I agree.

It may be a good idea to fix the F# compiler first so that the global setting does not cause problems for repo-specific workflows. VMR validation will catch problems in end-to-end official builds, etc. I won't catch problems in repo-specific workflows.

@aw0lid
Copy link
Author

aw0lid commented Jan 22, 2026

Exactly.
I'll split this into two steps:
Update dotnet/fsharp to explicitly opt-in to signing (Override) so it remains stable.
Update dotnet/arcade to change the global default to 'Off' for non-Windows, while keeping the OpenSSL logic available for those who opt-in (like F#). This ensures Zero-impact on the VMR and other repos. Starting with F# investigation now.

@aw0lid
Copy link
Author

aw0lid commented Jan 22, 2026

Update: As discussed, I have opened a PR in the F# repository (dotnet/fsharp#19236) to explicitly opt-in to assembly signing. This ensures F# remains stable before we move the global default in Arcade.

Once the F# PR is merged and the toolset is updated, I will proceed with the Arcade PR to change the default to false for all non-Windows platforms.

I'll keep this PR as a reference for now, but the final fix will be delivered via Arcade.

Thanks for the guidance @jkotas!

@aw0lid
Copy link
Author

aw0lid commented Jan 23, 2026

Quick update: The fix for the F# compiler root cause is ready and all CI checks are passing in dotnet/fsharp#19242. Once that's merged and the toolset is updated, I'll proceed with the Arcade PR to change the global default as discussed. Keeping this PR open for reference until we transition to the Arcade/VMR phase

@jkotas jkotas added the blocked Issue/PR is blocked on something - see comments label Jan 23, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area-Infrastructure blocked Issue/PR is blocked on something - see comments community-contribution Indicates that the PR has been added by a community member

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

Make building runtime easier on RHEL

5 participants