Problem parsing encapsulated Signed Data

classic Classic list List threaded Threaded
3 messages Options
Reply | Threaded
Open this post in threaded view
|

Problem parsing encapsulated Signed Data

Maria Sigal
This post was updated on .
Hi,
I am encapsulating EnvelopedData in SignedData and then in EnvelopedData.
encrypt->sign->encrypt . However when i decrypt the message and create
CMSSingedData out of decrypted content i get an error:
org.bouncycastle.cms.CMSException: IOException reading content.

        at org.bouncycastle.cms.CMSUtils.readContentInfo(Unknown Source)
        at org.bouncycastle.cms.CMSUtils.readContentInfo(Unknown Source)
        at org.bouncycastle.cms.CMSSignedData.<init>(Unknown Source)
        at SmimeTests.testEncryptSignEncrypt(SmimeTests.java:169)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
       

Caused by: java.io.IOException: DER length more than 4 bytes: 98

        at org.bouncycastle.asn1.ASN1InputStream.readLength(Unknown Source)
        at org.bouncycastle.asn1.ASN1StreamParser.readObject(Unknown Source)
        at org.bouncycastle.asn1.ASN1StreamParser.readVector(Unknown Source)
        at org.bouncycastle.asn1.BERSequenceParser.getLoadedObject(Unknown Source)
*
Here is the code, where i create the EnvelopedData : *

 CMSSignedDataStreamGenerator signedGenerator;
        CMSEnvelopedDataStreamGenerator envelopedGenerator;
        try {
            signedGenerator = getCMSSignedDataStreamGenerator(builder);
            envelopedGenerator =
getCMSEnvelopedDataStreamGenerator(builder);

       
            OutputStream envelopedStream2 =
envelopedGenerator.open(CMSObjectIdentifiers.signedData,out,settings.getEncryptor());
            OutputStream signingStream =
signedGenerator.open(CMSObjectIdentifiers.envelopedData,envelopedStream2,encapsulate);
            OutputStream envelopedStream1 =
envelopedGenerator.open(signingStream,settings.getEncryptor());
            content.writeTo(envelopedStream1);
            envelopedStream1.close();
            signingStream.close();
            envelopedStream2.close();


        }catch (CMSException e){
            throw new IOException(e.toString());

        }catch (MessagingException e) {
            throw new IOException(e.toString());

        }


*Here is my test :*

