SecretKeyStore.java

  1. /*
  2.  * GovWay - A customizable API Gateway
  3.  * https://govway.org
  4.  *
  5.  * Copyright (c) 2005-2025 Link.it srl (https://link.it).
  6.  *
  7.  * This program is free software: you can redistribute it and/or modify
  8.  * it under the terms of the GNU General Public License version 3, as published by
  9.  * the Free Software Foundation.
  10.  *
  11.  * This program is distributed in the hope that it will be useful,
  12.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.  * GNU General Public License for more details.
  15.  *
  16.  * You should have received a copy of the GNU General Public License
  17.  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  18.  *
  19.  */

  20. package org.openspcoop2.security.keystore;

  21. import java.io.Serializable;

  22. import javax.crypto.SecretKey;

  23. import org.openspcoop2.security.SecurityException;
  24. import org.openspcoop2.utils.certificate.SymmetricKeyUtils;
  25. import org.openspcoop2.utils.certificate.byok.BYOKCostanti;
  26. import org.openspcoop2.utils.certificate.byok.BYOKRequestParams;
  27. import org.openspcoop2.utils.security.CipherInfo;
  28. import org.openspcoop2.utils.security.EncryptOpenSSLPass;
  29. import org.openspcoop2.utils.security.EncryptOpenSSLPassPBKDF2;
  30. import org.openspcoop2.utils.security.OpenSSLEncryptionMode;

  31. /**
  32.  * SecretKeyStore
  33.  *
  34.  * @author Andrea Poli (apoli@link.it)
  35.  * @author $Author$
  36.  * @version $Rev$, $Date$
  37.  */
  38. public class SecretKeyStore implements Serializable {

  39.     /**
  40.      *
  41.      */
  42.     private static final long serialVersionUID = 1L;
  43.    
  44.     private String secretKeyPath;
  45.    
  46.     private byte[] secretKeyContent;
  47.     private transient SecretKey secretKey;
  48.    
  49.     private String algorithm;
  50.    
  51.     private byte[] iv;
  52.     private byte[] salt;
  53.    
  54.     @Override
  55.     public String toString() {
  56.         StringBuilder bf = new StringBuilder();
  57.         bf.append("SecretKeyStore (public:").append(this.secretKeyPath).append(")");
  58.         return bf.toString();
  59.     }
  60.    
  61.     public SecretKeyStore(String secretKeyPath, String algorithm) throws SecurityException{
  62.         this(secretKeyPath, algorithm, null);
  63.     }
  64.     public SecretKeyStore(String secretKeyPath, String algorithm, BYOKRequestParams requestParams) throws SecurityException{
  65.    
  66.         this.secretKeyPath = secretKeyPath;
  67.                
  68.         this.algorithm = algorithm==null ? SymmetricKeyUtils.ALGO_AES : algorithm;
  69.        
  70.         this.secretKeyContent = StoreUtils.readContent("SecretKey", this.secretKeyPath);
  71.        
  72.         this.secretKeyContent = StoreUtils.unwrapBYOK(this.secretKeyContent, requestParams);
  73.            
  74.     }
  75.    
  76.     public SecretKeyStore(byte[] secretKey, String algorithm) throws SecurityException{
  77.         this(secretKey, algorithm, null);
  78.     }
  79.     public SecretKeyStore(byte[] secretKey, String algorithm, BYOKRequestParams requestParams) throws SecurityException{

  80.         try{            
  81.             if(secretKey==null){
  82.                 throw new SecurityException("Store publicKey undefined");
  83.             }
  84.             this.secretKeyContent = secretKey;
  85.            
  86.             this.secretKeyContent = StoreUtils.unwrapBYOK(this.secretKeyContent, requestParams);

  87.             this.algorithm = algorithm==null ? SymmetricKeyUtils.ALGO_AES : algorithm;
  88.            
  89.         }catch(Exception e){
  90.             throw new SecurityException(e.getMessage(),e);
  91.         }
  92.        
  93.     }
  94.    
  95.     public SecretKeyStore(SecretPasswordKeyDerivationConfig passwordKeyDerivationConfig) throws SecurityException{
  96.         this(passwordKeyDerivationConfig, null);
  97.     }
  98.     public SecretKeyStore(SecretPasswordKeyDerivationConfig passwordKeyDerivationConfig, BYOKRequestParams requestParams) throws SecurityException{
  99.         /** NOTA: Ha senso SOLO per ottenere una chiave per cifrare; mentre per la decifratura la chiave deve essere derivata anche analizzando il testo cifrato */
  100.         try{            
  101.             if(passwordKeyDerivationConfig==null){
  102.                 throw new SecurityException("Password Key Derivation config undefined");
  103.             }
  104.             if(passwordKeyDerivationConfig.getPasswordEncryptionMode()==null){
  105.                 throw new SecurityException("Password Key Derivation mode undefined");
  106.             }
  107.             if(passwordKeyDerivationConfig.getPassword()==null){
  108.                 throw new SecurityException("Password Key Derivation undefined");
  109.             }
  110.             String pwd = null;
  111.             if(requestParams!=null) {
  112.                 pwd = new String(StoreUtils.unwrapBYOK(passwordKeyDerivationConfig.getPassword().getBytes(), requestParams));
  113.             }
  114.             else {
  115.                 pwd = passwordKeyDerivationConfig.getPassword();
  116.             }
  117.             if(BYOKCostanti.isOpenSSLPasswordDerivationKeyMode(passwordKeyDerivationConfig.getPasswordEncryptionMode())) {
  118.                 CipherInfo cipherInfo = null;
  119.                 if(BYOKCostanti.isOpenSSLPBKDF2PasswordDerivationKeyMode(passwordKeyDerivationConfig.getPasswordEncryptionMode())) {
  120.                     cipherInfo = EncryptOpenSSLPassPBKDF2.buildCipherInfo(pwd, passwordKeyDerivationConfig.getPasswordIterator(),
  121.                             OpenSSLEncryptionMode.toMode(passwordKeyDerivationConfig.getPasswordEncryptionMode()));
  122.                 }
  123.                 else {
  124.                     cipherInfo = EncryptOpenSSLPass.buildCipherInfo(pwd, null,
  125.                             OpenSSLEncryptionMode.toMode(passwordKeyDerivationConfig.getPasswordEncryptionMode()));
  126.                 }
  127.                 this.secretKeyContent = cipherInfo.getEncodedKey();
  128.                 this.secretKey = (SecretKey) cipherInfo.getKey();
  129.                 this.algorithm = SymmetricKeyUtils.ALGO_AES;
  130.                 this.iv = cipherInfo.getIv();
  131.                 this.salt = cipherInfo.getSalt();
  132.             }
  133.             else {
  134.                 throw new SecurityException("Password Key Derivation mode '"+passwordKeyDerivationConfig.getPasswordEncryptionMode()+"' unsupported");
  135.             }
  136.            
  137.         }catch(Exception e){
  138.             throw new SecurityException(e.getMessage(),e);
  139.         }
  140.        
  141.     }

  142.     public SecretKey getSecretKey() throws SecurityException {
  143.         if(this.secretKey==null) {
  144.             initializeSecretKey();
  145.         }
  146.         return this.secretKey;
  147.     }
  148.     private synchronized void initializeSecretKey() throws SecurityException {
  149.         if(this.secretKey==null) {
  150.             try {
  151.                 this.secretKey = SymmetricKeyUtils.getInstance(this.algorithm).getSecretKey(this.secretKeyContent);
  152.             }catch(Exception e){
  153.                 throw new SecurityException("Load public key failed: "+e.getMessage(),e);
  154.             }
  155.         }
  156.     }
  157.    
  158.     public byte[] getIv() {
  159.         return this.iv;
  160.     }
  161.     public byte[] getSalt() {
  162.         return this.salt;
  163.     }
  164.    
  165. }