Home » Articles

P6R demonstrates KMIP Client SDK’s Standards Conformance at RSA 2015

By Mark Joseph - April 24, 2015 @ 5:08 pm

P6R participated in the OASIS KMIP and PKCS #11 interoperability demonstration at the 2015 RSA conference.
P6R was showcasing the latest release of its SKC product, which contains a full featured KMIP Client with UEFI support, and PKCS11.

Here is a picture of the P6R station in the OASIS booth at the 2015 RSA Conference:

014

As part of this demonstration P6R participated in an OASIS run interoperation test with other vendors in the KMIP Technical Committee. The results of these tests is shown in the charts below.

Integrating KMIP, PKCS 11, and SSH

By Mark Joseph - January 2, 2015 @ 10:06 pm

Introduction

P6R has implemented a PKCS 11 Baseline Consumer as part of a SSH server’s Public Key Authentication protocol (i.e., RFC 4252). This implementation provides centralized Public Key management for SSH installations via the use of KMIP. With our PKCS 11 Consumer, the SSH server looks up a user’s Public Key on a remote KMIP server rather than some file system directory. This scheme makes adding or removing a user’s SSH login authentication as easy as creating or removing a set of keys from a KMIP server. This PKCS 11 Consumer is both a PKCS 11 and KMIP client.
(See PKCS11 Cryptographic Token Interface Profiles Version 2.40, 16-Sep-2014, OASIS Committee Specification 01, for the definition of a PKCS 11, Version 2.40, Baseline Consumer).

A PKCS 11 Consumer

This initial Consumer implementation was done as part of the
P6R’s SSH Server, but in the future it will be ported to other SSH servers. P6R’s SSH server includes support for the following authentication protocols: “The Secure Shell (SSH) Authentication Protocol”, RFC 4252, “Secure Shell Public Key Subsystem, RFC 4819, and “P6R’s Secure Shell Public Key Subsystem, RFC 7076. All three of these protocols have been implemented using PKCS 11 and comprise parts of the overall PKCS 11 Consumer client.

PKCS 11 Consumer

In the above figure, the Consumer is composed of all the blue boxes. The SecureCRT SSH client implements RFC 4252 & 4819, thus allowing a user to upload Public Keys into the SSH server for use in the Public Key Authentication protocol. SecureCRT also allows the user to list all uploaded Public Keys and to delete any from his account. Our server based implementation of RFC 4819 allows all keys to be stored on a KMIP server. After a user uploads a Public Key (initially logged in via a password) he can then switch his client to use Public Key Authentication instead of passwords. On his next login, the RFC 4252 plugin will find his matching Public Key on a KMIP server and he will be logged on.

The RFC 7076 plugin allows a user to upload Certificates as well as Public Keys. It supports the concept of namespaces which map directly to KMIP groups. P6R provides a SSH client that implements this protocol.

Why use PKCS 11?

P6R’s PKCS 11 Consumer is built using the P6R’s PKCS 11 provider. Currently this provider supports two token types: a KMIP server, and the P6R Software token with Keystore. The PKCS 11 API allows our SSH implementation to use either of these tokens with no code change. The token type in use is defined by a configuration file. Thus a customer using our PKCS 11 Consumer can easily choose to store their SSH Public Keys on a KMIP server, or a local Keystore using a remote Postgres database (see figure above), or a local Keystore using a local Sqlite database. In the future, when additional token types are supported more options for key storage become available again with no SSH server code changes.

Why use KMIP?

KMIP provides a standard way to manage all types of keys, certificates, and various opaque objects. It is supported by a growing list of vendors thus allowing choice and mobility from one vendor to another.
An introduction to its benefits appears in the following article: The rising danger to data is making KMIP important.

P6R’s PKCS 11 Provider

By Mark Joseph - November 22, 2014 @ 3:29 pm

This document was updated on 12 December 2022.

Introduction

P6R has implemented the PKCS 11 Version 2.40 and Version 3.0 specifications. Our library meets the requirements for conformance of a PKCS 11 Extended Provider and Authentication Token (see PKCS11 Cryptographic Token Interface Profiles Version 2.40, 16-Sep-2014, OASIS Committee Specification 01). Currently, our library supports eleven types of tokens: a KMIP server, a Software token, a Thales Luna HSM (SafeNet/Gemalto), a Utimaco CryptoServer HSM, a Entrust nShield Connect HSM (formerly nCipher), a FutureX HSM, a DocuSign HSM, a Utimaco Atalla AT1000 HSM, a YubiHSM 2.0, a AWS CloudHSM, and the Marvell LiquidSecurity HSM. Our library also allows a customer to provide their own token types via a plugin interface. One of the benefits of the PKCS 11 API is that it provides a standard based Keystore API.

Supporting these different types of tokens in one PKCS 11 library facilitates some interesting applications. For example, an application could store millions of keys in a KMIP server (along with extensive meta data) yet use an HSM to perform all encryption operations. In fact, the keys stored in the KMIP server could all be wrapped and only unwrapped once moved into an HSM. This can be done from a single PKCS 11 API instance. Another example is to use a KMIP server instead of an existing HSM vendor for Oracle TDE integration.

manyhsms

P6R’s PKCS 11 library is contained in both P6R’s Secure KMIP Client (SKC) and P11 products.


The KMIP Token

The KMIP token uses the facilities of a remote KMIP server to implement the features of the PKCS 11 Version 2.40 API. This token type uses P6R’s Secure KMIP Client (SKC) SDK to communicate with a configured KMIP server. As of this writing, SKC works with all known commercially available KMIP servers. Our PKCS 11 library allows the definition of any number of KMIP tokens all pointing to the same or different KMIP servers.

An important benefit of this token is that it allows developers familiar with PKCS 11 to store their keys on a KMIP server without having to learn about the KMIP protocol or KMIP SDKs. All that is required is that this token be properly configured to make a valid TLS connection to a remote KMIP server, which is a process an installer program can help with.

The KMIP token has the following limitations with object attributes. CKA_ENCRYPT, CKA_DECRYPT, CKA_SIGN, CKA_SIGN_RECOVER, CKA_VERIFY, CKA_VERIFY_RECOVER, CKA_WRAP, CKA_UNWRAP, and CKA_DERIVE attributes cannot be changed after an object (i.e., key, certificate, data, domain parameters) is created. This is because the KMIP protocol does not allow a client to modify the KMIP equivalent attributes after a KMIP object is created. However, this token implementation does support the modification of a CKO_DATA object’s CKA_VALUE attribute after the object has been created on a KMIP server.

The KMIP token currently implements the following PKCS 11 API functions: C_Initialize, C_Finalize, C_GetInfo, C_GetFunctionList, C_GetSlotList, C_GetSlotInfo, C_GetTokenInfo, C_GetMechanismList, C_GetMechanismInfo, C_InitToken, C_InitPIN, C_SetPIN, C_OpenSession, C_CloseSession, C_CloseAllSessions, C_GetSessionInfo, C_Login, C_Logout, C_CreateObject, C_CopyObject, C_DestroyObject, C_GetAttributeValue, C_SetAttributeValue, C_FindObjectsInit, C_FindObjects, C_FindObjectsFinal, C_GenerateKey (not including domain parameters), C_GenerateKeyPair, C_SeedRandom, C_GenerateRandom, C_SignInit, C_Sign, C_SignUpdate, C_SignFinal, C_VerifyInit, C_Verify, C_VerifyUpdate, C_VerifyFinal, C_EncryptInit, C_Encrypt, C_EncryptUpdate, C_EncryptFinal, C_DecryptInit, C_Decrypt, C_DecryptUpdate, C_DecryptFinal, C_DigestInit, C_Digest, C_DigestUpdate, C_DigestKey, C_DigestFinal, C_DeriveKey, C_WrapKey, C_UnwrapKey (if the KMIP server supports unwrapping), C_GetInterfaceList, C_GetInterface, C_LoginUser, C_SessionCancel, C_MessageEncryptInit, C_MessageEncryptFinal, C_EncryptMessage, C_EncryptMessageBegin, C_EncryptMessageNext, C_MessageDecryptInit, C_MessageDecryptFinal, C_DecryptMessage, C_DecryptMessageBegin, C_DecryptMessageNext, C_MessageSignInit, C_MessageSignFinal, C_SignMessage, C_SignMessageBegin,C_SignMessageNext, C_MessageVerifyInit, C_MessageVerifyFinal, C_VerifyMessage, C_VerifyMessageBegin, and C_VerifyMessageNext.

