Skip to content

Commit 685f920

Browse files
committed
Added provider support for composite public key components.
Added default provider key add method to composite private and public keys.
1 parent 5795691 commit 685f920

File tree

5 files changed

+244
-104
lines changed

5 files changed

+244
-104
lines changed

prov/src/main/java/org/bouncycastle/jcajce/CompositePrivateKey.java

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,11 @@ private Builder(AlgorithmIdentifier algorithmIdentifier)
4444
this.algorithmIdentifier = algorithmIdentifier;
4545
}
4646

47+
public Builder addPrivateKey(PrivateKey key)
48+
{
49+
return addPrivateKey(key, (Provider)null);
50+
}
51+
4752
public Builder addPrivateKey(PrivateKey key, String providerName)
4853
{
4954
return addPrivateKey(key, Security.getProvider(providerName));
@@ -64,6 +69,11 @@ public Builder addPrivateKey(PrivateKey key, Provider provider)
6469

6570
public CompositePrivateKey build()
6671
{
72+
if (providers[0] == null && providers[1] == null)
73+
{
74+
return new CompositePrivateKey(algorithmIdentifier, keys, null);
75+
}
76+
6777
return new CompositePrivateKey(algorithmIdentifier, keys, providers);
6878
}
6979
}
@@ -144,14 +154,26 @@ private CompositePrivateKey(AlgorithmIdentifier algorithmIdentifier, PrivateKey[
144154
}
145155

146156
List<PrivateKey> keyList = new ArrayList<PrivateKey>(keys.length);
147-
List<Provider> providerList = new ArrayList<Provider>(providers.length);
148-
for (int i = 0; i < keys.length; i++)
157+
if (providers == null)
149158
{
150-
providerList.add(providers[i]);
151-
keyList.add(processKey(keys[i]));
159+
for (int i = 0; i < keys.length; i++)
160+
{
161+
keyList.add(processKey(keys[i]));
162+
}
163+
this.providers = null;
164+
}
165+
else
166+
{
167+
List<Provider> providerList = new ArrayList<Provider>(providers.length);
168+
for (int i = 0; i < keys.length; i++)
169+
{
170+
providerList.add(providers[i]);
171+
keyList.add(processKey(keys[i]));
172+
}
173+
this.providers = Collections.unmodifiableList(providerList);
152174
}
153175
this.keys = Collections.unmodifiableList(keyList);
154-
this.providers = Collections.unmodifiableList(providerList);
176+
155177
}
156178

