Remove use of Objects.isNull/nonNull
[netconf.git] / netconf / tools / netconf-testtool / src / main / java / org / opendaylight / netconf / test / tool / VirtualKeyPairProvider.java
1 /*
2  * Copyright © 2019 FRINX s.r.o. All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.netconf.test.tool;
9
10 import java.security.GeneralSecurityException;
11 import java.security.KeyPair;
12 import java.security.KeyPairGenerator;
13 import java.security.spec.AlgorithmParameterSpec;
14 import java.util.Collections;
15 import org.apache.sshd.common.cipher.ECCurves;
16 import org.apache.sshd.common.config.keys.KeyUtils;
17 import org.apache.sshd.common.keyprovider.KeyPairProvider;
18 import org.apache.sshd.common.session.SessionContext;
19 import org.apache.sshd.common.util.security.SecurityUtils;
20 import org.slf4j.Logger;
21 import org.slf4j.LoggerFactory;
22
23 /**
24  * Key provider that allows to create exactly one key-pair in memory (key-pair is not persisted in memory).
25  * If the key-pair has already been generated, the existing one is used.
26  */
27 public class VirtualKeyPairProvider implements KeyPairProvider {
28     private static final Logger LOG = LoggerFactory.getLogger(VirtualKeyPairProvider.class);
29
30     private KeyPair generatedKeyPair;
31     private String algorithm = KeyUtils.RSA_ALGORITHM;
32     private AlgorithmParameterSpec keySpecification;
33     private Integer keySize;
34
35     /**
36      * Creation of the key-provider with default settings - RSA algorithm with key length of 2048.
37      *
38      * @see VirtualKeyPairProvider#VirtualKeyPairProvider(String, AlgorithmParameterSpec, Integer)
39      */
40     VirtualKeyPairProvider() {
41     }
42
43     /**
44      * Creation of the key-provider with explicitly defined algorithmic settings.
45      *
46      * @param algorithm        Algorithm that is used for generation of a new key-pair. Currently supported algorithms:
47      *                         {@link KeyUtils#RSA_ALGORITHM}, {@link KeyUtils#DSS_ALGORITHM},
48      *                         {@link KeyUtils#EC_ALGORITHM}.
49      * @param keySpecification Algorithm-specific settings.
50      * @param keySize          To be generated key length (must be adjusted against selected algorithm).
51      */
52     @SuppressWarnings("WeakerAccess")
53     VirtualKeyPairProvider(final String algorithm,
54                            final AlgorithmParameterSpec keySpecification,
55                            final Integer keySize) {
56         this.algorithm = algorithm;
57         this.keySpecification = keySpecification;
58         this.keySize = keySize;
59     }
60
61     @Override
62     public synchronized Iterable<KeyPair> loadKeys(final SessionContext session) {
63         if (generatedKeyPair == null) {
64             try {
65                 generatedKeyPair = generateKeyPair();
66             } catch (GeneralSecurityException e) {
67                 LOG.error("Cannot generate key with algorithm '{}', key specification '{}', and key size '{}'.",
68                         algorithm, keySpecification, keySize, e);
69                 throw new IllegalArgumentException("An error occurred during generation of a new ke pair.", e);
70             }
71         }
72         return Collections.singleton(generatedKeyPair);
73     }
74
75     /**
76      * Generating of the new key-pair using specified parameters - algorithm, key length, and key specification.
77      *
78      * @return Generated key-pair.
79      * @throws GeneralSecurityException If the generation process fails because of the wrong input parameters.
80      */
81     private KeyPair generateKeyPair() throws GeneralSecurityException {
82         final KeyPairGenerator generator = SecurityUtils.getKeyPairGenerator(algorithm);
83         if (keySpecification != null) {
84             generator.initialize(keySpecification);
85         } else if (keySize != null) {
86             generator.initialize(keySize);
87         } else if (KeyUtils.EC_ALGORITHM.equals(algorithm)) {
88             int numCurves = ECCurves.SORTED_KEY_SIZE.size();
89             ECCurves curve = ECCurves.SORTED_KEY_SIZE.get(numCurves - 1);
90             generator.initialize(curve.getParameters());
91         }
92         return generator.generateKeyPair();
93     }
94 }