验证使用openssl生成的分离的xml签名

时间:2014-03-18 13:24:50

标签: java

我目前已经分配了验证使用openssl生成的数字签名的任务。我收到的文件基本上是两个文件,一个是xml数据,另一个是xml数据的相应签名,用于签名数据的密钥是RSA,算法为SHA1,使用的openssl命令是:openssl smime -sign -binary -in {datafile} -out {signaturefile} -outform der -inkey {privatekey} -signer {publickey} 其中{datafile} =包含要签名的数据的CSV或XML格式的输入文件{signaturefile} =仅包含PKCS#7格式的数字签名的输出文件,与数据文件相同的文件名但扩展名为.sig { privatekey} =用于签名的密钥的私钥部分{publickey} =用于签名的密钥的公钥部分,我编写了一个类来验证这些文件但结果总是返回false意味着验证失败了。下面是我写的代码:有人可以帮助我如何使用java验证openssl分离签名?

public PublicKey pubTest(String path) throws Exception
 {
     FileInputStream fin = new FileInputStream(path);
     CertificateFactory f = CertificateFactory.getInstance("X.509");
     X509Certificate certificate = (X509Certificate)f.generateCertificate(fin);
     PublicKey pk = certificate.getPublicKey();
     System.out.println(pk);
     return pk;
 }
 public byte[] signature(String sigPath) throws Exception
 {
     FileInputStream sigfis = new FileInputStream(sigPath);
     byte[] sigToVerify = new byte[sigfis.available()]; 
     sigfis.read(sigToVerify);
     sigfis.close();
     System.out.println(sigToVerify.length);

     return sigToVerify ;
 }

 public boolean verification(PublicKey pubKey , String dataPath , byte[] sigToVerify ) throws Exception, NoSuchProviderException ,SignatureException
{

    Signature sig = Signature.getInstance("SHA1withRSA");
    sig.initVerify(pubKey);
    FileInputStream datafis = new FileInputStream(dataPath);
    BufferedInputStream bufin = new BufferedInputStream(datafis);
    byte[] buffer = new byte[1024];
    int len;
    while (bufin.available() != 0)
    {
        len = bufin.read(buffer);
      sig.update(buffer, 0, len);
    }
    System.out.println(buffer.length);
    bufin.close();
    boolean verifies = sig.verify(sigToVerify);
    System.out.println("signature verifies: " + verifies);
    return verifies ;
}

1 个答案:

答案 0 :(得分:0)

现在很晚,但如果有其他人遇到它:

默认情况下,

openssl smime -sign会生成"间接"分离签名,即不包含encapContentInfo中的数据但使用signedAttrs的签名。见https://www.ietf.org/rfc/rfc3369.txt 5.3至5.6;您需要将数据的哈希与signedAttrs中的message-digest属性进行比较,然后针对signedAttrs验证签名(将IMPLICIT标记恢复为基本)。

标准Java加密不(目前?)执行CMS / PKCS#7但BouncyCastle确实如果这是一个选项。考虑Correct way to sign and verify signature using bouncycastle