This token supports the following PKCS 11 objects: CKO_DATA, CKO_CERTIFICATE, CKO_PUBLIC_KEY, CKO_PRIVATE_KEY, CKO_SECRET_KEY, CKO_DOMAIN_PARAMETERS and CKO_PROFILE.

This token supports the PKCS 11 CKA_UNIQUE_ID attribute in both Versions 2.40 and 3.0. This attribute provides a token assigned unique identifier for any object residing on a token.

The Software Token

The Software Token uses P6R’s cryptographic API and Keystore to implement the features of the PKCS 11 Version 2.40 API. Both the cryptographic API and Keystore are included as part of the SKC product. Our PKCS 11 library allows the definition of any number of Software tokens where each token gets its own separate secure Keystore to manage PKCS 11 objects (e.g,. keys, certificates, domain parameters, data). P6R’s cryptographic API is a C/C++ object wrapper around OpenSSL’s C language API.

The Software token currently implements the following PKCS 11 API functions: C_Initialize, C_Finalize, C_GetInfo, C_GetFunctionList, C_GetSlotList, C_GetSlotInfo, C_GetTokenInfo, C_GetMechanismList, C_GetMechanismInfo, C_InitToken, C_InitPIN, C_SetPIN, C_OpenSession, C_CloseSession, C_CloseAllSessions, C_GetSessionInfo, C_Login, C_Logout, C_CreateObject, C_CopyObject, C_DestroyObject, C_GetAttributeValue, C_SetAttributeValue, C_FindObjectsInit, C_FindObjects, C_FindObjectsFinal, C_GenerateKey (not including domain parameters), C_GenerateKeyPair, C_GenerateRandom, C_SignInit, C_Sign, C_VerifyInit, C_Verify, C_EncryptInit, C_Encrypt, C_EncryptUpdate, C_EncryptFinal, C_DecryptInit, C_Decrypt, C_DecryptUpdate, C_DecryptFinal, C_DigestInit, C_Digest, C_DigestUpdate, C_DigestKey and C_DigestFinal.

This token also supports the new PKCS#11 CKA_UNIQUE_ID attribute. This new attribute provides a token assigned unique identifier for any object residing on a token.

The Thales Luna HSM Token (SafeNet/Gemalto)

The Thales Luna HSM can be configured to look like another token. We map one slot of a Thales Luna HSM into one slot of our P6R PKCS 11 library. To use this token requires the proper setup and configuration of a Luna HSM both on the hardware server and client machine as documented in the Thales product literature. Also the proper configuration of the P6R’s PKCS 11 library is required, which is described in detail in the SKC product documentation.

Utimaco Atalla AT1000 HSM Token (formerly HPE, Micro focus)

The Atalla AT1000 HSM (formerly Network Security Processor – NSP) can be configured to look like another token. We map each NSP and Virtual NSP into a separate slot of our P6R PKCS 11 library. We have written a special token for the NSP so that we could put a PKCS 11 API around it. Basically we added parts of our Software Token to build an NSP token that allows us to store all NSP generated keys into our Keystore. In addition, all PKCS 11 attributes, none of which are natively supported by the NSP, are also maintained in our Keystore. The P6R Keystore can use either a local Sqlite database or a local or remote Postgres database. Thus using our NSP token its generated keys and PKCS 11 attributes can be managed in a client local or networked centralized database.

This token supports the following PKCS 11 mechanisms: CKM_AES_KEY_GEN, CKM_DES_KEY_GEN, CKM_DES2_KEY_GEN, CKM_DES3_KEY_GEN, CKM_SHA_1_HMAC, CKM_SHA256_HMAC, CKM_RSA_PKCS_KEY_PAIR_GEN, CKM_RSA_PKCS, CKM_SHA1_RSA_PKCS, CKM_SHA224_RSA_PKCS, CKM_SHA256_RSA_PKCS, CKM_SHA384_RSA_PKCS, CKM_SHA512_RSA_PKCS, CKM_RSA_X_509, CKM_DES_CBC, CKM_DES_CBC_PAD, CKM_DES_CFB8, CKM_DES_CFB64, CKM_DES_OFB64, CKM_DES3_CBC, CKM_AES_CBC, CKM_AES_CBC_PAD, CKM_SHA_1, CKM_SHA224, CKM_SHA256, CKM_SHA384, CKM_SHA512, CKM_MD2, CKM_MD5, and CKM_RIPEMD160. All digest calculations are done in the PKCS 11 client with the use of OpenSSL, but all other calculations are done on the NSP.

This token currently implements the following PKCS 11 API functions: C_Initialize, C_Finalize, C_GetSlotInfo, C_InitToken, C_GetTokenInfo, C_GetMechanismList, C_GetMechanismInfo, C_OpenSession, C_CloseSession, C_GetSessionInfo, C_InitPIN, C_SetPIN, C_Login, C_Logout, C_CreateObject (objects stored in the P6R Keystore), C_DestroyObject, C_GetAttributeValue, C_SetAttributeValue, C_FindObjectsInit, C_FindObjects, C_FindObjectsFinal, C_GenerateRandom (uses NSP hardware random number generator), C_SignInit, C_Sign, C_SignUpdate, C_SignFinal, C_VerifyInit, C_Verify, C_VerifyUpdate, C_VerifyFinal, C_EncryptInit, C_Encrypt, C_EncryptUpdate, C_EncryptFinal, C_DecryptInit, C_Decrypt, C_DecryptUpdate, C_DecryptFinal, C_DigestInit, C_Digest, C_DigestUpdate, C_DigestFinal, C_GenerateKey, C_GenerateKeyPair, C_WrapKey, and C_UnwrapKey.

For this and all 3rd party tokens the PKCS 11 API functions: C_GetInfo, C_GetFunctionList, C_GetSlotList, and C_CloseAllSessions are handled by the PKCS 11 provider module that dynamically loads all tokens (i.e., the green box in the picture above).

This token also supports the new PKCS#11 CKA_UNIQUE_ID attribute. This new attribute provides a token assigned unique identifier for any object residing on a token.

The Utimaco HSM Token

The Utimaco CryptoServer HSM can be configured to look like another token. We map one slot of a Utimaco HSM into one slot of our P6R PKCS 11 library. This integration supports all existing Utimaco PKCS 11 vendor extensions. To use this token requires the proper setup and configuration of a network-attached HSM both on the hardware server and client machine as documented in the Utimaco product literature. Also the proper configuration of both the Utimaco and P6R’s PKCS 11 libraries is required, which is described in detail in the SKC product documentation.

Entrust (formerly nCipher)

The Entrust nShield Connect HSM can be configured to look like another token. We map one slot of an Entrust HSM into one slot of our P6R PKCS 11 library. This integration supports existing Entrust PKCS 11 vendor extensions (e.g., C_LoginBegin()). To use this token requires the proper setup and configuration of a nShield network-attached HSM both on the hardware server and client machine as documented in the Entrust product literature. The last step is the proper configuration of the P6R’s PKCS 11 library, which is described in detail in the SKC product documentation along with working examples.

The FutureX HSM Token

The FutureX HSM can be configured to look like another token. We map one slot of a FutureX HSM into one slot of our P6R PKCS 11 library. This integration supports most of the existing FutureX PKCS 11 vendor extensions (e.g., C_FX_GetLogFile()). To use this token requires the proper setup and configuration of a network-attached HSM both on the hardware server and client machine as documented in the FutureX product literature. The last step is the proper configuration of both the FutureX and P6R’s PKCS 11 libraries, which is described in detail in the SKC product documentation along with working examples.

The DocuSign HSM Token

