2017-02-08 2 views
0

BouncyCastle을 사용하여 서명을 확인하고 ".p7m"파일 (원본 내용, 서명자 등)에서 infos를 추출했습니다.timestamptoken validate java bouncycastle

이제 동일한 ".p7m"파일 내에서 TimeStamp의 정보를 확인하고 추출해야합니다.

어떻게 TimeStampToken의 유효성을 검사 할 수 있습니까? Signature에서 잘 작동하는이 코드를 작성했지만 TimeStamp의 유효성을 검사하지는 않습니다. Signature와 TimeStampToken을 모두 검증하기 위해 build() 메소드에 "cert"변수를 전달했습니다. 서명을 위해 괜찮아요,하지만 타임 스탬프를 위해 작동하지 않습니다 :(사전에 내가 잘못? 감사 할

.

import java.io.File; 
import java.io.FileInputStream; 
import java.io.FileOutputStream; 
import java.io.IOException; 
import java.security.Security; 
import java.util.Collection; 
import java.util.Iterator; 

import org.bouncycastle.asn1.ASN1Encodable; 
import org.bouncycastle.asn1.cms.Attribute; 
import org.bouncycastle.asn1.cms.AttributeTable; 
import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers; 
import org.bouncycastle.cert.X509CertificateHolder; 
import org.bouncycastle.cms.CMSException; 
import org.bouncycastle.cms.CMSProcessable; 
import org.bouncycastle.cms.CMSSignedData; 
import org.bouncycastle.cms.CMSSignedDataParser; 
import org.bouncycastle.cms.SignerInformation; 
import org.bouncycastle.cms.SignerInformationStore; 
import org.bouncycastle.cms.jcajce.JcaSimpleSignerInfoVerifierBuilder; 
import org.bouncycastle.operator.jcajce.JcaDigestCalculatorProviderBuilder; 
import org.bouncycastle.tsp.TimeStampToken; 
import org.bouncycastle.util.Store; 

public class Launcher3 { 

    public static void main(String[] args) throws Exception { 

     File myFile=new File("D:\\fdr\\bouncycastle\\New Text Document.txt.p7m"); 
     byte[] bytesArray = readContentIntoByteArray(myFile); 

     FileOutputStream fos = new FileOutputStream("D:\\fdr\\bouncycastle\\New Text Document.txt"); 
     byte[] bytesArrayOriginalFile=getData(bytesArray); 
     fos.write(bytesArrayOriginalFile); 
     fos.close(); 

     verifySign(bytesArray); 

    } 

    static public void verifySign(byte[] signedData) throws Exception { 
      Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider()); 

      CMSSignedDataParser  sp = new CMSSignedDataParser(new JcaDigestCalculatorProviderBuilder().setProvider("BC").build(), signedData); 

      sp.getSignedContent().drain(); 

      Store     certStore = sp.getCertificates(); 
      SignerInformationStore signers = sp.getSignerInfos(); 

      Collection    c = signers.getSigners(); 
      Iterator    it = c.iterator(); 

      while (it.hasNext()) 
      { 
       SignerInformation signer = (SignerInformation)it.next(); 
       Collection   certCollection = certStore.getMatches(signer.getSID()); 
       Iterator  certIt = certCollection.iterator(); 
       X509CertificateHolder cert = (X509CertificateHolder)certIt.next(); 

       System.out.println("info 1: "+cert.getIssuer()); 
       System.out.println("info 2: "+cert.getSubject()); 
       System.out.println("date from: "+cert.getNotBefore()); 
       System.out.println("date to: "+cert.getNotAfter()); 
       System.out.println("Serial n. "+cert.getSerialNumber()); 
       System.out.println("verify returns: " + signer.verify(new JcaSimpleSignerInfoVerifierBuilder().setProvider("BC").build(cert))); 
       // --------------------------------------------------------------------------------------------------------------------^ 
       // LOOK AT HERE: it works! 

       AttributeTable  attrs = signer.getUnsignedAttributes(); 
       Attribute   att = attrs.get(PKCSObjectIdentifiers.id_aa_signatureTimeStampToken); 
       ASN1Encodable  dob = att.getAttrValues().getObjectAt(0); 
       byte[] encodedTsp = dob.toASN1Primitive().getEncoded(); 

       TimeStampToken result = null; 

       if(encodedTsp!=null) { 
        CMSSignedData cms = new CMSSignedData(encodedTsp); 
        result = new TimeStampToken(cms); 

       System.out.println("timestamp: "+result.getTimeStampInfo().getGenTime()); 
       System.out.println("serial n. "+result.getTimeStampInfo().getSerialNumber()); 
       System.out.println("tsa: "+result.getTimeStampInfo().getTsa()); 
       System.out.println("policy: "+result.getTimeStampInfo().getPolicy()); 

       result.validate(new JcaSimpleSignerInfoVerifierBuilder().setProvider("BC").build(cert)); 
       // ------------------------------------------------------------------------------^ 
       // LOOK AT HERE: it doesn't work! 

       } 
      } 
    } 

    static public byte[] getData(final byte[] p7bytes) throws CMSException, IOException { 
     CMSSignedData signedData = new CMSSignedData(p7bytes); 
     CMSProcessable signedContent = signedData.getSignedContent(); 

     return (byte[])signedContent.getContent(); 

     } 

     private static byte[] readContentIntoByteArray(File file) 
     { 
      FileInputStream fileInputStream = null; 
      byte[] bFile = new byte[(int) file.length()]; 
      try 
      { 
      fileInputStream = new FileInputStream(file); 
      fileInputStream.read(bFile); 
      fileInputStream.close(); 
      } 
      catch (Exception e) 
      { 
      e.printStackTrace(); 
      } 
      return bFile; 
     } 

} 
+0

가 예외를 던지는 의미 "가 작동하지 않습니다"무엇 – Egl

+0

죄송합니다, 문제는 내가 잘못된 인증서와 체크이다 오류 : '스레드 "main"의 예외 org.bouncycastle.tsp.TSPValidationExce ption : 인증서 해시가 certID 해시와 일치하지 않습니다. ' 나는 해결했다! – albaserver

답변

0

나 자신에 의해 해결 (나는 너무 행복 해요). ? 나는이 방법으로 timestamptoken의 인증서를 찾을 필요가 :

Store storeTt = result.getCertificates(); 
Collection collTt = storeTt.getMatches(result.getSID()); 
Iterator certIt2 = collTt.iterator(); 
X509CertificateHolder cert2 = (X509CertificateHolder)certIt2.next(); 

System.out.println("timestamp's verify: "+result.isSignatureValid(new JcaSimpleSignerInfoVerifierBuilder().setProvider("BC").build(cert2))); 
result.validate(new JcaSimpleSignerInfoVerifierBuilder().setProvider("BC").build(cert2));