dotnet/maui · error · Exception

Failed to install signing cert into LocalMachine\TrustedPeop

Error message

Failed to install signing cert into LocalMachine\TrustedPeople. This step requires an elevated (administrator) shell on first run. After the cert is created once, subsequent runs can be performed without elevation.

What it means

Thrown in GenerateMsixCert during first-time cert creation: after generating a self-signed cert and re-importing it with UserKeySet, opening LocalMachine\TrustedPeople for ReadWrite and calling Add throws CryptographicException because writing to the LocalMachine store requires administrator privileges. The message explains this is a one-time elevation requirement.

Source

Thrown at eng/devices/windows.cake:161

		// current non-elevated user can use it to sign. LocalMachine\TrustedPeople only needs the
		// cert's public key for sideload trust validation, so a user-scope private key is enough.
		// Using MachineKeySet here would put the key in C:\ProgramData\Microsoft\Crypto\...
		// which is unreadable from a non-admin process — signtool then fails with "No certificates
		// were found that met all the given criteria" even though the cert is visible in the store.
		var tmpCert = new X509Certificate2(cert.Export(X509ContentType.Pfx), "", X509KeyStorageFlags.UserKeySet | X509KeyStorageFlags.PersistKeySet);
		certificateThumbprint = tmpCert.Thumbprint;

		// Writing to LocalMachine\TrustedPeople requires admin. If we don't have it, fail with a
		// clear message rather than the raw "Access is denied" from the store.
		try
		{
			localTrustedPeopleStore.Open(OpenFlags.ReadWrite);
			localTrustedPeopleStore.Add(tmpCert);
			localTrustedPeopleStore.Close();
		}
		catch (System.Security.Cryptography.CryptographicException ex)
		{
			throw new Exception(
				"Failed to install signing cert into LocalMachine\\TrustedPeople. " +
				"This step requires an elevated (administrator) shell on first run. " +
				"After the cert is created once, subsequent runs can be performed without elevation.",
				ex);
		}

		// CurrentUser\My only needs admin if the process doesn't own the profile, so do it after
		// the LocalMachine write succeeded.
		var currentUserMyStore = new X509Store("My", StoreLocation.CurrentUser);
		currentUserMyStore.Open(OpenFlags.ReadWrite);
		currentUserMyStore.Add(tmpCert);
		currentUserMyStore.Close();
	}
	else
	{
		Information("Reusing existing cert {0} from CurrentUser\\My.", certificateThumbprint);
	}

View on GitHub (pinned to f377ff1c5e)

Solutions

  1. Run the GenerateMsixCert task once from an elevated (administrator) terminal; the cert is then installed and later non-elevated runs reuse it (the IsCurrentUserSigningCertUsable branch).
  2. If you cannot get admin, ask an admin to run the task once, or pre-install the cert in LocalMachine\TrustedPeople out-of-band.
  3. Confirm the elevated run completed by checking 'Cert thumbprint:' prints a non-null value before building the MSIX.
  4. Avoid re-deleting the cert after first creation so you do not re-trigger the elevation requirement.
Defensive patterns

Strategy: try-catch

Validate before calling

// Detect first-run (no usable cert) and require elevation up front
var needsAdmin = string.IsNullOrEmpty(certificateThumbprint);
if (needsAdmin && !IsElevated())
    throw new Exception("First-run cert creation requires an elevated shell. Re-run as administrator.");

Try / catch

catch (System.Security.Cryptography.CryptographicException ex)
{
    throw new Exception("LocalMachine\\TrustedPeople write needs admin. Re-run elevated once; later runs are non-elevated.", ex);
}

Prevention

When it happens

Trigger: First run of the packaged test target on a non-elevated shell (no usable cert exists yet, so the creation path is taken); the cert was deleted and must be recreated; running on a fresh user profile or machine.

Common situations: New developer machine; CI runner without an admin-provisioned cert; LocalMachine\TrustedPeople cleared by policy; switching commonName so no existing cert matches.

Related errors


AI-assisted analysis of dotnet/maui@f377ff1c5e (2026-08-13). Data as JSON: /api/errors/633d40e7ad3468f3. Report an issue: GitHub.