The DocuSign HSM can be configured to look like another token. We map one slot of a DocuSign HSM into one slot of our P6R PKCS 11 library. To use this token requires the proper setup and configuration of a network-attached HSM both on the hardware server and client machine as documented in the DocuSign product literature. The last step is the proper configuration of both the DocuSign and P6R’s PKCS 11 libraries, which is described in detail in the SKC product documentation along with working examples.

YubiHSM 2.0 Token

The YubiHSM 2.0 can be configured to look like another token. We map one slot of a YubiHSM into one slot of our P6R PKCS 11 library. To use this token requires the proper setup of a YubiHSM using the software tools that come with the product. The form factor of this HSM makes for a set of interesting use cases (e.g., encrypting the keys used to protect a local P6R keystore).

AWS CloudHSM

The AWS CloudHSM can be configured to look like another token. We map one slot of a CloudHSM into one slot of our P6R PKCS 11 library. To use this token requires the proper setup of a CloudHSM using the software tools that AWS provides. Additionally, the P6R’s PKCS#11 library has to run on an AWS CloudHSM EC2 client instance.
P6R’s KSG product, which uses this PKCS#11 library, is listed under AWS CloudHSM Integrations.

Marvell LiquidSecurity HSM

The Marvell HSM can be configured to look like another token. We map one slot of a Marvell HSM into one slot of our P6R PKCS 11 library. To use this token requires the proper setup of a Marvell HSM using the software tools that Marvell provides. The Marvell HSM version that we tested with had slot identifiers starting at 1.

Slot & Token definition

P6R’s Provider allows any number of slots to be defined and in each slot any type of token can be configured. For example, it is possible to have a PKCS 11 installation that points to several different KMIP servers and several different software token instances each separate from the others. All slots and tokens are defined via a configuration file. This configuration file allows the definition of any P6R or customer specific behavior since the PKCS 11 interface allows for vendor extensions. All keys and certificates required to communicate with a KMIP server or to encrypt/sign a Keystore’s contents are themselves securely stored in a PKCS 11 wide Keystore once the library is initialized.

Oracle TDE Integration

P6R’s PKCS 11 Provider can be installed to work as an HSM with Oracle TDE. (See Section 8.2.6 Using Hardware Security Modules [HSM] with TDE.) Depending on how our PKCS 11 library is configured it can use anyone of the several supported token types: a KMIP Server, Utimaco HSM, Thales nShield HSM, or other market available HSM. In addition, via the supported plugin interface a customer could write their own token types and have it work with Oracle TDE (just as long as the required ciphers are supported by that token). Now a customer no longer needs a PKCS 11 library from each vendor but instead can simplify their development efforts with just one.

PrimeKey’s SignServer Integration

Both the KMIP and Micro Focus Atalla HSM tokens can be configured to work with PrimeKey’s SignServer. For a KMIP token all keys can be created and stored in the KMIP server and all encryption can be performed on a KMIP server. This integration requires a KMIP server with KMIP protocol version 1.3 and greater with streaming capability supported.

PDFlib Integration

The Micro Focus Atalla HSM token can be configured to work with the PDFlib PLOP DS. This integration supports document signing.

Java Security Provider

We have been improving our integration with Java. At first we worked on integration with Keytool and Jarsigner, now our PKCS#11 library, with the KMIP token, can be used by plain old Java. With straightforward configuration the following examples of Java call our PKCS#11 library and our KMIP token. The result is that a Java programmer can use KMIP without having to learn anything about KMIP. No KMIP company specific APIs to learn. Its even possible that existing Java programs can be converted (with the occasional tweak) to use KMIP this way.
Code example 1:

KeyGenerator keyGen = KeyGenerator.getInstance("AES", "SunPKCS11-P6RPKCS11");
keyGen.init(128);
Key key = keyGen.generateKey();

// replace an older key
if (ks.containsAlias("symmetric_aes_128_key")) ks.deleteEntry("symmetric_aes_128_key");
ks.setKeyEntry("symmetric_aes_128_key", key, null, null);

Don’t see any KMIP calls here right? The magic is in the specification of the provider:
“SunPKCS11-P6RPKCS11″. The result is that the above code calls the KMIP server to generate the AES key. Then that key can be found later by calls to the keystore.

Code example 2:

// the "12345678" is the keystore's password (i.e., the PKCS#11 token's PIN)
KeyStore ks = KeyStore.getInstance("PKCS11", "SunPKCS11-P6RPKCS11");
ks.load(null, "12345678".toCharArray());
Key secretKey = ks.getKey("symmetric_aes_128_key", null);

