internal static SignatureVerificationStatusFlags ValidateTimestamp(Timestamp timestamp, Signature signature, bool treatIssuesAsErrors, List <SignatureLog> issues, SigningSpecifications spec) { if (timestamp == null) { throw new ArgumentNullException(nameof(timestamp)); } if (signature == null) { throw new ArgumentNullException(nameof(signature)); } if (issues == null) { throw new ArgumentNullException(nameof(issues)); } // Default to specification v1 spec = spec ?? SigningSpecifications.V1; var validationFlags = SignatureVerificationStatusFlags.NoErrors; var signerInfo = timestamp.SignerInfo; if (timestamp.SignerInfo.Certificate != null) { try { signerInfo.CheckSignature(verifySignatureOnly: true); } catch (Exception e) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3021, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampSignatureValidationFailed, signature.FriendlyName))); issues.Add(SignatureLog.DebugLog(e.ToString())); validationFlags |= SignatureVerificationStatusFlags.SignatureCheckFailed; } if (!CertificateUtility.IsSignatureAlgorithmSupported(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3022, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampUnsupportedSignatureAlgorithm, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.SignatureAlgorithmUnsupported; } if (!CertificateUtility.IsCertificatePublicKeyValid(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3023, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampCertificateFailsPublicKeyLengthRequirement, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.CertificatePublicKeyInvalid; } if (!spec.AllowedHashAlgorithmOids.Contains(signerInfo.DigestAlgorithm.Value)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3024, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampUnsupportedSignatureAlgorithm, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.HashAlgorithmUnsupported; } try { var hashAlgorithm = CryptoHashUtility.OidToHashAlgorithmName(timestamp.TstInfo.HashAlgorithmId.Value); var signatureValue = signature.GetSignatureValue(); var messageHash = hashAlgorithm.ComputeHash(signatureValue); if (!timestamp.TstInfo.HasMessageHash(messageHash)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3019, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampIntegrityCheckFailed, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.IntegrityCheckFailed; } } catch { // If the hash algorithm is not supported OidToHashAlgorithmName will throw issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3030, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampMessageImprintUnsupportedHashAlgorithm, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.MessageImprintUnsupportedAlgorithm; } if (CertificateUtility.IsCertificateValidityPeriodInTheFuture(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3025, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampNotYetValid, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.CertificateValidityInTheFuture; } if (!CertificateUtility.IsDateInsideValidityPeriod(signerInfo.Certificate, timestamp.GeneralizedTime)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3036, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampGeneralizedTimeInvalid, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.GeneralizedTimeOutsideValidity; } } else { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3020, string.Format(CultureInfo.CurrentCulture, Strings.VerifyError_TimestampNoCertificate, signature.FriendlyName))); validationFlags |= SignatureVerificationStatusFlags.NoCertificate; } return(validationFlags); }
internal static bool IsTimestampValid(Timestamp timestamp, Signature signature, bool treatIssuesAsErrors, List <SignatureLog> issues, SigningSpecifications spec) { if (timestamp == null) { throw new ArgumentNullException(nameof(timestamp)); } if (signature == null) { throw new ArgumentNullException(nameof(signature)); } if (issues == null) { throw new ArgumentNullException(nameof(issues)); } // Default to specification v1 spec = spec ?? SigningSpecifications.V1; var isValid = true; var signerInfo = timestamp.SignerInfo; if (timestamp.SignerInfo.Certificate != null) { try { signerInfo.CheckSignature(verifySignatureOnly: true); } catch (Exception e) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3021, Strings.TimestampSignatureValidationFailed)); issues.Add(SignatureLog.DebugLog(e.ToString())); isValid = false; } if (!CertificateUtility.IsSignatureAlgorithmSupported(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3022, Strings.TimestampUnsupportedSignatureAlgorithm)); isValid = false; } if (!CertificateUtility.IsCertificatePublicKeyValid(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3023, Strings.TimestampCertificateFailsPublicKeyLengthRequirement)); isValid = false; } if (!spec.AllowedHashAlgorithmOids.Contains(signerInfo.DigestAlgorithm.Value)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3024, Strings.TimestampUnsupportedSignatureAlgorithm)); isValid = false; } try { var hashAlgorithm = CryptoHashUtility.OidToHashAlgorithmName(timestamp.TstInfo.HashAlgorithmId.Value); var signatureValue = signature.GetSignatureValue(); var messageHash = hashAlgorithm.ComputeHash(signatureValue); if (!timestamp.TstInfo.HasMessageHash(messageHash)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3019, Strings.TimestampIntegrityCheckFailed)); isValid = false; } } catch { // If the hash algorithm is not supported OidToHashAlgorithmName will throw issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3030, Strings.TimestampMessageImprintUnsupportedHashAlgorithm)); isValid = false; } if (CertificateUtility.IsCertificateValidityPeriodInTheFuture(signerInfo.Certificate)) { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3025, Strings.TimestampNotYetValid)); isValid = false; } } else { issues.Add(SignatureLog.Issue(treatIssuesAsErrors, NuGetLogCode.NU3020, Strings.TimestampNoCertificate)); isValid = false; } return(isValid); }