I'm working on XAdES implementation for Java, as such I require cryptographic implementation to be able to verify certificates in the past.
Unfortunately I have problems verifying revoked certificates. Situation looks like this:
(time)
↑
| ← in 1d: CA and user certificate notAfter date
|
| ← *now*: user certificate validation using time from time stamp (12h ago)
|
| ← 1h ago: CRL publishing
|
| ← 6h ago: user certificate revocation (reason: unknown)
|
| ← 12h ago: signature creation and time stamping
|
| ← 1 day ago:
| CA notBefore Date
| user notBefore Date
The Sun cryptographic provider (X509CRLSelector) can't use CRLs from "future", so validation using CRL published 1h ago when verification date is 12h in past fails outright. This behaviour is completely wrong for my use case as the Polish law requires a 1h grace period between signature time stamping and CRL publication before the document can be fully validated.
When using Bouncy Castle cryptographic provider, the X509CRLSelector problem is fixed, but when I try to validate the revoked certificate I get attached stack trace.
Do I understand certificate validation with revocation wrong (and the BC failure is correct behaviour) or is this CertPathBuilder behaviour wrong?
xades4j.providers.CannotBuildCertificationPathException: Certification path could not be validated.
at xades4j.providers.impl.PKIXCertificateValidationProvider.validateWithParams(PKIXCertificateValidationProvider.java:272)
at xades4j.providers.impl.PKIXCertificateValidationProvider.validate(PKIXCertificateValidationProvider.java:235)
at xades4j.verification.XadesVerifierImpl.verify(XadesVerifierImpl.java:175)
at xades4j.verification.AgedTimeStampTest.verifySignature(AgedTimeStampTest.java:339)
at xades4j.verification.AgedTimeStampTest.testT_3v(AgedTimeStampTest.java:287)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:31)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:73)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:46)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:180)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:41)
at org.junit.runners.ParentRunner$1.evaluate(ParentRunner.java:173)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:31)
at org.junit.runners.ParentRunner.run(ParentRunner.java:220)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
Caused by: java.security.cert.CertPathBuilderException: Certification path could not be validated.
at org.bouncycastle.jce.provider.PKIXCertPathBuilderSpi.engineBuild(PKIXCertPathBuilderSpi.java:112)
at java.security.cert.CertPathBuilder.build(CertPathBuilder.java:238)
at xades4j.providers.impl.PKIXCertificateValidationProvider.validateWithParams(PKIXCertificateValidationProvider.java:268)
... 28 more
Caused by: org.bouncycastle.jce.exception.ExtCertPathValidatorException: Certificate revocation after Thu Oct 18 08:46:09 CEST 2012, reason: unspecified
at org.bouncycastle.jce.provider.RFC3280CertPathUtilities.processCertA(RFC3280CertPathUtilities.java:1516)
at org.bouncycastle.jce.provider.PKIXCertPathValidatorSpi.engineValidate(PKIXCertPathValidatorSpi.java:274)
at java.security.cert.CertPathValidator.validate(CertPathValidator.java:250)
at org.bouncycastle.jce.provider.PKIXCertPathBuilderSpi.build(PKIXCertPathBuilderSpi.java:195)
at org.bouncycastle.jce.provider.PKIXCertPathBuilderSpi.engineBuild(PKIXCertPathBuilderSpi.java:105)
... 30 more
Caused by: org.bouncycastle.jce.provider.AnnotatedException: Certificate revocation after Thu Oct 18 08:46:09 CEST 2012, reason: unspecified
at org.bouncycastle.jce.provider.RFC3280CertPathUtilities.checkCRLs(RFC3280CertPathUtilities.java:2013)
at org.bouncycastle.jce.provider.RFC3280CertPathUtilities.processCertA(RFC3280CertPathUtilities.java:1506)
... 34 more
The validation time for this stacktrace was Thu Oct 18 02:46:07 CEST 2012