The three lines above actually do a KMIP Locate call for a key with a custom KMIP attribute set to “symmetric_aes_128_key”. In Java, “symmetric_aes_128_key” is referred to as the
alias. (Actually the code above first makes PKCS#11 C_FindObjects() calls which our KMIP token maps to KMIP Locate. Still all that is done for the Java programmer and totally hidden from them.)

Code example 3:

private static byte[] encryptData(Key secretKey, byte[] iv, String handling, byte[] clearText) { 
  byte[] cipherText = null;
  try {
      // with a security provider do the encrypt on the remote server
      Cipher encryptCipher = Cipher.getInstance(handling, "SunPKCS11-P6RPKCS11");
      IvParameterSpec IV = new IvParameterSpec(iv);
      encryptCipher.init(Cipher.ENCRYPT_MODE, secretKey, IV);
      cipherText = encryptCipher.doFinal(clearText);
   } catch (Exception e) {
       e.printStackTrace();
   }
   return cipherText;
}

Again see any KMIP calls here? The parameter “secretKey” was created in example 1 above. This code example shows that the encryption will be done on the KMIP server. We have also tested streaming encryption (requiring KMIP 1.3), with the call sequence encryptCipher.init(), encryptCipher.update() multiple calls of updates, and then encryptCipher.doFinal(), allowing encryption (and decryption) of large chunks of data. We have also done testing with public/private keys.

Other Applications

A customer has integrated our PKCS 11 library using the KMIP token with the Hashicorp Vault (https://www.vaultproject.io/docs/vs/hsm.html, https://www.vaultproject.io/docs/configuration/seal/pkcs11.html)

We have integrated our PKCS 11 library with our SSH server product that is described in the article: Integrating KMIP, PKCS 11, and SSH. While that article focuses on the KMIP token our SSH server implementation can use any of the tokens types defined above and any we add in the future.

P6R’s PKCS 11 library also ships with a command line tool. This executable is a PKCS 11 application in that it dynamically loads our library and calls C_GetFunctionList in order to obtain the API function pointers. A user can use this command line tool to initialize a token, set the SO or User’s PIN, list all configured slots, list information on a token, generate keys, import and export some certificates and keys, and list the contents of a token. We have been using this command line tool to manage our KMIP, Software, and HPE NSP tokens.

Vendor Extensions

P6R defines the following vendor defined attribute:

CKA_P6R_GROUP 0x80001000UL
Data Type: RFC 2279 string                                       
MUST be specified when object is created with C_CreateObject.
MUST be specified when object is created with C_GenerateKey or C_GenerateKeyPair.

The purpose of this extension is to provide basic support for KMIP groups. CKA_P6R_GROUP maps into the KMIP “Object Group” attribute. Without the CKA_P6R_GROUP attribute defined the “default” KMIP group is used. P6R’s Keystore has the concept of namespaces. These are similar to groups in that they provide collections of objects. When CKA_P6R_GROUP is used for the Software Token its value is mapped into the Keystore’s namespace parameter. Without the CKA_P6R_GROUP attribute defined the Software Token uses “PKCS11″ namespace by default.

References

  1. PKCS 11 OASIS standard
  2. KMIP OASIS standard
  3. P6R’s Secure KMIP Client SDK
  4. Key Management with a Powerful Keystore

Binary Compatible C++ Interfaces (Part 1)

By Jim Susoy - July 20, 2014 @ 2:58 pm

c++-175x117

Introduction

This is the first part of a multi-part series on the challenges and techniques for creating Binary Compatible C++ Interfaces (BCCI). In researching this topic, I often found the issues enumerated without (or with very little) explanation as to why something should be avoided. As a result I have tried to include the “why” along with the “what” in this series of posts.

This first post will go through the causes of incompatibilities and the reasons why. The second post will summarize these into a set of rules, and discuss various ways to prevent or work around the incompatibilities. The third installment will cover implementing binary compatible C++ interfaces using some of the techniques discussed.

One of C++’s greatest short comings (at least with regards to interoperability) is the lack of an Application Binary Interface (ABI) as part of the standard. C++ is a language specification after all, and many would argue that is out of the scope of the standard to define specific implementations. The result is that binaries produced with one compiler, are not necessarily compatible with those produced by another compiler (or even by different versions of the same compiler!). This simple fact greatly hampers our ability as developers to easily create C++ libraries for distribution to a broad audience. This leaves developers with only two distribution options: (1) provide source for their libraries, or (2) provide multiple binaries, one for each version of each compiler that a customer might use. The matrix for that can get out of hand quickly.

A solution to this is to attempt to export all public APIs using a mechanism that creates a stable and cross-compiler compatible binary interface. Doing this does come with compromises, however you will have to decide if they are worth it or not for your specific situation. Continue Reading »

p6COM Reference Counting: A Primer

By Jim Susoy - April 27, 2014 @ 8:49 pm

Introduction

Reference counting generally comes in two basic flavors: intrusive and non-intrusive. Non-intrusive reference counting basically means that the location of the variable which stores the reference value is outside of the “thing” being reference counted. COM interfaces make use of intrusive reference counting, meaning the underlying object maintains the reference count value itself internally. The purpose of having a reference count on a COM interface is to ensure that the lifetime of the underlying object includes the lifetimes of all the references to it.  P6COM follows the standard COM reference counting model, so if you are already familiar with COM reference counting, this should all be review. There are also many good references elsewhere on this topic (including section 3.3.2 of the official COM reference), this post is meant as a quick guide to COM reference counting rules, not an exhaustive treatise.

A Word On Smart Pointers

Most implementations of COM include smartptr’s to manage reference counting, and p6COM is no different in this regard. I strongly encourage you to use p6ComPtr<> to manage your interface pointers (or whichever smartptr your COM implementation provides). COM smart pointers reduce/remove interface leaks and reduce the amount of code that you need to write. They have huge benefits, please use them. See A Smart Pointer for p6COM for a small tutorial. That being said, you should still have a clear understanding of the rules involved.

The Rules

To be successful, it’s very important to understand exactly when to call addref() and release().  The following rules define a policy which must be consistently applied:

Rule 1 – Always call addref() on a new copy of an interface pointer and release() when it is no longer needed, except as the following rules specifiy.

In general, whenever you create or make a copy of an interface pointer you must call addref() on the pointer before you use it, and release() on the pointer when you no longer need it.

Rule 2 – Always addref() before returning an interface pointer to the caller.

You must ensure that when returning an interface pointer (directly or through an out parameter) it has a an additional reference count applied before returning. If the callee synthesizes the pointer, it must call addref():

P6ERR CSomeClass::createInstance(ISomeIface **ppIface)
{
   CSomeClass  *pSomeClass = NULL;

   if(!ppIface) return eInvalidArg;

   pSomeClass = new CSomeClass;
   (*ppIface) = static_cast<ISomeIface*>(pSomeClass);
   (*ppIface)->addref();      // addref() before returning

   return err;
}

If the callee makes a copy of an internal interface pointer, then addref() must be called.

P6ERR CSomeClass::createInstance(ISomeIface **ppIface)
{
   if(!ppIface) return eInvalidArg;

   (*ppIface) = m_pSomeIface; // An interface pointer stored internally in our object
   (*ppIface)->addref();      // addref() before returning
   return eOk;
}

It important to note that it is the callers (the one receiving the new interface pointer) responsibility to release() the interface when it is done using it. This is the thing that smart pointers are great at managing for you. No matter how diligent you try to be you will forget to do this at some point causing an interface leak. Smart pointers can ensure that this never happens.

Rule 2a – Exception: callee uses another method to create the interface pointer.

If the callee called another method which created the pointer, then it will have called addref() and no additional reference is needed.

P6ERR CSomeClass::createInstance(ISomeIface **ppIface)
{
   return someFactory(ppIface); // someFactory() will addref() before returning. 
                                // We just pass it up to the caller. Calling addref()
                                // again here would cause an interface leak.
}

As you can see it does not matter where the interface pointer came from, if you return it directly or through and out parameter, addref() must be called first.

Rule 3 – Call addref() when making a local copy of an interface pointer stored in a global variable.

A much better solution to this is not to use global variables. In a single threaded environment, called methods could release the global thereby invalidating the interface pointer in the local copy. You must call addref() before making any other calls. In a multi-threaded environment (assuming the interface itself if thread-safe), you must obtain the local copy and call addref() under a lock to ensure that it remains valid long enough to grab the reference. Once addref() has been called, the lock may be released and the interface used. You must call release on the local copy when you are done.

Rule 4 – addref() and release() need not be called on in parameters

The callee knows that by definition the interface pointer passed to it as an “in” parameter has a greater lifetime than itself. Therefore, the callee should not call addref() or release() on any “in” parameter.

P6ERR CSomeClass::someMethod(ISomeIface *pIface)
{
   // no addref()
   pIface->someOtherMethod();
   // No release()
   return eOk;
}

Rule 4a – Exception: callee stores interface pointer for later use.

An exception to this is if the callee makes a copy if the interface pointer for use at a later time (storing the copy internally or globally), addref() must called on the copy (and release once it is no longer needed).

P6ERR CSomeClass::someMethod(ISomeIface *pIface)
{
   m_pSomeIface = pIface;   // Save interface pointer for later use
   m_pSomeIface->addref();  // Make sure it sticks around till we need it
                            // We are now responsible for calling release()
                            // on m_pSomeIface when it is no longer needed.

   pIface->someOtherMethod();
   return eOk;
}

Rule 5 – addref() in-out parameters on the way in and out

This is somewhat of a special case and I urge you to not use in-out parameters of any type because they complicate things which leads to defects. When an interface pointer is passed via an “in-out” parameter, the caller must addref() the interface pointer on the way in (if it expects it to still be valid after the call) because the callee will need to release() it before storing the out-value on top of it. The callee then treats the out parameter as in Rule 2 above. It’s important to understand that the callee must always release() the incoming interface pointer, even if it is not overwritten with a new/different interface.

P6ERR CSomeClass::amethod(ISomeIface **ppInOutIface)
{   
   CSomeClass *pClass = NULL;

   (*ppInOutIface)->someMethod();  // Make use of the incoming interface
   (*ppInOutIface)->release();     // Release the incoming interface 
   (*ppInOutIface) = NULL;         // Good form to prevent anything from dangling

   if(NULL != (pClass = new CSomeClass)) {
      (*ppInOutIface) = static_cast<ISomeIface*>(pClass);
      (*ppInOutIface)->addref();
   }
   return eOk;
}

Here’s another example which calls another factory class to create the outbound interface and so does not have to addref() the interface pointer before returning.

P6ERR CSomeClass::aMethod(ISomeIface **ppInOutIface)
{
   (*ppInOutIface)->someMethod();  // Make use of the incoming interface
   (*ppInOutIface)->release();     // Release the incoming interface 
   (*ppInOutIface) = NULL;         // Good form to prevent anything from dangling

   // CSomeClass::createInstance() is a theoretical factory method 
   // which creates and returns an instance of ISomeIface. Following
   // Rule 2 it calls addref() on the interface pointer before 
   // returning it. Therefore we don't need to here and we pass it
   / back to the caller.
   return CSomeClass::createInstance(ppInOutIface); 
}

This should cover the majority of situations that you come across and the official documentation (and the plethora of books on COM) should handle the rest.

We believe in standards

By Mark Joseph - April 2, 2014 @ 11:03 am

This document was updated on 27 April 2015.


We believe that standards are important and whenever possible we build our products to them. Below is a list of the standards that we have incorporated into P6R products.

ASN.1

JSON

Key packaging & storage

KMIP

PKCS 11

LDAP

Regular Expressions

SNMP

SSH Server & Client

XML

Miscellaneous

Join us at RSA 2014

By Jim Susoy - February 15, 2014 @ 2:03 pm

We’ll be heading out soon to San Francisco’s Moscone Center  for RSA 2014 to meet up with clients, partners and friends. You can find us in the the OASIS booth #1909.

We’ll be showcasing our newest product, the SKC Secure KMIP Client SDK and promoting the OASIS KMIP protocol in general for interoperable key management. As part of our commitment to interoperabilty, we participated in the OASIS KMIP Interop testing that took place in January. During the interop, we tested our client SDK against KMIP servers from Cryptsoft, Dell, HP, IBM, SafeNet, Thales and Vormetric. In October of last year, we entered into a partnership with QuintessenceLabs to ensure interoperability with their KMIP servers, and we plan to continue to pursue interoperability testing with all KMIP vendors.

We are looking forward to seeing you there.

P6R’s Secure Shell Public Key Subsystem (RFC7076)

By Mark Joseph - November 23, 2013 @ 9:04 am

RFC7076 describes a new feature that we have built into our SSH server along with RFC4819.

Abstract of the RFC7076


The Secure Shell (SSH) Public Key Subsystem protocol defines a key distribution protocol that is limited to provisioning an SSH server with a user’s public keys. This document describes a new protocol that builds on the protocol defined in RFC 4819 to allow the provisioning of keys and certificates to a server using the SSH transport.

The new protocol allows the calling client to organize keys and certificates in different namespaces on a server. These namespaces can be used by the server to allow a client to configure any application running on the server (e.g., SSH, Key Management Interoperability Protocol (KMIP), Simple Network Management Protocol (SNMP)).

The new protocol provides a server-independent mechanism for clients to add public keys, remove public keys, add certificates, remove certificates, and list the current set of keys and certificates known by the server by namespace (e.g., list all public keys in the SSH namespace).

Rights to manage keys and certificates in a particular namespace are specific and limited to the authorized user and are defined as part of the server’s implementation. The described protocol is backward compatible to version 2 defined by RFC 4819.

Our implementation of RFC7076


With our implementation of RFC7076 a customer using our SSH server can provision the keys and certificates of the SSH server itself or any other application running on the same machine. As defined in RFC4819 a SSH user can only get access to the keys (and now certificates) that exist in their account. All uploaded keys and certificates using this protocol are stored in P6R’s shared keystore which any application can access given the proper access rights.

Detailed differences between KMIP 1.0 and 1.1

By Mark Joseph - February 15, 2012 @ 9:17 am

This document was updated on 23 August 2014.

As part of the process of modifying our KMIP 1.0 protocol implementation to support the new KMIP 1.1 specification we compared the two specifications and listed all of differences in the following document.   Once we had this information we updated our KMIP 1.0 implementation to take the new KMIP 1.1 changes into account.  Note, that all section numbers below are from the KMIP 1.1 draft unless otherwise stated.

P6R now ships a KMIP Client SDK that is a full implementation of KMIP 1.0, 1.1, and 1.2 protocol versions. Detailed information on that product can be found at https://www.p6r.com/software/skc.html

1. Section 2.1.2 Credential – A new Credential Value structure is defined for Device Credentials.  KMIP 1.0 only had Username and Password credentials.

2. Section 2.1.5 Key Wrapping Data – the new “Encoding Option” enumeration field is added to the Key Wrapping Data Object Structure.

3. Section 2.1.6 Key Wrapping Specification – the new “Encoding Option” enumeration field is added to the Key Wrapping Specification Object Structure.

4. Section 2.1.9 Extension Information defining the Extension Information Structure is new to KMIP 1.1.

5. Section 3.9 Certificate Length Attribute is new.

6. Sections 3.10 X.509 Certificate Identifier, 3.11 X.509 Certificate Subject, and 3.12 X.509 Certficate Issuer are all new.

7. Sections 3.13 Certificate Identifier (was Section 3.9 in KMIP 1.0), 3.14 Certificate Subject (was Section 3.10), and 3.15 Certificate Issuer (was Section 3.11) are all deprecated in KMIP 1.1.

8. Section 3.16 Digital Signature Algorithm is new.

9. Section 3.17 Digest (was Section 3.12 in KMIP 1.0) – the new “Key Format Type” enumeration field is added to the Digest Attribute Structure.

10. Section 3.34 Fresh Attribute is new.

11. Section 4.5 Re-key Key Pair request is new.  Also Re-key Key Pair is added to Section 3.18.2.1 Default Operation Policy for Secret Objects.

12. Section 4.9 Locate (was Section 4.8 in KMIP 1.0) – the new “Object Group Member” enumeration field is added to the Locate Request Payload. Section 4.10 Check (was Section 4.9 in KMIP 1.0) – in the response payload the Unique Identifier field is not always

13. Section 4.25 Query (was Section 4.24) – the new “Extension Information” structure is added to the Query Response Payload.

14. Section 4.26 Discover Versions request is new.

15. Section 9.1.3.1 Tags has the following deprecated tags – Certificate Identifier, Certificate Issuer, Certificate Issuer Alternative Name, Certificate Issuer Distinguished Name, Certificate Subject, Certificate Subject Alternative Name, Certificate Subject Distinguished Name, Issuer, Serial Number.

16. Section 9.1.3.1 Tags has the following new tags added – from Device Identifier (0x4200A2) to X.509 Certificate Subject (0x4200B7).  Also the “(Reserved)” tag range has been moved to start at 0x4200B8.

17. Section 9.1.3.2.7 Digital Signature Algorithm Enumeration is new.

18. Section 9.1.3.2.32 Encoding Option Enumeration is new.

19. Section 9.1.3.2.33 Object Group Member Enumeration is new.

20. Section 11.4 Register, the “Encoding Option” error definition is added.

21. Section 11.6 Re-key Key Pair (Error Handling) is new.

22. Section 11.12 Get has new items added to the error handling table.

 

 

 

P6R KMIP Toolkit Introduction

By Mark Joseph - January 30, 2012 @ 9:00 am

This document was updated on 22 Feb 2014.

See the related product page SKC.

P6R has taken a unique approach in its KMIP toolkit design by supporting the translation of a KMIP binary message into a standard DOM tree.  This approach builds on existing P6R technology that supports parsing JSON into DOM trees.  The result is a powerful new tool that can be used for KMIP 1.0, 1.1, 1.2, and any future version of KMIP.

Our toolkit provides a layered set of APIs and applications so that a developer can select at what level or levels of abstraction he wishes to manipulate KMIP messages.

1. LAYERS

Using figure 1 above as a guide we will describe each layer of the toolkit design.

Layer 1 (the lowest layer), contains the KMIP message parser and encoder objects.   All KMIP operations and key encodings are supported.   At this level the developer is working with binary messages.  However, this layer does not include encryption.   As a separate component P6R’s encryption layer is available for use with keys, certificates and SSL.
Also at this layer is a higher level KMIP API.  This higher level API supports simple operations (e.g.,Get one managed object, Locate managed object(s), Locate and Check managed object(s)).

Layer 2, is the DOM tree object.  Our DOM tree contains a plugin architecture that was previously used to support XML and JSON parsers (see XSLT and XPath for JSON).  We have extended this with a 3rd plugin that takes a KMIP binary message as input and calls the objects from layer 1 to populate a DOM tree.   Since a KMIP message is essentially a tree of nested structures this translation is straight forward.  Once the KMIP message is represented by a DOM tree a wealth of P6R technologies’ are available for use.   Note, that the DOM object by itself supports the output of its contents into XML, JSON, JsonML and a KMIP binary message.  In addition, our DOM tree  has been extended to directly support binary nodes such as would be necessary for keys.

Layer 3, XPath 2.0 and XSLT 2.0, as we have done with JSON we have now done with KMIP.  Any part of the KMIP message can be searched for and extracted using the features in the XPath 2.0 language.  Also XSLT 2.0 supports transformation such as taking out just part of a KMIP message to create a new message or translating the entire message into yet another format such as SOAP.  XPath is meant to be extensible allowing a developer to easily add their own XPath functions specific to KMIP (e.g., testing for a message reply or a specific batch item).   Thus via XPath and XSLT our toolkit can be customized by any user.

Also at Layer 3 is P6R’s Rule Engine.  The Rule Engine uses the DOM object to represent its input of “stated facts”.  The Rule Engine uses XPath as part of its rule language .   Thus, for example, a Rule Set could be created to implement a KMIP policy or a validation of a message’s contents.  In addition, several Rule sets can be defined with a different  one loaded depending on some protocol or system state.

Our KMIP toolkit includes several supporting components which include P6R’s cryptographic objects, a Keystore to save protected keys in a client or in a server, and a database object that can be used to store object attributes and configuration information.   The P6R database object supports both SQLite and Postgres databases.

2. BENEFITS

There are many benefits to our approach and our software, here are just a few:

1) As with all P6R software, this toolkit supports multiple platforms: Linux, Solaris, and Windows.  It also provides several language bindings such as Python, Perl, and PHP.   All P6R software is written in C++.

2) Future versions of KMIP may support XML and JSON formats.  Our toolkit already supports this by using existing P6R technology with KMIP specific extensions.