157179
/**

prov/src/main/java/org/bouncycastle/jcajce/CompositePublicKey.java

Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
package org.bouncycastle.jcajce;
22

33
import java.io.IOException;
4+
import java.security.Provider;
45
import java.security.PublicKey;
6+
import java.security.Security;
57
import java.util.ArrayList;
68
import java.util.Collections;
79
import java.util.List;
@@ -26,7 +28,60 @@
2628
public class CompositePublicKey
2729
implements PublicKey
2830
{
31+
public static class Builder
32+
{
33+
private final AlgorithmIdentifier algorithmIdentifier;
34+
private final PublicKey[] keys = new PublicKey[2];
35+
private final Provider[] providers = new Provider[2];
36+
37+
private int count = 0;
38+
39+
private Builder(AlgorithmIdentifier algorithmIdentifier)
40+
{
41+
this.algorithmIdentifier = algorithmIdentifier;
42+
}
43+
44+
public Builder addPublicKey(PublicKey key)
45+
{
46+
return addPublicKey(key, (Provider)null);
47+
}
48+
49+
public Builder addPublicKey(PublicKey key, String providerName)
50+
{
51+
return addPublicKey(key, Security.getProvider(providerName));
52+
}
53+
54+
public Builder addPublicKey(PublicKey key, Provider provider)
55+
{
56+
if (count == keys.length)
57+
{
58+
throw new IllegalStateException("only " + keys.length + " allowed in composite");
59+
}
60+
61+
keys[count] = key;
62+
providers[count++] = provider;
63+
64+
return this;
65+
}
66+
67+
public CompositePublicKey build()
68+
{
69+
if (providers[0] == null && providers[1] == null)
70+
{
71+
return new CompositePublicKey(algorithmIdentifier, keys, null);
72+
}
73+
74+
return new CompositePublicKey(algorithmIdentifier, keys, providers);
75+
}
76+
}
77+
78+
public static Builder builder(ASN1ObjectIdentifier compAlgOid)
79+
{
80+
return new Builder(new AlgorithmIdentifier(compAlgOid));
81+
}
82+
2983
private final List<PublicKey> keys;
84+
private final List<Provider> providers;
3085

3186
private final AlgorithmIdentifier algorithmIdentifier;
3287

@@ -69,6 +124,7 @@ public CompositePublicKey(AlgorithmIdentifier algorithmIdentifier, PublicKey...
69124
keyList.add(keys[i]);
70125
}
71126
this.keys = Collections.unmodifiableList(keyList);
127+
this.providers = null;
72128
}
73129

74130
/**
@@ -102,6 +158,38 @@ public CompositePublicKey(SubjectPublicKeyInfo keyInfo)
102158

103159
this.keys = publicKeyFromFactory.getPublicKeys();
104160
this.algorithmIdentifier = publicKeyFromFactory.getAlgorithmIdentifier();
161+
this.providers = null;
162+
}
163+
164+
private CompositePublicKey(AlgorithmIdentifier algorithmIdentifier, PublicKey[] keys, Provider[] providers)
165+
{
166+
this.algorithmIdentifier = algorithmIdentifier;
167+
168+
if (keys.length != 2)
169+
{
170+
throw new IllegalArgumentException("two keys required for composite private key");
171+
}
172+
173+
List<PublicKey> keyList = new ArrayList<PublicKey>(keys.length);
174+
if (providers == null)
175+
{
176+
for (int i = 0; i < keys.length; i++)
177+
{
178+
keyList.add(keys[i]);
179+
}
180+
this.providers = null;
181+
}
182+
else
183+
{
184+
List<Provider> providerList = new ArrayList<Provider>(providers.length);
185+
for (int i = 0; i < keys.length; i++)
186+
{
187+
providerList.add(providers[i]);
188+
keyList.add(keys[i]);
189+
}
190+
this.providers = Collections.unmodifiableList(providerList);
191+
}
192+
this.keys = Collections.unmodifiableList(keyList);
105193
}
106194

107195
/**
@@ -114,6 +202,16 @@ public List<PublicKey> getPublicKeys()
114202
return keys;
115203
}
116204

205+
/**
206+
* Return a list of the providers supporting the component private keys.
207+
*
208+
* @return an immutable list of Provider objects.
209+
*/
210+
public List<Provider> getProviders()
211+
{
212+
return providers;
213+
}
214+
117215
public String getAlgorithm()
118216
{
119217
return CompositeIndex.getAlgorithmName(this.algorithmIdentifier.getAlgorithm());

prov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/compositesignatures/SignatureSpi.java

Lines changed: 26 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@
77
import java.security.InvalidKeyException;
88
import java.security.InvalidParameterException;
99
import java.security.Key;
10+
import java.security.NoSuchAlgorithmException;
11+
import java.security.NoSuchProviderException;
1012
import java.security.PrivateKey;
1113
import java.security.Provider;
1214
import java.security.PublicKey;
@@ -134,7 +136,7 @@ protected void engineInitVerify(PublicKey publicKey)
134136
{
135137
throw new InvalidKeyException("Provided composite public key cannot be used with the composite signature algorithm.");
136138
}
137-
createComponentSignatures(compositePublicKey.getPublicKeys(), null);
139+
createComponentSignatures(compositePublicKey.getPublicKeys(), compositePublicKey.getProviders());
138140

139141
sigInitVerify();
140142
}
@@ -178,21 +180,22 @@ private void createComponentSignatures(List keys, List<Provider> providers)
178180
{
179181
for (int i = 0; i != componentSignatures.length; i++)
180182
{
181-
if (keys.get(i) instanceof BCKey)
182-
{
183-
componentSignatures[i] = Signature.getInstance(algs[i], "BC");
184-
}
185-
else
186-
{
187-
componentSignatures[i] = Signature.getInstance(algs[i]);
188-
}
183+
componentSignatures[i] = getDefaultSignature(algs[i], keys.get(i));
189184
}
190185
}
191186
else
192187
{
193188
for (int i = 0; i != componentSignatures.length; i++)
194189
{
195-
componentSignatures[i] = Signature.getInstance(algs[i], providers.get(i));
190+
Provider prov = providers.get(i);
191+
if (prov == null)
192+
{
193+
componentSignatures[i] = getDefaultSignature(algs[i], keys.get(i));
194+
}
195+
else
196+
{
197+
componentSignatures[i] = Signature.getInstance(algs[i], providers.get(i));
198+
}
196199
}
197200
}
198201
}
@@ -202,6 +205,19 @@ private void createComponentSignatures(List keys, List<Provider> providers)
202205
}
203206
}
204207

208+
private Signature getDefaultSignature(String alg, Object key)
209+
throws NoSuchAlgorithmException, NoSuchProviderException
210+
{
211+
if (key instanceof BCKey)
212+
{
213+
return helper.createSignature(alg);
214+
}
215+
else
216+
{
217+
return Signature.getInstance(alg);
218+
}
219+
}
220+
205221
private void sigInitSign()
206222
throws InvalidKeyException
207223
{
@@ -225,7 +241,6 @@ private void baseSigInit()
225241
{
226242
componentSignatures[1].setParameter(pssSpec);
227243
}
228-
229244
}
230245
catch (InvalidAlgorithmParameterException e)
231246
{

0 commit comments

Comments
 (0)