1. Project Clover database Tue Dec 20 2016 21:24:09 CET
  2. Package org.xwiki.crypto.password.internal

File DefaultPrivateKeyPasswordBasedEncryptor.java

 

Coverage histogram

../../../../../img/srcFileCovDistChart7.png
64% of files have more coverage

Code metrics

4
28
11
1
170
122
14
0.5
2.55
11
1.27

Classes

Class Line # Actions
DefaultPrivateKeyPasswordBasedEncryptor 56 28 0% 14 13
0.697674469.8%
 

Contributing tests

This file is covered by 7 tests. .

Source view

1    /*
2    * See the NOTICE file distributed with this work for additional
3    * information regarding copyright ownership.
4    *
5    * This is free software; you can redistribute it and/or modify it
6    * under the terms of the GNU Lesser General Public License as
7    * published by the Free Software Foundation; either version 2.1 of
8    * the License, or (at your option) any later version.
9    *
10    * This software is distributed in the hope that it will be useful,
11    * but WITHOUT ANY WARRANTY; without even the implied warranty of
12    * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13    * Lesser General Public License for more details.
14    *
15    * You should have received a copy of the GNU Lesser General Public
16    * License along with this software; if not, write to the Free
17    * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
18    * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
19    */
20    package org.xwiki.crypto.password.internal;
21   
22    import java.io.IOException;
23    import java.security.GeneralSecurityException;
24    import java.security.SecureRandom;
25   
26    import javax.inject.Inject;
27    import javax.inject.Provider;
28    import javax.inject.Singleton;
29   
30    import org.bouncycastle.asn1.pkcs.EncryptedPrivateKeyInfo;
31    import org.bouncycastle.asn1.x509.AlgorithmIdentifier;
32    import org.xwiki.component.annotation.Component;
33    import org.xwiki.component.manager.ComponentLookupException;
34    import org.xwiki.component.manager.ComponentManager;
35    import org.xwiki.crypto.AsymmetricKeyFactory;
36    import org.xwiki.crypto.params.cipher.asymmetric.PrivateKeyParameters;
37    import org.xwiki.crypto.params.cipher.symmetric.KeyWithIVParameters;
38    import org.xwiki.crypto.params.cipher.symmetric.SymmetricCipherParameters;
39    import org.xwiki.crypto.password.KeyDerivationFunction;
40    import org.xwiki.crypto.password.PasswordBasedCipher;
41    import org.xwiki.crypto.password.PasswordBasedCipherFactory;
42    import org.xwiki.crypto.password.PrivateKeyPasswordBasedEncryptor;
43    import org.xwiki.crypto.password.internal.pbe.AbstractBcPBCipher;
44    import org.xwiki.crypto.password.internal.pbe.factory.AbstractBcPBCipherFactory;
45    import org.xwiki.crypto.password.params.KeyDerivationFunctionParameters;
46    import org.xwiki.crypto.password.params.PBKDF2Parameters;
47   
48    /**
49    * Encrypter / Decrypter of private keys using password based ciphers as defined in PKCS #8.
50    *
51    * @version $Id: b7968d900e85bf6511d73b5a8697c2d15e1a6926 $
52    * @since 5.4RC1
53    */
54    @Component
55    @Singleton
 
