public async Task <TrustStatus> IsTrusted(string certificateFileOrSignedFile, CancellationToken cancellationToken = default)
{
X509Certificate2Collection certObject = null;
X509Certificate2 preferredCertObject = null;
try
{
switch (Path.GetExtension(certificateFileOrSignedFile).ToLowerInvariant())
{
case FileConstants.MsixExtension:
case FileConstants.AppxExtension:
case ".exe":
case ".dll":
case FileConstants.AppxBundleExtension:
case FileConstants.MsixBundleExtension:
Logger.Info("Verifying certificate from a signable file {0}...", certificateFileOrSignedFile);
try
{
// certObject = X509Certificate.CreateFromSignedFile(certificateFileOrSignedFile);
certObject = new X509Certificate2Collection();
certObject.Import(certificateFileOrSignedFile);
if (certObject.Count > 1)
{
preferredCertObject = new X509Certificate2(X509Certificate.CreateFromSignedFile(certificateFileOrSignedFile));
}
}
catch (Exception e)
{
Logger.Debug("Could not get certificate details from file " + certificateFileOrSignedFile, e);
return(new TrustStatus());
}
break;
case ".cer":
case ".p12":
case ".pfx":
case ".p7x":
Logger.Info("Verifying certificate file {0}...", certificateFileOrSignedFile);
try
{
// certObject = X509Certificate.CreateFromCertFile(certificateFileOrSignedFile);
certObject = new X509Certificate2Collection();
certObject.Import(certificateFileOrSignedFile);
if (certObject.Count > 1)
{
preferredCertObject = new X509Certificate2(X509Certificate.CreateFromCertFile(certificateFileOrSignedFile));
}
}
catch (Exception e)
{
Logger.Debug("Could not get certificate details from file " + certificateFileOrSignedFile, e);
return(new TrustStatus());
}
break;
default:
try
{
Logger.Info("Trying to verify the certificate from a potentially signable file {0}...", certificateFileOrSignedFile);
// certObject = X509Certificate.CreateFromSignedFile(certificateFileOrSignedFile);
certObject = new X509Certificate2Collection();
certObject.Import(certificateFileOrSignedFile);
if (certObject.Count > 1)
{
preferredCertObject = new X509Certificate2(X509Certificate.CreateFromSignedFile(certificateFileOrSignedFile));
}
}
catch (Exception)
{
Logger.Warn("The file {0} does not seem to be signed.", certificateFileOrSignedFile);
Logger.Info("Trying to verify the certificate from a potential certificate file {0}...", certificateFileOrSignedFile);
try
{
// certObject = X509Certificate.CreateFromCertFile(certificateFileOrSignedFile);
certObject = new X509Certificate2Collection();
certObject.Import(certificateFileOrSignedFile);
if (certObject.Count > 1)
{
preferredCertObject = new X509Certificate2(X509Certificate.CreateFromCertFile(certificateFileOrSignedFile));
}
}
catch (Exception e)
{
Logger.Debug("Could not get certificate details from file " + certificateFileOrSignedFile, e);
return(new TrustStatus());
}
}
break;
}
if (certObject.Count == 0)
{
Logger.Debug("Could not get certificate details from file " + certificateFileOrSignedFile + " because the list of certificates was empty.");
return(new TrustStatus());
}
// var cert5092 = new X509Certificate2(certObject);
cancellationToken.ThrowIfCancellationRequested();
// ReSharper disable once AccessToDisposedClosure
// ReSharper disable once RedundantEnumerableCastCall
var validated = await Task.Run(() => certObject.OfType <X509Certificate2>().FirstOrDefault(c => c.Verify()), cancellationToken).ConfigureAwait(false);
if (validated != null)
{
Logger.Debug("The certificate seems to be valid.");
return(new TrustStatus(true, (preferredCertObject ?? validated).GetNameInfo(X509NameType.SimpleName, false))
{
Expires = (preferredCertObject ?? validated).NotAfter,
Issuer = (preferredCertObject ?? validated).IssuerName.Name,
Thumbprint = (preferredCertObject ?? validated).Thumbprint
});
}
else
{
Logger.Warn("The certificate seems to be invalid.");
return(new TrustStatus(false, (preferredCertObject ?? certObject[0]).GetNameInfo(X509NameType.SimpleName, false))
{
Expires = (preferredCertObject ?? certObject[0]).NotAfter,
Issuer = (preferredCertObject ?? certObject[0]).IssuerName.Name,
Thumbprint = (preferredCertObject ?? certObject[0]).Thumbprint
});
}
}
finally
{
// ReSharper disable once RedundantEnumerableCastCall
foreach (var item in certObject?.OfType <X509Certificate2>() ?? Enumerable.Empty <X509Certificate2>())
{
item.Dispose();
}
preferredCertObject?.Dispose();
}
}