@Test
  public  void testEncryptSignEncrypt() throws  Exception{


      Properties props = System.getProperties();
      Session session = Session.getDefaultInstance(props, null);
      RecipientId recId = new JceKeyTransRecipientId(cert);
      MimeMessage msg = new MimeMessage(session, new
FileInputStream("EncryptSignEncryptPCKS7"));
      SMIMEEnveloped m = new SMIMEEnveloped(msg);
      ContentInfo contentInfo = m.toASN1Structure();
      EnvelopedData envData =
EnvelopedData.getInstance(contentInfo.getContent());

     System.out.println("The content of enveloped data " +
envData.getEncryptedContentInfo().getContentType());

      assertEquals(CMSObjectIdentifiers.signedData,
envData.getEncryptedContentInfo().getContentType(), "The content of
enveloped data, should be SignedData");

      byte[] cont = decrypt(smimeKey,m,cert);


      CMSSignedData signedData = new CMSSignedData(cont);


      assertEquals(CMSObjectIdentifiers.envelopedData.toString(),
signedData.getSignedContentTypeOID(), "The content of signed data, should be
enveloped data");


      assertEquals(true, verify(signedData), "the message was altered!");

  }

 private static byte[] decrypt(SmimeKey key, CMSEnvelopedData envelopedData,
X509Certificate cert) throws CMSException{

        RecipientId recId = new JceKeyTransRecipientId(cert);
        RecipientInformationStore recipients =
envelopedData.getRecipientInfos();
        RecipientInformation recipient = recipients.get(recId);
        byte[]  cont = recipient.getContent(new
JceKeyTransEnvelopedRecipient(smimeKey.getPrivateKey()).setProvider("BC"));

        return cont;
    }






--
Sent from: http://bouncy-castle.1462172.n4.nabble.com/Bouncy-Castle-Dev-f1462173.html

Reply | Threaded
Open this post in threaded view
|

Re: Problem parsing encapsulated Signed Data

David Hook-3

Not sure... normally an exception like this would suggest the decryption
key being used is incorrect, hence the invalid ASN.1 data.

Regards,

David

On 08/01/18 22:56, Maria Sigal wrote:

> Hi,
> I am encapsulating EnvelopedData in SignedData and then in EnvelopedData.
> encrypt->sign->encrypt . However when i decrypt the message and create
> CMSSingedData out of decrypted content i get an error:
> org.bouncycastle.cms.CMSException: IOException reading content.
>
> at org.bouncycastle.cms.CMSUtils.readContentInfo(Unknown Source)
> at org.bouncycastle.cms.CMSUtils.readContentInfo(Unknown Source)
> at org.bouncycastle.cms.CMSSignedData.<init>(Unknown Source)
> at SmimeTests.testEncryptSignEncrypt(SmimeTests.java:169)
> at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
> at
> sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
> at
> sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
> at java.lang.reflect.Method.invoke(Method.java:498)
> at
> org.junit.platform.commons.util.ReflectionUtils.invokeMethod(ReflectionUtils.java:389)
> at
> org.junit.jupiter.engine.execution.ExecutableInvoker.invoke(ExecutableInvoker.java:115)
> at
> org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$invokeTestMethod$6(TestMethodTestDescriptor.java:167)
> at
> org.junit.jupiter.engine.execution.ThrowableCollector.execute(ThrowableCollector.java:40)
> at
> org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.invokeTestMethod(TestMethodTestDescriptor.java:163)
> at
> org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:110)
> at
> org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:57)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:83)
> at
> org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$null$2(HierarchicalTestExecutor.java:92)
> at java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:184)
> at
> java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:175)
> at java.util.Iterator.forEachRemaining(Iterator.java:116)
> at
> java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)
> at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481)
> at
> java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
> at
> java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:151)
> at
> java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:174)
> at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
> at java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:418)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:92)
> at
> org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$null$2(HierarchicalTestExecutor.java:92)
> at java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:184)
> at
> java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:175)
> at java.util.Iterator.forEachRemaining(Iterator.java:116)
> at
> java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)
> at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481)
> at
> java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
> at
> java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:151)
> at
> java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:174)
> at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
> at java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:418)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:92)
> at
> org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:51)
> at
> org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:43)
> at
> org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:170)
> at
> org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:154)
> at
> org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:90)
> at
> com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:62)
> at
> com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
> at
> com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
> at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)
> Caused by: java.io.IOException: DER length more than 4 bytes: 98
> at org.bouncycastle.asn1.ASN1InputStream.readLength(Unknown Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readObject(Unknown Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readVector(Unknown Source)
> at org.bouncycastle.asn1.BERSequenceParser.getLoadedObject(Unknown Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readVector(Unknown Source)
> at org.bouncycastle.asn1.BERSequenceParser.getLoadedObject(Unknown Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readVector(Unknown Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readTaggedObject(Unknown Source)
> at org.bouncycastle.asn1.BERTaggedObjectParser.getLoadedObject(Unknown
> Source)
> at org.bouncycastle.asn1.ASN1StreamParser.readVector(Unknown Source)
> at org.bouncycastle.asn1.BERSequenceParser.getLoadedObject(Unknown Source)
> at org.bouncycastle.asn1.ASN1InputStream.readObject(Unknown Source)
> ... 55 more
>
> *
> Here is the code, where i create the EnvelopedData : *
>
>  CMSSignedDataStreamGenerator signedGenerator;
>         CMSEnvelopedDataStreamGenerator envelopedGenerator;
>         try {
>             signedGenerator = getCMSSignedDataStreamGenerator(builder);
>             envelopedGenerator =
> getCMSEnvelopedDataStreamGenerator(builder);
>
>             CommandMap commandMap = CommandMap.getDefaultCommandMap();
>
>             if (commandMap instanceof MailcapCommandMap)
>             {
>                
> content.getDataHandler().setCommandMap(addCommands((MailcapCommandMap)commandMap));
>             }
>
>            
>
>
>             OutputStream envelopedStream2 =
> envelopedGenerator.open(CMSObjectIdentifiers.signedData,out,settings.getEncryptor());
>             OutputStream signingStream =
> signedGenerator.open(CMSObjectIdentifiers.envelopedData,envelopedStream2,encapsulate);
>             OutputStream envelopedStream1 =
> envelopedGenerator.open(signingStream,settings.getEncryptor());
>             content.writeTo(envelopedStream1);
>             envelopedStream1.close();
>             signingStream.close();
>             envelopedStream2.close();
>
>
>         }catch (CMSException e){
>             throw new IOException(e.toString());
>
>         }catch (MessagingException e) {
>             throw new IOException(e.toString());
>
>         }
>
>
> *Here is my test :*
>
> @Test
>   public  void testEncryptSignEncrypt() throws  Exception{
>
>
>       Properties props = System.getProperties();
>       Session session = Session.getDefaultInstance(props, null);
>       RecipientId recId = new JceKeyTransRecipientId(cert);
>       MimeMessage msg = new MimeMessage(session, new
> FileInputStream("EncryptSignEncryptPCKS7"));
>       SMIMEEnveloped m = new SMIMEEnveloped(msg);
>       ContentInfo contentInfo = m.toASN1Structure();
>       EnvelopedData envData =
> EnvelopedData.getInstance(contentInfo.getContent());
>
>      System.out.println("The content of enveloped data " +
> envData.getEncryptedContentInfo().getContentType());
>
>       assertEquals(CMSObjectIdentifiers.signedData,
> envData.getEncryptedContentInfo().getContentType(), "The content of
> enveloped data, should be SignedData");
>
>       byte[] cont = decrypt(smimeKey,m,cert);
>
>
>       CMSSignedData signedData = new CMSSignedData(cont);
>
>
>       assertEquals(CMSObjectIdentifiers.envelopedData.toString(),
> signedData.getSignedContentTypeOID(), "The content of signed data, should be
> enveloped data");
>
>
>       assertEquals(true, verify(signedData), "the message was altered!");
>
>   }
>
>  private static byte[] decrypt(SmimeKey key, CMSEnvelopedData envelopedData,
> X509Certificate cert) throws CMSException{
>
>         RecipientId recId = new JceKeyTransRecipientId(cert);
>         RecipientInformationStore recipients =
> envelopedData.getRecipientInfos();
>         RecipientInformation recipient = recipients.get(recId);
>         byte[]  cont = recipient.getContent(new
> JceKeyTransEnvelopedRecipient(smimeKey.getPrivateKey()).setProvider("BC"));
>
>         return cont;
>     }
>
>
>
>
>
>
> --
> Sent from: http://bouncy-castle.1462172.n4.nabble.com/Bouncy-Castle-Dev-f1462173.html
>
>


Reply | Threaded
Open this post in threaded view
|

Re: Problem parsing encapsulated Signed Data

Maria Sigal
it's really weird. I use  the same key that i  use in  sing->encrypt and
everything works fine when i am decrypting  and verifying it.  So probably
something gets messed up when you use more than twice the stream generator

  OutputStream envelopedStream2 =

envelopedGenerator.open(CMSObjectIdentifiers.signedData,out,settings.getEncryptor());                
 OutputStream signingStream =

signedGenerator.open(CMSObjectIdentifiers.envelopedData,envelopedStream2,encapsulate);              
 OutputStream envelopedStream1 =
 envelopedGenerator.open(signingStream,settings.getEncryptor());
 content.writeTo(envelopedStream1);
 envelopedStream1.close();
 signingStream.close();
 envelopedStream2.close();



--
Sent from: http://bouncy-castle.1462172.n4.nabble.com/Bouncy-Castle-Dev-f1462173.html