56    public class DefaultPrivateKeyPasswordBasedEncryptor implements PrivateKeyPasswordBasedEncryptor
57    {
58    @Inject
59    private ComponentManager manager;
60   
61    @Inject
62    private AsymmetricKeyFactory keyFactory;
63   
64    @Inject
65    private Provider<SecureRandom> randomProvider;
66   
 
67  7 toggle @Override
68    public PrivateKeyParameters decrypt(byte[] password, byte[] encoded)
69    throws GeneralSecurityException, IOException
70    {
71  7 EncryptedPrivateKeyInfo encKeyInfo = EncryptedPrivateKeyInfo.getInstance(encoded);
72  7 return decrypt(password, encKeyInfo.getEncryptionAlgorithm(), encKeyInfo.getEncryptedData());
73    }
74   
 
75  0 toggle @Override
76    public PrivateKeyParameters decrypt(byte[] password, javax.crypto.EncryptedPrivateKeyInfo privateKeyInfo)
77    throws GeneralSecurityException, IOException
78    {
79  0 return decrypt(password, privateKeyInfo.getEncoded());
80    }
81   
 
82  7 toggle private PrivateKeyParameters decrypt(byte[] password, AlgorithmIdentifier algId, byte[] encoded)
83    throws GeneralSecurityException, IOException
84    {
85  7 return this.keyFactory.fromPKCS8(getPBECipher(password, algId).doFinal(encoded));
86    }
87   
 
88  7 toggle private PasswordBasedCipher getPBECipher(byte[] password, AlgorithmIdentifier algId) throws IOException
89    {
90  7 PasswordBasedCipherFactory factory = getPBEFactory(algId.getAlgorithm().getId());
91   
92    // Optimization
93  7 if (factory instanceof AbstractBcPBCipherFactory) {
94  7 return ((AbstractBcPBCipherFactory) factory).getInstance(false, password, algId);
95    }
96   
97  0 return factory.getInstance(false, password, algId.getEncoded());
98    }
99   
 
100  14 toggle private PasswordBasedCipherFactory getPBEFactory(String hint)
101    {
102  14 try {
103  14 return this.manager.getInstance(PasswordBasedCipherFactory.class, hint);
104    } catch (ComponentLookupException e) {
105  0 throw new UnsupportedOperationException("Password based cipher factory not found: " + hint, e);
106    }
107    }
108   
 
109  5 toggle @Override
110    public byte[] encrypt(String algHint, SymmetricCipherParameters password,
111    KeyDerivationFunctionParameters kdfParameters, PrivateKeyParameters privateKey)
112    throws GeneralSecurityException, IOException
113    {
114  5 PasswordBasedCipher cipher = getPBEFactory(algHint).getInstance(true, password, kdfParameters);
115  5 return encrypt(cipher, privateKey);
116    }
117   
 
118  0 toggle @Override
119    public byte[] encrypt(String algHint, SymmetricCipherParameters password, KeyDerivationFunction function,
120    PrivateKeyParameters privateKey) throws GeneralSecurityException, IOException
121    {
122  0 PasswordBasedCipher cipher = getPBEFactory(algHint).getInstance(true, password, function);
123  0 return encrypt(cipher, privateKey);
124    }
125   
 
126  0 toggle @Override
127    public byte[] encrypt(String algHint, byte[] password, byte[] encoded, PrivateKeyParameters privateKey)
128    throws GeneralSecurityException, IOException
129    {
130  0 PasswordBasedCipher cipher = getPBEFactory(algHint).getInstance(true, password, encoded);
131  0 return encrypt(cipher, privateKey);
132    }
133   
 
134  1 toggle @Override
135    public byte[] encrypt(String algHint, byte[] password, KeyDerivationFunctionParameters kdfParameters,
136    PrivateKeyParameters privateKey) throws GeneralSecurityException, IOException
137    {
138  1 PasswordBasedCipherFactory factory = getPBEFactory(algHint);
139  1 PasswordBasedCipher cipher = factory.getInstance(true,
140    new KeyWithIVParameters(password, factory.getIVSize(), this.randomProvider.get()),
141    kdfParameters);
142  1 return encrypt(cipher, privateKey);
143    }
144   
 
145  1 toggle @Override
146    public byte[] encrypt(byte[] password, PrivateKeyParameters privateKey) throws GeneralSecurityException, IOException
147    {
148  1 PasswordBasedCipherFactory factory = getPBEFactory("PBES2-AES-CBC-Pad");
149  1 PasswordBasedCipher cipher = factory.getInstance(true,
150    new KeyWithIVParameters(password, factory.getIVSize(), this.randomProvider.get()),
151    new PBKDF2Parameters(this.randomProvider.get()));
152  1 return encrypt(cipher, privateKey);
153    }
154   
 
155  7 toggle @Override
156    public byte[] encrypt(PasswordBasedCipher cipher, PrivateKeyParameters privateKey)
157    throws IOException, GeneralSecurityException
158    {
159  7 AlgorithmIdentifier algId;
160   
161    // Optimization
162  7 if (cipher instanceof AbstractBcPBCipher) {
163  7 algId = ((AbstractBcPBCipher) cipher).getPBEParameters();
164    } else {
165  0 algId = AlgorithmIdentifier.getInstance(cipher.getEncoded());
166    }
167   
168  7 return new EncryptedPrivateKeyInfo(algId, cipher.doFinal(privateKey.getEncoded())).getEncoded();
169    }
170    }