Skip to content

Commit 5af657e

Browse files
committed
added support for id-alg-noSignature
1 parent 0b48ab0 commit 5af657e

File tree

5 files changed

+201
-1
lines changed

5 files changed

+201
-1
lines changed

core/src/main/java/org/bouncycastle/asn1/x509/X509ObjectIdentifiers.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,11 @@ public interface X509ObjectIdentifiers
9595
*/
9696
static final ASN1ObjectIdentifier id_ecdsa_with_shake256 = pkix_algorithms.branch("33");
9797

98+
/**
99+
* id-alg-noSignature OBJECT IDENTIFIER ::= {id-pkix id-alg(6) 2}
100+
*/
101+
ASN1ObjectIdentifier id_alg_noSignature = pkix_algorithms.branch("2");
102+
98103
/** 1.3.6.1.5.5.7.9 */
99104
static final ASN1ObjectIdentifier id_pda = id_pkix.branch("9");
100105

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
package org.bouncycastle.operator;
2+
3+
import java.io.IOException;
4+
import java.io.OutputStream;
5+
6+
import org.bouncycastle.asn1.DERNull;
7+
import org.bouncycastle.asn1.x509.AlgorithmIdentifier;
8+
import org.bouncycastle.asn1.x509.X509ObjectIdentifiers;
9+
10+
/**
11+
* ContentSigner for "Unsigned X.509 Certificates"
12+
*/
13+
public class NoSignatureContentSigner
14+
implements ContentSigner
15+
{
16+
@Override
17+
public AlgorithmIdentifier getAlgorithmIdentifier()
18+
{
19+
return new AlgorithmIdentifier(X509ObjectIdentifiers.id_alg_noSignature, DERNull.INSTANCE);
20+
}
21+
22+
@Override
23+
public OutputStream getOutputStream()
24+
{
25+
return new OutputStream()
26+
{
27+
@Override
28+
public void write(byte[] buf, int off, int len)
29+
throws IOException
30+
{
31+
// do nothing
32+
}
33+
34+
@Override
35+
public void write(int i)
36+
throws IOException
37+
{
38+
// do nothing
39+
}
40+
};
41+
}
42+
43+
@Override
44+
public byte[] getSignature()
45+
{
46+
return new byte[0];
47+
}
48+
}

pkix/src/test/java/org/bouncycastle/cert/test/CertTest.java

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@
7777
import org.bouncycastle.asn1.x509.KeyPurposeId;
7878
import org.bouncycastle.asn1.x509.SubjectAltPublicKeyInfo;
7979
import org.bouncycastle.asn1.x509.SubjectPublicKeyInfo;
80+
import org.bouncycastle.asn1.x509.X509ObjectIdentifiers;
8081
import org.bouncycastle.asn1.x9.ECNamedCurveTable;
8182
import org.bouncycastle.asn1.x9.X9ECParameters;
8283
import org.bouncycastle.asn1.x9.X9ObjectIdentifiers;
@@ -118,6 +119,7 @@
118119
import org.bouncycastle.operator.ContentVerifierProvider;
119120
import org.bouncycastle.operator.DefaultDigestAlgorithmIdentifierFinder;
120121
import org.bouncycastle.operator.DefaultSignatureAlgorithmIdentifierFinder;
122+
import org.bouncycastle.operator.NoSignatureContentSigner;
121123
import org.bouncycastle.operator.bc.BcRSAContentSignerBuilder;
122124
import org.bouncycastle.operator.bc.BcRSAContentVerifierProviderBuilder;
123125
import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder;
@@ -3973,6 +3975,60 @@ public void checkCreationRSAPSS()
39733975
isTrue(null == crt.getSubjectPublicKeyInfo().getAlgorithm().getParameters());
39743976
}
39753977