3) Our layered approach allows a developer to use one or more layers of abstraction to process / generate KMIP messages.

4) Add in the rest of the P6R Platform and you are more than half way to a KMIP server (e.g., SNMP support is included and easily extended).  The toolkit by itself is intended for client development.

3. KMIP PROTOCOL CONFORMANCE

P6R’s KMIP client follows the standards defined in the following documents.

1) OASIS, “Key Management Interoperabilty Protocol Specification 1.0″, OASIS Standard, 15 June 2010.

2) OASIS, “Key Management Interoperabilty Protocol Specification 1.1″, OASIS Standard, 24 January 2013.

3) OASIS, “Key Management Interoperabilty Protocol Specification 1.2″, Working Draft 08, 21 August 2013.

4) OASIS, “Key Management Interoperability Protocol Test Cases Version 1.1″, Working Draft 10, 27 April 2012.

5) OASIS, “Key Management Interoperability Protocol Test Cases Version 1.2″, Working Draft 02, 06 August 2013.

6) OASIS, “KMIP Additional Message Encodings Version 1.0″, Working Draft 03, 10 August 2013.

7) OASIS, “KMIP Asymmetric Key Lifecycle Profile Version 1.0″, Working Draft 03, 10 August 2013.

8) OASIS, “KMIP Cryptographic Services Profile Version 1.0″, Working Draft 05, 10 August 2013.

