AbstractXmlCipher.java
/*
* GovWay - A customizable API Gateway
* https://govway.org
*
* Copyright (c) 2005-2024 Link.it srl (https://link.it).
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 3, as published by
* the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
package org.openspcoop2.utils.security;
import java.security.Provider;
import java.security.Security;
import javax.crypto.KeyGenerator;
import javax.crypto.SecretKey;
import org.apache.xml.security.encryption.XMLCipher;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.openspcoop2.utils.UtilsException;
import org.openspcoop2.utils.certificate.KeyStore;
/**
* Encrypt
*
* @author Poli Andrea (apoli@link.it)
* @author $Author$
* @version $Rev$, $Date$
*/
public abstract class AbstractXmlCipher {
protected java.security.Provider provider;
private java.security.Key keyWrapped;
private java.security.cert.Certificate certificateWrapped;
protected SecretKey secretKeyWrapped;
private int mode;
private SymmetricKeyWrappedMode encryptedKeyMode;
protected SecretKey secretKeyEncrypt;
public boolean isEncryptedKey() throws UtilsException {
if(this.encryptedKeyMode!=null) {
switch (this.encryptedKeyMode) {
case SYM_ENC_KEY_NO_WRAPPED:
return false;
case SYM_ENC_KEY_WRAPPED_SYMMETRIC_KEY:
case SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY:
return true;
}
}
throw new UtilsException("Wrapped Key Mode undefined");
}
// BOTH
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore, boolean symmetricKey, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String alias, String passwordPrivateKey) throws UtilsException{
this(mode, new KeyStore(keystore), symmetricKey, wrappedSymmetricKeyMode, alias, passwordPrivateKey, false);
}
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore, boolean symmetricKey, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String alias, String passwordPrivateKey,boolean addBouncyCastleProvider) throws UtilsException{
this(mode, new KeyStore(keystore), symmetricKey, wrappedSymmetricKeyMode, alias, passwordPrivateKey, addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, KeyStore keystore, boolean symmetricKey, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String alias, String passwordPrivateKey) throws UtilsException{
this(mode, keystore, symmetricKey, wrappedSymmetricKeyMode, alias, passwordPrivateKey, false);
}
protected AbstractXmlCipher(int mode, KeyStore keystore, boolean symmetricKey, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String alias, String passwordPrivateKey,boolean addBouncyCastleProvider) throws UtilsException{
if(symmetricKey) {
SecretKey secretKey = keystore.getSecretKey(alias, passwordPrivateKey);
this.initSymmetric(mode, wrappedSymmetricKeyMode, secretKey, addBouncyCastleProvider);
}
else {
this.initPrivate(mode, keystore, alias, passwordPrivateKey, addBouncyCastleProvider);
}
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, java.security.Key key) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, key, false);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, java.security.Key key,boolean addBouncyCastleProvider) throws UtilsException{
if(key instanceof SecretKey){
this.initSymmetric(mode, wrappedSymmetricKeyMode, (SecretKey) key, addBouncyCastleProvider);
}
else{
this.mode = mode;
this.keyWrapped = key;
this.encryptedKeyMode = SymmetricKeyWrappedMode.SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY;
this.init(addBouncyCastleProvider);
}
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, java.security.KeyStore keystore, String alias, String passwordPrivateKey) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, new KeyStore(keystore), alias, passwordPrivateKey, false);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, java.security.KeyStore keystore, String alias, String passwordPrivateKey,boolean addBouncyCastleProvider) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, new KeyStore(keystore), alias, passwordPrivateKey, addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, KeyStore keystore, String alias, String passwordPrivateKey) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, keystore, alias, passwordPrivateKey, false);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, KeyStore keystore, String alias, String passwordPrivateKey,boolean addBouncyCastleProvider) throws UtilsException{
if("jceks".equalsIgnoreCase(keystore.getKeystore().getType())) {
SecretKey secretKey = keystore.getSecretKey(alias, passwordPrivateKey);
this.initSymmetric(mode, wrappedSymmetricKeyMode, secretKey, addBouncyCastleProvider);
}
else {
this.initPrivate(mode, keystore, alias, passwordPrivateKey, addBouncyCastleProvider);
}
}
// SYMMETRIC
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, SecretKey secretKey) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, secretKey, false);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, SecretKey secretKey,boolean addBouncyCastleProvider) throws UtilsException{
this.initSymmetric(mode, wrappedSymmetricKeyMode, secretKey, addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String keyAlgorithm) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, keyAlgorithm, false);
}
protected AbstractXmlCipher(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, String keyAlgorithm,boolean addBouncyCastleProvider) throws UtilsException{
this(mode, wrappedSymmetricKeyMode, generateSecretKey(keyAlgorithm),addBouncyCastleProvider);
}
private void initSymmetric(int mode, SymmetricKeyWrappedMode wrappedSymmetricKeyMode, SecretKey secretKey, boolean addBouncyCastleProvider) throws UtilsException{
this.mode = mode;
switch (wrappedSymmetricKeyMode) {
case SYM_ENC_KEY_NO_WRAPPED:
this.secretKeyEncrypt = secretKey;
break;
default:
this.secretKeyWrapped = secretKey;
break;
}
this.encryptedKeyMode = wrappedSymmetricKeyMode;
this.init(addBouncyCastleProvider);
}
public SecretKey getSecretKeyEncryption() {
return this.secretKeyEncrypt;
}
public static SecretKey generateSecretKey(String algorithm) throws UtilsException {
return generateSecretKey(algorithm, null);
}
public static SecretKey generateSecretKey(String algorithm, Provider provider) throws UtilsException {
KeyGenerator keyGenerator = null;
try {
if(provider!=null) {
keyGenerator = KeyGenerator.getInstance(algorithm, provider);
}
else {
keyGenerator = KeyGenerator.getInstance(algorithm);
}
}catch(Exception e){
throw new UtilsException(e.getMessage(),e);
}
return keyGenerator.generateKey();
}
// ASYMMETRIC
private void initPrivate(int mode, KeyStore keystore, String alias, String passwordPrivateKey,boolean addBouncyCastleProvider) throws UtilsException{
this.mode = mode;
this.keyWrapped = keystore.getPrivateKey(alias, passwordPrivateKey);
this.encryptedKeyMode = SymmetricKeyWrappedMode.SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY;
// Non sembra necessario
/** if(keystore.getKeystoreType().equalsIgnoreCase(KeystoreType.PKCS11.getNome())) {
// this.provider = keystore.getKeystoreProvider();
// }*/
this.init(addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, java.security.cert.Certificate certificate) throws UtilsException{
this(mode, certificate, false);
}
protected AbstractXmlCipher(int mode, java.security.cert.Certificate certificate,boolean addBouncyCastleProvider) throws UtilsException{
this.mode = mode;
this.certificateWrapped = certificate;
this.encryptedKeyMode = SymmetricKeyWrappedMode.SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY;
this.init(addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore, String alias) throws UtilsException{
this(mode, new KeyStore(keystore), alias, false);
}
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore, String alias,boolean addBouncyCastleProvider) throws UtilsException{
this(mode, new KeyStore(keystore), alias, addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, KeyStore keystore, String alias) throws UtilsException{
this(mode, keystore, alias, false);
}
protected AbstractXmlCipher(int mode, KeyStore keystore, String alias,boolean addBouncyCastleProvider) throws UtilsException{
this.mode = mode;
this.certificateWrapped = keystore.getCertificate(alias);
this.encryptedKeyMode = SymmetricKeyWrappedMode.SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY;
this.init(addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore) throws UtilsException{
this(mode, new KeyStore(keystore), false);
}
protected AbstractXmlCipher(int mode, java.security.KeyStore keystore,boolean addBouncyCastleProvider) throws UtilsException{
this(mode, new KeyStore(keystore), addBouncyCastleProvider);
}
protected AbstractXmlCipher(int mode, KeyStore keystore) throws UtilsException{
this(mode, keystore, false);
}
protected AbstractXmlCipher(int mode, KeyStore keystore,boolean addBouncyCastleProvider) throws UtilsException{
this.mode = mode;
this.certificateWrapped = keystore.getCertificate();
this.encryptedKeyMode = SymmetricKeyWrappedMode.SYM_ENC_KEY_WRAPPED_ASYMMETRIC_KEY;
this.init(addBouncyCastleProvider);
}
private void init(boolean addBouncyCastleProvider) throws UtilsException{
try{
// Providers
if(addBouncyCastleProvider){
BouncyCastleProvider bouncyCastleProvider = new BouncyCastleProvider();
Security.addProvider(bouncyCastleProvider);
}
org.apache.xml.security.Init.init();
}catch(Exception e){
throw new UtilsException(e.getMessage(),e);
}
}
protected org.apache.xml.security.encryption.XMLCipher getXMLCipher() throws UtilsException{
try{
org.apache.xml.security.encryption.XMLCipher xmlCipher = null;
if(this.provider!=null) {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance(this.provider.getName());
}
else {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance();
}
xmlCipher.init(this.mode, null);
return xmlCipher;
}catch(Exception e){
throw new UtilsException(e.getMessage(),e);
}
}
protected org.apache.xml.security.encryption.XMLCipher getXMLCipher(String algorithm, String canon, String digest) throws UtilsException{
try{
org.apache.xml.security.encryption.XMLCipher xmlCipher = null;
if(canon!=null || digest!=null) {
if(this.provider!=null) {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getProviderInstance(algorithm, this.provider.getName(), canon, digest);
}
else {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance(algorithm,canon,digest);
}
}
else {
if(this.provider!=null) {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getProviderInstance(algorithm, this.provider.getName());
}
else {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance(algorithm);
}
}
if(this.secretKeyEncrypt==null) {
throw new UtilsException("Key for initialize cipher engine not found");
}
xmlCipher.init(this.mode, this.secretKeyEncrypt);
return xmlCipher;
}catch(Exception e){
throw new UtilsException(e.getMessage(),e);
}
}
protected org.apache.xml.security.encryption.XMLCipher getXMLCipherUnwrappedKey() throws UtilsException{
return this.getXMLCipherWrappedKey(null);
}
protected org.apache.xml.security.encryption.XMLCipher getXMLCipherWrappedKey(String algorithm) throws UtilsException{
try{
org.apache.xml.security.encryption.XMLCipher xmlCipher = null;
if(algorithm!=null){
if(this.provider!=null) {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getProviderInstance(algorithm, this.provider.getName());
}
else {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance(algorithm);
}
}
else{
if(this.provider!=null) {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getProviderInstance(this.provider.getName());
}
else {
xmlCipher = org.apache.xml.security.encryption.XMLCipher.getInstance();
}
}
int wrapMode = -1;
if(XMLCipher.ENCRYPT_MODE == this.mode){
wrapMode = XMLCipher.WRAP_MODE;
}
else{
wrapMode = XMLCipher.UNWRAP_MODE;
}
if(this.secretKeyWrapped!=null){
xmlCipher.init(wrapMode, this.secretKeyWrapped);
}
else if(this.keyWrapped!=null){
xmlCipher.init(wrapMode, this.keyWrapped);
}
else if(this.certificateWrapped!=null){
xmlCipher.init(wrapMode, this.certificateWrapped.getPublicKey());
}
else {
throw new UtilsException("Key for initialize cipher engine 'wrapped key' not found");
}
return xmlCipher;
}catch(Exception e){
throw new UtilsException(e.getMessage(),e);
}
}
}