使用Java中的BouncyCastle从PKCS7 PEM格式的证书创建X509Certificate



我有一个PEM格式的PKCS7证书链。基本上,我想使用BouncyCastle库在Java中执行以下openssl命令。

openssl pkcs7 -in client-certificate_pkcs7.pem -out client-certificate_chain.pem

我关注的是BouncyCastle提供的pdf(https://www.bouncycastle.org/fips-java/BCFipsIn100.pdf),但找不到任何能满足我需要的东西。

我发现CMSSignedData用于BouncyCastle中与pkcs7相关的操作,所以我尝试使用它,但我遇到了一个错误,我认为这是因为我使用了原始字符串。

String pkcs7Pem = "-----BEGIN PKCS7-----nMIIR...WTEAn-----END PKCS7-----n";
CMSSignedData data = new CMSSignedData(pkcs7Pem.getBytes());
Store certStore = data.getCertificates();
SignerInformationStore signerInfos = data.getSignerInfos();
Collection<SignerInformation> signers = signerInfos.getSigners();
List<X509Certificate> x509Certificates = new ArrayList<>();
for (SignerInformation signer : signers) {
Collection<X509CertificateHolder> matches = certStore.getMatches(signer.getSID());
for (X509CertificateHolder holder : matches) {
x509Certificates.add(new JcaX509CertificateConverter().setProvider("BC").getCertificate(holder));
}
}

这是我在new CMSSignedData(pkcs7Pem.getBytes());上得到的错误

org.bouncycastle.cms.CMSException: IOException reading content.

我也尝试过使用PEMParser,但下面的parser.readObject()返回null。

String pkcs7Pem = "-----BEGIN PKCS7-----nMIIR...WTEAn-----END PKCS7-----n";
PEMParser parser = new PEMParser(new StringReader(pkcs7Pem));
parser.readObject();

任何帮助都将不胜感激!

openssl pkcs7 -in client-certificate_pkcs7.pem -out client-certificate_chain.pem

该命令只将其输入(如果是PKCS7 PEM(复制到其输出,而不做任何更改。这没有用,也不需要BouncyCastle在Java中执行同样的操作。我怀疑你的意思是

openssl pkcs7 -print_certs -in (pkcs7) -out (chain)

其提取单独证书作为单独(PEM(对象的序列。

我发现CMSSignedData用于BouncyCastle 中的pkcs7相关操作

只有一些——有很多的PKCS7/CMS格式和操作可以完成,还有很多不同的BC类可以完成。但是,用于承载证书链的PKCS7/CMS格式(通常标记为p7b或p7c(是SignedData类型,由BouncyCastleCMSSignedData类实现。

我也尝试过使用PEMParser,但下面的parser.readObject((返回null。

如果你给它有效的PEM输入,而不是你发布的损坏版本,它就不应该。对我来说,如果我给它一个包含p7b/c证书链的有效PEM PKCS7,我会得到一个ContentInfo,然后可以如下解码(为了方便,我使用文件I/O,但任何JavaReaderWriter都可以工作(:

static void SO70048115PKCS7Certs (String[] args) throws Exception {
PEMParser p = new PEMParser(new FileReader(args[0])); 
CMSSignedData sd = new CMSSignedData( (ContentInfo)p.readObject() );
p.close();
JcaPEMWriter w = new JcaPEMWriter(new FileWriter(args[1])); 
for( X509CertificateHolder ch : sd.getCertificates().getMatches(null) ){
// optionally put subject,issuer as 'comments' like OpenSSL does
w.writeObject( new PemObject("CERTIFICATE",ch.getEncoded()) );
}
w.close();
}

请注意,根据惯例,p7b/c不包含任何签名(在PKCS7/CMS术语中,SignerInfo(,因此您发布的代码——旨在查找与签名相关的证书——是不合适的,也不起作用。您只需要使用证书,而不需要任何SignerInfo。

最新更新