9) OASIS, “KMIP Symmetric Key Foundry for FIPS 140-2 Profile Version 1.0″, Working Draft 03, 10 August 2013.

10) OASIS, “KMIP Symmetric Key Lifecycle Profile Version 1.0″, Working Draft 03, 10 August 2013.

11) OASIS, “KMIP Opaque Managed Object Store Profile Version 1.0″, Working Draft 03, 10 August 2013.

12) OASIS, “KMIP Tape Library Profile Version 1.0″, Working Draft 04a, 24 October 2013.

13) OASIS, “Key Management Interoperability Protocol Storage Array with Self-Encrypting Drives Profile Version 1.0″, Working Draft 04a, 24 October 2013.

KMIP 1.0 Operations — Client provides both synchronous and asynchronous versions of the following operations:

Create, Create Key Pair, Register, Re-key, Derive Key, Certify, Re-certify, Locate, Check, Get, Get Attributes, Get Attribute List, Add Attribute, Modify Attribute, Delete Attribute, Obtain Lease, Get Usage Allocation, Activate, Revoke, Destroy, Archive, Recover, Validate, Query (synch only), Cancel, Poll

KMIP 1.1 Operations — Client provides both synchronous and asynchronous versions of the following operations:

Create, Create Key Pair, Register, Re-key, Derive Key, Certify, Re-certify, Locate, Check, Get, Get Attributes, Get Attribute List, Add Attribute, Modify Attribute, Delete Attribute, Obtain Lease, Get Usage Allocation, Activate, Revoke, Destroy, Archive, Recover, Validate, Query (synch only), Cancel, Poll, Re-key Key Pair, Discover Versions (synch only)

KMIP 1.2 Operations — Client provides both synchronous and asynchronous versions of the following operations:

Create, Create Key Pair, Register, Re-key, Derive Key, Certify, Re-certify, Locate, Check, Get, Get Attributes, Get Attribute List, Add Attribute, Modify Attribute, Delete Attribute, Obtain Lease, Get Usage Allocation, Activate, Revoke, Destroy, Archive, Recover, Validate, Query (synch only), Cancel, Poll, Re-key Key Pair, Discover Versions (synch only), Encrypt, Decrypt, Sign, Signature Verify, MAC, MAC Verify, RNG Retrieve, RNG Seed, Hash, Create Split Key, Join Split Key

We claim conformance to the following standard defined test cases using Tag Type Length Value (TTLV), XML, and JSON message encodings for all tests:

KMIP Version 1.0 Test Cases Supported
TC-311-10	Create / Destroy
TC-312-10	Register / Create / Get attributes / Destroy
TC-313-10	Create / Locate / Get / Destroy
TC-314-10	Dual Client Test Case, ID Placeholder-linked Locate & Get Batch
TC-315-10	Register / Destroy Secret Data
TC-32-10	Asynchronous Locate
TC-41-10	Revoke Scenario
TC-51-10	Get Usage Allocation Scenario
TC-61-10	Import of a Third-party Key
TC-71-10	Unrecognized Message Extension with Criticality Indicator False
TC-72-10	Unrecognized Message Extension with Criticality Indicator True
TC-81-10	Create a Key Pair
TC-82-10	Register Both Halves of a Key Pair
TC-91-10	Create a Key, Re-key
TC-92-10	Existing Key Expired, Re-key with Same Life-cycle
TC-93-10	Existing Key Compromised, Re-key with Same Life-cycle
TC-94-10	Create Key, Re-key with New Life-cycle
TC-95-10	Obtain Lease for Expired Key
TC-101-10	Create a Key, Archive and Recover it
TC-111-10	Credential, Operation Policy, Destroy Date
TC-121-10	Query, Maximum Response Size
TC-131-10	Register an Asymmetric Key Pair in PKCS1 Format
TC-132-10	Register an Asymmetric Key Pair and a Corresponding X509 Certificate
TC-134-10	Register Key Pair, Certify and Re-certify Public Key

Symmetric Key Lifecycle Profile SKLC-M-1-10 Create, GetAttributes, Destroy SKLC-M-2-10 Create, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy SKLC-M-3-10 Create, GetAttributes, Activate, GetAttributes, ModifyAttribute, Revoke, GetAttributes, Destroy SKLC-O-1-10 Create, GetAttributes, Destroy, GetAttributes

Symmetric Key Foundry for FIPS 140-2 Profile SKFF-M-1-10 Create, Destroy AES-128 SKFF-M-2-10 Create, Destroy AES-192 SKFF-M-3-10 Create, Destroy AES-256 SKFF-M-4-10 Create, Destroy DES3-168 SKFF-M-5-10 Create, Locate, Get, Destroy, Locate AES-128 SKFF-M-6-10 Create, Locate, Get, Destroy, Locate AES-192 SKFF-M-7-10 Create, Locate, Get, Destroy, Locate AES-256 SKFF-M-8-10 Create, Locate, Get, Destroy, Locate DES3-168 SKFF-M-9-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-128 SKFF-M-10-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-192 SKFF-M-11-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-256 SKFF-M-12-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-168 SKFF-O-1-10 Create, Destroy SKIPJACK-80 SKFF-O-2-10 Create, Locate, Get, Destroy, Locate SKIPJACK-80 SKFF-O-3-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy SKIPJACK-80 SKFF-O-4-10 Create, Destroy DES3-112 SKFF-O-5-10 Create, Locate, Get, Destroy, Locate DES3-112 SKFF-O-6-10 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-112

Asymmetric Key Lifecycle Profile Supported AKLC-M-1-10 CreateKeyPair, GetAttributes, GetAttributes, Destroy AKLC-M-2-10 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-M-3-10 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-O-1-10 CreateKeyPair, GetAttributes, Destroy, GetAttributes

KMIP Opaque Managed Object Store Profile OMOS-M-1-10 Register small opaque object OMOS-O-1-10 Register large (>10k) opaque object

