use of org.bouncycastle.operator.ContentVerifierProvider in project xipki by xipki.
the class OcspServerImpl method checkSignature.
private Object checkSignature(byte[] request, RequestOption requestOption) throws OCSPException {
OCSPRequest req;
try {
if (!requestOption.isValidateSignature()) {
return OcspRequest.getInstance(request);
}
if (!OcspRequest.containsSignature(request)) {
if (requestOption.isSignatureRequired()) {
LOG.warn("signature in request required");
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.sigRequired);
} else {
return OcspRequest.getInstance(request);
}
}
try {
req = OCSPRequest.getInstance(request);
} catch (IllegalArgumentException ex) {
throw new EncodingException("could not parse OCSP request", ex);
}
} catch (EncodingException ex) {
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.malformedRequest);
}
OCSPReq ocspReq = new OCSPReq(req);
X509CertificateHolder[] bcCerts = ocspReq.getCerts();
if (bcCerts == null || bcCerts.length < 1) {
LOG.warn("no certificate found in request to verify the signature");
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.unauthorized);
}
X509Cert[] certs = new X509Cert[bcCerts.length];
for (int i = 0; i < certs.length; i++) {
certs[i] = new X509Cert(bcCerts[i]);
}
ContentVerifierProvider cvp;
try {
cvp = securityFactory.getContentVerifierProvider(certs[0]);
} catch (InvalidKeyException ex) {
String message = ex.getMessage();
LOG.warn("securityFactory.getContentVerifierProvider, InvalidKeyException: {}", message);
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.unauthorized);
}
boolean sigValid = ocspReq.isSignatureValid(cvp);
if (!sigValid) {
LOG.warn("request signature is invalid");
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.unauthorized);
}
// validate the certPath
Date referenceTime = new Date();
if (canBuildCertpath(certs, requestOption, referenceTime)) {
try {
return OcspRequest.getInstance(req);
} catch (EncodingException ex) {
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.malformedRequest);
}
}
LOG.warn("could not build certpath for the request's signer certificate");
return unsuccesfulOCSPRespMap.get(OcspResponseStatus.unauthorized);
}
use of org.bouncycastle.operator.ContentVerifierProvider in project xipki by xipki.
the class SecurityFactoryImpl method verifyPopo.
@Override
public boolean verifyPopo(PKCS10CertificationRequest csr, AlgorithmValidator algoValidator, DHSigStaticKeyCertPair ownerKeyAndCert) {
if (algoValidator != null) {
AlgorithmIdentifier algId = csr.getSignatureAlgorithm();
if (!algoValidator.isAlgorithmPermitted(algId)) {
String algoName;
try {
algoName = SignAlgo.getInstance(algId).getJceName();
} catch (NoSuchAlgorithmException ex) {
algoName = algId.getAlgorithm().getId();
}
LOG.error("POPO signature algorithm {} not permitted", algoName);
return false;
}
}
SubjectPublicKeyInfo pkInfo = csr.getSubjectPublicKeyInfo();
try {
PublicKey pk = KeyUtil.generatePublicKey(pkInfo);
ContentVerifierProvider cvp = getContentVerifierProvider(pk, ownerKeyAndCert);
return csr.isSignatureValid(cvp);
} catch (InvalidKeyException | PKCSException | InvalidKeySpecException ex) {
LogUtil.error(LOG, ex, "could not validate POPO of CSR");
return false;
}
}
use of org.bouncycastle.operator.ContentVerifierProvider in project xipki by xipki.
the class BaseCmpResponder method verifyPopo.
protected boolean verifyPopo(CertificateRequestMessage certRequest, SubjectPublicKeyInfo spki, boolean allowRaPopo) {
int popType = certRequest.getProofOfPossessionType();
if (popType == CertificateRequestMessage.popRaVerified && allowRaPopo) {
return true;
}
if (popType != CertificateRequestMessage.popSigningKey) {
LOG.error("unsupported POP type: " + popType);
return false;
}
// check the POP signature algorithm
ProofOfPossession pop = certRequest.toASN1Structure().getPopo();
POPOSigningKey popoSign = POPOSigningKey.getInstance(pop.getObject());
SignAlgo popoAlg;
try {
popoAlg = SignAlgo.getInstance(popoSign.getAlgorithmIdentifier());
} catch (NoSuchAlgorithmException ex) {
LogUtil.error(LOG, ex, "Cannot parse POPO signature algorithm");
return false;
}
AlgorithmValidator algoValidator = getCmpControl().getPopoAlgoValidator();
if (!algoValidator.isAlgorithmPermitted(popoAlg)) {
LOG.error("POPO signature algorithm {} not permitted", popoAlg.getJceName());
return false;
}
try {
PublicKey publicKey = securityFactory.generatePublicKey(spki);
DhpocControl dhpocControl = getCa().getCaInfo().getDhpocControl();
DHSigStaticKeyCertPair kaKeyAndCert = null;
if (SignAlgo.DHPOP_X25519 == popoAlg || SignAlgo.DHPOP_X448 == popoAlg) {
if (dhpocControl != null) {
DhSigStatic dhSigStatic = DhSigStatic.getInstance(popoSign.getSignature().getBytes());
IssuerAndSerialNumber isn = dhSigStatic.getIssuerAndSerial();
ASN1ObjectIdentifier keyAlgOid = spki.getAlgorithm().getAlgorithm();
kaKeyAndCert = dhpocControl.getKeyCertPair(isn.getName(), isn.getSerialNumber().getValue(), EdECConstants.getName(keyAlgOid));
}
if (kaKeyAndCert == null) {
return false;
}
}
ContentVerifierProvider cvp = securityFactory.getContentVerifierProvider(publicKey, kaKeyAndCert);
return certRequest.isValidSigningKeyPOP(cvp);
} catch (InvalidKeyException | IllegalStateException | CRMFException ex) {
LogUtil.error(LOG, ex);
}
return false;
}
use of org.bouncycastle.operator.ContentVerifierProvider in project pdfbox by apache.
the class TestCreateSignature method checkLTV.
private void checkLTV(File outFile) throws IOException, GeneralSecurityException, OCSPException, OperatorCreationException, CMSException {
try (PDDocument doc = Loader.loadPDF(outFile)) {
PDSignature signature = doc.getLastSignatureDictionary();
byte[] contents = signature.getContents();
PDDocumentCatalog docCatalog = doc.getDocumentCatalog();
COSDictionary dssDict = docCatalog.getCOSObject().getCOSDictionary(COSName.getPDFName("DSS"));
COSArray dssCertArray = dssDict.getCOSArray(COSName.getPDFName("Certs"));
COSDictionary vriDict = dssDict.getCOSDictionary(COSName.getPDFName("VRI"));
// Check that all known signature certificates are in the VRI/signaturehash/Cert array
byte[] signatureHash = MessageDigest.getInstance("SHA-1").digest(contents);
String hexSignatureHash = Hex.getString(signatureHash);
System.out.println("hexSignatureHash: " + hexSignatureHash);
CMSSignedData signedData = new CMSSignedData(contents);
Store<X509CertificateHolder> certificatesStore = signedData.getCertificates();
HashSet<X509CertificateHolder> certificateHolderSet = new HashSet<>(certificatesStore.getMatches(null));
COSDictionary sigDict = vriDict.getCOSDictionary(COSName.getPDFName(hexSignatureHash));
COSArray sigCertArray = sigDict.getCOSArray(COSName.getPDFName("Cert"));
Set<X509CertificateHolder> sigCertHolderSetFromVRIArray = new HashSet<>();
for (int i = 0; i < sigCertArray.size(); ++i) {
COSStream certStream = (COSStream) sigCertArray.getObject(i);
try (InputStream is = certStream.createInputStream()) {
sigCertHolderSetFromVRIArray.add(new X509CertificateHolder(IOUtils.toByteArray(is)));
}
}
for (X509CertificateHolder holder : certificateHolderSet) {
if (holder.getSubject().toString().contains("QuoVadis OCSP Authority Signature")) {
// not relevant here
continue;
}
// disabled until PDFBOX-5203 is fixed
// assertTrue(sigCertHolderSetFromVRIArray.contains(holder),
// "File '" + outFile + "' Root/DSS/VRI/" + hexSignatureHash +
// "/Cert array doesn't contain a certificate with subject '" +
// holder.getSubject() + "' and serial " + holder.getSerialNumber());
}
// Get all certificates. Each one should either be issued (= signed) by a certificate of the set
Set<X509Certificate> certSet = new HashSet<>();
for (int i = 0; i < dssCertArray.size(); ++i) {
COSStream certStream = (COSStream) dssCertArray.getObject(i);
try (InputStream is = certStream.createInputStream()) {
X509Certificate cert = (X509Certificate) certificateFactory.generateCertificate(is);
certSet.add(cert);
}
}
for (X509Certificate cert : certSet) {
boolean verified = false;
for (X509Certificate cert2 : certSet) {
try {
cert.verify(cert2.getPublicKey(), SecurityProvider.getProvider());
verified = true;
} catch (GeneralSecurityException ex) {
// not the issuer
}
}
// disabled until PDFBOX-5203 is fixed
// assertTrue(verified,
// "Certificate " + cert.getSubjectX500Principal() + " not issued by any certificate in the Certs array");
}
// Each CRL should be signed by one of the certificates in Certs
Set<X509CRL> crlSet = new HashSet<>();
COSArray crlArray = dssDict.getCOSArray(COSName.getPDFName("CRLs"));
for (int i = 0; i < crlArray.size(); ++i) {
COSStream crlStream = (COSStream) crlArray.getObject(i);
try (InputStream is = crlStream.createInputStream()) {
X509CRL cert = (X509CRL) certificateFactory.generateCRL(is);
crlSet.add(cert);
}
}
for (X509CRL crl : crlSet) {
boolean crlVerified = false;
X509Certificate crlIssuerCert = null;
for (X509Certificate cert : certSet) {
try {
crl.verify(cert.getPublicKey(), SecurityProvider.getProvider());
crlVerified = true;
crlIssuerCert = cert;
} catch (GeneralSecurityException ex) {
// not the issuer
}
}
assertTrue(crlVerified, "issuer of CRL not found in Certs array");
byte[] crlSignatureHash = MessageDigest.getInstance("SHA-1").digest(crl.getSignature());
String hexCrlSignatureHash = Hex.getString(crlSignatureHash);
System.out.println("hexCrlSignatureHash: " + hexCrlSignatureHash);
// Check that the issueing certificate is in the VRI array
COSDictionary crlSigDict = vriDict.getCOSDictionary(COSName.getPDFName(hexCrlSignatureHash));
COSArray certArray2 = crlSigDict.getCOSArray(COSName.getPDFName("Cert"));
COSStream certStream = (COSStream) certArray2.getObject(0);
X509CertificateHolder certHolder2;
try (InputStream is2 = certStream.createInputStream()) {
certHolder2 = new X509CertificateHolder(IOUtils.toByteArray(is2));
}
assertEquals(certHolder2, new X509CertificateHolder(crlIssuerCert.getEncoded()), "CRL issuer certificate missing in VRI " + hexCrlSignatureHash);
}
Set<OCSPResp> oscpSet = new HashSet<>();
COSArray ocspArray = dssDict.getCOSArray(COSName.getPDFName("OCSPs"));
for (int i = 0; i < ocspArray.size(); ++i) {
COSStream ocspStream = (COSStream) ocspArray.getObject(i);
try (InputStream is = ocspStream.createInputStream()) {
OCSPResp ocspResp = new OCSPResp(is);
oscpSet.add(ocspResp);
}
}
for (OCSPResp ocspResp : oscpSet) {
BasicOCSPResp basicResponse = (BasicOCSPResp) ocspResp.getResponseObject();
assertEquals(OCSPResponseStatus.SUCCESSFUL, ocspResp.getStatus());
assertTrue(basicResponse.getCerts().length >= 1, "OCSP should have at least 1 certificate");
byte[] ocspSignatureHash = MessageDigest.getInstance("SHA-1").digest(basicResponse.getSignature());
String hexOcspSignatureHash = Hex.getString(ocspSignatureHash);
System.out.println("ocspSignatureHash: " + hexOcspSignatureHash);
long secondsOld = (System.currentTimeMillis() - basicResponse.getProducedAt().getTime()) / 1000;
assertTrue(secondsOld < 20, "OCSP answer is too old, is from " + secondsOld + " seconds ago");
X509CertificateHolder ocspCertHolder = basicResponse.getCerts()[0];
ContentVerifierProvider verifier = new JcaContentVerifierProviderBuilder().setProvider(SecurityProvider.getProvider()).build(ocspCertHolder);
assertTrue(basicResponse.isSignatureValid(verifier));
COSDictionary ocspSigDict = vriDict.getCOSDictionary(COSName.getPDFName(hexOcspSignatureHash));
// Check that the Cert is in the VRI array
COSArray certArray2 = ocspSigDict.getCOSArray(COSName.getPDFName("Cert"));
COSStream certStream = (COSStream) certArray2.getObject(0);
X509CertificateHolder certHolder2;
try (InputStream is2 = certStream.createInputStream()) {
certHolder2 = new X509CertificateHolder(IOUtils.toByteArray(is2));
}
assertEquals(certHolder2, ocspCertHolder, "OCSP certificate is not in the VRI array");
}
}
}
use of org.bouncycastle.operator.ContentVerifierProvider in project ozone by apache.
the class TestCertificateSignRequest method testGenerateCSRwithSan.
@Test
public void testGenerateCSRwithSan() throws NoSuchProviderException, NoSuchAlgorithmException, SCMSecurityException, OperatorCreationException, PKCSException {
String clusterID = UUID.randomUUID().toString();
String scmID = UUID.randomUUID().toString();
String subject = "DN001";
HDDSKeyGenerator keyGen = new HDDSKeyGenerator(securityConfig.getConfiguration());
KeyPair keyPair = keyGen.generateKey();
CertificateSignRequest.Builder builder = new CertificateSignRequest.Builder().setSubject(subject).setScmID(scmID).setClusterID(clusterID).setKey(keyPair).setConfiguration(conf);
// Multi-home
builder.addIpAddress("192.168.1.1");
builder.addIpAddress("192.168.2.1");
builder.addServiceName("OzoneMarketingCluster003");
builder.addDnsName("dn1.abc.com");
PKCS10CertificationRequest csr = builder.build();
// Check the Subject Name is in the expected format.
String dnName = String.format(SecurityUtil.getDistinguishedNameFormat(), subject, scmID, clusterID);
Assert.assertEquals(csr.getSubject().toString(), dnName);
// Verify the public key info match
byte[] encoded = keyPair.getPublic().getEncoded();
SubjectPublicKeyInfo subjectPublicKeyInfo = SubjectPublicKeyInfo.getInstance(ASN1Sequence.getInstance(encoded));
SubjectPublicKeyInfo csrPublicKeyInfo = csr.getSubjectPublicKeyInfo();
Assert.assertEquals(csrPublicKeyInfo, subjectPublicKeyInfo);
// Verify CSR with attribute for extensions
Assert.assertEquals(1, csr.getAttributes().length);
Extensions extensions = SecurityUtil.getPkcs9Extensions(csr);
// Verify key usage extension
Extension sanExt = extensions.getExtension(Extension.keyUsage);
Assert.assertEquals(true, sanExt.isCritical());
verifyServiceId(extensions);
// Verify signature in CSR
ContentVerifierProvider verifierProvider = new JcaContentVerifierProviderBuilder().setProvider(securityConfig.getProvider()).build(csr.getSubjectPublicKeyInfo());
Assert.assertEquals(true, csr.isSignatureValid(verifierProvider));
}
Aggregations