aboutsummaryrefslogtreecommitdiffstats
path: root/libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java
diff options
context:
space:
mode:
Diffstat (limited to 'libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java')
-rw-r--r--libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java144
1 files changed, 144 insertions, 0 deletions
diff --git a/libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java b/libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java
new file mode 100644
index 000000000..3b975e4fa
--- /dev/null
+++ b/libraries/spongycastle/pkix/src/main/java/org/spongycastle/operator/bc/BcContentVerifierProviderBuilder.java
@@ -0,0 +1,144 @@
+package org.spongycastle.operator.bc;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+import org.spongycastle.asn1.x509.AlgorithmIdentifier;
+import org.spongycastle.asn1.x509.SubjectPublicKeyInfo;
+import org.spongycastle.cert.X509CertificateHolder;
+import org.spongycastle.crypto.Signer;
+import org.spongycastle.crypto.params.AsymmetricKeyParameter;
+import org.spongycastle.operator.ContentVerifier;
+import org.spongycastle.operator.ContentVerifierProvider;
+import org.spongycastle.operator.OperatorCreationException;
+
+public abstract class BcContentVerifierProviderBuilder
+{
+ protected BcDigestProvider digestProvider;
+
+ public BcContentVerifierProviderBuilder()
+ {
+ this.digestProvider = BcDefaultDigestProvider.INSTANCE;
+ }
+
+ public ContentVerifierProvider build(final X509CertificateHolder certHolder)
+ throws OperatorCreationException
+ {
+ return new ContentVerifierProvider()
+ {
+ public boolean hasAssociatedCertificate()
+ {
+ return true;
+ }
+
+ public X509CertificateHolder getAssociatedCertificate()
+ {
+ return certHolder;
+ }
+
+ public ContentVerifier get(AlgorithmIdentifier algorithm)
+ throws OperatorCreationException
+ {
+ try
+ {
+ AsymmetricKeyParameter publicKey = extractKeyParameters(certHolder.getSubjectPublicKeyInfo());
+ BcSignerOutputStream stream = createSignatureStream(algorithm, publicKey);
+
+ return new SigVerifier(algorithm, stream);
+ }
+ catch (IOException e)
+ {
+ throw new OperatorCreationException("exception on setup: " + e, e);
+ }
+ }
+ };
+ }
+
+ public ContentVerifierProvider build(final AsymmetricKeyParameter publicKey)
+ throws OperatorCreationException
+ {
+ return new ContentVerifierProvider()
+ {
+ public boolean hasAssociatedCertificate()
+ {
+ return false;
+ }
+
+ public X509CertificateHolder getAssociatedCertificate()
+ {
+ return null;
+ }
+
+ public ContentVerifier get(AlgorithmIdentifier algorithm)
+ throws OperatorCreationException
+ {
+ BcSignerOutputStream stream = createSignatureStream(algorithm, publicKey);
+
+ return new SigVerifier(algorithm, stream);
+ }
+ };
+ }
+
+ private BcSignerOutputStream createSignatureStream(AlgorithmIdentifier algorithm, AsymmetricKeyParameter publicKey)
+ throws OperatorCreationException
+ {
+ Signer sig = createSigner(algorithm);
+
+ sig.init(false, publicKey);
+
+ return new BcSignerOutputStream(sig);
+ }
+
+ /**
+ * Extract an AsymmetricKeyParameter from the passed in SubjectPublicKeyInfo structure.
+ *
+ * @param publicKeyInfo a publicKeyInfo structure describing the public key required.
+ * @return an AsymmetricKeyParameter object containing the appropriate public key.
+ * @throws IOException if the publicKeyInfo data cannot be parsed,
+ */
+ protected abstract AsymmetricKeyParameter extractKeyParameters(SubjectPublicKeyInfo publicKeyInfo)
+ throws IOException;
+
+ /**
+ * Create the correct signer for the algorithm identifier sigAlgId.
+ *
+ * @param sigAlgId the algorithm details for the signature we want to verify.
+ * @return a Signer object.
+ * @throws OperatorCreationException if the Signer cannot be constructed.
+ */
+ protected abstract Signer createSigner(AlgorithmIdentifier sigAlgId)
+ throws OperatorCreationException;
+
+ private class SigVerifier
+ implements ContentVerifier
+ {
+ private BcSignerOutputStream stream;
+ private AlgorithmIdentifier algorithm;
+
+ SigVerifier(AlgorithmIdentifier algorithm, BcSignerOutputStream stream)
+ {
+ this.algorithm = algorithm;
+ this.stream = stream;
+ }
+
+ public AlgorithmIdentifier getAlgorithmIdentifier()
+ {
+ return algorithm;
+ }
+
+ public OutputStream getOutputStream()
+ {
+ if (stream == null)
+ {
+ throw new IllegalStateException("verifier not initialised");
+ }
+
+ return stream;
+ }
+
+ public boolean verify(byte[] expected)
+ {
+ return stream.verify(expected);
+ }
+ }
+} \ No newline at end of file