KMIP Tape Library Profile Version 1.0 TL-M-1-10 Configuration TL-M-2-10 Write with new (created) key TL-M-3-10 Read an encrypted tape

Key Management Interoperability Protocol Storage Array with Self-Encrypting Drives Profile Version 1.0 SASED-M-1-10 Configuration SASED-M-2-10 Register the authentication key SASED-M-3-10 Retrieve Authentication Key

SEPATON Profile Version 1.0 SEPATON-1-10 Query SEPATON-2-10 Locate, Create SEPATON-3-10 Locate, Get, GetAttributes, Activate, GetAttributes

KMIP Version 1.1 Test Cases Supported TC-311-11 Create / Destroy TC-312-11 Register / Create / Get attributes / Destroy TC-313-11 Create / Locate / Get / Destroy TC-314-11 Dual Client Test Case, ID Placeholder-linked Locate & Get Batch TC-315-11 Register / Destroy Secret Data TC-32-11 Asynchronous Locate TC-41-11 Revoke Scenario TC-51-11 Get Usage Allocation Scenario TC-61-11 Import of a Third-party Key TC-71-11 Unrecognized Message Extension with Criticality Indicator False TC-72-11 Unrecognized Message Extension with Criticality Indicator True TC-81-11 Create a Key Pair TC-82-11 Register Both Halves of a Key Pair TC-91-11 Create a Key, Re-key TC-92-11 Existing Key Expired, Re-key with Same Life-cycle TC-93-11 Existing Key Compromised, Re-key with Same Life-cycle TC-94-11 Create Key, Re-key with New Life-cycle TC-95-11 Obtain Lease for Expired Key TC-101-11 Create a Key, Archive and Recover it TC-111-11 Credential, Operation Policy, Destroy Date TC-112-11 Device Credential, Operation Policy, Destroy Date TC-121-11 Query, Maximum Response Size TC-122-11 Query Vendor Extensions TC-131-11 Register an Asymmetric Key Pair in PKCS1 Format TC-132-11 Register an Asymmetric Key Pair and a Corresponding X509 Certificate TC-133-11 Create, Re-key Key Pair TC-134-11 Register Key Pair, Certify and Re-certify Public Key TC-141-11 Key Wrapping using AES Key Wrap and No Encoding TC-142-11 Key Wrapping using AES Key Wrap with Attributes TC-151-11 Locate a Fresh Object from the Default Group TC-152-11 Client-side Group Management TC-153-11 Default Object Group Member TC-161-11 Discover Versions TC-171-11 Handling of Attributes and Attribute Index Values TC-181-11 Digests of Symmetric Keys TC-182-11 Digests of RSA Private Keys

Symmetric Key Lifecycle Profile SKLC-M-1-11 Create, GetAttributes, Destroy SKLC-M-2-11 Create, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy SKLC-M-3-11 Create, GetAttributes, Activate, GetAttributes, ModifyAttribute, Revoke, GetAttributes, Destroy SKLC-O-1-11 Create, GetAttributes, Destroy, GetAttributes

Symmetric Key Foundry for FIPS 140-2 Profile SKFF-M-1-11 Create, Destroy AES-128 SKFF-M-2-11 Create, Destroy AES-192 SKFF-M-3-11 Create, Destroy AES-256 SKFF-M-4-11 Create, Destroy DES3-168 SKFF-M-5-11 Create, Locate, Get, Destroy, Locate AES-128 SKFF-M-6-11 Create, Locate, Get, Destroy, Locate AES-192 SKFF-M-7-11 Create, Locate, Get, Destroy, Locate AES-256 SKFF-M-8-11 Create, Locate, Get, Destroy, Locate DES3-168 SKFF-M-9-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-128 SKFF-M-10-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-192 SKFF-M-11-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-256 SKFF-M-12-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-168 SKFF-O-1-11 Create, Destroy SKIPJACK-80 SKFF-O-2-11 Create, Locate, Get, Destroy, Locate SKIPJACK-80 SKFF-O-3-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy SKIPJACK-80 SKFF-O-4-11 Create, Destroy DES3-112 SKFF-O-5-11 Create, Locate, Get, Destroy, Locate DES3-112 SKFF-O-6-11 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-112

Asymmetric Key Lifecycle Profile Supported AKLC-M-1-11 CreateKeyPair, GetAttributes, GetAttributes, Destroy AKLC-M-2-11 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-M-3-11 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-O-1-11 CreateKeyPair, GetAttributes, Destroy, GetAttributes

KMIP Opaque Managed Object Store Profile OMOS-M-1-11 Register small opaque object OMOS-O-1-11 Register large (>10k) opaque object

KMIP Tape Library Profile Version 1.0 TL-M-1-11 Configuration TL-M-2-11 Write with new (created) key TL-M-3-11 Read an encrypted tape

Key Management Interoperability Protocol Storage Array with Self-Encrypting Drives Profile Version 1.0 SASED-M-1-11 Configuration SASED-M-2-11 Register the authentication key SASED-M-3-11 Retrieve Authentication Key

KMIP Version 1.2 Test Cases Supported TC-311-12 Create / Destroy TC-312-12 Register / Create / Get attributes / Destroy TC-313-12 Create / Locate / Get / Destroy TC-314-12 Dual Client Test Case, ID Placeholder-linked Locate & Get Batch TC-315-12 Register / Destroy Secret Data TC-32-12 Asynchronous Locate TC-41-12 Revoke Scenario TC-51-12 Get Usage Allocation Scenario TC-61-12 Import of a Third-party Key TC-71-12 Unrecognized Message Extension with Criticality Indicator False TC-72-12 Unrecognized Message Extension with Criticality Indicator True TC-81-12 Create a Key Pair TC-82-12 Register Both Halves of a Key Pair TC-91-12 Create a Key, Re-key TC-92-12 Existing Key Expired, Re-key with Same Life-cycle TC-93-12 Existing Key Compromised, Re-key with Same Life-cycle TC-94-12 Create Key, Re-key with New Life-cycle TC-95-12 Obtain Lease for Expired Key TC-101-12 Create a Key, Archive and Recover it TC-111-12 Credential, Operation Policy, Destroy Date TC-112-12 Device Credential, Operation Policy, Destroy Date TC-121-12 Query, Maximum Response Size TC-122-12 Query Vendor Extensions TC-131-12 Register an Asymmetric Key Pair in PKCS1 Format TC-132-12 Register an Asymmetric Key Pair and a Corresponding X509 Certificate TC-133-12 Create, Re-key Key Pair TC-134-12 Register Key Pair, Certify and Re-certify Public Key TC-141-12 Key Wrapping using AES Key Wrap and No Encoding TC-142-12 Key Wrapping using AES Key Wrap with Attributes TC-151-12 Locate a Fresh Object from the Default Group TC-152-12 Client-side Group Management TC-153-12 Default Object Group Member TC-161-12 Discover Versions TC-171-12 Handling of Attributes and Attribute Index Values TC-181-12 Digests of Symmetric Keys TC-182-12 Digests of RSA Private Keys TC-PGP-1-12 Register PGP Key - RSA TC-MDO-1-12 Register MDO Key TC-MDO-2-12 Locate MDO keys by Key Value Present TC-MDO-3-12 Register MDO Key using PKCS11 URI TC-SJ-1-12 Create and Split/Join TC-SJ-2-12 Register and Split / Join TC-SJ-3-12 Join Split Keys TC-SJ-4-12 Register and Split / Join with XOR

Symmetric Key Lifecycle Profile SKLC-M-1-12 Create, GetAttributes, Destroy SKLC-M-2-12 Create, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy SKLC-M-3-12 Create, GetAttributes, Activate, GetAttributes, ModifyAttribute, Revoke, GetAttributes, Destroy SKLC-O-1-12 Create, GetAttributes, Destroy, GetAttributes