3978+
public void checkCreationNoSignature()
3979+
throws Exception
3980+
{
3981+
//
3982+
// set up the keys
3983+
//
3984+
KeyPairGenerator kpg = KeyPairGenerator.getInstance("RSASSA-PSS", BC);
3985+
3986+
KeyPair kp = kpg.generateKeyPair();
3987+
3988+
PrivateKey privKey = kp.getPrivate();
3989+
PublicKey pubKey = kp.getPublic();
3990+
3991+
//
3992+
// distinguished name table.
3993+
//
3994+
X500NameBuilder builder = createStdBuilder();
3995+
3996+
//
3997+
// create the certificate - version 3
3998+
//
3999+
ContentSigner sigGen = new NoSignatureContentSigner();
4000+
X509v3CertificateBuilder certGen = new JcaX509v3CertificateBuilder(builder.build(), BigInteger.valueOf(1), new Date(System.currentTimeMillis() - 50000), new Date(System.currentTimeMillis() + 50000), builder.build(), pubKey);
4001+
4002+
X509Certificate cert = new JcaX509CertificateConverter().setProvider(BC).getCertificate(certGen.build(sigGen));
4003+
4004+
cert.checkValidity(new Date());
4005+
4006+
//
4007+
// check fails on verify
4008+
//
4009+
try
4010+
{
4011+
cert.verify(pubKey);
4012+
fail("no exception");
4013+
}
4014+
catch (InvalidKeyException e)
4015+
{
4016+
isEquals(e.getMessage(), "attempt to pass public key to NoSig");
4017+
}
4018+
4019+
// convert and check components.
4020+
ByteArrayInputStream bIn = new ByteArrayInputStream(cert.getEncoded());
4021+
CertificateFactory fact = CertificateFactory.getInstance("X.509", BC);
4022+
4023+
cert = (X509Certificate)fact.generateCertificate(bIn);
4024+
4025+
org.bouncycastle.asn1.x509.Certificate crt = org.bouncycastle.asn1.x509.Certificate.getInstance(cert.getEncoded());
4026+
4027+
isTrue(new AlgorithmIdentifier(X509ObjectIdentifiers.id_alg_noSignature, DERNull.INSTANCE).equals(crt.getTBSCertificate().getSignature()));
4028+
isTrue(new AlgorithmIdentifier(X509ObjectIdentifiers.id_alg_noSignature, DERNull.INSTANCE).equals(crt.getSignatureAlgorithm()));
4029+
isTrue(0 == cert.getSignature().length);
4030+
}
4031+
39764032
/*
39774033
* we generate a self signed certificate across the range of ECDSA algorithms
39784034
*/
@@ -5644,6 +5700,7 @@ public void performTest()
56445700
checkCreationECDSA();
56455701
checkCreationRSA();
56465702
checkCreationRSAPSS();
5703+
checkCreationNoSignature();
56475704

56485705
checkCreationFalcon();
56495706
checkCreationDilithium();
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
package org.bouncycastle.jcajce.provider.asymmetric;
2+
3+
import java.security.InvalidKeyException;
4+
import java.security.InvalidParameterException;
5+
import java.security.PrivateKey;
6+
import java.security.PublicKey;
7+
import java.security.SignatureException;
8+
import java.security.SignatureSpi;
9+
10+
import org.bouncycastle.asn1.x509.X509ObjectIdentifiers;
11+
import org.bouncycastle.jcajce.provider.config.ConfigurableProvider;
12+
import org.bouncycastle.jcajce.provider.util.AsymmetricAlgorithmProvider;
13+
14+
public class NoSig
15+
{
16+
private static final String PREFIX = "org.bouncycastle.jcajce.provider.asymmetric.NoSig$";
17+
18+
public static class SigSpi
19+
extends SignatureSpi
20+
{
21+
@Override
22+
protected void engineInitVerify(PublicKey publicKey)
23+
throws InvalidKeyException
24+
{
25+
throw new InvalidKeyException("attempt to pass public key to NoSig");
26+
}
27+
28+
@Override
29+
protected void engineInitSign(PrivateKey privateKey)
30+
throws InvalidKeyException
31+
{
32+
throw new InvalidKeyException("attempt to pass private key to NoSig");
33+
}
34+
35+
@Override
36+
protected void engineUpdate(byte b)
37+
throws SignatureException
38+
{
39+
40+
}
41+
42+
@Override
43+
protected void engineUpdate(byte[] bytes, int i, int i1)
44+
throws SignatureException
45+
{
46+
47+
}
48+
49+
@Override
50+
protected byte[] engineSign()
51+
throws SignatureException
52+
{
53+
return new byte[0];
54+
}
55+
56+
@Override
57+
protected boolean engineVerify(byte[] bytes)
58+
throws SignatureException
59+
{
60+
return false;
61+
}
62+
63+
@Override
64+
protected void engineSetParameter(String s, Object o)
65+
throws InvalidParameterException
66+
{
67+
68+
}
69+
70+
@Override
71+
protected Object engineGetParameter(String s)
72+
throws InvalidParameterException
73+
{
74+
return null;
75+
}
76+
}
77+
78+
public static class Mappings
79+
extends AsymmetricAlgorithmProvider
80+
{
81+
public Mappings()
82+
{
83+
}
84+
85+
public void configure(ConfigurableProvider provider)
86+
{
87+
provider.addAlgorithm("Signature." + X509ObjectIdentifiers.id_alg_noSignature, PREFIX + "SigSpi");
88+
}
89+
}
90+
}

prov/src/main/java/org/bouncycastle/jce/provider/BouncyCastleProvider.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ public final class BouncyCastleProvider extends Provider
123123
// later ones configure it.
124124
private static final String[] ASYMMETRIC_GENERIC =
125125
{
126-
"X509", "IES", "COMPOSITE", "EXTERNAL", "CompositeSignatures"
126+
"X509", "IES", "COMPOSITE", "EXTERNAL", "CompositeSignatures", "NoSig"
127127
};
128128

129129
private static final String[] ASYMMETRIC_CIPHERS =

0 commit comments

Comments
 (0)