com.unbound.client.kmip.KMIPSession Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of unbound-java-provider Show documentation
Show all versions of unbound-java-provider Show documentation
This is a collection of JAVA libraries that implement Unbound cryptographic classes for JAVA provider, PKCS11 wrapper, cryptoki, and advapi
package com.unbound.client.kmip;
import com.unbound.client.*;
import com.unbound.common.Base64;
import com.unbound.common.JSON;
import com.unbound.common.Log;
import com.unbound.common.STR;
import com.unbound.common.crypto.EC;
import com.unbound.kmip.KMIP;
import com.unbound.kmip.KMIPConverter;
import com.unbound.kmip.attribute.*;
import com.unbound.kmip.request.*;
import com.unbound.kmip.request.dy.DyLoginRequest;
import com.unbound.kmip.response.*;
import com.unbound.kmip.response.dy.DyLoginResponse;
import com.unbound.provider.*;
import java.security.ProviderException;
import java.security.cert.X509Certificate;
import java.security.interfaces.ECPrivateKey;
import java.security.interfaces.RSAPrivateCrtKey;
import java.security.interfaces.RSAPublicKey;
import java.time.Clock;
import java.util.ArrayList;
import java.util.Map;
public class KMIPSession implements Session
{
private static final Clock clock = Clock.systemUTC();
private final KMIPPartition partition;
private KMIPServer server = null;
KMIPSession(KMIPPartition partition)
{
this.partition = partition;
}
private byte[] transmitBytes(byte[] in)
{
if (KMIPClient.simulator!=null) return KMIPClient.simTransmit(in);
if (server!=null) return server.transmit(partition, in);
KMIPServer[] servers = KMIPServer.getList();
int retry = servers.length;
for (KMIPServer server : servers)
{
try
{
byte[] out = server.transmit(partition, in);
this.server = server;
return out;
}
catch (Exception e)
{
retry--;
if (retry == 0) throw new ProviderException(e);
}
}
throw new ProviderException("No servers found");
}
ResponseMessage transmit(RequestMessage req)
{
Log log = Log.func("KMIPConnection.transmit").end(); try
{
if (partition!=null)
{
byte[] jwt;
long jwtValidityClock;
synchronized (partition)
{
jwt = partition.jwt;
jwtValidityClock = partition.jwtValidityClock;
}
if (req.header.auth==null && jwt!=null)
{
if (jwtValidityClock < clock.millis())
{
loginRenew();
}
req.header.auth = new Authentication();
req.header.auth.credType = KMIP.CredentialType.Attestation;
req.header.auth.attestationType = KMIP.AttestationType.DyJwtAssertion;
req.header.auth.attestationAssertion = jwt;
}
}
byte[] in = KMIPConverter.convert(req);
req.log();
byte[] out = transmitBytes(in);
ResponseMessage resp = KMIPConverter.convertResponseMessage(out);
resp.log();
if (resp.header.batchCount == 0)
{
throw new ProviderException("Invalid KMIP response");
}
ResponseItem item = resp.batch.get(0);
if (item.resultStatus != KMIP.ResultStatus.Success)
{
throw new ProviderException("KMIP error " + item.reason + " " + item.resultMsg);
}
return resp;
}
catch (Exception e) { log.failed(e); throw new ProviderException(e); } finally { log.leave(); }
}
ResponseItem transmit(RequestItem req)
{
RequestMessage reqMsg = new RequestMessage();
reqMsg.batch.add(req);
ResponseMessage respMsg = transmit(reqMsg);
return respMsg.batch.get(0);
}
private void loginRenew()
{
loginOrRenew(null, true);
}
void login(String password)
{
loginOrRenew(password, false);
}
private void loginOrRenew(String password, boolean renewWjt)
{
Log log = Log.func("KMIPSession.loginOrRenew").log("renewWjt", renewWjt).log("password", password!=null && !password.isEmpty()).end(); try
{
RequestMessage reqMsg = new RequestMessage();
reqMsg.header.auth = new Authentication();
if (renewWjt)
{
reqMsg.header.auth = new Authentication();
reqMsg.header.auth.credType = KMIP.CredentialType.Attestation;
reqMsg.header.auth.attestationType = KMIP.AttestationType.DyJwtAssertion;
reqMsg.header.auth.attestationAssertion = partition.jwt;
}
else
{
reqMsg.header.auth.credType = KMIP.CredentialType.UsernameAndPassword;
reqMsg.header.auth.username = "user";
reqMsg.header.auth.password = "";
if (password!=null)
{
String user;
try
{
Map json = (Map) JSON.convert(password);
user = (String) json.get("username");
password = (String) json.get("password");
}
catch (Exception e)
{
user = "user";
}
reqMsg.header.auth.password = password;
reqMsg.header.auth.username = user;
}
}
DyLoginRequest req = new DyLoginRequest();
req.doCreateWjt = true;
reqMsg.batch.add(req);
try
{
ResponseMessage respMsg = transmit(reqMsg);
DyLoginResponse resp = (DyLoginResponse) respMsg.batch.get(0);
if (resp.jwt!=null)
{
int validity = jwtTokenValidity(STR.utf8(resp.jwt));
if (validity>0)
{
synchronized (partition)
{
long now = clock.millis();
partition.jwt = resp.jwt;
partition.jwtValidityClock = now + validity*1000;
}
}
}
}
catch (Exception e)
{
synchronized (partition)
{
partition.jwt = null;
}
throw e;
}
}
catch (Exception e) { log.failed(e); throw new ProviderException(e); } finally { log.leave(); }
}
static int jwtTokenValidity(String jwt)
{
String[] t = jwt.split("\\.");
if (t.length!=3) return 0;
byte[] t1 = Base64.decodeUrl(t[1]);
String s = STR.utf8(t1);
Map root = (Map) JSON.convert(s);
Long iat = (Long)root.get("iat");
Long exp = (Long)root.get("exp");
return (int) (exp - iat - 30);
}
@Override
public Partition getPartition()
{
return partition;
}
@Override
public void release() { }
@Override
public SecretKeyObject generateSecretKey(String name, ObjectType type, int bitSize, KeyParameters kp)
{
return KMIPSecretKey.generate(this, name, type, bitSize, kp);
}
@Override
public SecretKeyObject importSecretKey(String name, ObjectType type, byte[] keyValue, KeyParameters kp)
{
return KMIPSecretKey.importKey(this, name, type, keyValue, kp);
}
@Override
public EDDSAPrivateKeyObject generateEddsaKey(String name, KeyParameters kp)
{
throw new ProviderException("Not implemented");
}
@Override
public RSAPrivateKeyObject importRsaKey(String name, RSAPrivateCrtKey keyValue, KeyParameters kp)
{
return KMIPRSAPrivateKey.importKey(this, name, keyValue, kp);
}
@Override
public ECPrivateKeyObject generateEcKey(String name, EC.Curve curve, KeyParameters kp)
{
return KMIPECPrivateKey.generate(this, name, curve, kp);
}
@Override
public RSAPublicKeyObject importPubRsaKey(String name, RSAPublicKey keyValue, KeyParameters kp)
{
return KMIPRSAPublicKey.importKey(this, name, keyValue, kp);
}
@Override
public ECPrivateKeyObject importEcKey(String name, ECPrivateKey keyValue, KeyParameters kp)
{
return KMIPECPrivateKey.importKey(this, name, keyValue, kp);
}
@Override
public ECPRFKey generateEcprfKey(String name, KeyParameters kp)
{
return KMIPECPRFKey.generate(this, name, kp);
}
@Override
public CertObject importCert(String name, X509Certificate cert)
{
return KMIPCert.importCert(this, name, cert);
}
@Override
public RSAPrivateKeyObject generateRsaKey(String name, int bitSize, KeyParameters kp)
{
return KMIPRSAPrivateKey.generate(this, name, bitSize, kp);
}
@Override
public BaseObject locate(ObjectType type, LocateParams params) { return KMIPObject.locate(this, type, params); }
@Override
public ArrayList locate(ObjectType type) { return KMIPObject.locate(this, type); }
}