KSM Locale
In questa sezione viene descritta la sintassi da utilizzare per definire i KMS funzionali ad operazioni di cifratura (wrap) o di decifratura (unwrap) dove la master key è presente in un keystore locale (risiedente su filesystem) o all’interno di un HSM;
Di seguito un esempio di KSM basato sulla cifratura di un’informazione tramite una chiave pubblica
# Esempio di KSM Wrap per una cifratura basata su chiave pubblica
ksm.govway-async-keys-wrap.label=GovWay AsyncKeys Wrap Example
ksm.govway-async-keys-wrap.type=async-keys-wrap
ksm.govway-async-keys-wrap.mode=wrap
ksm.govway-async-keys-wrap.encryptionMode=local
ksm.govway-async-keys-wrap.local.impl=java
ksm.govway-async-keys-wrap.local.keystore.type=public
ksm.govway-async-keys-wrap.local.key.path=/etc/govway/keys/keyPair-test.rsa.publicKey.pem
ksm.govway-async-keys-wrap.local.key.algorithm=RSA/ECB/OAEPWithSHA-256AndMGF1Padding
ksm.govway-async-keys-wrap.local.key.wrap=true
ksm.govway-async-keys-wrap.local.algorithm=AES/CBC/PKCS5Padding
ksm.govway-async-keys-wrap.local.encoding=base64
Il corrispettivo esempio di KSM necessario a decifrare l’informazione tramite la chiave privata associata.
# Esempio di KSM Unwrap per una cifratura basata su chiave asincrona
ksm.govway-async-keys-unwrap.label=GovWay AsyncKeys Unwrap Example
ksm.govway-async-keys-unwrap.type=async-keys-unwrap
ksm.govway-async-keys-unwrap.mode=unwrap
ksm.govway-async-keys-unwrap.encryptionMode=local
ksm.govway-async-keys-unwrap.local.impl=java
ksm.govway-async-keys-unwrap.local.keystore.type=keys
ksm.govway-async-keys-unwrap.local.key.path=/etc/govway/keys/keyPair-test.rsa.pkcs8_encrypted.privateKey.pem
ksm.govway-async-keys-unwrap.local.key.password=${envj:read(GOVWAY_PRIVATE_KEY_PASSWORD)}
ksm.govway-async-keys-unwrap.local.publicKey.path=/etc/govway/keys/keyPair-test.rsa.publicKey.pem
ksm.govway-async-keys-unwrap.local.key.algorithm=RSA/ECB/OAEPWithSHA-256AndMGF1Padding
ksm.govway-async-keys-unwrap.local.key.wrap=true
ksm.govway-async-keys-unwrap.local.algorithm=AES/CBC/PKCS5Padding
ksm.govway-async-keys-unwrap.local.encoding=base64
L’operazione viene descritta da un insieme di direttive definite tramite la sintassi:
“ksm.<idKsm>.local.<direttiva>”
Di seguito vengono fornite tutte le direttive supportate:
impl [required]: indica il tipo di token cifrato prodotto o atteso per essere decifrato:
jose: un token JSON Web Encryption (JWE) conforme al RFC 7516;
java: viene utilizzata la classe Cipher fornita dal package javax.crypto per cifrare i dati che poi verranno serializzati su file di log a seconda della direttiva “encoding” fornita;
openssl: viene prodotto un cipher text, attraverso una chiave derivata da una password, che può essere decifrato utilizzando i comandi di encryption “openssl”; richiede un keystore di tipo “pass”.
encoding [required; mode=java|openssl]: indica il tipo di codifica utilizzato per la rappresentazione dei dati cifrati:
base64: rappresentazione base64;
hex: rappresentazione esadecimale;
keystore.type [required]: indica il tipo di keystore utilizzato dove è presente la chiave di cifratura da utilizzare:
symm: indica l’utilizzo di una chiave simmetrica fornita attraverso tramite la direttiva:
key.inline: chiave simmetrica (es. Chiave AES dovà essere di 16, 24 o 32 byte);
key.path: [ignorata se presente “key.inline”] path su filesystem ad una chiave simmetrica (es. Chiave AES dovà essere di 16, 24 o 32 byte);
key.encoding: [optional; base64/hex] consente di indicare la codifica della chiave;
pass: indica la generazione di una chiave derivata da una password attraverso le seguenti direttive (non utilizzabile con la modalità “jose”):
password: la password utilizzata per derivare la chiave;
password.type: [opzionale; default=openssl-pbkdf2-aes-256-cbc] consente di selezionare l’algoritmo di derivazione tra le seguenti opzioni disponibili:
openssl-aes-256-cbc
openssl-pbkdf2-aes-128-cbc
openssl-pbkdf2-aes-192-cbc
openssl-pbkdf2-aes-256-cbc
password.iter: [optional] consente di indicare il numero di iterazioni durante la derivazione della chiave con l’algoritmo pbkdf2.
jceks: indica l’utilizzo di una chiave simmetrica presente in un keystore java di tipo JCEKS indirizzato tramite le seguenti direttive:
keystore.path: path su filesystem del keystore;
keystore.password: password del keystore;
key.alias: alias che identifica la chiave simmetrica nel keystore;
key.password: password della chiave simmetrica;
public: indica l’utilizzo di una chiave pubblica asimmetrica fornita attraverso le seguenti direttive:
key.inline: chiave pubblica asimmetrica in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
key.path: [ignorata se presente “key.inline”] path su filesystem ad una chiave pubblica asimmetrica in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
key.encoding: [optional; base64/hex] consente di indicare la codifica della chiave;
key.wrap [optional; mode=java; boolean true/false]: indicazione se la chiave pubblica debba essere utilizzata per cifrare direttamente i dati (key.wrap=false) o per cifrare una chiave simmetrica AES generata dinamicamente (key.wrap=true);
Nota
La modalità “key.wrap=false” è utilizzabile solamente con informazioni da cifrare «sufficientemente corte» rispetto alla capacità di cifratura della chiave RSA altrimenti si avrà un errore simile al seguente: «too much data for RSA block».
keys: indica l’utilizzo di chiavi asincrone fornita attraverso le seguenti direttive:
key.inline: chiave privata in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
key.path: [ignorata se presente “key.inline”] path su filesystem ad una chiave privata in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
key.password: password della chiave privata;
key.encoding: [optional; base64/hex] consente di indicare la codifica della chiave privata;
key.wrap [optional; mode=java; boolean true/false]: indicazione se la chiave pubblica è stata utilizzata per cifrare direttamente i dati (key.wrap=false) o per cifrare una chiave simmetrica AES generata dinamicamente (key.wrap=true);
publicKey.inline: chiave pubblica in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
publicKey.path: [ignorata se presente “publicKey.inline”] path su filesystem ad una chiave pubblica in formato PEM o DER (sono supportati sia i formati pkcs1 che pkcs8);
publicKey.encoding: [optional; base64/hex] consente di indicare la codifica della chiave pubblica;
jwk: indica l’utilizzo di keystore JWK che può contenere una chiave simmetrica o una chiave pubblica asimmetrica; le direttive supportate sono le seguenti:
keystore.path: path su filesystem del keystore;
key.alias: alias che identifica la chiave nel keystore;
key.wrap [optional; mode=java; boolean true/false]: indicazione se la chiave pubblica debba essere utilizzata per cifrare direttamente i dati (key.wrap=false) o per cifrare una chiave simmetrica AES generata dinamicamente (key.wrap=true);
jks o pkcs12: indica l’utilizzo di un certificato presente in un keystore java di tipo JKS o PKCS12 indirizzato tramite le seguenti direttive:
keystore.path: path su filesystem del keystore;
keystore.password: password del keystore;
key.alias: alias che identifica il certificato nel keystore;
key.wrap [optional; mode=java; boolean true/false]: indicazione se il certificato debba essere utilizzato per cifrare direttamente i dati (key.wrap=false) o per cifrare una chiave simmetrica AES generata dinamicamente (key.wrap=true);
<tipoRegistratoPKCS11>: indica l’utilizzo di uno dei tipi di keystore PKCS11 registrati (”Device PKCS11”) all’interno del quale è presente il certificato da utilizzare indicato tramite la direttiva:
key.alias: alias che identifica il certificato nel keystore;
key.wrap [optional; mode=java; boolean true/false]: indicazione se il certificato debba essere utilizzato per cifrare direttamente i dati (key.wrap=false) o per cifrare una chiave simmetrica AES generata dinamicamente (key.wrap=true);
key.algorithm [required]: specifica l’algoritmo utilizzato per generare o gestire le chiavi crittografiche utilizzate durante il processo di cifratura;
algorithm [required]: specifica l’algoritmo utilizzato per cifrare effettivamente i dati;
include.key.id [optional; mode=jose; boolean true/false]: indicazione se inserire nell’header del token JWE (claim “kid”) l’alias della chiave utilizzata per la cifratura;
key.id [optional; mode=jose]: indica il nome della chiave che verrà inserito nel claim “kid” presente nell’header del token JWE;
include.cert [optional; mode=jose; boolean true/false]: indicazione se inserire nell’header del token JWE (claim “x5c”) il certificato utilizzato per la cifratura;
include.cert.sha1 [optional; mode=jose; boolean true/false]: indicazione se inserire nell’header del token JWE (claim “x5t”) il digest SHA-1 del certificato utilizzato per la cifratura;
include.cert.sha256 [optional; mode=jose; boolean true/false]: indicazione se inserire nell’header del token JWE (claim “x5t#256”) il digest SHA-256 del certificato utilizzato per la cifratura;
include.public.key [optional; mode=jose; boolean true/false]: indicazione se inserire nell’header del token JWE (claim “jwk”) la chiave pubblica utilizzata per la cifratura.
Rappresentazione dei dati cifrati con mode=java
Come descritto in precedenza indicando la modalità “java” nella direttiva “mode” viene utilizzata la classe Cipher fornita dal package javax.crypto per cifrare i dati che poi verranno serializzati su file di log a seconda della direttiva “encoding” fornita: base64 o hex.
In funzione del tipo di chiave (simmetrica o asimmetrica) e della direttiva key.wrap la rappresentazione dei dati cifrati conterrà più parti che devono essere considerate per poter effettuare l’operazione inversa di decifratura:
chiave simmetrica: il dato cifrato è formato da due parti, separate tramite un punto, entrambe codificate in base64 o hex a seconda dell’encoding selezionato; la prima parte rappresenta il Vettore di Inizializzazione (IV) mentre la seconda sono i dati cifrati:
<IV>.<DatiCifrati>
chiave pubblica asimmetrica con direttiva key.wrap=true: il dato cifrato è formato da tre parti, separate tramite un punto, entrambe codificate in base64 o hex a seconda dell’encoding selezionato; la prima parte rappresenta la chiave AES generata dinamicamente e cifrata con la chiave pubblica (wrap), la seconda parte il Vettore di Inizializzazione (IV) della cifratura simmetrica e la terza parte sono i dati cifrati con la chiave simmetrica:
<WRAP_KEY>.<IV>.<DatiCifrati>
chiave pubblica asimmetrica con direttiva key.wrap=false: è presente solo una parte contenente i dati cifrati con la chiave pubblica asimmetrica:
<DatiCifrati>