Symmetric Key Foundry for FIPS 140-2 Profile SKFF-M-1-12 Create, Destroy AES-128 SKFF-M-2-12 Create, Destroy AES-192 SKFF-M-3-12 Create, Destroy AES-256 SKFF-M-4-12 Create, Destroy DES3-168 SKFF-M-5-12 Create, Locate, Get, Destroy, Locate AES-128 SKFF-M-6-12 Create, Locate, Get, Destroy, Locate AES-192 SKFF-M-7-12 Create, Locate, Get, Destroy, Locate AES-256 SKFF-M-8-12 Create, Locate, Get, Destroy, Locate DES3-168 SKFF-M-9-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-128 SKFF-M-10-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-192 SKFF-M-11-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy AES-256 SKFF-M-12-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-168 SKFF-O-1-12 Create, Destroy SKIPJACK-80 SKFF-O-2-12 Create, Locate, Get, Destroy, Locate SKIPJACK-80 SKFF-O-3-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy SKIPJACK-80 SKFF-O-4-12 Create, Destroy DES3-112 SKFF-O-5-12 Create, Locate, Get, Destroy, Locate DES3-112 SKFF-O-6-12 Create, Get, Activate, Revoke, Locate, Add/Mod/Del Attributes, Destroy DES3-112

Asymmetric Key Lifecycle Profile Supported AKLC-M-1-12 CreateKeyPair, GetAttributes, GetAttributes, Destroy AKLC-M-2-12 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-M-3-12 CreateKeyPair, GetAttributes, Activate, GetAttributes, Destroy, Revoke, GetAttributes, Destroy AKLC-O-1-12 CreateKeyPair, GetAttributes, Destroy, GetAttributes

KMIP Opaque Managed Object Store Profile OMOS-M-1-12 Register small opaque object OMOS-O-1-12 Register large (>10k) opaque object

KMIP Tape Library Profile Version 1.0 TL-M-1-12 TL-M-1-12 Configuration TL-M-2-12 TL-M-2-12 Write with new (created) key TL-M-3-12 TL-M-3-12 Read an encrypted tape

Key Management Interoperability Protocol Storage Array with Self-Encrypting Drives Profile Version 1.0 SASED-M-1-12 Configuration SASED-M-2-12 Register the authentication key SASED-M-3-12 Retrieve Authentication Key

KMIP Cryptographic Services Profile (KMIP 1.2) Supported CS-BC-M-1-12 Encrypt with New Symmetric Key CS-BC-M-2-12 Decrypt with New Symmetric Key CS-BC-M-3-12 Encrypt and Decrypt with New Symmetric Key CS-BC-M-4-12 Encrypt with Known Symmetric Key CS-BC-M-5-12 Decrypt with Known Symmetric Key CS-BC-M-6-12 Encrypt and Decrypt with Known Symmetric Key CS-BC-M-7-12 Encrypt with Known Symmetric Key with Usage Limits CS-BC-M-8-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding CS-BC-M-9-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding CS-BC-M-10-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding and CBC CS-BC-M-11-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding and CBC and IV CS-BC-M-12-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding and CBC and IV CS-BC-M-13-12 Encrypt and Decrypt with Known Symmetric Key and PKCS5 Padding and CBC and Random IV CS-BC-M-14-12 Encrypt and Decrypt with Known Symmetric Key Date Checks CS-RNG-M-1-12 RNG Retrieve CS-RNG-O-1-12 Seed RNG with Server Accept CS-RNG-O-2-12 Seed RNG with Server Partial Accept CS-RNG-O-3-12 Seed RNG with Server Ignore CS-RNG-O-4-12 Seed RNG with Server Deny CS-AC-M-1-12 Sign with Known Asymmetric Key CS_AC-M-2-12 Signature Verify with Known Asymmetric Key CS-AC-M-3-12 Sign and Signature Verify with Known Asymmetric Key CS-AC-M-4-12 MAC with Known Key CS_AC-M-5-12 MAC Verify with Known Key CS-AC-M-6-12 MAC and MAC Verify with Known Key CS-AC-M-7-12 Hash CS-AC-M-8-12 Sign and Signature Verify with Known Asymmetric Key Date Checks

KMIP Additional Message Encodings Supported (for KMIP 1.0, 1.1 & 1.2)
MSGENC-HTTPS-1-10 HTTPS POST: Query, Maximum Response Size
MSGENC-XML-1-10 Message Encoding XML: Query, Maximum Response Size (In addition, we have run all above test cases in XML mode.)
MSGENC-JSON-1-10 Message Encoding JSON: Query, Maximum Response Size (In addition, we have run all above test cases in JSON mode.)

Managed Objects Supported
Certificate, Symmetric Key, Public Key, Private Key, Split Key, Template, Secret Data, Opaque Object, PGP Key

Cryptographic Algorithms
DES, 3DES, DES-X, AES (including counter mode), RSA, DSA, DH, HMAC-SHA1, HMAC-SHA224
HMAC-SHA256, HMAC-SHA384, HMAC-SHA512, HMAC-MD2, HMAC-MD4, HMAC-MD5, Blowfish, CAST5, RC2

Key Format Types
Raw, Opaque, PKCS#1, PKCS#8, X.509, Transparent Symmetric Key, Transparent DSA Private Key
Transparent DSA Public Key, Transparent RSA Private Key, Transparent RSA Public Key

Certificate Types
X.509

Support for the Suite B Profile
This profile is defined by the document:
OASIS, “KMIP Suite B Profile Version 1.0″, Working Draft 03a, 24 October 2013. P6R’s KMIP client uses the OpenSSL library for its SSL/TLS support (see http://www.openssl.org/). Our client allows the user to select the ciphers to use for SSL/TLS via the API call:

setSSLOptions( const P6WCHAR* pCiphers, P6SECURESOCKETFLAGS fSecureFlags )

where the “pCiphers” paramter is a pointer to a NULL terminated character string containing the OpenSSL cipher command (see http://www.openssl.org/docs/apps/ciphers.html). If pCiphers parameter is NULL, then the secure default will be automatically be used: “TLSv1+HIGH:!SSLv2:!aNULL:!eNULL:!3DES:@STRENGTH” which enables SSLv3 and TLSv1, disables SSLv2, disables ciphers that do not use authentication, disables 3DES, and prefers the strongest ciphers first. The only constraint, is that the specified ciphers in the setSSLOptions API call are supported by the OpenSSL library in use, whether supplied by the customer or P6R.

4. A FEW EXAMPLES

Example 1: included below are 4 files containing the same KMIP 1.0 message. The first file is a dump of its binary bytes. The remaining files are translations into XML, JSON, and JsonML.  All the translated files came from the same DOM tree.

1) kmip-binary   2)  kmip-xml   3) kmip-json   4)  kmip-jsonml

Example 2: as a second example the same binary KMIP message used in #1 above is manipulated by an XSLT template to generate a Tag-Text output (with some values dropped).  The second file is the result of running the template on the same DOM tree generated in example 1.

Template: kmip-template1

Tag-Text result: kmip-tagtext

(Note that this template is just a very simple example of what is possible with XSLT & XPath 2.0.)

Example 3: the binary message below is generated from a KMIP test server while its XML version is an output from P6R’s KMIP client.  These messages are a more complex KMIP example of a response to a KMIP Query operation.

1) binary-queryresponse   2) xml-queryresponse

5. Product Summary

The toolkit provides C++ based component libraries that currently implement the KMIP 1.0/1.1/1.2 protocols. The toolkit provides full KMIP message parsing and message generation. The toolkit provides several different layers of abstraction, each building on the previous, enabling the developer to use whichever layer or layers best suit their needs. The toolkit comes with binaries for Linux, Solaris, and Windows platforms. The toolkit supports logging of incoming and outgoing KMIP messages in XML, JSON, and JsonML to simplify development and trouble shooting.

6. Interoperability Announcements

QuintessenceLabs Announces Interoperability Partnership With P6R – Project 6 Research

Thales e-Security (Thales Alliance for Solution and Application Providers (ASAP) member)

January 2014, OASIS Interop testing with the following KMIP servers: Cryptsoft (C and Java), Dell, HP, IBM, SafeNet, Thales, and Vormetric.

P6R in the OASIS Interop booth for RSA 2014

P6R, Inc is a member of OASIS and of the KMIP Technical Committee

www.oasis-open.org